xref: /aosp_15_r20/external/mesa3d/src/gallium/drivers/llvmpipe/lp_state_sampler.c (revision 6104692788411f58d303aa86923a9ff6ecaded22)
1 /**************************************************************************
2  *
3  * Copyright 2007 VMware, Inc.
4  * All Rights Reserved.
5  *
6  * Permission is hereby granted, free of charge, to any person obtaining a
7  * copy of this software and associated documentation files (the
8  * "Software"), to deal in the Software without restriction, including
9  * without limitation the rights to use, copy, modify, merge, publish,
10  * distribute, sub license, and/or sell copies of the Software, and to
11  * permit persons to whom the Software is furnished to do so, subject to
12  * the following conditions:
13  *
14  * The above copyright notice and this permission notice (including the
15  * next paragraph) shall be included in all copies or substantial portions
16  * of the Software.
17  *
18  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
19  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
21  * IN NO EVENT SHALL VMWARE AND/OR ITS SUPPLIERS BE LIABLE FOR
22  * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
23  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
24  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
25  *
26  **************************************************************************/
27 
28 /* Authors:
29  *  Brian Paul
30  */
31 
32 #include "util/u_inlines.h"
33 #include "util/u_memory.h"
34 
35 #include "draw/draw_context.h"
36 
37 #include "lp_context.h"
38 #include "lp_screen.h"
39 #include "lp_state.h"
40 #include "lp_debug.h"
41 #include "frontend/sw_winsys.h"
42 #include "lp_flush.h"
43 
44 
45 static void *
llvmpipe_create_sampler_state(struct pipe_context * pipe,const struct pipe_sampler_state * sampler)46 llvmpipe_create_sampler_state(struct pipe_context *pipe,
47                               const struct pipe_sampler_state *sampler)
48 {
49    struct pipe_sampler_state *state = mem_dup(sampler, sizeof *sampler);
50 
51    if (LP_PERF & PERF_NO_MIP_LINEAR) {
52       if (state->min_mip_filter == PIPE_TEX_MIPFILTER_LINEAR)
53          state->min_mip_filter = PIPE_TEX_MIPFILTER_NEAREST;
54    }
55 
56    if (LP_PERF & PERF_NO_MIPMAPS)
57       state->min_mip_filter = PIPE_TEX_MIPFILTER_NONE;
58 
59    if (LP_PERF & PERF_NO_LINEAR) {
60       state->mag_img_filter = PIPE_TEX_FILTER_NEAREST;
61       state->min_img_filter = PIPE_TEX_FILTER_NEAREST;
62    }
63 
64    return state;
65 }
66 
67 
68 static void
llvmpipe_bind_sampler_states(struct pipe_context * pipe,enum pipe_shader_type shader,unsigned start,unsigned num,void ** samplers)69 llvmpipe_bind_sampler_states(struct pipe_context *pipe,
70                              enum pipe_shader_type shader,
71                              unsigned start,
72                              unsigned num,
73                              void **samplers)
74 {
75    struct llvmpipe_context *llvmpipe = llvmpipe_context(pipe);
76 
77    assert(shader < PIPE_SHADER_MESH_TYPES);
78    assert(start + num <= ARRAY_SIZE(llvmpipe->samplers[shader]));
79 
80    draw_flush(llvmpipe->draw);
81 
82    /* set the new samplers */
83    for (unsigned i = 0; i < num; i++) {
84       void *sampler = NULL;
85 
86       if (samplers && samplers[i])
87          sampler = samplers[i];
88       llvmpipe->samplers[shader][start + i] = sampler;
89    }
90 
91    /* find highest non-null samplers[] entry */
92    {
93       unsigned j = MAX2(llvmpipe->num_samplers[shader], start + num);
94       while (j > 0 && llvmpipe->samplers[shader][j - 1] == NULL)
95          j--;
96       llvmpipe->num_samplers[shader] = j;
97    }
98 
99    switch (shader) {
100    case PIPE_SHADER_VERTEX:
101    case PIPE_SHADER_GEOMETRY:
102    case PIPE_SHADER_TESS_CTRL:
103    case PIPE_SHADER_TESS_EVAL:
104       draw_set_samplers(llvmpipe->draw,
105                         shader,
106                         llvmpipe->samplers[shader],
107                         llvmpipe->num_samplers[shader]);
108       break;
109    case PIPE_SHADER_COMPUTE:
110       llvmpipe->cs_dirty |= LP_CSNEW_SAMPLER;
111       break;
112    case PIPE_SHADER_FRAGMENT:
113       llvmpipe->dirty |= LP_NEW_SAMPLER;
114       break;
115    case PIPE_SHADER_TASK:
116       llvmpipe->dirty |= LP_NEW_TASK_SAMPLER;
117       break;
118    case PIPE_SHADER_MESH:
119       llvmpipe->dirty |= LP_NEW_MESH_SAMPLER;
120       break;
121    default:
122       unreachable("Illegal shader type");
123       break;
124    }
125 }
126 
127 
128 static void
llvmpipe_set_sampler_views(struct pipe_context * pipe,enum pipe_shader_type shader,unsigned start,unsigned num,unsigned unbind_num_trailing_slots,bool take_ownership,struct pipe_sampler_view ** views)129 llvmpipe_set_sampler_views(struct pipe_context *pipe,
130                            enum pipe_shader_type shader,
131                            unsigned start,
132                            unsigned num,
133                            unsigned unbind_num_trailing_slots,
134                            bool take_ownership,
135                            struct pipe_sampler_view **views)
136 {
137    struct llvmpipe_context *llvmpipe = llvmpipe_context(pipe);
138    uint i;
139 
140    assert(num <= PIPE_MAX_SHADER_SAMPLER_VIEWS);
141 
142    assert(shader < PIPE_SHADER_MESH_TYPES);
143    assert(start + num <= ARRAY_SIZE(llvmpipe->sampler_views[shader]));
144 
145    draw_flush(llvmpipe->draw);
146 
147    /* set the new sampler views */
148    for (i = 0; i < num; i++) {
149       struct pipe_sampler_view *view = NULL;
150 
151       if (views && views[i])
152          view = views[i];
153 
154       /*
155        * Warn if someone tries to set a view created in a different context
156        * (which is why we need the hack above in the first place).
157        * An assert would be better but st/mesa relies on it...
158        */
159       if (view && view->context != pipe) {
160          debug_printf("Illegal setting of sampler_view %d created in another "
161                       "context\n", i);
162       }
163 
164       if (view)
165          llvmpipe_flush_resource(pipe, view->texture, 0, true, false, false, "sampler_view");
166 
167       if (take_ownership) {
168          pipe_sampler_view_reference(&llvmpipe->sampler_views[shader][start + i],
169                                      NULL);
170          llvmpipe->sampler_views[shader][start + i] = view;
171       } else {
172          pipe_sampler_view_reference(&llvmpipe->sampler_views[shader][start + i],
173                                      view);
174       }
175    }
176 
177    for (; i < num + unbind_num_trailing_slots; i++) {
178       pipe_sampler_view_reference(&llvmpipe->sampler_views[shader][start + i],
179                                   NULL);
180    }
181 
182    /* find highest non-null sampler_views[] entry */
183    {
184       unsigned j = MAX2(llvmpipe->num_sampler_views[shader], start + num);
185       while (j > 0 && llvmpipe->sampler_views[shader][j - 1] == NULL)
186          j--;
187       llvmpipe->num_sampler_views[shader] = j;
188    }
189 
190    switch (shader) {
191    case PIPE_SHADER_VERTEX:
192    case PIPE_SHADER_GEOMETRY:
193    case PIPE_SHADER_TESS_CTRL:
194    case PIPE_SHADER_TESS_EVAL:
195       draw_set_sampler_views(llvmpipe->draw,
196                              shader,
197                              llvmpipe->sampler_views[shader],
198                              llvmpipe->num_sampler_views[shader]);
199       break;
200    case PIPE_SHADER_COMPUTE:
201       llvmpipe->cs_dirty |= LP_CSNEW_SAMPLER_VIEW;
202       break;
203    case PIPE_SHADER_FRAGMENT:
204       llvmpipe->dirty |= LP_NEW_SAMPLER_VIEW;
205       lp_setup_set_fragment_sampler_views(llvmpipe->setup,
206                                           llvmpipe->num_sampler_views[PIPE_SHADER_FRAGMENT],
207                                           llvmpipe->sampler_views[PIPE_SHADER_FRAGMENT]);
208       break;
209    case PIPE_SHADER_TASK:
210       llvmpipe->dirty |= LP_NEW_TASK_SAMPLER_VIEW;
211       break;
212    case PIPE_SHADER_MESH:
213       llvmpipe->dirty |= LP_NEW_MESH_SAMPLER_VIEW;
214       break;
215    default:
216       unreachable("Illegal shader type");
217       break;
218    }
219 }
220 
221 
222 static struct pipe_sampler_view *
llvmpipe_create_sampler_view(struct pipe_context * pipe,struct pipe_resource * texture,const struct pipe_sampler_view * templ)223 llvmpipe_create_sampler_view(struct pipe_context *pipe,
224                             struct pipe_resource *texture,
225                             const struct pipe_sampler_view *templ)
226 {
227    struct pipe_sampler_view *view = CALLOC_STRUCT(pipe_sampler_view);
228    /*
229     * XXX: bind flags from OpenGL state tracker are notoriously unreliable.
230     * This looks unfixable, so fix the bind flags instead when it happens.
231     */
232    if (!(texture->bind & PIPE_BIND_SAMPLER_VIEW)) {
233       debug_printf("Illegal sampler view creation without bind flag\n");
234       texture->bind |= PIPE_BIND_SAMPLER_VIEW;
235    }
236 
237    if (view) {
238       *view = *templ;
239       view->reference.count = 1;
240       view->texture = NULL;
241       pipe_resource_reference(&view->texture, texture);
242       view->context = pipe;
243 
244 #if MESA_DEBUG
245      /*
246       * This is possibly too lenient, but the primary reason is just
247       * to catch gallium frontends which forget to initialize this, so
248       * it only catches clearly impossible view targets.
249       */
250       if (view->target != texture->target) {
251          if (view->target == PIPE_TEXTURE_1D)
252             assert(texture->target == PIPE_TEXTURE_1D_ARRAY);
253          else if (view->target == PIPE_TEXTURE_1D_ARRAY)
254             assert(texture->target == PIPE_TEXTURE_1D);
255          else if (view->target == PIPE_TEXTURE_2D)
256             assert(texture->target == PIPE_TEXTURE_2D_ARRAY ||
257                    texture->target == PIPE_TEXTURE_3D ||
258                    texture->target == PIPE_TEXTURE_CUBE ||
259                    texture->target == PIPE_TEXTURE_CUBE_ARRAY);
260          else if (view->target == PIPE_TEXTURE_2D_ARRAY)
261             assert(texture->target == PIPE_TEXTURE_2D ||
262                    texture->target == PIPE_TEXTURE_CUBE ||
263                    texture->target == PIPE_TEXTURE_CUBE_ARRAY);
264          else if (view->target == PIPE_TEXTURE_CUBE)
265             assert(texture->target == PIPE_TEXTURE_CUBE_ARRAY ||
266                    texture->target == PIPE_TEXTURE_2D_ARRAY);
267          else if (view->target == PIPE_TEXTURE_CUBE_ARRAY)
268             assert(texture->target == PIPE_TEXTURE_CUBE ||
269                    texture->target == PIPE_TEXTURE_2D_ARRAY);
270          else
271             assert(0);
272       }
273 #endif
274    }
275 
276    return view;
277 }
278 
279 
280 static void
llvmpipe_sampler_view_destroy(struct pipe_context * pipe,struct pipe_sampler_view * view)281 llvmpipe_sampler_view_destroy(struct pipe_context *pipe,
282                               struct pipe_sampler_view *view)
283 {
284    pipe_resource_reference(&view->texture, NULL);
285    FREE(view);
286 }
287 
288 
289 static void
llvmpipe_delete_sampler_state(struct pipe_context * pipe,void * sampler)290 llvmpipe_delete_sampler_state(struct pipe_context *pipe,
291                               void *sampler)
292 {
293    FREE(sampler);
294 }
295 
296 
297 static void
prepare_shader_sampling(struct llvmpipe_context * lp,unsigned num,struct pipe_sampler_view ** views,enum pipe_shader_type shader_type)298 prepare_shader_sampling(struct llvmpipe_context *lp,
299                         unsigned num,
300                         struct pipe_sampler_view **views,
301                         enum pipe_shader_type shader_type)
302 {
303    uint32_t row_stride[PIPE_MAX_TEXTURE_LEVELS];
304    uint32_t img_stride[PIPE_MAX_TEXTURE_LEVELS];
305    uint32_t mip_offsets[PIPE_MAX_TEXTURE_LEVELS];
306    const void *addr;
307 
308    assert(num <= PIPE_MAX_SHADER_SAMPLER_VIEWS);
309    if (!num)
310       return;
311 
312    for (unsigned i = 0; i < num; i++) {
313       struct pipe_sampler_view *view = i < num ? views[i] : NULL;
314 
315       if (view) {
316          struct pipe_resource *tex = view->texture;
317          struct llvmpipe_resource *lp_tex = llvmpipe_resource(tex);
318          unsigned width0 = tex->width0;
319          unsigned num_layers = tex->depth0;
320          unsigned first_level = 0;
321          unsigned last_level = 0;
322          unsigned sample_stride = 0;
323          unsigned num_samples = tex->nr_samples;
324 
325          if (!lp_tex->dt) {
326             /* regular texture - setup array of mipmap level offsets */
327             struct pipe_resource *res = view->texture;
328 
329             if (llvmpipe_resource_is_texture(res)) {
330                first_level = view->u.tex.first_level;
331                last_level = view->u.tex.last_level;
332                assert(first_level <= last_level);
333                assert(last_level <= res->last_level);
334                addr = lp_tex->tex_data;
335 
336                sample_stride = lp_tex->sample_stride;
337 
338                for (unsigned j = first_level; j <= last_level; j++) {
339                   mip_offsets[j] = lp_tex->mip_offsets[j];
340                   row_stride[j] = lp_tex->row_stride[j];
341                   img_stride[j] = lp_tex->img_stride[j];
342                }
343                if (tex->target == PIPE_TEXTURE_1D_ARRAY ||
344                    tex->target == PIPE_TEXTURE_2D_ARRAY ||
345                    tex->target == PIPE_TEXTURE_CUBE ||
346                    tex->target == PIPE_TEXTURE_CUBE_ARRAY) {
347                   num_layers = view->u.tex.last_layer - view->u.tex.first_layer + 1;
348                   for (unsigned j = first_level; j <= last_level; j++) {
349                      mip_offsets[j] += view->u.tex.first_layer *
350                                        lp_tex->img_stride[j];
351                   }
352                   if (view->target == PIPE_TEXTURE_CUBE ||
353                       view->target == PIPE_TEXTURE_CUBE_ARRAY) {
354                      assert(num_layers % 6 == 0);
355                   }
356                   assert(view->u.tex.first_layer <= view->u.tex.last_layer);
357                   assert(view->u.tex.last_layer < res->array_size);
358                }
359             } else {
360                unsigned view_blocksize = util_format_get_blocksize(view->format);
361                addr = lp_tex->data;
362                /* probably don't really need to fill that out */
363                mip_offsets[0] = 0;
364                row_stride[0] = 0;
365                img_stride[0] = 0;
366 
367                /* everything specified in number of elements here. */
368                width0 = view->u.buf.size / view_blocksize;
369                addr = (uint8_t *)addr + view->u.buf.offset;
370                assert(view->u.buf.offset + view->u.buf.size <= res->width0);
371             }
372          } else {
373             /* display target texture/surface */
374             addr = llvmpipe_resource_map(tex, 0, 0, LP_TEX_USAGE_READ);
375             row_stride[0] = lp_tex->row_stride[0];
376             img_stride[0] = lp_tex->img_stride[0];
377             mip_offsets[0] = 0;
378             assert(addr);
379          }
380          draw_set_mapped_texture(lp->draw,
381                                  shader_type,
382                                  i,
383                                  width0, tex->height0, num_layers,
384                                  first_level, last_level,
385                                  num_samples, sample_stride,
386                                  addr,
387                                  row_stride, img_stride, mip_offsets);
388       }
389    }
390 }
391 
392 
393 /**
394  * Called whenever we're about to draw (no dirty flag, FIXME?).
395  */
396 void
llvmpipe_prepare_vertex_sampling(struct llvmpipe_context * lp,unsigned num,struct pipe_sampler_view ** views)397 llvmpipe_prepare_vertex_sampling(struct llvmpipe_context *lp,
398                                  unsigned num,
399                                  struct pipe_sampler_view **views)
400 {
401    prepare_shader_sampling(lp, num, views, PIPE_SHADER_VERTEX);
402 }
403 
404 
405 /**
406  * Called whenever we're about to draw (no dirty flag, FIXME?).
407  */
408 void
llvmpipe_prepare_geometry_sampling(struct llvmpipe_context * lp,unsigned num,struct pipe_sampler_view ** views)409 llvmpipe_prepare_geometry_sampling(struct llvmpipe_context *lp,
410                                    unsigned num,
411                                    struct pipe_sampler_view **views)
412 {
413    prepare_shader_sampling(lp, num, views, PIPE_SHADER_GEOMETRY);
414 }
415 
416 
417 /**
418  * Called whenever we're about to draw (no dirty flag, FIXME?).
419  */
420 void
llvmpipe_prepare_tess_ctrl_sampling(struct llvmpipe_context * lp,unsigned num,struct pipe_sampler_view ** views)421 llvmpipe_prepare_tess_ctrl_sampling(struct llvmpipe_context *lp,
422                                     unsigned num,
423                                     struct pipe_sampler_view **views)
424 {
425    prepare_shader_sampling(lp, num, views, PIPE_SHADER_TESS_CTRL);
426 }
427 
428 
429 /**
430  * Called whenever we're about to draw (no dirty flag, FIXME?).
431  */
432 void
llvmpipe_prepare_tess_eval_sampling(struct llvmpipe_context * lp,unsigned num,struct pipe_sampler_view ** views)433 llvmpipe_prepare_tess_eval_sampling(struct llvmpipe_context *lp,
434                                     unsigned num,
435                                     struct pipe_sampler_view **views)
436 {
437    prepare_shader_sampling(lp, num, views, PIPE_SHADER_TESS_EVAL);
438 }
439 
440 
441 void
llvmpipe_cleanup_stage_sampling(struct llvmpipe_context * ctx,enum pipe_shader_type stage)442 llvmpipe_cleanup_stage_sampling(struct llvmpipe_context *ctx,
443                                 enum pipe_shader_type stage)
444 {
445    assert(ctx);
446    assert(stage < ARRAY_SIZE(ctx->num_sampler_views));
447    assert(stage < ARRAY_SIZE(ctx->sampler_views));
448 
449    unsigned num = ctx->num_sampler_views[stage];
450    struct pipe_sampler_view **views = ctx->sampler_views[stage];
451 
452    assert(num <= PIPE_MAX_SHADER_SAMPLER_VIEWS);
453 
454    for (unsigned i = 0; i < num; i++) {
455       struct pipe_sampler_view *view = views[i];
456       if (view) {
457          struct pipe_resource *tex = view->texture;
458          if (tex)
459             llvmpipe_resource_unmap(tex, 0, 0);
460       }
461    }
462 }
463 
464 
465 static void
prepare_shader_images(struct llvmpipe_context * lp,unsigned num,struct pipe_image_view * views,enum pipe_shader_type shader_type)466 prepare_shader_images(struct llvmpipe_context *lp,
467                       unsigned num,
468                       struct pipe_image_view *views,
469                       enum pipe_shader_type shader_type)
470 {
471    assert(num <= PIPE_MAX_SHADER_SAMPLER_VIEWS);
472    if (!num)
473       return;
474 
475    for (unsigned i = 0; i < num; i++) {
476       struct pipe_image_view *view = i < num ? &views[i] : NULL;
477 
478       if (view) {
479          struct pipe_resource *img = view->resource;
480          struct llvmpipe_resource *lp_img = llvmpipe_resource(img);
481          if (!img)
482             continue;
483 
484          unsigned width = img->width0;
485          unsigned height = img->height0;
486          unsigned num_layers = img->depth0;
487          unsigned num_samples = img->nr_samples;
488 
489          width = u_minify(width, view->u.tex.level);
490          height = u_minify(height, view->u.tex.level);
491 
492          uint32_t row_stride;
493          uint32_t img_stride;
494          uint32_t sample_stride;
495          const void *addr;
496 
497          if (!lp_img->dt) {
498             /* regular texture - setup array of mipmap level offsets */
499             struct pipe_resource *res = view->resource;
500 
501             if (llvmpipe_resource_is_texture(res)) {
502                uint32_t mip_offset = lp_img->mip_offsets[view->u.tex.level];
503                addr = lp_img->tex_data;
504 
505                if (img->target == PIPE_TEXTURE_1D_ARRAY ||
506                    img->target == PIPE_TEXTURE_2D_ARRAY ||
507                    img->target == PIPE_TEXTURE_3D ||
508                    img->target == PIPE_TEXTURE_CUBE ||
509                    img->target == PIPE_TEXTURE_CUBE_ARRAY) {
510                   num_layers = view->u.tex.last_layer -
511                                view->u.tex.first_layer + 1;
512                   assert(view->u.tex.first_layer <= view->u.tex.last_layer);
513                   mip_offset += view->u.tex.first_layer *
514                                 lp_img->img_stride[view->u.tex.level];
515                }
516 
517                row_stride = lp_img->row_stride[view->u.tex.level];
518                img_stride = lp_img->img_stride[view->u.tex.level];
519                sample_stride = lp_img->sample_stride;
520                addr = (uint8_t *)addr + mip_offset;
521             } else {
522                unsigned view_blocksize =
523                   util_format_get_blocksize(view->format);
524                addr = lp_img->data;
525                /* probably don't really need to fill that out */
526                row_stride = 0;
527                img_stride = 0;
528                sample_stride = 0;
529 
530                /* everything specified in number of elements here. */
531                width = view->u.buf.size / view_blocksize;
532                addr = (uint8_t *)addr + view->u.buf.offset;
533                assert(view->u.buf.offset + view->u.buf.size <= res->width0);
534             }
535          } else {
536             /* display target texture/surface */
537             addr = llvmpipe_resource_map(img, 0, 0, LP_TEX_USAGE_READ);
538             row_stride = lp_img->row_stride[0];
539             img_stride = lp_img->img_stride[0];
540             sample_stride = 0;
541             assert(addr);
542          }
543          draw_set_mapped_image(lp->draw, shader_type, i,
544                                width, height, num_layers,
545                                addr, row_stride, img_stride,
546                                num_samples, sample_stride);
547       }
548    }
549 }
550 
551 
552 /**
553  * Called whenever we're about to draw (no dirty flag, FIXME?).
554  */
555 void
llvmpipe_prepare_vertex_images(struct llvmpipe_context * lp,unsigned num,struct pipe_image_view * views)556 llvmpipe_prepare_vertex_images(struct llvmpipe_context *lp,
557                                unsigned num,
558                                struct pipe_image_view *views)
559 {
560    prepare_shader_images(lp, num, views, PIPE_SHADER_VERTEX);
561 }
562 
563 
564 /**
565  * Called whenever we're about to draw (no dirty flag, FIXME?).
566  */
567 void
llvmpipe_prepare_geometry_images(struct llvmpipe_context * lp,unsigned num,struct pipe_image_view * views)568 llvmpipe_prepare_geometry_images(struct llvmpipe_context *lp,
569                                  unsigned num,
570                                  struct pipe_image_view *views)
571 {
572    prepare_shader_images(lp, num, views, PIPE_SHADER_GEOMETRY);
573 }
574 
575 
576 /**
577  * Called whenever we're about to draw (no dirty flag, FIXME?).
578  */
579 void
llvmpipe_prepare_tess_ctrl_images(struct llvmpipe_context * lp,unsigned num,struct pipe_image_view * views)580 llvmpipe_prepare_tess_ctrl_images(struct llvmpipe_context *lp,
581                                   unsigned num,
582                                   struct pipe_image_view *views)
583 {
584    prepare_shader_images(lp, num, views, PIPE_SHADER_TESS_CTRL);
585 }
586 
587 
588 /**
589  * Called whenever we're about to draw (no dirty flag, FIXME?).
590  */
591 void
llvmpipe_prepare_tess_eval_images(struct llvmpipe_context * lp,unsigned num,struct pipe_image_view * views)592 llvmpipe_prepare_tess_eval_images(struct llvmpipe_context *lp,
593                                   unsigned num,
594                                   struct pipe_image_view *views)
595 {
596    prepare_shader_images(lp, num, views, PIPE_SHADER_TESS_EVAL);
597 }
598 
599 
600 void
llvmpipe_cleanup_stage_images(struct llvmpipe_context * ctx,enum pipe_shader_type stage)601 llvmpipe_cleanup_stage_images(struct llvmpipe_context *ctx,
602                               enum pipe_shader_type stage)
603 {
604    assert(ctx);
605    assert(stage < ARRAY_SIZE(ctx->num_images));
606    assert(stage < ARRAY_SIZE(ctx->images));
607 
608    unsigned num = ctx->num_images[stage];
609    struct pipe_image_view *views = ctx->images[stage];
610 
611    assert(num <= LP_MAX_TGSI_SHADER_IMAGES);
612 
613    for (unsigned i = 0; i < num; i++) {
614       struct pipe_image_view *view = &views[i];
615       assert(view);
616       struct pipe_resource *img = view->resource;
617       if (img)
618          llvmpipe_resource_unmap(img, 0, 0);
619    }
620 }
621 
622 
623 void
llvmpipe_init_sampler_funcs(struct llvmpipe_context * llvmpipe)624 llvmpipe_init_sampler_funcs(struct llvmpipe_context *llvmpipe)
625 {
626    llvmpipe->pipe.create_sampler_state = llvmpipe_create_sampler_state;
627 
628    llvmpipe->pipe.bind_sampler_states = llvmpipe_bind_sampler_states;
629    llvmpipe->pipe.create_sampler_view = llvmpipe_create_sampler_view;
630    llvmpipe->pipe.set_sampler_views = llvmpipe_set_sampler_views;
631    llvmpipe->pipe.sampler_view_destroy = llvmpipe_sampler_view_destroy;
632    llvmpipe->pipe.delete_sampler_state = llvmpipe_delete_sampler_state;
633 }
634