const struct util_format_description *desc =
util_format_description(ptex->format);
bool is_depth, is_stencil;
- int r, i;
+ int r;
+ unsigned i, bpe, flags = 0;
is_depth = util_format_has_depth(desc);
is_stencil = util_format_has_stencil(desc);
- surface->npix_x = ptex->width0;
- surface->npix_y = ptex->height0;
- surface->npix_z = ptex->depth0;
- surface->blk_w = util_format_get_blockwidth(ptex->format);
- surface->blk_h = util_format_get_blockheight(ptex->format);
- surface->blk_d = 1;
- surface->array_size = 1;
- surface->last_level = ptex->last_level;
-
if (rscreen->chip_class >= EVERGREEN && !is_flushed_depth &&
ptex->format == PIPE_FORMAT_Z32_FLOAT_S8X24_UINT) {
- surface->bpe = 4; /* stencil is allocated separately on evergreen */
+ bpe = 4; /* stencil is allocated separately on evergreen */
} else {
- surface->bpe = util_format_get_blocksize(ptex->format);
+ bpe = util_format_get_blocksize(ptex->format);
/* align byte per element on dword */
- if (surface->bpe == 3) {
- surface->bpe = 4;
+ if (bpe == 3) {
+ bpe = 4;
}
}
- surface->nsamples = ptex->nr_samples ? ptex->nr_samples : 1;
- surface->flags = RADEON_SURF_SET(array_mode, MODE);
-
- switch (ptex->target) {
- case PIPE_TEXTURE_1D:
- surface->flags |= RADEON_SURF_SET(RADEON_SURF_TYPE_1D, TYPE);
- break;
- case PIPE_TEXTURE_RECT:
- case PIPE_TEXTURE_2D:
- surface->flags |= RADEON_SURF_SET(RADEON_SURF_TYPE_2D, TYPE);
- break;
- case PIPE_TEXTURE_3D:
- surface->flags |= RADEON_SURF_SET(RADEON_SURF_TYPE_3D, TYPE);
- break;
- case PIPE_TEXTURE_1D_ARRAY:
- surface->flags |= RADEON_SURF_SET(RADEON_SURF_TYPE_1D_ARRAY, TYPE);
- surface->array_size = ptex->array_size;
- break;
- case PIPE_TEXTURE_CUBE_ARRAY: /* cube array layout like 2d array */
- assert(ptex->array_size % 6 == 0);
- case PIPE_TEXTURE_2D_ARRAY:
- surface->flags |= RADEON_SURF_SET(RADEON_SURF_TYPE_2D_ARRAY, TYPE);
- surface->array_size = ptex->array_size;
- break;
- case PIPE_TEXTURE_CUBE:
- surface->flags |= RADEON_SURF_SET(RADEON_SURF_TYPE_CUBEMAP, TYPE);
- break;
- case PIPE_BUFFER:
- default:
- return -EINVAL;
- }
-
if (!is_flushed_depth && is_depth) {
- surface->flags |= RADEON_SURF_ZBUFFER;
+ flags |= RADEON_SURF_ZBUFFER;
if (tc_compatible_htile &&
array_mode == RADEON_SURF_MODE_2D) {
* Promote Z16 to Z32. DB->CB copies will convert
* the format for transfers.
*/
- surface->bpe = 4;
- surface->flags |= RADEON_SURF_TC_COMPATIBLE_HTILE;
- }
-
- if (is_stencil) {
- surface->flags |= RADEON_SURF_SBUFFER |
- RADEON_SURF_HAS_SBUFFER_MIPTREE;
+ bpe = 4;
+ flags |= RADEON_SURF_TC_COMPATIBLE_HTILE;
}
- }
- if (rscreen->chip_class >= SI) {
- surface->flags |= RADEON_SURF_HAS_TILE_MODE_INDEX;
+ if (is_stencil)
+ flags |= RADEON_SURF_SBUFFER;
}
if (rscreen->chip_class >= VI &&
(ptex->flags & R600_RESOURCE_FLAG_DISABLE_DCC ||
ptex->format == PIPE_FORMAT_R9G9B9E5_FLOAT))
- surface->flags |= RADEON_SURF_DISABLE_DCC;
+ flags |= RADEON_SURF_DISABLE_DCC;
if (ptex->bind & PIPE_BIND_SCANOUT || is_scanout) {
/* This should catch bugs in gallium users setting incorrect flags. */
ptex->array_size == 1 &&
ptex->depth0 == 1 &&
ptex->last_level == 0 &&
- !(surface->flags & RADEON_SURF_Z_OR_SBUFFER));
+ !(flags & RADEON_SURF_Z_OR_SBUFFER));
- surface->flags |= RADEON_SURF_SCANOUT;
+ flags |= RADEON_SURF_SCANOUT;
}
if (is_imported)
- surface->flags |= RADEON_SURF_IMPORTED;
+ flags |= RADEON_SURF_IMPORTED;
- r = rscreen->ws->surface_init(rscreen->ws, surface);
+ r = rscreen->ws->surface_init(rscreen->ws, ptex, flags, bpe,
+ array_mode, surface);
if (r) {
return r;
}
/* old ddx on evergreen over estimate alignment for 1d, only 1 level
* for those
*/
- surface->level[0].nblk_x = pitch_in_bytes_override / surface->bpe;
+ surface->level[0].nblk_x = pitch_in_bytes_override / bpe;
surface->level[0].pitch_bytes = pitch_in_bytes_override;
surface->level[0].slice_size = pitch_in_bytes_override * surface->level[0].nblk_y;
}
struct r600_fmask_info *out)
{
/* FMASK is allocated like an ordinary texture. */
- struct radeon_surf fmask = rtex->surface;
+ struct pipe_resource templ = rtex->resource.b.b;
+ struct radeon_surf fmask = {};
+ unsigned flags, bpe;
memset(out, 0, sizeof(*out));
- fmask.bo_alignment = 0;
- fmask.bo_size = 0;
- fmask.nsamples = 1;
- fmask.flags |= RADEON_SURF_FMASK;
+ templ.nr_samples = 1;
+ flags = rtex->surface.flags | RADEON_SURF_FMASK;
- /* Force 2D tiling if it wasn't set. This may occur when creating
- * FMASK for MSAA resolve on R6xx. On R6xx, the single-sample
- * destination buffer must have an FMASK too. */
- fmask.flags = RADEON_SURF_CLR(fmask.flags, MODE);
- fmask.flags |= RADEON_SURF_SET(RADEON_SURF_MODE_2D, MODE);
-
- if (rscreen->chip_class >= SI) {
- fmask.flags |= RADEON_SURF_HAS_TILE_MODE_INDEX;
- }
+ /* Use the same parameters and tile mode. */
+ fmask.bankw = rtex->surface.bankw;
+ fmask.bankh = rtex->surface.bankh;
+ fmask.mtilea = rtex->surface.mtilea;
+ fmask.tile_split = rtex->surface.tile_split;
switch (nr_samples) {
case 2:
case 4:
- fmask.bpe = 1;
+ bpe = 1;
if (rscreen->chip_class <= CAYMAN) {
fmask.bankh = 4;
}
break;
case 8:
- fmask.bpe = 4;
+ bpe = 4;
break;
default:
R600_ERR("Invalid sample count for FMASK allocation.\n");
* This can be fixed by writing a separate FMASK allocator specifically
* for R600-R700 asics. */
if (rscreen->chip_class <= R700) {
- fmask.bpe *= 2;
+ bpe *= 2;
}
- if (rscreen->ws->surface_init(rscreen->ws, &fmask)) {
+ if (rscreen->ws->surface_init(rscreen->ws, &templ, flags, bpe,
+ RADEON_SURF_MODE_2D, &fmask)) {
R600_ERR("Got error in surface_init while allocating FMASK.\n");
return;
}
out->tile_mode_index = fmask.tiling_index[0];
out->pitch_in_pixels = fmask.level[0].nblk_x;
out->bank_height = fmask.bankh;
- out->alignment = MAX2(256, fmask.bo_alignment);
- out->size = fmask.bo_size;
+ out->alignment = MAX2(256, fmask.surf_alignment);
+ out->size = fmask.surf_size;
}
static void r600_texture_allocate_fmask(struct r600_common_screen *rscreen,
p_atomic_inc(&rscreen->compressed_colortex_counter);
}
-static unsigned r600_texture_get_htile_size(struct r600_common_screen *rscreen,
- struct r600_texture *rtex)
+static void r600_texture_get_htile_size(struct r600_common_screen *rscreen,
+ struct r600_texture *rtex)
{
unsigned cl_width, cl_height, width, height;
unsigned slice_elements, slice_bytes, pipe_interleave_bytes, base_align;
unsigned num_pipes = rscreen->info.num_tile_pipes;
+ rtex->surface.htile_size = 0;
+
if (rscreen->chip_class <= EVERGREEN &&
rscreen->info.drm_major == 2 && rscreen->info.drm_minor < 26)
- return 0;
+ return;
/* HW bug on R6xx. */
if (rscreen->chip_class == R600 &&
- (rtex->surface.level[0].npix_x > 7680 ||
- rtex->surface.level[0].npix_y > 7680))
- return 0;
+ (rtex->resource.b.b.width0 > 7680 ||
+ rtex->resource.b.b.height0 > 7680))
+ return;
/* HTILE is broken with 1D tiling on old kernels and CIK. */
if (rscreen->chip_class >= CIK &&
rtex->surface.level[0].mode == RADEON_SURF_MODE_1D &&
rscreen->info.drm_major == 2 && rscreen->info.drm_minor < 38)
- return 0;
+ return;
/* Overalign HTILE on P2 configs to work around GPU hangs in
* piglit/depthstencil-render-miplevels 585.
break;
default:
assert(0);
- return 0;
+ return;
}
width = align(rtex->resource.b.b.width0, cl_width * 8);
pipe_interleave_bytes = rscreen->info.pipe_interleave_bytes;
base_align = num_pipes * pipe_interleave_bytes;
- rtex->htile.pitch = width;
- rtex->htile.height = height;
- rtex->htile.xalign = cl_width * 8;
- rtex->htile.yalign = cl_height * 8;
- rtex->htile.alignment = base_align;
-
- return (util_max_layer(&rtex->resource.b.b, 0) + 1) *
+ rtex->surface.htile_alignment = base_align;
+ rtex->surface.htile_size =
+ (util_max_layer(&rtex->resource.b.b, 0) + 1) *
align(slice_bytes, base_align);
}
static void r600_texture_allocate_htile(struct r600_common_screen *rscreen,
struct r600_texture *rtex)
{
- uint64_t htile_size, alignment;
uint32_t clear_value;
if (rtex->tc_compatible_htile) {
- htile_size = rtex->surface.htile_size;
- alignment = rtex->surface.htile_alignment;
clear_value = 0x0000030F;
} else {
- htile_size = r600_texture_get_htile_size(rscreen, rtex);
- alignment = rtex->htile.alignment;
+ r600_texture_get_htile_size(rscreen, rtex);
clear_value = 0;
}
- if (!htile_size)
+ if (!rtex->surface.htile_size)
return;
rtex->htile_buffer = (struct r600_resource*)
- r600_aligned_buffer_create(&rscreen->b, PIPE_BIND_CUSTOM,
- PIPE_USAGE_DEFAULT,
- htile_size, alignment);
+ r600_aligned_buffer_create(&rscreen->b, PIPE_BIND_CUSTOM,
+ PIPE_USAGE_DEFAULT,
+ rtex->surface.htile_size,
+ rtex->surface.htile_alignment);
if (rtex->htile_buffer == NULL) {
/* this is not a fatal error as we can still keep rendering
* without htile buffer */
R600_ERR("Failed to create buffer object for htile buffer.\n");
} else {
r600_screen_clear_buffer(rscreen, &rtex->htile_buffer->b.b,
- 0, htile_size, clear_value,
- R600_COHERENCY_NONE);
+ 0, rtex->surface.htile_size,
+ clear_value, R600_COHERENCY_NONE);
}
}
int i;
fprintf(f, " Info: npix_x=%u, npix_y=%u, npix_z=%u, blk_w=%u, "
- "blk_h=%u, blk_d=%u, array_size=%u, last_level=%u, "
+ "blk_h=%u, array_size=%u, last_level=%u, "
"bpe=%u, nsamples=%u, flags=0x%x, %s\n",
- rtex->surface.npix_x, rtex->surface.npix_y,
- rtex->surface.npix_z, rtex->surface.blk_w,
- rtex->surface.blk_h, rtex->surface.blk_d,
- rtex->surface.array_size, rtex->surface.last_level,
- rtex->surface.bpe, rtex->surface.nsamples,
+ rtex->resource.b.b.width0, rtex->resource.b.b.height0,
+ rtex->resource.b.b.depth0, rtex->surface.blk_w,
+ rtex->surface.blk_h,
+ rtex->resource.b.b.array_size, rtex->resource.b.b.last_level,
+ rtex->surface.bpe, rtex->resource.b.b.nr_samples,
rtex->surface.flags, util_format_short_name(rtex->resource.b.b.format));
- fprintf(f, " Layout: size=%"PRIu64", alignment=%"PRIu64", bankw=%u, "
+ fprintf(f, " Layout: size=%"PRIu64", alignment=%u, bankw=%u, "
"bankh=%u, nbanks=%u, mtilea=%u, tilesplit=%u, pipeconfig=%u, scanout=%u\n",
- rtex->surface.bo_size, rtex->surface.bo_alignment, rtex->surface.bankw,
+ rtex->surface.surf_size, rtex->surface.surf_alignment, rtex->surface.bankw,
rtex->surface.bankh, rtex->surface.num_banks, rtex->surface.mtilea,
rtex->surface.tile_split, rtex->surface.pipe_config,
(rtex->surface.flags & RADEON_SURF_SCANOUT) != 0);
rtex->cmask.yalign, rtex->cmask.slice_tile_max);
if (rtex->htile_buffer)
- fprintf(f, " HTile: size=%u, alignment=%u, pitch=%u, height=%u, "
- "xalign=%u, yalign=%u, TC_compatible = %u\n",
+ fprintf(f, " HTile: size=%u, alignment=%u, TC_compatible = %u\n",
rtex->htile_buffer->b.b.width0,
- rtex->htile_buffer->buf->alignment, rtex->htile.pitch,
- rtex->htile.height, rtex->htile.xalign, rtex->htile.yalign,
+ rtex->htile_buffer->buf->alignment,
rtex->tc_compatible_htile);
if (rtex->dcc_offset) {
- fprintf(f, " DCC: offset=%"PRIu64", size=%"PRIu64", alignment=%"PRIu64"\n",
+ fprintf(f, " DCC: offset=%"PRIu64", size=%"PRIu64", alignment=%u\n",
rtex->dcc_offset, rtex->surface.dcc_size,
rtex->surface.dcc_alignment);
for (i = 0; i <= rtex->resource.b.b.last_level; i++)
for (i = 0; i <= rtex->resource.b.b.last_level; i++)
fprintf(f, " Level[%i]: offset=%"PRIu64", slice_size=%"PRIu64", "
"npix_x=%u, npix_y=%u, npix_z=%u, nblk_x=%u, nblk_y=%u, "
- "nblk_z=%u, pitch_bytes=%u, mode=%u\n",
+ "pitch_bytes=%u, mode=%u, tiling_index = %u\n",
i, rtex->surface.level[i].offset,
rtex->surface.level[i].slice_size,
u_minify(rtex->resource.b.b.width0, i),
u_minify(rtex->resource.b.b.depth0, i),
rtex->surface.level[i].nblk_x,
rtex->surface.level[i].nblk_y,
- rtex->surface.level[i].nblk_z,
rtex->surface.level[i].pitch_bytes,
- rtex->surface.level[i].mode);
+ rtex->surface.level[i].mode,
+ rtex->surface.tiling_index[i]);
if (rtex->surface.flags & RADEON_SURF_SBUFFER) {
fprintf(f, " StencilLayout: tilesplit=%u\n",
fprintf(f, " StencilLevel[%i]: offset=%"PRIu64", "
"slice_size=%"PRIu64", npix_x=%u, "
"npix_y=%u, npix_z=%u, nblk_x=%u, nblk_y=%u, "
- "nblk_z=%u, pitch_bytes=%u, mode=%u\n",
+ "pitch_bytes=%u, mode=%u, tiling_index = %u\n",
i, rtex->surface.stencil_level[i].offset,
rtex->surface.stencil_level[i].slice_size,
u_minify(rtex->resource.b.b.width0, i),
u_minify(rtex->resource.b.b.depth0, i),
rtex->surface.stencil_level[i].nblk_x,
rtex->surface.stencil_level[i].nblk_y,
- rtex->surface.stencil_level[i].nblk_z,
rtex->surface.stencil_level[i].pitch_bytes,
- rtex->surface.stencil_level[i].mode);
+ rtex->surface.stencil_level[i].mode,
+ rtex->surface.stencil_tiling_index[i]);
}
}
}
rtex->is_depth = util_format_has_depth(util_format_description(rtex->resource.b.b.format));
rtex->surface = *surface;
- rtex->size = rtex->surface.bo_size;
+ rtex->size = rtex->surface.surf_size;
rtex->tc_compatible_htile = rtex->surface.htile_size != 0;
assert(!!(rtex->surface.flags & RADEON_SURF_TC_COMPATIBLE_HTILE) ==
/* Now create the backing buffer. */
if (!buf) {
r600_init_resource_fields(rscreen, resource, rtex->size,
- rtex->surface.bo_alignment);
+ rtex->surface.surf_alignment);
resource->flags |= RADEON_FLAG_HANDLE;