texconv: -ignoremips options for reading some invalid DDS files (#484)

This commit is contained in:
Chuck Walbourn 2024-07-01 18:47:31 -07:00 committed by GitHub
parent 6022b864e8
commit e102d0bd3e
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 40 additions and 20 deletions

View File

@ -236,6 +236,9 @@ namespace DirectX
DDS_FLAGS_PERMISSIVE = 0x80, DDS_FLAGS_PERMISSIVE = 0x80,
// Allow some file variants due to common bugs in the header written by various leagcy DDS writers // Allow some file variants due to common bugs in the header written by various leagcy DDS writers
DDS_FLAGS_IGNORE_MIPS = 0x100,
// Allow some files to be read that have incorrect mipcount values in the header by only reading the top-level mip
DDS_FLAGS_FORCE_DX10_EXT = 0x10000, DDS_FLAGS_FORCE_DX10_EXT = 0x10000,
// Always use the 'DX10' header extension for DDS writer (i.e. don't try to write DX9 compatible DDS files) // Always use the 'DX10' header extension for DDS writer (i.e. don't try to write DX9 compatible DDS files)

View File

@ -369,8 +369,10 @@ namespace
} }
metadata.mipLevels = pHeader->mipMapCount; metadata.mipLevels = pHeader->mipMapCount;
if (metadata.mipLevels == 0) if ((metadata.mipLevels == 0) || (flags & DDS_FLAGS_IGNORE_MIPS))
{
metadata.mipLevels = 1; metadata.mipLevels = 1;
}
// Check for DX10 extension // Check for DX10 extension
if ((pHeader->ddspf.flags & DDS_FOURCC) if ((pHeader->ddspf.flags & DDS_FOURCC)

View File

@ -110,6 +110,7 @@ namespace
OPT_DDS_DWORD_ALIGN, OPT_DDS_DWORD_ALIGN,
OPT_DDS_BAD_DXTN_TAILS, OPT_DDS_BAD_DXTN_TAILS,
OPT_DDS_PERMISSIVE, OPT_DDS_PERMISSIVE,
OPT_DDS_IGNORE_MIPS,
OPT_USE_DX10, OPT_USE_DX10,
OPT_USE_DX9, OPT_USE_DX9,
OPT_TGA20, OPT_TGA20,
@ -211,6 +212,7 @@ namespace
{ L"dword", OPT_DDS_DWORD_ALIGN }, { L"dword", OPT_DDS_DWORD_ALIGN },
{ L"badtails", OPT_DDS_BAD_DXTN_TAILS }, { L"badtails", OPT_DDS_BAD_DXTN_TAILS },
{ L"permissive", OPT_DDS_PERMISSIVE }, { L"permissive", OPT_DDS_PERMISSIVE },
{ L"ignoremips", OPT_DDS_IGNORE_MIPS },
{ L"dx10", OPT_USE_DX10 }, { L"dx10", OPT_USE_DX10 },
{ L"dx9", OPT_USE_DX9 }, { L"dx9", OPT_USE_DX9 },
{ L"tga20", OPT_TGA20 }, { L"tga20", OPT_TGA20 },
@ -1013,6 +1015,7 @@ namespace
L" -dword Use DWORD instead of BYTE alignment\n" L" -dword Use DWORD instead of BYTE alignment\n"
L" -badtails Fix for older DXTn with bad mipchain tails\n" L" -badtails Fix for older DXTn with bad mipchain tails\n"
L" -permissive Allow some DX9 variants with unusual header values\n" L" -permissive Allow some DX9 variants with unusual header values\n"
L" -ignoremips Reads just the top-level mip which reads some invalid files\n"
L" -fixbc4x4 Fix for odd-sized BC files that Direct3D can't load\n" L" -fixbc4x4 Fix for odd-sized BC files that Direct3D can't load\n"
L" -xlum expand legacy L8, L16, and A8P8 formats\n" L" -xlum expand legacy L8, L16, and A8P8 formats\n"
L"\n" L"\n"
@ -2240,6 +2243,8 @@ int __cdecl wmain(_In_ int argc, _In_z_count_(argc) wchar_t* argv[])
ddsFlags |= DDS_FLAGS_BAD_DXTN_TAILS; ddsFlags |= DDS_FLAGS_BAD_DXTN_TAILS;
if (dwOptions & (uint64_t(1) << OPT_DDS_PERMISSIVE)) if (dwOptions & (uint64_t(1) << OPT_DDS_PERMISSIVE))
ddsFlags |= DDS_FLAGS_PERMISSIVE; ddsFlags |= DDS_FLAGS_PERMISSIVE;
if (dwOptions & (uint64_t(1) << OPT_DDS_IGNORE_MIPS))
ddsFlags |= DDS_FLAGS_IGNORE_MIPS;
hr = LoadFromDDSFile(curpath.c_str(), ddsFlags, &info, *image); hr = LoadFromDDSFile(curpath.c_str(), ddsFlags, &info, *image);
} }

View File

@ -91,6 +91,8 @@ enum OPTIONS : uint32_t
OPT_FILTER, OPT_FILTER,
OPT_DDS_DWORD_ALIGN, OPT_DDS_DWORD_ALIGN,
OPT_DDS_BAD_DXTN_TAILS, OPT_DDS_BAD_DXTN_TAILS,
OPT_DDS_PERMISSIVE,
OPT_DDS_IGNORE_MIPS,
OPT_OUTPUTFILE, OPT_OUTPUTFILE,
OPT_TOLOWER, OPT_TOLOWER,
OPT_OVERWRITE, OPT_OVERWRITE,
@ -142,6 +144,8 @@ const SValue g_pOptions[] =
{ L"if", OPT_FILTER }, { L"if", OPT_FILTER },
{ L"dword", OPT_DDS_DWORD_ALIGN }, { L"dword", OPT_DDS_DWORD_ALIGN },
{ L"badtails", OPT_DDS_BAD_DXTN_TAILS }, { L"badtails", OPT_DDS_BAD_DXTN_TAILS },
{ L"permissive", OPT_DDS_PERMISSIVE },
{ L"ignoremips", OPT_DDS_IGNORE_MIPS },
{ L"nologo", OPT_NOLOGO }, { L"nologo", OPT_NOLOGO },
{ L"o", OPT_OUTPUTFILE }, { L"o", OPT_OUTPUTFILE },
{ L"l", OPT_TOLOWER }, { L"l", OPT_TOLOWER },
@ -706,6 +710,8 @@ namespace
L" -t{u|f} TYPELESS format is treated as UNORM or FLOAT\n" L" -t{u|f} TYPELESS format is treated as UNORM or FLOAT\n"
L" -dword Use DWORD instead of BYTE alignment\n" L" -dword Use DWORD instead of BYTE alignment\n"
L" -badtails Fix for older DXTn with bad mipchain tails\n" L" -badtails Fix for older DXTn with bad mipchain tails\n"
L" -permissive Allow some DX9 variants with unusual header values\n"
L" -ignoremips Reads just the top-level mip which reads some invalid files\n"
L" -xlum expand legacy L8, L16, and A8P8 formats\n" L" -xlum expand legacy L8, L16, and A8P8 formats\n"
L"\n" L"\n"
L" (diff only)\n" L" (diff only)\n"
@ -805,6 +811,10 @@ namespace
ddsFlags |= DDS_FLAGS_EXPAND_LUMINANCE; ddsFlags |= DDS_FLAGS_EXPAND_LUMINANCE;
if (dwOptions & (1 << OPT_DDS_BAD_DXTN_TAILS)) if (dwOptions & (1 << OPT_DDS_BAD_DXTN_TAILS))
ddsFlags |= DDS_FLAGS_BAD_DXTN_TAILS; ddsFlags |= DDS_FLAGS_BAD_DXTN_TAILS;
if (dwOptions & (1 << OPT_DDS_PERMISSIVE))
ddsFlags |= DDS_FLAGS_PERMISSIVE;
if (dwOptions & (1 << OPT_DDS_IGNORE_MIPS))
ddsFlags |= DDS_FLAGS_IGNORE_MIPS;
HRESULT hr = LoadFromDDSFile(fileName, ddsFlags, &info, *image); HRESULT hr = LoadFromDDSFile(fileName, ddsFlags, &info, *image);
if (FAILED(hr)) if (FAILED(hr))