1 /* $XFree86: xc/lib/GL/mesa/src/drv/i810/i810tris.c,v 1.7 2002/10/30 12:51:33 alanh Exp $ */
2 /**************************************************************************
4 Copyright 2001 VA Linux Systems Inc., Fremont, California.
8 Permission is hereby granted, free of charge, to any person obtaining a
9 copy of this software and associated documentation files (the "Software"),
10 to deal in the Software without restriction, including without limitation
11 on the rights to use, copy, modify, merge, publish, distribute, sub
12 license, and/or sell copies of the Software, and to permit persons to whom
13 the Software is furnished to do so, subject to the following conditions:
15 The above copyright notice and this permission notice (including the next
16 paragraph) shall be included in all copies or substantial portions of the
19 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21 FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
22 ATI, VA LINUX SYSTEMS AND/OR THEIR SUPPLIERS BE LIABLE FOR ANY CLAIM,
23 DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
24 OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
25 USE OR OTHER DEALINGS IN THE SOFTWARE.
27 **************************************************************************/
31 * Keith Whitwell <keith@tungstengraphics.com>
40 #include "swrast/swrast.h"
41 #include "swrast_setup/swrast_setup.h"
42 #include "tnl/t_context.h"
43 #include "tnl/t_pipeline.h"
45 #include "i810screen.h"
49 #include "i810state.h"
51 #include "i810ioctl.h"
53 static void i810RenderPrimitive( GLcontext
*ctx
, GLenum prim
);
55 /***********************************************************************
56 * Emit primitives as inline vertices *
57 ***********************************************************************/
59 #if defined(USE_X86_ASM)
60 #define COPY_DWORDS( j, vb, vertsize, v ) \
63 __asm__ __volatile__( "rep ; movsl" \
64 : "=%c" (j), "=D" (vb), "=S" (__tmp) \
70 #define COPY_DWORDS( j, vb, vertsize, v ) \
72 for ( j = 0 ; j < vertsize ; j++ ) \
73 vb[j] = ((GLuint *)v)[j]; \
78 static __inline__
void i810_draw_triangle( i810ContextPtr imesa
,
83 GLuint vertsize
= imesa
->vertex_size
;
84 GLuint
*vb
= i810AllocDmaLow( imesa
, 3 * 4 * vertsize
);
87 COPY_DWORDS( j
, vb
, vertsize
, v0
);
88 COPY_DWORDS( j
, vb
, vertsize
, v1
);
89 COPY_DWORDS( j
, vb
, vertsize
, v2
);
93 static __inline__
void i810_draw_quad( i810ContextPtr imesa
,
99 GLuint vertsize
= imesa
->vertex_size
;
100 GLuint
*vb
= i810AllocDmaLow( imesa
, 6 * 4 * vertsize
);
103 COPY_DWORDS( j
, vb
, vertsize
, v0
);
104 COPY_DWORDS( j
, vb
, vertsize
, v1
);
105 COPY_DWORDS( j
, vb
, vertsize
, v3
);
106 COPY_DWORDS( j
, vb
, vertsize
, v1
);
107 COPY_DWORDS( j
, vb
, vertsize
, v2
);
108 COPY_DWORDS( j
, vb
, vertsize
, v3
);
112 static __inline__
void i810_draw_point( i810ContextPtr imesa
,
115 GLfloat sz
= 0.5 * CLAMP(imesa
->glCtx
->Point
.Size
,
116 imesa
->glCtx
->Const
.MinPointSize
,
117 imesa
->glCtx
->Const
.MaxPointSize
);
118 int vertsize
= imesa
->vertex_size
;
119 GLuint
*vb
= i810AllocDmaLow( imesa
, 2 * 4 * vertsize
);
122 /* Draw a point as a horizontal line.
124 *(float *)&vb
[0] = tmp
->v
.x
- sz
+ 0.125;
125 for (j
= 1 ; j
< vertsize
; j
++)
129 *(float *)&vb
[0] = tmp
->v
.x
+ sz
+ 0.125;
130 for (j
= 1 ; j
< vertsize
; j
++)
136 static __inline__
void i810_draw_line( i810ContextPtr imesa
,
140 GLuint vertsize
= imesa
->vertex_size
;
141 GLuint
*vb
= i810AllocDmaLow( imesa
, 2 * 4 * vertsize
);
144 COPY_DWORDS( j
, vb
, vertsize
, v0
);
145 COPY_DWORDS( j
, vb
, vertsize
, v1
);
150 /***********************************************************************
151 * Macros for t_dd_tritmp.h to draw basic primitives *
152 ***********************************************************************/
154 #define TRI( a, b, c ) \
156 if (0) fprintf(stderr, "hw TRI\n"); \
158 imesa->draw_tri( imesa, a, b, c ); \
160 i810_draw_triangle( imesa, a, b, c ); \
163 #define QUAD( a, b, c, d ) \
165 if (0) fprintf(stderr, "hw QUAD\n"); \
167 imesa->draw_tri( imesa, a, b, d ); \
168 imesa->draw_tri( imesa, b, c, d ); \
170 i810_draw_quad( imesa, a, b, c, d ); \
173 #define LINE( v0, v1 ) \
175 if (0) fprintf(stderr, "hw LINE\n"); \
177 imesa->draw_line( imesa, v0, v1 ); \
179 i810_draw_line( imesa, v0, v1 ); \
182 #define POINT( v0 ) \
184 if (0) fprintf(stderr, "hw POINT\n"); \
186 imesa->draw_point( imesa, v0 ); \
188 i810_draw_point( imesa, v0 ); \
192 /***********************************************************************
193 * Build render functions from dd templates *
194 ***********************************************************************/
196 #define I810_OFFSET_BIT 0x01
197 #define I810_TWOSIDE_BIT 0x02
198 #define I810_UNFILLED_BIT 0x04
199 #define I810_FALLBACK_BIT 0x08
200 #define I810_MAX_TRIFUNC 0x10
204 tnl_points_func points
;
206 tnl_triangle_func triangle
;
208 } rast_tab
[I810_MAX_TRIFUNC
];
211 #define DO_FALLBACK (IND & I810_FALLBACK_BIT)
212 #define DO_OFFSET (IND & I810_OFFSET_BIT)
213 #define DO_UNFILLED (IND & I810_UNFILLED_BIT)
214 #define DO_TWOSIDE (IND & I810_TWOSIDE_BIT)
220 #define DO_FULL_QUAD 1
224 #define HAVE_BACK_COLORS 0
225 #define HAVE_HW_FLATSHADE 1
226 #define VERTEX i810Vertex
230 #define DEPTH_SCALE (1.0/0xffff)
231 #define UNFILLED_TRI unfilled_tri
232 #define UNFILLED_QUAD unfilled_quad
233 #define VERT_X(_v) _v->v.x
234 #define VERT_Y(_v) _v->v.y
235 #define VERT_Z(_v) _v->v.z
236 #define AREA_IS_CCW( a ) (a > 0)
237 #define GET_VERTEX(e) (imesa->verts + (e * imesa->vertex_size * sizeof(int)))
239 #define VERT_SET_RGBA( v, c ) \
241 i810_color_t *color = (i810_color_t *)&((v)->ui[coloroffset]); \
242 UNCLAMPED_FLOAT_TO_UBYTE(color->red, (c)[0]); \
243 UNCLAMPED_FLOAT_TO_UBYTE(color->green, (c)[1]); \
244 UNCLAMPED_FLOAT_TO_UBYTE(color->blue, (c)[2]); \
245 UNCLAMPED_FLOAT_TO_UBYTE(color->alpha, (c)[3]); \
248 #define VERT_COPY_RGBA( v0, v1 ) v0->ui[coloroffset] = v1->ui[coloroffset]
250 #define VERT_SET_SPEC( v0, c ) \
253 UNCLAMPED_FLOAT_TO_UBYTE(v0->v.specular.red, (c)[0]); \
254 UNCLAMPED_FLOAT_TO_UBYTE(v0->v.specular.green, (c)[1]); \
255 UNCLAMPED_FLOAT_TO_UBYTE(v0->v.specular.blue, (c)[2]); \
258 #define VERT_COPY_SPEC( v0, v1 ) \
261 v0->v.specular.red = v1->v.specular.red; \
262 v0->v.specular.green = v1->v.specular.green; \
263 v0->v.specular.blue = v1->v.specular.blue; \
267 #define VERT_SAVE_RGBA( idx ) color[idx] = v[idx]->ui[coloroffset]
268 #define VERT_RESTORE_RGBA( idx ) v[idx]->ui[coloroffset] = color[idx]
269 #define VERT_SAVE_SPEC( idx ) if (havespec) spec[idx] = v[idx]->ui[5]
270 #define VERT_RESTORE_SPEC( idx ) if (havespec) v[idx]->ui[5] = spec[idx]
272 #define LOCAL_VARS(n) \
273 i810ContextPtr imesa = I810_CONTEXT(ctx); \
274 GLuint color[n], spec[n]; \
275 GLuint coloroffset = (imesa->vertex_size == 4 ? 3 : 4); \
276 GLboolean havespec = (imesa->vertex_size > 4); \
277 (void) color; (void) spec; (void) coloroffset; (void) havespec;
280 /***********************************************************************
281 * Helpers for rendering unfilled primitives *
282 ***********************************************************************/
284 static const GLuint hw_prim
[GL_POLYGON
+1] = {
297 #define RASTERIZE(x) if (imesa->hw_primitive != hw_prim[x]) \
298 i810RasterPrimitive( ctx, x, hw_prim[x] )
299 #define RENDER_PRIMITIVE imesa->render_primitive
301 #define IND I810_FALLBACK_BIT
302 #include "tnl_dd/t_dd_unfilled.h"
305 /***********************************************************************
306 * Generate GL render functions *
307 ***********************************************************************/
311 #include "tnl_dd/t_dd_tritmp.h"
313 #define IND (I810_OFFSET_BIT)
314 #define TAG(x) x##_offset
315 #include "tnl_dd/t_dd_tritmp.h"
317 #define IND (I810_TWOSIDE_BIT)
318 #define TAG(x) x##_twoside
319 #include "tnl_dd/t_dd_tritmp.h"
321 #define IND (I810_TWOSIDE_BIT|I810_OFFSET_BIT)
322 #define TAG(x) x##_twoside_offset
323 #include "tnl_dd/t_dd_tritmp.h"
325 #define IND (I810_UNFILLED_BIT)
326 #define TAG(x) x##_unfilled
327 #include "tnl_dd/t_dd_tritmp.h"
329 #define IND (I810_OFFSET_BIT|I810_UNFILLED_BIT)
330 #define TAG(x) x##_offset_unfilled
331 #include "tnl_dd/t_dd_tritmp.h"
333 #define IND (I810_TWOSIDE_BIT|I810_UNFILLED_BIT)
334 #define TAG(x) x##_twoside_unfilled
335 #include "tnl_dd/t_dd_tritmp.h"
337 #define IND (I810_TWOSIDE_BIT|I810_OFFSET_BIT|I810_UNFILLED_BIT)
338 #define TAG(x) x##_twoside_offset_unfilled
339 #include "tnl_dd/t_dd_tritmp.h"
341 #define IND (I810_FALLBACK_BIT)
342 #define TAG(x) x##_fallback
343 #include "tnl_dd/t_dd_tritmp.h"
345 #define IND (I810_OFFSET_BIT|I810_FALLBACK_BIT)
346 #define TAG(x) x##_offset_fallback
347 #include "tnl_dd/t_dd_tritmp.h"
349 #define IND (I810_TWOSIDE_BIT|I810_FALLBACK_BIT)
350 #define TAG(x) x##_twoside_fallback
351 #include "tnl_dd/t_dd_tritmp.h"
353 #define IND (I810_TWOSIDE_BIT|I810_OFFSET_BIT|I810_FALLBACK_BIT)
354 #define TAG(x) x##_twoside_offset_fallback
355 #include "tnl_dd/t_dd_tritmp.h"
357 #define IND (I810_UNFILLED_BIT|I810_FALLBACK_BIT)
358 #define TAG(x) x##_unfilled_fallback
359 #include "tnl_dd/t_dd_tritmp.h"
361 #define IND (I810_OFFSET_BIT|I810_UNFILLED_BIT|I810_FALLBACK_BIT)
362 #define TAG(x) x##_offset_unfilled_fallback
363 #include "tnl_dd/t_dd_tritmp.h"
365 #define IND (I810_TWOSIDE_BIT|I810_UNFILLED_BIT|I810_FALLBACK_BIT)
366 #define TAG(x) x##_twoside_unfilled_fallback
367 #include "tnl_dd/t_dd_tritmp.h"
369 #define IND (I810_TWOSIDE_BIT|I810_OFFSET_BIT|I810_UNFILLED_BIT| \
371 #define TAG(x) x##_twoside_offset_unfilled_fallback
372 #include "tnl_dd/t_dd_tritmp.h"
375 static void init_rast_tab( void )
380 init_twoside_offset();
382 init_offset_unfilled();
383 init_twoside_unfilled();
384 init_twoside_offset_unfilled();
386 init_offset_fallback();
387 init_twoside_fallback();
388 init_twoside_offset_fallback();
389 init_unfilled_fallback();
390 init_offset_unfilled_fallback();
391 init_twoside_unfilled_fallback();
392 init_twoside_offset_unfilled_fallback();
396 /***********************************************************************
397 * Rasterization fallback helpers *
398 ***********************************************************************/
401 /* This code is hit only when a mix of accelerated and unaccelerated
402 * primitives are being drawn, and only for the unaccelerated
406 i810_fallback_tri( i810ContextPtr imesa
,
411 GLcontext
*ctx
= imesa
->glCtx
;
413 i810_translate_vertex( ctx
, v0
, &v
[0] );
414 i810_translate_vertex( ctx
, v1
, &v
[1] );
415 i810_translate_vertex( ctx
, v2
, &v
[2] );
416 _swrast_Triangle( ctx
, &v
[0], &v
[1], &v
[2] );
421 i810_fallback_line( i810ContextPtr imesa
,
425 GLcontext
*ctx
= imesa
->glCtx
;
427 i810_translate_vertex( ctx
, v0
, &v
[0] );
428 i810_translate_vertex( ctx
, v1
, &v
[1] );
429 _swrast_Line( ctx
, &v
[0], &v
[1] );
434 i810_fallback_point( i810ContextPtr imesa
,
437 GLcontext
*ctx
= imesa
->glCtx
;
439 i810_translate_vertex( ctx
, v0
, &v
[0] );
440 _swrast_Point( ctx
, &v
[0] );
445 /**********************************************************************/
446 /* Render unclipped begin/end objects */
447 /**********************************************************************/
450 #define V(x) (i810Vertex *)(vertptr + ((x)*vertsize*sizeof(int)))
451 #define RENDER_POINTS( start, count ) \
452 for ( ; start < count ; start++) POINT( V(ELT(start)) );
453 #define RENDER_LINE( v0, v1 ) LINE( V(v0), V(v1) )
454 #define RENDER_TRI( v0, v1, v2 ) TRI( V(v0), V(v1), V(v2) )
455 #define RENDER_QUAD( v0, v1, v2, v3 ) QUAD( V(v0), V(v1), V(v2), V(v3) )
456 #define INIT(x) i810RenderPrimitive( ctx, x )
459 i810ContextPtr imesa = I810_CONTEXT(ctx); \
460 GLubyte *vertptr = (GLubyte *)imesa->verts; \
461 const GLuint vertsize = imesa->vertex_size; \
462 const GLuint * const elt = TNL_CONTEXT(ctx)->vb.Elts; \
464 #define RESET_STIPPLE
465 #define RESET_OCCLUSION
466 #define PRESERVE_VB_DEFS
468 #define TAG(x) i810_##x##_verts
469 #include "tnl/t_vb_rendertmp.h"
472 #define TAG(x) i810_##x##_elts
473 #define ELT(x) elt[x]
474 #include "tnl/t_vb_rendertmp.h"
476 /**********************************************************************/
477 /* Render clipped primitives */
478 /**********************************************************************/
482 static void i810RenderClippedPoly( GLcontext
*ctx
, const GLuint
*elts
,
485 i810ContextPtr imesa
= I810_CONTEXT(ctx
);
486 TNLcontext
*tnl
= TNL_CONTEXT(ctx
);
487 struct vertex_buffer
*VB
= &TNL_CONTEXT(ctx
)->vb
;
488 GLuint prim
= imesa
->render_primitive
;
490 /* Render the new vertices as an unclipped polygon.
493 GLuint
*tmp
= VB
->Elts
;
494 VB
->Elts
= (GLuint
*)elts
;
495 tnl
->Driver
.Render
.PrimTabElts
[GL_POLYGON
]( ctx
, 0, n
,
496 PRIM_BEGIN
|PRIM_END
);
500 /* Restore the render primitive
502 if (prim
!= GL_POLYGON
)
503 tnl
->Driver
.Render
.PrimitiveNotify( ctx
, prim
);
506 static void i810RenderClippedLine( GLcontext
*ctx
, GLuint ii
, GLuint jj
)
508 TNLcontext
*tnl
= TNL_CONTEXT(ctx
);
509 tnl
->Driver
.Render
.Line( ctx
, ii
, jj
);
512 static void i810FastRenderClippedPoly( GLcontext
*ctx
, const GLuint
*elts
,
515 i810ContextPtr imesa
= I810_CONTEXT( ctx
);
516 GLuint vertsize
= imesa
->vertex_size
;
517 GLuint
*vb
= i810AllocDmaLow( imesa
, (n
-2) * 3 * 4 * vertsize
);
518 GLubyte
*vertptr
= (GLubyte
*)imesa
->verts
;
519 const GLuint
*start
= (const GLuint
*)V(elts
[0]);
522 for (i
= 2 ; i
< n
; i
++) {
523 COPY_DWORDS( j
, vb
, vertsize
, V(elts
[i
-1]) );
524 COPY_DWORDS( j
, vb
, vertsize
, V(elts
[i
]) );
525 COPY_DWORDS( j
, vb
, vertsize
, start
);
529 /**********************************************************************/
530 /* Choose render functions */
531 /**********************************************************************/
533 /***********************************************************************
534 * Rasterization fallback helpers *
535 ***********************************************************************/
539 #define _I810_NEW_RENDERSTATE (_DD_NEW_LINE_STIPPLE | \
540 _DD_NEW_TRI_UNFILLED | \
541 _DD_NEW_TRI_LIGHT_TWOSIDE | \
542 _DD_NEW_TRI_OFFSET | \
543 _DD_NEW_TRI_STIPPLE | \
546 #define POINT_FALLBACK (0)
547 #define LINE_FALLBACK (DD_LINE_STIPPLE)
548 #define TRI_FALLBACK (0)
549 #define ANY_FALLBACK_FLAGS (POINT_FALLBACK|LINE_FALLBACK|TRI_FALLBACK|\
551 #define ANY_RASTER_FLAGS (DD_TRI_LIGHT_TWOSIDE|DD_TRI_OFFSET|DD_TRI_UNFILLED)
553 static void i810ChooseRenderState(GLcontext
*ctx
)
555 TNLcontext
*tnl
= TNL_CONTEXT(ctx
);
556 i810ContextPtr imesa
= I810_CONTEXT(ctx
);
557 GLuint flags
= ctx
->_TriangleCaps
;
560 if (I810_DEBUG
& DEBUG_STATE
)
561 fprintf(stderr
,"\n%s\n",__FUNCTION__
);
563 if (flags
& (ANY_FALLBACK_FLAGS
|ANY_RASTER_FLAGS
)) {
564 if (flags
& ANY_RASTER_FLAGS
) {
565 if (flags
& DD_TRI_LIGHT_TWOSIDE
) index
|= I810_TWOSIDE_BIT
;
566 if (flags
& DD_TRI_OFFSET
) index
|= I810_OFFSET_BIT
;
567 if (flags
& DD_TRI_UNFILLED
) index
|= I810_UNFILLED_BIT
;
570 imesa
->draw_point
= i810_draw_point
;
571 imesa
->draw_line
= i810_draw_line
;
572 imesa
->draw_tri
= i810_draw_triangle
;
574 /* Hook in fallbacks for specific primitives.
576 if (flags
& ANY_FALLBACK_FLAGS
)
578 if (flags
& POINT_FALLBACK
)
579 imesa
->draw_point
= i810_fallback_point
;
581 if (flags
& LINE_FALLBACK
)
582 imesa
->draw_line
= i810_fallback_line
;
584 if (flags
& TRI_FALLBACK
)
585 imesa
->draw_tri
= i810_fallback_tri
;
587 if ((flags
& DD_TRI_STIPPLE
) && !imesa
->stipple_in_hw
)
588 imesa
->draw_tri
= i810_fallback_tri
;
590 index
|= I810_FALLBACK_BIT
;
594 if (imesa
->RenderIndex
!= index
) {
595 imesa
->RenderIndex
= index
;
597 tnl
->Driver
.Render
.Points
= rast_tab
[index
].points
;
598 tnl
->Driver
.Render
.Line
= rast_tab
[index
].line
;
599 tnl
->Driver
.Render
.Triangle
= rast_tab
[index
].triangle
;
600 tnl
->Driver
.Render
.Quad
= rast_tab
[index
].quad
;
603 tnl
->Driver
.Render
.PrimTabVerts
= i810_render_tab_verts
;
604 tnl
->Driver
.Render
.PrimTabElts
= i810_render_tab_elts
;
605 tnl
->Driver
.Render
.ClippedLine
= line
; /* from tritmp.h */
606 tnl
->Driver
.Render
.ClippedPolygon
= i810FastRenderClippedPoly
;
608 tnl
->Driver
.Render
.PrimTabVerts
= _tnl_render_tab_verts
;
609 tnl
->Driver
.Render
.PrimTabElts
= _tnl_render_tab_elts
;
610 tnl
->Driver
.Render
.ClippedLine
= i810RenderClippedLine
;
611 tnl
->Driver
.Render
.ClippedPolygon
= i810RenderClippedPoly
;
616 static const GLenum reduced_prim
[GL_POLYGON
+1] = {
630 /**********************************************************************/
631 /* High level hooks for t_vb_render.c */
632 /**********************************************************************/
636 /* Determine the rasterized primitive when not drawing unfilled
639 * Used only for the default render stage which always decomposes
640 * primitives to trianges/lines/points. For the accelerated stage,
641 * which renders strips as strips, the equivalent calculations are
642 * performed in i810render.c.
644 static void i810RenderPrimitive( GLcontext
*ctx
, GLenum prim
)
646 i810ContextPtr imesa
= I810_CONTEXT(ctx
);
647 GLuint rprim
= reduced_prim
[prim
];
649 imesa
->render_primitive
= prim
;
651 if (rprim
== GL_TRIANGLES
&& (ctx
->_TriangleCaps
& DD_TRI_UNFILLED
))
654 if (imesa
->reduced_primitive
!= rprim
||
655 hw_prim
[prim
] != imesa
->hw_primitive
) {
656 i810RasterPrimitive( ctx
, rprim
, hw_prim
[prim
] );
660 static void i810RunPipeline( GLcontext
*ctx
)
662 i810ContextPtr imesa
= I810_CONTEXT(ctx
);
664 if (imesa
->new_state
) {
665 if (imesa
->new_state
& _NEW_TEXTURE
)
666 i810UpdateTextureState( ctx
); /* may modify imesa->new_state */
668 if (!imesa
->Fallback
) {
669 if (imesa
->new_state
& _I810_NEW_VERTEX
)
670 i810ChooseVertexState( ctx
);
672 if (imesa
->new_state
& _I810_NEW_RENDERSTATE
)
673 i810ChooseRenderState( ctx
);
676 imesa
->new_state
= 0;
679 _tnl_run_pipeline( ctx
);
682 static void i810RenderStart( GLcontext
*ctx
)
684 /* Check for projective textureing. Make sure all texcoord
685 * pointers point to something. (fix in mesa?)
687 i810CheckTexSizes( ctx
);
690 static void i810RenderFinish( GLcontext
*ctx
)
692 if (I810_CONTEXT(ctx
)->RenderIndex
& I810_FALLBACK_BIT
)
693 _swrast_flush( ctx
);
699 /* System to flush dma and emit state changes based on the rasterized
702 void i810RasterPrimitive( GLcontext
*ctx
,
706 i810ContextPtr imesa
= I810_CONTEXT(ctx
);
707 GLuint st1
= imesa
->Setup
[I810_CTXREG_ST1
];
708 GLuint aa
= imesa
->Setup
[I810_CTXREG_AA
];
709 GLuint lcs
= imesa
->Setup
[I810_CTXREG_LCS
];
714 if (I810_DEBUG
& DEBUG_PRIMS
) {
715 /* Prints reduced prim, and hw prim */
716 char *prim_name
= "Unknown";
723 prim_name
= "LineStrip";
726 prim_name
= "Triangles";
729 prim_name
= "TriStrip_0";
732 prim_name
= "TriFan";
735 prim_name
= "Polygons";
741 fprintf(stderr
, "%s : rprim(%s), hwprim(%s)\n",
743 _mesa_lookup_enum_by_nr(rprim
),
749 if (ctx
->Polygon
.StippleFlag
)
751 if (ctx
->Polygon
.SmoothFlag
)
755 lcs
&= ~(LCS_LINEWIDTH_3_0
|LCS_LINEWIDTH_0_5
);
756 lcs
|= imesa
->LcsLineWidth
;
757 if (ctx
->Line
.SmoothFlag
) {
759 lcs
|= LCS_LINEWIDTH_0_5
;
763 lcs
&= ~(LCS_LINEWIDTH_3_0
|LCS_LINEWIDTH_0_5
);
764 lcs
|= imesa
->LcsPointSize
;
765 if (ctx
->Point
.SmoothFlag
) {
767 lcs
|= LCS_LINEWIDTH_0_5
;
774 imesa
->reduced_primitive
= rprim
;
776 if (st1
!= imesa
->Setup
[I810_CTXREG_ST1
] ||
777 aa
!= imesa
->Setup
[I810_CTXREG_AA
] ||
778 lcs
!= imesa
->Setup
[I810_CTXREG_LCS
])
780 I810_STATECHANGE(imesa
, I810_UPLOAD_CTX
);
781 imesa
->hw_primitive
= hwprim
;
782 imesa
->Setup
[I810_CTXREG_LCS
] = lcs
;
783 imesa
->Setup
[I810_CTXREG_ST1
] = st1
;
784 imesa
->Setup
[I810_CTXREG_AA
] = aa
;
786 else if (hwprim
!= imesa
->hw_primitive
) {
787 I810_STATECHANGE(imesa
, 0);
788 imesa
->hw_primitive
= hwprim
;
792 /**********************************************************************/
793 /* Transition to/from hardware rasterization. */
794 /**********************************************************************/
795 static char *fallbackStrings
[] = {
807 static char *getFallbackString(GLuint bit
)
814 return fallbackStrings
[i
];
817 void i810Fallback( i810ContextPtr imesa
, GLuint bit
, GLboolean mode
)
819 GLcontext
*ctx
= imesa
->glCtx
;
820 TNLcontext
*tnl
= TNL_CONTEXT(ctx
);
821 GLuint oldfallback
= imesa
->Fallback
;
823 if (0) fprintf(stderr
, "%s old %x bit %x mode %d\n", __FUNCTION__
,
824 imesa
->Fallback
, bit
, mode
);
827 imesa
->Fallback
|= bit
;
828 if (oldfallback
== 0) {
829 I810_FIREVERTICES(imesa
);
830 if (I810_DEBUG
& DEBUG_FALLBACKS
)
831 fprintf(stderr
, "ENTER FALLBACK %s\n", getFallbackString( bit
));
832 _swsetup_Wakeup( ctx
);
833 imesa
->RenderIndex
= ~0;
837 imesa
->Fallback
&= ~bit
;
838 if (oldfallback
== bit
) {
839 _swrast_flush( ctx
);
840 if (I810_DEBUG
& DEBUG_FALLBACKS
)
841 fprintf(stderr
, "LEAVE FALLBACK %s\n", getFallbackString( bit
));
842 tnl
->Driver
.Render
.Start
= i810RenderStart
;
843 tnl
->Driver
.Render
.PrimitiveNotify
= i810RenderPrimitive
;
844 tnl
->Driver
.Render
.Finish
= i810RenderFinish
;
845 tnl
->Driver
.Render
.BuildVertices
= i810BuildVertices
;
846 imesa
->new_state
|= (_I810_NEW_RENDERSTATE
|_I810_NEW_VERTEX
);
852 /**********************************************************************/
853 /* Initialization. */
854 /**********************************************************************/
857 void i810InitTriFuncs( GLcontext
*ctx
)
859 TNLcontext
*tnl
= TNL_CONTEXT(ctx
);
860 static int firsttime
= 1;
867 tnl
->Driver
.RunPipeline
= i810RunPipeline
;
868 tnl
->Driver
.Render
.Start
= i810RenderStart
;
869 tnl
->Driver
.Render
.Finish
= i810RenderFinish
;
870 tnl
->Driver
.Render
.PrimitiveNotify
= i810RenderPrimitive
;
871 tnl
->Driver
.Render
.ResetLineStipple
= _swrast_ResetLineStipple
;
872 tnl
->Driver
.Render
.BuildVertices
= i810BuildVertices
;