00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029 #include "i915_reg.h"
00030 #include "i915_context.h"
00031 #include "i915_winsys.h"
00032 #include "i915_batch.h"
00033 #include "i915_reg.h"
00034
00035 #include "pipe/p_context.h"
00036 #include "pipe/p_defines.h"
00037
00038 static unsigned translate_format( enum pipe_format format )
00039 {
00040 switch (format) {
00041 case PIPE_FORMAT_A8R8G8B8_UNORM:
00042 return COLOR_BUF_ARGB8888;
00043 case PIPE_FORMAT_R5G6B5_UNORM:
00044 return COLOR_BUF_RGB565;
00045 default:
00046 assert(0);
00047 return 0;
00048 }
00049 }
00050
00051 static unsigned translate_depth_format( enum pipe_format zformat )
00052 {
00053 switch (zformat) {
00054 case PIPE_FORMAT_S8Z24_UNORM:
00055 return DEPTH_FRMT_24_FIXED_8_OTHER;
00056 case PIPE_FORMAT_Z16_UNORM:
00057 return DEPTH_FRMT_16_FIXED;
00058 default:
00059 assert(0);
00060 return 0;
00061 }
00062 }
00063
00064
00068 static boolean
00069 framebuffer_size(const struct pipe_framebuffer_state *fb,
00070 uint *width, uint *height)
00071 {
00072 if (fb->cbufs[0]) {
00073 *width = fb->cbufs[0]->width;
00074 *height = fb->cbufs[0]->height;
00075 return TRUE;
00076 }
00077 else if (fb->zsbuf) {
00078 *width = fb->zsbuf->width;
00079 *height = fb->zsbuf->height;
00080 return TRUE;
00081 }
00082 else {
00083 *width = *height = 0;
00084 return FALSE;
00085 }
00086 }
00087
00088
00089
00090
00091 void
00092 i915_emit_hardware_state(struct i915_context *i915 )
00093 {
00094
00095 const unsigned dwords = ( 14 +
00096 7 +
00097 I915_MAX_DYNAMIC +
00098 8 +
00099 2 + I915_TEX_UNITS*3 +
00100 2 + I915_TEX_UNITS*3 +
00101 2 + I915_MAX_CONSTANT*4 +
00102 #if 0
00103 i915->current.program_len +
00104 #else
00105 i915->fs->program_len +
00106 #endif
00107 6
00108 ) * 3/2;
00109 const unsigned relocs = ( I915_TEX_UNITS +
00110 3
00111 ) * 3/2;
00112
00113 #if 0
00114 debug_printf("i915_emit_hardware_state: %d dwords, %d relocs\n", dwords, relocs);
00115 #endif
00116
00117 if(!BEGIN_BATCH(dwords, relocs)) {
00118 FLUSH_BATCH(NULL);
00119 assert(BEGIN_BATCH(dwords, relocs));
00120 }
00121
00122
00123 if (i915->hardware_dirty & I915_HW_INVARIENT)
00124 {
00125 OUT_BATCH(_3DSTATE_AA_CMD |
00126 AA_LINE_ECAAR_WIDTH_ENABLE |
00127 AA_LINE_ECAAR_WIDTH_1_0 |
00128 AA_LINE_REGION_WIDTH_ENABLE | AA_LINE_REGION_WIDTH_1_0);
00129
00130 OUT_BATCH(_3DSTATE_DFLT_DIFFUSE_CMD);
00131 OUT_BATCH(0);
00132
00133 OUT_BATCH(_3DSTATE_DFLT_SPEC_CMD);
00134 OUT_BATCH(0);
00135
00136 OUT_BATCH(_3DSTATE_DFLT_Z_CMD);
00137 OUT_BATCH(0);
00138
00139 OUT_BATCH(_3DSTATE_COORD_SET_BINDINGS |
00140 CSB_TCB(0, 0) |
00141 CSB_TCB(1, 1) |
00142 CSB_TCB(2, 2) |
00143 CSB_TCB(3, 3) |
00144 CSB_TCB(4, 4) |
00145 CSB_TCB(5, 5) |
00146 CSB_TCB(6, 6) |
00147 CSB_TCB(7, 7));
00148
00149 OUT_BATCH(_3DSTATE_RASTER_RULES_CMD |
00150 ENABLE_POINT_RASTER_RULE |
00151 OGL_POINT_RASTER_RULE |
00152 ENABLE_LINE_STRIP_PROVOKE_VRTX |
00153 ENABLE_TRI_FAN_PROVOKE_VRTX |
00154 LINE_STRIP_PROVOKE_VRTX(1) |
00155 TRI_FAN_PROVOKE_VRTX(2) |
00156 ENABLE_TEXKILL_3D_4D |
00157 TEXKILL_4D);
00158
00159
00160
00161 OUT_BATCH(_3DSTATE_LOAD_STATE_IMMEDIATE_1 | I1_LOAD_S(3) | (0));
00162 OUT_BATCH(0);
00163
00164 OUT_BATCH(_3DSTATE_DEPTH_SUBRECT_DISABLE);
00165
00166
00167
00168 OUT_BATCH(_3DSTATE_LOAD_INDIRECT | 0);
00169 OUT_BATCH(0);
00170 }
00171
00172
00173 if (i915->hardware_dirty & I915_HW_IMMEDIATE)
00174 {
00175 OUT_BATCH(_3DSTATE_LOAD_STATE_IMMEDIATE_1 |
00176 I1_LOAD_S(0) |
00177 I1_LOAD_S(1) |
00178 I1_LOAD_S(2) |
00179 I1_LOAD_S(4) |
00180 I1_LOAD_S(5) |
00181 I1_LOAD_S(6) |
00182 (5));
00183
00184 if(i915->vbo)
00185 OUT_RELOC(i915->vbo,
00186 I915_BUFFER_ACCESS_READ,
00187 i915->current.immediate[I915_IMMEDIATE_S0]);
00188 else
00189
00190 OUT_BATCH(0);
00191 OUT_BATCH(i915->current.immediate[I915_IMMEDIATE_S1]);
00192 OUT_BATCH(i915->current.immediate[I915_IMMEDIATE_S2]);
00193 OUT_BATCH(i915->current.immediate[I915_IMMEDIATE_S4]);
00194 OUT_BATCH(i915->current.immediate[I915_IMMEDIATE_S5]);
00195 OUT_BATCH(i915->current.immediate[I915_IMMEDIATE_S6]);
00196 }
00197
00198
00199 if (i915->hardware_dirty & I915_HW_DYNAMIC)
00200 {
00201 int i;
00202 for (i = 0; i < I915_MAX_DYNAMIC; i++) {
00203 OUT_BATCH(i915->current.dynamic[i]);
00204 }
00205 }
00206
00207
00208 if (i915->hardware_dirty & I915_HW_STATIC)
00209 {
00210 struct pipe_surface *cbuf_surface = i915->framebuffer.cbufs[0];
00211 struct pipe_surface *depth_surface = i915->framebuffer.zsbuf;
00212
00213 if (cbuf_surface) {
00214 unsigned cpitch = cbuf_surface->stride;
00215 unsigned ctile = BUF_3D_USE_FENCE;
00216 if (cbuf_surface->texture &&
00217 ((struct i915_texture*)(cbuf_surface->texture))->tiled) {
00218 ctile = BUF_3D_TILED_SURFACE;
00219 }
00220
00221 OUT_BATCH(_3DSTATE_BUF_INFO_CMD);
00222
00223 OUT_BATCH(BUF_3D_ID_COLOR_BACK |
00224 BUF_3D_PITCH(cpitch) |
00225 ctile);
00226
00227 OUT_RELOC(cbuf_surface->buffer,
00228 I915_BUFFER_ACCESS_WRITE,
00229 cbuf_surface->offset);
00230 }
00231
00232
00233
00234 if (depth_surface) {
00235 unsigned zpitch = depth_surface->stride;
00236 unsigned ztile = BUF_3D_USE_FENCE;
00237 if (depth_surface->texture &&
00238 ((struct i915_texture*)(depth_surface->texture))->tiled) {
00239 ztile = BUF_3D_TILED_SURFACE;
00240 }
00241
00242 OUT_BATCH(_3DSTATE_BUF_INFO_CMD);
00243
00244 OUT_BATCH(BUF_3D_ID_DEPTH |
00245 BUF_3D_PITCH(zpitch) |
00246 ztile);
00247
00248 OUT_RELOC(depth_surface->buffer,
00249 I915_BUFFER_ACCESS_WRITE,
00250 depth_surface->offset);
00251 }
00252
00253 {
00254 unsigned cformat, zformat = 0;
00255
00256 if (cbuf_surface)
00257 cformat = cbuf_surface->format;
00258 else
00259 cformat = PIPE_FORMAT_A8R8G8B8_UNORM;
00260 cformat = translate_format(cformat);
00261
00262 if (depth_surface)
00263 zformat = translate_depth_format( i915->framebuffer.zsbuf->format );
00264
00265 OUT_BATCH(_3DSTATE_DST_BUF_VARS_CMD);
00266 OUT_BATCH(DSTORG_HORT_BIAS(0x8) |
00267 DSTORG_VERT_BIAS(0x8) |
00268 LOD_PRECLAMP_OGL |
00269 TEX_DEFAULT_COLOR_OGL |
00270 cformat |
00271 zformat );
00272 }
00273 }
00274
00275 #if 01
00276
00277
00278 if (i915->hardware_dirty & (I915_HW_MAP | I915_HW_SAMPLER))
00279 {
00280 const uint nr = i915->current.sampler_enable_nr;
00281 if (nr) {
00282 const uint enabled = i915->current.sampler_enable_flags;
00283 uint unit;
00284 uint count = 0;
00285 OUT_BATCH(_3DSTATE_MAP_STATE | (3 * nr));
00286 OUT_BATCH(enabled);
00287 for (unit = 0; unit < I915_TEX_UNITS; unit++) {
00288 if (enabled & (1 << unit)) {
00289 struct pipe_buffer *buf =
00290 i915->texture[unit]->buffer;
00291 uint offset = 0;
00292 assert(buf);
00293
00294 count++;
00295
00296 OUT_RELOC(buf,
00297 I915_BUFFER_ACCESS_READ,
00298 offset);
00299 OUT_BATCH(i915->current.texbuffer[unit][0]);
00300 OUT_BATCH(i915->current.texbuffer[unit][1]);
00301 }
00302 }
00303 assert(count == nr);
00304 }
00305 }
00306 #endif
00307
00308 #if 01
00309
00310
00311 if (i915->hardware_dirty & I915_HW_SAMPLER)
00312 {
00313 if (i915->current.sampler_enable_nr) {
00314 int i;
00315
00316 OUT_BATCH( _3DSTATE_SAMPLER_STATE |
00317 (3 * i915->current.sampler_enable_nr) );
00318
00319 OUT_BATCH( i915->current.sampler_enable_flags );
00320
00321 for (i = 0; i < I915_TEX_UNITS; i++) {
00322 if (i915->current.sampler_enable_flags & (1<<i)) {
00323 OUT_BATCH( i915->current.sampler[i][0] );
00324 OUT_BATCH( i915->current.sampler[i][1] );
00325 OUT_BATCH( i915->current.sampler[i][2] );
00326 }
00327 }
00328 }
00329 }
00330 #endif
00331
00332
00333
00334 if (i915->hardware_dirty & I915_HW_PROGRAM)
00335 {
00336
00337
00338
00339 const uint nr = i915->fs->num_constants;
00340 if (nr) {
00341 uint i;
00342
00343 OUT_BATCH( _3DSTATE_PIXEL_SHADER_CONSTANTS | (nr * 4) );
00344 OUT_BATCH( (1 << (nr - 1)) | ((1 << (nr - 1)) - 1) );
00345
00346 for (i = 0; i < nr; i++) {
00347 const uint *c;
00348 if (i915->fs->constant_flags[i] == I915_CONSTFLAG_USER) {
00349
00350 c = (uint *) i915->current.constants[PIPE_SHADER_FRAGMENT][i];
00351 }
00352 else {
00353
00354 c = (uint *) i915->fs->constants[i];
00355 }
00356 #if 0
00357 {
00358 float *f = (float *) c;
00359 printf("Const %2d: %f %f %f %f %s\n", i, f[0], f[1], f[2], f[3],
00360 (i915->fs->constant_flags[i] == I915_CONSTFLAG_USER
00361 ? "user" : "immediate"));
00362 }
00363 #endif
00364 OUT_BATCH(*c++);
00365 OUT_BATCH(*c++);
00366 OUT_BATCH(*c++);
00367 OUT_BATCH(*c++);
00368 }
00369 }
00370 }
00371
00372
00373
00374 if (i915->hardware_dirty & I915_HW_PROGRAM)
00375 {
00376 uint i;
00377
00378 assert(i915->fs->program_len > 0);
00379 for (i = 0; i < i915->fs->program_len; i++) {
00380 OUT_BATCH(i915->fs->program[i]);
00381 }
00382 }
00383
00384
00385
00386 {
00387 uint w, h;
00388 boolean k = framebuffer_size(&i915->framebuffer, &w, &h);
00389 (void)k;
00390 assert(k);
00391
00392 OUT_BATCH(_3DSTATE_DRAW_RECT_CMD);
00393 OUT_BATCH(0);
00394 OUT_BATCH(0);
00395 OUT_BATCH(((w - 1) & 0xffff) | ((h - 1) << 16));
00396 OUT_BATCH(0);
00397 OUT_BATCH(0);
00398 }
00399
00400
00401 i915->hardware_dirty = 0;
00402 }