1 /*
2 * Copyright 2017 Intel Corporation
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
13 * Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
21 * IN THE SOFTWARE.
22 */
23
24 #include <assert.h>
25 #include <stdlib.h>
26
27 #include "drm-uapi/drm_fourcc.h"
28 #include "drm-uapi/i915_drm.h"
29
30 #include "isl.h"
31 #include "dev/intel_device_info.h"
32 #include "dev/intel_debug.h"
33
34 uint32_t
isl_tiling_to_i915_tiling(enum isl_tiling tiling)35 isl_tiling_to_i915_tiling(enum isl_tiling tiling)
36 {
37 switch (tiling) {
38 case ISL_TILING_LINEAR:
39 return I915_TILING_NONE;
40
41 case ISL_TILING_X:
42 return I915_TILING_X;
43
44 case ISL_TILING_Y0:
45 case ISL_TILING_HIZ:
46 case ISL_TILING_CCS:
47 return I915_TILING_Y;
48
49 case ISL_TILING_W:
50 case ISL_TILING_SKL_Yf:
51 case ISL_TILING_SKL_Ys:
52 case ISL_TILING_ICL_Yf:
53 case ISL_TILING_ICL_Ys:
54 case ISL_TILING_4:
55 case ISL_TILING_64:
56 case ISL_TILING_64_XE2:
57 return I915_TILING_NONE;
58 }
59
60 unreachable("Invalid ISL tiling");
61 }
62
63 enum isl_tiling
isl_tiling_from_i915_tiling(uint32_t tiling)64 isl_tiling_from_i915_tiling(uint32_t tiling)
65 {
66 switch (tiling) {
67 case I915_TILING_NONE:
68 return ISL_TILING_LINEAR;
69
70 case I915_TILING_X:
71 return ISL_TILING_X;
72
73 case I915_TILING_Y:
74 return ISL_TILING_Y0;
75 }
76
77 unreachable("Invalid i915 tiling");
78 }
79
80 /** Sentinel is DRM_FORMAT_MOD_INVALID. */
81 const struct isl_drm_modifier_info
82 isl_drm_modifier_info_list[] = {
83 {
84 .modifier = DRM_FORMAT_MOD_NONE,
85 .name = "DRM_FORMAT_MOD_NONE",
86 .tiling = ISL_TILING_LINEAR,
87 },
88 {
89 .modifier = I915_FORMAT_MOD_X_TILED,
90 .name = "I915_FORMAT_MOD_X_TILED",
91 .tiling = ISL_TILING_X,
92 },
93 {
94 .modifier = I915_FORMAT_MOD_Y_TILED,
95 .name = "I915_FORMAT_MOD_Y_TILED",
96 .tiling = ISL_TILING_Y0,
97 },
98 {
99 .modifier = I915_FORMAT_MOD_Y_TILED_CCS,
100 .name = "I915_FORMAT_MOD_Y_TILED_CCS",
101 .tiling = ISL_TILING_Y0,
102 .supports_render_compression = true,
103 .supports_clear_color = false,
104 },
105 {
106 .modifier = I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS,
107 .name = "I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS",
108 .tiling = ISL_TILING_Y0,
109 .supports_render_compression = true,
110 .supports_clear_color = false,
111 },
112 {
113 .modifier = I915_FORMAT_MOD_Y_TILED_GEN12_MC_CCS,
114 .name = "I915_FORMAT_MOD_Y_TILED_GEN12_MC_CCS",
115 .tiling = ISL_TILING_Y0,
116 .supports_media_compression = true,
117 .supports_clear_color = false,
118 },
119 {
120 .modifier = I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS_CC,
121 .name = "I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS_CC",
122 .tiling = ISL_TILING_Y0,
123 .supports_render_compression = true,
124 .supports_clear_color = true,
125 },
126 {
127 .modifier = I915_FORMAT_MOD_4_TILED,
128 .name = "I915_FORMAT_MOD_4_TILED",
129 .tiling = ISL_TILING_4,
130 },
131 {
132 .modifier = I915_FORMAT_MOD_4_TILED_DG2_RC_CCS,
133 .name = "I915_FORMAT_MOD_4_TILED_DG2_RC_CCS",
134 .tiling = ISL_TILING_4,
135 .supports_render_compression = true,
136 .supports_clear_color = false,
137 },
138 {
139 .modifier = I915_FORMAT_MOD_4_TILED_DG2_MC_CCS,
140 .name = "I915_FORMAT_MOD_4_TILED_DG2_MC_CCS",
141 .tiling = ISL_TILING_4,
142 .supports_media_compression = true,
143 .supports_clear_color = false,
144 },
145 {
146 .modifier = I915_FORMAT_MOD_4_TILED_DG2_RC_CCS_CC,
147 .name = "I915_FORMAT_MOD_4_TILED_DG2_RC_CCS_CC",
148 .tiling = ISL_TILING_4,
149 .supports_render_compression = true,
150 .supports_clear_color = true,
151 },
152 {
153 .modifier = I915_FORMAT_MOD_4_TILED_MTL_RC_CCS,
154 .name = "I915_FORMAT_MOD_4_TILED_MTL_RC_CCS",
155 .tiling = ISL_TILING_4,
156 .supports_render_compression = true,
157 .supports_clear_color = false,
158 },
159 {
160 .modifier = I915_FORMAT_MOD_4_TILED_MTL_RC_CCS_CC,
161 .name = "I915_FORMAT_MOD_4_TILED_MTL_RC_CCS_CC",
162 .tiling = ISL_TILING_4,
163 .supports_render_compression = true,
164 .supports_clear_color = true,
165 },
166 {
167 .modifier = I915_FORMAT_MOD_4_TILED_MTL_MC_CCS,
168 .name = "I915_FORMAT_MOD_4_TILED_MTL_MC_CCS",
169 .tiling = ISL_TILING_4,
170 .supports_media_compression = true,
171 .supports_clear_color = false,
172 },
173 {
174 .modifier = DRM_FORMAT_MOD_INVALID,
175 },
176 };
177
178 const struct isl_drm_modifier_info *
isl_drm_modifier_get_info(uint64_t modifier)179 isl_drm_modifier_get_info(uint64_t modifier)
180 {
181 isl_drm_modifier_info_for_each(info) {
182 if (info->modifier == modifier)
183 return info;
184 }
185
186 return NULL;
187 }
188
189 uint32_t
isl_drm_modifier_get_score(const struct intel_device_info * devinfo,uint64_t modifier)190 isl_drm_modifier_get_score(const struct intel_device_info *devinfo,
191 uint64_t modifier)
192 {
193 /* We want to know the absence of the debug environment variable
194 * and don't want to provide a default value either, so we don't
195 * use debug_get_num_option() here.
196 */
197 const char *mod_str = getenv("INTEL_MODIFIER_OVERRIDE");
198 if (mod_str != NULL) {
199 return modifier == strtoul(mod_str, NULL, 0);
200 }
201 /* FINISHME: Add gfx12 modifiers */
202 switch (modifier) {
203 default:
204 return 0;
205 case DRM_FORMAT_MOD_LINEAR:
206 return 1;
207 case I915_FORMAT_MOD_X_TILED:
208 return 2;
209 case I915_FORMAT_MOD_Y_TILED:
210 /* Gfx12.5 doesn't have Y-tiling. */
211 if (devinfo->verx10 >= 125)
212 return 0;
213
214 return 3;
215 case I915_FORMAT_MOD_Y_TILED_CCS:
216 /* Not supported before Gfx9 and also Gfx12's CCS layout differs from
217 * Gfx9-11.
218 */
219 if (devinfo->ver <= 8 || devinfo->ver >= 12)
220 return 0;
221
222 if (INTEL_DEBUG(DEBUG_NO_CCS))
223 return 0;
224
225 return 4;
226 case I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS:
227 if (devinfo->verx10 != 120)
228 return 0;
229
230 if (INTEL_DEBUG(DEBUG_NO_CCS))
231 return 0;
232
233 return 4;
234 case I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS_CC:
235 if (devinfo->verx10 != 120)
236 return 0;
237
238 if (INTEL_DEBUG(DEBUG_NO_CCS) || INTEL_DEBUG(DEBUG_NO_FAST_CLEAR))
239 return 0;
240
241 return 5;
242 case I915_FORMAT_MOD_4_TILED:
243 /* Gfx12.5 introduces Tile4. */
244 if (devinfo->verx10 < 125)
245 return 0;
246
247 return 3;
248 case I915_FORMAT_MOD_4_TILED_DG2_RC_CCS:
249 if (!intel_device_info_is_dg2(devinfo))
250 return 0;
251
252 if (INTEL_DEBUG(DEBUG_NO_CCS))
253 return 0;
254
255 return 4;
256 case I915_FORMAT_MOD_4_TILED_DG2_RC_CCS_CC:
257 if (!intel_device_info_is_dg2(devinfo))
258 return 0;
259
260 if (INTEL_DEBUG(DEBUG_NO_CCS) || INTEL_DEBUG(DEBUG_NO_FAST_CLEAR))
261 return 0;
262
263 return 5;
264 case I915_FORMAT_MOD_4_TILED_MTL_RC_CCS:
265 if (!intel_device_info_is_mtl_or_arl(devinfo))
266 return 0;
267
268 if (INTEL_DEBUG(DEBUG_NO_CCS))
269 return 0;
270
271 return 4;
272 case I915_FORMAT_MOD_4_TILED_MTL_RC_CCS_CC:
273 if (!intel_device_info_is_mtl_or_arl(devinfo))
274 return 0;
275
276 if (INTEL_DEBUG(DEBUG_NO_CCS) || INTEL_DEBUG(DEBUG_NO_FAST_CLEAR))
277 return 0;
278
279 return 5;
280 }
281 }
282
283 uint32_t
isl_drm_modifier_get_plane_count(const struct intel_device_info * devinfo,uint64_t modifier,uint32_t fmt_planes)284 isl_drm_modifier_get_plane_count(const struct intel_device_info *devinfo,
285 uint64_t modifier,
286 uint32_t fmt_planes)
287 {
288 /* This function could return the wrong value if the modifier is not
289 * supported by the device.
290 */
291 assert(isl_drm_modifier_get_score(devinfo, modifier) > 0);
292
293 /* Planar images don't support clear color. */
294 if (isl_drm_modifier_get_info(modifier)->supports_clear_color)
295 assert(fmt_planes == 1);
296
297 if (devinfo->has_flat_ccs) {
298 if (isl_drm_modifier_get_info(modifier)->supports_clear_color)
299 return 2 * fmt_planes;
300 else
301 return 1 * fmt_planes;
302 } else {
303 if (isl_drm_modifier_get_info(modifier)->supports_clear_color)
304 return 3 * fmt_planes;
305 else if (isl_drm_modifier_has_aux(modifier))
306 return 2 * fmt_planes;
307 else
308 return 1 * fmt_planes;
309 }
310 }
311