Go to the source code of this file.
Functions | |
static boolean | points (unsigned prim) |
static boolean | lines (unsigned prim) |
static boolean | triangles (unsigned prim) |
boolean | draw_need_pipeline (const struct draw_context *draw, const struct pipe_rasterizer_state *rasterizer, unsigned int prim) |
Default version of a function to check if we need any special pipeline stages, or whether prims/verts can go through untouched. | |
static struct draw_stage * | validate_pipeline (struct draw_stage *stage) |
Rebuild the rendering pipeline. | |
static void | validate_tri (struct draw_stage *stage, struct prim_header *header) |
static void | validate_line (struct draw_stage *stage, struct prim_header *header) |
static void | validate_point (struct draw_stage *stage, struct prim_header *header) |
static void | validate_reset_stipple_counter (struct draw_stage *stage) |
static void | validate_flush (struct draw_stage *stage, unsigned flags) |
static void | validate_destroy (struct draw_stage *stage) |
struct draw_stage * | draw_validate_stage (struct draw_context *draw) |
Create validate pipeline stage. |
boolean draw_need_pipeline | ( | const struct draw_context * | draw, | |
const struct pipe_rasterizer_state * | rasterizer, | |||
unsigned int | prim | |||
) |
Default version of a function to check if we need any special pipeline stages, or whether prims/verts can go through untouched.
Don't test for bypass clipping or vs modes, this function is just about the primitive pipeline stages.
This can be overridden by the driver.
Definition at line 64 of file draw_pipe_validate.c.
References draw_context::aaline, draw_context::aapoint, FALSE, pipe_rasterizer_state::fill_ccw, pipe_rasterizer_state::fill_cw, pipe_rasterizer_state::light_twoside, pipe_rasterizer_state::line_smooth, draw_context::line_stipple, pipe_rasterizer_state::line_stipple_enable, pipe_rasterizer_state::line_width, lines(), vbuf_render::need_pipeline, pipe_rasterizer_state::offset_ccw, pipe_rasterizer_state::offset_cw, PIPE_POLYGON_MODE_FILL, draw_context::pipeline, pipe_rasterizer_state::point_size, pipe_rasterizer_state::point_smooth, draw_context::point_sprite, pipe_rasterizer_state::point_sprite, points(), pipe_rasterizer_state::poly_stipple_enable, draw_context::pstipple, draw_context::render, triangles(), TRUE, draw_context::wide_line_threshold, and draw_context::wide_point_threshold.
00067 { 00068 /* If the driver has overridden this, use that version: 00069 */ 00070 if (draw->render && 00071 draw->render->need_pipeline) 00072 { 00073 return draw->render->need_pipeline( draw->render, 00074 rasterizer, 00075 prim ); 00076 } 00077 00078 /* Don't have to worry about triangles turning into lines/points 00079 * and triggering the pipeline, because we have to trigger the 00080 * pipeline *anyway* if unfilled mode is active. 00081 */ 00082 if (lines(prim)) 00083 { 00084 /* line stipple */ 00085 if (rasterizer->line_stipple_enable && draw->pipeline.line_stipple) 00086 return TRUE; 00087 00088 /* wide lines */ 00089 if (rasterizer->line_width > draw->pipeline.wide_line_threshold) 00090 return TRUE; 00091 00092 /* AA lines */ 00093 if (rasterizer->line_smooth && draw->pipeline.aaline) 00094 return TRUE; 00095 } 00096 00097 if (points(prim)) 00098 { 00099 /* large points */ 00100 if (rasterizer->point_size > draw->pipeline.wide_point_threshold) 00101 return TRUE; 00102 00103 /* AA points */ 00104 if (rasterizer->point_smooth && draw->pipeline.aapoint) 00105 return TRUE; 00106 00107 /* point sprites */ 00108 if (rasterizer->point_sprite && draw->pipeline.point_sprite) 00109 return TRUE; 00110 } 00111 00112 00113 if (triangles(prim)) 00114 { 00115 /* polygon stipple */ 00116 if (rasterizer->poly_stipple_enable && draw->pipeline.pstipple) 00117 return TRUE; 00118 00119 /* unfilled polygons */ 00120 if (rasterizer->fill_cw != PIPE_POLYGON_MODE_FILL || 00121 rasterizer->fill_ccw != PIPE_POLYGON_MODE_FILL) 00122 return TRUE; 00123 00124 /* polygon offset */ 00125 if (rasterizer->offset_cw || rasterizer->offset_ccw) 00126 return TRUE; 00127 00128 /* two-side lighting */ 00129 if (rasterizer->light_twoside) 00130 return TRUE; 00131 } 00132 00133 /* polygon cull - this is difficult - hardware can cull just fine 00134 * most of the time (though sometimes CULL_NEITHER is unsupported. 00135 * 00136 * Generally this isn't a reason to require the pipeline, though. 00137 * 00138 if (rasterizer->cull_mode) 00139 return TRUE; 00140 */ 00141 00142 return FALSE; 00143 }
struct draw_stage* draw_validate_stage | ( | struct draw_context * | draw | ) | [read] |
Create validate pipeline stage.
Definition at line 314 of file draw_pipe_validate.c.
References CALLOC_STRUCT, draw_stage::destroy, draw_stage::draw, draw_stage::flush, draw_stage::line, draw_stage::next, draw_stage::point, draw_stage::reset_stipple_counter, draw_stage::tri, validate_destroy(), validate_flush(), validate_line(), validate_point(), validate_reset_stipple_counter(), and validate_tri().
00315 { 00316 struct draw_stage *stage = CALLOC_STRUCT(draw_stage); 00317 if (stage == NULL) 00318 return NULL; 00319 00320 stage->draw = draw; 00321 stage->next = NULL; 00322 stage->point = validate_point; 00323 stage->line = validate_line; 00324 stage->tri = validate_tri; 00325 stage->flush = validate_flush; 00326 stage->reset_stipple_counter = validate_reset_stipple_counter; 00327 stage->destroy = validate_destroy; 00328 00329 return stage; 00330 }
static boolean lines | ( | unsigned | prim | ) | [static] |
Definition at line 43 of file draw_pipe_validate.c.
References PIPE_PRIM_LINE_LOOP, PIPE_PRIM_LINE_STRIP, and PIPE_PRIM_LINES.
00044 { 00045 return (prim == PIPE_PRIM_LINES || 00046 prim == PIPE_PRIM_LINE_STRIP || 00047 prim == PIPE_PRIM_LINE_LOOP); 00048 }
static boolean points | ( | unsigned | prim | ) | [static] |
Definition at line 38 of file draw_pipe_validate.c.
References PIPE_PRIM_POINTS.
00039 { 00040 return (prim == PIPE_PRIM_POINTS); 00041 }
static boolean triangles | ( | unsigned | prim | ) | [static] |
Definition at line 50 of file draw_pipe_validate.c.
References PIPE_PRIM_TRIANGLES.
00051 { 00052 return prim >= PIPE_PRIM_TRIANGLES; 00053 }
static void validate_destroy | ( | struct draw_stage * | stage | ) | [static] |
Definition at line 305 of file draw_pipe_validate.c.
References FREE.
00306 { 00307 FREE( stage ); 00308 }
static void validate_flush | ( | struct draw_stage * | stage, | |
unsigned | flags | |||
) | [static] |
Definition at line 295 of file draw_pipe_validate.c.
References draw_stage::flush, and draw_stage::next.
00297 { 00298 /* May need to pass a backend flush on to the rasterize stage. 00299 */ 00300 if (stage->next) 00301 stage->next->flush( stage->next, flags ); 00302 }
static void validate_line | ( | struct draw_stage * | stage, | |
struct prim_header * | header | |||
) | [static] |
Definition at line 275 of file draw_pipe_validate.c.
References draw_stage::line, and validate_pipeline().
00277 { 00278 struct draw_stage *pipeline = validate_pipeline( stage ); 00279 pipeline->line( pipeline, header ); 00280 }
static struct draw_stage* validate_pipeline | ( | struct draw_stage * | stage | ) | [static, read] |
Rebuild the rendering pipeline.
Definition at line 150 of file draw_pipe_validate.c.
References draw_context::aaline, draw_context::aapoint, draw_context::bypass_clipping, draw_context::clip, draw_context::cull, pipe_rasterizer_state::cull_mode, draw_stage::draw, draw, FALSE, pipe_rasterizer_state::fill_ccw, pipe_rasterizer_state::fill_cw, draw_context::first, draw_context::flatshade, pipe_rasterizer_state::flatshade, pipe_rasterizer_state::light_twoside, pipe_rasterizer_state::line_smooth, draw_context::line_stipple, pipe_rasterizer_state::line_stipple_enable, pipe_rasterizer_state::line_width, draw_stage::next, draw_context::offset, pipe_rasterizer_state::offset_ccw, pipe_rasterizer_state::offset_cw, PIPE_POLYGON_MODE_FILL, draw_context::pipeline, pipe_rasterizer_state::point_size, pipe_rasterizer_state::point_smooth, draw_context::point_sprite, pipe_rasterizer_state::point_sprite, pipe_rasterizer_state::poly_stipple_enable, draw_context::pstipple, draw_context::rasterize, draw_context::rasterizer, draw_context::stipple, TRUE, draw_context::twoside, draw_context::unfilled, draw_context::wide_line, draw_context::wide_line_threshold, draw_context::wide_point, and draw_context::wide_point_threshold.
00151 { 00152 struct draw_context *draw = stage->draw; 00153 struct draw_stage *next = draw->pipeline.rasterize; 00154 int need_det = 0; 00155 int precalc_flat = 0; 00156 boolean wide_lines, wide_points; 00157 00158 /* Set the validate's next stage to the rasterize stage, so that it 00159 * can be found later if needed for flushing. 00160 */ 00161 stage->next = next; 00162 00163 /* drawing wide lines? */ 00164 wide_lines = (draw->rasterizer->line_width > draw->pipeline.wide_line_threshold 00165 && !draw->rasterizer->line_smooth); 00166 00167 /* drawing large points? */ 00168 if (draw->rasterizer->point_sprite && draw->pipeline.point_sprite) 00169 wide_points = TRUE; 00170 else if (draw->rasterizer->point_smooth && draw->pipeline.aapoint) 00171 wide_points = FALSE; 00172 else if (draw->rasterizer->point_size > draw->pipeline.wide_point_threshold) 00173 wide_points = TRUE; 00174 else 00175 wide_points = FALSE; 00176 00177 /* 00178 * NOTE: we build up the pipeline in end-to-start order. 00179 * 00180 * TODO: make the current primitive part of the state and build 00181 * shorter pipelines for lines & points. 00182 */ 00183 00184 if (draw->rasterizer->line_smooth && draw->pipeline.aaline) { 00185 draw->pipeline.aaline->next = next; 00186 next = draw->pipeline.aaline; 00187 } 00188 00189 if (draw->rasterizer->point_smooth && draw->pipeline.aapoint) { 00190 draw->pipeline.aapoint->next = next; 00191 next = draw->pipeline.aapoint; 00192 } 00193 00194 if (wide_lines) { 00195 draw->pipeline.wide_line->next = next; 00196 next = draw->pipeline.wide_line; 00197 precalc_flat = 1; 00198 } 00199 00200 if (wide_points || draw->rasterizer->point_sprite) { 00201 draw->pipeline.wide_point->next = next; 00202 next = draw->pipeline.wide_point; 00203 } 00204 00205 if (draw->rasterizer->line_stipple_enable && draw->pipeline.line_stipple) { 00206 draw->pipeline.stipple->next = next; 00207 next = draw->pipeline.stipple; 00208 precalc_flat = 1; /* only needed for lines really */ 00209 } 00210 00211 if (draw->rasterizer->poly_stipple_enable 00212 && draw->pipeline.pstipple) { 00213 draw->pipeline.pstipple->next = next; 00214 next = draw->pipeline.pstipple; 00215 } 00216 00217 if (draw->rasterizer->fill_cw != PIPE_POLYGON_MODE_FILL || 00218 draw->rasterizer->fill_ccw != PIPE_POLYGON_MODE_FILL) { 00219 draw->pipeline.unfilled->next = next; 00220 next = draw->pipeline.unfilled; 00221 precalc_flat = 1; /* only needed for triangles really */ 00222 need_det = 1; 00223 } 00224 00225 if (draw->rasterizer->flatshade && precalc_flat) { 00226 draw->pipeline.flatshade->next = next; 00227 next = draw->pipeline.flatshade; 00228 } 00229 00230 if (draw->rasterizer->offset_cw || 00231 draw->rasterizer->offset_ccw) { 00232 draw->pipeline.offset->next = next; 00233 next = draw->pipeline.offset; 00234 need_det = 1; 00235 } 00236 00237 if (draw->rasterizer->light_twoside) { 00238 draw->pipeline.twoside->next = next; 00239 next = draw->pipeline.twoside; 00240 need_det = 1; 00241 } 00242 00243 /* Always run the cull stage as we calculate determinant there 00244 * also. 00245 * 00246 * This can actually be a win as culling out the triangles can lead 00247 * to less work emitting vertices, smaller vertex buffers, etc. 00248 * It's difficult to say whether this will be true in general. 00249 */ 00250 if (need_det || draw->rasterizer->cull_mode) { 00251 draw->pipeline.cull->next = next; 00252 next = draw->pipeline.cull; 00253 } 00254 00255 /* Clip stage 00256 */ 00257 if (!draw->bypass_clipping) 00258 { 00259 draw->pipeline.clip->next = next; 00260 next = draw->pipeline.clip; 00261 } 00262 00263 00264 draw->pipeline.first = next; 00265 return next; 00266 }
static void validate_point | ( | struct draw_stage * | stage, | |
struct prim_header * | header | |||
) | [static] |
Definition at line 282 of file draw_pipe_validate.c.
References draw_stage::point, and validate_pipeline().
00284 { 00285 struct draw_stage *pipeline = validate_pipeline( stage ); 00286 pipeline->point( pipeline, header ); 00287 }
static void validate_reset_stipple_counter | ( | struct draw_stage * | stage | ) | [static] |
Definition at line 289 of file draw_pipe_validate.c.
References draw_stage::reset_stipple_counter, and validate_pipeline().
00290 { 00291 struct draw_stage *pipeline = validate_pipeline( stage ); 00292 pipeline->reset_stipple_counter( pipeline ); 00293 }
static void validate_tri | ( | struct draw_stage * | stage, | |
struct prim_header * | header | |||
) | [static] |
Definition at line 268 of file draw_pipe_validate.c.
References draw_stage::tri, and validate_pipeline().
00270 { 00271 struct draw_stage *pipeline = validate_pipeline( stage ); 00272 pipeline->tri( pipeline, header ); 00273 }