[Mesa-dev] [PATCH 006/140] amdgpu/addrlib: Add a flag "tcCompatible" to surface info output structure.
Marek Olšák
maraeo at gmail.com
Mon Mar 20 22:42:16 UTC 2017
From: Carlos Xiong <clever.xiong at amd.com>
Even if surface info input flag "tcComaptible" is enabled, tc
compatible may be not supported if tile split happens for depth
surfaces. Add a new flag in output structure to notify client to
disable tc compatible in this case.
---
src/amd/addrlib/addrinterface.h | 13 +++++++---
src/amd/addrlib/core/addrlib.cpp | 1 +
src/amd/addrlib/r800/ciaddrlib.cpp | 51 +++++++++++++++++++++++++++++---------
3 files changed, 50 insertions(+), 15 deletions(-)
diff --git a/src/amd/addrlib/addrinterface.h b/src/amd/addrlib/addrinterface.h
index d9a2b82..d05c6ef 100644
--- a/src/amd/addrlib/addrinterface.h
+++ b/src/amd/addrlib/addrinterface.h
@@ -527,23 +527,30 @@ typedef struct _ADDR_COMPUTE_SURFACE_INFO_OUTPUT
UINT_32 sliceTileMax; ///< SLICE_TILE_MAX value for h/w register
UINT_32 numSamples; ///< Pass the effective numSamples processed in this call
/// r800 and later HWL parameters
ADDR_TILEINFO* pTileInfo; ///< Tile parameters used. Filled in if 0 on input
AddrTileType tileType; ///< Micro tiling type, only valid when tileIndex != -1
INT_32 tileIndex; ///< Tile index, MAY be "downgraded"
INT_32 macroModeIndex; ///< Index in macro tile mode table if there is one (CI)
- /// Special information to work around SI mipmap swizzle bug UBTS #317508
- BOOL_32 last2DLevel; ///< TRUE if this is the last 2D(3D) tiled
- ///< Only meaningful when create flag checkLast2DLevel is set
+ /// Output flags
+ struct
+ {
+ /// Special information to work around SI mipmap swizzle bug UBTS #317508
+ UINT_32 last2DLevel : 1; ///< TRUE if this is the last 2D(3D) tiled
+ ///< Only meaningful when create flag checkLast2DLevel is set
+ UINT_32 tcCompatible : 1; ///< If the surface can be shader compatible
+ UINT_32 reserved :30; ///< Reserved bits
+ };
+
/// Stereo info
ADDR_QBSTEREOINFO* pStereoInfo;///< Stereo information, needed when .qbStereo flag is TRUE
} ADDR_COMPUTE_SURFACE_INFO_OUTPUT;
/**
***************************************************************************************************
* AddrComputeSurfaceInfo
*
* @brief
* Compute surface width/height/depth/alignments and suitable tiling mode
diff --git a/src/amd/addrlib/core/addrlib.cpp b/src/amd/addrlib/core/addrlib.cpp
index b829eec..8cf4a24 100644
--- a/src/amd/addrlib/core/addrlib.cpp
+++ b/src/amd/addrlib/core/addrlib.cpp
@@ -442,20 +442,21 @@ ADDR_E_RETURNCODE AddrLib::ComputeSurfaceInfo(
}
UINT_32 expandX = 1;
UINT_32 expandY = 1;
AddrElemMode elemMode;
// Save outputs that may not go through HWL
pOut->pixelBits = localIn.bpp;
pOut->numSamples = localIn.numSamples;
pOut->last2DLevel = FALSE;
+ pOut->tcCompatible = FALSE;
#if !ALT_TEST
if (localIn.numSamples > 1)
{
ADDR_ASSERT(localIn.mipLevel == 0);
}
#endif
if (localIn.format != ADDR_FMT_INVALID) // Set format to INVALID will skip this conversion
{
diff --git a/src/amd/addrlib/r800/ciaddrlib.cpp b/src/amd/addrlib/r800/ciaddrlib.cpp
index 5f8a1fe..1024ff2 100644
--- a/src/amd/addrlib/r800/ciaddrlib.cpp
+++ b/src/amd/addrlib/r800/ciaddrlib.cpp
@@ -476,21 +476,22 @@ INT_32 CiAddrLib::HwlPostCheckTileIndex(
if (macroTiled)
{
// macro tile modes need all to match
if ((pInfo->pipeConfig == m_tileTable[index].info.pipeConfig) &&
(mode == m_tileTable[index].mode) &&
(type == m_tileTable[index].type))
{
// tileSplitBytes stored in m_tileTable is only valid for depth entries
if (type == ADDR_DEPTH_SAMPLE_ORDER)
{
- if (pInfo->tileSplitBytes == m_tileTable[index].info.tileSplitBytes)
+ if (Min(m_tileTable[index].info.tileSplitBytes,
+ m_rowSize) == pInfo->tileSplitBytes)
{
break;
}
}
else // other entries are determined by other 3 fields
{
break;
}
}
}
@@ -614,20 +615,23 @@ ADDR_E_RETURNCODE CiAddrLib::HwlComputeSurfaceInfo(
const ADDR_COMPUTE_SURFACE_INFO_INPUT* pIn, ///< [in] input structure
ADDR_COMPUTE_SURFACE_INFO_OUTPUT* pOut ///< [out] output structure
) const
{
// If tileIndex is invalid, force macroModeIndex to be invalid, too
if (pIn->tileIndex == TileIndexInvalid)
{
pOut->macroModeIndex = TileIndexInvalid;
}
+ // Pass tcCompatible flag from input to output; and turn off it if tile split occurs
+ pOut->tcCompatible = pIn->flags.tcCompatible;
+
ADDR_E_RETURNCODE retCode = SiAddrLib::HwlComputeSurfaceInfo(pIn,pOut);
if (pOut->macroModeIndex == TileIndexNoMacroIndex)
{
pOut->macroModeIndex = TileIndexInvalid;
}
return retCode;
}
@@ -1003,25 +1007,32 @@ VOID CiAddrLib::HwlSetupTileInfo(
{
inTileType = ADDR_DEPTH_SAMPLE_ORDER;
}
}
if (IsTileInfoAllZero(pTileInfo))
{
// See table entries 0-4
if (flags.depth || flags.stencil)
{
- if (flags.depth && (flags.nonSplit || flags.tcCompatible))
+ // tileSize = thickness * bpp * numSamples * 8 * 8 / 8
+ UINT_32 tileSize = thickness * bpp * numSamples * 8;
+
+ // Turn off tc compatible if row_size is smaller than tile size (tile split occurs).
+ if (m_rowSize < tileSize)
{
- // tileSize = bpp * numSamples * 8 * 8 / 8
- UINT_32 tileSize = bpp * numSamples * 8;
+ flags.tcCompatible = FALSE;
+ pOut->tcCompatible = FALSE;
+ }
+ if (flags.depth && (flags.nonSplit || flags.tcCompatible))
+ {
// Texure readable depth surface should not be split
switch (tileSize)
{
case 128:
index = 1;
break;
case 256:
index = 2;
break;
case 512:
@@ -1208,20 +1219,43 @@ VOID CiAddrLib::HwlSetupTileInfo(
pOut->tileIndex = TileIndexLinearGeneral;
// Copy linear-aligned entry??
*pTileInfo = m_tileTable[8].info;
}
else if (tileMode == ADDR_TM_LINEAR_ALIGNED)
{
pOut->tileIndex = 8;
*pTileInfo = m_tileTable[8].info;
}
+
+ // Turn off tcCompatible for color surface if tileSplit happens. Depth/stencil is
+ // handled at tileIndex selecting time.
+ if (pOut->tcCompatible && (inTileType != ADDR_DEPTH_SAMPLE_ORDER))
+ {
+ if (IsMacroTiled(tileMode))
+ {
+ // Non-depth entries store a split factor
+ UINT_32 sampleSplit = m_tileTable[pOut->tileIndex].info.tileSplitBytes;
+ UINT_32 tileBytes1x = BITS_TO_BYTES(bpp * MicroTilePixels * thickness);
+ UINT_32 colorTileSplit = Max(256u, sampleSplit * tileBytes1x);
+
+ if (m_rowSize < colorTileSplit)
+ {
+ pOut->tcCompatible = FALSE;
+ }
+ }
+ else
+ {
+ // Client should not enable tc compatible for linear and 1D tile modes.
+ pOut->tcCompatible = FALSE;
+ }
+ }
}
/**
***************************************************************************************************
* CiAddrLib::ReadGbTileMode
*
* @brief
* Convert GB_TILE_MODE HW value to ADDR_TILE_CONFIG.
* @return
* NA.
@@ -1510,28 +1544,21 @@ INT_32 CiAddrLib::HwlComputeMacroModeIndex(
macroModeIndex += PrtMacroModeOffset;
*pTileInfo = m_macroTileTable[macroModeIndex];
}
else
{
*pTileInfo = m_macroTileTable[macroModeIndex];
}
pTileInfo->pipeConfig = m_tileTable[tileIndex].info.pipeConfig;
- if (m_tileTable[tileIndex].type != ADDR_DEPTH_SAMPLE_ORDER)
- {
- pTileInfo->tileSplitBytes = tileSplitC;
- }
- else
- {
- pTileInfo->tileSplitBytes = m_tileTable[tileIndex].info.tileSplitBytes;
- }
+ pTileInfo->tileSplitBytes = tileSplitC;
}
if (NULL != pTileMode)
{
*pTileMode = tileMode;
}
if (NULL != pTileType)
{
*pTileType = tileType;
--
2.7.4
More information about the mesa-dev
mailing list