[Mesa-dev] [PATCH] llvmpipe: (trivial) get rid of triangle subdivision code
Zack Rusin
zackr at vmware.com
Thu Dec 12 20:34:02 PST 2013
Ah, good stuff, very sensual and does not need more cowbell.
Reviewed-by: Zack Rusin <zackr at vmware.com>
----- Original Message -----
> From: Roland Scheidegger <sroland at vmware.com>
>
> This code was always problematic, and with 64bit rasterization we no longer
> need it at all.
> ---
> src/gallium/drivers/llvmpipe/lp_setup.c | 8 +-
> src/gallium/drivers/llvmpipe/lp_setup_context.h | 1 -
> src/gallium/drivers/llvmpipe/lp_setup_tri.c | 174
> -----------------------
> 3 files changed, 1 insertion(+), 182 deletions(-)
>
> diff --git a/src/gallium/drivers/llvmpipe/lp_setup.c
> b/src/gallium/drivers/llvmpipe/lp_setup.c
> index 49962af..2fad469 100644
> --- a/src/gallium/drivers/llvmpipe/lp_setup.c
> +++ b/src/gallium/drivers/llvmpipe/lp_setup.c
> @@ -1081,14 +1081,8 @@ try_update_scene_state( struct lp_setup_context *setup
> )
> &setup->draw_regions[i]);
> }
> }
> - /*
> - * Subdivide triangles if the framebuffer is larger than the
> - * MAX_FIXED_LENGTH.
> - */
> - setup->subdivide_large_triangles = (setup->fb.width > MAX_FIXED_LENGTH
> ||
> - setup->fb.height >
> MAX_FIXED_LENGTH);
> }
> -
> +
> setup->dirty = 0;
>
> assert(setup->fs.stored);
> diff --git a/src/gallium/drivers/llvmpipe/lp_setup_context.h
> b/src/gallium/drivers/llvmpipe/lp_setup_context.h
> index 8bb95c1..b3fb24a 100644
> --- a/src/gallium/drivers/llvmpipe/lp_setup_context.h
> +++ b/src/gallium/drivers/llvmpipe/lp_setup_context.h
> @@ -93,7 +93,6 @@ struct lp_setup_context
> struct llvmpipe_query *active_queries[LP_MAX_ACTIVE_BINNED_QUERIES];
> unsigned active_binned_queries;
>
> - boolean subdivide_large_triangles;
> boolean flatshade_first;
> boolean ccw_is_frontface;
> boolean scissor_test;
> diff --git a/src/gallium/drivers/llvmpipe/lp_setup_tri.c
> b/src/gallium/drivers/llvmpipe/lp_setup_tri.c
> index e22f14c..ce3a0a7 100644
> --- a/src/gallium/drivers/llvmpipe/lp_setup_tri.c
> +++ b/src/gallium/drivers/llvmpipe/lp_setup_tri.c
> @@ -921,168 +921,6 @@ rotate_fixed_position_12( struct fixed_position*
> position )
> }
>
>
> -typedef void (*triangle_func_t)(struct lp_setup_context *setup,
> - const float (*v0)[4],
> - const float (*v1)[4],
> - const float (*v2)[4]);
> -
> -
> -/**
> - * Subdivide this triangle by bisecting edge (v0, v1).
> - * \param pv the provoking vertex (must = v0 or v1 or v2)
> - * TODO: should probably think about non-overflowing arithmetic elsewhere.
> - * This will definitely screw with pipeline counters for instance.
> - */
> -static void
> -subdiv_tri(struct lp_setup_context *setup,
> - const float (*v0)[4],
> - const float (*v1)[4],
> - const float (*v2)[4],
> - const float (*pv)[4],
> - triangle_func_t tri)
> -{
> - unsigned n = setup->fs.current.variant->shader->info.base.num_inputs + 1;
> - const struct lp_shader_input *inputs =
> - setup->fs.current.variant->shader->inputs;
> - PIPE_ALIGN_VAR(LP_MIN_VECTOR_ALIGN) float vmid[PIPE_MAX_ATTRIBS][4];
> - const float (*vm)[4] = (const float (*)[4]) vmid;
> - unsigned i;
> - float w0, w1, wm;
> - boolean flatshade = setup->fs.current.variant->key.flatshade;
> -
> - /* find position midpoint (attrib[0] = position) */
> - vmid[0][0] = 0.5f * (v1[0][0] + v0[0][0]);
> - vmid[0][1] = 0.5f * (v1[0][1] + v0[0][1]);
> - vmid[0][2] = 0.5f * (v1[0][2] + v0[0][2]);
> - vmid[0][3] = 0.5f * (v1[0][3] + v0[0][3]);
> -
> - w0 = v0[0][3];
> - w1 = v1[0][3];
> - wm = vmid[0][3];
> -
> - /* interpolate other attributes */
> - for (i = 1; i < n; i++) {
> - if ((inputs[i - 1].interp == LP_INTERP_COLOR && flatshade) ||
> - inputs[i - 1].interp == LP_INTERP_CONSTANT) {
> - /* copy the provoking vertex's attribute */
> - vmid[i][0] = pv[i][0];
> - vmid[i][1] = pv[i][1];
> - vmid[i][2] = pv[i][2];
> - vmid[i][3] = pv[i][3];
> - }
> - else {
> - /* interpolate with perspective correction (for linear too) */
> - vmid[i][0] = 0.5f * (v1[i][0] * w1 + v0[i][0] * w0) / wm;
> - vmid[i][1] = 0.5f * (v1[i][1] * w1 + v0[i][1] * w0) / wm;
> - vmid[i][2] = 0.5f * (v1[i][2] * w1 + v0[i][2] * w0) / wm;
> - vmid[i][3] = 0.5f * (v1[i][3] * w1 + v0[i][3] * w0) / wm;
> - }
> - }
> -
> - /* handling flat shading and first vs. last provoking vertex is a
> - * little tricky...
> - */
> - if (pv == v0) {
> - if (setup->flatshade_first) {
> - /* first vertex must be v0 or vm */
> - tri(setup, v0, vm, v2);
> - tri(setup, vm, v1, v2);
> - }
> - else {
> - /* last vertex must be v0 or vm */
> - tri(setup, vm, v2, v0);
> - tri(setup, v1, v2, vm);
> - }
> - }
> - else if (pv == v1) {
> - if (setup->flatshade_first) {
> - tri(setup, vm, v2, v0);
> - tri(setup, v1, v2, vm);
> - }
> - else {
> - tri(setup, v2, v0, vm);
> - tri(setup, v2, vm, v1);
> - }
> - }
> - else {
> - if (setup->flatshade_first) {
> - tri(setup, v2, v0, vm);
> - tri(setup, v2, vm, v1);
> - }
> - else {
> - tri(setup, v0, vm, v2);
> - tri(setup, vm, v1, v2);
> - }
> - }
> -}
> -
> -
> -/**
> - * Check the lengths of the edges of the triangle. If any edge is too
> - * long, subdivide the longest edge and draw two sub-triangles.
> - * Note: this may be called recursively.
> - * \return TRUE if triangle was subdivided, FALSE otherwise
> - */
> -static boolean
> -check_subdivide_triangle(struct lp_setup_context *setup,
> - const float (*v0)[4],
> - const float (*v1)[4],
> - const float (*v2)[4],
> - triangle_func_t tri)
> -{
> - const float maxLen = (float) MAX_FIXED_LENGTH; /* longest permissible
> edge, in pixels */
> - float dx10, dy10, len10;
> - float dx21, dy21, len21;
> - float dx02, dy02, len02;
> - const float (*pv)[4] = setup->flatshade_first ? v0 : v2;
> -
> - /* compute lengths of triangle edges, squared */
> - dx10 = v1[0][0] - v0[0][0];
> - dy10 = v1[0][1] - v0[0][1];
> - len10 = dx10 * dx10 + dy10 * dy10;
> -
> - dx21 = v2[0][0] - v1[0][0];
> - dy21 = v2[0][1] - v1[0][1];
> - len21 = dx21 * dx21 + dy21 * dy21;
> -
> - dx02 = v0[0][0] - v2[0][0];
> - dy02 = v0[0][1] - v2[0][1];
> - len02 = dx02 * dx02 + dy02 * dy02;
> -
> - /* Look for longest the edge that's longer than maxLen. If we find
> - * such an edge, split the triangle using the midpoint of that edge.
> - * Note: it's important to split the longest edge, not just any edge
> - * that's longer than maxLen. Otherwise, we can get into a degenerate
> - * situation and recurse indefinitely.
> - */
> - if (len10 > maxLen * maxLen &&
> - len10 >= len21 &&
> - len10 >= len02) {
> - /* subdivide v0, v1 edge */
> - subdiv_tri(setup, v0, v1, v2, pv, tri);
> - return TRUE;
> - }
> -
> - if (len21 > maxLen * maxLen &&
> - len21 >= len10 &&
> - len21 >= len02) {
> - /* subdivide v1, v2 edge */
> - subdiv_tri(setup, v1, v2, v0, pv, tri);
> - return TRUE;
> - }
> -
> - if (len02 > maxLen * maxLen &&
> - len02 >= len21 &&
> - len02 >= len10) {
> - /* subdivide v2, v0 edge */
> - subdiv_tri(setup, v2, v0, v1, pv, tri);
> - return TRUE;
> - }
> -
> - return FALSE;
> -}
> -
> -
> /**
> * Draw triangle if it's CW, cull otherwise.
> */
> @@ -1093,10 +931,6 @@ static void triangle_cw( struct lp_setup_context
> *setup,
> {
> struct fixed_position position;
>
> - if (setup->subdivide_large_triangles &&
> - check_subdivide_triangle(setup, v0, v1, v2, triangle_cw))
> - return;
> -
> calc_fixed_position(setup, &position, v0, v1, v2);
>
> if (position.area < 0) {
> @@ -1118,10 +952,6 @@ static void triangle_ccw( struct lp_setup_context
> *setup,
> {
> struct fixed_position position;
>
> - if (setup->subdivide_large_triangles &&
> - check_subdivide_triangle(setup, v0, v1, v2, triangle_ccw))
> - return;
> -
> calc_fixed_position(setup, &position, v0, v1, v2);
>
> if (position.area > 0)
> @@ -1139,10 +969,6 @@ static void triangle_both( struct lp_setup_context
> *setup,
> struct fixed_position position;
> struct llvmpipe_context *lp_context = (struct llvmpipe_context
> *)setup->pipe;
>
> - if (setup->subdivide_large_triangles &&
> - check_subdivide_triangle(setup, v0, v1, v2, triangle_both))
> - return;
> -
> if (lp_context->active_statistics_queries &&
> !llvmpipe_rasterization_disabled(lp_context)) {
> lp_context->pipeline_statistics.c_primitives++;
> --
> 1.7.9.5
>
More information about the mesa-dev
mailing list