etnaviv: fill in layer_stride for imported resources
[mesa.git] / src / gallium / drivers / etnaviv / etnaviv_resource.c
index aefe65bf0e47e79466b2e9fd8f0af25914f59d7e..dfd0870711932bbff817cb6a11125d5c3bb73674 100644 (file)
@@ -52,7 +52,8 @@ etna_screen_resource_alloc_ts(struct pipe_screen *pscreen,
 
    /* TS only for level 0 -- XXX is this formula correct? */
    pixels = rsc->levels[0].layer_stride / util_format_get_blocksize(rsc->base.format);
-   ts_layer_stride = align(pixels * screen->specs.bits_per_tile / 0x80, 0x100);
+   ts_layer_stride = align(pixels * screen->specs.bits_per_tile / 0x80,
+                           0x100 * screen->specs.pixel_pipes);
    rt_ts_size = ts_layer_stride * rsc->base.array_size;
    if (rt_ts_size == 0)
       return true;
@@ -179,7 +180,7 @@ etna_resource_alloc(struct pipe_screen *pscreen, unsigned layout,
                         &paddingY, &halign);
    assert(paddingX && paddingY);
 
-   if (templat->bind != PIPE_BUFFER) {
+   if (templat->target != PIPE_BUFFER) {
       unsigned min_paddingY = 4 * screen->specs.pixel_pipes;
       if (paddingY < min_paddingY)
          paddingY = min_paddingY;
@@ -201,7 +202,10 @@ etna_resource_alloc(struct pipe_screen *pscreen, unsigned layout,
 
    size = setup_miptree(rsc, paddingX, paddingY, msaa_xscale, msaa_yscale);
 
-   struct etna_bo *bo = etna_bo_new(screen->dev, size, DRM_ETNA_GEM_CACHE_WC);
+   uint32_t flags = DRM_ETNA_GEM_CACHE_WC;
+   if (templat->bind & PIPE_BIND_VERTEX_BUFFER)
+      flags |= DRM_ETNA_GEM_FORCE_MMU;
+   struct etna_bo *bo = etna_bo_new(screen->dev, size, flags);
    if (unlikely(bo == NULL)) {
       BUG("Problem allocating video memory for resource");
       return NULL;
@@ -227,12 +231,9 @@ etna_resource_create(struct pipe_screen *pscreen,
 {
    struct etna_screen *screen = etna_screen(pscreen);
 
-   /* Figure out what tiling to use -- for now, assume that textures cannot be
-    * supertiled, and cannot be linear.
-    * There is a feature flag SUPERTILED_TEXTURE (not supported on any known hw)
-    * that may allow this, as well
-    * as LINEAR_TEXTURE_SUPPORT (supported on gc880 and gc2000 at least), but
-    * not sure how it works.
+   /* Figure out what tiling to use -- for now, assume that texture cannot be linear.
+    * there is a capability LINEAR_TEXTURE_SUPPORT (supported on gc880 and
+    * gc2000 at least), but not sure how it works.
     * Buffers always have LINEAR layout.
     */
    unsigned layout = ETNA_LAYOUT_LINEAR;
@@ -245,8 +246,14 @@ etna_resource_create(struct pipe_screen *pscreen,
       if (util_format_is_compressed(templat->format))
          layout = ETNA_LAYOUT_LINEAR;
    } else if (templat->target != PIPE_BUFFER) {
-      bool want_multitiled = screen->specs.pixel_pipes > 1;
-      bool want_supertiled = screen->specs.can_supertile && !DBG_ENABLED(ETNA_DBG_NO_SUPERTILE);
+      bool want_multitiled = false;
+      bool want_supertiled = screen->specs.can_supertile;
+
+      /* When this GPU supports single-buffer rendering, don't ever enable
+       * multi-tiling. This replicates the blob behavior on GC3000.
+       */
+      if (!screen->specs.single_buffer)
+         want_multitiled = screen->specs.pixel_pipes > 1;
 
       /* Keep single byte blocksized resources as tiled, since we
        * are unable to use the RS blit to de-tile them. However,
@@ -274,6 +281,14 @@ etna_resource_create(struct pipe_screen *pscreen,
    return etna_resource_alloc(pscreen, layout, templat);
 }
 
+static void
+etna_resource_changed(struct pipe_screen *pscreen, struct pipe_resource *prsc)
+{
+   struct etna_resource *res = etna_resource(prsc);
+
+   res->seqno++;
+}
+
 static void
 etna_resource_destroy(struct pipe_screen *pscreen, struct pipe_resource *prsc)
 {
@@ -286,7 +301,7 @@ etna_resource_destroy(struct pipe_screen *pscreen, struct pipe_resource *prsc)
       etna_bo_del(rsc->ts_bo);
 
    if (rsc->scanout)
-      renderonly_scanout_destroy(rsc->scanout);
+      renderonly_scanout_destroy(rsc->scanout, etna_screen(pscreen)->ro);
 
    list_delinit(&rsc->list);
 
@@ -325,6 +340,8 @@ etna_resource_from_handle(struct pipe_screen *pscreen,
    if (!rsc->bo)
       goto fail;
 
+   rsc->seqno = 1;
+
    level->width = tmpl->width0;
    level->height = tmpl->height0;
 
@@ -335,6 +352,8 @@ etna_resource_from_handle(struct pipe_screen *pscreen,
 
    level->padded_width = align(level->width, paddingX);
    level->padded_height = align(level->height, paddingY);
+   level->layer_stride = level->stride * util_format_get_nblocksy(prsc->format,
+                                                                  level->padded_height);
 
    /* The DDX must give us a BO which conforms to our padding size.
     * The stride of the BO must be greater or equal to our padded
@@ -384,7 +403,8 @@ etna_resource_get_handle(struct pipe_screen *pscreen,
 {
    struct etna_resource *rsc = etna_resource(prsc);
 
-   if (renderonly_get_handle(rsc->scanout, handle))
+   if (handle->type == DRM_API_HANDLE_TYPE_KMS &&
+       renderonly_get_handle(rsc->scanout, handle))
       return TRUE;
 
    return etna_screen_bo_get_handle(pscreen, rsc->bo, rsc->levels[0].stride,
@@ -411,22 +431,6 @@ etna_resource_used(struct etna_context *ctx, struct pipe_resource *prsc,
    rsc->pending_ctx = ctx;
 }
 
-void
-etna_resource_wait(struct pipe_context *pctx, struct etna_resource *rsc)
-{
-   if (rsc->status & ETNA_PENDING_WRITE) {
-      struct pipe_fence_handle *fence;
-      struct pipe_screen *pscreen = pctx->screen;
-
-      pctx->flush(pctx, &fence, 0);
-
-      if (!pscreen->fence_finish(pscreen, pctx, fence, 5000000000ULL))
-         BUG("fence timed out (hung GPU?)");
-
-      pscreen->fence_reference(pscreen, &fence, NULL);
-   }
-}
-
 void
 etna_resource_screen_init(struct pipe_screen *pscreen)
 {
@@ -434,5 +438,6 @@ etna_resource_screen_init(struct pipe_screen *pscreen)
    pscreen->resource_create = etna_resource_create;
    pscreen->resource_from_handle = etna_resource_from_handle;
    pscreen->resource_get_handle = etna_resource_get_handle;
+   pscreen->resource_changed = etna_resource_changed;
    pscreen->resource_destroy = etna_resource_destroy;
 }