summaryrefslogtreecommitdiffstats
path: root/src/gallium/drivers/iris
diff options
context:
space:
mode:
authorJason Ekstrand <[email protected]>2019-06-19 15:52:55 -0500
committerJason Ekstrand <[email protected]>2019-06-21 14:18:59 +0000
commit13f0c278c528167b14badf8172827412526d2160 (patch)
tree592493d070a1d615832386e4b8fba35e384f545e /src/gallium/drivers/iris
parent60c581b57d9ce5f56900cdbd6cd7f02d125f0635 (diff)
i965,iris: Move guardband calculations to a common location
Reviewed-by: Kenneth Graunke <[email protected]> Reviewed-by: Lionel Landwerlin <[email protected]>
Diffstat (limited to 'src/gallium/drivers/iris')
-rw-r--r--src/gallium/drivers/iris/iris_state.c89
1 files changed, 5 insertions, 84 deletions
diff --git a/src/gallium/drivers/iris/iris_state.c b/src/gallium/drivers/iris/iris_state.c
index 13942df5008..b8d76bc8e12 100644
--- a/src/gallium/drivers/iris/iris_state.c
+++ b/src/gallium/drivers/iris/iris_state.c
@@ -161,6 +161,7 @@ __gen_combine_address(struct iris_batch *batch, void *location,
#include "genxml/genX_pack.h"
#include "genxml/gen_macros.h"
#include "genxml/genX_bits.h"
+#include "intel/common/gen_guardband.h"
#if GEN_GEN == 8
#define MOCS_PTE 0x18
@@ -2347,86 +2348,6 @@ viewport_extent(const struct pipe_viewport_state *state, int axis, float sign)
return copysignf(state->scale[axis], sign) + state->translate[axis];
}
-static void
-calculate_guardband_size(uint32_t fb_width, uint32_t fb_height,
- float m00, float m11, float m30, float m31,
- float *xmin, float *xmax,
- float *ymin, float *ymax)
-{
- /* According to the "Vertex X,Y Clamping and Quantization" section of the
- * Strips and Fans documentation:
- *
- * "The vertex X and Y screen-space coordinates are also /clamped/ to the
- * fixed-point "guardband" range supported by the rasterization hardware"
- *
- * and
- *
- * "In almost all circumstances, if an object’s vertices are actually
- * modified by this clamping (i.e., had X or Y coordinates outside of
- * the guardband extent the rendered object will not match the intended
- * result. Therefore software should take steps to ensure that this does
- * not happen - e.g., by clipping objects such that they do not exceed
- * these limits after the Drawing Rectangle is applied."
- *
- * I believe the fundamental restriction is that the rasterizer (in
- * the SF/WM stages) have a limit on the number of pixels that can be
- * rasterized. We need to ensure any coordinates beyond the rasterizer
- * limit are handled by the clipper. So effectively that limit becomes
- * the clipper's guardband size.
- *
- * It goes on to say:
- *
- * "In addition, in order to be correctly rendered, objects must have a
- * screenspace bounding box not exceeding 8K in the X or Y direction.
- * This additional restriction must also be comprehended by software,
- * i.e., enforced by use of clipping."
- *
- * This makes no sense. Gen7+ hardware supports 16K render targets,
- * and you definitely need to be able to draw polygons that fill the
- * surface. Our assumption is that the rasterizer was limited to 8K
- * on Sandybridge, which only supports 8K surfaces, and it was actually
- * increased to 16K on Ivybridge and later.
- *
- * So, limit the guardband to 16K on Gen7+ and 8K on Sandybridge.
- */
- const float gb_size = GEN_GEN >= 7 ? 16384.0f : 8192.0f;
-
- if (m00 != 0 && m11 != 0) {
- /* First, we compute the screen-space render area */
- const float ss_ra_xmin = MIN3( 0, m30 + m00, m30 - m00);
- const float ss_ra_xmax = MAX3( fb_width, m30 + m00, m30 - m00);
- const float ss_ra_ymin = MIN3( 0, m31 + m11, m31 - m11);
- const float ss_ra_ymax = MAX3(fb_height, m31 + m11, m31 - m11);
-
- /* We want the guardband to be centered on that */
- const float ss_gb_xmin = (ss_ra_xmin + ss_ra_xmax) / 2 - gb_size;
- const float ss_gb_xmax = (ss_ra_xmin + ss_ra_xmax) / 2 + gb_size;
- const float ss_gb_ymin = (ss_ra_ymin + ss_ra_ymax) / 2 - gb_size;
- const float ss_gb_ymax = (ss_ra_ymin + ss_ra_ymax) / 2 + gb_size;
-
- /* Now we need it in native device coordinates */
- const float ndc_gb_xmin = (ss_gb_xmin - m30) / m00;
- const float ndc_gb_xmax = (ss_gb_xmax - m30) / m00;
- const float ndc_gb_ymin = (ss_gb_ymin - m31) / m11;
- const float ndc_gb_ymax = (ss_gb_ymax - m31) / m11;
-
- /* Thanks to Y-flipping and ORIGIN_UPPER_LEFT, the Y coordinates may be
- * flipped upside-down. X should be fine though.
- */
- assert(ndc_gb_xmin <= ndc_gb_xmax);
- *xmin = ndc_gb_xmin;
- *xmax = ndc_gb_xmax;
- *ymin = MIN2(ndc_gb_ymin, ndc_gb_ymax);
- *ymax = MAX2(ndc_gb_ymin, ndc_gb_ymax);
- } else {
- /* The viewport scales to 0, so nothing will be rendered. */
- *xmin = 0.0f;
- *xmax = 0.0f;
- *ymin = 0.0f;
- *ymax = 0.0f;
- }
-}
-
/**
* The pipe->set_viewport_states() driver hook.
*
@@ -4560,10 +4481,10 @@ iris_upload_dirty_render_state(struct iris_context *ice,
float vp_ymin = viewport_extent(state, 1, -1.0f);
float vp_ymax = viewport_extent(state, 1, 1.0f);
- calculate_guardband_size(cso_fb->width, cso_fb->height,
- state->scale[0], state->scale[1],
- state->translate[0], state->translate[1],
- &gb_xmin, &gb_xmax, &gb_ymin, &gb_ymax);
+ gen_calculate_guardband_size(cso_fb->width, cso_fb->height,
+ state->scale[0], state->scale[1],
+ state->translate[0], state->translate[1],
+ &gb_xmin, &gb_xmax, &gb_ymin, &gb_ymax);
iris_pack_state(GENX(SF_CLIP_VIEWPORT), vp_map, vp) {
vp.ViewportMatrixElementm00 = state->scale[0];