diff options
author | Lucas Stach <[email protected]> | 2017-06-09 18:23:16 +0200 |
---|---|---|
committer | Lucas Stach <[email protected]> | 2017-07-19 16:26:49 +0200 |
commit | c4818808991134cc7d7741c8f29dc50f6d2102a0 (patch) | |
tree | 79added36f8a71a9687360cb024988e5822e4fe8 /src/gallium/drivers/etnaviv | |
parent | a9fad437f7ad1c1a8c0a694c2d8b4b6ad4d32098 (diff) |
renderonly/etnaviv: stop importing resource from renderonly
The current way of importing the resource from renderonly after allocation
is opaque and is taking away control from the driver, which it needs in
order to implement more advanced scenarios than the simple linear scanout
with matching stride alignments.
Signed-off-by: Lucas Stach <[email protected]>
Reviewed-by: Christian Gmeiner <[email protected]>
Acked-by: Daniel Stone <[email protected]>
Diffstat (limited to 'src/gallium/drivers/etnaviv')
-rw-r--r-- | src/gallium/drivers/etnaviv/etnaviv_clear_blit.c | 8 | ||||
-rw-r--r-- | src/gallium/drivers/etnaviv/etnaviv_resource.c | 34 | ||||
-rw-r--r-- | src/gallium/drivers/etnaviv/etnaviv_resource.h | 5 |
3 files changed, 35 insertions, 12 deletions
diff --git a/src/gallium/drivers/etnaviv/etnaviv_clear_blit.c b/src/gallium/drivers/etnaviv/etnaviv_clear_blit.c index d9ff9624fa4..b832dd8f263 100644 --- a/src/gallium/drivers/etnaviv/etnaviv_clear_blit.c +++ b/src/gallium/drivers/etnaviv/etnaviv_clear_blit.c @@ -610,10 +610,10 @@ etna_flush_resource(struct pipe_context *pctx, struct pipe_resource *prsc) { struct etna_resource *rsc = etna_resource(prsc); - if (rsc->scanout) { - if (etna_resource_older(etna_resource(rsc->scanout->prime), rsc)) { - etna_copy_resource(pctx, rsc->scanout->prime, prsc, 0, 0); - etna_resource(rsc->scanout->prime)->seqno = rsc->seqno; + if (rsc->external) { + if (etna_resource_older(etna_resource(rsc->external), rsc)) { + etna_copy_resource(pctx, rsc->external, prsc, 0, 0); + etna_resource(rsc->external)->seqno = rsc->seqno; } } else if (etna_resource_needs_flush(rsc)) { etna_copy_resource(pctx, prsc, prsc, 0, 0); diff --git a/src/gallium/drivers/etnaviv/etnaviv_resource.c b/src/gallium/drivers/etnaviv/etnaviv_resource.c index a709482c1b6..8d96baf2a04 100644 --- a/src/gallium/drivers/etnaviv/etnaviv_resource.c +++ b/src/gallium/drivers/etnaviv/etnaviv_resource.c @@ -214,8 +214,20 @@ etna_resource_alloc(struct pipe_screen *pscreen, unsigned layout, rsc->bo = bo; rsc->ts_bo = 0; /* TS is only created when first bound to surface */ - if (templat->bind & PIPE_BIND_SCANOUT) - rsc->scanout = renderonly_scanout_for_resource(&rsc->base, screen->ro); + if (templat->bind & PIPE_BIND_SCANOUT) { + struct winsys_handle handle; + rsc->scanout = renderonly_scanout_for_resource(&rsc->base, screen->ro, + &handle); + if (!rsc->scanout) + goto free_rsc; + + rsc->external = pscreen->resource_from_handle(pscreen, &rsc->base, + &handle, + PIPE_HANDLE_USAGE_WRITE); + close(handle.handle); + if (!rsc->external) + goto free_rsc; + } if (DBG_ENABLED(ETNA_DBG_ZERO)) { void *map = etna_bo_map(bo); @@ -310,6 +322,7 @@ etna_resource_destroy(struct pipe_screen *pscreen, struct pipe_resource *prsc) list_delinit(&rsc->list); pipe_resource_reference(&rsc->texture, NULL); + pipe_resource_reference(&rsc->external, NULL); FREE(rsc); } @@ -379,16 +392,12 @@ etna_resource_from_handle(struct pipe_screen *pscreen, /* Render targets are linear in Xorg but must be tiled * here. It would be nice if dri_drawable_get_format() * set scanout for these buffers too. */ - struct etna_resource *tiled; ptiled = etna_resource_create(pscreen, tmpl); if (!ptiled) goto fail; - tiled = etna_resource(ptiled); - tiled->scanout = renderonly_scanout_for_prime(prsc, screen->ro); - if (!tiled->scanout) - goto fail; + etna_resource(ptiled)->external = prsc; return ptiled; } @@ -410,9 +419,18 @@ etna_resource_get_handle(struct pipe_screen *pscreen, struct winsys_handle *handle, unsigned usage) { struct etna_resource *rsc = etna_resource(prsc); + /* Scanout is always attached to the base resource */ + struct renderonly_scanout *scanout = rsc->scanout; + + /* + * External resources are preferred, so a import->export chain of + * render/sampler incompatible buffers yield the same handle. + */ + if (rsc->external) + rsc = etna_resource(rsc->external); if (handle->type == DRM_API_HANDLE_TYPE_KMS && - renderonly_get_handle(rsc->scanout, handle)) + renderonly_get_handle(scanout, handle)) return TRUE; return etna_screen_bo_get_handle(pscreen, rsc->bo, rsc->levels[0].stride, diff --git a/src/gallium/drivers/etnaviv/etnaviv_resource.h b/src/gallium/drivers/etnaviv/etnaviv_resource.h index 3507e5ccecb..5f563c06adc 100644 --- a/src/gallium/drivers/etnaviv/etnaviv_resource.h +++ b/src/gallium/drivers/etnaviv/etnaviv_resource.h @@ -75,6 +75,11 @@ struct etna_resource { /* When we are rendering to a texture, we need a differently tiled resource */ struct pipe_resource *texture; + /* + * If imported resources have an render/sampler incompatible tiling, we keep + * them as an external resource, which is blitted as needed. + */ + struct pipe_resource *external; enum etna_resource_status status; |