diff --git a/.pick_status.json b/.pick_status.json index b84d7091e77..49e8badc1b6 100644 --- a/.pick_status.json +++ b/.pick_status.json @@ -10345,7 +10345,7 @@ "description": "etnaviv: use linear PE rendering only on properly aligned surfaces", "nominated": true, "nomination_type": 1, - "resolution": 0, + "resolution": 1, "main_sha": null, "because_sha": "53445284a427f79e94607dc4ca2f8bd8ac293356" }, diff --git a/src/gallium/drivers/etnaviv/etnaviv_resource.c b/src/gallium/drivers/etnaviv/etnaviv_resource.c index 6ad02dda152..7fc07a7e414 100644 --- a/src/gallium/drivers/etnaviv/etnaviv_resource.c +++ b/src/gallium/drivers/etnaviv/etnaviv_resource.c @@ -101,7 +101,9 @@ etna_screen_resource_alloc_ts(struct pipe_screen *pscreen, * the size of the resource might also determine if we want to use it or not */ if (VIV_FEATURE(screen, chipMinorFeatures6, CACHE128B256BPERLINE) && - ts_compress_fmt >= 0) + ts_compress_fmt >= 0 && + (rsc->layout != ETNA_LAYOUT_LINEAR || + rsc->levels[0].stride % 256 == 0) ) ts_mode = TS_MODE_256B; ts_layer_stride = align(DIV_ROUND_UP(rsc->levels[0].layer_stride, diff --git a/src/gallium/drivers/etnaviv/etnaviv_surface.c b/src/gallium/drivers/etnaviv/etnaviv_surface.c index fa2d152ee5a..bdcf099e087 100644 --- a/src/gallium/drivers/etnaviv/etnaviv_surface.c +++ b/src/gallium/drivers/etnaviv/etnaviv_surface.c @@ -41,19 +41,24 @@ #include "drm-uapi/drm_fourcc.h" static struct etna_resource * -etna_render_handle_incompatible(struct pipe_context *pctx, struct pipe_resource *prsc) +etna_render_handle_incompatible(struct pipe_context *pctx, + struct pipe_resource *prsc, + unsigned int level) { struct etna_context *ctx = etna_context(pctx); struct etna_screen *screen = ctx->screen; struct etna_resource *res = etna_resource(prsc); bool need_multitiled = screen->specs.pixel_pipes > 1 && !screen->specs.single_buffer; bool want_supertiled = screen->specs.can_supertile; + unsigned int min_tilesize = etna_screen_get_tile_size(screen, TS_MODE_128B); /* Resource is compatible if it is tiled or PE is able to render to linear * and has multi tiling when required. */ if ((res->layout != ETNA_LAYOUT_LINEAR || - VIV_FEATURE(screen, chipMinorFeatures2, LINEAR_PE)) && + (VIV_FEATURE(screen, chipMinorFeatures2, LINEAR_PE) && + (!VIV_FEATURE(screen, chipFeatures, FAST_CLEAR) || + res->levels[level].stride % min_tilesize == 0))) && (!need_multitiled || (res->layout & ETNA_LAYOUT_BIT_MULTI))) return res; @@ -81,16 +86,16 @@ etna_create_surface(struct pipe_context *pctx, struct pipe_resource *prsc, { struct etna_context *ctx = etna_context(pctx); struct etna_screen *screen = ctx->screen; - struct etna_resource *rsc = etna_render_handle_incompatible(pctx, prsc); + unsigned layer = templat->u.tex.first_layer; + unsigned level = templat->u.tex.level; + struct etna_resource *rsc = etna_render_handle_incompatible(pctx, prsc, level); struct etna_surface *surf = CALLOC_STRUCT(etna_surface); if (!surf) return NULL; assert(templat->u.tex.first_layer == templat->u.tex.last_layer); - unsigned layer = templat->u.tex.first_layer; - unsigned level = templat->u.tex.level; - assert(layer < rsc->base.array_size); + assert(layer <= util_max_layer(prsc, level)); surf->base.context = pctx;