1bf215546Sopenharmony_ci/* 2bf215546Sopenharmony_ci * Copyright (c) 2018 Intel Corporation 3bf215546Sopenharmony_ci * 4bf215546Sopenharmony_ci * Permission is hereby granted, free of charge, to any person obtaining a 5bf215546Sopenharmony_ci * copy of this software and associated documentation files (the "Software"), 6bf215546Sopenharmony_ci * to deal in the Software without restriction, including without limitation 7bf215546Sopenharmony_ci * the rights to use, copy, modify, merge, publish, distribute, sublicense, 8bf215546Sopenharmony_ci * and/or sell copies of the Software, and to permit persons to whom the 9bf215546Sopenharmony_ci * Software is furnished to do so, subject to the following conditions: 10bf215546Sopenharmony_ci * 11bf215546Sopenharmony_ci * The above copyright notice and this permission notice (including the next 12bf215546Sopenharmony_ci * paragraph) shall be included in all copies or substantial portions of the 13bf215546Sopenharmony_ci * Software. 14bf215546Sopenharmony_ci * 15bf215546Sopenharmony_ci * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16bf215546Sopenharmony_ci * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17bf215546Sopenharmony_ci * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 18bf215546Sopenharmony_ci * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19bf215546Sopenharmony_ci * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 20bf215546Sopenharmony_ci * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS 21bf215546Sopenharmony_ci * IN THE SOFTWARE. 22bf215546Sopenharmony_ci */ 23bf215546Sopenharmony_ci 24bf215546Sopenharmony_ci#include "isl_gfx9.h" 25bf215546Sopenharmony_ci#include "isl_gfx12.h" 26bf215546Sopenharmony_ci#include "isl_priv.h" 27bf215546Sopenharmony_ci 28bf215546Sopenharmony_ci/** 29bf215546Sopenharmony_ci * @brief Filter out tiling flags that are incompatible with the surface. 30bf215546Sopenharmony_ci * 31bf215546Sopenharmony_ci * The resultant outgoing @a flags is a subset of the incoming @a flags. The 32bf215546Sopenharmony_ci * outgoing flags may be empty (0x0) if the incoming flags were too 33bf215546Sopenharmony_ci * restrictive. 34bf215546Sopenharmony_ci * 35bf215546Sopenharmony_ci * For example, if the surface will be used for a display 36bf215546Sopenharmony_ci * (ISL_SURF_USAGE_DISPLAY_BIT), then this function filters out all tiling 37bf215546Sopenharmony_ci * flags except ISL_TILING_4_BIT, ISL_TILING_X_BIT, and ISL_TILING_LINEAR_BIT. 38bf215546Sopenharmony_ci */ 39bf215546Sopenharmony_civoid 40bf215546Sopenharmony_ciisl_gfx125_filter_tiling(const struct isl_device *dev, 41bf215546Sopenharmony_ci const struct isl_surf_init_info *restrict info, 42bf215546Sopenharmony_ci isl_tiling_flags_t *flags) 43bf215546Sopenharmony_ci{ 44bf215546Sopenharmony_ci /* Clear flags unsupported on this hardware */ 45bf215546Sopenharmony_ci assert(ISL_GFX_VERX10(dev) >= 125); 46bf215546Sopenharmony_ci *flags &= ISL_TILING_LINEAR_BIT | 47bf215546Sopenharmony_ci ISL_TILING_X_BIT | 48bf215546Sopenharmony_ci ISL_TILING_4_BIT | 49bf215546Sopenharmony_ci ISL_TILING_64_BIT; 50bf215546Sopenharmony_ci 51bf215546Sopenharmony_ci if (isl_surf_usage_is_depth_or_stencil(info->usage)) 52bf215546Sopenharmony_ci *flags &= ISL_TILING_4_BIT | ISL_TILING_64_BIT; 53bf215546Sopenharmony_ci 54bf215546Sopenharmony_ci if (info->usage & ISL_SURF_USAGE_DISPLAY_BIT) 55bf215546Sopenharmony_ci *flags &= ~ISL_TILING_64_BIT; 56bf215546Sopenharmony_ci 57bf215546Sopenharmony_ci /* From RENDER_SURFACE_STATE::AuxiliarySurfaceMode, 58bf215546Sopenharmony_ci * 59bf215546Sopenharmony_ci * MCS tiling format is always Tile4 60bf215546Sopenharmony_ci */ 61bf215546Sopenharmony_ci if (info->usage & ISL_SURF_USAGE_MCS_BIT) 62bf215546Sopenharmony_ci *flags &= ISL_TILING_4_BIT; 63bf215546Sopenharmony_ci 64bf215546Sopenharmony_ci /* From RENDER_SURFACE_STATE::TileMode, 65bf215546Sopenharmony_ci * 66bf215546Sopenharmony_ci * TILEMODE_XMAJOR is only allowed if Surface Type is SURFTYPE_2D. 67bf215546Sopenharmony_ci * 68bf215546Sopenharmony_ci * X-tiling is only allowed for 2D surfaces. 69bf215546Sopenharmony_ci */ 70bf215546Sopenharmony_ci if (info->dim != ISL_SURF_DIM_2D) 71bf215546Sopenharmony_ci *flags &= ~ISL_TILING_X_BIT; 72bf215546Sopenharmony_ci 73bf215546Sopenharmony_ci /* ISL only implements Tile64 support for 2D surfaces. */ 74bf215546Sopenharmony_ci if (info->dim != ISL_SURF_DIM_2D) 75bf215546Sopenharmony_ci *flags &= ~ISL_TILING_64_BIT; 76bf215546Sopenharmony_ci 77bf215546Sopenharmony_ci /* From RENDER_SURFACE_STATE::NumberofMultisamples, 78bf215546Sopenharmony_ci * 79bf215546Sopenharmony_ci * This field must not be programmed to anything other than 80bf215546Sopenharmony_ci * [MULTISAMPLECOUNT_1] unless the Tile Mode field is programmed to 81bf215546Sopenharmony_ci * Tile64. 82bf215546Sopenharmony_ci * 83bf215546Sopenharmony_ci * Tile64 is required for multisampling. 84bf215546Sopenharmony_ci */ 85bf215546Sopenharmony_ci if (info->samples > 1) 86bf215546Sopenharmony_ci *flags &= ISL_TILING_64_BIT; 87bf215546Sopenharmony_ci 88bf215546Sopenharmony_ci /* Tile64 is not defined for format sizes that are 24, 48, and 96 bpb. */ 89bf215546Sopenharmony_ci if (isl_format_get_layout(info->format)->bpb % 3 == 0) 90bf215546Sopenharmony_ci *flags &= ~ISL_TILING_64_BIT; 91bf215546Sopenharmony_ci 92bf215546Sopenharmony_ci /* BSpec 46962: 3DSTATE_CPSIZE_CONTROL_BUFFER::Tiled Mode : TILE4 & TILE64 93bf215546Sopenharmony_ci * are the only 2 valid values. 94bf215546Sopenharmony_ci * 95bf215546Sopenharmony_ci * TODO: For now we only TILE64 as we need to figure out potential 96bf215546Sopenharmony_ci * additional requirements for TILE4. 97bf215546Sopenharmony_ci */ 98bf215546Sopenharmony_ci if (info->usage & ISL_SURF_USAGE_CPB_BIT) 99bf215546Sopenharmony_ci *flags &= ISL_TILING_64_BIT; 100bf215546Sopenharmony_ci} 101bf215546Sopenharmony_ci 102bf215546Sopenharmony_civoid 103bf215546Sopenharmony_ciisl_gfx125_choose_image_alignment_el(const struct isl_device *dev, 104bf215546Sopenharmony_ci const struct isl_surf_init_info *restrict info, 105bf215546Sopenharmony_ci enum isl_tiling tiling, 106bf215546Sopenharmony_ci enum isl_dim_layout dim_layout, 107bf215546Sopenharmony_ci enum isl_msaa_layout msaa_layout, 108bf215546Sopenharmony_ci struct isl_extent3d *image_align_el) 109bf215546Sopenharmony_ci{ 110bf215546Sopenharmony_ci /* Handled by isl_choose_image_alignment_el */ 111bf215546Sopenharmony_ci assert(info->format != ISL_FORMAT_GFX125_HIZ); 112bf215546Sopenharmony_ci 113bf215546Sopenharmony_ci const struct isl_format_layout *fmtl = isl_format_get_layout(info->format); 114bf215546Sopenharmony_ci 115bf215546Sopenharmony_ci if (tiling == ISL_TILING_64) { 116bf215546Sopenharmony_ci /* From RENDER_SURFACE_STATE::SurfaceHorizontalAlignment, 117bf215546Sopenharmony_ci * 118bf215546Sopenharmony_ci * This field is ignored for Tile64 surface formats because horizontal 119bf215546Sopenharmony_ci * alignment is always to the start of the next tile in that case. 120bf215546Sopenharmony_ci * 121bf215546Sopenharmony_ci * From RENDER_SURFACE_STATE::SurfaceQPitch, 122bf215546Sopenharmony_ci * 123bf215546Sopenharmony_ci * Because MSAA is only supported for Tile64, QPitch must also be 124bf215546Sopenharmony_ci * programmed to an aligned tile boundary for MSAA surfaces. 125bf215546Sopenharmony_ci * 126bf215546Sopenharmony_ci * Images in this surface must be tile-aligned. The table on the Bspec 127bf215546Sopenharmony_ci * page, "2D/CUBE Alignment Requirement", shows that the vertical 128bf215546Sopenharmony_ci * alignment is also a tile height for non-MSAA as well. 129bf215546Sopenharmony_ci */ 130bf215546Sopenharmony_ci struct isl_tile_info tile_info; 131bf215546Sopenharmony_ci isl_tiling_get_info(tiling, info->dim, msaa_layout, fmtl->bpb, 132bf215546Sopenharmony_ci info->samples, &tile_info); 133bf215546Sopenharmony_ci 134bf215546Sopenharmony_ci *image_align_el = isl_extent3d(tile_info.logical_extent_el.w, 135bf215546Sopenharmony_ci tile_info.logical_extent_el.h, 136bf215546Sopenharmony_ci 1); 137bf215546Sopenharmony_ci } else if (isl_surf_usage_is_depth(info->usage)) { 138bf215546Sopenharmony_ci /* From RENDER_SURFACE_STATE::SurfaceHorizontalAlignment, 139bf215546Sopenharmony_ci * 140bf215546Sopenharmony_ci * - 16b Depth Surfaces Must Be HALIGN=16Bytes (8texels) 141bf215546Sopenharmony_ci * - 32b Depth Surfaces Must Be HALIGN=32Bytes (8texels) 142bf215546Sopenharmony_ci * 143bf215546Sopenharmony_ci * From RENDER_SURFACE_STATE::SurfaceVerticalAlignment, 144bf215546Sopenharmony_ci * 145bf215546Sopenharmony_ci * This field is intended to be set to VALIGN_4 if the surface 146bf215546Sopenharmony_ci * was rendered as a depth buffer [...] 147bf215546Sopenharmony_ci * 148bf215546Sopenharmony_ci * and 149bf215546Sopenharmony_ci * 150bf215546Sopenharmony_ci * This field should also be set to VALIGN_8 if the surface was 151bf215546Sopenharmony_ci * rendered as a D16_UNORM depth buffer [...] 152bf215546Sopenharmony_ci */ 153bf215546Sopenharmony_ci *image_align_el = 154bf215546Sopenharmony_ci info->format != ISL_FORMAT_R16_UNORM ? 155bf215546Sopenharmony_ci isl_extent3d(8, 4, 1) : 156bf215546Sopenharmony_ci isl_extent3d(8, 8, 1); 157bf215546Sopenharmony_ci } else if (isl_surf_usage_is_stencil(info->usage)) { 158bf215546Sopenharmony_ci /* From RENDER_SURFACE_STATE::SurfaceHorizontalAlignment, 159bf215546Sopenharmony_ci * 160bf215546Sopenharmony_ci * - Stencil Surfaces (8b) Must be HALIGN=16Bytes (16texels) 161bf215546Sopenharmony_ci * 162bf215546Sopenharmony_ci * From RENDER_SURFACE_STATE::SurfaceVerticalAlignment, 163bf215546Sopenharmony_ci * 164bf215546Sopenharmony_ci * This field is intended to be set to VALIGN_8 only if 165bf215546Sopenharmony_ci * the surface was rendered as a stencil buffer, since stencil buffer 166bf215546Sopenharmony_ci * surfaces support only alignment of 8. 167bf215546Sopenharmony_ci */ 168bf215546Sopenharmony_ci *image_align_el = isl_extent3d(16, 8, 1); 169bf215546Sopenharmony_ci } else if (!isl_is_pow2(fmtl->bpb)) { 170bf215546Sopenharmony_ci /* From RENDER_SURFACE_STATE::SurfaceHorizontalAlignment, 171bf215546Sopenharmony_ci * 172bf215546Sopenharmony_ci * - Linear Surfaces surfaces must use HALIGN=128, including 1D which 173bf215546Sopenharmony_ci * is always Linear. For 24,48 and 96bpp this means 128texels. 174bf215546Sopenharmony_ci * - Tiled 24bpp, 48bpp and 96bpp surfaces must use HALIGN=16 175bf215546Sopenharmony_ci */ 176bf215546Sopenharmony_ci *image_align_el = tiling == ISL_TILING_LINEAR ? 177bf215546Sopenharmony_ci isl_extent3d(128, 4, 1) : 178bf215546Sopenharmony_ci isl_extent3d(16, 4, 1); 179bf215546Sopenharmony_ci } else { 180bf215546Sopenharmony_ci /* From RENDER_SURFACE_STATE::SurfaceHorizontalAlignment, 181bf215546Sopenharmony_ci * 182bf215546Sopenharmony_ci * - Losslessly Compressed Surfaces Must be HALIGN=128 for all 183bf215546Sopenharmony_ci * supported Bpp 184bf215546Sopenharmony_ci * - 64bpe and 128bpe Surfaces Must Be HALIGN=64Bytes or 128Bytes (4, 185bf215546Sopenharmony_ci * 8 texels or 16 texels) 186bf215546Sopenharmony_ci * - Linear Surfaces surfaces must use HALIGN=128, including 1D which 187bf215546Sopenharmony_ci * is always Linear. 188bf215546Sopenharmony_ci * 189bf215546Sopenharmony_ci * Even though we could choose a horizontal alignment of 64B for certain 190bf215546Sopenharmony_ci * 64 and 128-bit formats, we want to be able to enable CCS whenever 191bf215546Sopenharmony_ci * possible and CCS requires 128B horizontal alignment. 192bf215546Sopenharmony_ci */ 193bf215546Sopenharmony_ci *image_align_el = isl_extent3d(128 * 8 / fmtl->bpb, 4, 1); 194bf215546Sopenharmony_ci } 195bf215546Sopenharmony_ci} 196bf215546Sopenharmony_ci 197bf215546Sopenharmony_civoid 198bf215546Sopenharmony_ciisl_gfx12_choose_image_alignment_el(const struct isl_device *dev, 199bf215546Sopenharmony_ci const struct isl_surf_init_info *restrict info, 200bf215546Sopenharmony_ci enum isl_tiling tiling, 201bf215546Sopenharmony_ci enum isl_dim_layout dim_layout, 202bf215546Sopenharmony_ci enum isl_msaa_layout msaa_layout, 203bf215546Sopenharmony_ci struct isl_extent3d *image_align_el) 204bf215546Sopenharmony_ci{ 205bf215546Sopenharmony_ci /* Handled by isl_choose_image_alignment_el */ 206bf215546Sopenharmony_ci assert(info->format != ISL_FORMAT_HIZ); 207bf215546Sopenharmony_ci 208bf215546Sopenharmony_ci const struct isl_format_layout *fmtl = isl_format_get_layout(info->format); 209bf215546Sopenharmony_ci if (fmtl->txc == ISL_TXC_CCS) { 210bf215546Sopenharmony_ci /* This CCS compresses a 2D-view of the entire surface. */ 211bf215546Sopenharmony_ci assert(info->levels == 1 && info->array_len == 1 && info->depth == 1); 212bf215546Sopenharmony_ci *image_align_el = isl_extent3d(1, 1, 1); 213bf215546Sopenharmony_ci return; 214bf215546Sopenharmony_ci } 215bf215546Sopenharmony_ci 216bf215546Sopenharmony_ci if (isl_surf_usage_is_depth(info->usage)) { 217bf215546Sopenharmony_ci /* The alignment parameters for depth buffers are summarized in the 218bf215546Sopenharmony_ci * following table: 219bf215546Sopenharmony_ci * 220bf215546Sopenharmony_ci * Surface Format | MSAA | Align Width | Align Height 221bf215546Sopenharmony_ci * -----------------+-------------+-------------+-------------- 222bf215546Sopenharmony_ci * D16_UNORM | 1x, 4x, 16x | 8 | 8 223bf215546Sopenharmony_ci * ----------------+-------------+-------------+-------------- 224bf215546Sopenharmony_ci * D16_UNORM | 2x, 8x | 16 | 4 225bf215546Sopenharmony_ci * ----------------+-------------+-------------+-------------- 226bf215546Sopenharmony_ci * other | any | 8 | 4 227bf215546Sopenharmony_ci * -----------------+-------------+-------------+-------------- 228bf215546Sopenharmony_ci */ 229bf215546Sopenharmony_ci assert(isl_is_pow2(info->samples)); 230bf215546Sopenharmony_ci *image_align_el = 231bf215546Sopenharmony_ci info->format != ISL_FORMAT_R16_UNORM ? 232bf215546Sopenharmony_ci isl_extent3d(8, 4, 1) : 233bf215546Sopenharmony_ci (info->samples == 2 || info->samples == 8 ? 234bf215546Sopenharmony_ci isl_extent3d(16, 4, 1) : isl_extent3d(8, 8, 1)); 235bf215546Sopenharmony_ci } else if (isl_surf_usage_is_stencil(info->usage)) { 236bf215546Sopenharmony_ci *image_align_el = isl_extent3d(16, 8, 1); 237bf215546Sopenharmony_ci } else { 238bf215546Sopenharmony_ci isl_gfx9_choose_image_alignment_el(dev, info, tiling, dim_layout, 239bf215546Sopenharmony_ci msaa_layout, image_align_el); 240bf215546Sopenharmony_ci } 241bf215546Sopenharmony_ci} 242