Skip to content
This repository was archived by the owner on Feb 23, 2026. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
49 changes: 34 additions & 15 deletions Core/DDSTextureLoader.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@

#include <algorithm>
#include <cassert>
#include <cstdint>
#include <memory>
#include <new>

Expand All @@ -43,6 +44,8 @@ using namespace DirectX;
//
// See DDS.h in the 'Texconv' sample and the 'DirectXTex' library
//--------------------------------------------------------------------------------------
namespace
{
#pragma pack(push,1)

constexpr uint32_t DDS_MAGIC = 0x20534444; // "DDS "
Expand Down Expand Up @@ -116,9 +119,15 @@ struct DDS_HEADER_DXT10

#pragma pack(pop)

static_assert(sizeof(DDS_PIXELFORMAT) == 32, "DDS pixel format size mismatch");
static_assert(sizeof(DDS_HEADER) == 124, "DDS Header size mismatch");
static_assert(sizeof(DDS_HEADER_DXT10) == 20, "DDS DX10 Extended Header size mismatch");

constexpr size_t DDS_MIN_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER);
constexpr size_t DDS_DX10_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10);
static_assert(DDS_DX10_HEADER_SIZE > DDS_MIN_HEADER_SIZE, "DDS DX10 Header should be larger than standard header");

//--------------------------------------------------------------------------------------
namespace
{
struct handle_closer { void operator()(HANDLE h) noexcept { if (h) CloseHandle(h); } };

using ScopedHandle = std::unique_ptr<void, handle_closer>;
Expand All @@ -134,8 +143,7 @@ namespace
#else
template<UINT TNameLength>
inline void SetDebugObjectName(_In_ ID3D11DeviceChild*, _In_ const char(&)[TNameLength]) noexcept
{
}
{}
#endif

//--------------------------------------------------------------------------------------
Expand All @@ -158,13 +166,13 @@ namespace
return E_FAIL;
}

if (ddsDataSize < (sizeof(uint32_t) + sizeof(DDS_HEADER)))
if (ddsDataSize < DDS_MIN_HEADER_SIZE)
{
return E_FAIL;
}

// DDS files always start with the same magic number ("DDS ")
auto const dwMagicNumber = *reinterpret_cast<const uint32_t*>(ddsData);
const auto dwMagicNumber = *reinterpret_cast<const uint32_t*>(ddsData);
if (dwMagicNumber != DDS_MAGIC)
{
return E_FAIL;
Expand All @@ -185,7 +193,7 @@ namespace
(MAKEFOURCC('D', 'X', '1', '0') == hdr->ddspf.fourCC))
{
// Must be long enough for both headers and magic value
if (ddsDataSize < (sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10)))
if (ddsDataSize < DDS_DX10_HEADER_SIZE)
{
return E_FAIL;
}
Expand All @@ -195,8 +203,7 @@ namespace

// setup the pointers in the process request
*header = hdr;
auto offset = sizeof(uint32_t)
+ sizeof(DDS_HEADER)
auto offset = DDS_MIN_HEADER_SIZE
+ (bDXT10Header ? sizeof(DDS_HEADER_DXT10) : 0u);
*bitData = ddsData + offset;
*bitSize = ddsDataSize - offset;
Expand Down Expand Up @@ -254,7 +261,7 @@ namespace
}

// Need at least enough data to fill the header and magic number to be a valid DDS
if (fileInfo.EndOfFile.LowPart < (sizeof(uint32_t) + sizeof(DDS_HEADER)))
if (fileInfo.EndOfFile.LowPart < DDS_MIN_HEADER_SIZE)
{
return E_FAIL;
}
Expand Down Expand Up @@ -286,7 +293,7 @@ namespace
}

// DDS files always start with the same magic number ("DDS ")
auto const dwMagicNumber = *reinterpret_cast<const uint32_t*>(ddsData.get());
const auto dwMagicNumber = *reinterpret_cast<const uint32_t*>(ddsData.get());
if (dwMagicNumber != DDS_MAGIC)
{
ddsData.reset();
Expand All @@ -309,7 +316,7 @@ namespace
(MAKEFOURCC('D', 'X', '1', '0') == hdr->ddspf.fourCC))
{
// Must be long enough for both headers and magic value
if (fileInfo.EndOfFile.LowPart < (sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10)))
if (fileInfo.EndOfFile.LowPart < DDS_DX10_HEADER_SIZE)
{
ddsData.reset();
return E_FAIL;
Expand All @@ -320,7 +327,7 @@ namespace

// setup the pointers in the process request
*header = hdr;
auto offset = sizeof(uint32_t) + sizeof(DDS_HEADER)
auto offset = DDS_MIN_HEADER_SIZE
+ (bDXT10Header ? sizeof(DDS_HEADER_DXT10) : 0u);
*bitData = ddsData.get() + offset;
*bitSize = fileInfo.EndOfFile.LowPart - offset;
Expand Down Expand Up @@ -484,7 +491,7 @@ namespace
_In_ size_t width,
_In_ size_t height,
_In_ DXGI_FORMAT fmt,
size_t* outNumBytes,
_Out_opt_ size_t* outNumBytes,
_Out_opt_ size_t* outRowBytes,
_Out_opt_ size_t* outNumRows) noexcept
{
Expand All @@ -498,6 +505,9 @@ namespace
size_t bpe = 0;
switch (fmt)
{
case DXGI_FORMAT_UNKNOWN:
return E_INVALIDARG;

case DXGI_FORMAT_BC1_TYPELESS:
case DXGI_FORMAT_BC1_UNORM:
case DXGI_FORMAT_BC1_UNORM_SRGB:
Expand Down Expand Up @@ -551,6 +561,15 @@ namespace
bpe = 2;
break;

#if (_WIN32_WINNT >= _WIN32_WINNT_WIN10)

case DXGI_FORMAT_P208:
planar = true;
bpe = 2;
break;

#endif

case DXGI_FORMAT_P010:
case DXGI_FORMAT_P016:
if ((height % 2) != 0)
Expand Down Expand Up @@ -1731,7 +1750,7 @@ namespace
if (MAKEFOURCC('D', 'X', '1', '0') == header->ddspf.fourCC)
{
auto d3d10ext = reinterpret_cast<const DDS_HEADER_DXT10*>(reinterpret_cast<const uint8_t*>(header) + sizeof(DDS_HEADER));
auto const mode = static_cast<DDS_ALPHA_MODE>(d3d10ext->miscFlags2 & DDS_MISC_FLAGS2_ALPHA_MODE_MASK);
const auto mode = static_cast<DDS_ALPHA_MODE>(d3d10ext->miscFlags2 & DDS_MISC_FLAGS2_ALPHA_MODE_MASK);
switch (mode)
{
case DDS_ALPHA_MODE_STRAIGHT:
Expand Down
19 changes: 14 additions & 5 deletions Core/ScreenGrab.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
#include <algorithm>
#include <cassert>
#include <cstddef>
#include <cstdint>
#include <cstring>
#include <memory>
#include <new>
Expand Down Expand Up @@ -62,7 +63,7 @@ namespace
{
#pragma pack(push,1)

#define DDS_MAGIC 0x20534444 // "DDS "
constexpr uint32_t DDS_MAGIC = 0x20534444; // "DDS "

struct DDS_PIXELFORMAT
{
Expand Down Expand Up @@ -120,6 +121,14 @@ namespace

#pragma pack(pop)

static_assert(sizeof(DDS_PIXELFORMAT) == 32, "DDS pixel format size mismatch");
static_assert(sizeof(DDS_HEADER) == 124, "DDS Header size mismatch");
static_assert(sizeof(DDS_HEADER_DXT10) == 20, "DDS DX10 Extended Header size mismatch");

constexpr size_t DDS_MIN_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER);
constexpr size_t DDS_DX10_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10);
static_assert(DDS_DX10_HEADER_SIZE > DDS_MIN_HEADER_SIZE, "DDS DX10 Header should be larger than standard header");

const DDS_PIXELFORMAT DDSPF_DXT1 =
{ sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','1'), 0, 0, 0, 0, 0 };

Expand Down Expand Up @@ -807,13 +816,13 @@ HRESULT DirectX::SaveDDSTextureToFile(
auto_delete_file delonfail(hFile.get());

// Setup header
constexpr size_t MAX_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10);
uint8_t fileHeader[MAX_HEADER_SIZE] = {};
uint8_t fileHeader[DDS_DX10_HEADER_SIZE] = {};


*reinterpret_cast<uint32_t*>(&fileHeader[0]) = DDS_MAGIC;

auto header = reinterpret_cast<DDS_HEADER*>(&fileHeader[0] + sizeof(uint32_t));
size_t headerSize = sizeof(uint32_t) + sizeof(DDS_HEADER);
size_t headerSize = DDS_MIN_HEADER_SIZE;
header->size = sizeof(DDS_HEADER);
header->flags = DDS_HEADER_FLAGS_TEXTURE | DDS_HEADER_FLAGS_MIPMAP;
header->height = desc.Height;
Expand Down Expand Up @@ -870,7 +879,7 @@ HRESULT DirectX::SaveDDSTextureToFile(
memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_DX10, sizeof(DDS_PIXELFORMAT));

headerSize += sizeof(DDS_HEADER_DXT10);
extHeader = reinterpret_cast<DDS_HEADER_DXT10*>(fileHeader + sizeof(uint32_t) + sizeof(DDS_HEADER));
extHeader = reinterpret_cast<DDS_HEADER_DXT10*>(fileHeader + DDS_MIN_HEADER_SIZE);
extHeader->dxgiFormat = desc.Format;
extHeader->resourceDimension = D3D11_RESOURCE_DIMENSION_TEXTURE2D;
extHeader->arraySize = 1;
Expand Down
2 changes: 1 addition & 1 deletion Core/ScreenGrab.h
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,6 @@ namespace DirectX
_In_ REFGUID guidContainerFormat,
_In_z_ const wchar_t* fileName,
_In_opt_ const GUID* targetFormat = nullptr,
std::function<void __cdecl(IPropertyBag2*)> setCustomProps = nullptr,
_In_ std::function<void __cdecl(IPropertyBag2*)> setCustomProps = nullptr,
_In_ bool forceSRGB = false);
}
13 changes: 7 additions & 6 deletions Core/WICTextureLoader.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -64,8 +64,7 @@ namespace
#else
template<UINT TNameLength>
inline void SetDebugObjectName(_In_ ID3D11DeviceChild*, _In_ const char(&)[TNameLength]) noexcept
{
}
{}
#endif

//-------------------------------------------------------------------------------------
Expand All @@ -78,7 +77,8 @@ namespace

constexpr WICTranslate(const GUID& wg, DXGI_FORMAT fmt) noexcept :
wic(wg),
format(fmt) {}
format(fmt)
{}
};

constexpr WICTranslate g_WICFormats[] =
Expand Down Expand Up @@ -116,7 +116,8 @@ namespace

constexpr WICConvert(const GUID& src, const GUID& tgt) noexcept :
source(src),
target(tgt) {}
target(tgt)
{}
};

constexpr WICConvert g_WICConvert[] =
Expand Down Expand Up @@ -594,8 +595,8 @@ namespace
if (rowBytes > UINT32_MAX || numBytes > UINT32_MAX)
return HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW);

auto const rowPitch = static_cast<size_t>(rowBytes);
auto const imageSize = static_cast<size_t>(numBytes);
const auto rowPitch = static_cast<size_t>(rowBytes);
const auto imageSize = static_cast<size_t>(numBytes);

std::unique_ptr<uint8_t[]> temp(new (std::nothrow) uint8_t[imageSize]);
if (!temp)
Expand Down
Loading