diff options
author | Jason Ekstrand <[email protected]> | 2016-06-23 20:57:41 -0700 |
---|---|---|
committer | Jason Ekstrand <[email protected]> | 2016-08-17 14:46:22 -0700 |
commit | 90ab43d1bbb825cef6fe9acd04a1e8e18cddb372 (patch) | |
tree | d2d487145e439f9f3af8db71926c81b62d29a1f8 /src/mesa/drivers | |
parent | ba88a9622dbbad5bf2bca7858f91dcf192d7439b (diff) |
i965/blorp: Use ISL to compute image offsets
For the moment, we still call the old miptree function; we just assert that
the two are equal.
Reviewed-by: Topi Pohjolainen <[email protected]>
Diffstat (limited to 'src/mesa/drivers')
-rw-r--r-- | src/mesa/drivers/dri/i965/brw_blorp.c | 94 |
1 files changed, 91 insertions, 3 deletions
diff --git a/src/mesa/drivers/dri/i965/brw_blorp.c b/src/mesa/drivers/dri/i965/brw_blorp.c index ef256a76443..c8cb41ae5f9 100644 --- a/src/mesa/drivers/dri/i965/brw_blorp.c +++ b/src/mesa/drivers/dri/i965/brw_blorp.c @@ -32,6 +32,88 @@ #define FILE_DEBUG_FLAG DEBUG_BLORP +/** + * A variant of isl_surf_get_image_offset_sa() specific to gen6 stencil and + * HiZ surfaces. + */ +static void +get_image_offset_sa_gen6_stencil(const struct isl_surf *surf, + uint32_t level, uint32_t logical_array_layer, + uint32_t *x_offset_sa, + uint32_t *y_offset_sa) +{ + assert(surf->tiling == ISL_TILING_W || surf->format == ISL_FORMAT_HIZ); + assert(level < surf->levels); + assert(logical_array_layer < surf->logical_level0_px.array_len); + + const struct isl_extent3d image_align_sa = + isl_surf_get_image_alignment_sa(surf); + + const uint32_t W0 = surf->phys_level0_sa.width; + const uint32_t H0 = surf->phys_level0_sa.height; + + uint32_t x = 0, y = 0; + for (uint32_t l = 0; l < level; ++l) { + if (l == 1) { + uint32_t W = minify(W0, l); + + if (surf->samples > 1) { + assert(surf->msaa_layout == ISL_MSAA_LAYOUT_INTERLEAVED); + assert(surf->samples == 4); + W = ALIGN(W, 2) * 2; + } + + x += ALIGN(W, image_align_sa.w); + } else { + uint32_t H = minify(H0, l); + + if (surf->samples > 1) { + assert(surf->msaa_layout == ISL_MSAA_LAYOUT_INTERLEAVED); + assert(surf->samples == 4); + H = ALIGN(H, 2) * 2; + } + + y += ALIGN(H, image_align_sa.h) * surf->logical_level0_px.array_len; + } + } + + /* Now account for our location within the given LOD */ + uint32_t Hl = minify(H0, level); + if (surf->samples > 1) { + assert(surf->msaa_layout == ISL_MSAA_LAYOUT_INTERLEAVED); + assert(surf->samples == 4); + Hl = ALIGN(Hl, 2) * 2; + } + y += ALIGN(Hl, image_align_sa.h) * logical_array_layer; + + *x_offset_sa = x; + *y_offset_sa = y; +} + +static void +blorp_get_image_offset_sa(struct isl_device *dev, const struct isl_surf *surf, + uint32_t level, uint32_t layer, + uint32_t *x_offset_sa, + uint32_t *y_offset_sa) +{ + if (ISL_DEV_GEN(dev) == 6 && surf->tiling == ISL_TILING_W) { + get_image_offset_sa_gen6_stencil(surf, level, layer, + x_offset_sa, y_offset_sa); + } else { + /* Using base_array_layer for Z in 3-D surfaces is a bit abusive, but it + * will go away soon enough. + */ + uint32_t z = 0; + if (surf->dim == ISL_SURF_DIM_3D) { + z = layer; + layer = 0; + } + + isl_surf_get_image_offset_sa(surf, level, layer, z, + x_offset_sa, y_offset_sa); + } +} + void brw_blorp_surface_info_init(struct brw_context *brw, struct brw_blorp_surface_info *info, @@ -125,10 +207,16 @@ brw_blorp_surface_info_init(struct brw_context *brw, } uint32_t x_offset, y_offset; - intel_miptree_get_image_offset(mt, level, layer, &x_offset, &y_offset); + blorp_get_image_offset_sa(&brw->isl_dev, &info->surf, + level, layer / layer_multiplier, + &x_offset, &y_offset); + + uint32_t mt_x, mt_y; + intel_miptree_get_image_offset(mt, level, layer, &mt_x, &mt_y); + assert(mt_x == x_offset && mt_y == y_offset); - uint8_t bs = isl_format_get_layout(info->view.format)->bpb / 8; - isl_tiling_get_intratile_offset_el(&brw->isl_dev, info->surf.tiling, bs, + isl_tiling_get_intratile_offset_sa(&brw->isl_dev, info->surf.tiling, + info->view.format, info->surf.row_pitch, x_offset, y_offset, &info->bo_offset, &info->tile_x_sa, &info->tile_y_sa); |