panfrost: Dynamically allocate array of texture pointers
authorTomeu Vizoso <tomeu.vizoso@collabora.com>
Thu, 2 Jan 2020 10:24:19 +0000 (11:24 +0100)
committerAlyssa Rosenzweig <alyssa.rosenzweig@collabora.com>
Thu, 2 Jan 2020 17:41:02 +0000 (12:41 -0500)
With 3D textures we can have lots of layers, so better allocate it
dynamically at runtime.

Signed-off-by: Tomeu Vizoso <tomeu.vizoso@collabora.com>
Reviewed-by: Alyssa Rosenzweig <alyssa.rosenzweig@collabora.com>
src/gallium/drivers/panfrost/pan_context.c
src/panfrost/include/panfrost-job.h
src/panfrost/pandecode/decode.c

index 984294b0b29f493f948b7353a97c78991a34ee4d..3a8d21d1d8f349a9d0d0cb8fc3c74dabe132b8ec 100644 (file)
@@ -531,6 +531,8 @@ panfrost_upload_tex(
 
         struct pipe_sampler_view *pview = &view->base;
         struct panfrost_resource *rsrc = pan_resource(pview->texture);
+        mali_ptr descriptor_gpu;
+        void *descriptor;
 
         /* Do we interleave an explicit stride with every element? */
 
@@ -565,22 +567,38 @@ panfrost_upload_tex(
          * strides in that order */
 
         unsigned idx = 0;
+        unsigned levels = 1 + last_level - first_level;
+        unsigned layers = 1 + last_layer - first_layer;
+        unsigned num_elements = levels * layers;
+        if (has_manual_stride)
+                num_elements *= 2;
+
+        descriptor = malloc(sizeof(struct mali_texture_descriptor) +
+                            sizeof(mali_ptr) * num_elements);
+        memcpy(descriptor, &view->hw, sizeof(struct mali_texture_descriptor));
+
+        mali_ptr *pointers_and_strides = descriptor +
+                                         sizeof(struct mali_texture_descriptor);
 
         for (unsigned l = first_level; l <= last_level; ++l) {
                 for (unsigned f = first_layer; f <= last_layer; ++f) {
 
-                        view->hw.payload[idx++] =
+                        pointers_and_strides[idx++] =
                                 panfrost_get_texture_address(rsrc, l, f) + afbc_bit;
 
                         if (has_manual_stride) {
-                                view->hw.payload[idx++] =
+                                pointers_and_strides[idx++] =
                                         rsrc->slices[l].stride;
                         }
                 }
         }
 
-        return panfrost_upload_transient(batch, &view->hw,
-                                         sizeof(struct mali_texture_descriptor));
+        descriptor_gpu = panfrost_upload_transient(batch, descriptor,
+                                  sizeof(struct mali_texture_descriptor) +
+                                          num_elements * sizeof(*pointers_and_strides));
+        free(descriptor);
+
+        return descriptor_gpu;
 }
 
 static void
index 85dd2b40e1d874be2783144596c5553acd88f529..49c55f1f93ee9309d09e421a4105f6d5338f39bf 100644 (file)
@@ -1231,8 +1231,6 @@ struct mali_texture_descriptor {
         uint32_t unknown5;
         uint32_t unknown6;
         uint32_t unknown7;
-
-        mali_ptr payload[MAX_MIP_LEVELS * MAX_CUBE_FACES * MAX_ELEMENTS];
 } __attribute__((packed));
 
 /* filter_mode */
index 9f9de0f0fb6943418f663a5973d92e28832b05af..80b9a66978b979218707974ae60e024ada1d0983 100644 (file)
@@ -2018,6 +2018,8 @@ pandecode_texture(mali_ptr u,
         /* Miptree for each face */
         if (f.type == MALI_TEX_CUBE)
                 bitmap_count *= 6;
+        else if (f.type == MALI_TEX_3D)
+                bitmap_count *= t->depth;
 
         /* Array of textures */
         bitmap_count *= (t->array_size + 1);
@@ -2026,22 +2028,20 @@ pandecode_texture(mali_ptr u,
         if (f.manual_stride)
                 bitmap_count *= 2;
 
-        /* Sanity check the size */
-        int max_count = sizeof(t->payload) / sizeof(t->payload[0]);
-        assert (bitmap_count <= max_count);
-
+        mali_ptr *pointers_and_strides = pandecode_fetch_gpu_mem(tmem,
+                u + sizeof(*t), sizeof(mali_ptr) * bitmap_count);
         for (int i = 0; i < bitmap_count; ++i) {
                 /* How we dump depends if this is a stride or a pointer */
 
                 if (f.manual_stride && (i & 1)) {
                         /* signed 32-bit snuck in as a 64-bit pointer */
-                        uint64_t stride_set = t->payload[i];
+                        uint64_t stride_set = pointers_and_strides[i];
                         uint32_t clamped_stride = stride_set;
                         int32_t stride = clamped_stride;
                         assert(stride_set == clamped_stride);
                         pandecode_log("(mali_ptr) %d /* stride */, \n", stride);
                 } else {
-                        char *a = pointer_as_memory_reference(t->payload[i]);
+                        char *a = pointer_as_memory_reference(pointers_and_strides[i]);
                         pandecode_log("%s, \n", a);
                         free(a);
                 }