intel-gem: Disable spantmp sse/mmx functions when tile swizzling.
[mesa.git] / src / mesa / drivers / dri / intel / intel_span.c
1 /**************************************************************************
2 *
3 * Copyright 2003 Tungsten Graphics, Inc., Cedar Park, Texas.
4 * All Rights Reserved.
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a
7 * copy of this software and associated documentation files (the
8 * "Software"), to deal in the Software without restriction, including
9 * without limitation the rights to use, copy, modify, merge, publish,
10 * distribute, sub license, and/or sell copies of the Software, and to
11 * permit persons to whom the Software is furnished to do so, subject to
12 * the following conditions:
13 *
14 * The above copyright notice and this permission notice (including the
15 * next paragraph) shall be included in all copies or substantial portions
16 * of the Software.
17 *
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
19 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
21 * IN NO EVENT SHALL TUNGSTEN GRAPHICS AND/OR ITS SUPPLIERS BE LIABLE FOR
22 * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
23 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
24 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
25 *
26 **************************************************************************/
27
28 #include "glheader.h"
29 #include "macros.h"
30 #include "mtypes.h"
31 #include "colormac.h"
32
33 #include "intel_fbo.h"
34 #include "intel_screen.h"
35 #include "intel_span.h"
36 #include "intel_regions.h"
37 #include "intel_ioctl.h"
38 #include "intel_tex.h"
39
40 #include "swrast/swrast.h"
41
42 static void
43 intel_set_span_functions(struct intel_context *intel,
44 struct gl_renderbuffer *rb);
45
46 /*
47 * Deal with tiled surfaces
48 */
49
50 #if 0
51 /* These are pre-965 tile swizzling functions -- power of two widths */
52 static uintptr_t x_tile_swizzle_pow2 (uintptr_t addr, int n)
53 {
54 uintptr_t a = addr;
55 uintptr_t base_mask = (((~0) << (n + 4)) | 0xff);
56 uintptr_t x_mask = ((~0) << 12) & ~base_mask;
57
58 a = ((a & base_mask) |
59 ((a >> (n-8)) & 0x7) |
60 ((a << 3) & x_mask));
61 _mesa_printf ("x_swizzle %08x (base %x yrow %x tile#x %x xsword %x byte %x) %08x\n",
62 addr,
63 addr >> (n + 4),
64 (addr >> (n + 1)) & 0x7,
65 (addr >> 9) & ((1 << (n-8)) - 1),
66 (addr >> 5) & 0xf,
67 (addr & 0x1f),
68 a);
69 return a;
70 }
71
72 static uintptr_t y_tile_swizzle_pow2 (uintptr_t addr, int n)
73 {
74 uintptr_t a = (uintptr_t) addr;
75 uintptr_t base_mask = (((~0) << (n + 6)) | 0xf);
76 uintptr_t x_mask = ((~0) << 9) & ~base_mask;
77
78 a = ((a & base_mask) |
79 ((a >> (n-3)) & 0x1f) |
80 ((a << 5) & x_mask));
81 _mesa_printf ("y_swizzle %08x (base %x yrow %x tile#x %x xoword %x byte %x) %08x\n",
82 addr,
83 addr >> (n + 6),
84 (addr >> (n + 1)) & 0x01f,
85 (addr >> 7) & ((1 << (n-6)) - 1),
86 (addr >> 4) & 0x7,
87 (addr & 0xf),
88 a);
89 return a;
90 }
91 #endif
92
93 static GLubyte *x_tile_swizzle(struct intel_renderbuffer *irb, struct intel_context *intel,
94 int x, int y)
95 {
96 GLubyte *buf = (GLubyte *) irb->pfMap;
97 int tile_stride;
98 int xbyte;
99 int x_tile_off, y_tile_off;
100 int x_tile_number, y_tile_number;
101 int tile_off, tile_base;
102
103 tile_stride = (irb->pfPitch * irb->region->cpp) << 3;
104
105 x += intel->drawX;
106 y += intel->drawY;
107
108 xbyte = x * irb->region->cpp;
109
110 x_tile_off = xbyte & 0x1ff;
111 y_tile_off = y & 7;
112
113 x_tile_number = xbyte >> 9;
114 y_tile_number = y >> 3;
115
116 tile_off = (y_tile_off << 9) + x_tile_off;
117
118 switch (irb->region->bit_6_swizzle) {
119 case I915_BIT_6_SWIZZLE_NONE:
120 break;
121 case I915_BIT_6_SWIZZLE_9:
122 tile_off ^= ((tile_off >> 3) & 64);
123 break;
124 case I915_BIT_6_SWIZZLE_9_10:
125 tile_off ^= ((tile_off >> 3) & 64) ^ ((tile_off >> 4) & 64);
126 break;
127 case I915_BIT_6_SWIZZLE_9_11:
128 tile_off ^= ((tile_off >> 3) & 64) ^ ((tile_off >> 5) & 64);
129 break;
130 case I915_BIT_6_SWIZZLE_9_10_11:
131 tile_off ^= ((tile_off >> 3) & 64) ^ ((tile_off >> 4) & 64) ^
132 ((tile_off >> 5) & 64);
133 break;
134 default:
135 fprintf(stderr, "Unknown tile swizzling mode %d\n",
136 irb->region->bit_6_swizzle);
137 exit(1);
138 }
139
140 tile_base = (x_tile_number << 12) + y_tile_number * tile_stride;
141
142 #if 0
143 printf("(%d,%d) -> %d + %d = %d (pitch = %d, tstride = %d)\n",
144 x, y, tile_off, tile_base,
145 tile_off + tile_base,
146 irb->pfPitch, tile_stride);
147 #endif
148
149 return buf + tile_base + tile_off;
150 }
151
152 static GLubyte *y_tile_swizzle(struct intel_renderbuffer *irb, struct intel_context *intel,
153 int x, int y)
154 {
155 GLubyte *buf = (GLubyte *) irb->pfMap;
156 int tile_stride;
157 int xbyte;
158 int x_tile_off, y_tile_off;
159 int x_tile_number, y_tile_number;
160 int tile_off, tile_base;
161
162 tile_stride = (irb->pfPitch * irb->region->cpp) << 5;
163
164 x += intel->drawX;
165 y += intel->drawY;
166
167 xbyte = x * irb->region->cpp;
168
169 x_tile_off = xbyte & 0x7f;
170 y_tile_off = y & 0x1f;
171
172 x_tile_number = xbyte >> 7;
173 y_tile_number = y >> 5;
174
175 tile_off = ((x_tile_off & ~0xf) << 5) + (y_tile_off << 4) +
176 (x_tile_off & 0xf);
177
178 switch (irb->region->bit_6_swizzle) {
179 case I915_BIT_6_SWIZZLE_NONE:
180 break;
181 case I915_BIT_6_SWIZZLE_9:
182 tile_off ^= ((tile_off >> 3) & 64);
183 break;
184 case I915_BIT_6_SWIZZLE_9_10:
185 tile_off ^= ((tile_off >> 3) & 64) ^ ((tile_off >> 4) & 64);
186 break;
187 case I915_BIT_6_SWIZZLE_9_11:
188 tile_off ^= ((tile_off >> 3) & 64) ^ ((tile_off >> 5) & 64);
189 break;
190 case I915_BIT_6_SWIZZLE_9_10_11:
191 tile_off ^= ((tile_off >> 3) & 64) ^ ((tile_off >> 4) & 64) ^
192 ((tile_off >> 5) & 64);
193 break;
194 default:
195 fprintf(stderr, "Unknown tile swizzling mode %d\n",
196 irb->region->bit_6_swizzle);
197 exit(1);
198 }
199
200 tile_base = (x_tile_number << 12) + y_tile_number * tile_stride;
201
202 return buf + tile_base + tile_off;
203 }
204
205 /*
206 break intelWriteRGBASpan_ARGB8888
207 */
208
209 #undef DBG
210 #define DBG 0
211
212 #define LOCAL_VARS \
213 struct intel_context *intel = intel_context(ctx); \
214 struct intel_renderbuffer *irb = intel_renderbuffer(rb); \
215 const GLint yScale = irb->RenderToTexture ? 1 : -1; \
216 const GLint yBias = irb->RenderToTexture ? 0 : irb->Base.Height - 1; \
217 GLubyte *buf = (GLubyte *) irb->pfMap \
218 + (intel->drawY * irb->pfPitch + intel->drawX) * irb->region->cpp;\
219 GLuint p; \
220 assert(irb->pfMap);\
221 (void) p; (void) buf;
222
223 /* XXX FBO: this is identical to the macro in spantmp2.h except we get
224 * the cliprect info from the context, not the driDrawable.
225 * Move this into spantmp2.h someday.
226 */
227 #define HW_CLIPLOOP() \
228 do { \
229 int _nc = intel->numClipRects; \
230 while ( _nc-- ) { \
231 int minx = intel->pClipRects[_nc].x1 - intel->drawX; \
232 int miny = intel->pClipRects[_nc].y1 - intel->drawY; \
233 int maxx = intel->pClipRects[_nc].x2 - intel->drawX; \
234 int maxy = intel->pClipRects[_nc].y2 - intel->drawY;
235
236 #if 0
237 }}
238 #endif
239
240 #define Y_FLIP(_y) ((_y) * yScale + yBias)
241
242 /* XXX with GEM, these need to tell the kernel */
243 #define HW_LOCK()
244
245 #define HW_UNLOCK()
246
247 /* 16 bit, RGB565 color spanline and pixel functions
248 */
249 #define SPANTMP_PIXEL_FMT GL_RGB
250 #define SPANTMP_PIXEL_TYPE GL_UNSIGNED_SHORT_5_6_5
251
252 #define TAG(x) intel##x##_RGB565
253 #define TAG2(x,y) intel##x##_RGB565##y
254 #define GET_PTR(X,Y) (buf + ((Y) * irb->pfPitch + (X)) * 2)
255 #include "spantmp2.h"
256
257 /* 32 bit, ARGB8888 color spanline and pixel functions
258 */
259 #define SPANTMP_PIXEL_FMT GL_BGRA
260 #define SPANTMP_PIXEL_TYPE GL_UNSIGNED_INT_8_8_8_8_REV
261
262 #define TAG(x) intel##x##_ARGB8888
263 #define TAG2(x,y) intel##x##_ARGB8888##y
264 #define GET_PTR(X,Y) (buf + ((Y) * irb->pfPitch + (X)) * 4)
265 #include "spantmp2.h"
266
267 /* 16 bit RGB565 color tile spanline and pixel functions
268 */
269
270 #define SPANTMP_PIXEL_FMT GL_RGB
271 #define SPANTMP_PIXEL_TYPE GL_UNSIGNED_SHORT_5_6_5
272
273 #define TAG(x) intel_XTile_##x##_RGB565
274 #define TAG2(x,y) intel_XTile_##x##_RGB565##y
275 #define GET_PTR(X,Y) x_tile_swizzle(irb, intel, X, Y)
276 #define GET_PTR_NONLINEAR 1
277 #include "spantmp2.h"
278
279 #define SPANTMP_PIXEL_FMT GL_RGB
280 #define SPANTMP_PIXEL_TYPE GL_UNSIGNED_SHORT_5_6_5
281
282 #define TAG(x) intel_YTile_##x##_RGB565
283 #define TAG2(x,y) intel_YTile_##x##_RGB565##y
284 #define GET_PTR(X,Y) y_tile_swizzle(irb, intel, X, Y)
285 #define GET_PTR_NONLINEAR 1
286 #include "spantmp2.h"
287
288 /* 32 bit ARGB888 color tile spanline and pixel functions
289 */
290
291 #define SPANTMP_PIXEL_FMT GL_BGRA
292 #define SPANTMP_PIXEL_TYPE GL_UNSIGNED_INT_8_8_8_8_REV
293
294 #define TAG(x) intel_XTile_##x##_ARGB8888
295 #define TAG2(x,y) intel_XTile_##x##_ARGB8888##y
296 #define GET_PTR(X,Y) x_tile_swizzle(irb, intel, X, Y)
297 #define GET_PTR_NONLINEAR 1
298 #include "spantmp2.h"
299
300 #define SPANTMP_PIXEL_FMT GL_BGRA
301 #define SPANTMP_PIXEL_TYPE GL_UNSIGNED_INT_8_8_8_8_REV
302
303 #define TAG(x) intel_YTile_##x##_ARGB8888
304 #define TAG2(x,y) intel_YTile_##x##_ARGB8888##y
305 #define GET_PTR(X,Y) y_tile_swizzle(irb, intel, X, Y)
306 #define GET_PTR_NONLINEAR 1
307 #include "spantmp2.h"
308
309 #define LOCAL_DEPTH_VARS \
310 struct intel_context *intel = intel_context(ctx); \
311 struct intel_renderbuffer *irb = intel_renderbuffer(rb); \
312 const GLuint pitch = irb->pfPitch/***XXX region->pitch*/; /* in pixels */ \
313 const GLint yScale = irb->RenderToTexture ? 1 : -1; \
314 const GLint yBias = irb->RenderToTexture ? 0 : irb->Base.Height - 1; \
315 char *buf = (char *) irb->pfMap/*XXX use region->map*/ + \
316 (intel->drawY * pitch + intel->drawX) * irb->region->cpp; (void) buf;
317
318
319 #define LOCAL_STENCIL_VARS LOCAL_DEPTH_VARS
320
321 /**
322 ** 16-bit depthbuffer functions.
323 **/
324 #define WRITE_DEPTH( _x, _y, d ) \
325 ((GLushort *)buf)[(_x) + (_y) * pitch] = d;
326
327 #define READ_DEPTH( d, _x, _y ) \
328 d = ((GLushort *)buf)[(_x) + (_y) * pitch];
329
330
331 #define TAG(x) intel##x##_z16
332 #include "depthtmp.h"
333
334
335 /**
336 ** 16-bit x tile depthbuffer functions.
337 **/
338 #define WRITE_DEPTH( _x, _y, d ) \
339 (*((GLushort *)x_tile_swizzle (irb, intel, _x, _y)) = d)
340
341 #define READ_DEPTH( d, _x, _y ) \
342 d = *((GLushort *)x_tile_swizzle (irb, intel, _x, _y))
343
344
345 #define TAG(x) intel_XTile_##x##_z16
346 #include "depthtmp.h"
347
348 /**
349 ** 16-bit y tile depthbuffer functions.
350 **/
351 #define WRITE_DEPTH( _x, _y, d ) \
352 (*((GLushort *)y_tile_swizzle (irb, intel, _x, _y)) = d)
353
354 #define READ_DEPTH( d, _x, _y ) \
355 (d = *((GLushort *)y_tile_swizzle (irb, intel, _x, _y)))
356
357
358 #define TAG(x) intel_YTile_##x##_z16
359 #include "depthtmp.h"
360
361
362 /**
363 ** 24/8-bit interleaved depth/stencil functions
364 ** Note: we're actually reading back combined depth+stencil values.
365 ** The wrappers in main/depthstencil.c are used to extract the depth
366 ** and stencil values.
367 **/
368 /* Change ZZZS -> SZZZ */
369 #define WRITE_DEPTH( _x, _y, d ) { \
370 GLuint tmp = ((d) >> 8) | ((d) << 24); \
371 ((GLuint *)buf)[(_x) + (_y) * pitch] = tmp; \
372 }
373
374 /* Change SZZZ -> ZZZS */
375 #define READ_DEPTH( d, _x, _y ) { \
376 GLuint tmp = ((GLuint *)buf)[(_x) + (_y) * pitch]; \
377 d = (tmp << 8) | (tmp >> 24); \
378 }
379
380 #define TAG(x) intel##x##_z24_s8
381 #include "depthtmp.h"
382
383
384 /**
385 ** 24/8-bit x-tile interleaved depth/stencil functions
386 ** Note: we're actually reading back combined depth+stencil values.
387 ** The wrappers in main/depthstencil.c are used to extract the depth
388 ** and stencil values.
389 **/
390 /* Change ZZZS -> SZZZ */
391 #define WRITE_DEPTH( _x, _y, d ) { \
392 GLuint tmp = ((d) >> 8) | ((d) << 24); \
393 *((GLuint *)x_tile_swizzle (irb, intel, _x, _y)) = tmp; \
394 }
395
396 /* Change SZZZ -> ZZZS */
397 #define READ_DEPTH( d, _x, _y ) { \
398 GLuint tmp = *((GLuint *)x_tile_swizzle (irb, intel, _x, _y)); \
399 d = (tmp << 8) | (tmp >> 24); \
400 }
401
402 #define TAG(x) intel_XTile_##x##_z24_s8
403 #include "depthtmp.h"
404
405 /**
406 ** 24/8-bit y-tile interleaved depth/stencil functions
407 ** Note: we're actually reading back combined depth+stencil values.
408 ** The wrappers in main/depthstencil.c are used to extract the depth
409 ** and stencil values.
410 **/
411 /* Change ZZZS -> SZZZ */
412 #define WRITE_DEPTH( _x, _y, d ) { \
413 GLuint tmp = ((d) >> 8) | ((d) << 24); \
414 *((GLuint *)y_tile_swizzle (irb, intel, _x, _y)) = tmp; \
415 }
416
417 /* Change SZZZ -> ZZZS */
418 #define READ_DEPTH( d, _x, _y ) { \
419 GLuint tmp = *((GLuint *)y_tile_swizzle (irb, intel, _x, _y)); \
420 d = (tmp << 8) | (tmp >> 24); \
421 }
422
423 #define TAG(x) intel_YTile_##x##_z24_s8
424 #include "depthtmp.h"
425
426
427 /**
428 ** 8-bit stencil function (XXX FBO: This is obsolete)
429 **/
430 #define WRITE_STENCIL( _x, _y, d ) { \
431 GLuint tmp = ((GLuint *)buf)[(_x) + (_y) * pitch]; \
432 tmp &= 0xffffff; \
433 tmp |= ((d) << 24); \
434 ((GLuint *) buf)[(_x) + (_y) * pitch] = tmp; \
435 }
436
437 #define READ_STENCIL( d, _x, _y ) \
438 d = ((GLuint *)buf)[(_x) + (_y) * pitch] >> 24;
439
440 #define TAG(x) intel##x##_z24_s8
441 #include "stenciltmp.h"
442
443 /**
444 ** 8-bit x-tile stencil function (XXX FBO: This is obsolete)
445 **/
446 #define WRITE_STENCIL( _x, _y, d ) { \
447 GLuint *a = (GLuint *) x_tile_swizzle (irb, intel, _x, _y); \
448 GLuint tmp = *a; \
449 tmp &= 0xffffff; \
450 tmp |= ((d) << 24); \
451 *a = tmp; \
452 }
453
454 #define READ_STENCIL( d, _x, _y ) \
455 (d = *((GLuint*) x_tile_swizzle (irb, intel, _x, _y)) >> 24)
456
457 #define TAG(x) intel_XTile_##x##_z24_s8
458 #include "stenciltmp.h"
459
460 /**
461 ** 8-bit y-tile stencil function (XXX FBO: This is obsolete)
462 **/
463 #define WRITE_STENCIL( _x, _y, d ) { \
464 GLuint *a = (GLuint *) y_tile_swizzle (irb, intel, _x, _y); \
465 GLuint tmp = *a; \
466 tmp &= 0xffffff; \
467 tmp |= ((d) << 24); \
468 *a = tmp; \
469 }
470
471 #define READ_STENCIL( d, _x, _y ) \
472 (d = *((GLuint*) y_tile_swizzle (irb, intel, _x, _y)) >> 24)
473
474 #define TAG(x) intel_YTile_##x##_z24_s8
475 #include "stenciltmp.h"
476
477
478
479 /**
480 * Map or unmap all the renderbuffers which we may need during
481 * software rendering.
482 * XXX in the future, we could probably convey extra information to
483 * reduce the number of mappings needed. I.e. if doing a glReadPixels
484 * from the depth buffer, we really only need one mapping.
485 *
486 * XXX Rewrite this function someday.
487 * We can probably just loop over all the renderbuffer attachments,
488 * map/unmap all of them, and not worry about the _ColorDrawBuffers
489 * _ColorReadBuffer, _DepthBuffer or _StencilBuffer fields.
490 */
491 static void
492 intel_map_unmap_buffers(struct intel_context *intel, GLboolean map)
493 {
494 GLcontext *ctx = &intel->ctx;
495 GLuint i, j;
496 struct intel_renderbuffer *irb;
497
498 /* color draw buffers */
499 for (j = 0; j < ctx->DrawBuffer->_NumColorDrawBuffers; j++) {
500 struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[j];
501 irb = intel_renderbuffer(rb);
502 if (irb && irb->region) {
503 intel_set_span_functions(intel, rb);
504 if (map)
505 intel_region_map(intel, irb->region);
506 else
507 intel_region_unmap(intel, irb->region);
508 irb->pfMap = irb->region->map;
509 irb->pfPitch = irb->region->pitch;
510 }
511 }
512
513 /* check for render to textures */
514 for (i = 0; i < BUFFER_COUNT; i++) {
515 struct gl_renderbuffer_attachment *att =
516 ctx->DrawBuffer->Attachment + i;
517 struct gl_texture_object *tex = att->Texture;
518 if (tex) {
519 /* render to texture */
520 ASSERT(att->Renderbuffer);
521 if (map) {
522 struct gl_texture_image *texImg;
523 texImg = tex->Image[att->CubeMapFace][att->TextureLevel];
524 intel_tex_map_images(intel, intel_texture_object(tex));
525 }
526 else {
527 intel_tex_unmap_images(intel, intel_texture_object(tex));
528 }
529 }
530 }
531
532 /* color read buffers */
533 irb = intel_renderbuffer(ctx->ReadBuffer->_ColorReadBuffer);
534 if (irb && irb->region) {
535 intel_set_span_functions(intel, ctx->ReadBuffer->_ColorReadBuffer);
536 if (map)
537 intel_region_map(intel, irb->region);
538 else
539 intel_region_unmap(intel, irb->region);
540 irb->pfMap = irb->region->map;
541 irb->pfPitch = irb->region->pitch;
542 }
543
544 /* Account for front/back color page flipping.
545 * The span routines use the pfMap and pfPitch fields which will
546 * swap the front/back region map/pitch if we're page flipped.
547 * Do this after mapping, above, so the map field is valid.
548 */
549 #if 0
550 if (map && ctx->DrawBuffer->Name == 0) {
551 struct intel_renderbuffer *irbFront
552 = intel_get_renderbuffer(ctx->DrawBuffer, BUFFER_FRONT_LEFT);
553 struct intel_renderbuffer *irbBack
554 = intel_get_renderbuffer(ctx->DrawBuffer, BUFFER_BACK_LEFT);
555 if (irbBack) {
556 /* double buffered */
557 if (intel->sarea->pf_current_page == 0) {
558 irbFront->pfMap = irbFront->region->map;
559 irbFront->pfPitch = irbFront->region->pitch;
560 irbBack->pfMap = irbBack->region->map;
561 irbBack->pfPitch = irbBack->region->pitch;
562 }
563 else {
564 irbFront->pfMap = irbBack->region->map;
565 irbFront->pfPitch = irbBack->region->pitch;
566 irbBack->pfMap = irbFront->region->map;
567 irbBack->pfPitch = irbFront->region->pitch;
568 }
569 }
570 }
571 #endif
572
573 /* depth buffer (Note wrapper!) */
574 if (ctx->DrawBuffer->_DepthBuffer) {
575 irb = intel_renderbuffer(ctx->DrawBuffer->_DepthBuffer->Wrapped);
576 if (irb && irb->region) {
577 if (map) {
578 intel_set_span_functions(intel,
579 ctx->DrawBuffer->_DepthBuffer->Wrapped);
580 intel_region_map(intel, irb->region);
581 irb->pfMap = irb->region->map;
582 irb->pfPitch = irb->region->pitch;
583 }
584 else {
585 intel_region_unmap(intel, irb->region);
586 irb->pfMap = irb->region->map;
587 irb->pfPitch = irb->region->pitch;
588 }
589 }
590 }
591
592 /* stencil buffer (Note wrapper!) */
593 if (ctx->DrawBuffer->_StencilBuffer) {
594 irb = intel_renderbuffer(ctx->DrawBuffer->_StencilBuffer->Wrapped);
595 if (irb && irb->region) {
596 if (map) {
597 intel_set_span_functions(intel,
598 ctx->DrawBuffer->_StencilBuffer->Wrapped);
599 intel_region_map(intel, irb->region);
600 irb->pfMap = irb->region->map;
601 irb->pfPitch = irb->region->pitch;
602 }
603 else {
604 intel_region_unmap(intel, irb->region);
605 irb->pfMap = irb->region->map;
606 irb->pfPitch = irb->region->pitch;
607 }
608 }
609 }
610 }
611
612
613
614 /**
615 * Prepare for softare rendering. Map current read/draw framebuffers'
616 * renderbuffes and all currently bound texture objects.
617 *
618 * Old note: Moved locking out to get reasonable span performance.
619 */
620 void
621 intelSpanRenderStart(GLcontext * ctx)
622 {
623 struct intel_context *intel = intel_context(ctx);
624 GLuint i;
625
626 intelFlush(&intel->ctx);
627 LOCK_HARDWARE(intel);
628
629 for (i = 0; i < ctx->Const.MaxTextureCoordUnits; i++) {
630 if (ctx->Texture.Unit[i]._ReallyEnabled) {
631 struct gl_texture_object *texObj = ctx->Texture.Unit[i]._Current;
632 intel_tex_map_images(intel, intel_texture_object(texObj));
633 }
634 }
635
636 intel_map_unmap_buffers(intel, GL_TRUE);
637 }
638
639 /**
640 * Called when done softare rendering. Unmap the buffers we mapped in
641 * the above function.
642 */
643 void
644 intelSpanRenderFinish(GLcontext * ctx)
645 {
646 struct intel_context *intel = intel_context(ctx);
647 GLuint i;
648
649 _swrast_flush(ctx);
650
651 for (i = 0; i < ctx->Const.MaxTextureCoordUnits; i++) {
652 if (ctx->Texture.Unit[i]._ReallyEnabled) {
653 struct gl_texture_object *texObj = ctx->Texture.Unit[i]._Current;
654 intel_tex_unmap_images(intel, intel_texture_object(texObj));
655 }
656 }
657
658 intel_map_unmap_buffers(intel, GL_FALSE);
659
660 UNLOCK_HARDWARE(intel);
661 }
662
663
664 void
665 intelInitSpanFuncs(GLcontext * ctx)
666 {
667 struct swrast_device_driver *swdd = _swrast_GetDeviceDriverReference(ctx);
668 swdd->SpanRenderStart = intelSpanRenderStart;
669 swdd->SpanRenderFinish = intelSpanRenderFinish;
670 }
671
672
673 /**
674 * Plug in appropriate span read/write functions for the given renderbuffer.
675 * These are used for the software fallbacks.
676 */
677 static void
678 intel_set_span_functions(struct intel_context *intel,
679 struct gl_renderbuffer *rb)
680 {
681 struct intel_renderbuffer *irb = (struct intel_renderbuffer *) rb;
682 uint32_t tiling;
683
684 /* If in GEM mode, we need to do the tile address swizzling ourselves,
685 * instead of the fence registers handling it.
686 */
687 if (intel->ttm)
688 tiling = irb->region->tiling;
689 else
690 tiling = I915_TILING_NONE;
691
692 if (rb->_ActualFormat == GL_RGB5) {
693 /* 565 RGB */
694 switch (tiling) {
695 case I915_TILING_NONE:
696 default:
697 intelInitPointers_RGB565(rb);
698 break;
699 case I915_TILING_X:
700 intel_XTile_InitPointers_RGB565(rb);
701 break;
702 case I915_TILING_Y:
703 intel_YTile_InitPointers_RGB565(rb);
704 break;
705 }
706 }
707 else if (rb->_ActualFormat == GL_RGBA8) {
708 /* 8888 RGBA */
709 switch (tiling) {
710 case I915_TILING_NONE:
711 default:
712 intelInitPointers_ARGB8888(rb);
713 break;
714 case I915_TILING_X:
715 intel_XTile_InitPointers_ARGB8888(rb);
716 break;
717 case I915_TILING_Y:
718 intel_YTile_InitPointers_ARGB8888(rb);
719 break;
720 }
721 }
722 else if (rb->_ActualFormat == GL_DEPTH_COMPONENT16) {
723 switch (tiling) {
724 case I915_TILING_NONE:
725 default:
726 intelInitDepthPointers_z16(rb);
727 break;
728 case I915_TILING_X:
729 intel_XTile_InitDepthPointers_z16(rb);
730 break;
731 case I915_TILING_Y:
732 intel_YTile_InitDepthPointers_z16(rb);
733 break;
734 }
735 }
736 else if (rb->_ActualFormat == GL_DEPTH_COMPONENT24 || /* XXX FBO remove */
737 rb->_ActualFormat == GL_DEPTH24_STENCIL8_EXT) {
738 switch (tiling) {
739 case I915_TILING_NONE:
740 default:
741 intelInitDepthPointers_z24_s8(rb);
742 break;
743 case I915_TILING_X:
744 intel_XTile_InitDepthPointers_z24_s8(rb);
745 break;
746 case I915_TILING_Y:
747 intel_YTile_InitDepthPointers_z24_s8(rb);
748 break;
749 }
750 }
751 else if (rb->_ActualFormat == GL_STENCIL_INDEX8_EXT) {
752 switch (tiling) {
753 case I915_TILING_NONE:
754 default:
755 intelInitStencilPointers_z24_s8(rb);
756 break;
757 case I915_TILING_X:
758 intel_XTile_InitStencilPointers_z24_s8(rb);
759 break;
760 case I915_TILING_Y:
761 intel_YTile_InitStencilPointers_z24_s8(rb);
762 break;
763 }
764 }
765 else {
766 _mesa_problem(NULL,
767 "Unexpected _ActualFormat in intelSetSpanFunctions");
768 }
769 }