iris: fix some hangs around null framebuffers
authorDave Airlie <airlied@redhat.com>
Tue, 31 Jul 2018 00:33:35 +0000 (10:33 +1000)
committerKenneth Graunke <kenneth@whitecape.org>
Thu, 21 Feb 2019 18:26:08 +0000 (10:26 -0800)
This fixes some cases in fbo-none* and framebuffer_no_attachments.

I'm not sure this is correct otherwise, the tests don't all pass yet

No idea if this is in any way the correct answer

src/gallium/drivers/iris/iris_context.h
src/gallium/drivers/iris/iris_state.c

index 5aba49a2832e99ef6a75474523e144746ca9700c..7db903acbc3074d019894ca628b2242ee44127b6 100644 (file)
@@ -316,6 +316,8 @@ struct iris_context {
 
       struct iris_state_ref unbound_tex;
 
+      struct iris_state_ref null_fb;
+
       struct u_upload_mgr *surface_uploader;
       // XXX: may want a separate uploader for "hey I made a CSO!" vs
       // "I'm streaming this out at draw time and never want it again!"
index afe95d4f6fe6098e31729a4a2517a094aa19cb98..abbdcda97ca005a8cc32b1ca13c12973677d995b 100644 (file)
@@ -1448,6 +1448,12 @@ iris_set_framebuffer_state(struct pipe_context *ctx,
 
    isl_emit_depth_stencil_hiz_s(isl_dev, cso_z->packets, &info);
 
+   /* Make a null surface for unbound buffers */
+   void *null_surf_map =
+      upload_state(ice->state.surface_uploader, &ice->state.null_fb,
+                   4 * GENX(RENDER_SURFACE_STATE_length), 64);
+   isl_null_fill_state(&screen->isl_dev, null_surf_map, isl_extent3d(cso->width, cso->height, cso->layers ? cso->layers : 1));
+
    ice->state.dirty |= IRIS_DIRTY_DEPTH_BUFFER;
 
    /* Render target change */
@@ -2629,6 +2635,16 @@ use_null_surface(struct iris_batch *batch, struct iris_context *ice)
    return ice->state.unbound_tex.offset;
 }
 
+static uint32_t
+use_null_fb_surface(struct iris_batch *batch, struct iris_context *ice)
+{
+   struct iris_bo *state_bo = iris_resource_bo(ice->state.null_fb.res);
+
+   iris_use_pinned_bo(batch, state_bo, false);
+
+   return ice->state.null_fb.offset;
+}
+
 static uint32_t
 use_ssbo(struct iris_batch *batch, struct iris_context *ice,
          struct iris_shader_state *shs, int i)
@@ -2670,9 +2686,15 @@ iris_populate_binding_table(struct iris_context *ice,
 
    if (stage == MESA_SHADER_FRAGMENT) {
       struct pipe_framebuffer_state *cso_fb = &ice->state.framebuffer;
-      for (unsigned i = 0; i < cso_fb->nr_cbufs; i++) {
-         bt_map[s++] = use_surface(batch, cso_fb->cbufs[i], true);
-      }
+      if (cso_fb->nr_cbufs) {
+         for (unsigned i = 0; i < cso_fb->nr_cbufs; i++) {
+            if (cso_fb->cbufs[i])
+               bt_map[s++] = use_surface(batch, cso_fb->cbufs[i], true);
+            else
+               bt_map[s++] = use_null_fb_surface(batch, ice);
+         }
+      } else
+         bt_map[s++] = use_null_fb_surface(batch, ice);
    }
 
    //assert(prog_data->binding_table.texture_start ==