1 /* $Id: s_depth.c,v 1.25 2002/10/30 19:49:30 brianp Exp $ */
4 * Mesa 3-D graphics library
7 * Copyright (C) 1999-2002 Brian Paul All Rights Reserved.
9 * Permission is hereby granted, free of charge, to any person obtaining a
10 * copy of this software and associated documentation files (the "Software"),
11 * to deal in the Software without restriction, including without limitation
12 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
13 * and/or sell copies of the Software, and to permit persons to whom the
14 * Software is furnished to do so, subject to the following conditions:
16 * The above copyright notice and this permission notice shall be included
17 * in all copies or substantial portions of the Software.
19 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
20 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
22 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
23 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
24 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
34 #include "s_context.h"
38 * Return address of depth buffer value for given window coord.
41 _mesa_zbuffer_address(GLcontext
*ctx
, GLint x
, GLint y
)
43 if (ctx
->Visual
.depthBits
<= 16)
44 return (GLushort
*) ctx
->DrawBuffer
->DepthBuffer
45 + ctx
->DrawBuffer
->Width
* y
+ x
;
47 return (GLuint
*) ctx
->DrawBuffer
->DepthBuffer
48 + ctx
->DrawBuffer
->Width
* y
+ x
;
52 #define Z_ADDRESS16( CTX, X, Y ) \
53 ( ((GLushort *) (CTX)->DrawBuffer->DepthBuffer) \
54 + (CTX)->DrawBuffer->Width * (Y) + (X) )
56 #define Z_ADDRESS32( CTX, X, Y ) \
57 ( ((GLuint *) (CTX)->DrawBuffer->DepthBuffer) \
58 + (CTX)->DrawBuffer->Width * (Y) + (X) )
62 /**********************************************************************/
63 /***** Depth Testing Functions *****/
64 /**********************************************************************/
68 * Do depth test for an array of fragments. This is used both for
69 * software and hardware Z buffers.
70 * Input: zbuffer - array of z values in the zbuffer
71 * z - array of fragment z values
72 * Return: number of fragments which pass the test.
75 depth_test_span16( GLcontext
*ctx
, GLuint n
,
76 GLushort zbuffer
[], const GLdepth z
[], GLubyte mask
[] )
80 /* switch cases ordered from most frequent to less frequent */
81 switch (ctx
->Depth
.Func
) {
83 if (ctx
->Depth
.Mask
) {
88 if (z
[i
] < zbuffer
[i
]) {
101 /* Don't update Z buffer */
103 for (i
=0; i
<n
; i
++) {
105 if (z
[i
] < zbuffer
[i
]) {
117 if (ctx
->Depth
.Mask
) {
118 /* Update Z buffer */
122 if (z
[i
] <= zbuffer
[i
]) {
133 /* Don't update Z buffer */
137 if (z
[i
] <= zbuffer
[i
]) {
149 if (ctx
->Depth
.Mask
) {
150 /* Update Z buffer */
154 if (z
[i
] >= zbuffer
[i
]) {
165 /* Don't update Z buffer */
169 if (z
[i
] >= zbuffer
[i
]) {
181 if (ctx
->Depth
.Mask
) {
182 /* Update Z buffer */
186 if (z
[i
] > zbuffer
[i
]) {
197 /* Don't update Z buffer */
201 if (z
[i
] > zbuffer
[i
]) {
213 if (ctx
->Depth
.Mask
) {
214 /* Update Z buffer */
218 if (z
[i
] != zbuffer
[i
]) {
229 /* Don't update Z buffer */
233 if (z
[i
] != zbuffer
[i
]) {
245 if (ctx
->Depth
.Mask
) {
246 /* Update Z buffer */
250 if (z
[i
] == zbuffer
[i
]) {
261 /* Don't update Z buffer */
265 if (z
[i
] == zbuffer
[i
]) {
277 if (ctx
->Depth
.Mask
) {
278 /* Update Z buffer */
288 /* Don't update Z buffer or mask */
293 _mesa_bzero(mask
, n
* sizeof(GLubyte
));
296 _mesa_problem(ctx
, "Bad depth func in depth_test_span16");
304 depth_test_span32( GLcontext
*ctx
, GLuint n
,
305 GLuint zbuffer
[], const GLdepth z
[], GLubyte mask
[] )
309 /* switch cases ordered from most frequent to less frequent */
310 switch (ctx
->Depth
.Func
) {
312 if (ctx
->Depth
.Mask
) {
313 /* Update Z buffer */
315 for (i
=0; i
<n
; i
++) {
317 if (z
[i
] < zbuffer
[i
]) {
330 /* Don't update Z buffer */
332 for (i
=0; i
<n
; i
++) {
334 if (z
[i
] < zbuffer
[i
]) {
346 if (ctx
->Depth
.Mask
) {
347 /* Update Z buffer */
351 if (z
[i
] <= zbuffer
[i
]) {
362 /* Don't update Z buffer */
366 if (z
[i
] <= zbuffer
[i
]) {
378 if (ctx
->Depth
.Mask
) {
379 /* Update Z buffer */
383 if (z
[i
] >= zbuffer
[i
]) {
394 /* Don't update Z buffer */
398 if (z
[i
] >= zbuffer
[i
]) {
410 if (ctx
->Depth
.Mask
) {
411 /* Update Z buffer */
415 if (z
[i
] > zbuffer
[i
]) {
426 /* Don't update Z buffer */
430 if (z
[i
] > zbuffer
[i
]) {
442 if (ctx
->Depth
.Mask
) {
443 /* Update Z buffer */
447 if (z
[i
] != zbuffer
[i
]) {
458 /* Don't update Z buffer */
462 if (z
[i
] != zbuffer
[i
]) {
474 if (ctx
->Depth
.Mask
) {
475 /* Update Z buffer */
479 if (z
[i
] == zbuffer
[i
]) {
490 /* Don't update Z buffer */
494 if (z
[i
] == zbuffer
[i
]) {
506 if (ctx
->Depth
.Mask
) {
507 /* Update Z buffer */
517 /* Don't update Z buffer or mask */
522 _mesa_bzero(mask
, n
* sizeof(GLubyte
));
525 _mesa_problem(ctx
, "Bad depth func in depth_test_span32");
534 * Apply depth test to span of fragments. Hardware or software z buffer.
537 depth_test_span( GLcontext
*ctx
, struct sw_span
*span
)
539 const GLint x
= span
->x
;
540 const GLint y
= span
->y
;
541 const GLuint n
= span
->end
;
542 SWcontext
*swrast
= SWRAST_CONTEXT(ctx
);
544 ASSERT((span
->arrayMask
& SPAN_XY
) == 0);
545 ASSERT(span
->arrayMask
& SPAN_Z
);
547 if (swrast
->Driver
.ReadDepthSpan
) {
548 /* hardware-based depth buffer */
549 GLdepth zbuffer
[MAX_WIDTH
];
551 (*swrast
->Driver
.ReadDepthSpan
)(ctx
, n
, x
, y
, zbuffer
);
552 passed
= depth_test_span32(ctx
, n
, zbuffer
, span
->array
->z
,
554 ASSERT(swrast
->Driver
.WriteDepthSpan
);
555 (*swrast
->Driver
.WriteDepthSpan
)(ctx
, n
, x
, y
, zbuffer
,
558 span
->writeAll
= GL_FALSE
;
563 /* software depth buffer */
564 if (ctx
->Visual
.depthBits
<= 16) {
565 GLushort
*zptr
= (GLushort
*) Z_ADDRESS16(ctx
, x
, y
);
566 passed
= depth_test_span16(ctx
, n
, zptr
, span
->array
->z
, span
->array
->mask
);
569 GLuint
*zptr
= (GLuint
*) Z_ADDRESS32(ctx
, x
, y
);
570 passed
= depth_test_span32(ctx
, n
, zptr
, span
->array
->z
, span
->array
->mask
);
573 if (passed
< span
->end
) {
574 span
->writeAll
= GL_FALSE
;
577 /* this causes a glDrawPixels(GL_DEPTH_COMPONENT) conformance failure */
578 if (passed
< span
->end
) {
579 span
->writeAll
= GL_FALSE
;
584 while (span
->end
> 0 && span
->mask
[span
->end
- 1] == 0)
596 * Do depth testing for an array of fragments using software Z buffer.
599 software_depth_test_pixels16( GLcontext
*ctx
, GLuint n
,
600 const GLint x
[], const GLint y
[],
601 const GLdepth z
[], GLubyte mask
[] )
603 /* switch cases ordered from most frequent to less frequent */
604 switch (ctx
->Depth
.Func
) {
606 if (ctx
->Depth
.Mask
) {
607 /* Update Z buffer */
609 for (i
=0; i
<n
; i
++) {
611 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
624 /* Don't update Z buffer */
626 for (i
=0; i
<n
; i
++) {
628 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
641 if (ctx
->Depth
.Mask
) {
642 /* Update Z buffer */
644 for (i
=0; i
<n
; i
++) {
646 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
659 /* Don't update Z buffer */
661 for (i
=0; i
<n
; i
++) {
663 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
676 if (ctx
->Depth
.Mask
) {
677 /* Update Z buffer */
679 for (i
=0; i
<n
; i
++) {
681 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
694 /* Don't update Z buffer */
696 for (i
=0; i
<n
; i
++) {
698 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
711 if (ctx
->Depth
.Mask
) {
712 /* Update Z buffer */
714 for (i
=0; i
<n
; i
++) {
716 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
729 /* Don't update Z buffer */
731 for (i
=0; i
<n
; i
++) {
733 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
746 if (ctx
->Depth
.Mask
) {
747 /* Update Z buffer */
749 for (i
=0; i
<n
; i
++) {
751 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
764 /* Don't update Z buffer */
766 for (i
=0; i
<n
; i
++) {
768 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
781 if (ctx
->Depth
.Mask
) {
782 /* Update Z buffer */
784 for (i
=0; i
<n
; i
++) {
786 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
799 /* Don't update Z buffer */
801 for (i
=0; i
<n
; i
++) {
803 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
816 if (ctx
->Depth
.Mask
) {
817 /* Update Z buffer */
819 for (i
=0; i
<n
; i
++) {
821 GLushort
*zptr
= Z_ADDRESS16(ctx
,x
[i
],y
[i
]);
827 /* Don't update Z buffer or mask */
831 /* depth test never passes */
832 _mesa_bzero(mask
, n
* sizeof(GLubyte
));
835 _mesa_problem(ctx
, "Bad depth func in software_depth_test_pixels");
842 * Do depth testing for an array of fragments using software Z buffer.
845 software_depth_test_pixels32( GLcontext
*ctx
, GLuint n
,
846 const GLint x
[], const GLint y
[],
847 const GLdepth z
[], GLubyte mask
[] )
849 /* switch cases ordered from most frequent to less frequent */
850 switch (ctx
->Depth
.Func
) {
852 if (ctx
->Depth
.Mask
) {
853 /* Update Z buffer */
855 for (i
=0; i
<n
; i
++) {
857 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
870 /* Don't update Z buffer */
872 for (i
=0; i
<n
; i
++) {
874 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
887 if (ctx
->Depth
.Mask
) {
888 /* Update Z buffer */
890 for (i
=0; i
<n
; i
++) {
892 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
905 /* Don't update Z buffer */
907 for (i
=0; i
<n
; i
++) {
909 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
922 if (ctx
->Depth
.Mask
) {
923 /* Update Z buffer */
925 for (i
=0; i
<n
; i
++) {
927 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
940 /* Don't update Z buffer */
942 for (i
=0; i
<n
; i
++) {
944 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
957 if (ctx
->Depth
.Mask
) {
958 /* Update Z buffer */
960 for (i
=0; i
<n
; i
++) {
962 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
975 /* Don't update Z buffer */
977 for (i
=0; i
<n
; i
++) {
979 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
992 if (ctx
->Depth
.Mask
) {
993 /* Update Z buffer */
995 for (i
=0; i
<n
; i
++) {
997 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
1010 /* Don't update Z buffer */
1012 for (i
=0; i
<n
; i
++) {
1014 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
1015 if (z
[i
] != *zptr
) {
1027 if (ctx
->Depth
.Mask
) {
1028 /* Update Z buffer */
1030 for (i
=0; i
<n
; i
++) {
1032 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
1033 if (z
[i
] == *zptr
) {
1045 /* Don't update Z buffer */
1047 for (i
=0; i
<n
; i
++) {
1049 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
1050 if (z
[i
] == *zptr
) {
1062 if (ctx
->Depth
.Mask
) {
1063 /* Update Z buffer */
1065 for (i
=0; i
<n
; i
++) {
1067 GLuint
*zptr
= Z_ADDRESS32(ctx
,x
[i
],y
[i
]);
1073 /* Don't update Z buffer or mask */
1077 /* depth test never passes */
1078 _mesa_bzero(mask
, n
* sizeof(GLubyte
));
1081 _mesa_problem(ctx
, "Bad depth func in software_depth_test_pixels");
1088 * Do depth testing for an array of pixels using hardware Z buffer.
1089 * Input/output: zbuffer - array of depth values from Z buffer
1090 * Input: z - array of fragment z values.
1093 hardware_depth_test_pixels( GLcontext
*ctx
, GLuint n
, GLdepth zbuffer
[],
1094 const GLdepth z
[], GLubyte mask
[] )
1096 /* switch cases ordered from most frequent to less frequent */
1097 switch (ctx
->Depth
.Func
) {
1099 if (ctx
->Depth
.Mask
) {
1100 /* Update Z buffer */
1102 for (i
=0; i
<n
; i
++) {
1104 if (z
[i
] < zbuffer
[i
]) {
1116 /* Don't update Z buffer */
1118 for (i
=0; i
<n
; i
++) {
1120 if (z
[i
] < zbuffer
[i
]) {
1132 if (ctx
->Depth
.Mask
) {
1133 /* Update Z buffer */
1135 for (i
=0; i
<n
; i
++) {
1137 if (z
[i
] <= zbuffer
[i
]) {
1149 /* Don't update Z buffer */
1151 for (i
=0; i
<n
; i
++) {
1153 if (z
[i
] <= zbuffer
[i
]) {
1165 if (ctx
->Depth
.Mask
) {
1166 /* Update Z buffer */
1168 for (i
=0; i
<n
; i
++) {
1170 if (z
[i
] >= zbuffer
[i
]) {
1182 /* Don't update Z buffer */
1184 for (i
=0; i
<n
; i
++) {
1186 if (z
[i
] >= zbuffer
[i
]) {
1198 if (ctx
->Depth
.Mask
) {
1199 /* Update Z buffer */
1201 for (i
=0; i
<n
; i
++) {
1203 if (z
[i
] > zbuffer
[i
]) {
1215 /* Don't update Z buffer */
1217 for (i
=0; i
<n
; i
++) {
1219 if (z
[i
] > zbuffer
[i
]) {
1231 if (ctx
->Depth
.Mask
) {
1232 /* Update Z buffer */
1234 for (i
=0; i
<n
; i
++) {
1236 if (z
[i
] != zbuffer
[i
]) {
1248 /* Don't update Z buffer */
1250 for (i
=0; i
<n
; i
++) {
1252 if (z
[i
] != zbuffer
[i
]) {
1264 if (ctx
->Depth
.Mask
) {
1265 /* Update Z buffer */
1267 for (i
=0; i
<n
; i
++) {
1269 if (z
[i
] == zbuffer
[i
]) {
1281 /* Don't update Z buffer */
1283 for (i
=0; i
<n
; i
++) {
1285 if (z
[i
] == zbuffer
[i
]) {
1297 if (ctx
->Depth
.Mask
) {
1298 /* Update Z buffer */
1300 for (i
=0; i
<n
; i
++) {
1307 /* Don't update Z buffer or mask */
1311 /* depth test never passes */
1312 _mesa_bzero(mask
, n
* sizeof(GLubyte
));
1315 _mesa_problem(ctx
, "Bad depth func in hardware_depth_test_pixels");
1322 depth_test_pixels( GLcontext
*ctx
, struct sw_span
*span
)
1324 SWcontext
*swrast
= SWRAST_CONTEXT(ctx
);
1325 const GLuint n
= span
->end
;
1326 const GLint
*x
= span
->array
->x
;
1327 const GLint
*y
= span
->array
->y
;
1328 const GLdepth
*z
= span
->array
->z
;
1329 GLubyte
*mask
= span
->array
->mask
;
1331 if (swrast
->Driver
.ReadDepthPixels
) {
1332 /* read depth values from hardware Z buffer */
1333 GLdepth zbuffer
[MAX_WIDTH
];
1334 (*swrast
->Driver
.ReadDepthPixels
)(ctx
, n
, x
, y
, zbuffer
);
1336 hardware_depth_test_pixels( ctx
, n
, zbuffer
, z
, mask
);
1338 /* update hardware Z buffer with new values */
1339 assert(swrast
->Driver
.WriteDepthPixels
);
1340 (*swrast
->Driver
.WriteDepthPixels
)(ctx
, n
, x
, y
, zbuffer
, mask
);
1343 /* software depth testing */
1344 if (ctx
->Visual
.depthBits
<= 16)
1345 software_depth_test_pixels16(ctx
, n
, x
, y
, z
, mask
);
1347 software_depth_test_pixels32(ctx
, n
, x
, y
, z
, mask
);
1349 return n
; /* not really correct, but OK */
1354 * Apply depth (Z) buffer testing to the span.
1355 * \return approx number of pixels that passed (only zero is reliable)
1358 _mesa_depth_test_span( GLcontext
*ctx
, struct sw_span
*span
)
1360 if (span
->arrayMask
& SPAN_XY
)
1361 return depth_test_pixels(ctx
, span
);
1363 return depth_test_span(ctx
, span
);
1368 /**********************************************************************/
1369 /***** Read Depth Buffer *****/
1370 /**********************************************************************/
1374 * Read a span of depth values from the depth buffer.
1375 * This function does clipping before calling the device driver function.
1378 _mesa_read_depth_span( GLcontext
*ctx
,
1379 GLint n
, GLint x
, GLint y
, GLdepth depth
[] )
1381 SWcontext
*swrast
= SWRAST_CONTEXT(ctx
);
1383 if (y
< 0 || y
>= (GLint
) ctx
->DrawBuffer
->Height
||
1384 x
+ (GLint
) n
<= 0 || x
>= (GLint
) ctx
->DrawBuffer
->Width
) {
1385 /* span is completely outside framebuffer */
1387 for (i
= 0; i
< n
; i
++)
1395 for (i
= 0; i
< dx
; i
++)
1401 if (x
+ n
> (GLint
) ctx
->DrawBuffer
->Width
) {
1402 GLint dx
= x
+ n
- (GLint
) ctx
->DrawBuffer
->Width
;
1404 for (i
= 0; i
< dx
; i
++)
1405 depth
[n
- i
- 1] = 0;
1412 if (ctx
->DrawBuffer
->DepthBuffer
) {
1413 /* read from software depth buffer */
1414 if (ctx
->Visual
.depthBits
<= 16) {
1415 const GLushort
*zptr
= Z_ADDRESS16( ctx
, x
, y
);
1417 for (i
= 0; i
< n
; i
++) {
1422 const GLuint
*zptr
= Z_ADDRESS32( ctx
, x
, y
);
1424 for (i
= 0; i
< n
; i
++) {
1429 else if (swrast
->Driver
.ReadDepthSpan
) {
1430 /* read from hardware depth buffer */
1431 (*swrast
->Driver
.ReadDepthSpan
)( ctx
, n
, x
, y
, depth
);
1434 /* no depth buffer */
1435 _mesa_bzero(depth
, n
* sizeof(GLfloat
));
1444 * Return a span of depth values from the depth buffer as floats in [0,1].
1445 * This is used for both hardware and software depth buffers.
1446 * Input: n - how many pixels
1447 * x,y - location of first pixel
1448 * Output: depth - the array of depth values
1451 _mesa_read_depth_span_float( GLcontext
*ctx
,
1452 GLint n
, GLint x
, GLint y
, GLfloat depth
[] )
1454 SWcontext
*swrast
= SWRAST_CONTEXT(ctx
);
1455 const GLfloat scale
= 1.0F
/ ctx
->DepthMaxF
;
1457 if (y
< 0 || y
>= (GLint
) ctx
->DrawBuffer
->Height
||
1458 x
+ (GLint
) n
<= 0 || x
>= (GLint
) ctx
->DrawBuffer
->Width
) {
1459 /* span is completely outside framebuffer */
1461 for (i
= 0; i
< n
; i
++)
1469 for (i
= 0; i
< dx
; i
++)
1474 if (x
+ n
> (GLint
) ctx
->DrawBuffer
->Width
) {
1475 GLint dx
= x
+ n
- (GLint
) ctx
->DrawBuffer
->Width
;
1477 for (i
= 0; i
< dx
; i
++)
1478 depth
[n
- i
- 1] = 0.0F
;
1485 if (ctx
->DrawBuffer
->DepthBuffer
) {
1486 /* read from software depth buffer */
1487 if (ctx
->Visual
.depthBits
<= 16) {
1488 const GLushort
*zptr
= Z_ADDRESS16( ctx
, x
, y
);
1490 for (i
= 0; i
< n
; i
++) {
1491 depth
[i
] = (GLfloat
) zptr
[i
] * scale
;
1495 const GLuint
*zptr
= Z_ADDRESS32( ctx
, x
, y
);
1497 for (i
= 0; i
< n
; i
++) {
1498 depth
[i
] = (GLfloat
) zptr
[i
] * scale
;
1502 else if (swrast
->Driver
.ReadDepthSpan
) {
1503 /* read from hardware depth buffer */
1504 GLdepth d
[MAX_WIDTH
];
1506 assert(n
<= MAX_WIDTH
);
1507 (*swrast
->Driver
.ReadDepthSpan
)( ctx
, n
, x
, y
, d
);
1508 for (i
= 0; i
< n
; i
++) {
1509 depth
[i
] = d
[i
] * scale
;
1513 /* no depth buffer */
1514 _mesa_bzero(depth
, n
* sizeof(GLfloat
));
1520 /**********************************************************************/
1521 /***** Allocate and Clear Depth Buffer *****/
1522 /**********************************************************************/
1527 * Allocate a new depth buffer. If there's already a depth buffer allocated
1528 * it will be free()'d. The new depth buffer will be uniniitalized.
1529 * This function is only called through Driver.alloc_depth_buffer.
1532 _mesa_alloc_depth_buffer( GLframebuffer
*buffer
)
1534 GLint bytesPerValue
;
1536 ASSERT(buffer
->UseSoftwareDepthBuffer
);
1538 /* deallocate current depth buffer if present */
1539 if (buffer
->DepthBuffer
) {
1540 MESA_PBUFFER_FREE(buffer
->DepthBuffer
);
1541 buffer
->DepthBuffer
= NULL
;
1544 /* allocate new depth buffer, but don't initialize it */
1545 if (buffer
->Visual
.depthBits
<= 16)
1546 bytesPerValue
= sizeof(GLushort
);
1548 bytesPerValue
= sizeof(GLuint
);
1550 buffer
->DepthBuffer
= MESA_PBUFFER_ALLOC(buffer
->Width
* buffer
->Height
1553 if (!buffer
->DepthBuffer
) {
1555 GET_CURRENT_CONTEXT(ctx
);
1557 ctx
->Depth
.Test
= GL_FALSE
;
1558 ctx
->NewState
|= _NEW_DEPTH
;
1559 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "Couldn't allocate depth buffer");
1566 * Clear the depth buffer. If the depth buffer doesn't exist yet we'll
1568 * This function is only called through Driver.clear_depth_buffer.
1571 _mesa_clear_depth_buffer( GLcontext
*ctx
)
1573 if (ctx
->Visual
.depthBits
== 0
1574 || !ctx
->DrawBuffer
->DepthBuffer
1575 || !ctx
->Depth
.Mask
) {
1576 /* no depth buffer, or writing to it is disabled */
1580 /* The loops in this function have been written so the IRIX 5.3
1581 * C compiler can unroll them. Hopefully other compilers can too!
1584 if (ctx
->Scissor
.Enabled
) {
1585 /* only clear scissor region */
1586 if (ctx
->Visual
.depthBits
<= 16) {
1587 const GLushort clearValue
= (GLushort
) (ctx
->Depth
.Clear
* ctx
->DepthMax
);
1588 const GLint rows
= ctx
->DrawBuffer
->_Ymax
- ctx
->DrawBuffer
->_Ymin
;
1589 const GLint cols
= ctx
->DrawBuffer
->_Xmax
- ctx
->DrawBuffer
->_Xmin
;
1590 const GLint rowStride
= ctx
->DrawBuffer
->Width
;
1591 GLushort
*dRow
= (GLushort
*) ctx
->DrawBuffer
->DepthBuffer
1592 + ctx
->DrawBuffer
->_Ymin
* rowStride
+ ctx
->DrawBuffer
->_Xmin
;
1594 for (i
= 0; i
< rows
; i
++) {
1595 for (j
= 0; j
< cols
; j
++) {
1596 dRow
[j
] = clearValue
;
1602 const GLuint clearValue
= (GLuint
) (ctx
->Depth
.Clear
* ctx
->DepthMax
);
1603 const GLint rows
= ctx
->DrawBuffer
->_Ymax
- ctx
->DrawBuffer
->_Ymin
;
1604 const GLint cols
= ctx
->DrawBuffer
->_Xmax
- ctx
->DrawBuffer
->_Xmin
;
1605 const GLint rowStride
= ctx
->DrawBuffer
->Width
;
1606 GLuint
*dRow
= (GLuint
*) ctx
->DrawBuffer
->DepthBuffer
1607 + ctx
->DrawBuffer
->_Ymin
* rowStride
+ ctx
->DrawBuffer
->_Xmin
;
1609 for (i
= 0; i
< rows
; i
++) {
1610 for (j
= 0; j
< cols
; j
++) {
1611 dRow
[j
] = clearValue
;
1618 /* clear whole buffer */
1619 if (ctx
->Visual
.depthBits
<= 16) {
1620 const GLushort clearValue
= (GLushort
) (ctx
->Depth
.Clear
* ctx
->DepthMax
);
1621 if ((clearValue
& 0xff) == (clearValue
>> 8)) {
1622 if (clearValue
== 0) {
1623 _mesa_bzero(ctx
->DrawBuffer
->DepthBuffer
,
1624 2*ctx
->DrawBuffer
->Width
*ctx
->DrawBuffer
->Height
);
1627 /* lower and upper bytes of clear_value are same, use MEMSET */
1628 MEMSET( ctx
->DrawBuffer
->DepthBuffer
, clearValue
& 0xff,
1629 2 * ctx
->DrawBuffer
->Width
* ctx
->DrawBuffer
->Height
);
1633 GLushort
*d
= (GLushort
*) ctx
->DrawBuffer
->DepthBuffer
;
1634 GLint n
= ctx
->DrawBuffer
->Width
* ctx
->DrawBuffer
->Height
;
1636 d
[0] = clearValue
; d
[1] = clearValue
;
1637 d
[2] = clearValue
; d
[3] = clearValue
;
1638 d
[4] = clearValue
; d
[5] = clearValue
;
1639 d
[6] = clearValue
; d
[7] = clearValue
;
1640 d
[8] = clearValue
; d
[9] = clearValue
;
1641 d
[10] = clearValue
; d
[11] = clearValue
;
1642 d
[12] = clearValue
; d
[13] = clearValue
;
1643 d
[14] = clearValue
; d
[15] = clearValue
;
1654 /* >16 bit depth buffer */
1655 const GLuint clearValue
= (GLuint
) (ctx
->Depth
.Clear
* ctx
->DepthMax
);
1656 if (clearValue
== 0) {
1657 _mesa_bzero(ctx
->DrawBuffer
->DepthBuffer
,
1658 ctx
->DrawBuffer
->Width
*ctx
->DrawBuffer
->Height
*sizeof(GLuint
));
1661 GLint n
= ctx
->DrawBuffer
->Width
* ctx
->DrawBuffer
->Height
;
1662 GLuint
*d
= (GLuint
*) ctx
->DrawBuffer
->DepthBuffer
;
1664 d
[0] = clearValue
; d
[1] = clearValue
;
1665 d
[2] = clearValue
; d
[3] = clearValue
;
1666 d
[4] = clearValue
; d
[5] = clearValue
;
1667 d
[6] = clearValue
; d
[7] = clearValue
;
1668 d
[8] = clearValue
; d
[9] = clearValue
;
1669 d
[10] = clearValue
; d
[11] = clearValue
;
1670 d
[12] = clearValue
; d
[13] = clearValue
;
1671 d
[14] = clearValue
; d
[15] = clearValue
;