1 /**************************************************************************
2  *
3  * Copyright 2006 Tungsten Graphics, Inc., Cedar Park, Texas.
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 TUNGSTEN GRAPHICS 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 #include <GL/gl.h>
29 #include <GL/internal/dri_interface.h>
30 
31 #include "intel_batchbuffer.h"
32 #include "intel_context.h"
33 #include "intel_mipmap_tree.h"
34 #include "intel_regions.h"
35 #include "intel_resolve_map.h"
36 #include "intel_span.h"
37 #include "intel_tex_layout.h"
38 #include "intel_tex.h"
39 #include "intel_blit.h"
40 
41 #ifndef I915
42 #include "brw_blorp.h"
43 #endif
44 
45 #include "main/enums.h"
46 #include "main/formats.h"
47 #include "main/glformats.h"
48 #include "main/texcompress_etc.h"
49 #include "main/teximage.h"
50 
51 #define FILE_DEBUG_FLAG DEBUG_MIPTREE
52 
53 static GLenum
target_to_target(GLenum target)54 target_to_target(GLenum target)
55 {
56    switch (target) {
57    case GL_TEXTURE_CUBE_MAP_POSITIVE_X_ARB:
58    case GL_TEXTURE_CUBE_MAP_NEGATIVE_X_ARB:
59    case GL_TEXTURE_CUBE_MAP_POSITIVE_Y_ARB:
60    case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y_ARB:
61    case GL_TEXTURE_CUBE_MAP_POSITIVE_Z_ARB:
62    case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z_ARB:
63       return GL_TEXTURE_CUBE_MAP_ARB;
64    default:
65       return target;
66    }
67 }
68 
69 /**
70  * @param for_region Indicates that the caller is
71  *        intel_miptree_create_for_region(). If true, then do not create
72  *        \c stencil_mt.
73  */
74 static struct intel_mipmap_tree *
intel_miptree_create_internal(struct intel_context * intel,GLenum target,gl_format format,GLuint first_level,GLuint last_level,GLuint width0,GLuint height0,GLuint depth0,bool for_region,GLuint num_samples,enum intel_msaa_layout msaa_layout)75 intel_miptree_create_internal(struct intel_context *intel,
76 			      GLenum target,
77 			      gl_format format,
78 			      GLuint first_level,
79 			      GLuint last_level,
80 			      GLuint width0,
81 			      GLuint height0,
82 			      GLuint depth0,
83 			      bool for_region,
84                               GLuint num_samples,
85                               enum intel_msaa_layout msaa_layout)
86 {
87    struct intel_mipmap_tree *mt = calloc(sizeof(*mt), 1);
88    int compress_byte = 0;
89 
90    DBG("%s target %s format %s level %d..%d <-- %p\n", __FUNCTION__,
91        _mesa_lookup_enum_by_nr(target),
92        _mesa_get_format_name(format),
93        first_level, last_level, mt);
94 
95    if (_mesa_is_format_compressed(format))
96       compress_byte = intel_compressed_num_bytes(format);
97 
98    mt->target = target_to_target(target);
99    mt->format = format;
100    mt->first_level = first_level;
101    mt->last_level = last_level;
102    mt->width0 = width0;
103    mt->height0 = height0;
104    mt->cpp = compress_byte ? compress_byte : _mesa_get_format_bytes(mt->format);
105    mt->num_samples = num_samples;
106    mt->compressed = compress_byte ? 1 : 0;
107    mt->msaa_layout = msaa_layout;
108    mt->refcount = 1;
109 
110    /* array_spacing_lod0 is only used for non-IMS MSAA surfaces.  TODO: can we
111     * use it elsewhere?
112     */
113    switch (msaa_layout) {
114    case INTEL_MSAA_LAYOUT_NONE:
115    case INTEL_MSAA_LAYOUT_IMS:
116       mt->array_spacing_lod0 = false;
117       break;
118    case INTEL_MSAA_LAYOUT_UMS:
119    case INTEL_MSAA_LAYOUT_CMS:
120       mt->array_spacing_lod0 = true;
121       break;
122    }
123 
124    if (target == GL_TEXTURE_CUBE_MAP) {
125       assert(depth0 == 1);
126       mt->depth0 = 6;
127    } else {
128       mt->depth0 = depth0;
129    }
130 
131    if (!for_region &&
132        _mesa_is_depthstencil_format(_mesa_get_format_base_format(format)) &&
133        (intel->must_use_separate_stencil ||
134 	(intel->has_separate_stencil &&
135 	 intel->vtbl.is_hiz_depth_format(intel, format)))) {
136       /* MSAA stencil surfaces always use IMS layout. */
137       enum intel_msaa_layout msaa_layout =
138          num_samples > 1 ? INTEL_MSAA_LAYOUT_IMS : INTEL_MSAA_LAYOUT_NONE;
139       mt->stencil_mt = intel_miptree_create(intel,
140                                             mt->target,
141                                             MESA_FORMAT_S8,
142                                             mt->first_level,
143                                             mt->last_level,
144                                             mt->width0,
145                                             mt->height0,
146                                             mt->depth0,
147                                             true,
148                                             num_samples,
149                                             msaa_layout);
150       if (!mt->stencil_mt) {
151 	 intel_miptree_release(&mt);
152 	 return NULL;
153       }
154 
155       /* Fix up the Z miptree format for how we're splitting out separate
156        * stencil.  Gen7 expects there to be no stencil bits in its depth buffer.
157        */
158       if (mt->format == MESA_FORMAT_S8_Z24) {
159 	 mt->format = MESA_FORMAT_X8_Z24;
160       } else if (mt->format == MESA_FORMAT_Z32_FLOAT_X24S8) {
161 	 mt->format = MESA_FORMAT_Z32_FLOAT;
162 	 mt->cpp = 4;
163       } else {
164 	 _mesa_problem(NULL, "Unknown format %s in separate stencil mt\n",
165 		       _mesa_get_format_name(mt->format));
166       }
167    }
168 
169    intel_get_texture_alignment_unit(intel, mt->format,
170 				    &mt->align_w, &mt->align_h);
171 
172 #ifdef I915
173    (void) intel;
174    if (intel->is_945)
175       i945_miptree_layout(mt);
176    else
177       i915_miptree_layout(mt);
178 #else
179    brw_miptree_layout(intel, mt);
180 #endif
181 
182    return mt;
183 }
184 
185 
186 struct intel_mipmap_tree *
intel_miptree_create(struct intel_context * intel,GLenum target,gl_format format,GLuint first_level,GLuint last_level,GLuint width0,GLuint height0,GLuint depth0,bool expect_accelerated_upload,GLuint num_samples,enum intel_msaa_layout msaa_layout)187 intel_miptree_create(struct intel_context *intel,
188 		     GLenum target,
189 		     gl_format format,
190 		     GLuint first_level,
191 		     GLuint last_level,
192 		     GLuint width0,
193 		     GLuint height0,
194 		     GLuint depth0,
195 		     bool expect_accelerated_upload,
196                      GLuint num_samples,
197                      enum intel_msaa_layout msaa_layout)
198 {
199    struct intel_mipmap_tree *mt;
200    uint32_t tiling = I915_TILING_NONE;
201    GLenum base_format;
202    bool wraps_etc1 = false;
203    GLuint total_width, total_height;
204 
205    if (format == MESA_FORMAT_ETC1_RGB8) {
206       format = MESA_FORMAT_RGBX8888_REV;
207       wraps_etc1 = true;
208    }
209 
210    base_format = _mesa_get_format_base_format(format);
211 
212    if (intel->use_texture_tiling && !_mesa_is_format_compressed(format)) {
213       if (intel->gen >= 4 &&
214 	  (base_format == GL_DEPTH_COMPONENT ||
215 	   base_format == GL_DEPTH_STENCIL_EXT))
216 	 tiling = I915_TILING_Y;
217       else if (msaa_layout != INTEL_MSAA_LAYOUT_NONE) {
218          /* From p82 of the Sandy Bridge PRM, dw3[1] of SURFACE_STATE ("Tiled
219           * Surface"):
220           *
221           *   [DevSNB+]: For multi-sample render targets, this field must be
222           *   1. MSRTs can only be tiled.
223           *
224           * Our usual reason for preferring X tiling (fast blits using the
225           * blitting engine) doesn't apply to MSAA, since we'll generally be
226           * downsampling or upsampling when blitting between the MSAA buffer
227           * and another buffer, and the blitting engine doesn't support that.
228           * So use Y tiling, since it makes better use of the cache.
229           */
230          tiling = I915_TILING_Y;
231       } else if (width0 >= 64)
232 	 tiling = I915_TILING_X;
233    }
234 
235    mt = intel_miptree_create_internal(intel, target, format,
236 				      first_level, last_level, width0,
237 				      height0, depth0,
238 				      false, num_samples, msaa_layout);
239    /*
240     * pitch == 0 || height == 0  indicates the null texture
241     */
242    if (!mt || !mt->total_width || !mt->total_height) {
243       intel_miptree_release(&mt);
244       return NULL;
245    }
246 
247    total_width = mt->total_width;
248    total_height = mt->total_height;
249 
250    if (format == MESA_FORMAT_S8) {
251       /* The stencil buffer is W tiled. However, we request from the kernel a
252        * non-tiled buffer because the GTT is incapable of W fencing.  So round
253        * up the width and height to match the size of W tiles (64x64).
254        */
255       tiling = I915_TILING_NONE;
256       total_width = ALIGN(total_width, 64);
257       total_height = ALIGN(total_height, 64);
258    }
259 
260    mt->wraps_etc1 = wraps_etc1;
261    mt->region = intel_region_alloc(intel->intelScreen,
262 				   tiling,
263 				   mt->cpp,
264 				   total_width,
265 				   total_height,
266 				   expect_accelerated_upload);
267    mt->offset = 0;
268 
269    if (!mt->region) {
270        intel_miptree_release(&mt);
271        return NULL;
272    }
273 
274    return mt;
275 }
276 
277 
278 struct intel_mipmap_tree *
intel_miptree_create_for_region(struct intel_context * intel,GLenum target,gl_format format,struct intel_region * region)279 intel_miptree_create_for_region(struct intel_context *intel,
280 				GLenum target,
281 				gl_format format,
282 				struct intel_region *region)
283 {
284    struct intel_mipmap_tree *mt;
285 
286    mt = intel_miptree_create_internal(intel, target, format,
287 				      0, 0,
288 				      region->width, region->height, 1,
289 				      true, 0 /* num_samples */,
290                                       INTEL_MSAA_LAYOUT_NONE);
291    if (!mt)
292       return mt;
293 
294    intel_region_reference(&mt->region, region);
295 
296    return mt;
297 }
298 
299 /**
300  * Determine which MSAA layout should be used by the MSAA surface being
301  * created, based on the chip generation and the surface type.
302  */
303 static enum intel_msaa_layout
compute_msaa_layout(struct intel_context * intel,gl_format format)304 compute_msaa_layout(struct intel_context *intel, gl_format format)
305 {
306    /* Prior to Gen7, all MSAA surfaces used IMS layout. */
307    if (intel->gen < 7)
308       return INTEL_MSAA_LAYOUT_IMS;
309 
310    /* In Gen7, IMS layout is only used for depth and stencil buffers. */
311    switch (_mesa_get_format_base_format(format)) {
312    case GL_DEPTH_COMPONENT:
313    case GL_STENCIL_INDEX:
314    case GL_DEPTH_STENCIL:
315       return INTEL_MSAA_LAYOUT_IMS;
316    default:
317       /* From the Ivy Bridge PRM, Vol4 Part1 p77 ("MCS Enable"):
318        *
319        *   This field must be set to 0 for all SINT MSRTs when all RT channels
320        *   are not written
321        *
322        * In practice this means that we have to disable MCS for all signed
323        * integer MSAA buffers.  The alternative, to disable MCS only when one
324        * of the render target channels is disabled, is impractical because it
325        * would require converting between CMS and UMS MSAA layouts on the fly,
326        * which is expensive.
327        */
328       if (_mesa_get_format_datatype(format) == GL_INT) {
329          /* TODO: is this workaround needed for future chipsets? */
330          assert(intel->gen == 7);
331          return INTEL_MSAA_LAYOUT_UMS;
332       } else {
333          return INTEL_MSAA_LAYOUT_CMS;
334       }
335    }
336 }
337 
338 /**
339  * For a singlesample DRI2 buffer, this simply wraps the given region with a miptree.
340  *
341  * For a multisample DRI2 buffer, this wraps the given region with
342  * a singlesample miptree, then creates a multisample miptree into which the
343  * singlesample miptree is embedded as a child.
344  */
345 struct intel_mipmap_tree*
intel_miptree_create_for_dri2_buffer(struct intel_context * intel,unsigned dri_attachment,gl_format format,uint32_t num_samples,struct intel_region * region)346 intel_miptree_create_for_dri2_buffer(struct intel_context *intel,
347                                      unsigned dri_attachment,
348                                      gl_format format,
349                                      uint32_t num_samples,
350                                      struct intel_region *region)
351 {
352    struct intel_mipmap_tree *singlesample_mt = NULL;
353    struct intel_mipmap_tree *multisample_mt = NULL;
354    GLenum base_format = _mesa_get_format_base_format(format);
355 
356    /* Only the front and back buffers, which are color buffers, are shared
357     * through DRI2.
358     */
359    assert(dri_attachment == __DRI_BUFFER_BACK_LEFT ||
360           dri_attachment == __DRI_BUFFER_FRONT_LEFT ||
361           dri_attachment == __DRI_BUFFER_FAKE_FRONT_LEFT);
362    assert(base_format == GL_RGB || base_format == GL_RGBA);
363 
364    singlesample_mt = intel_miptree_create_for_region(intel, GL_TEXTURE_2D,
365                                                      format, region);
366    if (!singlesample_mt)
367       return NULL;
368 
369    if (num_samples == 0)
370       return singlesample_mt;
371 
372    multisample_mt = intel_miptree_create_for_renderbuffer(intel,
373                                                           format,
374                                                           region->width,
375                                                           region->height,
376                                                           num_samples);
377    if (!multisample_mt) {
378       intel_miptree_release(&singlesample_mt);
379       return NULL;
380    }
381 
382    multisample_mt->singlesample_mt = singlesample_mt;
383    multisample_mt->need_downsample = false;
384 
385    if (intel->is_front_buffer_rendering &&
386        (dri_attachment == __DRI_BUFFER_FRONT_LEFT ||
387         dri_attachment == __DRI_BUFFER_FAKE_FRONT_LEFT)) {
388       intel_miptree_upsample(intel, multisample_mt);
389    }
390 
391    return multisample_mt;
392 }
393 
394 struct intel_mipmap_tree*
intel_miptree_create_for_renderbuffer(struct intel_context * intel,gl_format format,uint32_t width,uint32_t height,uint32_t num_samples)395 intel_miptree_create_for_renderbuffer(struct intel_context *intel,
396                                       gl_format format,
397                                       uint32_t width,
398                                       uint32_t height,
399                                       uint32_t num_samples)
400 {
401    struct intel_mipmap_tree *mt;
402    uint32_t depth = 1;
403    enum intel_msaa_layout msaa_layout = INTEL_MSAA_LAYOUT_NONE;
404    const uint32_t singlesample_width = width;
405    const uint32_t singlesample_height = height;
406    bool ok;
407 
408    if (num_samples > 1) {
409       /* Adjust width/height/depth for MSAA */
410       msaa_layout = compute_msaa_layout(intel, format);
411       if (msaa_layout == INTEL_MSAA_LAYOUT_IMS) {
412          /* In the Sandy Bridge PRM, volume 4, part 1, page 31, it says:
413           *
414           *     "Any of the other messages (sample*, LOD, load4) used with a
415           *      (4x) multisampled surface will in-effect sample a surface with
416           *      double the height and width as that indicated in the surface
417           *      state. Each pixel position on the original-sized surface is
418           *      replaced with a 2x2 of samples with the following arrangement:
419           *
420           *         sample 0 sample 2
421           *         sample 1 sample 3"
422           *
423           * Thus, when sampling from a multisampled texture, it behaves as
424           * though the layout in memory for (x,y,sample) is:
425           *
426           *      (0,0,0) (0,0,2)   (1,0,0) (1,0,2)
427           *      (0,0,1) (0,0,3)   (1,0,1) (1,0,3)
428           *
429           *      (0,1,0) (0,1,2)   (1,1,0) (1,1,2)
430           *      (0,1,1) (0,1,3)   (1,1,1) (1,1,3)
431           *
432           * However, the actual layout of multisampled data in memory is:
433           *
434           *      (0,0,0) (1,0,0)   (0,0,1) (1,0,1)
435           *      (0,1,0) (1,1,0)   (0,1,1) (1,1,1)
436           *
437           *      (0,0,2) (1,0,2)   (0,0,3) (1,0,3)
438           *      (0,1,2) (1,1,2)   (0,1,3) (1,1,3)
439           *
440           * This pattern repeats for each 2x2 pixel block.
441           *
442           * As a result, when calculating the size of our 4-sample buffer for
443           * an odd width or height, we have to align before scaling up because
444           * sample 3 is in that bottom right 2x2 block.
445           */
446          switch (num_samples) {
447          case 4:
448             width = ALIGN(width, 2) * 2;
449             height = ALIGN(height, 2) * 2;
450             break;
451          case 8:
452             width = ALIGN(width, 2) * 4;
453             height = ALIGN(height, 2) * 2;
454             break;
455          default:
456             /* num_samples should already have been quantized to 0, 1, 4, or
457              * 8.
458              */
459             assert(false);
460          }
461       } else {
462          /* Non-interleaved */
463          depth = num_samples;
464       }
465    }
466 
467    mt = intel_miptree_create(intel, GL_TEXTURE_2D, format, 0, 0,
468 			     width, height, depth, true, num_samples,
469                              msaa_layout);
470    if (!mt)
471       goto fail;
472 
473    if (intel->vtbl.is_hiz_depth_format(intel, format)) {
474       ok = intel_miptree_alloc_hiz(intel, mt, num_samples);
475       if (!ok)
476          goto fail;
477    }
478 
479    if (mt->msaa_layout == INTEL_MSAA_LAYOUT_CMS) {
480       ok = intel_miptree_alloc_mcs(intel, mt, num_samples);
481       if (!ok)
482          goto fail;
483    }
484 
485    mt->singlesample_width0 = singlesample_width;
486    mt->singlesample_height0 = singlesample_height;
487 
488    return mt;
489 
490 fail:
491    intel_miptree_release(&mt);
492    return NULL;
493 }
494 
495 void
intel_miptree_reference(struct intel_mipmap_tree ** dst,struct intel_mipmap_tree * src)496 intel_miptree_reference(struct intel_mipmap_tree **dst,
497                         struct intel_mipmap_tree *src)
498 {
499    if (*dst == src)
500       return;
501 
502    intel_miptree_release(dst);
503 
504    if (src) {
505       src->refcount++;
506       DBG("%s %p refcount now %d\n", __FUNCTION__, src, src->refcount);
507    }
508 
509    *dst = src;
510 }
511 
512 
513 void
intel_miptree_release(struct intel_mipmap_tree ** mt)514 intel_miptree_release(struct intel_mipmap_tree **mt)
515 {
516    if (!*mt)
517       return;
518 
519    DBG("%s %p refcount will be %d\n", __FUNCTION__, *mt, (*mt)->refcount - 1);
520    if (--(*mt)->refcount <= 0) {
521       GLuint i;
522 
523       DBG("%s deleting %p\n", __FUNCTION__, *mt);
524 
525       intel_region_release(&((*mt)->region));
526       intel_miptree_release(&(*mt)->stencil_mt);
527       intel_miptree_release(&(*mt)->hiz_mt);
528       intel_miptree_release(&(*mt)->mcs_mt);
529       intel_miptree_release(&(*mt)->singlesample_mt);
530       intel_resolve_map_clear(&(*mt)->hiz_map);
531 
532       for (i = 0; i < MAX_TEXTURE_LEVELS; i++) {
533 	 free((*mt)->level[i].slice);
534       }
535 
536       free(*mt);
537    }
538    *mt = NULL;
539 }
540 
541 void
intel_miptree_get_dimensions_for_image(struct gl_texture_image * image,int * width,int * height,int * depth)542 intel_miptree_get_dimensions_for_image(struct gl_texture_image *image,
543                                        int *width, int *height, int *depth)
544 {
545    switch (image->TexObject->Target) {
546    case GL_TEXTURE_1D_ARRAY:
547       *width = image->Width;
548       *height = 1;
549       *depth = image->Height;
550       break;
551    default:
552       *width = image->Width;
553       *height = image->Height;
554       *depth = image->Depth;
555       break;
556    }
557 }
558 
559 /**
560  * Can the image be pulled into a unified mipmap tree?  This mirrors
561  * the completeness test in a lot of ways.
562  *
563  * Not sure whether I want to pass gl_texture_image here.
564  */
565 bool
intel_miptree_match_image(struct intel_mipmap_tree * mt,struct gl_texture_image * image)566 intel_miptree_match_image(struct intel_mipmap_tree *mt,
567                           struct gl_texture_image *image)
568 {
569    struct intel_texture_image *intelImage = intel_texture_image(image);
570    GLuint level = intelImage->base.Base.Level;
571    int width, height, depth;
572 
573    if (target_to_target(image->TexObject->Target) != mt->target)
574       return false;
575 
576    if (image->TexFormat != mt->format &&
577        !(image->TexFormat == MESA_FORMAT_S8_Z24 &&
578 	 mt->format == MESA_FORMAT_X8_Z24 &&
579 	 mt->stencil_mt)) {
580       return false;
581    }
582 
583    intel_miptree_get_dimensions_for_image(image, &width, &height, &depth);
584 
585    if (mt->target == GL_TEXTURE_CUBE_MAP)
586       depth = 6;
587 
588    /* Test image dimensions against the base level image adjusted for
589     * minification.  This will also catch images not present in the
590     * tree, changed targets, etc.
591     */
592    if (width != mt->level[level].width ||
593        height != mt->level[level].height ||
594        depth != mt->level[level].depth)
595       return false;
596 
597    return true;
598 }
599 
600 
601 void
intel_miptree_set_level_info(struct intel_mipmap_tree * mt,GLuint level,GLuint x,GLuint y,GLuint w,GLuint h,GLuint d)602 intel_miptree_set_level_info(struct intel_mipmap_tree *mt,
603 			     GLuint level,
604 			     GLuint x, GLuint y,
605 			     GLuint w, GLuint h, GLuint d)
606 {
607    mt->level[level].width = w;
608    mt->level[level].height = h;
609    mt->level[level].depth = d;
610    mt->level[level].level_x = x;
611    mt->level[level].level_y = y;
612 
613    DBG("%s level %d size: %d,%d,%d offset %d,%d\n", __FUNCTION__,
614        level, w, h, d, x, y);
615 
616    assert(mt->level[level].slice == NULL);
617 
618    mt->level[level].slice = calloc(d, sizeof(*mt->level[0].slice));
619    mt->level[level].slice[0].x_offset = mt->level[level].level_x;
620    mt->level[level].slice[0].y_offset = mt->level[level].level_y;
621 }
622 
623 
624 void
intel_miptree_set_image_offset(struct intel_mipmap_tree * mt,GLuint level,GLuint img,GLuint x,GLuint y)625 intel_miptree_set_image_offset(struct intel_mipmap_tree *mt,
626 			       GLuint level, GLuint img,
627 			       GLuint x, GLuint y)
628 {
629    if (img == 0 && level == 0)
630       assert(x == 0 && y == 0);
631 
632    assert(img < mt->level[level].depth);
633 
634    mt->level[level].slice[img].x_offset = mt->level[level].level_x + x;
635    mt->level[level].slice[img].y_offset = mt->level[level].level_y + y;
636 
637    DBG("%s level %d img %d pos %d,%d\n",
638        __FUNCTION__, level, img,
639        mt->level[level].slice[img].x_offset,
640        mt->level[level].slice[img].y_offset);
641 }
642 
643 
644 /**
645  * For cube map textures, either the \c face parameter can be used, of course,
646  * or the cube face can be interpreted as a depth layer and the \c layer
647  * parameter used.
648  */
649 void
intel_miptree_get_image_offset(struct intel_mipmap_tree * mt,GLuint level,GLuint face,GLuint layer,GLuint * x,GLuint * y)650 intel_miptree_get_image_offset(struct intel_mipmap_tree *mt,
651 			       GLuint level, GLuint face, GLuint layer,
652 			       GLuint *x, GLuint *y)
653 {
654    int slice;
655 
656    if (face > 0) {
657       assert(mt->target == GL_TEXTURE_CUBE_MAP);
658       assert(face < 6);
659       assert(layer == 0);
660       slice = face;
661    } else {
662       /* This branch may be taken even if the texture target is a cube map. In
663        * that case, the caller chose to interpret each cube face as a layer.
664        */
665       assert(face == 0);
666       slice = layer;
667    }
668 
669    *x = mt->level[level].slice[slice].x_offset;
670    *y = mt->level[level].slice[slice].y_offset;
671 }
672 
673 static void
intel_miptree_copy_slice(struct intel_context * intel,struct intel_mipmap_tree * dst_mt,struct intel_mipmap_tree * src_mt,int level,int face,int depth)674 intel_miptree_copy_slice(struct intel_context *intel,
675 			 struct intel_mipmap_tree *dst_mt,
676 			 struct intel_mipmap_tree *src_mt,
677 			 int level,
678 			 int face,
679 			 int depth)
680 
681 {
682    gl_format format = src_mt->format;
683    uint32_t width = src_mt->level[level].width;
684    uint32_t height = src_mt->level[level].height;
685 
686    assert(depth < src_mt->level[level].depth);
687 
688    if (dst_mt->compressed) {
689       height = ALIGN(height, dst_mt->align_h) / dst_mt->align_h;
690       width = ALIGN(width, dst_mt->align_w);
691    }
692 
693    uint32_t dst_x, dst_y, src_x, src_y;
694    intel_miptree_get_image_offset(dst_mt, level, face, depth,
695 				  &dst_x, &dst_y);
696    intel_miptree_get_image_offset(src_mt, level, face, depth,
697 				  &src_x, &src_y);
698 
699    DBG("validate blit mt %p %d,%d/%d -> mt %p %d,%d/%d (%dx%d)\n",
700        src_mt, src_x, src_y, src_mt->region->pitch * src_mt->region->cpp,
701        dst_mt, dst_x, dst_y, dst_mt->region->pitch * dst_mt->region->cpp,
702        width, height);
703 
704    if (!intelEmitCopyBlit(intel,
705 			  dst_mt->region->cpp,
706 			  src_mt->region->pitch, src_mt->region->bo,
707 			  0, src_mt->region->tiling,
708 			  dst_mt->region->pitch, dst_mt->region->bo,
709 			  0, dst_mt->region->tiling,
710 			  src_x, src_y,
711 			  dst_x, dst_y,
712 			  width, height,
713 			  GL_COPY)) {
714 
715       fallback_debug("miptree validate blit for %s failed\n",
716 		     _mesa_get_format_name(format));
717       void *dst = intel_region_map(intel, dst_mt->region, GL_MAP_WRITE_BIT);
718       void *src = intel_region_map(intel, src_mt->region, GL_MAP_READ_BIT);
719 
720       _mesa_copy_rect(dst,
721 		      dst_mt->cpp,
722 		      dst_mt->region->pitch,
723 		      dst_x, dst_y,
724 		      width, height,
725 		      src, src_mt->region->pitch,
726 		      src_x, src_y);
727 
728       intel_region_unmap(intel, dst_mt->region);
729       intel_region_unmap(intel, src_mt->region);
730    }
731 
732    if (src_mt->stencil_mt) {
733       intel_miptree_copy_slice(intel,
734                                dst_mt->stencil_mt, src_mt->stencil_mt,
735                                level, face, depth);
736    }
737 }
738 
739 /**
740  * Copies the image's current data to the given miptree, and associates that
741  * miptree with the image.
742  */
743 void
intel_miptree_copy_teximage(struct intel_context * intel,struct intel_texture_image * intelImage,struct intel_mipmap_tree * dst_mt)744 intel_miptree_copy_teximage(struct intel_context *intel,
745 			    struct intel_texture_image *intelImage,
746 			    struct intel_mipmap_tree *dst_mt)
747 {
748    struct intel_mipmap_tree *src_mt = intelImage->mt;
749    int level = intelImage->base.Base.Level;
750    int face = intelImage->base.Base.Face;
751    GLuint depth = intelImage->base.Base.Depth;
752 
753    for (int slice = 0; slice < depth; slice++) {
754       intel_miptree_copy_slice(intel, dst_mt, src_mt, level, face, slice);
755    }
756 
757    intel_miptree_reference(&intelImage->mt, dst_mt);
758 }
759 
760 bool
intel_miptree_alloc_mcs(struct intel_context * intel,struct intel_mipmap_tree * mt,GLuint num_samples)761 intel_miptree_alloc_mcs(struct intel_context *intel,
762                         struct intel_mipmap_tree *mt,
763                         GLuint num_samples)
764 {
765    assert(mt->mcs_mt == NULL);
766    assert(intel->gen >= 7); /* MCS only used on Gen7+ */
767 
768    /* Choose the correct format for the MCS buffer.  All that really matters
769     * is that we allocate the right buffer size, since we'll always be
770     * accessing this miptree using MCS-specific hardware mechanisms, which
771     * infer the correct format based on num_samples.
772     */
773    gl_format format;
774    switch (num_samples) {
775    case 4:
776       /* 8 bits/pixel are required for MCS data when using 4x MSAA (2 bits for
777        * each sample).
778        */
779       format = MESA_FORMAT_R8;
780       break;
781    case 8:
782       /* 32 bits/pixel are required for MCS data when using 8x MSAA (3 bits
783        * for each sample, plus 8 padding bits).
784        */
785       format = MESA_FORMAT_R_UINT32;
786       break;
787    default:
788       assert(!"Unrecognized sample count in intel_miptree_alloc_mcs");
789       break;
790    };
791 
792    /* From the Ivy Bridge PRM, Vol4 Part1 p76, "MCS Base Address":
793     *
794     *     "The MCS surface must be stored as Tile Y."
795     *
796     * We set msaa_format to INTEL_MSAA_LAYOUT_CMS to force
797     * intel_miptree_create() to use Y tiling.  msaa_format is otherwise
798     * ignored for the MCS miptree.
799     */
800    mt->mcs_mt = intel_miptree_create(intel,
801                                      mt->target,
802                                      format,
803                                      mt->first_level,
804                                      mt->last_level,
805                                      mt->width0,
806                                      mt->height0,
807                                      mt->depth0,
808                                      true,
809                                      0 /* num_samples */,
810                                      INTEL_MSAA_LAYOUT_CMS);
811 
812    /* From the Ivy Bridge PRM, Vol 2 Part 1 p326:
813     *
814     *     When MCS buffer is enabled and bound to MSRT, it is required that it
815     *     is cleared prior to any rendering.
816     *
817     * Since we don't use the MCS buffer for any purpose other than rendering,
818     * it makes sense to just clear it immediately upon allocation.
819     *
820     * Note: the clear value for MCS buffers is all 1's, so we memset to 0xff.
821     */
822    void *data = intel_region_map(intel, mt->mcs_mt->region, 0);
823    memset(data, 0xff, mt->mcs_mt->region->bo->size);
824    intel_region_unmap(intel, mt->mcs_mt->region);
825 
826    return mt->mcs_mt;
827 }
828 
829 bool
intel_miptree_alloc_hiz(struct intel_context * intel,struct intel_mipmap_tree * mt,GLuint num_samples)830 intel_miptree_alloc_hiz(struct intel_context *intel,
831 			struct intel_mipmap_tree *mt,
832                         GLuint num_samples)
833 {
834    assert(mt->hiz_mt == NULL);
835    /* MSAA HiZ surfaces always use IMS layout. */
836    mt->hiz_mt = intel_miptree_create(intel,
837                                      mt->target,
838                                      MESA_FORMAT_X8_Z24,
839                                      mt->first_level,
840                                      mt->last_level,
841                                      mt->width0,
842                                      mt->height0,
843                                      mt->depth0,
844                                      true,
845                                      num_samples,
846                                      INTEL_MSAA_LAYOUT_IMS);
847 
848    if (!mt->hiz_mt)
849       return false;
850 
851    /* Mark that all slices need a HiZ resolve. */
852    struct intel_resolve_map *head = &mt->hiz_map;
853    for (int level = mt->first_level; level <= mt->last_level; ++level) {
854       for (int layer = 0; layer < mt->level[level].depth; ++layer) {
855 	 head->next = malloc(sizeof(*head->next));
856 	 head->next->prev = head;
857 	 head->next->next = NULL;
858 	 head = head->next;
859 
860 	 head->level = level;
861 	 head->layer = layer;
862 	 head->need = GEN6_HIZ_OP_HIZ_RESOLVE;
863       }
864    }
865 
866    return true;
867 }
868 
869 void
intel_miptree_slice_set_needs_hiz_resolve(struct intel_mipmap_tree * mt,uint32_t level,uint32_t layer)870 intel_miptree_slice_set_needs_hiz_resolve(struct intel_mipmap_tree *mt,
871 					  uint32_t level,
872 					  uint32_t layer)
873 {
874    intel_miptree_check_level_layer(mt, level, layer);
875 
876    if (!mt->hiz_mt)
877       return;
878 
879    intel_resolve_map_set(&mt->hiz_map,
880 			 level, layer, GEN6_HIZ_OP_HIZ_RESOLVE);
881 }
882 
883 
884 void
intel_miptree_slice_set_needs_depth_resolve(struct intel_mipmap_tree * mt,uint32_t level,uint32_t layer)885 intel_miptree_slice_set_needs_depth_resolve(struct intel_mipmap_tree *mt,
886                                             uint32_t level,
887                                             uint32_t layer)
888 {
889    intel_miptree_check_level_layer(mt, level, layer);
890 
891    if (!mt->hiz_mt)
892       return;
893 
894    intel_resolve_map_set(&mt->hiz_map,
895 			 level, layer, GEN6_HIZ_OP_DEPTH_RESOLVE);
896 }
897 
898 static bool
intel_miptree_slice_resolve(struct intel_context * intel,struct intel_mipmap_tree * mt,uint32_t level,uint32_t layer,enum gen6_hiz_op need)899 intel_miptree_slice_resolve(struct intel_context *intel,
900 			    struct intel_mipmap_tree *mt,
901 			    uint32_t level,
902 			    uint32_t layer,
903 			    enum gen6_hiz_op need)
904 {
905    intel_miptree_check_level_layer(mt, level, layer);
906 
907    struct intel_resolve_map *item =
908 	 intel_resolve_map_get(&mt->hiz_map, level, layer);
909 
910    if (!item || item->need != need)
911       return false;
912 
913    intel_hiz_exec(intel, mt, level, layer, need);
914    intel_resolve_map_remove(item);
915    return true;
916 }
917 
918 bool
intel_miptree_slice_resolve_hiz(struct intel_context * intel,struct intel_mipmap_tree * mt,uint32_t level,uint32_t layer)919 intel_miptree_slice_resolve_hiz(struct intel_context *intel,
920 				struct intel_mipmap_tree *mt,
921 				uint32_t level,
922 				uint32_t layer)
923 {
924    return intel_miptree_slice_resolve(intel, mt, level, layer,
925 				      GEN6_HIZ_OP_HIZ_RESOLVE);
926 }
927 
928 bool
intel_miptree_slice_resolve_depth(struct intel_context * intel,struct intel_mipmap_tree * mt,uint32_t level,uint32_t layer)929 intel_miptree_slice_resolve_depth(struct intel_context *intel,
930 				  struct intel_mipmap_tree *mt,
931 				  uint32_t level,
932 				  uint32_t layer)
933 {
934    return intel_miptree_slice_resolve(intel, mt, level, layer,
935 				      GEN6_HIZ_OP_DEPTH_RESOLVE);
936 }
937 
938 static bool
intel_miptree_all_slices_resolve(struct intel_context * intel,struct intel_mipmap_tree * mt,enum gen6_hiz_op need)939 intel_miptree_all_slices_resolve(struct intel_context *intel,
940 				 struct intel_mipmap_tree *mt,
941 				 enum gen6_hiz_op need)
942 {
943    bool did_resolve = false;
944    struct intel_resolve_map *i, *next;
945 
946    for (i = mt->hiz_map.next; i; i = next) {
947       next = i->next;
948       if (i->need != need)
949 	 continue;
950 
951       intel_hiz_exec(intel, mt, i->level, i->layer, need);
952       intel_resolve_map_remove(i);
953       did_resolve = true;
954    }
955 
956    return did_resolve;
957 }
958 
959 bool
intel_miptree_all_slices_resolve_hiz(struct intel_context * intel,struct intel_mipmap_tree * mt)960 intel_miptree_all_slices_resolve_hiz(struct intel_context *intel,
961 				     struct intel_mipmap_tree *mt)
962 {
963    return intel_miptree_all_slices_resolve(intel, mt,
964 					   GEN6_HIZ_OP_HIZ_RESOLVE);
965 }
966 
967 bool
intel_miptree_all_slices_resolve_depth(struct intel_context * intel,struct intel_mipmap_tree * mt)968 intel_miptree_all_slices_resolve_depth(struct intel_context *intel,
969 				       struct intel_mipmap_tree *mt)
970 {
971    return intel_miptree_all_slices_resolve(intel, mt,
972 					   GEN6_HIZ_OP_DEPTH_RESOLVE);
973 }
974 
975 static void
intel_miptree_updownsample(struct intel_context * intel,struct intel_mipmap_tree * src,struct intel_mipmap_tree * dst,unsigned width,unsigned height)976 intel_miptree_updownsample(struct intel_context *intel,
977                            struct intel_mipmap_tree *src,
978                            struct intel_mipmap_tree *dst,
979                            unsigned width,
980                            unsigned height)
981 {
982 #ifndef I915
983    int src_x0 = 0;
984    int src_y0 = 0;
985    int dst_x0 = 0;
986    int dst_y0 = 0;
987 
988    intel_miptree_slice_resolve_depth(intel, src, 0, 0);
989    intel_miptree_slice_resolve_depth(intel, dst, 0, 0);
990 
991    brw_blorp_blit_miptrees(intel,
992                            src, 0 /* level */, 0 /* layer */,
993                            dst, 0 /* level */, 0 /* layer */,
994                            src_x0, src_y0,
995                            dst_x0, dst_y0,
996                            width, height,
997                            false, false /*mirror x, y*/);
998 
999    if (src->stencil_mt) {
1000       brw_blorp_blit_miptrees(intel,
1001                               src->stencil_mt, 0 /* level */, 0 /* layer */,
1002                               dst->stencil_mt, 0 /* level */, 0 /* layer */,
1003                               src_x0, src_y0,
1004                               dst_x0, dst_y0,
1005                               width, height,
1006                               false, false /*mirror x, y*/);
1007    }
1008 #endif /* I915 */
1009 }
1010 
1011 static void
assert_is_flat(struct intel_mipmap_tree * mt)1012 assert_is_flat(struct intel_mipmap_tree *mt)
1013 {
1014    assert(mt->target == GL_TEXTURE_2D);
1015    assert(mt->first_level == 0);
1016    assert(mt->last_level == 0);
1017 }
1018 
1019 /**
1020  * \brief Downsample from mt to mt->singlesample_mt.
1021  *
1022  * If the miptree needs no downsample, then skip.
1023  */
1024 void
intel_miptree_downsample(struct intel_context * intel,struct intel_mipmap_tree * mt)1025 intel_miptree_downsample(struct intel_context *intel,
1026                          struct intel_mipmap_tree *mt)
1027 {
1028    /* Only flat, renderbuffer-like miptrees are supported. */
1029    assert_is_flat(mt);
1030 
1031    if (!mt->need_downsample)
1032       return;
1033    intel_miptree_updownsample(intel,
1034                               mt, mt->singlesample_mt,
1035                               mt->singlesample_mt->width0,
1036                               mt->singlesample_mt->height0);
1037    mt->need_downsample = false;
1038 
1039    /* Strictly speaking, after a downsample on a depth miptree, a hiz
1040     * resolve is needed on the singlesample miptree. However, since the
1041     * singlesample miptree is never rendered to, the hiz resolve will never
1042     * occur. Therefore we do not mark the needed hiz resolve after
1043     * downsampling.
1044     */
1045 }
1046 
1047 /**
1048  * \brief Upsample from mt->singlesample_mt to mt.
1049  *
1050  * The upsample is done unconditionally.
1051  */
1052 void
intel_miptree_upsample(struct intel_context * intel,struct intel_mipmap_tree * mt)1053 intel_miptree_upsample(struct intel_context *intel,
1054                        struct intel_mipmap_tree *mt)
1055 {
1056    /* Only flat, renderbuffer-like miptrees are supported. */
1057    assert_is_flat(mt);
1058    assert(!mt->need_downsample);
1059 
1060    intel_miptree_updownsample(intel,
1061                               mt->singlesample_mt, mt,
1062                               mt->singlesample_mt->width0,
1063                               mt->singlesample_mt->height0);
1064    intel_miptree_slice_set_needs_hiz_resolve(mt, 0, 0);
1065 }
1066 
1067 static void
intel_miptree_map_gtt(struct intel_context * intel,struct intel_mipmap_tree * mt,struct intel_miptree_map * map,unsigned int level,unsigned int slice)1068 intel_miptree_map_gtt(struct intel_context *intel,
1069 		      struct intel_mipmap_tree *mt,
1070 		      struct intel_miptree_map *map,
1071 		      unsigned int level, unsigned int slice)
1072 {
1073    unsigned int bw, bh;
1074    void *base;
1075    unsigned int image_x, image_y;
1076    int x = map->x;
1077    int y = map->y;
1078 
1079    /* For compressed formats, the stride is the number of bytes per
1080     * row of blocks.  intel_miptree_get_image_offset() already does
1081     * the divide.
1082     */
1083    _mesa_get_format_block_size(mt->format, &bw, &bh);
1084    assert(y % bh == 0);
1085    y /= bh;
1086 
1087    base = intel_region_map(intel, mt->region, map->mode);
1088 
1089    if (base == NULL)
1090       map->ptr = NULL;
1091    else {
1092       /* Note that in the case of cube maps, the caller must have passed the
1093        * slice number referencing the face.
1094       */
1095       intel_miptree_get_image_offset(mt, level, 0, slice, &image_x, &image_y);
1096       x += image_x;
1097       y += image_y;
1098 
1099       map->stride = mt->region->pitch * mt->cpp;
1100       map->ptr = base + y * map->stride + x * mt->cpp;
1101    }
1102 
1103    DBG("%s: %d,%d %dx%d from mt %p (%s) %d,%d = %p/%d\n", __FUNCTION__,
1104        map->x, map->y, map->w, map->h,
1105        mt, _mesa_get_format_name(mt->format),
1106        x, y, map->ptr, map->stride);
1107 }
1108 
1109 static void
intel_miptree_unmap_gtt(struct intel_context * intel,struct intel_mipmap_tree * mt,struct intel_miptree_map * map,unsigned int level,unsigned int slice)1110 intel_miptree_unmap_gtt(struct intel_context *intel,
1111 			struct intel_mipmap_tree *mt,
1112 			struct intel_miptree_map *map,
1113 			unsigned int level,
1114 			unsigned int slice)
1115 {
1116    intel_region_unmap(intel, mt->region);
1117 }
1118 
1119 static void
intel_miptree_map_blit(struct intel_context * intel,struct intel_mipmap_tree * mt,struct intel_miptree_map * map,unsigned int level,unsigned int slice)1120 intel_miptree_map_blit(struct intel_context *intel,
1121 		       struct intel_mipmap_tree *mt,
1122 		       struct intel_miptree_map *map,
1123 		       unsigned int level, unsigned int slice)
1124 {
1125    unsigned int image_x, image_y;
1126    int x = map->x;
1127    int y = map->y;
1128    int ret;
1129 
1130    /* The blitter requires the pitch to be aligned to 4. */
1131    map->stride = ALIGN(map->w * mt->region->cpp, 4);
1132 
1133    map->bo = drm_intel_bo_alloc(intel->bufmgr, "intel_miptree_map_blit() temp",
1134 				map->stride * map->h, 4096);
1135    if (!map->bo) {
1136       fprintf(stderr, "Failed to allocate blit temporary\n");
1137       goto fail;
1138    }
1139 
1140    intel_miptree_get_image_offset(mt, level, 0, slice, &image_x, &image_y);
1141    x += image_x;
1142    y += image_y;
1143 
1144    if (!intelEmitCopyBlit(intel,
1145 			  mt->region->cpp,
1146 			  mt->region->pitch, mt->region->bo,
1147 			  0, mt->region->tiling,
1148 			  map->stride / mt->region->cpp, map->bo,
1149 			  0, I915_TILING_NONE,
1150 			  x, y,
1151 			  0, 0,
1152 			  map->w, map->h,
1153 			  GL_COPY)) {
1154       fprintf(stderr, "Failed to blit\n");
1155       goto fail;
1156    }
1157 
1158    intel_batchbuffer_flush(intel);
1159    ret = drm_intel_bo_map(map->bo, (map->mode & GL_MAP_WRITE_BIT) != 0);
1160    if (ret) {
1161       fprintf(stderr, "Failed to map blit temporary\n");
1162       goto fail;
1163    }
1164 
1165    map->ptr = map->bo->virtual;
1166 
1167    DBG("%s: %d,%d %dx%d from mt %p (%s) %d,%d = %p/%d\n", __FUNCTION__,
1168        map->x, map->y, map->w, map->h,
1169        mt, _mesa_get_format_name(mt->format),
1170        x, y, map->ptr, map->stride);
1171 
1172    return;
1173 
1174 fail:
1175    drm_intel_bo_unreference(map->bo);
1176    map->ptr = NULL;
1177    map->stride = 0;
1178 }
1179 
1180 static void
intel_miptree_unmap_blit(struct intel_context * intel,struct intel_mipmap_tree * mt,struct intel_miptree_map * map,unsigned int level,unsigned int slice)1181 intel_miptree_unmap_blit(struct intel_context *intel,
1182 			 struct intel_mipmap_tree *mt,
1183 			 struct intel_miptree_map *map,
1184 			 unsigned int level,
1185 			 unsigned int slice)
1186 {
1187    assert(!(map->mode & GL_MAP_WRITE_BIT));
1188 
1189    drm_intel_bo_unmap(map->bo);
1190    drm_intel_bo_unreference(map->bo);
1191 }
1192 
1193 static void
intel_miptree_map_s8(struct intel_context * intel,struct intel_mipmap_tree * mt,struct intel_miptree_map * map,unsigned int level,unsigned int slice)1194 intel_miptree_map_s8(struct intel_context *intel,
1195 		     struct intel_mipmap_tree *mt,
1196 		     struct intel_miptree_map *map,
1197 		     unsigned int level, unsigned int slice)
1198 {
1199    map->stride = map->w;
1200    map->buffer = map->ptr = malloc(map->stride * map->h);
1201    if (!map->buffer)
1202       return;
1203 
1204    /* One of either READ_BIT or WRITE_BIT or both is set.  READ_BIT implies no
1205     * INVALIDATE_RANGE_BIT.  WRITE_BIT needs the original values read in unless
1206     * invalidate is set, since we'll be writing the whole rectangle from our
1207     * temporary buffer back out.
1208     */
1209    if (!(map->mode & GL_MAP_INVALIDATE_RANGE_BIT)) {
1210       uint8_t *untiled_s8_map = map->ptr;
1211       uint8_t *tiled_s8_map = intel_region_map(intel, mt->region,
1212 					       GL_MAP_READ_BIT);
1213       unsigned int image_x, image_y;
1214 
1215       intel_miptree_get_image_offset(mt, level, 0, slice, &image_x, &image_y);
1216 
1217       for (uint32_t y = 0; y < map->h; y++) {
1218 	 for (uint32_t x = 0; x < map->w; x++) {
1219 	    ptrdiff_t offset = intel_offset_S8(mt->region->pitch,
1220 	                                       x + image_x + map->x,
1221 	                                       y + image_y + map->y,
1222 					       intel->has_swizzling);
1223 	    untiled_s8_map[y * map->w + x] = tiled_s8_map[offset];
1224 	 }
1225       }
1226 
1227       intel_region_unmap(intel, mt->region);
1228 
1229       DBG("%s: %d,%d %dx%d from mt %p %d,%d = %p/%d\n", __FUNCTION__,
1230 	  map->x, map->y, map->w, map->h,
1231 	  mt, map->x + image_x, map->y + image_y, map->ptr, map->stride);
1232    } else {
1233       DBG("%s: %d,%d %dx%d from mt %p = %p/%d\n", __FUNCTION__,
1234 	  map->x, map->y, map->w, map->h,
1235 	  mt, map->ptr, map->stride);
1236    }
1237 }
1238 
1239 static void
intel_miptree_unmap_s8(struct intel_context * intel,struct intel_mipmap_tree * mt,struct intel_miptree_map * map,unsigned int level,unsigned int slice)1240 intel_miptree_unmap_s8(struct intel_context *intel,
1241 		       struct intel_mipmap_tree *mt,
1242 		       struct intel_miptree_map *map,
1243 		       unsigned int level,
1244 		       unsigned int slice)
1245 {
1246    if (map->mode & GL_MAP_WRITE_BIT) {
1247       unsigned int image_x, image_y;
1248       uint8_t *untiled_s8_map = map->ptr;
1249       uint8_t *tiled_s8_map = intel_region_map(intel, mt->region, map->mode);
1250 
1251       intel_miptree_get_image_offset(mt, level, 0, slice, &image_x, &image_y);
1252 
1253       for (uint32_t y = 0; y < map->h; y++) {
1254 	 for (uint32_t x = 0; x < map->w; x++) {
1255 	    ptrdiff_t offset = intel_offset_S8(mt->region->pitch,
1256 	                                       x + map->x,
1257 	                                       y + map->y,
1258 					       intel->has_swizzling);
1259 	    tiled_s8_map[offset] = untiled_s8_map[y * map->w + x];
1260 	 }
1261       }
1262 
1263       intel_region_unmap(intel, mt->region);
1264    }
1265 
1266    free(map->buffer);
1267 }
1268 
1269 static void
intel_miptree_map_etc1(struct intel_context * intel,struct intel_mipmap_tree * mt,struct intel_miptree_map * map,unsigned int level,unsigned int slice)1270 intel_miptree_map_etc1(struct intel_context *intel,
1271                        struct intel_mipmap_tree *mt,
1272                        struct intel_miptree_map *map,
1273                        unsigned int level,
1274                        unsigned int slice)
1275 {
1276    /* For justification of these invariants,
1277     * see intel_mipmap_tree:wraps_etc1.
1278     */
1279    assert(mt->wraps_etc1);
1280    assert(mt->format == MESA_FORMAT_RGBX8888_REV);
1281 
1282    /* From the GL_OES_compressed_ETC1_RGB8_texture spec:
1283     *   INVALID_OPERATION is generated by CompressedTexSubImage2D,
1284     *   TexSubImage2D, or CopyTexSubImage2D if the texture image <level>
1285     *   bound to <target> has internal format ETC1_RGB8_OES.
1286     *
1287     * This implies that intel_miptree_map_etc1() can only be called from
1288     * glCompressedTexImage2D, and hence the assertions below hold.
1289     */
1290    assert(map->mode & GL_MAP_WRITE_BIT);
1291    assert(map->mode & GL_MAP_INVALIDATE_RANGE_BIT);
1292    assert(map->x == 0);
1293    assert(map->y == 0);
1294 
1295    /* Each ETC1 block contains 4x4 pixels in 8 bytes. */
1296    map->stride = 2 * map->w;
1297    map->buffer = map->ptr = malloc(map->stride * map->h);
1298 }
1299 
1300 static void
intel_miptree_unmap_etc1(struct intel_context * intel,struct intel_mipmap_tree * mt,struct intel_miptree_map * map,unsigned int level,unsigned int slice)1301 intel_miptree_unmap_etc1(struct intel_context *intel,
1302                          struct intel_mipmap_tree *mt,
1303                          struct intel_miptree_map *map,
1304                          unsigned int level,
1305                          unsigned int slice)
1306 {
1307    uint32_t image_x;
1308    uint32_t image_y;
1309    intel_miptree_get_image_offset(mt, level, 0, slice, &image_x, &image_y);
1310 
1311    uint8_t *xbgr = intel_region_map(intel, mt->region, map->mode)
1312                  + image_y * mt->region->pitch * mt->region->cpp
1313                  + image_x * mt->region->cpp;
1314 
1315    _mesa_etc1_unpack_rgba8888(xbgr, mt->region->pitch * mt->region->cpp,
1316                               map->ptr, map->stride,
1317                               map->w, map->h);
1318 
1319    intel_region_unmap(intel, mt->region);
1320    free(map->buffer);
1321 }
1322 
1323 /**
1324  * Mapping function for packed depth/stencil miptrees backed by real separate
1325  * miptrees for depth and stencil.
1326  *
1327  * On gen7, and to support HiZ pre-gen7, we have to have the stencil buffer
1328  * separate from the depth buffer.  Yet at the GL API level, we have to expose
1329  * packed depth/stencil textures and FBO attachments, and Mesa core expects to
1330  * be able to map that memory for texture storage and glReadPixels-type
1331  * operations.  We give Mesa core that access by mallocing a temporary and
1332  * copying the data between the actual backing store and the temporary.
1333  */
1334 static void
intel_miptree_map_depthstencil(struct intel_context * intel,struct intel_mipmap_tree * mt,struct intel_miptree_map * map,unsigned int level,unsigned int slice)1335 intel_miptree_map_depthstencil(struct intel_context *intel,
1336 			       struct intel_mipmap_tree *mt,
1337 			       struct intel_miptree_map *map,
1338 			       unsigned int level, unsigned int slice)
1339 {
1340    struct intel_mipmap_tree *z_mt = mt;
1341    struct intel_mipmap_tree *s_mt = mt->stencil_mt;
1342    bool map_z32f_x24s8 = mt->format == MESA_FORMAT_Z32_FLOAT;
1343    int packed_bpp = map_z32f_x24s8 ? 8 : 4;
1344 
1345    map->stride = map->w * packed_bpp;
1346    map->buffer = map->ptr = malloc(map->stride * map->h);
1347    if (!map->buffer)
1348       return;
1349 
1350    /* One of either READ_BIT or WRITE_BIT or both is set.  READ_BIT implies no
1351     * INVALIDATE_RANGE_BIT.  WRITE_BIT needs the original values read in unless
1352     * invalidate is set, since we'll be writing the whole rectangle from our
1353     * temporary buffer back out.
1354     */
1355    if (!(map->mode & GL_MAP_INVALIDATE_RANGE_BIT)) {
1356       uint32_t *packed_map = map->ptr;
1357       uint8_t *s_map = intel_region_map(intel, s_mt->region, GL_MAP_READ_BIT);
1358       uint32_t *z_map = intel_region_map(intel, z_mt->region, GL_MAP_READ_BIT);
1359       unsigned int s_image_x, s_image_y;
1360       unsigned int z_image_x, z_image_y;
1361 
1362       intel_miptree_get_image_offset(s_mt, level, 0, slice,
1363 				     &s_image_x, &s_image_y);
1364       intel_miptree_get_image_offset(z_mt, level, 0, slice,
1365 				     &z_image_x, &z_image_y);
1366 
1367       for (uint32_t y = 0; y < map->h; y++) {
1368 	 for (uint32_t x = 0; x < map->w; x++) {
1369 	    int map_x = map->x + x, map_y = map->y + y;
1370 	    ptrdiff_t s_offset = intel_offset_S8(s_mt->region->pitch,
1371 						 map_x + s_image_x,
1372 						 map_y + s_image_y,
1373 						 intel->has_swizzling);
1374 	    ptrdiff_t z_offset = ((map_y + z_image_y) * z_mt->region->pitch +
1375 				  (map_x + z_image_x));
1376 	    uint8_t s = s_map[s_offset];
1377 	    uint32_t z = z_map[z_offset];
1378 
1379 	    if (map_z32f_x24s8) {
1380 	       packed_map[(y * map->w + x) * 2 + 0] = z;
1381 	       packed_map[(y * map->w + x) * 2 + 1] = s;
1382 	    } else {
1383 	       packed_map[y * map->w + x] = (s << 24) | (z & 0x00ffffff);
1384 	    }
1385 	 }
1386       }
1387 
1388       intel_region_unmap(intel, s_mt->region);
1389       intel_region_unmap(intel, z_mt->region);
1390 
1391       DBG("%s: %d,%d %dx%d from z mt %p %d,%d, s mt %p %d,%d = %p/%d\n",
1392 	  __FUNCTION__,
1393 	  map->x, map->y, map->w, map->h,
1394 	  z_mt, map->x + z_image_x, map->y + z_image_y,
1395 	  s_mt, map->x + s_image_x, map->y + s_image_y,
1396 	  map->ptr, map->stride);
1397    } else {
1398       DBG("%s: %d,%d %dx%d from mt %p = %p/%d\n", __FUNCTION__,
1399 	  map->x, map->y, map->w, map->h,
1400 	  mt, map->ptr, map->stride);
1401    }
1402 }
1403 
1404 static void
intel_miptree_unmap_depthstencil(struct intel_context * intel,struct intel_mipmap_tree * mt,struct intel_miptree_map * map,unsigned int level,unsigned int slice)1405 intel_miptree_unmap_depthstencil(struct intel_context *intel,
1406 				 struct intel_mipmap_tree *mt,
1407 				 struct intel_miptree_map *map,
1408 				 unsigned int level,
1409 				 unsigned int slice)
1410 {
1411    struct intel_mipmap_tree *z_mt = mt;
1412    struct intel_mipmap_tree *s_mt = mt->stencil_mt;
1413    bool map_z32f_x24s8 = mt->format == MESA_FORMAT_Z32_FLOAT;
1414 
1415    if (map->mode & GL_MAP_WRITE_BIT) {
1416       uint32_t *packed_map = map->ptr;
1417       uint8_t *s_map = intel_region_map(intel, s_mt->region, map->mode);
1418       uint32_t *z_map = intel_region_map(intel, z_mt->region, map->mode);
1419       unsigned int s_image_x, s_image_y;
1420       unsigned int z_image_x, z_image_y;
1421 
1422       intel_miptree_get_image_offset(s_mt, level, 0, slice,
1423 				     &s_image_x, &s_image_y);
1424       intel_miptree_get_image_offset(z_mt, level, 0, slice,
1425 				     &z_image_x, &z_image_y);
1426 
1427       for (uint32_t y = 0; y < map->h; y++) {
1428 	 for (uint32_t x = 0; x < map->w; x++) {
1429 	    ptrdiff_t s_offset = intel_offset_S8(s_mt->region->pitch,
1430 						 x + s_image_x + map->x,
1431 						 y + s_image_y + map->y,
1432 						 intel->has_swizzling);
1433 	    ptrdiff_t z_offset = ((y + z_image_y) * z_mt->region->pitch +
1434 				  (x + z_image_x));
1435 
1436 	    if (map_z32f_x24s8) {
1437 	       z_map[z_offset] = packed_map[(y * map->w + x) * 2 + 0];
1438 	       s_map[s_offset] = packed_map[(y * map->w + x) * 2 + 1];
1439 	    } else {
1440 	       uint32_t packed = packed_map[y * map->w + x];
1441 	       s_map[s_offset] = packed >> 24;
1442 	       z_map[z_offset] = packed;
1443 	    }
1444 	 }
1445       }
1446 
1447       intel_region_unmap(intel, s_mt->region);
1448       intel_region_unmap(intel, z_mt->region);
1449 
1450       DBG("%s: %d,%d %dx%d from z mt %p (%s) %d,%d, s mt %p %d,%d = %p/%d\n",
1451 	  __FUNCTION__,
1452 	  map->x, map->y, map->w, map->h,
1453 	  z_mt, _mesa_get_format_name(z_mt->format),
1454 	  map->x + z_image_x, map->y + z_image_y,
1455 	  s_mt, map->x + s_image_x, map->y + s_image_y,
1456 	  map->ptr, map->stride);
1457    }
1458 
1459    free(map->buffer);
1460 }
1461 
1462 /**
1463  * Create and attach a map to the miptree at (level, slice). Return the
1464  * attached map.
1465  */
1466 static struct intel_miptree_map*
intel_miptree_attach_map(struct intel_mipmap_tree * mt,unsigned int level,unsigned int slice,unsigned int x,unsigned int y,unsigned int w,unsigned int h,GLbitfield mode)1467 intel_miptree_attach_map(struct intel_mipmap_tree *mt,
1468                          unsigned int level,
1469                          unsigned int slice,
1470                          unsigned int x,
1471                          unsigned int y,
1472                          unsigned int w,
1473                          unsigned int h,
1474                          GLbitfield mode)
1475 {
1476    struct intel_miptree_map *map = calloc(1, sizeof(*map));
1477 
1478    if (!map)
1479       return NULL;
1480 
1481    assert(mt->level[level].slice[slice].map == NULL);
1482    mt->level[level].slice[slice].map = map;
1483 
1484    map->mode = mode;
1485    map->x = x;
1486    map->y = y;
1487    map->w = w;
1488    map->h = h;
1489 
1490    return map;
1491 }
1492 
1493 /**
1494  * Release the map at (level, slice).
1495  */
1496 static void
intel_miptree_release_map(struct intel_mipmap_tree * mt,unsigned int level,unsigned int slice)1497 intel_miptree_release_map(struct intel_mipmap_tree *mt,
1498                          unsigned int level,
1499                          unsigned int slice)
1500 {
1501    struct intel_miptree_map **map;
1502 
1503    map = &mt->level[level].slice[slice].map;
1504    free(*map);
1505    *map = NULL;
1506 }
1507 
1508 static void
intel_miptree_map_singlesample(struct intel_context * intel,struct intel_mipmap_tree * mt,unsigned int level,unsigned int slice,unsigned int x,unsigned int y,unsigned int w,unsigned int h,GLbitfield mode,void ** out_ptr,int * out_stride)1509 intel_miptree_map_singlesample(struct intel_context *intel,
1510                                struct intel_mipmap_tree *mt,
1511                                unsigned int level,
1512                                unsigned int slice,
1513                                unsigned int x,
1514                                unsigned int y,
1515                                unsigned int w,
1516                                unsigned int h,
1517                                GLbitfield mode,
1518                                void **out_ptr,
1519                                int *out_stride)
1520 {
1521    struct intel_miptree_map *map;
1522 
1523    assert(mt->num_samples <= 1);
1524 
1525    map = intel_miptree_attach_map(mt, level, slice, x, y, w, h, mode);
1526    if (!map){
1527       *out_ptr = NULL;
1528       *out_stride = 0;
1529       return;
1530    }
1531 
1532    intel_miptree_slice_resolve_depth(intel, mt, level, slice);
1533    if (map->mode & GL_MAP_WRITE_BIT) {
1534       intel_miptree_slice_set_needs_hiz_resolve(mt, level, slice);
1535    }
1536 
1537    if (mt->format == MESA_FORMAT_S8) {
1538       intel_miptree_map_s8(intel, mt, map, level, slice);
1539    } else if (mt->wraps_etc1) {
1540       intel_miptree_map_etc1(intel, mt, map, level, slice);
1541    } else if (mt->stencil_mt) {
1542       intel_miptree_map_depthstencil(intel, mt, map, level, slice);
1543    } else if (intel->has_llc &&
1544 	      !(mode & GL_MAP_WRITE_BIT) &&
1545 	      !mt->compressed &&
1546 	      mt->region->tiling == I915_TILING_X) {
1547       intel_miptree_map_blit(intel, mt, map, level, slice);
1548    } else {
1549       intel_miptree_map_gtt(intel, mt, map, level, slice);
1550    }
1551 
1552    *out_ptr = map->ptr;
1553    *out_stride = map->stride;
1554 
1555    if (map->ptr == NULL)
1556       intel_miptree_release_map(mt, level, slice);
1557 }
1558 
1559 static void
intel_miptree_unmap_singlesample(struct intel_context * intel,struct intel_mipmap_tree * mt,unsigned int level,unsigned int slice)1560 intel_miptree_unmap_singlesample(struct intel_context *intel,
1561                                  struct intel_mipmap_tree *mt,
1562                                  unsigned int level,
1563                                  unsigned int slice)
1564 {
1565    struct intel_miptree_map *map = mt->level[level].slice[slice].map;
1566 
1567    assert(mt->num_samples <= 1);
1568 
1569    if (!map)
1570       return;
1571 
1572    DBG("%s: mt %p (%s) level %d slice %d\n", __FUNCTION__,
1573        mt, _mesa_get_format_name(mt->format), level, slice);
1574 
1575    if (mt->format == MESA_FORMAT_S8) {
1576       intel_miptree_unmap_s8(intel, mt, map, level, slice);
1577    } else if (mt->wraps_etc1) {
1578       intel_miptree_unmap_etc1(intel, mt, map, level, slice);
1579    } else if (mt->stencil_mt) {
1580       intel_miptree_unmap_depthstencil(intel, mt, map, level, slice);
1581    } else if (map->bo) {
1582       intel_miptree_unmap_blit(intel, mt, map, level, slice);
1583    } else {
1584       intel_miptree_unmap_gtt(intel, mt, map, level, slice);
1585    }
1586 
1587    intel_miptree_release_map(mt, level, slice);
1588 }
1589 
1590 static void
intel_miptree_map_multisample(struct intel_context * intel,struct intel_mipmap_tree * mt,unsigned int level,unsigned int slice,unsigned int x,unsigned int y,unsigned int w,unsigned int h,GLbitfield mode,void ** out_ptr,int * out_stride)1591 intel_miptree_map_multisample(struct intel_context *intel,
1592                               struct intel_mipmap_tree *mt,
1593                               unsigned int level,
1594                               unsigned int slice,
1595                               unsigned int x,
1596                               unsigned int y,
1597                               unsigned int w,
1598                               unsigned int h,
1599                               GLbitfield mode,
1600                               void **out_ptr,
1601                               int *out_stride)
1602 {
1603    struct intel_miptree_map *map;
1604 
1605    assert(mt->num_samples > 1);
1606 
1607    /* Only flat, renderbuffer-like miptrees are supported. */
1608    if (mt->target != GL_TEXTURE_2D ||
1609        mt->first_level != 0 ||
1610        mt->last_level != 0) {
1611       _mesa_problem(&intel->ctx, "attempt to map a multisample miptree for "
1612                     "which (target, first_level, last_level != "
1613                     "(GL_TEXTURE_2D, 0, 0)");
1614       goto fail;
1615    }
1616 
1617    map = intel_miptree_attach_map(mt, level, slice, x, y, w, h, mode);
1618    if (!map)
1619       goto fail;
1620 
1621    if (!mt->singlesample_mt) {
1622       mt->singlesample_mt =
1623          intel_miptree_create_for_renderbuffer(intel,
1624                                                mt->format,
1625                                                mt->singlesample_width0,
1626                                                mt->singlesample_height0,
1627                                                0 /*num_samples*/);
1628       if (!mt->singlesample_mt)
1629          goto fail;
1630 
1631       map->singlesample_mt_is_tmp = true;
1632       mt->need_downsample = true;
1633    }
1634 
1635    intel_miptree_downsample(intel, mt);
1636    intel_miptree_map_singlesample(intel, mt->singlesample_mt,
1637                                   level, slice,
1638                                   x, y, w, h,
1639                                   mode,
1640                                   out_ptr, out_stride);
1641    return;
1642 
1643 fail:
1644    intel_miptree_release_map(mt, level, slice);
1645    *out_ptr = NULL;
1646    *out_stride = 0;
1647 }
1648 
1649 static void
intel_miptree_unmap_multisample(struct intel_context * intel,struct intel_mipmap_tree * mt,unsigned int level,unsigned int slice)1650 intel_miptree_unmap_multisample(struct intel_context *intel,
1651                                 struct intel_mipmap_tree *mt,
1652                                 unsigned int level,
1653                                 unsigned int slice)
1654 {
1655    struct intel_miptree_map *map = mt->level[level].slice[slice].map;
1656 
1657    assert(mt->num_samples > 1);
1658 
1659    if (!map)
1660       return;
1661 
1662    intel_miptree_unmap_singlesample(intel, mt->singlesample_mt, level, slice);
1663 
1664    mt->need_downsample = false;
1665    if (map->mode & GL_MAP_WRITE_BIT)
1666       intel_miptree_upsample(intel, mt);
1667 
1668    if (map->singlesample_mt_is_tmp)
1669       intel_miptree_release(&mt->singlesample_mt);
1670 
1671    intel_miptree_release_map(mt, level, slice);
1672 }
1673 
1674 void
intel_miptree_map(struct intel_context * intel,struct intel_mipmap_tree * mt,unsigned int level,unsigned int slice,unsigned int x,unsigned int y,unsigned int w,unsigned int h,GLbitfield mode,void ** out_ptr,int * out_stride)1675 intel_miptree_map(struct intel_context *intel,
1676 		  struct intel_mipmap_tree *mt,
1677 		  unsigned int level,
1678 		  unsigned int slice,
1679 		  unsigned int x,
1680 		  unsigned int y,
1681 		  unsigned int w,
1682 		  unsigned int h,
1683 		  GLbitfield mode,
1684 		  void **out_ptr,
1685 		  int *out_stride)
1686 {
1687    if (mt->num_samples <= 1)
1688       intel_miptree_map_singlesample(intel, mt,
1689                                      level, slice,
1690                                      x, y, w, h,
1691                                      mode,
1692                                      out_ptr, out_stride);
1693    else
1694       intel_miptree_map_multisample(intel, mt,
1695                                     level, slice,
1696                                     x, y, w, h,
1697                                     mode,
1698                                     out_ptr, out_stride);
1699 }
1700 
1701 void
intel_miptree_unmap(struct intel_context * intel,struct intel_mipmap_tree * mt,unsigned int level,unsigned int slice)1702 intel_miptree_unmap(struct intel_context *intel,
1703 		    struct intel_mipmap_tree *mt,
1704 		    unsigned int level,
1705 		    unsigned int slice)
1706 {
1707    if (mt->num_samples <= 1)
1708       intel_miptree_unmap_singlesample(intel, mt, level, slice);
1709    else
1710       intel_miptree_unmap_multisample(intel, mt, level, slice);
1711 }
1712