2 * Copyright © 2011 Red Hat All Rights Reserved.
4 * Permission is hereby granted, free of charge, to any person obtaining
5 * a copy of this software and associated documentation files (the
6 * "Software"), to deal in the Software without restriction, including
7 * without limitation the rights to use, copy, modify, merge, publish,
8 * distribute, sub license, and/or sell copies of the Software, and to
9 * permit persons to whom the Software is furnished to do so, subject to
10 * the following conditions:
12 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
13 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
14 * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
15 * NON-INFRINGEMENT. IN NO EVENT SHALL THE COPYRIGHT HOLDERS, AUTHORS
16 * AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
18 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
19 * USE OR OTHER DEALINGS IN THE SOFTWARE.
21 * The above copyright notice and this permission notice (including the
22 * next paragraph) shall be included in all copies or substantial portions
27 * Jérôme Glisse <jglisse@redhat.com>
34 #include <sys/ioctl.h>
37 #include "radeon_drm.h"
38 #include "radeon_surface.h"
40 #define ALIGN(value, alignment) (((value) + alignment - 1) & ~(alignment - 1))
41 #define MAX2(A, B) ((A) > (B) ? (A) : (B))
42 #define MIN2(A, B) ((A) < (B) ? (A) : (B))
44 /* keep this private */
74 typedef int (*hw_init_surface_t)(struct radeon_surface_manager *surf_man,
75 struct radeon_surface *surf);
76 typedef int (*hw_best_surface_t)(struct radeon_surface_manager *surf_man,
77 struct radeon_surface *surf);
79 struct radeon_hw_info {
89 struct radeon_surface_manager {
92 struct radeon_hw_info hw_info;
94 hw_init_surface_t surface_init;
95 hw_best_surface_t surface_best;
99 static int radeon_get_value(int fd, unsigned req, uint32_t *value)
101 struct drm_radeon_info info = {};
106 info.value = (uintptr_t)value;
107 r = drmCommandWriteRead(fd, DRM_RADEON_INFO, &info,
108 sizeof(struct drm_radeon_info));
112 static int radeon_get_family(struct radeon_surface_manager *surf_man)
114 switch (surf_man->device_id) {
115 #define CHIPSET(pci_id, name, fam) case pci_id: surf_man->family = CHIP_##fam; break;
116 #include "r600_pci_ids.h"
124 static unsigned next_power_of_two(unsigned x)
129 return (1 << ((sizeof(unsigned) * 8) - __builtin_clz(x - 1)));
132 static unsigned mip_minify(unsigned size, unsigned level)
136 val = MAX2(1, size >> level);
138 val = next_power_of_two(val);
142 static void surf_minify(struct radeon_surface *surf,
144 uint32_t xalign, uint32_t yalign, uint32_t zalign,
147 surf->level[level].npix_x = mip_minify(surf->npix_x, level);
148 surf->level[level].npix_y = mip_minify(surf->npix_y, level);
149 surf->level[level].npix_z = mip_minify(surf->npix_z, level);
150 surf->level[level].nblk_x = (surf->level[level].npix_x + surf->blk_w - 1) / surf->blk_w;
151 surf->level[level].nblk_y = (surf->level[level].npix_y + surf->blk_h - 1) / surf->blk_h;
152 surf->level[level].nblk_z = (surf->level[level].npix_z + surf->blk_d - 1) / surf->blk_d;
153 if (surf->level[level].mode == RADEON_SURF_MODE_2D) {
154 if (surf->level[level].nblk_x < xalign || surf->level[level].nblk_y < yalign) {
155 surf->level[level].mode = RADEON_SURF_MODE_1D;
159 surf->level[level].nblk_x = ALIGN(surf->level[level].nblk_x, xalign);
160 surf->level[level].nblk_y = ALIGN(surf->level[level].nblk_y, yalign);
161 surf->level[level].nblk_z = ALIGN(surf->level[level].nblk_z, zalign);
163 surf->level[level].offset = offset;
164 surf->level[level].pitch_bytes = surf->level[level].nblk_x * surf->bpe;
165 surf->level[level].slice_size = surf->level[level].pitch_bytes * surf->level[level].nblk_y;
167 surf->bo_size = offset + surf->level[level].slice_size * surf->level[level].nblk_z * surf->array_size;
170 /* ===========================================================================
173 static int r6_init_hw_info(struct radeon_surface_manager *surf_man)
175 uint32_t tiling_config;
176 drmVersionPtr version;
179 r = radeon_get_value(surf_man->fd, RADEON_INFO_TILING_CONFIG,
185 surf_man->hw_info.allow_2d = 0;
186 version = drmGetVersion(surf_man->fd);
187 if (version && version->version_minor >= 14) {
188 surf_man->hw_info.allow_2d = 1;
191 switch ((tiling_config & 0xe) >> 1) {
193 surf_man->hw_info.num_pipes = 1;
196 surf_man->hw_info.num_pipes = 2;
199 surf_man->hw_info.num_pipes = 4;
202 surf_man->hw_info.num_pipes = 8;
208 switch ((tiling_config & 0x30) >> 4) {
210 surf_man->hw_info.num_banks = 4;
213 surf_man->hw_info.num_banks = 8;
219 switch ((tiling_config & 0xc0) >> 6) {
221 surf_man->hw_info.group_bytes = 256;
224 surf_man->hw_info.group_bytes = 512;
232 static int r6_surface_init_linear(struct radeon_surface_manager *surf_man,
233 struct radeon_surface *surf,
234 uint64_t offset, unsigned start_level)
236 uint32_t xalign, yalign, zalign;
239 /* compute alignment */
241 surf->bo_alignment = MAX2(256, surf_man->hw_info.group_bytes);
243 /* the 32 alignment is for scanout, cb or db but to allow texture to be
244 * easily bound as such we force this alignment to all surface
246 xalign = MAX2(1, surf_man->hw_info.group_bytes / surf->bpe);
249 if (surf->flags & RADEON_SURF_SCANOUT) {
250 xalign = MAX2((surf->bpe == 1) ? 64 : 32, xalign);
253 /* build mipmap tree */
254 for (i = start_level; i <= surf->last_level; i++) {
255 surf->level[i].mode = RADEON_SURF_MODE_LINEAR;
256 surf_minify(surf, i, xalign, yalign, zalign, offset);
257 /* level0 and first mipmap need to have alignment */
258 offset = surf->bo_size;
260 offset = ALIGN(offset, surf->bo_alignment);
266 static int r6_surface_init_linear_aligned(struct radeon_surface_manager *surf_man,
267 struct radeon_surface *surf,
268 uint64_t offset, unsigned start_level)
270 uint32_t xalign, yalign, zalign;
273 /* compute alignment */
275 surf->bo_alignment = MAX2(256, surf_man->hw_info.group_bytes);
277 xalign = MAX2(64, surf_man->hw_info.group_bytes / surf->bpe);
281 /* build mipmap tree */
282 for (i = start_level; i <= surf->last_level; i++) {
283 surf->level[i].mode = RADEON_SURF_MODE_LINEAR_ALIGNED;
284 surf_minify(surf, i, xalign, yalign, zalign, offset);
285 /* level0 and first mipmap need to have alignment */
286 offset = surf->bo_size;
288 offset = ALIGN(offset, surf->bo_alignment);
294 static int r6_surface_init_1d(struct radeon_surface_manager *surf_man,
295 struct radeon_surface *surf,
296 uint64_t offset, unsigned start_level)
298 uint32_t xalign, yalign, zalign, tilew;
301 /* compute alignment */
303 xalign = surf_man->hw_info.group_bytes / (tilew * surf->bpe * surf->nsamples);
304 xalign = MAX2(tilew, xalign);
307 if (surf->flags & RADEON_SURF_SCANOUT) {
308 xalign = MAX2((surf->bpe == 1) ? 64 : 32, xalign);
311 surf->bo_alignment = MAX2(256, surf_man->hw_info.group_bytes);
314 /* build mipmap tree */
315 for (i = start_level; i <= surf->last_level; i++) {
316 surf->level[i].mode = RADEON_SURF_MODE_1D;
317 surf_minify(surf, i, xalign, yalign, zalign, offset);
318 /* level0 and first mipmap need to have alignment */
319 offset = surf->bo_size;
321 offset = ALIGN(offset, surf->bo_alignment);
327 static int r6_surface_init_2d(struct radeon_surface_manager *surf_man,
328 struct radeon_surface *surf,
329 uint64_t offset, unsigned start_level)
331 uint32_t xalign, yalign, zalign, tilew;
334 /* compute alignment */
337 xalign = (surf_man->hw_info.group_bytes * surf_man->hw_info.num_banks) /
338 (tilew * surf->bpe * surf->nsamples);
339 xalign = MAX2(tilew * surf_man->hw_info.num_banks, xalign);
340 yalign = tilew * surf_man->hw_info.num_pipes;
341 if (surf->flags & RADEON_SURF_SCANOUT) {
342 xalign = MAX2((surf->bpe == 1) ? 64 : 32, xalign);
346 MAX2(surf_man->hw_info.num_pipes *
347 surf_man->hw_info.num_banks *
349 xalign * yalign * surf->nsamples * surf->bpe);
352 /* build mipmap tree */
353 for (i = start_level; i <= surf->last_level; i++) {
354 surf->level[i].mode = RADEON_SURF_MODE_2D;
355 surf_minify(surf, i, xalign, yalign, zalign, offset);
356 if (surf->level[i].mode == RADEON_SURF_MODE_1D) {
357 return r6_surface_init_1d(surf_man, surf, offset, i);
359 /* level0 and first mipmap need to have alignment */
360 offset = surf->bo_size;
362 offset = ALIGN(offset, surf->bo_alignment);
368 static int r6_surface_init(struct radeon_surface_manager *surf_man,
369 struct radeon_surface *surf)
375 mode = (surf->flags >> RADEON_SURF_MODE_SHIFT) & RADEON_SURF_MODE_MASK;
377 /* force 1d on kernel that can't do 2d */
378 if (!surf_man->hw_info.allow_2d && mode > RADEON_SURF_MODE_1D) {
379 mode = RADEON_SURF_MODE_1D;
380 surf->flags = RADEON_SURF_CLR(surf->flags, MODE);
381 surf->flags |= RADEON_SURF_SET(mode, MODE);
384 /* check surface dimension */
385 if (surf->npix_x > 8192 || surf->npix_y > 8192 || surf->npix_z > 8192) {
389 /* check mipmap last_level */
390 if (surf->last_level > 14) {
394 /* check tiling mode */
396 case RADEON_SURF_MODE_LINEAR:
397 r = r6_surface_init_linear(surf_man, surf, 0, 0);
399 case RADEON_SURF_MODE_LINEAR_ALIGNED:
400 r = r6_surface_init_linear_aligned(surf_man, surf, 0, 0);
402 case RADEON_SURF_MODE_1D:
403 r = r6_surface_init_1d(surf_man, surf, 0, 0);
405 case RADEON_SURF_MODE_2D:
406 r = r6_surface_init_2d(surf_man, surf, 0, 0);
414 static int r6_surface_best(struct radeon_surface_manager *surf_man,
415 struct radeon_surface *surf)
417 /* no value to optimize for r6xx/r7xx */
422 /* ===========================================================================
425 static int eg_init_hw_info(struct radeon_surface_manager *surf_man)
427 uint32_t tiling_config;
428 drmVersionPtr version;
431 r = radeon_get_value(surf_man->fd, RADEON_INFO_TILING_CONFIG,
437 surf_man->hw_info.allow_2d = 0;
438 version = drmGetVersion(surf_man->fd);
439 if (version && version->version_minor >= 14) {
440 surf_man->hw_info.allow_2d = 1;
443 switch (tiling_config & 0xf) {
445 surf_man->hw_info.num_pipes = 1;
448 surf_man->hw_info.num_pipes = 2;
451 surf_man->hw_info.num_pipes = 4;
454 surf_man->hw_info.num_pipes = 8;
460 switch ((tiling_config & 0xf0) >> 4) {
462 surf_man->hw_info.num_banks = 4;
465 surf_man->hw_info.num_banks = 8;
468 surf_man->hw_info.num_banks = 16;
474 switch ((tiling_config & 0xf00) >> 8) {
476 surf_man->hw_info.group_bytes = 256;
479 surf_man->hw_info.group_bytes = 512;
485 switch ((tiling_config & 0xf000) >> 12) {
487 surf_man->hw_info.row_size = 1024;
490 surf_man->hw_info.row_size = 2048;
493 surf_man->hw_info.row_size = 4096;
501 static void eg_surf_minify(struct radeon_surface *surf,
509 unsigned mtile_pr, mtile_ps;
511 surf->level[level].npix_x = mip_minify(surf->npix_x, level);
512 surf->level[level].npix_y = mip_minify(surf->npix_y, level);
513 surf->level[level].npix_z = mip_minify(surf->npix_z, level);
514 surf->level[level].nblk_x = (surf->level[level].npix_x + surf->blk_w - 1) / surf->blk_w;
515 surf->level[level].nblk_y = (surf->level[level].npix_y + surf->blk_h - 1) / surf->blk_h;
516 surf->level[level].nblk_z = (surf->level[level].npix_z + surf->blk_d - 1) / surf->blk_d;
517 if (surf->level[level].mode == RADEON_SURF_MODE_2D) {
518 if (surf->level[level].nblk_x < mtilew || surf->level[level].nblk_y < mtileh) {
519 surf->level[level].mode = RADEON_SURF_MODE_1D;
523 surf->level[level].nblk_x = ALIGN(surf->level[level].nblk_x, mtilew);
524 surf->level[level].nblk_y = ALIGN(surf->level[level].nblk_y, mtileh);
525 surf->level[level].nblk_z = ALIGN(surf->level[level].nblk_z, 1);
527 /* macro tile per row */
528 mtile_pr = surf->level[level].nblk_x / mtilew;
529 /* macro tile per slice */
530 mtile_ps = (mtile_pr * surf->level[level].nblk_y) / mtileh;
532 surf->level[level].offset = offset;
533 surf->level[level].pitch_bytes = surf->level[level].nblk_x * surf->bpe * slice_pt;
534 surf->level[level].slice_size = mtile_ps * mtileb * slice_pt;
536 surf->bo_size = offset + surf->level[level].slice_size * surf->level[level].nblk_z * surf->array_size;
539 static int eg_surface_init_1d(struct radeon_surface_manager *surf_man,
540 struct radeon_surface *surf,
541 uint64_t offset, unsigned start_level)
543 uint32_t xalign, yalign, zalign, tilew;
546 /* compute alignment */
548 xalign = surf_man->hw_info.group_bytes / (tilew * surf->bpe * surf->nsamples);
549 if (surf->flags & RADEON_SURF_SBUFFER) {
550 surf->stencil_offset = 0;
551 surf->stencil_tile_split = 0;
552 xalign = surf_man->hw_info.group_bytes / (tilew * surf->nsamples);
554 xalign = MAX2(tilew, xalign);
557 if (surf->flags & RADEON_SURF_SCANOUT) {
558 xalign = MAX2((surf->bpe == 1) ? 64 : 32, xalign);
561 surf->bo_alignment = MAX2(256, surf_man->hw_info.group_bytes);
564 /* build mipmap tree */
565 for (i = start_level; i <= surf->last_level; i++) {
566 surf->level[i].mode = RADEON_SURF_MODE_1D;
567 surf_minify(surf, i, xalign, yalign, zalign, offset);
568 /* level0 and first mipmap need to have alignment */
569 offset = surf->bo_size;
571 offset = ALIGN(offset, surf->bo_alignment);
575 if (surf->flags & RADEON_SURF_SBUFFER) {
576 surf->stencil_offset = ALIGN(surf->bo_size, surf->bo_alignment);
577 surf->bo_size = surf->stencil_offset + surf->bo_size / 4;
583 static int eg_surface_init_2d(struct radeon_surface_manager *surf_man,
584 struct radeon_surface *surf,
585 uint64_t offset, unsigned start_level)
587 unsigned tilew, tileh, tileb;
588 unsigned mtilew, mtileh, mtileb;
592 surf->stencil_offset = 0;
593 /* compute tile values */
596 tileb = tilew * tileh * surf->bpe * surf->nsamples;
597 /* slices per tile */
599 if (tileb > surf->tile_split) {
600 slice_pt = tileb / surf->tile_split;
602 tileb = tileb / slice_pt;
604 /* macro tile width & height */
605 mtilew = (tilew * surf->bankw * surf_man->hw_info.num_pipes) * surf->mtilea;
606 mtileh = (tileh * surf->bankh * surf_man->hw_info.num_banks) / surf->mtilea;
607 /* macro tile bytes */
608 mtileb = (mtilew / tilew) * (mtileh / tileh) * tileb;
611 surf->bo_alignment = MAX2(256, mtileb);
614 /* build mipmap tree */
615 for (i = start_level; i <= surf->last_level; i++) {
616 surf->level[i].mode = RADEON_SURF_MODE_2D;
617 eg_surf_minify(surf, i, slice_pt, mtilew, mtileh, mtileb, offset);
618 if (surf->level[i].mode == RADEON_SURF_MODE_1D) {
619 return eg_surface_init_1d(surf_man, surf, offset, i);
621 /* level0 and first mipmap need to have alignment */
622 offset = surf->bo_size;
624 offset = ALIGN(offset, surf->bo_alignment);
628 if (surf->flags & RADEON_SURF_SBUFFER) {
629 surf->stencil_offset = ALIGN(surf->bo_size, surf->bo_alignment);
630 surf->bo_size = surf->stencil_offset + surf->bo_size / 4;
636 static int eg_surface_sanity(struct radeon_surface_manager *surf_man,
637 struct radeon_surface *surf,
642 /* check surface dimension */
643 if (surf->npix_x > 16384 || surf->npix_y > 16384 || surf->npix_z > 16384) {
647 /* check mipmap last_level */
648 if (surf->last_level > 15) {
652 /* force 1d on kernel that can't do 2d */
653 if (!surf_man->hw_info.allow_2d && mode > RADEON_SURF_MODE_1D) {
654 mode = RADEON_SURF_MODE_1D;
655 surf->flags = RADEON_SURF_CLR(surf->flags, MODE);
656 surf->flags |= RADEON_SURF_SET(mode, MODE);
659 /* check tile split */
660 if (mode == RADEON_SURF_MODE_2D) {
661 switch (surf->tile_split) {
673 switch (surf->mtilea) {
682 /* check aspect ratio */
683 if (surf_man->hw_info.num_banks < surf->mtilea) {
686 /* check bank width */
687 switch (surf->bankw) {
696 /* check bank height */
697 switch (surf->bankh) {
706 tileb = MIN2(surf->tile_split, 64 * surf->bpe * surf->nsamples);
707 if ((tileb * surf->bankh * surf->bankw) < surf_man->hw_info.group_bytes) {
715 static int eg_surface_init(struct radeon_surface_manager *surf_man,
716 struct radeon_surface *surf)
722 mode = (surf->flags >> RADEON_SURF_MODE_SHIFT) & RADEON_SURF_MODE_MASK;
724 /* for some reason eg need to have room for stencil right after depth */
725 if (surf->flags & RADEON_SURF_ZBUFFER) {
726 surf->flags |= RADEON_SURF_SBUFFER;
729 r = eg_surface_sanity(surf_man, surf, mode);
734 /* check tiling mode */
736 case RADEON_SURF_MODE_LINEAR:
737 r = r6_surface_init_linear(surf_man, surf, 0, 0);
739 case RADEON_SURF_MODE_LINEAR_ALIGNED:
740 r = r6_surface_init_linear_aligned(surf_man, surf, 0, 0);
742 case RADEON_SURF_MODE_1D:
743 r = eg_surface_init_1d(surf_man, surf, 0, 0);
745 case RADEON_SURF_MODE_2D:
746 r = eg_surface_init_2d(surf_man, surf, 0, 0);
754 static unsigned log2_int(unsigned x)
762 if ((unsigned)(1 << l) > x) {
769 /* compute best tile_split, bankw, bankh, mtilea
770 * depending on surface
772 static int eg_surface_best(struct radeon_surface_manager *surf_man,
773 struct radeon_surface *surf)
775 unsigned mode, tileb, h_over_w;
779 mode = (surf->flags >> RADEON_SURF_MODE_SHIFT) & RADEON_SURF_MODE_MASK;
781 /* for some reason eg need to have room for stencil right after depth */
782 if (surf->flags & RADEON_SURF_ZBUFFER) {
783 surf->flags |= RADEON_SURF_SBUFFER;
786 /* set some default value to avoid sanity check choking on them */
787 surf->tile_split = 1024;
790 surf->mtilea = surf_man->hw_info.num_banks;
791 tileb = MIN2(surf->tile_split, 64 * surf->bpe * surf->nsamples);
792 for (; surf->bankh <= 8; surf->bankh *= 2) {
793 if ((tileb * surf->bankh * surf->bankw) >= surf_man->hw_info.group_bytes) {
797 if (surf->mtilea > 8) {
801 r = eg_surface_sanity(surf_man, surf, mode);
806 if (mode != RADEON_SURF_MODE_2D) {
807 /* nothing to do for non 2D tiled surface */
811 /* set tile split to row size, optimize latter for multi-sample surface
812 * tile split >= 256 for render buffer surface. Also depth surface want
813 * smaller value for optimal performances.
815 surf->tile_split = surf_man->hw_info.row_size;
816 surf->stencil_tile_split = surf_man->hw_info.row_size / 2;
818 /* bankw or bankh greater than 1 increase alignment requirement, not
819 * sure if it's worth using smaller bankw & bankh to stick with 2D
820 * tiling on small surface rather than falling back to 1D tiling.
821 * Use recommanded value based on tile size for now.
823 * fmask buffer has different optimal value figure them out once we
826 if (surf->flags & (RADEON_SURF_ZBUFFER | RADEON_SURF_SBUFFER)) {
827 /* assume 1 bytes for stencil, we optimize for stencil as stencil
828 * and depth shares surface values
830 tileb = MIN2(surf->tile_split, 64 * surf->nsamples);
832 tileb = MIN2(surf->tile_split, 64 * surf->bpe * surf->nsamples);
835 /* use bankw of 1 to minimize width alignment, might be interesting to
836 * increase it for large surface
851 /* double check the constraint */
852 for (; surf->bankh <= 8; surf->bankh *= 2) {
853 if ((tileb * surf->bankh * surf->bankw) >= surf_man->hw_info.group_bytes) {
858 h_over_w = (((surf->bankh * surf_man->hw_info.num_banks) << 16) /
859 (surf->bankw * surf_man->hw_info.num_pipes)) >> 16;
860 surf->mtilea = 1 << (log2_int(h_over_w) >> 1);
866 /* ===========================================================================
869 struct radeon_surface_manager *radeon_surface_manager_new(int fd)
871 struct radeon_surface_manager *surf_man;
873 surf_man = calloc(1, sizeof(struct radeon_surface_manager));
874 if (surf_man == NULL) {
878 if (radeon_get_value(fd, RADEON_INFO_DEVICE_ID, &surf_man->device_id)) {
881 if (radeon_get_family(surf_man)) {
885 if (surf_man->family <= CHIP_RV740) {
886 if (r6_init_hw_info(surf_man)) {
889 surf_man->surface_init = &r6_surface_init;
890 surf_man->surface_best = &r6_surface_best;
892 if (eg_init_hw_info(surf_man)) {
895 surf_man->surface_init = &eg_surface_init;
896 surf_man->surface_best = &eg_surface_best;
905 void radeon_surface_manager_free(struct radeon_surface_manager *surf_man)
910 static int radeon_surface_sanity(struct radeon_surface_manager *surf_man,
911 struct radeon_surface *surf,
915 if (surf_man == NULL || surf_man->surface_init == NULL || surf == NULL) {
919 /* all dimension must be at least 1 ! */
920 if (!surf->npix_x || !surf->npix_y || !surf->npix_z) {
923 if (!surf->blk_w || !surf->blk_h || !surf->blk_d) {
926 if (!surf->array_size) {
929 /* array size must be a power of 2 */
930 surf->array_size = next_power_of_two(surf->array_size);
932 switch (surf->nsamples) {
943 case RADEON_SURF_TYPE_1D:
944 if (surf->npix_y > 1) {
947 case RADEON_SURF_TYPE_2D:
948 if (surf->npix_z > 1) {
952 case RADEON_SURF_TYPE_CUBEMAP:
953 if (surf->npix_z > 1) {
956 /* deal with cubemap as they were texture array */
957 if (surf_man->family >= CHIP_RV770) {
958 surf->array_size = 8;
960 surf->array_size = 6;
963 case RADEON_SURF_TYPE_3D:
965 case RADEON_SURF_TYPE_1D_ARRAY:
966 if (surf->npix_y > 1) {
969 case RADEON_SURF_TYPE_2D_ARRAY:
977 int radeon_surface_init(struct radeon_surface_manager *surf_man,
978 struct radeon_surface *surf)
983 type = RADEON_SURF_GET(surf->flags, TYPE);
984 mode = RADEON_SURF_GET(surf->flags, MODE);
986 r = radeon_surface_sanity(surf_man, surf, type, mode);
990 return surf_man->surface_init(surf_man, surf);
993 int radeon_surface_best(struct radeon_surface_manager *surf_man,
994 struct radeon_surface *surf)
999 type = RADEON_SURF_GET(surf->flags, TYPE);
1000 mode = RADEON_SURF_GET(surf->flags, MODE);
1002 r = radeon_surface_sanity(surf_man, surf, type, mode);
1006 return surf_man->surface_best(surf_man, surf);