diff --git a/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader.cpp b/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader.cpp new file mode 100644 index 0000000..911e51a --- /dev/null +++ b/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader.cpp @@ -0,0 +1,1827 @@ +//-------------------------------------------------------------------------------------- +// File: DDSTextureLoader.cpp +// +// Functions for loading a DDS texture and creating a Direct3D runtime resource for it +// +// Note these functions are useful as a light-weight runtime loader for DDS files. For +// a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#include "DDSTextureLoader.h" + +#include +#include +#include + +#if !defined(NO_D3D11_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) +#pragma comment(lib,"dxguid.lib") +#endif + +using namespace DirectX; + +//-------------------------------------------------------------------------------------- +// Macros +//-------------------------------------------------------------------------------------- +#ifndef MAKEFOURCC + #define MAKEFOURCC(ch0, ch1, ch2, ch3) \ + ((uint32_t)(uint8_t)(ch0) | ((uint32_t)(uint8_t)(ch1) << 8) | \ + ((uint32_t)(uint8_t)(ch2) << 16) | ((uint32_t)(uint8_t)(ch3) << 24 )) +#endif /* defined(MAKEFOURCC) */ + +//-------------------------------------------------------------------------------------- +// DDS file structure definitions +// +// See DDS.h in the 'Texconv' sample and the 'DirectXTex' library +//-------------------------------------------------------------------------------------- +#pragma pack(push,1) + +const uint32_t DDS_MAGIC = 0x20534444; // "DDS " + +struct DDS_PIXELFORMAT +{ + uint32_t size; + uint32_t flags; + uint32_t fourCC; + uint32_t RGBBitCount; + uint32_t RBitMask; + uint32_t GBitMask; + uint32_t BBitMask; + uint32_t ABitMask; +}; + +#define DDS_FOURCC 0x00000004 // DDPF_FOURCC +#define DDS_RGB 0x00000040 // DDPF_RGB +#define DDS_LUMINANCE 0x00020000 // DDPF_LUMINANCE +#define DDS_ALPHA 0x00000002 // DDPF_ALPHA +#define DDS_BUMPDUDV 0x00080000 // DDPF_BUMPDUDV + +#define DDS_HEADER_FLAGS_VOLUME 0x00800000 // DDSD_DEPTH + +#define DDS_HEIGHT 0x00000002 // DDSD_HEIGHT +#define DDS_WIDTH 0x00000004 // DDSD_WIDTH + +#define DDS_CUBEMAP_POSITIVEX 0x00000600 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEX +#define DDS_CUBEMAP_NEGATIVEX 0x00000a00 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEX +#define DDS_CUBEMAP_POSITIVEY 0x00001200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEY +#define DDS_CUBEMAP_NEGATIVEY 0x00002200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEY +#define DDS_CUBEMAP_POSITIVEZ 0x00004200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEZ +#define DDS_CUBEMAP_NEGATIVEZ 0x00008200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEZ + +#define DDS_CUBEMAP_ALLFACES ( DDS_CUBEMAP_POSITIVEX | DDS_CUBEMAP_NEGATIVEX |\ + DDS_CUBEMAP_POSITIVEY | DDS_CUBEMAP_NEGATIVEY |\ + DDS_CUBEMAP_POSITIVEZ | DDS_CUBEMAP_NEGATIVEZ ) + +#define DDS_CUBEMAP 0x00000200 // DDSCAPS2_CUBEMAP + +enum DDS_MISC_FLAGS2 +{ + DDS_MISC_FLAGS2_ALPHA_MODE_MASK = 0x7L, +}; + +struct DDS_HEADER +{ + uint32_t size; + uint32_t flags; + uint32_t height; + uint32_t width; + uint32_t pitchOrLinearSize; + uint32_t depth; // only if DDS_HEADER_FLAGS_VOLUME is set in flags + uint32_t mipMapCount; + uint32_t reserved1[11]; + DDS_PIXELFORMAT ddspf; + uint32_t caps; + uint32_t caps2; + uint32_t caps3; + uint32_t caps4; + uint32_t reserved2; +}; + +struct DDS_HEADER_DXT10 +{ + DXGI_FORMAT dxgiFormat; + uint32_t resourceDimension; + uint32_t miscFlag; // see D3D11_RESOURCE_MISC_FLAG + uint32_t arraySize; + uint32_t miscFlags2; +}; + +#pragma pack(pop) + +//-------------------------------------------------------------------------------------- +namespace +{ + struct handle_closer { void operator()(HANDLE h) { if (h) CloseHandle(h); } }; + + typedef public std::unique_ptr ScopedHandle; + + inline HANDLE safe_handle( HANDLE h ) { return (h == INVALID_HANDLE_VALUE) ? 0 : h; } + + template + inline void SetDebugObjectName(_In_ ID3D11DeviceChild* resource, _In_ const char (&name)[TNameLength]) + { + #if defined(_DEBUG) || defined(PROFILE) + resource->SetPrivateData(WKPDID_D3DDebugObjectName, TNameLength - 1, name); + #else + UNREFERENCED_PARAMETER(resource); + UNREFERENCED_PARAMETER(name); + #endif + } + + //-------------------------------------------------------------------------------------- + HRESULT LoadTextureDataFromFile( + _In_z_ const wchar_t* fileName, + std::unique_ptr& ddsData, + const DDS_HEADER** header, + const uint8_t** bitData, + size_t* bitSize) + { + if (!header || !bitData || !bitSize) + { + return E_POINTER; + } + + // open the file +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(fileName, + GENERIC_READ, + FILE_SHARE_READ, + OPEN_EXISTING, + nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(fileName, + GENERIC_READ, + FILE_SHARE_READ, + nullptr, + OPEN_EXISTING, + FILE_ATTRIBUTE_NORMAL, + nullptr))); +#endif + + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // Get the file size + FILE_STANDARD_INFO fileInfo; + if (!GetFileInformationByHandleEx(hFile.get(), FileStandardInfo, &fileInfo, sizeof(fileInfo))) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // File is too big for 32-bit allocation, so reject read + if (fileInfo.EndOfFile.HighPart > 0) + { + return E_FAIL; + } + + // Need at least enough data to fill the header and magic number to be a valid DDS + if (fileInfo.EndOfFile.LowPart < (sizeof(DDS_HEADER) + sizeof(uint32_t))) + { + return E_FAIL; + } + + // create enough space for the file data + ddsData.reset(new (std::nothrow) uint8_t[fileInfo.EndOfFile.LowPart]); + if (!ddsData) + { + return E_OUTOFMEMORY; + } + + // read the data in + DWORD BytesRead = 0; + if (!ReadFile(hFile.get(), + ddsData.get(), + fileInfo.EndOfFile.LowPart, + &BytesRead, + nullptr + )) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (BytesRead < fileInfo.EndOfFile.LowPart) + { + return E_FAIL; + } + + // DDS files always start with the same magic number ("DDS ") + uint32_t dwMagicNumber = *reinterpret_cast(ddsData.get()); + if (dwMagicNumber != DDS_MAGIC) + { + return E_FAIL; + } + + auto hdr = reinterpret_cast(ddsData.get() + sizeof(uint32_t)); + + // Verify header to validate DDS file + if (hdr->size != sizeof(DDS_HEADER) || + hdr->ddspf.size != sizeof(DDS_PIXELFORMAT)) + { + return E_FAIL; + } + + // Check for DX10 extension + bool bDXT10Header = false; + if ((hdr->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC('D', 'X', '1', '0') == hdr->ddspf.fourCC)) + { + // Must be long enough for both headers and magic value + if (fileInfo.EndOfFile.LowPart < (sizeof(DDS_HEADER) + sizeof(uint32_t) + sizeof(DDS_HEADER_DXT10))) + { + return E_FAIL; + } + + bDXT10Header = true; + } + + // setup the pointers in the process request + *header = hdr; + ptrdiff_t offset = sizeof(uint32_t) + sizeof(DDS_HEADER) + + (bDXT10Header ? sizeof(DDS_HEADER_DXT10) : 0); + *bitData = ddsData.get() + offset; + *bitSize = fileInfo.EndOfFile.LowPart - offset; + + return S_OK; + } + + + //-------------------------------------------------------------------------------------- + // Return the BPP for a particular format + //-------------------------------------------------------------------------------------- + size_t BitsPerPixel(_In_ DXGI_FORMAT fmt) + { + switch (fmt) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + return 128; + + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return 96; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_R32G32_TYPELESS: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + return 64; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R11G11B10_FLOAT: + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_R16G16_TYPELESS: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + case DXGI_FORMAT_R32_TYPELESS: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_YUY2: + return 32; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + return 24; + + case DXGI_FORMAT_R8G8_TYPELESS: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + case DXGI_FORMAT_R16_TYPELESS: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_A8P8: + case DXGI_FORMAT_B4G4R4A4_UNORM: + return 16; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + case DXGI_FORMAT_NV11: + return 12; + + case DXGI_FORMAT_R8_TYPELESS: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + return 8; + + case DXGI_FORMAT_R1_UNORM: + return 1; + + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + return 4; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return 8; + + default: + return 0; + } + } + + + //-------------------------------------------------------------------------------------- + // Get surface information for a particular format + //-------------------------------------------------------------------------------------- + void GetSurfaceInfo( + _In_ size_t width, + _In_ size_t height, + _In_ DXGI_FORMAT fmt, + size_t* outNumBytes, + _Out_opt_ size_t* outRowBytes, + _Out_opt_ size_t* outNumRows) + { + size_t numBytes = 0; + size_t rowBytes = 0; + size_t numRows = 0; + + bool bc = false; + bool packed = false; + bool planar = false; + size_t bpe = 0; + switch (fmt) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + bc = true; + bpe = 8; + break; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + bc = true; + bpe = 16; + break; + + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_YUY2: + packed = true; + bpe = 4; + break; + + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + packed = true; + bpe = 8; + break; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + planar = true; + bpe = 2; + break; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + planar = true; + bpe = 4; + break; + } + + if (bc) + { + size_t numBlocksWide = 0; + if (width > 0) + { + numBlocksWide = std::max(1, (width + 3) / 4); + } + size_t numBlocksHigh = 0; + if (height > 0) + { + numBlocksHigh = std::max(1, (height + 3) / 4); + } + rowBytes = numBlocksWide * bpe; + numRows = numBlocksHigh; + numBytes = rowBytes * numBlocksHigh; + } + else if (packed) + { + rowBytes = ((width + 1) >> 1) * bpe; + numRows = height; + numBytes = rowBytes * height; + } + else if (fmt == DXGI_FORMAT_NV11) + { + rowBytes = ((width + 3) >> 2) * 4; + numRows = height * 2; // Direct3D makes this simplifying assumption, although it is larger than the 4:1:1 data + numBytes = rowBytes * numRows; + } + else if (planar) + { + rowBytes = ((width + 1) >> 1) * bpe; + numBytes = (rowBytes * height) + ((rowBytes * height + 1) >> 1); + numRows = height + ((height + 1) >> 1); + } + else + { + size_t bpp = BitsPerPixel(fmt); + rowBytes = (width * bpp + 7) / 8; // round up to nearest byte + numRows = height; + numBytes = rowBytes * height; + } + + if (outNumBytes) + { + *outNumBytes = numBytes; + } + if (outRowBytes) + { + *outRowBytes = rowBytes; + } + if (outNumRows) + { + *outNumRows = numRows; + } + } + + + //-------------------------------------------------------------------------------------- + #define ISBITMASK( r,g,b,a ) ( ddpf.RBitMask == r && ddpf.GBitMask == g && ddpf.BBitMask == b && ddpf.ABitMask == a ) + + DXGI_FORMAT GetDXGIFormat(const DDS_PIXELFORMAT& ddpf) + { + if (ddpf.flags & DDS_RGB) + { + // Note that sRGB formats are written using the "DX10" extended header + + switch (ddpf.RGBBitCount) + { + case 32: + if (ISBITMASK(0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000)) + { + return DXGI_FORMAT_R8G8B8A8_UNORM; + } + + if (ISBITMASK(0x00ff0000, 0x0000ff00, 0x000000ff, 0xff000000)) + { + return DXGI_FORMAT_B8G8R8A8_UNORM; + } + + if (ISBITMASK(0x00ff0000, 0x0000ff00, 0x000000ff, 0x00000000)) + { + return DXGI_FORMAT_B8G8R8X8_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x000000ff,0x0000ff00,0x00ff0000,0x00000000) aka D3DFMT_X8B8G8R8 + + // Note that many common DDS reader/writers (including D3DX) swap the + // the RED/BLUE masks for 10:10:10:2 formats. We assume + // below that the 'backwards' header mask is being used since it is most + // likely written by D3DX. The more robust solution is to use the 'DX10' + // header extension and specify the DXGI_FORMAT_R10G10B10A2_UNORM format directly + + // For 'correct' writers, this should be 0x000003ff,0x000ffc00,0x3ff00000 for RGB data + if (ISBITMASK(0x3ff00000, 0x000ffc00, 0x000003ff, 0xc0000000)) + { + return DXGI_FORMAT_R10G10B10A2_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x000003ff,0x000ffc00,0x3ff00000,0xc0000000) aka D3DFMT_A2R10G10B10 + + if (ISBITMASK(0x0000ffff, 0xffff0000, 0x00000000, 0x00000000)) + { + return DXGI_FORMAT_R16G16_UNORM; + } + + if (ISBITMASK(0xffffffff, 0x00000000, 0x00000000, 0x00000000)) + { + // Only 32-bit color channel format in D3D9 was R32F + return DXGI_FORMAT_R32_FLOAT; // D3DX writes this out as a FourCC of 114 + } + break; + + case 24: + // No 24bpp DXGI formats aka D3DFMT_R8G8B8 + break; + + case 16: + if (ISBITMASK(0x7c00, 0x03e0, 0x001f, 0x8000)) + { + return DXGI_FORMAT_B5G5R5A1_UNORM; + } + if (ISBITMASK(0xf800, 0x07e0, 0x001f, 0x0000)) + { + return DXGI_FORMAT_B5G6R5_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x7c00,0x03e0,0x001f,0x0000) aka D3DFMT_X1R5G5B5 + + if (ISBITMASK(0x0f00, 0x00f0, 0x000f, 0xf000)) + { + return DXGI_FORMAT_B4G4R4A4_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x0f00,0x00f0,0x000f,0x0000) aka D3DFMT_X4R4G4B4 + + // No 3:3:2, 3:3:2:8, or paletted DXGI formats aka D3DFMT_A8R3G3B2, D3DFMT_R3G3B2, D3DFMT_P8, D3DFMT_A8P8, etc. + break; + } + } + else if (ddpf.flags & DDS_LUMINANCE) + { + if (8 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x000000ff, 0x00000000, 0x00000000, 0x00000000)) + { + return DXGI_FORMAT_R8_UNORM; // D3DX10/11 writes this out as DX10 extension + } + + // No DXGI format maps to ISBITMASK(0x0f,0x00,0x00,0xf0) aka D3DFMT_A4L4 + + if (ISBITMASK(0x000000ff, 0x00000000, 0x00000000, 0x0000ff00)) + { + return DXGI_FORMAT_R8G8_UNORM; // Some DDS writers assume the bitcount should be 8 instead of 16 + } + } + + if (16 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x0000ffff, 0x00000000, 0x00000000, 0x00000000)) + { + return DXGI_FORMAT_R16_UNORM; // D3DX10/11 writes this out as DX10 extension + } + if (ISBITMASK(0x000000ff, 0x00000000, 0x00000000, 0x0000ff00)) + { + return DXGI_FORMAT_R8G8_UNORM; // D3DX10/11 writes this out as DX10 extension + } + } + } + else if (ddpf.flags & DDS_ALPHA) + { + if (8 == ddpf.RGBBitCount) + { + return DXGI_FORMAT_A8_UNORM; + } + } + else if (ddpf.flags & DDS_BUMPDUDV) + { + if (16 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x00ff, 0xff00, 0x0000, 0x0000)) + { + return DXGI_FORMAT_R8G8_SNORM; // D3DX10/11 writes this out as DX10 extension + } + } + + if (32 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000)) + { + return DXGI_FORMAT_R8G8B8A8_SNORM; // D3DX10/11 writes this out as DX10 extension + } + if (ISBITMASK(0x0000ffff, 0xffff0000, 0x00000000, 0x00000000)) + { + return DXGI_FORMAT_R16G16_SNORM; // D3DX10/11 writes this out as DX10 extension + } + + // No DXGI format maps to ISBITMASK(0x3ff00000, 0x000ffc00, 0x000003ff, 0xc0000000) aka D3DFMT_A2W10V10U10 + } + } + else if (ddpf.flags & DDS_FOURCC) + { + if (MAKEFOURCC('D', 'X', 'T', '1') == ddpf.fourCC) + { + return DXGI_FORMAT_BC1_UNORM; + } + if (MAKEFOURCC('D', 'X', 'T', '3') == ddpf.fourCC) + { + return DXGI_FORMAT_BC2_UNORM; + } + if (MAKEFOURCC('D', 'X', 'T', '5') == ddpf.fourCC) + { + return DXGI_FORMAT_BC3_UNORM; + } + + // While pre-multiplied alpha isn't directly supported by the DXGI formats, + // they are basically the same as these BC formats so they can be mapped + if (MAKEFOURCC('D', 'X', 'T', '2') == ddpf.fourCC) + { + return DXGI_FORMAT_BC2_UNORM; + } + if (MAKEFOURCC('D', 'X', 'T', '4') == ddpf.fourCC) + { + return DXGI_FORMAT_BC3_UNORM; + } + + if (MAKEFOURCC('A', 'T', 'I', '1') == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_UNORM; + } + if (MAKEFOURCC('B', 'C', '4', 'U') == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_UNORM; + } + if (MAKEFOURCC('B', 'C', '4', 'S') == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_SNORM; + } + + if (MAKEFOURCC('A', 'T', 'I', '2') == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_UNORM; + } + if (MAKEFOURCC('B', 'C', '5', 'U') == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_UNORM; + } + if (MAKEFOURCC('B', 'C', '5', 'S') == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_SNORM; + } + + // BC6H and BC7 are written using the "DX10" extended header + + if (MAKEFOURCC('R', 'G', 'B', 'G') == ddpf.fourCC) + { + return DXGI_FORMAT_R8G8_B8G8_UNORM; + } + if (MAKEFOURCC('G', 'R', 'G', 'B') == ddpf.fourCC) + { + return DXGI_FORMAT_G8R8_G8B8_UNORM; + } + + if (MAKEFOURCC('Y', 'U', 'Y', '2') == ddpf.fourCC) + { + return DXGI_FORMAT_YUY2; + } + + // Check for D3DFORMAT enums being set here + switch (ddpf.fourCC) + { + case 36: // D3DFMT_A16B16G16R16 + return DXGI_FORMAT_R16G16B16A16_UNORM; + + case 110: // D3DFMT_Q16W16V16U16 + return DXGI_FORMAT_R16G16B16A16_SNORM; + + case 111: // D3DFMT_R16F + return DXGI_FORMAT_R16_FLOAT; + + case 112: // D3DFMT_G16R16F + return DXGI_FORMAT_R16G16_FLOAT; + + case 113: // D3DFMT_A16B16G16R16F + return DXGI_FORMAT_R16G16B16A16_FLOAT; + + case 114: // D3DFMT_R32F + return DXGI_FORMAT_R32_FLOAT; + + case 115: // D3DFMT_G32R32F + return DXGI_FORMAT_R32G32_FLOAT; + + case 116: // D3DFMT_A32B32G32R32F + return DXGI_FORMAT_R32G32B32A32_FLOAT; + } + } + + return DXGI_FORMAT_UNKNOWN; + } + + + //-------------------------------------------------------------------------------------- + DXGI_FORMAT MakeSRGB(_In_ DXGI_FORMAT format) + { + switch (format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + return DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + + case DXGI_FORMAT_BC1_UNORM: + return DXGI_FORMAT_BC1_UNORM_SRGB; + + case DXGI_FORMAT_BC2_UNORM: + return DXGI_FORMAT_BC2_UNORM_SRGB; + + case DXGI_FORMAT_BC3_UNORM: + return DXGI_FORMAT_BC3_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + return DXGI_FORMAT_B8G8R8A8_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + return DXGI_FORMAT_B8G8R8X8_UNORM_SRGB; + + case DXGI_FORMAT_BC7_UNORM: + return DXGI_FORMAT_BC7_UNORM_SRGB; + + default: + return format; + } + } + + + //-------------------------------------------------------------------------------------- + HRESULT FillInitData( + _In_ size_t width, + _In_ size_t height, + _In_ size_t depth, + _In_ size_t mipCount, + _In_ size_t arraySize, + _In_ DXGI_FORMAT format, + _In_ size_t maxsize, + _In_ size_t bitSize, + _In_reads_bytes_(bitSize) const uint8_t* bitData, + _Out_ size_t& twidth, + _Out_ size_t& theight, + _Out_ size_t& tdepth, + _Out_ size_t& skipMip, + _Out_writes_(mipCount*arraySize) D3D11_SUBRESOURCE_DATA* initData) + { + if (!bitData || !initData) + { + return E_POINTER; + } + + skipMip = 0; + twidth = 0; + theight = 0; + tdepth = 0; + + size_t NumBytes = 0; + size_t RowBytes = 0; + const uint8_t* pSrcBits = bitData; + const uint8_t* pEndBits = bitData + bitSize; + + size_t index = 0; + for (size_t j = 0; j < arraySize; j++) + { + size_t w = width; + size_t h = height; + size_t d = depth; + for (size_t i = 0; i < mipCount; i++) + { + GetSurfaceInfo(w, + h, + format, + &NumBytes, + &RowBytes, + nullptr + ); + + if ((mipCount <= 1) || !maxsize || (w <= maxsize && h <= maxsize && d <= maxsize)) + { + if (!twidth) + { + twidth = w; + theight = h; + tdepth = d; + } + + assert(index < mipCount * arraySize); + _Analysis_assume_(index < mipCount * arraySize); + initData[index].pSysMem = (const void*)pSrcBits; + initData[index].SysMemPitch = static_cast(RowBytes); + initData[index].SysMemSlicePitch = static_cast(NumBytes); + ++index; + } + else if (!j) + { + // Count number of skipped mipmaps (first item only) + ++skipMip; + } + + if (pSrcBits + (NumBytes*d) > pEndBits) + { + return HRESULT_FROM_WIN32(ERROR_HANDLE_EOF); + } + + pSrcBits += NumBytes * d; + + w = w >> 1; + h = h >> 1; + d = d >> 1; + if (w == 0) + { + w = 1; + } + if (h == 0) + { + h = 1; + } + if (d == 0) + { + d = 1; + } + } + } + + return (index > 0) ? S_OK : E_FAIL; + } + + + //-------------------------------------------------------------------------------------- + HRESULT CreateD3DResources( + _In_ ID3D11Device* d3dDevice, + _In_ uint32_t resDim, + _In_ size_t width, + _In_ size_t height, + _In_ size_t depth, + _In_ size_t mipCount, + _In_ size_t arraySize, + _In_ DXGI_FORMAT format, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _In_ bool isCubeMap, + _In_reads_opt_(mipCount*arraySize) D3D11_SUBRESOURCE_DATA* initData, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView) + { + if (!d3dDevice) + return E_POINTER; + + HRESULT hr = E_FAIL; + + if (forceSRGB) + { + format = MakeSRGB(format); + } + + switch (resDim) + { + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + { + D3D11_TEXTURE1D_DESC desc; + desc.Width = static_cast(width); + desc.MipLevels = static_cast(mipCount); + desc.ArraySize = static_cast(arraySize); + desc.Format = format; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + desc.MiscFlags = miscFlags & ~D3D11_RESOURCE_MISC_TEXTURECUBE; + + ID3D11Texture1D* tex = nullptr; + hr = d3dDevice->CreateTexture1D(&desc, + initData, + &tex + ); + if (SUCCEEDED(hr) && tex != 0) + { + if (textureView != 0) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc = {}; + SRVDesc.Format = format; + + if (arraySize > 1) + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE1DARRAY; + SRVDesc.Texture1DArray.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + SRVDesc.Texture1DArray.ArraySize = static_cast(arraySize); + } + else + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE1D; + SRVDesc.Texture1D.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + } + + hr = d3dDevice->CreateShaderResourceView(tex, + &SRVDesc, + textureView + ); + if (FAILED(hr)) + { + tex->Release(); + return hr; + } + } + + if (texture != 0) + { + *texture = tex; + } + else + { + SetDebugObjectName(tex, "DDSTextureLoader"); + tex->Release(); + } + } + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + { + D3D11_TEXTURE2D_DESC desc; + desc.Width = static_cast(width); + desc.Height = static_cast(height); + desc.MipLevels = static_cast(mipCount); + desc.ArraySize = static_cast(arraySize); + desc.Format = format; + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + if (isCubeMap) + { + desc.MiscFlags = miscFlags | D3D11_RESOURCE_MISC_TEXTURECUBE; + } + else + { + desc.MiscFlags = miscFlags & ~D3D11_RESOURCE_MISC_TEXTURECUBE; + } + + ID3D11Texture2D* tex = nullptr; + hr = d3dDevice->CreateTexture2D(&desc, + initData, + &tex + ); + if (SUCCEEDED(hr) && tex != 0) + { + if (textureView != 0) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc = {}; + SRVDesc.Format = format; + + if (isCubeMap) + { + if (arraySize > 6) + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBEARRAY; + SRVDesc.TextureCubeArray.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + + // Earlier we set arraySize to (NumCubes * 6) + SRVDesc.TextureCubeArray.NumCubes = static_cast(arraySize / 6); + } + else + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBE; + SRVDesc.TextureCube.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + } + } + else if (arraySize > 1) + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY; + SRVDesc.Texture2DArray.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + SRVDesc.Texture2DArray.ArraySize = static_cast(arraySize); + } + else + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + SRVDesc.Texture2D.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + } + + hr = d3dDevice->CreateShaderResourceView(tex, + &SRVDesc, + textureView + ); + if (FAILED(hr)) + { + tex->Release(); + return hr; + } + } + + if (texture != 0) + { + *texture = tex; + } + else + { + SetDebugObjectName(tex, "DDSTextureLoader"); + tex->Release(); + } + } + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + { + D3D11_TEXTURE3D_DESC desc; + desc.Width = static_cast(width); + desc.Height = static_cast(height); + desc.Depth = static_cast(depth); + desc.MipLevels = static_cast(mipCount); + desc.Format = format; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + desc.MiscFlags = miscFlags & ~D3D11_RESOURCE_MISC_TEXTURECUBE; + + ID3D11Texture3D* tex = nullptr; + hr = d3dDevice->CreateTexture3D(&desc, + initData, + &tex + ); + if (SUCCEEDED(hr) && tex != 0) + { + if (textureView != 0) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc = {}; + SRVDesc.Format = format; + + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE3D; + SRVDesc.Texture3D.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + + hr = d3dDevice->CreateShaderResourceView(tex, + &SRVDesc, + textureView + ); + if (FAILED(hr)) + { + tex->Release(); + return hr; + } + } + + if (texture != 0) + { + *texture = tex; + } + else + { + SetDebugObjectName(tex, "DDSTextureLoader"); + tex->Release(); + } + } + } + break; + } + + return hr; + } + + + //-------------------------------------------------------------------------------------- + HRESULT CreateTextureFromDDS( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_ const DDS_HEADER* header, + _In_reads_bytes_(bitSize) const uint8_t* bitData, + _In_ size_t bitSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView) + { + HRESULT hr = S_OK; + + UINT width = header->width; + UINT height = header->height; + UINT depth = header->depth; + + uint32_t resDim = D3D11_RESOURCE_DIMENSION_UNKNOWN; + UINT arraySize = 1; + DXGI_FORMAT format = DXGI_FORMAT_UNKNOWN; + bool isCubeMap = false; + + size_t mipCount = header->mipMapCount; + if (0 == mipCount) + { + mipCount = 1; + } + + if ((header->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC('D', 'X', '1', '0') == header->ddspf.fourCC)) + { + auto d3d10ext = reinterpret_cast((const char*)header + sizeof(DDS_HEADER)); + + arraySize = d3d10ext->arraySize; + if (arraySize == 0) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + switch (d3d10ext->dxgiFormat) + { + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case DXGI_FORMAT_A8P8: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + default: + if (BitsPerPixel(d3d10ext->dxgiFormat) == 0) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } + + format = d3d10ext->dxgiFormat; + + switch (d3d10ext->resourceDimension) + { + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + // D3DX writes 1D textures with a fixed Height of 1 + if ((header->flags & DDS_HEIGHT) && height != 1) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + height = depth = 1; + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + if (d3d10ext->miscFlag & D3D11_RESOURCE_MISC_TEXTURECUBE) + { + arraySize *= 6; + isCubeMap = true; + } + depth = 1; + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + if (!(header->flags & DDS_HEADER_FLAGS_VOLUME)) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + if (arraySize > 1) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + resDim = d3d10ext->resourceDimension; + } + else + { + format = GetDXGIFormat(header->ddspf); + + if (format == DXGI_FORMAT_UNKNOWN) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + if (header->flags & DDS_HEADER_FLAGS_VOLUME) + { + resDim = D3D11_RESOURCE_DIMENSION_TEXTURE3D; + } + else + { + if (header->caps2 & DDS_CUBEMAP) + { + // We require all six faces to be defined + if ((header->caps2 & DDS_CUBEMAP_ALLFACES) != DDS_CUBEMAP_ALLFACES) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + arraySize = 6; + isCubeMap = true; + } + + depth = 1; + resDim = D3D11_RESOURCE_DIMENSION_TEXTURE2D; + + // Note there's no way for a legacy Direct3D 9 DDS to express a '1D' texture + } + + assert(BitsPerPixel(format) != 0); + } + + // Bound sizes (for security purposes we don't trust DDS file metadata larger than the D3D 11.x hardware requirements) + if (mipCount > D3D11_REQ_MIP_LEVELS) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + switch (resDim) + { + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + if ((arraySize > D3D11_REQ_TEXTURE1D_ARRAY_AXIS_DIMENSION) || + (width > D3D11_REQ_TEXTURE1D_U_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + if (isCubeMap) + { + // This is the right bound because we set arraySize to (NumCubes*6) above + if ((arraySize > D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) || + (width > D3D11_REQ_TEXTURECUBE_DIMENSION) || + (height > D3D11_REQ_TEXTURECUBE_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } + else if ((arraySize > D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) || + (width > D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION) || + (height > D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + if ((arraySize > 1) || + (width > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) || + (height > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) || + (depth > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + bool autogen = false; + if (mipCount == 1 && d3dContext != 0 && textureView != 0) // Must have context and shader-view to auto generate mipmaps + { + // See if format is supported for auto-gen mipmaps (varies by feature level) + UINT fmtSupport = 0; + hr = d3dDevice->CheckFormatSupport(format, &fmtSupport); + if (SUCCEEDED(hr) && (fmtSupport & D3D11_FORMAT_SUPPORT_MIP_AUTOGEN)) + { + // 10level9 feature levels do not support auto-gen mipgen for volume textures + if ((resDim != D3D11_RESOURCE_DIMENSION_TEXTURE3D) + || (d3dDevice->GetFeatureLevel() >= D3D_FEATURE_LEVEL_10_0)) + { + autogen = true; + } + } + } + + if (autogen) + { + // Create texture with auto-generated mipmaps + ID3D11Resource* tex = nullptr; + hr = CreateD3DResources(d3dDevice, resDim, width, height, depth, 0, arraySize, + format, usage, + bindFlags | D3D11_BIND_RENDER_TARGET, + cpuAccessFlags, + miscFlags | D3D11_RESOURCE_MISC_GENERATE_MIPS, forceSRGB, + isCubeMap, nullptr, &tex, textureView); + if (SUCCEEDED(hr)) + { + size_t numBytes = 0; + size_t rowBytes = 0; + GetSurfaceInfo(width, height, format, &numBytes, &rowBytes, nullptr); + + if (numBytes > bitSize) + { + (*textureView)->Release(); + *textureView = nullptr; + tex->Release(); + return HRESULT_FROM_WIN32(ERROR_HANDLE_EOF); + } + + D3D11_SHADER_RESOURCE_VIEW_DESC desc; + (*textureView)->GetDesc(&desc); + + UINT mipLevels = 1; + + switch (desc.ViewDimension) + { + case D3D_SRV_DIMENSION_TEXTURE1D: mipLevels = desc.Texture1D.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE1DARRAY: mipLevels = desc.Texture1DArray.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE2D: mipLevels = desc.Texture2D.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE2DARRAY: mipLevels = desc.Texture2DArray.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURECUBE: mipLevels = desc.TextureCube.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURECUBEARRAY:mipLevels = desc.TextureCubeArray.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE3D: mipLevels = desc.Texture3D.MipLevels; break; + default: + (*textureView)->Release(); + *textureView = nullptr; + tex->Release(); + return E_UNEXPECTED; + } + + if (arraySize > 1) + { + const uint8_t* pSrcBits = bitData; + const uint8_t* pEndBits = bitData + bitSize; + for (UINT item = 0; item < arraySize; ++item) + { + if ((pSrcBits + numBytes) > pEndBits) + { + (*textureView)->Release(); + *textureView = nullptr; + tex->Release(); + return HRESULT_FROM_WIN32(ERROR_HANDLE_EOF); + } + + UINT res = D3D11CalcSubresource(0, item, mipLevels); + d3dContext->UpdateSubresource(tex, res, nullptr, pSrcBits, static_cast(rowBytes), static_cast(numBytes)); + pSrcBits += numBytes; + } + } + else + { + d3dContext->UpdateSubresource(tex, 0, nullptr, bitData, static_cast(rowBytes), static_cast(numBytes)); + } + + d3dContext->GenerateMips(*textureView); + + if (texture) + { + *texture = tex; + } + else + { + tex->Release(); + } + } + } + else + { + // Create the texture + std::unique_ptr initData(new (std::nothrow) D3D11_SUBRESOURCE_DATA[mipCount * arraySize]); + if (!initData) + { + return E_OUTOFMEMORY; + } + + size_t skipMip = 0; + size_t twidth = 0; + size_t theight = 0; + size_t tdepth = 0; + hr = FillInitData(width, height, depth, mipCount, arraySize, format, maxsize, bitSize, bitData, + twidth, theight, tdepth, skipMip, initData.get()); + + if (SUCCEEDED(hr)) + { + hr = CreateD3DResources(d3dDevice, resDim, twidth, theight, tdepth, mipCount - skipMip, arraySize, + format, usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + isCubeMap, initData.get(), texture, textureView); + + if (FAILED(hr) && !maxsize && (mipCount > 1)) + { + // Retry with a maxsize determined by feature level + switch (d3dDevice->GetFeatureLevel()) + { + case D3D_FEATURE_LEVEL_9_1: + case D3D_FEATURE_LEVEL_9_2: + if (isCubeMap) + { + maxsize = 512 /*D3D_FL9_1_REQ_TEXTURECUBE_DIMENSION*/; + } + else + { + maxsize = (resDim == D3D11_RESOURCE_DIMENSION_TEXTURE3D) + ? 256 /*D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION*/ + : 2048 /*D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + } + break; + + case D3D_FEATURE_LEVEL_9_3: + maxsize = (resDim == D3D11_RESOURCE_DIMENSION_TEXTURE3D) + ? 256 /*D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION*/ + : 4096 /*D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + + default: // D3D_FEATURE_LEVEL_10_0 & D3D_FEATURE_LEVEL_10_1 + maxsize = (resDim == D3D11_RESOURCE_DIMENSION_TEXTURE3D) + ? 2048 /*D3D10_REQ_TEXTURE3D_U_V_OR_W_DIMENSION*/ + : 8192 /*D3D10_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + } + + hr = FillInitData(width, height, depth, mipCount, arraySize, format, maxsize, bitSize, bitData, + twidth, theight, tdepth, skipMip, initData.get()); + if (SUCCEEDED(hr)) + { + hr = CreateD3DResources(d3dDevice, resDim, twidth, theight, tdepth, mipCount - skipMip, arraySize, + format, usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + isCubeMap, initData.get(), texture, textureView); + } + } + } + } + + return hr; + } + + + //-------------------------------------------------------------------------------------- + DDS_ALPHA_MODE GetAlphaMode(_In_ const DDS_HEADER* header) + { + if (header->ddspf.flags & DDS_FOURCC) + { + if (MAKEFOURCC('D', 'X', '1', '0') == header->ddspf.fourCC) + { + auto d3d10ext = reinterpret_cast((const char*)header + sizeof(DDS_HEADER)); + auto mode = static_cast(d3d10ext->miscFlags2 & DDS_MISC_FLAGS2_ALPHA_MODE_MASK); + switch (mode) + { + case DDS_ALPHA_MODE_STRAIGHT: + case DDS_ALPHA_MODE_PREMULTIPLIED: + case DDS_ALPHA_MODE_OPAQUE: + case DDS_ALPHA_MODE_CUSTOM: + return mode; + } + } + else if ((MAKEFOURCC('D', 'X', 'T', '2') == header->ddspf.fourCC) + || (MAKEFOURCC('D', 'X', 'T', '4') == header->ddspf.fourCC)) + { + return DDS_ALPHA_MODE_PREMULTIPLIED; + } + } + + return DDS_ALPHA_MODE_UNKNOWN; + } +} // anonymous namespace + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemory(ID3D11Device* d3dDevice, + const uint8_t* ddsData, + size_t ddsDataSize, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode) +{ + return CreateDDSTextureFromMemoryEx(d3dDevice, nullptr, ddsData, ddsDataSize, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, false, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemory(ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const uint8_t* ddsData, + size_t ddsDataSize, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode) +{ + return CreateDDSTextureFromMemoryEx(d3dDevice, d3dContext, ddsData, ddsDataSize, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, false, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemoryEx(ID3D11Device* d3dDevice, + const uint8_t* ddsData, + size_t ddsDataSize, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode) +{ + return CreateDDSTextureFromMemoryEx(d3dDevice, nullptr, ddsData, ddsDataSize, maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemoryEx(ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const uint8_t* ddsData, + size_t ddsDataSize, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode) +{ + if (texture) + { + *texture = nullptr; + } + if (textureView) + { + *textureView = nullptr; + } + if (alphaMode) + { + *alphaMode = DDS_ALPHA_MODE_UNKNOWN; + } + + if (!d3dDevice || !ddsData || (!texture && !textureView)) + { + return E_INVALIDARG; + } + + // Validate DDS file in memory + if (ddsDataSize < (sizeof(uint32_t) + sizeof(DDS_HEADER))) + { + return E_FAIL; + } + + uint32_t dwMagicNumber = *(const uint32_t*)(ddsData); + if (dwMagicNumber != DDS_MAGIC) + { + return E_FAIL; + } + + auto header = reinterpret_cast(ddsData + sizeof(uint32_t)); + + // Verify header to validate DDS file + if (header->size != sizeof(DDS_HEADER) || + header->ddspf.size != sizeof(DDS_PIXELFORMAT)) + { + return E_FAIL; + } + + // Check for DX10 extension + bool bDXT10Header = false; + if ((header->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC('D', 'X', '1', '0') == header->ddspf.fourCC)) + { + // Must be long enough for both headers and magic value + if (ddsDataSize < (sizeof(DDS_HEADER) + sizeof(uint32_t) + sizeof(DDS_HEADER_DXT10))) + { + return E_FAIL; + } + + bDXT10Header = true; + } + + ptrdiff_t offset = sizeof(uint32_t) + + sizeof(DDS_HEADER) + + (bDXT10Header ? sizeof(DDS_HEADER_DXT10) : 0); + + HRESULT hr = CreateTextureFromDDS(d3dDevice, d3dContext, header, + ddsData + offset, ddsDataSize - offset, maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + texture, textureView); + if (SUCCEEDED(hr)) + { + if (texture != 0 && *texture != 0) + { + SetDebugObjectName(*texture, "DDSTextureLoader"); + } + + if (textureView != 0 && *textureView != 0) + { + SetDebugObjectName(*textureView, "DDSTextureLoader"); + } + + if (alphaMode) + *alphaMode = GetAlphaMode(header); + } + + return hr; +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFile(ID3D11Device* d3dDevice, + const wchar_t* fileName, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode) +{ + return CreateDDSTextureFromFileEx(d3dDevice, nullptr, fileName, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, false, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFile(ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const wchar_t* fileName, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode) +{ + return CreateDDSTextureFromFileEx(d3dDevice, d3dContext, fileName, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, false, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFileEx(ID3D11Device* d3dDevice, + const wchar_t* fileName, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode) +{ + return CreateDDSTextureFromFileEx(d3dDevice, nullptr, fileName, maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFileEx(ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const wchar_t* fileName, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode) +{ + if (texture) + { + *texture = nullptr; + } + if (textureView) + { + *textureView = nullptr; + } + if (alphaMode) + { + *alphaMode = DDS_ALPHA_MODE_UNKNOWN; + } + + if (!d3dDevice || !fileName || (!texture && !textureView)) + { + return E_INVALIDARG; + } + + const DDS_HEADER* header = nullptr; + const uint8_t* bitData = nullptr; + size_t bitSize = 0; + + std::unique_ptr ddsData; + HRESULT hr = LoadTextureDataFromFile(fileName, + ddsData, + &header, + &bitData, + &bitSize + ); + if (FAILED(hr)) + { + return hr; + } + + hr = CreateTextureFromDDS(d3dDevice, d3dContext, header, + bitData, bitSize, maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + texture, textureView); + + if (SUCCEEDED(hr)) + { +#if !defined(NO_D3D11_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) + if (texture != 0 || textureView != 0) + { + CHAR strFileA[MAX_PATH]; + int result = WideCharToMultiByte(CP_ACP, + WC_NO_BEST_FIT_CHARS, + fileName, + -1, + strFileA, + MAX_PATH, + nullptr, + FALSE + ); + if (result > 0) + { + const CHAR* pstrName = strrchr(strFileA, '\\'); + if (!pstrName) + { + pstrName = strFileA; + } + else + { + pstrName++; + } + + if (texture != 0 && *texture != 0) + { + (*texture)->SetPrivateData(WKPDID_D3DDebugObjectName, + static_cast(strnlen_s(pstrName, MAX_PATH)), + pstrName + ); + } + + if (textureView != 0 && *textureView != 0) + { + (*textureView)->SetPrivateData(WKPDID_D3DDebugObjectName, + static_cast(strnlen_s(pstrName, MAX_PATH)), + pstrName + ); + } + } + } +#endif + + if (alphaMode) + *alphaMode = GetAlphaMode(header); + } + + return hr; +} diff --git a/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader.h b/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader.h new file mode 100644 index 0000000..b170226 --- /dev/null +++ b/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader.h @@ -0,0 +1,133 @@ +//-------------------------------------------------------------------------------------- +// File: DDSTextureLoader.h +// +// Functions for loading a DDS texture and creating a Direct3D runtime resource for it +// +// Note these functions are useful as a light-weight runtime loader for DDS files. For +// a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#pragma once + +#include +#include + + +namespace DirectX +{ + enum DDS_ALPHA_MODE + { + DDS_ALPHA_MODE_UNKNOWN = 0, + DDS_ALPHA_MODE_STRAIGHT = 1, + DDS_ALPHA_MODE_PREMULTIPLIED = 2, + DDS_ALPHA_MODE_OPAQUE = 3, + DDS_ALPHA_MODE_CUSTOM = 4, + }; + + // Standard version + HRESULT CreateDDSTextureFromMemory( + _In_ ID3D11Device* d3dDevice, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr); + + HRESULT CreateDDSTextureFromFile( + _In_ ID3D11Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr); + + // Standard version with optional auto-gen mipmap support + HRESULT CreateDDSTextureFromMemory( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr); + + HRESULT CreateDDSTextureFromFile( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_z_ const wchar_t* szFileName, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr); + + // Extended version + HRESULT CreateDDSTextureFromMemoryEx( + _In_ ID3D11Device* d3dDevice, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr); + + HRESULT CreateDDSTextureFromFileEx( + _In_ ID3D11Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr); + + // Extended version with optional auto-gen mipmap support + HRESULT CreateDDSTextureFromMemoryEx( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr); + + HRESULT CreateDDSTextureFromFileEx( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_z_ const wchar_t* szFileName, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr); +} \ No newline at end of file diff --git a/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader12.cpp b/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader12.cpp new file mode 100644 index 0000000..08e51d2 --- /dev/null +++ b/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader12.cpp @@ -0,0 +1,1570 @@ +//-------------------------------------------------------------------------------------- +// File: DDSTextureLoader12.cpp +// +// Functions for loading a DDS texture and creating a Direct3D runtime resource for it +// +// Note these functions are useful as a light-weight runtime loader for DDS files. For +// a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkID=615561 +//-------------------------------------------------------------------------------------- + +#include "DDSTextureLoader12.h" + +#include +#include +#include + +#include + +using namespace DirectX; + +//-------------------------------------------------------------------------------------- +// Macros +//-------------------------------------------------------------------------------------- +#ifndef MAKEFOURCC +#define MAKEFOURCC(ch0, ch1, ch2, ch3) \ + ((uint32_t)(uint8_t)(ch0) | ((uint32_t)(uint8_t)(ch1) << 8) | \ + ((uint32_t)(uint8_t)(ch2) << 16) | ((uint32_t)(uint8_t)(ch3) << 24 )) +#endif /* defined(MAKEFOURCC) */ + +//-------------------------------------------------------------------------------------- +// DDS file structure definitions +// +// See DDS.h in the 'Texconv' sample and the 'DirectXTex' library +//-------------------------------------------------------------------------------------- +#pragma pack(push,1) + +const uint32_t DDS_MAGIC = 0x20534444; // "DDS " + +struct DDS_PIXELFORMAT +{ + uint32_t size; + uint32_t flags; + uint32_t fourCC; + uint32_t RGBBitCount; + uint32_t RBitMask; + uint32_t GBitMask; + uint32_t BBitMask; + uint32_t ABitMask; +}; + +#define DDS_FOURCC 0x00000004 // DDPF_FOURCC +#define DDS_RGB 0x00000040 // DDPF_RGB +#define DDS_LUMINANCE 0x00020000 // DDPF_LUMINANCE +#define DDS_ALPHA 0x00000002 // DDPF_ALPHA +#define DDS_BUMPDUDV 0x00080000 // DDPF_BUMPDUDV + +#define DDS_HEADER_FLAGS_VOLUME 0x00800000 // DDSD_DEPTH + +#define DDS_HEIGHT 0x00000002 // DDSD_HEIGHT +#define DDS_WIDTH 0x00000004 // DDSD_WIDTH + +#define DDS_CUBEMAP_POSITIVEX 0x00000600 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEX +#define DDS_CUBEMAP_NEGATIVEX 0x00000a00 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEX +#define DDS_CUBEMAP_POSITIVEY 0x00001200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEY +#define DDS_CUBEMAP_NEGATIVEY 0x00002200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEY +#define DDS_CUBEMAP_POSITIVEZ 0x00004200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEZ +#define DDS_CUBEMAP_NEGATIVEZ 0x00008200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEZ + +#define DDS_CUBEMAP_ALLFACES ( DDS_CUBEMAP_POSITIVEX | DDS_CUBEMAP_NEGATIVEX |\ + DDS_CUBEMAP_POSITIVEY | DDS_CUBEMAP_NEGATIVEY |\ + DDS_CUBEMAP_POSITIVEZ | DDS_CUBEMAP_NEGATIVEZ ) + +#define DDS_CUBEMAP 0x00000200 // DDSCAPS2_CUBEMAP + +enum DDS_MISC_FLAGS2 +{ + DDS_MISC_FLAGS2_ALPHA_MODE_MASK = 0x7L, +}; + +struct DDS_HEADER +{ + uint32_t size; + uint32_t flags; + uint32_t height; + uint32_t width; + uint32_t pitchOrLinearSize; + uint32_t depth; // only if DDS_HEADER_FLAGS_VOLUME is set in flags + uint32_t mipMapCount; + uint32_t reserved1[11]; + DDS_PIXELFORMAT ddspf; + uint32_t caps; + uint32_t caps2; + uint32_t caps3; + uint32_t caps4; + uint32_t reserved2; +}; + +struct DDS_HEADER_DXT10 +{ + DXGI_FORMAT dxgiFormat; + uint32_t resourceDimension; + uint32_t miscFlag; // see D3D11_RESOURCE_MISC_FLAG + uint32_t arraySize; + uint32_t miscFlags2; +}; + +#pragma pack(pop) + +//-------------------------------------------------------------------------------------- +namespace +{ + struct handle_closer { void operator()(HANDLE h) { if (h) CloseHandle(h); } }; + + typedef public std::unique_ptr ScopedHandle; + + inline HANDLE safe_handle(HANDLE h) { return (h == INVALID_HANDLE_VALUE) ? 0 : h; } + + template + inline void SetDebugObjectName(_In_ ID3D12DeviceChild* resource, _In_z_ const wchar_t(&name)[TNameLength]) + { + #if !defined(NO_D3D12_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) + resource->SetName(name); + #else + UNREFERENCED_PARAMETER(resource); + UNREFERENCED_PARAMETER(name); + #endif + } + + inline uint32_t CountMips(uint32_t width, uint32_t height) + { + if (width == 0 || height == 0) + return 0; + + uint32_t count = 1; + while (width > 1 || height > 1) + { + width >>= 1; + height >>= 1; + count++; + } + return count; + } + + //-------------------------------------------------------------------------------------- + HRESULT LoadTextureDataFromFile( + _In_z_ const wchar_t* fileName, + std::unique_ptr& ddsData, + const DDS_HEADER** header, + const uint8_t** bitData, + size_t* bitSize) + { + if (!header || !bitData || !bitSize) + { + return E_POINTER; + } + + // open the file + ScopedHandle hFile(safe_handle(CreateFile2(fileName, + GENERIC_READ, + FILE_SHARE_READ, + OPEN_EXISTING, + nullptr))); + + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // Get the file size + FILE_STANDARD_INFO fileInfo; + if (!GetFileInformationByHandleEx(hFile.get(), FileStandardInfo, &fileInfo, sizeof(fileInfo))) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // File is too big for 32-bit allocation, so reject read + if (fileInfo.EndOfFile.HighPart > 0) + { + return E_FAIL; + } + + // Need at least enough data to fill the header and magic number to be a valid DDS + if (fileInfo.EndOfFile.LowPart < (sizeof(DDS_HEADER) + sizeof(uint32_t))) + { + return E_FAIL; + } + + // create enough space for the file data + ddsData.reset(new (std::nothrow) uint8_t[fileInfo.EndOfFile.LowPart]); + if (!ddsData) + { + return E_OUTOFMEMORY; + } + + // read the data in + DWORD BytesRead = 0; + if (!ReadFile(hFile.get(), + ddsData.get(), + fileInfo.EndOfFile.LowPart, + &BytesRead, + nullptr + )) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (BytesRead < fileInfo.EndOfFile.LowPart) + { + return E_FAIL; + } + + // DDS files always start with the same magic number ("DDS ") + uint32_t dwMagicNumber = *reinterpret_cast(ddsData.get()); + if (dwMagicNumber != DDS_MAGIC) + { + return E_FAIL; + } + + auto hdr = reinterpret_cast(ddsData.get() + sizeof(uint32_t)); + + // Verify header to validate DDS file + if (hdr->size != sizeof(DDS_HEADER) || + hdr->ddspf.size != sizeof(DDS_PIXELFORMAT)) + { + return E_FAIL; + } + + // Check for DX10 extension + bool bDXT10Header = false; + if ((hdr->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC('D', 'X', '1', '0') == hdr->ddspf.fourCC)) + { + // Must be long enough for both headers and magic value + if (fileInfo.EndOfFile.LowPart < (sizeof(DDS_HEADER) + sizeof(uint32_t) + sizeof(DDS_HEADER_DXT10))) + { + return E_FAIL; + } + + bDXT10Header = true; + } + + // setup the pointers in the process request + *header = hdr; + ptrdiff_t offset = sizeof(uint32_t) + sizeof(DDS_HEADER) + + (bDXT10Header ? sizeof(DDS_HEADER_DXT10) : 0); + *bitData = ddsData.get() + offset; + *bitSize = fileInfo.EndOfFile.LowPart - offset; + + return S_OK; + } + + + //-------------------------------------------------------------------------------------- + // Return the BPP for a particular format + //-------------------------------------------------------------------------------------- + size_t BitsPerPixel( _In_ DXGI_FORMAT fmt ) + { + switch( fmt ) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + return 128; + + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return 96; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_R32G32_TYPELESS: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + return 64; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R11G11B10_FLOAT: + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_R16G16_TYPELESS: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + case DXGI_FORMAT_R32_TYPELESS: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_YUY2: + return 32; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + return 24; + + case DXGI_FORMAT_R8G8_TYPELESS: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + case DXGI_FORMAT_R16_TYPELESS: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_A8P8: + case DXGI_FORMAT_B4G4R4A4_UNORM: + return 16; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + case DXGI_FORMAT_NV11: + return 12; + + case DXGI_FORMAT_R8_TYPELESS: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + return 8; + + case DXGI_FORMAT_R1_UNORM: + return 1; + + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + return 4; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return 8; + + default: + return 0; + } + } + + + //-------------------------------------------------------------------------------------- + // Get surface information for a particular format + //-------------------------------------------------------------------------------------- + void GetSurfaceInfo( + _In_ size_t width, + _In_ size_t height, + _In_ DXGI_FORMAT fmt, + size_t* outNumBytes, + _Out_opt_ size_t* outRowBytes, + _Out_opt_ size_t* outNumRows ) + { + size_t numBytes = 0; + size_t rowBytes = 0; + size_t numRows = 0; + + bool bc = false; + bool packed = false; + bool planar = false; + size_t bpe = 0; + switch (fmt) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + bc=true; + bpe = 8; + break; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + bc = true; + bpe = 16; + break; + + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_YUY2: + packed = true; + bpe = 4; + break; + + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + packed = true; + bpe = 8; + break; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + planar = true; + bpe = 2; + break; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + planar = true; + bpe = 4; + break; + } + + if (bc) + { + size_t numBlocksWide = 0; + if (width > 0) + { + numBlocksWide = std::max( 1, (width + 3) / 4 ); + } + size_t numBlocksHigh = 0; + if (height > 0) + { + numBlocksHigh = std::max( 1, (height + 3) / 4 ); + } + rowBytes = numBlocksWide * bpe; + numRows = numBlocksHigh; + numBytes = rowBytes * numBlocksHigh; + } + else if (packed) + { + rowBytes = ( ( width + 1 ) >> 1 ) * bpe; + numRows = height; + numBytes = rowBytes * height; + } + else if ( fmt == DXGI_FORMAT_NV11 ) + { + rowBytes = ( ( width + 3 ) >> 2 ) * 4; + numRows = height * 2; // Direct3D makes this simplifying assumption, although it is larger than the 4:1:1 data + numBytes = rowBytes * numRows; + } + else if (planar) + { + rowBytes = ( ( width + 1 ) >> 1 ) * bpe; + numBytes = ( rowBytes * height ) + ( ( rowBytes * height + 1 ) >> 1 ); + numRows = height + ( ( height + 1 ) >> 1 ); + } + else + { + size_t bpp = BitsPerPixel( fmt ); + rowBytes = ( width * bpp + 7 ) / 8; // round up to nearest byte + numRows = height; + numBytes = rowBytes * height; + } + + if (outNumBytes) + { + *outNumBytes = numBytes; + } + if (outRowBytes) + { + *outRowBytes = rowBytes; + } + if (outNumRows) + { + *outNumRows = numRows; + } + } + + + //-------------------------------------------------------------------------------------- + #define ISBITMASK( r,g,b,a ) ( ddpf.RBitMask == r && ddpf.GBitMask == g && ddpf.BBitMask == b && ddpf.ABitMask == a ) + + DXGI_FORMAT GetDXGIFormat( const DDS_PIXELFORMAT& ddpf ) + { + if (ddpf.flags & DDS_RGB) + { + // Note that sRGB formats are written using the "DX10" extended header + + switch (ddpf.RGBBitCount) + { + case 32: + if (ISBITMASK(0x000000ff,0x0000ff00,0x00ff0000,0xff000000)) + { + return DXGI_FORMAT_R8G8B8A8_UNORM; + } + + if (ISBITMASK(0x00ff0000,0x0000ff00,0x000000ff,0xff000000)) + { + return DXGI_FORMAT_B8G8R8A8_UNORM; + } + + if (ISBITMASK(0x00ff0000,0x0000ff00,0x000000ff,0x00000000)) + { + return DXGI_FORMAT_B8G8R8X8_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x000000ff,0x0000ff00,0x00ff0000,0x00000000) aka D3DFMT_X8B8G8R8 + + // Note that many common DDS reader/writers (including D3DX) swap the + // the RED/BLUE masks for 10:10:10:2 formats. We assume + // below that the 'backwards' header mask is being used since it is most + // likely written by D3DX. The more robust solution is to use the 'DX10' + // header extension and specify the DXGI_FORMAT_R10G10B10A2_UNORM format directly + + // For 'correct' writers, this should be 0x000003ff,0x000ffc00,0x3ff00000 for RGB data + if (ISBITMASK(0x3ff00000,0x000ffc00,0x000003ff,0xc0000000)) + { + return DXGI_FORMAT_R10G10B10A2_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x000003ff,0x000ffc00,0x3ff00000,0xc0000000) aka D3DFMT_A2R10G10B10 + + if (ISBITMASK(0x0000ffff,0xffff0000,0x00000000,0x00000000)) + { + return DXGI_FORMAT_R16G16_UNORM; + } + + if (ISBITMASK(0xffffffff,0x00000000,0x00000000,0x00000000)) + { + // Only 32-bit color channel format in D3D9 was R32F + return DXGI_FORMAT_R32_FLOAT; // D3DX writes this out as a FourCC of 114 + } + break; + + case 24: + // No 24bpp DXGI formats aka D3DFMT_R8G8B8 + break; + + case 16: + if (ISBITMASK(0x7c00,0x03e0,0x001f,0x8000)) + { + return DXGI_FORMAT_B5G5R5A1_UNORM; + } + if (ISBITMASK(0xf800,0x07e0,0x001f,0x0000)) + { + return DXGI_FORMAT_B5G6R5_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x7c00,0x03e0,0x001f,0x0000) aka D3DFMT_X1R5G5B5 + + if (ISBITMASK(0x0f00,0x00f0,0x000f,0xf000)) + { + return DXGI_FORMAT_B4G4R4A4_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x0f00,0x00f0,0x000f,0x0000) aka D3DFMT_X4R4G4B4 + + // No 3:3:2, 3:3:2:8, or paletted DXGI formats aka D3DFMT_A8R3G3B2, D3DFMT_R3G3B2, D3DFMT_P8, D3DFMT_A8P8, etc. + break; + } + } + else if (ddpf.flags & DDS_LUMINANCE) + { + if (8 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x000000ff,0x00000000,0x00000000,0x00000000)) + { + return DXGI_FORMAT_R8_UNORM; // D3DX10/11 writes this out as DX10 extension + } + + // No DXGI format maps to ISBITMASK(0x0f,0x00,0x00,0xf0) aka D3DFMT_A4L4 + + if (ISBITMASK(0x000000ff, 0x00000000, 0x00000000, 0x0000ff00)) + { + return DXGI_FORMAT_R8G8_UNORM; // Some DDS writers assume the bitcount should be 8 instead of 16 + } + } + + if (16 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x0000ffff,0x00000000,0x00000000,0x00000000)) + { + return DXGI_FORMAT_R16_UNORM; // D3DX10/11 writes this out as DX10 extension + } + if (ISBITMASK(0x000000ff,0x00000000,0x00000000,0x0000ff00)) + { + return DXGI_FORMAT_R8G8_UNORM; // D3DX10/11 writes this out as DX10 extension + } + } + } + else if (ddpf.flags & DDS_ALPHA) + { + if (8 == ddpf.RGBBitCount) + { + return DXGI_FORMAT_A8_UNORM; + } + } + else if (ddpf.flags & DDS_BUMPDUDV) + { + if (16 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x00ff, 0xff00, 0x0000, 0x0000)) + { + return DXGI_FORMAT_R8G8_SNORM; // D3DX10/11 writes this out as DX10 extension + } + } + + if (32 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000)) + { + return DXGI_FORMAT_R8G8B8A8_SNORM; // D3DX10/11 writes this out as DX10 extension + } + if (ISBITMASK(0x0000ffff, 0xffff0000, 0x00000000, 0x00000000)) + { + return DXGI_FORMAT_R16G16_SNORM; // D3DX10/11 writes this out as DX10 extension + } + + // No DXGI format maps to ISBITMASK(0x3ff00000, 0x000ffc00, 0x000003ff, 0xc0000000) aka D3DFMT_A2W10V10U10 + } + } + else if (ddpf.flags & DDS_FOURCC) + { + if (MAKEFOURCC( 'D', 'X', 'T', '1' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC1_UNORM; + } + if (MAKEFOURCC( 'D', 'X', 'T', '3' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC2_UNORM; + } + if (MAKEFOURCC( 'D', 'X', 'T', '5' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC3_UNORM; + } + + // While pre-multiplied alpha isn't directly supported by the DXGI formats, + // they are basically the same as these BC formats so they can be mapped + if (MAKEFOURCC( 'D', 'X', 'T', '2' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC2_UNORM; + } + if (MAKEFOURCC( 'D', 'X', 'T', '4' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC3_UNORM; + } + + if (MAKEFOURCC( 'A', 'T', 'I', '1' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_UNORM; + } + if (MAKEFOURCC( 'B', 'C', '4', 'U' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_UNORM; + } + if (MAKEFOURCC( 'B', 'C', '4', 'S' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_SNORM; + } + + if (MAKEFOURCC( 'A', 'T', 'I', '2' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_UNORM; + } + if (MAKEFOURCC( 'B', 'C', '5', 'U' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_UNORM; + } + if (MAKEFOURCC( 'B', 'C', '5', 'S' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_SNORM; + } + + // BC6H and BC7 are written using the "DX10" extended header + + if (MAKEFOURCC( 'R', 'G', 'B', 'G' ) == ddpf.fourCC) + { + return DXGI_FORMAT_R8G8_B8G8_UNORM; + } + if (MAKEFOURCC( 'G', 'R', 'G', 'B' ) == ddpf.fourCC) + { + return DXGI_FORMAT_G8R8_G8B8_UNORM; + } + + if (MAKEFOURCC('Y','U','Y','2') == ddpf.fourCC) + { + return DXGI_FORMAT_YUY2; + } + + // Check for D3DFORMAT enums being set here + switch( ddpf.fourCC ) + { + case 36: // D3DFMT_A16B16G16R16 + return DXGI_FORMAT_R16G16B16A16_UNORM; + + case 110: // D3DFMT_Q16W16V16U16 + return DXGI_FORMAT_R16G16B16A16_SNORM; + + case 111: // D3DFMT_R16F + return DXGI_FORMAT_R16_FLOAT; + + case 112: // D3DFMT_G16R16F + return DXGI_FORMAT_R16G16_FLOAT; + + case 113: // D3DFMT_A16B16G16R16F + return DXGI_FORMAT_R16G16B16A16_FLOAT; + + case 114: // D3DFMT_R32F + return DXGI_FORMAT_R32_FLOAT; + + case 115: // D3DFMT_G32R32F + return DXGI_FORMAT_R32G32_FLOAT; + + case 116: // D3DFMT_A32B32G32R32F + return DXGI_FORMAT_R32G32B32A32_FLOAT; + } + } + + return DXGI_FORMAT_UNKNOWN; + } + + + //-------------------------------------------------------------------------------------- + DXGI_FORMAT MakeSRGB( _In_ DXGI_FORMAT format ) + { + switch( format ) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + return DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + + case DXGI_FORMAT_BC1_UNORM: + return DXGI_FORMAT_BC1_UNORM_SRGB; + + case DXGI_FORMAT_BC2_UNORM: + return DXGI_FORMAT_BC2_UNORM_SRGB; + + case DXGI_FORMAT_BC3_UNORM: + return DXGI_FORMAT_BC3_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + return DXGI_FORMAT_B8G8R8A8_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + return DXGI_FORMAT_B8G8R8X8_UNORM_SRGB; + + case DXGI_FORMAT_BC7_UNORM: + return DXGI_FORMAT_BC7_UNORM_SRGB; + + default: + return format; + } + } + + + //-------------------------------------------------------------------------------------- + inline bool IsDepthStencil(DXGI_FORMAT fmt) + { + switch (fmt) + { + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_D16_UNORM: + return true; + + default: + return false; + } + } + + + //-------------------------------------------------------------------------------------- + inline void AdjustPlaneResource( + _In_ DXGI_FORMAT fmt, + _In_ size_t height, + _In_ size_t slicePlane, + _Inout_ D3D12_SUBRESOURCE_DATA& res) + { + switch (fmt) + { + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + +#if defined(_XBOX_ONE) && defined(_TITLE) + case DXGI_FORMAT_D16_UNORM_S8_UINT: + case DXGI_FORMAT_R16_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X16_TYPELESS_G8_UINT: +#endif + if (!slicePlane) + { + // Plane 0 + res.SlicePitch = res.RowPitch * height; + } + else + { + // Plane 1 + res.pData = reinterpret_cast(res.pData) + res.RowPitch * height; + res.SlicePitch = res.RowPitch * ((height + 1) >> 1); + } + break; + + case DXGI_FORMAT_NV11: + if (!slicePlane) + { + // Plane 0 + res.SlicePitch = res.RowPitch * height; + } + else + { + // Plane 1 + res.pData = reinterpret_cast(res.pData) + res.RowPitch * height; + res.RowPitch = (res.RowPitch >> 1); + res.SlicePitch = res.RowPitch * height; + } + break; + } + } + + + //-------------------------------------------------------------------------------------- + HRESULT FillInitData(_In_ size_t width, + _In_ size_t height, + _In_ size_t depth, + _In_ size_t mipCount, + _In_ size_t arraySize, + _In_ size_t numberOfPlanes, + _In_ DXGI_FORMAT format, + _In_ size_t maxsize, + _In_ size_t bitSize, + _In_reads_bytes_(bitSize) const uint8_t* bitData, + _Out_ size_t& twidth, + _Out_ size_t& theight, + _Out_ size_t& tdepth, + _Out_ size_t& skipMip, + std::vector& initData) + { + if (!bitData) + { + return E_POINTER; + } + + skipMip = 0; + twidth = 0; + theight = 0; + tdepth = 0; + + size_t NumBytes = 0; + size_t RowBytes = 0; + const uint8_t* pEndBits = bitData + bitSize; + + initData.clear(); + + for (size_t p = 0; p < numberOfPlanes; ++p) + { + const uint8_t* pSrcBits = bitData; + + for (size_t j = 0; j < arraySize; j++) + { + size_t w = width; + size_t h = height; + size_t d = depth; + for (size_t i = 0; i < mipCount; i++) + { + GetSurfaceInfo(w, + h, + format, + &NumBytes, + &RowBytes, + nullptr + ); + + if ((mipCount <= 1) || !maxsize || (w <= maxsize && h <= maxsize && d <= maxsize)) + { + if (!twidth) + { + twidth = w; + theight = h; + tdepth = d; + } + + D3D12_SUBRESOURCE_DATA res = + { + reinterpret_cast(pSrcBits), + static_cast(RowBytes), + static_cast(NumBytes) + }; + + AdjustPlaneResource(format, h, p, res); + + initData.emplace_back(res); + } + else if (!j) + { + // Count number of skipped mipmaps (first item only) + ++skipMip; + } + + if (pSrcBits + (NumBytes*d) > pEndBits) + { + return HRESULT_FROM_WIN32(ERROR_HANDLE_EOF); + } + + pSrcBits += NumBytes * d; + + w = w >> 1; + h = h >> 1; + d = d >> 1; + if (w == 0) + { + w = 1; + } + if (h == 0) + { + h = 1; + } + if (d == 0) + { + d = 1; + } + } + } + } + + return initData.empty() ? E_FAIL : S_OK; + } + + + //-------------------------------------------------------------------------------------- + HRESULT CreateTextureResource( + _In_ ID3D12Device* d3dDevice, + D3D12_RESOURCE_DIMENSION resDim, + size_t width, + size_t height, + size_t depth, + size_t mipCount, + size_t arraySize, + DXGI_FORMAT format, + D3D12_RESOURCE_FLAGS resFlags, + unsigned int loadFlags, + _Outptr_ ID3D12Resource** texture) + { + if (!d3dDevice) + return E_POINTER; + + HRESULT hr = E_FAIL; + + if (loadFlags & DDS_LOADER_FORCE_SRGB) + { + format = MakeSRGB(format); + } + + D3D12_RESOURCE_DESC desc = {}; + desc.Width = static_cast(width); + desc.Height = static_cast(height); + desc.MipLevels = static_cast(mipCount); + desc.DepthOrArraySize = (resDim == D3D12_RESOURCE_DIMENSION_TEXTURE3D) ? static_cast(depth) : static_cast(arraySize); + desc.Format = format; + desc.Flags = resFlags; + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Dimension = resDim; + + CD3DX12_HEAP_PROPERTIES defaultHeapProperties(D3D12_HEAP_TYPE_DEFAULT); + + hr = d3dDevice->CreateCommittedResource( + &defaultHeapProperties, + D3D12_HEAP_FLAG_NONE, + &desc, + D3D12_RESOURCE_STATE_COPY_DEST, + nullptr, + IID_PPV_ARGS(texture)); + if (SUCCEEDED(hr)) + { + _Analysis_assume_(*texture != 0); + + SetDebugObjectName(*texture, L"DDSTextureLoader"); + } + + return hr; + } + + //-------------------------------------------------------------------------------------- + HRESULT CreateTextureFromDDS(_In_ ID3D12Device* d3dDevice, + _In_ const DDS_HEADER* header, + _In_reads_bytes_(bitSize) const uint8_t* bitData, + size_t bitSize, + size_t maxsize, + D3D12_RESOURCE_FLAGS resFlags, + unsigned int loadFlags, + _Outptr_ ID3D12Resource** texture, + std::vector& subresources, + _Out_opt_ bool* outIsCubeMap) + { + HRESULT hr = S_OK; + + UINT width = header->width; + UINT height = header->height; + UINT depth = header->depth; + + D3D12_RESOURCE_DIMENSION resDim = D3D12_RESOURCE_DIMENSION_UNKNOWN; + UINT arraySize = 1; + DXGI_FORMAT format = DXGI_FORMAT_UNKNOWN; + bool isCubeMap = false; + + size_t mipCount = header->mipMapCount; + if (0 == mipCount) + { + mipCount = 1; + } + + if ((header->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC('D', 'X', '1', '0') == header->ddspf.fourCC)) + { + auto d3d10ext = reinterpret_cast((const char*)header + sizeof(DDS_HEADER)); + + arraySize = d3d10ext->arraySize; + if (arraySize == 0) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + switch (d3d10ext->dxgiFormat) + { + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case DXGI_FORMAT_A8P8: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + default: + if (BitsPerPixel(d3d10ext->dxgiFormat) == 0) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } + + format = d3d10ext->dxgiFormat; + + switch (d3d10ext->resourceDimension) + { + case D3D12_RESOURCE_DIMENSION_TEXTURE1D: + // D3DX writes 1D textures with a fixed Height of 1 + if ((header->flags & DDS_HEIGHT) && height != 1) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + height = depth = 1; + break; + + case D3D12_RESOURCE_DIMENSION_TEXTURE2D: + if (d3d10ext->miscFlag & 0x4 /* RESOURCE_MISC_TEXTURECUBE */) + { + arraySize *= 6; + isCubeMap = true; + } + depth = 1; + break; + + case D3D12_RESOURCE_DIMENSION_TEXTURE3D: + if (!(header->flags & DDS_HEADER_FLAGS_VOLUME)) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + if (arraySize > 1) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + resDim = static_cast(d3d10ext->resourceDimension); + } + else + { + format = GetDXGIFormat(header->ddspf); + + if (format == DXGI_FORMAT_UNKNOWN) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + if (header->flags & DDS_HEADER_FLAGS_VOLUME) + { + resDim = D3D12_RESOURCE_DIMENSION_TEXTURE3D; + } + else + { + if (header->caps2 & DDS_CUBEMAP) + { + // We require all six faces to be defined + if ((header->caps2 & DDS_CUBEMAP_ALLFACES) != DDS_CUBEMAP_ALLFACES) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + arraySize = 6; + isCubeMap = true; + } + + depth = 1; + resDim = D3D12_RESOURCE_DIMENSION_TEXTURE2D; + + // Note there's no way for a legacy Direct3D 9 DDS to express a '1D' texture + } + + assert(BitsPerPixel(format) != 0); + } + + // Bound sizes (for security purposes we don't trust DDS file metadata larger than the Direct3D hardware requirements) + if (mipCount > D3D12_REQ_MIP_LEVELS) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + switch (resDim) + { + case D3D12_RESOURCE_DIMENSION_TEXTURE1D: + if ((arraySize > D3D12_REQ_TEXTURE1D_ARRAY_AXIS_DIMENSION) || + (width > D3D12_REQ_TEXTURE1D_U_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + case D3D12_RESOURCE_DIMENSION_TEXTURE2D: + if (isCubeMap) + { + // This is the right bound because we set arraySize to (NumCubes*6) above + if ((arraySize > D3D12_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) || + (width > D3D12_REQ_TEXTURECUBE_DIMENSION) || + (height > D3D12_REQ_TEXTURECUBE_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } + else if ((arraySize > D3D12_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) || + (width > D3D12_REQ_TEXTURE2D_U_OR_V_DIMENSION) || + (height > D3D12_REQ_TEXTURE2D_U_OR_V_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + case D3D12_RESOURCE_DIMENSION_TEXTURE3D: + if ((arraySize > 1) || + (width > D3D12_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) || + (height > D3D12_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) || + (depth > D3D12_REQ_TEXTURE3D_U_V_OR_W_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + UINT numberOfPlanes = D3D12GetFormatPlaneCount(d3dDevice, format); + if (!numberOfPlanes) + return E_INVALIDARG; + + if ((numberOfPlanes > 1) && IsDepthStencil(format)) + { + // DirectX 12 uses planes for stencil, DirectX 11 does not + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + if (outIsCubeMap != nullptr) + { + *outIsCubeMap = isCubeMap; + } + + // Create the texture + size_t numberOfResources = (resDim == D3D12_RESOURCE_DIMENSION_TEXTURE3D) + ? 1 : arraySize; + numberOfResources *= mipCount; + numberOfResources *= numberOfPlanes; + + if (numberOfResources > D3D12_REQ_SUBRESOURCES) + return E_INVALIDARG; + + subresources.reserve(numberOfResources); + + size_t skipMip = 0; + size_t twidth = 0; + size_t theight = 0; + size_t tdepth = 0; + hr = FillInitData(width, height, depth, mipCount, arraySize, + numberOfPlanes, format, + maxsize, bitSize, bitData, + twidth, theight, tdepth, skipMip, subresources); + + if (SUCCEEDED(hr)) + { + size_t reservedMips = mipCount; + if (loadFlags & DDS_LOADER_MIP_RESERVE) + { + reservedMips = std::min(D3D12_REQ_MIP_LEVELS, CountMips(width, height)); + } + + hr = CreateTextureResource(d3dDevice, resDim, twidth, theight, tdepth, reservedMips - skipMip, arraySize, + format, resFlags, loadFlags, texture); + + if (FAILED(hr) && !maxsize && (mipCount > 1)) + { + subresources.clear(); + + maxsize = (resDim == D3D12_RESOURCE_DIMENSION_TEXTURE3D) + ? D3D12_REQ_TEXTURE3D_U_V_OR_W_DIMENSION + : D3D12_REQ_TEXTURE2D_U_OR_V_DIMENSION; + + hr = FillInitData(width, height, depth, mipCount, arraySize, + numberOfPlanes, format, + maxsize, bitSize, bitData, + twidth, theight, tdepth, skipMip, subresources); + if (SUCCEEDED(hr)) + { + hr = CreateTextureResource(d3dDevice, resDim, twidth, theight, tdepth, mipCount - skipMip, arraySize, + format, resFlags, loadFlags, texture); + } + } + } + + if (FAILED(hr)) + { + subresources.clear(); + } + + return hr; + } + + //-------------------------------------------------------------------------------------- + DDS_ALPHA_MODE GetAlphaMode( _In_ const DDS_HEADER* header ) + { + if ( header->ddspf.flags & DDS_FOURCC ) + { + if ( MAKEFOURCC( 'D', 'X', '1', '0' ) == header->ddspf.fourCC ) + { + auto d3d10ext = reinterpret_cast( (const char*)header + sizeof(DDS_HEADER) ); + auto mode = static_cast( d3d10ext->miscFlags2 & DDS_MISC_FLAGS2_ALPHA_MODE_MASK ); + switch( mode ) + { + case DDS_ALPHA_MODE_STRAIGHT: + case DDS_ALPHA_MODE_PREMULTIPLIED: + case DDS_ALPHA_MODE_OPAQUE: + case DDS_ALPHA_MODE_CUSTOM: + return mode; + } + } + else if ( ( MAKEFOURCC( 'D', 'X', 'T', '2' ) == header->ddspf.fourCC ) + || ( MAKEFOURCC( 'D', 'X', 'T', '4' ) == header->ddspf.fourCC ) ) + { + return DDS_ALPHA_MODE_PREMULTIPLIED; + } + } + + return DDS_ALPHA_MODE_UNKNOWN; + } +} // anonymous namespace + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadDDSTextureFromMemory( + ID3D12Device* d3dDevice, + const uint8_t* ddsData, + size_t ddsDataSize, + ID3D12Resource** texture, + std::vector& subresources, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode, + bool* isCubeMap) +{ + return LoadDDSTextureFromMemoryEx( + d3dDevice, + ddsData, + ddsDataSize, + maxsize, + D3D12_RESOURCE_FLAG_NONE, + DDS_LOADER_DEFAULT, + texture, + subresources, + alphaMode, + isCubeMap); +} + + +_Use_decl_annotations_ +HRESULT DirectX::LoadDDSTextureFromMemoryEx( + ID3D12Device* d3dDevice, + const uint8_t* ddsData, + size_t ddsDataSize, + size_t maxsize, + D3D12_RESOURCE_FLAGS resFlags, + unsigned int loadFlags, + ID3D12Resource** texture, + std::vector& subresources, + DDS_ALPHA_MODE* alphaMode, + bool* isCubeMap) +{ + if (texture) + { + *texture = nullptr; + } + if (alphaMode) + { + *alphaMode = DDS_ALPHA_MODE_UNKNOWN; + } + if (isCubeMap) + { + *isCubeMap = false; + } + + if (!d3dDevice || !ddsData || !texture) + { + return E_INVALIDARG; + } + + // Validate DDS file in memory + if (ddsDataSize < (sizeof(uint32_t) + sizeof(DDS_HEADER))) + { + return E_FAIL; + } + + uint32_t dwMagicNumber = *(const uint32_t*)(ddsData); + if (dwMagicNumber != DDS_MAGIC) + { + return E_FAIL; + } + + auto header = reinterpret_cast(ddsData + sizeof(uint32_t)); + + // Verify header to validate DDS file + if (header->size != sizeof(DDS_HEADER) || + header->ddspf.size != sizeof(DDS_PIXELFORMAT)) + { + return E_FAIL; + } + + // Check for DX10 extension + bool bDXT10Header = false; + if ((header->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC('D', 'X', '1', '0') == header->ddspf.fourCC)) + { + // Must be long enough for both headers and magic value + if (ddsDataSize < (sizeof(DDS_HEADER) + sizeof(uint32_t) + sizeof(DDS_HEADER_DXT10))) + { + return E_FAIL; + } + + bDXT10Header = true; + } + + ptrdiff_t offset = sizeof(uint32_t) + + sizeof(DDS_HEADER) + + (bDXT10Header ? sizeof(DDS_HEADER_DXT10) : 0); + + HRESULT hr = CreateTextureFromDDS(d3dDevice, + header, ddsData + offset, ddsDataSize - offset, maxsize, + resFlags, loadFlags, + texture, subresources, isCubeMap); + if (SUCCEEDED(hr)) + { + if (texture != 0 && *texture != 0) + { + SetDebugObjectName(*texture, L"DDSTextureLoader"); + } + + if (alphaMode) + *alphaMode = GetAlphaMode(header); + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadDDSTextureFromFile( + ID3D12Device* d3dDevice, + const wchar_t* fileName, + ID3D12Resource** texture, + std::unique_ptr& ddsData, + std::vector& subresources, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode, + bool* isCubeMap) +{ + return LoadDDSTextureFromFileEx( + d3dDevice, + fileName, + maxsize, + D3D12_RESOURCE_FLAG_NONE, + DDS_LOADER_DEFAULT, + texture, + ddsData, + subresources, + alphaMode, + isCubeMap); +} + +_Use_decl_annotations_ +HRESULT DirectX::LoadDDSTextureFromFileEx( + ID3D12Device* d3dDevice, + const wchar_t* fileName, + size_t maxsize, + D3D12_RESOURCE_FLAGS resFlags, + unsigned int loadFlags, + ID3D12Resource** texture, + std::unique_ptr& ddsData, + std::vector& subresources, + DDS_ALPHA_MODE* alphaMode, + bool* isCubeMap) +{ + if (texture) + { + *texture = nullptr; + } + if (alphaMode) + { + *alphaMode = DDS_ALPHA_MODE_UNKNOWN; + } + if (isCubeMap) + { + *isCubeMap = false; + } + + if (!d3dDevice || !fileName || !texture) + { + return E_INVALIDARG; + } + + const DDS_HEADER* header = nullptr; + const uint8_t* bitData = nullptr; + size_t bitSize = 0; + + HRESULT hr = LoadTextureDataFromFile(fileName, + ddsData, + &header, + &bitData, + &bitSize + ); + if (FAILED(hr)) + { + return hr; + } + + hr = CreateTextureFromDDS(d3dDevice, + header, bitData, bitSize, maxsize, + resFlags, loadFlags, + texture, subresources, isCubeMap); + + if (SUCCEEDED(hr)) + { +#if !defined(NO_D3D12_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) + if (texture != 0) + { + CHAR strFileA[MAX_PATH]; + int result = WideCharToMultiByte(CP_ACP, + WC_NO_BEST_FIT_CHARS, + fileName, + -1, + strFileA, + MAX_PATH, + nullptr, + FALSE + ); + if (result > 0) + { + const wchar_t* pstrName = wcsrchr(fileName, '\\'); + if (!pstrName) + { + pstrName = fileName; + } + else + { + pstrName++; + } + + if (texture != 0 && *texture != 0) + { + (*texture)->SetName(pstrName); + } + } + } +#endif + + if (alphaMode) + *alphaMode = GetAlphaMode(header); + } + + return hr; +} diff --git a/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader12.h b/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader12.h new file mode 100644 index 0000000..30d95f9 --- /dev/null +++ b/deps/DirectXTex/DDSTextureLoader/DDSTextureLoader12.h @@ -0,0 +1,93 @@ +//-------------------------------------------------------------------------------------- +// File: DDSTextureLoader12.h +// +// Functions for loading a DDS texture and creating a Direct3D runtime resource for it +// +// Note these functions are useful as a light-weight runtime loader for DDS files. For +// a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkID=615561 +//-------------------------------------------------------------------------------------- + +#pragma once + +#include + +#include +#include +#include + + +namespace DirectX +{ + enum DDS_ALPHA_MODE + { + DDS_ALPHA_MODE_UNKNOWN = 0, + DDS_ALPHA_MODE_STRAIGHT = 1, + DDS_ALPHA_MODE_PREMULTIPLIED = 2, + DDS_ALPHA_MODE_OPAQUE = 3, + DDS_ALPHA_MODE_CUSTOM = 4, + }; + + enum DDS_LOADER_FLAGS + { + DDS_LOADER_DEFAULT = 0, + DDS_LOADER_FORCE_SRGB = 0x1, + DDS_LOADER_MIP_RESERVE = 0x8, + }; + + // Standard version + HRESULT __cdecl LoadDDSTextureFromMemory( + _In_ ID3D12Device* d3dDevice, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + size_t ddsDataSize, + _Outptr_ ID3D12Resource** texture, + std::vector& subresources, + size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr, + _Out_opt_ bool* isCubeMap = nullptr); + + HRESULT __cdecl LoadDDSTextureFromFile( + _In_ ID3D12Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _Outptr_ ID3D12Resource** texture, + std::unique_ptr& ddsData, + std::vector& subresources, + size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr, + _Out_opt_ bool* isCubeMap = nullptr); + + // Extended version + HRESULT __cdecl LoadDDSTextureFromMemoryEx( + _In_ ID3D12Device* d3dDevice, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + size_t ddsDataSize, + size_t maxsize, + D3D12_RESOURCE_FLAGS resFlags, + unsigned int loadFlags, + _Outptr_ ID3D12Resource** texture, + std::vector& subresources, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr, + _Out_opt_ bool* isCubeMap = nullptr); + + HRESULT __cdecl LoadDDSTextureFromFileEx( + _In_ ID3D12Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + size_t maxsize, + D3D12_RESOURCE_FLAGS resFlags, + unsigned int loadFlags, + _Outptr_ ID3D12Resource** texture, + std::unique_ptr& ddsData, + std::vector& subresources, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr, + _Out_opt_ bool* isCubeMap = nullptr); +} diff --git a/deps/DirectXTex/DDSView/DDSView.rc b/deps/DirectXTex/DDSView/DDSView.rc new file mode 100644 index 0000000..49efb34 --- /dev/null +++ b/deps/DirectXTex/DDSView/DDSView.rc @@ -0,0 +1,75 @@ +// Microsoft Visual C++ generated resource script. +// +#define APSTUDIO_READONLY_SYMBOLS +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 2 resource. +// +#define IDC_STATIC -1 +#define IDI_MAIN_ICON 100 +#include + +///////////////////////////////////////////////////////////////////////////// +#undef APSTUDIO_READONLY_SYMBOLS + +///////////////////////////////////////////////////////////////////////////// +// English (U.S.) resources + +#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) +#ifdef _WIN32 +LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US +#pragma code_page(1252) +#endif //_WIN32 + +///////////////////////////////////////////////////////////////////////////// +// +// Icon +// + +// Icon with lowest ID value placed first to ensure application icon +// remains consistent on all systems. +IDI_MAIN_ICON ICON "directx.ico" + +#ifdef APSTUDIO_INVOKED +///////////////////////////////////////////////////////////////////////////// +// +// TEXTINCLUDE +// + +1 TEXTINCLUDE +BEGIN + "resource.h\0" +END + +2 TEXTINCLUDE +BEGIN + "#define IDC_STATIC -1\r\n" + "#include \r\n" + "\r\n" + "\r\n" + "\0" +END + +3 TEXTINCLUDE +BEGIN + "\r\n" + "\0" +END + +#endif // APSTUDIO_INVOKED + +#endif // English (U.S.) resources +///////////////////////////////////////////////////////////////////////////// + + + +#ifndef APSTUDIO_INVOKED +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 3 resource. +// + + +///////////////////////////////////////////////////////////////////////////// +#endif // not APSTUDIO_INVOKED + diff --git a/deps/DirectXTex/DDSView/DDSView_Desktop_2013.vcxproj b/deps/DirectXTex/DDSView/DDSView_Desktop_2013.vcxproj new file mode 100644 index 0000000..9e2aba3 --- /dev/null +++ b/deps/DirectXTex/DDSView/DDSView_Desktop_2013.vcxproj @@ -0,0 +1,408 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DDSView + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84} + DDSView + Win32Proj + $(VCTargetsPath11) + + + + Application + Unicode + v120 + + + Application + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DDSView + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DDSView + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Windows + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Windows + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DDSView/DDSView_Desktop_2013.vcxproj.filters b/deps/DirectXTex/DDSView/DDSView_Desktop_2013.vcxproj.filters new file mode 100644 index 0000000..ab6eee7 --- /dev/null +++ b/deps/DirectXTex/DDSView/DDSView_Desktop_2013.vcxproj.filters @@ -0,0 +1,20 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DDSView/DDSView_Desktop_2015.vcxproj b/deps/DirectXTex/DDSView/DDSView_Desktop_2015.vcxproj new file mode 100644 index 0000000..5887daf --- /dev/null +++ b/deps/DirectXTex/DDSView/DDSView_Desktop_2015.vcxproj @@ -0,0 +1,407 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DDSView + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84} + DDSView + Win32Proj + + + + Application + Unicode + v140 + + + Application + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DDSView + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DDSView + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Windows + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Windows + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DDSView/DDSView_Desktop_2015.vcxproj.filters b/deps/DirectXTex/DDSView/DDSView_Desktop_2015.vcxproj.filters new file mode 100644 index 0000000..ab6eee7 --- /dev/null +++ b/deps/DirectXTex/DDSView/DDSView_Desktop_2015.vcxproj.filters @@ -0,0 +1,20 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DDSView/DDSView_Desktop_2017.vcxproj b/deps/DirectXTex/DDSView/DDSView_Desktop_2017.vcxproj new file mode 100644 index 0000000..fc7722f --- /dev/null +++ b/deps/DirectXTex/DDSView/DDSView_Desktop_2017.vcxproj @@ -0,0 +1,414 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DDSView + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84} + DDSView + Win32Proj + 10.0.15063.0 + + + + Application + Unicode + v141 + + + Application + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DDSView + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DDSView + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DDSView + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + 4996 + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Windows + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + 4996 + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Windows + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + d3d11.lib;ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DDSView/DDSView_Desktop_2017.vcxproj.filters b/deps/DirectXTex/DDSView/DDSView_Desktop_2017.vcxproj.filters new file mode 100644 index 0000000..ab6eee7 --- /dev/null +++ b/deps/DirectXTex/DDSView/DDSView_Desktop_2017.vcxproj.filters @@ -0,0 +1,20 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DDSView/ddsview.cpp b/deps/DirectXTex/DDSView/ddsview.cpp new file mode 100644 index 0000000..7476c39 --- /dev/null +++ b/deps/DirectXTex/DDSView/ddsview.cpp @@ -0,0 +1,744 @@ +//-------------------------------------------------------------------------------------- +// File: DDSView.cpp +// +// DirectX 11 DDS File Viewer +// +// Copyright (c) Microsoft Corporation. All rights reserved. +//-------------------------------------------------------------------------------------- + +#define WIN32_LEAN_AND_MEAN +#define NOMINMAX +#include + +#include +#include +#include +#include + +#include + +#include + +#include "DirectXTex.h" + +using namespace DirectX; + +//-------------------------------------------------------------------------------------- +#define IDI_MAIN_ICON 100 + +//-------------------------------------------------------------------------------------- +#pragma pack(push,1) +struct SimpleVertex +{ + XMFLOAT4 Pos; + XMFLOAT4 Tex; +}; + +struct CBArrayControl +{ + float Index; + float pad[3]; +}; +#pragma pack(pop) + +//-------------------------------------------------------------------------------------- + +// fxc ddsview.fx /nologo /EVS /Tvs_4_1 /Fhshaders\vs.h +#include "shaders\vs.h" + +// fxc ddsview.fx /nologo /EPS_1D /Tps_4_1 /Fhshaders\ps1D.h +#include "shaders\ps1D.h" + +// fxc ddsview.fx /nologo /EPS_1DArray /Tps_4_1 /Fhshaders\ps1Darray.h +#include "shaders\\ps1Darray.h" + +// fxc ddsview.fx /nologo /EPS_2D /Tps_4_1 /Fhshaders\ps2D.h +#include "shaders\\ps2D.h" + +// fxc ddsview.fx /nologo /EPS_2DArray /Tps_4_1 /Fhshaders\ps2Darray.h +#include "shaders\ps2Darray.h" + +// fxc ddsview.fx /nologo /EPS_3D /Tps_4_1 /Fhshaders\ps3D.h +#include "shaders\ps3D.h" + +// fxc ddsview.fx /nologo /EPS_Cube /Tps_4_1 /Fhshaders\psCube.h +#include "shaders\psCube.h" + +//-------------------------------------------------------------------------------------- +HINSTANCE g_hInst = nullptr; +HWND g_hWnd = nullptr; +D3D_DRIVER_TYPE g_driverType = D3D_DRIVER_TYPE_NULL; +D3D_FEATURE_LEVEL g_featureLevel = D3D_FEATURE_LEVEL_11_0; +ID3D11Device* g_pd3dDevice = nullptr; +ID3D11DeviceContext* g_pImmediateContext = nullptr; +IDXGISwapChain* g_pSwapChain = nullptr; +ID3D11RenderTargetView* g_pRenderTargetView = nullptr; +ID3D11Texture2D* g_pDepthStencil = nullptr; +ID3D11DepthStencilView* g_pDepthStencilView = nullptr; +ID3D11VertexShader* g_pVertexShader = nullptr; +ID3D11PixelShader* g_pPixelShader = nullptr; +ID3D11InputLayout* g_pVertexLayout = nullptr; +ID3D11Buffer* g_pVertexBuffer = nullptr; +ID3D11Buffer* g_pIndexBuffer = nullptr; +ID3D11Buffer* g_pCBArrayControl = nullptr; +ID3D11ShaderResourceView* g_pSRV = nullptr; +ID3D11BlendState* g_AlphaBlendState = nullptr; +ID3D11SamplerState* g_pSamplerLinear = nullptr; + +UINT g_iCurrentIndex = 0; +UINT g_iMaxIndex = 1; + +UINT g_iIndices = 0; + + +//-------------------------------------------------------------------------------------- +HRESULT InitWindow( HINSTANCE hInstance, int nCmdShow, const TexMetadata& mdata ); +HRESULT InitDevice( const TexMetadata& mdata ); +void CleanupDevice(); +LRESULT CALLBACK WndProc( HWND, UINT, WPARAM, LPARAM ); +void Render(); + +//-------------------------------------------------------------------------------------- +#pragma warning( suppress : 6262 ) +int WINAPI wWinMain( _In_ HINSTANCE hInstance, _In_opt_ HINSTANCE hPrevInstance, _In_ LPWSTR lpCmdLine, _In_ int nCmdShow ) +{ + UNREFERENCED_PARAMETER( hPrevInstance ); + UNREFERENCED_PARAMETER( lpCmdLine ); + + if ( !*lpCmdLine ) + { + MessageBox( nullptr, L"Usage: ddsview ", L"DDSView", MB_OK | MB_ICONEXCLAMATION ); + return 0; + } + + TexMetadata mdata; + HRESULT hr = GetMetadataFromDDSFile( lpCmdLine, DDS_FLAGS_NONE, mdata ); + if ( FAILED(hr) ) + { + wchar_t buff[2048] = { 0 }; + swprintf_s( buff, L"Failed to open texture file\n\nFilename = %ls\nHRESULT %08X", lpCmdLine, hr ); + MessageBox( nullptr, buff, L"DDSView", MB_OK | MB_ICONEXCLAMATION ); + return 0; + } + + if( FAILED( InitWindow( hInstance, nCmdShow, mdata ) ) ) + return 0; + + SetWindowTextW( g_hWnd, lpCmdLine ); + + if( FAILED( InitDevice( mdata ) ) ) + { + CleanupDevice(); + return 0; + } + + if (mdata.dimension == TEX_DIMENSION_TEXTURE3D) + { + if ( mdata.arraySize > 1 ) + { + wchar_t buff[2048] = { 0 }; + swprintf_s( buff, L"Arrays of volume textures are not supported\n\nFilename = %ls\nArray size %Iu", lpCmdLine, mdata.arraySize ); + MessageBox( nullptr, buff, L"DDSView", MB_OK | MB_ICONEXCLAMATION ); + return 0; + } + + g_iMaxIndex = static_cast( mdata.depth ); + } + else + { + g_iMaxIndex = static_cast( mdata.arraySize ); + } + + switch( mdata.format ) + { + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + if ( g_featureLevel < D3D_FEATURE_LEVEL_11_0 ) + { + wchar_t buff[2048] = { 0 }; + swprintf_s( buff, L"BC6H/BC7 requires DirectX 11 hardware\n\nFilename = %ls\nDXGI Format %d\nFeature Level %d", lpCmdLine, mdata.format, g_featureLevel ); + MessageBox( nullptr, buff, L"DDSView", MB_OK | MB_ICONEXCLAMATION ); + return 0; + } + break; + + default: + { + UINT flags = 0; + hr = g_pd3dDevice->CheckFormatSupport ( mdata.format, &flags ); + if ( FAILED(hr) || !(flags & (D3D11_FORMAT_SUPPORT_TEXTURE1D|D3D11_FORMAT_SUPPORT_TEXTURE2D|D3D11_FORMAT_SUPPORT_TEXTURE3D)) ) + { + wchar_t buff[2048] = { 0 }; + swprintf_s( buff, L"Format not supported by DirectX hardware\n\nFilename = %ls\nDXGI Format %d\nFeature Level %d\nHRESULT = %08X", lpCmdLine, mdata.format, g_featureLevel, hr ); + MessageBox( nullptr, buff, L"DDSView", MB_OK | MB_ICONEXCLAMATION ); + return 0; + } + } + break; + } + + ScratchImage image; + hr = LoadFromDDSFile( lpCmdLine, DDS_FLAGS_NONE, &mdata, image ); + if ( FAILED(hr) ) + { + wchar_t buff[2048] = { 0 }; + swprintf_s( buff, L"Failed to load texture file\n\nFilename = %ls\nHRESULT %08X", lpCmdLine, hr ); + MessageBox( nullptr, buff, L"DDSView", MB_OK | MB_ICONEXCLAMATION ); + return 0; + } + + // Special case to make sure Texture cubes remain arrays + mdata.miscFlags &= ~TEX_MISC_TEXTURECUBE; + + hr = CreateShaderResourceView( g_pd3dDevice, image.GetImages(), image.GetImageCount(), mdata, &g_pSRV ); + if ( FAILED(hr) ) + { + wchar_t buff[2048] = { 0 }; + swprintf_s( buff, L"Failed creating texture from file\n\nFilename = %ls\nHRESULT = %08X", lpCmdLine, hr ); + MessageBox( nullptr, buff, L"DDSView", MB_OK | MB_ICONEXCLAMATION ); + return 0; + } + + // Main message loop + MSG msg = {0}; + while( WM_QUIT != msg.message ) + { + if( PeekMessage( &msg, nullptr, 0, 0, PM_REMOVE ) ) + { + TranslateMessage( &msg ); + DispatchMessage( &msg ); + } + else + { + Render(); + } + } + + CleanupDevice(); + + return ( int )msg.wParam; +} + +//-------------------------------------------------------------------------------------- +HRESULT InitWindow( HINSTANCE hInstance, int nCmdShow, const TexMetadata& mdata ) +{ + // Register class + WNDCLASSEX wcex; + wcex.cbSize = sizeof( WNDCLASSEX ); + wcex.style = CS_HREDRAW | CS_VREDRAW; + wcex.lpfnWndProc = WndProc; + wcex.cbClsExtra = 0; + wcex.cbWndExtra = 0; + wcex.hInstance = hInstance; + wcex.hIcon = LoadIcon( hInstance, ( LPCTSTR )IDI_MAIN_ICON ); + wcex.hCursor = LoadCursor( nullptr, IDC_ARROW ); + wcex.hbrBackground = ( HBRUSH )( COLOR_WINDOW + 1 ); + wcex.lpszMenuName = nullptr; + wcex.lpszClassName = L"DDSViewWindowClass"; + wcex.hIconSm = LoadIcon( wcex.hInstance, ( LPCTSTR )IDI_MAIN_ICON ); + if( !RegisterClassEx( &wcex ) ) + return E_FAIL; + + // Create window + g_hInst = hInstance; + RECT rc = { 0, 0, 640, 480 }; + + int cxborder = GetSystemMetrics( SM_CXBORDER ); + int cxedge = GetSystemMetrics( SM_CXEDGE ); + int screenX = GetSystemMetrics( SM_CXSCREEN ) - std::max( cxborder, cxedge ); + if( rc.right < (LONG)mdata.width ) + rc.right = (LONG)mdata.width; + if ( rc.right > screenX ) + rc.right = screenX; + + int cyborder = GetSystemMetrics( SM_CYBORDER ); + int cyedge = GetSystemMetrics( SM_CYEDGE ); + int screenY = GetSystemMetrics( SM_CYSCREEN ) - std::max( cyborder, cyedge ); + if ( rc.bottom < (LONG)mdata.height ) + rc.bottom = (LONG)mdata.height; + if ( rc.bottom > screenY ) + rc.bottom = screenY; + + AdjustWindowRect( &rc, WS_OVERLAPPEDWINDOW, FALSE ); + g_hWnd = CreateWindow( L"DDSViewWindowClass", L"DDS View", WS_OVERLAPPEDWINDOW, + CW_USEDEFAULT, CW_USEDEFAULT, rc.right - rc.left, rc.bottom - rc.top, nullptr, nullptr, hInstance, + nullptr ); + if( !g_hWnd ) + return E_FAIL; + + ShowWindow( g_hWnd, nCmdShow ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +LRESULT CALLBACK WndProc( HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam ) +{ + PAINTSTRUCT ps; + HDC hdc; + + switch( message ) + { + case WM_PAINT: + hdc = BeginPaint( hWnd, &ps ); + EndPaint( hWnd, &ps ); + break; + + case WM_DESTROY: + PostQuitMessage( 0 ); + break; + + case WM_KEYDOWN: + if ( wParam == VK_RIGHT ) + { + if ( g_iCurrentIndex < g_iMaxIndex-1 ) + ++g_iCurrentIndex; + } + else if ( wParam == VK_LEFT ) + { + if ( g_iCurrentIndex > 0 ) + { + --g_iCurrentIndex; + } + } + else if ( wParam >= '0' && wParam <= '9' ) + { + UINT index = (wParam == '0') ? 10 : ((UINT) (wParam - '1')); + if ( index < g_iMaxIndex ) + g_iCurrentIndex = index; + } + InvalidateRect( hWnd, nullptr, FALSE ); + break; + + default: + return DefWindowProc( hWnd, message, wParam, lParam ); + } + + return 0; +} + + +//-------------------------------------------------------------------------------------- +HRESULT InitDevice( const TexMetadata& mdata ) +{ + HRESULT hr = S_OK; + + RECT rc; + GetClientRect( g_hWnd, &rc ); + UINT width = rc.right - rc.left; + UINT height = rc.bottom - rc.top; + + UINT createDeviceFlags = 0; +#if defined( DEBUG ) || defined( _DEBUG ) + createDeviceFlags |= D3D11_CREATE_DEVICE_DEBUG; +#endif + + D3D_DRIVER_TYPE driverTypes[] = + { + D3D_DRIVER_TYPE_HARDWARE, + D3D_DRIVER_TYPE_WARP, + D3D_DRIVER_TYPE_REFERENCE, + }; + UINT numDriverTypes = ARRAYSIZE( driverTypes ); + + D3D_FEATURE_LEVEL featureLevels[] = + { + D3D_FEATURE_LEVEL_11_0, + D3D_FEATURE_LEVEL_10_1, + D3D_FEATURE_LEVEL_10_0, + }; + UINT numFeatureLevels = ARRAYSIZE( featureLevels ); + + DXGI_SWAP_CHAIN_DESC sd; + ZeroMemory( &sd, sizeof( sd ) ); + sd.BufferCount = 1; + sd.BufferDesc.Width = width; + sd.BufferDesc.Height = height; + sd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; + sd.BufferDesc.RefreshRate.Numerator = 60; + sd.BufferDesc.RefreshRate.Denominator = 1; + sd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; + sd.OutputWindow = g_hWnd; + sd.SampleDesc.Count = 1; + sd.SampleDesc.Quality = 0; + sd.Windowed = TRUE; + + for( UINT driverTypeIndex = 0; driverTypeIndex < numDriverTypes; driverTypeIndex++ ) + { + g_driverType = driverTypes[driverTypeIndex]; + hr = D3D11CreateDeviceAndSwapChain( nullptr, g_driverType, nullptr, createDeviceFlags, featureLevels, numFeatureLevels, + D3D11_SDK_VERSION, &sd, &g_pSwapChain, &g_pd3dDevice, &g_featureLevel, &g_pImmediateContext ); + if( SUCCEEDED( hr ) ) + break; + } + if( FAILED( hr ) ) + return hr; + + // Create a render target view + ID3D11Texture2D* pBackBuffer = nullptr; + hr = g_pSwapChain->GetBuffer( 0, IID_PPV_ARGS(&pBackBuffer) ); + if( FAILED( hr ) ) + return hr; + + hr = g_pd3dDevice->CreateRenderTargetView( pBackBuffer, nullptr, &g_pRenderTargetView ); + pBackBuffer->Release(); + if( FAILED( hr ) ) + return hr; + + // Create depth stencil texture + D3D11_TEXTURE2D_DESC descDepth; + ZeroMemory( &descDepth, sizeof(descDepth) ); + descDepth.Width = width; + descDepth.Height = height; + descDepth.MipLevels = 1; + descDepth.ArraySize = 1; + descDepth.Format = DXGI_FORMAT_D24_UNORM_S8_UINT; + descDepth.SampleDesc.Count = 1; + descDepth.SampleDesc.Quality = 0; + descDepth.Usage = D3D11_USAGE_DEFAULT; + descDepth.BindFlags = D3D11_BIND_DEPTH_STENCIL; + descDepth.CPUAccessFlags = 0; + descDepth.MiscFlags = 0; + hr = g_pd3dDevice->CreateTexture2D( &descDepth, nullptr, &g_pDepthStencil ); + if( FAILED( hr ) ) + return hr; + + // Create the depth stencil view + D3D11_DEPTH_STENCIL_VIEW_DESC descDSV; + ZeroMemory( &descDSV, sizeof(descDSV) ); + descDSV.Format = descDepth.Format; + descDSV.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D; + descDSV.Texture2D.MipSlice = 0; + hr = g_pd3dDevice->CreateDepthStencilView( g_pDepthStencil, &descDSV, &g_pDepthStencilView ); + if( FAILED( hr ) ) + return hr; + + g_pImmediateContext->OMSetRenderTargets( 1, &g_pRenderTargetView, g_pDepthStencilView ); + + // Setup the viewport + D3D11_VIEWPORT vp; + vp.Width = (FLOAT)width; + vp.Height = (FLOAT)height; + vp.MinDepth = 0.0f; + vp.MaxDepth = 1.0f; + vp.TopLeftX = 0; + vp.TopLeftY = 0; + g_pImmediateContext->RSSetViewports( 1, &vp ); + + // Create the vertex shader + hr = g_pd3dDevice->CreateVertexShader( g_VS, sizeof(g_VS), nullptr, &g_pVertexShader ); + if( FAILED( hr ) ) + return hr; + + // Define the input layout + D3D11_INPUT_ELEMENT_DESC layout[] = + { + { "POSITION", 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "TEXCOORD", 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, sizeof(XMFLOAT4), D3D11_INPUT_PER_VERTEX_DATA, 0 }, + }; + UINT numElements = ARRAYSIZE( layout ); + + // Create the input layout + hr = g_pd3dDevice->CreateInputLayout( layout, numElements, g_VS, sizeof(g_VS), &g_pVertexLayout ); + if( FAILED( hr ) ) + return hr; + + // Set the input layout + g_pImmediateContext->IASetInputLayout( g_pVertexLayout ); + + // Select the pixel shader + bool isCubeMap = false; + bool is1D = false; + const BYTE* pshader = nullptr; + size_t pshader_size = 0; + + switch ( mdata.dimension ) + { + case TEX_DIMENSION_TEXTURE1D: + if ( mdata.arraySize > 1) + { + pshader = g_PS_1DArray; + pshader_size = sizeof(g_PS_1DArray); + } + else + { + pshader = g_PS_1D; + pshader_size = sizeof(g_PS_1D); + } + is1D = true; + break; + + case TEX_DIMENSION_TEXTURE2D: + if ( mdata.miscFlags & TEX_MISC_TEXTURECUBE ) + { + pshader = g_PS_Cube; + pshader_size = sizeof(g_PS_Cube); + isCubeMap = true; + } + else if ( mdata.arraySize > 1 ) + { + pshader = g_PS_2DArray; + pshader_size = sizeof(g_PS_2DArray); + } + else + { + pshader = g_PS_2D; + pshader_size = sizeof(g_PS_2D); + } + break; + + case TEX_DIMENSION_TEXTURE3D: + pshader = g_PS_3D; + pshader_size = sizeof(g_PS_3D); + break; + + default: + return E_FAIL; + } + + assert( pshader && pshader_size > 0 ); + + // Create the pixel shader + hr = g_pd3dDevice->CreatePixelShader( pshader, pshader_size, nullptr, &g_pPixelShader ); + if( FAILED( hr ) ) + return hr; + + // Create vertex buffer + UINT nverts; + D3D11_SUBRESOURCE_DATA InitData; + ZeroMemory( &InitData, sizeof(InitData) ); + + static const SimpleVertex verticesCube[] = + { + // Render cubemaps as horizontal cross + + // XPOS + { XMFLOAT4( .5f, .25f, 0.f, 1.f ), XMFLOAT4( 0.f, 0.f, 0.f, 0.f ) }, + { XMFLOAT4( 1.f, .25f, 0.f, 1.f ), XMFLOAT4( 1.f, 0.f, 0.f, 0.f ) }, + { XMFLOAT4( .5f, -.25f, 0.f, 1.f ), XMFLOAT4( 0.f, 1.f, 0.f, 0.f ) }, + { XMFLOAT4( 1.f, -.25f, 0.f, 1.f ), XMFLOAT4( 1.f, 1.f, 0.f, 0.f ) }, + + // XNEG + { XMFLOAT4( -.5f, .25f, 0.f, 1.f ), XMFLOAT4( 0.f, 0.f, 1.f, 0.f ) }, + { XMFLOAT4( 0.f, .25f, 0.f, 1.f ), XMFLOAT4( 1.f, 0.f, 1.f, 0.f ) }, + { XMFLOAT4( -.5f, -.25f, 0.f, 1.f ), XMFLOAT4( 0.f, 1.f, 1.f, 0.f ) }, + { XMFLOAT4( 0.f, -.25f, 0.f, 1.f ), XMFLOAT4( 1.f, 1.f, 1.f, 0.f ) }, + + // YPOS + { XMFLOAT4( -.5f, .75f, 0.f, 1.f ), XMFLOAT4( 0.f, 0.f, 2.f, 0.f ) }, + { XMFLOAT4( 0.f, .75f, 0.f, 1.f ), XMFLOAT4( 1.f, 0.f, 2.f, 0.f ) }, + { XMFLOAT4( -.5f, .25f, 0.f, 1.f ), XMFLOAT4( 0.f, 1.f, 2.f, 0.f ) }, + { XMFLOAT4( 0.f, .25f, 0.f, 1.f ), XMFLOAT4( 1.f, 1.f, 2.f, 0.f ) }, + + // YNEG + { XMFLOAT4( -.5f, -.25f, 0.f, 1.f ), XMFLOAT4( 0.f, 0.f, 3.f, 0.f ) }, + { XMFLOAT4( 0.f, -.25f, 0.f, 1.f ), XMFLOAT4( 1.f, 0.f, 3.f, 0.f ) }, + { XMFLOAT4( -.5f, -.75f, 0.f, 1.f ), XMFLOAT4( 0.f, 1.f, 3.f, 0.f ) }, + { XMFLOAT4( 0.f, -.75f, 0.f, 1.f ), XMFLOAT4( 1.f, 1.f, 3.f, 0.f ) }, + + // ZPOS + { XMFLOAT4( 0.f, .25f, 0.f, 1.f ), XMFLOAT4( 0.f, 0.f, 4.f, 0.f ) }, + { XMFLOAT4( .5f, .25f, 0.f, 1.f ), XMFLOAT4( 1.f, 0.f, 4.f, 0.f ) }, + { XMFLOAT4( 0.f, -.25f, 0.f, 1.f ), XMFLOAT4( 0.f, 1.f, 4.f, 0.f ) }, + { XMFLOAT4( .5f, -.25f, 0.f, 1.f ), XMFLOAT4( 1.f, 1.f, 4.f, 0.f ) }, + + // ZNEG + { XMFLOAT4( -1.f, .25f, 0.f, 1.f ), XMFLOAT4( 0.f, 0.f, 5.f, 0.f ) }, + { XMFLOAT4( -.5f, .25f, 0.f, 1.f ), XMFLOAT4( 1.f, 0.f, 5.f, 0.f ) }, + { XMFLOAT4( -1.f, -.25f, 0.f, 1.f ), XMFLOAT4( 0.f, 1.f, 5.f, 0.f ) }, + { XMFLOAT4( -.5f, -.25f, 0.f, 1.f ), XMFLOAT4( 1.f, 1.f, 5.f, 0.f ) }, + }; + + static const SimpleVertex vertices[] = + { + { XMFLOAT4( -1.f, 1.f, 0.f, 1.f ), XMFLOAT4( 0.f, 0.f, 0.f, 0.f ) }, + { XMFLOAT4( 1.f, 1.f, 0.f, 1.f ), XMFLOAT4( 1.f, 0.f, 0.f, 0.f ) }, + { XMFLOAT4( -1.f, -1.f, 0.f, 1.f ), XMFLOAT4( 0.f, 1.f, 0.f, 0.f ) }, + { XMFLOAT4( 1.f, -1.f, 0.f, 1.f ), XMFLOAT4( 1.f, 1.f, 0.f, 0.f ) }, + }; + + static const SimpleVertex vertices1D[] = + { + { XMFLOAT4( -1.f, .05f, 0.f, 1.f ), XMFLOAT4( 0.f, 0.f, 0.f, 0.f ) }, + { XMFLOAT4( 1.f, .05f, 0.f, 1.f ), XMFLOAT4( 1.f, 0.f, 0.f, 0.f ) }, + { XMFLOAT4( -1.f, -.05f, 0.f, 1.f ), XMFLOAT4( 0.f, 0.f, 0.f, 0.f ) }, + { XMFLOAT4( 1.f, -.05f, 0.f, 1.f ), XMFLOAT4( 1.f, 0.f, 0.f, 0.f ) }, + }; + + if ( isCubeMap ) + { + nverts = _countof(verticesCube); + InitData.pSysMem = verticesCube; + } + else if ( is1D ) + { + nverts = _countof(vertices1D); + InitData.pSysMem = vertices1D; + } + else + { + nverts = _countof(vertices); + InitData.pSysMem = vertices; + } + + D3D11_BUFFER_DESC bd; + ZeroMemory( &bd, sizeof(bd) ); + bd.Usage = D3D11_USAGE_DEFAULT; + bd.ByteWidth = sizeof( SimpleVertex ) * nverts; + bd.BindFlags = D3D11_BIND_VERTEX_BUFFER; + bd.CPUAccessFlags = 0; + hr = g_pd3dDevice->CreateBuffer( &bd, &InitData, &g_pVertexBuffer ); + if( FAILED( hr ) ) + return hr; + + // Set vertex buffer + UINT stride = sizeof( SimpleVertex ); + UINT offset = 0; + g_pImmediateContext->IASetVertexBuffers( 0, 1, &g_pVertexBuffer, &stride, &offset ); + + // Create index buffer + static const WORD indicesCube[] = + { + 0, 1, 2, + 2, 1, 3, + 4, 5, 6, + 6, 5, 7, + 8, 9, 10, + 10, 9, 11, + 12, 13, 14, + 14, 13, 15, + 16, 17, 18, + 18, 17, 19, + 20, 21, 22, + 22, 21, 23 + }; + + static const WORD indices[] = + { + 0, 1, 2, + 2, 1, 3 + }; + + if ( isCubeMap ) + { + g_iIndices = _countof(indicesCube); + InitData.pSysMem = indicesCube; + } + else + { + g_iIndices = _countof(indices); + InitData.pSysMem = indices; + } + + bd.Usage = D3D11_USAGE_DEFAULT; + bd.ByteWidth = g_iIndices * sizeof(WORD); + bd.BindFlags = D3D11_BIND_INDEX_BUFFER; + bd.CPUAccessFlags = 0; + hr = g_pd3dDevice->CreateBuffer( &bd, &InitData, &g_pIndexBuffer ); + if( FAILED( hr ) ) + return hr; + + // Set index buffer + g_pImmediateContext->IASetIndexBuffer( g_pIndexBuffer, DXGI_FORMAT_R16_UINT, 0 ); + + // Set primitive topology + g_pImmediateContext->IASetPrimitiveTopology( D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST ); + + // Create the constant buffers + bd.Usage = D3D11_USAGE_DEFAULT; + bd.ByteWidth = sizeof(CBArrayControl); + bd.BindFlags = D3D11_BIND_CONSTANT_BUFFER; + bd.CPUAccessFlags = 0; + hr = g_pd3dDevice->CreateBuffer( &bd, nullptr, &g_pCBArrayControl ); + if( FAILED( hr ) ) + return hr; + + // Create the state objects + D3D11_SAMPLER_DESC sampDesc; + ZeroMemory( &sampDesc, sizeof(sampDesc) ); + sampDesc.Filter = D3D11_FILTER_MIN_MAG_MIP_POINT; + sampDesc.AddressU = D3D11_TEXTURE_ADDRESS_WRAP; + sampDesc.AddressV = D3D11_TEXTURE_ADDRESS_WRAP; + sampDesc.AddressW = D3D11_TEXTURE_ADDRESS_WRAP; + sampDesc.ComparisonFunc = D3D11_COMPARISON_NEVER; + sampDesc.MinLOD = 0; + sampDesc.MaxLOD = D3D11_FLOAT32_MAX; + hr = g_pd3dDevice->CreateSamplerState( &sampDesc, &g_pSamplerLinear ); + if( FAILED( hr ) ) + return hr; + + D3D11_BLEND_DESC dsc = + { + false, + false, + { + true, + D3D11_BLEND_SRC_ALPHA, + D3D11_BLEND_INV_SRC_ALPHA, + D3D11_BLEND_OP_ADD, + D3D11_BLEND_ZERO, + D3D11_BLEND_ZERO, + D3D11_BLEND_OP_ADD, + D3D11_COLOR_WRITE_ENABLE_ALL + } + }; + hr = g_pd3dDevice->CreateBlendState(&dsc, &g_AlphaBlendState ); + if( FAILED(hr) ) + return hr; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +void Render() +{ + float ClearColor[4] = { 0.f, 1.f, 1.f, 1.0f }; //red,green,blue,alpha + g_pImmediateContext->ClearRenderTargetView( g_pRenderTargetView, ClearColor ); + g_pImmediateContext->ClearDepthStencilView( g_pDepthStencilView, D3D11_CLEAR_DEPTH, 1.0f, 0 ); + + float bf [4] = {1.0f, 1.0f, 1.0f, 1.0f}; + g_pImmediateContext->OMSetBlendState( g_AlphaBlendState, bf, 0xffffffff ); + + CBArrayControl cb; + cb.Index = (float)g_iCurrentIndex; + g_pImmediateContext->UpdateSubresource( g_pCBArrayControl, 0, nullptr, &cb, 0, 0 ); + + g_pImmediateContext->VSSetShader( g_pVertexShader, nullptr, 0 ); + g_pImmediateContext->PSSetShader( g_pPixelShader, nullptr, 0 ); + g_pImmediateContext->PSSetConstantBuffers( 0, 1, &g_pCBArrayControl ); + g_pImmediateContext->PSSetShaderResources( 0, 1, &g_pSRV ); + g_pImmediateContext->PSSetSamplers( 0, 1, &g_pSamplerLinear ); + g_pImmediateContext->DrawIndexed( g_iIndices, 0, 0 ); + + g_pSwapChain->Present( 0, 0 ); +} + + +//-------------------------------------------------------------------------------------- +void CleanupDevice() +{ + if( g_pImmediateContext ) g_pImmediateContext->ClearState(); + + if( g_pSamplerLinear ) g_pSamplerLinear->Release(); + if( g_AlphaBlendState ) g_AlphaBlendState->Release(); + if( g_pSRV ) g_pSRV->Release(); + if( g_pVertexBuffer ) g_pVertexBuffer->Release(); + if( g_pIndexBuffer ) g_pIndexBuffer->Release(); + if( g_pCBArrayControl ) g_pCBArrayControl->Release(); + if( g_pVertexLayout ) g_pVertexLayout->Release(); + if( g_pVertexShader ) g_pVertexShader->Release(); + if( g_pPixelShader ) g_pPixelShader->Release(); + if( g_pDepthStencil ) g_pDepthStencil->Release(); + if( g_pDepthStencilView ) g_pDepthStencilView->Release(); + if( g_pRenderTargetView ) g_pRenderTargetView->Release(); + if( g_pSwapChain ) g_pSwapChain->Release(); + if( g_pImmediateContext ) g_pImmediateContext->Release(); + if( g_pd3dDevice ) g_pd3dDevice->Release(); +} + diff --git a/deps/DirectXTex/DDSView/ddsview.fx b/deps/DirectXTex/DDSView/ddsview.fx new file mode 100644 index 0000000..dc40f69 --- /dev/null +++ b/deps/DirectXTex/DDSView/ddsview.fx @@ -0,0 +1,85 @@ +//-------------------------------------------------------------------------------------- +// File: ddsview.fx +// +// Copyright (c) Microsoft Corporation. All rights reserved. +//-------------------------------------------------------------------------------------- + +//-------------------------------------------------------------------------------------- +// Constant Buffer Variables +//-------------------------------------------------------------------------------------- +Texture1D tx1D : register( t0 ); +Texture1DArray tx1DArray : register( t0 ); + +Texture2D tx2D : register( t0 ); +Texture2DArray tx2DArray : register( t0 ); + +Texture3D tx3D : register( t0 ); + +SamplerState samLinear : register( s0 ); + +cbuffer cbArrayControl : register( b0 ) +{ + float Index; +}; + +//-------------------------------------------------------------------------------------- +struct VS_INPUT +{ + float4 Pos : POSITION; + float4 Tex : TEXCOORD0; +}; + +struct PS_INPUT +{ + float4 Pos : SV_POSITION; + float4 Tex : TEXCOORD0; +}; + + +//-------------------------------------------------------------------------------------- +// Vertex Shader +//-------------------------------------------------------------------------------------- +PS_INPUT VS( VS_INPUT input ) +{ + PS_INPUT output = (PS_INPUT)0; + output.Pos = input.Pos; + output.Tex = input.Tex; + return output; +} + + +//-------------------------------------------------------------------------------------- +// Pixel Shader +//-------------------------------------------------------------------------------------- +float4 PS_1D( PS_INPUT input) : SV_Target +{ + return tx1D.Sample( samLinear, input.Tex.x ); +} + +float4 PS_1DArray( PS_INPUT input) : SV_Target +{ + return tx1DArray.Sample( samLinear, float2(input.Tex.x, Index) ); +} + +float4 PS_2D( PS_INPUT input) : SV_Target +{ + return tx2D.Sample( samLinear, input.Tex.xy ); +} + +float4 PS_2DArray( PS_INPUT input) : SV_Target +{ + return tx2DArray.Sample( samLinear, float3(input.Tex.xy, Index) ); +} + +float4 PS_3D( PS_INPUT input) : SV_Target +{ + int Width, Height, Depth; + tx3D.GetDimensions( Width, Height, Depth); + + return tx3D.Sample( samLinear, float3(input.Tex.xy, Index / Depth) ); +} + +float4 PS_Cube( PS_INPUT input) : SV_Target +{ + return tx2DArray.Sample( samLinear, float3(input.Tex.xy, input.Tex.z + (6*Index)) ); +} diff --git a/deps/DirectXTex/DDSView/directx.ico b/deps/DirectXTex/DDSView/directx.ico new file mode 100644 index 0000000..bc43c1b Binary files /dev/null and b/deps/DirectXTex/DDSView/directx.ico differ diff --git a/deps/DirectXTex/DDSView/hlsl.cmd b/deps/DirectXTex/DDSView/hlsl.cmd new file mode 100644 index 0000000..cc7253b --- /dev/null +++ b/deps/DirectXTex/DDSView/hlsl.cmd @@ -0,0 +1,8 @@ +fxc ddsview.fx /nologo /EVS /Tvs_4_1 /Fhshaders\vs.h +fxc ddsview.fx /nologo /EPS_1D /Tps_4_1 /Fhshaders\ps1D.h +fxc ddsview.fx /nologo /EPS_1DArray /Tps_4_1 /Fhshaders\ps1Darray.h +fxc ddsview.fx /nologo /EPS_2D /Tps_4_1 /Fhshaders\ps2D.h +fxc ddsview.fx /nologo /EPS_2DArray /Tps_4_1 /Fhshaders\ps2Darray.h +fxc ddsview.fx /nologo /EPS_3D /Tps_4_1 /Fhshaders\ps3D.h +fxc ddsview.fx /nologo /EPS_Cube /Tps_4_1 /Fhshaders\psCube.h + diff --git a/deps/DirectXTex/DDSView/shaders/ps1D.h b/deps/DirectXTex/DDSView/shaders/ps1D.h new file mode 100644 index 0000000..d9344fd --- /dev/null +++ b/deps/DirectXTex/DDSView/shaders/ps1D.h @@ -0,0 +1,179 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 9.29.952.3111 +// +// +// fxc ddsview.fx /nologo /EPS_1D /Tps_4_1 /Fhshaders\ps1D.h +// +// +// Buffer Definitions: +// +// cbuffer cbArrayControl +// { +// +// float Index; // Offset: 0 Size: 4 [unused] +// +// } +// +// +// Resource Bindings: +// +// Name Type Format Dim Slot Elements +// ------------------------------ ---------- ------- ----------- ---- -------- +// samLinear sampler NA NA 0 1 +// tx1D texture float4 1d 0 1 +// cbArrayControl cbuffer NA NA 0 1 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_POSITION 0 xyzw 0 POS float +// TEXCOORD 0 xyzw 1 NONE float x +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_Target 0 xyzw 0 TARGET float xyzw +// +ps_4_1 +dcl_globalFlags refactoringAllowed +dcl_constantbuffer cb0[1], immediateIndexed +dcl_sampler s0, mode_default +dcl_resource_texture1d (float,float,float,float) t0 +dcl_input_ps linear v1.x +dcl_output o0.xyzw +sample o0.xyzw, v1.xxxx, t0.xyzw, s0 +ret +// Approximately 2 instruction slots used +#endif + +const BYTE g_PS_1D[] = +{ + 68, 88, 66, 67, 71, 33, + 105, 235, 206, 215, 61, 110, + 190, 73, 39, 172, 36, 251, + 31, 148, 1, 0, 0, 0, + 220, 2, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 84, 1, 0, 0, 172, 1, + 0, 0, 224, 1, 0, 0, + 96, 2, 0, 0, 82, 68, + 69, 70, 24, 1, 0, 0, + 1, 0, 0, 0, 156, 0, + 0, 0, 3, 0, 0, 0, + 28, 0, 0, 0, 1, 4, + 255, 255, 0, 1, 0, 0, + 228, 0, 0, 0, 124, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 134, 0, 0, 0, 2, 0, + 0, 0, 5, 0, 0, 0, + 2, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 1, 0, 0, 0, 13, 0, + 0, 0, 139, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 115, 97, + 109, 76, 105, 110, 101, 97, + 114, 0, 116, 120, 49, 68, + 0, 99, 98, 65, 114, 114, + 97, 121, 67, 111, 110, 116, + 114, 111, 108, 0, 171, 171, + 139, 0, 0, 0, 1, 0, + 0, 0, 180, 0, 0, 0, + 16, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 204, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 212, 0, + 0, 0, 0, 0, 0, 0, + 73, 110, 100, 101, 120, 0, + 171, 171, 0, 0, 3, 0, + 1, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 77, 105, 99, 114, 111, 115, + 111, 102, 116, 32, 40, 82, + 41, 32, 72, 76, 83, 76, + 32, 83, 104, 97, 100, 101, + 114, 32, 67, 111, 109, 112, + 105, 108, 101, 114, 32, 57, + 46, 50, 57, 46, 57, 53, + 50, 46, 51, 49, 49, 49, + 0, 171, 171, 171, 73, 83, + 71, 78, 80, 0, 0, 0, + 2, 0, 0, 0, 8, 0, + 0, 0, 56, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 68, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 0, 15, 1, + 0, 0, 83, 86, 95, 80, + 79, 83, 73, 84, 73, 79, + 78, 0, 84, 69, 88, 67, + 79, 79, 82, 68, 0, 171, + 171, 171, 79, 83, 71, 78, + 44, 0, 0, 0, 1, 0, + 0, 0, 8, 0, 0, 0, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 83, 86, 95, 84, 97, 114, + 103, 101, 116, 0, 171, 171, + 83, 72, 68, 82, 120, 0, + 0, 0, 65, 0, 0, 0, + 30, 0, 0, 0, 106, 8, + 0, 1, 89, 0, 0, 4, + 70, 142, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 90, 0, 0, 3, 0, 96, + 16, 0, 0, 0, 0, 0, + 88, 16, 0, 4, 0, 112, + 16, 0, 0, 0, 0, 0, + 85, 85, 0, 0, 98, 16, + 0, 3, 18, 16, 16, 0, + 1, 0, 0, 0, 101, 0, + 0, 3, 242, 32, 16, 0, + 0, 0, 0, 0, 69, 0, + 0, 9, 242, 32, 16, 0, + 0, 0, 0, 0, 6, 16, + 16, 0, 1, 0, 0, 0, + 70, 126, 16, 0, 0, 0, + 0, 0, 0, 96, 16, 0, + 0, 0, 0, 0, 62, 0, + 0, 1, 83, 84, 65, 84, + 116, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0 +}; diff --git a/deps/DirectXTex/DDSView/shaders/ps1Darray.h b/deps/DirectXTex/DDSView/shaders/ps1Darray.h new file mode 100644 index 0000000..9f236b0 --- /dev/null +++ b/deps/DirectXTex/DDSView/shaders/ps1Darray.h @@ -0,0 +1,192 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 9.29.952.3111 +// +// +// fxc ddsview.fx /nologo /EPS_1DArray /Tps_4_1 /Fhshaders\ps1Darray.h +// +// +// Buffer Definitions: +// +// cbuffer cbArrayControl +// { +// +// float Index; // Offset: 0 Size: 4 +// +// } +// +// +// Resource Bindings: +// +// Name Type Format Dim Slot Elements +// ------------------------------ ---------- ------- ----------- ---- -------- +// samLinear sampler NA NA 0 1 +// tx1DArray texture float4 1darray 0 1 +// cbArrayControl cbuffer NA NA 0 1 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_POSITION 0 xyzw 0 POS float +// TEXCOORD 0 xyzw 1 NONE float x +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_Target 0 xyzw 0 TARGET float xyzw +// +ps_4_1 +dcl_globalFlags refactoringAllowed +dcl_constantbuffer cb0[1], immediateIndexed +dcl_sampler s0, mode_default +dcl_resource_texture1darray (float,float,float,float) t0 +dcl_input_ps linear v1.x +dcl_output o0.xyzw +dcl_temps 1 +mov r0.x, v1.x +mov r0.y, cb0[0].x +sample o0.xyzw, r0.xyxx, t0.xyzw, s0 +ret +// Approximately 4 instruction slots used +#endif + +const BYTE g_PS_1DArray[] = +{ + 68, 88, 66, 67, 210, 249, + 153, 123, 172, 65, 50, 100, + 250, 1, 76, 219, 67, 149, + 143, 209, 1, 0, 0, 0, + 20, 3, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 88, 1, 0, 0, 176, 1, + 0, 0, 228, 1, 0, 0, + 152, 2, 0, 0, 82, 68, + 69, 70, 28, 1, 0, 0, + 1, 0, 0, 0, 160, 0, + 0, 0, 3, 0, 0, 0, + 28, 0, 0, 0, 1, 4, + 255, 255, 0, 1, 0, 0, + 232, 0, 0, 0, 124, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 134, 0, 0, 0, 2, 0, + 0, 0, 5, 0, 0, 0, + 3, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 1, 0, 0, 0, 13, 0, + 0, 0, 144, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 115, 97, + 109, 76, 105, 110, 101, 97, + 114, 0, 116, 120, 49, 68, + 65, 114, 114, 97, 121, 0, + 99, 98, 65, 114, 114, 97, + 121, 67, 111, 110, 116, 114, + 111, 108, 0, 171, 144, 0, + 0, 0, 1, 0, 0, 0, + 184, 0, 0, 0, 16, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 208, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 2, 0, + 0, 0, 216, 0, 0, 0, + 0, 0, 0, 0, 73, 110, + 100, 101, 120, 0, 171, 171, + 0, 0, 3, 0, 1, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 77, 105, + 99, 114, 111, 115, 111, 102, + 116, 32, 40, 82, 41, 32, + 72, 76, 83, 76, 32, 83, + 104, 97, 100, 101, 114, 32, + 67, 111, 109, 112, 105, 108, + 101, 114, 32, 57, 46, 50, + 57, 46, 57, 53, 50, 46, + 51, 49, 49, 49, 0, 171, + 171, 171, 73, 83, 71, 78, + 80, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 56, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 68, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 0, 15, 1, 0, 0, + 83, 86, 95, 80, 79, 83, + 73, 84, 73, 79, 78, 0, + 84, 69, 88, 67, 79, 79, + 82, 68, 0, 171, 171, 171, + 79, 83, 71, 78, 44, 0, + 0, 0, 1, 0, 0, 0, + 8, 0, 0, 0, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 83, 86, + 95, 84, 97, 114, 103, 101, + 116, 0, 171, 171, 83, 72, + 68, 82, 172, 0, 0, 0, + 65, 0, 0, 0, 43, 0, + 0, 0, 106, 8, 0, 1, + 89, 0, 0, 4, 70, 142, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 90, 0, + 0, 3, 0, 96, 16, 0, + 0, 0, 0, 0, 88, 56, + 0, 4, 0, 112, 16, 0, + 0, 0, 0, 0, 85, 85, + 0, 0, 98, 16, 0, 3, + 18, 16, 16, 0, 1, 0, + 0, 0, 101, 0, 0, 3, + 242, 32, 16, 0, 0, 0, + 0, 0, 104, 0, 0, 2, + 1, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 16, + 16, 0, 1, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 69, 0, 0, 9, 242, 32, + 16, 0, 0, 0, 0, 0, + 70, 0, 16, 0, 0, 0, + 0, 0, 70, 126, 16, 0, + 0, 0, 0, 0, 0, 96, + 16, 0, 0, 0, 0, 0, + 62, 0, 0, 1, 83, 84, + 65, 84, 116, 0, 0, 0, + 4, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0 +}; diff --git a/deps/DirectXTex/DDSView/shaders/ps2D.h b/deps/DirectXTex/DDSView/shaders/ps2D.h new file mode 100644 index 0000000..2274034 --- /dev/null +++ b/deps/DirectXTex/DDSView/shaders/ps2D.h @@ -0,0 +1,144 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 9.29.952.3111 +// +// +// fxc ddsview.fx /nologo /EPS_2D /Tps_4_1 /Fhshaders\ps2D.h +// +// +// Resource Bindings: +// +// Name Type Format Dim Slot Elements +// ------------------------------ ---------- ------- ----------- ---- -------- +// samLinear sampler NA NA 0 1 +// tx2D texture float4 2d 0 1 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_POSITION 0 xyzw 0 POS float +// TEXCOORD 0 xyzw 1 NONE float xy +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_Target 0 xyzw 0 TARGET float xyzw +// +ps_4_1 +dcl_globalFlags refactoringAllowed +dcl_sampler s0, mode_default +dcl_resource_texture2d (float,float,float,float) t0 +dcl_input_ps linear v1.xy +dcl_output o0.xyzw +sample o0.xyzw, v1.xyxx, t0.xyzw, s0 +ret +// Approximately 2 instruction slots used +#endif + +const BYTE g_PS_2D[] = +{ + 68, 88, 66, 67, 45, 73, + 251, 77, 247, 44, 253, 34, + 100, 41, 211, 74, 100, 236, + 72, 69, 1, 0, 0, 0, + 80, 2, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 216, 0, 0, 0, 48, 1, + 0, 0, 100, 1, 0, 0, + 212, 1, 0, 0, 82, 68, + 69, 70, 156, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 28, 0, 0, 0, 1, 4, + 255, 255, 0, 1, 0, 0, + 107, 0, 0, 0, 92, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 102, 0, 0, 0, 2, 0, + 0, 0, 5, 0, 0, 0, + 4, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 1, 0, 0, 0, 13, 0, + 0, 0, 115, 97, 109, 76, + 105, 110, 101, 97, 114, 0, + 116, 120, 50, 68, 0, 77, + 105, 99, 114, 111, 115, 111, + 102, 116, 32, 40, 82, 41, + 32, 72, 76, 83, 76, 32, + 83, 104, 97, 100, 101, 114, + 32, 67, 111, 109, 112, 105, + 108, 101, 114, 32, 57, 46, + 50, 57, 46, 57, 53, 50, + 46, 51, 49, 49, 49, 0, + 73, 83, 71, 78, 80, 0, + 0, 0, 2, 0, 0, 0, + 8, 0, 0, 0, 56, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 68, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 0, + 15, 3, 0, 0, 83, 86, + 95, 80, 79, 83, 73, 84, + 73, 79, 78, 0, 84, 69, + 88, 67, 79, 79, 82, 68, + 0, 171, 171, 171, 79, 83, + 71, 78, 44, 0, 0, 0, + 1, 0, 0, 0, 8, 0, + 0, 0, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 83, 86, 95, 84, + 97, 114, 103, 101, 116, 0, + 171, 171, 83, 72, 68, 82, + 104, 0, 0, 0, 65, 0, + 0, 0, 26, 0, 0, 0, + 106, 8, 0, 1, 90, 0, + 0, 3, 0, 96, 16, 0, + 0, 0, 0, 0, 88, 24, + 0, 4, 0, 112, 16, 0, + 0, 0, 0, 0, 85, 85, + 0, 0, 98, 16, 0, 3, + 50, 16, 16, 0, 1, 0, + 0, 0, 101, 0, 0, 3, + 242, 32, 16, 0, 0, 0, + 0, 0, 69, 0, 0, 9, + 242, 32, 16, 0, 0, 0, + 0, 0, 70, 16, 16, 0, + 1, 0, 0, 0, 70, 126, + 16, 0, 0, 0, 0, 0, + 0, 96, 16, 0, 0, 0, + 0, 0, 62, 0, 0, 1, + 83, 84, 65, 84, 116, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0 +}; diff --git a/deps/DirectXTex/DDSView/shaders/ps2Darray.h b/deps/DirectXTex/DDSView/shaders/ps2Darray.h new file mode 100644 index 0000000..2104ee3 --- /dev/null +++ b/deps/DirectXTex/DDSView/shaders/ps2Darray.h @@ -0,0 +1,192 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 9.29.952.3111 +// +// +// fxc ddsview.fx /nologo /EPS_2DArray /Tps_4_1 /Fhshaders\ps2Darray.h +// +// +// Buffer Definitions: +// +// cbuffer cbArrayControl +// { +// +// float Index; // Offset: 0 Size: 4 +// +// } +// +// +// Resource Bindings: +// +// Name Type Format Dim Slot Elements +// ------------------------------ ---------- ------- ----------- ---- -------- +// samLinear sampler NA NA 0 1 +// tx2DArray texture float4 2darray 0 1 +// cbArrayControl cbuffer NA NA 0 1 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_POSITION 0 xyzw 0 POS float +// TEXCOORD 0 xyzw 1 NONE float xy +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_Target 0 xyzw 0 TARGET float xyzw +// +ps_4_1 +dcl_globalFlags refactoringAllowed +dcl_constantbuffer cb0[1], immediateIndexed +dcl_sampler s0, mode_default +dcl_resource_texture2darray (float,float,float,float) t0 +dcl_input_ps linear v1.xy +dcl_output o0.xyzw +dcl_temps 1 +mov r0.xy, v1.xyxx +mov r0.z, cb0[0].x +sample o0.xyzw, r0.xyzx, t0.xyzw, s0 +ret +// Approximately 4 instruction slots used +#endif + +const BYTE g_PS_2DArray[] = +{ + 68, 88, 66, 67, 55, 138, + 65, 43, 181, 212, 29, 116, + 142, 112, 89, 51, 193, 95, + 148, 33, 1, 0, 0, 0, + 20, 3, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 88, 1, 0, 0, 176, 1, + 0, 0, 228, 1, 0, 0, + 152, 2, 0, 0, 82, 68, + 69, 70, 28, 1, 0, 0, + 1, 0, 0, 0, 160, 0, + 0, 0, 3, 0, 0, 0, + 28, 0, 0, 0, 1, 4, + 255, 255, 0, 1, 0, 0, + 232, 0, 0, 0, 124, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 134, 0, 0, 0, 2, 0, + 0, 0, 5, 0, 0, 0, + 5, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 1, 0, 0, 0, 13, 0, + 0, 0, 144, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 115, 97, + 109, 76, 105, 110, 101, 97, + 114, 0, 116, 120, 50, 68, + 65, 114, 114, 97, 121, 0, + 99, 98, 65, 114, 114, 97, + 121, 67, 111, 110, 116, 114, + 111, 108, 0, 171, 144, 0, + 0, 0, 1, 0, 0, 0, + 184, 0, 0, 0, 16, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 208, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 2, 0, + 0, 0, 216, 0, 0, 0, + 0, 0, 0, 0, 73, 110, + 100, 101, 120, 0, 171, 171, + 0, 0, 3, 0, 1, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 77, 105, + 99, 114, 111, 115, 111, 102, + 116, 32, 40, 82, 41, 32, + 72, 76, 83, 76, 32, 83, + 104, 97, 100, 101, 114, 32, + 67, 111, 109, 112, 105, 108, + 101, 114, 32, 57, 46, 50, + 57, 46, 57, 53, 50, 46, + 51, 49, 49, 49, 0, 171, + 171, 171, 73, 83, 71, 78, + 80, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 56, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 68, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 0, 15, 3, 0, 0, + 83, 86, 95, 80, 79, 83, + 73, 84, 73, 79, 78, 0, + 84, 69, 88, 67, 79, 79, + 82, 68, 0, 171, 171, 171, + 79, 83, 71, 78, 44, 0, + 0, 0, 1, 0, 0, 0, + 8, 0, 0, 0, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 83, 86, + 95, 84, 97, 114, 103, 101, + 116, 0, 171, 171, 83, 72, + 68, 82, 172, 0, 0, 0, + 65, 0, 0, 0, 43, 0, + 0, 0, 106, 8, 0, 1, + 89, 0, 0, 4, 70, 142, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 90, 0, + 0, 3, 0, 96, 16, 0, + 0, 0, 0, 0, 88, 64, + 0, 4, 0, 112, 16, 0, + 0, 0, 0, 0, 85, 85, + 0, 0, 98, 16, 0, 3, + 50, 16, 16, 0, 1, 0, + 0, 0, 101, 0, 0, 3, + 242, 32, 16, 0, 0, 0, + 0, 0, 104, 0, 0, 2, + 1, 0, 0, 0, 54, 0, + 0, 5, 50, 0, 16, 0, + 0, 0, 0, 0, 70, 16, + 16, 0, 1, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 69, 0, 0, 9, 242, 32, + 16, 0, 0, 0, 0, 0, + 70, 2, 16, 0, 0, 0, + 0, 0, 70, 126, 16, 0, + 0, 0, 0, 0, 0, 96, + 16, 0, 0, 0, 0, 0, + 62, 0, 0, 1, 83, 84, + 65, 84, 116, 0, 0, 0, + 4, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0 +}; diff --git a/deps/DirectXTex/DDSView/shaders/ps3D.h b/deps/DirectXTex/DDSView/shaders/ps3D.h new file mode 100644 index 0000000..6e6f192 --- /dev/null +++ b/deps/DirectXTex/DDSView/shaders/ps3D.h @@ -0,0 +1,198 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 9.29.952.3111 +// +// +// fxc ddsview.fx /nologo /EPS_3D /Tps_4_1 /Fhshaders\ps3D.h +// +// +// Buffer Definitions: +// +// cbuffer cbArrayControl +// { +// +// float Index; // Offset: 0 Size: 4 +// +// } +// +// +// Resource Bindings: +// +// Name Type Format Dim Slot Elements +// ------------------------------ ---------- ------- ----------- ---- -------- +// samLinear sampler NA NA 0 1 +// tx3D texture float4 3d 0 1 +// cbArrayControl cbuffer NA NA 0 1 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_POSITION 0 xyzw 0 POS float +// TEXCOORD 0 xyzw 1 NONE float xy +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_Target 0 xyzw 0 TARGET float xyzw +// +ps_4_1 +dcl_globalFlags refactoringAllowed +dcl_constantbuffer cb0[1], immediateIndexed +dcl_sampler s0, mode_default +dcl_resource_texture3d (float,float,float,float) t0 +dcl_input_ps linear v1.xy +dcl_output o0.xyzw +dcl_temps 1 +resinfo r0.x, l(0), t0.zxyw +div r0.z, cb0[0].x, r0.x +mov r0.xy, v1.xyxx +sample o0.xyzw, r0.xyzx, t0.xyzw, s0 +ret +// Approximately 5 instruction slots used +#endif + +const BYTE g_PS_3D[] = +{ + 68, 88, 66, 67, 119, 18, + 113, 52, 66, 105, 65, 45, + 139, 58, 175, 102, 69, 213, + 121, 186, 1, 0, 0, 0, + 52, 3, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 84, 1, 0, 0, 172, 1, + 0, 0, 224, 1, 0, 0, + 184, 2, 0, 0, 82, 68, + 69, 70, 24, 1, 0, 0, + 1, 0, 0, 0, 156, 0, + 0, 0, 3, 0, 0, 0, + 28, 0, 0, 0, 1, 4, + 255, 255, 0, 1, 0, 0, + 228, 0, 0, 0, 124, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 134, 0, 0, 0, 2, 0, + 0, 0, 5, 0, 0, 0, + 8, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 1, 0, 0, 0, 13, 0, + 0, 0, 139, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 115, 97, + 109, 76, 105, 110, 101, 97, + 114, 0, 116, 120, 51, 68, + 0, 99, 98, 65, 114, 114, + 97, 121, 67, 111, 110, 116, + 114, 111, 108, 0, 171, 171, + 139, 0, 0, 0, 1, 0, + 0, 0, 180, 0, 0, 0, + 16, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 204, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 2, 0, 0, 0, 212, 0, + 0, 0, 0, 0, 0, 0, + 73, 110, 100, 101, 120, 0, + 171, 171, 0, 0, 3, 0, + 1, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 77, 105, 99, 114, 111, 115, + 111, 102, 116, 32, 40, 82, + 41, 32, 72, 76, 83, 76, + 32, 83, 104, 97, 100, 101, + 114, 32, 67, 111, 109, 112, + 105, 108, 101, 114, 32, 57, + 46, 50, 57, 46, 57, 53, + 50, 46, 51, 49, 49, 49, + 0, 171, 171, 171, 73, 83, + 71, 78, 80, 0, 0, 0, + 2, 0, 0, 0, 8, 0, + 0, 0, 56, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 68, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 0, 15, 3, + 0, 0, 83, 86, 95, 80, + 79, 83, 73, 84, 73, 79, + 78, 0, 84, 69, 88, 67, + 79, 79, 82, 68, 0, 171, + 171, 171, 79, 83, 71, 78, + 44, 0, 0, 0, 1, 0, + 0, 0, 8, 0, 0, 0, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 83, 86, 95, 84, 97, 114, + 103, 101, 116, 0, 171, 171, + 83, 72, 68, 82, 208, 0, + 0, 0, 65, 0, 0, 0, + 52, 0, 0, 0, 106, 8, + 0, 1, 89, 0, 0, 4, + 70, 142, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 90, 0, 0, 3, 0, 96, + 16, 0, 0, 0, 0, 0, + 88, 40, 0, 4, 0, 112, + 16, 0, 0, 0, 0, 0, + 85, 85, 0, 0, 98, 16, + 0, 3, 50, 16, 16, 0, + 1, 0, 0, 0, 101, 0, + 0, 3, 242, 32, 16, 0, + 0, 0, 0, 0, 104, 0, + 0, 2, 1, 0, 0, 0, + 61, 0, 0, 7, 18, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 38, 125, 16, 0, + 0, 0, 0, 0, 14, 0, + 0, 8, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 128, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 50, 0, + 16, 0, 0, 0, 0, 0, + 70, 16, 16, 0, 1, 0, + 0, 0, 69, 0, 0, 9, + 242, 32, 16, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 0, 0, 0, 0, 70, 126, + 16, 0, 0, 0, 0, 0, + 0, 96, 16, 0, 0, 0, + 0, 0, 62, 0, 0, 1, + 83, 84, 65, 84, 116, 0, + 0, 0, 5, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0 +}; diff --git a/deps/DirectXTex/DDSView/shaders/psCube.h b/deps/DirectXTex/DDSView/shaders/psCube.h new file mode 100644 index 0000000..6cfe845 --- /dev/null +++ b/deps/DirectXTex/DDSView/shaders/psCube.h @@ -0,0 +1,194 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 9.29.952.3111 +// +// +// fxc ddsview.fx /nologo /EPS_Cube /Tps_4_1 /Fhshaders\psCube.h +// +// +// Buffer Definitions: +// +// cbuffer cbArrayControl +// { +// +// float Index; // Offset: 0 Size: 4 +// +// } +// +// +// Resource Bindings: +// +// Name Type Format Dim Slot Elements +// ------------------------------ ---------- ------- ----------- ---- -------- +// samLinear sampler NA NA 0 1 +// tx2DArray texture float4 2darray 0 1 +// cbArrayControl cbuffer NA NA 0 1 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_POSITION 0 xyzw 0 POS float +// TEXCOORD 0 xyzw 1 NONE float xyz +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_Target 0 xyzw 0 TARGET float xyzw +// +ps_4_1 +dcl_globalFlags refactoringAllowed +dcl_constantbuffer cb0[1], immediateIndexed +dcl_sampler s0, mode_default +dcl_resource_texture2darray (float,float,float,float) t0 +dcl_input_ps linear v1.xyz +dcl_output o0.xyzw +dcl_temps 1 +mad r0.z, cb0[0].x, l(6.000000), v1.z +mov r0.xy, v1.xyxx +sample o0.xyzw, r0.xyzx, t0.xyzw, s0 +ret +// Approximately 4 instruction slots used +#endif + +const BYTE g_PS_Cube[] = +{ + 68, 88, 66, 67, 255, 88, + 222, 202, 51, 233, 113, 192, + 119, 52, 43, 119, 92, 83, + 243, 127, 1, 0, 0, 0, + 36, 3, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 88, 1, 0, 0, 176, 1, + 0, 0, 228, 1, 0, 0, + 168, 2, 0, 0, 82, 68, + 69, 70, 28, 1, 0, 0, + 1, 0, 0, 0, 160, 0, + 0, 0, 3, 0, 0, 0, + 28, 0, 0, 0, 1, 4, + 255, 255, 0, 1, 0, 0, + 232, 0, 0, 0, 124, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 134, 0, 0, 0, 2, 0, + 0, 0, 5, 0, 0, 0, + 5, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 1, 0, 0, 0, 13, 0, + 0, 0, 144, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 115, 97, + 109, 76, 105, 110, 101, 97, + 114, 0, 116, 120, 50, 68, + 65, 114, 114, 97, 121, 0, + 99, 98, 65, 114, 114, 97, + 121, 67, 111, 110, 116, 114, + 111, 108, 0, 171, 144, 0, + 0, 0, 1, 0, 0, 0, + 184, 0, 0, 0, 16, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 208, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 2, 0, + 0, 0, 216, 0, 0, 0, + 0, 0, 0, 0, 73, 110, + 100, 101, 120, 0, 171, 171, + 0, 0, 3, 0, 1, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 77, 105, + 99, 114, 111, 115, 111, 102, + 116, 32, 40, 82, 41, 32, + 72, 76, 83, 76, 32, 83, + 104, 97, 100, 101, 114, 32, + 67, 111, 109, 112, 105, 108, + 101, 114, 32, 57, 46, 50, + 57, 46, 57, 53, 50, 46, + 51, 49, 49, 49, 0, 171, + 171, 171, 73, 83, 71, 78, + 80, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 56, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 68, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 0, 15, 7, 0, 0, + 83, 86, 95, 80, 79, 83, + 73, 84, 73, 79, 78, 0, + 84, 69, 88, 67, 79, 79, + 82, 68, 0, 171, 171, 171, + 79, 83, 71, 78, 44, 0, + 0, 0, 1, 0, 0, 0, + 8, 0, 0, 0, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 83, 86, + 95, 84, 97, 114, 103, 101, + 116, 0, 171, 171, 83, 72, + 68, 82, 188, 0, 0, 0, + 65, 0, 0, 0, 47, 0, + 0, 0, 106, 8, 0, 1, + 89, 0, 0, 4, 70, 142, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 90, 0, + 0, 3, 0, 96, 16, 0, + 0, 0, 0, 0, 88, 64, + 0, 4, 0, 112, 16, 0, + 0, 0, 0, 0, 85, 85, + 0, 0, 98, 16, 0, 3, + 114, 16, 16, 0, 1, 0, + 0, 0, 101, 0, 0, 3, + 242, 32, 16, 0, 0, 0, + 0, 0, 104, 0, 0, 2, + 1, 0, 0, 0, 50, 0, + 0, 10, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 128, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 192, 64, + 42, 16, 16, 0, 1, 0, + 0, 0, 54, 0, 0, 5, + 50, 0, 16, 0, 0, 0, + 0, 0, 70, 16, 16, 0, + 1, 0, 0, 0, 69, 0, + 0, 9, 242, 32, 16, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 0, 0, 0, 0, + 70, 126, 16, 0, 0, 0, + 0, 0, 0, 96, 16, 0, + 0, 0, 0, 0, 62, 0, + 0, 1, 83, 84, 65, 84, + 116, 0, 0, 0, 4, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0 +}; diff --git a/deps/DirectXTex/DDSView/shaders/vs.h b/deps/DirectXTex/DDSView/shaders/vs.h new file mode 100644 index 0000000..0277eae --- /dev/null +++ b/deps/DirectXTex/DDSView/shaders/vs.h @@ -0,0 +1,131 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 9.29.952.3111 +// +// +// fxc ddsview.fx /nologo /EVS /Tvs_4_1 /Fhshaders\vs.h +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// POSITION 0 xyzw 0 NONE float xyzw +// TEXCOORD 0 xyzw 1 NONE float xyzw +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------ ------ +// SV_POSITION 0 xyzw 0 POS float xyzw +// TEXCOORD 0 xyzw 1 NONE float xyzw +// +vs_4_1 +dcl_globalFlags refactoringAllowed +dcl_input v0.xyzw +dcl_input v1.xyzw +dcl_output_siv o0.xyzw, position +dcl_output o1.xyzw +mov o0.xyzw, v0.xyzw +mov o1.xyzw, v1.xyzw +ret +// Approximately 3 instruction slots used +#endif + +const BYTE g_VS[] = +{ + 68, 88, 66, 67, 243, 4, + 207, 4, 72, 185, 125, 253, + 86, 236, 11, 103, 199, 128, + 83, 243, 1, 0, 0, 0, + 40, 2, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 140, 0, 0, 0, 224, 0, + 0, 0, 56, 1, 0, 0, + 172, 1, 0, 0, 82, 68, + 69, 70, 80, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 28, 0, 0, 0, 1, 4, + 254, 255, 0, 1, 0, 0, + 28, 0, 0, 0, 77, 105, + 99, 114, 111, 115, 111, 102, + 116, 32, 40, 82, 41, 32, + 72, 76, 83, 76, 32, 83, + 104, 97, 100, 101, 114, 32, + 67, 111, 109, 112, 105, 108, + 101, 114, 32, 57, 46, 50, + 57, 46, 57, 53, 50, 46, + 51, 49, 49, 49, 0, 171, + 171, 171, 73, 83, 71, 78, + 76, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 56, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 15, 0, 0, + 65, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 0, 15, 15, 0, 0, + 80, 79, 83, 73, 84, 73, + 79, 78, 0, 84, 69, 88, + 67, 79, 79, 82, 68, 0, + 171, 171, 79, 83, 71, 78, + 80, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 56, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 68, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 0, 15, 0, 0, 0, + 83, 86, 95, 80, 79, 83, + 73, 84, 73, 79, 78, 0, + 84, 69, 88, 67, 79, 79, + 82, 68, 0, 171, 171, 171, + 83, 72, 68, 82, 108, 0, + 0, 0, 65, 0, 1, 0, + 27, 0, 0, 0, 106, 8, + 0, 1, 95, 0, 0, 3, + 242, 16, 16, 0, 0, 0, + 0, 0, 95, 0, 0, 3, + 242, 16, 16, 0, 1, 0, + 0, 0, 103, 0, 0, 4, + 242, 32, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 101, 0, 0, 3, 242, 32, + 16, 0, 1, 0, 0, 0, + 54, 0, 0, 5, 242, 32, + 16, 0, 0, 0, 0, 0, + 70, 30, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 242, 32, 16, 0, 1, 0, + 0, 0, 70, 30, 16, 0, + 1, 0, 0, 0, 62, 0, + 0, 1, 83, 84, 65, 84, + 116, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0 +}; diff --git a/deps/DirectXTex/DirectXTex/BC.cpp b/deps/DirectXTex/DirectXTex/BC.cpp new file mode 100644 index 0000000..a342f2a --- /dev/null +++ b/deps/DirectXTex/DirectXTex/BC.cpp @@ -0,0 +1,1148 @@ +//------------------------------------------------------------------------------------- +// BC.cpp +// +// Block-compression (BC) functionality for BC1, BC2, BC3 (orginal DXTn formats) +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +// Experiemental encoding variants, not enabled by default +//#define COLOR_WEIGHTS +//#define COLOR_AVG_0WEIGHTS + +#include "BC.h" + +using namespace DirectX; +using namespace DirectX::PackedVector; + +namespace +{ + //------------------------------------------------------------------------------------- + // Constants + //------------------------------------------------------------------------------------- + + // Perceptual weightings for the importance of each channel. + const HDRColorA g_Luminance(0.2125f / 0.7154f, 1.0f, 0.0721f / 0.7154f, 1.0f); + const HDRColorA g_LuminanceInv(0.7154f / 0.2125f, 1.0f, 0.7154f / 0.0721f, 1.0f); + + //------------------------------------------------------------------------------------- + // Decode/Encode RGB 5/6/5 colors + //------------------------------------------------------------------------------------- + inline void Decode565(_Out_ HDRColorA *pColor, _In_ const uint16_t w565) + { + pColor->r = (float)((w565 >> 11) & 31) * (1.0f / 31.0f); + pColor->g = (float)((w565 >> 5) & 63) * (1.0f / 63.0f); + pColor->b = (float)((w565 >> 0) & 31) * (1.0f / 31.0f); + pColor->a = 1.0f; + } + + inline uint16_t Encode565(_In_ const HDRColorA *pColor) + { + HDRColorA Color; + + Color.r = (pColor->r < 0.0f) ? 0.0f : (pColor->r > 1.0f) ? 1.0f : pColor->r; + Color.g = (pColor->g < 0.0f) ? 0.0f : (pColor->g > 1.0f) ? 1.0f : pColor->g; + Color.b = (pColor->b < 0.0f) ? 0.0f : (pColor->b > 1.0f) ? 1.0f : pColor->b; + + uint16_t w; + + w = (uint16_t)((static_cast(Color.r * 31.0f + 0.5f) << 11) | + (static_cast(Color.g * 63.0f + 0.5f) << 5) | + (static_cast(Color.b * 31.0f + 0.5f) << 0)); + + return w; + } + + + //------------------------------------------------------------------------------------- + void OptimizeRGB( + _Out_ HDRColorA *pX, + _Out_ HDRColorA *pY, + _In_reads_(NUM_PIXELS_PER_BLOCK) const HDRColorA *pPoints, + size_t cSteps, + DWORD flags) + { + static const float fEpsilon = (0.25f / 64.0f) * (0.25f / 64.0f); + static const float pC3[] = { 2.0f / 2.0f, 1.0f / 2.0f, 0.0f / 2.0f }; + static const float pD3[] = { 0.0f / 2.0f, 1.0f / 2.0f, 2.0f / 2.0f }; + static const float pC4[] = { 3.0f / 3.0f, 2.0f / 3.0f, 1.0f / 3.0f, 0.0f / 3.0f }; + static const float pD4[] = { 0.0f / 3.0f, 1.0f / 3.0f, 2.0f / 3.0f, 3.0f / 3.0f }; + + const float *pC = (3 == cSteps) ? pC3 : pC4; + const float *pD = (3 == cSteps) ? pD3 : pD4; + + // Find Min and Max points, as starting point + HDRColorA X = (flags & BC_FLAGS_UNIFORM) ? HDRColorA(1.f, 1.f, 1.f, 1.f) : g_Luminance; + HDRColorA Y = HDRColorA(0.0f, 0.0f, 0.0f, 1.0f); + + for (size_t iPoint = 0; iPoint < NUM_PIXELS_PER_BLOCK; iPoint++) + { +#ifdef COLOR_WEIGHTS + if (pPoints[iPoint].a > 0.0f) +#endif // COLOR_WEIGHTS + { + if (pPoints[iPoint].r < X.r) + X.r = pPoints[iPoint].r; + + if (pPoints[iPoint].g < X.g) + X.g = pPoints[iPoint].g; + + if (pPoints[iPoint].b < X.b) + X.b = pPoints[iPoint].b; + + if (pPoints[iPoint].r > Y.r) + Y.r = pPoints[iPoint].r; + + if (pPoints[iPoint].g > Y.g) + Y.g = pPoints[iPoint].g; + + if (pPoints[iPoint].b > Y.b) + Y.b = pPoints[iPoint].b; + } + } + + // Diagonal axis + HDRColorA AB; + + AB.r = Y.r - X.r; + AB.g = Y.g - X.g; + AB.b = Y.b - X.b; + + float fAB = AB.r * AB.r + AB.g * AB.g + AB.b * AB.b; + + // Single color block.. no need to root-find + if (fAB < FLT_MIN) + { + pX->r = X.r; pX->g = X.g; pX->b = X.b; + pY->r = Y.r; pY->g = Y.g; pY->b = Y.b; + return; + } + + // Try all four axis directions, to determine which diagonal best fits data + float fABInv = 1.0f / fAB; + + HDRColorA Dir; + Dir.r = AB.r * fABInv; + Dir.g = AB.g * fABInv; + Dir.b = AB.b * fABInv; + + HDRColorA Mid; + Mid.r = (X.r + Y.r) * 0.5f; + Mid.g = (X.g + Y.g) * 0.5f; + Mid.b = (X.b + Y.b) * 0.5f; + + float fDir[4]; + fDir[0] = fDir[1] = fDir[2] = fDir[3] = 0.0f; + + + for (size_t iPoint = 0; iPoint < NUM_PIXELS_PER_BLOCK; iPoint++) + { + HDRColorA Pt; + Pt.r = (pPoints[iPoint].r - Mid.r) * Dir.r; + Pt.g = (pPoints[iPoint].g - Mid.g) * Dir.g; + Pt.b = (pPoints[iPoint].b - Mid.b) * Dir.b; + + float f; + +#ifdef COLOR_WEIGHTS + f = Pt.r + Pt.g + Pt.b; + fDir[0] += pPoints[iPoint].a * f * f; + + f = Pt.r + Pt.g - Pt.b; + fDir[1] += pPoints[iPoint].a * f * f; + + f = Pt.r - Pt.g + Pt.b; + fDir[2] += pPoints[iPoint].a * f * f; + + f = Pt.r - Pt.g - Pt.b; + fDir[3] += pPoints[iPoint].a * f * f; +#else + f = Pt.r + Pt.g + Pt.b; + fDir[0] += f * f; + + f = Pt.r + Pt.g - Pt.b; + fDir[1] += f * f; + + f = Pt.r - Pt.g + Pt.b; + fDir[2] += f * f; + + f = Pt.r - Pt.g - Pt.b; + fDir[3] += f * f; +#endif // COLOR_WEIGHTS + } + + float fDirMax = fDir[0]; + size_t iDirMax = 0; + + for (size_t iDir = 1; iDir < 4; iDir++) + { + if (fDir[iDir] > fDirMax) + { + fDirMax = fDir[iDir]; + iDirMax = iDir; + } + } + + if (iDirMax & 2) + { + float f = X.g; X.g = Y.g; Y.g = f; + } + + if (iDirMax & 1) + { + float f = X.b; X.b = Y.b; Y.b = f; + } + + + // Two color block.. no need to root-find + if (fAB < 1.0f / 4096.0f) + { + pX->r = X.r; pX->g = X.g; pX->b = X.b; + pY->r = Y.r; pY->g = Y.g; pY->b = Y.b; + return; + } + + // Use Newton's Method to find local minima of sum-of-squares error. + float fSteps = (float)(cSteps - 1); + + for (size_t iIteration = 0; iIteration < 8; iIteration++) + { + // Calculate new steps + HDRColorA pSteps[4]; + + for (size_t iStep = 0; iStep < cSteps; iStep++) + { + pSteps[iStep].r = X.r * pC[iStep] + Y.r * pD[iStep]; + pSteps[iStep].g = X.g * pC[iStep] + Y.g * pD[iStep]; + pSteps[iStep].b = X.b * pC[iStep] + Y.b * pD[iStep]; + } + + + // Calculate color direction + Dir.r = Y.r - X.r; + Dir.g = Y.g - X.g; + Dir.b = Y.b - X.b; + + float fLen = (Dir.r * Dir.r + Dir.g * Dir.g + Dir.b * Dir.b); + + if (fLen < (1.0f / 4096.0f)) + break; + + float fScale = fSteps / fLen; + + Dir.r *= fScale; + Dir.g *= fScale; + Dir.b *= fScale; + + + // Evaluate function, and derivatives + float d2X, d2Y; + HDRColorA dX, dY; + d2X = d2Y = dX.r = dX.g = dX.b = dY.r = dY.g = dY.b = 0.0f; + + for (size_t iPoint = 0; iPoint < NUM_PIXELS_PER_BLOCK; iPoint++) + { + float fDot = (pPoints[iPoint].r - X.r) * Dir.r + + (pPoints[iPoint].g - X.g) * Dir.g + + (pPoints[iPoint].b - X.b) * Dir.b; + + + size_t iStep; + if (fDot <= 0.0f) + iStep = 0; + else if (fDot >= fSteps) + iStep = cSteps - 1; + else + iStep = static_cast(fDot + 0.5f); + + + HDRColorA Diff; + Diff.r = pSteps[iStep].r - pPoints[iPoint].r; + Diff.g = pSteps[iStep].g - pPoints[iPoint].g; + Diff.b = pSteps[iStep].b - pPoints[iPoint].b; + +#ifdef COLOR_WEIGHTS + float fC = pC[iStep] * pPoints[iPoint].a * (1.0f / 8.0f); + float fD = pD[iStep] * pPoints[iPoint].a * (1.0f / 8.0f); +#else + float fC = pC[iStep] * (1.0f / 8.0f); + float fD = pD[iStep] * (1.0f / 8.0f); +#endif // COLOR_WEIGHTS + + d2X += fC * pC[iStep]; + dX.r += fC * Diff.r; + dX.g += fC * Diff.g; + dX.b += fC * Diff.b; + + d2Y += fD * pD[iStep]; + dY.r += fD * Diff.r; + dY.g += fD * Diff.g; + dY.b += fD * Diff.b; + } + + // Move endpoints + if (d2X > 0.0f) + { + float f = -1.0f / d2X; + + X.r += dX.r * f; + X.g += dX.g * f; + X.b += dX.b * f; + } + + if (d2Y > 0.0f) + { + float f = -1.0f / d2Y; + + Y.r += dY.r * f; + Y.g += dY.g * f; + Y.b += dY.b * f; + } + + if ((dX.r * dX.r < fEpsilon) && (dX.g * dX.g < fEpsilon) && (dX.b * dX.b < fEpsilon) && + (dY.r * dY.r < fEpsilon) && (dY.g * dY.g < fEpsilon) && (dY.b * dY.b < fEpsilon)) + { + break; + } + } + + pX->r = X.r; pX->g = X.g; pX->b = X.b; + pY->r = Y.r; pY->g = Y.g; pY->b = Y.b; + } + + + //------------------------------------------------------------------------------------- + inline void DecodeBC1( + _Out_writes_(NUM_PIXELS_PER_BLOCK) XMVECTOR *pColor, + _In_ const D3DX_BC1 *pBC, + bool isbc1) + { + assert(pColor && pBC); + static_assert(sizeof(D3DX_BC1) == 8, "D3DX_BC1 should be 8 bytes"); + + static XMVECTORF32 s_Scale = { { { 1.f / 31.f, 1.f / 63.f, 1.f / 31.f, 1.f } } }; + + XMVECTOR clr0 = XMLoadU565(reinterpret_cast(&pBC->rgb[0])); + XMVECTOR clr1 = XMLoadU565(reinterpret_cast(&pBC->rgb[1])); + + clr0 = XMVectorMultiply(clr0, s_Scale); + clr1 = XMVectorMultiply(clr1, s_Scale); + + clr0 = XMVectorSwizzle<2, 1, 0, 3>(clr0); + clr1 = XMVectorSwizzle<2, 1, 0, 3>(clr1); + + clr0 = XMVectorSelect(g_XMIdentityR3, clr0, g_XMSelect1110); + clr1 = XMVectorSelect(g_XMIdentityR3, clr1, g_XMSelect1110); + + XMVECTOR clr2, clr3; + if (isbc1 && (pBC->rgb[0] <= pBC->rgb[1])) + { + clr2 = XMVectorLerp(clr0, clr1, 0.5f); + clr3 = XMVectorZero(); // Alpha of 0 + } + else + { + clr2 = XMVectorLerp(clr0, clr1, 1.f / 3.f); + clr3 = XMVectorLerp(clr0, clr1, 2.f / 3.f); + } + + uint32_t dw = pBC->bitmap; + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i, dw >>= 2) + { + switch (dw & 3) + { + case 0: pColor[i] = clr0; break; + case 1: pColor[i] = clr1; break; + case 2: pColor[i] = clr2; break; + + case 3: + default: pColor[i] = clr3; break; + } + } + } + + + //------------------------------------------------------------------------------------- + void EncodeBC1( + _Out_ D3DX_BC1 *pBC, + _In_reads_(NUM_PIXELS_PER_BLOCK) const HDRColorA *pColor, + bool bColorKey, + float threshold, + DWORD flags) + { + assert(pBC && pColor); + static_assert(sizeof(D3DX_BC1) == 8, "D3DX_BC1 should be 8 bytes"); + + // Determine if we need to colorkey this block + size_t uSteps; + + if (bColorKey) + { + size_t uColorKey = 0; + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + if (pColor[i].a < threshold) + uColorKey++; + } + + if (NUM_PIXELS_PER_BLOCK == uColorKey) + { + pBC->rgb[0] = 0x0000; + pBC->rgb[1] = 0xffff; + pBC->bitmap = 0xffffffff; + return; + } + + uSteps = (uColorKey > 0) ? 3 : 4; + } + else + { + uSteps = 4; + } + + // Quantize block to R56B5, using Floyd Stienberg error diffusion. This + // increases the chance that colors will map directly to the quantized + // axis endpoints. + HDRColorA Color[NUM_PIXELS_PER_BLOCK]; + HDRColorA Error[NUM_PIXELS_PER_BLOCK]; + + if (flags & BC_FLAGS_DITHER_RGB) + memset(Error, 0x00, NUM_PIXELS_PER_BLOCK * sizeof(HDRColorA)); + + size_t i; + for (i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + HDRColorA Clr; + Clr.r = pColor[i].r; + Clr.g = pColor[i].g; + Clr.b = pColor[i].b; + + if (flags & BC_FLAGS_DITHER_RGB) + { + Clr.r += Error[i].r; + Clr.g += Error[i].g; + Clr.b += Error[i].b; + } + + Color[i].r = (float) static_cast(Clr.r * 31.0f + 0.5f) * (1.0f / 31.0f); + Color[i].g = (float) static_cast(Clr.g * 63.0f + 0.5f) * (1.0f / 63.0f); + Color[i].b = (float) static_cast(Clr.b * 31.0f + 0.5f) * (1.0f / 31.0f); + +#ifdef COLOR_WEIGHTS + Color[i].a = pColor[i].a; +#else + Color[i].a = 1.0f; +#endif // COLOR_WEIGHTS + + if (flags & BC_FLAGS_DITHER_RGB) + { + HDRColorA Diff; + Diff.r = Color[i].a * (Clr.r - Color[i].r); + Diff.g = Color[i].a * (Clr.g - Color[i].g); + Diff.b = Color[i].a * (Clr.b - Color[i].b); + + if (3 != (i & 3)) + { + assert(i < 15); + _Analysis_assume_(i < 15); + Error[i + 1].r += Diff.r * (7.0f / 16.0f); + Error[i + 1].g += Diff.g * (7.0f / 16.0f); + Error[i + 1].b += Diff.b * (7.0f / 16.0f); + } + + if (i < 12) + { + if (i & 3) + { + Error[i + 3].r += Diff.r * (3.0f / 16.0f); + Error[i + 3].g += Diff.g * (3.0f / 16.0f); + Error[i + 3].b += Diff.b * (3.0f / 16.0f); + } + + Error[i + 4].r += Diff.r * (5.0f / 16.0f); + Error[i + 4].g += Diff.g * (5.0f / 16.0f); + Error[i + 4].b += Diff.b * (5.0f / 16.0f); + + if (3 != (i & 3)) + { + assert(i < 11); + _Analysis_assume_(i < 11); + Error[i + 5].r += Diff.r * (1.0f / 16.0f); + Error[i + 5].g += Diff.g * (1.0f / 16.0f); + Error[i + 5].b += Diff.b * (1.0f / 16.0f); + } + } + } + + if (!(flags & BC_FLAGS_UNIFORM)) + { + Color[i].r *= g_Luminance.r; + Color[i].g *= g_Luminance.g; + Color[i].b *= g_Luminance.b; + } + } + + // Perform 6D root finding function to find two endpoints of color axis. + // Then quantize and sort the endpoints depending on mode. + HDRColorA ColorA, ColorB, ColorC, ColorD; + + OptimizeRGB(&ColorA, &ColorB, Color, uSteps, flags); + + if (flags & BC_FLAGS_UNIFORM) + { + ColorC = ColorA; + ColorD = ColorB; + } + else + { + ColorC.r = ColorA.r * g_LuminanceInv.r; + ColorC.g = ColorA.g * g_LuminanceInv.g; + ColorC.b = ColorA.b * g_LuminanceInv.b; + + ColorD.r = ColorB.r * g_LuminanceInv.r; + ColorD.g = ColorB.g * g_LuminanceInv.g; + ColorD.b = ColorB.b * g_LuminanceInv.b; + } + + uint16_t wColorA = Encode565(&ColorC); + uint16_t wColorB = Encode565(&ColorD); + + if ((uSteps == 4) && (wColorA == wColorB)) + { + pBC->rgb[0] = wColorA; + pBC->rgb[1] = wColorB; + pBC->bitmap = 0x00000000; + return; + } + + Decode565(&ColorC, wColorA); + Decode565(&ColorD, wColorB); + + if (flags & BC_FLAGS_UNIFORM) + { + ColorA = ColorC; + ColorB = ColorD; + } + else + { + ColorA.r = ColorC.r * g_Luminance.r; + ColorA.g = ColorC.g * g_Luminance.g; + ColorA.b = ColorC.b * g_Luminance.b; + + ColorB.r = ColorD.r * g_Luminance.r; + ColorB.g = ColorD.g * g_Luminance.g; + ColorB.b = ColorD.b * g_Luminance.b; + } + + // Calculate color steps + HDRColorA Step[4]; + + if ((3 == uSteps) == (wColorA <= wColorB)) + { + pBC->rgb[0] = wColorA; + pBC->rgb[1] = wColorB; + + Step[0] = ColorA; + Step[1] = ColorB; + } + else + { + pBC->rgb[0] = wColorB; + pBC->rgb[1] = wColorA; + + Step[0] = ColorB; + Step[1] = ColorA; + } + + static const size_t pSteps3[] = { 0, 2, 1 }; + static const size_t pSteps4[] = { 0, 2, 3, 1 }; + const size_t *pSteps; + + if (3 == uSteps) + { + pSteps = pSteps3; + + HDRColorALerp(&Step[2], &Step[0], &Step[1], 0.5f); + } + else + { + pSteps = pSteps4; + + HDRColorALerp(&Step[2], &Step[0], &Step[1], 1.0f / 3.0f); + HDRColorALerp(&Step[3], &Step[0], &Step[1], 2.0f / 3.0f); + } + + // Calculate color direction + HDRColorA Dir; + + Dir.r = Step[1].r - Step[0].r; + Dir.g = Step[1].g - Step[0].g; + Dir.b = Step[1].b - Step[0].b; + + float fSteps = (float)(uSteps - 1); + float fScale = (wColorA != wColorB) ? (fSteps / (Dir.r * Dir.r + Dir.g * Dir.g + Dir.b * Dir.b)) : 0.0f; + + Dir.r *= fScale; + Dir.g *= fScale; + Dir.b *= fScale; + + // Encode colors + uint32_t dw = 0; + if (flags & BC_FLAGS_DITHER_RGB) + memset(Error, 0x00, NUM_PIXELS_PER_BLOCK * sizeof(HDRColorA)); + + for (i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + if ((3 == uSteps) && (pColor[i].a < threshold)) + { + dw = (3 << 30) | (dw >> 2); + } + else + { + HDRColorA Clr; + if (flags & BC_FLAGS_UNIFORM) + { + Clr.r = pColor[i].r; + Clr.g = pColor[i].g; + Clr.b = pColor[i].b; + } + else + { + Clr.r = pColor[i].r * g_Luminance.r; + Clr.g = pColor[i].g * g_Luminance.g; + Clr.b = pColor[i].b * g_Luminance.b; + } + + if (flags & BC_FLAGS_DITHER_RGB) + { + Clr.r += Error[i].r; + Clr.g += Error[i].g; + Clr.b += Error[i].b; + } + + float fDot = (Clr.r - Step[0].r) * Dir.r + (Clr.g - Step[0].g) * Dir.g + (Clr.b - Step[0].b) * Dir.b; + uint32_t iStep; + + if (fDot <= 0.0f) + iStep = 0; + else if (fDot >= fSteps) + iStep = 1; + else + iStep = static_cast(pSteps[static_cast(fDot + 0.5f)]); + + dw = (iStep << 30) | (dw >> 2); + + if (flags & BC_FLAGS_DITHER_RGB) + { + HDRColorA Diff; + Diff.r = Color[i].a * (Clr.r - Step[iStep].r); + Diff.g = Color[i].a * (Clr.g - Step[iStep].g); + Diff.b = Color[i].a * (Clr.b - Step[iStep].b); + + if (3 != (i & 3)) + { + Error[i + 1].r += Diff.r * (7.0f / 16.0f); + Error[i + 1].g += Diff.g * (7.0f / 16.0f); + Error[i + 1].b += Diff.b * (7.0f / 16.0f); + } + + if (i < 12) + { + if (i & 3) + { + Error[i + 3].r += Diff.r * (3.0f / 16.0f); + Error[i + 3].g += Diff.g * (3.0f / 16.0f); + Error[i + 3].b += Diff.b * (3.0f / 16.0f); + } + + Error[i + 4].r += Diff.r * (5.0f / 16.0f); + Error[i + 4].g += Diff.g * (5.0f / 16.0f); + Error[i + 4].b += Diff.b * (5.0f / 16.0f); + + if (3 != (i & 3)) + { + Error[i + 5].r += Diff.r * (1.0f / 16.0f); + Error[i + 5].g += Diff.g * (1.0f / 16.0f); + Error[i + 5].b += Diff.b * (1.0f / 16.0f); + } + } + } + } + } + + pBC->bitmap = dw; + } + + //------------------------------------------------------------------------------------- +#ifdef COLOR_WEIGHTS + void EncodeSolidBC1(_Out_ D3DX_BC1 *pBC, _In_reads_(NUM_PIXELS_PER_BLOCK) const HDRColorA *pColor) + { +#ifdef COLOR_AVG_0WEIGHTS + // Compute avg color + HDRColorA Color; + Color.r = pColor[0].r; + Color.g = pColor[0].g; + Color.b = pColor[0].b; + + for (size_t i = 1; i < NUM_PIXELS_PER_BLOCK; ++i) + { + Color.r += pColor[i].r; + Color.g += pColor[i].g; + Color.b += pColor[i].b; + } + + Color.r *= 1.0f / 16.0f; + Color.g *= 1.0f / 16.0f; + Color.b *= 1.0f / 16.0f; + + uint16_t wColor = Encode565(&Color); +#else + uint16_t wColor = 0x0000; +#endif // COLOR_AVG_0WEIGHTS + + // Encode solid block + pBC->rgb[0] = wColor; + pBC->rgb[1] = wColor; + pBC->bitmap = 0x00000000; + } +#endif // COLOR_WEIGHTS +} + + +//===================================================================================== +// Entry points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// BC1 Compression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DirectX::D3DXDecodeBC1(XMVECTOR *pColor, const uint8_t *pBC) +{ + auto pBC1 = reinterpret_cast(pBC); + DecodeBC1(pColor, pBC1, true); +} + +_Use_decl_annotations_ +void DirectX::D3DXEncodeBC1(uint8_t *pBC, const XMVECTOR *pColor, float threshold, DWORD flags) +{ + assert(pBC && pColor); + + HDRColorA Color[NUM_PIXELS_PER_BLOCK]; + + if (flags & BC_FLAGS_DITHER_A) + { + float fError[NUM_PIXELS_PER_BLOCK]; + memset(fError, 0x00, NUM_PIXELS_PER_BLOCK * sizeof(float)); + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + HDRColorA clr; + XMStoreFloat4(reinterpret_cast(&clr), pColor[i]); + + float fAlph = clr.a + fError[i]; + + Color[i].r = clr.r; + Color[i].g = clr.g; + Color[i].b = clr.b; + Color[i].a = (float) static_cast(clr.a + fError[i] + 0.5f); + + float fDiff = fAlph - Color[i].a; + + if (3 != (i & 3)) + { + assert(i < 15); + _Analysis_assume_(i < 15); + fError[i + 1] += fDiff * (7.0f / 16.0f); + } + + if (i < 12) + { + if (i & 3) + fError[i + 3] += fDiff * (3.0f / 16.0f); + + fError[i + 4] += fDiff * (5.0f / 16.0f); + + if (3 != (i & 3)) + { + assert(i < 11); + _Analysis_assume_(i < 11); + fError[i + 5] += fDiff * (1.0f / 16.0f); + } + } + } + } + else + { + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + XMStoreFloat4(reinterpret_cast(&Color[i]), pColor[i]); + } + } + + auto pBC1 = reinterpret_cast(pBC); + EncodeBC1(pBC1, Color, true, threshold, flags); +} + + +//------------------------------------------------------------------------------------- +// BC2 Compression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DirectX::D3DXDecodeBC2(XMVECTOR *pColor, const uint8_t *pBC) +{ + assert(pColor && pBC); + static_assert(sizeof(D3DX_BC2) == 16, "D3DX_BC2 should be 16 bytes"); + + auto pBC2 = reinterpret_cast(pBC); + + // RGB part + DecodeBC1(pColor, &pBC2->bc1, false); + + // 4-bit alpha part + DWORD dw = pBC2->bitmap[0]; + + for (size_t i = 0; i < 8; ++i, dw >>= 4) + { +#pragma prefast(suppress:22103, "writing blocks in two halves confuses tool") + pColor[i] = XMVectorSetW(pColor[i], (float)(dw & 0xf) * (1.0f / 15.0f)); + } + + dw = pBC2->bitmap[1]; + + for (size_t i = 8; i < NUM_PIXELS_PER_BLOCK; ++i, dw >>= 4) + pColor[i] = XMVectorSetW(pColor[i], (float)(dw & 0xf) * (1.0f / 15.0f)); +} + +_Use_decl_annotations_ +void DirectX::D3DXEncodeBC2(uint8_t *pBC, const XMVECTOR *pColor, DWORD flags) +{ + assert(pBC && pColor); + static_assert(sizeof(D3DX_BC2) == 16, "D3DX_BC2 should be 16 bytes"); + + HDRColorA Color[NUM_PIXELS_PER_BLOCK]; + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + XMStoreFloat4(reinterpret_cast(&Color[i]), pColor[i]); + } + + auto pBC2 = reinterpret_cast(pBC); + + // 4-bit alpha part. Dithered using Floyd Stienberg error diffusion. + pBC2->bitmap[0] = 0; + pBC2->bitmap[1] = 0; + + float fError[NUM_PIXELS_PER_BLOCK]; + if (flags & BC_FLAGS_DITHER_A) + memset(fError, 0x00, NUM_PIXELS_PER_BLOCK * sizeof(float)); + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + float fAlph = Color[i].a; + if (flags & BC_FLAGS_DITHER_A) + fAlph += fError[i]; + + uint32_t u = (uint32_t) static_cast(fAlph * 15.0f + 0.5f); + + pBC2->bitmap[i >> 3] >>= 4; + pBC2->bitmap[i >> 3] |= (u << 28); + + if (flags & BC_FLAGS_DITHER_A) + { + float fDiff = fAlph - (float)u * (1.0f / 15.0f); + + if (3 != (i & 3)) + { + assert(i < 15); + _Analysis_assume_(i < 15); + fError[i + 1] += fDiff * (7.0f / 16.0f); + } + + if (i < 12) + { + if (i & 3) + fError[i + 3] += fDiff * (3.0f / 16.0f); + + fError[i + 4] += fDiff * (5.0f / 16.0f); + + if (3 != (i & 3)) + { + assert(i < 11); + _Analysis_assume_(i < 11); + fError[i + 5] += fDiff * (1.0f / 16.0f); + } + } + } + } + + // RGB part +#ifdef COLOR_WEIGHTS + if (!pBC2->bitmap[0] && !pBC2->bitmap[1]) + { + EncodeSolidBC1(pBC2->dxt1, Color); + return; + } +#endif // COLOR_WEIGHTS + + EncodeBC1(&pBC2->bc1, Color, false, 0.f, flags); +} + + +//------------------------------------------------------------------------------------- +// BC3 Compression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DirectX::D3DXDecodeBC3(XMVECTOR *pColor, const uint8_t *pBC) +{ + assert(pColor && pBC); + static_assert(sizeof(D3DX_BC3) == 16, "D3DX_BC3 should be 16 bytes"); + + auto pBC3 = reinterpret_cast(pBC); + + // RGB part + DecodeBC1(pColor, &pBC3->bc1, false); + + // Adaptive 3-bit alpha part + float fAlpha[8]; + + fAlpha[0] = ((float)pBC3->alpha[0]) * (1.0f / 255.0f); + fAlpha[1] = ((float)pBC3->alpha[1]) * (1.0f / 255.0f); + + if (pBC3->alpha[0] > pBC3->alpha[1]) + { + for (size_t i = 1; i < 7; ++i) + fAlpha[i + 1] = (fAlpha[0] * (7 - i) + fAlpha[1] * i) * (1.0f / 7.0f); + } + else + { + for (size_t i = 1; i < 5; ++i) + fAlpha[i + 1] = (fAlpha[0] * (5 - i) + fAlpha[1] * i) * (1.0f / 5.0f); + + fAlpha[6] = 0.0f; + fAlpha[7] = 1.0f; + } + + DWORD dw = pBC3->bitmap[0] | (pBC3->bitmap[1] << 8) | (pBC3->bitmap[2] << 16); + + for (size_t i = 0; i < 8; ++i, dw >>= 3) + pColor[i] = XMVectorSetW(pColor[i], fAlpha[dw & 0x7]); + + dw = pBC3->bitmap[3] | (pBC3->bitmap[4] << 8) | (pBC3->bitmap[5] << 16); + + for (size_t i = 8; i < NUM_PIXELS_PER_BLOCK; ++i, dw >>= 3) + pColor[i] = XMVectorSetW(pColor[i], fAlpha[dw & 0x7]); +} + +_Use_decl_annotations_ +void DirectX::D3DXEncodeBC3(uint8_t *pBC, const XMVECTOR *pColor, DWORD flags) +{ + assert(pBC && pColor); + static_assert(sizeof(D3DX_BC3) == 16, "D3DX_BC3 should be 16 bytes"); + + HDRColorA Color[NUM_PIXELS_PER_BLOCK]; + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + XMStoreFloat4(reinterpret_cast(&Color[i]), pColor[i]); + } + + auto pBC3 = reinterpret_cast(pBC); + + // Quantize block to A8, using Floyd Stienberg error diffusion. This + // increases the chance that colors will map directly to the quantized + // axis endpoints. + float fAlpha[NUM_PIXELS_PER_BLOCK]; + float fError[NUM_PIXELS_PER_BLOCK]; + + float fMinAlpha = Color[0].a; + float fMaxAlpha = Color[0].a; + + if (flags & BC_FLAGS_DITHER_A) + memset(fError, 0x00, NUM_PIXELS_PER_BLOCK * sizeof(float)); + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + float fAlph = Color[i].a; + if (flags & BC_FLAGS_DITHER_A) + fAlph += fError[i]; + + fAlpha[i] = static_cast(fAlph * 255.0f + 0.5f) * (1.0f / 255.0f); + + if (fAlpha[i] < fMinAlpha) + fMinAlpha = fAlpha[i]; + else if (fAlpha[i] > fMaxAlpha) + fMaxAlpha = fAlpha[i]; + + if (flags & BC_FLAGS_DITHER_A) + { + float fDiff = fAlph - fAlpha[i]; + + if (3 != (i & 3)) + { + assert(i < 15); + _Analysis_assume_(i < 15); + fError[i + 1] += fDiff * (7.0f / 16.0f); + } + + if (i < 12) + { + if (i & 3) + fError[i + 3] += fDiff * (3.0f / 16.0f); + + fError[i + 4] += fDiff * (5.0f / 16.0f); + + if (3 != (i & 3)) + { + assert(i < 11); + _Analysis_assume_(i < 11); + fError[i + 5] += fDiff * (1.0f / 16.0f); + } + } + } + } + +#ifdef COLOR_WEIGHTS + if (0.0f == fMaxAlpha) + { + EncodeSolidBC1(&pBC3->dxt1, Color); + pBC3->alpha[0] = 0x00; + pBC3->alpha[1] = 0x00; + memset(pBC3->bitmap, 0x00, 6); + } +#endif + + // RGB part + EncodeBC1(&pBC3->bc1, Color, false, 0.f, flags); + + // Alpha part + if (1.0f == fMinAlpha) + { + pBC3->alpha[0] = 0xff; + pBC3->alpha[1] = 0xff; + memset(pBC3->bitmap, 0x00, 6); + return; + } + + // Optimize and Quantize Min and Max values + size_t uSteps = ((0.0f == fMinAlpha) || (1.0f == fMaxAlpha)) ? 6 : 8; + + float fAlphaA, fAlphaB; + OptimizeAlpha(&fAlphaA, &fAlphaB, fAlpha, uSteps); + + uint8_t bAlphaA = (uint8_t) static_cast(fAlphaA * 255.0f + 0.5f); + uint8_t bAlphaB = (uint8_t) static_cast(fAlphaB * 255.0f + 0.5f); + + fAlphaA = (float)bAlphaA * (1.0f / 255.0f); + fAlphaB = (float)bAlphaB * (1.0f / 255.0f); + + // Setup block + if ((8 == uSteps) && (bAlphaA == bAlphaB)) + { + pBC3->alpha[0] = bAlphaA; + pBC3->alpha[1] = bAlphaB; + memset(pBC3->bitmap, 0x00, 6); + return; + } + + static const size_t pSteps6[] = { 0, 2, 3, 4, 5, 1 }; + static const size_t pSteps8[] = { 0, 2, 3, 4, 5, 6, 7, 1 }; + + const size_t *pSteps; + float fStep[8]; + + if (6 == uSteps) + { + pBC3->alpha[0] = bAlphaA; + pBC3->alpha[1] = bAlphaB; + + fStep[0] = fAlphaA; + fStep[1] = fAlphaB; + + for (size_t i = 1; i < 5; ++i) + fStep[i + 1] = (fStep[0] * (5 - i) + fStep[1] * i) * (1.0f / 5.0f); + + fStep[6] = 0.0f; + fStep[7] = 1.0f; + + pSteps = pSteps6; + } + else + { + pBC3->alpha[0] = bAlphaB; + pBC3->alpha[1] = bAlphaA; + + fStep[0] = fAlphaB; + fStep[1] = fAlphaA; + + for (size_t i = 1; i < 7; ++i) + fStep[i + 1] = (fStep[0] * (7 - i) + fStep[1] * i) * (1.0f / 7.0f); + + pSteps = pSteps8; + } + + // Encode alpha bitmap + float fSteps = (float)(uSteps - 1); + float fScale = (fStep[0] != fStep[1]) ? (fSteps / (fStep[1] - fStep[0])) : 0.0f; + + if (flags & BC_FLAGS_DITHER_A) + memset(fError, 0x00, NUM_PIXELS_PER_BLOCK * sizeof(float)); + + for (size_t iSet = 0; iSet < 2; iSet++) + { + uint32_t dw = 0; + + size_t iMin = iSet * 8; + size_t iLim = iMin + 8; + + for (size_t i = iMin; i < iLim; ++i) + { + float fAlph = Color[i].a; + if (flags & BC_FLAGS_DITHER_A) + fAlph += fError[i]; + float fDot = (fAlph - fStep[0]) * fScale; + + uint32_t iStep; + if (fDot <= 0.0f) + iStep = ((6 == uSteps) && (fAlph <= fStep[0] * 0.5f)) ? 6 : 0; + else if (fDot >= fSteps) + iStep = ((6 == uSteps) && (fAlph >= (fStep[1] + 1.0f) * 0.5f)) ? 7 : 1; + else + iStep = static_cast(pSteps[static_cast(fDot + 0.5f)]); + + dw = (iStep << 21) | (dw >> 3); + + if (flags & BC_FLAGS_DITHER_A) + { + float fDiff = (fAlph - fStep[iStep]); + + if (3 != (i & 3)) + fError[i + 1] += fDiff * (7.0f / 16.0f); + + if (i < 12) + { + if (i & 3) + fError[i + 3] += fDiff * (3.0f / 16.0f); + + fError[i + 4] += fDiff * (5.0f / 16.0f); + + if (3 != (i & 3)) + fError[i + 5] += fDiff * (1.0f / 16.0f); + } + } + } + + pBC3->bitmap[0 + iSet * 3] = ((uint8_t *)&dw)[0]; + pBC3->bitmap[1 + iSet * 3] = ((uint8_t *)&dw)[1]; + pBC3->bitmap[2 + iSet * 3] = ((uint8_t *)&dw)[2]; + } +} diff --git a/deps/DirectXTex/DirectXTex/BC.h b/deps/DirectXTex/DirectXTex/BC.h new file mode 100644 index 0000000..e735716 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/BC.h @@ -0,0 +1,332 @@ +//------------------------------------------------------------------------------------- +// BC.h +// +// Block-compression (BC) functionality +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#pragma once + +#include +#include +#include + +namespace DirectX +{ +//------------------------------------------------------------------------------------- +// Macros +//------------------------------------------------------------------------------------- + +// Because these are used in SAL annotations, they need to remain macros rather than const values +#define NUM_PIXELS_PER_BLOCK 16 + +//------------------------------------------------------------------------------------- +// Constants +//------------------------------------------------------------------------------------- + +enum BC_FLAGS +{ + BC_FLAGS_NONE = 0x0, + BC_FLAGS_DITHER_RGB = 0x10000, // Enables dithering for RGB colors for BC1-3 + BC_FLAGS_DITHER_A = 0x20000, // Enables dithering for Alpha channel for BC1-3 + BC_FLAGS_UNIFORM = 0x40000, // By default, uses perceptual weighting for BC1-3; this flag makes it a uniform weighting + BC_FLAGS_USE_3SUBSETS = 0x80000, // By default, BC7 skips mode 0 & 2; this flag adds those modes back + BC_FLAGS_FORCE_BC7_MODE6 = 0x100000, // BC7 should only use mode 6; skip other modes +}; + +//------------------------------------------------------------------------------------- +// Structures +//------------------------------------------------------------------------------------- +class LDRColorA; + +class HDRColorA +{ +public: + float r, g, b, a; + +public: + HDRColorA() = default; + HDRColorA(float _r, float _g, float _b, float _a) : r(_r), g(_g), b(_b), a(_a) {} + HDRColorA(const HDRColorA& c) : r(c.r), g(c.g), b(c.b), a(c.a) {} + + // binary operators + HDRColorA operator + ( const HDRColorA& c ) const + { + return HDRColorA(r + c.r, g + c.g, b + c.b, a + c.a); + } + + HDRColorA operator - ( const HDRColorA& c ) const + { + return HDRColorA(r - c.r, g - c.g, b - c.b, a - c.a); + } + + HDRColorA operator * ( float f ) const + { + return HDRColorA(r * f, g * f, b * f, a * f); + } + + HDRColorA operator / ( float f ) const + { + float fInv = 1.0f / f; + return HDRColorA(r * fInv, g * fInv, b * fInv, a * fInv); + } + + float operator * ( const HDRColorA& c ) const + { + return r * c.r + g * c.g + b * c.b + a * c.a; + } + + // assignment operators + HDRColorA& operator += ( const HDRColorA& c ) + { + r += c.r; + g += c.g; + b += c.b; + a += c.a; + return *this; + } + + HDRColorA& operator -= ( const HDRColorA& c ) + { + r -= c.r; + g -= c.g; + b -= c.b; + a -= c.a; + return *this; + } + + HDRColorA& operator *= ( float f ) + { + r *= f; + g *= f; + b *= f; + a *= f; + return *this; + } + + HDRColorA& operator /= ( float f ) + { + float fInv = 1.0f / f; + r *= fInv; + g *= fInv; + b *= fInv; + a *= fInv; + return *this; + } + + HDRColorA& Clamp(_In_ float fMin, _In_ float fMax) + { + r = std::min(fMax, std::max(fMin, r)); + g = std::min(fMax, std::max(fMin, g)); + b = std::min(fMax, std::max(fMin, b)); + a = std::min(fMax, std::max(fMin, a)); + return *this; + } + + HDRColorA(const LDRColorA& c); + HDRColorA& operator = (const LDRColorA& c); + LDRColorA ToLDRColorA() const; +}; + +inline HDRColorA* HDRColorALerp(_Out_ HDRColorA *pOut, _In_ const HDRColorA *pC1, _In_ const HDRColorA *pC2, _In_ float s) +{ + pOut->r = pC1->r + s * (pC2->r - pC1->r); + pOut->g = pC1->g + s * (pC2->g - pC1->g); + pOut->b = pC1->b + s * (pC2->b - pC1->b); + pOut->a = pC1->a + s * (pC2->a - pC1->a); + return pOut; +} + +#pragma pack(push,1) +// BC1/DXT1 compression (4 bits per texel) +struct D3DX_BC1 +{ + uint16_t rgb[2]; // 565 colors + uint32_t bitmap; // 2bpp rgb bitmap +}; + +// BC2/DXT2/3 compression (8 bits per texel) +struct D3DX_BC2 +{ + uint32_t bitmap[2]; // 4bpp alpha bitmap + D3DX_BC1 bc1; // BC1 rgb data +}; + +// BC3/DXT4/5 compression (8 bits per texel) +struct D3DX_BC3 +{ + uint8_t alpha[2]; // alpha values + uint8_t bitmap[6]; // 3bpp alpha bitmap + D3DX_BC1 bc1; // BC1 rgb data +}; +#pragma pack(pop) + +//------------------------------------------------------------------------------------- +// Templates +//------------------------------------------------------------------------------------- +#pragma warning(push) +#pragma warning(disable : 4127) +template void OptimizeAlpha(float *pX, float *pY, const float *pPoints, size_t cSteps) +{ + static const float pC6[] = { 5.0f / 5.0f, 4.0f / 5.0f, 3.0f / 5.0f, 2.0f / 5.0f, 1.0f / 5.0f, 0.0f / 5.0f }; + static const float pD6[] = { 0.0f / 5.0f, 1.0f / 5.0f, 2.0f / 5.0f, 3.0f / 5.0f, 4.0f / 5.0f, 5.0f / 5.0f }; + static const float pC8[] = { 7.0f / 7.0f, 6.0f / 7.0f, 5.0f / 7.0f, 4.0f / 7.0f, 3.0f / 7.0f, 2.0f / 7.0f, 1.0f / 7.0f, 0.0f / 7.0f }; + static const float pD8[] = { 0.0f / 7.0f, 1.0f / 7.0f, 2.0f / 7.0f, 3.0f / 7.0f, 4.0f / 7.0f, 5.0f / 7.0f, 6.0f / 7.0f, 7.0f / 7.0f }; + + const float *pC = (6 == cSteps) ? pC6 : pC8; + const float *pD = (6 == cSteps) ? pD6 : pD8; + + const float MAX_VALUE = 1.0f; + const float MIN_VALUE = (bRange) ? -1.0f : 0.0f; + + // Find Min and Max points, as starting point + float fX = MAX_VALUE; + float fY = MIN_VALUE; + + if (8 == cSteps) + { + for (size_t iPoint = 0; iPoint < NUM_PIXELS_PER_BLOCK; iPoint++) + { + if (pPoints[iPoint] < fX) + fX = pPoints[iPoint]; + + if (pPoints[iPoint] > fY) + fY = pPoints[iPoint]; + } + } + else + { + for (size_t iPoint = 0; iPoint < NUM_PIXELS_PER_BLOCK; iPoint++) + { + if (pPoints[iPoint] < fX && pPoints[iPoint] > MIN_VALUE) + fX = pPoints[iPoint]; + + if (pPoints[iPoint] > fY && pPoints[iPoint] < MAX_VALUE) + fY = pPoints[iPoint]; + } + + if (fX == fY) + { + fY = MAX_VALUE; + } + } + + // Use Newton's Method to find local minima of sum-of-squares error. + float fSteps = (float)(cSteps - 1); + + for (size_t iIteration = 0; iIteration < 8; iIteration++) + { + float fScale; + + if ((fY - fX) < (1.0f / 256.0f)) + break; + + fScale = fSteps / (fY - fX); + + // Calculate new steps + float pSteps[8]; + + for (size_t iStep = 0; iStep < cSteps; iStep++) + pSteps[iStep] = pC[iStep] * fX + pD[iStep] * fY; + + if (6 == cSteps) + { + pSteps[6] = MIN_VALUE; + pSteps[7] = MAX_VALUE; + } + + // Evaluate function, and derivatives + float dX = 0.0f; + float dY = 0.0f; + float d2X = 0.0f; + float d2Y = 0.0f; + + for (size_t iPoint = 0; iPoint < NUM_PIXELS_PER_BLOCK; iPoint++) + { + float fDot = (pPoints[iPoint] - fX) * fScale; + + size_t iStep; + + if (fDot <= 0.0f) + iStep = ((6 == cSteps) && (pPoints[iPoint] <= fX * 0.5f)) ? 6 : 0; + else if (fDot >= fSteps) + iStep = ((6 == cSteps) && (pPoints[iPoint] >= (fY + 1.0f) * 0.5f)) ? 7 : (cSteps - 1); + else + iStep = static_cast(fDot + 0.5f); + + + if (iStep < cSteps) + { + // D3DX had this computation backwards (pPoints[iPoint] - pSteps[iStep]) + // this fix improves RMS of the alpha component + float fDiff = pSteps[iStep] - pPoints[iPoint]; + + dX += pC[iStep] * fDiff; + d2X += pC[iStep] * pC[iStep]; + + dY += pD[iStep] * fDiff; + d2Y += pD[iStep] * pD[iStep]; + } + } + + // Move endpoints + if (d2X > 0.0f) + fX -= dX / d2X; + + if (d2Y > 0.0f) + fY -= dY / d2Y; + + if (fX > fY) + { + float f = fX; fX = fY; fY = f; + } + + if ((dX * dX < (1.0f / 64.0f)) && (dY * dY < (1.0f / 64.0f))) + break; + } + + *pX = (fX < MIN_VALUE) ? MIN_VALUE : (fX > MAX_VALUE) ? MAX_VALUE : fX; + *pY = (fY < MIN_VALUE) ? MIN_VALUE : (fY > MAX_VALUE) ? MAX_VALUE : fY; +} +#pragma warning(pop) + +//------------------------------------------------------------------------------------- +// Functions +//------------------------------------------------------------------------------------- + +typedef void (*BC_DECODE)(XMVECTOR *pColor, const uint8_t *pBC); +typedef void (*BC_ENCODE)(uint8_t *pDXT, const XMVECTOR *pColor, DWORD flags); + +void D3DXDecodeBC1(_Out_writes_(NUM_PIXELS_PER_BLOCK) XMVECTOR *pColor, _In_reads_(8) const uint8_t *pBC); +void D3DXDecodeBC2(_Out_writes_(NUM_PIXELS_PER_BLOCK) XMVECTOR *pColor, _In_reads_(16) const uint8_t *pBC); +void D3DXDecodeBC3(_Out_writes_(NUM_PIXELS_PER_BLOCK) XMVECTOR *pColor, _In_reads_(16) const uint8_t *pBC); +void D3DXDecodeBC4U(_Out_writes_(NUM_PIXELS_PER_BLOCK) XMVECTOR *pColor, _In_reads_(8) const uint8_t *pBC); +void D3DXDecodeBC4S(_Out_writes_(NUM_PIXELS_PER_BLOCK) XMVECTOR *pColor, _In_reads_(8) const uint8_t *pBC); +void D3DXDecodeBC5U(_Out_writes_(NUM_PIXELS_PER_BLOCK) XMVECTOR *pColor, _In_reads_(16) const uint8_t *pBC); +void D3DXDecodeBC5S(_Out_writes_(NUM_PIXELS_PER_BLOCK) XMVECTOR *pColor, _In_reads_(16) const uint8_t *pBC); +void D3DXDecodeBC6HU(_Out_writes_(NUM_PIXELS_PER_BLOCK) XMVECTOR *pColor, _In_reads_(16) const uint8_t *pBC); +void D3DXDecodeBC6HS(_Out_writes_(NUM_PIXELS_PER_BLOCK) XMVECTOR *pColor, _In_reads_(16) const uint8_t *pBC); +void D3DXDecodeBC7(_Out_writes_(NUM_PIXELS_PER_BLOCK) XMVECTOR *pColor, _In_reads_(16) const uint8_t *pBC); + +void D3DXEncodeBC1(_Out_writes_(8) uint8_t *pBC, _In_reads_(NUM_PIXELS_PER_BLOCK) const XMVECTOR *pColor, _In_ float threshold, _In_ DWORD flags); + // BC1 requires one additional parameter, so it doesn't match signature of BC_ENCODE above + +void D3DXEncodeBC2(_Out_writes_(16) uint8_t *pBC, _In_reads_(NUM_PIXELS_PER_BLOCK) const XMVECTOR *pColor, _In_ DWORD flags); +void D3DXEncodeBC3(_Out_writes_(16) uint8_t *pBC, _In_reads_(NUM_PIXELS_PER_BLOCK) const XMVECTOR *pColor, _In_ DWORD flags); +void D3DXEncodeBC4U(_Out_writes_(8) uint8_t *pBC, _In_reads_(NUM_PIXELS_PER_BLOCK) const XMVECTOR *pColor, _In_ DWORD flags); +void D3DXEncodeBC4S(_Out_writes_(8) uint8_t *pBC, _In_reads_(NUM_PIXELS_PER_BLOCK) const XMVECTOR *pColor, _In_ DWORD flags); +void D3DXEncodeBC5U(_Out_writes_(16) uint8_t *pBC, _In_reads_(NUM_PIXELS_PER_BLOCK) const XMVECTOR *pColor, _In_ DWORD flags); +void D3DXEncodeBC5S(_Out_writes_(16) uint8_t *pBC, _In_reads_(NUM_PIXELS_PER_BLOCK) const XMVECTOR *pColor, _In_ DWORD flags); +void D3DXEncodeBC6HU(_Out_writes_(16) uint8_t *pBC, _In_reads_(NUM_PIXELS_PER_BLOCK) const XMVECTOR *pColor, _In_ DWORD flags); +void D3DXEncodeBC6HS(_Out_writes_(16) uint8_t *pBC, _In_reads_(NUM_PIXELS_PER_BLOCK) const XMVECTOR *pColor, _In_ DWORD flags); +void D3DXEncodeBC7(_Out_writes_(16) uint8_t *pBC, _In_reads_(NUM_PIXELS_PER_BLOCK) const XMVECTOR *pColor, _In_ DWORD flags); + +}; // namespace diff --git a/deps/DirectXTex/DirectXTex/BC4BC5.cpp b/deps/DirectXTex/DirectXTex/BC4BC5.cpp new file mode 100644 index 0000000..8824df4 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/BC4BC5.cpp @@ -0,0 +1,566 @@ +//------------------------------------------------------------------------------------- +// BC4BC5.cpp +// +// Block-compression (BC) functionality for BC4 and BC5 (DirectX 10 texture compression) +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +#include "BC.h" + +using namespace DirectX; + +//------------------------------------------------------------------------------------ +// Constants +//------------------------------------------------------------------------------------ + +// Because these are used in SAL annotations, they need to remain macros rather than const values +#define BLOCK_LEN 4 +// length of each block in texel + +#define BLOCK_SIZE (BLOCK_LEN * BLOCK_LEN) +// total texels in a 4x4 block. + +namespace +{ + //------------------------------------------------------------------------------------ + // Structures + //------------------------------------------------------------------------------------- + +#pragma warning(push) +#pragma warning(disable : 4201) + + // BC4U/BC5U + struct BC4_UNORM + { + float R(size_t uOffset) const + { + size_t uIndex = GetIndex(uOffset); + return DecodeFromIndex(uIndex); + } + + float DecodeFromIndex(size_t uIndex) const + { + if (uIndex == 0) + return red_0 / 255.0f; + if (uIndex == 1) + return red_1 / 255.0f; + float fred_0 = red_0 / 255.0f; + float fred_1 = red_1 / 255.0f; + if (red_0 > red_1) + { + uIndex -= 1; + return (fred_0 * (7 - uIndex) + fred_1 * uIndex) / 7.0f; + } + else + { + if (uIndex == 6) + return 0.0f; + if (uIndex == 7) + return 1.0f; + uIndex -= 1; + return (fred_0 * (5 - uIndex) + fred_1 * uIndex) / 5.0f; + } + } + + size_t GetIndex(size_t uOffset) const + { + return (size_t)((data >> (3 * uOffset + 16)) & 0x07); + } + + void SetIndex(size_t uOffset, size_t uIndex) + { + data &= ~((uint64_t)0x07 << (3 * uOffset + 16)); + data |= ((uint64_t)uIndex << (3 * uOffset + 16)); + } + + union + { + struct + { + uint8_t red_0; + uint8_t red_1; + uint8_t indices[6]; + }; + uint64_t data; + }; + }; + + // BC4S/BC5S + struct BC4_SNORM + { + float R(size_t uOffset) const + { + size_t uIndex = GetIndex(uOffset); + return DecodeFromIndex(uIndex); + } + + float DecodeFromIndex(size_t uIndex) const + { + int8_t sred_0 = (red_0 == -128) ? -127 : red_0; + int8_t sred_1 = (red_1 == -128) ? -127 : red_1; + + if (uIndex == 0) + return sred_0 / 127.0f; + if (uIndex == 1) + return sred_1 / 127.0f; + float fred_0 = sred_0 / 127.0f; + float fred_1 = sred_1 / 127.0f; + if (red_0 > red_1) + { + uIndex -= 1; + return (fred_0 * (7 - uIndex) + fred_1 * uIndex) / 7.0f; + } + else + { + if (uIndex == 6) + return -1.0f; + if (uIndex == 7) + return 1.0f; + uIndex -= 1; + return (fred_0 * (5 - uIndex) + fred_1 * uIndex) / 5.0f; + } + } + + size_t GetIndex(size_t uOffset) const + { + return (size_t)((data >> (3 * uOffset + 16)) & 0x07); + } + + void SetIndex(size_t uOffset, size_t uIndex) + { + data &= ~((uint64_t)0x07 << (3 * uOffset + 16)); + data |= ((uint64_t)uIndex << (3 * uOffset + 16)); + } + + union + { + struct + { + int8_t red_0; + int8_t red_1; + uint8_t indices[6]; + }; + uint64_t data; + }; + }; + +#pragma warning(pop) + + //------------------------------------------------------------------------------------- + // Convert a floating point value to an 8-bit SNORM + //------------------------------------------------------------------------------------- + void inline FloatToSNorm(_In_ float fVal, _Out_ int8_t *piSNorm) + { + const uint32_t dwMostNeg = (1 << (8 * sizeof(int8_t) - 1)); + + if (_isnan(fVal)) + fVal = 0; + else + if (fVal > 1) + fVal = 1; // Clamp to 1 + else + if (fVal < -1) + fVal = -1; // Clamp to -1 + + fVal = fVal * (int8_t)(dwMostNeg - 1); + + if (fVal >= 0) + fVal += .5f; + else + fVal -= .5f; + + *piSNorm = (int8_t)(fVal); + } + + + //------------------------------------------------------------------------------ + void FindEndPointsBC4U( + _In_reads_(BLOCK_SIZE) const float theTexelsU[], + _Out_ uint8_t &endpointU_0, + _Out_ uint8_t &endpointU_1) + { + // The boundary of codec for signed/unsigned format + const float MIN_NORM = 0.f; + const float MAX_NORM = 1.f; + + // Find max/min of input texels + float fBlockMax = theTexelsU[0]; + float fBlockMin = theTexelsU[0]; + for (size_t i = 0; i < BLOCK_SIZE; ++i) + { + if (theTexelsU[i] < fBlockMin) + { + fBlockMin = theTexelsU[i]; + } + else if (theTexelsU[i] > fBlockMax) + { + fBlockMax = theTexelsU[i]; + } + } + + // If there are boundary values in input texels, should use 4 interpolated color values to guarantee + // the exact code of the boundary values. + bool bUsing4BlockCodec = (MIN_NORM == fBlockMin || MAX_NORM == fBlockMax); + + // Using Optimize + float fStart, fEnd; + + if (!bUsing4BlockCodec) + { + // 6 interpolated color values + OptimizeAlpha(&fStart, &fEnd, theTexelsU, 8); + + uint8_t iStart = static_cast(fStart * 255.0f); + uint8_t iEnd = static_cast(fEnd * 255.0f); + + endpointU_0 = iEnd; + endpointU_1 = iStart; + } + else + { + // 4 interpolated color values + OptimizeAlpha(&fStart, &fEnd, theTexelsU, 6); + + uint8_t iStart = static_cast(fStart * 255.0f); + uint8_t iEnd = static_cast(fEnd * 255.0f); + + endpointU_1 = iEnd; + endpointU_0 = iStart; + } + } + + void FindEndPointsBC4S( + _In_reads_(BLOCK_SIZE) const float theTexelsU[], + _Out_ int8_t &endpointU_0, + _Out_ int8_t &endpointU_1) + { + // The boundary of codec for signed/unsigned format + const float MIN_NORM = -1.f; + const float MAX_NORM = 1.f; + + // Find max/min of input texels + float fBlockMax = theTexelsU[0]; + float fBlockMin = theTexelsU[0]; + for (size_t i = 0; i < BLOCK_SIZE; ++i) + { + if (theTexelsU[i] < fBlockMin) + { + fBlockMin = theTexelsU[i]; + } + else if (theTexelsU[i] > fBlockMax) + { + fBlockMax = theTexelsU[i]; + } + } + + // If there are boundary values in input texels, should use 4 interpolated color values to guarantee + // the exact code of the boundary values. + bool bUsing4BlockCodec = (MIN_NORM == fBlockMin || MAX_NORM == fBlockMax); + + // Using Optimize + float fStart, fEnd; + + if (!bUsing4BlockCodec) + { + // 6 interpolated color values + OptimizeAlpha(&fStart, &fEnd, theTexelsU, 8); + + int8_t iStart, iEnd; + FloatToSNorm(fStart, &iStart); + FloatToSNorm(fEnd, &iEnd); + + endpointU_0 = iEnd; + endpointU_1 = iStart; + } + else + { + // 4 interpolated color values + OptimizeAlpha(&fStart, &fEnd, theTexelsU, 6); + + int8_t iStart, iEnd; + FloatToSNorm(fStart, &iStart); + FloatToSNorm(fEnd, &iEnd); + + endpointU_1 = iEnd; + endpointU_0 = iStart; + } + } + + + //------------------------------------------------------------------------------ + inline void FindEndPointsBC5U( + _In_reads_(BLOCK_SIZE) const float theTexelsU[], + _In_reads_(BLOCK_SIZE) const float theTexelsV[], + _Out_ uint8_t &endpointU_0, + _Out_ uint8_t &endpointU_1, + _Out_ uint8_t &endpointV_0, + _Out_ uint8_t &endpointV_1) + { + //Encoding the U and V channel by BC4 codec separately. + FindEndPointsBC4U(theTexelsU, endpointU_0, endpointU_1); + FindEndPointsBC4U(theTexelsV, endpointV_0, endpointV_1); + } + + inline void FindEndPointsBC5S( + _In_reads_(BLOCK_SIZE) const float theTexelsU[], + _In_reads_(BLOCK_SIZE) const float theTexelsV[], + _Out_ int8_t &endpointU_0, + _Out_ int8_t &endpointU_1, + _Out_ int8_t &endpointV_0, + _Out_ int8_t &endpointV_1) + { + //Encoding the U and V channel by BC4 codec separately. + FindEndPointsBC4S(theTexelsU, endpointU_0, endpointU_1); + FindEndPointsBC4S(theTexelsV, endpointV_0, endpointV_1); + } + + + //------------------------------------------------------------------------------ + void FindClosestUNORM( + _Inout_ BC4_UNORM* pBC, + _In_reads_(NUM_PIXELS_PER_BLOCK) const float theTexelsU[]) + { + float rGradient[8]; + for (size_t i = 0; i < 8; ++i) + { + rGradient[i] = pBC->DecodeFromIndex(i); + } + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + size_t uBestIndex = 0; + float fBestDelta = 100000; + for (size_t uIndex = 0; uIndex < 8; uIndex++) + { + float fCurrentDelta = fabsf(rGradient[uIndex] - theTexelsU[i]); + if (fCurrentDelta < fBestDelta) + { + uBestIndex = uIndex; + fBestDelta = fCurrentDelta; + } + } + pBC->SetIndex(i, uBestIndex); + } + } + + void FindClosestSNORM( + _Inout_ BC4_SNORM* pBC, + _In_reads_(NUM_PIXELS_PER_BLOCK) const float theTexelsU[]) + { + float rGradient[8]; + for (size_t i = 0; i < 8; ++i) + { + rGradient[i] = pBC->DecodeFromIndex(i); + } + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + size_t uBestIndex = 0; + float fBestDelta = 100000; + for (size_t uIndex = 0; uIndex < 8; uIndex++) + { + float fCurrentDelta = fabsf(rGradient[uIndex] - theTexelsU[i]); + if (fCurrentDelta < fBestDelta) + { + uBestIndex = uIndex; + fBestDelta = fCurrentDelta; + } + } + pBC->SetIndex(i, uBestIndex); + } + } +} + + +//===================================================================================== +// Entry points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// BC4 Compression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DirectX::D3DXDecodeBC4U(XMVECTOR *pColor, const uint8_t *pBC) +{ + assert(pColor && pBC); + static_assert(sizeof(BC4_UNORM) == 8, "BC4_UNORM should be 8 bytes"); + + auto pBC4 = reinterpret_cast(pBC); + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { +#pragma prefast(suppress:22103, "writing blocks in two halves confuses tool") + pColor[i] = XMVectorSet(pBC4->R(i), 0, 0, 1.0f); + } +} + +_Use_decl_annotations_ +void DirectX::D3DXDecodeBC4S(XMVECTOR *pColor, const uint8_t *pBC) +{ + assert(pColor && pBC); + static_assert(sizeof(BC4_SNORM) == 8, "BC4_SNORM should be 8 bytes"); + + auto pBC4 = reinterpret_cast(pBC); + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { +#pragma prefast(suppress:22103, "writing blocks in two halves confuses tool") + pColor[i] = XMVectorSet(pBC4->R(i), 0, 0, 1.0f); + } +} + +_Use_decl_annotations_ +void DirectX::D3DXEncodeBC4U(uint8_t *pBC, const XMVECTOR *pColor, DWORD flags) +{ + UNREFERENCED_PARAMETER(flags); + + assert(pBC && pColor); + static_assert(sizeof(BC4_UNORM) == 8, "BC4_UNORM should be 8 bytes"); + + memset(pBC, 0, sizeof(BC4_UNORM)); + auto pBC4 = reinterpret_cast(pBC); + float theTexelsU[NUM_PIXELS_PER_BLOCK]; + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + theTexelsU[i] = XMVectorGetX(pColor[i]); + } + + FindEndPointsBC4U(theTexelsU, pBC4->red_0, pBC4->red_1); + FindClosestUNORM(pBC4, theTexelsU); +} + +_Use_decl_annotations_ +void DirectX::D3DXEncodeBC4S(uint8_t *pBC, const XMVECTOR *pColor, DWORD flags) +{ + UNREFERENCED_PARAMETER(flags); + + assert(pBC && pColor); + static_assert(sizeof(BC4_SNORM) == 8, "BC4_SNORM should be 8 bytes"); + + memset(pBC, 0, sizeof(BC4_UNORM)); + auto pBC4 = reinterpret_cast(pBC); + float theTexelsU[NUM_PIXELS_PER_BLOCK]; + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + theTexelsU[i] = XMVectorGetX(pColor[i]); + } + + FindEndPointsBC4S(theTexelsU, pBC4->red_0, pBC4->red_1); + FindClosestSNORM(pBC4, theTexelsU); +} + + +//------------------------------------------------------------------------------------- +// BC5 Compression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DirectX::D3DXDecodeBC5U(XMVECTOR *pColor, const uint8_t *pBC) +{ + assert(pColor && pBC); + static_assert(sizeof(BC4_UNORM) == 8, "BC4_UNORM should be 8 bytes"); + + auto pBCR = reinterpret_cast(pBC); + auto pBCG = reinterpret_cast(pBC + sizeof(BC4_UNORM)); + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { +#pragma prefast(suppress:22103, "writing blocks in two halves confuses tool") + pColor[i] = XMVectorSet(pBCR->R(i), pBCG->R(i), 0, 1.0f); + } +} + +_Use_decl_annotations_ +void DirectX::D3DXDecodeBC5S(XMVECTOR *pColor, const uint8_t *pBC) +{ + assert(pColor && pBC); + static_assert(sizeof(BC4_SNORM) == 8, "BC4_SNORM should be 8 bytes"); + + auto pBCR = reinterpret_cast(pBC); + auto pBCG = reinterpret_cast(pBC + sizeof(BC4_SNORM)); + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { +#pragma prefast(suppress:22103, "writing blocks in two halves confuses tool") + pColor[i] = XMVectorSet(pBCR->R(i), pBCG->R(i), 0, 1.0f); + } +} + +_Use_decl_annotations_ +void DirectX::D3DXEncodeBC5U(uint8_t *pBC, const XMVECTOR *pColor, DWORD flags) +{ + UNREFERENCED_PARAMETER(flags); + + assert(pBC && pColor); + static_assert(sizeof(BC4_UNORM) == 8, "BC4_UNORM should be 8 bytes"); + + memset(pBC, 0, sizeof(BC4_UNORM) * 2); + auto pBCR = reinterpret_cast(pBC); + auto pBCG = reinterpret_cast(pBC + sizeof(BC4_UNORM)); + float theTexelsU[NUM_PIXELS_PER_BLOCK]; + float theTexelsV[NUM_PIXELS_PER_BLOCK]; + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + XMFLOAT4A clr; + XMStoreFloat4A(&clr, pColor[i]); + theTexelsU[i] = clr.x; + theTexelsV[i] = clr.y; + } + + FindEndPointsBC5U( + theTexelsU, + theTexelsV, + pBCR->red_0, + pBCR->red_1, + pBCG->red_0, + pBCG->red_1); + + FindClosestUNORM(pBCR, theTexelsU); + FindClosestUNORM(pBCG, theTexelsV); +} + +_Use_decl_annotations_ +void DirectX::D3DXEncodeBC5S(uint8_t *pBC, const XMVECTOR *pColor, DWORD flags) +{ + UNREFERENCED_PARAMETER(flags); + + assert(pBC && pColor); + static_assert(sizeof(BC4_SNORM) == 8, "BC4_SNORM should be 8 bytes"); + + memset(pBC, 0, sizeof(BC4_UNORM) * 2); + auto pBCR = reinterpret_cast(pBC); + auto pBCG = reinterpret_cast(pBC + sizeof(BC4_SNORM)); + float theTexelsU[NUM_PIXELS_PER_BLOCK]; + float theTexelsV[NUM_PIXELS_PER_BLOCK]; + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + XMFLOAT4A clr; + XMStoreFloat4A(&clr, pColor[i]); + theTexelsU[i] = clr.x; + theTexelsV[i] = clr.y; + } + + FindEndPointsBC5S( + theTexelsU, + theTexelsV, + pBCR->red_0, + pBCR->red_1, + pBCG->red_0, + pBCG->red_1); + + FindClosestSNORM(pBCR, theTexelsU); + FindClosestSNORM(pBCG, theTexelsV); +} \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/BC6HBC7.cpp b/deps/DirectXTex/DirectXTex/BC6HBC7.cpp new file mode 100644 index 0000000..b98eef1 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/BC6HBC7.cpp @@ -0,0 +1,3470 @@ +//------------------------------------------------------------------------------------- +// BC6HBC7.cpp +// +// Block-compression (BC) functionality for BC6H and BC7 (DirectX 11 texture compression) +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +#include "BC.h" + +using namespace DirectX; +using namespace DirectX::PackedVector; + +//------------------------------------------------------------------------------------- +// Macros +//------------------------------------------------------------------------------------- + +#define SIGN_EXTEND(x,nb) ((((x)&(1<<((nb)-1)))?((~0)<<(nb)):0)|(x)) + +// Because these are used in SAL annotations, they need to remain macros rather than const values +#define BC6H_MAX_REGIONS 2 +#define BC6H_MAX_INDICES 16 +#define BC7_MAX_REGIONS 3 +#define BC7_MAX_INDICES 16 + +namespace +{ + //------------------------------------------------------------------------------------- + // Constants + //------------------------------------------------------------------------------------- + + const uint16_t F16S_MASK = 0x8000; // f16 sign mask + const uint16_t F16EM_MASK = 0x7fff; // f16 exp & mantissa mask + const uint16_t F16MAX = 0x7bff; // MAXFLT bit pattern for XMHALF + + const size_t BC6H_NUM_CHANNELS = 3; + const size_t BC6H_MAX_SHAPES = 32; + + const size_t BC7_NUM_CHANNELS = 4; + const size_t BC7_MAX_SHAPES = 64; + + const int32_t BC67_WEIGHT_MAX = 64; + const uint32_t BC67_WEIGHT_SHIFT = 6; + const int32_t BC67_WEIGHT_ROUND = 32; + + const float fEpsilon = (0.25f / 64.0f) * (0.25f / 64.0f); + const float pC3[] = { 2.0f / 2.0f, 1.0f / 2.0f, 0.0f / 2.0f }; + const float pD3[] = { 0.0f / 2.0f, 1.0f / 2.0f, 2.0f / 2.0f }; + const float pC4[] = { 3.0f / 3.0f, 2.0f / 3.0f, 1.0f / 3.0f, 0.0f / 3.0f }; + const float pD4[] = { 0.0f / 3.0f, 1.0f / 3.0f, 2.0f / 3.0f, 3.0f / 3.0f }; + + // Partition, Shape, Pixel (index into 4x4 block) + const uint8_t g_aPartitionTable[3][64][16] = + { + { // 1 Region case has no subsets (all 0) + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } + }, + + { // BC6H/BC7 Partition Set for 2 Subsets + { 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1 }, // Shape 0 + { 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1 }, // Shape 1 + { 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 1 }, // Shape 2 + { 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0, 1, 1, 1 }, // Shape 3 + { 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1 }, // Shape 4 + { 0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1 }, // Shape 5 + { 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1 }, // Shape 6 + { 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1 }, // Shape 7 + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1 }, // Shape 8 + { 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }, // Shape 9 + { 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 1, 1 }, // Shape 10 + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1 }, // Shape 11 + { 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }, // Shape 12 + { 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1 }, // Shape 13 + { 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }, // Shape 14 + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1 }, // Shape 15 + { 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 1, 0, 1, 1, 1, 1 }, // Shape 16 + { 0, 1, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0 }, // Shape 17 + { 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 1, 0 }, // Shape 18 + { 0, 1, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0 }, // Shape 19 + { 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0 }, // Shape 20 + { 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0 }, // Shape 21 + { 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0 }, // Shape 22 + { 0, 1, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1 }, // Shape 23 + { 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0 }, // Shape 24 + { 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0 }, // Shape 25 + { 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0 }, // Shape 26 + { 0, 0, 1, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 1, 0, 0 }, // Shape 27 + { 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 0, 0 }, // Shape 28 + { 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0 }, // Shape 29 + { 0, 1, 1, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 1, 0 }, // Shape 30 + { 0, 0, 1, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 0 }, // Shape 31 + + // BC7 Partition Set for 2 Subsets (second-half) + { 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1 }, // Shape 32 + { 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 1, 1, 1, 1 }, // Shape 33 + { 0, 1, 0, 1, 1, 0, 1, 0, 0, 1, 0, 1, 1, 0, 1, 0 }, // Shape 34 + { 0, 0, 1, 1, 0, 0, 1, 1, 1, 1, 0, 0, 1, 1, 0, 0 }, // Shape 35 + { 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0 }, // Shape 36 + { 0, 1, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0 }, // Shape 37 + { 0, 1, 1, 0, 1, 0, 0, 1, 0, 1, 1, 0, 1, 0, 0, 1 }, // Shape 38 + { 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 0, 1 }, // Shape 39 + { 0, 1, 1, 1, 0, 0, 1, 1, 1, 1, 0, 0, 1, 1, 1, 0 }, // Shape 40 + { 0, 0, 0, 1, 0, 0, 1, 1, 1, 1, 0, 0, 1, 0, 0, 0 }, // Shape 41 + { 0, 0, 1, 1, 0, 0, 1, 0, 0, 1, 0, 0, 1, 1, 0, 0 }, // Shape 42 + { 0, 0, 1, 1, 1, 0, 1, 1, 1, 1, 0, 1, 1, 1, 0, 0 }, // Shape 43 + { 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0 }, // Shape 44 + { 0, 0, 1, 1, 1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1 }, // Shape 45 + { 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1 }, // Shape 46 + { 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0 }, // Shape 47 + { 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0 }, // Shape 48 + { 0, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 0, 0, 0 }, // Shape 49 + { 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0 }, // Shape 50 + { 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0 }, // Shape 51 + { 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 0, 1, 0, 0, 1, 1 }, // Shape 52 + { 0, 0, 1, 1, 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 0, 1 }, // Shape 53 + { 0, 1, 1, 0, 0, 0, 1, 1, 1, 0, 0, 1, 1, 1, 0, 0 }, // Shape 54 + { 0, 0, 1, 1, 1, 0, 0, 1, 1, 1, 0, 0, 0, 1, 1, 0 }, // Shape 55 + { 0, 1, 1, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 0, 0, 1 }, // Shape 56 + { 0, 1, 1, 0, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 0, 1 }, // Shape 57 + { 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 1 }, // Shape 58 + { 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 1, 0, 0, 1, 1, 1 }, // Shape 59 + { 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1 }, // Shape 60 + { 0, 0, 1, 1, 0, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0 }, // Shape 61 + { 0, 0, 1, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0 }, // Shape 62 + { 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 1, 1, 0, 1, 1, 1 } // Shape 63 + }, + + { // BC7 Partition Set for 3 Subsets + { 0, 0, 1, 1, 0, 0, 1, 1, 0, 2, 2, 1, 2, 2, 2, 2 }, // Shape 0 + { 0, 0, 0, 1, 0, 0, 1, 1, 2, 2, 1, 1, 2, 2, 2, 1 }, // Shape 1 + { 0, 0, 0, 0, 2, 0, 0, 1, 2, 2, 1, 1, 2, 2, 1, 1 }, // Shape 2 + { 0, 2, 2, 2, 0, 0, 2, 2, 0, 0, 1, 1, 0, 1, 1, 1 }, // Shape 3 + { 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 2, 2, 1, 1, 2, 2 }, // Shape 4 + { 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 2, 2, 0, 0, 2, 2 }, // Shape 5 + { 0, 0, 2, 2, 0, 0, 2, 2, 1, 1, 1, 1, 1, 1, 1, 1 }, // Shape 6 + { 0, 0, 1, 1, 0, 0, 1, 1, 2, 2, 1, 1, 2, 2, 1, 1 }, // Shape 7 + { 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 2 }, // Shape 8 + { 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2 }, // Shape 9 + { 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 2, 2 }, // Shape 10 + { 0, 0, 1, 2, 0, 0, 1, 2, 0, 0, 1, 2, 0, 0, 1, 2 }, // Shape 11 + { 0, 1, 1, 2, 0, 1, 1, 2, 0, 1, 1, 2, 0, 1, 1, 2 }, // Shape 12 + { 0, 1, 2, 2, 0, 1, 2, 2, 0, 1, 2, 2, 0, 1, 2, 2 }, // Shape 13 + { 0, 0, 1, 1, 0, 1, 1, 2, 1, 1, 2, 2, 1, 2, 2, 2 }, // Shape 14 + { 0, 0, 1, 1, 2, 0, 0, 1, 2, 2, 0, 0, 2, 2, 2, 0 }, // Shape 15 + { 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 2, 1, 1, 2, 2 }, // Shape 16 + { 0, 1, 1, 1, 0, 0, 1, 1, 2, 0, 0, 1, 2, 2, 0, 0 }, // Shape 17 + { 0, 0, 0, 0, 1, 1, 2, 2, 1, 1, 2, 2, 1, 1, 2, 2 }, // Shape 18 + { 0, 0, 2, 2, 0, 0, 2, 2, 0, 0, 2, 2, 1, 1, 1, 1 }, // Shape 19 + { 0, 1, 1, 1, 0, 1, 1, 1, 0, 2, 2, 2, 0, 2, 2, 2 }, // Shape 20 + { 0, 0, 0, 1, 0, 0, 0, 1, 2, 2, 2, 1, 2, 2, 2, 1 }, // Shape 21 + { 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 2, 2, 0, 1, 2, 2 }, // Shape 22 + { 0, 0, 0, 0, 1, 1, 0, 0, 2, 2, 1, 0, 2, 2, 1, 0 }, // Shape 23 + { 0, 1, 2, 2, 0, 1, 2, 2, 0, 0, 1, 1, 0, 0, 0, 0 }, // Shape 24 + { 0, 0, 1, 2, 0, 0, 1, 2, 1, 1, 2, 2, 2, 2, 2, 2 }, // Shape 25 + { 0, 1, 1, 0, 1, 2, 2, 1, 1, 2, 2, 1, 0, 1, 1, 0 }, // Shape 26 + { 0, 0, 0, 0, 0, 1, 1, 0, 1, 2, 2, 1, 1, 2, 2, 1 }, // Shape 27 + { 0, 0, 2, 2, 1, 1, 0, 2, 1, 1, 0, 2, 0, 0, 2, 2 }, // Shape 28 + { 0, 1, 1, 0, 0, 1, 1, 0, 2, 0, 0, 2, 2, 2, 2, 2 }, // Shape 29 + { 0, 0, 1, 1, 0, 1, 2, 2, 0, 1, 2, 2, 0, 0, 1, 1 }, // Shape 30 + { 0, 0, 0, 0, 2, 0, 0, 0, 2, 2, 1, 1, 2, 2, 2, 1 }, // Shape 31 + { 0, 0, 0, 0, 0, 0, 0, 2, 1, 1, 2, 2, 1, 2, 2, 2 }, // Shape 32 + { 0, 2, 2, 2, 0, 0, 2, 2, 0, 0, 1, 2, 0, 0, 1, 1 }, // Shape 33 + { 0, 0, 1, 1, 0, 0, 1, 2, 0, 0, 2, 2, 0, 2, 2, 2 }, // Shape 34 + { 0, 1, 2, 0, 0, 1, 2, 0, 0, 1, 2, 0, 0, 1, 2, 0 }, // Shape 35 + { 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 0, 0, 0, 0 }, // Shape 36 + { 0, 1, 2, 0, 1, 2, 0, 1, 2, 0, 1, 2, 0, 1, 2, 0 }, // Shape 37 + { 0, 1, 2, 0, 2, 0, 1, 2, 1, 2, 0, 1, 0, 1, 2, 0 }, // Shape 38 + { 0, 0, 1, 1, 2, 2, 0, 0, 1, 1, 2, 2, 0, 0, 1, 1 }, // Shape 39 + { 0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 0, 0, 0, 0, 1, 1 }, // Shape 40 + { 0, 1, 0, 1, 0, 1, 0, 1, 2, 2, 2, 2, 2, 2, 2, 2 }, // Shape 41 + { 0, 0, 0, 0, 0, 0, 0, 0, 2, 1, 2, 1, 2, 1, 2, 1 }, // Shape 42 + { 0, 0, 2, 2, 1, 1, 2, 2, 0, 0, 2, 2, 1, 1, 2, 2 }, // Shape 43 + { 0, 0, 2, 2, 0, 0, 1, 1, 0, 0, 2, 2, 0, 0, 1, 1 }, // Shape 44 + { 0, 2, 2, 0, 1, 2, 2, 1, 0, 2, 2, 0, 1, 2, 2, 1 }, // Shape 45 + { 0, 1, 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 0, 1, 0, 1 }, // Shape 46 + { 0, 0, 0, 0, 2, 1, 2, 1, 2, 1, 2, 1, 2, 1, 2, 1 }, // Shape 47 + { 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 2, 2, 2, 2 }, // Shape 48 + { 0, 2, 2, 2, 0, 1, 1, 1, 0, 2, 2, 2, 0, 1, 1, 1 }, // Shape 49 + { 0, 0, 0, 2, 1, 1, 1, 2, 0, 0, 0, 2, 1, 1, 1, 2 }, // Shape 50 + { 0, 0, 0, 0, 2, 1, 1, 2, 2, 1, 1, 2, 2, 1, 1, 2 }, // Shape 51 + { 0, 2, 2, 2, 0, 1, 1, 1, 0, 1, 1, 1, 0, 2, 2, 2 }, // Shape 52 + { 0, 0, 0, 2, 1, 1, 1, 2, 1, 1, 1, 2, 0, 0, 0, 2 }, // Shape 53 + { 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0, 2, 2, 2, 2 }, // Shape 54 + { 0, 0, 0, 0, 0, 0, 0, 0, 2, 1, 1, 2, 2, 1, 1, 2 }, // Shape 55 + { 0, 1, 1, 0, 0, 1, 1, 0, 2, 2, 2, 2, 2, 2, 2, 2 }, // Shape 56 + { 0, 0, 2, 2, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 2, 2 }, // Shape 57 + { 0, 0, 2, 2, 1, 1, 2, 2, 1, 1, 2, 2, 0, 0, 2, 2 }, // Shape 58 + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 1, 1, 2 }, // Shape 59 + { 0, 0, 0, 2, 0, 0, 0, 1, 0, 0, 0, 2, 0, 0, 0, 1 }, // Shape 60 + { 0, 2, 2, 2, 1, 2, 2, 2, 0, 2, 2, 2, 1, 2, 2, 2 }, // Shape 61 + { 0, 1, 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2 }, // Shape 62 + { 0, 1, 1, 1, 2, 0, 1, 1, 2, 2, 0, 1, 2, 2, 2, 0 } // Shape 63 + } + }; + + // Partition, Shape, Fixup + const uint8_t g_aFixUp[3][64][3] = + { + { // No fix-ups for 1st subset for BC6H or BC7 + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 } + }, + + { // BC6H/BC7 Partition Set Fixups for 2 Subsets + { 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0,15, 0 },{ 0, 2, 0 },{ 0, 8, 0 },{ 0, 2, 0 }, + { 0, 2, 0 },{ 0, 8, 0 },{ 0, 8, 0 },{ 0,15, 0 }, + { 0, 2, 0 },{ 0, 8, 0 },{ 0, 2, 0 },{ 0, 2, 0 }, + { 0, 8, 0 },{ 0, 8, 0 },{ 0, 2, 0 },{ 0, 2, 0 }, + + // BC7 Partition Set Fixups for 2 Subsets (second-half) + { 0,15, 0 },{ 0,15, 0 },{ 0, 6, 0 },{ 0, 8, 0 }, + { 0, 2, 0 },{ 0, 8, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0, 2, 0 },{ 0, 8, 0 },{ 0, 2, 0 },{ 0, 2, 0 }, + { 0, 2, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0, 6, 0 }, + { 0, 6, 0 },{ 0, 2, 0 },{ 0, 6, 0 },{ 0, 8, 0 }, + { 0,15, 0 },{ 0,15, 0 },{ 0, 2, 0 },{ 0, 2, 0 }, + { 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0,15, 0 },{ 0, 2, 0 },{ 0, 2, 0 },{ 0,15, 0 } + }, + + { // BC7 Partition Set Fixups for 3 Subsets + { 0, 3,15 },{ 0, 3, 8 },{ 0,15, 8 },{ 0,15, 3 }, + { 0, 8,15 },{ 0, 3,15 },{ 0,15, 3 },{ 0,15, 8 }, + { 0, 8,15 },{ 0, 8,15 },{ 0, 6,15 },{ 0, 6,15 }, + { 0, 6,15 },{ 0, 5,15 },{ 0, 3,15 },{ 0, 3, 8 }, + { 0, 3,15 },{ 0, 3, 8 },{ 0, 8,15 },{ 0,15, 3 }, + { 0, 3,15 },{ 0, 3, 8 },{ 0, 6,15 },{ 0,10, 8 }, + { 0, 5, 3 },{ 0, 8,15 },{ 0, 8, 6 },{ 0, 6,10 }, + { 0, 8,15 },{ 0, 5,15 },{ 0,15,10 },{ 0,15, 8 }, + { 0, 8,15 },{ 0,15, 3 },{ 0, 3,15 },{ 0, 5,10 }, + { 0, 6,10 },{ 0,10, 8 },{ 0, 8, 9 },{ 0,15,10 }, + { 0,15, 6 },{ 0, 3,15 },{ 0,15, 8 },{ 0, 5,15 }, + { 0,15, 3 },{ 0,15, 6 },{ 0,15, 6 },{ 0,15, 8 }, + { 0, 3,15 },{ 0,15, 3 },{ 0, 5,15 },{ 0, 5,15 }, + { 0, 5,15 },{ 0, 8,15 },{ 0, 5,15 },{ 0,10,15 }, + { 0, 5,15 },{ 0,10,15 },{ 0, 8,15 },{ 0,13,15 }, + { 0,15, 3 },{ 0,12,15 },{ 0, 3,15 },{ 0, 3, 8 } + } + }; + + const int g_aWeights2[] = { 0, 21, 43, 64 }; + const int g_aWeights3[] = { 0, 9, 18, 27, 37, 46, 55, 64 }; + const int g_aWeights4[] = { 0, 4, 9, 13, 17, 21, 26, 30, 34, 38, 43, 47, 51, 55, 60, 64 }; +} + +namespace DirectX +{ + class LDRColorA + { + public: + uint8_t r, g, b, a; + + LDRColorA() = default; + LDRColorA(uint8_t _r, uint8_t _g, uint8_t _b, uint8_t _a) : r(_r), g(_g), b(_b), a(_a) {} + + const uint8_t& operator [] (_In_range_(0, 3) size_t uElement) const + { + switch (uElement) + { + case 0: return r; + case 1: return g; + case 2: return b; + case 3: return a; + default: assert(false); return r; + } + } + + uint8_t& operator [] (_In_range_(0, 3) size_t uElement) + { + switch (uElement) + { + case 0: return r; + case 1: return g; + case 2: return b; + case 3: return a; + default: assert(false); return r; + } + } + + LDRColorA operator = (_In_ const HDRColorA& c) + { + LDRColorA ret; + HDRColorA tmp(c); + tmp = tmp.Clamp(0.0f, 1.0f) * 255.0f; + ret.r = uint8_t(tmp.r + 0.001f); + ret.g = uint8_t(tmp.g + 0.001f); + ret.b = uint8_t(tmp.b + 0.001f); + ret.a = uint8_t(tmp.a + 0.001f); + return ret; + } + + static void InterpolateRGB(_In_ const LDRColorA& c0, _In_ const LDRColorA& c1, _In_ size_t wc, _In_ _In_range_(2, 4) size_t wcprec, _Out_ LDRColorA& out) + { + const int* aWeights = nullptr; + switch (wcprec) + { + case 2: aWeights = g_aWeights2; assert(wc < 4); _Analysis_assume_(wc < 4); break; + case 3: aWeights = g_aWeights3; assert(wc < 8); _Analysis_assume_(wc < 8); break; + case 4: aWeights = g_aWeights4; assert(wc < 16); _Analysis_assume_(wc < 16); break; + default: assert(false); out.r = out.g = out.b = 0; return; + } + out.r = uint8_t((uint32_t(c0.r) * uint32_t(BC67_WEIGHT_MAX - aWeights[wc]) + uint32_t(c1.r) * uint32_t(aWeights[wc]) + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT); + out.g = uint8_t((uint32_t(c0.g) * uint32_t(BC67_WEIGHT_MAX - aWeights[wc]) + uint32_t(c1.g) * uint32_t(aWeights[wc]) + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT); + out.b = uint8_t((uint32_t(c0.b) * uint32_t(BC67_WEIGHT_MAX - aWeights[wc]) + uint32_t(c1.b) * uint32_t(aWeights[wc]) + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT); + } + + static void InterpolateA(_In_ const LDRColorA& c0, _In_ const LDRColorA& c1, _In_ size_t wa, _In_range_(2, 4) _In_ size_t waprec, _Out_ LDRColorA& out) + { + const int* aWeights = nullptr; + switch (waprec) + { + case 2: aWeights = g_aWeights2; assert(wa < 4); _Analysis_assume_(wa < 4); break; + case 3: aWeights = g_aWeights3; assert(wa < 8); _Analysis_assume_(wa < 8); break; + case 4: aWeights = g_aWeights4; assert(wa < 16); _Analysis_assume_(wa < 16); break; + default: assert(false); out.a = 0; return; + } + out.a = uint8_t((uint32_t(c0.a) * uint32_t(BC67_WEIGHT_MAX - aWeights[wa]) + uint32_t(c1.a) * uint32_t(aWeights[wa]) + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT); + } + + static void Interpolate(_In_ const LDRColorA& c0, _In_ const LDRColorA& c1, _In_ size_t wc, _In_ size_t wa, _In_ _In_range_(2, 4) size_t wcprec, _In_ _In_range_(2, 4) size_t waprec, _Out_ LDRColorA& out) + { + InterpolateRGB(c0, c1, wc, wcprec, out); + InterpolateA(c0, c1, wa, waprec, out); + } + }; + + static_assert(sizeof(LDRColorA) == 4, "Unexpected packing"); + + struct LDREndPntPair + { + LDRColorA A; + LDRColorA B; + }; + + inline HDRColorA::HDRColorA(const LDRColorA& c) + { + r = float(c.r) * (1.0f / 255.0f); + g = float(c.g) * (1.0f / 255.0f); + b = float(c.b) * (1.0f / 255.0f); + a = float(c.a) * (1.0f / 255.0f); + } + + inline HDRColorA& HDRColorA::operator = (const LDRColorA& c) + { + r = (float)c.r; + g = (float)c.g; + b = (float)c.b; + a = (float)c.a; + return *this; + } + + inline LDRColorA HDRColorA::ToLDRColorA() const + { + return LDRColorA((uint8_t)(r + 0.01f), (uint8_t)(g + 0.01f), (uint8_t)(b + 0.01f), (uint8_t)(a + 0.01f)); + } +} + +namespace +{ + class INTColor + { + public: + int r, g, b; + int pad; + + public: + INTColor() = default; + INTColor(int nr, int ng, int nb) { r = nr; g = ng; b = nb; } + INTColor(const INTColor& c) { r = c.r; g = c.g; b = c.b; } + + INTColor operator - (_In_ const INTColor& c) const + { + return INTColor(r - c.r, g - c.g, b - c.b); + } + + INTColor& operator += (_In_ const INTColor& c) + { + r += c.r; + g += c.g; + b += c.b; + return *this; + } + + INTColor& operator -= (_In_ const INTColor& c) + { + r -= c.r; + g -= c.g; + b -= c.b; + return *this; + } + + INTColor& operator &= (_In_ const INTColor& c) + { + r &= c.r; + g &= c.g; + b &= c.b; + return *this; + } + + int& operator [] (_In_ uint8_t i) + { + assert(i < sizeof(INTColor) / sizeof(int)); + _Analysis_assume_(i < sizeof(INTColor) / sizeof(int)); + return ((int*) this)[i]; + } + + void Set(_In_ const HDRColorA& c, _In_ bool bSigned) + { + PackedVector::XMHALF4 aF16; + + XMVECTOR v = XMLoadFloat4((const XMFLOAT4*)& c); + XMStoreHalf4(&aF16, v); + + r = F16ToINT(aF16.x, bSigned); + g = F16ToINT(aF16.y, bSigned); + b = F16ToINT(aF16.z, bSigned); + } + + INTColor& Clamp(_In_ int iMin, _In_ int iMax) + { + r = std::min(iMax, std::max(iMin, r)); + g = std::min(iMax, std::max(iMin, g)); + b = std::min(iMax, std::max(iMin, b)); + return *this; + } + + INTColor& SignExtend(_In_ const LDRColorA& Prec) + { + r = SIGN_EXTEND(r, Prec.r); + g = SIGN_EXTEND(g, Prec.g); + b = SIGN_EXTEND(b, Prec.b); + return *this; + } + + void ToF16(_Out_writes_(3) PackedVector::HALF aF16[3], _In_ bool bSigned) const + { + aF16[0] = INT2F16(r, bSigned); + aF16[1] = INT2F16(g, bSigned); + aF16[2] = INT2F16(b, bSigned); + } + + private: + static int F16ToINT(_In_ const PackedVector::HALF& f, _In_ bool bSigned) + { + uint16_t input = *((const uint16_t*)&f); + int out, s; + if (bSigned) + { + s = input & F16S_MASK; + input &= F16EM_MASK; + if (input > F16MAX) out = F16MAX; + else out = input; + out = s ? -out : out; + } + else + { + if (input & F16S_MASK) out = 0; + else out = input; + } + return out; + } + + static PackedVector::HALF INT2F16(_In_ int input, _In_ bool bSigned) + { + PackedVector::HALF h; + uint16_t out; + if (bSigned) + { + int s = 0; + if (input < 0) + { + s = F16S_MASK; + input = -input; + } + out = uint16_t(s | input); + } + else + { + assert(input >= 0 && input <= F16MAX); + out = (uint16_t)input; + } + + *((uint16_t*)&h) = out; + return h; + } + }; + + static_assert(sizeof(INTColor) == 16, "Unexpected packing"); + + struct INTEndPntPair + { + INTColor A; + INTColor B; + }; + + template< size_t SizeInBytes > + class CBits + { + public: + uint8_t GetBit(_Inout_ size_t& uStartBit) const + { + assert(uStartBit < 128); + _Analysis_assume_(uStartBit < 128); + size_t uIndex = uStartBit >> 3; + uint8_t ret = (m_uBits[uIndex] >> (uStartBit - (uIndex << 3))) & 0x01; + uStartBit++; + return ret; + } + + uint8_t GetBits(_Inout_ size_t& uStartBit, _In_ size_t uNumBits) const + { + if (uNumBits == 0) return 0; + assert(uStartBit + uNumBits <= 128 && uNumBits <= 8); + _Analysis_assume_(uStartBit + uNumBits <= 128 && uNumBits <= 8); + uint8_t ret; + size_t uIndex = uStartBit >> 3; + size_t uBase = uStartBit - (uIndex << 3); + if (uBase + uNumBits > 8) + { + size_t uFirstIndexBits = 8 - uBase; + size_t uNextIndexBits = uNumBits - uFirstIndexBits; + ret = (m_uBits[uIndex] >> uBase) | ((m_uBits[uIndex + 1] & ((1 << uNextIndexBits) - 1)) << uFirstIndexBits); + } + else + { + ret = (m_uBits[uIndex] >> uBase) & ((1 << uNumBits) - 1); + } + assert(ret < (1 << uNumBits)); + uStartBit += uNumBits; + return ret; + } + + void SetBit(_Inout_ size_t& uStartBit, _In_ uint8_t uValue) + { + assert(uStartBit < 128 && uValue < 2); + _Analysis_assume_(uStartBit < 128 && uValue < 2); + size_t uIndex = uStartBit >> 3; + size_t uBase = uStartBit - (uIndex << 3); + m_uBits[uIndex] &= ~(1 << uBase); + m_uBits[uIndex] |= uValue << uBase; + uStartBit++; + } + + void SetBits(_Inout_ size_t& uStartBit, _In_ size_t uNumBits, _In_ uint8_t uValue) + { + if (uNumBits == 0) + return; + assert(uStartBit + uNumBits <= 128 && uNumBits <= 8); + _Analysis_assume_(uStartBit + uNumBits <= 128 && uNumBits <= 8); + assert(uValue < (1 << uNumBits)); + size_t uIndex = uStartBit >> 3; + size_t uBase = uStartBit - (uIndex << 3); + if (uBase + uNumBits > 8) + { + size_t uFirstIndexBits = 8 - uBase; + size_t uNextIndexBits = uNumBits - uFirstIndexBits; + m_uBits[uIndex] &= ~(((1 << uFirstIndexBits) - 1) << uBase); + m_uBits[uIndex] |= uValue << uBase; + m_uBits[uIndex + 1] &= ~((1 << uNextIndexBits) - 1); + m_uBits[uIndex + 1] |= uValue >> uFirstIndexBits; + } + else + { + m_uBits[uIndex] &= ~(((1 << uNumBits) - 1) << uBase); + m_uBits[uIndex] |= uValue << uBase; + } + uStartBit += uNumBits; + } + + private: + uint8_t m_uBits[SizeInBytes]; + }; + + // BC6H compression (16 bits per texel) + class D3DX_BC6H : private CBits< 16 > + { + public: + void Decode(_In_ bool bSigned, _Out_writes_(NUM_PIXELS_PER_BLOCK) HDRColorA* pOut) const; + void Encode(_In_ bool bSigned, _In_reads_(NUM_PIXELS_PER_BLOCK) const HDRColorA* const pIn); + + private: +#pragma warning(push) +#pragma warning(disable : 4480) + enum EField : uint8_t + { + NA, // N/A + M, // Mode + D, // Shape + RW, + RX, + RY, + RZ, + GW, + GX, + GY, + GZ, + BW, + BX, + BY, + BZ, + }; +#pragma warning(pop) + + struct ModeDescriptor + { + EField m_eField; + uint8_t m_uBit; + }; + + struct ModeInfo + { + uint8_t uMode; + uint8_t uPartitions; + bool bTransformed; + uint8_t uIndexPrec; + LDRColorA RGBAPrec[BC6H_MAX_REGIONS][2]; + }; + +#pragma warning(push) +#pragma warning(disable : 4512) + struct EncodeParams + { + float fBestErr; + const bool bSigned; + uint8_t uMode; + uint8_t uShape; + const HDRColorA* const aHDRPixels; + INTEndPntPair aUnqEndPts[BC6H_MAX_SHAPES][BC6H_MAX_REGIONS]; + INTColor aIPixels[NUM_PIXELS_PER_BLOCK]; + + EncodeParams(const HDRColorA* const aOriginal, bool bSignedFormat) : + fBestErr(FLT_MAX), bSigned(bSignedFormat), aHDRPixels(aOriginal) + { + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + aIPixels[i].Set(aOriginal[i], bSigned); + } + } + }; +#pragma warning(pop) + + static int Quantize(_In_ int iValue, _In_ int prec, _In_ bool bSigned); + static int Unquantize(_In_ int comp, _In_ uint8_t uBitsPerComp, _In_ bool bSigned); + static int FinishUnquantize(_In_ int comp, _In_ bool bSigned); + + static bool EndPointsFit(_In_ const EncodeParams* pEP, _In_reads_(BC6H_MAX_REGIONS) const INTEndPntPair aEndPts[]); + + void GeneratePaletteQuantized(_In_ const EncodeParams* pEP, _In_ const INTEndPntPair& endPts, + _Out_writes_(BC6H_MAX_INDICES) INTColor aPalette[]) const; + float MapColorsQuantized(_In_ const EncodeParams* pEP, _In_reads_(np) const INTColor aColors[], _In_ size_t np, _In_ const INTEndPntPair &endPts) const; + float PerturbOne(_In_ const EncodeParams* pEP, _In_reads_(np) const INTColor aColors[], _In_ size_t np, _In_ uint8_t ch, + _In_ const INTEndPntPair& oldEndPts, _Out_ INTEndPntPair& newEndPts, _In_ float fOldErr, _In_ int do_b) const; + void OptimizeOne(_In_ const EncodeParams* pEP, _In_reads_(np) const INTColor aColors[], _In_ size_t np, _In_ float aOrgErr, + _In_ const INTEndPntPair &aOrgEndPts, _Out_ INTEndPntPair &aOptEndPts) const; + void OptimizeEndPoints(_In_ const EncodeParams* pEP, _In_reads_(BC6H_MAX_REGIONS) const float aOrgErr[], + _In_reads_(BC6H_MAX_REGIONS) const INTEndPntPair aOrgEndPts[], + _Out_writes_all_(BC6H_MAX_REGIONS) INTEndPntPair aOptEndPts[]) const; + static void SwapIndices(_In_ const EncodeParams* pEP, _Inout_updates_all_(BC6H_MAX_REGIONS) INTEndPntPair aEndPts[], + _In_reads_(NUM_PIXELS_PER_BLOCK) size_t aIndices[]); + void AssignIndices(_In_ const EncodeParams* pEP, _In_reads_(BC6H_MAX_REGIONS) const INTEndPntPair aEndPts[], + _Out_writes_(NUM_PIXELS_PER_BLOCK) size_t aIndices[], + _Out_writes_(BC6H_MAX_REGIONS) float aTotErr[]) const; + void QuantizeEndPts(_In_ const EncodeParams* pEP, _Out_writes_(BC6H_MAX_REGIONS) INTEndPntPair* qQntEndPts) const; + void EmitBlock(_In_ const EncodeParams* pEP, _In_reads_(BC6H_MAX_REGIONS) const INTEndPntPair aEndPts[], + _In_reads_(NUM_PIXELS_PER_BLOCK) const size_t aIndices[]); + void Refine(_Inout_ EncodeParams* pEP); + + static void GeneratePaletteUnquantized(_In_ const EncodeParams* pEP, _In_ size_t uRegion, _Out_writes_(BC6H_MAX_INDICES) INTColor aPalette[]); + float MapColors(_In_ const EncodeParams* pEP, _In_ size_t uRegion, _In_ size_t np, _In_reads_(np) const size_t* auIndex) const; + float RoughMSE(_Inout_ EncodeParams* pEP) const; + + private: + const static ModeDescriptor ms_aDesc[][82]; + const static ModeInfo ms_aInfo[]; + const static int ms_aModeToInfo[]; + }; + + // BC67 compression (16b bits per texel) + class D3DX_BC7 : private CBits< 16 > + { + public: + void Decode(_Out_writes_(NUM_PIXELS_PER_BLOCK) HDRColorA* pOut) const; + void Encode(DWORD flags, _In_reads_(NUM_PIXELS_PER_BLOCK) const HDRColorA* const pIn); + + private: + struct ModeInfo + { + uint8_t uPartitions; + uint8_t uPartitionBits; + uint8_t uPBits; + uint8_t uRotationBits; + uint8_t uIndexModeBits; + uint8_t uIndexPrec; + uint8_t uIndexPrec2; + LDRColorA RGBAPrec; + LDRColorA RGBAPrecWithP; + }; + +#pragma warning(push) +#pragma warning(disable : 4512) + struct EncodeParams + { + uint8_t uMode; + LDREndPntPair aEndPts[BC7_MAX_SHAPES][BC7_MAX_REGIONS]; + LDRColorA aLDRPixels[NUM_PIXELS_PER_BLOCK]; + const HDRColorA* const aHDRPixels; + + EncodeParams(const HDRColorA* const aOriginal) : aHDRPixels(aOriginal) {} + }; +#pragma warning(pop) + + static uint8_t Quantize(_In_ uint8_t comp, _In_ uint8_t uPrec) + { + assert(0 < uPrec && uPrec <= 8); + uint8_t rnd = (uint8_t)std::min(255, uint16_t(comp) + (1 << (7 - uPrec))); + return rnd >> (8 - uPrec); + } + + static LDRColorA Quantize(_In_ const LDRColorA& c, _In_ const LDRColorA& RGBAPrec) + { + LDRColorA q; + q.r = Quantize(c.r, RGBAPrec.r); + q.g = Quantize(c.g, RGBAPrec.g); + q.b = Quantize(c.b, RGBAPrec.b); + if (RGBAPrec.a) + q.a = Quantize(c.a, RGBAPrec.a); + else + q.a = 255; + return q; + } + + static uint8_t Unquantize(_In_ uint8_t comp, _In_ size_t uPrec) + { + assert(0 < uPrec && uPrec <= 8); + comp = comp << (8 - uPrec); + return comp | (comp >> uPrec); + } + + static LDRColorA Unquantize(_In_ const LDRColorA& c, _In_ const LDRColorA& RGBAPrec) + { + LDRColorA q; + q.r = Unquantize(c.r, RGBAPrec.r); + q.g = Unquantize(c.g, RGBAPrec.g); + q.b = Unquantize(c.b, RGBAPrec.b); + q.a = RGBAPrec.a > 0 ? Unquantize(c.a, RGBAPrec.a) : 255; + return q; + } + + void GeneratePaletteQuantized(_In_ const EncodeParams* pEP, _In_ size_t uIndexMode, _In_ const LDREndPntPair& endpts, + _Out_writes_(BC7_MAX_INDICES) LDRColorA aPalette[]) const; + float PerturbOne(_In_ const EncodeParams* pEP, _In_reads_(np) const LDRColorA colors[], _In_ size_t np, _In_ size_t uIndexMode, + _In_ size_t ch, _In_ const LDREndPntPair &old_endpts, + _Out_ LDREndPntPair &new_endpts, _In_ float old_err, _In_ uint8_t do_b) const; + void Exhaustive(_In_ const EncodeParams* pEP, _In_reads_(np) const LDRColorA aColors[], _In_ size_t np, _In_ size_t uIndexMode, + _In_ size_t ch, _Inout_ float& fOrgErr, _Inout_ LDREndPntPair& optEndPt) const; + void OptimizeOne(_In_ const EncodeParams* pEP, _In_reads_(np) const LDRColorA colors[], _In_ size_t np, _In_ size_t uIndexMode, + _In_ float orig_err, _In_ const LDREndPntPair &orig_endpts, _Out_ LDREndPntPair &opt_endpts) const; + void OptimizeEndPoints(_In_ const EncodeParams* pEP, _In_ size_t uShape, _In_ size_t uIndexMode, + _In_reads_(BC7_MAX_REGIONS) const float orig_err[], + _In_reads_(BC7_MAX_REGIONS) const LDREndPntPair orig_endpts[], + _Out_writes_(BC7_MAX_REGIONS) LDREndPntPair opt_endpts[]) const; + void AssignIndices(_In_ const EncodeParams* pEP, _In_ size_t uShape, _In_ size_t uIndexMode, + _In_reads_(BC7_MAX_REGIONS) LDREndPntPair endpts[], + _Out_writes_(NUM_PIXELS_PER_BLOCK) size_t aIndices[], _Out_writes_(NUM_PIXELS_PER_BLOCK) size_t aIndices2[], + _Out_writes_(BC7_MAX_REGIONS) float afTotErr[]) const; + void EmitBlock(_In_ const EncodeParams* pEP, _In_ size_t uShape, _In_ size_t uRotation, _In_ size_t uIndexMode, + _In_reads_(BC7_MAX_REGIONS) const LDREndPntPair aEndPts[], + _In_reads_(NUM_PIXELS_PER_BLOCK) const size_t aIndex[], + _In_reads_(NUM_PIXELS_PER_BLOCK) const size_t aIndex2[]); + float Refine(_In_ const EncodeParams* pEP, _In_ size_t uShape, _In_ size_t uRotation, _In_ size_t uIndexMode); + + float MapColors(_In_ const EncodeParams* pEP, _In_reads_(np) const LDRColorA aColors[], _In_ size_t np, _In_ size_t uIndexMode, + _In_ const LDREndPntPair& endPts, _In_ float fMinErr) const; + static float RoughMSE(_Inout_ EncodeParams* pEP, _In_ size_t uShape, _In_ size_t uIndexMode); + + private: + const static ModeInfo ms_aInfo[]; + }; +} + +// BC6H Compression +const D3DX_BC6H::ModeDescriptor D3DX_BC6H::ms_aDesc[14][82] = +{ + { // Mode 1 (0x00) - 10 5 5 5 + { M, 0}, { M, 1}, {GY, 4}, {BY, 4}, {BZ, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, + {GZ, 4}, {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, + {BZ, 0}, {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, + {BZ, 1}, {BY, 0}, {BY, 1}, {BY, 2}, {BY, 3}, {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, + {BZ, 2}, {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4}, {BZ, 3}, { D, 0}, { D, 1}, { D, 2}, + { D, 3}, { D, 4}, + }, + + { // Mode 2 (0x01) - 7 6 6 6 + { M, 0}, { M, 1}, {GY, 5}, {GZ, 4}, {GZ, 5}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {BZ, 0}, {BZ, 1}, {BY, 4}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {BY, 5}, {BZ, 2}, {GY, 4}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BZ, 3}, {BZ, 5}, {BZ, 4}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, + {RX, 5}, {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, + {GX, 5}, {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, + {BX, 5}, {BY, 0}, {BY, 1}, {BY, 2}, {BY, 3}, {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, + {RY, 5}, {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4}, {RZ, 5}, { D, 0}, { D, 1}, { D, 2}, + { D, 3}, { D, 4}, + }, + + { // Mode 3 (0x02) - 11 5 4 4 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, + {RW,10}, {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GW,10}, + {BZ, 0}, {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BW,10}, + {BZ, 1}, {BY, 0}, {BY, 1}, {BY, 2}, {BY, 3}, {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, + {BZ, 2}, {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4}, {BZ, 3}, { D, 0}, { D, 1}, { D, 2}, + { D, 3}, { D, 4}, + }, + + { // Mode 4 (0x06) - 11 4 5 4 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RW,10}, + {GZ, 4}, {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, + {GW,10}, {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BW,10}, + {BZ, 1}, {BY, 0}, {BY, 1}, {BY, 2}, {BY, 3}, {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {BZ, 0}, + {BZ, 2}, {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {GY, 4}, {BZ, 3}, { D, 0}, { D, 1}, { D, 2}, + { D, 3}, { D, 4}, + }, + + { // Mode 5 (0x0a) - 11 4 4 5 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RW,10}, + {BY, 4}, {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GW,10}, + {BZ, 0}, {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, + {BW,10}, {BY, 0}, {BY, 1}, {BY, 2}, {BY, 3}, {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {BZ, 1}, + {BZ, 2}, {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {BZ, 4}, {BZ, 3}, { D, 0}, { D, 1}, { D, 2}, + { D, 3}, { D, 4}, + }, + + { // Mode 6 (0x0e) - 9 5 5 5 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {BY, 4}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GY, 4}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BZ, 4}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, + {GZ, 4}, {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, + {BZ, 0}, {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, + {BZ, 1}, {BY, 0}, {BY, 1}, {BY, 2}, {BY, 3}, {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, + {BZ, 2}, {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4}, {BZ, 3}, { D, 0}, { D, 1}, { D, 2}, + { D, 3}, { D, 4}, + }, + + { // Mode 7 (0x12) - 8 6 5 5 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {GZ, 4}, {BY, 4}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {BZ, 2}, {GY, 4}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {BZ, 3}, {BZ, 4}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, + {RX, 5}, {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, + {BZ, 0}, {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, + {BZ, 1}, {BY, 0}, {BY, 1}, {BY, 2}, {BY, 3}, {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, + {RY, 5}, {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4}, {RZ, 5}, { D, 0}, { D, 1}, { D, 2}, + { D, 3}, { D, 4}, + }, + + { // Mode 8 (0x16) - 8 5 6 5 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {BZ, 0}, {BY, 4}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {GY, 5}, {GY, 4}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {GZ, 5}, {BZ, 4}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, + {GZ, 4}, {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, + {GX, 5}, {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, + {BZ, 1}, {BY, 0}, {BY, 1}, {BY, 2}, {BY, 3}, {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, + {BZ, 2}, {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4}, {BZ, 3}, { D, 0}, { D, 1}, { D, 2}, + { D, 3}, { D, 4}, + }, + + { // Mode 9 (0x1a) - 8 5 5 6 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {BZ, 1}, {BY, 4}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {BY, 5}, {GY, 4}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {BZ, 5}, {BZ, 4}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, + {GZ, 4}, {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, + {BZ, 0}, {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, + {BX, 5}, {BY, 0}, {BY, 1}, {BY, 2}, {BY, 3}, {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, + {BZ, 2}, {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4}, {BZ, 3}, { D, 0}, { D, 1}, { D, 2}, + { D, 3}, { D, 4}, + }, + + { // Mode 10 (0x1e) - 6 6 6 6 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {GZ, 4}, {BZ, 0}, {BZ, 1}, {BY, 4}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GY, 5}, {BY, 5}, {BZ, 2}, {GY, 4}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {GZ, 5}, {BZ, 3}, {BZ, 5}, {BZ, 4}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, + {RX, 5}, {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, + {GX, 5}, {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, + {BX, 5}, {BY, 0}, {BY, 1}, {BY, 2}, {BY, 3}, {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, + {RY, 5}, {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4}, {RZ, 5}, { D, 0}, { D, 1}, { D, 2}, + { D, 3}, { D, 4}, + }, + + { // Mode 11 (0x03) - 10 10 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, + {RX, 5}, {RX, 6}, {RX, 7}, {RX, 8}, {RX, 9}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, + {GX, 5}, {GX, 6}, {GX, 7}, {GX, 8}, {GX, 9}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, + {BX, 5}, {BX, 6}, {BX, 7}, {BX, 8}, {BX, 9}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, + {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, + {NA, 0}, {NA, 0}, + }, + + { // Mode 12 (0x07) - 11 9 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, + {RX, 5}, {RX, 6}, {RX, 7}, {RX, 8}, {RW,10}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, + {GX, 5}, {GX, 6}, {GX, 7}, {GX, 8}, {GW,10}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, + {BX, 5}, {BX, 6}, {BX, 7}, {BX, 8}, {BW,10}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, + {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, + {NA, 0}, {NA, 0}, + }, + + { // Mode 13 (0x0b) - 12 8 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, + {RX, 5}, {RX, 6}, {RX, 7}, {RW,11}, {RW,10}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, + {GX, 5}, {GX, 6}, {GX, 7}, {GW,11}, {GW,10}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, + {BX, 5}, {BX, 6}, {BX, 7}, {BW,11}, {BW,10}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, + {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, + {NA, 0}, {NA, 0}, + }, + + { // Mode 14 (0x0f) - 16 4 + { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4}, {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, + {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9}, {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, + {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9}, {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, + {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9}, {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RW,15}, + {RW,14}, {RW,13}, {RW,12}, {RW,11}, {RW,10}, {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GW,15}, + {GW,14}, {GW,13}, {GW,12}, {GW,11}, {GW,10}, {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BW,15}, + {BW,14}, {BW,13}, {BW,12}, {BW,11}, {BW,10}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, + {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, {NA, 0}, + {NA, 0}, {NA, 0}, + }, +}; + +// Mode, Partitions, Transformed, IndexPrec, RGBAPrec +const D3DX_BC6H::ModeInfo D3DX_BC6H::ms_aInfo[] = +{ + {0x00, 1, true, 3, { { LDRColorA(10,10,10,0), LDRColorA( 5, 5, 5,0) }, { LDRColorA(5,5,5,0), LDRColorA(5,5,5,0) } } }, // Mode 1 + {0x01, 1, true, 3, { { LDRColorA( 7, 7, 7,0), LDRColorA( 6, 6, 6,0) }, { LDRColorA(6,6,6,0), LDRColorA(6,6,6,0) } } }, // Mode 2 + {0x02, 1, true, 3, { { LDRColorA(11,11,11,0), LDRColorA( 5, 4, 4,0) }, { LDRColorA(5,4,4,0), LDRColorA(5,4,4,0) } } }, // Mode 3 + {0x06, 1, true, 3, { { LDRColorA(11,11,11,0), LDRColorA( 4, 5, 4,0) }, { LDRColorA(4,5,4,0), LDRColorA(4,5,4,0) } } }, // Mode 4 + {0x0a, 1, true, 3, { { LDRColorA(11,11,11,0), LDRColorA( 4, 4, 5,0) }, { LDRColorA(4,4,5,0), LDRColorA(4,4,5,0) } } }, // Mode 5 + {0x0e, 1, true, 3, { { LDRColorA( 9, 9, 9,0), LDRColorA( 5, 5, 5,0) }, { LDRColorA(5,5,5,0), LDRColorA(5,5,5,0) } } }, // Mode 6 + {0x12, 1, true, 3, { { LDRColorA( 8, 8, 8,0), LDRColorA( 6, 5, 5,0) }, { LDRColorA(6,5,5,0), LDRColorA(6,5,5,0) } } }, // Mode 7 + {0x16, 1, true, 3, { { LDRColorA( 8, 8, 8,0), LDRColorA( 5, 6, 5,0) }, { LDRColorA(5,6,5,0), LDRColorA(5,6,5,0) } } }, // Mode 8 + {0x1a, 1, true, 3, { { LDRColorA( 8, 8, 8,0), LDRColorA( 5, 5, 6,0) }, { LDRColorA(5,5,6,0), LDRColorA(5,5,6,0) } } }, // Mode 9 + {0x1e, 1, false, 3, { { LDRColorA( 6, 6, 6,0), LDRColorA( 6, 6, 6,0) }, { LDRColorA(6,6,6,0), LDRColorA(6,6,6,0) } } }, // Mode 10 + {0x03, 0, false, 4, { { LDRColorA(10,10,10,0), LDRColorA(10,10,10,0) }, { LDRColorA(0,0,0,0), LDRColorA(0,0,0,0) } } }, // Mode 11 + {0x07, 0, true, 4, { { LDRColorA(11,11,11,0), LDRColorA( 9, 9, 9,0) }, { LDRColorA(0,0,0,0), LDRColorA(0,0,0,0) } } }, // Mode 12 + {0x0b, 0, true, 4, { { LDRColorA(12,12,12,0), LDRColorA( 8, 8, 8,0) }, { LDRColorA(0,0,0,0), LDRColorA(0,0,0,0) } } }, // Mode 13 + {0x0f, 0, true, 4, { { LDRColorA(16,16,16,0), LDRColorA( 4, 4, 4,0) }, { LDRColorA(0,0,0,0), LDRColorA(0,0,0,0) } } }, // Mode 14 +}; + +const int D3DX_BC6H::ms_aModeToInfo[] = +{ + 0, // Mode 1 - 0x00 + 1, // Mode 2 - 0x01 + 2, // Mode 3 - 0x02 + 10, // Mode 11 - 0x03 + -1, // Invalid - 0x04 + -1, // Invalid - 0x05 + 3, // Mode 4 - 0x06 + 11, // Mode 12 - 0x07 + -1, // Invalid - 0x08 + -1, // Invalid - 0x09 + 4, // Mode 5 - 0x0a + 12, // Mode 13 - 0x0b + -1, // Invalid - 0x0c + -1, // Invalid - 0x0d + 5, // Mode 6 - 0x0e + 13, // Mode 14 - 0x0f + -1, // Invalid - 0x10 + -1, // Invalid - 0x11 + 6, // Mode 7 - 0x12 + -1, // Reserved - 0x13 + -1, // Invalid - 0x14 + -1, // Invalid - 0x15 + 7, // Mode 8 - 0x16 + -1, // Reserved - 0x17 + -1, // Invalid - 0x18 + -1, // Invalid - 0x19 + 8, // Mode 9 - 0x1a + -1, // Reserved - 0x1b + -1, // Invalid - 0x1c + -1, // Invalid - 0x1d + 9, // Mode 10 - 0x1e + -1, // Resreved - 0x1f +}; + +// BC7 compression: uPartitions, uPartitionBits, uPBits, uRotationBits, uIndexModeBits, uIndexPrec, uIndexPrec2, RGBAPrec, RGBAPrecWithP +const D3DX_BC7::ModeInfo D3DX_BC7::ms_aInfo[] = +{ + {2, 4, 6, 0, 0, 3, 0, LDRColorA(4,4,4,0), LDRColorA(5,5,5,0)}, + // Mode 0: Color only, 3 Subsets, RGBP 4441 (unique P-bit), 3-bit indecies, 16 partitions + {1, 6, 2, 0, 0, 3, 0, LDRColorA(6,6,6,0), LDRColorA(7,7,7,0)}, + // Mode 1: Color only, 2 Subsets, RGBP 6661 (shared P-bit), 3-bit indecies, 64 partitions + {2, 6, 0, 0, 0, 2, 0, LDRColorA(5,5,5,0), LDRColorA(5,5,5,0)}, + // Mode 2: Color only, 3 Subsets, RGB 555, 2-bit indecies, 64 partitions + {1, 6, 4, 0, 0, 2, 0, LDRColorA(7,7,7,0), LDRColorA(8,8,8,0)}, + // Mode 3: Color only, 2 Subsets, RGBP 7771 (unique P-bit), 2-bits indecies, 64 partitions + {0, 0, 0, 2, 1, 2, 3, LDRColorA(5,5,5,6), LDRColorA(5,5,5,6)}, + // Mode 4: Color w/ Separate Alpha, 1 Subset, RGB 555, A6, 16x2/16x3-bit indices, 2-bit rotation, 1-bit index selector + {0, 0, 0, 2, 0, 2, 2, LDRColorA(7,7,7,8), LDRColorA(7,7,7,8)}, + // Mode 5: Color w/ Separate Alpha, 1 Subset, RGB 777, A8, 16x2/16x2-bit indices, 2-bit rotation + {0, 0, 2, 0, 0, 4, 0, LDRColorA(7,7,7,7), LDRColorA(8,8,8,8)}, + // Mode 6: Color+Alpha, 1 Subset, RGBAP 77771 (unique P-bit), 16x4-bit indecies + {1, 6, 4, 0, 0, 2, 0, LDRColorA(5,5,5,5), LDRColorA(6,6,6,6)} + // Mode 7: Color+Alpha, 2 Subsets, RGBAP 55551 (unique P-bit), 2-bit indices, 64 partitions +}; + + +namespace +{ + //------------------------------------------------------------------------------------- + // Helper functions + //------------------------------------------------------------------------------------- + inline bool IsFixUpOffset(_In_range_(0, 2) size_t uPartitions, _In_range_(0, 63) size_t uShape, _In_range_(0, 15) size_t uOffset) + { + assert(uPartitions < 3 && uShape < 64 && uOffset < 16); + _Analysis_assume_(uPartitions < 3 && uShape < 64 && uOffset < 16); + for (size_t p = 0; p <= uPartitions; p++) + { + if (uOffset == g_aFixUp[uPartitions][uShape][p]) + { + return true; + } + } + return false; + } + + inline void TransformForward(_Inout_updates_all_(BC6H_MAX_REGIONS) INTEndPntPair aEndPts[]) + { + aEndPts[0].B -= aEndPts[0].A; + aEndPts[1].A -= aEndPts[0].A; + aEndPts[1].B -= aEndPts[0].A; + } + + inline void TransformInverse(_Inout_updates_all_(BC6H_MAX_REGIONS) INTEndPntPair aEndPts[], _In_ const LDRColorA& Prec, _In_ bool bSigned) + { + INTColor WrapMask((1 << Prec.r) - 1, (1 << Prec.g) - 1, (1 << Prec.b) - 1); + aEndPts[0].B += aEndPts[0].A; aEndPts[0].B &= WrapMask; + aEndPts[1].A += aEndPts[0].A; aEndPts[1].A &= WrapMask; + aEndPts[1].B += aEndPts[0].A; aEndPts[1].B &= WrapMask; + if (bSigned) + { + aEndPts[0].B.SignExtend(Prec); + aEndPts[1].A.SignExtend(Prec); + aEndPts[1].B.SignExtend(Prec); + } + } + + inline float Norm(_In_ const INTColor& a, _In_ const INTColor& b) + { + float dr = float(a.r) - float(b.r); + float dg = float(a.g) - float(b.g); + float db = float(a.b) - float(b.b); + return dr * dr + dg * dg + db * db; + } + + // return # of bits needed to store n. handle signed or unsigned cases properly + inline int NBits(_In_ int n, _In_ bool bIsSigned) + { + int nb; + if (n == 0) + { + return 0; // no bits needed for 0, signed or not + } + else if (n > 0) + { + for (nb = 0; n; ++nb, n >>= 1); + return nb + (bIsSigned ? 1 : 0); + } + else + { + assert(bIsSigned); + for (nb = 0; n < -1; ++nb, n >>= 1); + return nb + 1; + } + } + + + //------------------------------------------------------------------------------------- + float OptimizeRGB( + _In_reads_(NUM_PIXELS_PER_BLOCK) const HDRColorA* const pPoints, + _Out_ HDRColorA* pX, + _Out_ HDRColorA* pY, + _In_range_(3, 4) size_t cSteps, + size_t cPixels, + _In_reads_(cPixels) const size_t* pIndex) + { + float fError = FLT_MAX; + const float *pC = (3 == cSteps) ? pC3 : pC4; + const float *pD = (3 == cSteps) ? pD3 : pD4; + + // Find Min and Max points, as starting point + HDRColorA X(1.0f, 1.0f, 1.0f, 0.0f); + HDRColorA Y(0.0f, 0.0f, 0.0f, 0.0f); + + for (size_t iPoint = 0; iPoint < cPixels; iPoint++) + { + if (pPoints[pIndex[iPoint]].r < X.r) X.r = pPoints[pIndex[iPoint]].r; + if (pPoints[pIndex[iPoint]].g < X.g) X.g = pPoints[pIndex[iPoint]].g; + if (pPoints[pIndex[iPoint]].b < X.b) X.b = pPoints[pIndex[iPoint]].b; + if (pPoints[pIndex[iPoint]].r > Y.r) Y.r = pPoints[pIndex[iPoint]].r; + if (pPoints[pIndex[iPoint]].g > Y.g) Y.g = pPoints[pIndex[iPoint]].g; + if (pPoints[pIndex[iPoint]].b > Y.b) Y.b = pPoints[pIndex[iPoint]].b; + } + + // Diagonal axis + HDRColorA AB; + AB.r = Y.r - X.r; + AB.g = Y.g - X.g; + AB.b = Y.b - X.b; + + float fAB = AB.r * AB.r + AB.g * AB.g + AB.b * AB.b; + + // Single color block.. no need to root-find + if (fAB < FLT_MIN) + { + pX->r = X.r; pX->g = X.g; pX->b = X.b; + pY->r = Y.r; pY->g = Y.g; pY->b = Y.b; + return 0.0f; + } + + // Try all four axis directions, to determine which diagonal best fits data + float fABInv = 1.0f / fAB; + + HDRColorA Dir; + Dir.r = AB.r * fABInv; + Dir.g = AB.g * fABInv; + Dir.b = AB.b * fABInv; + + HDRColorA Mid; + Mid.r = (X.r + Y.r) * 0.5f; + Mid.g = (X.g + Y.g) * 0.5f; + Mid.b = (X.b + Y.b) * 0.5f; + + float fDir[4]; + fDir[0] = fDir[1] = fDir[2] = fDir[3] = 0.0f; + + for (size_t iPoint = 0; iPoint < cPixels; iPoint++) + { + HDRColorA Pt; + Pt.r = (pPoints[pIndex[iPoint]].r - Mid.r) * Dir.r; + Pt.g = (pPoints[pIndex[iPoint]].g - Mid.g) * Dir.g; + Pt.b = (pPoints[pIndex[iPoint]].b - Mid.b) * Dir.b; + + float f; + f = Pt.r + Pt.g + Pt.b; fDir[0] += f * f; + f = Pt.r + Pt.g - Pt.b; fDir[1] += f * f; + f = Pt.r - Pt.g + Pt.b; fDir[2] += f * f; + f = Pt.r - Pt.g - Pt.b; fDir[3] += f * f; + } + + float fDirMax = fDir[0]; + size_t iDirMax = 0; + + for (size_t iDir = 1; iDir < 4; iDir++) + { + if (fDir[iDir] > fDirMax) + { + fDirMax = fDir[iDir]; + iDirMax = iDir; + } + } + + if (iDirMax & 2) std::swap(X.g, Y.g); + if (iDirMax & 1) std::swap(X.b, Y.b); + + // Two color block.. no need to root-find + if (fAB < 1.0f / 4096.0f) + { + pX->r = X.r; pX->g = X.g; pX->b = X.b; + pY->r = Y.r; pY->g = Y.g; pY->b = Y.b; + return 0.0f; + } + + // Use Newton's Method to find local minima of sum-of-squares error. + float fSteps = (float)(cSteps - 1); + + for (size_t iIteration = 0; iIteration < 8; iIteration++) + { + // Calculate new steps + HDRColorA pSteps[4] = {}; + + for (size_t iStep = 0; iStep < cSteps; iStep++) + { + pSteps[iStep].r = X.r * pC[iStep] + Y.r * pD[iStep]; + pSteps[iStep].g = X.g * pC[iStep] + Y.g * pD[iStep]; + pSteps[iStep].b = X.b * pC[iStep] + Y.b * pD[iStep]; + } + + // Calculate color direction + Dir.r = Y.r - X.r; + Dir.g = Y.g - X.g; + Dir.b = Y.b - X.b; + + float fLen = (Dir.r * Dir.r + Dir.g * Dir.g + Dir.b * Dir.b); + + if (fLen < (1.0f / 4096.0f)) + break; + + float fScale = fSteps / fLen; + + Dir.r *= fScale; + Dir.g *= fScale; + Dir.b *= fScale; + + // Evaluate function, and derivatives + float d2X = 0.0f, d2Y = 0.0f; + HDRColorA dX(0.0f, 0.0f, 0.0f, 0.0f), dY(0.0f, 0.0f, 0.0f, 0.0f); + + for (size_t iPoint = 0; iPoint < cPixels; iPoint++) + { + float fDot = (pPoints[pIndex[iPoint]].r - X.r) * Dir.r + + (pPoints[pIndex[iPoint]].g - X.g) * Dir.g + + (pPoints[pIndex[iPoint]].b - X.b) * Dir.b; + + size_t iStep; + if (fDot <= 0.0f) + iStep = 0; + if (fDot >= fSteps) + iStep = cSteps - 1; + else + iStep = size_t(fDot + 0.5f); + + HDRColorA Diff; + Diff.r = pSteps[iStep].r - pPoints[pIndex[iPoint]].r; + Diff.g = pSteps[iStep].g - pPoints[pIndex[iPoint]].g; + Diff.b = pSteps[iStep].b - pPoints[pIndex[iPoint]].b; + + float fC = pC[iStep] * (1.0f / 8.0f); + float fD = pD[iStep] * (1.0f / 8.0f); + + d2X += fC * pC[iStep]; + dX.r += fC * Diff.r; + dX.g += fC * Diff.g; + dX.b += fC * Diff.b; + + d2Y += fD * pD[iStep]; + dY.r += fD * Diff.r; + dY.g += fD * Diff.g; + dY.b += fD * Diff.b; + } + + // Move endpoints + if (d2X > 0.0f) + { + float f = -1.0f / d2X; + + X.r += dX.r * f; + X.g += dX.g * f; + X.b += dX.b * f; + } + + if (d2Y > 0.0f) + { + float f = -1.0f / d2Y; + + Y.r += dY.r * f; + Y.g += dY.g * f; + Y.b += dY.b * f; + } + + if ((dX.r * dX.r < fEpsilon) && (dX.g * dX.g < fEpsilon) && (dX.b * dX.b < fEpsilon) && + (dY.r * dY.r < fEpsilon) && (dY.g * dY.g < fEpsilon) && (dY.b * dY.b < fEpsilon)) + { + break; + } + } + + pX->r = X.r; pX->g = X.g; pX->b = X.b; + pY->r = Y.r; pY->g = Y.g; pY->b = Y.b; + return fError; + } + + + //------------------------------------------------------------------------------------- + float OptimizeRGBA( + _In_reads_(NUM_PIXELS_PER_BLOCK) const HDRColorA* const pPoints, + _Out_ HDRColorA* pX, + _Out_ HDRColorA* pY, + _In_range_(3, 4) size_t cSteps, + size_t cPixels, + _In_reads_(cPixels) const size_t* pIndex) + { + float fError = FLT_MAX; + const float *pC = (3 == cSteps) ? pC3 : pC4; + const float *pD = (3 == cSteps) ? pD3 : pD4; + + // Find Min and Max points, as starting point + HDRColorA X(1.0f, 1.0f, 1.0f, 1.0f); + HDRColorA Y(0.0f, 0.0f, 0.0f, 0.0f); + + for (size_t iPoint = 0; iPoint < cPixels; iPoint++) + { + if (pPoints[pIndex[iPoint]].r < X.r) X.r = pPoints[pIndex[iPoint]].r; + if (pPoints[pIndex[iPoint]].g < X.g) X.g = pPoints[pIndex[iPoint]].g; + if (pPoints[pIndex[iPoint]].b < X.b) X.b = pPoints[pIndex[iPoint]].b; + if (pPoints[pIndex[iPoint]].a < X.a) X.a = pPoints[pIndex[iPoint]].a; + if (pPoints[pIndex[iPoint]].r > Y.r) Y.r = pPoints[pIndex[iPoint]].r; + if (pPoints[pIndex[iPoint]].g > Y.g) Y.g = pPoints[pIndex[iPoint]].g; + if (pPoints[pIndex[iPoint]].b > Y.b) Y.b = pPoints[pIndex[iPoint]].b; + if (pPoints[pIndex[iPoint]].a > Y.a) Y.a = pPoints[pIndex[iPoint]].a; + } + + // Diagonal axis + HDRColorA AB = Y - X; + float fAB = AB * AB; + + // Single color block.. no need to root-find + if (fAB < FLT_MIN) + { + *pX = X; + *pY = Y; + return 0.0f; + } + + // Try all four axis directions, to determine which diagonal best fits data + float fABInv = 1.0f / fAB; + HDRColorA Dir = AB * fABInv; + HDRColorA Mid = (X + Y) * 0.5f; + + float fDir[8]; + fDir[0] = fDir[1] = fDir[2] = fDir[3] = fDir[4] = fDir[5] = fDir[6] = fDir[7] = 0.0f; + + for (size_t iPoint = 0; iPoint < cPixels; iPoint++) + { + HDRColorA Pt; + Pt.r = (pPoints[pIndex[iPoint]].r - Mid.r) * Dir.r; + Pt.g = (pPoints[pIndex[iPoint]].g - Mid.g) * Dir.g; + Pt.b = (pPoints[pIndex[iPoint]].b - Mid.b) * Dir.b; + Pt.a = (pPoints[pIndex[iPoint]].a - Mid.a) * Dir.a; + + float f; + f = Pt.r + Pt.g + Pt.b + Pt.a; fDir[0] += f * f; + f = Pt.r + Pt.g + Pt.b - Pt.a; fDir[1] += f * f; + f = Pt.r + Pt.g - Pt.b + Pt.a; fDir[2] += f * f; + f = Pt.r + Pt.g - Pt.b - Pt.a; fDir[3] += f * f; + f = Pt.r - Pt.g + Pt.b + Pt.a; fDir[4] += f * f; + f = Pt.r - Pt.g + Pt.b - Pt.a; fDir[5] += f * f; + f = Pt.r - Pt.g - Pt.b + Pt.a; fDir[6] += f * f; + f = Pt.r - Pt.g - Pt.b - Pt.a; fDir[7] += f * f; + } + + float fDirMax = fDir[0]; + size_t iDirMax = 0; + + for (size_t iDir = 1; iDir < 8; iDir++) + { + if (fDir[iDir] > fDirMax) + { + fDirMax = fDir[iDir]; + iDirMax = iDir; + } + } + + if (iDirMax & 4) std::swap(X.g, Y.g); + if (iDirMax & 2) std::swap(X.b, Y.b); + if (iDirMax & 1) std::swap(X.a, Y.a); + + // Two color block.. no need to root-find + if (fAB < 1.0f / 4096.0f) + { + *pX = X; + *pY = Y; + return 0.0f; + } + + // Use Newton's Method to find local minima of sum-of-squares error. + float fSteps = (float)(cSteps - 1); + + for (size_t iIteration = 0; iIteration < 8 && fError > 0.0f; iIteration++) + { + // Calculate new steps + HDRColorA pSteps[BC7_MAX_INDICES]; + + LDRColorA lX, lY; + lX = (X * 255.0f).ToLDRColorA(); + lY = (Y * 255.0f).ToLDRColorA(); + + for (size_t iStep = 0; iStep < cSteps; iStep++) + { + pSteps[iStep] = X * pC[iStep] + Y * pD[iStep]; + //LDRColorA::Interpolate(lX, lY, i, i, wcprec, waprec, aSteps[i]); + } + + // Calculate color direction + Dir = Y - X; + float fLen = Dir * Dir; + if (fLen < (1.0f / 4096.0f)) + break; + + float fScale = fSteps / fLen; + Dir *= fScale; + + // Evaluate function, and derivatives + float d2X = 0.0f, d2Y = 0.0f; + HDRColorA dX(0.0f, 0.0f, 0.0f, 0.0f), dY(0.0f, 0.0f, 0.0f, 0.0f); + + for (size_t iPoint = 0; iPoint < cPixels; ++iPoint) + { + float fDot = (pPoints[pIndex[iPoint]] - X) * Dir; + size_t iStep; + if (fDot <= 0.0f) + iStep = 0; + if (fDot >= fSteps) + iStep = cSteps - 1; + else + iStep = size_t(fDot + 0.5f); + + HDRColorA Diff = pSteps[iStep] - pPoints[pIndex[iPoint]]; + float fC = pC[iStep] * (1.0f / 8.0f); + float fD = pD[iStep] * (1.0f / 8.0f); + + d2X += fC * pC[iStep]; + dX += Diff * fC; + + d2Y += fD * pD[iStep]; + dY += Diff * fD; + } + + // Move endpoints + if (d2X > 0.0f) + { + float f = -1.0f / d2X; + X += dX * f; + } + + if (d2Y > 0.0f) + { + float f = -1.0f / d2Y; + Y += dY * f; + } + + if ((dX * dX < fEpsilon) && (dY * dY < fEpsilon)) + break; + } + + *pX = X; + *pY = Y; + return fError; + } + + + //------------------------------------------------------------------------------------- + float ComputeError( + _Inout_ const LDRColorA& pixel, + _In_reads_(1 << uIndexPrec) const LDRColorA aPalette[], + uint8_t uIndexPrec, + uint8_t uIndexPrec2, + _Out_opt_ size_t* pBestIndex = nullptr, + _Out_opt_ size_t* pBestIndex2 = nullptr) + { + const size_t uNumIndices = size_t(1) << uIndexPrec; + const size_t uNumIndices2 = size_t(1) << uIndexPrec2; + float fTotalErr = 0; + float fBestErr = FLT_MAX; + + if (pBestIndex) + *pBestIndex = 0; + if (pBestIndex2) + *pBestIndex2 = 0; + + XMVECTOR vpixel = XMLoadUByte4(reinterpret_cast(&pixel)); + + if (uIndexPrec2 == 0) + { + for (size_t i = 0; i < uNumIndices && fBestErr > 0; i++) + { + XMVECTOR tpixel = XMLoadUByte4(reinterpret_cast(&aPalette[i])); + // Compute ErrorMetric + tpixel = XMVectorSubtract(vpixel, tpixel); + float fErr = XMVectorGetX(XMVector4Dot(tpixel, tpixel)); + if (fErr > fBestErr) // error increased, so we're done searching + break; + if (fErr < fBestErr) + { + fBestErr = fErr; + if (pBestIndex) + *pBestIndex = i; + } + } + fTotalErr += fBestErr; + } + else + { + for (size_t i = 0; i < uNumIndices && fBestErr > 0; i++) + { + XMVECTOR tpixel = XMLoadUByte4(reinterpret_cast(&aPalette[i])); + // Compute ErrorMetricRGB + tpixel = XMVectorSubtract(vpixel, tpixel); + float fErr = XMVectorGetX(XMVector3Dot(tpixel, tpixel)); + if (fErr > fBestErr) // error increased, so we're done searching + break; + if (fErr < fBestErr) + { + fBestErr = fErr; + if (pBestIndex) + *pBestIndex = i; + } + } + fTotalErr += fBestErr; + fBestErr = FLT_MAX; + for (size_t i = 0; i < uNumIndices2 && fBestErr > 0; i++) + { + // Compute ErrorMetricAlpha + float ea = float(pixel.a) - float(aPalette[i].a); + float fErr = ea*ea; + if (fErr > fBestErr) // error increased, so we're done searching + break; + if (fErr < fBestErr) + { + fBestErr = fErr; + if (pBestIndex2) + *pBestIndex2 = i; + } + } + fTotalErr += fBestErr; + } + + return fTotalErr; + } + + + void FillWithErrorColors(_Out_writes_(NUM_PIXELS_PER_BLOCK) HDRColorA* pOut) + { + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { +#ifdef _DEBUG + // Use Magenta in debug as a highly-visible error color + pOut[i] = HDRColorA(1.0f, 0.0f, 1.0f, 1.0f); +#else + // In production use, default to black + pOut[i] = HDRColorA(0.0f, 0.0f, 0.0f, 1.0f); +#endif + } + } +} + + +//------------------------------------------------------------------------------------- +// BC6H Compression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void D3DX_BC6H::Decode(bool bSigned, HDRColorA* pOut) const +{ + assert(pOut); + + size_t uStartBit = 0; + uint8_t uMode = GetBits(uStartBit, 2); + if (uMode != 0x00 && uMode != 0x01) + { + uMode = (GetBits(uStartBit, 3) << 2) | uMode; + } + + assert(uMode < 32); + _Analysis_assume_(uMode < 32); + + if (ms_aModeToInfo[uMode] >= 0) + { + assert(ms_aModeToInfo[uMode] < ARRAYSIZE(ms_aInfo)); + _Analysis_assume_(ms_aModeToInfo[uMode] < ARRAYSIZE(ms_aInfo)); + const ModeDescriptor* desc = ms_aDesc[ms_aModeToInfo[uMode]]; + + assert(ms_aModeToInfo[uMode] < ARRAYSIZE(ms_aDesc)); + _Analysis_assume_(ms_aModeToInfo[uMode] < ARRAYSIZE(ms_aDesc)); + const ModeInfo& info = ms_aInfo[ms_aModeToInfo[uMode]]; + + INTEndPntPair aEndPts[BC6H_MAX_REGIONS]; + memset(aEndPts, 0, BC6H_MAX_REGIONS * 2 * sizeof(INTColor)); + uint32_t uShape = 0; + + // Read header + const size_t uHeaderBits = info.uPartitions > 0 ? 82 : 65; + while (uStartBit < uHeaderBits) + { + size_t uCurBit = uStartBit; + if (GetBit(uStartBit)) + { + switch (desc[uCurBit].m_eField) + { + case D: uShape |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case RW: aEndPts[0].A.r |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case RX: aEndPts[0].B.r |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case RY: aEndPts[1].A.r |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case RZ: aEndPts[1].B.r |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case GW: aEndPts[0].A.g |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case GX: aEndPts[0].B.g |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case GY: aEndPts[1].A.g |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case GZ: aEndPts[1].B.g |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case BW: aEndPts[0].A.b |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case BX: aEndPts[0].B.b |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case BY: aEndPts[1].A.b |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + case BZ: aEndPts[1].B.b |= 1 << uint32_t(desc[uCurBit].m_uBit); break; + default: + { +#ifdef _DEBUG + OutputDebugStringA("BC6H: Invalid header bits encountered during decoding\n"); +#endif + FillWithErrorColors(pOut); + return; + } + } + } + } + + assert(uShape < 64); + _Analysis_assume_(uShape < 64); + + // Sign extend necessary end points + if (bSigned) + { + aEndPts[0].A.SignExtend(info.RGBAPrec[0][0]); + } + if (bSigned || info.bTransformed) + { + assert(info.uPartitions < BC6H_MAX_REGIONS); + _Analysis_assume_(info.uPartitions < BC6H_MAX_REGIONS); + for (size_t p = 0; p <= info.uPartitions; ++p) + { + if (p != 0) + { + aEndPts[p].A.SignExtend(info.RGBAPrec[p][0]); + } + aEndPts[p].B.SignExtend(info.RGBAPrec[p][1]); + } + } + + // Inverse transform the end points + if (info.bTransformed) + { + TransformInverse(aEndPts, info.RGBAPrec[0][0], bSigned); + } + + // Read indices + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + size_t uNumBits = IsFixUpOffset(info.uPartitions, uShape, i) ? info.uIndexPrec - 1 : info.uIndexPrec; + if (uStartBit + uNumBits > 128) + { +#ifdef _DEBUG + OutputDebugStringA("BC6H: Invalid block encountered during decoding\n"); +#endif + FillWithErrorColors(pOut); + return; + } + uint8_t uIndex = GetBits(uStartBit, uNumBits); + + if (uIndex >= ((info.uPartitions > 0) ? 8 : 16)) + { +#ifdef _DEBUG + OutputDebugStringA("BC6H: Invalid index encountered during decoding\n"); +#endif + FillWithErrorColors(pOut); + return; + } + + size_t uRegion = g_aPartitionTable[info.uPartitions][uShape][i]; + assert(uRegion < BC6H_MAX_REGIONS); + _Analysis_assume_(uRegion < BC6H_MAX_REGIONS); + + // Unquantize endpoints and interpolate + int r1 = Unquantize(aEndPts[uRegion].A.r, info.RGBAPrec[0][0].r, bSigned); + int g1 = Unquantize(aEndPts[uRegion].A.g, info.RGBAPrec[0][0].g, bSigned); + int b1 = Unquantize(aEndPts[uRegion].A.b, info.RGBAPrec[0][0].b, bSigned); + int r2 = Unquantize(aEndPts[uRegion].B.r, info.RGBAPrec[0][0].r, bSigned); + int g2 = Unquantize(aEndPts[uRegion].B.g, info.RGBAPrec[0][0].g, bSigned); + int b2 = Unquantize(aEndPts[uRegion].B.b, info.RGBAPrec[0][0].b, bSigned); + const int* aWeights = info.uPartitions > 0 ? g_aWeights3 : g_aWeights4; + INTColor fc; + fc.r = FinishUnquantize((r1 * (BC67_WEIGHT_MAX - aWeights[uIndex]) + r2 * aWeights[uIndex] + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT, bSigned); + fc.g = FinishUnquantize((g1 * (BC67_WEIGHT_MAX - aWeights[uIndex]) + g2 * aWeights[uIndex] + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT, bSigned); + fc.b = FinishUnquantize((b1 * (BC67_WEIGHT_MAX - aWeights[uIndex]) + b2 * aWeights[uIndex] + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT, bSigned); + + HALF rgb[3]; + fc.ToF16(rgb, bSigned); + + pOut[i].r = XMConvertHalfToFloat(rgb[0]); + pOut[i].g = XMConvertHalfToFloat(rgb[1]); + pOut[i].b = XMConvertHalfToFloat(rgb[2]); + pOut[i].a = 1.0f; + } + } + else + { +#ifdef _DEBUG + const char* warnstr = "BC6H: Invalid mode encountered during decoding\n"; + switch (uMode) + { + case 0x13: warnstr = "BC6H: Reserved mode 10011 encountered during decoding\n"; break; + case 0x17: warnstr = "BC6H: Reserved mode 10111 encountered during decoding\n"; break; + case 0x1B: warnstr = "BC6H: Reserved mode 11011 encountered during decoding\n"; break; + case 0x1F: warnstr = "BC6H: Reserved mode 11111 encountered during decoding\n"; break; + } + OutputDebugStringA(warnstr); +#endif + // Per the BC6H format spec, we must return opaque black + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + pOut[i] = HDRColorA(0.0f, 0.0f, 0.0f, 1.0f); + } + } +} + + +_Use_decl_annotations_ +void D3DX_BC6H::Encode(bool bSigned, const HDRColorA* const pIn) +{ + assert(pIn); + + EncodeParams EP(pIn, bSigned); + + for (EP.uMode = 0; EP.uMode < ARRAYSIZE(ms_aInfo) && EP.fBestErr > 0; ++EP.uMode) + { + const uint8_t uShapes = ms_aInfo[EP.uMode].uPartitions ? 32 : 1; + // Number of rough cases to look at. reasonable values of this are 1, uShapes/4, and uShapes + // uShapes/4 gets nearly all the cases; you can increase that a bit (say by 3 or 4) if you really want to squeeze the last bit out + const size_t uItems = std::max(1, uShapes >> 2); + float afRoughMSE[BC6H_MAX_SHAPES]; + uint8_t auShape[BC6H_MAX_SHAPES]; + + // pick the best uItems shapes and refine these. + for (EP.uShape = 0; EP.uShape < uShapes; ++EP.uShape) + { + size_t uShape = EP.uShape; + afRoughMSE[uShape] = RoughMSE(&EP); + auShape[uShape] = static_cast(uShape); + } + + // Bubble up the first uItems items + for (size_t i = 0; i < uItems; i++) + { + for (size_t j = i + 1; j < uShapes; j++) + { + if (afRoughMSE[i] > afRoughMSE[j]) + { + std::swap(afRoughMSE[i], afRoughMSE[j]); + std::swap(auShape[i], auShape[j]); + } + } + } + + for (size_t i = 0; i < uItems && EP.fBestErr > 0; i++) + { + EP.uShape = auShape[i]; + Refine(&EP); + } + } +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +int D3DX_BC6H::Quantize(int iValue, int prec, bool bSigned) +{ + assert(prec > 1); // didn't bother to make it work for 1 + int q, s = 0; + if (bSigned) + { + assert(iValue >= -F16MAX && iValue <= F16MAX); + if (iValue < 0) + { + s = 1; + iValue = -iValue; + } + q = (prec >= 16) ? iValue : (iValue << (prec - 1)) / (F16MAX + 1); + if (s) + q = -q; + assert(q > -(1 << (prec - 1)) && q < (1 << (prec - 1))); + } + else + { + assert(iValue >= 0 && iValue <= F16MAX); + q = (prec >= 15) ? iValue : (iValue << prec) / (F16MAX + 1); + assert(q >= 0 && q < (1 << prec)); + } + + return q; +} + + +_Use_decl_annotations_ +int D3DX_BC6H::Unquantize(int comp, uint8_t uBitsPerComp, bool bSigned) +{ + int unq = 0, s = 0; + if (bSigned) + { + if (uBitsPerComp >= 16) + { + unq = comp; + } + else + { + if (comp < 0) + { + s = 1; + comp = -comp; + } + + if (comp == 0) unq = 0; + else if (comp >= ((1 << (uBitsPerComp - 1)) - 1)) unq = 0x7FFF; + else unq = ((comp << 15) + 0x4000) >> (uBitsPerComp - 1); + + if (s) unq = -unq; + } + } + else + { + if (uBitsPerComp >= 15) unq = comp; + else if (comp == 0) unq = 0; + else if (comp == ((1 << uBitsPerComp) - 1)) unq = 0xFFFF; + else unq = ((comp << 16) + 0x8000) >> uBitsPerComp; + } + + return unq; +} + + +_Use_decl_annotations_ +int D3DX_BC6H::FinishUnquantize(int comp, bool bSigned) +{ + if (bSigned) + { + return (comp < 0) ? -(((-comp) * 31) >> 5) : (comp * 31) >> 5; // scale the magnitude by 31/32 + } + else + { + return (comp * 31) >> 6; // scale the magnitude by 31/64 + } +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool D3DX_BC6H::EndPointsFit(const EncodeParams* pEP, const INTEndPntPair aEndPts[]) +{ + assert(pEP); + const bool bTransformed = ms_aInfo[pEP->uMode].bTransformed; + const bool bIsSigned = pEP->bSigned; + const LDRColorA& Prec0 = ms_aInfo[pEP->uMode].RGBAPrec[0][0]; + const LDRColorA& Prec1 = ms_aInfo[pEP->uMode].RGBAPrec[0][1]; + const LDRColorA& Prec2 = ms_aInfo[pEP->uMode].RGBAPrec[1][0]; + const LDRColorA& Prec3 = ms_aInfo[pEP->uMode].RGBAPrec[1][1]; + + INTColor aBits[4]; + aBits[0].r = NBits(aEndPts[0].A.r, bIsSigned); + aBits[0].g = NBits(aEndPts[0].A.g, bIsSigned); + aBits[0].b = NBits(aEndPts[0].A.b, bIsSigned); + aBits[1].r = NBits(aEndPts[0].B.r, bTransformed || bIsSigned); + aBits[1].g = NBits(aEndPts[0].B.g, bTransformed || bIsSigned); + aBits[1].b = NBits(aEndPts[0].B.b, bTransformed || bIsSigned); + if (aBits[0].r > Prec0.r || aBits[1].r > Prec1.r || + aBits[0].g > Prec0.g || aBits[1].g > Prec1.g || + aBits[0].b > Prec0.b || aBits[1].b > Prec1.b) + return false; + + if (ms_aInfo[pEP->uMode].uPartitions) + { + aBits[2].r = NBits(aEndPts[1].A.r, bTransformed || bIsSigned); + aBits[2].g = NBits(aEndPts[1].A.g, bTransformed || bIsSigned); + aBits[2].b = NBits(aEndPts[1].A.b, bTransformed || bIsSigned); + aBits[3].r = NBits(aEndPts[1].B.r, bTransformed || bIsSigned); + aBits[3].g = NBits(aEndPts[1].B.g, bTransformed || bIsSigned); + aBits[3].b = NBits(aEndPts[1].B.b, bTransformed || bIsSigned); + + if (aBits[2].r > Prec2.r || aBits[3].r > Prec3.r || + aBits[2].g > Prec2.g || aBits[3].g > Prec3.g || + aBits[2].b > Prec2.b || aBits[3].b > Prec3.b) + return false; + } + + return true; +} + + +_Use_decl_annotations_ +void D3DX_BC6H::GeneratePaletteQuantized(const EncodeParams* pEP, const INTEndPntPair& endPts, INTColor aPalette[]) const +{ + assert(pEP); + const size_t uIndexPrec = ms_aInfo[pEP->uMode].uIndexPrec; + const size_t uNumIndices = size_t(1) << uIndexPrec; + assert(uNumIndices > 0); + _Analysis_assume_(uNumIndices > 0); + const LDRColorA& Prec = ms_aInfo[pEP->uMode].RGBAPrec[0][0]; + + // scale endpoints + INTEndPntPair unqEndPts; + unqEndPts.A.r = Unquantize(endPts.A.r, Prec.r, pEP->bSigned); + unqEndPts.A.g = Unquantize(endPts.A.g, Prec.g, pEP->bSigned); + unqEndPts.A.b = Unquantize(endPts.A.b, Prec.b, pEP->bSigned); + unqEndPts.B.r = Unquantize(endPts.B.r, Prec.r, pEP->bSigned); + unqEndPts.B.g = Unquantize(endPts.B.g, Prec.g, pEP->bSigned); + unqEndPts.B.b = Unquantize(endPts.B.b, Prec.b, pEP->bSigned); + + // interpolate + const int* aWeights = nullptr; + switch (uIndexPrec) + { + case 3: aWeights = g_aWeights3; assert(uNumIndices <= 8); _Analysis_assume_(uNumIndices <= 8); break; + case 4: aWeights = g_aWeights4; assert(uNumIndices <= 16); _Analysis_assume_(uNumIndices <= 16); break; + default: + assert(false); + for (size_t i = 0; i < uNumIndices; ++i) + { +#pragma prefast(suppress:22102 22103, "writing blocks in two halves confuses tool") + aPalette[i] = INTColor(0, 0, 0); + } + return; + } + + for (size_t i = 0; i < uNumIndices; ++i) + { + aPalette[i].r = FinishUnquantize( + (unqEndPts.A.r * (BC67_WEIGHT_MAX - aWeights[i]) + unqEndPts.B.r * aWeights[i] + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT, + pEP->bSigned); + aPalette[i].g = FinishUnquantize( + (unqEndPts.A.g * (BC67_WEIGHT_MAX - aWeights[i]) + unqEndPts.B.g * aWeights[i] + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT, + pEP->bSigned); + aPalette[i].b = FinishUnquantize( + (unqEndPts.A.b * (BC67_WEIGHT_MAX - aWeights[i]) + unqEndPts.B.b * aWeights[i] + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT, + pEP->bSigned); + } +} + + +// given a collection of colors and quantized endpoints, generate a palette, choose best entries, and return a single toterr +_Use_decl_annotations_ +float D3DX_BC6H::MapColorsQuantized(const EncodeParams* pEP, const INTColor aColors[], size_t np, const INTEndPntPair &endPts) const +{ + assert(pEP); + + const uint8_t uIndexPrec = ms_aInfo[pEP->uMode].uIndexPrec; + const uint8_t uNumIndices = 1 << uIndexPrec; + INTColor aPalette[BC6H_MAX_INDICES]; + GeneratePaletteQuantized(pEP, endPts, aPalette); + + float fTotErr = 0; + for (size_t i = 0; i < np; ++i) + { + XMVECTOR vcolors = XMLoadSInt4(reinterpret_cast(&aColors[i])); + + // Compute ErrorMetricRGB + XMVECTOR tpal = XMLoadSInt4(reinterpret_cast(&aPalette[0])); + tpal = XMVectorSubtract(vcolors, tpal); + float fBestErr = XMVectorGetX(XMVector3Dot(tpal, tpal)); + + for (int j = 1; j < uNumIndices && fBestErr > 0; ++j) + { + // Compute ErrorMetricRGB + tpal = XMLoadSInt4(reinterpret_cast(&aPalette[j])); + tpal = XMVectorSubtract(vcolors, tpal); + float fErr = XMVectorGetX(XMVector3Dot(tpal, tpal)); + if (fErr > fBestErr) break; // error increased, so we're done searching + if (fErr < fBestErr) fBestErr = fErr; + } + fTotErr += fBestErr; + } + return fTotErr; +} + + +_Use_decl_annotations_ +float D3DX_BC6H::PerturbOne(const EncodeParams* pEP, const INTColor aColors[], size_t np, uint8_t ch, + const INTEndPntPair& oldEndPts, INTEndPntPair& newEndPts, float fOldErr, int do_b) const +{ + assert(pEP); + uint8_t uPrec; + switch (ch) + { + case 0: uPrec = ms_aInfo[pEP->uMode].RGBAPrec[0][0].r; break; + case 1: uPrec = ms_aInfo[pEP->uMode].RGBAPrec[0][0].g; break; + case 2: uPrec = ms_aInfo[pEP->uMode].RGBAPrec[0][0].b; break; + default: assert(false); newEndPts = oldEndPts; return FLT_MAX; + } + INTEndPntPair tmpEndPts; + float fMinErr = fOldErr; + int beststep = 0; + + // copy real endpoints so we can perturb them + tmpEndPts = newEndPts = oldEndPts; + + // do a logarithmic search for the best error for this endpoint (which) + for (int step = 1 << (uPrec - 1); step; step >>= 1) + { + bool bImproved = false; + for (int sign = -1; sign <= 1; sign += 2) + { + if (do_b == 0) + { + tmpEndPts.A[ch] = newEndPts.A[ch] + sign * step; + if (tmpEndPts.A[ch] < 0 || tmpEndPts.A[ch] >= (1 << uPrec)) + continue; + } + else + { + tmpEndPts.B[ch] = newEndPts.B[ch] + sign * step; + if (tmpEndPts.B[ch] < 0 || tmpEndPts.B[ch] >= (1 << uPrec)) + continue; + } + + float fErr = MapColorsQuantized(pEP, aColors, np, tmpEndPts); + + if (fErr < fMinErr) + { + bImproved = true; + fMinErr = fErr; + beststep = sign * step; + } + } + // if this was an improvement, move the endpoint and continue search from there + if (bImproved) + { + if (do_b == 0) + newEndPts.A[ch] += beststep; + else + newEndPts.B[ch] += beststep; + } + } + return fMinErr; +} + + +_Use_decl_annotations_ +void D3DX_BC6H::OptimizeOne(const EncodeParams* pEP, const INTColor aColors[], size_t np, float aOrgErr, + const INTEndPntPair &aOrgEndPts, INTEndPntPair &aOptEndPts) const +{ + assert(pEP); + float aOptErr = aOrgErr; + aOptEndPts.A = aOrgEndPts.A; + aOptEndPts.B = aOrgEndPts.B; + + INTEndPntPair new_a, new_b; + INTEndPntPair newEndPts; + int do_b; + + // now optimize each channel separately + for (uint8_t ch = 0; ch < 3; ++ch) + { + // figure out which endpoint when perturbed gives the most improvement and start there + // if we just alternate, we can easily end up in a local minima + float fErr0 = PerturbOne(pEP, aColors, np, ch, aOptEndPts, new_a, aOptErr, 0); // perturb endpt A + float fErr1 = PerturbOne(pEP, aColors, np, ch, aOptEndPts, new_b, aOptErr, 1); // perturb endpt B + + if (fErr0 < fErr1) + { + if (fErr0 >= aOptErr) continue; + aOptEndPts.A[ch] = new_a.A[ch]; + aOptErr = fErr0; + do_b = 1; // do B next + } + else + { + if (fErr1 >= aOptErr) continue; + aOptEndPts.B[ch] = new_b.B[ch]; + aOptErr = fErr1; + do_b = 0; // do A next + } + + // now alternate endpoints and keep trying until there is no improvement + for (;;) + { + float fErr = PerturbOne(pEP, aColors, np, ch, aOptEndPts, newEndPts, aOptErr, do_b); + if (fErr >= aOptErr) + break; + if (do_b == 0) + aOptEndPts.A[ch] = newEndPts.A[ch]; + else + aOptEndPts.B[ch] = newEndPts.B[ch]; + aOptErr = fErr; + do_b = 1 - do_b; // now move the other endpoint + } + } +} + + +_Use_decl_annotations_ +void D3DX_BC6H::OptimizeEndPoints(const EncodeParams* pEP, const float aOrgErr[], const INTEndPntPair aOrgEndPts[], INTEndPntPair aOptEndPts[]) const +{ + assert(pEP); + const uint8_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + assert(uPartitions < BC6H_MAX_REGIONS); + _Analysis_assume_(uPartitions < BC6H_MAX_REGIONS); + INTColor aPixels[NUM_PIXELS_PER_BLOCK]; + + for (size_t p = 0; p <= uPartitions; ++p) + { + // collect the pixels in the region + size_t np = 0; + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + if (g_aPartitionTable[p][pEP->uShape][i] == p) + { + aPixels[np++] = pEP->aIPixels[i]; + } + } + + OptimizeOne(pEP, aPixels, np, aOrgErr[p], aOrgEndPts[p], aOptEndPts[p]); + } +} + + +// Swap endpoints as needed to ensure that the indices at fix up have a 0 high-order bit +_Use_decl_annotations_ +void D3DX_BC6H::SwapIndices(const EncodeParams* pEP, INTEndPntPair aEndPts[], size_t aIndices[]) +{ + assert(pEP); + const size_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + const size_t uNumIndices = size_t(1) << ms_aInfo[pEP->uMode].uIndexPrec; + const size_t uHighIndexBit = uNumIndices >> 1; + + assert(uPartitions < BC6H_MAX_REGIONS && pEP->uShape < BC6H_MAX_SHAPES); + _Analysis_assume_(uPartitions < BC6H_MAX_REGIONS && pEP->uShape < BC6H_MAX_SHAPES); + + for (size_t p = 0; p <= uPartitions; ++p) + { + size_t i = g_aFixUp[uPartitions][pEP->uShape][p]; + assert(g_aPartitionTable[uPartitions][pEP->uShape][i] == p); + if (aIndices[i] & uHighIndexBit) + { + // high bit is set, swap the aEndPts and indices for this region + std::swap(aEndPts[p].A, aEndPts[p].B); + + for (size_t j = 0; j < NUM_PIXELS_PER_BLOCK; ++j) + if (g_aPartitionTable[uPartitions][pEP->uShape][j] == p) + aIndices[j] = uNumIndices - 1 - aIndices[j]; + } + } +} + + +// assign indices given a tile, shape, and quantized endpoints, return toterr for each region +_Use_decl_annotations_ +void D3DX_BC6H::AssignIndices(const EncodeParams* pEP, const INTEndPntPair aEndPts[], size_t aIndices[], float aTotErr[]) const +{ + assert(pEP); + const uint8_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + const uint8_t uNumIndices = 1 << ms_aInfo[pEP->uMode].uIndexPrec; + + assert(uPartitions < BC6H_MAX_REGIONS && pEP->uShape < BC6H_MAX_SHAPES); + _Analysis_assume_(uPartitions < BC6H_MAX_REGIONS && pEP->uShape < BC6H_MAX_SHAPES); + + // build list of possibles + INTColor aPalette[BC6H_MAX_REGIONS][BC6H_MAX_INDICES]; + + for (size_t p = 0; p <= uPartitions; ++p) + { + GeneratePaletteQuantized(pEP, aEndPts[p], aPalette[p]); + aTotErr[p] = 0; + } + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + const uint8_t uRegion = g_aPartitionTable[uPartitions][pEP->uShape][i]; + assert(uRegion < BC6H_MAX_REGIONS); + _Analysis_assume_(uRegion < BC6H_MAX_REGIONS); + float fBestErr = Norm(pEP->aIPixels[i], aPalette[uRegion][0]); + aIndices[i] = 0; + + for (uint8_t j = 1; j < uNumIndices && fBestErr > 0; ++j) + { + float fErr = Norm(pEP->aIPixels[i], aPalette[uRegion][j]); + if (fErr > fBestErr) break; // error increased, so we're done searching + if (fErr < fBestErr) + { + fBestErr = fErr; + aIndices[i] = j; + } + } + aTotErr[uRegion] += fBestErr; + } +} + + +_Use_decl_annotations_ +void D3DX_BC6H::QuantizeEndPts(const EncodeParams* pEP, INTEndPntPair* aQntEndPts) const +{ + assert(pEP && aQntEndPts); + const INTEndPntPair* aUnqEndPts = pEP->aUnqEndPts[pEP->uShape]; + const LDRColorA& Prec = ms_aInfo[pEP->uMode].RGBAPrec[0][0]; + const uint8_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + assert(uPartitions < BC6H_MAX_REGIONS); + _Analysis_assume_(uPartitions < BC6H_MAX_REGIONS); + + for (size_t p = 0; p <= uPartitions; ++p) + { + aQntEndPts[p].A.r = Quantize(aUnqEndPts[p].A.r, Prec.r, pEP->bSigned); + aQntEndPts[p].A.g = Quantize(aUnqEndPts[p].A.g, Prec.g, pEP->bSigned); + aQntEndPts[p].A.b = Quantize(aUnqEndPts[p].A.b, Prec.b, pEP->bSigned); + aQntEndPts[p].B.r = Quantize(aUnqEndPts[p].B.r, Prec.r, pEP->bSigned); + aQntEndPts[p].B.g = Quantize(aUnqEndPts[p].B.g, Prec.g, pEP->bSigned); + aQntEndPts[p].B.b = Quantize(aUnqEndPts[p].B.b, Prec.b, pEP->bSigned); + } +} + + +_Use_decl_annotations_ +void D3DX_BC6H::EmitBlock(const EncodeParams* pEP, const INTEndPntPair aEndPts[], const size_t aIndices[]) +{ + assert(pEP); + const uint8_t uRealMode = ms_aInfo[pEP->uMode].uMode; + const uint8_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + const uint8_t uIndexPrec = ms_aInfo[pEP->uMode].uIndexPrec; + const size_t uHeaderBits = uPartitions > 0 ? 82 : 65; + const ModeDescriptor* desc = ms_aDesc[pEP->uMode]; + size_t uStartBit = 0; + + while (uStartBit < uHeaderBits) + { + switch (desc[uStartBit].m_eField) + { + case M: SetBit(uStartBit, uint8_t(uRealMode >> desc[uStartBit].m_uBit) & 0x01); break; + case D: SetBit(uStartBit, uint8_t(pEP->uShape >> desc[uStartBit].m_uBit) & 0x01); break; + case RW: SetBit(uStartBit, uint8_t(aEndPts[0].A.r >> desc[uStartBit].m_uBit) & 0x01); break; + case RX: SetBit(uStartBit, uint8_t(aEndPts[0].B.r >> desc[uStartBit].m_uBit) & 0x01); break; + case RY: SetBit(uStartBit, uint8_t(aEndPts[1].A.r >> desc[uStartBit].m_uBit) & 0x01); break; + case RZ: SetBit(uStartBit, uint8_t(aEndPts[1].B.r >> desc[uStartBit].m_uBit) & 0x01); break; + case GW: SetBit(uStartBit, uint8_t(aEndPts[0].A.g >> desc[uStartBit].m_uBit) & 0x01); break; + case GX: SetBit(uStartBit, uint8_t(aEndPts[0].B.g >> desc[uStartBit].m_uBit) & 0x01); break; + case GY: SetBit(uStartBit, uint8_t(aEndPts[1].A.g >> desc[uStartBit].m_uBit) & 0x01); break; + case GZ: SetBit(uStartBit, uint8_t(aEndPts[1].B.g >> desc[uStartBit].m_uBit) & 0x01); break; + case BW: SetBit(uStartBit, uint8_t(aEndPts[0].A.b >> desc[uStartBit].m_uBit) & 0x01); break; + case BX: SetBit(uStartBit, uint8_t(aEndPts[0].B.b >> desc[uStartBit].m_uBit) & 0x01); break; + case BY: SetBit(uStartBit, uint8_t(aEndPts[1].A.b >> desc[uStartBit].m_uBit) & 0x01); break; + case BZ: SetBit(uStartBit, uint8_t(aEndPts[1].B.b >> desc[uStartBit].m_uBit) & 0x01); break; + default: assert(false); + } + } + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + if (IsFixUpOffset(ms_aInfo[pEP->uMode].uPartitions, pEP->uShape, i)) + SetBits(uStartBit, uIndexPrec - 1, static_cast(aIndices[i])); + else + SetBits(uStartBit, uIndexPrec, static_cast(aIndices[i])); + } + assert(uStartBit == 128); +} + + +_Use_decl_annotations_ +void D3DX_BC6H::Refine(EncodeParams* pEP) +{ + assert(pEP); + const uint8_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + assert(uPartitions < BC6H_MAX_REGIONS); + _Analysis_assume_(uPartitions < BC6H_MAX_REGIONS); + + const bool bTransformed = ms_aInfo[pEP->uMode].bTransformed; + float aOrgErr[BC6H_MAX_REGIONS], aOptErr[BC6H_MAX_REGIONS]; + INTEndPntPair aOrgEndPts[BC6H_MAX_REGIONS], aOptEndPts[BC6H_MAX_REGIONS]; + size_t aOrgIdx[NUM_PIXELS_PER_BLOCK], aOptIdx[NUM_PIXELS_PER_BLOCK]; + + QuantizeEndPts(pEP, aOrgEndPts); + AssignIndices(pEP, aOrgEndPts, aOrgIdx, aOrgErr); + SwapIndices(pEP, aOrgEndPts, aOrgIdx); + + if (bTransformed) TransformForward(aOrgEndPts); + if (EndPointsFit(pEP, aOrgEndPts)) + { + if (bTransformed) TransformInverse(aOrgEndPts, ms_aInfo[pEP->uMode].RGBAPrec[0][0], pEP->bSigned); + OptimizeEndPoints(pEP, aOrgErr, aOrgEndPts, aOptEndPts); + AssignIndices(pEP, aOptEndPts, aOptIdx, aOptErr); + SwapIndices(pEP, aOptEndPts, aOptIdx); + + float fOrgTotErr = 0.0f, fOptTotErr = 0.0f; + for (size_t p = 0; p <= uPartitions; ++p) + { + fOrgTotErr += aOrgErr[p]; + fOptTotErr += aOptErr[p]; + } + + if (bTransformed) TransformForward(aOptEndPts); + if (EndPointsFit(pEP, aOptEndPts) && fOptTotErr < fOrgTotErr && fOptTotErr < pEP->fBestErr) + { + pEP->fBestErr = fOptTotErr; + EmitBlock(pEP, aOptEndPts, aOptIdx); + } + else if (fOrgTotErr < pEP->fBestErr) + { + // either it stopped fitting when we optimized it, or there was no improvement + // so go back to the unoptimized endpoints which we know will fit + if (bTransformed) TransformForward(aOrgEndPts); + pEP->fBestErr = fOrgTotErr; + EmitBlock(pEP, aOrgEndPts, aOrgIdx); + } + } +} + + +_Use_decl_annotations_ +void D3DX_BC6H::GeneratePaletteUnquantized(const EncodeParams* pEP, size_t uRegion, INTColor aPalette[]) +{ + assert(pEP); + assert(uRegion < BC6H_MAX_REGIONS && pEP->uShape < BC6H_MAX_SHAPES); + _Analysis_assume_(uRegion < BC6H_MAX_REGIONS && pEP->uShape < BC6H_MAX_SHAPES); + const INTEndPntPair& endPts = pEP->aUnqEndPts[pEP->uShape][uRegion]; + const uint8_t uIndexPrec = ms_aInfo[pEP->uMode].uIndexPrec; + const uint8_t uNumIndices = 1 << uIndexPrec; + assert(uNumIndices > 0); + _Analysis_assume_(uNumIndices > 0); + + const int* aWeights = nullptr; + switch (uIndexPrec) + { + case 3: aWeights = g_aWeights3; assert(uNumIndices <= 8); _Analysis_assume_(uNumIndices <= 8); break; + case 4: aWeights = g_aWeights4; assert(uNumIndices <= 16); _Analysis_assume_(uNumIndices <= 16); break; + default: + assert(false); + for (size_t i = 0; i < uNumIndices; ++i) + { +#pragma prefast(suppress:22102 22103, "writing blocks in two halves confuses tool") + aPalette[i] = INTColor(0, 0, 0); + } + return; + } + + for (size_t i = 0; i < uNumIndices; ++i) + { + aPalette[i].r = (endPts.A.r * (BC67_WEIGHT_MAX - aWeights[i]) + endPts.B.r * aWeights[i] + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT; + aPalette[i].g = (endPts.A.g * (BC67_WEIGHT_MAX - aWeights[i]) + endPts.B.g * aWeights[i] + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT; + aPalette[i].b = (endPts.A.b * (BC67_WEIGHT_MAX - aWeights[i]) + endPts.B.b * aWeights[i] + BC67_WEIGHT_ROUND) >> BC67_WEIGHT_SHIFT; + } +} + + +_Use_decl_annotations_ +float D3DX_BC6H::MapColors(const EncodeParams* pEP, size_t uRegion, size_t np, const size_t* auIndex) const +{ + assert(pEP); + const uint8_t uIndexPrec = ms_aInfo[pEP->uMode].uIndexPrec; + const uint8_t uNumIndices = 1 << uIndexPrec; + INTColor aPalette[BC6H_MAX_INDICES]; + GeneratePaletteUnquantized(pEP, uRegion, aPalette); + + float fTotalErr = 0.0f; + for (size_t i = 0; i < np; ++i) + { + float fBestErr = Norm(pEP->aIPixels[auIndex[i]], aPalette[0]); + for (uint8_t j = 1; j < uNumIndices && fBestErr > 0.0f; ++j) + { + float fErr = Norm(pEP->aIPixels[auIndex[i]], aPalette[j]); + if (fErr > fBestErr) break; // error increased, so we're done searching + if (fErr < fBestErr) fBestErr = fErr; + } + fTotalErr += fBestErr; + } + + return fTotalErr; +} + +_Use_decl_annotations_ +float D3DX_BC6H::RoughMSE(EncodeParams* pEP) const +{ + assert(pEP); + assert(pEP->uShape < BC6H_MAX_SHAPES); + _Analysis_assume_(pEP->uShape < BC6H_MAX_SHAPES); + + INTEndPntPair* aEndPts = pEP->aUnqEndPts[pEP->uShape]; + + const uint8_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + assert(uPartitions < BC6H_MAX_REGIONS); + _Analysis_assume_(uPartitions < BC6H_MAX_REGIONS); + + size_t auPixIdx[NUM_PIXELS_PER_BLOCK]; + + float fError = 0.0f; + for (size_t p = 0; p <= uPartitions; ++p) + { + size_t np = 0; + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + if (g_aPartitionTable[uPartitions][pEP->uShape][i] == p) + { + auPixIdx[np++] = i; + } + } + + // handle simple cases + assert(np > 0); + if (np == 1) + { + aEndPts[p].A = pEP->aIPixels[auPixIdx[0]]; + aEndPts[p].B = pEP->aIPixels[auPixIdx[0]]; + continue; + } + else if (np == 2) + { + aEndPts[p].A = pEP->aIPixels[auPixIdx[0]]; + aEndPts[p].B = pEP->aIPixels[auPixIdx[1]]; + continue; + } + + HDRColorA epA, epB; + OptimizeRGB(pEP->aHDRPixels, &epA, &epB, 4, np, auPixIdx); + aEndPts[p].A.Set(epA, pEP->bSigned); + aEndPts[p].B.Set(epB, pEP->bSigned); + if (pEP->bSigned) + { + aEndPts[p].A.Clamp(-F16MAX, F16MAX); + aEndPts[p].B.Clamp(-F16MAX, F16MAX); + } + else + { + aEndPts[p].A.Clamp(0, F16MAX); + aEndPts[p].B.Clamp(0, F16MAX); + } + + fError += MapColors(pEP, p, np, auPixIdx); + } + + return fError; +} + + +//------------------------------------------------------------------------------------- +// BC7 Compression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void D3DX_BC7::Decode(HDRColorA* pOut) const +{ + assert(pOut); + + size_t uFirst = 0; + while (uFirst < 128 && !GetBit(uFirst)) {} + uint8_t uMode = uint8_t(uFirst - 1); + + if (uMode < 8) + { + const uint8_t uPartitions = ms_aInfo[uMode].uPartitions; + assert(uPartitions < BC7_MAX_REGIONS); + _Analysis_assume_(uPartitions < BC7_MAX_REGIONS); + + const uint8_t uNumEndPts = (uPartitions + 1) << 1; + const uint8_t uIndexPrec = ms_aInfo[uMode].uIndexPrec; + const uint8_t uIndexPrec2 = ms_aInfo[uMode].uIndexPrec2; + size_t i; + size_t uStartBit = uMode + 1; + uint8_t P[6]; + uint8_t uShape = GetBits(uStartBit, ms_aInfo[uMode].uPartitionBits); + assert(uShape < BC7_MAX_SHAPES); + _Analysis_assume_(uShape < BC7_MAX_SHAPES); + + uint8_t uRotation = GetBits(uStartBit, ms_aInfo[uMode].uRotationBits); + assert(uRotation < 4); + + uint8_t uIndexMode = GetBits(uStartBit, ms_aInfo[uMode].uIndexModeBits); + assert(uIndexMode < 2); + + LDRColorA c[BC7_MAX_REGIONS << 1]; + const LDRColorA RGBAPrec = ms_aInfo[uMode].RGBAPrec; + const LDRColorA RGBAPrecWithP = ms_aInfo[uMode].RGBAPrecWithP; + + assert(uNumEndPts <= (BC7_MAX_REGIONS << 1)); + + // Red channel + for (i = 0; i < uNumEndPts; i++) + { + if (uStartBit + RGBAPrec.r > 128) + { +#ifdef _DEBUG + OutputDebugStringA("BC7: Invalid block encountered during decoding\n"); +#endif + FillWithErrorColors(pOut); + return; + } + + c[i].r = GetBits(uStartBit, RGBAPrec.r); + } + + // Green channel + for (i = 0; i < uNumEndPts; i++) + { + if (uStartBit + RGBAPrec.g > 128) + { +#ifdef _DEBUG + OutputDebugStringA("BC7: Invalid block encountered during decoding\n"); +#endif + FillWithErrorColors(pOut); + return; + } + + c[i].g = GetBits(uStartBit, RGBAPrec.g); + } + + // Blue channel + for (i = 0; i < uNumEndPts; i++) + { + if (uStartBit + RGBAPrec.b > 128) + { +#ifdef _DEBUG + OutputDebugStringA("BC7: Invalid block encountered during decoding\n"); +#endif + FillWithErrorColors(pOut); + return; + } + + c[i].b = GetBits(uStartBit, RGBAPrec.b); + } + + // Alpha channel + for (i = 0; i < uNumEndPts; i++) + { + if (uStartBit + RGBAPrec.a > 128) + { +#ifdef _DEBUG + OutputDebugStringA("BC7: Invalid block encountered during decoding\n"); +#endif + FillWithErrorColors(pOut); + return; + } + + c[i].a = RGBAPrec.a ? GetBits(uStartBit, RGBAPrec.a) : 255; + } + + // P-bits + assert(ms_aInfo[uMode].uPBits <= 6); + _Analysis_assume_(ms_aInfo[uMode].uPBits <= 6); + for (i = 0; i < ms_aInfo[uMode].uPBits; i++) + { + if (uStartBit > 127) + { +#ifdef _DEBUG + OutputDebugStringA("BC7: Invalid block encountered during decoding\n"); +#endif + FillWithErrorColors(pOut); + return; + } + + P[i] = GetBit(uStartBit); + } + + if (ms_aInfo[uMode].uPBits) + { + for (i = 0; i < uNumEndPts; i++) + { + size_t pi = i * ms_aInfo[uMode].uPBits / uNumEndPts; + for (uint8_t ch = 0; ch < BC7_NUM_CHANNELS; ch++) + { + if (RGBAPrec[ch] != RGBAPrecWithP[ch]) + { + c[i][ch] = (c[i][ch] << 1) | P[pi]; + } + } + } + } + + for (i = 0; i < uNumEndPts; i++) + { + c[i] = Unquantize(c[i], RGBAPrecWithP); + } + + uint8_t w1[NUM_PIXELS_PER_BLOCK], w2[NUM_PIXELS_PER_BLOCK]; + + // read color indices + for (i = 0; i < NUM_PIXELS_PER_BLOCK; i++) + { + size_t uNumBits = IsFixUpOffset(ms_aInfo[uMode].uPartitions, uShape, i) ? uIndexPrec - 1 : uIndexPrec; + if (uStartBit + uNumBits > 128) + { +#ifdef _DEBUG + OutputDebugStringA("BC7: Invalid block encountered during decoding\n"); +#endif + FillWithErrorColors(pOut); + return; + } + w1[i] = GetBits(uStartBit, uNumBits); + } + + // read alpha indices + if (uIndexPrec2) + { + for (i = 0; i < NUM_PIXELS_PER_BLOCK; i++) + { + size_t uNumBits = i ? uIndexPrec2 : uIndexPrec2 - 1; + if (uStartBit + uNumBits > 128) + { +#ifdef _DEBUG + OutputDebugStringA("BC7: Invalid block encountered during decoding\n"); +#endif + FillWithErrorColors(pOut); + return; + } + w2[i] = GetBits(uStartBit, uNumBits); + } + } + + for (i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + uint8_t uRegion = g_aPartitionTable[uPartitions][uShape][i]; + LDRColorA outPixel; + if (uIndexPrec2 == 0) + { + LDRColorA::Interpolate(c[uRegion << 1], c[(uRegion << 1) + 1], w1[i], w1[i], uIndexPrec, uIndexPrec, outPixel); + } + else + { + if (uIndexMode == 0) + { + LDRColorA::Interpolate(c[uRegion << 1], c[(uRegion << 1) + 1], w1[i], w2[i], uIndexPrec, uIndexPrec2, outPixel); + } + else + { + LDRColorA::Interpolate(c[uRegion << 1], c[(uRegion << 1) + 1], w2[i], w1[i], uIndexPrec2, uIndexPrec, outPixel); + } + } + + switch (uRotation) + { + case 1: std::swap(outPixel.r, outPixel.a); break; + case 2: std::swap(outPixel.g, outPixel.a); break; + case 3: std::swap(outPixel.b, outPixel.a); break; + } + + pOut[i] = HDRColorA(outPixel); + } + } + else + { +#ifdef _DEBUG + OutputDebugStringA("BC7: Reserved mode 8 encountered during decoding\n"); +#endif + // Per the BC7 format spec, we must return transparent black + memset(pOut, 0, sizeof(HDRColorA) * NUM_PIXELS_PER_BLOCK); + } +} + +_Use_decl_annotations_ +void D3DX_BC7::Encode(DWORD flags, const HDRColorA* const pIn) +{ + assert(pIn); + + D3DX_BC7 final = *this; + EncodeParams EP(pIn); + float fMSEBest = FLT_MAX; + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + EP.aLDRPixels[i].r = uint8_t(std::max(0.0f, std::min(255.0f, pIn[i].r * 255.0f + 0.01f))); + EP.aLDRPixels[i].g = uint8_t(std::max(0.0f, std::min(255.0f, pIn[i].g * 255.0f + 0.01f))); + EP.aLDRPixels[i].b = uint8_t(std::max(0.0f, std::min(255.0f, pIn[i].b * 255.0f + 0.01f))); + EP.aLDRPixels[i].a = uint8_t(std::max(0.0f, std::min(255.0f, pIn[i].a * 255.0f + 0.01f))); + } + + for (EP.uMode = 0; EP.uMode < 8 && fMSEBest > 0; ++EP.uMode) + { + if (!(flags & BC_FLAGS_USE_3SUBSETS) && (EP.uMode == 0 || EP.uMode == 2)) + { + // 3 subset modes tend to be used rarely and add significant compression time + continue; + } + + if ((flags & TEX_COMPRESS_BC7_QUICK) && (EP.uMode != 6)) + { + // Use only mode 6 + continue; + } + + const size_t uShapes = size_t(1) << ms_aInfo[EP.uMode].uPartitionBits; + assert(uShapes <= BC7_MAX_SHAPES); + _Analysis_assume_(uShapes <= BC7_MAX_SHAPES); + + const size_t uNumRots = size_t(1) << ms_aInfo[EP.uMode].uRotationBits; + const size_t uNumIdxMode = size_t(1) << ms_aInfo[EP.uMode].uIndexModeBits; + // Number of rough cases to look at. reasonable values of this are 1, uShapes/4, and uShapes + // uShapes/4 gets nearly all the cases; you can increase that a bit (say by 3 or 4) if you really want to squeeze the last bit out + const size_t uItems = std::max(1, uShapes >> 2); + float afRoughMSE[BC7_MAX_SHAPES]; + size_t auShape[BC7_MAX_SHAPES]; + + for (size_t r = 0; r < uNumRots && fMSEBest > 0; ++r) + { + switch (r) + { + case 1: for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) std::swap(EP.aLDRPixels[i].r, EP.aLDRPixels[i].a); break; + case 2: for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) std::swap(EP.aLDRPixels[i].g, EP.aLDRPixels[i].a); break; + case 3: for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) std::swap(EP.aLDRPixels[i].b, EP.aLDRPixels[i].a); break; + } + + for (size_t im = 0; im < uNumIdxMode && fMSEBest > 0; ++im) + { + // pick the best uItems shapes and refine these. + for (size_t s = 0; s < uShapes; s++) + { + afRoughMSE[s] = RoughMSE(&EP, s, im); + auShape[s] = s; + } + + // Bubble up the first uItems items + for (size_t i = 0; i < uItems; i++) + { + for (size_t j = i + 1; j < uShapes; j++) + { + if (afRoughMSE[i] > afRoughMSE[j]) + { + std::swap(afRoughMSE[i], afRoughMSE[j]); + std::swap(auShape[i], auShape[j]); + } + } + } + + for (size_t i = 0; i < uItems && fMSEBest > 0; i++) + { + float fMSE = Refine(&EP, auShape[i], r, im); + if (fMSE < fMSEBest) + { + final = *this; + fMSEBest = fMSE; + } + } + } + + switch (r) + { + case 1: for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) std::swap(EP.aLDRPixels[i].r, EP.aLDRPixels[i].a); break; + case 2: for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) std::swap(EP.aLDRPixels[i].g, EP.aLDRPixels[i].a); break; + case 3: for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) std::swap(EP.aLDRPixels[i].b, EP.aLDRPixels[i].a); break; + } + } + } + + *this = final; +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void D3DX_BC7::GeneratePaletteQuantized(const EncodeParams* pEP, size_t uIndexMode, const LDREndPntPair& endPts, LDRColorA aPalette[]) const +{ + assert(pEP); + const size_t uIndexPrec = uIndexMode ? ms_aInfo[pEP->uMode].uIndexPrec2 : ms_aInfo[pEP->uMode].uIndexPrec; + const size_t uIndexPrec2 = uIndexMode ? ms_aInfo[pEP->uMode].uIndexPrec : ms_aInfo[pEP->uMode].uIndexPrec2; + const size_t uNumIndices = size_t(1) << uIndexPrec; + const size_t uNumIndices2 = size_t(1) << uIndexPrec2; + assert(uNumIndices > 0 && uNumIndices2 > 0); + _Analysis_assume_(uNumIndices > 0 && uNumIndices2 > 0); + assert((uNumIndices <= BC7_MAX_INDICES) && (uNumIndices2 <= BC7_MAX_INDICES)); + _Analysis_assume_((uNumIndices <= BC7_MAX_INDICES) && (uNumIndices2 <= BC7_MAX_INDICES)); + + LDRColorA a = Unquantize(endPts.A, ms_aInfo[pEP->uMode].RGBAPrecWithP); + LDRColorA b = Unquantize(endPts.B, ms_aInfo[pEP->uMode].RGBAPrecWithP); + if (uIndexPrec2 == 0) + { + for (size_t i = 0; i < uNumIndices; i++) + LDRColorA::Interpolate(a, b, i, i, uIndexPrec, uIndexPrec, aPalette[i]); + } + else + { + for (size_t i = 0; i < uNumIndices; i++) + LDRColorA::InterpolateRGB(a, b, i, uIndexPrec, aPalette[i]); + for (size_t i = 0; i < uNumIndices2; i++) + LDRColorA::InterpolateA(a, b, i, uIndexPrec2, aPalette[i]); + } +} + +_Use_decl_annotations_ +float D3DX_BC7::PerturbOne(const EncodeParams* pEP, const LDRColorA aColors[], size_t np, size_t uIndexMode, size_t ch, + const LDREndPntPair &oldEndPts, LDREndPntPair &newEndPts, float fOldErr, uint8_t do_b) const +{ + assert(pEP); + const int prec = ms_aInfo[pEP->uMode].RGBAPrecWithP[ch]; + LDREndPntPair tmp_endPts = newEndPts = oldEndPts; + float fMinErr = fOldErr; + uint8_t* pnew_c = (do_b ? &newEndPts.B[ch] : &newEndPts.A[ch]); + uint8_t* ptmp_c = (do_b ? &tmp_endPts.B[ch] : &tmp_endPts.A[ch]); + + // do a logarithmic search for the best error for this endpoint (which) + for (int step = 1 << (prec - 1); step; step >>= 1) + { + bool bImproved = false; + int beststep = 0; + for (int sign = -1; sign <= 1; sign += 2) + { + int tmp = int(*pnew_c) + sign * step; + if (tmp < 0 || tmp >= (1 << prec)) + continue; + else + *ptmp_c = (uint8_t)tmp; + + float fTotalErr = MapColors(pEP, aColors, np, uIndexMode, tmp_endPts, fMinErr); + if (fTotalErr < fMinErr) + { + bImproved = true; + fMinErr = fTotalErr; + beststep = sign * step; + } + } + + // if this was an improvement, move the endpoint and continue search from there + if (bImproved) + *pnew_c = uint8_t(int(*pnew_c) + beststep); + } + return fMinErr; +} + +// perturb the endpoints at least -3 to 3. +// always ensure endpoint ordering is preserved (no need to overlap the scan) +_Use_decl_annotations_ +void D3DX_BC7::Exhaustive(const EncodeParams* pEP, const LDRColorA aColors[], size_t np, size_t uIndexMode, size_t ch, + float& fOrgErr, LDREndPntPair& optEndPt) const +{ + assert(pEP); + const uint8_t uPrec = ms_aInfo[pEP->uMode].RGBAPrecWithP[ch]; + LDREndPntPair tmpEndPt; + if (fOrgErr == 0) + return; + + int delta = 5; + + // ok figure out the range of A and B + tmpEndPt = optEndPt; + int alow = std::max(0, int(optEndPt.A[ch]) - delta); + int ahigh = std::min((1 << uPrec) - 1, int(optEndPt.A[ch]) + delta); + int blow = std::max(0, int(optEndPt.B[ch]) - delta); + int bhigh = std::min((1 << uPrec) - 1, int(optEndPt.B[ch]) + delta); + int amin = 0; + int bmin = 0; + + float fBestErr = fOrgErr; + if (optEndPt.A[ch] <= optEndPt.B[ch]) + { + // keep a <= b + for (int a = alow; a <= ahigh; ++a) + { + for (int b = std::max(a, blow); b < bhigh; ++b) + { + tmpEndPt.A[ch] = (uint8_t)a; + tmpEndPt.B[ch] = (uint8_t)b; + + float fErr = MapColors(pEP, aColors, np, uIndexMode, tmpEndPt, fBestErr); + if (fErr < fBestErr) + { + amin = a; + bmin = b; + fBestErr = fErr; + } + } + } + } + else + { + // keep b <= a + for (int b = blow; b < bhigh; ++b) + { + for (int a = std::max(b, alow); a <= ahigh; ++a) + { + tmpEndPt.A[ch] = (uint8_t)a; + tmpEndPt.B[ch] = (uint8_t)b; + + float fErr = MapColors(pEP, aColors, np, uIndexMode, tmpEndPt, fBestErr); + if (fErr < fBestErr) + { + amin = a; + bmin = b; + fBestErr = fErr; + } + } + } + } + + if (fBestErr < fOrgErr) + { + optEndPt.A[ch] = (uint8_t)amin; + optEndPt.B[ch] = (uint8_t)bmin; + fOrgErr = fBestErr; + } +} + +_Use_decl_annotations_ +void D3DX_BC7::OptimizeOne(const EncodeParams* pEP, const LDRColorA aColors[], size_t np, size_t uIndexMode, + float fOrgErr, const LDREndPntPair& org, LDREndPntPair& opt) const +{ + assert(pEP); + + float fOptErr = fOrgErr; + opt = org; + + LDREndPntPair new_a, new_b; + LDREndPntPair newEndPts; + uint8_t do_b; + + // now optimize each channel separately + for (size_t ch = 0; ch < BC7_NUM_CHANNELS; ++ch) + { + if (ms_aInfo[pEP->uMode].RGBAPrecWithP[ch] == 0) + continue; + + // figure out which endpoint when perturbed gives the most improvement and start there + // if we just alternate, we can easily end up in a local minima + float fErr0 = PerturbOne(pEP, aColors, np, uIndexMode, ch, opt, new_a, fOptErr, 0); // perturb endpt A + float fErr1 = PerturbOne(pEP, aColors, np, uIndexMode, ch, opt, new_b, fOptErr, 1); // perturb endpt B + + uint8_t& copt_a = opt.A[ch]; + uint8_t& copt_b = opt.B[ch]; + uint8_t& cnew_a = new_a.A[ch]; + uint8_t& cnew_b = new_a.B[ch]; + + if (fErr0 < fErr1) + { + if (fErr0 >= fOptErr) + continue; + copt_a = cnew_a; + fOptErr = fErr0; + do_b = 1; // do B next + } + else + { + if (fErr1 >= fOptErr) + continue; + copt_b = cnew_b; + fOptErr = fErr1; + do_b = 0; // do A next + } + + // now alternate endpoints and keep trying until there is no improvement + for (; ; ) + { + float fErr = PerturbOne(pEP, aColors, np, uIndexMode, ch, opt, newEndPts, fOptErr, do_b); + if (fErr >= fOptErr) + break; + if (do_b == 0) + copt_a = cnew_a; + else + copt_b = cnew_b; + fOptErr = fErr; + do_b = 1 - do_b; // now move the other endpoint + } + } + + // finally, do a small exhaustive search around what we think is the global minima to be sure + for (size_t ch = 0; ch < BC7_NUM_CHANNELS; ch++) + Exhaustive(pEP, aColors, np, uIndexMode, ch, fOptErr, opt); +} + +_Use_decl_annotations_ +void D3DX_BC7::OptimizeEndPoints(const EncodeParams* pEP, size_t uShape, size_t uIndexMode, const float afOrgErr[], + const LDREndPntPair aOrgEndPts[], LDREndPntPair aOptEndPts[]) const +{ + assert(pEP); + const uint8_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + assert(uPartitions < BC7_MAX_REGIONS && uShape < BC7_MAX_SHAPES); + _Analysis_assume_(uPartitions < BC7_MAX_REGIONS && uShape < BC7_MAX_SHAPES); + + LDRColorA aPixels[NUM_PIXELS_PER_BLOCK]; + + for (size_t p = 0; p <= uPartitions; ++p) + { + // collect the pixels in the region + size_t np = 0; + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + if (g_aPartitionTable[uPartitions][uShape][i] == p) + aPixels[np++] = pEP->aLDRPixels[i]; + + OptimizeOne(pEP, aPixels, np, uIndexMode, afOrgErr[p], aOrgEndPts[p], aOptEndPts[p]); + } +} + +_Use_decl_annotations_ +void D3DX_BC7::AssignIndices(const EncodeParams* pEP, size_t uShape, size_t uIndexMode, LDREndPntPair endPts[], size_t aIndices[], size_t aIndices2[], + float afTotErr[]) const +{ + assert(pEP); + assert(uShape < BC7_MAX_SHAPES); + _Analysis_assume_(uShape < BC7_MAX_SHAPES); + + const uint8_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + assert(uPartitions < BC7_MAX_REGIONS); + _Analysis_assume_(uPartitions < BC7_MAX_REGIONS); + + const uint8_t uIndexPrec = uIndexMode ? ms_aInfo[pEP->uMode].uIndexPrec2 : ms_aInfo[pEP->uMode].uIndexPrec; + const uint8_t uIndexPrec2 = uIndexMode ? ms_aInfo[pEP->uMode].uIndexPrec : ms_aInfo[pEP->uMode].uIndexPrec2; + const uint8_t uNumIndices = 1 << uIndexPrec; + const uint8_t uNumIndices2 = 1 << uIndexPrec2; + + assert((uNumIndices <= BC7_MAX_INDICES) && (uNumIndices2 <= BC7_MAX_INDICES)); + _Analysis_assume_((uNumIndices <= BC7_MAX_INDICES) && (uNumIndices2 <= BC7_MAX_INDICES)); + + const uint8_t uHighestIndexBit = uNumIndices >> 1; + const uint8_t uHighestIndexBit2 = uNumIndices2 >> 1; + LDRColorA aPalette[BC7_MAX_REGIONS][BC7_MAX_INDICES]; + + // build list of possibles + for (size_t p = 0; p <= uPartitions; p++) + { + GeneratePaletteQuantized(pEP, uIndexMode, endPts[p], aPalette[p]); + afTotErr[p] = 0; + } + + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) + { + uint8_t uRegion = g_aPartitionTable[uPartitions][uShape][i]; + assert(uRegion < BC7_MAX_REGIONS); + _Analysis_assume_(uRegion < BC7_MAX_REGIONS); + afTotErr[uRegion] += ComputeError(pEP->aLDRPixels[i], aPalette[uRegion], uIndexPrec, uIndexPrec2, &(aIndices[i]), &(aIndices2[i])); + } + + // swap endpoints as needed to ensure that the indices at index_positions have a 0 high-order bit + if (uIndexPrec2 == 0) + { + for (size_t p = 0; p <= uPartitions; p++) + { + if (aIndices[g_aFixUp[uPartitions][uShape][p]] & uHighestIndexBit) + { + std::swap(endPts[p].A, endPts[p].B); + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) + if (g_aPartitionTable[uPartitions][uShape][i] == p) + aIndices[i] = uNumIndices - 1 - aIndices[i]; + } + assert((aIndices[g_aFixUp[uPartitions][uShape][p]] & uHighestIndexBit) == 0); + } + } + else + { + for (size_t p = 0; p <= uPartitions; p++) + { + if (aIndices[g_aFixUp[uPartitions][uShape][p]] & uHighestIndexBit) + { + std::swap(endPts[p].A.r, endPts[p].B.r); + std::swap(endPts[p].A.g, endPts[p].B.g); + std::swap(endPts[p].A.b, endPts[p].B.b); + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) + if (g_aPartitionTable[uPartitions][uShape][i] == p) + aIndices[i] = uNumIndices - 1 - aIndices[i]; + } + assert((aIndices[g_aFixUp[uPartitions][uShape][p]] & uHighestIndexBit) == 0); + + if (aIndices2[0] & uHighestIndexBit2) + { + std::swap(endPts[p].A.a, endPts[p].B.a); + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) + aIndices2[i] = uNumIndices2 - 1 - aIndices2[i]; + } + assert((aIndices2[0] & uHighestIndexBit2) == 0); + } + } +} + +_Use_decl_annotations_ +void D3DX_BC7::EmitBlock(const EncodeParams* pEP, size_t uShape, size_t uRotation, size_t uIndexMode, const LDREndPntPair aEndPts[], const size_t aIndex[], const size_t aIndex2[]) +{ + assert(pEP); + const uint8_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + assert(uPartitions < BC7_MAX_REGIONS); + _Analysis_assume_(uPartitions < BC7_MAX_REGIONS); + + const size_t uPBits = ms_aInfo[pEP->uMode].uPBits; + const size_t uIndexPrec = ms_aInfo[pEP->uMode].uIndexPrec; + const size_t uIndexPrec2 = ms_aInfo[pEP->uMode].uIndexPrec2; + const LDRColorA RGBAPrec = ms_aInfo[pEP->uMode].RGBAPrec; + const LDRColorA RGBAPrecWithP = ms_aInfo[pEP->uMode].RGBAPrecWithP; + size_t i; + size_t uStartBit = 0; + SetBits(uStartBit, pEP->uMode, 0); + SetBits(uStartBit, 1, 1); + SetBits(uStartBit, ms_aInfo[pEP->uMode].uRotationBits, static_cast(uRotation)); + SetBits(uStartBit, ms_aInfo[pEP->uMode].uIndexModeBits, static_cast(uIndexMode)); + SetBits(uStartBit, ms_aInfo[pEP->uMode].uPartitionBits, static_cast(uShape)); + + if (uPBits) + { + const size_t uNumEP = size_t(1 + uPartitions) << 1; + uint8_t aPVote[BC7_MAX_REGIONS << 1] = { 0,0,0,0,0,0 }; + uint8_t aCount[BC7_MAX_REGIONS << 1] = { 0,0,0,0,0,0 }; + for (uint8_t ch = 0; ch < BC7_NUM_CHANNELS; ch++) + { + uint8_t ep = 0; + for (i = 0; i <= uPartitions; i++) + { + if (RGBAPrec[ch] == RGBAPrecWithP[ch]) + { + SetBits(uStartBit, RGBAPrec[ch], aEndPts[i].A[ch]); + SetBits(uStartBit, RGBAPrec[ch], aEndPts[i].B[ch]); + } + else + { + SetBits(uStartBit, RGBAPrec[ch], aEndPts[i].A[ch] >> 1); + SetBits(uStartBit, RGBAPrec[ch], aEndPts[i].B[ch] >> 1); + size_t idx = ep++ * uPBits / uNumEP; + assert(idx < (BC7_MAX_REGIONS << 1)); + _Analysis_assume_(idx < (BC7_MAX_REGIONS << 1)); + aPVote[idx] += aEndPts[i].A[ch] & 0x01; + aCount[idx]++; + idx = ep++ * uPBits / uNumEP; + assert(idx < (BC7_MAX_REGIONS << 1)); + _Analysis_assume_(idx < (BC7_MAX_REGIONS << 1)); + aPVote[idx] += aEndPts[i].B[ch] & 0x01; + aCount[idx]++; + } + } + } + + for (i = 0; i < uPBits; i++) + { + SetBits(uStartBit, 1, aPVote[i] > (aCount[i] >> 1) ? 1 : 0); + } + } + else + { + for (size_t ch = 0; ch < BC7_NUM_CHANNELS; ch++) + { + for (i = 0; i <= uPartitions; i++) + { + SetBits(uStartBit, RGBAPrec[ch], aEndPts[i].A[ch]); + SetBits(uStartBit, RGBAPrec[ch], aEndPts[i].B[ch]); + } + } + } + + const size_t* aI1 = uIndexMode ? aIndex2 : aIndex; + const size_t* aI2 = uIndexMode ? aIndex : aIndex2; + for (i = 0; i < NUM_PIXELS_PER_BLOCK; i++) + { + if (IsFixUpOffset(ms_aInfo[pEP->uMode].uPartitions, uShape, i)) + SetBits(uStartBit, uIndexPrec - 1, static_cast(aI1[i])); + else + SetBits(uStartBit, uIndexPrec, static_cast(aI1[i])); + } + if (uIndexPrec2) + for (i = 0; i < NUM_PIXELS_PER_BLOCK; i++) + SetBits(uStartBit, i ? uIndexPrec2 : uIndexPrec2 - 1, static_cast(aI2[i])); + + assert(uStartBit == 128); +} + +_Use_decl_annotations_ +float D3DX_BC7::Refine(const EncodeParams* pEP, size_t uShape, size_t uRotation, size_t uIndexMode) +{ + assert( pEP ); + assert( uShape < BC7_MAX_SHAPES ); + _Analysis_assume_( uShape < BC7_MAX_SHAPES ); + const LDREndPntPair* aEndPts = pEP->aEndPts[uShape]; + + const size_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + assert( uPartitions < BC7_MAX_REGIONS ); + _Analysis_assume_( uPartitions < BC7_MAX_REGIONS ); + + LDREndPntPair aOrgEndPts[BC7_MAX_REGIONS]; + LDREndPntPair aOptEndPts[BC7_MAX_REGIONS]; + size_t aOrgIdx[NUM_PIXELS_PER_BLOCK]; + size_t aOrgIdx2[NUM_PIXELS_PER_BLOCK]; + size_t aOptIdx[NUM_PIXELS_PER_BLOCK]; + size_t aOptIdx2[NUM_PIXELS_PER_BLOCK]; + float aOrgErr[BC7_MAX_REGIONS]; + float aOptErr[BC7_MAX_REGIONS]; + + for(size_t p = 0; p <= uPartitions; p++) + { + aOrgEndPts[p].A = Quantize(aEndPts[p].A, ms_aInfo[pEP->uMode].RGBAPrecWithP); + aOrgEndPts[p].B = Quantize(aEndPts[p].B, ms_aInfo[pEP->uMode].RGBAPrecWithP); + } + + AssignIndices(pEP, uShape, uIndexMode, aOrgEndPts, aOrgIdx, aOrgIdx2, aOrgErr); + OptimizeEndPoints(pEP, uShape, uIndexMode, aOrgErr, aOrgEndPts, aOptEndPts); + AssignIndices(pEP, uShape, uIndexMode, aOptEndPts, aOptIdx, aOptIdx2, aOptErr); + + float fOrgTotErr = 0, fOptTotErr = 0; + for(size_t p = 0; p <= uPartitions; p++) + { + fOrgTotErr += aOrgErr[p]; + fOptTotErr += aOptErr[p]; + } + if(fOptTotErr < fOrgTotErr) + { + EmitBlock(pEP, uShape, uRotation, uIndexMode, aOptEndPts, aOptIdx, aOptIdx2); + return fOptTotErr; + } + else + { + EmitBlock(pEP, uShape, uRotation, uIndexMode, aOrgEndPts, aOrgIdx, aOrgIdx2); + return fOrgTotErr; + } +} + +_Use_decl_annotations_ +float D3DX_BC7::MapColors(const EncodeParams* pEP, const LDRColorA aColors[], size_t np, size_t uIndexMode, const LDREndPntPair& endPts, float fMinErr) const +{ + assert(pEP); + const uint8_t uIndexPrec = uIndexMode ? ms_aInfo[pEP->uMode].uIndexPrec2 : ms_aInfo[pEP->uMode].uIndexPrec; + const uint8_t uIndexPrec2 = uIndexMode ? ms_aInfo[pEP->uMode].uIndexPrec : ms_aInfo[pEP->uMode].uIndexPrec2; + LDRColorA aPalette[BC7_MAX_INDICES]; + float fTotalErr = 0; + + GeneratePaletteQuantized(pEP, uIndexMode, endPts, aPalette); + for (size_t i = 0; i < np; ++i) + { + fTotalErr += ComputeError(aColors[i], aPalette, uIndexPrec, uIndexPrec2); + if (fTotalErr > fMinErr) // check for early exit + { + fTotalErr = FLT_MAX; + break; + } + } + + return fTotalErr; +} + +_Use_decl_annotations_ +float D3DX_BC7::RoughMSE(EncodeParams* pEP, size_t uShape, size_t uIndexMode) +{ + assert(pEP); + assert(uShape < BC7_MAX_SHAPES); + _Analysis_assume_(uShape < BC7_MAX_SHAPES); + LDREndPntPair* aEndPts = pEP->aEndPts[uShape]; + + const uint8_t uPartitions = ms_aInfo[pEP->uMode].uPartitions; + assert(uPartitions < BC7_MAX_REGIONS); + _Analysis_assume_(uPartitions < BC7_MAX_REGIONS); + + const uint8_t uIndexPrec = uIndexMode ? ms_aInfo[pEP->uMode].uIndexPrec2 : ms_aInfo[pEP->uMode].uIndexPrec; + const uint8_t uIndexPrec2 = uIndexMode ? ms_aInfo[pEP->uMode].uIndexPrec : ms_aInfo[pEP->uMode].uIndexPrec2; + const uint8_t uNumIndices = 1 << uIndexPrec; + const uint8_t uNumIndices2 = 1 << uIndexPrec2; + size_t auPixIdx[NUM_PIXELS_PER_BLOCK]; + LDRColorA aPalette[BC7_MAX_REGIONS][BC7_MAX_INDICES]; + + for (size_t p = 0; p <= uPartitions; p++) + { + size_t np = 0; + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) + { + if (g_aPartitionTable[uPartitions][uShape][i] == p) + { + auPixIdx[np++] = i; + } + } + + // handle simple cases + assert(np > 0); + if (np == 1) + { + aEndPts[p].A = pEP->aLDRPixels[auPixIdx[0]]; + aEndPts[p].B = pEP->aLDRPixels[auPixIdx[0]]; + continue; + } + else if (np == 2) + { + aEndPts[p].A = pEP->aLDRPixels[auPixIdx[0]]; + aEndPts[p].B = pEP->aLDRPixels[auPixIdx[1]]; + continue; + } + + if (uIndexPrec2 == 0) + { + HDRColorA epA, epB; + OptimizeRGBA(pEP->aHDRPixels, &epA, &epB, 4, np, auPixIdx); + epA.Clamp(0.0f, 1.0f); + epB.Clamp(0.0f, 1.0f); + epA *= 255.0f; + epB *= 255.0f; + aEndPts[p].A = epA.ToLDRColorA(); + aEndPts[p].B = epB.ToLDRColorA(); + } + else + { + uint8_t uMinAlpha = 255, uMaxAlpha = 0; + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; ++i) + { + uMinAlpha = std::min(uMinAlpha, pEP->aLDRPixels[auPixIdx[i]].a); + uMaxAlpha = std::max(uMaxAlpha, pEP->aLDRPixels[auPixIdx[i]].a); + } + + HDRColorA epA, epB; + OptimizeRGB(pEP->aHDRPixels, &epA, &epB, 4, np, auPixIdx); + epA.Clamp(0.0f, 1.0f); + epB.Clamp(0.0f, 1.0f); + epA *= 255.0f; + epB *= 255.0f; + aEndPts[p].A = epA.ToLDRColorA(); + aEndPts[p].B = epB.ToLDRColorA(); + aEndPts[p].A.a = uMinAlpha; + aEndPts[p].B.a = uMaxAlpha; + } + } + + if (uIndexPrec2 == 0) + { + for (size_t p = 0; p <= uPartitions; p++) + for (size_t i = 0; i < uNumIndices; i++) + LDRColorA::Interpolate(aEndPts[p].A, aEndPts[p].B, i, i, uIndexPrec, uIndexPrec, aPalette[p][i]); + } + else + { + for (size_t p = 0; p <= uPartitions; p++) + { + for (size_t i = 0; i < uNumIndices; i++) + LDRColorA::InterpolateRGB(aEndPts[p].A, aEndPts[p].B, i, uIndexPrec, aPalette[p][i]); + for (size_t i = 0; i < uNumIndices2; i++) + LDRColorA::InterpolateA(aEndPts[p].A, aEndPts[p].B, i, uIndexPrec2, aPalette[p][i]); + } + } + + float fTotalErr = 0; + for (size_t i = 0; i < NUM_PIXELS_PER_BLOCK; i++) + { + uint8_t uRegion = g_aPartitionTable[uPartitions][uShape][i]; + fTotalErr += ComputeError(pEP->aLDRPixels[i], aPalette[uRegion], uIndexPrec, uIndexPrec2); + } + + return fTotalErr; +} + + +//===================================================================================== +// Entry points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// BC6H Compression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DirectX::D3DXDecodeBC6HU(XMVECTOR *pColor, const uint8_t *pBC) +{ + assert(pColor && pBC); + static_assert(sizeof(D3DX_BC6H) == 16, "D3DX_BC6H should be 16 bytes"); + reinterpret_cast(pBC)->Decode(false, reinterpret_cast(pColor)); +} + +_Use_decl_annotations_ +void DirectX::D3DXDecodeBC6HS(XMVECTOR *pColor, const uint8_t *pBC) +{ + assert(pColor && pBC); + static_assert(sizeof(D3DX_BC6H) == 16, "D3DX_BC6H should be 16 bytes"); + reinterpret_cast(pBC)->Decode(true, reinterpret_cast(pColor)); +} + +_Use_decl_annotations_ +void DirectX::D3DXEncodeBC6HU(uint8_t *pBC, const XMVECTOR *pColor, DWORD flags) +{ + UNREFERENCED_PARAMETER(flags); + assert(pBC && pColor); + static_assert(sizeof(D3DX_BC6H) == 16, "D3DX_BC6H should be 16 bytes"); + reinterpret_cast(pBC)->Encode(false, reinterpret_cast(pColor)); +} + +_Use_decl_annotations_ +void DirectX::D3DXEncodeBC6HS(uint8_t *pBC, const XMVECTOR *pColor, DWORD flags) +{ + UNREFERENCED_PARAMETER(flags); + assert(pBC && pColor); + static_assert(sizeof(D3DX_BC6H) == 16, "D3DX_BC6H should be 16 bytes"); + reinterpret_cast(pBC)->Encode(true, reinterpret_cast(pColor)); +} + + +//------------------------------------------------------------------------------------- +// BC7 Compression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DirectX::D3DXDecodeBC7(XMVECTOR *pColor, const uint8_t *pBC) +{ + assert(pColor && pBC); + static_assert(sizeof(D3DX_BC7) == 16, "D3DX_BC7 should be 16 bytes"); + reinterpret_cast(pBC)->Decode(reinterpret_cast(pColor)); +} + +_Use_decl_annotations_ +void DirectX::D3DXEncodeBC7(uint8_t *pBC, const XMVECTOR *pColor, DWORD flags) +{ + assert(pBC && pColor); + static_assert(sizeof(D3DX_BC7) == 16, "D3DX_BC7 should be 16 bytes"); + reinterpret_cast(pBC)->Encode(flags, reinterpret_cast(pColor)); +} diff --git a/deps/DirectXTex/DirectXTex/BCDirectCompute.cpp b/deps/DirectXTex/DirectXTex/BCDirectCompute.cpp new file mode 100644 index 0000000..5a063b7 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/BCDirectCompute.cpp @@ -0,0 +1,613 @@ +//------------------------------------------------------------------------------------- +// BCDirectCompute.cpp +// +// Direct3D 11 Compute Shader BC Compressor +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +#include "BCDirectCompute.h" + +#if defined(_DEBUG) || defined(PROFILE) +#pragma comment(lib,"dxguid.lib") +#endif + +using namespace DirectX; +using Microsoft::WRL::ComPtr; + +namespace +{ + #include "Shaders\Compiled\BC7Encode_EncodeBlockCS.inc" + #include "Shaders\Compiled\BC7Encode_TryMode02CS.inc" + #include "Shaders\Compiled\BC7Encode_TryMode137CS.inc" + #include "Shaders\Compiled\BC7Encode_TryMode456CS.inc" + #include "Shaders\Compiled\BC6HEncode_EncodeBlockCS.inc" + #include "Shaders\Compiled\BC6HEncode_TryModeG10CS.inc" + #include "Shaders\Compiled\BC6HEncode_TryModeLE10CS.inc" + + struct BufferBC6HBC7 + { + UINT color[4]; + }; + + struct ConstantsBC6HBC7 + { + UINT tex_width; + UINT num_block_x; + UINT format; + UINT mode_id; + UINT start_block_id; + UINT num_total_blocks; + float alpha_weight; + UINT reserved; + }; + + static_assert( sizeof(ConstantsBC6HBC7) == sizeof(UINT)*8, "Constant buffer size mismatch" ); + + inline void RunComputeShader( ID3D11DeviceContext* pContext, + ID3D11ComputeShader* shader, + ID3D11ShaderResourceView** pSRVs, + UINT srvCount, + ID3D11Buffer* pCB, + ID3D11UnorderedAccessView* pUAV, + UINT X ) + { + // Force UAV to nullptr before setting SRV since we are swapping buffers + ID3D11UnorderedAccessView* nullUAV = nullptr; + pContext->CSSetUnorderedAccessViews( 0, 1, &nullUAV, nullptr ); + + pContext->CSSetShader( shader, nullptr, 0 ); + pContext->CSSetShaderResources( 0, srvCount, pSRVs ); + pContext->CSSetUnorderedAccessViews( 0, 1, &pUAV, nullptr ); + pContext->CSSetConstantBuffers( 0, 1, &pCB ); + pContext->Dispatch( X, 1, 1 ); + } + + inline void ResetContext( ID3D11DeviceContext* pContext ) + { + ID3D11UnorderedAccessView* nullUAV = nullptr; + pContext->CSSetUnorderedAccessViews( 0, 1, &nullUAV, nullptr ); + + ID3D11ShaderResourceView* nullSRV[3] = { nullptr, nullptr, nullptr }; + pContext->CSSetShaderResources( 0, 3, nullSRV ); + + ID3D11Buffer* nullBuffer[1] = { nullptr }; + pContext->CSSetConstantBuffers( 0, 1, nullBuffer ); + } +}; + +GPUCompressBC::GPUCompressBC() : + m_bcformat(DXGI_FORMAT_UNKNOWN), + m_srcformat(DXGI_FORMAT_UNKNOWN), + m_alphaWeight(1.f), + m_width(0), + m_height(0) +{ +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT GPUCompressBC::Initialize(ID3D11Device* pDevice) +{ + if (!pDevice) + return E_INVALIDARG; + + // Check for DirectCompute support + D3D_FEATURE_LEVEL fl = pDevice->GetFeatureLevel(); + + if (fl < D3D_FEATURE_LEVEL_10_0) + { + // DirectCompute not supported on Feature Level 9.x hardware + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + if (fl < D3D_FEATURE_LEVEL_11_0) + { + // DirectCompute support on Feature Level 10.x hardware is optional, and this function needs it + D3D11_FEATURE_DATA_D3D10_X_HARDWARE_OPTIONS hwopts; + HRESULT hr = pDevice->CheckFeatureSupport(D3D11_FEATURE_D3D10_X_HARDWARE_OPTIONS, &hwopts, sizeof(hwopts)); + if (FAILED(hr)) + { + memset(&hwopts, 0, sizeof(hwopts)); + } + + if (!hwopts.ComputeShaders_Plus_RawAndStructuredBuffers_Via_Shader_4_x) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } + + // Save a device reference and obtain immediate context + m_device = pDevice; + + pDevice->GetImmediateContext(m_context.ReleaseAndGetAddressOf()); + assert(m_context); + + //--- Create compute shader library: BC6H ----------------------------------------- + + // Modes 11-14 + HRESULT hr = pDevice->CreateComputeShader(BC6HEncode_TryModeG10CS, sizeof(BC6HEncode_TryModeG10CS), nullptr, m_BC6H_tryModeG10CS.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + return hr; + + // Modes 1-10 + hr = pDevice->CreateComputeShader(BC6HEncode_TryModeLE10CS, sizeof(BC6HEncode_TryModeLE10CS), nullptr, m_BC6H_tryModeLE10CS.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + return hr; + + // Encode + hr = pDevice->CreateComputeShader(BC6HEncode_EncodeBlockCS, sizeof(BC6HEncode_EncodeBlockCS), nullptr, m_BC6H_encodeBlockCS.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + return hr; + + //--- Create compute shader library: BC7 ------------------------------------------ + + // Modes 4, 5, 6 + hr = pDevice->CreateComputeShader(BC7Encode_TryMode456CS, sizeof(BC7Encode_TryMode456CS), nullptr, m_BC7_tryMode456CS.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + return hr; + + // Modes 1, 3, 7 + hr = pDevice->CreateComputeShader(BC7Encode_TryMode137CS, sizeof(BC7Encode_TryMode137CS), nullptr, m_BC7_tryMode137CS.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + return hr; + + // Modes 0, 2 + hr = pDevice->CreateComputeShader(BC7Encode_TryMode02CS, sizeof(BC7Encode_TryMode02CS), nullptr, m_BC7_tryMode02CS.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + return hr; + + // Encode + hr = pDevice->CreateComputeShader(BC7Encode_EncodeBlockCS, sizeof(BC7Encode_EncodeBlockCS), nullptr, m_BC7_encodeBlockCS.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + return hr; + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +HRESULT GPUCompressBC::Prepare(size_t width, size_t height, DWORD flags, DXGI_FORMAT format, float alphaWeight) +{ + if (!width || !height || alphaWeight < 0.f) + return E_INVALIDARG; + + if ((width > UINT32_MAX) || (height > UINT32_MAX)) + return E_INVALIDARG; + + m_width = width; + m_height = height; + + m_alphaWeight = alphaWeight; + + if (flags & TEX_COMPRESS_BC7_QUICK) + { + m_bc7_mode02 = false; + m_bc7_mode137 = false; + } + else + { + m_bc7_mode02 = (flags & TEX_COMPRESS_BC7_USE_3SUBSETS) != 0; + m_bc7_mode137 = true; + } + + size_t xblocks = std::max(1, (width + 3) >> 2); + size_t yblocks = std::max(1, (height + 3) >> 2); + size_t num_blocks = xblocks * yblocks; + + switch (format) + { + // BC6H GPU compressor takes RGBAF32 as input + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + m_srcformat = DXGI_FORMAT_R32G32B32A32_FLOAT; + break; + + // BC7 GPU compressor takes RGBA32 as input + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + m_srcformat = DXGI_FORMAT_R8G8B8A8_UNORM; + break; + + case DXGI_FORMAT_BC7_UNORM_SRGB: + m_srcformat = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + break; + + default: + m_bcformat = m_srcformat = DXGI_FORMAT_UNKNOWN; + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + m_bcformat = format; + + auto pDevice = m_device.Get(); + if (!pDevice) + return E_POINTER; + + // Create structured buffers + size_t bufferSize = num_blocks * sizeof(BufferBC6HBC7); + { + D3D11_BUFFER_DESC desc = {}; + desc.BindFlags = D3D11_BIND_UNORDERED_ACCESS | D3D11_BIND_SHADER_RESOURCE; + desc.Usage = D3D11_USAGE_DEFAULT; + desc.MiscFlags = D3D11_RESOURCE_MISC_BUFFER_STRUCTURED; + desc.StructureByteStride = sizeof(BufferBC6HBC7); + desc.ByteWidth = static_cast(bufferSize); + + HRESULT hr = pDevice->CreateBuffer(&desc, nullptr, m_output.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + + hr = pDevice->CreateBuffer(&desc, nullptr, m_err1.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + + hr = pDevice->CreateBuffer(&desc, nullptr, m_err2.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + } + + // Create staging output buffer + { + D3D11_BUFFER_DESC desc = {}; + desc.Usage = D3D11_USAGE_STAGING; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.ByteWidth = static_cast(bufferSize); + + HRESULT hr = pDevice->CreateBuffer(&desc, nullptr, m_outputCPU.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + } + + // Create constant buffer + { + D3D11_BUFFER_DESC desc = {}; + desc.BindFlags = D3D11_BIND_CONSTANT_BUFFER; + desc.Usage = D3D11_USAGE_DYNAMIC; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; + desc.ByteWidth = sizeof(ConstantsBC6HBC7); + + HRESULT hr = pDevice->CreateBuffer(&desc, nullptr, m_constBuffer.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + } + + // Create shader resource views + { + D3D11_SHADER_RESOURCE_VIEW_DESC desc = {}; + desc.Buffer.NumElements = static_cast(num_blocks); + desc.ViewDimension = D3D11_SRV_DIMENSION_BUFFER; + + HRESULT hr = pDevice->CreateShaderResourceView(m_err1.Get(), &desc, m_err1SRV.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + + hr = pDevice->CreateShaderResourceView(m_err2.Get(), &desc, m_err2SRV.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + } + + // Create unordered access views + { + D3D11_UNORDERED_ACCESS_VIEW_DESC desc = {}; + desc.Buffer.NumElements = static_cast(num_blocks); + desc.ViewDimension = D3D11_UAV_DIMENSION_BUFFER; + + HRESULT hr = pDevice->CreateUnorderedAccessView(m_output.Get(), &desc, m_outputUAV.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + + hr = pDevice->CreateUnorderedAccessView(m_err1.Get(), &desc, m_err1UAV.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + + hr = pDevice->CreateUnorderedAccessView(m_err2.Get(), &desc, m_err2UAV.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +HRESULT GPUCompressBC::Compress(const Image& srcImage, const Image& destImage) +{ + if (!srcImage.pixels || !destImage.pixels) + return E_INVALIDARG; + + if (srcImage.width != destImage.width + || srcImage.height != destImage.height + || srcImage.width != m_width + || srcImage.height != m_height + || srcImage.format != m_srcformat + || destImage.format != m_bcformat) + { + return E_UNEXPECTED; + } + + //--- Create input texture -------------------------------------------------------- + auto pDevice = m_device.Get(); + if (!pDevice) + return E_POINTER; + + // We need to avoid the hardware doing additional colorspace conversion + DXGI_FORMAT inputFormat = (m_srcformat == DXGI_FORMAT_R8G8B8A8_UNORM_SRGB) ? DXGI_FORMAT_R8G8B8A8_UNORM : m_srcformat; + + ComPtr sourceTex; + { + D3D11_TEXTURE2D_DESC desc = {}; + desc.Width = static_cast(srcImage.width); + desc.Height = static_cast(srcImage.height); + desc.MipLevels = 1; + desc.ArraySize = 1; + desc.Format = inputFormat; + desc.SampleDesc.Count = 1; + desc.Usage = D3D11_USAGE_DEFAULT; + desc.BindFlags = D3D11_BIND_SHADER_RESOURCE; + + D3D11_SUBRESOURCE_DATA initData; + initData.pSysMem = srcImage.pixels; + initData.SysMemPitch = static_cast(srcImage.rowPitch); + initData.SysMemSlicePitch = static_cast(srcImage.slicePitch); + + HRESULT hr = pDevice->CreateTexture2D(&desc, &initData, sourceTex.GetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + } + + ComPtr sourceSRV; + { + D3D11_SHADER_RESOURCE_VIEW_DESC desc = {}; + desc.Texture2D.MipLevels = 1; + desc.Format = inputFormat; + desc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + + HRESULT hr = pDevice->CreateShaderResourceView(sourceTex.Get(), &desc, sourceSRV.GetAddressOf()); + if (FAILED(hr)) + { + return hr; + } + } + + //--- Compress using DirectCompute ------------------------------------------------ + bool isbc7 = false; + switch (m_bcformat) + { + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + break; + + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + isbc7 = true; + break; + + default: + return E_UNEXPECTED; + } + + const UINT MAX_BLOCK_BATCH = 64; + + auto pContext = m_context.Get(); + if (!pContext) + return E_UNEXPECTED; + + size_t xblocks = std::max(1, (m_width + 3) >> 2); + size_t yblocks = std::max(1, (m_height + 3) >> 2); + + UINT num_total_blocks = static_cast(xblocks * yblocks); + UINT num_blocks = num_total_blocks; + int start_block_id = 0; + while (num_blocks > 0) + { + UINT n = std::min(num_blocks, MAX_BLOCK_BATCH); + UINT uThreadGroupCount = n; + + { + D3D11_MAPPED_SUBRESOURCE mapped; + HRESULT hr = pContext->Map(m_constBuffer.Get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mapped); + if (FAILED(hr)) + return hr; + + ConstantsBC6HBC7 param; + param.tex_width = static_cast(srcImage.width); + param.num_block_x = static_cast(xblocks); + param.format = m_bcformat; + param.mode_id = 0; + param.start_block_id = start_block_id; + param.num_total_blocks = num_total_blocks; + param.alpha_weight = m_alphaWeight; + memcpy(mapped.pData, ¶m, sizeof(param)); + + pContext->Unmap(m_constBuffer.Get(), 0); + } + + if (isbc7) + { + //--- BC7 ----------------------------------------------------------------- + ID3D11ShaderResourceView* pSRVs[] = { sourceSRV.Get(), nullptr }; + RunComputeShader(pContext, m_BC7_tryMode456CS.Get(), pSRVs, 2, m_constBuffer.Get(), + m_err1UAV.Get(), std::max((uThreadGroupCount + 3) / 4, 1)); + + if (m_bc7_mode137) + { + for (UINT i = 0; i < 3; ++i) + { + static const UINT modes[] = { 1, 3, 7 }; + + // Mode 1: err1 -> err2 + // Mode 3: err2 -> err1 + // Mode 7: err1 -> err2 + { + D3D11_MAPPED_SUBRESOURCE mapped; + HRESULT hr = pContext->Map(m_constBuffer.Get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mapped); + if (FAILED(hr)) + { + ResetContext(pContext); + return hr; + } + + ConstantsBC6HBC7 param; + param.tex_width = static_cast(srcImage.width); + param.num_block_x = static_cast(xblocks); + param.format = m_bcformat; + param.mode_id = modes[i]; + param.start_block_id = start_block_id; + param.num_total_blocks = num_total_blocks; + param.alpha_weight = m_alphaWeight; + memcpy(mapped.pData, ¶m, sizeof(param)); + pContext->Unmap(m_constBuffer.Get(), 0); + } + + pSRVs[1] = (i & 1) ? m_err2SRV.Get() : m_err1SRV.Get(); + RunComputeShader(pContext, m_BC7_tryMode137CS.Get(), pSRVs, 2, m_constBuffer.Get(), + (i & 1) ? m_err1UAV.Get() : m_err2UAV.Get(), uThreadGroupCount); + } + } + + if (m_bc7_mode02) + { + // 3 subset modes tend to be used rarely and add significant compression time + for (UINT i = 0; i < 2; ++i) + { + static const UINT modes[] = { 0, 2 }; + // Mode 0: err2 -> err1 + // Mode 2: err1 -> err2 + { + D3D11_MAPPED_SUBRESOURCE mapped; + HRESULT hr = pContext->Map(m_constBuffer.Get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mapped); + if (FAILED(hr)) + { + ResetContext(pContext); + return hr; + } + + ConstantsBC6HBC7 param; + param.tex_width = static_cast(srcImage.width); + param.num_block_x = static_cast(xblocks); + param.format = m_bcformat; + param.mode_id = modes[i]; + param.start_block_id = start_block_id; + param.num_total_blocks = num_total_blocks; + param.alpha_weight = m_alphaWeight; + memcpy(mapped.pData, ¶m, sizeof(param)); + pContext->Unmap(m_constBuffer.Get(), 0); + } + + pSRVs[1] = (i & 1) ? m_err1SRV.Get() : m_err2SRV.Get(); + RunComputeShader(pContext, m_BC7_tryMode02CS.Get(), pSRVs, 2, m_constBuffer.Get(), + (i & 1) ? m_err2UAV.Get() : m_err1UAV.Get(), uThreadGroupCount); + } + } + + pSRVs[1] = (m_bc7_mode02 || m_bc7_mode137) ? m_err2SRV.Get() : m_err1SRV.Get(); + RunComputeShader(pContext, m_BC7_encodeBlockCS.Get(), pSRVs, 2, m_constBuffer.Get(), + m_outputUAV.Get(), std::max((uThreadGroupCount + 3) / 4, 1)); + } + else + { + //--- BC6H ---------------------------------------------------------------- + ID3D11ShaderResourceView* pSRVs[] = { sourceSRV.Get(), nullptr }; + RunComputeShader(pContext, m_BC6H_tryModeG10CS.Get(), pSRVs, 2, m_constBuffer.Get(), + m_err1UAV.Get(), std::max((uThreadGroupCount + 3) / 4, 1)); + + for (UINT i = 0; i < 10; ++i) + { + { + D3D11_MAPPED_SUBRESOURCE mapped; + HRESULT hr = pContext->Map(m_constBuffer.Get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mapped); + if (FAILED(hr)) + { + ResetContext(pContext); + return hr; + } + + ConstantsBC6HBC7 param; + param.tex_width = static_cast(srcImage.width); + param.num_block_x = static_cast(xblocks); + param.format = m_bcformat; + param.mode_id = i; + param.start_block_id = start_block_id; + param.num_total_blocks = num_total_blocks; + memcpy(mapped.pData, ¶m, sizeof(param)); + pContext->Unmap(m_constBuffer.Get(), 0); + } + + pSRVs[1] = (i & 1) ? m_err2SRV.Get() : m_err1SRV.Get(); + RunComputeShader(pContext, m_BC6H_tryModeLE10CS.Get(), pSRVs, 2, m_constBuffer.Get(), + (i & 1) ? m_err1UAV.Get() : m_err2UAV.Get(), std::max((uThreadGroupCount + 1) / 2, 1)); + } + + pSRVs[1] = m_err1SRV.Get(); + RunComputeShader(pContext, m_BC6H_encodeBlockCS.Get(), pSRVs, 2, m_constBuffer.Get(), + m_outputUAV.Get(), std::max((uThreadGroupCount + 1) / 2, 1)); + } + + start_block_id += n; + num_blocks -= n; + } + + ResetContext(pContext); + + //--- Copy output texture back to CPU --------------------------------------------- + + pContext->CopyResource(m_outputCPU.Get(), m_output.Get()); + + D3D11_MAPPED_SUBRESOURCE mapped; + HRESULT hr = pContext->Map(m_outputCPU.Get(), 0, D3D11_MAP_READ, 0, &mapped); + if (SUCCEEDED(hr)) + { + const uint8_t *pSrc = reinterpret_cast(mapped.pData); + uint8_t *pDest = destImage.pixels; + + size_t pitch = xblocks * sizeof(BufferBC6HBC7); + + size_t rows = std::max(1, (destImage.height + 3) >> 2); + + for (size_t h = 0; h < rows; ++h) + { + memcpy(pDest, pSrc, destImage.rowPitch); + + pSrc += pitch; + pDest += destImage.rowPitch; + } + + pContext->Unmap(m_outputCPU.Get(), 0); + } + + return hr; +} \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/BCDirectCompute.h b/deps/DirectXTex/DirectXTex/BCDirectCompute.h new file mode 100644 index 0000000..bedc982 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/BCDirectCompute.h @@ -0,0 +1,68 @@ +//------------------------------------------------------------------------------------- +// BCDirectCompute.h +// +// Direct3D 11 Compute Shader BC Compressor +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +//------------------------------------------------------------------------------------- + +#pragma once + +namespace DirectX +{ + +class GPUCompressBC +{ +public: + GPUCompressBC(); + + HRESULT Initialize( _In_ ID3D11Device* pDevice ); + + HRESULT Prepare( size_t width, size_t height, DWORD flags, DXGI_FORMAT format, float alphaWeight ); + + HRESULT Compress( const Image& srcImage, const Image& destImage ); + + DXGI_FORMAT GetSourceFormat() const { return m_srcformat; } + +private: + DXGI_FORMAT m_bcformat; + DXGI_FORMAT m_srcformat; + float m_alphaWeight; + bool m_bc7_mode02; + bool m_bc7_mode137; + size_t m_width; + size_t m_height; + + Microsoft::WRL::ComPtr m_device; + Microsoft::WRL::ComPtr m_context; + + Microsoft::WRL::ComPtr m_err1; + Microsoft::WRL::ComPtr m_err1UAV; + Microsoft::WRL::ComPtr m_err1SRV; + + Microsoft::WRL::ComPtr m_err2; + Microsoft::WRL::ComPtr m_err2UAV; + Microsoft::WRL::ComPtr m_err2SRV; + + Microsoft::WRL::ComPtr m_output; + Microsoft::WRL::ComPtr m_outputCPU; + Microsoft::WRL::ComPtr m_outputUAV; + Microsoft::WRL::ComPtr m_constBuffer; + + // Compute shader library + Microsoft::WRL::ComPtr m_BC6H_tryModeG10CS; + Microsoft::WRL::ComPtr m_BC6H_tryModeLE10CS; + Microsoft::WRL::ComPtr m_BC6H_encodeBlockCS; + + Microsoft::WRL::ComPtr m_BC7_tryMode456CS; + Microsoft::WRL::ComPtr m_BC7_tryMode137CS; + Microsoft::WRL::ComPtr m_BC7_tryMode02CS; + Microsoft::WRL::ComPtr m_BC7_encodeBlockCS; +}; + +}; // namespace \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DDS.h b/deps/DirectXTex/DirectXTex/DDS.h new file mode 100644 index 0000000..9d85587 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DDS.h @@ -0,0 +1,247 @@ +//-------------------------------------------------------------------------------------- +// dds.h +// +// This header defines constants and structures that are useful when parsing +// DDS files. DDS files were originally designed to use several structures +// and constants that are native to DirectDraw and are defined in ddraw.h, +// such as DDSURFACEDESC2 and DDSCAPS2. This file defines similar +// (compatible) constants and structures so that one can use DDS files +// without needing to include ddraw.h. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//-------------------------------------------------------------------------------------- + +#pragma once + +#if defined(_XBOX_ONE) && defined(_TITLE) +#include +#else +#include +#endif + +#include + +namespace DirectX +{ + +#pragma pack(push,1) + +const uint32_t DDS_MAGIC = 0x20534444; // "DDS " + +struct DDS_PIXELFORMAT +{ + uint32_t dwSize; + uint32_t dwFlags; + uint32_t dwFourCC; + uint32_t dwRGBBitCount; + uint32_t dwRBitMask; + uint32_t dwGBitMask; + uint32_t dwBBitMask; + uint32_t dwABitMask; +}; + +#define DDS_FOURCC 0x00000004 // DDPF_FOURCC +#define DDS_RGB 0x00000040 // DDPF_RGB +#define DDS_RGBA 0x00000041 // DDPF_RGB | DDPF_ALPHAPIXELS +#define DDS_LUMINANCE 0x00020000 // DDPF_LUMINANCE +#define DDS_LUMINANCEA 0x00020001 // DDPF_LUMINANCE | DDPF_ALPHAPIXELS +#define DDS_ALPHA 0x00000002 // DDPF_ALPHA +#define DDS_PAL8 0x00000020 // DDPF_PALETTEINDEXED8 +#define DDS_PAL8A 0x00000021 // DDPF_PALETTEINDEXED8 | DDPF_ALPHAPIXELS +#define DDS_BUMPDUDV 0x00080000 // DDPF_BUMPDUDV + +#ifndef MAKEFOURCC + #define MAKEFOURCC(ch0, ch1, ch2, ch3) \ + ((uint32_t)(uint8_t)(ch0) | ((uint32_t)(uint8_t)(ch1) << 8) | \ + ((uint32_t)(uint8_t)(ch2) << 16) | ((uint32_t)(uint8_t)(ch3) << 24 )) +#endif /* defined(MAKEFOURCC) */ + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_DXT1 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','1'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_DXT2 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','2'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_DXT3 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','3'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_DXT4 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','4'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_DXT5 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','5'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_BC4_UNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','4','U'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_BC4_SNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','4','S'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_BC5_UNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','5','U'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_BC5_SNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','5','S'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_R8G8_B8G8 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('R','G','B','G'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_G8R8_G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('G','R','G','B'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_YUY2 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('Y','U','Y','2'), 0, 0, 0, 0, 0 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_A8R8G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x00ff0000, 0x0000ff00, 0x000000ff, 0xff000000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_X8R8G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00000000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_A8B8G8R8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_X8B8G8R8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0x000000ff, 0x0000ff00, 0x00ff0000, 0x00000000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_G16R16 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0x0000ffff, 0xffff0000, 0x00000000, 0x00000000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_R5G6B5 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 16, 0x0000f800, 0x000007e0, 0x0000001f, 0x00000000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_A1R5G5B5 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x00007c00, 0x000003e0, 0x0000001f, 0x00008000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_A4R4G4B4 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x00000f00, 0x000000f0, 0x0000000f, 0x0000f000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_R8G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 24, 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00000000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_L8 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCE, 0, 8, 0xff, 0x00, 0x00, 0x00 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_L16 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCE, 0, 16, 0xffff, 0x0000, 0x0000, 0x0000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_A8L8 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCEA, 0, 16, 0x00ff, 0x0000, 0x0000, 0xff00 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_A8L8_ALT = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCEA, 0, 8, 0x00ff, 0x0000, 0x0000, 0xff00 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_A8 = + { sizeof(DDS_PIXELFORMAT), DDS_ALPHA, 0, 8, 0x00, 0x00, 0x00, 0xff }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_V8U8 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 16, 0x00ff, 0xff00, 0x0000, 0x0000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_Q8W8V8U8 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 32, 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; + +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_V16U16 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 32, 0x0000ffff, 0xffff0000, 0x00000000, 0x00000000 }; + +// D3DFMT_A2R10G10B10/D3DFMT_A2B10G10R10 should be written using DX10 extension to avoid D3DX 10:10:10:2 reversal issue + +// This indicates the DDS_HEADER_DXT10 extension is present (the format is in dxgiFormat) +extern __declspec(selectany) const DDS_PIXELFORMAT DDSPF_DX10 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','1','0'), 0, 0, 0, 0, 0 }; + +#define DDS_HEADER_FLAGS_TEXTURE 0x00001007 // DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT +#define DDS_HEADER_FLAGS_MIPMAP 0x00020000 // DDSD_MIPMAPCOUNT +#define DDS_HEADER_FLAGS_VOLUME 0x00800000 // DDSD_DEPTH +#define DDS_HEADER_FLAGS_PITCH 0x00000008 // DDSD_PITCH +#define DDS_HEADER_FLAGS_LINEARSIZE 0x00080000 // DDSD_LINEARSIZE + +#define DDS_HEIGHT 0x00000002 // DDSD_HEIGHT +#define DDS_WIDTH 0x00000004 // DDSD_WIDTH + +#define DDS_SURFACE_FLAGS_TEXTURE 0x00001000 // DDSCAPS_TEXTURE +#define DDS_SURFACE_FLAGS_MIPMAP 0x00400008 // DDSCAPS_COMPLEX | DDSCAPS_MIPMAP +#define DDS_SURFACE_FLAGS_CUBEMAP 0x00000008 // DDSCAPS_COMPLEX + +#define DDS_CUBEMAP_POSITIVEX 0x00000600 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEX +#define DDS_CUBEMAP_NEGATIVEX 0x00000a00 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEX +#define DDS_CUBEMAP_POSITIVEY 0x00001200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEY +#define DDS_CUBEMAP_NEGATIVEY 0x00002200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEY +#define DDS_CUBEMAP_POSITIVEZ 0x00004200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEZ +#define DDS_CUBEMAP_NEGATIVEZ 0x00008200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEZ + +#define DDS_CUBEMAP_ALLFACES ( DDS_CUBEMAP_POSITIVEX | DDS_CUBEMAP_NEGATIVEX |\ + DDS_CUBEMAP_POSITIVEY | DDS_CUBEMAP_NEGATIVEY |\ + DDS_CUBEMAP_POSITIVEZ | DDS_CUBEMAP_NEGATIVEZ ) + +#define DDS_CUBEMAP 0x00000200 // DDSCAPS2_CUBEMAP + +#define DDS_FLAGS_VOLUME 0x00200000 // DDSCAPS2_VOLUME + +// Subset here matches D3D10_RESOURCE_DIMENSION and D3D11_RESOURCE_DIMENSION +enum DDS_RESOURCE_DIMENSION +{ + DDS_DIMENSION_TEXTURE1D = 2, + DDS_DIMENSION_TEXTURE2D = 3, + DDS_DIMENSION_TEXTURE3D = 4, +}; + +// Subset here matches D3D10_RESOURCE_MISC_FLAG and D3D11_RESOURCE_MISC_FLAG +enum DDS_RESOURCE_MISC_FLAG +{ + DDS_RESOURCE_MISC_TEXTURECUBE = 0x4L, +}; + +enum DDS_MISC_FLAGS2 +{ + DDS_MISC_FLAGS2_ALPHA_MODE_MASK = 0x7L, +}; + +enum DDS_ALPHA_MODE +{ + DDS_ALPHA_MODE_UNKNOWN = 0, + DDS_ALPHA_MODE_STRAIGHT = 1, + DDS_ALPHA_MODE_PREMULTIPLIED = 2, + DDS_ALPHA_MODE_OPAQUE = 3, + DDS_ALPHA_MODE_CUSTOM = 4, +}; + +struct DDS_HEADER +{ + uint32_t dwSize; + uint32_t dwFlags; + uint32_t dwHeight; + uint32_t dwWidth; + uint32_t dwPitchOrLinearSize; + uint32_t dwDepth; // only if DDS_HEADER_FLAGS_VOLUME is set in dwFlags + uint32_t dwMipMapCount; + uint32_t dwReserved1[11]; + DDS_PIXELFORMAT ddspf; + uint32_t dwCaps; + uint32_t dwCaps2; + uint32_t dwCaps3; + uint32_t dwCaps4; + uint32_t dwReserved2; +}; + +struct DDS_HEADER_DXT10 +{ + DXGI_FORMAT dxgiFormat; + uint32_t resourceDimension; + uint32_t miscFlag; // see DDS_RESOURCE_MISC_FLAG + uint32_t arraySize; + uint32_t miscFlags2; // see DDS_MISC_FLAGS2 +}; + +#pragma pack(pop) + +static_assert( sizeof(DDS_HEADER) == 124, "DDS Header size mismatch" ); +static_assert( sizeof(DDS_HEADER_DXT10) == 20, "DDS DX10 Extended Header size mismatch"); + +}; // namespace diff --git a/deps/DirectXTex/DirectXTex/DirectXTex.h b/deps/DirectXTex/DirectXTex/DirectXTex.h new file mode 100644 index 0000000..f4a55d5 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex.h @@ -0,0 +1,709 @@ +//------------------------------------------------------------------------------------- +// DirectXTex.h +// +// DirectX Texture Library +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#pragma once + +#include + +#include +#include +#include + +#if !defined(__d3d11_h__) && !defined(__d3d11_x_h__) && !defined(__d3d12_h__) && !defined(__d3d12_x_h__) +#if defined(_XBOX_ONE) && defined(_TITLE) +#include +#define DCOMMON_H_INCLUDED +#else +#include +#endif +#endif + +#include + +#include + +#define DIRECTX_TEX_VERSION 151 + +struct IWICImagingFactory; +struct IWICMetadataQueryReader; + + +namespace DirectX +{ + + //--------------------------------------------------------------------------------- + // DXGI Format Utilities + bool __cdecl IsValid( _In_ DXGI_FORMAT fmt ); + bool __cdecl IsCompressed( _In_ DXGI_FORMAT fmt ); + bool __cdecl IsPacked( _In_ DXGI_FORMAT fmt ); + bool __cdecl IsVideo( _In_ DXGI_FORMAT fmt ); + bool __cdecl IsPlanar( _In_ DXGI_FORMAT fmt ); + bool __cdecl IsPalettized( _In_ DXGI_FORMAT fmt ); + bool __cdecl IsDepthStencil(_In_ DXGI_FORMAT fmt ); + bool __cdecl IsSRGB( _In_ DXGI_FORMAT fmt ); + bool __cdecl IsTypeless( _In_ DXGI_FORMAT fmt, _In_ bool partialTypeless = true ); + + bool __cdecl HasAlpha( _In_ DXGI_FORMAT fmt ); + + size_t __cdecl BitsPerPixel( _In_ DXGI_FORMAT fmt ); + + size_t __cdecl BitsPerColor( _In_ DXGI_FORMAT fmt ); + + enum CP_FLAGS + { + CP_FLAGS_NONE = 0x0, // Normal operation + CP_FLAGS_LEGACY_DWORD = 0x1, // Assume pitch is DWORD aligned instead of BYTE aligned + CP_FLAGS_PARAGRAPH = 0x2, // Assume pitch is 16-byte aligned instead of BYTE aligned + CP_FLAGS_YMM = 0x4, // Assume pitch is 32-byte aligned instead of BYTE aligned + CP_FLAGS_ZMM = 0x8, // Assume pitch is 64-byte aligned instead of BYTE aligned + CP_FLAGS_PAGE4K = 0x200, // Assume pitch is 4096-byte aligned instead of BYTE aligned + CP_FLAGS_BAD_DXTN_TAILS = 0x1000, // BC formats with malformed mipchain blocks smaller than 4x4 + CP_FLAGS_24BPP = 0x10000, // Override with a legacy 24 bits-per-pixel format size + CP_FLAGS_16BPP = 0x20000, // Override with a legacy 16 bits-per-pixel format size + CP_FLAGS_8BPP = 0x40000, // Override with a legacy 8 bits-per-pixel format size + }; + + void __cdecl ComputePitch( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, + _Out_ size_t& rowPitch, _Out_ size_t& slicePitch, _In_ DWORD flags = CP_FLAGS_NONE ); + + size_t __cdecl ComputeScanlines( _In_ DXGI_FORMAT fmt, _In_ size_t height ); + + DXGI_FORMAT __cdecl MakeSRGB( _In_ DXGI_FORMAT fmt ); + DXGI_FORMAT __cdecl MakeTypeless( _In_ DXGI_FORMAT fmt ); + DXGI_FORMAT __cdecl MakeTypelessUNORM( _In_ DXGI_FORMAT fmt ); + DXGI_FORMAT __cdecl MakeTypelessFLOAT( _In_ DXGI_FORMAT fmt ); + + //--------------------------------------------------------------------------------- + // Texture metadata + enum TEX_DIMENSION + // Subset here matches D3D10_RESOURCE_DIMENSION and D3D11_RESOURCE_DIMENSION + { + TEX_DIMENSION_TEXTURE1D = 2, + TEX_DIMENSION_TEXTURE2D = 3, + TEX_DIMENSION_TEXTURE3D = 4, + }; + + enum TEX_MISC_FLAG + // Subset here matches D3D10_RESOURCE_MISC_FLAG and D3D11_RESOURCE_MISC_FLAG + { + TEX_MISC_TEXTURECUBE = 0x4L, + }; + + enum TEX_MISC_FLAG2 + { + TEX_MISC2_ALPHA_MODE_MASK = 0x7L, + }; + + enum TEX_ALPHA_MODE + // Matches DDS_ALPHA_MODE, encoded in MISC_FLAGS2 + { + TEX_ALPHA_MODE_UNKNOWN = 0, + TEX_ALPHA_MODE_STRAIGHT = 1, + TEX_ALPHA_MODE_PREMULTIPLIED = 2, + TEX_ALPHA_MODE_OPAQUE = 3, + TEX_ALPHA_MODE_CUSTOM = 4, + }; + + struct TexMetadata + { + size_t width; + size_t height; // Should be 1 for 1D textures + size_t depth; // Should be 1 for 1D or 2D textures + size_t arraySize; // For cubemap, this is a multiple of 6 + size_t mipLevels; + uint32_t miscFlags; + uint32_t miscFlags2; + DXGI_FORMAT format; + TEX_DIMENSION dimension; + + size_t __cdecl ComputeIndex( _In_ size_t mip, _In_ size_t item, _In_ size_t slice ) const; + // Returns size_t(-1) to indicate an out-of-range error + + bool __cdecl IsCubemap() const { return (miscFlags & TEX_MISC_TEXTURECUBE) != 0; } + // Helper for miscFlags + + bool __cdecl IsPMAlpha() const { return ((miscFlags2 & TEX_MISC2_ALPHA_MODE_MASK) == TEX_ALPHA_MODE_PREMULTIPLIED) != 0; } + void __cdecl SetAlphaMode( TEX_ALPHA_MODE mode ) { miscFlags2 = (miscFlags2 & ~TEX_MISC2_ALPHA_MODE_MASK) | static_cast(mode); } + TEX_ALPHA_MODE __cdecl GetAlphaMode() const { return static_cast(miscFlags2 & TEX_MISC2_ALPHA_MODE_MASK); } + // Helpers for miscFlags2 + + bool __cdecl IsVolumemap() const { return (dimension == TEX_DIMENSION_TEXTURE3D); } + // Helper for dimension + }; + + enum DDS_FLAGS + { + DDS_FLAGS_NONE = 0x0, + + DDS_FLAGS_LEGACY_DWORD = 0x1, + // Assume pitch is DWORD aligned instead of BYTE aligned (used by some legacy DDS files) + + DDS_FLAGS_NO_LEGACY_EXPANSION = 0x2, + // Do not implicitly convert legacy formats that result in larger pixel sizes (24 bpp, 3:3:2, A8L8, A4L4, P8, A8P8) + + DDS_FLAGS_NO_R10B10G10A2_FIXUP = 0x4, + // Do not use work-around for long-standing D3DX DDS file format issue which reversed the 10:10:10:2 color order masks + + DDS_FLAGS_FORCE_RGB = 0x8, + // Convert DXGI 1.1 BGR formats to DXGI_FORMAT_R8G8B8A8_UNORM to avoid use of optional WDDM 1.1 formats + + DDS_FLAGS_NO_16BPP = 0x10, + // Conversions avoid use of 565, 5551, and 4444 formats and instead expand to 8888 to avoid use of optional WDDM 1.2 formats + + DDS_FLAGS_EXPAND_LUMINANCE = 0x20, + // When loading legacy luminance formats expand replicating the color channels rather than leaving them packed (L8, L16, A8L8) + + DDS_FLAGS_BAD_DXTN_TAILS = 0x40, + // Some older DXTn DDS files incorrectly handle mipchain tails for blocks smaller than 4x4 + + 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) + + DDS_FLAGS_FORCE_DX10_EXT_MISC2 = 0x20000, + // DDS_FLAGS_FORCE_DX10_EXT including miscFlags2 information (result may not be compatible with D3DX10 or D3DX11) + }; + + enum WIC_FLAGS + { + WIC_FLAGS_NONE = 0x0, + + WIC_FLAGS_FORCE_RGB = 0x1, + // Loads DXGI 1.1 BGR formats as DXGI_FORMAT_R8G8B8A8_UNORM to avoid use of optional WDDM 1.1 formats + + WIC_FLAGS_NO_X2_BIAS = 0x2, + // Loads DXGI 1.1 X2 10:10:10:2 format as DXGI_FORMAT_R10G10B10A2_UNORM + + WIC_FLAGS_NO_16BPP = 0x4, + // Loads 565, 5551, and 4444 formats as 8888 to avoid use of optional WDDM 1.2 formats + + WIC_FLAGS_ALLOW_MONO = 0x8, + // Loads 1-bit monochrome (black & white) as R1_UNORM rather than 8-bit grayscale + + WIC_FLAGS_ALL_FRAMES = 0x10, + // Loads all images in a multi-frame file, converting/resizing to match the first frame as needed, defaults to 0th frame otherwise + + WIC_FLAGS_IGNORE_SRGB = 0x20, + // Ignores sRGB metadata if present in the file + + WIC_FLAGS_DITHER = 0x10000, + // Use ordered 4x4 dithering for any required conversions + + WIC_FLAGS_DITHER_DIFFUSION = 0x20000, + // Use error-diffusion dithering for any required conversions + + WIC_FLAGS_FILTER_POINT = 0x100000, + WIC_FLAGS_FILTER_LINEAR = 0x200000, + WIC_FLAGS_FILTER_CUBIC = 0x300000, + WIC_FLAGS_FILTER_FANT = 0x400000, // Combination of Linear and Box filter + // Filtering mode to use for any required image resizing (only needed when loading arrays of differently sized images; defaults to Fant) + }; + + HRESULT __cdecl GetMetadataFromDDSMemory( _In_reads_bytes_(size) const void* pSource, _In_ size_t size, _In_ DWORD flags, + _Out_ TexMetadata& metadata ); + HRESULT __cdecl GetMetadataFromDDSFile( _In_z_ const wchar_t* szFile, _In_ DWORD flags, + _Out_ TexMetadata& metadata ); + + HRESULT __cdecl GetMetadataFromHDRMemory( _In_reads_bytes_(size) const void* pSource, _In_ size_t size, + _Out_ TexMetadata& metadata ); + HRESULT __cdecl GetMetadataFromHDRFile( _In_z_ const wchar_t* szFile, + _Out_ TexMetadata& metadata ); + + HRESULT __cdecl GetMetadataFromTGAMemory( _In_reads_bytes_(size) const void* pSource, _In_ size_t size, + _Out_ TexMetadata& metadata ); + HRESULT __cdecl GetMetadataFromTGAFile( _In_z_ const wchar_t* szFile, + _Out_ TexMetadata& metadata ); + + HRESULT __cdecl GetMetadataFromWICMemory( _In_reads_bytes_(size) const void* pSource, _In_ size_t size, _In_ DWORD flags, + _Out_ TexMetadata& metadata, + _In_opt_ std::function getMQR = nullptr); + + HRESULT __cdecl GetMetadataFromWICFile( _In_z_ const wchar_t* szFile, _In_ DWORD flags, + _Out_ TexMetadata& metadata, + _In_opt_ std::function getMQR = nullptr); + + //--------------------------------------------------------------------------------- + // Bitmap image container + struct Image + { + size_t width; + size_t height; + DXGI_FORMAT format; + size_t rowPitch; + size_t slicePitch; + uint8_t* pixels; + }; + + class ScratchImage + { + public: + ScratchImage() + : m_nimages(0), m_size(0), m_metadata{}, m_image(nullptr), m_memory(nullptr) {} + ScratchImage(ScratchImage&& moveFrom) + : m_nimages(0), m_size(0), m_metadata{}, m_image(nullptr), m_memory(nullptr) { *this = std::move(moveFrom); } + ~ScratchImage() { Release(); } + + ScratchImage& __cdecl operator= (ScratchImage&& moveFrom); + + ScratchImage(const ScratchImage&) = delete; + ScratchImage& operator=(const ScratchImage&) = delete; + + HRESULT __cdecl Initialize( _In_ const TexMetadata& mdata, _In_ DWORD flags = CP_FLAGS_NONE ); + + HRESULT __cdecl Initialize1D( _In_ DXGI_FORMAT fmt, _In_ size_t length, _In_ size_t arraySize, _In_ size_t mipLevels, _In_ DWORD flags = CP_FLAGS_NONE ); + HRESULT __cdecl Initialize2D( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t arraySize, _In_ size_t mipLevels, _In_ DWORD flags = CP_FLAGS_NONE ); + HRESULT __cdecl Initialize3D( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t depth, _In_ size_t mipLevels, _In_ DWORD flags = CP_FLAGS_NONE ); + HRESULT __cdecl InitializeCube( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t nCubes, _In_ size_t mipLevels, _In_ DWORD flags = CP_FLAGS_NONE ); + + HRESULT __cdecl InitializeFromImage( _In_ const Image& srcImage, _In_ bool allow1D = false, _In_ DWORD flags = CP_FLAGS_NONE ); + HRESULT __cdecl InitializeArrayFromImages( _In_reads_(nImages) const Image* images, _In_ size_t nImages, _In_ bool allow1D = false, _In_ DWORD flags = CP_FLAGS_NONE ); + HRESULT __cdecl InitializeCubeFromImages( _In_reads_(nImages) const Image* images, _In_ size_t nImages, _In_ DWORD flags = CP_FLAGS_NONE ); + HRESULT __cdecl Initialize3DFromImages( _In_reads_(depth) const Image* images, _In_ size_t depth, _In_ DWORD flags = CP_FLAGS_NONE ); + + void __cdecl Release(); + + bool __cdecl OverrideFormat( _In_ DXGI_FORMAT f ); + + const TexMetadata& __cdecl GetMetadata() const { return m_metadata; } + const Image* __cdecl GetImage(_In_ size_t mip, _In_ size_t item, _In_ size_t slice) const; + + const Image* __cdecl GetImages() const { return m_image; } + size_t __cdecl GetImageCount() const { return m_nimages; } + + uint8_t* __cdecl GetPixels() const { return m_memory; } + size_t __cdecl GetPixelsSize() const { return m_size; } + + bool __cdecl IsAlphaAllOpaque() const; + + private: + size_t m_nimages; + size_t m_size; + TexMetadata m_metadata; + Image* m_image; + uint8_t* m_memory; + }; + + //--------------------------------------------------------------------------------- + // Memory blob (allocated buffer pointer is always 16-byte aligned) + class Blob + { + public: + Blob() : m_buffer(nullptr), m_size(0) {} + Blob(Blob&& moveFrom) : m_buffer(nullptr), m_size(0) { *this = std::move(moveFrom); } + ~Blob() { Release(); } + + Blob& __cdecl operator= (Blob&& moveFrom); + + Blob(const Blob&) = delete; + Blob& operator=(const Blob&) = delete; + + HRESULT __cdecl Initialize( _In_ size_t size ); + + void __cdecl Release(); + + void *__cdecl GetBufferPointer() const { return m_buffer; } + size_t __cdecl GetBufferSize() const { return m_size; } + + HRESULT __cdecl Trim(size_t size); + + private: + void* m_buffer; + size_t m_size; + }; + + //--------------------------------------------------------------------------------- + // Image I/O + + // DDS operations + HRESULT __cdecl LoadFromDDSMemory( _In_reads_bytes_(size) const void* pSource, _In_ size_t size, _In_ DWORD flags, + _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image ); + HRESULT __cdecl LoadFromDDSFile( _In_z_ const wchar_t* szFile, _In_ DWORD flags, + _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image ); + + HRESULT __cdecl SaveToDDSMemory( _In_ const Image& image, _In_ DWORD flags, + _Out_ Blob& blob ); + HRESULT __cdecl SaveToDDSMemory( _In_reads_(nimages) const Image* images, _In_ size_t nimages, _In_ const TexMetadata& metadata, _In_ DWORD flags, + _Out_ Blob& blob ); + + HRESULT __cdecl SaveToDDSFile( _In_ const Image& image, _In_ DWORD flags, _In_z_ const wchar_t* szFile ); + HRESULT __cdecl SaveToDDSFile( _In_reads_(nimages) const Image* images, _In_ size_t nimages, _In_ const TexMetadata& metadata, _In_ DWORD flags, _In_z_ const wchar_t* szFile ); + + // HDR operations + HRESULT __cdecl LoadFromHDRMemory( _In_reads_bytes_(size) const void* pSource, _In_ size_t size, + _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image ); + HRESULT __cdecl LoadFromHDRFile( _In_z_ const wchar_t* szFile, + _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image ); + + HRESULT __cdecl SaveToHDRMemory( _In_ const Image& image, _Out_ Blob& blob ); + HRESULT __cdecl SaveToHDRFile( _In_ const Image& image, _In_z_ const wchar_t* szFile ); + + // TGA operations + HRESULT __cdecl LoadFromTGAMemory( _In_reads_bytes_(size) const void* pSource, _In_ size_t size, + _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image ); + HRESULT __cdecl LoadFromTGAFile( _In_z_ const wchar_t* szFile, + _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image ); + + HRESULT __cdecl SaveToTGAMemory( _In_ const Image& image, _Out_ Blob& blob ); + HRESULT __cdecl SaveToTGAFile( _In_ const Image& image, _In_z_ const wchar_t* szFile ); + + // WIC operations + HRESULT __cdecl LoadFromWICMemory( _In_reads_bytes_(size) const void* pSource, _In_ size_t size, _In_ DWORD flags, + _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image, + _In_opt_ std::function getMQR = nullptr); + HRESULT __cdecl LoadFromWICFile( _In_z_ const wchar_t* szFile, _In_ DWORD flags, + _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image, + _In_opt_ std::function getMQR = nullptr); + + HRESULT __cdecl SaveToWICMemory( _In_ const Image& image, _In_ DWORD flags, _In_ REFGUID guidContainerFormat, + _Out_ Blob& blob, _In_opt_ const GUID* targetFormat = nullptr, + _In_opt_ std::function setCustomProps = nullptr ); + HRESULT __cdecl SaveToWICMemory( _In_count_(nimages) const Image* images, _In_ size_t nimages, _In_ DWORD flags, _In_ REFGUID guidContainerFormat, + _Out_ Blob& blob, _In_opt_ const GUID* targetFormat = nullptr, + _In_opt_ std::function setCustomProps = nullptr ); + + HRESULT __cdecl SaveToWICFile( _In_ const Image& image, _In_ DWORD flags, _In_ REFGUID guidContainerFormat, + _In_z_ const wchar_t* szFile, _In_opt_ const GUID* targetFormat = nullptr, + _In_opt_ std::function setCustomProps = nullptr ); + HRESULT __cdecl SaveToWICFile( _In_count_(nimages) const Image* images, _In_ size_t nimages, _In_ DWORD flags, _In_ REFGUID guidContainerFormat, + _In_z_ const wchar_t* szFile, _In_opt_ const GUID* targetFormat = nullptr, + _In_opt_ std::function setCustomProps = nullptr ); + + //--------------------------------------------------------------------------------- + // Texture conversion, resizing, mipmap generation, and block compression + + enum TEX_FR_FLAGS + { + TEX_FR_ROTATE0 = 0x0, + TEX_FR_ROTATE90 = 0x1, + TEX_FR_ROTATE180 = 0x2, + TEX_FR_ROTATE270 = 0x3, + TEX_FR_FLIP_HORIZONTAL = 0x08, + TEX_FR_FLIP_VERTICAL = 0x10, + }; + + HRESULT __cdecl FlipRotate( _In_ const Image& srcImage, _In_ DWORD flags, _Out_ ScratchImage& image ); + HRESULT __cdecl FlipRotate( _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ DWORD flags, _Out_ ScratchImage& result ); + // Flip and/or rotate image + + enum TEX_FILTER_FLAGS + { + TEX_FILTER_DEFAULT = 0, + + TEX_FILTER_WRAP_U = 0x1, + TEX_FILTER_WRAP_V = 0x2, + TEX_FILTER_WRAP_W = 0x4, + TEX_FILTER_WRAP = ( TEX_FILTER_WRAP_U | TEX_FILTER_WRAP_V | TEX_FILTER_WRAP_W ), + TEX_FILTER_MIRROR_U = 0x10, + TEX_FILTER_MIRROR_V = 0x20, + TEX_FILTER_MIRROR_W = 0x40, + TEX_FILTER_MIRROR = ( TEX_FILTER_MIRROR_U | TEX_FILTER_MIRROR_V | TEX_FILTER_MIRROR_W ), + // Wrap vs. Mirror vs. Clamp filtering options + + TEX_FILTER_SEPARATE_ALPHA = 0x100, + // Resize color and alpha channel independently + + TEX_FILTER_FLOAT_X2BIAS = 0x200, + // Enable *2 - 1 conversion cases for unorm<->float and positive-only float formats + + TEX_FILTER_RGB_COPY_RED = 0x1000, + TEX_FILTER_RGB_COPY_GREEN = 0x2000, + TEX_FILTER_RGB_COPY_BLUE = 0x4000, + // When converting RGB to R, defaults to using grayscale. These flags indicate copying a specific channel instead + // When converting RGB to RG, defaults to copying RED | GREEN. These flags control which channels are selected instead. + + TEX_FILTER_DITHER = 0x10000, + // Use ordered 4x4 dithering for any required conversions + TEX_FILTER_DITHER_DIFFUSION = 0x20000, + // Use error-diffusion dithering for any required conversions + + TEX_FILTER_POINT = 0x100000, + TEX_FILTER_LINEAR = 0x200000, + TEX_FILTER_CUBIC = 0x300000, + TEX_FILTER_BOX = 0x400000, + TEX_FILTER_FANT = 0x400000, // Equiv to Box filtering for mipmap generation + TEX_FILTER_TRIANGLE = 0x500000, + // Filtering mode to use for any required image resizing + + TEX_FILTER_SRGB_IN = 0x1000000, + TEX_FILTER_SRGB_OUT = 0x2000000, + TEX_FILTER_SRGB = ( TEX_FILTER_SRGB_IN | TEX_FILTER_SRGB_OUT ), + // sRGB <-> RGB for use in conversion operations + // if the input format type is IsSRGB(), then SRGB_IN is on by default + // if the output format type is IsSRGB(), then SRGB_OUT is on by default + + TEX_FILTER_FORCE_NON_WIC = 0x10000000, + // Forces use of the non-WIC path when both are an option + + TEX_FILTER_FORCE_WIC = 0x20000000, + // Forces use of the WIC path even when logic would have picked a non-WIC path when both are an option + }; + + HRESULT __cdecl Resize( _In_ const Image& srcImage, _In_ size_t width, _In_ size_t height, _In_ DWORD filter, + _Out_ ScratchImage& image ); + HRESULT __cdecl Resize( _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ size_t width, _In_ size_t height, _In_ DWORD filter, _Out_ ScratchImage& result ); + // Resize the image to width x height. Defaults to Fant filtering. + // Note for a complex resize, the result will always have mipLevels == 1 + + const float TEX_THRESHOLD_DEFAULT = 0.5f; + // Default value for alpha threshold used when converting to 1-bit alpha + + HRESULT __cdecl Convert( _In_ const Image& srcImage, _In_ DXGI_FORMAT format, _In_ DWORD filter, _In_ float threshold, + _Out_ ScratchImage& image ); + HRESULT __cdecl Convert( _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ DXGI_FORMAT format, _In_ DWORD filter, _In_ float threshold, _Out_ ScratchImage& result ); + // Convert the image to a new format + + HRESULT __cdecl ConvertToSinglePlane( _In_ const Image& srcImage, _Out_ ScratchImage& image ); + HRESULT __cdecl ConvertToSinglePlane( _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _Out_ ScratchImage& image ); + // Converts the image from a planar format to an equivalent non-planar format + + HRESULT __cdecl GenerateMipMaps( _In_ const Image& baseImage, _In_ DWORD filter, _In_ size_t levels, + _Inout_ ScratchImage& mipChain, _In_ bool allow1D = false ); + HRESULT __cdecl GenerateMipMaps( _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ DWORD filter, _In_ size_t levels, _Inout_ ScratchImage& mipChain ); + // levels of '0' indicates a full mipchain, otherwise is generates that number of total levels (including the source base image) + // Defaults to Fant filtering which is equivalent to a box filter + + HRESULT __cdecl GenerateMipMaps3D( _In_reads_(depth) const Image* baseImages, _In_ size_t depth, _In_ DWORD filter, _In_ size_t levels, + _Out_ ScratchImage& mipChain ); + HRESULT __cdecl GenerateMipMaps3D( _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ DWORD filter, _In_ size_t levels, _Out_ ScratchImage& mipChain ); + // levels of '0' indicates a full mipchain, otherwise is generates that number of total levels (including the source base image) + // Defaults to Fant filtering which is equivalent to a box filter + + enum TEX_PMALPHA_FLAGS + { + TEX_PMALPHA_DEFAULT = 0, + + TEX_PMALPHA_IGNORE_SRGB = 0x1, + // ignores sRGB colorspace conversions + + TEX_PMALPHA_REVERSE = 0x2, + // converts from premultiplied alpha back to straight alpha + + TEX_PMALPHA_SRGB_IN = 0x1000000, + TEX_PMALPHA_SRGB_OUT = 0x2000000, + TEX_PMALPHA_SRGB = ( TEX_PMALPHA_SRGB_IN | TEX_PMALPHA_SRGB_OUT ), + // if the input format type is IsSRGB(), then SRGB_IN is on by default + // if the output format type is IsSRGB(), then SRGB_OUT is on by default + }; + + HRESULT __cdecl PremultiplyAlpha( _In_ const Image& srcImage, _In_ DWORD flags, _Out_ ScratchImage& image ); + HRESULT __cdecl PremultiplyAlpha( _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ DWORD flags, _Out_ ScratchImage& result ); + // Converts to/from a premultiplied alpha version of the texture + + enum TEX_COMPRESS_FLAGS + { + TEX_COMPRESS_DEFAULT = 0, + + TEX_COMPRESS_RGB_DITHER = 0x10000, + // Enables dithering RGB colors for BC1-3 compression + + TEX_COMPRESS_A_DITHER = 0x20000, + // Enables dithering alpha for BC1-3 compression + + TEX_COMPRESS_DITHER = 0x30000, + // Enables both RGB and alpha dithering for BC1-3 compression + + TEX_COMPRESS_UNIFORM = 0x40000, + // Uniform color weighting for BC1-3 compression; by default uses perceptual weighting + + TEX_COMPRESS_BC7_USE_3SUBSETS = 0x80000, + // Enables exhaustive search for BC7 compress for mode 0 and 2; by default skips trying these modes + + TEX_COMPRESS_BC7_QUICK = 0x100000, + // Minimal modes (usually mode 6) for BC7 compression + + TEX_COMPRESS_SRGB_IN = 0x1000000, + TEX_COMPRESS_SRGB_OUT = 0x2000000, + TEX_COMPRESS_SRGB = ( TEX_COMPRESS_SRGB_IN | TEX_COMPRESS_SRGB_OUT ), + // if the input format type is IsSRGB(), then SRGB_IN is on by default + // if the output format type is IsSRGB(), then SRGB_OUT is on by default + + TEX_COMPRESS_PARALLEL = 0x10000000, + // Compress is free to use multithreading to improve performance (by default it does not use multithreading) + }; + + HRESULT __cdecl Compress( _In_ const Image& srcImage, _In_ DXGI_FORMAT format, _In_ DWORD compress, _In_ float threshold, + _Out_ ScratchImage& cImage ); + HRESULT __cdecl Compress( _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ DXGI_FORMAT format, _In_ DWORD compress, _In_ float threshold, _Out_ ScratchImage& cImages ); + // Note that threshold is only used by BC1. TEX_THRESHOLD_DEFAULT is a typical value to use + +#if defined(__d3d11_h__) || defined(__d3d11_x_h__) + HRESULT __cdecl Compress( _In_ ID3D11Device* pDevice, _In_ const Image& srcImage, _In_ DXGI_FORMAT format, _In_ DWORD compress, + _In_ float alphaWeight, _Out_ ScratchImage& image ); + HRESULT __cdecl Compress( _In_ ID3D11Device* pDevice, _In_ const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ DXGI_FORMAT format, _In_ DWORD compress, _In_ float alphaWeight, _Out_ ScratchImage& cImages ); + // DirectCompute-based compression (alphaWeight is only used by BC7. 1.0 is the typical value to use) +#endif + + HRESULT __cdecl Decompress( _In_ const Image& cImage, _In_ DXGI_FORMAT format, _Out_ ScratchImage& image ); + HRESULT __cdecl Decompress( _In_reads_(nimages) const Image* cImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ DXGI_FORMAT format, _Out_ ScratchImage& images ); + + //--------------------------------------------------------------------------------- + // Normal map operations + + enum CNMAP_FLAGS + { + CNMAP_DEFAULT = 0, + + CNMAP_CHANNEL_RED = 0x1, + CNMAP_CHANNEL_GREEN = 0x2, + CNMAP_CHANNEL_BLUE = 0x3, + CNMAP_CHANNEL_ALPHA = 0x4, + CNMAP_CHANNEL_LUMINANCE = 0x5, + // Channel selection when evaluting color value for height + // Luminance is a combination of red, green, and blue + + CNMAP_MIRROR_U = 0x1000, + CNMAP_MIRROR_V = 0x2000, + CNMAP_MIRROR = 0x3000, + // Use mirror semantics for scanline references (defaults to wrap) + + CNMAP_INVERT_SIGN = 0x4000, + // Inverts normal sign + + CNMAP_COMPUTE_OCCLUSION = 0x8000, + // Computes a crude occlusion term stored in the alpha channel + }; + + HRESULT __cdecl ComputeNormalMap( _In_ const Image& srcImage, _In_ DWORD flags, _In_ float amplitude, + _In_ DXGI_FORMAT format, _Out_ ScratchImage& normalMap ); + HRESULT __cdecl ComputeNormalMap( _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ DWORD flags, _In_ float amplitude, _In_ DXGI_FORMAT format, _Out_ ScratchImage& normalMaps ); + + //--------------------------------------------------------------------------------- + // Misc image operations + + struct Rect + { + size_t x; + size_t y; + size_t w; + size_t h; + + Rect() = default; + Rect( size_t _x, size_t _y, size_t _w, size_t _h ) : x(_x), y(_y), w(_w), h(_h) {} + }; + + HRESULT __cdecl CopyRectangle( _In_ const Image& srcImage, _In_ const Rect& srcRect, _In_ const Image& dstImage, + _In_ DWORD filter, _In_ size_t xOffset, _In_ size_t yOffset ); + + enum CMSE_FLAGS + { + CMSE_DEFAULT = 0, + + CMSE_IMAGE1_SRGB = 0x1, + CMSE_IMAGE2_SRGB = 0x2, + // Indicates that image needs gamma correction before comparision + + CMSE_IGNORE_RED = 0x10, + CMSE_IGNORE_GREEN = 0x20, + CMSE_IGNORE_BLUE = 0x40, + CMSE_IGNORE_ALPHA = 0x80, + // Ignore the channel when computing MSE + + CMSE_IMAGE1_X2_BIAS = 0x100, + CMSE_IMAGE2_X2_BIAS = 0x200, + // Indicates that image should be scaled and biased before comparison (i.e. UNORM -> SNORM) + }; + + HRESULT __cdecl ComputeMSE( _In_ const Image& image1, _In_ const Image& image2, _Out_ float& mse, _Out_writes_opt_(4) float* mseV, _In_ DWORD flags = 0 ); + + HRESULT __cdecl EvaluateImage( _In_ const Image& image, + _In_ std::function pixelFunc ); + HRESULT __cdecl EvaluateImage( _In_reads_(nimages) const Image* images, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ std::function pixelFunc ); + + HRESULT __cdecl TransformImage( _In_ const Image& image, + _In_ std::function pixelFunc, + ScratchImage& result ); + HRESULT __cdecl TransformImage( _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ std::function pixelFunc, + ScratchImage& result ); + + //--------------------------------------------------------------------------------- + // WIC utility code + + enum WICCodecs + { + WIC_CODEC_BMP = 1, // Windows Bitmap (.bmp) + WIC_CODEC_JPEG, // Joint Photographic Experts Group (.jpg, .jpeg) + WIC_CODEC_PNG, // Portable Network Graphics (.png) + WIC_CODEC_TIFF, // Tagged Image File Format (.tif, .tiff) + WIC_CODEC_GIF, // Graphics Interchange Format (.gif) + WIC_CODEC_WMP, // Windows Media Photo / HD Photo / JPEG XR (.hdp, .jxr, .wdp) + WIC_CODEC_ICO, // Windows Icon (.ico) + }; + + REFGUID __cdecl GetWICCodec(_In_ WICCodecs codec); + + IWICImagingFactory* __cdecl GetWICFactory( bool& iswic2 ); + void __cdecl SetWICFactory( _In_opt_ IWICImagingFactory* pWIC); + + //--------------------------------------------------------------------------------- + // Direct3D 11 functions +#if defined(__d3d11_h__) || defined(__d3d11_x_h__) + bool __cdecl IsSupportedTexture( _In_ ID3D11Device* pDevice, _In_ const TexMetadata& metadata ); + + HRESULT __cdecl CreateTexture( _In_ ID3D11Device* pDevice, _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _Outptr_ ID3D11Resource** ppResource ); + + HRESULT __cdecl CreateShaderResourceView( _In_ ID3D11Device* pDevice, _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _Outptr_ ID3D11ShaderResourceView** ppSRV ); + + HRESULT __cdecl CreateTextureEx( _In_ ID3D11Device* pDevice, _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ D3D11_USAGE usage, _In_ unsigned int bindFlags, _In_ unsigned int cpuAccessFlags, _In_ unsigned int miscFlags, _In_ bool forceSRGB, + _Outptr_ ID3D11Resource** ppResource ); + + HRESULT __cdecl CreateShaderResourceViewEx( _In_ ID3D11Device* pDevice, _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ D3D11_USAGE usage, _In_ unsigned int bindFlags, _In_ unsigned int cpuAccessFlags, _In_ unsigned int miscFlags, _In_ bool forceSRGB, + _Outptr_ ID3D11ShaderResourceView** ppSRV ); + + HRESULT __cdecl CaptureTexture( _In_ ID3D11Device* pDevice, _In_ ID3D11DeviceContext* pContext, _In_ ID3D11Resource* pSource, _Out_ ScratchImage& result ); +#endif + + //--------------------------------------------------------------------------------- + // Direct3D 12 functions +#if defined(__d3d12_h__) || defined(__d3d12_x_h__) + bool __cdecl IsSupportedTexture( _In_ ID3D12Device* pDevice, _In_ const TexMetadata& metadata ); + + HRESULT __cdecl CreateTexture( _In_ ID3D12Device* pDevice, _In_ const TexMetadata& metadata, + _Outptr_ ID3D12Resource** ppResource ); + + HRESULT __cdecl CreateTextureEx( _In_ ID3D12Device* pDevice, _In_ const TexMetadata& metadata, + _In_ D3D12_RESOURCE_FLAGS resFlags, _In_ bool forceSRGB, + _Outptr_ ID3D12Resource** ppResource ); + + HRESULT __cdecl PrepareUpload( _In_ ID3D12Device* pDevice, + _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + std::vector& subresources ); + + HRESULT __cdecl CaptureTexture( _In_ ID3D12CommandQueue* pCommandQueue, _In_ ID3D12Resource* pSource, _In_ bool isCubeMap, + _Out_ ScratchImage& result, + _In_ D3D12_RESOURCE_STATES beforeState = D3D12_RESOURCE_STATE_RENDER_TARGET, + _In_ D3D12_RESOURCE_STATES afterState = D3D12_RESOURCE_STATE_RENDER_TARGET ); +#endif + +#include "DirectXTex.inl" + +}; // namespace diff --git a/deps/DirectXTex/DirectXTex/DirectXTex.inl b/deps/DirectXTex/DirectXTex/DirectXTex.inl new file mode 100644 index 0000000..5173869 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex.inl @@ -0,0 +1,128 @@ +//------------------------------------------------------------------------------------- +// DirectXTex.inl +// +// DirectX Texture Library +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#pragma once + +//===================================================================================== +// DXGI Format Utilities +//===================================================================================== + +_Use_decl_annotations_ +inline bool __cdecl IsValid( DXGI_FORMAT fmt ) +{ + return ( static_cast(fmt) >= 1 && static_cast(fmt) <= 190 ); +} + +_Use_decl_annotations_ +inline bool __cdecl IsCompressed(DXGI_FORMAT fmt) +{ + switch ( fmt ) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return true; + + default: + return false; + } +} + +_Use_decl_annotations_ +inline bool __cdecl IsPalettized(DXGI_FORMAT fmt) +{ + switch( fmt ) + { + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case DXGI_FORMAT_A8P8: + return true; + + default: + return false; + } +} + +_Use_decl_annotations_ +inline bool __cdecl IsSRGB(DXGI_FORMAT fmt) +{ + switch( fmt ) + { + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return true; + + default: + return false; + } +} + + +//===================================================================================== +// Image I/O +//===================================================================================== +_Use_decl_annotations_ +inline HRESULT __cdecl SaveToDDSMemory(const Image& image, DWORD flags, Blob& blob) +{ + TexMetadata mdata = {}; + mdata.width = image.width; + mdata.height = image.height; + mdata.depth = 1; + mdata.arraySize = 1; + mdata.mipLevels = 1; + mdata.format = image.format; + mdata.dimension = TEX_DIMENSION_TEXTURE2D; + + return SaveToDDSMemory( &image, 1, mdata, flags, blob ); +} + +_Use_decl_annotations_ +inline HRESULT __cdecl SaveToDDSFile(const Image& image, DWORD flags, const wchar_t* szFile) +{ + TexMetadata mdata = {}; + mdata.width = image.width; + mdata.height = image.height; + mdata.depth = 1; + mdata.arraySize = 1; + mdata.mipLevels = 1; + mdata.format = image.format; + mdata.dimension = TEX_DIMENSION_TEXTURE2D; + + return SaveToDDSFile( &image, 1, mdata, flags, szFile ); +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexCompress.cpp b/deps/DirectXTex/DirectXTex/DirectXTexCompress.cpp new file mode 100644 index 0000000..2c25c54 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexCompress.cpp @@ -0,0 +1,855 @@ +//------------------------------------------------------------------------------------- +// DirectXTexCompress.cpp +// +// DirectX Texture Library - Texture compression +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +#ifdef _OPENMP +#include +#pragma warning(disable : 4616 6993) +#endif + +#include "bc.h" + +using namespace DirectX; + +namespace +{ + inline DWORD GetBCFlags(_In_ DWORD compress) + { + static_assert(static_cast(TEX_COMPRESS_RGB_DITHER) == static_cast(BC_FLAGS_DITHER_RGB), "TEX_COMPRESS_* flags should match BC_FLAGS_*"); + static_assert(static_cast(TEX_COMPRESS_A_DITHER) == static_cast(BC_FLAGS_DITHER_A), "TEX_COMPRESS_* flags should match BC_FLAGS_*"); + static_assert(static_cast(TEX_COMPRESS_DITHER) == static_cast(BC_FLAGS_DITHER_RGB | BC_FLAGS_DITHER_A), "TEX_COMPRESS_* flags should match BC_FLAGS_*"); + static_assert(static_cast(TEX_COMPRESS_UNIFORM) == static_cast(BC_FLAGS_UNIFORM), "TEX_COMPRESS_* flags should match BC_FLAGS_*"); + static_assert(static_cast(TEX_COMPRESS_BC7_USE_3SUBSETS) == static_cast(BC_FLAGS_USE_3SUBSETS), "TEX_COMPRESS_* flags should match BC_FLAGS_*"); + static_assert(static_cast(TEX_COMPRESS_BC7_QUICK) == static_cast(BC_FLAGS_FORCE_BC7_MODE6), "TEX_COMPRESS_* flags should match BC_FLAGS_*"); + return (compress & (BC_FLAGS_DITHER_RGB | BC_FLAGS_DITHER_A | BC_FLAGS_UNIFORM | BC_FLAGS_USE_3SUBSETS | BC_FLAGS_FORCE_BC7_MODE6)); + } + + inline DWORD GetSRGBFlags(_In_ DWORD compress) + { + static_assert(static_cast(TEX_COMPRESS_SRGB_IN) == static_cast(TEX_FILTER_SRGB_IN), "TEX_COMPRESS_SRGB* should match TEX_FILTER_SRGB*"); + static_assert(static_cast(TEX_COMPRESS_SRGB_OUT) == static_cast(TEX_FILTER_SRGB_OUT), "TEX_COMPRESS_SRGB* should match TEX_FILTER_SRGB*"); + static_assert(static_cast(TEX_COMPRESS_SRGB) == static_cast(TEX_FILTER_SRGB), "TEX_COMPRESS_SRGB* should match TEX_FILTER_SRGB*"); + return (compress & TEX_COMPRESS_SRGB); + } + + inline bool DetermineEncoderSettings(_In_ DXGI_FORMAT format, _Out_ BC_ENCODE& pfEncode, _Out_ size_t& blocksize, _Out_ DWORD& cflags) + { + switch (format) + { + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: pfEncode = nullptr; blocksize = 8; cflags = 0; break; + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: pfEncode = D3DXEncodeBC2; blocksize = 16; cflags = 0; break; + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: pfEncode = D3DXEncodeBC3; blocksize = 16; cflags = 0; break; + case DXGI_FORMAT_BC4_UNORM: pfEncode = D3DXEncodeBC4U; blocksize = 8; cflags = TEX_FILTER_RGB_COPY_RED; break; + case DXGI_FORMAT_BC4_SNORM: pfEncode = D3DXEncodeBC4S; blocksize = 8; cflags = TEX_FILTER_RGB_COPY_RED; break; + case DXGI_FORMAT_BC5_UNORM: pfEncode = D3DXEncodeBC5U; blocksize = 16; cflags = TEX_FILTER_RGB_COPY_RED | TEX_FILTER_RGB_COPY_GREEN; break; + case DXGI_FORMAT_BC5_SNORM: pfEncode = D3DXEncodeBC5S; blocksize = 16; cflags = TEX_FILTER_RGB_COPY_RED | TEX_FILTER_RGB_COPY_GREEN; break; + case DXGI_FORMAT_BC6H_UF16: pfEncode = D3DXEncodeBC6HU; blocksize = 16; cflags = 0; break; + case DXGI_FORMAT_BC6H_SF16: pfEncode = D3DXEncodeBC6HS; blocksize = 16; cflags = 0; break; + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: pfEncode = D3DXEncodeBC7; blocksize = 16; cflags = 0; break; + default: pfEncode = nullptr; blocksize = 0; cflags = 0; return false; + } + + return true; + } + + + //------------------------------------------------------------------------------------- + HRESULT CompressBC( + const Image& image, + const Image& result, + DWORD bcflags, + DWORD srgb, + float threshold) + { + if (!image.pixels || !result.pixels) + return E_POINTER; + + assert(image.width == result.width); + assert(image.height == result.height); + + const DXGI_FORMAT format = image.format; + size_t sbpp = BitsPerPixel(format); + if (!sbpp) + return E_FAIL; + + if (sbpp < 8) + { + // We don't support compressing from monochrome (DXGI_FORMAT_R1_UNORM) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + // Round to bytes + sbpp = (sbpp + 7) / 8; + + uint8_t *pDest = result.pixels; + + // Determine BC format encoder + BC_ENCODE pfEncode; + size_t blocksize; + DWORD cflags; + if (!DetermineEncoderSettings(result.format, pfEncode, blocksize, cflags)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + __declspec(align(16)) XMVECTOR temp[16]; + const uint8_t *pSrc = image.pixels; + const uint8_t *pEnd = image.pixels + image.slicePitch; + const size_t rowPitch = image.rowPitch; + for (size_t h = 0; h < image.height; h += 4) + { + const uint8_t *sptr = pSrc; + uint8_t* dptr = pDest; + size_t ph = std::min(4, image.height - h); + size_t w = 0; + for (size_t count = 0; (count < result.rowPitch) && (w < image.width); count += blocksize, w += 4) + { + size_t pw = std::min(4, image.width - w); + assert(pw > 0 && ph > 0); + + ptrdiff_t bytesLeft = pEnd - sptr; + assert(bytesLeft > 0); + size_t bytesToRead = std::min(rowPitch, bytesLeft); + if (!_LoadScanline(&temp[0], pw, sptr, bytesToRead, format)) + return E_FAIL; + + if (ph > 1) + { + bytesToRead = std::min(rowPitch, bytesLeft - rowPitch); + if (!_LoadScanline(&temp[4], pw, sptr + rowPitch, bytesToRead, format)) + return E_FAIL; + + if (ph > 2) + { + bytesToRead = std::min(rowPitch, bytesLeft - rowPitch * 2); + if (!_LoadScanline(&temp[8], pw, sptr + rowPitch * 2, bytesToRead, format)) + return E_FAIL; + + if (ph > 3) + { + bytesToRead = std::min(rowPitch, bytesLeft - rowPitch * 3); + if (!_LoadScanline(&temp[12], pw, sptr + rowPitch * 3, bytesToRead, format)) + return E_FAIL; + } + } + } + + if (pw != 4 || ph != 4) + { + // Replicate pixels for partial block + static const size_t uSrc[] = { 0, 0, 0, 1 }; + + if (pw < 4) + { + for (size_t t = 0; t < ph && t < 4; ++t) + { + for (size_t s = pw; s < 4; ++s) + { +#pragma prefast(suppress: 26000, "PREFAST false positive") + temp[(t << 2) | s] = temp[(t << 2) | uSrc[s]]; + } + } + } + + if (ph < 4) + { + for (size_t t = ph; t < 4; ++t) + { + for (size_t s = 0; s < 4; ++s) + { +#pragma prefast(suppress: 26000, "PREFAST false positive") + temp[(t << 2) | s] = temp[(uSrc[t] << 2) | s]; + } + } + } + } + + _ConvertScanline(temp, 16, result.format, format, cflags | srgb); + + if (pfEncode) + pfEncode(dptr, temp, bcflags); + else + D3DXEncodeBC1(dptr, temp, threshold, bcflags); + + sptr += sbpp * 4; + dptr += blocksize; + } + + pSrc += rowPitch * 4; + pDest += result.rowPitch; + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- +#ifdef _OPENMP + HRESULT CompressBC_Parallel( + const Image& image, + const Image& result, + DWORD bcflags, + DWORD srgb, + float threshold) + { + if (!image.pixels || !result.pixels) + return E_POINTER; + + assert(image.width == result.width); + assert(image.height == result.height); + + const DXGI_FORMAT format = image.format; + size_t sbpp = BitsPerPixel(format); + if (!sbpp) + return E_FAIL; + + if (sbpp < 8) + { + // We don't support compressing from monochrome (DXGI_FORMAT_R1_UNORM) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + // Round to bytes + sbpp = (sbpp + 7) / 8; + + const uint8_t *pEnd = image.pixels + image.slicePitch; + + // Determine BC format encoder + BC_ENCODE pfEncode; + size_t blocksize; + DWORD cflags; + if (!DetermineEncoderSettings(result.format, pfEncode, blocksize, cflags)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + // Refactored version of loop to support parallel independance + const size_t nBlocks = std::max(1, (image.width + 3) / 4) * std::max(1, (image.height + 3) / 4); + + bool fail = false; + +#pragma omp parallel for + for (int nb = 0; nb < static_cast(nBlocks); ++nb) + { + int nbWidth = std::max(1, int((image.width + 3) / 4)); + + int y = nb / nbWidth; + int x = (nb - (y*nbWidth)) * 4; + y *= 4; + + assert((x >= 0) && (x < int(image.width))); + assert((y >= 0) && (y < int(image.height))); + + size_t rowPitch = image.rowPitch; + const uint8_t *pSrc = image.pixels + (y*rowPitch) + (x*sbpp); + + uint8_t *pDest = result.pixels + (nb*blocksize); + + size_t ph = std::min(4, image.height - y); + size_t pw = std::min(4, image.width - x); + assert(pw > 0 && ph > 0); + + ptrdiff_t bytesLeft = pEnd - pSrc; + assert(bytesLeft > 0); + size_t bytesToRead = std::min(rowPitch, bytesLeft); + + __declspec(align(16)) XMVECTOR temp[16]; + if (!_LoadScanline(&temp[0], pw, pSrc, bytesToRead, format)) + fail = true; + + if (ph > 1) + { + bytesToRead = std::min(rowPitch, bytesLeft - rowPitch); + if (!_LoadScanline(&temp[4], pw, pSrc + rowPitch, bytesToRead, format)) + fail = true; + + if (ph > 2) + { + bytesToRead = std::min(rowPitch, bytesLeft - rowPitch * 2); + if (!_LoadScanline(&temp[8], pw, pSrc + rowPitch * 2, bytesToRead, format)) + fail = true; + + if (ph > 3) + { + bytesToRead = std::min(rowPitch, bytesLeft - rowPitch * 3); + if (!_LoadScanline(&temp[12], pw, pSrc + rowPitch * 3, bytesToRead, format)) + fail = true; + } + } + } + + if (pw != 4 || ph != 4) + { + // Replicate pixels for partial block + static const size_t uSrc[] = { 0, 0, 0, 1 }; + + if (pw < 4) + { + for (size_t t = 0; t < ph && t < 4; ++t) + { + for (size_t s = pw; s < 4; ++s) + { + temp[(t << 2) | s] = temp[(t << 2) | uSrc[s]]; + } + } + } + + if (ph < 4) + { + for (size_t t = ph; t < 4; ++t) + { + for (size_t s = 0; s < 4; ++s) + { + temp[(t << 2) | s] = temp[(uSrc[t] << 2) | s]; + } + } + } + } + + _ConvertScanline(temp, 16, result.format, format, cflags | srgb); + + if (pfEncode) + pfEncode(pDest, temp, bcflags); + else + D3DXEncodeBC1(pDest, temp, threshold, bcflags); + } + + return (fail) ? E_FAIL : S_OK; + } +#endif // _OPENMP + + + //------------------------------------------------------------------------------------- + DXGI_FORMAT DefaultDecompress(_In_ DXGI_FORMAT format) + { + switch (format) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + return DXGI_FORMAT_R8G8B8A8_UNORM; + + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + return DXGI_FORMAT_R8_UNORM; + + case DXGI_FORMAT_BC4_SNORM: + return DXGI_FORMAT_R8_SNORM; + + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + return DXGI_FORMAT_R8G8_UNORM; + + case DXGI_FORMAT_BC5_SNORM: + return DXGI_FORMAT_R8G8_SNORM; + + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + // We could use DXGI_FORMAT_R32G32B32_FLOAT here since BC6H is always Alpha 1.0, + // but this format is more supported by viewers + return DXGI_FORMAT_R32G32B32A32_FLOAT; + + default: + return DXGI_FORMAT_UNKNOWN; + } + } + + + //------------------------------------------------------------------------------------- + HRESULT DecompressBC(_In_ const Image& cImage, _In_ const Image& result) + { + if (!cImage.pixels || !result.pixels) + return E_POINTER; + + assert(cImage.width == result.width); + assert(cImage.height == result.height); + + const DXGI_FORMAT format = result.format; + size_t dbpp = BitsPerPixel(format); + if (!dbpp) + return E_FAIL; + + if (dbpp < 8) + { + // We don't support decompressing to monochrome (DXGI_FORMAT_R1_UNORM) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + // Round to bytes + dbpp = (dbpp + 7) / 8; + + uint8_t *pDest = result.pixels; + if (!pDest) + return E_POINTER; + + // Promote "typeless" BC formats + DXGI_FORMAT cformat; + switch (cImage.format) + { + case DXGI_FORMAT_BC1_TYPELESS: cformat = DXGI_FORMAT_BC1_UNORM; break; + case DXGI_FORMAT_BC2_TYPELESS: cformat = DXGI_FORMAT_BC2_UNORM; break; + case DXGI_FORMAT_BC3_TYPELESS: cformat = DXGI_FORMAT_BC3_UNORM; break; + case DXGI_FORMAT_BC4_TYPELESS: cformat = DXGI_FORMAT_BC4_UNORM; break; + case DXGI_FORMAT_BC5_TYPELESS: cformat = DXGI_FORMAT_BC5_UNORM; break; + case DXGI_FORMAT_BC6H_TYPELESS: cformat = DXGI_FORMAT_BC6H_UF16; break; + case DXGI_FORMAT_BC7_TYPELESS: cformat = DXGI_FORMAT_BC7_UNORM; break; + default: cformat = cImage.format; break; + } + + // Determine BC format decoder + BC_DECODE pfDecode; + size_t sbpp; + switch (cformat) + { + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: pfDecode = D3DXDecodeBC1; sbpp = 8; break; + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: pfDecode = D3DXDecodeBC2; sbpp = 16; break; + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: pfDecode = D3DXDecodeBC3; sbpp = 16; break; + case DXGI_FORMAT_BC4_UNORM: pfDecode = D3DXDecodeBC4U; sbpp = 8; break; + case DXGI_FORMAT_BC4_SNORM: pfDecode = D3DXDecodeBC4S; sbpp = 8; break; + case DXGI_FORMAT_BC5_UNORM: pfDecode = D3DXDecodeBC5U; sbpp = 16; break; + case DXGI_FORMAT_BC5_SNORM: pfDecode = D3DXDecodeBC5S; sbpp = 16; break; + case DXGI_FORMAT_BC6H_UF16: pfDecode = D3DXDecodeBC6HU; sbpp = 16; break; + case DXGI_FORMAT_BC6H_SF16: pfDecode = D3DXDecodeBC6HS; sbpp = 16; break; + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: pfDecode = D3DXDecodeBC7; sbpp = 16; break; + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + __declspec(align(16)) XMVECTOR temp[16]; + const uint8_t *pSrc = cImage.pixels; + const size_t rowPitch = result.rowPitch; + for (size_t h = 0; h < cImage.height; h += 4) + { + const uint8_t *sptr = pSrc; + uint8_t* dptr = pDest; + size_t ph = std::min(4, cImage.height - h); + size_t w = 0; + for (size_t count = 0; (count < cImage.rowPitch) && (w < cImage.width); count += sbpp, w += 4) + { + pfDecode(temp, sptr); + _ConvertScanline(temp, 16, format, cformat, 0); + + size_t pw = std::min(4, cImage.width - w); + assert(pw > 0 && ph > 0); + + if (!_StoreScanline(dptr, rowPitch, format, &temp[0], pw)) + return E_FAIL; + + if (ph > 1) + { + if (!_StoreScanline(dptr + rowPitch, rowPitch, format, &temp[4], pw)) + return E_FAIL; + + if (ph > 2) + { + if (!_StoreScanline(dptr + rowPitch * 2, rowPitch, format, &temp[8], pw)) + return E_FAIL; + + if (ph > 3) + { + if (!_StoreScanline(dptr + rowPitch * 3, rowPitch, format, &temp[12], pw)) + return E_FAIL; + } + } + } + + sptr += sbpp; + dptr += dbpp * 4; + } + + pSrc += cImage.rowPitch; + pDest += rowPitch * 4; + } + + return S_OK; + } +} + +//------------------------------------------------------------------------------------- +namespace DirectX +{ + bool _IsAlphaAllOpaqueBC(_In_ const Image& cImage) + { + if (!cImage.pixels) + return false; + + // Promote "typeless" BC formats + DXGI_FORMAT cformat; + switch (cImage.format) + { + case DXGI_FORMAT_BC1_TYPELESS: cformat = DXGI_FORMAT_BC1_UNORM; break; + case DXGI_FORMAT_BC2_TYPELESS: cformat = DXGI_FORMAT_BC2_UNORM; break; + case DXGI_FORMAT_BC3_TYPELESS: cformat = DXGI_FORMAT_BC3_UNORM; break; + case DXGI_FORMAT_BC7_TYPELESS: cformat = DXGI_FORMAT_BC7_UNORM; break; + default: cformat = cImage.format; break; + } + + // Determine BC format decoder + BC_DECODE pfDecode; + size_t sbpp; + switch (cformat) + { + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: pfDecode = D3DXDecodeBC1; sbpp = 8; break; + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: pfDecode = D3DXDecodeBC2; sbpp = 16; break; + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: pfDecode = D3DXDecodeBC3; sbpp = 16; break; + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: pfDecode = D3DXDecodeBC7; sbpp = 16; break; + default: + // BC4, BC5, and BC6 don't have alpha channels + return false; + } + + // Scan blocks for non-opaque alpha + static const XMVECTORF32 threshold = { { { 0.99f, 0.99f, 0.99f, 0.99f } } }; + + __declspec(align(16)) XMVECTOR temp[16]; + const uint8_t *pPixels = cImage.pixels; + for (size_t h = 0; h < cImage.height; h += 4) + { + const uint8_t *ptr = pPixels; + size_t ph = std::min(4, cImage.height - h); + size_t w = 0; + for (size_t count = 0; (count < cImage.rowPitch) && (w < cImage.width); count += sbpp, w += 4) + { + pfDecode(temp, ptr); + + size_t pw = std::min(4, cImage.width - w); + assert(pw > 0 && ph > 0); + + if (pw == 4 && ph == 4) + { + // Full blocks + for (size_t j = 0; j < 16; ++j) + { + XMVECTOR alpha = XMVectorSplatW(temp[j]); + if (XMVector4Less(alpha, threshold)) + return false; + } + } + else + { + // Handle partial blocks + for (size_t y = 0; y < ph; ++y) + { + for (size_t x = 0; x < pw; ++x) + { + XMVECTOR alpha = XMVectorSplatW(temp[y * 4 + x]); + if (XMVector4Less(alpha, threshold)) + return false; + } + } + } + + ptr += sbpp; + } + + pPixels += cImage.rowPitch; + } + + return true; + } +}; + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Compression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::Compress( + const Image& srcImage, + DXGI_FORMAT format, + DWORD compress, + float threshold, + ScratchImage& image) +{ + if (IsCompressed(srcImage.format) || !IsCompressed(format)) + return E_INVALIDARG; + + if (IsTypeless(format) + || IsTypeless(srcImage.format) || IsPlanar(srcImage.format) || IsPalettized(srcImage.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + // Create compressed image + HRESULT hr = image.Initialize2D(format, srcImage.width, srcImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *img = image.GetImage(0, 0, 0); + if (!img) + { + image.Release(); + return E_POINTER; + } + + // Compress single image + if (compress & TEX_COMPRESS_PARALLEL) + { +#ifndef _OPENMP + return E_NOTIMPL; +#else + hr = CompressBC_Parallel(srcImage, *img, GetBCFlags(compress), GetSRGBFlags(compress), threshold); +#endif // _OPENMP + } + else + { + hr = CompressBC(srcImage, *img, GetBCFlags(compress), GetSRGBFlags(compress), threshold); + } + + if (FAILED(hr)) + image.Release(); + + return hr; +} + +_Use_decl_annotations_ +HRESULT DirectX::Compress( + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + DXGI_FORMAT format, + DWORD compress, + float threshold, + ScratchImage& cImages) +{ + if (!srcImages || !nimages) + return E_INVALIDARG; + + if (IsCompressed(metadata.format) || !IsCompressed(format)) + return E_INVALIDARG; + + if (IsTypeless(format) + || IsTypeless(metadata.format) || IsPlanar(metadata.format) || IsPalettized(metadata.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + cImages.Release(); + + TexMetadata mdata2 = metadata; + mdata2.format = format; + HRESULT hr = cImages.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + if (nimages != cImages.GetImageCount()) + { + cImages.Release(); + return E_FAIL; + } + + const Image* dest = cImages.GetImages(); + if (!dest) + { + cImages.Release(); + return E_POINTER; + } + + for (size_t index = 0; index < nimages; ++index) + { + assert(dest[index].format == format); + + const Image& src = srcImages[index]; + + if (src.width != dest[index].width || src.height != dest[index].height) + { + cImages.Release(); + return E_FAIL; + } + + if ((compress & TEX_COMPRESS_PARALLEL)) + { +#ifndef _OPENMP + return E_NOTIMPL; +#else + if (compress & TEX_COMPRESS_PARALLEL) + { + hr = CompressBC_Parallel(src, dest[index], GetBCFlags(compress), GetSRGBFlags(compress), threshold); + if (FAILED(hr)) + { + cImages.Release(); + return hr; + } + } +#endif // _OPENMP + } + else + { + hr = CompressBC(src, dest[index], GetBCFlags(compress), GetSRGBFlags(compress), threshold); + if (FAILED(hr)) + { + cImages.Release(); + return hr; + } + } + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Decompression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::Decompress( + const Image& cImage, + DXGI_FORMAT format, + ScratchImage& image) +{ + if (!IsCompressed(cImage.format) || IsCompressed(format)) + return E_INVALIDARG; + + if (format == DXGI_FORMAT_UNKNOWN) + { + // Pick a default decompressed format based on BC input format + format = DefaultDecompress(cImage.format); + if (format == DXGI_FORMAT_UNKNOWN) + { + // Input is not a compressed format + return E_INVALIDARG; + } + } + else + { + if (!IsValid(format)) + return E_INVALIDARG; + + if (IsTypeless(format) || IsPlanar(format) || IsPalettized(format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + // Create decompressed image + HRESULT hr = image.Initialize2D(format, cImage.width, cImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *img = image.GetImage(0, 0, 0); + if (!img) + { + image.Release(); + return E_POINTER; + } + + // Decompress single image + hr = DecompressBC(cImage, *img); + if (FAILED(hr)) + image.Release(); + + return hr; +} + +_Use_decl_annotations_ +HRESULT DirectX::Decompress( + const Image* cImages, + size_t nimages, + const TexMetadata& metadata, + DXGI_FORMAT format, + ScratchImage& images) +{ + if (!cImages || !nimages) + return E_INVALIDARG; + + if (!IsCompressed(metadata.format) || IsCompressed(format)) + return E_INVALIDARG; + + if (format == DXGI_FORMAT_UNKNOWN) + { + // Pick a default decompressed format based on BC input format + format = DefaultDecompress(cImages[0].format); + if (format == DXGI_FORMAT_UNKNOWN) + { + // Input is not a compressed format + return E_FAIL; + } + } + else + { + if (!IsValid(format)) + return E_INVALIDARG; + + if (IsTypeless(format) || IsPlanar(format) || IsPalettized(format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + images.Release(); + + TexMetadata mdata2 = metadata; + mdata2.format = format; + HRESULT hr = images.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + if (nimages != images.GetImageCount()) + { + images.Release(); + return E_FAIL; + } + + const Image* dest = images.GetImages(); + if (!dest) + { + images.Release(); + return E_POINTER; + } + + for (size_t index = 0; index < nimages; ++index) + { + assert(dest[index].format == format); + + const Image& src = cImages[index]; + if (!IsCompressed(src.format)) + { + images.Release(); + return E_FAIL; + } + + if (src.width != dest[index].width || src.height != dest[index].height) + { + images.Release(); + return E_FAIL; + } + + hr = DecompressBC(src, dest[index]); + if (FAILED(hr)) + { + images.Release(); + return hr; + } + } + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexCompressGPU.cpp b/deps/DirectXTex/DirectXTex/DirectXTexCompressGPU.cpp new file mode 100644 index 0000000..076be2a --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexCompressGPU.cpp @@ -0,0 +1,425 @@ +//------------------------------------------------------------------------------------- +// DirectXTexCompressGPU.cpp +// +// DirectX Texture Library - DirectCompute-based texture compression +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +#include "bcdirectcompute.h" + +using namespace DirectX; + +namespace +{ + inline DWORD GetSRGBFlags(_In_ DWORD compress) + { + static_assert(static_cast(TEX_COMPRESS_SRGB_IN) == static_cast(TEX_FILTER_SRGB_IN), "TEX_COMPRESS_SRGB* should match TEX_FILTER_SRGB*"); + static_assert(static_cast(TEX_COMPRESS_SRGB_OUT) == static_cast(TEX_FILTER_SRGB_OUT), "TEX_COMPRESS_SRGB* should match TEX_FILTER_SRGB*"); + static_assert(static_cast(TEX_COMPRESS_SRGB) == static_cast(TEX_FILTER_SRGB), "TEX_COMPRESS_SRGB* should match TEX_FILTER_SRGB*"); + return (compress & TEX_COMPRESS_SRGB); + } + + + //------------------------------------------------------------------------------------- + // Converts to R8G8B8A8_UNORM or R8G8B8A8_UNORM_SRGB doing any conversion logic needed + //------------------------------------------------------------------------------------- + HRESULT ConvertToRGBA32( + const Image& srcImage, + ScratchImage& image, + bool srgb, + DWORD filter) + { + if (!srcImage.pixels) + return E_POINTER; + + DXGI_FORMAT format = srgb ? DXGI_FORMAT_R8G8B8A8_UNORM_SRGB : DXGI_FORMAT_R8G8B8A8_UNORM; + + HRESULT hr = image.Initialize2D(format, srcImage.width, srcImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *img = image.GetImage(0, 0, 0); + if (!img) + { + image.Release(); + return E_POINTER; + } + + uint8_t* pDest = img->pixels; + if (!pDest) + { + image.Release(); + return E_POINTER; + } + + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR) * srcImage.width), 16))); + if (!scanline) + { + image.Release(); + return E_OUTOFMEMORY; + } + + const uint8_t *pSrc = srcImage.pixels; + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_LoadScanline(scanline.get(), srcImage.width, pSrc, srcImage.rowPitch, srcImage.format)) + { + image.Release(); + return E_FAIL; + } + + _ConvertScanline(scanline.get(), srcImage.width, format, srcImage.format, filter); + + if (!_StoreScanline(pDest, img->rowPitch, format, scanline.get(), srcImage.width)) + { + image.Release(); + return E_FAIL; + } + + pSrc += srcImage.rowPitch; + pDest += img->rowPitch; + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Converts to DXGI_FORMAT_R32G32B32A32_FLOAT doing any conversion logic needed + //------------------------------------------------------------------------------------- + HRESULT ConvertToRGBAF32( + const Image& srcImage, + ScratchImage& image, + DWORD filter) + { + if (!srcImage.pixels) + return E_POINTER; + + HRESULT hr = image.Initialize2D(DXGI_FORMAT_R32G32B32A32_FLOAT, srcImage.width, srcImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *img = image.GetImage(0, 0, 0); + if (!img) + { + image.Release(); + return E_POINTER; + } + + uint8_t* pDest = img->pixels; + if (!pDest) + { + image.Release(); + return E_POINTER; + } + + const uint8_t *pSrc = srcImage.pixels; + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_LoadScanline(reinterpret_cast(pDest), srcImage.width, pSrc, srcImage.rowPitch, srcImage.format)) + { + image.Release(); + return E_FAIL; + } + + _ConvertScanline(reinterpret_cast(pDest), srcImage.width, DXGI_FORMAT_R32G32B32A32_FLOAT, srcImage.format, filter); + + pSrc += srcImage.rowPitch; + pDest += img->rowPitch; + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Compress using GPU, converting to the proper input format for the shader if needed + //------------------------------------------------------------------------------------- + inline HRESULT GPUCompress( + _In_ GPUCompressBC* gpubc, + const Image& srcImage, + const Image& destImage, + DWORD compress) + { + if (!gpubc) + return E_POINTER; + + assert(srcImage.pixels && destImage.pixels); + + DXGI_FORMAT format = gpubc->GetSourceFormat(); + + if (srcImage.format == format) + { + // Input is already in our required source format + return gpubc->Compress(srcImage, destImage); + } + else + { + // Convert format and then use as the source image + ScratchImage image; + HRESULT hr; + + DWORD srgb = GetSRGBFlags(compress); + + switch (format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + hr = ConvertToRGBA32(srcImage, image, false, srgb); + break; + + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + hr = ConvertToRGBA32(srcImage, image, true, srgb); + break; + + case DXGI_FORMAT_R32G32B32A32_FLOAT: + hr = ConvertToRGBAF32(srcImage, image, srgb); + break; + + default: + hr = E_UNEXPECTED; + break; + } + + if (FAILED(hr)) + return hr; + + const Image *img = image.GetImage(0, 0, 0); + if (!img) + return E_POINTER; + + return gpubc->Compress(*img, destImage); + } + } +}; + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Compression +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::Compress( + ID3D11Device* pDevice, + const Image& srcImage, + DXGI_FORMAT format, + DWORD compress, + float alphaWeight, + ScratchImage& image) +{ + if (!pDevice || IsCompressed(srcImage.format) || !IsCompressed(format)) + return E_INVALIDARG; + + if (IsTypeless(format) + || IsTypeless(srcImage.format) || IsPlanar(srcImage.format) || IsPalettized(srcImage.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + // Setup GPU compressor + std::unique_ptr gpubc(new (std::nothrow) GPUCompressBC); + if (!gpubc) + return E_OUTOFMEMORY; + + HRESULT hr = gpubc->Initialize(pDevice); + if (FAILED(hr)) + return hr; + + hr = gpubc->Prepare(srcImage.width, srcImage.height, compress, format, alphaWeight); + if (FAILED(hr)) + return hr; + + // Create workspace for result + hr = image.Initialize2D(format, srcImage.width, srcImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *img = image.GetImage(0, 0, 0); + if (!img) + { + image.Release(); + return E_POINTER; + } + + hr = GPUCompress(gpubc.get(), srcImage, *img, compress); + if (FAILED(hr)) + image.Release(); + + return hr; +} + +_Use_decl_annotations_ +HRESULT DirectX::Compress( + ID3D11Device* pDevice, + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + DXGI_FORMAT format, + DWORD compress, + float alphaWeight, + ScratchImage& cImages) +{ + if (!pDevice || !srcImages || !nimages) + return E_INVALIDARG; + + if (IsCompressed(metadata.format) || !IsCompressed(format)) + return E_INVALIDARG; + + if (IsTypeless(format) + || IsTypeless(metadata.format) || IsPlanar(metadata.format) || IsPalettized(metadata.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + cImages.Release(); + + // Setup GPU compressor + std::unique_ptr gpubc(new (std::nothrow) GPUCompressBC); + if (!gpubc) + return E_OUTOFMEMORY; + + HRESULT hr = gpubc->Initialize(pDevice); + if (FAILED(hr)) + return hr; + + // Create workspace for result + TexMetadata mdata2 = metadata; + mdata2.format = format; + hr = cImages.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + if (nimages != cImages.GetImageCount()) + { + cImages.Release(); + return E_FAIL; + } + + const Image* dest = cImages.GetImages(); + if (!dest) + { + cImages.Release(); + return E_POINTER; + } + + // Process images (ordered by size) + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + case TEX_DIMENSION_TEXTURE2D: + { + size_t w = metadata.width; + size_t h = metadata.height; + + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + hr = gpubc->Prepare(w, h, compress, format, alphaWeight); + if (FAILED(hr)) + { + cImages.Release(); + return hr; + } + + for (size_t item = 0; item < metadata.arraySize; ++item) + { + size_t index = metadata.ComputeIndex(level, item, 0); + if (index >= nimages) + { + cImages.Release(); + return E_FAIL; + } + + assert(dest[index].format == format); + + const Image& src = srcImages[index]; + + if (src.width != dest[index].width || src.height != dest[index].height) + { + cImages.Release(); + return E_FAIL; + } + + hr = GPUCompress(gpubc.get(), src, dest[index], compress); + if (FAILED(hr)) + { + cImages.Release(); + return hr; + } + } + + if (h > 1) + h >>= 1; + + if (w > 1) + w >>= 1; + } + } + break; + + case TEX_DIMENSION_TEXTURE3D: + { + size_t w = metadata.width; + size_t h = metadata.height; + size_t d = metadata.depth; + + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + hr = gpubc->Prepare(w, h, compress, format, alphaWeight); + if (FAILED(hr)) + { + cImages.Release(); + return hr; + } + + for (size_t slice = 0; slice < d; ++slice) + { + size_t index = metadata.ComputeIndex(level, 0, slice); + if (index >= nimages) + { + cImages.Release(); + return E_FAIL; + } + + assert(dest[index].format == format); + + const Image& src = srcImages[index]; + + if (src.width != dest[index].width || src.height != dest[index].height) + { + cImages.Release(); + return E_FAIL; + } + + hr = GPUCompress(gpubc.get(), src, dest[index], compress); + if (FAILED(hr)) + { + cImages.Release(); + return hr; + } + } + + if (h > 1) + h >>= 1; + + if (w > 1) + w >>= 1; + + if (d > 1) + d >>= 1; + } + } + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexConvert.cpp b/deps/DirectXTex/DirectXTex/DirectXTexConvert.cpp new file mode 100644 index 0000000..b791556 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexConvert.cpp @@ -0,0 +1,5025 @@ +//------------------------------------------------------------------------------------- +// DirectXTexConvert.cpp +// +// DirectX Texture Library - Image pixel format conversion +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +using namespace DirectX; +using namespace DirectX::PackedVector; +using Microsoft::WRL::ComPtr; + +namespace +{ + inline uint32_t FloatTo7e3(float Value) + { + uint32_t IValue = reinterpret_cast(&Value)[0]; + + if (IValue & 0x80000000U) + { + // Positive only + return 0; + } + else if (IValue > 0x41FF73FFU) + { + // The number is too large to be represented as a 7e3. Saturate. + return 0x3FFU; + } + else + { + if (IValue < 0x3E800000U) + { + // The number is too small to be represented as a normalized 7e3. + // Convert it to a denormalized value. + uint32_t Shift = 125U - (IValue >> 23U); + IValue = (0x800000U | (IValue & 0x7FFFFFU)) >> Shift; + } + else + { + // Rebias the exponent to represent the value as a normalized 7e3. + IValue += 0xC2000000U; + } + + return ((IValue + 0x7FFFU + ((IValue >> 16U) & 1U)) >> 16U) & 0x3FFU; + } + } + + inline float FloatFrom7e3(uint32_t Value) + { + uint32_t Mantissa = (uint32_t)(Value & 0x7F); + + uint32_t Exponent = (Value & 0x380); + if (Exponent != 0) // The value is normalized + { + Exponent = (uint32_t)((Value >> 7) & 0x7); + } + else if (Mantissa != 0) // The value is denormalized + { + // Normalize the value in the resulting float + Exponent = 1; + + do + { + Exponent--; + Mantissa <<= 1; + } while ((Mantissa & 0x80) == 0); + + Mantissa &= 0x7F; + } + else // The value is zero + { + Exponent = (uint32_t)-124; + } + + uint32_t Result = ((Exponent + 124) << 23) | // Exponent + (Mantissa << 16); // Mantissa + + return reinterpret_cast(&Result)[0]; + } + + inline uint32_t FloatTo6e4(float Value) + { + uint32_t IValue = reinterpret_cast(&Value)[0]; + + if (IValue & 0x80000000U) + { + // Positive only + return 0; + } + else if (IValue > 0x43FEFFFFU) + { + // The number is too large to be represented as a 6e4. Saturate. + return 0x3FFU; + } + else + { + if (IValue < 0x3C800000U) + { + // The number is too small to be represented as a normalized 6e4. + // Convert it to a denormalized value. + uint32_t Shift = 121U - (IValue >> 23U); + IValue = (0x800000U | (IValue & 0x7FFFFFU)) >> Shift; + } + else + { + // Rebias the exponent to represent the value as a normalized 6e4. + IValue += 0xC4000000U; + } + + return ((IValue + 0xFFFFU + ((IValue >> 17U) & 1U)) >> 17U) & 0x3FFU; + } + } + + inline float FloatFrom6e4(uint32_t Value) + { + uint32_t Mantissa = (uint32_t)(Value & 0x3F); + + uint32_t Exponent = (Value & 0x3C0); + if (Exponent != 0) // The value is normalized + { + Exponent = (uint32_t)((Value >> 6) & 0xF); + } + else if (Mantissa != 0) // The value is denormalized + { + // Normalize the value in the resulting float + Exponent = 1; + + do + { + Exponent--; + Mantissa <<= 1; + } while ((Mantissa & 0x40) == 0); + + Mantissa &= 0x3F; + } + else // The value is zero + { + Exponent = (uint32_t)-120; + } + + uint32_t Result = ((Exponent + 120) << 23) | // Exponent + (Mantissa << 17); // Mantissa + + return reinterpret_cast(&Result)[0]; + } + +#if DIRECTX_MATH_VERSION >= 310 +#define StoreFloat3SE XMStoreFloat3SE +#else + inline void XM_CALLCONV StoreFloat3SE(_Out_ XMFLOAT3SE* pDestination, DirectX::FXMVECTOR V) + { + assert(pDestination); + + DirectX::XMFLOAT3A tmp; + DirectX::XMStoreFloat3A(&tmp, V); + + static const float maxf9 = float(0x1FF << 7); + static const float minf9 = float(1.f / (1 << 16)); + + float x = (tmp.x >= 0.f) ? ((tmp.x > maxf9) ? maxf9 : tmp.x) : 0.f; + float y = (tmp.y >= 0.f) ? ((tmp.y > maxf9) ? maxf9 : tmp.y) : 0.f; + float z = (tmp.z >= 0.f) ? ((tmp.z > maxf9) ? maxf9 : tmp.z) : 0.f; + + const float max_xy = (x > y) ? x : y; + const float max_xyz = (max_xy > z) ? max_xy : z; + + const float maxColor = (max_xyz > minf9) ? max_xyz : minf9; + + union { float f; int32_t i; } fi; + fi.f = maxColor; + fi.i += 0x00004000; // round up leaving 9 bits in fraction (including assumed 1) + + // Fix applied from DirectXMath 3.10 + uint32_t exp = fi.i >> 23; + pDestination->e = exp - 0x6f; + + fi.i = 0x83000000 - (exp << 23); + float ScaleR = fi.f; + + pDestination->xm = static_cast(lroundf(x * ScaleR)); + pDestination->ym = static_cast(lroundf(y * ScaleR)); + pDestination->zm = static_cast(lroundf(z * ScaleR)); + } +#endif + + const XMVECTORF32 g_Grayscale = { { { 0.2125f, 0.7154f, 0.0721f, 0.0f } } }; + const XMVECTORF32 g_HalfMin = { { { -65504.f, -65504.f, -65504.f, -65504.f } } }; + const XMVECTORF32 g_HalfMax = { { { 65504.f, 65504.f, 65504.f, 65504.f } } }; + const XMVECTORF32 g_8BitBias = { { { 0.5f / 255.f, 0.5f / 255.f, 0.5f / 255.f, 0.5f / 255.f } } }; +} + +//------------------------------------------------------------------------------------- +// Copies an image row with optional clearing of alpha value to 1.0 +// (can be used in place as well) otherwise copies the image row unmodified. +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DirectX::_CopyScanline( + void* pDestination, + size_t outSize, + const void* pSource, + size_t inSize, + DXGI_FORMAT format, + DWORD flags) +{ + assert(pDestination && outSize > 0); + assert(pSource && inSize > 0); + assert(IsValid(format) && !IsPalettized(format)); + + if (flags & TEXP_SCANLINE_SETALPHA) + { + switch (static_cast(format)) + { + //----------------------------------------------------------------------------- + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + if (inSize >= 16 && outSize >= 16) + { + uint32_t alpha; + if (format == DXGI_FORMAT_R32G32B32A32_FLOAT) + alpha = 0x3f800000; + else if (format == DXGI_FORMAT_R32G32B32A32_SINT) + alpha = 0x7fffffff; + else + alpha = 0xffffffff; + + if (pDestination == pSource) + { + uint32_t *dPtr = reinterpret_cast (pDestination); + for (size_t count = 0; count < (outSize - 15); count += 16) + { + dPtr += 3; + *(dPtr++) = alpha; + } + } + else + { + const uint32_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + size_t size = std::min(outSize, inSize); + for (size_t count = 0; count < (size - 15); count += 16) + { + *(dPtr++) = *(sPtr++); + *(dPtr++) = *(sPtr++); + *(dPtr++) = *(sPtr++); + *(dPtr++) = alpha; + ++sPtr; + } + } + } + return; + + //----------------------------------------------------------------------------- + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_Y416: + if (inSize >= 8 && outSize >= 8) + { + uint16_t alpha; + if (format == DXGI_FORMAT_R16G16B16A16_FLOAT) + alpha = 0x3c00; + else if (format == DXGI_FORMAT_R16G16B16A16_SNORM || format == DXGI_FORMAT_R16G16B16A16_SINT) + alpha = 0x7fff; + else + alpha = 0xffff; + + if (pDestination == pSource) + { + uint16_t *dPtr = reinterpret_cast(pDestination); + for (size_t count = 0; count < (outSize - 7); count += 8) + { + dPtr += 3; + *(dPtr++) = alpha; + } + } + else + { + const uint16_t * __restrict sPtr = reinterpret_cast(pSource); + uint16_t * __restrict dPtr = reinterpret_cast(pDestination); + size_t size = std::min(outSize, inSize); + for (size_t count = 0; count < (size - 7); count += 8) + { + *(dPtr++) = *(sPtr++); + *(dPtr++) = *(sPtr++); + *(dPtr++) = *(sPtr++); + *(dPtr++) = alpha; + ++sPtr; + } + } + } + return; + + //----------------------------------------------------------------------------- + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_Y410: + case XBOX_DXGI_FORMAT_R10G10B10_7E3_A2_FLOAT: + case XBOX_DXGI_FORMAT_R10G10B10_6E4_A2_FLOAT: + case XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM: + if (inSize >= 4 && outSize >= 4) + { + if (pDestination == pSource) + { + uint32_t *dPtr = reinterpret_cast(pDestination); + for (size_t count = 0; count < (outSize - 3); count += 4) + { + *dPtr |= 0xC0000000; + ++dPtr; + } + } + else + { + const uint32_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + size_t size = std::min(outSize, inSize); + for (size_t count = 0; count < (size - 3); count += 4) + { + *(dPtr++) = *(sPtr++) | 0xC0000000; + } + } + } + return; + + //----------------------------------------------------------------------------- + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + if (inSize >= 4 && outSize >= 4) + { + const uint32_t alpha = (format == DXGI_FORMAT_R8G8B8A8_SNORM || format == DXGI_FORMAT_R8G8B8A8_SINT) ? 0x7f000000 : 0xff000000; + + if (pDestination == pSource) + { + uint32_t *dPtr = reinterpret_cast(pDestination); + for (size_t count = 0; count < (outSize - 3); count += 4) + { + uint32_t t = *dPtr & 0xFFFFFF; + t |= alpha; + *(dPtr++) = t; + } + } + else + { + const uint32_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + size_t size = std::min(outSize, inSize); + for (size_t count = 0; count < (size - 3); count += 4) + { + uint32_t t = *(sPtr++) & 0xFFFFFF; + t |= alpha; + *(dPtr++) = t; + } + } + } + return; + + //----------------------------------------------------------------------------- + case DXGI_FORMAT_B5G5R5A1_UNORM: + if (inSize >= 2 && outSize >= 2) + { + if (pDestination == pSource) + { + uint16_t *dPtr = reinterpret_cast(pDestination); + for (size_t count = 0; count < (outSize - 1); count += 2) + { + *(dPtr++) |= 0x8000; + } + } + else + { + const uint16_t * __restrict sPtr = reinterpret_cast(pSource); + uint16_t * __restrict dPtr = reinterpret_cast(pDestination); + size_t size = std::min(outSize, inSize); + for (size_t count = 0; count < (size - 1); count += 2) + { + *(dPtr++) = *(sPtr++) | 0x8000; + } + } + } + return; + + //----------------------------------------------------------------------------- + case DXGI_FORMAT_A8_UNORM: + memset(pDestination, 0xff, outSize); + return; + + //----------------------------------------------------------------------------- + case DXGI_FORMAT_B4G4R4A4_UNORM: + if (inSize >= 2 && outSize >= 2) + { + if (pDestination == pSource) + { + uint16_t *dPtr = reinterpret_cast(pDestination); + for (size_t count = 0; count < (outSize - 1); count += 2) + { + *(dPtr++) |= 0xF000; + } + } + else + { + const uint16_t * __restrict sPtr = reinterpret_cast(pSource); + uint16_t * __restrict dPtr = reinterpret_cast(pDestination); + size_t size = std::min(outSize, inSize); + for (size_t count = 0; count < (size - 1); count += 2) + { + *(dPtr++) = *(sPtr++) | 0xF000; + } + } + } + return; + } + } + + // Fall-through case is to just use memcpy (assuming this is not an in-place operation) + if (pDestination == pSource) + return; + + size_t size = std::min(outSize, inSize); + memcpy_s(pDestination, outSize, pSource, size); +} + + +//------------------------------------------------------------------------------------- +// Swizzles (RGB <-> BGR) an image row with optional clearing of alpha value to 1.0 +// (can be used in place as well) otherwise copies the image row unmodified. +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DirectX::_SwizzleScanline( + void* pDestination, + size_t outSize, + const void* pSource, + size_t inSize, + DXGI_FORMAT format, + DWORD flags) +{ + assert(pDestination && outSize > 0); + assert(pSource && inSize > 0); + assert(IsValid(format) && !IsPlanar(format) && !IsPalettized(format)); + + switch (static_cast(format)) + { + //--------------------------------------------------------------------------------- + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM: + if (inSize >= 4 && outSize >= 4) + { + if (flags & TEXP_SCANLINE_LEGACY) + { + // Swap Red (R) and Blue (B) channel (used for D3DFMT_A2R10G10B10 legacy sources) + if (pDestination == pSource) + { + uint32_t *dPtr = reinterpret_cast(pDestination); + for (size_t count = 0; count < (outSize - 3); count += 4) + { + uint32_t t = *dPtr; + + uint32_t t1 = (t & 0x3ff00000) >> 20; + uint32_t t2 = (t & 0x000003ff) << 20; + uint32_t t3 = (t & 0x000ffc00); + uint32_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xC0000000 : (t & 0xC0000000); + + *(dPtr++) = t1 | t2 | t3 | ta; + } + } + else + { + const uint32_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + size_t size = std::min(outSize, inSize); + for (size_t count = 0; count < (size - 3); count += 4) + { + uint32_t t = *(sPtr++); + + uint32_t t1 = (t & 0x3ff00000) >> 20; + uint32_t t2 = (t & 0x000003ff) << 20; + uint32_t t3 = (t & 0x000ffc00); + uint32_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xC0000000 : (t & 0xC0000000); + + *(dPtr++) = t1 | t2 | t3 | ta; + } + } + return; + } + } + break; + + //--------------------------------------------------------------------------------- + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + if (inSize >= 4 && outSize >= 4) + { + // Swap Red (R) and Blue (B) channels (used to convert from DXGI 1.1 BGR formats to DXGI 1.0 RGB) + if (pDestination == pSource) + { + uint32_t *dPtr = reinterpret_cast(pDestination); + for (size_t count = 0; count < (outSize - 3); count += 4) + { + uint32_t t = *dPtr; + + uint32_t t1 = (t & 0x00ff0000) >> 16; + uint32_t t2 = (t & 0x000000ff) << 16; + uint32_t t3 = (t & 0x0000ff00); + uint32_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xff000000 : (t & 0xFF000000); + + *(dPtr++) = t1 | t2 | t3 | ta; + } + } + else + { + const uint32_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + size_t size = std::min(outSize, inSize); + for (size_t count = 0; count < (size - 3); count += 4) + { + uint32_t t = *(sPtr++); + + uint32_t t1 = (t & 0x00ff0000) >> 16; + uint32_t t2 = (t & 0x000000ff) << 16; + uint32_t t3 = (t & 0x0000ff00); + uint32_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xff000000 : (t & 0xFF000000); + + *(dPtr++) = t1 | t2 | t3 | ta; + } + } + return; + } + break; + + //--------------------------------------------------------------------------------- + case DXGI_FORMAT_YUY2: + if (inSize >= 4 && outSize >= 4) + { + if (flags & TEXP_SCANLINE_LEGACY) + { + // Reorder YUV components (used to convert legacy UYVY -> YUY2) + if (pDestination == pSource) + { + uint32_t *dPtr = reinterpret_cast(pDestination); + for (size_t count = 0; count < (outSize - 3); count += 4) + { + uint32_t t = *dPtr; + + uint32_t t1 = (t & 0x000000ff) << 8; + uint32_t t2 = (t & 0x0000ff00) >> 8; + uint32_t t3 = (t & 0x00ff0000) << 8; + uint32_t t4 = (t & 0xff000000) >> 8; + + *(dPtr++) = t1 | t2 | t3 | t4; + } + } + else + { + const uint32_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + size_t size = std::min(outSize, inSize); + for (size_t count = 0; count < (size - 3); count += 4) + { + uint32_t t = *(sPtr++); + + uint32_t t1 = (t & 0x000000ff) << 8; + uint32_t t2 = (t & 0x0000ff00) >> 8; + uint32_t t3 = (t & 0x00ff0000) << 8; + uint32_t t4 = (t & 0xff000000) >> 8; + + *(dPtr++) = t1 | t2 | t3 | t4; + } + } + return; + } + } + break; + } + + // Fall-through case is to just use memcpy (assuming this is not an in-place operation) + if (pDestination == pSource) + return; + + size_t size = std::min(outSize, inSize); + memcpy_s(pDestination, outSize, pSource, size); +} + + +//------------------------------------------------------------------------------------- +// Converts an image row with optional clearing of alpha value to 1.0 +// Returns true if supported, false if expansion case not supported +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::_ExpandScanline( + void* pDestination, + size_t outSize, + DXGI_FORMAT outFormat, + const void* pSource, + size_t inSize, + DXGI_FORMAT inFormat, + DWORD flags) +{ + assert(pDestination && outSize > 0); + assert(pSource && inSize > 0); + assert(IsValid(outFormat) && !IsPlanar(outFormat) && !IsPalettized(outFormat)); + assert(IsValid(inFormat) && !IsPlanar(inFormat) && !IsPalettized(inFormat)); + + switch (inFormat) + { + case DXGI_FORMAT_B5G6R5_UNORM: + if (outFormat != DXGI_FORMAT_R8G8B8A8_UNORM) + return false; + + // DXGI_FORMAT_B5G6R5_UNORM -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 2 && outSize >= 4) + { + const uint16_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < (inSize - 1)) && (ocount < (outSize - 3))); icount += 2, ocount += 4) + { + uint16_t t = *(sPtr++); + + uint32_t t1 = ((t & 0xf800) >> 8) | ((t & 0xe000) >> 13); + uint32_t t2 = ((t & 0x07e0) << 5) | ((t & 0x0600) >> 5); + uint32_t t3 = ((t & 0x001f) << 19) | ((t & 0x001c) << 14); + + *(dPtr++) = t1 | t2 | t3 | 0xff000000; + } + return true; + } + return false; + + case DXGI_FORMAT_B5G5R5A1_UNORM: + if (outFormat != DXGI_FORMAT_R8G8B8A8_UNORM) + return false; + + // DXGI_FORMAT_B5G5R5A1_UNORM -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 2 && outSize >= 4) + { + const uint16_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < (inSize - 1)) && (ocount < (outSize - 3))); icount += 2, ocount += 4) + { + uint16_t t = *(sPtr++); + + uint32_t t1 = ((t & 0x7c00) >> 7) | ((t & 0x7000) >> 12); + uint32_t t2 = ((t & 0x03e0) << 6) | ((t & 0x0380) << 1); + uint32_t t3 = ((t & 0x001f) << 19) | ((t & 0x001c) << 14); + uint32_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xff000000 : ((t & 0x8000) ? 0xff000000 : 0); + + *(dPtr++) = t1 | t2 | t3 | ta; + } + return true; + } + return false; + + case DXGI_FORMAT_B4G4R4A4_UNORM: + if (outFormat != DXGI_FORMAT_R8G8B8A8_UNORM) + return false; + + // DXGI_FORMAT_B4G4R4A4_UNORM -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 2 && outSize >= 4) + { + const uint16_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < (inSize - 1)) && (ocount < (outSize - 3))); icount += 2, ocount += 4) + { + uint16_t t = *(sPtr++); + + uint32_t t1 = ((t & 0x0f00) >> 4) | ((t & 0x0f00) >> 8); + uint32_t t2 = ((t & 0x00f0) << 8) | ((t & 0x00f0) << 4); + uint32_t t3 = ((t & 0x000f) << 20) | ((t & 0x000f) << 16); + uint32_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xff000000 : (((t & 0xf000) << 16) | ((t & 0xf000) << 12)); + + *(dPtr++) = t1 | t2 | t3 | ta; + } + return true; + } + return false; + + default: + return false; + } +} + + +//------------------------------------------------------------------------------------- +// Loads an image row into standard RGBA XMVECTOR (aligned) array +//------------------------------------------------------------------------------------- +#define LOAD_SCANLINE( type, func )\ + if ( size >= sizeof(type) )\ + {\ + const type * __restrict sPtr = reinterpret_cast(pSource);\ + for( size_t icount = 0; icount < ( size - sizeof(type) + 1 ); icount += sizeof(type) )\ + {\ + if ( dPtr >= ePtr ) break;\ + *(dPtr++) = func( sPtr++ );\ + }\ + return true;\ + }\ + return false; + +#define LOAD_SCANLINE3( type, func, defvec )\ + if ( size >= sizeof(type) )\ + {\ + const type * __restrict sPtr = reinterpret_cast(pSource);\ + for( size_t icount = 0; icount < ( size - sizeof(type) + 1 ); icount += sizeof(type) )\ + {\ + XMVECTOR v = func( sPtr++ );\ + if ( dPtr >= ePtr ) break;\ + *(dPtr++) = XMVectorSelect( defvec, v, g_XMSelect1110 );\ + }\ + return true;\ + }\ + return false; + +#define LOAD_SCANLINE2( type, func, defvec )\ + if ( size >= sizeof(type) )\ + {\ + const type * __restrict sPtr = reinterpret_cast(pSource);\ + for( size_t icount = 0; icount < ( size - sizeof(type) + 1 ); icount += sizeof(type) )\ + {\ + XMVECTOR v = func( sPtr++ );\ + if ( dPtr >= ePtr ) break;\ + *(dPtr++) = XMVectorSelect( defvec, v, g_XMSelect1100 );\ + }\ + return true;\ + }\ + return false; + +#pragma warning(suppress: 6101) +_Use_decl_annotations_ bool DirectX::_LoadScanline( + XMVECTOR* pDestination, + size_t count, + const void* pSource, + size_t size, + DXGI_FORMAT format) +{ + assert(pDestination && count > 0 && (((uintptr_t)pDestination & 0xF) == 0)); + assert(pSource && size > 0); + assert(IsValid(format) && !IsTypeless(format, false) && !IsCompressed(format) && !IsPlanar(format) && !IsPalettized(format)); + + XMVECTOR* __restrict dPtr = pDestination; + if (!dPtr) + return false; + + const XMVECTOR* ePtr = pDestination + count; + + switch (static_cast(format)) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: + { + size_t msize = (size > (sizeof(XMVECTOR)*count)) ? (sizeof(XMVECTOR)*count) : size; + memcpy_s(dPtr, sizeof(XMVECTOR)*count, pSource, msize); + } + return true; + + case DXGI_FORMAT_R32G32B32A32_UINT: + LOAD_SCANLINE(XMUINT4, XMLoadUInt4) + + case DXGI_FORMAT_R32G32B32A32_SINT: + LOAD_SCANLINE(XMINT4, XMLoadSInt4) + + case DXGI_FORMAT_R32G32B32_FLOAT: + LOAD_SCANLINE3(XMFLOAT3, XMLoadFloat3, g_XMIdentityR3) + + case DXGI_FORMAT_R32G32B32_UINT: + LOAD_SCANLINE3(XMUINT3, XMLoadUInt3, g_XMIdentityR3) + + case DXGI_FORMAT_R32G32B32_SINT: + LOAD_SCANLINE3(XMINT3, XMLoadSInt3, g_XMIdentityR3) + + case DXGI_FORMAT_R16G16B16A16_FLOAT: + LOAD_SCANLINE(XMHALF4, XMLoadHalf4) + + case DXGI_FORMAT_R16G16B16A16_UNORM: + LOAD_SCANLINE(XMUSHORTN4, XMLoadUShortN4) + + case DXGI_FORMAT_R16G16B16A16_UINT: + LOAD_SCANLINE(XMUSHORT4, XMLoadUShort4) + + case DXGI_FORMAT_R16G16B16A16_SNORM: + LOAD_SCANLINE(XMSHORTN4, XMLoadShortN4) + + case DXGI_FORMAT_R16G16B16A16_SINT: + LOAD_SCANLINE(XMSHORT4, XMLoadShort4) + + case DXGI_FORMAT_R32G32_FLOAT: + LOAD_SCANLINE2(XMFLOAT2, XMLoadFloat2, g_XMIdentityR3) + + case DXGI_FORMAT_R32G32_UINT: + LOAD_SCANLINE2(XMUINT2, XMLoadUInt2, g_XMIdentityR3) + + case DXGI_FORMAT_R32G32_SINT: + LOAD_SCANLINE2(XMINT2, XMLoadSInt2, g_XMIdentityR3) + + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + { + const size_t psize = sizeof(float) + sizeof(uint32_t); + if (size >= psize) + { + const float * sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - psize + 1); icount += psize) + { + const uint8_t* ps8 = reinterpret_cast(&sPtr[1]); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(sPtr[0], static_cast(*ps8), 0.f, 1.f); + sPtr += 2; + } + return true; + } + } + return false; + + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + { + const size_t psize = sizeof(float) + sizeof(uint32_t); + if (size >= psize) + { + const float * sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - psize + 1); icount += psize) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(sPtr[0], 0.f /* typeless component assumed zero */, 0.f, 1.f); + sPtr += 2; + } + return true; + } + } + return false; + + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + { + const size_t psize = sizeof(float) + sizeof(uint32_t); + if (size >= psize) + { + const float * sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - psize + 1); icount += psize) + { + const uint8_t* pg8 = reinterpret_cast(&sPtr[1]); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(0.f /* typeless component assumed zero */, static_cast(*pg8), 0.f, 1.f); + sPtr += 2; + } + return true; + } + } + return false; + + case DXGI_FORMAT_R10G10B10A2_UNORM: + LOAD_SCANLINE(XMUDECN4, XMLoadUDecN4); + + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + LOAD_SCANLINE(XMUDECN4, XMLoadUDecN4_XR); + + case DXGI_FORMAT_R10G10B10A2_UINT: + LOAD_SCANLINE(XMUDEC4, XMLoadUDec4); + + case DXGI_FORMAT_R11G11B10_FLOAT: + LOAD_SCANLINE3(XMFLOAT3PK, XMLoadFloat3PK, g_XMIdentityR3); + + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + LOAD_SCANLINE(XMUBYTEN4, XMLoadUByteN4) + + case DXGI_FORMAT_R8G8B8A8_UINT: + LOAD_SCANLINE(XMUBYTE4, XMLoadUByte4) + + case DXGI_FORMAT_R8G8B8A8_SNORM: + LOAD_SCANLINE(XMBYTEN4, XMLoadByteN4) + + case DXGI_FORMAT_R8G8B8A8_SINT: + LOAD_SCANLINE(XMBYTE4, XMLoadByte4) + + case DXGI_FORMAT_R16G16_FLOAT: + LOAD_SCANLINE2(XMHALF2, XMLoadHalf2, g_XMIdentityR3) + + case DXGI_FORMAT_R16G16_UNORM: + LOAD_SCANLINE2(XMUSHORTN2, XMLoadUShortN2, g_XMIdentityR3) + + case DXGI_FORMAT_R16G16_UINT: + LOAD_SCANLINE2(XMUSHORT2, XMLoadUShort2, g_XMIdentityR3) + + case DXGI_FORMAT_R16G16_SNORM: + LOAD_SCANLINE2(XMSHORTN2, XMLoadShortN2, g_XMIdentityR3) + + case DXGI_FORMAT_R16G16_SINT: + LOAD_SCANLINE2(XMSHORT2, XMLoadShort2, g_XMIdentityR3) + + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + if (size >= sizeof(float)) + { + const float* __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(float) + 1); icount += sizeof(float)) + { + XMVECTOR v = XMLoadFloat(sPtr++); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSelect(g_XMIdentityR3, v, g_XMSelect1000); + } + return true; + } + return false; + + case DXGI_FORMAT_R32_UINT: + if (size >= sizeof(uint32_t)) + { + const uint32_t* __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(uint32_t) + 1); icount += sizeof(uint32_t)) + { + XMVECTOR v = XMLoadInt(sPtr++); + v = XMConvertVectorUIntToFloat(v, 0); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSelect(g_XMIdentityR3, v, g_XMSelect1000); + } + return true; + } + return false; + + case DXGI_FORMAT_R32_SINT: + if (size >= sizeof(int32_t)) + { + const int32_t * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(int32_t) + 1); icount += sizeof(int32_t)) + { + XMVECTOR v = XMLoadInt(reinterpret_cast (sPtr++)); + v = XMConvertVectorIntToFloat(v, 0); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSelect(g_XMIdentityR3, v, g_XMSelect1000); + } + return true; + } + return false; + + case DXGI_FORMAT_D24_UNORM_S8_UINT: + if (size >= sizeof(uint32_t)) + { + const uint32_t * sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(uint32_t) + 1); icount += sizeof(uint32_t)) + { + float d = static_cast(*sPtr & 0xFFFFFF) / 16777215.f; + float s = static_cast((*sPtr & 0xFF000000) >> 24); + ++sPtr; + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(d, s, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + if (size >= sizeof(uint32_t)) + { + const uint32_t * sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(uint32_t) + 1); icount += sizeof(uint32_t)) + { + float r = static_cast(*sPtr & 0xFFFFFF) / 16777215.f; + ++sPtr; + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(r, 0.f /* typeless component assumed zero */, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + if (size >= sizeof(uint32_t)) + { + const uint32_t * sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(uint32_t) + 1); icount += sizeof(uint32_t)) + { + float g = static_cast((*sPtr & 0xFF000000) >> 24); + ++sPtr; + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(0.f /* typeless component assumed zero */, g, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R8G8_UNORM: + LOAD_SCANLINE2(XMUBYTEN2, XMLoadUByteN2, g_XMIdentityR3) + + case DXGI_FORMAT_R8G8_UINT: + LOAD_SCANLINE2(XMUBYTE2, XMLoadUByte2, g_XMIdentityR3) + + case DXGI_FORMAT_R8G8_SNORM: + LOAD_SCANLINE2(XMBYTEN2, XMLoadByteN2, g_XMIdentityR3) + + case DXGI_FORMAT_R8G8_SINT: + LOAD_SCANLINE2(XMBYTE2, XMLoadByte2, g_XMIdentityR3) + + case DXGI_FORMAT_R16_FLOAT: + if (size >= sizeof(HALF)) + { + const HALF * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(HALF) + 1); icount += sizeof(HALF)) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(XMConvertHalfToFloat(*sPtr++), 0.f, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + if (size >= sizeof(uint16_t)) + { + const uint16_t* __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(uint16_t) + 1); icount += sizeof(uint16_t)) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(static_cast(*sPtr++) / 65535.f, 0.f, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R16_UINT: + if (size >= sizeof(uint16_t)) + { + const uint16_t * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(uint16_t) + 1); icount += sizeof(uint16_t)) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(static_cast(*sPtr++), 0.f, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R16_SNORM: + if (size >= sizeof(int16_t)) + { + const int16_t * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(int16_t) + 1); icount += sizeof(int16_t)) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(static_cast(*sPtr++) / 32767.f, 0.f, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R16_SINT: + if (size >= sizeof(int16_t)) + { + const int16_t * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(int16_t) + 1); icount += sizeof(int16_t)) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(static_cast(*sPtr++), 0.f, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R8_UNORM: + if (size >= sizeof(uint8_t)) + { + const uint8_t * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < size; icount += sizeof(uint8_t)) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(static_cast(*sPtr++) / 255.f, 0.f, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R8_UINT: + if (size >= sizeof(uint8_t)) + { + const uint8_t * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < size; icount += sizeof(uint8_t)) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(static_cast(*sPtr++), 0.f, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R8_SNORM: + if (size >= sizeof(int8_t)) + { + const int8_t * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < size; icount += sizeof(int8_t)) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(static_cast(*sPtr++) / 127.f, 0.f, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R8_SINT: + if (size >= sizeof(int8_t)) + { + const int8_t * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < size; icount += sizeof(int8_t)) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(static_cast(*sPtr++), 0.f, 0.f, 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_A8_UNORM: + if (size >= sizeof(uint8_t)) + { + const uint8_t * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < size; icount += sizeof(uint8_t)) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(0.f, 0.f, 0.f, static_cast(*sPtr++) / 255.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R1_UNORM: + if (size >= sizeof(uint8_t)) + { + const uint8_t * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < size; icount += sizeof(uint8_t)) + { + for (size_t bcount = 8; bcount > 0; --bcount) + { + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet((((*sPtr >> (bcount - 1)) & 0x1) ? 1.f : 0.f), 0.f, 0.f, 1.f); + } + + ++sPtr; + } + return true; + } + return false; + + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + LOAD_SCANLINE3(XMFLOAT3SE, XMLoadFloat3SE, g_XMIdentityR3) + + case DXGI_FORMAT_R8G8_B8G8_UNORM: + if (size >= sizeof(XMUBYTEN4)) + { + const XMUBYTEN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + XMVECTOR v = XMLoadUByteN4(sPtr++); + XMVECTOR v1 = XMVectorSwizzle<0, 3, 2, 1>(v); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSelect(g_XMIdentityR3, v, g_XMSelect1110); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSelect(g_XMIdentityR3, v1, g_XMSelect1110); + } + return true; + } + return false; + + case DXGI_FORMAT_G8R8_G8B8_UNORM: + if (size >= sizeof(XMUBYTEN4)) + { + const XMUBYTEN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + XMVECTOR v = XMLoadUByteN4(sPtr++); + XMVECTOR v0 = XMVectorSwizzle<1, 0, 3, 2>(v); + XMVECTOR v1 = XMVectorSwizzle<1, 2, 3, 0>(v); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSelect(g_XMIdentityR3, v0, g_XMSelect1110); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSelect(g_XMIdentityR3, v1, g_XMSelect1110); + } + return true; + } + return false; + + case DXGI_FORMAT_B5G6R5_UNORM: + if (size >= sizeof(XMU565)) + { + static const XMVECTORF32 s_Scale = { { { 1.f / 31.f, 1.f / 63.f, 1.f / 31.f, 1.f } } }; + const XMU565 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMU565) + 1); icount += sizeof(XMU565)) + { + XMVECTOR v = XMLoadU565(sPtr++); + v = XMVectorMultiply(v, s_Scale); + v = XMVectorSwizzle<2, 1, 0, 3>(v); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSelect(g_XMIdentityR3, v, g_XMSelect1110); + } + return true; + } + return false; + + case DXGI_FORMAT_B5G5R5A1_UNORM: + if (size >= sizeof(XMU555)) + { + static const XMVECTORF32 s_Scale = { { { 1.f / 31.f, 1.f / 31.f, 1.f / 31.f, 1.f } } }; + const XMU555 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMU555) + 1); icount += sizeof(XMU555)) + { + XMVECTOR v = XMLoadU555(sPtr++); + v = XMVectorMultiply(v, s_Scale); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSwizzle<2, 1, 0, 3>(v); + } + return true; + } + return false; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + if (size >= sizeof(XMUBYTEN4)) + { + const XMUBYTEN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + XMVECTOR v = XMLoadUByteN4(sPtr++); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSwizzle<2, 1, 0, 3>(v); + } + return true; + } + return false; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + if (size >= sizeof(XMUBYTEN4)) + { + const XMUBYTEN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + XMVECTOR v = XMLoadUByteN4(sPtr++); + v = XMVectorSwizzle<2, 1, 0, 3>(v); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSelect(g_XMIdentityR3, v, g_XMSelect1110); + } + return true; + } + return false; + + case DXGI_FORMAT_AYUV: + if (size >= sizeof(XMUBYTEN4)) + { + const XMUBYTEN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + int v = int(sPtr->x) - 128; + int u = int(sPtr->y) - 128; + int y = int(sPtr->z) - 16; + unsigned int a = sPtr->w; + ++sPtr; + + // http://msdn.microsoft.com/en-us/library/windows/desktop/dd206750.aspx + + // Y’ = Y - 16 + // Cb’ = Cb - 128 + // Cr’ = Cr - 128 + + // R = 1.1644Y’ + 1.5960Cr’ + // G = 1.1644Y’ - 0.3917Cb’ - 0.8128Cr’ + // B = 1.1644Y’ + 2.0172Cb’ + + int r = (298 * y + 409 * v + 128) >> 8; + int g = (298 * y - 100 * u - 208 * v + 128) >> 8; + int b = (298 * y + 516 * u + 128) >> 8; + + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(float(std::min(std::max(r, 0), 255)) / 255.f, + float(std::min(std::max(g, 0), 255)) / 255.f, + float(std::min(std::max(b, 0), 255)) / 255.f, + float(a / 255.f)); + } + return true; + } + return false; + + case DXGI_FORMAT_Y410: + if (size >= sizeof(XMUDECN4)) + { + const XMUDECN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUDECN4) + 1); icount += sizeof(XMUDECN4)) + { + int64_t u = int(sPtr->x) - 512; + int64_t y = int(sPtr->y) - 64; + int64_t v = int(sPtr->z) - 512; + unsigned int a = sPtr->w; + ++sPtr; + + // http://msdn.microsoft.com/en-us/library/windows/desktop/bb970578.aspx + + // Y’ = Y - 64 + // Cb’ = Cb - 512 + // Cr’ = Cr - 512 + + // R = 1.1678Y’ + 1.6007Cr’ + // G = 1.1678Y’ - 0.3929Cb’ - 0.8152Cr’ + // B = 1.1678Y’ + 2.0232Cb’ + + int r = static_cast((76533 * y + 104905 * v + 32768) >> 16); + int g = static_cast((76533 * y - 25747 * u - 53425 * v + 32768) >> 16); + int b = static_cast((76533 * y + 132590 * u + 32768) >> 16); + + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(float(std::min(std::max(r, 0), 1023)) / 1023.f, + float(std::min(std::max(g, 0), 1023)) / 1023.f, + float(std::min(std::max(b, 0), 1023)) / 1023.f, + float(a / 3.f)); + } + return true; + } + return false; + + case DXGI_FORMAT_Y416: + if (size >= sizeof(XMUSHORTN4)) + { + const XMUSHORTN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUSHORTN4) + 1); icount += sizeof(XMUSHORTN4)) + { + int64_t u = int64_t(sPtr->x) - 32768; + int64_t y = int64_t(sPtr->y) - 4096; + int64_t v = int64_t(sPtr->z) - 32768; + unsigned int a = sPtr->w; + ++sPtr; + + // http://msdn.microsoft.com/en-us/library/windows/desktop/bb970578.aspx + + // Y’ = Y - 4096 + // Cb’ = Cb - 32768 + // Cr’ = Cr - 32768 + + // R = 1.1689Y’ + 1.6023Cr’ + // G = 1.1689Y’ - 0.3933Cb’ - 0.8160Cr’ + // B = 1.1689Y’+ 2.0251Cb’ + + int r = static_cast((76607 * y + 105006 * v + 32768) >> 16); + int g = static_cast((76607 * y - 25772 * u - 53477 * v + 32768) >> 16); + int b = static_cast((76607 * y + 132718 * u + 32768) >> 16); + + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(float(std::min(std::max(r, 0), 65535)) / 65535.f, + float(std::min(std::max(g, 0), 65535)) / 65535.f, + float(std::min(std::max(b, 0), 65535)) / 65535.f, + float(std::min(std::max(a, 0), 65535)) / 65535.f); + } + return true; + } + return false; + + case DXGI_FORMAT_YUY2: + if (size >= sizeof(XMUBYTEN4)) + { + const XMUBYTEN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + int y0 = int(sPtr->x) - 16; + int u = int(sPtr->y) - 128; + int y1 = int(sPtr->z) - 16; + int v = int(sPtr->w) - 128; + ++sPtr; + + // See AYUV + int r = (298 * y0 + 409 * v + 128) >> 8; + int g = (298 * y0 - 100 * u - 208 * v + 128) >> 8; + int b = (298 * y0 + 516 * u + 128) >> 8; + + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(float(std::min(std::max(r, 0), 255)) / 255.f, + float(std::min(std::max(g, 0), 255)) / 255.f, + float(std::min(std::max(b, 0), 255)) / 255.f, + 1.f); + + r = (298 * y1 + 409 * v + 128) >> 8; + g = (298 * y1 - 100 * u - 208 * v + 128) >> 8; + b = (298 * y1 + 516 * u + 128) >> 8; + + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(float(std::min(std::max(r, 0), 255)) / 255.f, + float(std::min(std::max(g, 0), 255)) / 255.f, + float(std::min(std::max(b, 0), 255)) / 255.f, + 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_Y210: + // Same as Y216 with least significant 6 bits set to zero + if (size >= sizeof(XMUSHORTN4)) + { + const XMUSHORTN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUSHORTN4) + 1); icount += sizeof(XMUSHORTN4)) + { + int64_t y0 = int64_t(sPtr->x >> 6) - 64; + int64_t u = int64_t(sPtr->y >> 6) - 512; + int64_t y1 = int64_t(sPtr->z >> 6) - 64; + int64_t v = int64_t(sPtr->w >> 6) - 512; + ++sPtr; + + // See Y410 + int r = static_cast((76533 * y0 + 104905 * v + 32768) >> 16); + int g = static_cast((76533 * y0 - 25747 * u - 53425 * v + 32768) >> 16); + int b = static_cast((76533 * y0 + 132590 * u + 32768) >> 16); + + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(float(std::min(std::max(r, 0), 1023)) / 1023.f, + float(std::min(std::max(g, 0), 1023)) / 1023.f, + float(std::min(std::max(b, 0), 1023)) / 1023.f, + 1.f); + + r = static_cast((76533 * y1 + 104905 * v + 32768) >> 16); + g = static_cast((76533 * y1 - 25747 * u - 53425 * v + 32768) >> 16); + b = static_cast((76533 * y1 + 132590 * u + 32768) >> 16); + + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(float(std::min(std::max(r, 0), 1023)) / 1023.f, + float(std::min(std::max(g, 0), 1023)) / 1023.f, + float(std::min(std::max(b, 0), 1023)) / 1023.f, + 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_Y216: + if (size >= sizeof(XMUSHORTN4)) + { + const XMUSHORTN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUSHORTN4) + 1); icount += sizeof(XMUSHORTN4)) + { + int64_t y0 = int64_t(sPtr->x) - 4096; + int64_t u = int64_t(sPtr->y) - 32768; + int64_t y1 = int64_t(sPtr->z) - 4096; + int64_t v = int64_t(sPtr->w) - 32768; + ++sPtr; + + // See Y416 + int r = static_cast((76607 * y0 + 105006 * v + 32768) >> 16); + int g = static_cast((76607 * y0 - 25772 * u - 53477 * v + 32768) >> 16); + int b = static_cast((76607 * y0 + 132718 * u + 32768) >> 16); + + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(float(std::min(std::max(r, 0), 65535)) / 65535.f, + float(std::min(std::max(g, 0), 65535)) / 65535.f, + float(std::min(std::max(b, 0), 65535)) / 65535.f, + 1.f); + + r = static_cast((76607 * y1 + 105006 * v + 32768) >> 16); + g = static_cast((76607 * y1 - 25772 * u - 53477 * v + 32768) >> 16); + b = static_cast((76607 * y1 + 132718 * u + 32768) >> 16); + + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSet(float(std::min(std::max(r, 0), 65535)) / 65535.f, + float(std::min(std::max(g, 0), 65535)) / 65535.f, + float(std::min(std::max(b, 0), 65535)) / 65535.f, + 1.f); + } + return true; + } + return false; + + case DXGI_FORMAT_B4G4R4A4_UNORM: + if (size >= sizeof(XMUNIBBLE4)) + { + static const XMVECTORF32 s_Scale = { { { 1.f / 15.f, 1.f / 15.f, 1.f / 15.f, 1.f / 15.f } } }; + const XMUNIBBLE4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUNIBBLE4) + 1); icount += sizeof(XMUNIBBLE4)) + { + XMVECTOR v = XMLoadUNibble4(sPtr++); + v = XMVectorMultiply(v, s_Scale); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSwizzle<2, 1, 0, 3>(v); + } + return true; + } + return false; + + case XBOX_DXGI_FORMAT_R10G10B10_7E3_A2_FLOAT: + // Xbox One specific 7e3 format + if (size >= sizeof(XMUDECN4)) + { + const XMUDECN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUDECN4) + 1); icount += sizeof(XMUDECN4)) + { + if (dPtr >= ePtr) break; + + XMVECTORF32 vResult = { { { + FloatFrom7e3(sPtr->x), + FloatFrom7e3(sPtr->y), + FloatFrom7e3(sPtr->z), + (float)(sPtr->v >> 30) / 3.0f + } } }; + + ++sPtr; + + *(dPtr++) = vResult.v; + } + return true; + } + return false; + + case XBOX_DXGI_FORMAT_R10G10B10_6E4_A2_FLOAT: + // Xbox One specific 6e4 format + if (size >= sizeof(XMUDECN4)) + { + const XMUDECN4 * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(XMUDECN4) + 1); icount += sizeof(XMUDECN4)) + { + if (dPtr >= ePtr) break; + + XMVECTORF32 vResult = { { { + FloatFrom6e4(sPtr->x), + FloatFrom6e4(sPtr->y), + FloatFrom6e4(sPtr->z), + (float)(sPtr->v >> 30) / 3.0f + } } }; + + ++sPtr; + + *(dPtr++) = vResult.v; + } + return true; + } + return false; + + case XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM: + // Xbox One specific format + LOAD_SCANLINE(XMXDECN4, XMLoadXDecN4); + + case XBOX_DXGI_FORMAT_R4G4_UNORM: + // Xbox One specific format + if (size >= sizeof(uint8_t)) + { + static const XMVECTORF32 s_Scale = { { { 1.f / 15.f, 1.f / 15.f, 0.f, 0.f } } }; + const uint8_t * __restrict sPtr = reinterpret_cast(pSource); + for (size_t icount = 0; icount < (size - sizeof(uint8_t) + 1); icount += sizeof(uint8_t)) + { + XMUNIBBLE4 nibble; + nibble.v = static_cast(*sPtr++); + XMVECTOR v = XMLoadUNibble4(&nibble); + v = XMVectorMultiply(v, s_Scale); + if (dPtr >= ePtr) break; + *(dPtr++) = XMVectorSelect(g_XMIdentityR3, v, g_XMSelect1100); + } + return true; + } + return false; + + // We don't support the planar or palettized formats + + default: + return false; + } +} + +#undef LOAD_SCANLINE +#undef LOAD_SCANLINE3 +#undef LOAD_SCANLINE2 + + +//------------------------------------------------------------------------------------- +// Stores an image row from standard RGBA XMVECTOR (aligned) array +//------------------------------------------------------------------------------------- +#define STORE_SCANLINE( type, func )\ + if ( size >= sizeof(type) )\ + {\ + type * __restrict dPtr = reinterpret_cast(pDestination);\ + for( size_t icount = 0; icount < ( size - sizeof(type) + 1 ); icount += sizeof(type) )\ + {\ + if ( sPtr >= ePtr ) break;\ + func( dPtr++, *sPtr++ );\ + }\ + return true; \ + }\ + return false; + +_Use_decl_annotations_ +bool DirectX::_StoreScanline( + void* pDestination, + size_t size, + DXGI_FORMAT format, + const XMVECTOR* pSource, + size_t count, + float threshold) +{ + assert(pDestination && size > 0); + assert(pSource && count > 0 && (((uintptr_t)pSource & 0xF) == 0)); + assert(IsValid(format) && !IsTypeless(format) && !IsCompressed(format) && !IsPlanar(format) && !IsPalettized(format)); + + const XMVECTOR* __restrict sPtr = pSource; + if (!sPtr) + return false; + + const XMVECTOR* ePtr = pSource + count; + + switch (static_cast(format)) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: + STORE_SCANLINE(XMFLOAT4, XMStoreFloat4) + + case DXGI_FORMAT_R32G32B32A32_UINT: + STORE_SCANLINE(XMUINT4, XMStoreUInt4) + + case DXGI_FORMAT_R32G32B32A32_SINT: + STORE_SCANLINE(XMINT4, XMStoreSInt4) + + case DXGI_FORMAT_R32G32B32_FLOAT: + STORE_SCANLINE(XMFLOAT3, XMStoreFloat3) + + case DXGI_FORMAT_R32G32B32_UINT: + STORE_SCANLINE(XMUINT3, XMStoreUInt3) + + case DXGI_FORMAT_R32G32B32_SINT: + STORE_SCANLINE(XMINT3, XMStoreSInt3) + + case DXGI_FORMAT_R16G16B16A16_FLOAT: + if (size >= sizeof(XMHALF4)) + { + XMHALF4* __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMHALF4) + 1); icount += sizeof(XMHALF4)) + { + if (sPtr >= ePtr) break; + XMVECTOR v = *sPtr++; + v = XMVectorClamp(v, g_HalfMin, g_HalfMax); + XMStoreHalf4(dPtr++, v); + } + return true; + } + return false; + + case DXGI_FORMAT_R16G16B16A16_UNORM: + STORE_SCANLINE(XMUSHORTN4, XMStoreUShortN4) + + case DXGI_FORMAT_R16G16B16A16_UINT: + STORE_SCANLINE(XMUSHORT4, XMStoreUShort4) + + case DXGI_FORMAT_R16G16B16A16_SNORM: + STORE_SCANLINE(XMSHORTN4, XMStoreShortN4) + + case DXGI_FORMAT_R16G16B16A16_SINT: + STORE_SCANLINE(XMSHORT4, XMStoreShort4) + + case DXGI_FORMAT_R32G32_FLOAT: + STORE_SCANLINE(XMFLOAT2, XMStoreFloat2) + + case DXGI_FORMAT_R32G32_UINT: + STORE_SCANLINE(XMUINT2, XMStoreUInt2) + + case DXGI_FORMAT_R32G32_SINT: + STORE_SCANLINE(XMINT2, XMStoreSInt2) + + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + { + const size_t psize = sizeof(float) + sizeof(uint32_t); + if (size >= psize) + { + float *dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - psize + 1); icount += psize) + { + if (sPtr >= ePtr) break; + XMFLOAT4 f; + XMStoreFloat4(&f, *sPtr++); + dPtr[0] = f.x; + uint8_t* ps8 = reinterpret_cast(&dPtr[1]); + ps8[0] = static_cast(std::min(255.f, std::max(0.f, f.y))); + ps8[1] = ps8[2] = ps8[3] = 0; + dPtr += 2; + } + return true; + } + } + return false; + + case DXGI_FORMAT_R10G10B10A2_UNORM: + STORE_SCANLINE(XMUDECN4, XMStoreUDecN4); + + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + STORE_SCANLINE(XMUDECN4, XMStoreUDecN4_XR); + + case DXGI_FORMAT_R10G10B10A2_UINT: + STORE_SCANLINE(XMUDEC4, XMStoreUDec4); + + case DXGI_FORMAT_R11G11B10_FLOAT: + STORE_SCANLINE(XMFLOAT3PK, XMStoreFloat3PK); + + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + if (size >= sizeof(XMUBYTEN4)) + { + XMUBYTEN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + if (sPtr >= ePtr) break; + XMVECTOR v = XMVectorAdd(*sPtr++, g_8BitBias); + XMStoreUByteN4(dPtr++, v); + } + return true; + } + return false; + + case DXGI_FORMAT_R8G8B8A8_UINT: + STORE_SCANLINE(XMUBYTE4, XMStoreUByte4) + + case DXGI_FORMAT_R8G8B8A8_SNORM: + STORE_SCANLINE(XMBYTEN4, XMStoreByteN4) + + case DXGI_FORMAT_R8G8B8A8_SINT: + STORE_SCANLINE(XMBYTE4, XMStoreByte4) + + case DXGI_FORMAT_R16G16_FLOAT: + if (size >= sizeof(XMHALF2)) + { + XMHALF2* __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMHALF2) + 1); icount += sizeof(XMHALF2)) + { + if (sPtr >= ePtr) break; + XMVECTOR v = *sPtr++; + v = XMVectorClamp(v, g_HalfMin, g_HalfMax); + XMStoreHalf2(dPtr++, v); + } + return true; + } + return false; + + case DXGI_FORMAT_R16G16_UNORM: + STORE_SCANLINE(XMUSHORTN2, XMStoreUShortN2) + + case DXGI_FORMAT_R16G16_UINT: + STORE_SCANLINE(XMUSHORT2, XMStoreUShort2) + + case DXGI_FORMAT_R16G16_SNORM: + STORE_SCANLINE(XMSHORTN2, XMStoreShortN2) + + case DXGI_FORMAT_R16G16_SINT: + STORE_SCANLINE(XMSHORT2, XMStoreShort2) + + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + if (size >= sizeof(float)) + { + float * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(float) + 1); icount += sizeof(float)) + { + if (sPtr >= ePtr) break; + XMStoreFloat(dPtr++, *(sPtr++)); + } + return true; + } + return false; + + case DXGI_FORMAT_R32_UINT: + if (size >= sizeof(uint32_t)) + { + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(uint32_t) + 1); icount += sizeof(uint32_t)) + { + if (sPtr >= ePtr) break; + XMVECTOR v = XMConvertVectorFloatToUInt(*(sPtr++), 0); + XMStoreInt(dPtr++, v); + } + return true; + } + return false; + + case DXGI_FORMAT_R32_SINT: + if (size >= sizeof(int32_t)) + { + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(int32_t) + 1); icount += sizeof(int32_t)) + { + if (sPtr >= ePtr) break; + XMVECTOR v = XMConvertVectorFloatToInt(*(sPtr++), 0); + XMStoreInt(dPtr++, v); + } + return true; + } + return false; + + case DXGI_FORMAT_D24_UNORM_S8_UINT: + if (size >= sizeof(uint32_t)) + { + static const XMVECTORF32 clamp = { { { 1.f, 255.f, 0.f, 0.f } } }; + XMVECTOR zero = XMVectorZero(); + uint32_t *dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(uint32_t) + 1); icount += sizeof(uint32_t)) + { + if (sPtr >= ePtr) break; + XMFLOAT4 f; + XMStoreFloat4(&f, XMVectorClamp(*sPtr++, zero, clamp)); + *dPtr++ = (static_cast(f.x * 16777215.f) & 0xFFFFFF) + | ((static_cast(f.y) & 0xFF) << 24); + } + return true; + } + return false; + + case DXGI_FORMAT_R8G8_UNORM: + STORE_SCANLINE(XMUBYTEN2, XMStoreUByteN2) + + case DXGI_FORMAT_R8G8_UINT: + STORE_SCANLINE(XMUBYTE2, XMStoreUByte2) + + case DXGI_FORMAT_R8G8_SNORM: + STORE_SCANLINE(XMBYTEN2, XMStoreByteN2) + + case DXGI_FORMAT_R8G8_SINT: + STORE_SCANLINE(XMBYTE2, XMStoreByte2) + + case DXGI_FORMAT_R16_FLOAT: + if (size >= sizeof(HALF)) + { + HALF * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(HALF) + 1); icount += sizeof(HALF)) + { + if (sPtr >= ePtr) break; + float v = XMVectorGetX(*sPtr++); + v = std::max(std::min(v, 65504.f), -65504.f); + *(dPtr++) = XMConvertFloatToHalf(v); + } + return true; + } + return false; + + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + if (size >= sizeof(uint16_t)) + { + uint16_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(uint16_t) + 1); icount += sizeof(uint16_t)) + { + if (sPtr >= ePtr) break; + float v = XMVectorGetX(*sPtr++); + v = std::max(std::min(v, 1.f), 0.f); + *(dPtr++) = static_cast(v*65535.f + 0.5f); + } + return true; + } + return false; + + case DXGI_FORMAT_R16_UINT: + if (size >= sizeof(uint16_t)) + { + uint16_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(uint16_t) + 1); icount += sizeof(uint16_t)) + { + if (sPtr >= ePtr) break; + float v = XMVectorGetX(*sPtr++); + v = std::max(std::min(v, 65535.f), 0.f); + *(dPtr++) = static_cast(v); + } + return true; + } + return false; + + case DXGI_FORMAT_R16_SNORM: + if (size >= sizeof(int16_t)) + { + int16_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(int16_t) + 1); icount += sizeof(int16_t)) + { + if (sPtr >= ePtr) break; + float v = XMVectorGetX(*sPtr++); + v = std::max(std::min(v, 1.f), -1.f); + *(dPtr++) = static_cast(v * 32767.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R16_SINT: + if (size >= sizeof(int16_t)) + { + int16_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(int16_t) + 1); icount += sizeof(int16_t)) + { + if (sPtr >= ePtr) break; + float v = XMVectorGetX(*sPtr++); + v = std::max(std::min(v, 32767.f), -32767.f); + *(dPtr++) = static_cast(v); + } + return true; + } + return false; + + case DXGI_FORMAT_R8_UNORM: + if (size >= sizeof(uint8_t)) + { + uint8_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < size; icount += sizeof(uint8_t)) + { + if (sPtr >= ePtr) break; + float v = XMVectorGetX(*sPtr++); + v = std::max(std::min(v, 1.f), 0.f); + *(dPtr++) = static_cast(v * 255.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R8_UINT: + if (size >= sizeof(uint8_t)) + { + uint8_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < size; icount += sizeof(uint8_t)) + { + if (sPtr >= ePtr) break; + float v = XMVectorGetX(*sPtr++); + v = std::max(std::min(v, 255.f), 0.f); + *(dPtr++) = static_cast(v); + } + return true; + } + return false; + + case DXGI_FORMAT_R8_SNORM: + if (size >= sizeof(int8_t)) + { + int8_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < size; icount += sizeof(int8_t)) + { + if (sPtr >= ePtr) break; + float v = XMVectorGetX(*sPtr++); + v = std::max(std::min(v, 1.f), -1.f); + *(dPtr++) = static_cast(v * 127.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R8_SINT: + if (size >= sizeof(int8_t)) + { + int8_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < size; icount += sizeof(int8_t)) + { + if (sPtr >= ePtr) break; + float v = XMVectorGetX(*sPtr++); + v = std::max(std::min(v, 127.f), -127.f); + *(dPtr++) = static_cast(v); + } + return true; + } + return false; + + case DXGI_FORMAT_A8_UNORM: + if (size >= sizeof(uint8_t)) + { + uint8_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < size; icount += sizeof(uint8_t)) + { + if (sPtr >= ePtr) break; + float v = XMVectorGetW(*sPtr++); + v = std::max(std::min(v, 1.f), 0.f); + *(dPtr++) = static_cast(v * 255.f); + } + return true; + } + return false; + + case DXGI_FORMAT_R1_UNORM: + if (size >= sizeof(uint8_t)) + { + uint8_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < size; icount += sizeof(uint8_t)) + { + uint8_t pixels = 0; + for (size_t bcount = 8; bcount > 0; --bcount) + { + if (sPtr >= ePtr) break; + float v = XMVectorGetX(*sPtr++); + + // Absolute thresholding generally doesn't give good results for all images + // Picking the 'right' threshold automatically requires whole-image analysis + + if (v > 0.25f) + pixels |= 1 << (bcount - 1); + } + *(dPtr++) = pixels; + } + return true; + } + return false; + + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + STORE_SCANLINE(XMFLOAT3SE, StoreFloat3SE) + + case DXGI_FORMAT_R8G8_B8G8_UNORM: + if (size >= sizeof(XMUBYTEN4)) + { + XMUBYTEN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + if (sPtr >= ePtr) break; + XMVECTOR v0 = *sPtr++; + XMVECTOR v1 = (sPtr < ePtr) ? XMVectorSplatY(*sPtr++) : XMVectorZero(); + XMVECTOR v = XMVectorSelect(v1, v0, g_XMSelect1110); + v = XMVectorAdd(v, g_8BitBias); + XMStoreUByteN4(dPtr++, v); + } + return true; + } + return false; + + case DXGI_FORMAT_G8R8_G8B8_UNORM: + if (size >= sizeof(XMUBYTEN4)) + { + static XMVECTORU32 select1101 = { { { XM_SELECT_1, XM_SELECT_1, XM_SELECT_0, XM_SELECT_1 } } }; + + XMUBYTEN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + if (sPtr >= ePtr) break; + XMVECTOR v0 = XMVectorSwizzle<1, 0, 3, 2>(*sPtr++); + XMVECTOR v1 = (sPtr < ePtr) ? XMVectorSplatY(*sPtr++) : XMVectorZero(); + XMVECTOR v = XMVectorSelect(v1, v0, select1101); + v = XMVectorAdd(v, g_8BitBias); + XMStoreUByteN4(dPtr++, v); + } + return true; + } + return false; + + case DXGI_FORMAT_B5G6R5_UNORM: + if (size >= sizeof(XMU565)) + { + static const XMVECTORF32 s_Scale = { { { 31.f, 63.f, 31.f, 1.f } } }; + XMU565 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMU565) + 1); icount += sizeof(XMU565)) + { + if (sPtr >= ePtr) break; + XMVECTOR v = XMVectorSwizzle<2, 1, 0, 3>(*sPtr++); + v = XMVectorMultiply(v, s_Scale); + XMStoreU565(dPtr++, v); + } + return true; + } + return false; + + case DXGI_FORMAT_B5G5R5A1_UNORM: + if (size >= sizeof(XMU555)) + { + static const XMVECTORF32 s_Scale = { { { 31.f, 31.f, 31.f, 1.f } } }; + XMU555 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMU555) + 1); icount += sizeof(XMU555)) + { + if (sPtr >= ePtr) break; + XMVECTOR v = XMVectorSwizzle<2, 1, 0, 3>(*sPtr++); + v = XMVectorMultiply(v, s_Scale); + XMStoreU555(dPtr, v); + dPtr->w = (XMVectorGetW(v) > threshold) ? 1 : 0; + ++dPtr; + } + return true; + } + return false; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + if (size >= sizeof(XMUBYTEN4)) + { + XMUBYTEN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + if (sPtr >= ePtr) break; + XMVECTOR v = XMVectorSwizzle<2, 1, 0, 3>(*sPtr++); + v = XMVectorAdd(v, g_8BitBias); + XMStoreUByteN4(dPtr++, v); + } + return true; + } + return false; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + if (size >= sizeof(XMUBYTEN4)) + { + XMUBYTEN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + if (sPtr >= ePtr) break; + XMVECTOR v = XMVectorPermute<2, 1, 0, 7>(*sPtr++, g_XMIdentityR3); + v = XMVectorAdd(v, g_8BitBias); + XMStoreUByteN4(dPtr++, v); + } + return true; + } + return false; + + case DXGI_FORMAT_AYUV: + if (size >= sizeof(XMUBYTEN4)) + { + XMUBYTEN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + if (sPtr >= ePtr) break; + + XMUBYTEN4 rgba; + XMStoreUByteN4(&rgba, *sPtr++); + + // http://msdn.microsoft.com/en-us/library/windows/desktop/dd206750.aspx + + // Y = 0.2568R + 0.5041G + 0.1001B + 16 + // Cb = -0.1482R - 0.2910G + 0.4392B + 128 + // Cr = 0.4392R - 0.3678G - 0.0714B + 128 + + int y = ((66 * rgba.x + 129 * rgba.y + 25 * rgba.z + 128) >> 8) + 16; + int u = ((-38 * rgba.x - 74 * rgba.y + 112 * rgba.z + 128) >> 8) + 128; + int v = ((112 * rgba.x - 94 * rgba.y - 18 * rgba.z + 128) >> 8) + 128; + + dPtr->x = static_cast(std::min(std::max(v, 0), 255)); + dPtr->y = static_cast(std::min(std::max(u, 0), 255)); + dPtr->z = static_cast(std::min(std::max(y, 0), 255)); + dPtr->w = rgba.w; + ++dPtr; + } + return true; + } + return false; + + case DXGI_FORMAT_Y410: + if (size >= sizeof(XMUDECN4)) + { + XMUDECN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUDECN4) + 1); icount += sizeof(XMUDECN4)) + { + if (sPtr >= ePtr) break; + + XMUDECN4 rgba; + XMStoreUDecN4(&rgba, *sPtr++); + + // http://msdn.microsoft.com/en-us/library/windows/desktop/bb970578.aspx + + // Y = 0.2560R + 0.5027G + 0.0998B + 64 + // Cb = -0.1478R - 0.2902G + 0.4379B + 512 + // Cr = 0.4379R - 0.3667G - 0.0712B + 512 + + int64_t r = rgba.x; + int64_t g = rgba.y; + int64_t b = rgba.z; + + int y = static_cast((16780 * r + 32942 * g + 6544 * b + 32768) >> 16) + 64; + int u = static_cast((-9683 * r - 19017 * g + 28700 * b + 32768) >> 16) + 512; + int v = static_cast((28700 * r - 24033 * g - 4667 * b + 32768) >> 16) + 512; + + dPtr->x = static_cast(std::min(std::max(u, 0), 1023)); + dPtr->y = static_cast(std::min(std::max(y, 0), 1023)); + dPtr->z = static_cast(std::min(std::max(v, 0), 1023)); + dPtr->w = rgba.w; + ++dPtr; + } + return true; + } + return false; + + case DXGI_FORMAT_Y416: + if (size >= sizeof(XMUSHORTN4)) + { + XMUSHORTN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUSHORTN4) + 1); icount += sizeof(XMUSHORTN4)) + { + if (sPtr >= ePtr) break; + + XMUSHORTN4 rgba; + XMStoreUShortN4(&rgba, *sPtr++); + + // http://msdn.microsoft.com/en-us/library/windows/desktop/bb970578.aspx + + // Y = 0.2558R + 0.5022G + 0.0998B + 4096 + // Cb = -0.1476R - 0.2899G + 0.4375B + 32768 + // Cr = 0.4375R - 0.3664G - 0.0711B + 32768 + + int64_t r = int64_t(rgba.x); + int64_t g = int64_t(rgba.y); + int64_t b = int64_t(rgba.z); + + int y = static_cast((16763 * r + 32910 * g + 6537 * b + 32768) >> 16) + 4096; + int u = static_cast((-9674 * r - 18998 * g + 28672 * b + 32768) >> 16) + 32768; + int v = static_cast((28672 * r - 24010 * g - 4662 * b + 32768) >> 16) + 32768; + + dPtr->x = static_cast(std::min(std::max(u, 0), 65535)); + dPtr->y = static_cast(std::min(std::max(y, 0), 65535)); + dPtr->z = static_cast(std::min(std::max(v, 0), 65535)); + dPtr->w = rgba.w; + ++dPtr; + } + return true; + } + return false; + + case DXGI_FORMAT_YUY2: + if (size >= sizeof(XMUBYTEN4)) + { + XMUBYTEN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUBYTEN4) + 1); icount += sizeof(XMUBYTEN4)) + { + if (sPtr >= ePtr) break; + + XMUBYTEN4 rgb1; + XMStoreUByteN4(&rgb1, *sPtr++); + + // See AYUV + int y0 = ((66 * rgb1.x + 129 * rgb1.y + 25 * rgb1.z + 128) >> 8) + 16; + int u0 = ((-38 * rgb1.x - 74 * rgb1.y + 112 * rgb1.z + 128) >> 8) + 128; + int v0 = ((112 * rgb1.x - 94 * rgb1.y - 18 * rgb1.z + 128) >> 8) + 128; + + XMUBYTEN4 rgb2; + if (sPtr < ePtr) + { + XMStoreUByteN4(&rgb2, *sPtr++); + } + else + { + rgb2.x = rgb2.y = rgb2.z = rgb2.w = 0; + } + + int y1 = ((66 * rgb2.x + 129 * rgb2.y + 25 * rgb2.z + 128) >> 8) + 16; + int u1 = ((-38 * rgb2.x - 74 * rgb2.y + 112 * rgb2.z + 128) >> 8) + 128; + int v1 = ((112 * rgb2.x - 94 * rgb2.y - 18 * rgb2.z + 128) >> 8) + 128; + + dPtr->x = static_cast(std::min(std::max(y0, 0), 255)); + dPtr->y = static_cast(std::min(std::max((u0 + u1) >> 1, 0), 255)); + dPtr->z = static_cast(std::min(std::max(y1, 0), 255)); + dPtr->w = static_cast(std::min(std::max((v0 + v1) >> 1, 0), 255)); + ++dPtr; + } + return true; + } + return false; + + case DXGI_FORMAT_Y210: + // Same as Y216 with least significant 6 bits set to zero + if (size >= sizeof(XMUSHORTN4)) + { + XMUSHORTN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUSHORTN4) + 1); icount += sizeof(XMUSHORTN4)) + { + if (sPtr >= ePtr) break; + + XMUDECN4 rgb1; + XMStoreUDecN4(&rgb1, *sPtr++); + + // See Y410 + int64_t r = rgb1.x; + int64_t g = rgb1.y; + int64_t b = rgb1.z; + + int y0 = static_cast((16780 * r + 32942 * g + 6544 * b + 32768) >> 16) + 64; + int u0 = static_cast((-9683 * r - 19017 * g + 28700 * b + 32768) >> 16) + 512; + int v0 = static_cast((28700 * r - 24033 * g - 4667 * b + 32768) >> 16) + 512; + + XMUDECN4 rgb2; + if (sPtr < ePtr) + { + XMStoreUDecN4(&rgb2, *sPtr++); + } + else + { + rgb2.x = rgb2.y = rgb2.z = rgb2.w = 0; + } + + r = rgb2.x; + g = rgb2.y; + b = rgb2.z; + + int y1 = static_cast((16780 * r + 32942 * g + 6544 * b + 32768) >> 16) + 64; + int u1 = static_cast((-9683 * r - 19017 * g + 28700 * b + 32768) >> 16) + 512; + int v1 = static_cast((28700 * r - 24033 * g - 4667 * b + 32768) >> 16) + 512; + + dPtr->x = static_cast(std::min(std::max(y0, 0), 1023) << 6); + dPtr->y = static_cast(std::min(std::max((u0 + u1) >> 1, 0), 1023) << 6); + dPtr->z = static_cast(std::min(std::max(y1, 0), 1023) << 6); + dPtr->w = static_cast(std::min(std::max((v0 + v1) >> 1, 0), 1023) << 6); + ++dPtr; + } + return true; + } + return false; + + case DXGI_FORMAT_Y216: + if (size >= sizeof(XMUSHORTN4)) + { + XMUSHORTN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUSHORTN4) + 1); icount += sizeof(XMUSHORTN4)) + { + if (sPtr >= ePtr) break; + + XMUSHORTN4 rgb1; + XMStoreUShortN4(&rgb1, *sPtr++); + + // See Y416 + int64_t r = int64_t(rgb1.x); + int64_t g = int64_t(rgb1.y); + int64_t b = int64_t(rgb1.z); + + int y0 = static_cast((16763 * r + 32910 * g + 6537 * b + 32768) >> 16) + 4096; + int u0 = static_cast((-9674 * r - 18998 * g + 28672 * b + 32768) >> 16) + 32768; + int v0 = static_cast((28672 * r - 24010 * g - 4662 * b + 32768) >> 16) + 32768; + + XMUSHORTN4 rgb2; + if (sPtr < ePtr) + { + XMStoreUShortN4(&rgb2, *sPtr++); + } + else + { + rgb2.x = rgb2.y = rgb2.z = rgb2.w = 0; + } + + r = int64_t(rgb2.x); + g = int64_t(rgb2.y); + b = int64_t(rgb2.z); + + int y1 = static_cast((16763 * r + 32910 * g + 6537 * b + 32768) >> 16) + 4096; + int u1 = static_cast((-9674 * r - 18998 * g + 28672 * b + 32768) >> 16) + 32768; + int v1 = static_cast((28672 * r - 24010 * g - 4662 * b + 32768) >> 16) + 32768; + + dPtr->x = static_cast(std::min(std::max(y0, 0), 65535)); + dPtr->y = static_cast(std::min(std::max((u0 + u1) >> 1, 0), 65535)); + dPtr->z = static_cast(std::min(std::max(y1, 0), 65535)); + dPtr->w = static_cast(std::min(std::max((v0 + v1) >> 1, 0), 65535)); + ++dPtr; + } + return true; + } + return false; + + case DXGI_FORMAT_B4G4R4A4_UNORM: + if (size >= sizeof(XMUNIBBLE4)) + { + static const XMVECTORF32 s_Scale = { { { 15.f, 15.f, 15.f, 15.f } } }; + XMUNIBBLE4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUNIBBLE4) + 1); icount += sizeof(XMUNIBBLE4)) + { + if (sPtr >= ePtr) break; + XMVECTOR v = XMVectorSwizzle<2, 1, 0, 3>(*sPtr++); + v = XMVectorMultiply(v, s_Scale); + XMStoreUNibble4(dPtr++, v); + } + return true; + } + return false; + + case XBOX_DXGI_FORMAT_R10G10B10_7E3_A2_FLOAT: + // Xbox One specific 7e3 format with alpha + if (size >= sizeof(XMUDECN4)) + { + static const XMVECTORF32 Scale = { { { 1.0f, 1.0f, 1.0f, 3.0f } } }; + static const XMVECTORF32 C = { { { 31.875f, 31.875f, 31.875f, 3.f } } }; + + XMUDECN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUDECN4) + 1); icount += sizeof(XMUDECN4)) + { + if (sPtr >= ePtr) break; + + XMVECTOR V = XMVectorMultiply(*sPtr++, Scale); + V = XMVectorClamp(V, g_XMZero, C); + + XMFLOAT4A tmp; + XMStoreFloat4A(&tmp, V); + + dPtr->x = FloatTo7e3(tmp.x); + dPtr->y = FloatTo7e3(tmp.y); + dPtr->z = FloatTo7e3(tmp.z); + dPtr->w = (uint32_t)tmp.w; + ++dPtr; + } + return true; + } + return false; + + case XBOX_DXGI_FORMAT_R10G10B10_6E4_A2_FLOAT: + // Xbox One specific 6e4 format with alpha + if (size >= sizeof(XMUDECN4)) + { + static const XMVECTORF32 Scale = { { { 1.0f, 1.0f, 1.0f, 3.0f } } }; + static const XMVECTORF32 C = { { { 508.f, 508.f, 508.f, 3.f } } }; + + XMUDECN4 * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(XMUDECN4) + 1); icount += sizeof(XMUDECN4)) + { + if (sPtr >= ePtr) break; + + XMVECTOR V = XMVectorMultiply(*sPtr++, Scale); + V = XMVectorClamp(V, g_XMZero, C); + + XMFLOAT4A tmp; + XMStoreFloat4A(&tmp, V); + + dPtr->x = FloatTo6e4(tmp.x); + dPtr->y = FloatTo6e4(tmp.y); + dPtr->z = FloatTo6e4(tmp.z); + dPtr->w = (uint32_t)tmp.w; + ++dPtr; + } + return true; + } + return false; + + case XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM: + // Xbox One specific format + STORE_SCANLINE(XMXDECN4, XMStoreXDecN4); + + case XBOX_DXGI_FORMAT_R4G4_UNORM: + // Xbox One specific format + if (size >= sizeof(uint8_t)) + { + static const XMVECTORF32 s_Scale = { { { 15.f, 15.f, 0.f, 0.f } } }; + uint8_t * __restrict dPtr = reinterpret_cast(pDestination); + for (size_t icount = 0; icount < (size - sizeof(uint8_t) + 1); icount += sizeof(uint8_t)) + { + if (sPtr >= ePtr) break; + XMVECTOR v = XMVectorMultiply(*sPtr++, s_Scale); + + XMUNIBBLE4 nibble; + XMStoreUNibble4(&nibble, v); + *dPtr = static_cast(nibble.v); + ++dPtr; + } + return true; + } + return false; + + // We don't support the planar or palettized formats + + default: + return false; + } +} + +#undef STORE_SCANLINE + + +//------------------------------------------------------------------------------------- +// Convert DXGI image to/from GUID_WICPixelFormat128bppRGBAFloat (no range conversions) +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::_ConvertToR32G32B32A32(const Image& srcImage, ScratchImage& image) +{ + if (!srcImage.pixels) + return E_POINTER; + + HRESULT hr = image.Initialize2D(DXGI_FORMAT_R32G32B32A32_FLOAT, srcImage.width, srcImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *img = image.GetImage(0, 0, 0); + if (!img) + { + image.Release(); + return E_POINTER; + } + + uint8_t* pDest = img->pixels; + if (!pDest) + { + image.Release(); + return E_POINTER; + } + + const uint8_t *pSrc = srcImage.pixels; + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_LoadScanline(reinterpret_cast(pDest), srcImage.width, pSrc, srcImage.rowPitch, srcImage.format)) + { + image.Release(); + return E_FAIL; + } + + pSrc += srcImage.rowPitch; + pDest += img->rowPitch; + } + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT DirectX::_ConvertFromR32G32B32A32(const Image& srcImage, const Image& destImage) +{ + assert(srcImage.format == DXGI_FORMAT_R32G32B32A32_FLOAT); + + if (!srcImage.pixels || !destImage.pixels) + return E_POINTER; + + if (srcImage.width != destImage.width || srcImage.height != destImage.height) + return E_FAIL; + + const uint8_t *pSrc = srcImage.pixels; + uint8_t* pDest = destImage.pixels; + + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_StoreScanline(pDest, destImage.rowPitch, destImage.format, reinterpret_cast(pSrc), srcImage.width)) + return E_FAIL; + + pSrc += srcImage.rowPitch; + pDest += destImage.rowPitch; + } + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT DirectX::_ConvertFromR32G32B32A32(const Image& srcImage, DXGI_FORMAT format, ScratchImage& image) +{ + if (!srcImage.pixels) + return E_POINTER; + + HRESULT hr = image.Initialize2D(format, srcImage.width, srcImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *img = image.GetImage(0, 0, 0); + if (!img) + { + image.Release(); + return E_POINTER; + } + + hr = _ConvertFromR32G32B32A32(srcImage, *img); + if (FAILED(hr)) + { + image.Release(); + return hr; + } + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT DirectX::_ConvertFromR32G32B32A32( + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + DXGI_FORMAT format, + ScratchImage& result) +{ + if (!srcImages) + return E_POINTER; + + result.Release(); + + assert(metadata.format == DXGI_FORMAT_R32G32B32A32_FLOAT); + + TexMetadata mdata2 = metadata; + mdata2.format = format; + HRESULT hr = result.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + if (nimages != result.GetImageCount()) + { + result.Release(); + return E_FAIL; + } + + const Image* dest = result.GetImages(); + if (!dest) + { + result.Release(); + return E_POINTER; + } + + for (size_t index = 0; index < nimages; ++index) + { + const Image& src = srcImages[index]; + const Image& dst = dest[index]; + + assert(src.format == DXGI_FORMAT_R32G32B32A32_FLOAT); + assert(dst.format == format); + + if (src.width != dst.width || src.height != dst.height) + { + result.Release(); + return E_FAIL; + } + + const uint8_t* pSrc = src.pixels; + uint8_t* pDest = dst.pixels; + if (!pSrc || !pDest) + { + result.Release(); + return E_POINTER; + } + + for (size_t h = 0; h < src.height; ++h) + { + if (!_StoreScanline(pDest, dst.rowPitch, format, reinterpret_cast(pSrc), src.width)) + { + result.Release(); + return E_FAIL; + } + + pSrc += src.rowPitch; + pDest += dst.rowPitch; + } + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Convert from Linear RGB to sRGB +// +// if C_linear <= 0.0031308 -> C_srgb = 12.92 * C_linear +// if C_linear > 0.0031308 -> C_srgb = ( 1 + a ) * pow( C_Linear, 1 / 2.4 ) - a +// where a = 0.055 +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::_StoreScanlineLinear( + void* pDestination, + size_t size, + DXGI_FORMAT format, + XMVECTOR* pSource, + size_t count, + DWORD flags, + float threshold) +{ + assert(pDestination && size > 0); + assert(pSource && count > 0 && (((uintptr_t)pSource & 0xF) == 0)); + assert(IsValid(format) && !IsTypeless(format) && !IsCompressed(format) && !IsPlanar(format) && !IsPalettized(format)); + + switch (format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + flags |= TEX_FILTER_SRGB; + break; + + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R11G11B10_FLOAT: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B4G4R4A4_UNORM: + break; + + default: + // can't treat A8, XR, Depth, SNORM, UINT, or SINT as sRGB + flags &= ~TEX_FILTER_SRGB; + break; + } + + // sRGB output processing (Linear RGB -> sRGB) + if (flags & TEX_FILTER_SRGB_OUT) + { + // To avoid the need for another temporary scanline buffer, we allow this function to overwrite the source buffer in-place + // Given the intended usage in the filtering routines, this is not a problem. + XMVECTOR* ptr = pSource; + for (size_t i = 0; i < count; ++i, ++ptr) + { + *ptr = XMColorRGBToSRGB(*ptr); + } + } + + return _StoreScanline(pDestination, size, format, pSource, count, threshold); +} + + +//------------------------------------------------------------------------------------- +// Convert from sRGB to Linear RGB +// +// if C_srgb <= 0.04045 -> C_linear = C_srgb / 12.92 +// if C_srgb > 0.04045 -> C_linear = pow( ( C_srgb + a ) / ( 1 + a ), 2.4 ) +// where a = 0.055 +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::_LoadScanlineLinear( + XMVECTOR* pDestination, + size_t count, + const void* pSource, + size_t size, + DXGI_FORMAT format, + DWORD flags) +{ + assert(pDestination && count > 0 && (((uintptr_t)pDestination & 0xF) == 0)); + assert(pSource && size > 0); + assert(IsValid(format) && !IsTypeless(format, false) && !IsCompressed(format) && !IsPlanar(format) && !IsPalettized(format)); + + switch (format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + flags |= TEX_FILTER_SRGB; + break; + + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R11G11B10_FLOAT: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B4G4R4A4_UNORM: + break; + + default: + // can't treat A8, XR, Depth, SNORM, UINT, or SINT as sRGB + flags &= ~TEX_FILTER_SRGB; + break; + } + + if (_LoadScanline(pDestination, count, pSource, size, format)) + { + // sRGB input processing (sRGB -> Linear RGB) + if (flags & TEX_FILTER_SRGB_IN) + { + XMVECTOR* ptr = pDestination; + for (size_t i = 0; i < count; ++i, ++ptr) + { + *ptr = XMColorSRGBToRGB(*ptr); + } + } + + return true; + } + + return false; +} + + +//------------------------------------------------------------------------------------- +// Convert scanline based on source/target formats +//------------------------------------------------------------------------------------- +namespace +{ + struct ConvertData + { + DXGI_FORMAT format; + size_t datasize; + DWORD flags; + }; + + const ConvertData g_ConvertTable[] = + { + { DXGI_FORMAT_R32G32B32A32_FLOAT, 32, CONVF_FLOAT | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R32G32B32A32_UINT, 32, CONVF_UINT | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R32G32B32A32_SINT, 32, CONVF_SINT | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R32G32B32_FLOAT, 32, CONVF_FLOAT | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_R32G32B32_UINT, 32, CONVF_UINT | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_R32G32B32_SINT, 32, CONVF_SINT | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_R16G16B16A16_FLOAT, 16, CONVF_FLOAT | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R16G16B16A16_UNORM, 16, CONVF_UNORM | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R16G16B16A16_UINT, 16, CONVF_UINT | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R16G16B16A16_SNORM, 16, CONVF_SNORM | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R16G16B16A16_SINT, 16, CONVF_SINT | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R32G32_FLOAT, 32, CONVF_FLOAT | CONVF_R | CONVF_G }, + { DXGI_FORMAT_R32G32_UINT, 32, CONVF_UINT | CONVF_R | CONVF_G }, + { DXGI_FORMAT_R32G32_SINT, 32, CONVF_SINT | CONVF_R | CONVF_G }, + { DXGI_FORMAT_D32_FLOAT_S8X24_UINT, 32, CONVF_FLOAT | CONVF_DEPTH | CONVF_STENCIL }, + { DXGI_FORMAT_R10G10B10A2_UNORM, 10, CONVF_UNORM | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R10G10B10A2_UINT, 10, CONVF_UINT | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R11G11B10_FLOAT, 10, CONVF_FLOAT | CONVF_POS_ONLY | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_R8G8B8A8_UNORM, 8, CONVF_UNORM | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, 8, CONVF_UNORM | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R8G8B8A8_UINT, 8, CONVF_UINT | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R8G8B8A8_SNORM, 8, CONVF_SNORM | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R8G8B8A8_SINT, 8, CONVF_SINT | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_R16G16_FLOAT, 16, CONVF_FLOAT | CONVF_R | CONVF_G }, + { DXGI_FORMAT_R16G16_UNORM, 16, CONVF_UNORM | CONVF_R | CONVF_G }, + { DXGI_FORMAT_R16G16_UINT, 16, CONVF_UINT | CONVF_R | CONVF_G }, + { DXGI_FORMAT_R16G16_SNORM, 16, CONVF_SNORM | CONVF_R | CONVF_G }, + { DXGI_FORMAT_R16G16_SINT, 16, CONVF_SINT | CONVF_R | CONVF_G }, + { DXGI_FORMAT_D32_FLOAT, 32, CONVF_FLOAT | CONVF_DEPTH }, + { DXGI_FORMAT_R32_FLOAT, 32, CONVF_FLOAT | CONVF_R }, + { DXGI_FORMAT_R32_UINT, 32, CONVF_UINT | CONVF_R }, + { DXGI_FORMAT_R32_SINT, 32, CONVF_SINT | CONVF_R }, + { DXGI_FORMAT_D24_UNORM_S8_UINT, 32, CONVF_UNORM | CONVF_DEPTH | CONVF_STENCIL }, + { DXGI_FORMAT_R8G8_UNORM, 8, CONVF_UNORM | CONVF_R | CONVF_G }, + { DXGI_FORMAT_R8G8_UINT, 8, CONVF_UINT | CONVF_R | CONVF_G }, + { DXGI_FORMAT_R8G8_SNORM, 8, CONVF_SNORM | CONVF_R | CONVF_G }, + { DXGI_FORMAT_R8G8_SINT, 8, CONVF_SINT | CONVF_R | CONVF_G }, + { DXGI_FORMAT_R16_FLOAT, 16, CONVF_FLOAT | CONVF_R }, + { DXGI_FORMAT_D16_UNORM, 16, CONVF_UNORM | CONVF_DEPTH }, + { DXGI_FORMAT_R16_UNORM, 16, CONVF_UNORM | CONVF_R }, + { DXGI_FORMAT_R16_UINT, 16, CONVF_UINT | CONVF_R }, + { DXGI_FORMAT_R16_SNORM, 16, CONVF_SNORM | CONVF_R }, + { DXGI_FORMAT_R16_SINT, 16, CONVF_SINT | CONVF_R }, + { DXGI_FORMAT_R8_UNORM, 8, CONVF_UNORM | CONVF_R }, + { DXGI_FORMAT_R8_UINT, 8, CONVF_UINT | CONVF_R }, + { DXGI_FORMAT_R8_SNORM, 8, CONVF_SNORM | CONVF_R }, + { DXGI_FORMAT_R8_SINT, 8, CONVF_SINT | CONVF_R }, + { DXGI_FORMAT_A8_UNORM, 8, CONVF_UNORM | CONVF_A }, + { DXGI_FORMAT_R1_UNORM, 1, CONVF_UNORM | CONVF_R }, + { DXGI_FORMAT_R9G9B9E5_SHAREDEXP, 9, CONVF_FLOAT | CONVF_SHAREDEXP | CONVF_POS_ONLY | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_R8G8_B8G8_UNORM, 8, CONVF_UNORM | CONVF_PACKED | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_G8R8_G8B8_UNORM, 8, CONVF_UNORM | CONVF_PACKED | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_BC1_UNORM, 8, CONVF_UNORM | CONVF_BC | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_BC1_UNORM_SRGB, 8, CONVF_UNORM | CONVF_BC | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_BC2_UNORM, 8, CONVF_UNORM | CONVF_BC | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_BC2_UNORM_SRGB, 8, CONVF_UNORM | CONVF_BC | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_BC3_UNORM, 8, CONVF_UNORM | CONVF_BC | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_BC3_UNORM_SRGB, 8, CONVF_UNORM | CONVF_BC | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_BC4_UNORM, 8, CONVF_UNORM | CONVF_BC | CONVF_R }, + { DXGI_FORMAT_BC4_SNORM, 8, CONVF_SNORM | CONVF_BC | CONVF_R }, + { DXGI_FORMAT_BC5_UNORM, 8, CONVF_UNORM | CONVF_BC | CONVF_R | CONVF_G }, + { DXGI_FORMAT_BC5_SNORM, 8, CONVF_SNORM | CONVF_BC | CONVF_R | CONVF_G }, + { DXGI_FORMAT_B5G6R5_UNORM, 5, CONVF_UNORM | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_B5G5R5A1_UNORM, 5, CONVF_UNORM | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_B8G8R8A8_UNORM, 8, CONVF_UNORM | CONVF_BGR | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_B8G8R8X8_UNORM, 8, CONVF_UNORM | CONVF_BGR | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM, 10, CONVF_UNORM | CONVF_XR | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_B8G8R8A8_UNORM_SRGB, 8, CONVF_UNORM | CONVF_BGR | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_B8G8R8X8_UNORM_SRGB, 8, CONVF_UNORM | CONVF_BGR | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_BC6H_UF16, 16, CONVF_FLOAT | CONVF_BC | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_BC6H_SF16, 16, CONVF_FLOAT | CONVF_BC | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_BC7_UNORM, 8, CONVF_UNORM | CONVF_BC | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_BC7_UNORM_SRGB, 8, CONVF_UNORM | CONVF_BC | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_AYUV, 8, CONVF_UNORM | CONVF_YUV | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_Y410, 10, CONVF_UNORM | CONVF_YUV | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_Y416, 16, CONVF_UNORM | CONVF_YUV | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { DXGI_FORMAT_YUY2, 8, CONVF_UNORM | CONVF_YUV | CONVF_PACKED | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_Y210, 10, CONVF_UNORM | CONVF_YUV | CONVF_PACKED | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_Y216, 16, CONVF_UNORM | CONVF_YUV | CONVF_PACKED | CONVF_R | CONVF_G | CONVF_B }, + { DXGI_FORMAT_B4G4R4A4_UNORM, 4, CONVF_UNORM | CONVF_BGR | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { XBOX_DXGI_FORMAT_R10G10B10_7E3_A2_FLOAT, 10, CONVF_FLOAT | CONVF_POS_ONLY | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { XBOX_DXGI_FORMAT_R10G10B10_6E4_A2_FLOAT, 10, CONVF_FLOAT | CONVF_POS_ONLY | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM,10, CONVF_SNORM | CONVF_R | CONVF_G | CONVF_B | CONVF_A }, + { XBOX_DXGI_FORMAT_R4G4_UNORM, 4, CONVF_UNORM | CONVF_R | CONVF_G }, + }; + +#pragma prefast( suppress : 25004, "Signature must match bsearch_s" ); + int __cdecl _ConvertCompare(void *context, const void* ptr1, const void *ptr2) + { + UNREFERENCED_PARAMETER(context); + const ConvertData *p1 = reinterpret_cast(ptr1); + const ConvertData *p2 = reinterpret_cast(ptr2); + if (p1->format == p2->format) return 0; + else return (p1->format < p2->format) ? -1 : 1; + } +} + +_Use_decl_annotations_ +DWORD DirectX::_GetConvertFlags(DXGI_FORMAT format) +{ +#ifdef _DEBUG + // Ensure conversion table is in ascending order + assert(_countof(g_ConvertTable) > 0); + DXGI_FORMAT lastvalue = g_ConvertTable[0].format; + for (size_t index = 1; index < _countof(g_ConvertTable); ++index) + { + assert(g_ConvertTable[index].format > lastvalue); + lastvalue = g_ConvertTable[index].format; + } +#endif + + ConvertData key = { format, 0 }; + const ConvertData* in = (const ConvertData*)bsearch_s(&key, g_ConvertTable, _countof(g_ConvertTable), sizeof(ConvertData), + _ConvertCompare, nullptr); + return (in) ? in->flags : 0; +} + +_Use_decl_annotations_ +void DirectX::_ConvertScanline( + XMVECTOR* pBuffer, + size_t count, + DXGI_FORMAT outFormat, + DXGI_FORMAT inFormat, + DWORD flags) +{ + assert(pBuffer && count > 0 && (((uintptr_t)pBuffer & 0xF) == 0)); + assert(IsValid(outFormat) && !IsTypeless(outFormat) && !IsPlanar(outFormat) && !IsPalettized(outFormat)); + assert(IsValid(inFormat) && !IsTypeless(inFormat) && !IsPlanar(inFormat) && !IsPalettized(inFormat)); + + if (!pBuffer) + return; + +#ifdef _DEBUG + // Ensure conversion table is in ascending order + assert(_countof(g_ConvertTable) > 0); + DXGI_FORMAT lastvalue = g_ConvertTable[0].format; + for (size_t index = 1; index < _countof(g_ConvertTable); ++index) + { + assert(g_ConvertTable[index].format > lastvalue); + lastvalue = g_ConvertTable[index].format; + } +#endif + + // Determine conversion details about source and dest formats + ConvertData key = { inFormat, 0 }; + const ConvertData* in = (const ConvertData*)bsearch_s(&key, g_ConvertTable, _countof(g_ConvertTable), sizeof(ConvertData), + _ConvertCompare, nullptr); + key.format = outFormat; + const ConvertData* out = (const ConvertData*)bsearch_s(&key, g_ConvertTable, _countof(g_ConvertTable), sizeof(ConvertData), + _ConvertCompare, nullptr); + if (!in || !out) + { + assert(false); + return; + } + + assert(_GetConvertFlags(inFormat) == in->flags); + assert(_GetConvertFlags(outFormat) == out->flags); + + // Handle SRGB filtering modes + switch (inFormat) + { + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_BC7_UNORM_SRGB: + flags |= TEX_FILTER_SRGB_IN; + break; + + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + flags &= ~TEX_FILTER_SRGB_IN; + break; + + default: + break; + } + + switch (outFormat) + { + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_BC7_UNORM_SRGB: + flags |= TEX_FILTER_SRGB_OUT; + break; + + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + flags &= ~TEX_FILTER_SRGB_OUT; + break; + + default: + break; + } + + if ((flags & (TEX_FILTER_SRGB_IN | TEX_FILTER_SRGB_OUT)) == (TEX_FILTER_SRGB_IN | TEX_FILTER_SRGB_OUT)) + { + flags &= ~(TEX_FILTER_SRGB_IN | TEX_FILTER_SRGB_OUT); + } + + // sRGB input processing (sRGB -> Linear RGB) + if (flags & TEX_FILTER_SRGB_IN) + { + if (!(in->flags & CONVF_DEPTH) && ((in->flags & CONVF_FLOAT) || (in->flags & CONVF_UNORM))) + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i, ++ptr) + { + *ptr = XMColorSRGBToRGB(*ptr); + } + } + } + + // Handle conversion special cases + DWORD diffFlags = in->flags ^ out->flags; + if (diffFlags != 0) + { + if (diffFlags & CONVF_DEPTH) + { + //--- Depth conversions --- + if (in->flags & CONVF_DEPTH) + { + // CONVF_DEPTH -> !CONVF_DEPTH + if (in->flags & CONVF_STENCIL) + { + // Stencil -> Alpha + static const XMVECTORF32 S = { { { 1.f, 1.f, 1.f, 255.f } } }; + + if (out->flags & CONVF_UNORM) + { + // UINT -> UNORM + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatY(v); + v1 = XMVectorClamp(v1, g_XMZero, S); + v1 = XMVectorDivide(v1, S); + *ptr++ = XMVectorSelect(v1, v, g_XMSelect1110); + } + } + else if (out->flags & CONVF_SNORM) + { + // UINT -> SNORM + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatY(v); + v1 = XMVectorClamp(v1, g_XMZero, S); + v1 = XMVectorDivide(v1, S); + v1 = XMVectorMultiplyAdd(v1, g_XMTwo, g_XMNegativeOne); + *ptr++ = XMVectorSelect(v1, v, g_XMSelect1110); + } + } + else + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatY(v); + *ptr++ = XMVectorSelect(v1, v, g_XMSelect1110); + } + } + } + + // Depth -> RGB + if ((out->flags & CONVF_UNORM) && (in->flags & CONVF_FLOAT)) + { + // Depth FLOAT -> UNORM + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSaturate(v); + v1 = XMVectorSplatX(v1); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1110); + } + } + else if (out->flags & CONVF_SNORM) + { + if (in->flags & CONVF_UNORM) + { + // Depth UNORM -> SNORM + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorMultiplyAdd(v, g_XMTwo, g_XMNegativeOne); + v1 = XMVectorSplatX(v1); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1110); + } + } + else + { + // Depth FLOAT -> SNORM + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorClamp(v, g_XMNegativeOne, g_XMOne); + v1 = XMVectorSplatX(v1); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1110); + } + } + } + else + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatX(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1110); + } + } + } + else + { + // !CONVF_DEPTH -> CONVF_DEPTH + + // RGB -> Depth (red channel) + switch (flags & (TEX_FILTER_RGB_COPY_RED | TEX_FILTER_RGB_COPY_GREEN | TEX_FILTER_RGB_COPY_BLUE)) + { + case TEX_FILTER_RGB_COPY_GREEN: + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatY(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1000); + } + } + break; + + case TEX_FILTER_RGB_COPY_BLUE: + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatZ(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1000); + } + } + break; + + default: + if ((in->flags & CONVF_UNORM) && ((in->flags & CONVF_RGB_MASK) == (CONVF_R | CONVF_G | CONVF_B))) + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVector3Dot(v, g_Grayscale); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1000); + } + break; + } + + __fallthrough; + + case TEX_FILTER_RGB_COPY_RED: + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatX(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1000); + } + } + break; + } + + // Finialize type conversion for depth (red channel) + if (out->flags & CONVF_UNORM) + { + if (in->flags & CONVF_SNORM) + { + // SNORM -> UNORM + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorMultiplyAdd(v, g_XMOneHalf, g_XMOneHalf); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1000); + } + } + else if (in->flags & CONVF_FLOAT) + { + // FLOAT -> UNORM + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSaturate(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1000); + } + } + } + + if (out->flags & CONVF_STENCIL) + { + // Alpha -> Stencil (green channel) + static const XMVECTORU32 select0100 = { { { XM_SELECT_0, XM_SELECT_1, XM_SELECT_0, XM_SELECT_0 } } }; + static const XMVECTORF32 S = { { { 255.f, 255.f, 255.f, 255.f } } }; + + if (in->flags & CONVF_UNORM) + { + // UNORM -> UINT + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorMultiply(v, S); + v1 = XMVectorSplatW(v1); + *ptr++ = XMVectorSelect(v, v1, select0100); + } + } + else if (in->flags & CONVF_SNORM) + { + // SNORM -> UINT + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorMultiplyAdd(v, g_XMOneHalf, g_XMOneHalf); + v1 = XMVectorMultiply(v1, S); + v1 = XMVectorSplatW(v1); + *ptr++ = XMVectorSelect(v, v1, select0100); + } + } + else + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatW(v); + *ptr++ = XMVectorSelect(v, v1, select0100); + } + } + } + } + } + else if (out->flags & CONVF_DEPTH) + { + // CONVF_DEPTH -> CONVF_DEPTH + if (diffFlags & CONVF_FLOAT) + { + if (in->flags & CONVF_FLOAT) + { + // FLOAT -> UNORM depth, preserve stencil + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSaturate(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1000); + } + } + } + } + else if (out->flags & CONVF_UNORM) + { + //--- Converting to a UNORM --- + if (in->flags & CONVF_SNORM) + { + // SNORM -> UNORM + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + *ptr++ = XMVectorMultiplyAdd(v, g_XMOneHalf, g_XMOneHalf); + } + } + else if (in->flags & CONVF_FLOAT) + { + XMVECTOR* ptr = pBuffer; + if (!(in->flags & CONVF_POS_ONLY) && (flags & TEX_FILTER_FLOAT_X2BIAS)) + { + // FLOAT -> UNORM (x2 bias) + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + v = XMVectorClamp(v, g_XMNegativeOne, g_XMOne); + *ptr++ = XMVectorMultiplyAdd(v, g_XMOneHalf, g_XMOneHalf); + } + } + else + { + // FLOAT -> UNORM + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + *ptr++ = XMVectorSaturate(v); + } + } + } + } + else if (out->flags & CONVF_SNORM) + { + //--- Converting to a SNORM --- + if (in->flags & CONVF_UNORM) + { + // UNORM -> SNORM + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + *ptr++ = XMVectorMultiplyAdd(v, g_XMTwo, g_XMNegativeOne); + } + } + else if (in->flags & CONVF_FLOAT) + { + XMVECTOR* ptr = pBuffer; + if ((in->flags & CONVF_POS_ONLY) && (flags & TEX_FILTER_FLOAT_X2BIAS)) + { + // FLOAT (positive only, x2 bias) -> SNORM + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + v = XMVectorSaturate(v); + *ptr++ = XMVectorMultiplyAdd(v, g_XMTwo, g_XMNegativeOne); + } + } + else + { + // FLOAT -> SNORM + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + *ptr++ = XMVectorClamp(v, g_XMNegativeOne, g_XMOne); + } + } + } + } + else if (diffFlags & CONVF_UNORM) + { + //--- Converting from a UNORM --- + assert(in->flags & CONVF_UNORM); + if (out->flags & CONVF_FLOAT) + { + if (!(out->flags & CONVF_POS_ONLY) && (flags & TEX_FILTER_FLOAT_X2BIAS)) + { + // UNORM (x2 bias) -> FLOAT + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + *ptr++ = XMVectorMultiplyAdd(v, g_XMTwo, g_XMNegativeOne); + } + } + } + } + else if (diffFlags & CONVF_POS_ONLY) + { + if (flags & TEX_FILTER_FLOAT_X2BIAS) + { + if (in->flags & CONVF_POS_ONLY) + { + if (out->flags & CONVF_FLOAT) + { + // FLOAT (positive only, x2 bias) -> FLOAT + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + v = XMVectorSaturate(v); + *ptr++ = XMVectorMultiplyAdd(v, g_XMTwo, g_XMNegativeOne); + } + } + } + else if (out->flags & CONVF_POS_ONLY) + { + if (in->flags & CONVF_FLOAT) + { + // FLOAT -> FLOAT (positive only, x2 bias) + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + v = XMVectorClamp(v, g_XMNegativeOne, g_XMOne); + *ptr++ = XMVectorMultiplyAdd(v, g_XMOneHalf, g_XMOneHalf); + } + } + else if (in->flags & CONVF_SNORM) + { + // SNORM -> FLOAT (positive only, x2 bias) + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + *ptr++ = XMVectorMultiplyAdd(v, g_XMOneHalf, g_XMOneHalf); + } + } + } + } + } + + // !CONVF_A -> CONVF_A is handled because LoadScanline ensures alpha defaults to 1.0 for no-alpha formats + + // CONVF_PACKED cases are handled because LoadScanline/StoreScanline handles packing/unpacking + + if (((out->flags & CONVF_RGBA_MASK) == CONVF_A) && !(in->flags & CONVF_A)) + { + // !CONVF_A -> A format + switch (flags & (TEX_FILTER_RGB_COPY_RED | TEX_FILTER_RGB_COPY_GREEN | TEX_FILTER_RGB_COPY_BLUE)) + { + case TEX_FILTER_RGB_COPY_GREEN: + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + *ptr++ = XMVectorSplatY(v); + } + } + break; + + case TEX_FILTER_RGB_COPY_BLUE: + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + *ptr++ = XMVectorSplatZ(v); + } + } + break; + + default: + if ((in->flags & CONVF_UNORM) && ((in->flags & CONVF_RGB_MASK) == (CONVF_R | CONVF_G | CONVF_B))) + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + *ptr++ = XMVector3Dot(v, g_Grayscale); + } + break; + } + + __fallthrough; + + case TEX_FILTER_RGB_COPY_RED: + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + *ptr++ = XMVectorSplatX(v); + } + } + break; + } + } + else if (((in->flags & CONVF_RGBA_MASK) == CONVF_A) && !(out->flags & CONVF_A)) + { + // A format -> !CONVF_A + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + *ptr++ = XMVectorSplatW(v); + } + } + else if ((in->flags & CONVF_RGB_MASK) == CONVF_R) + { + if ((out->flags & CONVF_RGB_MASK) == (CONVF_R | CONVF_G | CONVF_B)) + { + // R format -> RGB format + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatX(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1110); + } + } + else if ((out->flags & CONVF_RGB_MASK) == (CONVF_R | CONVF_G)) + { + // R format -> RG format + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatX(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1100); + } + } + } + else if ((in->flags & CONVF_RGB_MASK) == (CONVF_R | CONVF_G | CONVF_B)) + { + if ((out->flags & CONVF_RGB_MASK) == CONVF_R) + { + // RGB format -> R format + switch (flags & (TEX_FILTER_RGB_COPY_RED | TEX_FILTER_RGB_COPY_GREEN | TEX_FILTER_RGB_COPY_BLUE)) + { + case TEX_FILTER_RGB_COPY_GREEN: + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatY(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1110); + } + } + break; + + case TEX_FILTER_RGB_COPY_BLUE: + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSplatZ(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1110); + } + } + break; + + default: + if (in->flags & CONVF_UNORM) + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVector3Dot(v, g_Grayscale); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1110); + } + break; + } + + __fallthrough; + + case TEX_FILTER_RGB_COPY_RED: + // Leave data unchanged and the store will handle this... + break; + } + } + else if ((out->flags & CONVF_RGB_MASK) == (CONVF_R | CONVF_G)) + { + // RGB format -> RG format + switch (flags & (TEX_FILTER_RGB_COPY_RED | TEX_FILTER_RGB_COPY_GREEN | TEX_FILTER_RGB_COPY_BLUE)) + { + case TEX_FILTER_RGB_COPY_RED | TEX_FILTER_RGB_COPY_BLUE: + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSwizzle<0, 2, 0, 2>(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1100); + } + } + break; + + case TEX_FILTER_RGB_COPY_GREEN | TEX_FILTER_RGB_COPY_BLUE: + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i) + { + XMVECTOR v = *ptr; + XMVECTOR v1 = XMVectorSwizzle<1, 2, 3, 0>(v); + *ptr++ = XMVectorSelect(v, v1, g_XMSelect1100); + } + } + break; + + case TEX_FILTER_RGB_COPY_RED | TEX_FILTER_RGB_COPY_GREEN: + default: + // Leave data unchanged and the store will handle this... + break; + } + } + } + } + + // sRGB output processing (Linear RGB -> sRGB) + if (flags & TEX_FILTER_SRGB_OUT) + { + if (!(out->flags & CONVF_DEPTH) && ((out->flags & CONVF_FLOAT) || (out->flags & CONVF_UNORM))) + { + XMVECTOR* ptr = pBuffer; + for (size_t i = 0; i < count; ++i, ++ptr) + { + *ptr = XMColorRGBToSRGB(*ptr); + } + } + } +} + + +//------------------------------------------------------------------------------------- +// Dithering +//------------------------------------------------------------------------------------- +namespace +{ + // 4X4X4 ordered dithering matrix + const float g_Dither[] = + { + // (z & 3) + ( (y & 3) * 8) + (x & 3) + 0.468750f, -0.031250f, 0.343750f, -0.156250f, 0.468750f, -0.031250f, 0.343750f, -0.156250f, + -0.281250f, 0.218750f, -0.406250f, 0.093750f, -0.281250f, 0.218750f, -0.406250f, 0.093750f, + 0.281250f, -0.218750f, 0.406250f, -0.093750f, 0.281250f, -0.218750f, 0.406250f, -0.093750f, + -0.468750f, 0.031250f, -0.343750f, 0.156250f, -0.468750f, 0.031250f, -0.343750f, 0.156250f, + }; + + const XMVECTORF32 g_Scale16pc = { { { 65535.f, 65535.f, 65535.f, 65535.f } } }; + const XMVECTORF32 g_Scale15pc = { { { 32767.f, 32767.f, 32767.f, 32767.f } } }; + const XMVECTORF32 g_Scale10pc = { { { 1023.f, 1023.f, 1023.f, 3.f } } }; + const XMVECTORF32 g_Scale9pc = { { { 511.f, 511.f, 511.f, 3.f } } }; + const XMVECTORF32 g_Scale8pc = { { { 255.f, 255.f, 255.f, 255.f } } }; + const XMVECTORF32 g_Scale7pc = { { { 127.f, 127.f, 127.f, 127.f } } }; + const XMVECTORF32 g_Scale565pc = { { { 31.f, 63.f, 31.f, 1.f } } }; + const XMVECTORF32 g_Scale5551pc = { { { 31.f, 31.f, 31.f, 1.f } } }; + const XMVECTORF32 g_Scale4pc = { { { 15.f, 15.f, 15.f, 15.f } } }; + + const XMVECTORF32 g_ErrorWeight3 = { { { 3.f / 16.f, 3.f / 16.f, 3.f / 16.f, 3.f / 16.f } } }; + const XMVECTORF32 g_ErrorWeight5 = { { { 5.f / 16.f, 5.f / 16.f, 5.f / 16.f, 5.f / 16.f } } }; + const XMVECTORF32 g_ErrorWeight1 = { { { 1.f / 16.f, 1.f / 16.f, 1.f / 16.f, 1.f / 16.f } } }; + const XMVECTORF32 g_ErrorWeight7 = { { { 7.f / 16.f, 7.f / 16.f, 7.f / 16.f, 7.f / 16.f } } }; + +#define STORE_SCANLINE( type, scalev, clampzero, norm, itype, mask, row, bgr ) \ + if ( size >= sizeof(type) ) \ + { \ + type * __restrict dest = reinterpret_cast(pDestination); \ + for( size_t i = 0; i < count; ++i ) \ + { \ + ptrdiff_t index = static_cast( ( row & 1 ) ? ( count - i - 1 ) : i ); \ + ptrdiff_t delta = ( row & 1 ) ? -2 : 0; \ + \ + XMVECTOR v = sPtr[ index ]; \ + if ( bgr ) { v = XMVectorSwizzle<2, 1, 0, 3>( v ); } \ + if ( norm && clampzero ) v = XMVectorSaturate( v ) ; \ + else if ( clampzero ) v = XMVectorClamp( v, g_XMZero, scalev ); \ + else if ( norm ) v = XMVectorClamp( v, g_XMNegativeOne, g_XMOne ); \ + else v = XMVectorClamp( v, -scalev + g_XMOne, scalev ); \ + v = XMVectorAdd( v, vError ); \ + if ( norm ) v = XMVectorMultiply( v, scalev ); \ + \ + XMVECTOR target; \ + if ( pDiffusionErrors ) \ + { \ + target = XMVectorRound( v ); \ + vError = XMVectorSubtract( v, target ); \ + if (norm) vError = XMVectorDivide( vError, scalev ); \ + \ + /* Distribute error to next scanline and next pixel */ \ + pDiffusionErrors[ index-delta ] += XMVectorMultiply( g_ErrorWeight3, vError ); \ + pDiffusionErrors[ index+1 ] += XMVectorMultiply( g_ErrorWeight5, vError ); \ + pDiffusionErrors[ index+2+delta ] += XMVectorMultiply( g_ErrorWeight1, vError ); \ + vError = XMVectorMultiply( vError, g_ErrorWeight7 ); \ + } \ + else \ + { \ + /* Applied ordered dither */ \ + target = XMVectorAdd( v, ordered[ index & 3 ] ); \ + target = XMVectorRound( target ); \ + } \ + \ + target = XMVectorMin( scalev, target ); \ + target = XMVectorMax( (clampzero) ? g_XMZero : ( -scalev + g_XMOne ), target ); \ + \ + XMFLOAT4A tmp; \ + XMStoreFloat4A( &tmp, target ); \ + \ + auto dPtr = &dest[ index ]; \ + if (dPtr >= ePtr) break; \ + dPtr->x = static_cast( tmp.x ) & mask; \ + dPtr->y = static_cast( tmp.y ) & mask; \ + dPtr->z = static_cast( tmp.z ) & mask; \ + dPtr->w = static_cast( tmp.w ) & mask; \ + } \ + return true; \ + } \ + return false; + +#define STORE_SCANLINE2( type, scalev, clampzero, norm, itype, mask, row ) \ + /* The 2 component cases are always bgr=false */ \ + if ( size >= sizeof(type) ) \ + { \ + type * __restrict dest = reinterpret_cast(pDestination); \ + for( size_t i = 0; i < count; ++i ) \ + { \ + ptrdiff_t index = static_cast( ( row & 1 ) ? ( count - i - 1 ) : i ); \ + ptrdiff_t delta = ( row & 1 ) ? -2 : 0; \ + \ + XMVECTOR v = sPtr[ index ]; \ + if ( norm && clampzero ) v = XMVectorSaturate( v ) ; \ + else if ( clampzero ) v = XMVectorClamp( v, g_XMZero, scalev ); \ + else if ( norm ) v = XMVectorClamp( v, g_XMNegativeOne, g_XMOne ); \ + else v = XMVectorClamp( v, -scalev + g_XMOne, scalev ); \ + v = XMVectorAdd( v, vError ); \ + if ( norm ) v = XMVectorMultiply( v, scalev ); \ + \ + XMVECTOR target; \ + if ( pDiffusionErrors ) \ + { \ + target = XMVectorRound( v ); \ + vError = XMVectorSubtract( v, target ); \ + if (norm) vError = XMVectorDivide( vError, scalev ); \ + \ + /* Distribute error to next scanline and next pixel */ \ + pDiffusionErrors[ index-delta ] += XMVectorMultiply( g_ErrorWeight3, vError ); \ + pDiffusionErrors[ index+1 ] += XMVectorMultiply( g_ErrorWeight5, vError ); \ + pDiffusionErrors[ index+2+delta ] += XMVectorMultiply( g_ErrorWeight1, vError ); \ + vError = XMVectorMultiply( vError, g_ErrorWeight7 ); \ + } \ + else \ + { \ + /* Applied ordered dither */ \ + target = XMVectorAdd( v, ordered[ index & 3 ] ); \ + target = XMVectorRound( target ); \ + } \ + \ + target = XMVectorMin( scalev, target ); \ + target = XMVectorMax( (clampzero) ? g_XMZero : ( -scalev + g_XMOne ), target ); \ + \ + XMFLOAT4A tmp; \ + XMStoreFloat4A( &tmp, target ); \ + \ + auto dPtr = &dest[ index ]; \ + if (dPtr >= ePtr) break; \ + dPtr->x = static_cast( tmp.x ) & mask; \ + dPtr->y = static_cast( tmp.y ) & mask; \ + } \ + return true; \ + } \ + return false; + +#define STORE_SCANLINE1( type, scalev, clampzero, norm, mask, row, selectw ) \ + /* The 1 component cases are always bgr=false */ \ + if ( size >= sizeof(type) ) \ + { \ + type * __restrict dest = reinterpret_cast(pDestination); \ + for( size_t i = 0; i < count; ++i ) \ + { \ + ptrdiff_t index = static_cast( ( row & 1 ) ? ( count - i - 1 ) : i ); \ + ptrdiff_t delta = ( row & 1 ) ? -2 : 0; \ + \ + XMVECTOR v = sPtr[ index ]; \ + if ( norm && clampzero ) v = XMVectorSaturate( v ) ; \ + else if ( clampzero ) v = XMVectorClamp( v, g_XMZero, scalev ); \ + else if ( norm ) v = XMVectorClamp( v, g_XMNegativeOne, g_XMOne ); \ + else v = XMVectorClamp( v, -scalev + g_XMOne, scalev ); \ + v = XMVectorAdd( v, vError ); \ + if ( norm ) v = XMVectorMultiply( v, scalev ); \ + \ + XMVECTOR target; \ + if ( pDiffusionErrors ) \ + { \ + target = XMVectorRound( v ); \ + vError = XMVectorSubtract( v, target ); \ + if (norm) vError = XMVectorDivide( vError, scalev ); \ + \ + /* Distribute error to next scanline and next pixel */ \ + pDiffusionErrors[ index-delta ] += XMVectorMultiply( g_ErrorWeight3, vError ); \ + pDiffusionErrors[ index+1 ] += XMVectorMultiply( g_ErrorWeight5, vError ); \ + pDiffusionErrors[ index+2+delta ] += XMVectorMultiply( g_ErrorWeight1, vError ); \ + vError = XMVectorMultiply( vError, g_ErrorWeight7 ); \ + } \ + else \ + { \ + /* Applied ordered dither */ \ + target = XMVectorAdd( v, ordered[ index & 3 ] ); \ + target = XMVectorRound( target ); \ + } \ + \ + target = XMVectorMin( scalev, target ); \ + target = XMVectorMax( (clampzero) ? g_XMZero : ( -scalev + g_XMOne ), target ); \ + \ + auto dPtr = &dest[ index ]; \ + if (dPtr >= ePtr) break; \ + *dPtr = static_cast( (selectw) ? XMVectorGetW( target ) : XMVectorGetX( target ) ) & mask; \ + } \ + return true; \ + } \ + return false; +} + +#pragma warning(push) +#pragma warning( disable : 4127 ) + +_Use_decl_annotations_ +bool DirectX::_StoreScanlineDither( + void* pDestination, + size_t size, + DXGI_FORMAT format, + XMVECTOR* pSource, + size_t count, + float threshold, + size_t y, + size_t z, + XMVECTOR* pDiffusionErrors) +{ + assert(pDestination && size > 0); + assert(pSource && count > 0 && (((uintptr_t)pSource & 0xF) == 0)); + assert(IsValid(format) && !IsTypeless(format) && !IsCompressed(format) && !IsPlanar(format) && !IsPalettized(format)); + + XMVECTOR ordered[4]; + if (pDiffusionErrors) + { + // If pDiffusionErrors != 0, then this function performs error diffusion dithering (aka Floyd-Steinberg dithering) + + // To avoid the need for another temporary scanline buffer, we allow this function to overwrite the source buffer in-place + // Given the intended usage in the conversion routines, this is not a problem. + + XMVECTOR* ptr = pSource; + const XMVECTOR* err = pDiffusionErrors + 1; + for (size_t i = 0; i < count; ++i) + { + // Add contribution from previous scanline + XMVECTOR v = XMVectorAdd(*ptr, *err++); + *ptr++ = v; + } + + // Reset errors for next scanline + memset(pDiffusionErrors, 0, sizeof(XMVECTOR)*(count + 2)); + } + else + { + // If pDiffusionErrors == 0, then this function performs ordered dithering + + XMVECTOR dither = XMLoadFloat4(reinterpret_cast(g_Dither + (z & 3) + ((y & 3) * 8))); + + ordered[0] = XMVectorSplatX(dither); + ordered[1] = XMVectorSplatY(dither); + ordered[2] = XMVectorSplatZ(dither); + ordered[3] = XMVectorSplatW(dither); + } + + const XMVECTOR* __restrict sPtr = pSource; + if (!sPtr) + return false; + + const void* ePtr = reinterpret_cast(pDestination) + size; + + XMVECTOR vError = XMVectorZero(); + + switch (static_cast(format)) + { + case DXGI_FORMAT_R16G16B16A16_UNORM: + STORE_SCANLINE(XMUSHORTN4, g_Scale16pc, true, true, uint16_t, 0xFFFF, y, false) + + case DXGI_FORMAT_R16G16B16A16_UINT: + STORE_SCANLINE(XMUSHORT4, g_Scale16pc, true, false, uint16_t, 0xFFFF, y, false) + + case DXGI_FORMAT_R16G16B16A16_SNORM: + STORE_SCANLINE(XMSHORTN4, g_Scale15pc, false, true, int16_t, 0xFFFF, y, false) + + case DXGI_FORMAT_R16G16B16A16_SINT: + STORE_SCANLINE(XMSHORT4, g_Scale15pc, false, false, int16_t, 0xFFFF, y, false) + + case DXGI_FORMAT_R10G10B10A2_UNORM: + STORE_SCANLINE(XMUDECN4, g_Scale10pc, true, true, uint16_t, 0x3FF, y, false) + + case DXGI_FORMAT_R10G10B10A2_UINT: + STORE_SCANLINE(XMUDEC4, g_Scale10pc, true, false, uint16_t, 0x3FF, y, false) + + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + if (size >= sizeof(XMUDEC4)) + { + static const XMVECTORF32 Scale = { { { 510.0f, 510.0f, 510.0f, 3.0f } } }; + static const XMVECTORF32 Bias = { { { 384.0f, 384.0f, 384.0f, 0.0f } } }; + static const XMVECTORF32 MinXR = { { { -0.7529f, -0.7529f, -0.7529f, 0.f } } }; + static const XMVECTORF32 MaxXR = { { { 1.2529f, 1.2529f, 1.2529f, 1.0f } } }; + + XMUDEC4 * __restrict dest = reinterpret_cast(pDestination); + for (size_t i = 0; i < count; ++i) + { + ptrdiff_t index = static_cast((y & 1) ? (count - i - 1) : i); + ptrdiff_t delta = (y & 1) ? -2 : 0; + + XMVECTOR v = XMVectorClamp(sPtr[index], MinXR, MaxXR); + v = XMVectorMultiplyAdd(v, Scale, vError); + + XMVECTOR target; + if (pDiffusionErrors) + { + target = XMVectorRound(v); + vError = XMVectorSubtract(v, target); + vError = XMVectorDivide(vError, Scale); + + // Distribute error to next scanline and next pixel + pDiffusionErrors[index - delta] += XMVectorMultiply(g_ErrorWeight3, vError); + pDiffusionErrors[index + 1] += XMVectorMultiply(g_ErrorWeight5, vError); + pDiffusionErrors[index + 2 + delta] += XMVectorMultiply(g_ErrorWeight1, vError); + vError = XMVectorMultiply(vError, g_ErrorWeight7); + } + else + { + // Applied ordered dither + target = XMVectorAdd(v, ordered[index & 3]); + target = XMVectorRound(target); + } + + target = XMVectorAdd(target, Bias); + target = XMVectorClamp(target, g_XMZero, g_Scale10pc); + + XMFLOAT4A tmp; + XMStoreFloat4A(&tmp, target); + + auto dPtr = &dest[index]; + if (dPtr >= ePtr) break; + dPtr->x = static_cast(tmp.x) & 0x3FF; + dPtr->y = static_cast(tmp.y) & 0x3FF; + dPtr->z = static_cast(tmp.z) & 0x3FF; + dPtr->w = static_cast(tmp.w); + } + return true; + } + return false; + + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + STORE_SCANLINE(XMUBYTEN4, g_Scale8pc, true, true, uint8_t, 0xFF, y, false) + + case DXGI_FORMAT_R8G8B8A8_UINT: + STORE_SCANLINE(XMUBYTE4, g_Scale8pc, true, false, uint8_t, 0xFF, y, false) + + case DXGI_FORMAT_R8G8B8A8_SNORM: + STORE_SCANLINE(XMBYTEN4, g_Scale7pc, false, true, int8_t, 0xFF, y, false) + + case DXGI_FORMAT_R8G8B8A8_SINT: + STORE_SCANLINE(XMBYTE4, g_Scale7pc, false, false, int8_t, 0xFF, y, false) + + case DXGI_FORMAT_R16G16_UNORM: + STORE_SCANLINE2(XMUSHORTN2, g_Scale16pc, true, true, uint16_t, 0xFFFF, y) + + case DXGI_FORMAT_R16G16_UINT: + STORE_SCANLINE2(XMUSHORT2, g_Scale16pc, true, false, uint16_t, 0xFFFF, y) + + case DXGI_FORMAT_R16G16_SNORM: + STORE_SCANLINE2(XMSHORTN2, g_Scale15pc, false, true, int16_t, 0xFFFF, y) + + case DXGI_FORMAT_R16G16_SINT: + STORE_SCANLINE2(XMSHORT2, g_Scale15pc, false, false, int16_t, 0xFFFF, y) + + case DXGI_FORMAT_D24_UNORM_S8_UINT: + if (size >= sizeof(uint32_t)) + { + static const XMVECTORF32 Clamp = { { { 1.f, 255.f, 0.f, 0.f } } }; + static const XMVECTORF32 Scale = { { { 16777215.f, 1.f, 0.f, 0.f } } }; + static const XMVECTORF32 Scale2 = { { { 16777215.f, 255.f, 0.f, 0.f } } }; + + uint32_t * __restrict dest = reinterpret_cast(pDestination); + for (size_t i = 0; i < count; ++i) + { + ptrdiff_t index = static_cast((y & 1) ? (count - i - 1) : i); + ptrdiff_t delta = (y & 1) ? -2 : 0; + + XMVECTOR v = XMVectorClamp(sPtr[index], g_XMZero, Clamp); + v = XMVectorAdd(v, vError); + v = XMVectorMultiply(v, Scale); + + XMVECTOR target; + if (pDiffusionErrors) + { + target = XMVectorRound(v); + vError = XMVectorSubtract(v, target); + vError = XMVectorDivide(vError, Scale); + + // Distribute error to next scanline and next pixel + pDiffusionErrors[index - delta] += XMVectorMultiply(g_ErrorWeight3, vError); + pDiffusionErrors[index + 1] += XMVectorMultiply(g_ErrorWeight5, vError); + pDiffusionErrors[index + 2 + delta] += XMVectorMultiply(g_ErrorWeight1, vError); + vError = XMVectorMultiply(vError, g_ErrorWeight7); + } + else + { + // Applied ordered dither + target = XMVectorAdd(v, ordered[index & 3]); + target = XMVectorRound(target); + } + + target = XMVectorClamp(target, g_XMZero, Scale2); + + XMFLOAT4A tmp; + XMStoreFloat4A(&tmp, target); + + auto dPtr = &dest[index]; + if (dPtr >= ePtr) break; + *dPtr = (static_cast(tmp.x) & 0xFFFFFF) + | ((static_cast(tmp.y) & 0xFF) << 24); + } + return true; + } + return false; + + case DXGI_FORMAT_R8G8_UNORM: + STORE_SCANLINE2(XMUBYTEN2, g_Scale8pc, true, true, uint8_t, 0xFF, y) + + case DXGI_FORMAT_R8G8_UINT: + STORE_SCANLINE2(XMUBYTE2, g_Scale8pc, true, false, uint8_t, 0xFF, y) + + case DXGI_FORMAT_R8G8_SNORM: + STORE_SCANLINE2(XMBYTEN2, g_Scale7pc, false, true, int8_t, 0xFF, y) + + case DXGI_FORMAT_R8G8_SINT: + STORE_SCANLINE2(XMBYTE2, g_Scale7pc, false, false, int8_t, 0xFF, y) + + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + STORE_SCANLINE1(uint16_t, g_Scale16pc, true, true, 0xFFFF, y, false) + + case DXGI_FORMAT_R16_UINT: + STORE_SCANLINE1(uint16_t, g_Scale16pc, true, false, 0xFFFF, y, false) + + case DXGI_FORMAT_R16_SNORM: + STORE_SCANLINE1(int16_t, g_Scale15pc, false, true, 0xFFFF, y, false) + + case DXGI_FORMAT_R16_SINT: + STORE_SCANLINE1(int16_t, g_Scale15pc, false, false, 0xFFFF, y, false) + + case DXGI_FORMAT_R8_UNORM: + STORE_SCANLINE1(uint8_t, g_Scale8pc, true, true, 0xFF, y, false) + + case DXGI_FORMAT_R8_UINT: + STORE_SCANLINE1(uint8_t, g_Scale8pc, true, false, 0xFF, y, false) + + case DXGI_FORMAT_R8_SNORM: + STORE_SCANLINE1(int8_t, g_Scale7pc, false, true, 0xFF, y, false) + + case DXGI_FORMAT_R8_SINT: + STORE_SCANLINE1(int8_t, g_Scale7pc, false, false, 0xFF, y, false) + + case DXGI_FORMAT_A8_UNORM: + STORE_SCANLINE1(uint8_t, g_Scale8pc, true, true, 0xFF, y, true) + + case DXGI_FORMAT_B5G6R5_UNORM: + if (size >= sizeof(XMU565)) + { + XMU565 * __restrict dest = reinterpret_cast(pDestination); + for (size_t i = 0; i < count; ++i) + { + ptrdiff_t index = static_cast((y & 1) ? (count - i - 1) : i); + ptrdiff_t delta = (y & 1) ? -2 : 0; + + XMVECTOR v = XMVectorSwizzle<2, 1, 0, 3>(sPtr[index]); + v = XMVectorSaturate(v); + v = XMVectorAdd(v, vError); + v = XMVectorMultiply(v, g_Scale565pc); + + XMVECTOR target; + if (pDiffusionErrors) + { + target = XMVectorRound(v); + vError = XMVectorSubtract(v, target); + vError = XMVectorDivide(vError, g_Scale565pc); + + // Distribute error to next scanline and next pixel + pDiffusionErrors[index - delta] += XMVectorMultiply(g_ErrorWeight3, vError); + pDiffusionErrors[index + 1] += XMVectorMultiply(g_ErrorWeight5, vError); + pDiffusionErrors[index + 2 + delta] += XMVectorMultiply(g_ErrorWeight1, vError); + vError = XMVectorMultiply(vError, g_ErrorWeight7); + } + else + { + // Applied ordered dither + target = XMVectorAdd(v, ordered[index & 3]); + target = XMVectorRound(target); + } + + target = XMVectorClamp(target, g_XMZero, g_Scale565pc); + + XMFLOAT4A tmp; + XMStoreFloat4A(&tmp, target); + + auto dPtr = &dest[index]; + if (dPtr >= ePtr) break; + dPtr->x = static_cast(tmp.x) & 0x1F; + dPtr->y = static_cast(tmp.y) & 0x3F; + dPtr->z = static_cast(tmp.z) & 0x1F; + } + return true; + } + return false; + + case DXGI_FORMAT_B5G5R5A1_UNORM: + if (size >= sizeof(XMU555)) + { + XMU555 * __restrict dest = reinterpret_cast(pDestination); + for (size_t i = 0; i < count; ++i) + { + ptrdiff_t index = static_cast((y & 1) ? (count - i - 1) : i); + ptrdiff_t delta = (y & 1) ? -2 : 0; + + XMVECTOR v = XMVectorSwizzle<2, 1, 0, 3>(sPtr[index]); + v = XMVectorSaturate(v); + v = XMVectorAdd(v, vError); + v = XMVectorMultiply(v, g_Scale5551pc); + + XMVECTOR target; + if (pDiffusionErrors) + { + target = XMVectorRound(v); + vError = XMVectorSubtract(v, target); + vError = XMVectorDivide(vError, g_Scale5551pc); + + // Distribute error to next scanline and next pixel + pDiffusionErrors[index - delta] += XMVectorMultiply(g_ErrorWeight3, vError); + pDiffusionErrors[index + 1] += XMVectorMultiply(g_ErrorWeight5, vError); + pDiffusionErrors[index + 2 + delta] += XMVectorMultiply(g_ErrorWeight1, vError); + vError = XMVectorMultiply(vError, g_ErrorWeight7); + } + else + { + // Applied ordered dither + target = XMVectorAdd(v, ordered[index & 3]); + target = XMVectorRound(target); + } + + target = XMVectorClamp(target, g_XMZero, g_Scale5551pc); + + XMFLOAT4A tmp; + XMStoreFloat4A(&tmp, target); + + auto dPtr = &dest[index]; + if (dPtr >= ePtr) break; + dPtr->x = static_cast(tmp.x) & 0x1F; + dPtr->y = static_cast(tmp.y) & 0x1F; + dPtr->z = static_cast(tmp.z) & 0x1F; + dPtr->w = (XMVectorGetW(target) > threshold) ? 1 : 0; + } + return true; + } + return false; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + STORE_SCANLINE(XMUBYTEN4, g_Scale8pc, true, true, uint8_t, 0xFF, y, true) + + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + if (size >= sizeof(XMUBYTEN4)) + { + XMUBYTEN4 * __restrict dest = reinterpret_cast(pDestination); + for (size_t i = 0; i < count; ++i) + { + ptrdiff_t index = static_cast((y & 1) ? (count - i - 1) : i); + ptrdiff_t delta = (y & 1) ? -2 : 0; + + XMVECTOR v = XMVectorSwizzle<2, 1, 0, 3>(sPtr[index]); + v = XMVectorSaturate(v); + v = XMVectorAdd(v, vError); + v = XMVectorMultiply(v, g_Scale8pc); + + XMVECTOR target; + if (pDiffusionErrors) + { + target = XMVectorRound(v); + vError = XMVectorSubtract(v, target); + vError = XMVectorDivide(vError, g_Scale8pc); + + // Distribute error to next scanline and next pixel + pDiffusionErrors[index - delta] += XMVectorMultiply(g_ErrorWeight3, vError); + pDiffusionErrors[index + 1] += XMVectorMultiply(g_ErrorWeight5, vError); + pDiffusionErrors[index + 2 + delta] += XMVectorMultiply(g_ErrorWeight1, vError); + vError = XMVectorMultiply(vError, g_ErrorWeight7); + } + else + { + // Applied ordered dither + target = XMVectorAdd(v, ordered[index & 3]); + target = XMVectorRound(target); + } + + target = XMVectorClamp(target, g_XMZero, g_Scale8pc); + + XMFLOAT4A tmp; + XMStoreFloat4A(&tmp, target); + + auto dPtr = &dest[index]; + if (dPtr >= ePtr) break; + dPtr->x = static_cast(tmp.x) & 0xFF; + dPtr->y = static_cast(tmp.y) & 0xFF; + dPtr->z = static_cast(tmp.z) & 0xFF; + dPtr->w = 0; + } + return true; + } + return false; + + case DXGI_FORMAT_B4G4R4A4_UNORM: + STORE_SCANLINE(XMUNIBBLE4, g_Scale4pc, true, true, uint8_t, 0xF, y, true) + + case XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM: + STORE_SCANLINE(XMXDECN4, g_Scale9pc, false, true, uint16_t, 0x3FF, y, false) + + case XBOX_DXGI_FORMAT_R4G4_UNORM: + if (size >= sizeof(uint8_t)) + { + uint8_t * __restrict dest = reinterpret_cast(pDestination); + for (size_t i = 0; i < count; ++i) + { + ptrdiff_t index = static_cast((y & 1) ? (count - i - 1) : i); + ptrdiff_t delta = (y & 1) ? -2 : 0; + + XMVECTOR v = XMVectorSaturate(sPtr[index]); + v = XMVectorAdd(v, vError); + v = XMVectorMultiply(v, g_Scale4pc); + + XMVECTOR target; + if (pDiffusionErrors) + { + target = XMVectorRound(v); + vError = XMVectorSubtract(v, target); + vError = XMVectorDivide(vError, g_Scale4pc); + + // Distribute error to next scanline and next pixel + pDiffusionErrors[index - delta] += XMVectorMultiply(g_ErrorWeight3, vError); + pDiffusionErrors[index + 1] += XMVectorMultiply(g_ErrorWeight5, vError); + pDiffusionErrors[index + 2 + delta] += XMVectorMultiply(g_ErrorWeight1, vError); + vError = XMVectorMultiply(vError, g_ErrorWeight7); + } + else + { + // Applied ordered dither + target = XMVectorAdd(v, ordered[index & 3]); + target = XMVectorRound(target); + } + + target = XMVectorClamp(target, g_XMZero, g_Scale4pc); + + XMFLOAT4A tmp; + XMStoreFloat4A(&tmp, target); + + auto dPtr = &dest[index]; + if (dPtr >= ePtr) break; + *dPtr = (static_cast(tmp.x) & 0xF) + | ((static_cast(tmp.y) & 0xF) << 4); + } + return true; + } + return false; + + default: + return _StoreScanline(pDestination, size, format, pSource, count, threshold); + } +} + +#pragma warning(pop) + +#undef STORE_SCANLINE +#undef STORE_SCANLINE2 +#undef STORE_SCANLINE1 + +namespace +{ + //------------------------------------------------------------------------------------- + // Selection logic for using WIC vs. our own routines + //------------------------------------------------------------------------------------- + inline bool UseWICConversion( + _In_ DWORD filter, + _In_ DXGI_FORMAT sformat, + _In_ DXGI_FORMAT tformat, + _Out_ WICPixelFormatGUID& pfGUID, + _Out_ WICPixelFormatGUID& targetGUID) + { + memcpy(&pfGUID, &GUID_NULL, sizeof(GUID)); + memcpy(&targetGUID, &GUID_NULL, sizeof(GUID)); + + if (filter & TEX_FILTER_FORCE_NON_WIC) + { + // Explicit flag indicates use of non-WIC code paths + return false; + } + + if (!_DXGIToWIC(sformat, pfGUID) || !_DXGIToWIC(tformat, targetGUID)) + { + // Source or target format are not WIC supported native pixel formats + return false; + } + + if (filter & TEX_FILTER_FORCE_WIC) + { + // Explicit flag to use WIC code paths, skips all the case checks below + return true; + } + + if (filter & TEX_FILTER_SEPARATE_ALPHA) + { + // Alpha is not premultiplied, so use non-WIC code paths + return false; + } + + if (filter & TEX_FILTER_FLOAT_X2BIAS) + { + // X2 Scale & Bias conversions not supported by WIC code paths + return false; + } + +#if defined(_XBOX_ONE) && defined(_TITLE) + if (sformat == DXGI_FORMAT_R16G16B16A16_FLOAT + || sformat == DXGI_FORMAT_R16_FLOAT + || tformat == DXGI_FORMAT_R16G16B16A16_FLOAT + || tformat == DXGI_FORMAT_R16_FLOAT) + { + // Use non-WIC code paths as these conversions are not supported by Xbox One XDK + return false; + } +#endif + + // Check for special cases + switch (sformat) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + switch (tformat) + { + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_D32_FLOAT: + // WIC converts via UNORM formats and ends up converting colorspaces for these cases + case DXGI_FORMAT_A8_UNORM: + // Conversion logic for these kinds of textures is unintuitive for WIC code paths + return false; + + default: + break; + } + break; + + case DXGI_FORMAT_R16_FLOAT: + switch (tformat) + { + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_D32_FLOAT: + // WIC converts via UNORM formats and ends up converting colorspaces for these cases + case DXGI_FORMAT_A8_UNORM: + // Conversion logic for these kinds of textures is unintuitive for WIC code paths + return false; + + default: + break; + } + break; + + case DXGI_FORMAT_A8_UNORM: + // Conversion logic for these kinds of textures is unintuitive for WIC code paths + return false; + + default: + switch (tformat) + { + case DXGI_FORMAT_A8_UNORM: + // Conversion logic for these kinds of textures is unintuitive for WIC code paths + return false; + + default: + break; + } + } + + // Check for implicit color space changes + if (IsSRGB(sformat)) + filter |= TEX_FILTER_SRGB_IN; + + if (IsSRGB(tformat)) + filter |= TEX_FILTER_SRGB_OUT; + + if ((filter & (TEX_FILTER_SRGB_IN | TEX_FILTER_SRGB_OUT)) == (TEX_FILTER_SRGB_IN | TEX_FILTER_SRGB_OUT)) + { + filter &= ~(TEX_FILTER_SRGB_IN | TEX_FILTER_SRGB_OUT); + } + + DWORD wicsrgb = _CheckWICColorSpace(pfGUID, targetGUID); + + if (wicsrgb != (filter & (TEX_FILTER_SRGB_IN | TEX_FILTER_SRGB_OUT))) + { + // WIC will perform a colorspace conversion we didn't request + return false; + } + + return true; + } + + //------------------------------------------------------------------------------------- + // Convert the source image using WIC + //------------------------------------------------------------------------------------- + HRESULT ConvertUsingWIC( + _In_ const Image& srcImage, + _In_ const WICPixelFormatGUID& pfGUID, + _In_ const WICPixelFormatGUID& targetGUID, + _In_ DWORD filter, + _In_ float threshold, + _In_ const Image& destImage) + { + assert(srcImage.width == destImage.width); + assert(srcImage.height == destImage.height); + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr FC; + HRESULT hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + // Note that WIC conversion ignores the TEX_FILTER_SRGB_IN and TEX_FILTER_SRGB_OUT flags, + // but also always assumes UNORM <-> FLOAT conversions are changing color spaces sRGB <-> scRGB + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pfGUID, targetGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + // This case is not an issue for the subset of WIC formats that map directly to DXGI + return E_UNEXPECTED; + } + + ComPtr source; + hr = pWIC->CreateBitmapFromMemory(static_cast(srcImage.width), static_cast(srcImage.height), pfGUID, + static_cast(srcImage.rowPitch), static_cast(srcImage.slicePitch), + srcImage.pixels, source.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = FC->Initialize(source.Get(), targetGUID, _GetWICDither(filter), nullptr, threshold * 100.f, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(0, static_cast(destImage.rowPitch), static_cast(destImage.slicePitch), destImage.pixels); + if (FAILED(hr)) + return hr; + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Convert the source image (not using WIC) + //------------------------------------------------------------------------------------- + HRESULT ConvertCustom( + _In_ const Image& srcImage, + _In_ DWORD filter, + _In_ const Image& destImage, + _In_ float threshold, + size_t z) + { + assert(srcImage.width == destImage.width); + assert(srcImage.height == destImage.height); + + const uint8_t *pSrc = srcImage.pixels; + uint8_t *pDest = destImage.pixels; + if (!pSrc || !pDest) + return E_POINTER; + + size_t width = srcImage.width; + + if (filter & TEX_FILTER_DITHER_DIFFUSION) + { + // Error diffusion dithering (aka Floyd-Steinberg dithering) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*(width * 2 + 2)), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + XMVECTOR* pDiffusionErrors = scanline.get() + width; + memset(pDiffusionErrors, 0, sizeof(XMVECTOR)*(width + 2)); + + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_LoadScanline(scanline.get(), width, pSrc, srcImage.rowPitch, srcImage.format)) + return E_FAIL; + + _ConvertScanline(scanline.get(), width, destImage.format, srcImage.format, filter); + + if (!_StoreScanlineDither(pDest, destImage.rowPitch, destImage.format, scanline.get(), width, threshold, h, z, pDiffusionErrors)) + return E_FAIL; + + pSrc += srcImage.rowPitch; + pDest += destImage.rowPitch; + } + } + else + { + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + if (filter & TEX_FILTER_DITHER) + { + // Ordered dithering + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_LoadScanline(scanline.get(), width, pSrc, srcImage.rowPitch, srcImage.format)) + return E_FAIL; + + _ConvertScanline(scanline.get(), width, destImage.format, srcImage.format, filter); + + if (!_StoreScanlineDither(pDest, destImage.rowPitch, destImage.format, scanline.get(), width, threshold, h, z, nullptr)) + return E_FAIL; + + pSrc += srcImage.rowPitch; + pDest += destImage.rowPitch; + } + } + else + { + // No dithering + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_LoadScanline(scanline.get(), width, pSrc, srcImage.rowPitch, srcImage.format)) + return E_FAIL; + + _ConvertScanline(scanline.get(), width, destImage.format, srcImage.format, filter); + + if (!_StoreScanline(pDest, destImage.rowPitch, destImage.format, scanline.get(), width, threshold)) + return E_FAIL; + + pSrc += srcImage.rowPitch; + pDest += destImage.rowPitch; + } + } + } + + return S_OK; + } + + //------------------------------------------------------------------------------------- + DXGI_FORMAT _PlanarToSingle(_In_ DXGI_FORMAT format) + { + switch (format) + { + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_NV11: + return DXGI_FORMAT_YUY2; + + case DXGI_FORMAT_P010: + return DXGI_FORMAT_Y210; + + case DXGI_FORMAT_P016: + return DXGI_FORMAT_Y216; + + // We currently do not support conversion for Xbox One specific 16-bit depth formats + + // We can't do anything with DXGI_FORMAT_420_OPAQUE because it's an opaque blob of bits + + // We don't support conversion of JPEG Hardware decode formats + + default: + return DXGI_FORMAT_UNKNOWN; + } + } + + //------------------------------------------------------------------------------------- + // Convert the image from a planar to non-planar image + //------------------------------------------------------------------------------------- +#define CONVERT_420_TO_422( srcType, destType )\ + {\ + size_t rowPitch = srcImage.rowPitch;\ + \ + auto sourceE = reinterpret_cast( pSrc + srcImage.slicePitch );\ + auto pSrcUV = pSrc + ( srcImage.height * rowPitch );\ + \ + for( size_t y = 0; y < srcImage.height; y+= 2 )\ + {\ + auto sPtrY0 = reinterpret_cast( pSrc );\ + auto sPtrY2 = reinterpret_cast( pSrc + rowPitch );\ + auto sPtrUV = reinterpret_cast( pSrcUV );\ + \ + destType * __restrict dPtr0 = reinterpret_cast(pDest);\ + destType * __restrict dPtr1 = reinterpret_cast(pDest + destImage.rowPitch);\ + \ + for( size_t x = 0; x < srcImage.width; x+= 2 )\ + {\ + if ( (sPtrUV+1) >= sourceE ) break;\ + \ + srcType u = *(sPtrUV++);\ + srcType v = *(sPtrUV++);\ + \ + dPtr0->x = *(sPtrY0++);\ + dPtr0->y = u;\ + dPtr0->z = *(sPtrY0++);\ + dPtr0->w = v;\ + ++dPtr0;\ + \ + dPtr1->x = *(sPtrY2++);\ + dPtr1->y = u;\ + dPtr1->z = *(sPtrY2++);\ + dPtr1->w = v;\ + ++dPtr1;\ + }\ + \ + pSrc += rowPitch * 2;\ + pSrcUV += rowPitch;\ + \ + pDest += destImage.rowPitch * 2;\ + }\ + } + + HRESULT ConvertToSinglePlane_(_In_ const Image& srcImage, _In_ const Image& destImage) + { + assert(srcImage.width == destImage.width); + assert(srcImage.height == destImage.height); + + const uint8_t *pSrc = srcImage.pixels; + uint8_t *pDest = destImage.pixels; + if (!pSrc || !pDest) + return E_POINTER; + + switch (srcImage.format) + { + case DXGI_FORMAT_NV12: + assert(destImage.format == DXGI_FORMAT_YUY2); + CONVERT_420_TO_422(uint8_t, XMUBYTEN4); + return S_OK; + + case DXGI_FORMAT_P010: + assert(destImage.format == DXGI_FORMAT_Y210); + CONVERT_420_TO_422(uint16_t, XMUSHORTN4); + return S_OK; + + case DXGI_FORMAT_P016: + assert(destImage.format == DXGI_FORMAT_Y216); + CONVERT_420_TO_422(uint16_t, XMUSHORTN4); + return S_OK; + + case DXGI_FORMAT_NV11: + assert(destImage.format == DXGI_FORMAT_YUY2); + // Convert 4:1:1 to 4:2:2 + { + size_t rowPitch = srcImage.rowPitch; + + const uint8_t* sourceE = pSrc + srcImage.slicePitch; + const uint8_t* pSrcUV = pSrc + (srcImage.height * rowPitch); + + for (size_t y = 0; y < srcImage.height; ++y) + { + const uint8_t* sPtrY = pSrc; + const uint8_t* sPtrUV = pSrcUV; + + XMUBYTEN4 * __restrict dPtr = reinterpret_cast(pDest); + + for (size_t x = 0; x < srcImage.width; x += 4) + { + if ((sPtrUV + 1) >= sourceE) break; + + uint8_t u = *(sPtrUV++); + uint8_t v = *(sPtrUV++); + + dPtr->x = *(sPtrY++); + dPtr->y = u; + dPtr->z = *(sPtrY++); + dPtr->w = v; + ++dPtr; + + dPtr->x = *(sPtrY++); + dPtr->y = u; + dPtr->z = *(sPtrY++); + dPtr->w = v; + ++dPtr; + } + + pSrc += rowPitch; + pSrcUV += (rowPitch >> 1); + + pDest += destImage.rowPitch; + } + } + return S_OK; + + default: + return E_UNEXPECTED; + } + } + +#undef CONVERT_420_TO_422 +} + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Convert image +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::Convert( + const Image& srcImage, + DXGI_FORMAT format, + DWORD filter, + float threshold, + ScratchImage& image) +{ + if ((srcImage.format == format) || !IsValid(format)) + return E_INVALIDARG; + + if (!srcImage.pixels) + return E_POINTER; + + if (IsCompressed(srcImage.format) || IsCompressed(format) + || IsPlanar(srcImage.format) || IsPlanar(format) + || IsPalettized(srcImage.format) || IsPalettized(format) + || IsTypeless(srcImage.format) || IsTypeless(format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if ((srcImage.width > UINT32_MAX) || (srcImage.height > UINT32_MAX)) + return E_INVALIDARG; + + HRESULT hr = image.Initialize2D(format, srcImage.width, srcImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *rimage = image.GetImage(0, 0, 0); + if (!rimage) + { + image.Release(); + return E_POINTER; + } + + WICPixelFormatGUID pfGUID, targetGUID; + if (UseWICConversion(filter, srcImage.format, format, pfGUID, targetGUID)) + { + hr = ConvertUsingWIC(srcImage, pfGUID, targetGUID, filter, threshold, *rimage); + } + else + { + hr = ConvertCustom(srcImage, filter, *rimage, threshold, 0); + } + + if (FAILED(hr)) + { + image.Release(); + return hr; + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Convert image (complex) +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::Convert( + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + DXGI_FORMAT format, + DWORD filter, + float threshold, + ScratchImage& result) +{ + if (!srcImages || !nimages || (metadata.format == format) || !IsValid(format)) + return E_INVALIDARG; + + if (IsCompressed(metadata.format) || IsCompressed(format) + || IsPlanar(metadata.format) || IsPlanar(format) + || IsPalettized(metadata.format) || IsPalettized(format) + || IsTypeless(metadata.format) || IsTypeless(format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if ((metadata.width > UINT32_MAX) || (metadata.height > UINT32_MAX)) + return E_INVALIDARG; + + TexMetadata mdata2 = metadata; + mdata2.format = format; + HRESULT hr = result.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + if (nimages != result.GetImageCount()) + { + result.Release(); + return E_FAIL; + } + + const Image* dest = result.GetImages(); + if (!dest) + { + result.Release(); + return E_POINTER; + } + + WICPixelFormatGUID pfGUID, targetGUID; + bool usewic = !metadata.IsPMAlpha() && UseWICConversion(filter, metadata.format, format, pfGUID, targetGUID); + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + case TEX_DIMENSION_TEXTURE2D: + for (size_t index = 0; index < nimages; ++index) + { + const Image& src = srcImages[index]; + if (src.format != metadata.format) + { + result.Release(); + return E_FAIL; + } + + if ((src.width > UINT32_MAX) || (src.height > UINT32_MAX)) + { + result.Release(); + return E_FAIL; + } + + const Image& dst = dest[index]; + assert(dst.format == format); + + if (src.width != dst.width || src.height != dst.height) + { + result.Release(); + return E_FAIL; + } + + if (usewic) + { + hr = ConvertUsingWIC(src, pfGUID, targetGUID, filter, threshold, dst); + } + else + { + hr = ConvertCustom(src, filter, dst, threshold, 0); + } + + if (FAILED(hr)) + { + result.Release(); + return hr; + } + } + break; + + case TEX_DIMENSION_TEXTURE3D: + { + size_t index = 0; + size_t d = metadata.depth; + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + for (size_t slice = 0; slice < d; ++slice, ++index) + { + if (index >= nimages) + { + result.Release(); + return E_FAIL; + } + + const Image& src = srcImages[index]; + if (src.format != metadata.format) + { + result.Release(); + return E_FAIL; + } + + if ((src.width > UINT32_MAX) || (src.height > UINT32_MAX)) + { + result.Release(); + return E_FAIL; + } + + const Image& dst = dest[index]; + assert(dst.format == format); + + if (src.width != dst.width || src.height != dst.height) + { + result.Release(); + return E_FAIL; + } + + if (usewic) + { + hr = ConvertUsingWIC(src, pfGUID, targetGUID, filter, threshold, dst); + } + else + { + hr = ConvertCustom(src, filter, dst, threshold, slice); + } + + if (FAILED(hr)) + { + result.Release(); + return hr; + } + } + + if (d > 1) + d >>= 1; + } + } + break; + + default: + result.Release(); + return E_FAIL; + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Convert image from planar to single plane (image) +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::ConvertToSinglePlane(const Image& srcImage, ScratchImage& image) +{ + if (!IsPlanar(srcImage.format)) + return E_INVALIDARG; + + if (!srcImage.pixels) + return E_POINTER; + + DXGI_FORMAT format = _PlanarToSingle(srcImage.format); + if (format == DXGI_FORMAT_UNKNOWN) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if ((srcImage.width > UINT32_MAX) || (srcImage.height > UINT32_MAX)) + return E_INVALIDARG; + + HRESULT hr = image.Initialize2D(format, srcImage.width, srcImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *rimage = image.GetImage(0, 0, 0); + if (!rimage) + { + image.Release(); + return E_POINTER; + } + + hr = ConvertToSinglePlane_(srcImage, *rimage); + if (FAILED(hr)) + { + image.Release(); + return hr; + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Convert image from planar to single plane (complex) +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::ConvertToSinglePlane( + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + ScratchImage& result) +{ + if (!srcImages || !nimages) + return E_INVALIDARG; + + if (metadata.IsVolumemap()) + { + // Direct3D does not support any planar formats for Texture3D + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + DXGI_FORMAT format = _PlanarToSingle(metadata.format); + if (format == DXGI_FORMAT_UNKNOWN) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if ((metadata.width > UINT32_MAX) || (metadata.height > UINT32_MAX)) + return E_INVALIDARG; + + TexMetadata mdata2 = metadata; + mdata2.format = format; + HRESULT hr = result.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + if (nimages != result.GetImageCount()) + { + result.Release(); + return E_FAIL; + } + + const Image* dest = result.GetImages(); + if (!dest) + { + result.Release(); + return E_POINTER; + } + + for (size_t index = 0; index < nimages; ++index) + { + const Image& src = srcImages[index]; + if (src.format != metadata.format) + { + result.Release(); + return E_FAIL; + } + + if ((src.width > UINT32_MAX) || (src.height > UINT32_MAX)) + return E_FAIL; + + const Image& dst = dest[index]; + assert(dst.format == format); + + if (src.width != dst.width || src.height != dst.height) + { + result.Release(); + return E_FAIL; + } + + hr = ConvertToSinglePlane_(src, dst); + if (FAILED(hr)) + { + result.Release(); + return hr; + } + } + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexD3D11.cpp b/deps/DirectXTex/DirectXTex/DirectXTexD3D11.cpp new file mode 100644 index 0000000..29f2dae --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexD3D11.cpp @@ -0,0 +1,968 @@ +//------------------------------------------------------------------------------------- +// DirectXTexD3D11.cpp +// +// DirectX Texture Library - Direct3D 11 helpers +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +#if !defined(_XBOX_ONE) || !defined(_TITLE) +#include +#endif + +#ifndef IID_GRAPHICS_PPV_ARGS +#define IID_GRAPHICS_PPV_ARGS(x) IID_PPV_ARGS(x) +#endif + +using namespace DirectX; +using Microsoft::WRL::ComPtr; + +static_assert(static_cast(TEX_DIMENSION_TEXTURE1D) == static_cast(D3D11_RESOURCE_DIMENSION_TEXTURE1D), "header enum mismatch"); +static_assert(static_cast(TEX_DIMENSION_TEXTURE2D) == static_cast(D3D11_RESOURCE_DIMENSION_TEXTURE2D), "header enum mismatch"); +static_assert(static_cast(TEX_DIMENSION_TEXTURE3D) == static_cast(D3D11_RESOURCE_DIMENSION_TEXTURE3D), "header enum mismatch"); + +namespace +{ + HRESULT Capture( + _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + const TexMetadata& metadata, + const ScratchImage& result) + { + if (!pContext || !pSource || !result.GetPixels()) + return E_POINTER; + +#if defined(_XBOX_ONE) && defined(_TITLE) + + ComPtr d3dDevice; + pContext->GetDevice(d3dDevice.GetAddressOf()); + + if (d3dDevice->GetCreationFlags() & D3D11_CREATE_DEVICE_IMMEDIATE_CONTEXT_FAST_SEMANTICS) + { + ComPtr d3dDeviceX; + HRESULT hr = d3dDevice.As(&d3dDeviceX); + if (FAILED(hr)) + return hr; + + ComPtr d3dContextX; + hr = pContext->QueryInterface(IID_GRAPHICS_PPV_ARGS(d3dContextX.GetAddressOf())); + if (FAILED(hr)) + return hr; + + UINT64 copyFence = d3dContextX->InsertFence(0); + + while (d3dDeviceX->IsFencePending(copyFence)) + { + SwitchToThread(); + } + } + +#endif + + if (metadata.IsVolumemap()) + { + //--- Volume texture ---------------------------------------------------------- + assert(metadata.arraySize == 1); + + size_t height = metadata.height; + size_t depth = metadata.depth; + + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + UINT dindex = D3D11CalcSubresource(static_cast(level), 0, static_cast(metadata.mipLevels)); + + D3D11_MAPPED_SUBRESOURCE mapped; + HRESULT hr = pContext->Map(pSource, dindex, D3D11_MAP_READ, 0, &mapped); + if (FAILED(hr)) + return hr; + + auto pslice = reinterpret_cast(mapped.pData); + if (!pslice) + { + pContext->Unmap(pSource, dindex); + return E_POINTER; + } + + size_t lines = ComputeScanlines(metadata.format, height); + if (!lines) + { + pContext->Unmap(pSource, dindex); + return E_UNEXPECTED; + } + + for (size_t slice = 0; slice < depth; ++slice) + { + const Image* img = result.GetImage(level, 0, slice); + if (!img) + { + pContext->Unmap(pSource, dindex); + return E_FAIL; + } + + if (!img->pixels) + { + pContext->Unmap(pSource, dindex); + return E_POINTER; + } + + const uint8_t* sptr = pslice; + uint8_t* dptr = img->pixels; + for (size_t h = 0; h < lines; ++h) + { + size_t msize = std::min(img->rowPitch, mapped.RowPitch); + memcpy_s(dptr, img->rowPitch, sptr, msize); + sptr += mapped.RowPitch; + dptr += img->rowPitch; + } + + pslice += mapped.DepthPitch; + } + + pContext->Unmap(pSource, dindex); + + if (height > 1) + height >>= 1; + if (depth > 1) + depth >>= 1; + } + } + else + { + //--- 1D or 2D texture -------------------------------------------------------- + assert(metadata.depth == 1); + + for (size_t item = 0; item < metadata.arraySize; ++item) + { + size_t height = metadata.height; + + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + UINT dindex = D3D11CalcSubresource(static_cast(level), static_cast(item), static_cast(metadata.mipLevels)); + + D3D11_MAPPED_SUBRESOURCE mapped; + HRESULT hr = pContext->Map(pSource, dindex, D3D11_MAP_READ, 0, &mapped); + if (FAILED(hr)) + return hr; + + const Image* img = result.GetImage(level, item, 0); + if (!img) + { + pContext->Unmap(pSource, dindex); + return E_FAIL; + } + + if (!img->pixels) + { + pContext->Unmap(pSource, dindex); + return E_POINTER; + } + + size_t lines = ComputeScanlines(metadata.format, height); + if (!lines) + { + pContext->Unmap(pSource, dindex); + return E_UNEXPECTED; + } + + auto sptr = reinterpret_cast(mapped.pData); + uint8_t* dptr = img->pixels; + for (size_t h = 0; h < lines; ++h) + { + size_t msize = std::min(img->rowPitch, mapped.RowPitch); + memcpy_s(dptr, img->rowPitch, sptr, msize); + sptr += mapped.RowPitch; + dptr += img->rowPitch; + } + + pContext->Unmap(pSource, dindex); + + if (height > 1) + height >>= 1; + } + } + } + + return S_OK; + } +} + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Determine if given texture metadata is supported on the given device +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::IsSupportedTexture( + ID3D11Device* pDevice, + const TexMetadata& metadata) +{ + if (!pDevice) + return false; + + D3D_FEATURE_LEVEL fl = pDevice->GetFeatureLevel(); + + // Validate format + DXGI_FORMAT fmt = metadata.format; + + if (!IsValid(fmt)) + return false; + + switch (fmt) + { + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + if (fl < D3D_FEATURE_LEVEL_10_0) + return false; + break; + + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + if (fl < D3D_FEATURE_LEVEL_11_0) + return false; + break; + + default: + break; + } + + // Validate miplevel count + if (metadata.mipLevels > D3D11_REQ_MIP_LEVELS) + return false; + + // Validate array size, dimension, and width/height + size_t arraySize = metadata.arraySize; + size_t iWidth = metadata.width; + size_t iHeight = metadata.height; + size_t iDepth = metadata.depth; + + // Most cases are known apriori based on feature level, but we use this for robustness to handle the few optional cases + UINT formatSupport = 0; + HRESULT hr = pDevice->CheckFormatSupport(fmt, &formatSupport); + if (FAILED(hr)) + { + formatSupport = 0; + } + + if (metadata.mipLevels > 1 && !(formatSupport & D3D11_FORMAT_SUPPORT_MIP)) + { + return false; + } + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + if (!(formatSupport & D3D11_FORMAT_SUPPORT_TEXTURE1D)) + return false; + + if ((arraySize > D3D11_REQ_TEXTURE1D_ARRAY_AXIS_DIMENSION) + || (iWidth > D3D11_REQ_TEXTURE1D_U_DIMENSION)) + return false; + + if (fl < D3D_FEATURE_LEVEL_11_0) + { + if ((arraySize > D3D10_REQ_TEXTURE1D_ARRAY_AXIS_DIMENSION) + || (iWidth > D3D10_REQ_TEXTURE1D_U_DIMENSION)) + return false; + + if (fl < D3D_FEATURE_LEVEL_10_0) + { + if ((arraySize > 1) || (iWidth > D3D_FL9_3_REQ_TEXTURE1D_U_DIMENSION)) + return false; + + if ((fl < D3D_FEATURE_LEVEL_9_3) && (iWidth > D3D_FL9_1_REQ_TEXTURE1D_U_DIMENSION)) + return false; + } + } + break; + + case TEX_DIMENSION_TEXTURE2D: + if (metadata.IsCubemap()) + { + if (!(formatSupport & D3D11_FORMAT_SUPPORT_TEXTURECUBE)) + return false; + + if ((arraySize > D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) + || (iWidth > D3D11_REQ_TEXTURECUBE_DIMENSION) + || (iHeight > D3D11_REQ_TEXTURECUBE_DIMENSION)) + return false; + + if (fl < D3D_FEATURE_LEVEL_11_0) + { + if ((arraySize > D3D10_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) + || (iWidth > D3D10_REQ_TEXTURECUBE_DIMENSION) + || (iHeight > D3D10_REQ_TEXTURECUBE_DIMENSION)) + return false; + + if ((fl < D3D_FEATURE_LEVEL_10_1) && (arraySize != 6)) + return false; + + if (fl < D3D_FEATURE_LEVEL_10_0) + { + if ((iWidth > D3D_FL9_3_REQ_TEXTURECUBE_DIMENSION) + || (iHeight > D3D_FL9_3_REQ_TEXTURECUBE_DIMENSION)) + return false; + + if ((fl < D3D_FEATURE_LEVEL_9_3) + && ((iWidth > D3D_FL9_1_REQ_TEXTURECUBE_DIMENSION) + || (iHeight > D3D_FL9_1_REQ_TEXTURECUBE_DIMENSION))) + return false; + } + } + } + else // Not a cube map + { + if (!(formatSupport & D3D11_FORMAT_SUPPORT_TEXTURE2D)) + return false; + + if ((arraySize > D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) + || (iWidth > D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION) + || (iHeight > D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION)) + return false; + + if (fl < D3D_FEATURE_LEVEL_11_0) + { + if ((arraySize > D3D10_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) + || (iWidth > D3D10_REQ_TEXTURE2D_U_OR_V_DIMENSION) + || (iHeight > D3D10_REQ_TEXTURE2D_U_OR_V_DIMENSION)) + return false; + + if (fl < D3D_FEATURE_LEVEL_10_0) + { + if ((arraySize > 1) + || (iWidth > D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION) + || (iHeight > D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION)) + return false; + + if ((fl < D3D_FEATURE_LEVEL_9_3) + && ((iWidth > D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION) + || (iHeight > D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION))) + return false; + } + } + } + break; + + case TEX_DIMENSION_TEXTURE3D: + if (!(formatSupport & D3D11_FORMAT_SUPPORT_TEXTURE3D)) + return false; + + if ((arraySize > 1) + || (iWidth > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) + || (iHeight > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) + || (iDepth > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION)) + return false; + + if (fl < D3D_FEATURE_LEVEL_11_0) + { + if ((iWidth > D3D10_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) + || (iHeight > D3D10_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) + || (iDepth > D3D10_REQ_TEXTURE3D_U_V_OR_W_DIMENSION)) + return false; + + if (fl < D3D_FEATURE_LEVEL_10_0) + { + if ((iWidth > D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) + || (iHeight > D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) + || (iDepth > D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION)) + return false; + } + } + break; + + default: + // Not a supported dimension + return false; + } + + return true; +} + + +//------------------------------------------------------------------------------------- +// Create a texture resource +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateTexture( + ID3D11Device* pDevice, + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + ID3D11Resource** ppResource) +{ + return CreateTextureEx( + pDevice, srcImages, nimages, metadata, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, false, + ppResource); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateTextureEx( + ID3D11Device* pDevice, + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** ppResource) +{ + if (!pDevice || !srcImages || !nimages || !ppResource) + return E_INVALIDARG; + + *ppResource = nullptr; + + if (!metadata.mipLevels || !metadata.arraySize) + return E_INVALIDARG; + + if ((metadata.width > UINT32_MAX) || (metadata.height > UINT32_MAX) + || (metadata.mipLevels > UINT16_MAX) || (metadata.arraySize > UINT16_MAX)) + return E_INVALIDARG; + + std::unique_ptr initData(new (std::nothrow) D3D11_SUBRESOURCE_DATA[metadata.mipLevels * metadata.arraySize]); + if (!initData) + return E_OUTOFMEMORY; + + // Fill out subresource array + if (metadata.IsVolumemap()) + { + //--- Volume case ------------------------------------------------------------- + if (!metadata.depth) + return E_INVALIDARG; + + if (metadata.depth > UINT16_MAX) + return E_INVALIDARG; + + if (metadata.arraySize > 1) + // Direct3D 11 doesn't support arrays of 3D textures + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + size_t depth = metadata.depth; + + size_t idx = 0; + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + size_t index = metadata.ComputeIndex(level, 0, 0); + if (index >= nimages) + return E_FAIL; + + const Image& img = srcImages[index]; + + if (img.format != metadata.format) + return E_FAIL; + + if (!img.pixels) + return E_POINTER; + + // Verify pixels in image 1 .. (depth-1) are exactly image->slicePitch apart + // For 3D textures, this relies on all slices of the same miplevel being continous in memory + // (this is how ScratchImage lays them out), which is why we just give the 0th slice to Direct3D 11 + const uint8_t* pSlice = img.pixels + img.slicePitch; + for (size_t slice = 1; slice < depth; ++slice) + { + size_t tindex = metadata.ComputeIndex(level, 0, slice); + if (tindex >= nimages) + return E_FAIL; + + const Image& timg = srcImages[tindex]; + + if (!timg.pixels) + return E_POINTER; + + if (timg.pixels != pSlice + || timg.format != metadata.format + || timg.rowPitch != img.rowPitch + || timg.slicePitch != img.slicePitch) + return E_FAIL; + + pSlice = timg.pixels + img.slicePitch; + } + + assert(idx < (metadata.mipLevels * metadata.arraySize)); + + initData[idx].pSysMem = img.pixels; + initData[idx].SysMemPitch = static_cast(img.rowPitch); + initData[idx].SysMemSlicePitch = static_cast(img.slicePitch); + ++idx; + + if (depth > 1) + depth >>= 1; + } + } + else + { + //--- 1D or 2D texture case --------------------------------------------------- + size_t idx = 0; + for (size_t item = 0; item < metadata.arraySize; ++item) + { + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + size_t index = metadata.ComputeIndex(level, item, 0); + if (index >= nimages) + return E_FAIL; + + const Image& img = srcImages[index]; + + if (img.format != metadata.format) + return E_FAIL; + + if (!img.pixels) + return E_POINTER; + + assert(idx < (metadata.mipLevels * metadata.arraySize)); + + initData[idx].pSysMem = img.pixels; + initData[idx].SysMemPitch = static_cast(img.rowPitch); + initData[idx].SysMemSlicePitch = static_cast(img.slicePitch); + ++idx; + } + } + } + + // Create texture using static initialization data + HRESULT hr = E_FAIL; + + DXGI_FORMAT tformat = (forceSRGB) ? MakeSRGB(metadata.format) : metadata.format; + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + { + D3D11_TEXTURE1D_DESC desc = {}; + desc.Width = static_cast(metadata.width); + desc.MipLevels = static_cast(metadata.mipLevels); + desc.ArraySize = static_cast(metadata.arraySize); + desc.Format = tformat; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + desc.MiscFlags = miscFlags & ~D3D11_RESOURCE_MISC_TEXTURECUBE; + + hr = pDevice->CreateTexture1D(&desc, initData.get(), reinterpret_cast(ppResource)); + } + break; + + case TEX_DIMENSION_TEXTURE2D: + { + D3D11_TEXTURE2D_DESC desc = {}; + desc.Width = static_cast(metadata.width); + desc.Height = static_cast(metadata.height); + desc.MipLevels = static_cast(metadata.mipLevels); + desc.ArraySize = static_cast(metadata.arraySize); + desc.Format = tformat; + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + if (metadata.IsCubemap()) + desc.MiscFlags = miscFlags | D3D11_RESOURCE_MISC_TEXTURECUBE; + else + desc.MiscFlags = miscFlags & ~D3D11_RESOURCE_MISC_TEXTURECUBE; + + hr = pDevice->CreateTexture2D(&desc, initData.get(), reinterpret_cast(ppResource)); + } + break; + + case TEX_DIMENSION_TEXTURE3D: + { + D3D11_TEXTURE3D_DESC desc = {}; + desc.Width = static_cast(metadata.width); + desc.Height = static_cast(metadata.height); + desc.Depth = static_cast(metadata.depth); + desc.MipLevels = static_cast(metadata.mipLevels); + desc.Format = tformat; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + desc.MiscFlags = miscFlags & ~D3D11_RESOURCE_MISC_TEXTURECUBE; + + hr = pDevice->CreateTexture3D(&desc, initData.get(), reinterpret_cast(ppResource)); + } + break; + } + + return hr; +} + + +//------------------------------------------------------------------------------------- +// Create a shader resource view and associated texture +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateShaderResourceView( + ID3D11Device* pDevice, + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + ID3D11ShaderResourceView** ppSRV) +{ + return CreateShaderResourceViewEx( + pDevice, srcImages, nimages, metadata, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, false, + ppSRV); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateShaderResourceViewEx( + ID3D11Device* pDevice, + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11ShaderResourceView** ppSRV) +{ + if (!ppSRV) + return E_INVALIDARG; + + *ppSRV = nullptr; + + ComPtr resource; + HRESULT hr = CreateTextureEx(pDevice, srcImages, nimages, metadata, + usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + resource.GetAddressOf()); + if (FAILED(hr)) + return hr; + + assert(resource); + + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc = {}; + if (forceSRGB) + SRVDesc.Format = MakeSRGB(metadata.format); + else + SRVDesc.Format = metadata.format; + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + if (metadata.arraySize > 1) + { + SRVDesc.ViewDimension = D3D_SRV_DIMENSION_TEXTURE1DARRAY; + SRVDesc.Texture1DArray.MipLevels = static_cast(metadata.mipLevels); + SRVDesc.Texture1DArray.ArraySize = static_cast(metadata.arraySize); + } + else + { + SRVDesc.ViewDimension = D3D_SRV_DIMENSION_TEXTURE1D; + SRVDesc.Texture1D.MipLevels = static_cast(metadata.mipLevels); + } + break; + + case TEX_DIMENSION_TEXTURE2D: + if (metadata.IsCubemap()) + { + if (metadata.arraySize > 6) + { + assert((metadata.arraySize % 6) == 0); + SRVDesc.ViewDimension = D3D_SRV_DIMENSION_TEXTURECUBEARRAY; + SRVDesc.TextureCubeArray.MipLevels = static_cast(metadata.mipLevels); + SRVDesc.TextureCubeArray.NumCubes = static_cast(metadata.arraySize / 6); + } + else + { + SRVDesc.ViewDimension = D3D_SRV_DIMENSION_TEXTURECUBE; + SRVDesc.TextureCube.MipLevels = static_cast(metadata.mipLevels); + } + } + else if (metadata.arraySize > 1) + { + SRVDesc.ViewDimension = D3D_SRV_DIMENSION_TEXTURE2DARRAY; + SRVDesc.Texture2DArray.MipLevels = static_cast(metadata.mipLevels); + SRVDesc.Texture2DArray.ArraySize = static_cast(metadata.arraySize); + } + else + { + SRVDesc.ViewDimension = D3D_SRV_DIMENSION_TEXTURE2D; + SRVDesc.Texture2D.MipLevels = static_cast(metadata.mipLevels); + } + break; + + case TEX_DIMENSION_TEXTURE3D: + assert(metadata.arraySize == 1); + SRVDesc.ViewDimension = D3D_SRV_DIMENSION_TEXTURE3D; + SRVDesc.Texture3D.MipLevels = static_cast(metadata.mipLevels); + break; + + default: + return E_FAIL; + } + + hr = pDevice->CreateShaderResourceView(resource.Get(), &SRVDesc, ppSRV); + if (FAILED(hr)) + return hr; + + assert(*ppSRV); + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Save a texture resource +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CaptureTexture( + ID3D11Device* pDevice, + ID3D11DeviceContext* pContext, + ID3D11Resource* pSource, + ScratchImage& result) +{ + if (!pDevice || !pContext || !pSource) + return E_INVALIDARG; + + D3D11_RESOURCE_DIMENSION resType = D3D11_RESOURCE_DIMENSION_UNKNOWN; + pSource->GetType(&resType); + + HRESULT hr; + + switch (resType) + { + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + { + ComPtr pTexture; + hr = pSource->QueryInterface(IID_GRAPHICS_PPV_ARGS(pTexture.GetAddressOf())); + if (FAILED(hr)) + break; + + assert(pTexture); + + D3D11_TEXTURE1D_DESC desc; + pTexture->GetDesc(&desc); + + ComPtr pStaging; + if ((desc.Usage == D3D11_USAGE_STAGING) && (desc.CPUAccessFlags & D3D11_CPU_ACCESS_READ)) + { + // Handle case where the source is already a staging texture we can use directly + pStaging = pTexture; + } + else + { + desc.BindFlags = 0; + desc.MiscFlags = 0; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.Usage = D3D11_USAGE_STAGING; + + hr = pDevice->CreateTexture1D(&desc, 0, pStaging.GetAddressOf()); + if (FAILED(hr)) + break; + + assert(pStaging); + + pContext->CopyResource(pStaging.Get(), pSource); + } + + TexMetadata mdata; + mdata.width = desc.Width; + mdata.height = mdata.depth = 1; + mdata.arraySize = desc.ArraySize; + mdata.mipLevels = desc.MipLevels; + mdata.miscFlags = 0; + mdata.miscFlags2 = 0; + mdata.format = desc.Format; + mdata.dimension = TEX_DIMENSION_TEXTURE1D; + + hr = result.Initialize(mdata); + if (FAILED(hr)) + break; + + hr = Capture(pContext, pStaging.Get(), mdata, result); + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + { + ComPtr pTexture; + hr = pSource->QueryInterface(IID_GRAPHICS_PPV_ARGS(pTexture.GetAddressOf())); + if (FAILED(hr)) + break; + + assert(pTexture); + + D3D11_TEXTURE2D_DESC desc; + pTexture->GetDesc(&desc); + + ComPtr pStaging; + if (desc.SampleDesc.Count > 1) + { + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + + ComPtr pTemp; + hr = pDevice->CreateTexture2D(&desc, 0, pTemp.GetAddressOf()); + if (FAILED(hr)) + break; + + assert(pTemp); + + DXGI_FORMAT fmt = desc.Format; + if (IsTypeless(fmt)) + { + // Assume a UNORM if it exists otherwise use FLOAT + fmt = MakeTypelessUNORM(fmt); + fmt = MakeTypelessFLOAT(fmt); + } + + UINT support = 0; + hr = pDevice->CheckFormatSupport(fmt, &support); + if (FAILED(hr)) + break; + + if (!(support & D3D11_FORMAT_SUPPORT_MULTISAMPLE_RESOLVE)) + { + hr = E_FAIL; + break; + } + + for (UINT item = 0; item < desc.ArraySize; ++item) + { + for (UINT level = 0; level < desc.MipLevels; ++level) + { + UINT index = D3D11CalcSubresource(level, item, desc.MipLevels); + pContext->ResolveSubresource(pTemp.Get(), index, pSource, index, fmt); + } + } + + desc.BindFlags = 0; + desc.MiscFlags &= D3D11_RESOURCE_MISC_TEXTURECUBE; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.Usage = D3D11_USAGE_STAGING; + + hr = pDevice->CreateTexture2D(&desc, 0, pStaging.GetAddressOf()); + if (FAILED(hr)) + break; + + assert(pStaging); + + pContext->CopyResource(pStaging.Get(), pTemp.Get()); + } + else if ((desc.Usage == D3D11_USAGE_STAGING) && (desc.CPUAccessFlags & D3D11_CPU_ACCESS_READ)) + { + // Handle case where the source is already a staging texture we can use directly + pStaging = pTexture; + } + else + { + desc.BindFlags = 0; + desc.MiscFlags &= D3D11_RESOURCE_MISC_TEXTURECUBE; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.Usage = D3D11_USAGE_STAGING; + + hr = pDevice->CreateTexture2D(&desc, 0, &pStaging); + if (FAILED(hr)) + break; + + assert(pStaging); + + pContext->CopyResource(pStaging.Get(), pSource); + } + + TexMetadata mdata; + mdata.width = desc.Width; + mdata.height = desc.Height; + mdata.depth = 1; + mdata.arraySize = desc.ArraySize; + mdata.mipLevels = desc.MipLevels; + mdata.miscFlags = (desc.MiscFlags & D3D11_RESOURCE_MISC_TEXTURECUBE) ? TEX_MISC_TEXTURECUBE : 0; + mdata.miscFlags2 = 0; + mdata.format = desc.Format; + mdata.dimension = TEX_DIMENSION_TEXTURE2D; + + hr = result.Initialize(mdata); + if (FAILED(hr)) + break; + + hr = Capture(pContext, pStaging.Get(), mdata, result); + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + { + ComPtr pTexture; + hr = pSource->QueryInterface(IID_GRAPHICS_PPV_ARGS(pTexture.GetAddressOf())); + if (FAILED(hr)) + break; + + assert(pTexture); + + D3D11_TEXTURE3D_DESC desc; + pTexture->GetDesc(&desc); + + ComPtr pStaging; + if ((desc.Usage == D3D11_USAGE_STAGING) && (desc.CPUAccessFlags & D3D11_CPU_ACCESS_READ)) + { + // Handle case where the source is already a staging texture we can use directly + pStaging = pTexture; + } + else + { + desc.BindFlags = 0; + desc.MiscFlags = 0; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.Usage = D3D11_USAGE_STAGING; + + hr = pDevice->CreateTexture3D(&desc, 0, pStaging.GetAddressOf()); + if (FAILED(hr)) + break; + + assert(pStaging); + + pContext->CopyResource(pStaging.Get(), pSource); + } + + TexMetadata mdata; + mdata.width = desc.Width; + mdata.height = desc.Height; + mdata.depth = desc.Depth; + mdata.arraySize = 1; + mdata.mipLevels = desc.MipLevels; + mdata.miscFlags = 0; + mdata.miscFlags2 = 0; + mdata.format = desc.Format; + mdata.dimension = TEX_DIMENSION_TEXTURE3D; + + hr = result.Initialize(mdata); + if (FAILED(hr)) + break; + + hr = Capture(pContext, pStaging.Get(), mdata, result); + } + break; + + default: + hr = E_FAIL; + break; + } + + if (FAILED(hr)) + { + result.Release(); + return hr; + } + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexD3D12.cpp b/deps/DirectXTex/DirectXTex/DirectXTexD3D12.cpp new file mode 100644 index 0000000..768da0d --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexD3D12.cpp @@ -0,0 +1,810 @@ +//------------------------------------------------------------------------------------- +// DirectXTexD3D12.cpp +// +// DirectX Texture Library - Direct3D 12 helpers +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +#if defined(_XBOX_ONE) && defined(_TITLE) +#include "d3dx12_x.h" +#else +#include "d3dx12.h" +#endif + +#ifndef IID_GRAPHICS_PPV_ARGS +#define IID_GRAPHICS_PPV_ARGS(x) IID_PPV_ARGS(x) +#endif + +using namespace DirectX; +using Microsoft::WRL::ComPtr; + +static_assert(static_cast(TEX_DIMENSION_TEXTURE1D) == static_cast(D3D12_RESOURCE_DIMENSION_TEXTURE1D), "header enum mismatch"); +static_assert(static_cast(TEX_DIMENSION_TEXTURE2D) == static_cast(D3D12_RESOURCE_DIMENSION_TEXTURE2D), "header enum mismatch"); +static_assert(static_cast(TEX_DIMENSION_TEXTURE3D) == static_cast(D3D12_RESOURCE_DIMENSION_TEXTURE3D), "header enum mismatch"); + +namespace +{ + template void AdjustPlaneResource( + _In_ DXGI_FORMAT fmt, + _In_ size_t height, + _In_ size_t slicePlane, + _Inout_ T& res) + { + switch (static_cast(fmt)) + { + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + case XBOX_DXGI_FORMAT_D16_UNORM_S8_UINT: + case XBOX_DXGI_FORMAT_R16_UNORM_X8_TYPELESS: + case XBOX_DXGI_FORMAT_X16_TYPELESS_G8_UINT: + if (!slicePlane) + { + // Plane 0 + res.SlicePitch = res.RowPitch * height; + } + else + { + // Plane 1 + res.pData = (uint8_t*)(res.pData) + res.RowPitch * height; + res.SlicePitch = res.RowPitch * ((height + 1) >> 1); + } + break; + + case DXGI_FORMAT_NV11: + if (!slicePlane) + { + // Plane 0 + res.SlicePitch = res.RowPitch * height; + } + else + { + // Plane 1 + res.pData = (uint8_t*)(res.pData) + res.RowPitch * height; + res.RowPitch = (res.RowPitch >> 1); + res.SlicePitch = res.RowPitch * height; + } + break; + } + } + + + //-------------------------------------------------------------------------------------- + inline void TransitionResource( + _In_ ID3D12GraphicsCommandList* commandList, + _In_ ID3D12Resource* resource, + _In_ D3D12_RESOURCE_STATES stateBefore, + _In_ D3D12_RESOURCE_STATES stateAfter) + { + assert(commandList != 0); + assert(resource != 0); + + if (stateBefore == stateAfter) + return; + + D3D12_RESOURCE_BARRIER desc = {}; + desc.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; + desc.Transition.pResource = resource; + desc.Transition.Subresource = D3D12_RESOURCE_BARRIER_ALL_SUBRESOURCES; + desc.Transition.StateBefore = stateBefore; + desc.Transition.StateAfter = stateAfter; + + commandList->ResourceBarrier(1, &desc); + } + + + //-------------------------------------------------------------------------------------- + HRESULT Capture(_In_ ID3D12Device* device, + _In_ ID3D12CommandQueue* pCommandQ, + _In_ ID3D12Resource* pSource, + const D3D12_RESOURCE_DESC& desc, + ComPtr& pStaging, + std::unique_ptr& layoutBuff, + UINT& numberOfPlanes, + UINT& numberOfResources, + D3D12_RESOURCE_STATES beforeState, + D3D12_RESOURCE_STATES afterState) + { + if (!pCommandQ || !pSource) + return E_INVALIDARG; + + numberOfPlanes = D3D12GetFormatPlaneCount(device, desc.Format); + if (!numberOfPlanes) + return E_INVALIDARG; + + if ((numberOfPlanes > 1) && IsDepthStencil(desc.Format)) + { + // DirectX 12 uses planes for stencil, DirectX 11 does not + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + D3D12_HEAP_PROPERTIES sourceHeapProperties; + D3D12_HEAP_FLAGS sourceHeapFlags; + HRESULT hr = pSource->GetHeapProperties(&sourceHeapProperties, &sourceHeapFlags); + if (FAILED(hr)) + return hr; + + numberOfResources = (desc.Dimension == D3D12_RESOURCE_DIMENSION_TEXTURE3D) + ? 1 : desc.DepthOrArraySize; + numberOfResources *= desc.MipLevels; + numberOfResources *= numberOfPlanes; + + if (numberOfResources > D3D12_REQ_SUBRESOURCES) + return E_UNEXPECTED; + + size_t memAlloc = (sizeof(D3D12_PLACED_SUBRESOURCE_FOOTPRINT) + sizeof(UINT) + sizeof(UINT64)) * numberOfResources; + if (memAlloc > SIZE_MAX) + return E_UNEXPECTED; + + layoutBuff.reset(new uint8_t[memAlloc]); + + auto pLayout = reinterpret_cast(layoutBuff.get()); + auto pRowSizesInBytes = reinterpret_cast(pLayout + numberOfResources); + auto pNumRows = reinterpret_cast(pRowSizesInBytes + numberOfResources); + + UINT64 totalResourceSize = 0; + device->GetCopyableFootprints(&desc, 0, numberOfResources, 0, + pLayout, pNumRows, pRowSizesInBytes, &totalResourceSize); + + if (sourceHeapProperties.Type == D3D12_HEAP_TYPE_READBACK) + { + // Handle case where the source is already a staging texture we can use directly + pStaging = pSource; + return S_OK; + } + + // Create a command allocator + ComPtr commandAlloc; + hr = device->CreateCommandAllocator(D3D12_COMMAND_LIST_TYPE_DIRECT, IID_GRAPHICS_PPV_ARGS(commandAlloc.GetAddressOf())); + if (FAILED(hr)) + return hr; + + // Spin up a new command list + ComPtr commandList; + hr = device->CreateCommandList(0, D3D12_COMMAND_LIST_TYPE_DIRECT, commandAlloc.Get(), nullptr, IID_GRAPHICS_PPV_ARGS(commandList.GetAddressOf())); + if (FAILED(hr)) + return hr; + + // Create a fence + ComPtr fence; + hr = device->CreateFence(0, D3D12_FENCE_FLAG_NONE, IID_GRAPHICS_PPV_ARGS(fence.GetAddressOf())); + if (FAILED(hr)) + return hr; + + CD3DX12_HEAP_PROPERTIES defaultHeapProperties(D3D12_HEAP_TYPE_DEFAULT); + CD3DX12_HEAP_PROPERTIES readBackHeapProperties(D3D12_HEAP_TYPE_READBACK); + + // Readback resources must be buffers + D3D12_RESOURCE_DESC bufferDesc = {}; + bufferDesc.Alignment = desc.Alignment; + bufferDesc.DepthOrArraySize = 1; + bufferDesc.Dimension = D3D12_RESOURCE_DIMENSION_BUFFER; + bufferDesc.Flags = D3D12_RESOURCE_FLAG_NONE; + bufferDesc.Format = DXGI_FORMAT_UNKNOWN; + bufferDesc.Height = 1; + bufferDesc.Width = totalResourceSize; + bufferDesc.Layout = D3D12_TEXTURE_LAYOUT_ROW_MAJOR; + bufferDesc.MipLevels = 1; + bufferDesc.SampleDesc.Count = 1; + bufferDesc.SampleDesc.Quality = 0; + + ComPtr copySource(pSource); + if (desc.SampleDesc.Count > 1) + { + // MSAA content must be resolved before being copied to a staging texture + auto descCopy = desc; + descCopy.SampleDesc.Count = 1; + descCopy.SampleDesc.Quality = 0; + + ComPtr pTemp; + hr = device->CreateCommittedResource( + &defaultHeapProperties, + D3D12_HEAP_FLAG_NONE, + &descCopy, + D3D12_RESOURCE_STATE_COPY_DEST, + nullptr, + IID_GRAPHICS_PPV_ARGS(pTemp.GetAddressOf())); + if (FAILED(hr)) + return hr; + + assert(pTemp); + + DXGI_FORMAT fmt = desc.Format; + if (IsTypeless(fmt)) + { + // Assume a UNORM if it exists otherwise use FLOAT + fmt = MakeTypelessUNORM(fmt); + fmt = MakeTypelessFLOAT(fmt); + } + + D3D12_FEATURE_DATA_FORMAT_SUPPORT formatInfo = { fmt }; + hr = device->CheckFeatureSupport(D3D12_FEATURE_FORMAT_SUPPORT, &formatInfo, sizeof(formatInfo)); + if (FAILED(hr)) + return hr; + + if (!(formatInfo.Support1 & D3D12_FORMAT_SUPPORT1_TEXTURE2D)) + return E_FAIL; + + for (UINT plane = 0; plane < numberOfPlanes; ++plane) + { + for (UINT item = 0; item < desc.DepthOrArraySize; ++item) + { + for (UINT level = 0; level < desc.MipLevels; ++level) + { + UINT index = D3D12CalcSubresource(level, item, plane, desc.MipLevels, desc.DepthOrArraySize); + commandList->ResolveSubresource(pTemp.Get(), index, pSource, index, fmt); + } + } + } + + copySource = pTemp; + } + + // Create a staging texture + hr = device->CreateCommittedResource( + &readBackHeapProperties, + D3D12_HEAP_FLAG_NONE, + &bufferDesc, + D3D12_RESOURCE_STATE_COPY_DEST, + nullptr, + IID_GRAPHICS_PPV_ARGS(pStaging.GetAddressOf())); + if (FAILED(hr)) + return hr; + + assert(pStaging); + + // Transition the resource if necessary + TransitionResource(commandList.Get(), pSource, beforeState, D3D12_RESOURCE_STATE_COPY_SOURCE); + + // Get the copy target location + for (UINT j = 0; j < numberOfResources; ++j) + { + CD3DX12_TEXTURE_COPY_LOCATION copyDest(pStaging.Get(), pLayout[j]); + CD3DX12_TEXTURE_COPY_LOCATION copySrc(copySource.Get(), j); + commandList->CopyTextureRegion(©Dest, 0, 0, 0, ©Src, nullptr); + } + + // Transition the resource to the next state + TransitionResource(commandList.Get(), pSource, D3D12_RESOURCE_STATE_COPY_SOURCE, afterState); + + hr = commandList->Close(); + if (FAILED(hr)) + return hr; + + // Execute the command list + pCommandQ->ExecuteCommandLists(1, (ID3D12CommandList**)commandList.GetAddressOf()); + + // Signal the fence + hr = pCommandQ->Signal(fence.Get(), 1); + if (FAILED(hr)) + return hr; + + // Block until the copy is complete + while (fence->GetCompletedValue() < 1) + SwitchToThread(); + + return S_OK; + } +} + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Determine if given texture metadata is supported on the given device +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::IsSupportedTexture( + ID3D12Device* pDevice, + const TexMetadata& metadata) +{ + if (!pDevice) + return false; + + // Validate format + DXGI_FORMAT fmt = metadata.format; + + if (!IsValid(fmt)) + return false; + + // Validate miplevel count + if (metadata.mipLevels > D3D12_REQ_MIP_LEVELS) + return false; + + // Validate array size, dimension, and width/height + size_t arraySize = metadata.arraySize; + size_t iWidth = metadata.width; + size_t iHeight = metadata.height; + size_t iDepth = metadata.depth; + + // Most cases are known apriori based on feature level, but we use this for robustness to handle the few optional cases + D3D12_FEATURE_DATA_FORMAT_SUPPORT formatSupport = { fmt }; + HRESULT hr = pDevice->CheckFeatureSupport(D3D12_FEATURE_FORMAT_SUPPORT, &formatSupport, sizeof(formatSupport)); + if (FAILED(hr)) + { + memset(&formatSupport, 0, sizeof(formatSupport)); + } + + if (metadata.mipLevels > 1 && !(formatSupport.Support1 & D3D12_FORMAT_SUPPORT1_MIP)) + { + return false; + } + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + if (!(formatSupport.Support1 & D3D12_FORMAT_SUPPORT1_TEXTURE1D)) + return false; + + if ((arraySize > D3D12_REQ_TEXTURE1D_ARRAY_AXIS_DIMENSION) + || (iWidth > D3D12_REQ_TEXTURE1D_U_DIMENSION)) + return false; + + { + UINT numberOfResources = static_cast(arraySize * metadata.mipLevels); + if (numberOfResources > D3D12_REQ_SUBRESOURCES) + return false; + } + break; + + case TEX_DIMENSION_TEXTURE2D: + if (metadata.IsCubemap()) + { + if (!(formatSupport.Support1 & D3D12_FORMAT_SUPPORT1_TEXTURECUBE)) + return false; + + if ((arraySize > D3D12_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) + || (iWidth > D3D12_REQ_TEXTURECUBE_DIMENSION) + || (iHeight > D3D12_REQ_TEXTURECUBE_DIMENSION)) + return false; + } + else // Not a cube map + { + if (!(formatSupport.Support1 & D3D12_FORMAT_SUPPORT1_TEXTURE2D)) + return false; + + if ((arraySize > D3D12_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) + || (iWidth > D3D12_REQ_TEXTURE2D_U_OR_V_DIMENSION) + || (iHeight > D3D12_REQ_TEXTURE2D_U_OR_V_DIMENSION)) + return false; + } + + { + UINT numberOfResources = static_cast(arraySize * metadata.mipLevels); + if (numberOfResources > D3D12_REQ_SUBRESOURCES) + return false; + } + break; + + case TEX_DIMENSION_TEXTURE3D: + if (!(formatSupport.Support1 & D3D12_FORMAT_SUPPORT1_TEXTURE3D)) + return false; + + if ((arraySize > 1) + || (iWidth > D3D12_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) + || (iHeight > D3D12_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) + || (iDepth > D3D12_REQ_TEXTURE3D_U_V_OR_W_DIMENSION)) + return false; + + { + UINT numberOfResources = static_cast(metadata.mipLevels); + if (numberOfResources > D3D12_REQ_SUBRESOURCES) + return false; + } + break; + + default: + // Not a supported dimension + return false; + } + + return true; +} + + +//------------------------------------------------------------------------------------- +// Create a texture resource +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateTexture( + ID3D12Device* pDevice, + const TexMetadata& metadata, + ID3D12Resource** ppResource) +{ + return CreateTextureEx( + pDevice, metadata, + D3D12_RESOURCE_FLAG_NONE, false, + ppResource); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateTextureEx( + ID3D12Device* pDevice, + const TexMetadata& metadata, + D3D12_RESOURCE_FLAGS resFlags, + bool forceSRGB, + ID3D12Resource** ppResource) +{ + if (!pDevice || !ppResource) + return E_INVALIDARG; + + *ppResource = nullptr; + + if (!metadata.mipLevels || !metadata.arraySize) + return E_INVALIDARG; + + if ((metadata.width > UINT32_MAX) || (metadata.height > UINT32_MAX) + || (metadata.mipLevels > UINT16_MAX) || (metadata.arraySize > UINT16_MAX)) + return E_INVALIDARG; + + DXGI_FORMAT format = metadata.format; + if (forceSRGB) + { + format = MakeSRGB(format); + } + + D3D12_RESOURCE_DESC desc = {}; + desc.Width = static_cast(metadata.width); + desc.Height = static_cast(metadata.height); + desc.MipLevels = static_cast(metadata.mipLevels); + desc.DepthOrArraySize = (metadata.dimension == TEX_DIMENSION_TEXTURE3D) + ? static_cast(metadata.depth) + : static_cast(metadata.arraySize); + desc.Format = format; + desc.Flags = resFlags; + desc.SampleDesc.Count = 1; + desc.Dimension = static_cast(metadata.dimension); + + CD3DX12_HEAP_PROPERTIES defaultHeapProperties(D3D12_HEAP_TYPE_DEFAULT); + + HRESULT hr = pDevice->CreateCommittedResource( + &defaultHeapProperties, + D3D12_HEAP_FLAG_NONE, + &desc, + D3D12_RESOURCE_STATE_COPY_DEST, + nullptr, + IID_GRAPHICS_PPV_ARGS(ppResource)); + + return hr; +} + + +//------------------------------------------------------------------------------------- +// Prepares a texture resource for upload +//------------------------------------------------------------------------------------- + +_Use_decl_annotations_ +HRESULT DirectX::PrepareUpload( + ID3D12Device* pDevice, + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + std::vector& subresources) +{ + if (!pDevice || !srcImages || !nimages || !metadata.mipLevels || !metadata.arraySize) + return E_INVALIDARG; + + UINT numberOfPlanes = D3D12GetFormatPlaneCount(pDevice, metadata.format); + if (!numberOfPlanes) + return E_INVALIDARG; + + if ((numberOfPlanes > 1) && IsDepthStencil(metadata.format)) + { + // DirectX 12 uses planes for stencil, DirectX 11 does not + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + size_t numberOfResources = (metadata.dimension == TEX_DIMENSION_TEXTURE3D) + ? 1 : metadata.arraySize; + numberOfResources *= metadata.mipLevels; + numberOfResources *= numberOfPlanes; + + if (numberOfResources > D3D12_REQ_SUBRESOURCES) + return E_INVALIDARG; + + subresources.clear(); + subresources.reserve(numberOfResources); + + // Fill out subresource array + if (metadata.IsVolumemap()) + { + //--- Volume case ------------------------------------------------------------- + if (!metadata.depth) + return E_INVALIDARG; + + if (metadata.depth > UINT16_MAX) + return E_INVALIDARG; + + if (metadata.arraySize > 1) + // Direct3D 12 doesn't support arrays of 3D textures + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + for (size_t plane = 0; plane < numberOfPlanes; ++plane) + { + size_t depth = metadata.depth; + + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + size_t index = metadata.ComputeIndex(level, 0, 0); + if (index >= nimages) + return E_FAIL; + + const Image& img = srcImages[index]; + + if (img.format != metadata.format) + return E_FAIL; + + if (!img.pixels) + return E_POINTER; + + // Verify pixels in image 1 .. (depth-1) are exactly image->slicePitch apart + // For 3D textures, this relies on all slices of the same miplevel being continous in memory + // (this is how ScratchImage lays them out), which is why we just give the 0th slice to Direct3D 11 + const uint8_t* pSlice = img.pixels + img.slicePitch; + for (size_t slice = 1; slice < depth; ++slice) + { + size_t tindex = metadata.ComputeIndex(level, 0, slice); + if (tindex >= nimages) + return E_FAIL; + + const Image& timg = srcImages[tindex]; + + if (!timg.pixels) + return E_POINTER; + + if (timg.pixels != pSlice + || timg.format != metadata.format + || timg.rowPitch != img.rowPitch + || timg.slicePitch != img.slicePitch) + return E_FAIL; + + pSlice = timg.pixels + img.slicePitch; + } + + D3D12_SUBRESOURCE_DATA res = + { + img.pixels, + static_cast(img.rowPitch), + static_cast(img.slicePitch) + }; + + AdjustPlaneResource(metadata.format, img.height, plane, res); + + subresources.emplace_back(res); + + if (depth > 1) + depth >>= 1; + } + } + } + else + { + //--- 1D or 2D texture case --------------------------------------------------- + for (size_t plane = 0; plane < numberOfPlanes; ++plane) + { + for (size_t item = 0; item < metadata.arraySize; ++item) + { + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + size_t index = metadata.ComputeIndex(level, item, 0); + if (index >= nimages) + return E_FAIL; + + const Image& img = srcImages[index]; + + if (img.format != metadata.format) + return E_FAIL; + + if (!img.pixels) + return E_POINTER; + + D3D12_SUBRESOURCE_DATA res = + { + img.pixels, + static_cast(img.rowPitch), + static_cast(img.slicePitch) + }; + + AdjustPlaneResource(metadata.format, img.height, plane, res); + + subresources.emplace_back(res); + } + } + } + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Save a texture resource +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CaptureTexture( + ID3D12CommandQueue* pCommandQueue, + ID3D12Resource* pSource, + bool isCubeMap, + ScratchImage& result, + D3D12_RESOURCE_STATES beforeState, + D3D12_RESOURCE_STATES afterState) +{ + if (!pCommandQueue || !pSource) + return E_INVALIDARG; + + ComPtr device; + pCommandQueue->GetDevice(IID_GRAPHICS_PPV_ARGS(device.GetAddressOf())); + + auto desc = pSource->GetDesc(); + + ComPtr pStaging; + std::unique_ptr layoutBuff; + UINT numberOfPlanes, numberOfResources; + HRESULT hr = Capture(device.Get(), + pCommandQueue, + pSource, + desc, + pStaging, + layoutBuff, + numberOfPlanes, + numberOfResources, + beforeState, + afterState); + if (FAILED(hr)) + return hr; + + if (!layoutBuff || !numberOfPlanes || !numberOfResources) + return E_UNEXPECTED; + + auto pLayout = reinterpret_cast(layoutBuff.get()); + auto pRowSizesInBytes = reinterpret_cast(pLayout + numberOfResources); + auto pNumRows = reinterpret_cast(pRowSizesInBytes + numberOfResources); + + switch (desc.Dimension) + { + case D3D12_RESOURCE_DIMENSION_TEXTURE1D: + { + TexMetadata mdata; + mdata.width = static_cast(desc.Width); + mdata.height = mdata.depth = 1; + mdata.arraySize = desc.DepthOrArraySize; + mdata.mipLevels = desc.MipLevels; + mdata.miscFlags = 0; + mdata.miscFlags2 = 0; + mdata.format = desc.Format; + mdata.dimension = TEX_DIMENSION_TEXTURE1D; + + hr = result.Initialize(mdata); + if (FAILED(hr)) + return hr; + } + break; + + case D3D12_RESOURCE_DIMENSION_TEXTURE2D: + { + TexMetadata mdata; + mdata.width = static_cast(desc.Width); + mdata.height = desc.Height; + mdata.depth = 1; + mdata.arraySize = desc.DepthOrArraySize; + mdata.mipLevels = desc.MipLevels; + mdata.miscFlags = isCubeMap ? TEX_MISC_TEXTURECUBE : 0; + mdata.miscFlags2 = 0; + mdata.format = desc.Format; + mdata.dimension = TEX_DIMENSION_TEXTURE2D; + + hr = result.Initialize(mdata); + if (FAILED(hr)) + return hr; + } + break; + + case D3D12_RESOURCE_DIMENSION_TEXTURE3D: + { + TexMetadata mdata; + mdata.width = static_cast(desc.Width); + mdata.height = desc.Height; + mdata.depth = desc.DepthOrArraySize; + mdata.arraySize = 1; + mdata.mipLevels = desc.MipLevels; + mdata.miscFlags = 0; + mdata.miscFlags2 = 0; + mdata.format = desc.Format; + mdata.dimension = TEX_DIMENSION_TEXTURE3D; + + hr = result.Initialize(mdata); + if (FAILED(hr)) + return hr; + } + break; + + default: + return E_FAIL; + } + + BYTE* pData; + hr = pStaging->Map(0, nullptr, reinterpret_cast(&pData)); + if (FAILED(hr)) + { + result.Release(); + return E_FAIL; + } + + UINT arraySize, depth; + if (desc.Dimension == D3D12_RESOURCE_DIMENSION_TEXTURE3D) + { + arraySize = 1; + depth = desc.DepthOrArraySize; + } + else + { + arraySize = desc.DepthOrArraySize; + depth = 1; + } + + for (UINT plane = 0; plane < numberOfPlanes; ++plane) + { + for (UINT item = 0; item < arraySize; ++item) + { + for (UINT level = 0; level < desc.MipLevels; ++level) + { + UINT dindex = D3D12CalcSubresource(level, item, plane, desc.MipLevels, arraySize); + assert(dindex < numberOfResources); + + const Image* img = result.GetImage(level, item, 0); + if (!img) + { + pStaging->Unmap(0, nullptr); + result.Release(); + return E_FAIL; + } + + if (!img->pixels) + { + pStaging->Unmap(0, nullptr); + result.Release(); + return E_POINTER; + } + + D3D12_MEMCPY_DEST destData = { img->pixels, img->rowPitch, img->slicePitch }; + + AdjustPlaneResource(img->format, img->height, plane, destData); + + D3D12_SUBRESOURCE_DATA srcData = + { + pData + pLayout[dindex].Offset, + static_cast(pLayout[dindex].Footprint.RowPitch), + static_cast(pLayout[dindex].Footprint.RowPitch * pNumRows[dindex]) + }; + + if (pRowSizesInBytes[dindex] > (SIZE_T)-1) + { + pStaging->Unmap(0, nullptr); + result.Release(); + return E_FAIL; + } + + MemcpySubresource(&destData, &srcData, + (SIZE_T)pRowSizesInBytes[dindex], + pNumRows[dindex], + pLayout[dindex].Footprint.Depth); + } + } + } + + pStaging->Unmap(0, nullptr); + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexDDS.cpp b/deps/DirectXTex/DirectXTex/DirectXTexDDS.cpp new file mode 100644 index 0000000..9f68568 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexDDS.cpp @@ -0,0 +1,2175 @@ +//------------------------------------------------------------------------------------- +// DirectXTexDDS.cpp +// +// DirectX Texture Library - Microsoft DirectDraw Surface (DDS) file format reader/writer +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +#include "dds.h" + +using namespace DirectX; + +static_assert(static_cast(TEX_DIMENSION_TEXTURE1D) == static_cast(DDS_DIMENSION_TEXTURE1D), "header enum mismatch"); +static_assert(static_cast(TEX_DIMENSION_TEXTURE2D) == static_cast(DDS_DIMENSION_TEXTURE2D), "header enum mismatch"); +static_assert(static_cast(TEX_DIMENSION_TEXTURE3D) == static_cast(DDS_DIMENSION_TEXTURE3D), "header enum mismatch"); + +namespace +{ + //------------------------------------------------------------------------------------- + // Legacy format mapping table (used for DDS files without 'DX10' extended header) + //------------------------------------------------------------------------------------- + enum CONVERSION_FLAGS + { + CONV_FLAGS_NONE = 0x0, + CONV_FLAGS_EXPAND = 0x1, // Conversion requires expanded pixel size + CONV_FLAGS_NOALPHA = 0x2, // Conversion requires setting alpha to known value + CONV_FLAGS_SWIZZLE = 0x4, // BGR/RGB order swizzling required + CONV_FLAGS_PAL8 = 0x8, // Has an 8-bit palette + CONV_FLAGS_888 = 0x10, // Source is an 8:8:8 (24bpp) format + CONV_FLAGS_565 = 0x20, // Source is a 5:6:5 (16bpp) format + CONV_FLAGS_5551 = 0x40, // Source is a 5:5:5:1 (16bpp) format + CONV_FLAGS_4444 = 0x80, // Source is a 4:4:4:4 (16bpp) format + CONV_FLAGS_44 = 0x100, // Source is a 4:4 (8bpp) format + CONV_FLAGS_332 = 0x200, // Source is a 3:3:2 (8bpp) format + CONV_FLAGS_8332 = 0x400, // Source is a 8:3:3:2 (16bpp) format + CONV_FLAGS_A8P8 = 0x800, // Has an 8-bit palette with an alpha channel + CONV_FLAGS_DX10 = 0x10000, // Has the 'DX10' extension header + CONV_FLAGS_PMALPHA = 0x20000, // Contains premultiplied alpha data + CONV_FLAGS_L8 = 0x40000, // Source is a 8 luminance format + CONV_FLAGS_L16 = 0x80000, // Source is a 16 luminance format + CONV_FLAGS_A8L8 = 0x100000, // Source is a 8:8 luminance format + }; + + struct LegacyDDS + { + DXGI_FORMAT format; + DWORD convFlags; + DDS_PIXELFORMAT ddpf; + }; + + const LegacyDDS g_LegacyDDSMap[] = + { + { DXGI_FORMAT_BC1_UNORM, CONV_FLAGS_NONE, DDSPF_DXT1 }, // D3DFMT_DXT1 + { DXGI_FORMAT_BC2_UNORM, CONV_FLAGS_NONE, DDSPF_DXT3 }, // D3DFMT_DXT3 + { DXGI_FORMAT_BC3_UNORM, CONV_FLAGS_NONE, DDSPF_DXT5 }, // D3DFMT_DXT5 + + { DXGI_FORMAT_BC2_UNORM, CONV_FLAGS_PMALPHA, DDSPF_DXT2 }, // D3DFMT_DXT2 + { DXGI_FORMAT_BC3_UNORM, CONV_FLAGS_PMALPHA, DDSPF_DXT4 }, // D3DFMT_DXT4 + + { DXGI_FORMAT_BC4_UNORM, CONV_FLAGS_NONE, DDSPF_BC4_UNORM }, + { DXGI_FORMAT_BC4_SNORM, CONV_FLAGS_NONE, DDSPF_BC4_SNORM }, + { DXGI_FORMAT_BC5_UNORM, CONV_FLAGS_NONE, DDSPF_BC5_UNORM }, + { DXGI_FORMAT_BC5_SNORM, CONV_FLAGS_NONE, DDSPF_BC5_SNORM }, + + { DXGI_FORMAT_BC4_UNORM, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('A', 'T', 'I', '1'), 0, 0, 0, 0, 0 } }, + { DXGI_FORMAT_BC5_UNORM, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('A', 'T', 'I', '2'), 0, 0, 0, 0, 0 } }, + + { DXGI_FORMAT_R8G8_B8G8_UNORM, CONV_FLAGS_NONE, DDSPF_R8G8_B8G8 }, // D3DFMT_R8G8_B8G8 + { DXGI_FORMAT_G8R8_G8B8_UNORM, CONV_FLAGS_NONE, DDSPF_G8R8_G8B8 }, // D3DFMT_G8R8_G8B8 + + { DXGI_FORMAT_B8G8R8A8_UNORM, CONV_FLAGS_NONE, DDSPF_A8R8G8B8 }, // D3DFMT_A8R8G8B8 (uses DXGI 1.1 format) + { DXGI_FORMAT_B8G8R8X8_UNORM, CONV_FLAGS_NONE, DDSPF_X8R8G8B8 }, // D3DFMT_X8R8G8B8 (uses DXGI 1.1 format) + { DXGI_FORMAT_R8G8B8A8_UNORM, CONV_FLAGS_NONE, DDSPF_A8B8G8R8 }, // D3DFMT_A8B8G8R8 + { DXGI_FORMAT_R8G8B8A8_UNORM, CONV_FLAGS_NOALPHA, DDSPF_X8B8G8R8 }, // D3DFMT_X8B8G8R8 + { DXGI_FORMAT_R16G16_UNORM, CONV_FLAGS_NONE, DDSPF_G16R16 }, // D3DFMT_G16R16 + + { DXGI_FORMAT_R10G10B10A2_UNORM, CONV_FLAGS_SWIZZLE, { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x000003ff, 0x000ffc00, 0x3ff00000, 0xc0000000 } }, // D3DFMT_A2R10G10B10 (D3DX reversal issue workaround) + { DXGI_FORMAT_R10G10B10A2_UNORM, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x3ff00000, 0x000ffc00, 0x000003ff, 0xc0000000 } }, // D3DFMT_A2B10G10R10 (D3DX reversal issue workaround) + + { DXGI_FORMAT_R8G8B8A8_UNORM, CONV_FLAGS_EXPAND + | CONV_FLAGS_NOALPHA + | CONV_FLAGS_888, DDSPF_R8G8B8 }, // D3DFMT_R8G8B8 + + { DXGI_FORMAT_B5G6R5_UNORM, CONV_FLAGS_565, DDSPF_R5G6B5 }, // D3DFMT_R5G6B5 + { DXGI_FORMAT_B5G5R5A1_UNORM, CONV_FLAGS_5551, DDSPF_A1R5G5B5 }, // D3DFMT_A1R5G5B5 + { DXGI_FORMAT_B5G5R5A1_UNORM, CONV_FLAGS_5551 + | CONV_FLAGS_NOALPHA, { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 16, 0x7c00, 0x03e0, 0x001f, 0x0000 } }, // D3DFMT_X1R5G5B5 + + { DXGI_FORMAT_R8G8B8A8_UNORM, CONV_FLAGS_EXPAND + | CONV_FLAGS_8332, { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x00e0, 0x001c, 0x0003, 0xff00 } }, // D3DFMT_A8R3G3B2 + { DXGI_FORMAT_B5G6R5_UNORM, CONV_FLAGS_EXPAND + | CONV_FLAGS_332, { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 8, 0xe0, 0x1c, 0x03, 0x00 } }, // D3DFMT_R3G3B2 + + { DXGI_FORMAT_R8_UNORM, CONV_FLAGS_NONE, DDSPF_L8 }, // D3DFMT_L8 + { DXGI_FORMAT_R16_UNORM, CONV_FLAGS_NONE, DDSPF_L16 }, // D3DFMT_L16 + { DXGI_FORMAT_R8G8_UNORM, CONV_FLAGS_NONE, DDSPF_A8L8 }, // D3DFMT_A8L8 + { DXGI_FORMAT_R8G8_UNORM, CONV_FLAGS_NONE, DDSPF_A8L8_ALT }, // D3DFMT_A8L8 (alternative bitcount) + + { DXGI_FORMAT_A8_UNORM, CONV_FLAGS_NONE, DDSPF_A8 }, // D3DFMT_A8 + + { DXGI_FORMAT_R16G16B16A16_UNORM, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, 36, 0, 0, 0, 0, 0 } }, // D3DFMT_A16B16G16R16 + { DXGI_FORMAT_R16G16B16A16_SNORM, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, 110, 0, 0, 0, 0, 0 } }, // D3DFMT_Q16W16V16U16 + { DXGI_FORMAT_R16_FLOAT, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, 111, 0, 0, 0, 0, 0 } }, // D3DFMT_R16F + { DXGI_FORMAT_R16G16_FLOAT, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, 112, 0, 0, 0, 0, 0 } }, // D3DFMT_G16R16F + { DXGI_FORMAT_R16G16B16A16_FLOAT, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, 113, 0, 0, 0, 0, 0 } }, // D3DFMT_A16B16G16R16F + { DXGI_FORMAT_R32_FLOAT, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, 114, 0, 0, 0, 0, 0 } }, // D3DFMT_R32F + { DXGI_FORMAT_R32G32_FLOAT, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, 115, 0, 0, 0, 0, 0 } }, // D3DFMT_G32R32F + { DXGI_FORMAT_R32G32B32A32_FLOAT, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, 116, 0, 0, 0, 0, 0 } }, // D3DFMT_A32B32G32R32F + + { DXGI_FORMAT_R32_FLOAT, CONV_FLAGS_NONE, { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0xffffffff, 0x00000000, 0x00000000, 0x00000000 } }, // D3DFMT_R32F (D3DX uses FourCC 114 instead) + + { DXGI_FORMAT_R8G8B8A8_UNORM, CONV_FLAGS_EXPAND + | CONV_FLAGS_PAL8 + | CONV_FLAGS_A8P8, { sizeof(DDS_PIXELFORMAT), DDS_PAL8A, 0, 16, 0, 0, 0, 0 } }, // D3DFMT_A8P8 + { DXGI_FORMAT_R8G8B8A8_UNORM, CONV_FLAGS_EXPAND + | CONV_FLAGS_PAL8, { sizeof(DDS_PIXELFORMAT), DDS_PAL8, 0, 8, 0, 0, 0, 0 } }, // D3DFMT_P8 + + { DXGI_FORMAT_B4G4R4A4_UNORM, CONV_FLAGS_4444, DDSPF_A4R4G4B4 }, // D3DFMT_A4R4G4B4 (uses DXGI 1.2 format) + { DXGI_FORMAT_B4G4R4A4_UNORM, CONV_FLAGS_NOALPHA + | CONV_FLAGS_4444, { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 16, 0x0f00, 0x00f0, 0x000f, 0x0000 } }, // D3DFMT_X4R4G4B4 (uses DXGI 1.2 format) + { DXGI_FORMAT_B4G4R4A4_UNORM, CONV_FLAGS_EXPAND + | CONV_FLAGS_44, { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCEA,0, 8, 0x0f, 0x00, 0x00, 0xf0 } }, // D3DFMT_A4L4 (uses DXGI 1.2 format) + + { DXGI_FORMAT_YUY2, CONV_FLAGS_NONE, DDSPF_YUY2 }, // D3DFMT_YUY2 (uses DXGI 1.2 format) + { DXGI_FORMAT_YUY2, CONV_FLAGS_SWIZZLE, { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('U','Y','V','Y'), 0, 0, 0, 0, 0 } }, // D3DFMT_UYVY (uses DXGI 1.2 format) + + { DXGI_FORMAT_R8G8_SNORM, CONV_FLAGS_NONE, DDSPF_V8U8 }, // D3DFMT_V8U8 + { DXGI_FORMAT_R8G8B8A8_SNORM, CONV_FLAGS_NONE, DDSPF_Q8W8V8U8 }, // D3DFMT_Q8W8V8U8 + { DXGI_FORMAT_R16G16_SNORM, CONV_FLAGS_NONE, DDSPF_V16U16 }, // D3DFMT_V16U16 + }; + + // Note that many common DDS reader/writers (including D3DX) swap the + // the RED/BLUE masks for 10:10:10:2 formats. We assumme + // below that the 'backwards' header mask is being used since it is most + // likely written by D3DX. The more robust solution is to use the 'DX10' + // header extension and specify the DXGI_FORMAT_R10G10B10A2_UNORM format directly + + // We do not support the following legacy Direct3D 9 formats: + // BumpDuDv D3DFMT_A2W10V10U10 + // BumpLuminance D3DFMT_L6V5U5, D3DFMT_X8L8V8U8 + // FourCC 117 D3DFMT_CxV8U8 + // ZBuffer D3DFMT_D16_LOCKABLE + // FourCC 82 D3DFMT_D32F_LOCKABLE + + // We do not support the following known FourCC codes: + // FourCC CTX1 (Xbox 360 only) + // FourCC EAR, EARG, ET2, ET2A (Ericsson Texture Compression) + + DXGI_FORMAT GetDXGIFormat(const DDS_HEADER& hdr, const DDS_PIXELFORMAT& ddpf, DWORD flags, _Inout_ DWORD& convFlags) + { + uint32_t ddpfFlags = ddpf.dwFlags; + if (hdr.dwReserved1[9] == MAKEFOURCC('N', 'V', 'T', 'T')) + { + // Clear out non-standard nVidia DDS flags + ddpfFlags &= ~0xC0000000 /* DDPF_SRGB | DDPF_NORMAL */; + } + + const size_t MAP_SIZE = sizeof(g_LegacyDDSMap) / sizeof(LegacyDDS); + size_t index = 0; + for (index = 0; index < MAP_SIZE; ++index) + { + const LegacyDDS* entry = &g_LegacyDDSMap[index]; + + if (ddpfFlags == entry->ddpf.dwFlags) + { + if (entry->ddpf.dwFlags & DDS_FOURCC) + { + if (ddpf.dwFourCC == entry->ddpf.dwFourCC) + break; + } + else if (entry->ddpf.dwFlags & DDS_PAL8) + { + if (ddpf.dwRGBBitCount == entry->ddpf.dwRGBBitCount) + break; + } + else if (entry->ddpf.dwFlags & DDS_ALPHA) + { + if (ddpf.dwRGBBitCount == entry->ddpf.dwRGBBitCount + && ddpf.dwABitMask == entry->ddpf.dwABitMask) + break; + } + else if (entry->ddpf.dwFlags & DDS_LUMINANCE) + { + if (entry->ddpf.dwFlags & 0x1 /*DDPF_ALPHAPIXELS*/) + { + // LUMINANCEA + if (ddpf.dwRGBBitCount == entry->ddpf.dwRGBBitCount + && ddpf.dwRBitMask == entry->ddpf.dwRBitMask + && ddpf.dwABitMask == entry->ddpf.dwABitMask) + break; + } + else + { + // LUMINANCE + if (ddpf.dwRGBBitCount == entry->ddpf.dwRGBBitCount + && ddpf.dwRBitMask == entry->ddpf.dwRBitMask) + break; + } + } + else if (entry->ddpf.dwFlags & DDS_BUMPDUDV) + { + if (ddpf.dwRGBBitCount == entry->ddpf.dwRGBBitCount + && ddpf.dwRBitMask == entry->ddpf.dwRBitMask + && ddpf.dwGBitMask == entry->ddpf.dwGBitMask + && ddpf.dwBBitMask == entry->ddpf.dwBBitMask + && ddpf.dwABitMask == entry->ddpf.dwABitMask) + break; + } + else if (ddpf.dwRGBBitCount == entry->ddpf.dwRGBBitCount) + { + if (entry->ddpf.dwFlags & 0x1 /*DDPF_ALPHAPIXELS*/) + { + // RGBA + if (ddpf.dwRBitMask == entry->ddpf.dwRBitMask + && ddpf.dwGBitMask == entry->ddpf.dwGBitMask + && ddpf.dwBBitMask == entry->ddpf.dwBBitMask + && ddpf.dwABitMask == entry->ddpf.dwABitMask) + break; + } + else + { + // RGB + if (ddpf.dwRBitMask == entry->ddpf.dwRBitMask + && ddpf.dwGBitMask == entry->ddpf.dwGBitMask + && ddpf.dwBBitMask == entry->ddpf.dwBBitMask) + break; + } + } + } + } + + if (index >= MAP_SIZE) + return DXGI_FORMAT_UNKNOWN; + + DWORD cflags = g_LegacyDDSMap[index].convFlags; + DXGI_FORMAT format = g_LegacyDDSMap[index].format; + + if ((cflags & CONV_FLAGS_EXPAND) && (flags & DDS_FLAGS_NO_LEGACY_EXPANSION)) + return DXGI_FORMAT_UNKNOWN; + + if ((format == DXGI_FORMAT_R10G10B10A2_UNORM) && (flags & DDS_FLAGS_NO_R10B10G10A2_FIXUP)) + { + cflags ^= CONV_FLAGS_SWIZZLE; + } + + if ((hdr.dwReserved1[9] == MAKEFOURCC('N', 'V', 'T', 'T')) + && (ddpf.dwFlags & 0x40000000 /* DDPF_SRGB */)) + { + format = MakeSRGB(format); + } + + convFlags = cflags; + + return format; + } + + + //------------------------------------------------------------------------------------- + // Decodes DDS header including optional DX10 extended header + //------------------------------------------------------------------------------------- + HRESULT DecodeDDSHeader( + _In_reads_bytes_(size) const void* pSource, + size_t size, + DWORD flags, + _Out_ TexMetadata& metadata, + _Inout_ DWORD& convFlags) + { + if (!pSource) + return E_INVALIDARG; + + memset(&metadata, 0, sizeof(TexMetadata)); + + if (size < (sizeof(DDS_HEADER) + sizeof(uint32_t))) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + // DDS files always start with the same magic number ("DDS ") + uint32_t dwMagicNumber = *reinterpret_cast(pSource); + if (dwMagicNumber != DDS_MAGIC) + { + return E_FAIL; + } + + auto pHeader = reinterpret_cast((const uint8_t*)pSource + sizeof(uint32_t)); + + // Verify header to validate DDS file + if (pHeader->dwSize != sizeof(DDS_HEADER) + || pHeader->ddspf.dwSize != sizeof(DDS_PIXELFORMAT)) + { + return E_FAIL; + } + + metadata.mipLevels = pHeader->dwMipMapCount; + if (metadata.mipLevels == 0) + metadata.mipLevels = 1; + + // Check for DX10 extension + if ((pHeader->ddspf.dwFlags & DDS_FOURCC) + && (MAKEFOURCC('D', 'X', '1', '0') == pHeader->ddspf.dwFourCC)) + { + // Buffer must be big enough for both headers and magic value + if (size < (sizeof(DDS_HEADER) + sizeof(uint32_t) + sizeof(DDS_HEADER_DXT10))) + { + return E_FAIL; + } + + auto d3d10ext = reinterpret_cast((const uint8_t*)pSource + sizeof(uint32_t) + sizeof(DDS_HEADER)); + convFlags |= CONV_FLAGS_DX10; + + metadata.arraySize = d3d10ext->arraySize; + if (metadata.arraySize == 0) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + metadata.format = d3d10ext->dxgiFormat; + if (!IsValid(metadata.format) || IsPalettized(metadata.format)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + static_assert(static_cast(TEX_MISC_TEXTURECUBE) == static_cast(DDS_RESOURCE_MISC_TEXTURECUBE), "DDS header mismatch"); + + metadata.miscFlags = d3d10ext->miscFlag & ~TEX_MISC_TEXTURECUBE; + + switch (d3d10ext->resourceDimension) + { + case DDS_DIMENSION_TEXTURE1D: + + // D3DX writes 1D textures with a fixed Height of 1 + if ((pHeader->dwFlags & DDS_HEIGHT) && pHeader->dwHeight != 1) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + metadata.width = pHeader->dwWidth; + metadata.height = 1; + metadata.depth = 1; + metadata.dimension = TEX_DIMENSION_TEXTURE1D; + break; + + case DDS_DIMENSION_TEXTURE2D: + if (d3d10ext->miscFlag & DDS_RESOURCE_MISC_TEXTURECUBE) + { + metadata.miscFlags |= TEX_MISC_TEXTURECUBE; + metadata.arraySize *= 6; + } + + metadata.width = pHeader->dwWidth; + metadata.height = pHeader->dwHeight; + metadata.depth = 1; + metadata.dimension = TEX_DIMENSION_TEXTURE2D; + break; + + case DDS_DIMENSION_TEXTURE3D: + if (!(pHeader->dwFlags & DDS_HEADER_FLAGS_VOLUME)) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + if (metadata.arraySize > 1) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + metadata.width = pHeader->dwWidth; + metadata.height = pHeader->dwHeight; + metadata.depth = pHeader->dwDepth; + metadata.dimension = TEX_DIMENSION_TEXTURE3D; + break; + + default: + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + static_assert(static_cast(TEX_MISC2_ALPHA_MODE_MASK) == static_cast(DDS_MISC_FLAGS2_ALPHA_MODE_MASK), "DDS header mismatch"); + + static_assert(static_cast(TEX_ALPHA_MODE_UNKNOWN) == static_cast(DDS_ALPHA_MODE_UNKNOWN), "DDS header mismatch"); + static_assert(static_cast(TEX_ALPHA_MODE_STRAIGHT) == static_cast(DDS_ALPHA_MODE_STRAIGHT), "DDS header mismatch"); + static_assert(static_cast(TEX_ALPHA_MODE_PREMULTIPLIED) == static_cast(DDS_ALPHA_MODE_PREMULTIPLIED), "DDS header mismatch"); + static_assert(static_cast(TEX_ALPHA_MODE_OPAQUE) == static_cast(DDS_ALPHA_MODE_OPAQUE), "DDS header mismatch"); + static_assert(static_cast(TEX_ALPHA_MODE_CUSTOM) == static_cast(DDS_ALPHA_MODE_CUSTOM), "DDS header mismatch"); + + metadata.miscFlags2 = d3d10ext->miscFlags2; + } + else + { + metadata.arraySize = 1; + + if (pHeader->dwFlags & DDS_HEADER_FLAGS_VOLUME) + { + metadata.width = pHeader->dwWidth; + metadata.height = pHeader->dwHeight; + metadata.depth = pHeader->dwDepth; + metadata.dimension = TEX_DIMENSION_TEXTURE3D; + } + else + { + if (pHeader->dwCaps2 & DDS_CUBEMAP) + { + // We require all six faces to be defined + if ((pHeader->dwCaps2 & DDS_CUBEMAP_ALLFACES) != DDS_CUBEMAP_ALLFACES) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + metadata.arraySize = 6; + metadata.miscFlags |= TEX_MISC_TEXTURECUBE; + } + + metadata.width = pHeader->dwWidth; + metadata.height = pHeader->dwHeight; + metadata.depth = 1; + metadata.dimension = TEX_DIMENSION_TEXTURE2D; + + // Note there's no way for a legacy Direct3D 9 DDS to express a '1D' texture + } + + metadata.format = GetDXGIFormat(*pHeader, pHeader->ddspf, flags, convFlags); + + if (metadata.format == DXGI_FORMAT_UNKNOWN) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (convFlags & CONV_FLAGS_PMALPHA) + metadata.miscFlags2 |= TEX_ALPHA_MODE_PREMULTIPLIED; + + // Special flag for handling LUMINANCE legacy formats + if (flags & DDS_FLAGS_EXPAND_LUMINANCE) + { + switch (metadata.format) + { + case DXGI_FORMAT_R8_UNORM: + metadata.format = DXGI_FORMAT_R8G8B8A8_UNORM; + convFlags |= CONV_FLAGS_L8 | CONV_FLAGS_EXPAND; + break; + + case DXGI_FORMAT_R8G8_UNORM: + metadata.format = DXGI_FORMAT_R8G8B8A8_UNORM; + convFlags |= CONV_FLAGS_A8L8 | CONV_FLAGS_EXPAND; + break; + + case DXGI_FORMAT_R16_UNORM: + metadata.format = DXGI_FORMAT_R16G16B16A16_UNORM; + convFlags |= CONV_FLAGS_L16 | CONV_FLAGS_EXPAND; + break; + + default: + break; + } + } + } + + // Special flag for handling BGR DXGI 1.1 formats + if (flags & DDS_FLAGS_FORCE_RGB) + { + switch (metadata.format) + { + case DXGI_FORMAT_B8G8R8A8_UNORM: + metadata.format = DXGI_FORMAT_R8G8B8A8_UNORM; + convFlags |= CONV_FLAGS_SWIZZLE; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + metadata.format = DXGI_FORMAT_R8G8B8A8_UNORM; + convFlags |= CONV_FLAGS_SWIZZLE | CONV_FLAGS_NOALPHA; + break; + + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + metadata.format = DXGI_FORMAT_R8G8B8A8_TYPELESS; + convFlags |= CONV_FLAGS_SWIZZLE; + break; + + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + metadata.format = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + convFlags |= CONV_FLAGS_SWIZZLE; + break; + + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + metadata.format = DXGI_FORMAT_R8G8B8A8_TYPELESS; + convFlags |= CONV_FLAGS_SWIZZLE | CONV_FLAGS_NOALPHA; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + metadata.format = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + convFlags |= CONV_FLAGS_SWIZZLE | CONV_FLAGS_NOALPHA; + break; + + default: + break; + } + } + + // Special flag for handling 16bpp formats + if (flags & DDS_FLAGS_NO_16BPP) + { + switch (metadata.format) + { + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_B4G4R4A4_UNORM: + metadata.format = DXGI_FORMAT_R8G8B8A8_UNORM; + convFlags |= CONV_FLAGS_EXPAND; + if (metadata.format == DXGI_FORMAT_B5G6R5_UNORM) + convFlags |= CONV_FLAGS_NOALPHA; + + default: + break; + } + } + + return S_OK; + } +} + + +//------------------------------------------------------------------------------------- +// Encodes DDS file header (magic value, header, optional DX10 extended header) +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::_EncodeDDSHeader( + const TexMetadata& metadata, + DWORD flags, + void* pDestination, + size_t maxsize, + size_t& required) +{ + if (!IsValid(metadata.format)) + return E_INVALIDARG; + + if (IsPalettized(metadata.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (metadata.arraySize > 1) + { + if ((metadata.arraySize != 6) || (metadata.dimension != TEX_DIMENSION_TEXTURE2D) || !(metadata.IsCubemap())) + { + // Texture1D arrays, Texture2D arrays, and Cubemap arrays must be stored using 'DX10' extended header + flags |= DDS_FLAGS_FORCE_DX10_EXT; + } + } + + if (flags & DDS_FLAGS_FORCE_DX10_EXT_MISC2) + { + flags |= DDS_FLAGS_FORCE_DX10_EXT; + } + + DDS_PIXELFORMAT ddpf = { 0 }; + if (!(flags & DDS_FLAGS_FORCE_DX10_EXT)) + { + switch (metadata.format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_A8B8G8R8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R16G16_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_G16R16, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R8G8_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_A8L8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R16_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_L16, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R8_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_L8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_A8_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_A8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R8G8_B8G8_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_R8G8_B8G8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_G8R8_G8B8_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_G8R8_G8B8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC1_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_DXT1, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC2_UNORM: memcpy_s(&ddpf, sizeof(ddpf), metadata.IsPMAlpha() ? (&DDSPF_DXT2) : (&DDSPF_DXT3), sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC3_UNORM: memcpy_s(&ddpf, sizeof(ddpf), metadata.IsPMAlpha() ? (&DDSPF_DXT4) : (&DDSPF_DXT5), sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC4_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_BC4_UNORM, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC4_SNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_BC4_SNORM, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC5_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_BC5_UNORM, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC5_SNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_BC5_SNORM, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_B5G6R5_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_R5G6B5, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_B5G5R5A1_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_A1R5G5B5, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R8G8_SNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_V8U8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R8G8B8A8_SNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_Q8W8V8U8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R16G16_SNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_V16U16, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_B8G8R8A8_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_A8R8G8B8, sizeof(DDS_PIXELFORMAT)); break; // DXGI 1.1 + case DXGI_FORMAT_B8G8R8X8_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_X8R8G8B8, sizeof(DDS_PIXELFORMAT)); break; // DXGI 1.1 + case DXGI_FORMAT_B4G4R4A4_UNORM: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_A4R4G4B4, sizeof(DDS_PIXELFORMAT)); break; // DXGI 1.2 + case DXGI_FORMAT_YUY2: memcpy_s(&ddpf, sizeof(ddpf), &DDSPF_YUY2, sizeof(DDS_PIXELFORMAT)); break; // DXGI 1.2 + + // Legacy D3DX formats using D3DFMT enum value as FourCC + case DXGI_FORMAT_R32G32B32A32_FLOAT: + ddpf.dwSize = sizeof(DDS_PIXELFORMAT); ddpf.dwFlags = DDS_FOURCC; ddpf.dwFourCC = 116; // D3DFMT_A32B32G32R32F + break; + case DXGI_FORMAT_R16G16B16A16_FLOAT: + ddpf.dwSize = sizeof(DDS_PIXELFORMAT); ddpf.dwFlags = DDS_FOURCC; ddpf.dwFourCC = 113; // D3DFMT_A16B16G16R16F + break; + case DXGI_FORMAT_R16G16B16A16_UNORM: + ddpf.dwSize = sizeof(DDS_PIXELFORMAT); ddpf.dwFlags = DDS_FOURCC; ddpf.dwFourCC = 36; // D3DFMT_A16B16G16R16 + break; + case DXGI_FORMAT_R16G16B16A16_SNORM: + ddpf.dwSize = sizeof(DDS_PIXELFORMAT); ddpf.dwFlags = DDS_FOURCC; ddpf.dwFourCC = 110; // D3DFMT_Q16W16V16U16 + break; + case DXGI_FORMAT_R32G32_FLOAT: + ddpf.dwSize = sizeof(DDS_PIXELFORMAT); ddpf.dwFlags = DDS_FOURCC; ddpf.dwFourCC = 115; // D3DFMT_G32R32F + break; + case DXGI_FORMAT_R16G16_FLOAT: + ddpf.dwSize = sizeof(DDS_PIXELFORMAT); ddpf.dwFlags = DDS_FOURCC; ddpf.dwFourCC = 112; // D3DFMT_G16R16F + break; + case DXGI_FORMAT_R32_FLOAT: + ddpf.dwSize = sizeof(DDS_PIXELFORMAT); ddpf.dwFlags = DDS_FOURCC; ddpf.dwFourCC = 114; // D3DFMT_R32F + break; + case DXGI_FORMAT_R16_FLOAT: + ddpf.dwSize = sizeof(DDS_PIXELFORMAT); ddpf.dwFlags = DDS_FOURCC; ddpf.dwFourCC = 111; // D3DFMT_R16F + break; + + default: + break; + } + } + + required = sizeof(uint32_t) + sizeof(DDS_HEADER); + + if (ddpf.dwSize == 0) + required += sizeof(DDS_HEADER_DXT10); + + if (!pDestination) + return S_OK; + + if (maxsize < required) + return E_NOT_SUFFICIENT_BUFFER; + + *reinterpret_cast(pDestination) = DDS_MAGIC; + + auto header = reinterpret_cast(reinterpret_cast(pDestination) + sizeof(uint32_t)); + assert(header); + + memset(header, 0, sizeof(DDS_HEADER)); + header->dwSize = sizeof(DDS_HEADER); + header->dwFlags = DDS_HEADER_FLAGS_TEXTURE; + header->dwCaps = DDS_SURFACE_FLAGS_TEXTURE; + + if (metadata.mipLevels > 0) + { + header->dwFlags |= DDS_HEADER_FLAGS_MIPMAP; + + if (metadata.mipLevels > UINT16_MAX) + return E_INVALIDARG; + + header->dwMipMapCount = static_cast(metadata.mipLevels); + + if (header->dwMipMapCount > 1) + header->dwCaps |= DDS_SURFACE_FLAGS_MIPMAP; + } + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + if (metadata.width > UINT32_MAX) + return E_INVALIDARG; + + header->dwWidth = static_cast(metadata.width); + header->dwHeight = header->dwDepth = 1; + break; + + case TEX_DIMENSION_TEXTURE2D: + if (metadata.height > UINT32_MAX + || metadata.width > UINT32_MAX) + return E_INVALIDARG; + + header->dwHeight = static_cast(metadata.height); + header->dwWidth = static_cast(metadata.width); + header->dwDepth = 1; + + if (metadata.IsCubemap()) + { + header->dwCaps |= DDS_SURFACE_FLAGS_CUBEMAP; + header->dwCaps2 |= DDS_CUBEMAP_ALLFACES; + } + break; + + case TEX_DIMENSION_TEXTURE3D: + if (metadata.height > UINT32_MAX + || metadata.width > UINT32_MAX + || metadata.depth > UINT16_MAX) + return E_INVALIDARG; + + header->dwFlags |= DDS_HEADER_FLAGS_VOLUME; + header->dwCaps2 |= DDS_FLAGS_VOLUME; + header->dwHeight = static_cast(metadata.height); + header->dwWidth = static_cast(metadata.width); + header->dwDepth = static_cast(metadata.depth); + break; + + default: + return E_FAIL; + } + + size_t rowPitch, slicePitch; + ComputePitch(metadata.format, metadata.width, metadata.height, rowPitch, slicePitch, CP_FLAGS_NONE); + + if (slicePitch > UINT32_MAX + || rowPitch > UINT32_MAX) + return E_FAIL; + + if (IsCompressed(metadata.format)) + { + header->dwFlags |= DDS_HEADER_FLAGS_LINEARSIZE; + header->dwPitchOrLinearSize = static_cast(slicePitch); + } + else + { + header->dwFlags |= DDS_HEADER_FLAGS_PITCH; + header->dwPitchOrLinearSize = static_cast(rowPitch); + } + + if (ddpf.dwSize == 0) + { + memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_DX10, sizeof(DDS_PIXELFORMAT)); + + auto ext = reinterpret_cast(reinterpret_cast(header) + sizeof(DDS_HEADER)); + assert(ext); + + memset(ext, 0, sizeof(DDS_HEADER_DXT10)); + ext->dxgiFormat = metadata.format; + ext->resourceDimension = metadata.dimension; + + if (metadata.arraySize > UINT16_MAX) + return E_INVALIDARG; + + static_assert(static_cast(TEX_MISC_TEXTURECUBE) == static_cast(DDS_RESOURCE_MISC_TEXTURECUBE), "DDS header mismatch"); + + ext->miscFlag = metadata.miscFlags & ~TEX_MISC_TEXTURECUBE; + + if (metadata.miscFlags & TEX_MISC_TEXTURECUBE) + { + ext->miscFlag |= TEX_MISC_TEXTURECUBE; + assert((metadata.arraySize % 6) == 0); + ext->arraySize = static_cast(metadata.arraySize / 6); + } + else + { + ext->arraySize = static_cast(metadata.arraySize); + } + + static_assert(static_cast(TEX_MISC2_ALPHA_MODE_MASK) == static_cast(DDS_MISC_FLAGS2_ALPHA_MODE_MASK), "DDS header mismatch"); + + static_assert(static_cast(TEX_ALPHA_MODE_UNKNOWN) == static_cast(DDS_ALPHA_MODE_UNKNOWN), "DDS header mismatch"); + static_assert(static_cast(TEX_ALPHA_MODE_STRAIGHT) == static_cast(DDS_ALPHA_MODE_STRAIGHT), "DDS header mismatch"); + static_assert(static_cast(TEX_ALPHA_MODE_PREMULTIPLIED) == static_cast(DDS_ALPHA_MODE_PREMULTIPLIED), "DDS header mismatch"); + static_assert(static_cast(TEX_ALPHA_MODE_OPAQUE) == static_cast(DDS_ALPHA_MODE_OPAQUE), "DDS header mismatch"); + static_assert(static_cast(TEX_ALPHA_MODE_CUSTOM) == static_cast(DDS_ALPHA_MODE_CUSTOM), "DDS header mismatch"); + + if (flags & DDS_FLAGS_FORCE_DX10_EXT_MISC2) + { + // This was formerly 'reserved'. D3DX10 and D3DX11 will fail if this value is anything other than 0 + ext->miscFlags2 = metadata.miscFlags2; + } + } + else + { + memcpy_s(&header->ddspf, sizeof(header->ddspf), &ddpf, sizeof(ddpf)); + } + + return S_OK; +} + + +namespace +{ + //------------------------------------------------------------------------------------- + // Converts an image row with optional clearing of alpha value to 1.0 + // Returns true if supported, false if expansion case not supported + //------------------------------------------------------------------------------------- + enum TEXP_LEGACY_FORMAT + { + TEXP_LEGACY_UNKNOWN = 0, + TEXP_LEGACY_R8G8B8, + TEXP_LEGACY_R3G3B2, + TEXP_LEGACY_A8R3G3B2, + TEXP_LEGACY_P8, + TEXP_LEGACY_A8P8, + TEXP_LEGACY_A4L4, + TEXP_LEGACY_B4G4R4A4, + TEXP_LEGACY_L8, + TEXP_LEGACY_L16, + TEXP_LEGACY_A8L8 + }; + + inline TEXP_LEGACY_FORMAT _FindLegacyFormat(DWORD flags) + { + TEXP_LEGACY_FORMAT lformat = TEXP_LEGACY_UNKNOWN; + + if (flags & CONV_FLAGS_PAL8) + { + lformat = (flags & CONV_FLAGS_A8P8) ? TEXP_LEGACY_A8P8 : TEXP_LEGACY_P8; + } + else if (flags & CONV_FLAGS_888) + lformat = TEXP_LEGACY_R8G8B8; + else if (flags & CONV_FLAGS_332) + lformat = TEXP_LEGACY_R3G3B2; + else if (flags & CONV_FLAGS_8332) + lformat = TEXP_LEGACY_A8R3G3B2; + else if (flags & CONV_FLAGS_44) + lformat = TEXP_LEGACY_A4L4; + else if (flags & CONV_FLAGS_4444) + lformat = TEXP_LEGACY_B4G4R4A4; + else if (flags & CONV_FLAGS_L8) + lformat = TEXP_LEGACY_L8; + else if (flags & CONV_FLAGS_L16) + lformat = TEXP_LEGACY_L16; + else if (flags & CONV_FLAGS_A8L8) + lformat = TEXP_LEGACY_A8L8; + + return lformat; + } + + _Success_(return != false) + bool LegacyExpandScanline( + _Out_writes_bytes_(outSize) void* pDestination, + size_t outSize, + _In_ DXGI_FORMAT outFormat, + _In_reads_bytes_(inSize) const void* pSource, + size_t inSize, + _In_ TEXP_LEGACY_FORMAT inFormat, + _In_reads_opt_(256) const uint32_t* pal8, + _In_ DWORD flags) + { + assert(pDestination && outSize > 0); + assert(pSource && inSize > 0); + assert(IsValid(outFormat) && !IsPlanar(outFormat) && !IsPalettized(outFormat)); + + switch (inFormat) + { + case TEXP_LEGACY_R8G8B8: + if (outFormat != DXGI_FORMAT_R8G8B8A8_UNORM) + return false; + + // D3DFMT_R8G8B8 -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 3 && outSize >= 4) + { + const uint8_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < (inSize - 2)) && (ocount < (outSize - 3))); icount += 3, ocount += 4) + { + // 24bpp Direct3D 9 files are actually BGR, so need to swizzle as well + uint32_t t1 = (*(sPtr) << 16); + uint32_t t2 = (*(sPtr + 1) << 8); + uint32_t t3 = *(sPtr + 2); + + *(dPtr++) = t1 | t2 | t3 | 0xff000000; + sPtr += 3; + } + return true; + } + return false; + + case TEXP_LEGACY_R3G3B2: + switch (outFormat) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + // D3DFMT_R3G3B2 -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 1 && outSize >= 4) + { + const uint8_t* __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < inSize) && (ocount < (outSize - 3))); ++icount, ocount += 4) + { + uint8_t t = *(sPtr++); + + uint32_t t1 = (t & 0xe0) | ((t & 0xe0) >> 3) | ((t & 0xc0) >> 6); + uint32_t t2 = ((t & 0x1c) << 11) | ((t & 0x1c) << 8) | ((t & 0x18) << 5); + uint32_t t3 = ((t & 0x03) << 22) | ((t & 0x03) << 20) | ((t & 0x03) << 18) | ((t & 0x03) << 16); + + *(dPtr++) = t1 | t2 | t3 | 0xff000000; + } + return true; + } + return false; + + case DXGI_FORMAT_B5G6R5_UNORM: + // D3DFMT_R3G3B2 -> DXGI_FORMAT_B5G6R5_UNORM + if (inSize >= 1 && outSize >= 2) + { + const uint8_t* __restrict sPtr = reinterpret_cast(pSource); + uint16_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < inSize) && (ocount < (outSize - 1))); ++icount, ocount += 2) + { + uint8_t t = *(sPtr++); + + uint16_t t1 = ((t & 0xe0) << 8) | ((t & 0xc0) << 5); + uint16_t t2 = ((t & 0x1c) << 6) | ((t & 0x1c) << 3); + uint16_t t3 = ((t & 0x03) << 3) | ((t & 0x03) << 1) | ((t & 0x02) >> 1); + + *(dPtr++) = t1 | t2 | t3; + } + return true; + } + return false; + + default: + return false; + } + break; + + case TEXP_LEGACY_A8R3G3B2: + if (outFormat != DXGI_FORMAT_R8G8B8A8_UNORM) + return false; + + // D3DFMT_A8R3G3B2 -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 2 && outSize >= 4) + { + const uint16_t* __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < (inSize - 1)) && (ocount < (outSize - 3))); icount += 2, ocount += 4) + { + uint16_t t = *(sPtr++); + + uint32_t t1 = (t & 0x00e0) | ((t & 0x00e0) >> 3) | ((t & 0x00c0) >> 6); + uint32_t t2 = ((t & 0x001c) << 11) | ((t & 0x001c) << 8) | ((t & 0x0018) << 5); + uint32_t t3 = ((t & 0x0003) << 22) | ((t & 0x0003) << 20) | ((t & 0x0003) << 18) | ((t & 0x0003) << 16); + uint32_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xff000000 : ((t & 0xff00) << 16); + + *(dPtr++) = t1 | t2 | t3 | ta; + } + return true; + } + return false; + + case TEXP_LEGACY_P8: + if ((outFormat != DXGI_FORMAT_R8G8B8A8_UNORM) || !pal8) + return false; + + // D3DFMT_P8 -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 1 && outSize >= 4) + { + const uint8_t* __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < inSize) && (ocount < (outSize - 3))); ++icount, ocount += 4) + { + uint8_t t = *(sPtr++); + + *(dPtr++) = pal8[t]; + } + return true; + } + return false; + + case TEXP_LEGACY_A8P8: + if ((outFormat != DXGI_FORMAT_R8G8B8A8_UNORM) || !pal8) + return false; + + // D3DFMT_A8P8 -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 2 && outSize >= 4) + { + const uint16_t* __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < (inSize - 1)) && (ocount < (outSize - 3))); icount += 2, ocount += 4) + { + uint16_t t = *(sPtr++); + + uint32_t t1 = pal8[t & 0xff]; + uint32_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xff000000 : ((t & 0xff00) << 16); + + *(dPtr++) = t1 | ta; + } + return true; + } + return false; + + case TEXP_LEGACY_A4L4: + switch (outFormat) + { + case DXGI_FORMAT_B4G4R4A4_UNORM: + // D3DFMT_A4L4 -> DXGI_FORMAT_B4G4R4A4_UNORM + if (inSize >= 1 && outSize >= 2) + { + const uint8_t * __restrict sPtr = reinterpret_cast(pSource); + uint16_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < inSize) && (ocount < (outSize - 1))); ++icount, ocount += 2) + { + uint8_t t = *(sPtr++); + + uint16_t t1 = (t & 0x0f); + uint16_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xf000 : ((t & 0xf0) << 8); + + *(dPtr++) = t1 | (t1 << 4) | (t1 << 8) | ta; + } + return true; + } + return false; + + case DXGI_FORMAT_R8G8B8A8_UNORM: + // D3DFMT_A4L4 -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 1 && outSize >= 4) + { + const uint8_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < inSize) && (ocount < (outSize - 3))); ++icount, ocount += 4) + { + uint8_t t = *(sPtr++); + + uint32_t t1 = ((t & 0x0f) << 4) | (t & 0x0f); + uint32_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xff000000 : (((t & 0xf0) << 24) | ((t & 0xf0) << 20)); + + *(dPtr++) = t1 | (t1 << 8) | (t1 << 16) | ta; + } + return true; + } + return false; + + default: + return false; + } + break; + + case TEXP_LEGACY_B4G4R4A4: + if (outFormat != DXGI_FORMAT_R8G8B8A8_UNORM) + return false; + + // D3DFMT_A4R4G4B4 -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 2 && outSize >= 4) + { + const uint16_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < (inSize - 1)) && (ocount < (outSize - 3))); icount += 2, ocount += 4) + { + uint16_t t = *(sPtr++); + + uint32_t t1 = ((t & 0x0f00) >> 4) | ((t & 0x0f00) >> 8); + uint32_t t2 = ((t & 0x00f0) << 8) | ((t & 0x00f0) << 4); + uint32_t t3 = ((t & 0x000f) << 20) | ((t & 0x000f) << 16); + uint32_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xff000000 : (((t & 0xf000) << 16) | ((t & 0xf000) << 12)); + + *(dPtr++) = t1 | t2 | t3 | ta; + } + return true; + } + return false; + + case TEXP_LEGACY_L8: + if (outFormat != DXGI_FORMAT_R8G8B8A8_UNORM) + return false; + + // D3DFMT_L8 -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 1 && outSize >= 4) + { + const uint8_t * __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < inSize) && (ocount < (outSize - 3))); ++icount, ocount += 4) + { + uint32_t t1 = *(sPtr++); + uint32_t t2 = (t1 << 8); + uint32_t t3 = (t1 << 16); + + *(dPtr++) = t1 | t2 | t3 | 0xff000000; + } + return true; + } + return false; + + case TEXP_LEGACY_L16: + if (outFormat != DXGI_FORMAT_R16G16B16A16_UNORM) + return false; + + // D3DFMT_L16 -> DXGI_FORMAT_R16G16B16A16_UNORM + if (inSize >= 2 && outSize >= 8) + { + const uint16_t* __restrict sPtr = reinterpret_cast(pSource); + uint64_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < (inSize - 1)) && (ocount < (outSize - 7))); icount += 2, ocount += 8) + { + uint16_t t = *(sPtr++); + + uint64_t t1 = t; + uint64_t t2 = (t1 << 16); + uint64_t t3 = (t1 << 32); + + *(dPtr++) = t1 | t2 | t3 | 0xffff000000000000; + } + return true; + } + return false; + + case TEXP_LEGACY_A8L8: + if (outFormat != DXGI_FORMAT_R8G8B8A8_UNORM) + return false; + + // D3DFMT_A8L8 -> DXGI_FORMAT_R8G8B8A8_UNORM + if (inSize >= 2 && outSize >= 4) + { + const uint16_t* __restrict sPtr = reinterpret_cast(pSource); + uint32_t * __restrict dPtr = reinterpret_cast(pDestination); + + for (size_t ocount = 0, icount = 0; ((icount < (inSize - 1)) && (ocount < (outSize - 3))); icount += 2, ocount += 4) + { + uint16_t t = *(sPtr++); + + uint32_t t1 = (t & 0xff); + uint32_t t2 = (t1 << 8); + uint32_t t3 = (t1 << 16); + uint32_t ta = (flags & TEXP_SCANLINE_SETALPHA) ? 0xff000000 : ((t & 0xff00) << 16); + + *(dPtr++) = t1 | t2 | t3 | ta; + } + return true; + } + return false; + + default: + return false; + } + } + + + //------------------------------------------------------------------------------------- + // Converts or copies image data from pPixels into scratch image data + //------------------------------------------------------------------------------------- + HRESULT CopyImage( + _In_reads_bytes_(size) const void* pPixels, + _In_ size_t size, + _In_ const TexMetadata& metadata, + _In_ DWORD cpFlags, + _In_ DWORD convFlags, + _In_reads_opt_(256) const uint32_t *pal8, + _In_ const ScratchImage& image) + { + assert(pPixels); + assert(image.GetPixels()); + + if (!size) + return E_FAIL; + + if (convFlags & CONV_FLAGS_EXPAND) + { + if (convFlags & CONV_FLAGS_888) + cpFlags |= CP_FLAGS_24BPP; + else if (convFlags & (CONV_FLAGS_565 | CONV_FLAGS_5551 | CONV_FLAGS_4444 | CONV_FLAGS_8332 | CONV_FLAGS_A8P8 | CONV_FLAGS_L16 | CONV_FLAGS_A8L8)) + cpFlags |= CP_FLAGS_16BPP; + else if (convFlags & (CONV_FLAGS_44 | CONV_FLAGS_332 | CONV_FLAGS_PAL8 | CONV_FLAGS_L8)) + cpFlags |= CP_FLAGS_8BPP; + } + + size_t pixelSize, nimages; + _DetermineImageArray(metadata, cpFlags, nimages, pixelSize); + if ((nimages == 0) || (nimages != image.GetImageCount())) + { + return E_FAIL; + } + + if (pixelSize > size) + { + return HRESULT_FROM_WIN32( ERROR_HANDLE_EOF ); + } + + std::unique_ptr timages(new (std::nothrow) Image[nimages]); + if (!timages) + { + return E_OUTOFMEMORY; + } + + if (!_SetupImageArray((uint8_t*)pPixels, pixelSize, metadata, cpFlags, timages.get(), nimages)) + { + return E_FAIL; + } + + if (nimages != image.GetImageCount()) + { + return E_FAIL; + } + + const Image* images = image.GetImages(); + if (!images) + { + return E_FAIL; + } + + DWORD tflags = (convFlags & CONV_FLAGS_NOALPHA) ? TEXP_SCANLINE_SETALPHA : 0; + if (convFlags & CONV_FLAGS_SWIZZLE) + tflags |= TEXP_SCANLINE_LEGACY; + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + case TEX_DIMENSION_TEXTURE2D: + { + size_t index = 0; + for (size_t item = 0; item < metadata.arraySize; ++item) + { + size_t lastgood = 0; + for (size_t level = 0; level < metadata.mipLevels; ++level, ++index) + { + if (index >= nimages) + return E_FAIL; + + if (images[index].height != timages[index].height) + return E_FAIL; + + size_t dpitch = images[index].rowPitch; + size_t spitch = timages[index].rowPitch; + + const uint8_t *pSrc = const_cast(timages[index].pixels); + if (!pSrc) + return E_POINTER; + + uint8_t *pDest = images[index].pixels; + if (!pDest) + return E_POINTER; + + if (IsCompressed(metadata.format)) + { + size_t csize = std::min(images[index].slicePitch, timages[index].slicePitch); + memcpy_s(pDest, images[index].slicePitch, pSrc, csize); + + if (cpFlags & CP_FLAGS_BAD_DXTN_TAILS) + { + if (images[index].width < 4 || images[index].height < 4) + { + csize = std::min(images[index].slicePitch, timages[lastgood].slicePitch); + memcpy_s(pDest, images[index].slicePitch, timages[lastgood].pixels, csize); + } + else + { + lastgood = index; + } + } + } + else if (IsPlanar(metadata.format)) + { + size_t count = ComputeScanlines(metadata.format, images[index].height); + if (!count) + return E_UNEXPECTED; + + size_t csize = std::min(dpitch, spitch); + for (size_t h = 0; h < count; ++h) + { + memcpy_s(pDest, dpitch, pSrc, csize); + pSrc += spitch; + pDest += dpitch; + } + } + else + { + for (size_t h = 0; h < images[index].height; ++h) + { + if (convFlags & CONV_FLAGS_EXPAND) + { + if (convFlags & (CONV_FLAGS_565 | CONV_FLAGS_5551 | CONV_FLAGS_4444)) + { + if (!_ExpandScanline(pDest, dpitch, DXGI_FORMAT_R8G8B8A8_UNORM, + pSrc, spitch, + (convFlags & CONV_FLAGS_565) ? DXGI_FORMAT_B5G6R5_UNORM : DXGI_FORMAT_B5G5R5A1_UNORM, + tflags)) + return E_FAIL; + } + else + { + TEXP_LEGACY_FORMAT lformat = _FindLegacyFormat(convFlags); + if (!LegacyExpandScanline(pDest, dpitch, metadata.format, + pSrc, spitch, lformat, pal8, + tflags)) + return E_FAIL; + } + } + else if (convFlags & CONV_FLAGS_SWIZZLE) + { + _SwizzleScanline(pDest, dpitch, pSrc, spitch, + metadata.format, tflags); + } + else + { + _CopyScanline(pDest, dpitch, pSrc, spitch, + metadata.format, tflags); + } + + pSrc += spitch; + pDest += dpitch; + } + } + } + } + } + break; + + case TEX_DIMENSION_TEXTURE3D: + { + size_t index = 0; + size_t d = metadata.depth; + + size_t lastgood = 0; + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + for (size_t slice = 0; slice < d; ++slice, ++index) + { + if (index >= nimages) + return E_FAIL; + + if (images[index].height != timages[index].height) + return E_FAIL; + + size_t dpitch = images[index].rowPitch; + size_t spitch = timages[index].rowPitch; + + const uint8_t *pSrc = const_cast(timages[index].pixels); + if (!pSrc) + return E_POINTER; + + uint8_t *pDest = images[index].pixels; + if (!pDest) + return E_POINTER; + + if (IsCompressed(metadata.format)) + { + size_t csize = std::min(images[index].slicePitch, timages[index].slicePitch); + memcpy_s(pDest, images[index].slicePitch, pSrc, csize); + + if (cpFlags & CP_FLAGS_BAD_DXTN_TAILS) + { + if (images[index].width < 4 || images[index].height < 4) + { + csize = std::min(images[index].slicePitch, timages[lastgood + slice].slicePitch); + memcpy_s(pDest, images[index].slicePitch, timages[lastgood + slice].pixels, csize); + } + else if (!slice) + { + lastgood = index; + } + } + } + else if (IsPlanar(metadata.format)) + { + // Direct3D does not support any planar formats for Texture3D + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + else + { + for (size_t h = 0; h < images[index].height; ++h) + { + if (convFlags & CONV_FLAGS_EXPAND) + { + if (convFlags & (CONV_FLAGS_565 | CONV_FLAGS_5551 | CONV_FLAGS_4444)) + { + if (!_ExpandScanline(pDest, dpitch, DXGI_FORMAT_R8G8B8A8_UNORM, + pSrc, spitch, + (convFlags & CONV_FLAGS_565) ? DXGI_FORMAT_B5G6R5_UNORM : DXGI_FORMAT_B5G5R5A1_UNORM, + tflags)) + return E_FAIL; + } + else + { + TEXP_LEGACY_FORMAT lformat = _FindLegacyFormat(convFlags); + if (!LegacyExpandScanline(pDest, dpitch, metadata.format, + pSrc, spitch, lformat, pal8, + tflags)) + return E_FAIL; + } + } + else if (convFlags & CONV_FLAGS_SWIZZLE) + { + _SwizzleScanline(pDest, dpitch, pSrc, spitch, metadata.format, tflags); + } + else + { + _CopyScanline(pDest, dpitch, pSrc, spitch, metadata.format, tflags); + } + + pSrc += spitch; + pDest += dpitch; + } + } + } + + if (d > 1) + d >>= 1; + } + } + break; + + default: + return E_FAIL; + } + + return S_OK; + } + + HRESULT CopyImageInPlace(DWORD convFlags, _In_ const ScratchImage& image) + { + if (!image.GetPixels()) + return E_FAIL; + + const Image* images = image.GetImages(); + if (!images) + return E_FAIL; + + const TexMetadata& metadata = image.GetMetadata(); + + if (IsPlanar(metadata.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + DWORD tflags = (convFlags & CONV_FLAGS_NOALPHA) ? TEXP_SCANLINE_SETALPHA : 0; + if (convFlags & CONV_FLAGS_SWIZZLE) + tflags |= TEXP_SCANLINE_LEGACY; + + for (size_t i = 0; i < image.GetImageCount(); ++i) + { + const Image* img = &images[i]; + uint8_t *pPixels = img->pixels; + if (!pPixels) + return E_POINTER; + + size_t rowPitch = img->rowPitch; + + for (size_t h = 0; h < img->height; ++h) + { + if (convFlags & CONV_FLAGS_SWIZZLE) + { + _SwizzleScanline(pPixels, rowPitch, pPixels, rowPitch, metadata.format, tflags); + } + else + { + _CopyScanline(pPixels, rowPitch, pPixels, rowPitch, metadata.format, tflags); + } + + pPixels += rowPitch; + } + } + + return S_OK; + } +} + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Obtain metadata from DDS file in memory/on disk +//------------------------------------------------------------------------------------- + +_Use_decl_annotations_ +HRESULT DirectX::GetMetadataFromDDSMemory( + const void* pSource, + size_t size, + DWORD flags, + TexMetadata& metadata) +{ + if (!pSource || size == 0) + return E_INVALIDARG; + + DWORD convFlags = 0; + return DecodeDDSHeader(pSource, size, flags, metadata, convFlags); +} + +_Use_decl_annotations_ +HRESULT DirectX::GetMetadataFromDDSFile( + const wchar_t* szFile, + DWORD flags, + TexMetadata& metadata) +{ + if (!szFile) + return E_INVALIDARG; + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(szFile, GENERIC_READ, FILE_SHARE_READ, OPEN_EXISTING, nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(szFile, GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, + FILE_FLAG_SEQUENTIAL_SCAN, nullptr))); +#endif + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // Get the file size + FILE_STANDARD_INFO fileInfo; + if (!GetFileInformationByHandleEx(hFile.get(), FileStandardInfo, &fileInfo, sizeof(fileInfo))) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // File is too big for 32-bit allocation, so reject read (4 GB should be plenty large enough for a valid DDS file) + if (fileInfo.EndOfFile.HighPart > 0) + { + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + } + + // Need at least enough data to fill the standard header and magic number to be a valid DDS + if (fileInfo.EndOfFile.LowPart < (sizeof(DDS_HEADER) + sizeof(uint32_t))) + { + return E_FAIL; + } + + // Read the header in (including extended header if present) + const size_t MAX_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10); + uint8_t header[MAX_HEADER_SIZE]; + + DWORD bytesRead = 0; + if (!ReadFile(hFile.get(), header, MAX_HEADER_SIZE, &bytesRead, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + DWORD convFlags = 0; + return DecodeDDSHeader(header, bytesRead, flags, metadata, convFlags); +} + + +//------------------------------------------------------------------------------------- +// Load a DDS file in memory +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadFromDDSMemory( + const void* pSource, + size_t size, + DWORD flags, + TexMetadata* metadata, + ScratchImage& image) +{ + if (!pSource || size == 0) + return E_INVALIDARG; + + image.Release(); + + DWORD convFlags = 0; + TexMetadata mdata; + HRESULT hr = DecodeDDSHeader(pSource, size, flags, mdata, convFlags); + if (FAILED(hr)) + return hr; + + size_t offset = sizeof(uint32_t) + sizeof(DDS_HEADER); + if (convFlags & CONV_FLAGS_DX10) + offset += sizeof(DDS_HEADER_DXT10); + + assert(offset <= size); + + const uint32_t *pal8 = nullptr; + if (convFlags & CONV_FLAGS_PAL8) + { + pal8 = reinterpret_cast(reinterpret_cast(pSource) + offset); + assert(pal8); + offset += (256 * sizeof(uint32_t)); + if (size < offset) + return E_FAIL; + } + + hr = image.Initialize(mdata); + if (FAILED(hr)) + return hr; + + DWORD cflags = CP_FLAGS_NONE; + if (flags & DDS_FLAGS_LEGACY_DWORD) + { + cflags |= CP_FLAGS_LEGACY_DWORD; + } + if (flags & DDS_FLAGS_BAD_DXTN_TAILS) + { + cflags |= CP_FLAGS_BAD_DXTN_TAILS; + } + + auto pPixels = reinterpret_cast(reinterpret_cast(pSource) + offset); + assert(pPixels); + hr = CopyImage(pPixels, + size - offset, + mdata, + cflags, + convFlags, + pal8, + image); + if (FAILED(hr)) + { + image.Release(); + return hr; + } + if (metadata) + memcpy(metadata, &mdata, sizeof(TexMetadata)); + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Load a DDS file from disk +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadFromDDSFile( + const wchar_t* szFile, + DWORD flags, + TexMetadata* metadata, + ScratchImage& image) +{ + if (!szFile) + return E_INVALIDARG; + + image.Release(); + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(szFile, GENERIC_READ, FILE_SHARE_READ, OPEN_EXISTING, nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(szFile, GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, + FILE_FLAG_SEQUENTIAL_SCAN, nullptr))); +#endif + + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // Get the file size + FILE_STANDARD_INFO fileInfo; + if (!GetFileInformationByHandleEx(hFile.get(), FileStandardInfo, &fileInfo, sizeof(fileInfo))) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // File is too big for 32-bit allocation, so reject read (4 GB should be plenty large enough for a valid DDS file) + if (fileInfo.EndOfFile.HighPart > 0) + { + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + } + + // Need at least enough data to fill the standard header and magic number to be a valid DDS + if (fileInfo.EndOfFile.LowPart < (sizeof(DDS_HEADER) + sizeof(uint32_t))) + { + return E_FAIL; + } + + // Read the header in (including extended header if present) + const size_t MAX_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10); + uint8_t header[MAX_HEADER_SIZE]; + + DWORD bytesRead = 0; + if (!ReadFile(hFile.get(), header, MAX_HEADER_SIZE, &bytesRead, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + DWORD convFlags = 0; + TexMetadata mdata; + HRESULT hr = DecodeDDSHeader(header, bytesRead, flags, mdata, convFlags); + if (FAILED(hr)) + return hr; + + DWORD offset = MAX_HEADER_SIZE; + + if (!(convFlags & CONV_FLAGS_DX10)) + { + // Must reset file position since we read more than the standard header above + LARGE_INTEGER filePos = { { sizeof(uint32_t) + sizeof(DDS_HEADER), 0 } }; + if (!SetFilePointerEx(hFile.get(), filePos, 0, FILE_BEGIN)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + offset = sizeof(uint32_t) + sizeof(DDS_HEADER); + } + + std::unique_ptr pal8; + if (convFlags & CONV_FLAGS_PAL8) + { + pal8.reset(new (std::nothrow) uint32_t[256]); + if (!pal8) + { + return E_OUTOFMEMORY; + } + + if (!ReadFile(hFile.get(), pal8.get(), 256 * sizeof(uint32_t), &bytesRead, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesRead != (256 * sizeof(uint32_t))) + { + return E_FAIL; + } + + offset += (256 * sizeof(uint32_t)); + } + + DWORD remaining = fileInfo.EndOfFile.LowPart - offset; + if (remaining == 0) + return E_FAIL; + + hr = image.Initialize(mdata); + if (FAILED(hr)) + return hr; + + if ((convFlags & CONV_FLAGS_EXPAND) || (flags & (DDS_FLAGS_LEGACY_DWORD | DDS_FLAGS_BAD_DXTN_TAILS))) + { + std::unique_ptr temp(new (std::nothrow) uint8_t[remaining]); + if (!temp) + { + image.Release(); + return E_OUTOFMEMORY; + } + + if (!ReadFile(hFile.get(), temp.get(), remaining, &bytesRead, nullptr)) + { + image.Release(); + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesRead != remaining) + { + image.Release(); + return E_FAIL; + } + + DWORD cflags = CP_FLAGS_NONE; + if (flags & DDS_FLAGS_LEGACY_DWORD) + { + cflags |= CP_FLAGS_LEGACY_DWORD; + } + if (flags & DDS_FLAGS_BAD_DXTN_TAILS) + { + cflags |= CP_FLAGS_BAD_DXTN_TAILS; + } + + hr = CopyImage(temp.get(), + remaining, + mdata, + cflags, + convFlags, + pal8.get(), + image); + if (FAILED(hr)) + { + image.Release(); + return hr; + } + } + else + { + if (remaining < image.GetPixelsSize()) + { + image.Release(); + return HRESULT_FROM_WIN32( ERROR_HANDLE_EOF ); + } + + if (!ReadFile(hFile.get(), image.GetPixels(), static_cast(image.GetPixelsSize()), &bytesRead, nullptr)) + { + image.Release(); + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (convFlags & (CONV_FLAGS_SWIZZLE | CONV_FLAGS_NOALPHA)) + { + // Swizzle/copy image in place + hr = CopyImageInPlace(convFlags, image); + if (FAILED(hr)) + { + image.Release(); + return hr; + } + } + } + + if (metadata) + memcpy(metadata, &mdata, sizeof(TexMetadata)); + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Save a DDS file to memory +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveToDDSMemory( + const Image* images, + size_t nimages, + const TexMetadata& metadata, + DWORD flags, + Blob& blob) +{ + if (!images || (nimages == 0)) + return E_INVALIDARG; + + // Determine memory required + size_t required = 0; + HRESULT hr = _EncodeDDSHeader(metadata, flags, 0, 0, required); + if (FAILED(hr)) + return hr; + + bool fastpath = true; + + for (size_t i = 0; i < nimages; ++i) + { + if (!images[i].pixels) + return E_POINTER; + + if (images[i].format != metadata.format) + return E_FAIL; + + size_t ddsRowPitch, ddsSlicePitch; + ComputePitch(metadata.format, images[i].width, images[i].height, ddsRowPitch, ddsSlicePitch, CP_FLAGS_NONE); + + assert(images[i].rowPitch > 0); + assert(images[i].slicePitch > 0); + + if ((images[i].rowPitch != ddsRowPitch) || (images[i].slicePitch != ddsSlicePitch)) + { + fastpath = false; + } + + required += ddsSlicePitch; + } + + assert(required > 0); + + blob.Release(); + + hr = blob.Initialize(required); + if (FAILED(hr)) + return hr; + + auto pDestination = reinterpret_cast(blob.GetBufferPointer()); + assert(pDestination); + + hr = _EncodeDDSHeader(metadata, flags, pDestination, blob.GetBufferSize(), required); + if (FAILED(hr)) + { + blob.Release(); + return hr; + } + + size_t remaining = blob.GetBufferSize() - required; + pDestination += required; + + if (!remaining) + { + blob.Release(); + return E_FAIL; + } + + switch (metadata.dimension) + { + case DDS_DIMENSION_TEXTURE1D: + case DDS_DIMENSION_TEXTURE2D: + { + size_t index = 0; + for (size_t item = 0; item < metadata.arraySize; ++item) + { + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + if (index >= nimages) + { + blob.Release(); + return E_FAIL; + } + + if (fastpath) + { + size_t pixsize = images[index].slicePitch; + if (memcpy_s(pDestination, remaining, images[index].pixels, pixsize)) + { + blob.Release(); + return E_FAIL; + } + + pDestination += pixsize; + remaining -= pixsize; + } + else + { + size_t ddsRowPitch, ddsSlicePitch; + ComputePitch(metadata.format, images[index].width, images[index].height, ddsRowPitch, ddsSlicePitch, CP_FLAGS_NONE); + + size_t rowPitch = images[index].rowPitch; + + const uint8_t * __restrict sPtr = images[index].pixels; + uint8_t * __restrict dPtr = reinterpret_cast(pDestination); + + size_t lines = ComputeScanlines(metadata.format, images[index].height); + size_t csize = std::min(rowPitch, ddsRowPitch); + size_t tremaining = remaining; + for (size_t j = 0; j < lines; ++j) + { + if (memcpy_s(dPtr, tremaining, sPtr, csize)) + { + blob.Release(); + return E_FAIL; + } + + sPtr += rowPitch; + dPtr += ddsRowPitch; + tremaining -= ddsRowPitch; + } + + pDestination += ddsSlicePitch; + remaining -= ddsSlicePitch; + } + + ++index; + } + } + } + break; + + case DDS_DIMENSION_TEXTURE3D: + { + if (metadata.arraySize != 1) + { + blob.Release(); + return E_FAIL; + } + + size_t d = metadata.depth; + + size_t index = 0; + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + for (size_t slice = 0; slice < d; ++slice) + { + if (index >= nimages) + { + blob.Release(); + return E_FAIL; + } + + if (fastpath) + { + size_t pixsize = images[index].slicePitch; + if (memcpy_s(pDestination, remaining, images[index].pixels, pixsize)) + { + blob.Release(); + return E_FAIL; + } + + pDestination += pixsize; + remaining -= pixsize; + } + else + { + size_t ddsRowPitch, ddsSlicePitch; + ComputePitch(metadata.format, images[index].width, images[index].height, ddsRowPitch, ddsSlicePitch, CP_FLAGS_NONE); + + size_t rowPitch = images[index].rowPitch; + + const uint8_t * __restrict sPtr = images[index].pixels; + uint8_t * __restrict dPtr = reinterpret_cast(pDestination); + + size_t lines = ComputeScanlines(metadata.format, images[index].height); + size_t csize = std::min(rowPitch, ddsRowPitch); + size_t tremaining = remaining; + for (size_t j = 0; j < lines; ++j) + { + if (memcpy_s(dPtr, tremaining, sPtr, csize)) + { + blob.Release(); + return E_FAIL; + } + + sPtr += rowPitch; + dPtr += ddsRowPitch; + tremaining -= ddsRowPitch; + } + + pDestination += ddsSlicePitch; + remaining -= ddsSlicePitch; + } + + ++index; + } + + if (d > 1) + d >>= 1; + } + } + break; + + default: + blob.Release(); + return E_FAIL; + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Save a DDS file to disk +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveToDDSFile( + const Image* images, + size_t nimages, + const TexMetadata& metadata, + DWORD flags, + const wchar_t* szFile) +{ + if (!szFile) + return E_INVALIDARG; + + // Create DDS Header + const size_t MAX_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10); + uint8_t header[MAX_HEADER_SIZE]; + size_t required; + HRESULT hr = _EncodeDDSHeader(metadata, flags, header, MAX_HEADER_SIZE, required); + if (FAILED(hr)) + return hr; + + // Create file and write header +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(szFile, GENERIC_WRITE | DELETE, 0, CREATE_ALWAYS, nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(szFile, GENERIC_WRITE | DELETE, 0, nullptr, CREATE_ALWAYS, 0, nullptr))); +#endif + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + auto_delete_file delonfail(hFile.get()); + + DWORD bytesWritten; + if (!WriteFile(hFile.get(), header, static_cast(required), &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != required) + { + return E_FAIL; + } + + // Write images + switch (metadata.dimension) + { + case DDS_DIMENSION_TEXTURE1D: + case DDS_DIMENSION_TEXTURE2D: + { + size_t index = 0; + for (size_t item = 0; item < metadata.arraySize; ++item) + { + for (size_t level = 0; level < metadata.mipLevels; ++level, ++index) + { + if (index >= nimages) + return E_FAIL; + + if (!images[index].pixels) + return E_POINTER; + + assert(images[index].rowPitch > 0); + assert(images[index].slicePitch > 0); + + size_t ddsRowPitch, ddsSlicePitch; + ComputePitch(metadata.format, images[index].width, images[index].height, ddsRowPitch, ddsSlicePitch, CP_FLAGS_NONE); + + if (images[index].slicePitch == ddsSlicePitch) + { + if (!WriteFile(hFile.get(), images[index].pixels, static_cast(ddsSlicePitch), &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != ddsSlicePitch) + { + return E_FAIL; + } + } + else + { + size_t rowPitch = images[index].rowPitch; + if (rowPitch < ddsRowPitch) + { + // DDS uses 1-byte alignment, so if this is happening then the input pitch isn't actually a full line of data + return E_FAIL; + } + + const uint8_t * __restrict sPtr = images[index].pixels; + + size_t lines = ComputeScanlines(metadata.format, images[index].height); + for (size_t j = 0; j < lines; ++j) + { + if (!WriteFile(hFile.get(), sPtr, static_cast(ddsRowPitch), &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != ddsRowPitch) + { + return E_FAIL; + } + + sPtr += rowPitch; + } + } + } + } + } + break; + + case DDS_DIMENSION_TEXTURE3D: + { + if (metadata.arraySize != 1) + return E_FAIL; + + size_t d = metadata.depth; + + size_t index = 0; + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + for (size_t slice = 0; slice < d; ++slice, ++index) + { + if (index >= nimages) + return E_FAIL; + + if (!images[index].pixels) + return E_POINTER; + + assert(images[index].rowPitch > 0); + assert(images[index].slicePitch > 0); + + size_t ddsRowPitch, ddsSlicePitch; + ComputePitch(metadata.format, images[index].width, images[index].height, ddsRowPitch, ddsSlicePitch, CP_FLAGS_NONE); + + if (images[index].slicePitch == ddsSlicePitch) + { + if (!WriteFile(hFile.get(), images[index].pixels, static_cast(ddsSlicePitch), &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != ddsSlicePitch) + { + return E_FAIL; + } + } + else + { + size_t rowPitch = images[index].rowPitch; + if (rowPitch < ddsRowPitch) + { + // DDS uses 1-byte alignment, so if this is happening then the input pitch isn't actually a full line of data + return E_FAIL; + } + + const uint8_t * __restrict sPtr = images[index].pixels; + + size_t lines = ComputeScanlines(metadata.format, images[index].height); + for (size_t j = 0; j < lines; ++j) + { + if (!WriteFile(hFile.get(), sPtr, static_cast(ddsRowPitch), &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != ddsRowPitch) + { + return E_FAIL; + } + + sPtr += rowPitch; + } + } + } + + if (d > 1) + d >>= 1; + } + } + break; + + default: + return E_FAIL; + } + + delonfail.clear(); + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexFlipRotate.cpp b/deps/DirectXTex/DirectXTex/DirectXTexFlipRotate.cpp new file mode 100644 index 0000000..8a6ad21 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexFlipRotate.cpp @@ -0,0 +1,343 @@ +//------------------------------------------------------------------------------------- +// DirectXTexFlipRotate.cpp +// +// DirectX Texture Library - Image flip/rotate operations +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +using namespace DirectX; +using Microsoft::WRL::ComPtr; + +namespace +{ + //------------------------------------------------------------------------------------- + // Do flip/rotate operation using WIC + //------------------------------------------------------------------------------------- + HRESULT PerformFlipRotateUsingWIC( + const Image& srcImage, + DWORD flags, + const WICPixelFormatGUID& pfGUID, + const Image& destImage) + { + if (!srcImage.pixels || !destImage.pixels) + return E_POINTER; + + assert(srcImage.format == destImage.format); + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr source; + HRESULT hr = pWIC->CreateBitmapFromMemory(static_cast(srcImage.width), static_cast(srcImage.height), pfGUID, + static_cast(srcImage.rowPitch), static_cast(srcImage.slicePitch), + srcImage.pixels, source.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr FR; + hr = pWIC->CreateBitmapFlipRotator(FR.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = FR->Initialize(source.Get(), static_cast(flags)); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID pfFR; + hr = FR->GetPixelFormat(&pfFR); + if (FAILED(hr)) + return hr; + + if (memcmp(&pfFR, &pfGUID, sizeof(GUID)) != 0) + { + // Flip/rotate should return the same format as the source... + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + UINT nwidth, nheight; + hr = FR->GetSize(&nwidth, &nheight); + if (FAILED(hr)) + return hr; + + if (destImage.width != nwidth || destImage.height != nheight) + return E_FAIL; + + hr = FR->CopyPixels(0, static_cast(destImage.rowPitch), static_cast(destImage.slicePitch), destImage.pixels); + if (FAILED(hr)) + return hr; + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Do conversion, flip/rotate using WIC, conversion cycle + //------------------------------------------------------------------------------------- + HRESULT PerformFlipRotateViaF32( + const Image& srcImage, + DWORD flags, + const Image& destImage) + { + if (!srcImage.pixels || !destImage.pixels) + return E_POINTER; + + assert(srcImage.format != DXGI_FORMAT_R32G32B32A32_FLOAT); + assert(srcImage.format == destImage.format); + + ScratchImage temp; + HRESULT hr = _ConvertToR32G32B32A32(srcImage, temp); + if (FAILED(hr)) + return hr; + + const Image *tsrc = temp.GetImage(0, 0, 0); + if (!tsrc) + return E_POINTER; + + ScratchImage rtemp; + hr = rtemp.Initialize2D(DXGI_FORMAT_R32G32B32A32_FLOAT, destImage.width, destImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *tdest = rtemp.GetImage(0, 0, 0); + if (!tdest) + return E_POINTER; + + hr = PerformFlipRotateUsingWIC(*tsrc, flags, GUID_WICPixelFormat128bppRGBAFloat, *tdest); + if (FAILED(hr)) + return hr; + + temp.Release(); + + hr = _ConvertFromR32G32B32A32(*tdest, destImage); + if (FAILED(hr)) + return hr; + + return S_OK; + } +} + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Flip/rotate image +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::FlipRotate( + const Image& srcImage, + DWORD flags, + ScratchImage& image) +{ + if (!srcImage.pixels) + return E_POINTER; + + if (!flags) + return E_INVALIDARG; + + if ((srcImage.width > UINT32_MAX) || (srcImage.height > UINT32_MAX)) + return E_INVALIDARG; + + if (IsCompressed(srcImage.format)) + { + // We don't support flip/rotate operations on compressed images + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + static_assert(static_cast(TEX_FR_ROTATE0) == static_cast(WICBitmapTransformRotate0), "TEX_FR_ROTATE0 no longer matches WIC"); + static_assert(static_cast(TEX_FR_ROTATE90) == static_cast(WICBitmapTransformRotate90), "TEX_FR_ROTATE90 no longer matches WIC"); + static_assert(static_cast(TEX_FR_ROTATE180) == static_cast(WICBitmapTransformRotate180), "TEX_FR_ROTATE180 no longer matches WIC"); + static_assert(static_cast(TEX_FR_ROTATE270) == static_cast(WICBitmapTransformRotate270), "TEX_FR_ROTATE270 no longer matches WIC"); + static_assert(static_cast(TEX_FR_FLIP_HORIZONTAL) == static_cast(WICBitmapTransformFlipHorizontal), "TEX_FR_FLIP_HORIZONTAL no longer matches WIC"); + static_assert(static_cast(TEX_FR_FLIP_VERTICAL) == static_cast(WICBitmapTransformFlipVertical), "TEX_FR_FLIP_VERTICAL no longer matches WIC"); + + // Only supports 90, 180, 270, or no rotation flags... not a combination of rotation flags + switch (flags & (TEX_FR_ROTATE90 | TEX_FR_ROTATE180 | TEX_FR_ROTATE270)) + { + case 0: + case TEX_FR_ROTATE90: + case TEX_FR_ROTATE180: + case TEX_FR_ROTATE270: + break; + + default: + return E_INVALIDARG; + } + + size_t nwidth = srcImage.width; + size_t nheight = srcImage.height; + + if (flags & (TEX_FR_ROTATE90 | TEX_FR_ROTATE270)) + { + nwidth = srcImage.height; + nheight = srcImage.width; + } + + HRESULT hr = image.Initialize2D(srcImage.format, nwidth, nheight, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *rimage = image.GetImage(0, 0, 0); + if (!rimage) + { + image.Release(); + return E_POINTER; + } + + WICPixelFormatGUID pfGUID; + if (_DXGIToWIC(srcImage.format, pfGUID)) + { + // Case 1: Source format is supported by Windows Imaging Component + hr = PerformFlipRotateUsingWIC(srcImage, flags, pfGUID, *rimage); + } + else + { + // Case 2: Source format is not supported by WIC, so we have to convert, flip/rotate, and convert back + hr = PerformFlipRotateViaF32(srcImage, flags, *rimage); + } + + if (FAILED(hr)) + { + image.Release(); + return hr; + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Flip/rotate image (complex) +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::FlipRotate( + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + DWORD flags, + ScratchImage& result) +{ + if (!srcImages || !nimages) + return E_INVALIDARG; + + if (IsCompressed(metadata.format)) + { + // We don't support flip/rotate operations on compressed images + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + static_assert(static_cast(TEX_FR_ROTATE0) == static_cast(WICBitmapTransformRotate0), "TEX_FR_ROTATE0 no longer matches WIC"); + static_assert(static_cast(TEX_FR_ROTATE90) == static_cast(WICBitmapTransformRotate90), "TEX_FR_ROTATE90 no longer matches WIC"); + static_assert(static_cast(TEX_FR_ROTATE180) == static_cast(WICBitmapTransformRotate180), "TEX_FR_ROTATE180 no longer matches WIC"); + static_assert(static_cast(TEX_FR_ROTATE270) == static_cast(WICBitmapTransformRotate270), "TEX_FR_ROTATE270 no longer matches WIC"); + static_assert(static_cast(TEX_FR_FLIP_HORIZONTAL) == static_cast(WICBitmapTransformFlipHorizontal), "TEX_FR_FLIP_HORIZONTAL no longer matches WIC"); + static_assert(static_cast(TEX_FR_FLIP_VERTICAL) == static_cast(WICBitmapTransformFlipVertical), "TEX_FR_FLIP_VERTICAL no longer matches WIC"); + + // Only supports 90, 180, 270, or no rotation flags... not a combination of rotation flags + switch (flags & (TEX_FR_ROTATE90 | TEX_FR_ROTATE180 | TEX_FR_ROTATE270)) + { + case 0: + case TEX_FR_ROTATE90: + case TEX_FR_ROTATE180: + case TEX_FR_ROTATE270: + break; + + default: + return E_INVALIDARG; + } + + TexMetadata mdata2 = metadata; + + bool flipwh = false; + if (flags & (TEX_FR_ROTATE90 | TEX_FR_ROTATE270)) + { + flipwh = true; + mdata2.width = metadata.height; + mdata2.height = metadata.width; + } + + HRESULT hr = result.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + if (nimages != result.GetImageCount()) + { + result.Release(); + return E_FAIL; + } + + const Image* dest = result.GetImages(); + if (!dest) + { + result.Release(); + return E_POINTER; + } + + WICPixelFormatGUID pfGUID; + bool wicpf = _DXGIToWIC(metadata.format, pfGUID); + + for (size_t index = 0; index < nimages; ++index) + { + const Image& src = srcImages[index]; + if (src.format != metadata.format) + { + result.Release(); + return E_FAIL; + } + + if ((src.width > UINT32_MAX) || (src.height > UINT32_MAX)) + return E_FAIL; + + const Image& dst = dest[index]; + assert(dst.format == metadata.format); + + if (flipwh) + { + if (src.width != dst.height || src.height != dst.width) + { + result.Release(); + return E_FAIL; + } + } + else + { + if (src.width != dst.width || src.height != dst.height) + { + result.Release(); + return E_FAIL; + } + } + + if (wicpf) + { + // Case 1: Source format is supported by Windows Imaging Component + hr = PerformFlipRotateUsingWIC(src, flags, pfGUID, dst); + } + else + { + // Case 2: Source format is not supported by WIC, so we have to convert, flip/rotate, and convert back + hr = PerformFlipRotateViaF32(src, flags, dst); + } + + if (FAILED(hr)) + { + result.Release(); + return hr; + } + } + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexHDR.cpp b/deps/DirectXTex/DirectXTex/DirectXTexHDR.cpp new file mode 100644 index 0000000..5d1925c --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexHDR.cpp @@ -0,0 +1,1114 @@ +//------------------------------------------------------------------------------------- +// DirectXTexHDR.cpp +// +// DirectX Texture Library - Radiance HDR (RGBE) file format reader/writer +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +// +// In theory HDR (RGBE) Radiance files can have any of the following data orientations +// +// +X width +Y height +// +X width -Y height +// -X width +Y height +// -X width -Y height +// +Y height +X width +// -Y height +X width +// +Y height -X width +// -Y height -X width +// +// All HDR files we've encountered are always written as "-Y height +X width", so +// we support only that one as that's what other Radiance parsing code does as well. +// + +//Uncomment to disable the use of adapative RLE encoding when writing an HDR. Used for testing only. +//#define DISABLE_COMPRESS + +//Uncomment to use "old colors" standard RLE encoding when writing an HDR. Used for testing only. +//#define WRITE_OLD_COLORS + +using namespace DirectX; + +namespace +{ + const char g_Signature[] = "#?RADIANCE"; + const char g_Format[] = "FORMAT="; + const char g_Exposure[] = "EXPOSURE="; + + const char g_sRGBE[] = "32-bit_rle_rgbe"; + const char g_sXYZE[] = "32-bit_rle_xyze"; + + const char g_Header[] = + "#?RADIANCE\n"\ + "FORMAT=32-bit_rle_rgbe\n"\ + "\n"\ + "-Y %u +X %u\n"; + + inline size_t FindEOL(const char* str, size_t maxlen) + { + size_t pos = 0; + + while (pos < maxlen) + { + if (str[pos] == '\n') + return pos; + else if (str[pos] == '\0') + return size_t(-1); + ++pos; + } + + return 0; + } + + //------------------------------------------------------------------------------------- + // Decodes HDR header + //------------------------------------------------------------------------------------- + HRESULT DecodeHDRHeader( + _In_reads_bytes_(size) const void* pSource, + size_t size, + _Out_ TexMetadata& metadata, + size_t& offset, + float& exposure) + { + if (!pSource) + return E_INVALIDARG; + + memset(&metadata, 0, sizeof(TexMetadata)); + + exposure = 1.f; + + if (size < sizeof(g_Signature)) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + // Verify magic signature + if (memcmp(pSource, g_Signature, sizeof(g_Signature) - 1) != 0) + { + return E_FAIL; + } + + // Process first part of header + bool formatFound = false; + const char* info = reinterpret_cast(pSource); + while (size > 0) + { + if (*info == '\n') + { + ++info; + --size; + break; + } + + const size_t formatLen = sizeof(g_Format) - 1; + const size_t exposureLen = sizeof(g_Exposure) - 1; + if ((size > formatLen) && memcmp(info, g_Format, formatLen) == 0) + { + info += formatLen; + size -= formatLen; + + // Trim whitespace + while (*info == ' ' || *info == '\t') + { + if (--size == 0) + return E_FAIL; + ++info; + } + + static_assert(sizeof(g_sRGBE) == sizeof(g_sXYZE), "Format strings length mismatch"); + + const size_t encodingLen = sizeof(g_sRGBE) - 1; + + if (size < encodingLen) + { + return E_FAIL; + } + + if (memcmp(info, g_sRGBE, encodingLen) != 0 && memcmp(info, g_sXYZE, encodingLen) != 0) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + formatFound = true; + + size_t len = FindEOL(info, size); + if (len == size_t(-1)) + { + return E_FAIL; + } + + info += len + 1; + size -= len + 1; + } + else if ((size > exposureLen) && memcmp(info, g_Exposure, exposureLen) == 0) + { + info += exposureLen; + size -= exposureLen; + + // Trim whitespace + while (*info == ' ' || *info == '\t') + { + if (--size == 0) + return E_FAIL; + ++info; + } + + size_t len = FindEOL(info, size); + if (len == size_t(-1) + || len < 1) + { + return E_FAIL; + } + + char buff[32] = {}; + strncpy_s(buff, info, std::min(31, len)); + + float newExposure = static_cast(atof(buff)); + if ((newExposure >= 1e-12) && (newExposure <= 1e12)) + { + // Note that we ignore strange exposure values (like EXPOSURE=0) + exposure *= newExposure; + } + + info += len + 1; + size -= len + 1; + } + else + { + size_t len = FindEOL(info, size); + if (len == size_t(-1)) + { + return E_FAIL; + } + + info += len + 1; + size -= len + 1; + } + } + + if (!formatFound) + { + return E_FAIL; + } + + // Get orientation + char orient[256] = {}; + + size_t len = FindEOL(info, std::min(sizeof(orient), size - 1)); + if (len == size_t(-1) + || len <= 2) + { + return E_FAIL; + } + + strncpy_s(orient, info, len); + + if (orient[0] != '-' && orient[1] != 'Y') + { + // We only support the -Y +X orientation (see top of file) + return HRESULT_FROM_WIN32( + ((orient[0] == '+' || orient[0] == '-') && (orient[1] == 'X' || orient[1] == 'Y')) + ? ERROR_NOT_SUPPORTED : ERROR_INVALID_DATA + ); + } + + uint32_t height = 0; + if (sscanf_s(orient + 2, "%u", &height) != 1) + { + return E_FAIL; + } + + const char* ptr = orient + 2; + while (*ptr != 0 && *ptr != '-' && *ptr != '+') + ++ptr; + + if (*ptr == 0) + { + return E_FAIL; + } + else if (*ptr != '+') + { + // We only support the -Y +X orientation (see top of file) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + ++ptr; + if (*ptr == 0 || (*ptr != 'X' && *ptr != 'Y')) + { + return E_FAIL; + } + else if (*ptr != 'X') + { + // We only support the -Y +X orientation (see top of file) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + ++ptr; + uint32_t width; + if (sscanf_s(ptr, "%u", &width) != 1) + { + return E_FAIL; + } + + info += len + 1; + size -= len + 1; + + if (!width || !height) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + if (size == 0) + { + return E_FAIL; + } + + offset = info - reinterpret_cast(pSource); + + metadata.width = width; + metadata.height = height; + metadata.depth = metadata.arraySize = metadata.mipLevels = 1; + metadata.format = DXGI_FORMAT_R32G32B32A32_FLOAT; + metadata.dimension = TEX_DIMENSION_TEXTURE2D; + + return S_OK; + } + + //------------------------------------------------------------------------------------- + // FloatToRGBE + //------------------------------------------------------------------------------------- + inline void FloatToRGBE(_Out_writes_(width*4) uint8_t* pDestination, _In_reads_(width*fpp) const float* pSource, size_t width, _In_range_(3, 4) int fpp) + { + auto ePtr = pSource + width * fpp; + + for (size_t j = 0; j < width; ++j) + { + if (pSource + 2 >= ePtr) break; + float r = pSource[0] >= 0.f ? pSource[0] : 0.f; + float g = pSource[1] >= 0.f ? pSource[1] : 0.f; + float b = pSource[2] >= 0.f ? pSource[2] : 0.f; + pSource += fpp; + + const float max_xy = (r > g) ? r : g; + float max_xyz = (max_xy > b) ? max_xy : b; + + if (max_xyz > 1e-32) + { + int e; + max_xyz = frexpf(max_xyz, &e) * 256.f / max_xyz; + e += 128; + + uint8_t red = uint8_t(r * max_xyz); + uint8_t green = uint8_t(g * max_xyz); + uint8_t blue = uint8_t(b * max_xyz); + + pDestination[0] = red; + pDestination[1] = green; + pDestination[2] = blue; + pDestination[3] = (red || green || blue) ? uint8_t(e & 0xff) : 0; + } + else + { + pDestination[0] = pDestination[1] = pDestination[2] = pDestination[3] = 0; + } + + pDestination += 4; + } + } + + //------------------------------------------------------------------------------------- + // Encode using Adapative RLE + //------------------------------------------------------------------------------------- + _Success_(return > 0) + size_t EncodeRLE(_Out_writes_(width * 4) uint8_t* enc, _In_reads_(width * 4) const uint8_t* rgbe, size_t rowPitch, size_t width) + { + if (width < 8 || width > 32767) + { + // Don't try to compress too narrow or too wide scan-lines + return 0; + } + +#ifdef WRITE_OLD_COLORS + size_t encSize = 0; + + const uint8_t* scanPtr = rgbe; + for (size_t pixelCount = 0; pixelCount < width;) + { + size_t spanLen = 1; + const uint32_t* spanPtr = reinterpret_cast(scanPtr); + while (pixelCount + spanLen < width && spanLen < 32767) + { + if (spanPtr[spanLen] == *spanPtr) + { + ++spanLen; + } + else + break; + } + + if (spanLen > 2) + { + if (scanPtr[0] == 1 && scanPtr[1] == 1 && scanPtr[2] == 1) + { + return 0; + } + + if (encSize + 8 > rowPitch) + return 0; + + uint8_t rleLen = static_cast(std::min(spanLen - 1, 255)); + + enc[0] = scanPtr[0]; + enc[1] = scanPtr[1]; + enc[2] = scanPtr[2]; + enc[3] = scanPtr[3]; + enc[4] = 1; + enc[5] = 1; + enc[6] = 1; + enc[7] = rleLen; + enc += 8; + encSize += 8; + + size_t remaining = spanLen - 1 - rleLen; + + if (remaining > 0) + { + rleLen = static_cast(remaining >> 8); + + if (rleLen > 0) + { + if (encSize + 4 > rowPitch) + return 0; + + enc[0] = 1; + enc[1] = 1; + enc[2] = 1; + enc[3] = rleLen; + enc += 4; + encSize += 4; + + remaining -= (rleLen << 8); + } + + while (remaining > 0) + { + if (encSize + 4 > rowPitch) + return 0; + + enc[0] = scanPtr[0]; + enc[1] = scanPtr[1]; + enc[2] = scanPtr[2]; + enc[3] = scanPtr[3]; + enc += 4; + encSize += 4; + + --remaining; + } + } + + scanPtr += spanLen * 4; + pixelCount += spanLen; + } + else if (scanPtr[0] == 1 && scanPtr[1] == 1 && scanPtr[2] == 1) + { + return 0; + } + else + { + if (encSize + 4 > rowPitch) + return 0; + + enc[0] = scanPtr[0]; + enc[1] = scanPtr[1]; + enc[2] = scanPtr[2]; + enc[3] = scanPtr[3]; + enc += 4; + encSize += 4; + ++pixelCount; + scanPtr += 4; + } + } + + return encSize; +#else + enc[0] = 2; + enc[1] = 2; + enc[2] = uint8_t(width >> 8); + enc[3] = uint8_t(width & 0xff); + enc += 4; + size_t encSize = 4; + + uint8_t scan[128] = {}; + + for (int channel = 0; channel < 4; ++channel) + { + const uint8_t* spanPtr = rgbe + channel; + for (size_t pixelCount = 0; pixelCount < width;) + { + uint8_t spanLen = 1; + while (pixelCount + spanLen < width && spanLen < 127) + { + if (spanPtr[spanLen * 4] == *spanPtr) + { + ++spanLen; + } + else + break; + } + + if (spanLen > 1) + { + if (encSize + 2 > rowPitch) + return 0; + + enc[0] = 128 + spanLen; + enc[1] = *spanPtr; + enc += 2; + encSize += 2; + spanPtr += spanLen * 4; + pixelCount += spanLen; + } + else + { + uint8_t runLen = 1; + scan[0] = *spanPtr; + while (pixelCount + runLen < width && runLen < 127) + { + if (spanPtr[(runLen - 1) * 4] != spanPtr[runLen * 4]) + { + scan[runLen] = spanPtr[runLen * 4]; + runLen++; + } + else + break; + } + + if (encSize + runLen + 1 > rowPitch) + return 0; + + *enc++ = runLen; + memcpy(enc, scan, runLen); + enc += runLen; + encSize += runLen + 1; + spanPtr += runLen * 4; + pixelCount += runLen; + } + } + } + + return encSize; +#endif + } +} + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Obtain metadata from HDR file in memory/on disk +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::GetMetadataFromHDRMemory(const void* pSource, size_t size, TexMetadata& metadata) +{ + if (!pSource || size == 0) + return E_INVALIDARG; + + size_t offset; + float exposure; + return DecodeHDRHeader(pSource, size, metadata, offset, exposure); +} + +_Use_decl_annotations_ +HRESULT DirectX::GetMetadataFromHDRFile(const wchar_t* szFile, TexMetadata& metadata) +{ + if (!szFile) + return E_INVALIDARG; + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(szFile, GENERIC_READ, FILE_SHARE_READ, OPEN_EXISTING, nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(szFile, GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, + FILE_FLAG_SEQUENTIAL_SCAN, nullptr))); +#endif + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // Get the file size + FILE_STANDARD_INFO fileInfo; + if (!GetFileInformationByHandleEx(hFile.get(), FileStandardInfo, &fileInfo, sizeof(fileInfo))) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // File is too big for 32-bit allocation, so reject read (4 GB should be plenty large enough for a valid HDR file) + if (fileInfo.EndOfFile.HighPart > 0) + { + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + } + + // Need at least enough data to fill the standard header to be a valid HDR + if (fileInfo.EndOfFile.LowPart < sizeof(g_Signature)) + { + return E_FAIL; + } + + // Read the first part of the file to find the header + uint8_t header[8192]; + DWORD bytesRead = 0; + if (!ReadFile(hFile.get(), header, std::min(sizeof(header), fileInfo.EndOfFile.LowPart), &bytesRead, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + size_t offset; + float exposure; + return DecodeHDRHeader(header, bytesRead, metadata, offset, exposure); +} + + +//------------------------------------------------------------------------------------- +// Load a HDR file in memory +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadFromHDRMemory(const void* pSource, size_t size, TexMetadata* metadata, ScratchImage& image) +{ + if (!pSource || size == 0) + return E_INVALIDARG; + + image.Release(); + + size_t offset; + float exposure; + TexMetadata mdata; + HRESULT hr = DecodeHDRHeader(pSource, size, mdata, offset, exposure); + if (FAILED(hr)) + return hr; + + if (offset > size) + return E_FAIL; + + size_t remaining = size - offset; + if (remaining == 0) + return E_FAIL; + + hr = image.Initialize2D(mdata.format, mdata.width, mdata.height, 1, 1); + if (FAILED(hr)) + return hr; + + // Copy pixels + auto sourcePtr = reinterpret_cast(pSource) + offset; + + size_t pixelLen = remaining; + + const Image* img = image.GetImage(0, 0, 0); + if (!img) + { + image.Release(); + return E_POINTER; + } + + auto destPtr = img->pixels; + +#ifdef _DEBUG + memset(img->pixels, 0xFF, img->rowPitch * img->height); +#endif + + for (size_t scan = 0; scan < mdata.height; ++scan) + { + if (pixelLen < 4) + { + image.Release(); + return E_FAIL; + } + + uint8_t inColor[4]; + memcpy(inColor, sourcePtr, 4); + sourcePtr += 4; + pixelLen -= 4; + + auto scanLine = reinterpret_cast(destPtr); + + if (inColor[0] == 2 && inColor[1] == 2 && inColor[2] < 128) + { + // Adaptive Run Length Encoding (RLE) + if (size_t((inColor[2] << 8) + inColor[3]) != mdata.width) + { + image.Release(); + return E_FAIL; + } + + for (int channel = 0; channel < 4; ++channel) + { + auto pixelLoc = scanLine + channel; + for(size_t pixelCount = 0; pixelCount < mdata.width;) + { + if (pixelLen < 2) + { + image.Release(); + return E_FAIL; + } + + assert(sourcePtr < (reinterpret_cast(pSource) + size)); + + uint8_t runLen = *sourcePtr; + if (runLen > 128) + { + runLen &= 127; + if (pixelCount + runLen > mdata.width) + { + image.Release(); + return E_FAIL; + } + + float val = static_cast(sourcePtr[1]); + for (uint8_t j = 0; j < runLen; ++j) + { + *pixelLoc = val; + pixelLoc += 4; + } + pixelCount += runLen; + sourcePtr += 2; + pixelLen -= 2; + } + else if ((size < size_t(runLen + 1)) || ((pixelCount + runLen) > mdata.width)) + { + image.Release(); + return E_FAIL; + } + else + { + ++sourcePtr; + for (uint8_t j = 0; j < runLen; ++j) + { + float val = static_cast(*sourcePtr++); + *pixelLoc = val; + pixelLoc += 4; + } + pixelCount += runLen; + pixelLen -= runLen + 1; + } + } + } + } + else + { + auto pixelLoc = scanLine; + + float prevColor[4]; + prevColor[0] = inColor[0]; + prevColor[1] = inColor[1]; + prevColor[2] = inColor[2]; + prevColor[3] = inColor[3]; + + int bitShift = 0; + for (size_t pixelCount = 0; pixelCount < mdata.width;) + { + if (inColor[0] == 1 && inColor[1] == 1 && inColor[2] == 1) + { + if (bitShift > 24) + { + image.Release(); + return E_FAIL; + } + + // "Standard" Run Length Encoding + size_t spanLen = size_t(inColor[3]) << bitShift; + if (spanLen + pixelCount > mdata.width) + { + image.Release(); + return E_FAIL; + } + + for (size_t j = 0; j < spanLen; ++j) + { + pixelLoc[0] = prevColor[0]; + pixelLoc[1] = prevColor[1]; + pixelLoc[2] = prevColor[2]; + pixelLoc[3] = prevColor[3]; + pixelLoc += 4; + } + pixelCount += spanLen; + bitShift += 8; + } + else + { + // Uncompressed + pixelLoc[0] = prevColor[0] = inColor[0]; + pixelLoc[1] = prevColor[1] = inColor[1]; + pixelLoc[2] = prevColor[2] = inColor[2]; + pixelLoc[3] = prevColor[3] = inColor[3]; + bitShift = 0; + ++pixelCount; + pixelLoc += 4; + } + + if (pixelCount >= mdata.width) + break; + + if (pixelLen < 4) + { + image.Release(); + return E_FAIL; + } + + memcpy(inColor, sourcePtr, 4); + sourcePtr += 4; + pixelLen -= 4; + } + } + + destPtr += img->rowPitch; + } + + // Transform values + { + auto fdata = reinterpret_cast(image.GetPixels()); + + for (size_t j = 0; j < image.GetPixelsSize(); j += 16) + { + int exponent = static_cast(fdata[3]); + fdata[0] = 1.0f / exposure*ldexpf((fdata[0] + 0.5f), exponent - (128 + 8)); + fdata[1] = 1.0f / exposure*ldexpf((fdata[1] + 0.5f), exponent - (128 + 8)); + fdata[2] = 1.0f / exposure*ldexpf((fdata[2] + 0.5f), exponent - (128 + 8)); + fdata[3] = 1.f; + + fdata += 4; + } + } + + if (metadata) + memcpy(metadata, &mdata, sizeof(TexMetadata)); + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Load a HDR file from disk +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadFromHDRFile(const wchar_t* szFile, TexMetadata* metadata, ScratchImage& image) +{ + if (!szFile) + return E_INVALIDARG; + + image.Release(); + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(szFile, GENERIC_READ, FILE_SHARE_READ, OPEN_EXISTING, nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(szFile, GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, + FILE_FLAG_SEQUENTIAL_SCAN, nullptr))); +#endif + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // Get the file size + FILE_STANDARD_INFO fileInfo; + if (!GetFileInformationByHandleEx(hFile.get(), FileStandardInfo, &fileInfo, sizeof(fileInfo))) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // File is too big for 32-bit allocation, so reject read (4 GB should be plenty large enough for a valid HDR file) + if (fileInfo.EndOfFile.HighPart > 0) + { + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + } + + // Need at least enough data to fill the header to be a valid HDR + if (fileInfo.EndOfFile.LowPart < sizeof(g_Signature)) + { + return E_FAIL; + } + + // Read file + std::unique_ptr temp(new (std::nothrow) uint8_t[fileInfo.EndOfFile.LowPart]); + if (!temp) + { + return E_OUTOFMEMORY; + } + + DWORD bytesRead = 0; + if (!ReadFile(hFile.get(), temp.get(), fileInfo.EndOfFile.LowPart, &bytesRead, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesRead != fileInfo.EndOfFile.LowPart) + { + return E_FAIL; + } + + return LoadFromHDRMemory(temp.get(), fileInfo.EndOfFile.LowPart, metadata, image); +} + + +//------------------------------------------------------------------------------------- +// Save a HDR file to memory +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveToHDRMemory(const Image& image, Blob& blob) +{ + if (!image.pixels) + return E_POINTER; + + if (image.width > 32767 || image.height > 32767) + { + // Images larger than this can't be RLE encoded. They are technically allowed as + // uncompresssed, but we just don't support them. + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + int fpp; + switch (image.format) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: + fpp = 4; + break; + + case DXGI_FORMAT_R32G32B32_FLOAT: + fpp = 3; + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + blob.Release(); + + char header[256] = {}; + sprintf_s(header, g_Header, image.height, image.width); + + auto headerLen = static_cast(strlen(header)); + + size_t rowPitch = image.width * 4; + size_t slicePitch = image.height * rowPitch; + + HRESULT hr = blob.Initialize(headerLen + slicePitch); + if (FAILED(hr)) + return hr; + + // Copy header + auto dPtr = reinterpret_cast(blob.GetBufferPointer()); + assert(dPtr != 0); + memcpy_s(dPtr, blob.GetBufferSize(), header, headerLen); + dPtr += headerLen; + +#ifdef DISABLE_COMPRESS + // Uncompressed write + auto sPtr = reinterpret_cast(image.pixels); + for (size_t scan = 0; scan < image.height; ++scan) + { + FloatToRGBE(dPtr, reinterpret_cast(sPtr), image.width, fpp); + dPtr += rowPitch; + sPtr += image.rowPitch; + } +#else + std::unique_ptr temp(new (std::nothrow) uint8_t[rowPitch * 2]); + if (!temp) + { + blob.Release(); + return E_OUTOFMEMORY; + } + + auto rgbe = temp.get(); + auto enc = temp.get() + rowPitch; + + auto sPtr = reinterpret_cast(image.pixels); + for (size_t scan = 0; scan < image.height; ++scan) + { + FloatToRGBE(rgbe, reinterpret_cast(sPtr), image.width, fpp); + sPtr += image.rowPitch; + + size_t encSize = EncodeRLE(enc, rgbe, rowPitch, image.width); + if (encSize > 0) + { + memcpy(dPtr, enc, encSize); + dPtr += encSize; + } + else + { + memcpy(dPtr, rgbe, rowPitch); + dPtr += rowPitch; + } + } +#endif + + hr = blob.Trim(dPtr - reinterpret_cast(blob.GetBufferPointer())); + if (FAILED(hr)) + { + blob.Release(); + return hr; + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Save a HDR file to disk +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveToHDRFile(const Image& image, const wchar_t* szFile) +{ + if (!szFile) + return E_INVALIDARG; + + if (!image.pixels) + return E_POINTER; + + if (image.width > 32767 || image.height > 32767) + { + // Images larger than this can't be RLE encoded. They are technically allowed as + // uncompresssed, but we just don't support them. + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + int fpp; + switch (image.format) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: + fpp = 4; + break; + + case DXGI_FORMAT_R32G32B32_FLOAT: + fpp = 3; + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + // Create file and write header +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(szFile, GENERIC_WRITE, 0, CREATE_ALWAYS, nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(szFile, GENERIC_WRITE, 0, nullptr, CREATE_ALWAYS, 0, nullptr))); +#endif + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + auto_delete_file delonfail(hFile.get()); + + size_t rowPitch = image.width * 4; + size_t slicePitch = image.height * rowPitch; + + if (slicePitch < 65535) + { + // For small images, it is better to create an in-memory file and write it out + Blob blob; + + HRESULT hr = SaveToHDRMemory(image, blob); + if (FAILED(hr)) + return hr; + + // Write blob + const DWORD bytesToWrite = static_cast(blob.GetBufferSize()); + DWORD bytesWritten; + if (!WriteFile(hFile.get(), blob.GetBufferPointer(), bytesToWrite, &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != bytesToWrite) + { + return E_FAIL; + } + } + else + { + // Otherwise, write the image one scanline at a time... + std::unique_ptr temp(new (std::nothrow) uint8_t[rowPitch * 2]); + if (!temp) + return E_OUTOFMEMORY; + + auto rgbe = temp.get(); + + // Write header + char header[256] = {}; + sprintf_s(header, g_Header, image.height, image.width); + + auto headerLen = static_cast(strlen(header)); + + DWORD bytesWritten; + if (!WriteFile(hFile.get(), header, headerLen, &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != headerLen) + return E_FAIL; + +#ifdef DISABLE_COMPRESS + // Uncompressed write + auto sPtr = reinterpret_cast(image.pixels); + for (size_t scan = 0; scan < image.height; ++scan) + { + FloatToRGBE(rgbe, reinterpret_cast(sPtr), image.width, fpp); + sPtr += image.rowPitch; + + if (!WriteFile(hFile.get(), rgbe, static_cast(rowPitch), &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != rowPitch) + return E_FAIL; + } +#else + auto enc = temp.get() + rowPitch; + + auto sPtr = reinterpret_cast(image.pixels); + for (size_t scan = 0; scan < image.height; ++scan) + { + FloatToRGBE(rgbe, reinterpret_cast(sPtr), image.width, fpp); + sPtr += image.rowPitch; + + size_t encSize = EncodeRLE(enc, rgbe, rowPitch, image.width); + if (encSize > 0) + { + if (!WriteFile(hFile.get(), enc, static_cast(encSize), &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != encSize) + return E_FAIL; + } + else + { + if (!WriteFile(hFile.get(), rgbe, static_cast(rowPitch), &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != rowPitch) + return E_FAIL; + } + } +#endif + } + + delonfail.clear(); + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexImage.cpp b/deps/DirectXTex/DirectXTex/DirectXTexImage.cpp new file mode 100644 index 0000000..5a6077f --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexImage.cpp @@ -0,0 +1,801 @@ +//------------------------------------------------------------------------------------- +// DirectXTexImage.cpp +// +// DirectX Texture Library - Image container +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +namespace DirectX +{ + extern bool _CalculateMipLevels(_In_ size_t width, _In_ size_t height, _Inout_ size_t& mipLevels); + extern bool _CalculateMipLevels3D(_In_ size_t width, _In_ size_t height, _In_ size_t depth, _Inout_ size_t& mipLevels); + extern bool _IsAlphaAllOpaqueBC(_In_ const Image& cImage); +} + +using namespace DirectX; + +//------------------------------------------------------------------------------------- +// Determines number of image array entries and pixel size +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DirectX::_DetermineImageArray( + const TexMetadata& metadata, + DWORD cpFlags, + size_t& nImages, + size_t& pixelSize) +{ + assert(metadata.width > 0 && metadata.height > 0 && metadata.depth > 0); + assert(metadata.arraySize > 0); + assert(metadata.mipLevels > 0); + + size_t _pixelSize = 0; + size_t _nimages = 0; + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + case TEX_DIMENSION_TEXTURE2D: + for (size_t item = 0; item < metadata.arraySize; ++item) + { + size_t w = metadata.width; + size_t h = metadata.height; + + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + size_t rowPitch, slicePitch; + ComputePitch(metadata.format, w, h, rowPitch, slicePitch, cpFlags); + + _pixelSize += slicePitch; + ++_nimages; + + if (h > 1) + h >>= 1; + + if (w > 1) + w >>= 1; + } + } + break; + + case TEX_DIMENSION_TEXTURE3D: + { + size_t w = metadata.width; + size_t h = metadata.height; + size_t d = metadata.depth; + + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + size_t rowPitch, slicePitch; + ComputePitch(metadata.format, w, h, rowPitch, slicePitch, cpFlags); + + for (size_t slice = 0; slice < d; ++slice) + { + _pixelSize += slicePitch; + ++_nimages; + } + + if (h > 1) + h >>= 1; + + if (w > 1) + w >>= 1; + + if (d > 1) + d >>= 1; + } + } + break; + + default: + assert(false); + break; + } + + nImages = _nimages; + pixelSize = _pixelSize; +} + + +//------------------------------------------------------------------------------------- +// Fills in the image array entries +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::_SetupImageArray( + uint8_t *pMemory, + size_t pixelSize, + const TexMetadata& metadata, + DWORD cpFlags, + Image* images, + size_t nImages) +{ + assert(pMemory); + assert(pixelSize > 0); + assert(nImages > 0); + + if (!images) + return false; + + size_t index = 0; + uint8_t* pixels = pMemory; + const uint8_t* pEndBits = pMemory + pixelSize; + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + case TEX_DIMENSION_TEXTURE2D: + if (metadata.arraySize == 0 || metadata.mipLevels == 0) + { + return false; + } + + for (size_t item = 0; item < metadata.arraySize; ++item) + { + size_t w = metadata.width; + size_t h = metadata.height; + + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + if (index >= nImages) + { + return false; + } + + size_t rowPitch, slicePitch; + ComputePitch(metadata.format, w, h, rowPitch, slicePitch, cpFlags); + + images[index].width = w; + images[index].height = h; + images[index].format = metadata.format; + images[index].rowPitch = rowPitch; + images[index].slicePitch = slicePitch; + images[index].pixels = pixels; + ++index; + + pixels += slicePitch; + if (pixels > pEndBits) + { + return false; + } + + if (h > 1) + h >>= 1; + + if (w > 1) + w >>= 1; + } + } + return true; + + case TEX_DIMENSION_TEXTURE3D: + { + if (metadata.mipLevels == 0 || metadata.depth == 0) + { + return false; + } + + size_t w = metadata.width; + size_t h = metadata.height; + size_t d = metadata.depth; + + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + size_t rowPitch, slicePitch; + ComputePitch(metadata.format, w, h, rowPitch, slicePitch, cpFlags); + + for (size_t slice = 0; slice < d; ++slice) + { + if (index >= nImages) + { + return false; + } + + // We use the same memory organization that Direct3D 11 needs for D3D11_SUBRESOURCE_DATA + // with all slices of a given miplevel being continuous in memory + images[index].width = w; + images[index].height = h; + images[index].format = metadata.format; + images[index].rowPitch = rowPitch; + images[index].slicePitch = slicePitch; + images[index].pixels = pixels; + ++index; + + pixels += slicePitch; + if (pixels > pEndBits) + { + return false; + } + } + + if (h > 1) + h >>= 1; + + if (w > 1) + w >>= 1; + + if (d > 1) + d >>= 1; + } + } + return true; + + default: + return false; + } +} + + +//===================================================================================== +// ScratchImage - Bitmap image container +//===================================================================================== + +ScratchImage& ScratchImage::operator= (ScratchImage&& moveFrom) +{ + if (this != &moveFrom) + { + Release(); + + m_nimages = moveFrom.m_nimages; + m_size = moveFrom.m_size; + m_metadata = moveFrom.m_metadata; + m_image = moveFrom.m_image; + m_memory = moveFrom.m_memory; + + moveFrom.m_nimages = 0; + moveFrom.m_size = 0; + moveFrom.m_image = nullptr; + moveFrom.m_memory = nullptr; + } + return *this; +} + + +//------------------------------------------------------------------------------------- +// Methods +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT ScratchImage::Initialize(const TexMetadata& mdata, DWORD flags) +{ + if (!IsValid(mdata.format)) + return E_INVALIDARG; + + if (IsPalettized(mdata.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + size_t mipLevels = mdata.mipLevels; + + switch (mdata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + if (!mdata.width || mdata.height != 1 || mdata.depth != 1 || !mdata.arraySize) + return E_INVALIDARG; + + if (!_CalculateMipLevels(mdata.width, 1, mipLevels)) + return E_INVALIDARG; + break; + + case TEX_DIMENSION_TEXTURE2D: + if (!mdata.width || !mdata.height || mdata.depth != 1 || !mdata.arraySize) + return E_INVALIDARG; + + if (mdata.IsCubemap()) + { + if ((mdata.arraySize % 6) != 0) + return E_INVALIDARG; + } + + if (!_CalculateMipLevels(mdata.width, mdata.height, mipLevels)) + return E_INVALIDARG; + break; + + case TEX_DIMENSION_TEXTURE3D: + if (!mdata.width || !mdata.height || !mdata.depth || mdata.arraySize != 1) + return E_INVALIDARG; + + if (!_CalculateMipLevels3D(mdata.width, mdata.height, mdata.depth, mipLevels)) + return E_INVALIDARG; + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + Release(); + + m_metadata.width = mdata.width; + m_metadata.height = mdata.height; + m_metadata.depth = mdata.depth; + m_metadata.arraySize = mdata.arraySize; + m_metadata.mipLevels = mipLevels; + m_metadata.miscFlags = mdata.miscFlags; + m_metadata.miscFlags2 = mdata.miscFlags2; + m_metadata.format = mdata.format; + m_metadata.dimension = mdata.dimension; + + size_t pixelSize, nimages; + _DetermineImageArray(m_metadata, flags, nimages, pixelSize); + + m_image = new (std::nothrow) Image[nimages]; + if (!m_image) + return E_OUTOFMEMORY; + + m_nimages = nimages; + memset(m_image, 0, sizeof(Image) * nimages); + + m_memory = reinterpret_cast(_aligned_malloc(pixelSize, 16)); + if (!m_memory) + { + Release(); + return E_OUTOFMEMORY; + } + m_size = pixelSize; + if (!_SetupImageArray(m_memory, pixelSize, m_metadata, flags, m_image, nimages)) + { + Release(); + return E_FAIL; + } + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT ScratchImage::Initialize1D(DXGI_FORMAT fmt, size_t length, size_t arraySize, size_t mipLevels, DWORD flags) +{ + if (!length || !arraySize) + return E_INVALIDARG; + + // 1D is a special case of the 2D case + HRESULT hr = Initialize2D(fmt, length, 1, arraySize, mipLevels, flags); + if (FAILED(hr)) + return hr; + + m_metadata.dimension = TEX_DIMENSION_TEXTURE1D; + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT ScratchImage::Initialize2D(DXGI_FORMAT fmt, size_t width, size_t height, size_t arraySize, size_t mipLevels, DWORD flags) +{ + if (!IsValid(fmt) || !width || !height || !arraySize) + return E_INVALIDARG; + + if (IsPalettized(fmt)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (!_CalculateMipLevels(width, height, mipLevels)) + return E_INVALIDARG; + + Release(); + + m_metadata.width = width; + m_metadata.height = height; + m_metadata.depth = 1; + m_metadata.arraySize = arraySize; + m_metadata.mipLevels = mipLevels; + m_metadata.miscFlags = 0; + m_metadata.miscFlags2 = 0; + m_metadata.format = fmt; + m_metadata.dimension = TEX_DIMENSION_TEXTURE2D; + + size_t pixelSize, nimages; + _DetermineImageArray(m_metadata, flags, nimages, pixelSize); + + m_image = new (std::nothrow) Image[nimages]; + if (!m_image) + return E_OUTOFMEMORY; + + m_nimages = nimages; + memset(m_image, 0, sizeof(Image) * nimages); + + m_memory = reinterpret_cast(_aligned_malloc(pixelSize, 16)); + if (!m_memory) + { + Release(); + return E_OUTOFMEMORY; + } + m_size = pixelSize; + if (!_SetupImageArray(m_memory, pixelSize, m_metadata, flags, m_image, nimages)) + { + Release(); + return E_FAIL; + } + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT ScratchImage::Initialize3D(DXGI_FORMAT fmt, size_t width, size_t height, size_t depth, size_t mipLevels, DWORD flags) +{ + if (!IsValid(fmt) || !width || !height || !depth) + return E_INVALIDARG; + + if (IsPalettized(fmt)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (!_CalculateMipLevels3D(width, height, depth, mipLevels)) + return E_INVALIDARG; + + Release(); + + m_metadata.width = width; + m_metadata.height = height; + m_metadata.depth = depth; + m_metadata.arraySize = 1; // Direct3D 10.x/11 does not support arrays of 3D textures + m_metadata.mipLevels = mipLevels; + m_metadata.miscFlags = 0; + m_metadata.miscFlags2 = 0; + m_metadata.format = fmt; + m_metadata.dimension = TEX_DIMENSION_TEXTURE3D; + + size_t pixelSize, nimages; + _DetermineImageArray(m_metadata, flags, nimages, pixelSize); + + m_image = new (std::nothrow) Image[nimages]; + if (!m_image) + { + Release(); + return E_OUTOFMEMORY; + } + m_nimages = nimages; + memset(m_image, 0, sizeof(Image) * nimages); + + m_memory = reinterpret_cast(_aligned_malloc(pixelSize, 16)); + if (!m_memory) + { + Release(); + return E_OUTOFMEMORY; + } + m_size = pixelSize; + + if (!_SetupImageArray(m_memory, pixelSize, m_metadata, flags, m_image, nimages)) + { + Release(); + return E_FAIL; + } + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT ScratchImage::InitializeCube(DXGI_FORMAT fmt, size_t width, size_t height, size_t nCubes, size_t mipLevels, DWORD flags) +{ + if (!width || !height || !nCubes) + return E_INVALIDARG; + + // A DirectX11 cubemap is just a 2D texture array that is a multiple of 6 for each cube + HRESULT hr = Initialize2D(fmt, width, height, nCubes * 6, mipLevels, flags); + if (FAILED(hr)) + return hr; + + m_metadata.miscFlags |= TEX_MISC_TEXTURECUBE; + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT ScratchImage::InitializeFromImage(const Image& srcImage, bool allow1D, DWORD flags) +{ + HRESULT hr = (srcImage.height > 1 || !allow1D) + ? Initialize2D(srcImage.format, srcImage.width, srcImage.height, 1, 1, flags) + : Initialize1D(srcImage.format, srcImage.width, 1, 1, flags); + + if (FAILED(hr)) + return hr; + + size_t rowCount = ComputeScanlines(srcImage.format, srcImage.height); + if (!rowCount) + return E_UNEXPECTED; + + const uint8_t* sptr = reinterpret_cast(srcImage.pixels); + if (!sptr) + return E_POINTER; + + auto dptr = reinterpret_cast(m_image[0].pixels); + if (!dptr) + return E_POINTER; + + size_t spitch = srcImage.rowPitch; + size_t dpitch = m_image[0].rowPitch; + + size_t size = std::min(dpitch, spitch); + + for (size_t y = 0; y < rowCount; ++y) + { + memcpy_s(dptr, dpitch, sptr, size); + sptr += spitch; + dptr += dpitch; + } + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT ScratchImage::InitializeArrayFromImages(const Image* images, size_t nImages, bool allow1D, DWORD flags) +{ + if (!images || !nImages) + return E_INVALIDARG; + + DXGI_FORMAT format = images[0].format; + size_t width = images[0].width; + size_t height = images[0].height; + + for (size_t index = 0; index < nImages; ++index) + { + if (!images[index].pixels) + return E_POINTER; + + if (images[index].format != format || images[index].width != width || images[index].height != height) + { + // All images must be the same format, width, and height + return E_FAIL; + } + } + + HRESULT hr = (height > 1 || !allow1D) + ? Initialize2D(format, width, height, nImages, 1, flags) + : Initialize1D(format, width, nImages, 1, flags); + + if (FAILED(hr)) + return hr; + + size_t rowCount = ComputeScanlines(format, height); + if (!rowCount) + return E_UNEXPECTED; + + for (size_t index = 0; index < nImages; ++index) + { + auto sptr = reinterpret_cast(images[index].pixels); + if (!sptr) + return E_POINTER; + + assert(index < m_nimages); + auto dptr = reinterpret_cast(m_image[index].pixels); + if (!dptr) + return E_POINTER; + + size_t spitch = images[index].rowPitch; + size_t dpitch = m_image[index].rowPitch; + + size_t size = std::min(dpitch, spitch); + + for (size_t y = 0; y < rowCount; ++y) + { + memcpy_s(dptr, dpitch, sptr, size); + sptr += spitch; + dptr += dpitch; + } + } + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT ScratchImage::InitializeCubeFromImages(const Image* images, size_t nImages, DWORD flags) +{ + if (!images || !nImages) + return E_INVALIDARG; + + // A DirectX11 cubemap is just a 2D texture array that is a multiple of 6 for each cube + if ((nImages % 6) != 0) + return E_INVALIDARG; + + HRESULT hr = InitializeArrayFromImages(images, nImages, false, flags); + if (FAILED(hr)) + return hr; + + m_metadata.miscFlags |= TEX_MISC_TEXTURECUBE; + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT ScratchImage::Initialize3DFromImages(const Image* images, size_t depth, DWORD flags) +{ + if (!images || !depth) + return E_INVALIDARG; + + DXGI_FORMAT format = images[0].format; + size_t width = images[0].width; + size_t height = images[0].height; + + for (size_t slice = 0; slice < depth; ++slice) + { + if (!images[slice].pixels) + return E_POINTER; + + if (images[slice].format != format || images[slice].width != width || images[slice].height != height) + { + // All images must be the same format, width, and height + return E_FAIL; + } + } + + HRESULT hr = Initialize3D(format, width, height, depth, 1, flags); + if (FAILED(hr)) + return hr; + + size_t rowCount = ComputeScanlines(format, height); + if (!rowCount) + return E_UNEXPECTED; + + for (size_t slice = 0; slice < depth; ++slice) + { + auto sptr = reinterpret_cast(images[slice].pixels); + if (!sptr) + return E_POINTER; + + assert(slice < m_nimages); + auto dptr = reinterpret_cast(m_image[slice].pixels); + if (!dptr) + return E_POINTER; + + size_t spitch = images[slice].rowPitch; + size_t dpitch = m_image[slice].rowPitch; + + size_t size = std::min(dpitch, spitch); + + for (size_t y = 0; y < rowCount; ++y) + { + memcpy_s(dptr, dpitch, sptr, size); + sptr += spitch; + dptr += dpitch; + } + } + + return S_OK; +} + +void ScratchImage::Release() +{ + m_nimages = 0; + m_size = 0; + + if (m_image) + { + delete[] m_image; + m_image = nullptr; + } + + if (m_memory) + { + _aligned_free(m_memory); + m_memory = nullptr; + } + + memset(&m_metadata, 0, sizeof(m_metadata)); +} + +_Use_decl_annotations_ +bool ScratchImage::OverrideFormat(DXGI_FORMAT f) +{ + if (!m_image) + return false; + + if (!IsValid(f) || IsPlanar(f) || IsPalettized(f)) + return false; + + for (size_t index = 0; index < m_nimages; ++index) + { + m_image[index].format = f; + } + + m_metadata.format = f; + + return true; +} + +_Use_decl_annotations_ +const Image* ScratchImage::GetImage(size_t mip, size_t item, size_t slice) const +{ + if (mip >= m_metadata.mipLevels) + return nullptr; + + size_t index = 0; + + switch (m_metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + case TEX_DIMENSION_TEXTURE2D: + if (slice > 0) + return nullptr; + + if (item >= m_metadata.arraySize) + return nullptr; + + index = item*(m_metadata.mipLevels) + mip; + break; + + case TEX_DIMENSION_TEXTURE3D: + if (item > 0) + { + // No support for arrays of volumes + return nullptr; + } + else + { + size_t d = m_metadata.depth; + + for (size_t level = 0; level < mip; ++level) + { + index += d; + if (d > 1) + d >>= 1; + } + + if (slice >= d) + return nullptr; + + index += slice; + } + break; + + default: + return nullptr; + } + + return &m_image[index]; +} + +bool ScratchImage::IsAlphaAllOpaque() const +{ + if (!m_image) + return false; + + if (!HasAlpha(m_metadata.format)) + return true; + + if (IsCompressed(m_metadata.format)) + { + for (size_t index = 0; index < m_nimages; ++index) + { + if (!_IsAlphaAllOpaqueBC(m_image[index])) + return false; + } + } + else + { + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*m_metadata.width), 16))); + if (!scanline) + return false; + + static const XMVECTORF32 threshold = { { { 0.99f, 0.99f, 0.99f, 0.99f } } }; + + for (size_t index = 0; index < m_nimages; ++index) + { +#pragma warning( suppress : 6011 ) + const Image& img = m_image[index]; + + const uint8_t *pPixels = img.pixels; + assert(pPixels); + + for (size_t h = 0; h < img.height; ++h) + { + if (!_LoadScanline(scanline.get(), img.width, pPixels, img.rowPitch, img.format)) + return false; + + const XMVECTOR* ptr = scanline.get(); + for (size_t w = 0; w < img.width; ++w) + { + XMVECTOR alpha = XMVectorSplatW(*ptr); + if (XMVector4Less(alpha, threshold)) + return false; + ++ptr; + } + + pPixels += img.rowPitch; + } + } + } + + return true; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexMipmaps.cpp b/deps/DirectXTex/DirectXTex/DirectXTexMipmaps.cpp new file mode 100644 index 0000000..5d330cc --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexMipmaps.cpp @@ -0,0 +1,3139 @@ +//------------------------------------------------------------------------------------- +// DirectXTexMipMaps.cpp +// +// DirectX Texture Library - Mip-map generation +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +#include "filters.h" + +using namespace DirectX; +using Microsoft::WRL::ComPtr; + +namespace +{ + inline bool ispow2(_In_ size_t x) + { + return ((x != 0) && !(x & (x - 1))); + } + + + size_t _CountMips(_In_ size_t width, _In_ size_t height) + { + size_t mipLevels = 1; + + while (height > 1 || width > 1) + { + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + + ++mipLevels; + } + + return mipLevels; + } + + + size_t _CountMips3D(_In_ size_t width, _In_ size_t height, _In_ size_t depth) + { + size_t mipLevels = 1; + + while (height > 1 || width > 1 || depth > 1) + { + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + + if (depth > 1) + depth >>= 1; + + ++mipLevels; + } + + return mipLevels; + } + + + HRESULT EnsureWicBitmapPixelFormat( + _In_ IWICImagingFactory* pWIC, + _In_ IWICBitmap* src, + _In_ DWORD filter, + _In_ const WICPixelFormatGUID& desiredPixelFormat, + _Deref_out_ IWICBitmap** dest) + { + if (!pWIC || !src || !dest) + return E_POINTER; + + *dest = nullptr; + + WICPixelFormatGUID actualPixelFormat; + HRESULT hr = src->GetPixelFormat(&actualPixelFormat); + + if (SUCCEEDED(hr)) + { + if (memcmp(&actualPixelFormat, &desiredPixelFormat, sizeof(WICPixelFormatGUID)) == 0) + { + src->AddRef(); + *dest = src; + } + else + { + ComPtr converter; + hr = pWIC->CreateFormatConverter(converter.GetAddressOf()); + + if (SUCCEEDED(hr)) + { + BOOL canConvert = FALSE; + hr = converter->CanConvert(actualPixelFormat, desiredPixelFormat, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + } + + if (SUCCEEDED(hr)) + { + hr = converter->Initialize(src, desiredPixelFormat, _GetWICDither(filter), nullptr, 0, WICBitmapPaletteTypeMedianCut); + } + + if (SUCCEEDED(hr)) + { + hr = pWIC->CreateBitmapFromSource(converter.Get(), WICBitmapCacheOnDemand, dest); + } + } + } + + return hr; + } +} + + +namespace DirectX +{ + bool _CalculateMipLevels(_In_ size_t width, _In_ size_t height, _Inout_ size_t& mipLevels) + { + if (mipLevels > 1) + { + size_t maxMips = _CountMips(width, height); + if (mipLevels > maxMips) + return false; + } + else if (mipLevels == 0) + { + mipLevels = _CountMips(width, height); + } + else + { + mipLevels = 1; + } + return true; + } + + bool _CalculateMipLevels3D(_In_ size_t width, _In_ size_t height, _In_ size_t depth, _Inout_ size_t& mipLevels) + { + if (mipLevels > 1) + { + size_t maxMips = _CountMips3D(width, height, depth); + if (mipLevels > maxMips) + return false; + } + else if (mipLevels == 0) + { + mipLevels = _CountMips3D(width, height, depth); + } + else + { + mipLevels = 1; + } + return true; + } + + //--- Resizing color and alpha channels separately using WIC --- + HRESULT _ResizeSeparateColorAndAlpha( + _In_ IWICImagingFactory* pWIC, + _In_ bool iswic2, + _In_ IWICBitmap* original, + _In_ size_t newWidth, + _In_ size_t newHeight, + _In_ DWORD filter, + _Inout_ const Image* img) + { + if (!pWIC || !original || !img) + return E_POINTER; + + const WICBitmapInterpolationMode interpolationMode = _GetWICInterp(filter); + + WICPixelFormatGUID desiredPixelFormat = GUID_WICPixelFormatUndefined; + HRESULT hr = original->GetPixelFormat(&desiredPixelFormat); + + size_t colorBytesInPixel = 0; + size_t colorBytesPerPixel = 0; + size_t colorWithAlphaBytesPerPixel = 0; + WICPixelFormatGUID colorPixelFormat = GUID_WICPixelFormatUndefined; + WICPixelFormatGUID colorWithAlphaPixelFormat = GUID_WICPixelFormatUndefined; + + if (SUCCEEDED(hr)) + { + ComPtr componentInfo; + hr = pWIC->CreateComponentInfo(desiredPixelFormat, componentInfo.GetAddressOf()); + + ComPtr pixelFormatInfo; + if (SUCCEEDED(hr)) + { + hr = componentInfo.As(&pixelFormatInfo); + } + + UINT bitsPerPixel = 0; + if (SUCCEEDED(hr)) + { + hr = pixelFormatInfo->GetBitsPerPixel(&bitsPerPixel); + } + + if (SUCCEEDED(hr)) + { + if (bitsPerPixel <= 32) + { + colorBytesInPixel = colorBytesPerPixel = 3; + colorPixelFormat = GUID_WICPixelFormat24bppBGR; + + colorWithAlphaBytesPerPixel = 4; + colorWithAlphaPixelFormat = GUID_WICPixelFormat32bppBGRA; + } + else + { +#if(_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + if (iswic2) + { + colorBytesInPixel = colorBytesPerPixel = 12; + colorPixelFormat = GUID_WICPixelFormat96bppRGBFloat; + } + else +#else + UNREFERENCED_PARAMETER(iswic2); +#endif + { + colorBytesInPixel = 12; + colorBytesPerPixel = 16; + colorPixelFormat = GUID_WICPixelFormat128bppRGBFloat; + } + + colorWithAlphaBytesPerPixel = 16; + colorWithAlphaPixelFormat = GUID_WICPixelFormat128bppRGBAFloat; + } + } + } + + // Resize color only image (no alpha channel) + ComPtr resizedColor; + if (SUCCEEDED(hr)) + { + ComPtr colorScaler; + hr = pWIC->CreateBitmapScaler(colorScaler.GetAddressOf()); + if (SUCCEEDED(hr)) + { + ComPtr converted; + hr = EnsureWicBitmapPixelFormat(pWIC, original, filter, colorPixelFormat, converted.GetAddressOf()); + if (SUCCEEDED(hr)) + { + hr = colorScaler->Initialize(converted.Get(), static_cast(newWidth), static_cast(newHeight), interpolationMode); + } + } + + if (SUCCEEDED(hr)) + { + ComPtr resized; + hr = pWIC->CreateBitmapFromSource(colorScaler.Get(), WICBitmapCacheOnDemand, resized.GetAddressOf()); + if (SUCCEEDED(hr)) + { + hr = EnsureWicBitmapPixelFormat(pWIC, resized.Get(), filter, colorPixelFormat, resizedColor.GetAddressOf()); + } + } + } + + // Resize color+alpha image + ComPtr resizedColorWithAlpha; + if (SUCCEEDED(hr)) + { + ComPtr colorWithAlphaScaler; + hr = pWIC->CreateBitmapScaler(colorWithAlphaScaler.GetAddressOf()); + if (SUCCEEDED(hr)) + { + ComPtr converted; + hr = EnsureWicBitmapPixelFormat(pWIC, original, filter, colorWithAlphaPixelFormat, converted.GetAddressOf()); + if (SUCCEEDED(hr)) + { + hr = colorWithAlphaScaler->Initialize(converted.Get(), static_cast(newWidth), static_cast(newHeight), interpolationMode); + } + } + + if (SUCCEEDED(hr)) + { + ComPtr resized; + hr = pWIC->CreateBitmapFromSource(colorWithAlphaScaler.Get(), WICBitmapCacheOnDemand, resized.GetAddressOf()); + if (SUCCEEDED(hr)) + { + hr = EnsureWicBitmapPixelFormat(pWIC, resized.Get(), filter, colorWithAlphaPixelFormat, resizedColorWithAlpha.GetAddressOf()); + } + } + } + + // Merge pixels (copying color channels from color only image to color+alpha image) + if (SUCCEEDED(hr)) + { + ComPtr colorLock; + ComPtr colorWithAlphaLock; + hr = resizedColor->Lock(nullptr, WICBitmapLockRead, colorLock.GetAddressOf()); + if (SUCCEEDED(hr)) + { + hr = resizedColorWithAlpha->Lock(nullptr, WICBitmapLockWrite, colorWithAlphaLock.GetAddressOf()); + } + + if (SUCCEEDED(hr)) + { + WICInProcPointer colorWithAlphaData = nullptr; + UINT colorWithAlphaSizeInBytes = 0; + UINT colorWithAlphaStride = 0; + + hr = colorWithAlphaLock->GetDataPointer(&colorWithAlphaSizeInBytes, &colorWithAlphaData); + if (SUCCEEDED(hr)) + { + if (!colorWithAlphaData) + { + hr = E_POINTER; + } + else + { + hr = colorWithAlphaLock->GetStride(&colorWithAlphaStride); + } + } + + WICInProcPointer colorData = nullptr; + UINT colorSizeInBytes = 0; + UINT colorStride = 0; + if (SUCCEEDED(hr)) + { + hr = colorLock->GetDataPointer(&colorSizeInBytes, &colorData); + if (SUCCEEDED(hr)) + { + if (!colorData) + { + hr = E_POINTER; + } + else + { + hr = colorLock->GetStride(&colorStride); + } + } + } + + for (size_t j = 0; SUCCEEDED(hr) && j < newHeight; j++) + { + for (size_t i = 0; SUCCEEDED(hr) && i < newWidth; i++) + { + size_t colorWithAlphaIndex = (j * colorWithAlphaStride) + (i * colorWithAlphaBytesPerPixel); + size_t colorIndex = (j * colorStride) + (i * colorBytesPerPixel); + + if (((colorWithAlphaIndex + colorBytesInPixel) > colorWithAlphaSizeInBytes) + || ((colorIndex + colorBytesPerPixel) > colorSizeInBytes)) + { + hr = E_INVALIDARG; + } + else + { +#pragma warning( suppress : 26014 6386 ) // No overflow possible here + memcpy_s(colorWithAlphaData + colorWithAlphaIndex, colorWithAlphaBytesPerPixel, colorData + colorIndex, colorBytesInPixel); + } + } + } + } + } + + if (SUCCEEDED(hr)) + { + ComPtr wicBitmap; + hr = EnsureWicBitmapPixelFormat(pWIC, resizedColorWithAlpha.Get(), filter, desiredPixelFormat, wicBitmap.GetAddressOf()); + if (SUCCEEDED(hr)) + { + hr = wicBitmap->CopyPixels(nullptr, static_cast(img->rowPitch), static_cast(img->slicePitch), img->pixels); + } + } + + return hr; + } +} + +namespace +{ + //--- determine when to use WIC vs. non-WIC paths --- + bool UseWICFiltering(_In_ DXGI_FORMAT format, _In_ DWORD filter) + { + if (filter & TEX_FILTER_FORCE_NON_WIC) + { + // Explicit flag indicates use of non-WIC code paths + return false; + } + + if (filter & TEX_FILTER_FORCE_WIC) + { + // Explicit flag to use WIC code paths, skips all the case checks below + return true; + } + + if (IsSRGB(format) || (filter & TEX_FILTER_SRGB)) + { + // Use non-WIC code paths for sRGB correct filtering + return false; + } + +#if defined(_XBOX_ONE) && defined(_TITLE) + if (format == DXGI_FORMAT_R16G16B16A16_FLOAT + || format == DXGI_FORMAT_R16_FLOAT) + { + // Use non-WIC code paths as these conversions are not supported by Xbox One XDK + return false; + } +#endif + + static_assert(TEX_FILTER_POINT == 0x100000, "TEX_FILTER_ flag values don't match TEX_FILTER_MASK"); + + switch (filter & TEX_FILTER_MASK) + { + case TEX_FILTER_LINEAR: + if (filter & TEX_FILTER_WRAP) + { + // WIC only supports 'clamp' semantics (MIRROR is equivalent to clamp for linear) + return false; + } + + if (BitsPerColor(format) > 8) + { + // Avoid the WIC bitmap scaler when doing Linear filtering of XR/HDR formats + return false; + } + break; + + case TEX_FILTER_CUBIC: + if (filter & (TEX_FILTER_WRAP | TEX_FILTER_MIRROR)) + { + // WIC only supports 'clamp' semantics + return false; + } + + if (BitsPerColor(format) > 8) + { + // Avoid the WIC bitmap scaler when doing Cubic filtering of XR/HDR formats + return false; + } + break; + + case TEX_FILTER_TRIANGLE: + // WIC does not implement this filter + return false; + } + + return true; + } + + + //--- mipmap (1D/2D) generation using WIC image scalar --- + HRESULT GenerateMipMapsUsingWIC( + _In_ const Image& baseImage, + _In_ DWORD filter, + _In_ size_t levels, + _In_ const WICPixelFormatGUID& pfGUID, + _In_ const ScratchImage& mipChain, + _In_ size_t item) + { + assert(levels > 1); + + if (!baseImage.pixels || !mipChain.GetPixels()) + return E_POINTER; + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + size_t width = baseImage.width; + size_t height = baseImage.height; + + ComPtr source; + HRESULT hr = pWIC->CreateBitmapFromMemory(static_cast(width), static_cast(height), pfGUID, + static_cast(baseImage.rowPitch), static_cast(baseImage.slicePitch), + baseImage.pixels, source.GetAddressOf()); + if (FAILED(hr)) + return hr; + + // Copy base image to top miplevel + const Image *img0 = mipChain.GetImage(0, item, 0); + if (!img0) + return E_POINTER; + + uint8_t* pDest = img0->pixels; + if (!pDest) + return E_POINTER; + + const uint8_t *pSrc = baseImage.pixels; + for (size_t h = 0; h < height; ++h) + { + size_t msize = std::min(img0->rowPitch, baseImage.rowPitch); + memcpy_s(pDest, img0->rowPitch, pSrc, msize); + pSrc += baseImage.rowPitch; + pDest += img0->rowPitch; + } + + ComPtr componentInfo; + hr = pWIC->CreateComponentInfo(pfGUID, componentInfo.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr pixelFormatInfo; + hr = componentInfo.As(&pixelFormatInfo); + if (FAILED(hr)) + return hr; + + BOOL supportsTransparency = FALSE; + hr = pixelFormatInfo->SupportsTransparency(&supportsTransparency); + if (FAILED(hr)) + return hr; + + // Resize base image to each target mip level + for (size_t level = 1; level < levels; ++level) + { + const Image *img = mipChain.GetImage(level, item, 0); + if (!img) + return E_POINTER; + + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + + assert(img->width == width && img->height == height && img->format == baseImage.format); + + if ((filter & TEX_FILTER_SEPARATE_ALPHA) && supportsTransparency) + { + hr = _ResizeSeparateColorAndAlpha(pWIC, iswic2, source.Get(), width, height, filter, img); + if (FAILED(hr)) + return hr; + } + else + { + ComPtr scaler; + hr = pWIC->CreateBitmapScaler(scaler.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = scaler->Initialize(source.Get(), static_cast(width), static_cast(height), _GetWICInterp(filter)); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID pfScaler; + hr = scaler->GetPixelFormat(&pfScaler); + if (FAILED(hr)) + return hr; + + if (memcmp(&pfScaler, &pfGUID, sizeof(WICPixelFormatGUID)) == 0) + { + hr = scaler->CopyPixels(0, static_cast(img->rowPitch), static_cast(img->slicePitch), img->pixels); + if (FAILED(hr)) + return hr; + } + else + { + // The WIC bitmap scaler is free to return a different pixel format than the source image, so here we + // convert it back + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pfScaler, pfGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(scaler.Get(), pfGUID, _GetWICDither(filter), nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(0, static_cast(img->rowPitch), static_cast(img->slicePitch), img->pixels); + if (FAILED(hr)) + return hr; + } + } + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Generate (1D/2D) mip-map helpers (custom filtering) + //------------------------------------------------------------------------------------- + HRESULT Setup2DMips( + _In_reads_(nimages) const Image* baseImages, + _In_ size_t nimages, + _In_ const TexMetadata& mdata, + _Out_ ScratchImage& mipChain) + { + if (!baseImages || !nimages) + return E_INVALIDARG; + + assert(mdata.mipLevels > 1); + assert(mdata.arraySize == nimages); + assert(mdata.depth == 1 && mdata.dimension != TEX_DIMENSION_TEXTURE3D); + assert(mdata.width == baseImages[0].width); + assert(mdata.height == baseImages[0].height); + assert(mdata.format == baseImages[0].format); + + HRESULT hr = mipChain.Initialize(mdata); + if (FAILED(hr)) + return hr; + + // Copy base image(s) to top of mip chain + for (size_t item = 0; item < nimages; ++item) + { + const Image& src = baseImages[item]; + + const Image *dest = mipChain.GetImage(0, item, 0); + if (!dest) + { + mipChain.Release(); + return E_POINTER; + } + + assert(src.format == dest->format); + + uint8_t* pDest = dest->pixels; + if (!pDest) + { + mipChain.Release(); + return E_POINTER; + } + + const uint8_t *pSrc = src.pixels; + size_t rowPitch = src.rowPitch; + for (size_t h = 0; h < mdata.height; ++h) + { + size_t msize = std::min(dest->rowPitch, rowPitch); + memcpy_s(pDest, dest->rowPitch, pSrc, msize); + pSrc += rowPitch; + pDest += dest->rowPitch; + } + } + + return S_OK; + } + + //--- 2D Point Filter --- + HRESULT Generate2DMipsPointFilter(size_t levels, const ScratchImage& mipChain, size_t item) + { + if (!mipChain.GetImages()) + return E_INVALIDARG; + + // This assumes that the base image is already placed into the mipChain at the top level... (see _Setup2DMips) + + assert(levels > 1); + + size_t width = mipChain.GetMetadata().width; + size_t height = mipChain.GetMetadata().height; + + // Allocate temporary space (2 scanlines) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width * 2), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + XMVECTOR* target = scanline.get(); + + XMVECTOR* row = target + width; + + // Resize base image to each target mip level + for (size_t level = 1; level < levels; ++level) + { +#ifdef _DEBUG + memset(row, 0xCD, sizeof(XMVECTOR)*width); +#endif + + // 2D point filter + const Image* src = mipChain.GetImage(level - 1, item, 0); + const Image* dest = mipChain.GetImage(level, item, 0); + + if (!src || !dest) + return E_POINTER; + + const uint8_t* pSrc = src->pixels; + uint8_t* pDest = dest->pixels; + + size_t rowPitch = src->rowPitch; + + size_t nwidth = (width > 1) ? (width >> 1) : 1; + size_t nheight = (height > 1) ? (height >> 1) : 1; + + size_t xinc = (width << 16) / nwidth; + size_t yinc = (height << 16) / nheight; + + size_t lasty = size_t(-1); + + size_t sy = 0; + for (size_t y = 0; y < nheight; ++y) + { + if ((lasty ^ sy) >> 16) + { + if (!_LoadScanline(row, width, pSrc + (rowPitch * (sy >> 16)), rowPitch, src->format)) + return E_FAIL; + lasty = sy; + } + + size_t sx = 0; + for (size_t x = 0; x < nwidth; ++x) + { + target[x] = row[sx >> 16]; + sx += xinc; + } + + if (!_StoreScanline(pDest, dest->rowPitch, dest->format, target, nwidth)) + return E_FAIL; + pDest += dest->rowPitch; + + sy += yinc; + } + + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + } + + return S_OK; + } + + + //--- 2D Box Filter --- + HRESULT Generate2DMipsBoxFilter(size_t levels, DWORD filter, const ScratchImage& mipChain, size_t item) + { + if (!mipChain.GetImages()) + return E_INVALIDARG; + + // This assumes that the base image is already placed into the mipChain at the top level... (see _Setup2DMips) + + assert(levels > 1); + + size_t width = mipChain.GetMetadata().width; + size_t height = mipChain.GetMetadata().height; + + if (!ispow2(width) || !ispow2(height)) + return E_FAIL; + + // Allocate temporary space (3 scanlines) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width * 3), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + XMVECTOR* target = scanline.get(); + + XMVECTOR* urow0 = target + width; + XMVECTOR* urow1 = target + width * 2; + + const XMVECTOR* urow2 = urow0 + 1; + const XMVECTOR* urow3 = urow1 + 1; + + // Resize base image to each target mip level + for (size_t level = 1; level < levels; ++level) + { + if (height <= 1) + { + urow1 = urow0; + } + + if (width <= 1) + { + urow2 = urow0; + urow3 = urow1; + } + + // 2D box filter + const Image* src = mipChain.GetImage(level - 1, item, 0); + const Image* dest = mipChain.GetImage(level, item, 0); + + if (!src || !dest) + return E_POINTER; + + const uint8_t* pSrc = src->pixels; + uint8_t* pDest = dest->pixels; + + size_t rowPitch = src->rowPitch; + + size_t nwidth = (width > 1) ? (width >> 1) : 1; + size_t nheight = (height > 1) ? (height >> 1) : 1; + + for (size_t y = 0; y < nheight; ++y) + { + if (!_LoadScanlineLinear(urow0, width, pSrc, rowPitch, src->format, filter)) + return E_FAIL; + pSrc += rowPitch; + + if (urow0 != urow1) + { + if (!_LoadScanlineLinear(urow1, width, pSrc, rowPitch, src->format, filter)) + return E_FAIL; + pSrc += rowPitch; + } + + for (size_t x = 0; x < nwidth; ++x) + { + size_t x2 = x << 1; + + AVERAGE4(target[x], urow0[x2], urow1[x2], urow2[x2], urow3[x2]); + } + + if (!_StoreScanlineLinear(pDest, dest->rowPitch, dest->format, target, nwidth, filter)) + return E_FAIL; + pDest += dest->rowPitch; + } + + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + } + + return S_OK; + } + + + //--- 2D Linear Filter --- + HRESULT Generate2DMipsLinearFilter(size_t levels, DWORD filter, const ScratchImage& mipChain, size_t item) + { + if (!mipChain.GetImages()) + return E_INVALIDARG; + + // This assumes that the base image is already placed into the mipChain at the top level... (see _Setup2DMips) + + assert(levels > 1); + + size_t width = mipChain.GetMetadata().width; + size_t height = mipChain.GetMetadata().height; + + // Allocate temporary space (3 scanlines, plus X and Y filters) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width * 3), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + std::unique_ptr lf(new (std::nothrow) LinearFilter[width + height]); + if (!lf) + return E_OUTOFMEMORY; + + LinearFilter* lfX = lf.get(); + LinearFilter* lfY = lf.get() + width; + + XMVECTOR* target = scanline.get(); + + XMVECTOR* row0 = target + width; + XMVECTOR* row1 = target + width * 2; + + // Resize base image to each target mip level + for (size_t level = 1; level < levels; ++level) + { + // 2D linear filter + const Image* src = mipChain.GetImage(level - 1, item, 0); + const Image* dest = mipChain.GetImage(level, item, 0); + + if (!src || !dest) + return E_POINTER; + + const uint8_t* pSrc = src->pixels; + uint8_t* pDest = dest->pixels; + + size_t rowPitch = src->rowPitch; + + size_t nwidth = (width > 1) ? (width >> 1) : 1; + _CreateLinearFilter(width, nwidth, (filter & TEX_FILTER_WRAP_U) != 0, lfX); + + size_t nheight = (height > 1) ? (height >> 1) : 1; + _CreateLinearFilter(height, nheight, (filter & TEX_FILTER_WRAP_V) != 0, lfY); + +#ifdef _DEBUG + memset(row0, 0xCD, sizeof(XMVECTOR)*width); + memset(row1, 0xDD, sizeof(XMVECTOR)*width); +#endif + + size_t u0 = size_t(-1); + size_t u1 = size_t(-1); + + for (size_t y = 0; y < nheight; ++y) + { + auto& toY = lfY[y]; + + if (toY.u0 != u0) + { + if (toY.u0 != u1) + { + u0 = toY.u0; + + if (!_LoadScanlineLinear(row0, width, pSrc + (rowPitch * u0), rowPitch, src->format, filter)) + return E_FAIL; + } + else + { + u0 = u1; + u1 = size_t(-1); + + std::swap(row0, row1); + } + } + + if (toY.u1 != u1) + { + u1 = toY.u1; + + if (!_LoadScanlineLinear(row1, width, pSrc + (rowPitch * u1), rowPitch, src->format, filter)) + return E_FAIL; + } + + for (size_t x = 0; x < nwidth; ++x) + { + auto& toX = lfX[x]; + + BILINEAR_INTERPOLATE(target[x], toX, toY, row0, row1); + } + + if (!_StoreScanlineLinear(pDest, dest->rowPitch, dest->format, target, nwidth, filter)) + return E_FAIL; + pDest += dest->rowPitch; + } + + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + } + + return S_OK; + } + + //--- 2D Cubic Filter --- + HRESULT Generate2DMipsCubicFilter(size_t levels, DWORD filter, const ScratchImage& mipChain, size_t item) + { + if (!mipChain.GetImages()) + return E_INVALIDARG; + + // This assumes that the base image is already placed into the mipChain at the top level... (see _Setup2DMips) + + assert(levels > 1); + + size_t width = mipChain.GetMetadata().width; + size_t height = mipChain.GetMetadata().height; + + // Allocate temporary space (5 scanlines, plus X and Y filters) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width * 5), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + std::unique_ptr cf(new (std::nothrow) CubicFilter[width + height]); + if (!cf) + return E_OUTOFMEMORY; + + CubicFilter* cfX = cf.get(); + CubicFilter* cfY = cf.get() + width; + + XMVECTOR* target = scanline.get(); + + XMVECTOR* row0 = target + width; + XMVECTOR* row1 = target + width * 2; + XMVECTOR* row2 = target + width * 3; + XMVECTOR* row3 = target + width * 4; + + // Resize base image to each target mip level + for (size_t level = 1; level < levels; ++level) + { + // 2D cubic filter + const Image* src = mipChain.GetImage(level - 1, item, 0); + const Image* dest = mipChain.GetImage(level, item, 0); + + if (!src || !dest) + return E_POINTER; + + const uint8_t* pSrc = src->pixels; + uint8_t* pDest = dest->pixels; + + size_t rowPitch = src->rowPitch; + + size_t nwidth = (width > 1) ? (width >> 1) : 1; + _CreateCubicFilter(width, nwidth, (filter & TEX_FILTER_WRAP_U) != 0, (filter & TEX_FILTER_MIRROR_U) != 0, cfX); + + size_t nheight = (height > 1) ? (height >> 1) : 1; + _CreateCubicFilter(height, nheight, (filter & TEX_FILTER_WRAP_V) != 0, (filter & TEX_FILTER_MIRROR_V) != 0, cfY); + +#ifdef _DEBUG + memset(row0, 0xCD, sizeof(XMVECTOR)*width); + memset(row1, 0xDD, sizeof(XMVECTOR)*width); + memset(row2, 0xED, sizeof(XMVECTOR)*width); + memset(row3, 0xFD, sizeof(XMVECTOR)*width); +#endif + + size_t u0 = size_t(-1); + size_t u1 = size_t(-1); + size_t u2 = size_t(-1); + size_t u3 = size_t(-1); + + for (size_t y = 0; y < nheight; ++y) + { + auto& toY = cfY[y]; + + // Scanline 1 + if (toY.u0 != u0) + { + if (toY.u0 != u1 && toY.u0 != u2 && toY.u0 != u3) + { + u0 = toY.u0; + + if (!_LoadScanlineLinear(row0, width, pSrc + (rowPitch * u0), rowPitch, src->format, filter)) + return E_FAIL; + } + else if (toY.u0 == u1) + { + u0 = u1; + u1 = size_t(-1); + + std::swap(row0, row1); + } + else if (toY.u0 == u2) + { + u0 = u2; + u2 = size_t(-1); + + std::swap(row0, row2); + } + else if (toY.u0 == u3) + { + u0 = u3; + u3 = size_t(-1); + + std::swap(row0, row3); + } + } + + // Scanline 2 + if (toY.u1 != u1) + { + if (toY.u1 != u2 && toY.u1 != u3) + { + u1 = toY.u1; + + if (!_LoadScanlineLinear(row1, width, pSrc + (rowPitch * u1), rowPitch, src->format, filter)) + return E_FAIL; + } + else if (toY.u1 == u2) + { + u1 = u2; + u2 = size_t(-1); + + std::swap(row1, row2); + } + else if (toY.u1 == u3) + { + u1 = u3; + u3 = size_t(-1); + + std::swap(row1, row3); + } + } + + // Scanline 3 + if (toY.u2 != u2) + { + if (toY.u2 != u3) + { + u2 = toY.u2; + + if (!_LoadScanlineLinear(row2, width, pSrc + (rowPitch * u2), rowPitch, src->format, filter)) + return E_FAIL; + } + else + { + u2 = u3; + u3 = size_t(-1); + + std::swap(row2, row3); + } + } + + // Scanline 4 + if (toY.u3 != u3) + { + u3 = toY.u3; + + if (!_LoadScanlineLinear(row3, width, pSrc + (rowPitch * u3), rowPitch, src->format, filter)) + return E_FAIL; + } + + for (size_t x = 0; x < nwidth; ++x) + { + auto& toX = cfX[x]; + + XMVECTOR C0, C1, C2, C3; + + CUBIC_INTERPOLATE(C0, toX.x, row0[toX.u0], row0[toX.u1], row0[toX.u2], row0[toX.u3]); + CUBIC_INTERPOLATE(C1, toX.x, row1[toX.u0], row1[toX.u1], row1[toX.u2], row1[toX.u3]); + CUBIC_INTERPOLATE(C2, toX.x, row2[toX.u0], row2[toX.u1], row2[toX.u2], row2[toX.u3]); + CUBIC_INTERPOLATE(C3, toX.x, row3[toX.u0], row3[toX.u1], row3[toX.u2], row3[toX.u3]); + + CUBIC_INTERPOLATE(target[x], toY.x, C0, C1, C2, C3); + } + + if (!_StoreScanlineLinear(pDest, dest->rowPitch, dest->format, target, nwidth, filter)) + return E_FAIL; + pDest += dest->rowPitch; + } + + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + } + + return S_OK; + } + + + //--- 2D Triangle Filter --- + HRESULT Generate2DMipsTriangleFilter(size_t levels, DWORD filter, const ScratchImage& mipChain, size_t item) + { + if (!mipChain.GetImages()) + return E_INVALIDARG; + + using namespace TriangleFilter; + + // This assumes that the base image is already placed into the mipChain at the top level... (see _Setup2DMips) + + assert(levels > 1); + + size_t width = mipChain.GetMetadata().width; + size_t height = mipChain.GetMetadata().height; + + // Allocate initial temporary space (1 scanline, accumulation rows, plus X and Y filters) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc(sizeof(XMVECTOR) * width, 16))); + if (!scanline) + return E_OUTOFMEMORY; + + std::unique_ptr rowActive(new (std::nothrow) TriangleRow[height]); + if (!rowActive) + return E_OUTOFMEMORY; + + TriangleRow * rowFree = nullptr; + + std::unique_ptr tfX, tfY; + + XMVECTOR* row = scanline.get(); + + // Resize base image to each target mip level + for (size_t level = 1; level < levels; ++level) + { + // 2D triangle filter + const Image* src = mipChain.GetImage(level - 1, item, 0); + const Image* dest = mipChain.GetImage(level, item, 0); + + if (!src || !dest) + return E_POINTER; + + const uint8_t* pSrc = src->pixels; + size_t rowPitch = src->rowPitch; + const uint8_t* pEndSrc = pSrc + rowPitch * height; + + uint8_t* pDest = dest->pixels; + + size_t nwidth = (width > 1) ? (width >> 1) : 1; + HRESULT hr = _Create(width, nwidth, (filter & TEX_FILTER_WRAP_U) != 0, tfX); + if (FAILED(hr)) + return hr; + + size_t nheight = (height > 1) ? (height >> 1) : 1; + hr = _Create(height, nheight, (filter & TEX_FILTER_WRAP_V) != 0, tfY); + if (FAILED(hr)) + return hr; + +#ifdef _DEBUG + memset(row, 0xCD, sizeof(XMVECTOR)*width); +#endif + + auto xFromEnd = reinterpret_cast(reinterpret_cast(tfX.get()) + tfX->sizeInBytes); + auto yFromEnd = reinterpret_cast(reinterpret_cast(tfY.get()) + tfY->sizeInBytes); + + // Count times rows get written (and clear out any leftover accumulation rows from last miplevel) + for (FilterFrom* yFrom = tfY->from; yFrom < yFromEnd; ) + { + for (size_t j = 0; j < yFrom->count; ++j) + { + size_t v = yFrom->to[j].u; + assert(v < nheight); + TriangleRow* rowAcc = &rowActive[v]; + + ++rowAcc->remaining; + + if (rowAcc->scanline) + { + memset(rowAcc->scanline.get(), 0, sizeof(XMVECTOR) * nwidth); + } + } + + yFrom = reinterpret_cast(reinterpret_cast(yFrom) + yFrom->sizeInBytes); + } + + // Filter image + for (FilterFrom* yFrom = tfY->from; yFrom < yFromEnd; ) + { + // Create accumulation rows as needed + for (size_t j = 0; j < yFrom->count; ++j) + { + size_t v = yFrom->to[j].u; + assert(v < nheight); + TriangleRow* rowAcc = &rowActive[v]; + + if (!rowAcc->scanline) + { + if (rowFree) + { + // Steal and reuse scanline from 'free row' list + // (it will always be at least as wide as nwidth due to loop decending order) + assert(rowFree->scanline != 0); + rowAcc->scanline.reset(rowFree->scanline.release()); + rowFree = rowFree->next; + } + else + { + rowAcc->scanline.reset(reinterpret_cast(_aligned_malloc(sizeof(XMVECTOR) * nwidth, 16))); + if (!rowAcc->scanline) + return E_OUTOFMEMORY; + } + + memset(rowAcc->scanline.get(), 0, sizeof(XMVECTOR) * nwidth); + } + } + + // Load source scanline + if ((pSrc + rowPitch) > pEndSrc) + return E_FAIL; + + if (!_LoadScanlineLinear(row, width, pSrc, rowPitch, src->format, filter)) + return E_FAIL; + + pSrc += rowPitch; + + // Process row + size_t x = 0; + for (FilterFrom* xFrom = tfX->from; xFrom < xFromEnd; ++x) + { + for (size_t j = 0; j < yFrom->count; ++j) + { + size_t v = yFrom->to[j].u; + assert(v < nheight); + float yweight = yFrom->to[j].weight; + + XMVECTOR* accPtr = rowActive[v].scanline.get(); + if (!accPtr) + return E_POINTER; + + for (size_t k = 0; k < xFrom->count; ++k) + { + size_t u = xFrom->to[k].u; + assert(u < nwidth); + + XMVECTOR weight = XMVectorReplicate(yweight * xFrom->to[k].weight); + + assert(x < width); + accPtr[u] = XMVectorMultiplyAdd(row[x], weight, accPtr[u]); + } + } + + xFrom = reinterpret_cast(reinterpret_cast(xFrom) + xFrom->sizeInBytes); + } + + // Write completed accumulation rows + for (size_t j = 0; j < yFrom->count; ++j) + { + size_t v = yFrom->to[j].u; + assert(v < nheight); + TriangleRow* rowAcc = &rowActive[v]; + + assert(rowAcc->remaining > 0); + --rowAcc->remaining; + + if (!rowAcc->remaining) + { + XMVECTOR* pAccSrc = rowAcc->scanline.get(); + if (!pAccSrc) + return E_POINTER; + + switch (dest->format) + { + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + { + // Need to slightly bias results for floating-point error accumulation which can + // be visible with harshly quantized values + static const XMVECTORF32 Bias = { { { 0.f, 0.f, 0.f, 0.1f } } }; + + XMVECTOR* ptr = pAccSrc; + for (size_t i = 0; i < dest->width; ++i, ++ptr) + { + *ptr = XMVectorAdd(*ptr, Bias); + } + } + break; + + default: + break; + } + + // This performs any required clamping + if (!_StoreScanlineLinear(pDest + (dest->rowPitch * v), dest->rowPitch, dest->format, pAccSrc, dest->width, filter)) + return E_FAIL; + + // Put row on freelist to reuse it's allocated scanline + rowAcc->next = rowFree; + rowFree = rowAcc; + } + } + + yFrom = reinterpret_cast(reinterpret_cast(yFrom) + yFrom->sizeInBytes); + } + + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Generate volume mip-map helpers + //------------------------------------------------------------------------------------- + HRESULT Setup3DMips( + _In_reads_(depth) const Image* baseImages, + size_t depth, + size_t levels, + _Out_ ScratchImage& mipChain) + { + if (!baseImages || !depth) + return E_INVALIDARG; + + assert(levels > 1); + + size_t width = baseImages[0].width; + size_t height = baseImages[0].height; + + HRESULT hr = mipChain.Initialize3D(baseImages[0].format, width, height, depth, levels); + if (FAILED(hr)) + return hr; + + // Copy base images to top slice + for (size_t slice = 0; slice < depth; ++slice) + { + const Image& src = baseImages[slice]; + + const Image *dest = mipChain.GetImage(0, 0, slice); + if (!dest) + { + mipChain.Release(); + return E_POINTER; + } + + assert(src.format == dest->format); + + uint8_t* pDest = dest->pixels; + if (!pDest) + { + mipChain.Release(); + return E_POINTER; + } + + const uint8_t *pSrc = src.pixels; + size_t rowPitch = src.rowPitch; + for (size_t h = 0; h < height; ++h) + { + size_t msize = std::min(dest->rowPitch, rowPitch); + memcpy_s(pDest, dest->rowPitch, pSrc, msize); + pSrc += rowPitch; + pDest += dest->rowPitch; + } + } + + return S_OK; + } + + + //--- 3D Point Filter --- + HRESULT Generate3DMipsPointFilter(size_t depth, size_t levels, const ScratchImage& mipChain) + { + if (!depth || !mipChain.GetImages()) + return E_INVALIDARG; + + // This assumes that the base images are already placed into the mipChain at the top level... (see _Setup3DMips) + + assert(levels > 1); + + size_t width = mipChain.GetMetadata().width; + size_t height = mipChain.GetMetadata().height; + + // Allocate temporary space (2 scanlines) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width * 2), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + XMVECTOR* target = scanline.get(); + + XMVECTOR* row = target + width; + + // Resize base image to each target mip level + for (size_t level = 1; level < levels; ++level) + { +#ifdef _DEBUG + memset(row, 0xCD, sizeof(XMVECTOR)*width); +#endif + + if (depth > 1) + { + // 3D point filter + size_t ndepth = depth >> 1; + + size_t zinc = (depth << 16) / ndepth; + + size_t sz = 0; + for (size_t slice = 0; slice < ndepth; ++slice) + { + const Image* src = mipChain.GetImage(level - 1, 0, (sz >> 16)); + const Image* dest = mipChain.GetImage(level, 0, slice); + + if (!src || !dest) + return E_POINTER; + + const uint8_t* pSrc = src->pixels; + uint8_t* pDest = dest->pixels; + + size_t rowPitch = src->rowPitch; + + size_t nwidth = (width > 1) ? (width >> 1) : 1; + size_t nheight = (height > 1) ? (height >> 1) : 1; + + size_t xinc = (width << 16) / nwidth; + size_t yinc = (height << 16) / nheight; + + size_t lasty = size_t(-1); + + size_t sy = 0; + for (size_t y = 0; y < nheight; ++y) + { + if ((lasty ^ sy) >> 16) + { + if (!_LoadScanline(row, width, pSrc + (rowPitch * (sy >> 16)), rowPitch, src->format)) + return E_FAIL; + lasty = sy; + } + + size_t sx = 0; + for (size_t x = 0; x < nwidth; ++x) + { + target[x] = row[sx >> 16]; + sx += xinc; + } + + if (!_StoreScanline(pDest, dest->rowPitch, dest->format, target, nwidth)) + return E_FAIL; + pDest += dest->rowPitch; + + sy += yinc; + } + + sz += zinc; + } + } + else + { + // 2D point filter + const Image* src = mipChain.GetImage(level - 1, 0, 0); + const Image* dest = mipChain.GetImage(level, 0, 0); + + if (!src || !dest) + return E_POINTER; + + const uint8_t* pSrc = src->pixels; + uint8_t* pDest = dest->pixels; + + size_t rowPitch = src->rowPitch; + + size_t nwidth = (width > 1) ? (width >> 1) : 1; + size_t nheight = (height > 1) ? (height >> 1) : 1; + + size_t xinc = (width << 16) / nwidth; + size_t yinc = (height << 16) / nheight; + + size_t lasty = size_t(-1); + + size_t sy = 0; + for (size_t y = 0; y < nheight; ++y) + { + if ((lasty ^ sy) >> 16) + { + if (!_LoadScanline(row, width, pSrc + (rowPitch * (sy >> 16)), rowPitch, src->format)) + return E_FAIL; + lasty = sy; + } + + size_t sx = 0; + for (size_t x = 0; x < nwidth; ++x) + { + target[x] = row[sx >> 16]; + sx += xinc; + } + + if (!_StoreScanline(pDest, dest->rowPitch, dest->format, target, nwidth)) + return E_FAIL; + pDest += dest->rowPitch; + + sy += yinc; + } + } + + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + + if (depth > 1) + depth >>= 1; + } + + return S_OK; + } + + + //--- 3D Box Filter --- + HRESULT Generate3DMipsBoxFilter(size_t depth, size_t levels, DWORD filter, const ScratchImage& mipChain) + { + if (!depth || !mipChain.GetImages()) + return E_INVALIDARG; + + // This assumes that the base images are already placed into the mipChain at the top level... (see _Setup3DMips) + + assert(levels > 1); + + size_t width = mipChain.GetMetadata().width; + size_t height = mipChain.GetMetadata().height; + + if (!ispow2(width) || !ispow2(height) || !ispow2(depth)) + return E_FAIL; + + // Allocate temporary space (5 scanlines) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width * 5), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + XMVECTOR* target = scanline.get(); + + XMVECTOR* urow0 = target + width; + XMVECTOR* urow1 = target + width * 2; + XMVECTOR* vrow0 = target + width * 3; + XMVECTOR* vrow1 = target + width * 4; + + const XMVECTOR* urow2 = urow0 + 1; + const XMVECTOR* urow3 = urow1 + 1; + const XMVECTOR* vrow2 = vrow0 + 1; + const XMVECTOR* vrow3 = vrow1 + 1; + + // Resize base image to each target mip level + for (size_t level = 1; level < levels; ++level) + { + if (height <= 1) + { + urow1 = urow0; + vrow1 = vrow0; + } + + if (width <= 1) + { + urow2 = urow0; + urow3 = urow1; + vrow2 = vrow0; + vrow3 = vrow1; + } + + if (depth > 1) + { + // 3D box filter + size_t ndepth = depth >> 1; + + for (size_t slice = 0; slice < ndepth; ++slice) + { + size_t slicea = std::min(slice * 2, depth - 1); + size_t sliceb = std::min(slicea + 1, depth - 1); + + const Image* srca = mipChain.GetImage(level - 1, 0, slicea); + const Image* srcb = mipChain.GetImage(level - 1, 0, sliceb); + const Image* dest = mipChain.GetImage(level, 0, slice); + + if (!srca || !srcb || !dest) + return E_POINTER; + + const uint8_t* pSrc1 = srca->pixels; + const uint8_t* pSrc2 = srcb->pixels; + uint8_t* pDest = dest->pixels; + + size_t aRowPitch = srca->rowPitch; + size_t bRowPitch = srcb->rowPitch; + + size_t nwidth = (width > 1) ? (width >> 1) : 1; + size_t nheight = (height > 1) ? (height >> 1) : 1; + + for (size_t y = 0; y < nheight; ++y) + { + if (!_LoadScanlineLinear(urow0, width, pSrc1, aRowPitch, srca->format, filter)) + return E_FAIL; + pSrc1 += aRowPitch; + + if (urow0 != urow1) + { + if (!_LoadScanlineLinear(urow1, width, pSrc1, aRowPitch, srca->format, filter)) + return E_FAIL; + pSrc1 += aRowPitch; + } + + if (!_LoadScanlineLinear(vrow0, width, pSrc2, bRowPitch, srcb->format, filter)) + return E_FAIL; + pSrc2 += bRowPitch; + + if (vrow0 != vrow1) + { + if (!_LoadScanlineLinear(vrow1, width, pSrc2, bRowPitch, srcb->format, filter)) + return E_FAIL; + pSrc2 += bRowPitch; + } + + for (size_t x = 0; x < nwidth; ++x) + { + size_t x2 = x << 1; + + AVERAGE8(target[x], urow0[x2], urow1[x2], urow2[x2], urow3[x2], + vrow0[x2], vrow1[x2], vrow2[x2], vrow3[x2]); + } + + if (!_StoreScanlineLinear(pDest, dest->rowPitch, dest->format, target, nwidth, filter)) + return E_FAIL; + pDest += dest->rowPitch; + } + } + } + else + { + // 2D box filter + const Image* src = mipChain.GetImage(level - 1, 0, 0); + const Image* dest = mipChain.GetImage(level, 0, 0); + + if (!src || !dest) + return E_POINTER; + + const uint8_t* pSrc = src->pixels; + uint8_t* pDest = dest->pixels; + + size_t rowPitch = src->rowPitch; + + size_t nwidth = (width > 1) ? (width >> 1) : 1; + size_t nheight = (height > 1) ? (height >> 1) : 1; + + for (size_t y = 0; y < nheight; ++y) + { + if (!_LoadScanlineLinear(urow0, width, pSrc, rowPitch, src->format, filter)) + return E_FAIL; + pSrc += rowPitch; + + if (urow0 != urow1) + { + if (!_LoadScanlineLinear(urow1, width, pSrc, rowPitch, src->format, filter)) + return E_FAIL; + pSrc += rowPitch; + } + + for (size_t x = 0; x < nwidth; ++x) + { + size_t x2 = x << 1; + + AVERAGE4(target[x], urow0[x2], urow1[x2], urow2[x2], urow3[x2]); + } + + if (!_StoreScanlineLinear(pDest, dest->rowPitch, dest->format, target, nwidth, filter)) + return E_FAIL; + pDest += dest->rowPitch; + } + } + + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + + if (depth > 1) + depth >>= 1; + } + + return S_OK; + } + + + //--- 3D Linear Filter --- + HRESULT Generate3DMipsLinearFilter(size_t depth, size_t levels, DWORD filter, const ScratchImage& mipChain) + { + if (!depth || !mipChain.GetImages()) + return E_INVALIDARG; + + // This assumes that the base images are already placed into the mipChain at the top level... (see _Setup3DMips) + + assert(levels > 1); + + size_t width = mipChain.GetMetadata().width; + size_t height = mipChain.GetMetadata().height; + + // Allocate temporary space (5 scanlines, plus X/Y/Z filters) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width * 5), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + std::unique_ptr lf(new (std::nothrow) LinearFilter[width + height + depth]); + if (!lf) + return E_OUTOFMEMORY; + + LinearFilter* lfX = lf.get(); + LinearFilter* lfY = lf.get() + width; + LinearFilter* lfZ = lf.get() + width + height; + + XMVECTOR* target = scanline.get(); + + XMVECTOR* urow0 = target + width; + XMVECTOR* urow1 = target + width * 2; + XMVECTOR* vrow0 = target + width * 3; + XMVECTOR* vrow1 = target + width * 4; + + // Resize base image to each target mip level + for (size_t level = 1; level < levels; ++level) + { + size_t nwidth = (width > 1) ? (width >> 1) : 1; + _CreateLinearFilter(width, nwidth, (filter & TEX_FILTER_WRAP_U) != 0, lfX); + + size_t nheight = (height > 1) ? (height >> 1) : 1; + _CreateLinearFilter(height, nheight, (filter & TEX_FILTER_WRAP_V) != 0, lfY); + +#ifdef _DEBUG + memset(urow0, 0xCD, sizeof(XMVECTOR)*width); + memset(urow1, 0xDD, sizeof(XMVECTOR)*width); + memset(vrow0, 0xED, sizeof(XMVECTOR)*width); + memset(vrow1, 0xFD, sizeof(XMVECTOR)*width); +#endif + + if (depth > 1) + { + // 3D linear filter + size_t ndepth = depth >> 1; + _CreateLinearFilter(depth, ndepth, (filter & TEX_FILTER_WRAP_W) != 0, lfZ); + + for (size_t slice = 0; slice < ndepth; ++slice) + { + auto& toZ = lfZ[slice]; + + const Image* srca = mipChain.GetImage(level - 1, 0, toZ.u0); + const Image* srcb = mipChain.GetImage(level - 1, 0, toZ.u1); + if (!srca || !srcb) + return E_POINTER; + + size_t u0 = size_t(-1); + size_t u1 = size_t(-1); + + const Image* dest = mipChain.GetImage(level, 0, slice); + if (!dest) + return E_POINTER; + + uint8_t* pDest = dest->pixels; + + for (size_t y = 0; y < nheight; ++y) + { + auto& toY = lfY[y]; + + if (toY.u0 != u0) + { + if (toY.u0 != u1) + { + u0 = toY.u0; + + if (!_LoadScanlineLinear(urow0, width, srca->pixels + (srca->rowPitch * u0), srca->rowPitch, srca->format, filter) + || !_LoadScanlineLinear(vrow0, width, srcb->pixels + (srcb->rowPitch * u0), srcb->rowPitch, srcb->format, filter)) + return E_FAIL; + } + else + { + u0 = u1; + u1 = size_t(-1); + + std::swap(urow0, urow1); + std::swap(vrow0, vrow1); + } + } + + if (toY.u1 != u1) + { + u1 = toY.u1; + + if (!_LoadScanlineLinear(urow1, width, srca->pixels + (srca->rowPitch * u1), srca->rowPitch, srca->format, filter) + || !_LoadScanlineLinear(vrow1, width, srcb->pixels + (srcb->rowPitch * u1), srcb->rowPitch, srcb->format, filter)) + return E_FAIL; + } + + for (size_t x = 0; x < nwidth; ++x) + { + auto& toX = lfX[x]; + + TRILINEAR_INTERPOLATE(target[x], toX, toY, toZ, urow0, urow1, vrow0, vrow1); + } + + if (!_StoreScanlineLinear(pDest, dest->rowPitch, dest->format, target, nwidth, filter)) + return E_FAIL; + pDest += dest->rowPitch; + } + } + } + else + { + // 2D linear filter + const Image* src = mipChain.GetImage(level - 1, 0, 0); + const Image* dest = mipChain.GetImage(level, 0, 0); + + if (!src || !dest) + return E_POINTER; + + const uint8_t* pSrc = src->pixels; + uint8_t* pDest = dest->pixels; + + size_t rowPitch = src->rowPitch; + + size_t u0 = size_t(-1); + size_t u1 = size_t(-1); + + for (size_t y = 0; y < nheight; ++y) + { + auto& toY = lfY[y]; + + if (toY.u0 != u0) + { + if (toY.u0 != u1) + { + u0 = toY.u0; + + if (!_LoadScanlineLinear(urow0, width, pSrc + (rowPitch * u0), rowPitch, src->format, filter)) + return E_FAIL; + } + else + { + u0 = u1; + u1 = size_t(-1); + + std::swap(urow0, urow1); + } + } + + if (toY.u1 != u1) + { + u1 = toY.u1; + + if (!_LoadScanlineLinear(urow1, width, pSrc + (rowPitch * u1), rowPitch, src->format, filter)) + return E_FAIL; + } + + for (size_t x = 0; x < nwidth; ++x) + { + auto& toX = lfX[x]; + + BILINEAR_INTERPOLATE(target[x], toX, toY, urow0, urow1); + } + + if (!_StoreScanlineLinear(pDest, dest->rowPitch, dest->format, target, nwidth, filter)) + return E_FAIL; + pDest += dest->rowPitch; + } + } + + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + + if (depth > 1) + depth >>= 1; + } + + return S_OK; + } + + + //--- 3D Cubic Filter --- + HRESULT Generate3DMipsCubicFilter(size_t depth, size_t levels, DWORD filter, const ScratchImage& mipChain) + { + if (!depth || !mipChain.GetImages()) + return E_INVALIDARG; + + // This assumes that the base images are already placed into the mipChain at the top level... (see _Setup3DMips) + + assert(levels > 1); + + size_t width = mipChain.GetMetadata().width; + size_t height = mipChain.GetMetadata().height; + + // Allocate temporary space (17 scanlines, plus X/Y/Z filters) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width * 17), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + std::unique_ptr cf(new (std::nothrow) CubicFilter[width + height + depth]); + if (!cf) + return E_OUTOFMEMORY; + + CubicFilter* cfX = cf.get(); + CubicFilter* cfY = cf.get() + width; + CubicFilter* cfZ = cf.get() + width + height; + + XMVECTOR* target = scanline.get(); + + XMVECTOR* urow[4]; + XMVECTOR* vrow[4]; + XMVECTOR* srow[4]; + XMVECTOR* trow[4]; + + XMVECTOR *ptr = scanline.get() + width; + for (size_t j = 0; j < 4; ++j) + { + urow[j] = ptr; ptr += width; + vrow[j] = ptr; ptr += width; + srow[j] = ptr; ptr += width; + trow[j] = ptr; ptr += width; + } + + // Resize base image to each target mip level + for (size_t level = 1; level < levels; ++level) + { + size_t nwidth = (width > 1) ? (width >> 1) : 1; + _CreateCubicFilter(width, nwidth, (filter & TEX_FILTER_WRAP_U) != 0, (filter & TEX_FILTER_MIRROR_U) != 0, cfX); + + size_t nheight = (height > 1) ? (height >> 1) : 1; + _CreateCubicFilter(height, nheight, (filter & TEX_FILTER_WRAP_V) != 0, (filter & TEX_FILTER_MIRROR_V) != 0, cfY); + +#ifdef _DEBUG + for (size_t j = 0; j < 4; ++j) + { + memset(urow[j], 0xCD, sizeof(XMVECTOR)*width); + memset(vrow[j], 0xDD, sizeof(XMVECTOR)*width); + memset(srow[j], 0xED, sizeof(XMVECTOR)*width); + memset(trow[j], 0xFD, sizeof(XMVECTOR)*width); + } +#endif + + if (depth > 1) + { + // 3D cubic filter + size_t ndepth = depth >> 1; + _CreateCubicFilter(depth, ndepth, (filter & TEX_FILTER_WRAP_W) != 0, (filter & TEX_FILTER_MIRROR_W) != 0, cfZ); + + for (size_t slice = 0; slice < ndepth; ++slice) + { + auto& toZ = cfZ[slice]; + + const Image* srca = mipChain.GetImage(level - 1, 0, toZ.u0); + const Image* srcb = mipChain.GetImage(level - 1, 0, toZ.u1); + const Image* srcc = mipChain.GetImage(level - 1, 0, toZ.u2); + const Image* srcd = mipChain.GetImage(level - 1, 0, toZ.u3); + if (!srca || !srcb || !srcc || !srcd) + return E_POINTER; + + size_t u0 = size_t(-1); + size_t u1 = size_t(-1); + size_t u2 = size_t(-1); + size_t u3 = size_t(-1); + + const Image* dest = mipChain.GetImage(level, 0, slice); + if (!dest) + return E_POINTER; + + uint8_t* pDest = dest->pixels; + + for (size_t y = 0; y < nheight; ++y) + { + auto& toY = cfY[y]; + + // Scanline 1 + if (toY.u0 != u0) + { + if (toY.u0 != u1 && toY.u0 != u2 && toY.u0 != u3) + { + u0 = toY.u0; + + if (!_LoadScanlineLinear(urow[0], width, srca->pixels + (srca->rowPitch * u0), srca->rowPitch, srca->format, filter) + || !_LoadScanlineLinear(urow[1], width, srcb->pixels + (srcb->rowPitch * u0), srcb->rowPitch, srcb->format, filter) + || !_LoadScanlineLinear(urow[2], width, srcc->pixels + (srcc->rowPitch * u0), srcc->rowPitch, srcc->format, filter) + || !_LoadScanlineLinear(urow[3], width, srcd->pixels + (srcd->rowPitch * u0), srcd->rowPitch, srcd->format, filter)) + return E_FAIL; + } + else if (toY.u0 == u1) + { + u0 = u1; + u1 = size_t(-1); + + std::swap(urow[0], vrow[0]); + std::swap(urow[1], vrow[1]); + std::swap(urow[2], vrow[2]); + std::swap(urow[3], vrow[3]); + } + else if (toY.u0 == u2) + { + u0 = u2; + u2 = size_t(-1); + + std::swap(urow[0], srow[0]); + std::swap(urow[1], srow[1]); + std::swap(urow[2], srow[2]); + std::swap(urow[3], srow[3]); + } + else if (toY.u0 == u3) + { + u0 = u3; + u3 = size_t(-1); + + std::swap(urow[0], trow[0]); + std::swap(urow[1], trow[1]); + std::swap(urow[2], trow[2]); + std::swap(urow[3], trow[3]); + } + } + + // Scanline 2 + if (toY.u1 != u1) + { + if (toY.u1 != u2 && toY.u1 != u3) + { + u1 = toY.u1; + + if (!_LoadScanlineLinear(vrow[0], width, srca->pixels + (srca->rowPitch * u1), srca->rowPitch, srca->format, filter) + || !_LoadScanlineLinear(vrow[1], width, srcb->pixels + (srcb->rowPitch * u1), srcb->rowPitch, srcb->format, filter) + || !_LoadScanlineLinear(vrow[2], width, srcc->pixels + (srcc->rowPitch * u1), srcc->rowPitch, srcc->format, filter) + || !_LoadScanlineLinear(vrow[3], width, srcd->pixels + (srcd->rowPitch * u1), srcd->rowPitch, srcd->format, filter)) + return E_FAIL; + } + else if (toY.u1 == u2) + { + u1 = u2; + u2 = size_t(-1); + + std::swap(vrow[0], srow[0]); + std::swap(vrow[1], srow[1]); + std::swap(vrow[2], srow[2]); + std::swap(vrow[3], srow[3]); + } + else if (toY.u1 == u3) + { + u1 = u3; + u3 = size_t(-1); + + std::swap(vrow[0], trow[0]); + std::swap(vrow[1], trow[1]); + std::swap(vrow[2], trow[2]); + std::swap(vrow[3], trow[3]); + } + } + + // Scanline 3 + if (toY.u2 != u2) + { + if (toY.u2 != u3) + { + u2 = toY.u2; + + if (!_LoadScanlineLinear(srow[0], width, srca->pixels + (srca->rowPitch * u2), srca->rowPitch, srca->format, filter) + || !_LoadScanlineLinear(srow[1], width, srcb->pixels + (srcb->rowPitch * u2), srcb->rowPitch, srcb->format, filter) + || !_LoadScanlineLinear(srow[2], width, srcc->pixels + (srcc->rowPitch * u2), srcc->rowPitch, srcc->format, filter) + || !_LoadScanlineLinear(srow[3], width, srcd->pixels + (srcd->rowPitch * u2), srcd->rowPitch, srcd->format, filter)) + return E_FAIL; + } + else + { + u2 = u3; + u3 = size_t(-1); + + std::swap(srow[0], trow[0]); + std::swap(srow[1], trow[1]); + std::swap(srow[2], trow[2]); + std::swap(srow[3], trow[3]); + } + } + + // Scanline 4 + if (toY.u3 != u3) + { + u3 = toY.u3; + + if (!_LoadScanlineLinear(trow[0], width, srca->pixels + (srca->rowPitch * u3), srca->rowPitch, srca->format, filter) + || !_LoadScanlineLinear(trow[1], width, srcb->pixels + (srcb->rowPitch * u3), srcb->rowPitch, srcb->format, filter) + || !_LoadScanlineLinear(trow[2], width, srcc->pixels + (srcc->rowPitch * u3), srcc->rowPitch, srcc->format, filter) + || !_LoadScanlineLinear(trow[3], width, srcd->pixels + (srcd->rowPitch * u3), srcd->rowPitch, srcd->format, filter)) + return E_FAIL; + } + + for (size_t x = 0; x < nwidth; ++x) + { + auto& toX = cfX[x]; + + XMVECTOR D[4]; + + for (size_t j = 0; j < 4; ++j) + { + XMVECTOR C0, C1, C2, C3; + CUBIC_INTERPOLATE(C0, toX.x, urow[j][toX.u0], urow[j][toX.u1], urow[j][toX.u2], urow[j][toX.u3]); + CUBIC_INTERPOLATE(C1, toX.x, vrow[j][toX.u0], vrow[j][toX.u1], vrow[j][toX.u2], vrow[j][toX.u3]); + CUBIC_INTERPOLATE(C2, toX.x, srow[j][toX.u0], srow[j][toX.u1], srow[j][toX.u2], srow[j][toX.u3]); + CUBIC_INTERPOLATE(C3, toX.x, trow[j][toX.u0], trow[j][toX.u1], trow[j][toX.u2], trow[j][toX.u3]); + + CUBIC_INTERPOLATE(D[j], toY.x, C0, C1, C2, C3); + } + + CUBIC_INTERPOLATE(target[x], toZ.x, D[0], D[1], D[2], D[3]); + } + + if (!_StoreScanlineLinear(pDest, dest->rowPitch, dest->format, target, nwidth, filter)) + return E_FAIL; + pDest += dest->rowPitch; + } + } + } + else + { + // 2D cubic filter + const Image* src = mipChain.GetImage(level - 1, 0, 0); + const Image* dest = mipChain.GetImage(level, 0, 0); + + if (!src || !dest) + return E_POINTER; + + const uint8_t* pSrc = src->pixels; + uint8_t* pDest = dest->pixels; + + size_t rowPitch = src->rowPitch; + + size_t u0 = size_t(-1); + size_t u1 = size_t(-1); + size_t u2 = size_t(-1); + size_t u3 = size_t(-1); + + for (size_t y = 0; y < nheight; ++y) + { + auto& toY = cfY[y]; + + // Scanline 1 + if (toY.u0 != u0) + { + if (toY.u0 != u1 && toY.u0 != u2 && toY.u0 != u3) + { + u0 = toY.u0; + + if (!_LoadScanlineLinear(urow[0], width, pSrc + (rowPitch * u0), rowPitch, src->format, filter)) + return E_FAIL; + } + else if (toY.u0 == u1) + { + u0 = u1; + u1 = size_t(-1); + + std::swap(urow[0], vrow[0]); + } + else if (toY.u0 == u2) + { + u0 = u2; + u2 = size_t(-1); + + std::swap(urow[0], srow[0]); + } + else if (toY.u0 == u3) + { + u0 = u3; + u3 = size_t(-1); + + std::swap(urow[0], trow[0]); + } + } + + // Scanline 2 + if (toY.u1 != u1) + { + if (toY.u1 != u2 && toY.u1 != u3) + { + u1 = toY.u1; + + if (!_LoadScanlineLinear(vrow[0], width, pSrc + (rowPitch * u1), rowPitch, src->format, filter)) + return E_FAIL; + } + else if (toY.u1 == u2) + { + u1 = u2; + u2 = size_t(-1); + + std::swap(vrow[0], srow[0]); + } + else if (toY.u1 == u3) + { + u1 = u3; + u3 = size_t(-1); + + std::swap(vrow[0], trow[0]); + } + } + + // Scanline 3 + if (toY.u2 != u2) + { + if (toY.u2 != u3) + { + u2 = toY.u2; + + if (!_LoadScanlineLinear(srow[0], width, pSrc + (rowPitch * u2), rowPitch, src->format, filter)) + return E_FAIL; + } + else + { + u2 = u3; + u3 = size_t(-1); + + std::swap(srow[0], trow[0]); + } + } + + // Scanline 4 + if (toY.u3 != u3) + { + u3 = toY.u3; + + if (!_LoadScanlineLinear(trow[0], width, pSrc + (rowPitch * u3), rowPitch, src->format, filter)) + return E_FAIL; + } + + for (size_t x = 0; x < nwidth; ++x) + { + auto& toX = cfX[x]; + + XMVECTOR C0, C1, C2, C3; + CUBIC_INTERPOLATE(C0, toX.x, urow[0][toX.u0], urow[0][toX.u1], urow[0][toX.u2], urow[0][toX.u3]); + CUBIC_INTERPOLATE(C1, toX.x, vrow[0][toX.u0], vrow[0][toX.u1], vrow[0][toX.u2], vrow[0][toX.u3]); + CUBIC_INTERPOLATE(C2, toX.x, srow[0][toX.u0], srow[0][toX.u1], srow[0][toX.u2], srow[0][toX.u3]); + CUBIC_INTERPOLATE(C3, toX.x, trow[0][toX.u0], trow[0][toX.u1], trow[0][toX.u2], trow[0][toX.u3]); + + CUBIC_INTERPOLATE(target[x], toY.x, C0, C1, C2, C3); + } + + if (!_StoreScanlineLinear(pDest, dest->rowPitch, dest->format, target, nwidth, filter)) + return E_FAIL; + pDest += dest->rowPitch; + } + } + + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + + if (depth > 1) + depth >>= 1; + } + + return S_OK; + } + + + //--- 3D Triangle Filter --- + HRESULT Generate3DMipsTriangleFilter(size_t depth, size_t levels, DWORD filter, const ScratchImage& mipChain) + { + if (!depth || !mipChain.GetImages()) + return E_INVALIDARG; + + using namespace TriangleFilter; + + // This assumes that the base images are already placed into the mipChain at the top level... (see _Setup3DMips) + + assert(levels > 1); + + size_t width = mipChain.GetMetadata().width; + size_t height = mipChain.GetMetadata().height; + + // Allocate initial temporary space (1 scanline, accumulation rows, plus X/Y/Z filters) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc(sizeof(XMVECTOR) * width, 16))); + if (!scanline) + return E_OUTOFMEMORY; + + std::unique_ptr sliceActive(new (std::nothrow) TriangleRow[depth]); + if (!sliceActive) + return E_OUTOFMEMORY; + + TriangleRow * sliceFree = nullptr; + + std::unique_ptr tfX, tfY, tfZ; + + XMVECTOR* row = scanline.get(); + + // Resize base image to each target mip level + for (size_t level = 1; level < levels; ++level) + { + size_t nwidth = (width > 1) ? (width >> 1) : 1; + HRESULT hr = _Create(width, nwidth, (filter & TEX_FILTER_WRAP_U) != 0, tfX); + if (FAILED(hr)) + return hr; + + size_t nheight = (height > 1) ? (height >> 1) : 1; + hr = _Create(height, nheight, (filter & TEX_FILTER_WRAP_V) != 0, tfY); + if (FAILED(hr)) + return hr; + + size_t ndepth = (depth > 1) ? (depth >> 1) : 1; + hr = _Create(depth, ndepth, (filter & TEX_FILTER_WRAP_W) != 0, tfZ); + if (FAILED(hr)) + return hr; + +#ifdef _DEBUG + memset(row, 0xCD, sizeof(XMVECTOR)*width); +#endif + + auto xFromEnd = reinterpret_cast(reinterpret_cast(tfX.get()) + tfX->sizeInBytes); + auto yFromEnd = reinterpret_cast(reinterpret_cast(tfY.get()) + tfY->sizeInBytes); + auto zFromEnd = reinterpret_cast(reinterpret_cast(tfZ.get()) + tfZ->sizeInBytes); + + // Count times slices get written (and clear out any leftover accumulation slices from last miplevel) + for (FilterFrom* zFrom = tfZ->from; zFrom < zFromEnd; ) + { + for (size_t j = 0; j < zFrom->count; ++j) + { + size_t w = zFrom->to[j].u; + assert(w < ndepth); + TriangleRow* sliceAcc = &sliceActive[w]; + + ++sliceAcc->remaining; + + if (sliceAcc->scanline) + { + memset(sliceAcc->scanline.get(), 0, sizeof(XMVECTOR) * nwidth * nheight); + } + } + + zFrom = reinterpret_cast(reinterpret_cast(zFrom) + zFrom->sizeInBytes); + } + + // Filter image + size_t z = 0; + for (FilterFrom* zFrom = tfZ->from; zFrom < zFromEnd; ++z) + { + // Create accumulation slices as needed + for (size_t j = 0; j < zFrom->count; ++j) + { + size_t w = zFrom->to[j].u; + assert(w < ndepth); + TriangleRow* sliceAcc = &sliceActive[w]; + + if (!sliceAcc->scanline) + { + if (sliceFree) + { + // Steal and reuse scanline from 'free slice' list + // (it will always be at least as large as nwidth*nheight due to loop decending order) + assert(sliceFree->scanline != 0); + sliceAcc->scanline.reset(sliceFree->scanline.release()); + sliceFree = sliceFree->next; + } + else + { + size_t bytes = sizeof(XMVECTOR) * nwidth * nheight; + sliceAcc->scanline.reset(reinterpret_cast(_aligned_malloc(bytes, 16))); + if (!sliceAcc->scanline) + return E_OUTOFMEMORY; + } + + memset(sliceAcc->scanline.get(), 0, sizeof(XMVECTOR) * nwidth * nheight); + } + } + + assert(z < depth); + const Image* src = mipChain.GetImage(level - 1, 0, z); + if (!src) + return E_POINTER; + + const uint8_t* pSrc = src->pixels; + size_t rowPitch = src->rowPitch; + const uint8_t* pEndSrc = pSrc + rowPitch * height; + + for (FilterFrom* yFrom = tfY->from; yFrom < yFromEnd; ) + { + // Load source scanline + if ((pSrc + rowPitch) > pEndSrc) + return E_FAIL; + + if (!_LoadScanlineLinear(row, width, pSrc, rowPitch, src->format, filter)) + return E_FAIL; + + pSrc += rowPitch; + + // Process row + size_t x = 0; + for (FilterFrom* xFrom = tfX->from; xFrom < xFromEnd; ++x) + { + for (size_t j = 0; j < zFrom->count; ++j) + { + size_t w = zFrom->to[j].u; + assert(w < ndepth); + float zweight = zFrom->to[j].weight; + + XMVECTOR* accSlice = sliceActive[w].scanline.get(); + if (!accSlice) + return E_POINTER; + + for (size_t k = 0; k < yFrom->count; ++k) + { + size_t v = yFrom->to[k].u; + assert(v < nheight); + float yweight = yFrom->to[k].weight; + + XMVECTOR * accPtr = accSlice + v * nwidth; + + for (size_t l = 0; l < xFrom->count; ++l) + { + size_t u = xFrom->to[l].u; + assert(u < nwidth); + + XMVECTOR weight = XMVectorReplicate(zweight * yweight * xFrom->to[l].weight); + + assert(x < width); + accPtr[u] = XMVectorMultiplyAdd(row[x], weight, accPtr[u]); + } + } + } + + xFrom = reinterpret_cast(reinterpret_cast(xFrom) + xFrom->sizeInBytes); + } + + yFrom = reinterpret_cast(reinterpret_cast(yFrom) + yFrom->sizeInBytes); + } + + // Write completed accumulation slices + for (size_t j = 0; j < zFrom->count; ++j) + { + size_t w = zFrom->to[j].u; + assert(w < ndepth); + TriangleRow* sliceAcc = &sliceActive[w]; + + assert(sliceAcc->remaining > 0); + --sliceAcc->remaining; + + if (!sliceAcc->remaining) + { + const Image* dest = mipChain.GetImage(level, 0, w); + XMVECTOR* pAccSrc = sliceAcc->scanline.get(); + if (!dest || !pAccSrc) + return E_POINTER; + + uint8_t* pDest = dest->pixels; + + for (size_t h = 0; h < nheight; ++h) + { + switch (dest->format) + { + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + { + // Need to slightly bias results for floating-point error accumulation which can + // be visible with harshly quantized values + static const XMVECTORF32 Bias = { { { 0.f, 0.f, 0.f, 0.1f } } }; + + XMVECTOR* ptr = pAccSrc; + for (size_t i = 0; i < dest->width; ++i, ++ptr) + { + *ptr = XMVectorAdd(*ptr, Bias); + } + } + break; + + default: + break; + } + + // This performs any required clamping + if (!_StoreScanlineLinear(pDest, dest->rowPitch, dest->format, pAccSrc, dest->width, filter)) + return E_FAIL; + + pDest += dest->rowPitch; + pAccSrc += nwidth; + } + + // Put slice on freelist to reuse it's allocated scanline + sliceAcc->next = sliceFree; + sliceFree = sliceAcc; + } + } + + zFrom = reinterpret_cast(reinterpret_cast(zFrom) + zFrom->sizeInBytes); + } + + if (height > 1) + height >>= 1; + + if (width > 1) + width >>= 1; + + if (depth > 1) + depth >>= 1; + } + + return S_OK; + } +} + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Generate mipmap chain +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::GenerateMipMaps( + const Image& baseImage, + DWORD filter, + size_t levels, + ScratchImage& mipChain, + bool allow1D) +{ + if (!IsValid(baseImage.format)) + return E_INVALIDARG; + + if (!baseImage.pixels) + return E_POINTER; + + if (!_CalculateMipLevels(baseImage.width, baseImage.height, levels)) + return E_INVALIDARG; + + if (levels <= 1) + return E_INVALIDARG; + + if (IsCompressed(baseImage.format) || IsTypeless(baseImage.format) || IsPlanar(baseImage.format) || IsPalettized(baseImage.format)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + HRESULT hr; + + static_assert(TEX_FILTER_POINT == 0x100000, "TEX_FILTER_ flag values don't match TEX_FILTER_MASK"); + + if (UseWICFiltering(baseImage.format, filter)) + { + //--- Use WIC filtering to generate mipmaps ----------------------------------- + switch (filter & TEX_FILTER_MASK) + { + case 0: + case TEX_FILTER_POINT: + case TEX_FILTER_FANT: // Equivalent to Box filter + case TEX_FILTER_LINEAR: + case TEX_FILTER_CUBIC: + { + static_assert(TEX_FILTER_FANT == TEX_FILTER_BOX, "TEX_FILTER_ flag alias mismatch"); + + WICPixelFormatGUID pfGUID; + if (_DXGIToWIC(baseImage.format, pfGUID, true)) + { + // Case 1: Base image format is supported by Windows Imaging Component + hr = (baseImage.height > 1 || !allow1D) + ? mipChain.Initialize2D(baseImage.format, baseImage.width, baseImage.height, 1, levels) + : mipChain.Initialize1D(baseImage.format, baseImage.width, 1, levels); + if (FAILED(hr)) + return hr; + + return GenerateMipMapsUsingWIC(baseImage, filter, levels, pfGUID, mipChain, 0); + } + else + { + // Case 2: Base image format is not supported by WIC, so we have to convert, generate, and convert back + assert(baseImage.format != DXGI_FORMAT_R32G32B32A32_FLOAT); + ScratchImage temp; + hr = _ConvertToR32G32B32A32(baseImage, temp); + if (FAILED(hr)) + return hr; + + const Image *timg = temp.GetImage(0, 0, 0); + if (!timg) + return E_POINTER; + + ScratchImage tMipChain; + hr = (baseImage.height > 1 || !allow1D) + ? tMipChain.Initialize2D(DXGI_FORMAT_R32G32B32A32_FLOAT, baseImage.width, baseImage.height, 1, levels) + : tMipChain.Initialize1D(DXGI_FORMAT_R32G32B32A32_FLOAT, baseImage.width, 1, levels); + if (FAILED(hr)) + return hr; + + hr = GenerateMipMapsUsingWIC(*timg, filter, levels, GUID_WICPixelFormat128bppRGBAFloat, tMipChain, 0); + if (FAILED(hr)) + return hr; + + temp.Release(); + + return _ConvertFromR32G32B32A32(tMipChain.GetImages(), tMipChain.GetImageCount(), tMipChain.GetMetadata(), baseImage.format, mipChain); + } + } + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } + else + { + //--- Use custom filters to generate mipmaps ---------------------------------- + TexMetadata mdata = {}; + mdata.width = baseImage.width; + if (baseImage.height > 1 || !allow1D) + { + mdata.height = baseImage.height; + mdata.dimension = TEX_DIMENSION_TEXTURE2D; + } + else + { + mdata.height = 1; + mdata.dimension = TEX_DIMENSION_TEXTURE1D; + } + mdata.depth = mdata.arraySize = 1; + mdata.mipLevels = levels; + mdata.format = baseImage.format; + + DWORD filter_select = (filter & TEX_FILTER_MASK); + if (!filter_select) + { + // Default filter choice + filter_select = (ispow2(baseImage.width) && ispow2(baseImage.height)) ? TEX_FILTER_BOX : TEX_FILTER_LINEAR; + } + + switch (filter_select) + { + case TEX_FILTER_BOX: + hr = Setup2DMips(&baseImage, 1, mdata, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate2DMipsBoxFilter(levels, filter, mipChain, 0); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_POINT: + hr = Setup2DMips(&baseImage, 1, mdata, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate2DMipsPointFilter(levels, mipChain, 0); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_LINEAR: + hr = Setup2DMips(&baseImage, 1, mdata, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate2DMipsLinearFilter(levels, filter, mipChain, 0); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_CUBIC: + hr = Setup2DMips(&baseImage, 1, mdata, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate2DMipsCubicFilter(levels, filter, mipChain, 0); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_TRIANGLE: + hr = Setup2DMips(&baseImage, 1, mdata, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate2DMipsTriangleFilter(levels, filter, mipChain, 0); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } +} + +_Use_decl_annotations_ +HRESULT DirectX::GenerateMipMaps( + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + DWORD filter, + size_t levels, + ScratchImage& mipChain) +{ + if (!srcImages || !nimages || !IsValid(metadata.format)) + return E_INVALIDARG; + + if (metadata.IsVolumemap() + || IsCompressed(metadata.format) || IsTypeless(metadata.format) || IsPlanar(metadata.format) || IsPalettized(metadata.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (!_CalculateMipLevels(metadata.width, metadata.height, levels)) + return E_INVALIDARG; + + if (levels <= 1) + return E_INVALIDARG; + + std::vector baseImages; + baseImages.reserve(metadata.arraySize); + for (size_t item = 0; item < metadata.arraySize; ++item) + { + size_t index = metadata.ComputeIndex(0, item, 0); + if (index >= nimages) + return E_FAIL; + + const Image& src = srcImages[index]; + if (!src.pixels) + return E_POINTER; + + if (src.format != metadata.format || src.width != metadata.width || src.height != metadata.height) + { + // All base images must be the same format, width, and height + return E_FAIL; + } + + baseImages.push_back(src); + } + + assert(baseImages.size() == metadata.arraySize); + + HRESULT hr; + + static_assert(TEX_FILTER_POINT == 0x100000, "TEX_FILTER_ flag values don't match TEX_FILTER_MASK"); + + if (!metadata.IsPMAlpha() && UseWICFiltering(metadata.format, filter)) + { + //--- Use WIC filtering to generate mipmaps ----------------------------------- + switch (filter & TEX_FILTER_MASK) + { + case 0: + case TEX_FILTER_POINT: + case TEX_FILTER_FANT: // Equivalent to Box filter + case TEX_FILTER_LINEAR: + case TEX_FILTER_CUBIC: + { + static_assert(TEX_FILTER_FANT == TEX_FILTER_BOX, "TEX_FILTER_ flag alias mismatch"); + + WICPixelFormatGUID pfGUID; + if (_DXGIToWIC(metadata.format, pfGUID, true)) + { + // Case 1: Base image format is supported by Windows Imaging Component + TexMetadata mdata2 = metadata; + mdata2.mipLevels = levels; + hr = mipChain.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + for (size_t item = 0; item < metadata.arraySize; ++item) + { + hr = GenerateMipMapsUsingWIC(baseImages[item], filter, levels, pfGUID, mipChain, item); + if (FAILED(hr)) + { + mipChain.Release(); + return hr; + } + } + + return S_OK; + } + else + { + // Case 2: Base image format is not supported by WIC, so we have to convert, generate, and convert back + assert(metadata.format != DXGI_FORMAT_R32G32B32A32_FLOAT); + + TexMetadata mdata2 = metadata; + mdata2.mipLevels = levels; + mdata2.format = DXGI_FORMAT_R32G32B32A32_FLOAT; + ScratchImage tMipChain; + hr = tMipChain.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + for (size_t item = 0; item < metadata.arraySize; ++item) + { + ScratchImage temp; + hr = _ConvertToR32G32B32A32(baseImages[item], temp); + if (FAILED(hr)) + return hr; + + const Image *timg = temp.GetImage(0, 0, 0); + if (!timg) + return E_POINTER; + + hr = GenerateMipMapsUsingWIC(*timg, filter, levels, GUID_WICPixelFormat128bppRGBAFloat, tMipChain, item); + if (FAILED(hr)) + return hr; + } + + return _ConvertFromR32G32B32A32(tMipChain.GetImages(), tMipChain.GetImageCount(), tMipChain.GetMetadata(), metadata.format, mipChain); + } + } + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } + else + { + //--- Use custom filters to generate mipmaps ---------------------------------- + TexMetadata mdata2 = metadata; + mdata2.mipLevels = levels; + + DWORD filter_select = (filter & TEX_FILTER_MASK); + if (!filter_select) + { + // Default filter choice + filter_select = (ispow2(metadata.width) && ispow2(metadata.height)) ? TEX_FILTER_BOX : TEX_FILTER_LINEAR; + } + + switch (filter_select) + { + case TEX_FILTER_BOX: + hr = Setup2DMips(&baseImages[0], metadata.arraySize, mdata2, mipChain); + if (FAILED(hr)) + return hr; + + for (size_t item = 0; item < metadata.arraySize; ++item) + { + hr = Generate2DMipsBoxFilter(levels, filter, mipChain, item); + if (FAILED(hr)) + mipChain.Release(); + } + return hr; + + case TEX_FILTER_POINT: + hr = Setup2DMips(&baseImages[0], metadata.arraySize, mdata2, mipChain); + if (FAILED(hr)) + return hr; + + for (size_t item = 0; item < metadata.arraySize; ++item) + { + hr = Generate2DMipsPointFilter(levels, mipChain, item); + if (FAILED(hr)) + mipChain.Release(); + } + return hr; + + case TEX_FILTER_LINEAR: + hr = Setup2DMips(&baseImages[0], metadata.arraySize, mdata2, mipChain); + if (FAILED(hr)) + return hr; + + for (size_t item = 0; item < metadata.arraySize; ++item) + { + hr = Generate2DMipsLinearFilter(levels, filter, mipChain, item); + if (FAILED(hr)) + mipChain.Release(); + } + return hr; + + case TEX_FILTER_CUBIC: + hr = Setup2DMips(&baseImages[0], metadata.arraySize, mdata2, mipChain); + if (FAILED(hr)) + return hr; + + for (size_t item = 0; item < metadata.arraySize; ++item) + { + hr = Generate2DMipsCubicFilter(levels, filter, mipChain, item); + if (FAILED(hr)) + mipChain.Release(); + } + return hr; + + case TEX_FILTER_TRIANGLE: + hr = Setup2DMips(&baseImages[0], metadata.arraySize, mdata2, mipChain); + if (FAILED(hr)) + return hr; + + for (size_t item = 0; item < metadata.arraySize; ++item) + { + hr = Generate2DMipsTriangleFilter(levels, filter, mipChain, item); + if (FAILED(hr)) + mipChain.Release(); + } + return hr; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } +} + + +//------------------------------------------------------------------------------------- +// Generate mipmap chain for volume texture +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::GenerateMipMaps3D( + const Image* baseImages, + size_t depth, + DWORD filter, + size_t levels, + ScratchImage& mipChain) +{ + if (!baseImages || !depth) + return E_INVALIDARG; + + if (filter & TEX_FILTER_FORCE_WIC) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + DXGI_FORMAT format = baseImages[0].format; + size_t width = baseImages[0].width; + size_t height = baseImages[0].height; + + if (!_CalculateMipLevels3D(width, height, depth, levels)) + return E_INVALIDARG; + + if (levels <= 1) + return E_INVALIDARG; + + for (size_t slice = 0; slice < depth; ++slice) + { + if (!baseImages[slice].pixels) + return E_POINTER; + + if (baseImages[slice].format != format || baseImages[slice].width != width || baseImages[slice].height != height) + { + // All base images must be the same format, width, and height + return E_FAIL; + } + } + + if (IsCompressed(format) || IsTypeless(format) || IsPlanar(format) || IsPalettized(format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + static_assert(TEX_FILTER_POINT == 0x100000, "TEX_FILTER_ flag values don't match TEX_FILTER_MASK"); + + HRESULT hr; + + DWORD filter_select = (filter & TEX_FILTER_MASK); + if (!filter_select) + { + // Default filter choice + filter_select = (ispow2(width) && ispow2(height) && ispow2(depth)) ? TEX_FILTER_BOX : TEX_FILTER_TRIANGLE; + } + + switch (filter_select) + { + case TEX_FILTER_BOX: + hr = Setup3DMips(baseImages, depth, levels, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate3DMipsBoxFilter(depth, levels, filter, mipChain); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_POINT: + hr = Setup3DMips(baseImages, depth, levels, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate3DMipsPointFilter(depth, levels, mipChain); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_LINEAR: + hr = Setup3DMips(baseImages, depth, levels, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate3DMipsLinearFilter(depth, levels, filter, mipChain); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_CUBIC: + hr = Setup3DMips(baseImages, depth, levels, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate3DMipsCubicFilter(depth, levels, filter, mipChain); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_TRIANGLE: + hr = Setup3DMips(baseImages, depth, levels, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate3DMipsTriangleFilter(depth, levels, filter, mipChain); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } +} + +_Use_decl_annotations_ +HRESULT DirectX::GenerateMipMaps3D( + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + DWORD filter, + size_t levels, + ScratchImage& mipChain) +{ + if (!srcImages || !nimages || !IsValid(metadata.format)) + return E_INVALIDARG; + + if (filter & TEX_FILTER_FORCE_WIC) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (!metadata.IsVolumemap() + || IsCompressed(metadata.format) || IsTypeless(metadata.format) || IsPlanar(metadata.format) || IsPalettized(metadata.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (!_CalculateMipLevels3D(metadata.width, metadata.height, metadata.depth, levels)) + return E_INVALIDARG; + + if (levels <= 1) + return E_INVALIDARG; + + std::vector baseImages; + baseImages.reserve(metadata.depth); + for (size_t slice = 0; slice < metadata.depth; ++slice) + { + size_t index = metadata.ComputeIndex(0, 0, slice); + if (index >= nimages) + return E_FAIL; + + const Image& src = srcImages[index]; + if (!src.pixels) + return E_POINTER; + + if (src.format != metadata.format || src.width != metadata.width || src.height != metadata.height) + { + // All base images must be the same format, width, and height + return E_FAIL; + } + + baseImages.push_back(src); + } + + assert(baseImages.size() == metadata.depth); + + HRESULT hr; + + static_assert(TEX_FILTER_POINT == 0x100000, "TEX_FILTER_ flag values don't match TEX_FILTER_MASK"); + + DWORD filter_select = (filter & TEX_FILTER_MASK); + if (!filter_select) + { + // Default filter choice + filter_select = (ispow2(metadata.width) && ispow2(metadata.height) && ispow2(metadata.depth)) ? TEX_FILTER_BOX : TEX_FILTER_TRIANGLE; + } + + switch (filter_select) + { + case TEX_FILTER_BOX: + hr = Setup3DMips(&baseImages[0], metadata.depth, levels, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate3DMipsBoxFilter(metadata.depth, levels, filter, mipChain); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_POINT: + hr = Setup3DMips(&baseImages[0], metadata.depth, levels, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate3DMipsPointFilter(metadata.depth, levels, mipChain); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_LINEAR: + hr = Setup3DMips(&baseImages[0], metadata.depth, levels, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate3DMipsLinearFilter(metadata.depth, levels, filter, mipChain); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_CUBIC: + hr = Setup3DMips(&baseImages[0], metadata.depth, levels, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate3DMipsCubicFilter(metadata.depth, levels, filter, mipChain); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + case TEX_FILTER_TRIANGLE: + hr = Setup3DMips(&baseImages[0], metadata.depth, levels, mipChain); + if (FAILED(hr)) + return hr; + + hr = Generate3DMipsTriangleFilter(metadata.depth, levels, filter, mipChain); + if (FAILED(hr)) + mipChain.Release(); + return hr; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexMisc.cpp b/deps/DirectXTex/DirectXTex/DirectXTexMisc.cpp new file mode 100644 index 0000000..2768360 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexMisc.cpp @@ -0,0 +1,765 @@ +//------------------------------------------------------------------------------------- +// DirectXTexMisc.cpp +// +// DirectX Texture Library - Misc image operations +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +using namespace DirectX; + +namespace +{ + const XMVECTORF32 g_Gamma22 = { { { 2.2f, 2.2f, 2.2f, 1.f } } }; + + //------------------------------------------------------------------------------------- + HRESULT ComputeMSE_( + const Image& image1, + const Image& image2, + float& mse, + _Out_writes_opt_(4) float* mseV, + DWORD flags) + { + if (!image1.pixels || !image2.pixels) + return E_POINTER; + + assert(image1.width == image2.width && image1.height == image2.height); + assert(!IsCompressed(image1.format) && !IsCompressed(image2.format)); + + const size_t width = image1.width; + + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width) * 2, 16))); + if (!scanline) + return E_OUTOFMEMORY; + + // Flags implied from image formats + switch (image1.format) + { + case DXGI_FORMAT_B8G8R8X8_UNORM: + flags |= CMSE_IGNORE_ALPHA; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + flags |= CMSE_IMAGE1_SRGB | CMSE_IGNORE_ALPHA; + break; + + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_BC7_UNORM_SRGB: + flags |= CMSE_IMAGE1_SRGB; + break; + + default: + break; + } + + switch (image2.format) + { + case DXGI_FORMAT_B8G8R8X8_UNORM: + flags |= CMSE_IGNORE_ALPHA; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + flags |= CMSE_IMAGE2_SRGB | CMSE_IGNORE_ALPHA; + break; + + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_BC7_UNORM_SRGB: + flags |= CMSE_IMAGE2_SRGB; + break; + + default: + break; + } + + const uint8_t *pSrc1 = image1.pixels; + const size_t rowPitch1 = image1.rowPitch; + + const uint8_t *pSrc2 = image2.pixels; + const size_t rowPitch2 = image2.rowPitch; + + XMVECTOR acc = g_XMZero; + static XMVECTORF32 two = { { { 2.0f, 2.0f, 2.0f, 2.0f } } }; + + for (size_t h = 0; h < image1.height; ++h) + { + XMVECTOR* ptr1 = scanline.get(); + if (!_LoadScanline(ptr1, width, pSrc1, rowPitch1, image1.format)) + return E_FAIL; + + XMVECTOR* ptr2 = scanline.get() + width; + if (!_LoadScanline(ptr2, width, pSrc2, rowPitch2, image2.format)) + return E_FAIL; + + for (size_t i = 0; i < width; ++i) + { + XMVECTOR v1 = *(ptr1++); + if (flags & CMSE_IMAGE1_SRGB) + { + v1 = XMVectorPow(v1, g_Gamma22); + } + if (flags & CMSE_IMAGE1_X2_BIAS) + { + v1 = XMVectorMultiplyAdd(v1, two, g_XMNegativeOne); + } + + XMVECTOR v2 = *(ptr2++); + if (flags & CMSE_IMAGE2_SRGB) + { + v2 = XMVectorPow(v2, g_Gamma22); + } + if (flags & CMSE_IMAGE2_X2_BIAS) + { + v2 = XMVectorMultiplyAdd(v2, two, g_XMNegativeOne); + } + + // sum[ (I1 - I2)^2 ] + XMVECTOR v = XMVectorSubtract(v1, v2); + if (flags & CMSE_IGNORE_RED) + { + v = XMVectorSelect(v, g_XMZero, g_XMMaskX); + } + if (flags & CMSE_IGNORE_GREEN) + { + v = XMVectorSelect(v, g_XMZero, g_XMMaskY); + } + if (flags & CMSE_IGNORE_BLUE) + { + v = XMVectorSelect(v, g_XMZero, g_XMMaskZ); + } + if (flags & CMSE_IGNORE_ALPHA) + { + v = XMVectorSelect(v, g_XMZero, g_XMMaskW); + } + + acc = XMVectorMultiplyAdd(v, v, acc); + } + + pSrc1 += rowPitch1; + pSrc2 += rowPitch2; + } + + // MSE = sum[ (I1 - I2)^2 ] / w*h + XMVECTOR d = XMVectorReplicate(float(image1.width * image1.height)); + XMVECTOR v = XMVectorDivide(acc, d); + if (mseV) + { + XMStoreFloat4(reinterpret_cast(mseV), v); + mse = mseV[0] + mseV[1] + mseV[2] + mseV[3]; + } + else + { + XMFLOAT4 _mseV; + XMStoreFloat4(&_mseV, v); + mse = _mseV.x + _mseV.y + _mseV.z + _mseV.w; + } + + return S_OK; + } + + //------------------------------------------------------------------------------------- + HRESULT EvaluateImage_( + const Image& image, + std::function& pixelFunc) + { + if (!pixelFunc) + return E_INVALIDARG; + + if (!image.pixels) + return E_POINTER; + + assert(!IsCompressed(image.format)); + + const size_t width = image.width; + + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + const uint8_t *pSrc = image.pixels; + const size_t rowPitch = image.rowPitch; + + for (size_t h = 0; h < image.height; ++h) + { + if (!_LoadScanline(scanline.get(), width, pSrc, rowPitch, image.format)) + return E_FAIL; + + pixelFunc(scanline.get(), width, h); + + pSrc += rowPitch; + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + HRESULT TransformImage_( + const Image& srcImage, + std::function& pixelFunc, + const Image& destImage) + { + if (!pixelFunc) + return E_INVALIDARG; + + if (!srcImage.pixels || !destImage.pixels) + return E_POINTER; + + if (srcImage.width != destImage.width || srcImage.height != destImage.height || srcImage.format != destImage.format) + return E_FAIL; + + const size_t width = srcImage.width; + + ScopedAlignedArrayXMVECTOR scanlines(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width*2), 16))); + if (!scanlines) + return E_OUTOFMEMORY; + + XMVECTOR* sScanline = scanlines.get(); + XMVECTOR* dScanline = scanlines.get() + width; + + const uint8_t *pSrc = srcImage.pixels; + const size_t spitch = srcImage.rowPitch; + + uint8_t *pDest = destImage.pixels; + const size_t dpitch = destImage.rowPitch; + + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_LoadScanline(sScanline, width, pSrc, spitch, srcImage.format)) + return E_FAIL; + +#ifdef _DEBUG + memset(dScanline, 0xCD, sizeof(XMVECTOR)*width); +#endif + + pixelFunc(dScanline, sScanline, width, h); + + if (!_StoreScanline(pDest, destImage.rowPitch, destImage.format, dScanline, width)) + return E_FAIL; + + pSrc += spitch; + pDest += dpitch; + } + + return S_OK; + } +}; + + +//===================================================================================== +// Entry points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Copies a rectangle from one image into another +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CopyRectangle( + const Image& srcImage, + const Rect& srcRect, + const Image& dstImage, + DWORD filter, + size_t xOffset, + size_t yOffset) +{ + if (!srcImage.pixels || !dstImage.pixels) + return E_POINTER; + + if (IsCompressed(srcImage.format) || IsCompressed(dstImage.format) + || IsPlanar(srcImage.format) || IsPlanar(dstImage.format) + || IsPalettized(srcImage.format) || IsPalettized(dstImage.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + // Validate rectangle/offset + if (!srcRect.w || !srcRect.h || ((srcRect.x + srcRect.w) > srcImage.width) || ((srcRect.y + srcRect.h) > srcImage.height)) + { + return E_INVALIDARG; + } + + if (((xOffset + srcRect.w) > dstImage.width) || ((yOffset + srcRect.h) > dstImage.height)) + { + return E_INVALIDARG; + } + + // Compute source bytes-per-pixel + size_t sbpp = BitsPerPixel(srcImage.format); + if (!sbpp) + return E_FAIL; + + if (sbpp < 8) + { + // We don't support monochrome (DXGI_FORMAT_R1_UNORM) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + const uint8_t* pEndSrc = srcImage.pixels + srcImage.rowPitch*srcImage.height; + const uint8_t* pEndDest = dstImage.pixels + dstImage.rowPitch*dstImage.height; + + // Round to bytes + sbpp = (sbpp + 7) / 8; + + const uint8_t* pSrc = srcImage.pixels + (srcRect.y * srcImage.rowPitch) + (srcRect.x * sbpp); + + if (srcImage.format == dstImage.format) + { + // Direct copy case (avoid intermediate conversions) + uint8_t* pDest = dstImage.pixels + (yOffset * dstImage.rowPitch) + (xOffset * sbpp); + const size_t copyW = srcRect.w * sbpp; + for (size_t h = 0; h < srcRect.h; ++h) + { + if (((pSrc + copyW) > pEndSrc) || (pDest > pEndDest)) + return E_FAIL; + + memcpy_s(pDest, pEndDest - pDest, pSrc, copyW); + + pSrc += srcImage.rowPitch; + pDest += dstImage.rowPitch; + } + + return S_OK; + } + + // Compute destination bytes-per-pixel (not the same format as source) + size_t dbpp = BitsPerPixel(dstImage.format); + if (!dbpp) + return E_FAIL; + + if (dbpp < 8) + { + // We don't support monochrome (DXGI_FORMAT_R1_UNORM) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + // Round to bytes + dbpp = (dbpp + 7) / 8; + + uint8_t* pDest = dstImage.pixels + (yOffset * dstImage.rowPitch) + (xOffset * dbpp); + + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*srcRect.w), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + const size_t copyS = srcRect.w * sbpp; + const size_t copyD = srcRect.w * dbpp; + + for (size_t h = 0; h < srcRect.h; ++h) + { + if (((pSrc + copyS) > pEndSrc) || ((pDest + copyD) > pEndDest)) + return E_FAIL; + + if (!_LoadScanline(scanline.get(), srcRect.w, pSrc, copyS, srcImage.format)) + return E_FAIL; + + _ConvertScanline(scanline.get(), srcRect.w, dstImage.format, srcImage.format, filter); + + if (!_StoreScanline(pDest, copyD, dstImage.format, scanline.get(), srcRect.w)) + return E_FAIL; + + pSrc += srcImage.rowPitch; + pDest += dstImage.rowPitch; + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Computes the Mean-Squared-Error (MSE) between two images +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::ComputeMSE( + const Image& image1, + const Image& image2, + float& mse, + float* mseV, + DWORD flags) +{ + if (!image1.pixels || !image2.pixels) + return E_POINTER; + + if (image1.width != image2.width || image1.height != image2.height) + return E_INVALIDARG; + + if (!IsValid(image1.format) || !IsValid(image2.format)) + return E_INVALIDARG; + + if (IsPlanar(image1.format) || IsPlanar(image2.format) + || IsPalettized(image1.format) || IsPalettized(image2.format) + || IsTypeless(image1.format) || IsTypeless(image2.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (IsCompressed(image1.format)) + { + if (IsCompressed(image2.format)) + { + // Case 1: both images are compressed, expand to RGBA32F + ScratchImage temp1; + HRESULT hr = Decompress(image1, DXGI_FORMAT_R32G32B32A32_FLOAT, temp1); + if (FAILED(hr)) + return hr; + + ScratchImage temp2; + hr = Decompress(image2, DXGI_FORMAT_R32G32B32A32_FLOAT, temp2); + if (FAILED(hr)) + return hr; + + const Image* img1 = temp1.GetImage(0, 0, 0); + const Image* img2 = temp2.GetImage(0, 0, 0); + if (!img1 || !img2) + return E_POINTER; + + return ComputeMSE_(*img1, *img2, mse, mseV, flags); + } + else + { + // Case 2: image1 is compressed, expand to RGBA32F + ScratchImage temp; + HRESULT hr = Decompress(image1, DXGI_FORMAT_R32G32B32A32_FLOAT, temp); + if (FAILED(hr)) + return hr; + + const Image* img = temp.GetImage(0, 0, 0); + if (!img) + return E_POINTER; + + return ComputeMSE_(*img, image2, mse, mseV, flags); + } + } + else + { + if (IsCompressed(image2.format)) + { + // Case 3: image2 is compressed, expand to RGBA32F + ScratchImage temp; + HRESULT hr = Decompress(image2, DXGI_FORMAT_R32G32B32A32_FLOAT, temp); + if (FAILED(hr)) + return hr; + + const Image* img = temp.GetImage(0, 0, 0); + if (!img) + return E_POINTER; + + return ComputeMSE_(image1, *img, mse, mseV, flags); + } + else + { + // Case 4: neither image is compressed + return ComputeMSE_(image1, image2, mse, mseV, flags); + } + } +} + + +//------------------------------------------------------------------------------------- +// Evaluates a user-supplied function for all the pixels in the image +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::EvaluateImage( + const Image& image, + std::function pixelFunc) +{ + if (image.width > UINT32_MAX + || image.height > UINT32_MAX) + return E_INVALIDARG; + + if (!IsValid(image.format)) + return E_INVALIDARG; + + if (IsPlanar(image.format) || IsPalettized(image.format) || IsTypeless(image.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (IsCompressed(image.format)) + { + ScratchImage temp; + HRESULT hr = Decompress(image, DXGI_FORMAT_R32G32B32A32_FLOAT, temp); + if (FAILED(hr)) + return hr; + + const Image* img = temp.GetImage(0, 0, 0); + if (!img) + return E_POINTER; + + return EvaluateImage_(*img, pixelFunc); + } + else + { + return EvaluateImage_(image, pixelFunc); + } +} + +_Use_decl_annotations_ +HRESULT DirectX::EvaluateImage( + const Image* images, + size_t nimages, + const TexMetadata& metadata, + std::function pixelFunc) +{ + if (!images || !nimages) + return E_INVALIDARG; + + if (!IsValid(metadata.format)) + return E_INVALIDARG; + + if (IsPlanar(metadata.format) || IsPalettized(metadata.format) || IsTypeless(metadata.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (metadata.width > UINT32_MAX + || metadata.height > UINT32_MAX) + return E_INVALIDARG; + + if (metadata.IsVolumemap() && metadata.depth > UINT16_MAX) + return E_INVALIDARG; + + ScratchImage temp; + DXGI_FORMAT format = metadata.format; + if (IsCompressed(format)) + { + HRESULT hr = Decompress(images, nimages, metadata, DXGI_FORMAT_R32G32B32A32_FLOAT, temp); + if (FAILED(hr)) + return hr; + + if (nimages != temp.GetImageCount()) + return E_UNEXPECTED; + + images = temp.GetImages(); + format = DXGI_FORMAT_R32G32B32A32_FLOAT; + } + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + case TEX_DIMENSION_TEXTURE2D: + for (size_t index = 0; index < nimages; ++index) + { + const Image& img = images[index]; + if (img.format != format) + return E_FAIL; + + if ((img.width > UINT32_MAX) || (img.height > UINT32_MAX)) + return E_FAIL; + + HRESULT hr = EvaluateImage_(img, pixelFunc); + if (FAILED(hr)) + return hr; + } + break; + + case TEX_DIMENSION_TEXTURE3D: + { + size_t index = 0; + size_t d = metadata.depth; + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + for (size_t slice = 0; slice < d; ++slice, ++index) + { + if (index >= nimages) + return E_FAIL; + + const Image& img = images[index]; + if (img.format != format) + return E_FAIL; + + if ((img.width > UINT32_MAX) || (img.height > UINT32_MAX)) + return E_FAIL; + + HRESULT hr = EvaluateImage_(img, pixelFunc); + if (FAILED(hr)) + return hr; + } + + if (d > 1) + d >>= 1; + } + } + break; + + default: + return E_FAIL; + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Use a user-supplied function to compute a new image from an input image +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::TransformImage( + const Image& image, + std::function pixelFunc, + ScratchImage& result) +{ + if (image.width > UINT32_MAX + || image.height > UINT32_MAX) + return E_INVALIDARG; + + if (IsPlanar(image.format) || IsPalettized(image.format) || IsCompressed(image.format) || IsTypeless(image.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + HRESULT hr = result.Initialize2D(image.format, image.width, image.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image* dimg = result.GetImage(0, 0, 0); + if (!dimg) + { + result.Release(); + return E_POINTER; + } + + hr = TransformImage_(image, pixelFunc, *dimg); + if (FAILED(hr)) + { + result.Release(); + return hr; + } + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT DirectX::TransformImage( + const Image* srcImages, + size_t nimages, const TexMetadata& metadata, + std::function pixelFunc, + ScratchImage& result) +{ + if (!srcImages || !nimages) + return E_INVALIDARG; + + if (IsPlanar(metadata.format) || IsPalettized(metadata.format) || IsCompressed(metadata.format) || IsTypeless(metadata.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (metadata.width > UINT32_MAX + || metadata.height > UINT32_MAX) + return E_INVALIDARG; + + if (metadata.IsVolumemap() && metadata.depth > UINT16_MAX) + return E_INVALIDARG; + + HRESULT hr = result.Initialize(metadata); + if (FAILED(hr)) + return hr; + + if (nimages != result.GetImageCount()) + { + result.Release(); + return E_FAIL; + } + + const Image* dest = result.GetImages(); + if (!dest) + { + result.Release(); + return E_POINTER; + } + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + case TEX_DIMENSION_TEXTURE2D: + for (size_t index = 0; index < nimages; ++index) + { + const Image& src = srcImages[index]; + if (src.format != metadata.format) + { + result.Release(); + return E_FAIL; + } + + if ((src.width > UINT32_MAX) || (src.height > UINT32_MAX)) + { + result.Release(); + return E_FAIL; + } + + const Image& dst = dest[index]; + + if (src.width != dst.width || src.height != dst.height) + { + result.Release(); + return E_FAIL; + } + + hr = TransformImage_(src, pixelFunc, dst); + if (FAILED(hr)) + { + result.Release(); + return hr; + } + } + break; + + case TEX_DIMENSION_TEXTURE3D: + { + size_t index = 0; + size_t d = metadata.depth; + for (size_t level = 0; level < metadata.mipLevels; ++level) + { + for (size_t slice = 0; slice < d; ++slice, ++index) + { + if (index >= nimages) + { + result.Release(); + return E_FAIL; + } + + const Image& src = srcImages[index]; + if (src.format != metadata.format) + { + result.Release(); + return E_FAIL; + } + + if ((src.width > UINT32_MAX) || (src.height > UINT32_MAX)) + { + result.Release(); + return E_FAIL; + } + + const Image& dst = dest[index]; + + if (src.width != dst.width || src.height != dst.height) + { + result.Release(); + return E_FAIL; + } + + hr = TransformImage_(src, pixelFunc, dst); + if (FAILED(hr)) + { + result.Release(); + return hr; + } + } + + if (d > 1) + d >>= 1; + } + } + break; + + default: + result.Release(); + return E_FAIL; + } + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexNormalMaps.cpp b/deps/DirectXTex/DirectXTex/DirectXTexNormalMaps.cpp new file mode 100644 index 0000000..be00499 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexNormalMaps.cpp @@ -0,0 +1,397 @@ +//------------------------------------------------------------------------------------- +// DirectXTexNormalMaps.cpp +// +// DirectX Texture Library - Normal map operations +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +using namespace DirectX; + +namespace +{ + +#pragma prefast(suppress : 25000, "FXMVECTOR is 16 bytes") + inline float EvaluateColor(_In_ FXMVECTOR val, _In_ DWORD flags) + { + XMFLOAT4A f; + + static XMVECTORF32 lScale = { { { 0.2125f, 0.7154f, 0.0721f, 1.f } } }; + + static_assert(CNMAP_CHANNEL_RED == 0x1, "CNMAP_CHANNEL_ flag values don't match mask"); + switch (flags & 0xf) + { + case 0: + case CNMAP_CHANNEL_RED: return XMVectorGetX(val); + case CNMAP_CHANNEL_GREEN: return XMVectorGetY(val); + case CNMAP_CHANNEL_BLUE: return XMVectorGetZ(val); + case CNMAP_CHANNEL_ALPHA: return XMVectorGetW(val); + + case CNMAP_CHANNEL_LUMINANCE: + { + XMVECTOR v = XMVectorMultiply(val, lScale); + XMStoreFloat4A(&f, v); + return f.x + f.y + f.z; + } + break; + + default: + assert(false); + return 0.f; + } + } + + void EvaluateRow( + _In_reads_(width) const XMVECTOR* pSource, + _Out_writes_(width + 2) float* pDest, + size_t width, + DWORD flags) + { + assert(pSource && pDest); + assert(width > 0); + + for (size_t x = 0; x < width; ++x) + { + pDest[x + 1] = EvaluateColor(pSource[x], flags); + } + + if (flags & CNMAP_MIRROR_U) + { + // Mirror in U + pDest[0] = EvaluateColor(pSource[0], flags); + pDest[width + 1] = EvaluateColor(pSource[width - 1], flags); + } + else + { + // Wrap in U + pDest[0] = EvaluateColor(pSource[width - 1], flags); + pDest[width + 1] = EvaluateColor(pSource[0], flags); + } + } + + HRESULT ComputeNMap(_In_ const Image& srcImage, _In_ DWORD flags, _In_ float amplitude, + _In_ DXGI_FORMAT format, _In_ const Image& normalMap) + { + if (!srcImage.pixels || !normalMap.pixels) + return E_INVALIDARG; + + const DWORD convFlags = _GetConvertFlags(format); + if (!convFlags) + return E_FAIL; + + if (!(convFlags & (CONVF_UNORM | CONVF_SNORM | CONVF_FLOAT))) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + const size_t width = srcImage.width; + const size_t height = srcImage.height; + if (width != normalMap.width || height != normalMap.height) + return E_FAIL; + + // Allocate temporary space (4 scanlines and 3 evaluated rows) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*width * 4), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + ScopedAlignedArrayFloat buffer(reinterpret_cast(_aligned_malloc(((sizeof(float) * (width + 2)) * 3), 16))); + if (!buffer) + return E_OUTOFMEMORY; + + uint8_t* pDest = normalMap.pixels; + if (!pDest) + return E_POINTER; + + XMVECTOR* row0 = scanline.get(); + XMVECTOR* row1 = row0 + width; + XMVECTOR* row2 = row1 + width; + XMVECTOR* target = row2 + width; + + float* val0 = buffer.get(); + float* val1 = val0 + width + 2; + float* val2 = val1 + width + 2; + + const size_t rowPitch = srcImage.rowPitch; + const uint8_t* pSrc = srcImage.pixels; + + // Read first scanline row into 'row1' + if (!_LoadScanline(row1, width, pSrc, rowPitch, srcImage.format)) + return E_FAIL; + + // Setup 'row0' + if (flags & CNMAP_MIRROR_V) + { + // Mirror first row + memcpy_s(row0, rowPitch, row1, rowPitch); + } + else + { + // Read last row (Wrap V) + if (!_LoadScanline(row0, width, pSrc + (rowPitch * (height - 1)), rowPitch, srcImage.format)) + return E_FAIL; + } + + // Evaluate the initial rows + EvaluateRow(row0, val0, width, flags); + EvaluateRow(row1, val1, width, flags); + + pSrc += rowPitch; + + for (size_t y = 0; y < height; ++y) + { + // Load next scanline of source image + if (y < (height - 1)) + { + if (!_LoadScanline(row2, width, pSrc, rowPitch, srcImage.format)) + return E_FAIL; + } + else + { + if (flags & CNMAP_MIRROR_V) + { + // Use last row of source image + if (!_LoadScanline(row2, width, srcImage.pixels + (rowPitch * (height - 1)), rowPitch, srcImage.format)) + return E_FAIL; + } + else + { + // Use first row of source image (Wrap V) + if (!_LoadScanline(row2, width, srcImage.pixels, rowPitch, srcImage.format)) + return E_FAIL; + } + } + + // Evaluate row + EvaluateRow(row2, val2, width, flags); + + // Generate target scanline + XMVECTOR *dptr = target; + for (size_t x = 0; x < width; ++x) + { + // Compute normal via central differencing + float totDelta = (val0[x] - val0[x + 2]) + (val1[x] - val1[x + 2]) + (val2[x] - val2[x + 2]); + float deltaZX = totDelta * amplitude / 6.f; + + totDelta = (val0[x] - val2[x]) + (val0[x + 1] - val2[x + 1]) + (val0[x + 2] - val2[x + 2]); + float deltaZY = totDelta * amplitude / 6.f; + + XMVECTOR vx = XMVectorSetZ(g_XMNegIdentityR0, deltaZX); // (-1.0f, 0.0f, deltaZX) + XMVECTOR vy = XMVectorSetZ(g_XMNegIdentityR1, deltaZY); // (0.0f, -1.0f, deltaZY) + + XMVECTOR normal = XMVector3Normalize(XMVector3Cross(vx, vy)); + + // Compute alpha (1.0 or an occlusion term) + float alpha = 1.f; + + if (flags & CNMAP_COMPUTE_OCCLUSION) + { + float delta = 0.f; + float c = val1[x + 1]; + + float t = val0[x] - c; if (t > 0.f) delta += t; + t = val0[x + 1] - c; if (t > 0.f) delta += t; + t = val0[x + 2] - c; if (t > 0.f) delta += t; + t = val1[x] - c; if (t > 0.f) delta += t; + // Skip current pixel + t = val1[x + 2] - c; if (t > 0.f) delta += t; + t = val2[x] - c; if (t > 0.f) delta += t; + t = val2[x + 1] - c; if (t > 0.f) delta += t; + t = val2[x + 2] - c; if (t > 0.f) delta += t; + + // Average delta (divide by 8, scale by amplitude factor) + delta *= 0.125f * amplitude; + if (delta > 0.f) + { + // If < 0, then no occlusion + float r = sqrtf(1.f + delta*delta); + alpha = (r - delta) / r; + } + } + + // Encode based on target format + if (convFlags & CONVF_UNORM) + { + // 0.5f*normal + 0.5f -or- invert sign case: -0.5f*normal + 0.5f + XMVECTOR n1 = XMVectorMultiplyAdd((flags & CNMAP_INVERT_SIGN) ? g_XMNegativeOneHalf : g_XMOneHalf, normal, g_XMOneHalf); + *dptr++ = XMVectorSetW(n1, alpha); + } + else if (flags & CNMAP_INVERT_SIGN) + { + *dptr++ = XMVectorSetW(XMVectorNegate(normal), alpha); + } + else + { + *dptr++ = XMVectorSetW(normal, alpha); + } + } + + if (!_StoreScanline(pDest, normalMap.rowPitch, format, target, width)) + return E_FAIL; + + // Cycle buffers + float* temp = val0; + val0 = val1; + val1 = val2; + val2 = temp; + + pSrc += rowPitch; + pDest += normalMap.rowPitch; + } + + return S_OK; + } +} + + +//===================================================================================== +// Entry points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Generates a normal map from a height-map +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::ComputeNormalMap( + const Image& srcImage, + DWORD flags, + float amplitude, + DXGI_FORMAT format, + ScratchImage& normalMap) +{ + if (!srcImage.pixels || !IsValid(format)) + return E_INVALIDARG; + + static_assert(CNMAP_CHANNEL_RED == 0x1, "CNMAP_CHANNEL_ flag values don't match mask"); + switch (flags & 0xf) + { + case 0: + case CNMAP_CHANNEL_RED: + case CNMAP_CHANNEL_GREEN: + case CNMAP_CHANNEL_BLUE: + case CNMAP_CHANNEL_ALPHA: + case CNMAP_CHANNEL_LUMINANCE: + break; + + default: + return E_INVALIDARG; + } + + if (IsCompressed(format) || IsCompressed(srcImage.format) + || IsTypeless(format) || IsTypeless(srcImage.format) + || IsPlanar(format) || IsPlanar(srcImage.format) + || IsPalettized(format) || IsPalettized(srcImage.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + // Setup target image + normalMap.Release(); + + HRESULT hr = normalMap.Initialize2D(format, srcImage.width, srcImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *img = normalMap.GetImage(0, 0, 0); + if (!img) + { + normalMap.Release(); + return E_POINTER; + } + + hr = ComputeNMap(srcImage, flags, amplitude, format, *img); + if (FAILED(hr)) + { + normalMap.Release(); + return hr; + } + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT DirectX::ComputeNormalMap( + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + DWORD flags, + float amplitude, + DXGI_FORMAT format, + ScratchImage& normalMaps) +{ + if (!srcImages || !nimages || !IsValid(format)) + return E_INVALIDARG; + + if (IsCompressed(format) || IsCompressed(metadata.format) + || IsTypeless(format) || IsTypeless(metadata.format) + || IsPlanar(format) || IsPlanar(metadata.format) + || IsPalettized(format) || IsPalettized(metadata.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + static_assert(CNMAP_CHANNEL_RED == 0x1, "CNMAP_CHANNEL_ flag values don't match mask"); + switch (flags & 0xf) + { + case 0: + case CNMAP_CHANNEL_RED: + case CNMAP_CHANNEL_GREEN: + case CNMAP_CHANNEL_BLUE: + case CNMAP_CHANNEL_ALPHA: + case CNMAP_CHANNEL_LUMINANCE: + break; + + default: + return E_INVALIDARG; + } + + normalMaps.Release(); + + TexMetadata mdata2 = metadata; + mdata2.format = format; + HRESULT hr = normalMaps.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + if (nimages != normalMaps.GetImageCount()) + { + normalMaps.Release(); + return E_FAIL; + } + + const Image* dest = normalMaps.GetImages(); + if (!dest) + { + normalMaps.Release(); + return E_POINTER; + } + + for (size_t index = 0; index < nimages; ++index) + { + assert(dest[index].format == format); + + const Image& src = srcImages[index]; + if (IsCompressed(src.format) || IsTypeless(src.format)) + { + normalMaps.Release(); + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + if (src.width != dest[index].width || src.height != dest[index].height) + { + normalMaps.Release(); + return E_FAIL; + } + + hr = ComputeNMap(src, flags, amplitude, format, dest[index]); + if (FAILED(hr)) + { + normalMaps.Release(); + return hr; + } + } + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexP.h b/deps/DirectXTex/DirectXTex/DirectXTexP.h new file mode 100644 index 0000000..cb20422 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexP.h @@ -0,0 +1,277 @@ +//------------------------------------------------------------------------------------- +// DirectXTexp.h +// +// DirectX Texture Library - Private header +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#pragma once + +// VS 2013 related Off by default warnings +#pragma warning(disable : 4619 4616 4350 4351 4472 4640) +// C4619/4616 #pragma warning warnings +// C4350 behavior change +// C4351 behavior change; warning removed in later versions +// C4472 'X' is a native enum: add an access specifier (private/public) to declare a WinRT enum +// C4640 construction of local static object is not thread-safe + +// Off by default warnings +#pragma warning(disable : 4061 4265 4365 4571 4623 4625 4626 4668 4710 4711 4746 4774 4820 4987 5026 5027 5031 5032) +// C4061 enumerator 'X' in switch of enum 'X' is not explicitly handled by a case label +// C4265 class has virtual functions, but destructor is not virtual +// C4365 signed/unsigned mismatch +// C4571 behavior change +// C4623 default constructor was implicitly defined as deleted +// C4625 copy constructor was implicitly defined as deleted +// C4626 assignment operator was implicitly defined as deleted +// C4668 not defined as a preprocessor macro +// C4710 function not inlined +// C4711 selected for automatic inline expansion +// C4746 volatile access of '' is subject to /volatile: setting +// C4774 format string expected in argument 3 is not a string literal +// C4820 padding added after data member +// C4987 nonstandard extension used +// C5026 move constructor was implicitly defined as deleted +// C5027 move assignment operator was implicitly defined as deleted +// C5031/5032 push/pop mismatches in windows headers + +// Windows 8.1 SDK related Off by default warnings +#pragma warning(disable : 4471 4917 4986 5029) +// C4471 forward declaration of an unscoped enumeration must have an underlying type +// C4917 a GUID can only be associated with a class, interface or namespace +// C4986 exception specification does not match previous declaration +// C5029 nonstandard extension used + +#pragma warning(push) +#pragma warning(disable : 4005) +#define WIN32_LEAN_AND_MEAN +#define NOMINMAX +#define NODRAWTEXT +#define NOGDI +#define NOBITMAP +#define NOMCX +#define NOSERVICE +#define NOHELP +#pragma warning(pop) + +#ifndef _WIN32_WINNT_WIN10 +#define _WIN32_WINNT_WIN10 0x0A00 +#endif + +#include + +#if defined(_XBOX_ONE) && defined(_TITLE) +#include +#include +#elif (_WIN32_WINNT >= _WIN32_WINNT_WIN10) +#include +#include +#else +#include +#endif + +#include +#include +#include + +#include +#include + +#include + +#include +#include + +#include + +#include "directxtex.h" + +#include + +#include + +#include "scoped.h" + +#define TEX_FILTER_MASK 0xF00000 + +#define XBOX_DXGI_FORMAT_R10G10B10_7E3_A2_FLOAT DXGI_FORMAT(116) +#define XBOX_DXGI_FORMAT_R10G10B10_6E4_A2_FLOAT DXGI_FORMAT(117) +#define XBOX_DXGI_FORMAT_D16_UNORM_S8_UINT DXGI_FORMAT(118) +#define XBOX_DXGI_FORMAT_R16_UNORM_X8_TYPELESS DXGI_FORMAT(119) +#define XBOX_DXGI_FORMAT_X16_TYPELESS_G8_UINT DXGI_FORMAT(120) + +#define WIN10_DXGI_FORMAT_P208 DXGI_FORMAT(130) +#define WIN10_DXGI_FORMAT_V208 DXGI_FORMAT(131) +#define WIN10_DXGI_FORMAT_V408 DXGI_FORMAT(132) + +#ifndef XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM +#define XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM DXGI_FORMAT(189) +#endif + +#define XBOX_DXGI_FORMAT_R4G4_UNORM DXGI_FORMAT(190) + + +namespace DirectX +{ + //--------------------------------------------------------------------------------- + // WIC helper functions + DXGI_FORMAT __cdecl _WICToDXGI( _In_ const GUID& guid ); + bool __cdecl _DXGIToWIC( _In_ DXGI_FORMAT format, _Out_ GUID& guid, _In_ bool ignoreRGBvsBGR = false ); + + DWORD __cdecl _CheckWICColorSpace( _In_ const GUID& sourceGUID, _In_ const GUID& targetGUID ); + + inline WICBitmapDitherType __cdecl _GetWICDither( _In_ DWORD flags ) + { + static_assert( TEX_FILTER_DITHER == 0x10000, "TEX_FILTER_DITHER* flag values don't match mask" ); + + static_assert(static_cast(TEX_FILTER_DITHER) == static_cast(WIC_FLAGS_DITHER), "TEX_FILTER_DITHER* should match WIC_FLAGS_DITHER*"); + static_assert(static_cast(TEX_FILTER_DITHER_DIFFUSION) == static_cast(WIC_FLAGS_DITHER_DIFFUSION), "TEX_FILTER_DITHER* should match WIC_FLAGS_DITHER*"); + + switch( flags & 0xF0000 ) + { + case TEX_FILTER_DITHER: + return WICBitmapDitherTypeOrdered4x4; + + case TEX_FILTER_DITHER_DIFFUSION: + return WICBitmapDitherTypeErrorDiffusion; + + default: + return WICBitmapDitherTypeNone; + } + } + + inline WICBitmapInterpolationMode __cdecl _GetWICInterp( _In_ DWORD flags ) + { + static_assert( TEX_FILTER_POINT == 0x100000, "TEX_FILTER_ flag values don't match TEX_FILTER_MASK" ); + + static_assert(static_cast(TEX_FILTER_POINT) == static_cast(WIC_FLAGS_FILTER_POINT), "TEX_FILTER_* flags should match WIC_FLAGS_FILTER_*"); + static_assert(static_cast(TEX_FILTER_LINEAR) == static_cast(WIC_FLAGS_FILTER_LINEAR), "TEX_FILTER_* flags should match WIC_FLAGS_FILTER_*"); + static_assert(static_cast(TEX_FILTER_CUBIC) == static_cast(WIC_FLAGS_FILTER_CUBIC), "TEX_FILTER_* flags should match WIC_FLAGS_FILTER_*"); + static_assert(static_cast(TEX_FILTER_FANT) == static_cast(WIC_FLAGS_FILTER_FANT), "TEX_FILTER_* flags should match WIC_FLAGS_FILTER_*"); + + switch( flags & TEX_FILTER_MASK ) + { + case TEX_FILTER_POINT: + return WICBitmapInterpolationModeNearestNeighbor; + + case TEX_FILTER_LINEAR: + return WICBitmapInterpolationModeLinear; + + case TEX_FILTER_CUBIC: + return WICBitmapInterpolationModeCubic; + + case TEX_FILTER_FANT: + default: + return WICBitmapInterpolationModeFant; + } + } + + //--------------------------------------------------------------------------------- + // Image helper functions + void __cdecl _DetermineImageArray( _In_ const TexMetadata& metadata, _In_ DWORD cpFlags, + _Out_ size_t& nImages, _Out_ size_t& pixelSize ); + + _Success_(return != false) + bool __cdecl _SetupImageArray( _In_reads_bytes_(pixelSize) uint8_t *pMemory, _In_ size_t pixelSize, + _In_ const TexMetadata& metadata, _In_ DWORD cpFlags, + _Out_writes_(nImages) Image* images, _In_ size_t nImages ); + + //--------------------------------------------------------------------------------- + // Conversion helper functions + + enum TEXP_SCANLINE_FLAGS + { + TEXP_SCANLINE_NONE = 0, + TEXP_SCANLINE_SETALPHA = 0x1, // Set alpha channel to known opaque value + TEXP_SCANLINE_LEGACY = 0x2, // Enables specific legacy format conversion cases + }; + + enum CONVERT_FLAGS + { + CONVF_FLOAT = 0x1, + CONVF_UNORM = 0x2, + CONVF_UINT = 0x4, + CONVF_SNORM = 0x8, + CONVF_SINT = 0x10, + CONVF_DEPTH = 0x20, + CONVF_STENCIL = 0x40, + CONVF_SHAREDEXP = 0x80, + CONVF_BGR = 0x100, + CONVF_XR = 0x200, + CONVF_PACKED = 0x400, + CONVF_BC = 0x800, + CONVF_YUV = 0x1000, + CONVF_POS_ONLY = 0x2000, + CONVF_R = 0x10000, + CONVF_G = 0x20000, + CONVF_B = 0x40000, + CONVF_A = 0x80000, + CONVF_RGB_MASK = 0x70000, + CONVF_RGBA_MASK = 0xF0000, + }; + + DWORD __cdecl _GetConvertFlags( _In_ DXGI_FORMAT format ); + + void __cdecl _CopyScanline( _When_(pDestination == pSource, _Inout_updates_bytes_(outSize)) + _When_(pDestination != pSource, _Out_writes_bytes_(outSize)) + void* pDestination, _In_ size_t outSize, + _In_reads_bytes_(inSize) const void* pSource, _In_ size_t inSize, + _In_ DXGI_FORMAT format, _In_ DWORD flags ); + + void __cdecl _SwizzleScanline( _When_(pDestination == pSource, _In_) + _When_(pDestination != pSource, _Out_writes_bytes_(outSize)) + void* pDestination, _In_ size_t outSize, + _In_reads_bytes_(inSize) const void* pSource, _In_ size_t inSize, + _In_ DXGI_FORMAT format, _In_ DWORD flags ); + + _Success_(return != false) + bool __cdecl _ExpandScanline( _Out_writes_bytes_(outSize) void* pDestination, _In_ size_t outSize, + _In_ DXGI_FORMAT outFormat, + _In_reads_bytes_(inSize) const void* pSource, _In_ size_t inSize, + _In_ DXGI_FORMAT inFormat, _In_ DWORD flags ); + + _Success_(return != false) + bool __cdecl _LoadScanline( _Out_writes_(count) XMVECTOR* pDestination, _In_ size_t count, + _In_reads_bytes_(size) const void* pSource, _In_ size_t size, _In_ DXGI_FORMAT format ); + + _Success_(return != false) + bool __cdecl _LoadScanlineLinear( _Out_writes_(count) XMVECTOR* pDestination, _In_ size_t count, + _In_reads_bytes_(size) const void* pSource, _In_ size_t size, _In_ DXGI_FORMAT format, _In_ DWORD flags ); + + _Success_(return != false) + bool __cdecl _StoreScanline( _Out_writes_bytes_(size) void* pDestination, _In_ size_t size, _In_ DXGI_FORMAT format, + _In_reads_(count) const XMVECTOR* pSource, _In_ size_t count, _In_ float threshold = 0 ); + + _Success_(return != false) + bool __cdecl _StoreScanlineLinear( _Out_writes_bytes_(size) void* pDestination, _In_ size_t size, _In_ DXGI_FORMAT format, + _Inout_updates_all_(count) XMVECTOR* pSource, _In_ size_t count, _In_ DWORD flags, _In_ float threshold = 0 ); + + _Success_(return != false) + bool __cdecl _StoreScanlineDither( _Out_writes_bytes_(size) void* pDestination, _In_ size_t size, _In_ DXGI_FORMAT format, + _Inout_updates_all_(count) XMVECTOR* pSource, _In_ size_t count, _In_ float threshold, size_t y, size_t z, + _Inout_updates_all_opt_(count+2) XMVECTOR* pDiffusionErrors ); + + HRESULT __cdecl _ConvertToR32G32B32A32( _In_ const Image& srcImage, _Inout_ ScratchImage& image ); + + HRESULT __cdecl _ConvertFromR32G32B32A32( _In_ const Image& srcImage, _In_ const Image& destImage ); + HRESULT __cdecl _ConvertFromR32G32B32A32( _In_ const Image& srcImage, _In_ DXGI_FORMAT format, _Inout_ ScratchImage& image ); + HRESULT __cdecl _ConvertFromR32G32B32A32( _In_reads_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata, + _In_ DXGI_FORMAT format, _Out_ ScratchImage& result ); + + void __cdecl _ConvertScanline( _Inout_updates_all_(count) XMVECTOR* pBuffer, _In_ size_t count, + _In_ DXGI_FORMAT outFormat, _In_ DXGI_FORMAT inFormat, _In_ DWORD flags ); + + //--------------------------------------------------------------------------------- + // DDS helper functions + HRESULT __cdecl _EncodeDDSHeader( _In_ const TexMetadata& metadata, DWORD flags, + _Out_writes_bytes_to_opt_(maxsize, required) void* pDestination, _In_ size_t maxsize, _Out_ size_t& required ); + +}; // namespace diff --git a/deps/DirectXTex/DirectXTex/DirectXTexPMAlpha.cpp b/deps/DirectXTex/DirectXTex/DirectXTexPMAlpha.cpp new file mode 100644 index 0000000..233e667 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexPMAlpha.cpp @@ -0,0 +1,328 @@ +//------------------------------------------------------------------------------------- +// DirectXTexPMAlpha.cpp +// +// DirectX Texture Library - Premultiplied alpha operations +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +using namespace DirectX; + +namespace +{ + //--------------------------------------------------------------------------------- + // NonPremultiplied alpha -> Premultiplied alpha + HRESULT PremultiplyAlpha_(const Image& srcImage, const Image& destImage) + { + assert(srcImage.width == destImage.width); + assert(srcImage.height == destImage.height); + + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*srcImage.width), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + const uint8_t *pSrc = srcImage.pixels; + uint8_t *pDest = destImage.pixels; + if (!pSrc || !pDest) + return E_POINTER; + + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_LoadScanline(scanline.get(), srcImage.width, pSrc, srcImage.rowPitch, srcImage.format)) + return E_FAIL; + + XMVECTOR* ptr = scanline.get(); + for (size_t w = 0; w < srcImage.width; ++w) + { + XMVECTOR v = *ptr; + XMVECTOR alpha = XMVectorSplatW(*ptr); + alpha = XMVectorMultiply(v, alpha); + *(ptr++) = XMVectorSelect(v, alpha, g_XMSelect1110); + } + + if (!_StoreScanline(pDest, destImage.rowPitch, destImage.format, scanline.get(), srcImage.width)) + return E_FAIL; + + pSrc += srcImage.rowPitch; + pDest += destImage.rowPitch; + } + + return S_OK; + } + + HRESULT PremultiplyAlphaLinear(const Image& srcImage, DWORD flags, const Image& destImage) + { + assert(srcImage.width == destImage.width); + assert(srcImage.height == destImage.height); + + static_assert(static_cast(TEX_PMALPHA_SRGB_IN) == static_cast(TEX_FILTER_SRGB_IN), "TEX_PMALHPA_SRGB* should match TEX_FILTER_SRGB*"); + static_assert(static_cast(TEX_PMALPHA_SRGB_OUT) == static_cast(TEX_FILTER_SRGB_OUT), "TEX_PMALHPA_SRGB* should match TEX_FILTER_SRGB*"); + static_assert(static_cast(TEX_PMALPHA_SRGB) == static_cast(TEX_FILTER_SRGB), "TEX_PMALHPA_SRGB* should match TEX_FILTER_SRGB*"); + flags &= TEX_PMALPHA_SRGB; + + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*srcImage.width), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + const uint8_t *pSrc = srcImage.pixels; + uint8_t *pDest = destImage.pixels; + if (!pSrc || !pDest) + return E_POINTER; + + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_LoadScanlineLinear(scanline.get(), srcImage.width, pSrc, srcImage.rowPitch, srcImage.format, flags)) + return E_FAIL; + + XMVECTOR* ptr = scanline.get(); + for (size_t w = 0; w < srcImage.width; ++w) + { + XMVECTOR v = *ptr; + XMVECTOR alpha = XMVectorSplatW(*ptr); + alpha = XMVectorMultiply(v, alpha); + *(ptr++) = XMVectorSelect(v, alpha, g_XMSelect1110); + } + + if (!_StoreScanlineLinear(pDest, destImage.rowPitch, destImage.format, scanline.get(), srcImage.width, flags)) + return E_FAIL; + + pSrc += srcImage.rowPitch; + pDest += destImage.rowPitch; + } + + return S_OK; + } + + //--------------------------------------------------------------------------------- + // Premultiplied alpha -> NonPremultiplied alpha (a.k.a. Straight alpha) + HRESULT DemultiplyAlpha(const Image& srcImage, const Image& destImage) + { + assert(srcImage.width == destImage.width); + assert(srcImage.height == destImage.height); + + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*srcImage.width), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + const uint8_t *pSrc = srcImage.pixels; + uint8_t *pDest = destImage.pixels; + if (!pSrc || !pDest) + return E_POINTER; + + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_LoadScanline(scanline.get(), srcImage.width, pSrc, srcImage.rowPitch, srcImage.format)) + return E_FAIL; + + XMVECTOR* ptr = scanline.get(); + for (size_t w = 0; w < srcImage.width; ++w) + { + XMVECTOR v = *ptr; + XMVECTOR alpha = XMVectorSplatW(*ptr); + alpha = XMVectorDivide(v, alpha); + *(ptr++) = XMVectorSelect(v, alpha, g_XMSelect1110); + } + + if (!_StoreScanline(pDest, destImage.rowPitch, destImage.format, scanline.get(), srcImage.width)) + return E_FAIL; + + pSrc += srcImage.rowPitch; + pDest += destImage.rowPitch; + } + + return S_OK; + } + + HRESULT DemultiplyAlphaLinear(const Image& srcImage, DWORD flags, const Image& destImage) + { + assert(srcImage.width == destImage.width); + assert(srcImage.height == destImage.height); + + static_assert(static_cast(TEX_PMALPHA_SRGB_IN) == static_cast(TEX_FILTER_SRGB_IN), "TEX_PMALHPA_SRGB* should match TEX_FILTER_SRGB*"); + static_assert(static_cast(TEX_PMALPHA_SRGB_OUT) == static_cast(TEX_FILTER_SRGB_OUT), "TEX_PMALHPA_SRGB* should match TEX_FILTER_SRGB*"); + static_assert(static_cast(TEX_PMALPHA_SRGB) == static_cast(TEX_FILTER_SRGB), "TEX_PMALHPA_SRGB* should match TEX_FILTER_SRGB*"); + flags &= TEX_PMALPHA_SRGB; + + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc((sizeof(XMVECTOR)*srcImage.width), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + const uint8_t *pSrc = srcImage.pixels; + uint8_t *pDest = destImage.pixels; + if (!pSrc || !pDest) + return E_POINTER; + + for (size_t h = 0; h < srcImage.height; ++h) + { + if (!_LoadScanlineLinear(scanline.get(), srcImage.width, pSrc, srcImage.rowPitch, srcImage.format, flags)) + return E_FAIL; + + XMVECTOR* ptr = scanline.get(); + for (size_t w = 0; w < srcImage.width; ++w) + { + XMVECTOR v = *ptr; + XMVECTOR alpha = XMVectorSplatW(*ptr); + alpha = XMVectorDivide(v, alpha); + *(ptr++) = XMVectorSelect(v, alpha, g_XMSelect1110); + } + + if (!_StoreScanlineLinear(pDest, destImage.rowPitch, destImage.format, scanline.get(), srcImage.width, flags)) + return E_FAIL; + + pSrc += srcImage.rowPitch; + pDest += destImage.rowPitch; + } + + return S_OK; + } +} + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Converts to/from a premultiplied alpha version of the texture +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::PremultiplyAlpha( + const Image& srcImage, + DWORD flags, + ScratchImage& image) +{ + if (!srcImage.pixels) + return E_POINTER; + + if (IsCompressed(srcImage.format) + || IsPlanar(srcImage.format) + || IsPalettized(srcImage.format) + || IsTypeless(srcImage.format) + || !HasAlpha(srcImage.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if ((srcImage.width > UINT32_MAX) || (srcImage.height > UINT32_MAX)) + return E_INVALIDARG; + + HRESULT hr = image.Initialize2D(srcImage.format, srcImage.width, srcImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *rimage = image.GetImage(0, 0, 0); + if (!rimage) + { + image.Release(); + return E_POINTER; + } + + if (flags & TEX_PMALPHA_REVERSE) + { + hr = (flags & TEX_PMALPHA_IGNORE_SRGB) ? DemultiplyAlpha(srcImage, *rimage) : DemultiplyAlphaLinear(srcImage, flags, *rimage); + } + else + { + hr = (flags & TEX_PMALPHA_IGNORE_SRGB) ? PremultiplyAlpha_(srcImage, *rimage) : PremultiplyAlphaLinear(srcImage, flags, *rimage); + } + if (FAILED(hr)) + { + image.Release(); + return hr; + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Converts to/from a premultiplied alpha version of the texture (complex) +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::PremultiplyAlpha( + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + DWORD flags, + ScratchImage& result) +{ + if (!srcImages || !nimages) + return E_INVALIDARG; + + if (IsCompressed(metadata.format) + || IsPlanar(metadata.format) + || IsPalettized(metadata.format) + || IsTypeless(metadata.format) + || !HasAlpha(metadata.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if ((metadata.width > UINT32_MAX) || (metadata.height > UINT32_MAX)) + return E_INVALIDARG; + + if (metadata.IsPMAlpha() != ((flags & TEX_PMALPHA_REVERSE) != 0)) + return E_FAIL; + + TexMetadata mdata2 = metadata; + mdata2.SetAlphaMode((flags & TEX_PMALPHA_REVERSE) ? TEX_ALPHA_MODE_STRAIGHT : TEX_ALPHA_MODE_PREMULTIPLIED); + HRESULT hr = result.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + if (nimages != result.GetImageCount()) + { + result.Release(); + return E_FAIL; + } + + const Image* dest = result.GetImages(); + if (!dest) + { + result.Release(); + return E_POINTER; + } + + for (size_t index = 0; index < nimages; ++index) + { + const Image& src = srcImages[index]; + if (src.format != metadata.format) + { + result.Release(); + return E_FAIL; + } + + if ((src.width > UINT32_MAX) || (src.height > UINT32_MAX)) + return E_FAIL; + + const Image& dst = dest[index]; + assert(dst.format == metadata.format); + + if (src.width != dst.width || src.height != dst.height) + { + result.Release(); + return E_FAIL; + } + + if (flags & TEX_PMALPHA_REVERSE) + { + hr = (flags & TEX_PMALPHA_IGNORE_SRGB) ? DemultiplyAlpha(src, dst) : DemultiplyAlphaLinear(src, flags, dst); + } + else + { + hr = (flags & TEX_PMALPHA_IGNORE_SRGB) ? PremultiplyAlpha_(src, dst) : PremultiplyAlphaLinear(src, flags, dst); + } + if (FAILED(hr)) + { + result.Release(); + return hr; + } + } + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexResize.cpp b/deps/DirectXTex/DirectXTex/DirectXTexResize.cpp new file mode 100644 index 0000000..49c723f --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexResize.cpp @@ -0,0 +1,1061 @@ +//------------------------------------------------------------------------------------- +// DirectXTexResize.cpp +// +// DirectX Texture Library - Image resizing operations +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +#include "filters.h" + +using namespace DirectX; +using Microsoft::WRL::ComPtr; + +namespace DirectX +{ + extern HRESULT _ResizeSeparateColorAndAlpha(_In_ IWICImagingFactory* pWIC, _In_ bool iswic2, _In_ IWICBitmap* original, + _In_ size_t newWidth, _In_ size_t newHeight, _In_ DWORD filter, _Inout_ const Image* img); +} + +namespace +{ + //--- Do image resize using WIC --- + HRESULT PerformResizeUsingWIC( + const Image& srcImage, + DWORD filter, + const WICPixelFormatGUID& pfGUID, + const Image& destImage) + { + if (!srcImage.pixels || !destImage.pixels) + return E_POINTER; + + assert(srcImage.format == destImage.format); + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr componentInfo; + HRESULT hr = pWIC->CreateComponentInfo(pfGUID, componentInfo.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr pixelFormatInfo; + hr = componentInfo.As(&pixelFormatInfo); + if (FAILED(hr)) + return hr; + + BOOL supportsTransparency = FALSE; + hr = pixelFormatInfo->SupportsTransparency(&supportsTransparency); + if (FAILED(hr)) + return hr; + + ComPtr source; + hr = pWIC->CreateBitmapFromMemory(static_cast(srcImage.width), static_cast(srcImage.height), pfGUID, + static_cast(srcImage.rowPitch), static_cast(srcImage.slicePitch), + srcImage.pixels, source.GetAddressOf()); + if (FAILED(hr)) + return hr; + + if ((filter & TEX_FILTER_SEPARATE_ALPHA) && supportsTransparency) + { + hr = _ResizeSeparateColorAndAlpha(pWIC, iswic2, source.Get(), destImage.width, destImage.height, filter, &destImage); + if (FAILED(hr)) + return hr; + } + else + { + ComPtr scaler; + hr = pWIC->CreateBitmapScaler(scaler.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = scaler->Initialize(source.Get(), static_cast(destImage.width), static_cast(destImage.height), _GetWICInterp(filter)); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID pfScaler; + hr = scaler->GetPixelFormat(&pfScaler); + if (FAILED(hr)) + return hr; + + if (memcmp(&pfScaler, &pfGUID, sizeof(WICPixelFormatGUID)) == 0) + { + hr = scaler->CopyPixels(0, static_cast(destImage.rowPitch), static_cast(destImage.slicePitch), destImage.pixels); + if (FAILED(hr)) + return hr; + } + else + { + // The WIC bitmap scaler is free to return a different pixel format than the source image, so here we + // convert it back + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pfScaler, pfGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(scaler.Get(), pfGUID, _GetWICDither(filter), nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(0, static_cast(destImage.rowPitch), static_cast(destImage.slicePitch), destImage.pixels); + if (FAILED(hr)) + return hr; + } + } + + return S_OK; + } + + + //--- Do conversion, resize using WIC, conversion cycle --- + HRESULT PerformResizeViaF32( + const Image& srcImage, + DWORD filter, + const Image& destImage) + { + if (!srcImage.pixels || !destImage.pixels) + return E_POINTER; + + assert(srcImage.format != DXGI_FORMAT_R32G32B32A32_FLOAT); + assert(srcImage.format == destImage.format); + + ScratchImage temp; + HRESULT hr = _ConvertToR32G32B32A32(srcImage, temp); + if (FAILED(hr)) + return hr; + + const Image *tsrc = temp.GetImage(0, 0, 0); + if (!tsrc) + return E_POINTER; + + ScratchImage rtemp; + hr = rtemp.Initialize2D(DXGI_FORMAT_R32G32B32A32_FLOAT, destImage.width, destImage.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *tdest = rtemp.GetImage(0, 0, 0); + if (!tdest) + return E_POINTER; + + hr = PerformResizeUsingWIC(*tsrc, filter, GUID_WICPixelFormat128bppRGBAFloat, *tdest); + if (FAILED(hr)) + return hr; + + temp.Release(); + + hr = _ConvertFromR32G32B32A32(*tdest, destImage); + if (FAILED(hr)) + return hr; + + return S_OK; + } + + + //--- determine when to use WIC vs. non-WIC paths --- + bool UseWICFiltering(_In_ DXGI_FORMAT format, _In_ DWORD filter) + { + if (filter & TEX_FILTER_FORCE_NON_WIC) + { + // Explicit flag indicates use of non-WIC code paths + return false; + } + + if (filter & TEX_FILTER_FORCE_WIC) + { + // Explicit flag to use WIC code paths, skips all the case checks below + return true; + } + + if (IsSRGB(format) || (filter & TEX_FILTER_SRGB)) + { + // Use non-WIC code paths for sRGB correct filtering + return false; + } + +#if defined(_XBOX_ONE) && defined(_TITLE) + if (format == DXGI_FORMAT_R16G16B16A16_FLOAT + || format == DXGI_FORMAT_R16_FLOAT) + { + // Use non-WIC code paths as these conversions are not supported by Xbox One XDK + return false; + } +#endif + + static_assert(TEX_FILTER_POINT == 0x100000, "TEX_FILTER_ flag values don't match TEX_FILTER_MASK"); + + switch (filter & TEX_FILTER_MASK) + { + case TEX_FILTER_LINEAR: + if (filter & TEX_FILTER_WRAP) + { + // WIC only supports 'clamp' semantics (MIRROR is equivalent to clamp for linear) + return false; + } + + if (BitsPerColor(format) > 8) + { + // Avoid the WIC bitmap scaler when doing Linear filtering of XR/HDR formats + return false; + } + break; + + case TEX_FILTER_CUBIC: + if (filter & (TEX_FILTER_WRAP | TEX_FILTER_MIRROR)) + { + // WIC only supports 'clamp' semantics + return false; + } + + if (BitsPerColor(format) > 8) + { + // Avoid the WIC bitmap scaler when doing Cubic filtering of XR/HDR formats + return false; + } + break; + + case TEX_FILTER_TRIANGLE: + // WIC does not implement this filter + return false; + } + + return true; + } + + + //------------------------------------------------------------------------------------- + // Resize custom filters + //------------------------------------------------------------------------------------- + + //--- Point Filter --- + HRESULT ResizePointFilter(const Image& srcImage, const Image& destImage) + { + assert(srcImage.pixels && destImage.pixels); + assert(srcImage.format == destImage.format); + + // Allocate temporary space (2 scanlines) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc( + (sizeof(XMVECTOR) * (srcImage.width + destImage.width)), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + XMVECTOR* target = scanline.get(); + + XMVECTOR* row = target + destImage.width; + +#ifdef _DEBUG + memset(row, 0xCD, sizeof(XMVECTOR)*srcImage.width); +#endif + + const uint8_t* pSrc = srcImage.pixels; + uint8_t* pDest = destImage.pixels; + + size_t rowPitch = srcImage.rowPitch; + + size_t xinc = (srcImage.width << 16) / destImage.width; + size_t yinc = (srcImage.height << 16) / destImage.height; + + size_t lasty = size_t(-1); + + size_t sy = 0; + for (size_t y = 0; y < destImage.height; ++y) + { + if ((lasty ^ sy) >> 16) + { + if (!_LoadScanline(row, srcImage.width, pSrc + (rowPitch * (sy >> 16)), rowPitch, srcImage.format)) + return E_FAIL; + lasty = sy; + } + + size_t sx = 0; + for (size_t x = 0; x < destImage.width; ++x) + { + target[x] = row[sx >> 16]; + sx += xinc; + } + + if (!_StoreScanline(pDest, destImage.rowPitch, destImage.format, target, destImage.width)) + return E_FAIL; + pDest += destImage.rowPitch; + + sy += yinc; + } + + return S_OK; + } + + + //--- Box Filter --- + HRESULT ResizeBoxFilter(const Image& srcImage, DWORD filter, const Image& destImage) + { + assert(srcImage.pixels && destImage.pixels); + assert(srcImage.format == destImage.format); + + if (((destImage.width << 1) != srcImage.width) || ((destImage.height << 1) != srcImage.height)) + return E_FAIL; + + // Allocate temporary space (3 scanlines) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc( + (sizeof(XMVECTOR) * (srcImage.width * 2 + destImage.width)), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + XMVECTOR* target = scanline.get(); + + XMVECTOR* urow0 = target + destImage.width; + XMVECTOR* urow1 = urow0 + srcImage.width; + +#ifdef _DEBUG + memset(urow0, 0xCD, sizeof(XMVECTOR)*srcImage.width); + memset(urow1, 0xDD, sizeof(XMVECTOR)*srcImage.width); +#endif + + const XMVECTOR* urow2 = urow0 + 1; + const XMVECTOR* urow3 = urow1 + 1; + + const uint8_t* pSrc = srcImage.pixels; + uint8_t* pDest = destImage.pixels; + + size_t rowPitch = srcImage.rowPitch; + + for (size_t y = 0; y < destImage.height; ++y) + { + if (!_LoadScanlineLinear(urow0, srcImage.width, pSrc, rowPitch, srcImage.format, filter)) + return E_FAIL; + pSrc += rowPitch; + + if (urow0 != urow1) + { + if (!_LoadScanlineLinear(urow1, srcImage.width, pSrc, rowPitch, srcImage.format, filter)) + return E_FAIL; + pSrc += rowPitch; + } + + for (size_t x = 0; x < destImage.width; ++x) + { + size_t x2 = x << 1; + + AVERAGE4(target[x], urow0[x2], urow1[x2], urow2[x2], urow3[x2]); + } + + if (!_StoreScanlineLinear(pDest, destImage.rowPitch, destImage.format, target, destImage.width, filter)) + return E_FAIL; + pDest += destImage.rowPitch; + } + + return S_OK; + } + + + //--- Linear Filter --- + HRESULT ResizeLinearFilter(const Image& srcImage, DWORD filter, const Image& destImage) + { + assert(srcImage.pixels && destImage.pixels); + assert(srcImage.format == destImage.format); + + // Allocate temporary space (3 scanlines, plus X and Y filters) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc( + (sizeof(XMVECTOR) * (srcImage.width * 2 + destImage.width)), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + std::unique_ptr lf(new (std::nothrow) LinearFilter[destImage.width + destImage.height]); + if (!lf) + return E_OUTOFMEMORY; + + LinearFilter* lfX = lf.get(); + LinearFilter* lfY = lf.get() + destImage.width; + + _CreateLinearFilter(srcImage.width, destImage.width, (filter & TEX_FILTER_WRAP_U) != 0, lfX); + _CreateLinearFilter(srcImage.height, destImage.height, (filter & TEX_FILTER_WRAP_V) != 0, lfY); + + XMVECTOR* target = scanline.get(); + + XMVECTOR* row0 = target + destImage.width; + XMVECTOR* row1 = row0 + srcImage.width; + +#ifdef _DEBUG + memset(row0, 0xCD, sizeof(XMVECTOR)*srcImage.width); + memset(row1, 0xDD, sizeof(XMVECTOR)*srcImage.width); +#endif + + const uint8_t* pSrc = srcImage.pixels; + uint8_t* pDest = destImage.pixels; + + size_t rowPitch = srcImage.rowPitch; + + size_t u0 = size_t(-1); + size_t u1 = size_t(-1); + + for (size_t y = 0; y < destImage.height; ++y) + { + auto& toY = lfY[y]; + + if (toY.u0 != u0) + { + if (toY.u0 != u1) + { + u0 = toY.u0; + + if (!_LoadScanlineLinear(row0, srcImage.width, pSrc + (rowPitch * u0), rowPitch, srcImage.format, filter)) + return E_FAIL; + } + else + { + u0 = u1; + u1 = size_t(-1); + + std::swap(row0, row1); + } + } + + if (toY.u1 != u1) + { + u1 = toY.u1; + + if (!_LoadScanlineLinear(row1, srcImage.width, pSrc + (rowPitch * u1), rowPitch, srcImage.format, filter)) + return E_FAIL; + } + + for (size_t x = 0; x < destImage.width; ++x) + { + auto& toX = lfX[x]; + + BILINEAR_INTERPOLATE(target[x], toX, toY, row0, row1); + } + + if (!_StoreScanlineLinear(pDest, destImage.rowPitch, destImage.format, target, destImage.width, filter)) + return E_FAIL; + pDest += destImage.rowPitch; + } + + return S_OK; + } + + + //--- Cubic Filter --- + HRESULT ResizeCubicFilter(const Image& srcImage, DWORD filter, const Image& destImage) + { + assert(srcImage.pixels && destImage.pixels); + assert(srcImage.format == destImage.format); + + // Allocate temporary space (5 scanlines, plus X and Y filters) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc( + (sizeof(XMVECTOR) * (srcImage.width * 4 + destImage.width)), 16))); + if (!scanline) + return E_OUTOFMEMORY; + + std::unique_ptr cf(new (std::nothrow) CubicFilter[destImage.width + destImage.height]); + if (!cf) + return E_OUTOFMEMORY; + + CubicFilter* cfX = cf.get(); + CubicFilter* cfY = cf.get() + destImage.width; + + _CreateCubicFilter(srcImage.width, destImage.width, (filter & TEX_FILTER_WRAP_U) != 0, (filter & TEX_FILTER_MIRROR_U) != 0, cfX); + _CreateCubicFilter(srcImage.height, destImage.height, (filter & TEX_FILTER_WRAP_V) != 0, (filter & TEX_FILTER_MIRROR_V) != 0, cfY); + + XMVECTOR* target = scanline.get(); + + XMVECTOR* row0 = target + destImage.width; + XMVECTOR* row1 = row0 + srcImage.width; + XMVECTOR* row2 = row0 + srcImage.width * 2; + XMVECTOR* row3 = row0 + srcImage.width * 3; + +#ifdef _DEBUG + memset(row0, 0xCD, sizeof(XMVECTOR)*srcImage.width); + memset(row1, 0xDD, sizeof(XMVECTOR)*srcImage.width); + memset(row2, 0xED, sizeof(XMVECTOR)*srcImage.width); + memset(row3, 0xFD, sizeof(XMVECTOR)*srcImage.width); +#endif + + const uint8_t* pSrc = srcImage.pixels; + uint8_t* pDest = destImage.pixels; + + size_t rowPitch = srcImage.rowPitch; + + size_t u0 = size_t(-1); + size_t u1 = size_t(-1); + size_t u2 = size_t(-1); + size_t u3 = size_t(-1); + + for (size_t y = 0; y < destImage.height; ++y) + { + auto& toY = cfY[y]; + + // Scanline 1 + if (toY.u0 != u0) + { + if (toY.u0 != u1 && toY.u0 != u2 && toY.u0 != u3) + { + u0 = toY.u0; + + if (!_LoadScanlineLinear(row0, srcImage.width, pSrc + (rowPitch * u0), rowPitch, srcImage.format, filter)) + return E_FAIL; + } + else if (toY.u0 == u1) + { + u0 = u1; + u1 = size_t(-1); + + std::swap(row0, row1); + } + else if (toY.u0 == u2) + { + u0 = u2; + u2 = size_t(-1); + + std::swap(row0, row2); + } + else if (toY.u0 == u3) + { + u0 = u3; + u3 = size_t(-1); + + std::swap(row0, row3); + } + } + + // Scanline 2 + if (toY.u1 != u1) + { + if (toY.u1 != u2 && toY.u1 != u3) + { + u1 = toY.u1; + + if (!_LoadScanlineLinear(row1, srcImage.width, pSrc + (rowPitch * u1), rowPitch, srcImage.format, filter)) + return E_FAIL; + } + else if (toY.u1 == u2) + { + u1 = u2; + u2 = size_t(-1); + + std::swap(row1, row2); + } + else if (toY.u1 == u3) + { + u1 = u3; + u3 = size_t(-1); + + std::swap(row1, row3); + } + } + + // Scanline 3 + if (toY.u2 != u2) + { + if (toY.u2 != u3) + { + u2 = toY.u2; + + if (!_LoadScanlineLinear(row2, srcImage.width, pSrc + (rowPitch * u2), rowPitch, srcImage.format, filter)) + return E_FAIL; + } + else + { + u2 = u3; + u3 = size_t(-1); + + std::swap(row2, row3); + } + } + + // Scanline 4 + if (toY.u3 != u3) + { + u3 = toY.u3; + + if (!_LoadScanlineLinear(row3, srcImage.width, pSrc + (rowPitch * u3), rowPitch, srcImage.format, filter)) + return E_FAIL; + } + + for (size_t x = 0; x < destImage.width; ++x) + { + auto& toX = cfX[x]; + + XMVECTOR C0, C1, C2, C3; + + CUBIC_INTERPOLATE(C0, toX.x, row0[toX.u0], row0[toX.u1], row0[toX.u2], row0[toX.u3]); + CUBIC_INTERPOLATE(C1, toX.x, row1[toX.u0], row1[toX.u1], row1[toX.u2], row1[toX.u3]); + CUBIC_INTERPOLATE(C2, toX.x, row2[toX.u0], row2[toX.u1], row2[toX.u2], row2[toX.u3]); + CUBIC_INTERPOLATE(C3, toX.x, row3[toX.u0], row3[toX.u1], row3[toX.u2], row3[toX.u3]); + + CUBIC_INTERPOLATE(target[x], toY.x, C0, C1, C2, C3); + } + + if (!_StoreScanlineLinear(pDest, destImage.rowPitch, destImage.format, target, destImage.width, filter)) + return E_FAIL; + pDest += destImage.rowPitch; + } + + return S_OK; + } + + + //--- Triangle Filter --- + HRESULT ResizeTriangleFilter(const Image& srcImage, DWORD filter, const Image& destImage) + { + assert(srcImage.pixels && destImage.pixels); + assert(srcImage.format == destImage.format); + + using namespace TriangleFilter; + + // Allocate initial temporary space (1 scanline, accumulation rows, plus X and Y filters) + ScopedAlignedArrayXMVECTOR scanline(reinterpret_cast(_aligned_malloc(sizeof(XMVECTOR) * srcImage.width, 16))); + if (!scanline) + return E_OUTOFMEMORY; + + std::unique_ptr rowActive(new (std::nothrow) TriangleRow[destImage.height]); + if (!rowActive) + return E_OUTOFMEMORY; + + TriangleRow * rowFree = nullptr; + + std::unique_ptr tfX; + HRESULT hr = _Create(srcImage.width, destImage.width, (filter & TEX_FILTER_WRAP_U) != 0, tfX); + if (FAILED(hr)) + return hr; + + std::unique_ptr tfY; + hr = _Create(srcImage.height, destImage.height, (filter & TEX_FILTER_WRAP_V) != 0, tfY); + if (FAILED(hr)) + return hr; + + XMVECTOR* row = scanline.get(); + +#ifdef _DEBUG + memset(row, 0xCD, sizeof(XMVECTOR)*srcImage.width); +#endif + + auto xFromEnd = reinterpret_cast(reinterpret_cast(tfX.get()) + tfX->sizeInBytes); + auto yFromEnd = reinterpret_cast(reinterpret_cast(tfY.get()) + tfY->sizeInBytes); + + // Count times rows get written + for (FilterFrom* yFrom = tfY->from; yFrom < yFromEnd; ) + { + for (size_t j = 0; j < yFrom->count; ++j) + { + size_t v = yFrom->to[j].u; + assert(v < destImage.height); + ++rowActive[v].remaining; + } + + yFrom = reinterpret_cast(reinterpret_cast(yFrom) + yFrom->sizeInBytes); + } + + // Filter image + const uint8_t* pSrc = srcImage.pixels; + size_t rowPitch = srcImage.rowPitch; + const uint8_t* pEndSrc = pSrc + rowPitch * srcImage.height; + + uint8_t* pDest = destImage.pixels; + + for (FilterFrom* yFrom = tfY->from; yFrom < yFromEnd; ) + { + // Create accumulation rows as needed + for (size_t j = 0; j < yFrom->count; ++j) + { + size_t v = yFrom->to[j].u; + assert(v < destImage.height); + TriangleRow* rowAcc = &rowActive[v]; + + if (!rowAcc->scanline) + { + if (rowFree) + { + // Steal and reuse scanline from 'free row' list + assert(rowFree->scanline != 0); + rowAcc->scanline.reset(rowFree->scanline.release()); + rowFree = rowFree->next; + } + else + { + rowAcc->scanline.reset(reinterpret_cast(_aligned_malloc(sizeof(XMVECTOR) * destImage.width, 16))); + if (!rowAcc->scanline) + return E_OUTOFMEMORY; + } + + memset(rowAcc->scanline.get(), 0, sizeof(XMVECTOR) * destImage.width); + } + } + + // Load source scanline + if ((pSrc + rowPitch) > pEndSrc) + return E_FAIL; + + if (!_LoadScanlineLinear(row, srcImage.width, pSrc, rowPitch, srcImage.format, filter)) + return E_FAIL; + + pSrc += rowPitch; + + // Process row + size_t x = 0; + for (FilterFrom* xFrom = tfX->from; xFrom < xFromEnd; ++x) + { + for (size_t j = 0; j < yFrom->count; ++j) + { + size_t v = yFrom->to[j].u; + assert(v < destImage.height); + float yweight = yFrom->to[j].weight; + + XMVECTOR* accPtr = rowActive[v].scanline.get(); + if (!accPtr) + return E_POINTER; + + for (size_t k = 0; k < xFrom->count; ++k) + { + size_t u = xFrom->to[k].u; + assert(u < destImage.width); + + XMVECTOR weight = XMVectorReplicate(yweight * xFrom->to[k].weight); + + assert(x < srcImage.width); + accPtr[u] = XMVectorMultiplyAdd(row[x], weight, accPtr[u]); + } + } + + xFrom = reinterpret_cast(reinterpret_cast(xFrom) + xFrom->sizeInBytes); + } + + // Write completed accumulation rows + for (size_t j = 0; j < yFrom->count; ++j) + { + size_t v = yFrom->to[j].u; + assert(v < destImage.height); + TriangleRow* rowAcc = &rowActive[v]; + + assert(rowAcc->remaining > 0); + --rowAcc->remaining; + + if (!rowAcc->remaining) + { + XMVECTOR* pAccSrc = rowAcc->scanline.get(); + if (!pAccSrc) + return E_POINTER; + + switch (destImage.format) + { + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + { + // Need to slightly bias results for floating-point error accumulation which can + // be visible with harshly quantized values + static const XMVECTORF32 Bias = { { { 0.f, 0.f, 0.f, 0.1f } } }; + + XMVECTOR* ptr = pAccSrc; + for (size_t i = 0; i < destImage.width; ++i, ++ptr) + { + *ptr = XMVectorAdd(*ptr, Bias); + } + } + break; + + default: + break; + } + + // This performs any required clamping + if (!_StoreScanlineLinear(pDest + (destImage.rowPitch * v), destImage.rowPitch, destImage.format, pAccSrc, destImage.width, filter)) + return E_FAIL; + + // Put row on freelist to reuse it's allocated scanline + rowAcc->next = rowFree; + rowFree = rowAcc; + } + } + + yFrom = reinterpret_cast(reinterpret_cast(yFrom) + yFrom->sizeInBytes); + } + + return S_OK; + } + + + //--- Custom filter resize --- + HRESULT PerformResizeUsingCustomFilters(const Image& srcImage, DWORD filter, const Image& destImage) + { + if (!srcImage.pixels || !destImage.pixels) + return E_POINTER; + + static_assert(TEX_FILTER_POINT == 0x100000, "TEX_FILTER_ flag values don't match TEX_FILTER_MASK"); + + DWORD filter_select = (filter & TEX_FILTER_MASK); + if (!filter_select) + { + // Default filter choice + filter_select = (((destImage.width << 1) == srcImage.width) && ((destImage.height << 1) == srcImage.height)) + ? TEX_FILTER_BOX : TEX_FILTER_LINEAR; + } + + switch (filter_select) + { + case TEX_FILTER_POINT: + return ResizePointFilter(srcImage, destImage); + + case TEX_FILTER_BOX: + return ResizeBoxFilter(srcImage, filter, destImage); + + case TEX_FILTER_LINEAR: + return ResizeLinearFilter(srcImage, filter, destImage); + + case TEX_FILTER_CUBIC: + return ResizeCubicFilter(srcImage, filter, destImage); + + case TEX_FILTER_TRIANGLE: + return ResizeTriangleFilter(srcImage, filter, destImage); + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } +} + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Resize image +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::Resize( + const Image& srcImage, + size_t width, + size_t height, + DWORD filter, + ScratchImage& image) +{ + if (width == 0 || height == 0) + return E_INVALIDARG; + + if ((srcImage.width > UINT32_MAX) || (srcImage.height > UINT32_MAX)) + return E_INVALIDARG; + + if ((width > UINT32_MAX) || (height > UINT32_MAX)) + return E_INVALIDARG; + + if (!srcImage.pixels) + return E_POINTER; + + if (IsCompressed(srcImage.format)) + { + // We don't support resizing compressed images + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + HRESULT hr = image.Initialize2D(srcImage.format, width, height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *rimage = image.GetImage(0, 0, 0); + if (!rimage) + return E_POINTER; + + if (UseWICFiltering(srcImage.format, filter)) + { + WICPixelFormatGUID pfGUID; + if (_DXGIToWIC(srcImage.format, pfGUID, true)) + { + // Case 1: Source format is supported by Windows Imaging Component + hr = PerformResizeUsingWIC(srcImage, filter, pfGUID, *rimage); + } + else + { + // Case 2: Source format is not supported by WIC, so we have to convert, resize, and convert back + hr = PerformResizeViaF32(srcImage, filter, *rimage); + } + } + else + { + hr = PerformResizeUsingCustomFilters(srcImage, filter, *rimage); + } + + if (FAILED(hr)) + { + image.Release(); + return hr; + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Resize image (complex) +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::Resize( + const Image* srcImages, + size_t nimages, + const TexMetadata& metadata, + size_t width, + size_t height, + DWORD filter, + ScratchImage& result) +{ + if (!srcImages || !nimages || width == 0 || height == 0) + return E_INVALIDARG; + + if ((width > UINT32_MAX) || (height > UINT32_MAX)) + return E_INVALIDARG; + + TexMetadata mdata2 = metadata; + mdata2.width = width; + mdata2.height = height; + mdata2.mipLevels = 1; + HRESULT hr = result.Initialize(mdata2); + if (FAILED(hr)) + return hr; + + bool usewic = !metadata.IsPMAlpha() && UseWICFiltering(metadata.format, filter); + + WICPixelFormatGUID pfGUID = { 0 }; + bool wicpf = (usewic) ? _DXGIToWIC(metadata.format, pfGUID, true) : false; + + switch (metadata.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + case TEX_DIMENSION_TEXTURE2D: + assert(metadata.depth == 1); + + for (size_t item = 0; item < metadata.arraySize; ++item) + { + size_t srcIndex = metadata.ComputeIndex(0, item, 0); + if (srcIndex >= nimages) + { + result.Release(); + return E_FAIL; + } + + const Image* srcimg = &srcImages[srcIndex]; + const Image* destimg = result.GetImage(0, item, 0); + if (!srcimg || !destimg) + { + result.Release(); + return E_POINTER; + } + + if (srcimg->format != metadata.format) + { + result.Release(); + return E_FAIL; + } + + if ((srcimg->width > UINT32_MAX) || (srcimg->height > UINT32_MAX)) + { + result.Release(); + return E_FAIL; + } + + if (usewic) + { + if (wicpf) + { + // Case 1: Source format is supported by Windows Imaging Component + hr = PerformResizeUsingWIC(*srcimg, filter, pfGUID, *destimg); + } + else + { + // Case 2: Source format is not supported by WIC, so we have to convert, resize, and convert back + hr = PerformResizeViaF32(*srcimg, filter, *destimg); + } + } + else + { + // Case 3: not using WIC resizing + hr = PerformResizeUsingCustomFilters(*srcimg, filter, *destimg); + } + + if (FAILED(hr)) + { + result.Release(); + return hr; + } + } + break; + + case TEX_DIMENSION_TEXTURE3D: + assert(metadata.arraySize == 1); + + for (size_t slice = 0; slice < metadata.depth; ++slice) + { + size_t srcIndex = metadata.ComputeIndex(0, 0, slice); + if (srcIndex >= nimages) + { + result.Release(); + return E_FAIL; + } + + const Image* srcimg = &srcImages[srcIndex]; + const Image* destimg = result.GetImage(0, 0, slice); + if (!srcimg || !destimg) + { + result.Release(); + return E_POINTER; + } + + if (srcimg->format != metadata.format) + { + result.Release(); + return E_FAIL; + } + + if ((srcimg->width > UINT32_MAX) || (srcimg->height > UINT32_MAX)) + { + result.Release(); + return E_FAIL; + } + + if (usewic) + { + if (wicpf) + { + // Case 1: Source format is supported by Windows Imaging Component + hr = PerformResizeUsingWIC(*srcimg, filter, pfGUID, *destimg); + } + else + { + // Case 2: Source format is not supported by WIC, so we have to convert, resize, and convert back + hr = PerformResizeViaF32(*srcimg, filter, *destimg); + } + } + else + { + // Case 3: not using WIC resizing + hr = PerformResizeUsingCustomFilters(*srcimg, filter, *destimg); + } + + if (FAILED(hr)) + { + result.Release(); + return hr; + } + } + break; + + default: + result.Release(); + return E_FAIL; + } + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexTGA.cpp b/deps/DirectXTex/DirectXTex/DirectXTexTGA.cpp new file mode 100644 index 0000000..13a6444 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexTGA.cpp @@ -0,0 +1,1418 @@ +//------------------------------------------------------------------------------------- +// DirectXTexTGA.cpp +// +// DirectX Texture Library - Targa Truevision (TGA) file format reader/writer +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +// +// The implementation here has the following limitations: +// * Does not support files that contain color maps (these are rare in practice) +// * Interleaved files are not supported (deprecated aspect of TGA format) +// * Only supports 8-bit grayscale; 16-, 24-, and 32-bit truecolor images +// * Always writes uncompressed files (i.e. can read RLE compression, but does not write it) +// + +using namespace DirectX; + +namespace +{ + enum TGAImageType + { + TGA_NO_IMAGE = 0, + TGA_COLOR_MAPPED = 1, + TGA_TRUECOLOR = 2, + TGA_BLACK_AND_WHITE = 3, + TGA_COLOR_MAPPED_RLE = 9, + TGA_TRUECOLOR_RLE = 10, + TGA_BLACK_AND_WHITE_RLE = 11, + }; + + enum TGADescriptorFlags + { + TGA_FLAGS_INVERTX = 0x10, + TGA_FLAGS_INVERTY = 0x20, + TGA_FLAGS_INTERLEAVED_2WAY = 0x40, // Deprecated + TGA_FLAGS_INTERLEAVED_4WAY = 0x80, // Deprecated + }; + + const char* g_TGA20_Signature = "TRUEVISION-XFILE."; + +#pragma pack(push,1) + struct TGA_HEADER + { + uint8_t bIDLength; + uint8_t bColorMapType; + uint8_t bImageType; + uint16_t wColorMapFirst; + uint16_t wColorMapLength; + uint8_t bColorMapSize; + uint16_t wXOrigin; + uint16_t wYOrigin; + uint16_t wWidth; + uint16_t wHeight; + uint8_t bBitsPerPixel; + uint8_t bDescriptor; + }; + + struct TGA_FOOTER + { + uint16_t dwExtensionOffset; + uint16_t dwDeveloperOffset; + char Signature[18]; + }; + + struct TGA_EXTENSION + { + uint16_t wSize; + char szAuthorName[41]; + char szAuthorComment[324]; + uint16_t wStampMonth; + uint16_t wStampDay; + uint16_t wStampYear; + uint16_t wStampHour; + uint16_t wStampMinute; + uint16_t wStampSecond; + char szJobName[41]; + uint16_t wJobHour; + uint16_t wJobMinute; + uint16_t wJobSecond; + char szSoftwareId[41]; + uint16_t wVersionNumber; + uint8_t bVersionLetter; + uint32_t dwKeyColor; + uint16_t wPixelNumerator; + uint16_t wPixelDenominator; + uint16_t wGammaNumerator; + uint16_t wGammaDenominator; + uint32_t dwColorOffset; + uint32_t dwStampOffset; + uint32_t dwScanOffset; + uint8_t bAttributesType; + }; +#pragma pack(pop) + + enum CONVERSION_FLAGS + { + CONV_FLAGS_NONE = 0x0, + CONV_FLAGS_EXPAND = 0x1, // Conversion requires expanded pixel size + CONV_FLAGS_INVERTX = 0x2, // If set, scanlines are right-to-left + CONV_FLAGS_INVERTY = 0x4, // If set, scanlines are top-to-bottom + CONV_FLAGS_RLE = 0x8, // Source data is RLE compressed + + CONV_FLAGS_SWIZZLE = 0x10000, // Swizzle BGR<->RGB data + CONV_FLAGS_888 = 0x20000, // 24bpp format + }; + + + //------------------------------------------------------------------------------------- + // Decodes TGA header + //------------------------------------------------------------------------------------- + HRESULT DecodeTGAHeader( + _In_reads_bytes_(size) const void* pSource, + size_t size, + _Out_ TexMetadata& metadata, + size_t& offset, + _Inout_opt_ DWORD* convFlags) + { + if (!pSource) + return E_INVALIDARG; + + memset(&metadata, 0, sizeof(TexMetadata)); + + if (size < sizeof(TGA_HEADER)) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + auto pHeader = reinterpret_cast(pSource); + + if (pHeader->bColorMapType != 0 + || pHeader->wColorMapLength != 0) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + if (pHeader->bDescriptor & (TGA_FLAGS_INTERLEAVED_2WAY | TGA_FLAGS_INTERLEAVED_4WAY)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + if (!pHeader->wWidth || !pHeader->wHeight) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + switch (pHeader->bImageType) + { + case TGA_TRUECOLOR: + case TGA_TRUECOLOR_RLE: + switch (pHeader->bBitsPerPixel) + { + case 16: + metadata.format = DXGI_FORMAT_B5G5R5A1_UNORM; + break; + + case 24: + metadata.format = DXGI_FORMAT_R8G8B8A8_UNORM; + if (convFlags) + *convFlags |= CONV_FLAGS_EXPAND; + // We could use DXGI_FORMAT_B8G8R8X8_UNORM, but we prefer DXGI 1.0 formats + break; + + case 32: + metadata.format = DXGI_FORMAT_R8G8B8A8_UNORM; + // We could use DXGI_FORMAT_B8G8R8A8_UNORM, but we prefer DXGI 1.0 formats + break; + } + + if (convFlags && (pHeader->bImageType == TGA_TRUECOLOR_RLE)) + { + *convFlags |= CONV_FLAGS_RLE; + } + break; + + case TGA_BLACK_AND_WHITE: + case TGA_BLACK_AND_WHITE_RLE: + switch (pHeader->bBitsPerPixel) + { + case 8: + metadata.format = DXGI_FORMAT_R8_UNORM; + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + if (convFlags && (pHeader->bImageType == TGA_BLACK_AND_WHITE_RLE)) + { + *convFlags |= CONV_FLAGS_RLE; + } + break; + + case TGA_NO_IMAGE: + case TGA_COLOR_MAPPED: + case TGA_COLOR_MAPPED_RLE: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + default: + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + metadata.width = pHeader->wWidth; + metadata.height = pHeader->wHeight; + metadata.depth = metadata.arraySize = metadata.mipLevels = 1; + metadata.dimension = TEX_DIMENSION_TEXTURE2D; + + if (convFlags) + { + if (pHeader->bDescriptor & TGA_FLAGS_INVERTX) + *convFlags |= CONV_FLAGS_INVERTX; + + if (pHeader->bDescriptor & TGA_FLAGS_INVERTY) + *convFlags |= CONV_FLAGS_INVERTY; + } + + offset = sizeof(TGA_HEADER); + + if (pHeader->bIDLength != 0) + { + offset += pHeader->bIDLength; + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Set alpha for images with all 0 alpha channel + //------------------------------------------------------------------------------------- + HRESULT SetAlphaChannelToOpaque(_In_ const Image* image) + { + assert(image); + + auto pPixels = reinterpret_cast(image->pixels); + if (!pPixels) + return E_POINTER; + + for (size_t y = 0; y < image->height; ++y) + { + _CopyScanline(pPixels, image->rowPitch, pPixels, image->rowPitch, image->format, TEXP_SCANLINE_SETALPHA); + pPixels += image->rowPitch; + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Uncompress pixel data from a TGA into the target image + //------------------------------------------------------------------------------------- + HRESULT UncompressPixels( + _In_reads_bytes_(size) const void* pSource, + size_t size, + _In_ const Image* image, + _In_ DWORD convFlags) + { + assert(pSource && size > 0); + + if (!image || !image->pixels) + return E_POINTER; + + // Compute TGA image data pitch + size_t rowPitch; + if (convFlags & CONV_FLAGS_EXPAND) + { + rowPitch = image->width * 3; + } + else + { + size_t slicePitch; + ComputePitch(image->format, image->width, image->height, rowPitch, slicePitch, CP_FLAGS_NONE); + } + + auto sPtr = reinterpret_cast(pSource); + const uint8_t* endPtr = sPtr + size; + + switch (image->format) + { + //--------------------------------------------------------------------------- 8-bit + case DXGI_FORMAT_R8_UNORM: + for (size_t y = 0; y < image->height; ++y) + { + size_t offset = ((convFlags & CONV_FLAGS_INVERTX) ? (image->width - 1) : 0); + assert(offset < rowPitch); + + uint8_t* dPtr = reinterpret_cast(image->pixels) + + (image->rowPitch * ((convFlags & CONV_FLAGS_INVERTY) ? y : (image->height - y - 1))) + + offset; + + for (size_t x = 0; x < image->width; ) + { + if (sPtr >= endPtr) + return E_FAIL; + + if (*sPtr & 0x80) + { + // Repeat + size_t j = (*sPtr & 0x7F) + 1; + if (++sPtr >= endPtr) + return E_FAIL; + + for (; j > 0; --j, ++x) + { + if (x >= image->width) + return E_FAIL; + + *dPtr = *sPtr; + + if (convFlags & CONV_FLAGS_INVERTX) + --dPtr; + else + ++dPtr; + } + + ++sPtr; + } + else + { + // Literal + size_t j = (*sPtr & 0x7F) + 1; + ++sPtr; + + if (sPtr + j > endPtr) + return E_FAIL; + + for (; j > 0; --j, ++x) + { + if (x >= image->width) + return E_FAIL; + + *dPtr = *(sPtr++); + + if (convFlags & CONV_FLAGS_INVERTX) + --dPtr; + else + ++dPtr; + } + } + } + } + break; + + //-------------------------------------------------------------------------- 16-bit + case DXGI_FORMAT_B5G5R5A1_UNORM: + { + bool nonzeroa = false; + for (size_t y = 0; y < image->height; ++y) + { + size_t offset = ((convFlags & CONV_FLAGS_INVERTX) ? (image->width - 1) : 0); + assert(offset * 2 < rowPitch); + + uint16_t* dPtr = reinterpret_cast(reinterpret_cast(image->pixels) + + (image->rowPitch * ((convFlags & CONV_FLAGS_INVERTY) ? y : (image->height - y - 1)))) + + offset; + + for (size_t x = 0; x < image->width; ) + { + if (sPtr >= endPtr) + return E_FAIL; + + if (*sPtr & 0x80) + { + // Repeat + size_t j = (*sPtr & 0x7F) + 1; + ++sPtr; + + if (sPtr + 1 >= endPtr) + return E_FAIL; + + uint16_t t = *sPtr | (*(sPtr + 1) << 8); + if (t & 0x8000) + nonzeroa = true; + sPtr += 2; + + for (; j > 0; --j, ++x) + { + if (x >= image->width) + return E_FAIL; + + *dPtr = t; + + if (convFlags & CONV_FLAGS_INVERTX) + --dPtr; + else + ++dPtr; + } + } + else + { + // Literal + size_t j = (*sPtr & 0x7F) + 1; + ++sPtr; + + if (sPtr + (j * 2) > endPtr) + return E_FAIL; + + for (; j > 0; --j, ++x) + { + if (x >= image->width) + return E_FAIL; + + uint16_t t = *sPtr | (*(sPtr + 1) << 8); + if (t & 0x8000) + nonzeroa = true; + sPtr += 2; + *dPtr = t; + + if (convFlags & CONV_FLAGS_INVERTX) + --dPtr; + else + ++dPtr; + } + } + } + } + + // If there are no non-zero alpha channel entries, we'll assume alpha is not used and force it to opaque + if (!nonzeroa) + { + HRESULT hr = SetAlphaChannelToOpaque(image); + if (FAILED(hr)) + return hr; + } + } + break; + + //----------------------------------------------------------------------- 24/32-bit + case DXGI_FORMAT_R8G8B8A8_UNORM: + { + bool nonzeroa = false; + for (size_t y = 0; y < image->height; ++y) + { + size_t offset = ((convFlags & CONV_FLAGS_INVERTX) ? (image->width - 1) : 0); + + uint32_t* dPtr = reinterpret_cast(reinterpret_cast(image->pixels) + + (image->rowPitch * ((convFlags & CONV_FLAGS_INVERTY) ? y : (image->height - y - 1)))) + + offset; + + for (size_t x = 0; x < image->width; ) + { + if (sPtr >= endPtr) + return E_FAIL; + + if (*sPtr & 0x80) + { + // Repeat + size_t j = (*sPtr & 0x7F) + 1; + ++sPtr; + + DWORD t; + if (convFlags & CONV_FLAGS_EXPAND) + { + assert(offset * 3 < rowPitch); + + if (sPtr + 2 >= endPtr) + return E_FAIL; + + // BGR -> RGBA + t = (*sPtr << 16) | (*(sPtr + 1) << 8) | (*(sPtr + 2)) | 0xFF000000; + sPtr += 3; + + nonzeroa = true; + } + else + { + assert(offset * 4 < rowPitch); + + if (sPtr + 3 >= endPtr) + return E_FAIL; + + // BGRA -> RGBA + t = (*sPtr << 16) | (*(sPtr + 1) << 8) | (*(sPtr + 2)) | (*(sPtr + 3) << 24); + + if (*(sPtr + 3) > 0) + nonzeroa = true; + + sPtr += 4; + } + + for (; j > 0; --j, ++x) + { + if (x >= image->width) + return E_FAIL; + + *dPtr = t; + + if (convFlags & CONV_FLAGS_INVERTX) + --dPtr; + else + ++dPtr; + } + } + else + { + // Literal + size_t j = (*sPtr & 0x7F) + 1; + ++sPtr; + + if (convFlags & CONV_FLAGS_EXPAND) + { + if (sPtr + (j * 3) > endPtr) + return E_FAIL; + } + else + { + if (sPtr + (j * 4) > endPtr) + return E_FAIL; + } + + for (; j > 0; --j, ++x) + { + if (x >= image->width) + return E_FAIL; + + if (convFlags & CONV_FLAGS_EXPAND) + { + assert(offset * 3 < rowPitch); + + if (sPtr + 2 >= endPtr) + return E_FAIL; + + // BGR -> RGBA + *dPtr = (*sPtr << 16) | (*(sPtr + 1) << 8) | (*(sPtr + 2)) | 0xFF000000; + sPtr += 3; + + nonzeroa = true; + } + else + { + assert(offset * 4 < rowPitch); + + if (sPtr + 3 >= endPtr) + return E_FAIL; + + // BGRA -> RGBA + *dPtr = (*sPtr << 16) | (*(sPtr + 1) << 8) | (*(sPtr + 2)) | (*(sPtr + 3) << 24); + + if (*(sPtr + 3) > 0) + nonzeroa = true; + + sPtr += 4; + } + + if (convFlags & CONV_FLAGS_INVERTX) + --dPtr; + else + ++dPtr; + } + } + } + } + + // If there are no non-zero alpha channel entries, we'll assume alpha is not used and force it to opaque + if (!nonzeroa) + { + HRESULT hr = SetAlphaChannelToOpaque(image); + if (FAILED(hr)) + return hr; + } + } + break; + + //--------------------------------------------------------------------------------- + default: + return E_FAIL; + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Copies pixel data from a TGA into the target image + //------------------------------------------------------------------------------------- + HRESULT CopyPixels( + _In_reads_bytes_(size) const void* pSource, + size_t size, + _In_ const Image* image, + _In_ DWORD convFlags) + { + assert(pSource && size > 0); + + if (!image || !image->pixels) + return E_POINTER; + + // Compute TGA image data pitch + size_t rowPitch; + if (convFlags & CONV_FLAGS_EXPAND) + { + rowPitch = image->width * 3; + } + else + { + size_t slicePitch; + ComputePitch(image->format, image->width, image->height, rowPitch, slicePitch, CP_FLAGS_NONE); + } + + const uint8_t* sPtr = reinterpret_cast(pSource); + const uint8_t* endPtr = sPtr + size; + + switch (image->format) + { + //--------------------------------------------------------------------------- 8-bit + case DXGI_FORMAT_R8_UNORM: + for (size_t y = 0; y < image->height; ++y) + { + size_t offset = ((convFlags & CONV_FLAGS_INVERTX) ? (image->width - 1) : 0); + assert(offset < rowPitch); + + uint8_t* dPtr = reinterpret_cast(image->pixels) + + (image->rowPitch * ((convFlags & CONV_FLAGS_INVERTY) ? y : (image->height - y - 1))) + + offset; + + for (size_t x = 0; x < image->width; ++x) + { + if (sPtr >= endPtr) + return E_FAIL; + + *dPtr = *(sPtr++); + + if (convFlags & CONV_FLAGS_INVERTX) + --dPtr; + else + ++dPtr; + } + } + break; + + //-------------------------------------------------------------------------- 16-bit + case DXGI_FORMAT_B5G5R5A1_UNORM: + { + bool nonzeroa = false; + for (size_t y = 0; y < image->height; ++y) + { + size_t offset = ((convFlags & CONV_FLAGS_INVERTX) ? (image->width - 1) : 0); + assert(offset * 2 < rowPitch); + + uint16_t* dPtr = reinterpret_cast(reinterpret_cast(image->pixels) + + (image->rowPitch * ((convFlags & CONV_FLAGS_INVERTY) ? y : (image->height - y - 1)))) + + offset; + + for (size_t x = 0; x < image->width; ++x) + { + if (sPtr + 1 >= endPtr) + return E_FAIL; + + uint16_t t = *sPtr | (*(sPtr + 1) << 8); + sPtr += 2; + *dPtr = t; + + if (t & 0x8000) + nonzeroa = true; + + if (convFlags & CONV_FLAGS_INVERTX) + --dPtr; + else + ++dPtr; + } + } + + // If there are no non-zero alpha channel entries, we'll assume alpha is not used and force it to opaque + if (!nonzeroa) + { + HRESULT hr = SetAlphaChannelToOpaque(image); + if (FAILED(hr)) + return hr; + } + } + break; + + //----------------------------------------------------------------------- 24/32-bit + case DXGI_FORMAT_R8G8B8A8_UNORM: + { + bool nonzeroa = false; + for (size_t y = 0; y < image->height; ++y) + { + size_t offset = ((convFlags & CONV_FLAGS_INVERTX) ? (image->width - 1) : 0); + + uint32_t* dPtr = reinterpret_cast(reinterpret_cast(image->pixels) + + (image->rowPitch * ((convFlags & CONV_FLAGS_INVERTY) ? y : (image->height - y - 1)))) + + offset; + + for (size_t x = 0; x < image->width; ++x) + { + if (convFlags & CONV_FLAGS_EXPAND) + { + assert(offset * 3 < rowPitch); + + if (sPtr + 2 >= endPtr) + return E_FAIL; + + // BGR -> RGBA + *dPtr = (*sPtr << 16) | (*(sPtr + 1) << 8) | (*(sPtr + 2)) | 0xFF000000; + sPtr += 3; + + nonzeroa = true; + } + else + { + assert(offset * 4 < rowPitch); + + if (sPtr + 3 >= endPtr) + return E_FAIL; + + // BGRA -> RGBA + *dPtr = (*sPtr << 16) | (*(sPtr + 1) << 8) | (*(sPtr + 2)) | (*(sPtr + 3) << 24); + + if (*(sPtr + 3) > 0) + nonzeroa = true; + + sPtr += 4; + } + + if (convFlags & CONV_FLAGS_INVERTX) + --dPtr; + else + ++dPtr; + } + } + + // If there are no non-zero alpha channel entries, we'll assume alpha is not used and force it to opaque + if (!nonzeroa) + { + HRESULT hr = SetAlphaChannelToOpaque(image); + if (FAILED(hr)) + return hr; + } + } + break; + + //--------------------------------------------------------------------------------- + default: + return E_FAIL; + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Encodes TGA file header + //------------------------------------------------------------------------------------- + HRESULT EncodeTGAHeader(_In_ const Image& image, _Out_ TGA_HEADER& header, _Inout_ DWORD& convFlags) + { + memset(&header, 0, sizeof(TGA_HEADER)); + + if ((image.width > 0xFFFF) + || (image.height > 0xFFFF)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + header.wWidth = static_cast(image.width); + header.wHeight = static_cast(image.height); + + switch (image.format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + header.bImageType = TGA_TRUECOLOR; + header.bBitsPerPixel = 32; + header.bDescriptor = TGA_FLAGS_INVERTY | 8; + convFlags |= CONV_FLAGS_SWIZZLE; + break; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + header.bImageType = TGA_TRUECOLOR; + header.bBitsPerPixel = 32; + header.bDescriptor = TGA_FLAGS_INVERTY | 8; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + header.bImageType = TGA_TRUECOLOR; + header.bBitsPerPixel = 24; + header.bDescriptor = TGA_FLAGS_INVERTY; + convFlags |= CONV_FLAGS_888; + break; + + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_A8_UNORM: + header.bImageType = TGA_BLACK_AND_WHITE; + header.bBitsPerPixel = 8; + header.bDescriptor = TGA_FLAGS_INVERTY; + break; + + case DXGI_FORMAT_B5G5R5A1_UNORM: + header.bImageType = TGA_TRUECOLOR; + header.bBitsPerPixel = 16; + header.bDescriptor = TGA_FLAGS_INVERTY | 1; + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Copies BGRX data to form BGR 24bpp data + //------------------------------------------------------------------------------------- +#pragma warning(suppress: 6001 6101) // In the case where outSize is insufficient we do not write to pDestination + void Copy24bppScanline( + _Out_writes_bytes_(outSize) void* pDestination, + _In_ size_t outSize, + _In_reads_bytes_(inSize) const void* pSource, + _In_ size_t inSize) + { + assert(pDestination && outSize > 0); + assert(pSource && inSize > 0); + + assert(pDestination != pSource); + + const uint32_t * __restrict sPtr = reinterpret_cast(pSource); + uint8_t * __restrict dPtr = reinterpret_cast(pDestination); + + if (inSize >= 4 && outSize >= 3) + { + const uint8_t* endPtr = dPtr + outSize; + + for (size_t count = 0; count < (inSize - 3); count += 4) + { + uint32_t t = *(sPtr++); + + if (dPtr + 3 > endPtr) + return; + + *(dPtr++) = uint8_t(t & 0xFF); // Blue + *(dPtr++) = uint8_t((t & 0xFF00) >> 8); // Green + *(dPtr++) = uint8_t((t & 0xFF0000) >> 16); // Red + } + } + } +} + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Obtain metadata from TGA file in memory/on disk +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::GetMetadataFromTGAMemory( + const void* pSource, + size_t size, + TexMetadata& metadata ) +{ + if ( !pSource || size == 0 ) + return E_INVALIDARG; + + size_t offset; + return DecodeTGAHeader( pSource, size, metadata, offset, 0 ); +} + +_Use_decl_annotations_ +HRESULT DirectX::GetMetadataFromTGAFile(const wchar_t* szFile, TexMetadata& metadata) +{ + if (!szFile) + return E_INVALIDARG; + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(szFile, GENERIC_READ, FILE_SHARE_READ, OPEN_EXISTING, nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(szFile, GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, + FILE_FLAG_SEQUENTIAL_SCAN, nullptr))); +#endif + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // Get the file size + FILE_STANDARD_INFO fileInfo; + if (!GetFileInformationByHandleEx(hFile.get(), FileStandardInfo, &fileInfo, sizeof(fileInfo))) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // File is too big for 32-bit allocation, so reject read (4 GB should be plenty large enough for a valid TGA file) + if (fileInfo.EndOfFile.HighPart > 0) + { + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + } + + // Need at least enough data to fill the standard header to be a valid TGA + if (fileInfo.EndOfFile.LowPart < (sizeof(TGA_HEADER))) + { + return E_FAIL; + } + + // Read the standard header (we don't need the file footer to parse the file) + uint8_t header[sizeof(TGA_HEADER)]; + DWORD bytesRead = 0; + if (!ReadFile(hFile.get(), header, sizeof(TGA_HEADER), &bytesRead, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + size_t offset; + return DecodeTGAHeader(header, bytesRead, metadata, offset, 0); +} + + +//------------------------------------------------------------------------------------- +// Load a TGA file in memory +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadFromTGAMemory( + const void* pSource, + size_t size, + TexMetadata* metadata, + ScratchImage& image) +{ + if (!pSource || size == 0) + return E_INVALIDARG; + + image.Release(); + + size_t offset; + DWORD convFlags = 0; + TexMetadata mdata; + HRESULT hr = DecodeTGAHeader(pSource, size, mdata, offset, &convFlags); + if (FAILED(hr)) + return hr; + + if (offset > size) + return E_FAIL; + + auto pPixels = reinterpret_cast(reinterpret_cast(pSource) + offset); + + size_t remaining = size - offset; + if (remaining == 0) + return E_FAIL; + + hr = image.Initialize2D(mdata.format, mdata.width, mdata.height, 1, 1); + if (FAILED(hr)) + return hr; + + if (convFlags & CONV_FLAGS_RLE) + { + hr = UncompressPixels(pPixels, remaining, image.GetImage(0, 0, 0), convFlags); + } + else + { + hr = CopyPixels(pPixels, remaining, image.GetImage(0, 0, 0), convFlags); + } + + if (FAILED(hr)) + { + image.Release(); + return hr; + } + + if (metadata) + memcpy(metadata, &mdata, sizeof(TexMetadata)); + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Load a TGA file from disk +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadFromTGAFile( + const wchar_t* szFile, + TexMetadata* metadata, + ScratchImage& image) +{ + if (!szFile) + return E_INVALIDARG; + + image.Release(); + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(szFile, GENERIC_READ, FILE_SHARE_READ, OPEN_EXISTING, nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(szFile, GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, + FILE_FLAG_SEQUENTIAL_SCAN, nullptr))); +#endif + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // Get the file size + FILE_STANDARD_INFO fileInfo; + if (!GetFileInformationByHandleEx(hFile.get(), FileStandardInfo, &fileInfo, sizeof(fileInfo))) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // File is too big for 32-bit allocation, so reject read (4 GB should be plenty large enough for a valid TGA file) + if (fileInfo.EndOfFile.HighPart > 0) + { + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + } + + // Need at least enough data to fill the header to be a valid TGA + if (fileInfo.EndOfFile.LowPart < sizeof(TGA_HEADER)) + { + return E_FAIL; + } + + // Read the header + uint8_t header[sizeof(TGA_HEADER)]; + DWORD bytesRead = 0; + if (!ReadFile(hFile.get(), header, sizeof(TGA_HEADER), &bytesRead, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + size_t offset; + DWORD convFlags = 0; + TexMetadata mdata; + HRESULT hr = DecodeTGAHeader(header, bytesRead, mdata, offset, &convFlags); + if (FAILED(hr)) + return hr; + + // Read the pixels + DWORD remaining = static_cast(fileInfo.EndOfFile.LowPart - offset); + if (remaining == 0) + return E_FAIL; + + if (offset > sizeof(TGA_HEADER)) + { + // Skip past the id string + LARGE_INTEGER filePos = { { static_cast(offset), 0 } }; + if (!SetFilePointerEx(hFile.get(), filePos, 0, FILE_BEGIN)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + } + + hr = image.Initialize2D(mdata.format, mdata.width, mdata.height, 1, 1); + if (FAILED(hr)) + return hr; + + assert(image.GetPixels()); + + if (!(convFlags & (CONV_FLAGS_RLE | CONV_FLAGS_EXPAND | CONV_FLAGS_INVERTX)) && (convFlags & CONV_FLAGS_INVERTY)) + { + // This case we can read directly into the image buffer in place + if (!ReadFile(hFile.get(), image.GetPixels(), static_cast(image.GetPixelsSize()), &bytesRead, nullptr)) + { + image.Release(); + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesRead != image.GetPixelsSize()) + { + image.Release(); + return E_FAIL; + } + + switch (mdata.format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + { + // TGA stores 32-bit data in BGRA form, need to swizzle to RGBA + assert(image.GetImageCount() == 1); + const Image* img = image.GetImage(0, 0, 0); + if (!img) + { + image.Release(); + return E_POINTER; + } + + uint8_t *pPixels = img->pixels; + if (!pPixels) + { + image.Release(); + return E_POINTER; + } + + size_t rowPitch = img->rowPitch; + + // Scan for non-zero alpha channel + bool nonzeroa = false; + + for (size_t h = 0; h < img->height; ++h) + { + const uint32_t* sPtr = reinterpret_cast(pPixels); + + for (size_t x = 0; x < img->width; ++x) + { + if ((*sPtr) & 0xff000000) + { + nonzeroa = true; + break; + } + + ++sPtr; + } + + if (nonzeroa) + break; + + pPixels += rowPitch; + } + + DWORD tflags = (!nonzeroa) ? TEXP_SCANLINE_SETALPHA : TEXP_SCANLINE_NONE; + + // Swizzle scanlines + pPixels = img->pixels; + + for (size_t h = 0; h < img->height; ++h) + { + _SwizzleScanline(pPixels, rowPitch, pPixels, rowPitch, mdata.format, tflags); + pPixels += rowPitch; + } + } + break; + + // If we start using DXGI_FORMAT_B8G8R8X8_UNORM or DXGI_FORMAT_B8G8R8A8_UNORM we need to check for a fully 0 alpha channel + + case DXGI_FORMAT_B5G5R5A1_UNORM: + { + assert(image.GetImageCount() == 1); + const Image* img = image.GetImage(0, 0, 0); + if (!img) + { + image.Release(); + return E_POINTER; + } + + // Scan for non-zero alpha channel + bool nonzeroa = false; + + const uint8_t *pPixels = img->pixels; + if (!pPixels) + { + image.Release(); + return E_POINTER; + } + + size_t rowPitch = img->rowPitch; + + for (size_t h = 0; h < img->height; ++h) + { + const uint16_t* sPtr = reinterpret_cast(pPixels); + + for (size_t x = 0; x < img->width; ++x) + { + if (*sPtr & 0x8000) + { + nonzeroa = true; + break; + } + + ++sPtr; + } + + if (nonzeroa) + break; + + pPixels += rowPitch; + } + + // If there are no non-zero alpha channel entries, we'll assume alpha is not used and force it to opaque + if (!nonzeroa) + { + hr = SetAlphaChannelToOpaque(img); + if (FAILED(hr)) + { + image.Release(); + return hr; + } + } + } + break; + + default: + break; + } + } + else // RLE || EXPAND || INVERTX || !INVERTY + { + std::unique_ptr temp(new (std::nothrow) uint8_t[remaining]); + if (!temp) + { + image.Release(); + return E_OUTOFMEMORY; + } + + if (!ReadFile(hFile.get(), temp.get(), remaining, &bytesRead, nullptr)) + { + image.Release(); + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesRead != remaining) + { + image.Release(); + return E_FAIL; + } + + if (convFlags & CONV_FLAGS_RLE) + { + hr = UncompressPixels(temp.get(), remaining, image.GetImage(0, 0, 0), convFlags); + } + else + { + hr = CopyPixels(temp.get(), remaining, image.GetImage(0, 0, 0), convFlags); + } + + if (FAILED(hr)) + { + image.Release(); + return hr; + } + } + + if (metadata) + memcpy(metadata, &mdata, sizeof(TexMetadata)); + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Save a TGA file to memory +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveToTGAMemory(const Image& image, Blob& blob) +{ + if (!image.pixels) + return E_POINTER; + + TGA_HEADER tga_header; + DWORD convFlags = 0; + HRESULT hr = EncodeTGAHeader(image, tga_header, convFlags); + if (FAILED(hr)) + return hr; + + blob.Release(); + + // Determine memory required for image data + size_t rowPitch, slicePitch; + if (convFlags & CONV_FLAGS_888) + { + rowPitch = image.width * 3; + slicePitch = image.height * rowPitch; + } + else + { + ComputePitch(image.format, image.width, image.height, rowPitch, slicePitch, CP_FLAGS_NONE); + } + + hr = blob.Initialize(sizeof(TGA_HEADER) + slicePitch); + if (FAILED(hr)) + return hr; + + // Copy header + auto dPtr = reinterpret_cast(blob.GetBufferPointer()); + assert(dPtr != 0); + memcpy_s(dPtr, blob.GetBufferSize(), &tga_header, sizeof(TGA_HEADER)); + dPtr += sizeof(TGA_HEADER); + + auto pPixels = reinterpret_cast(image.pixels); + assert(pPixels); + + for (size_t y = 0; y < image.height; ++y) + { + // Copy pixels + if (convFlags & CONV_FLAGS_888) + { + Copy24bppScanline(dPtr, rowPitch, pPixels, image.rowPitch); + } + else if (convFlags & CONV_FLAGS_SWIZZLE) + { + _SwizzleScanline(dPtr, rowPitch, pPixels, image.rowPitch, image.format, TEXP_SCANLINE_NONE); + } + else + { + _CopyScanline(dPtr, rowPitch, pPixels, image.rowPitch, image.format, TEXP_SCANLINE_NONE); + } + + dPtr += rowPitch; + pPixels += image.rowPitch; + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Save a TGA file to disk +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveToTGAFile(const Image& image, const wchar_t* szFile) +{ + if (!szFile) + return E_INVALIDARG; + + if (!image.pixels) + return E_POINTER; + + TGA_HEADER tga_header; + DWORD convFlags = 0; + HRESULT hr = EncodeTGAHeader(image, tga_header, convFlags); + if (FAILED(hr)) + return hr; + + // Create file and write header +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(szFile, GENERIC_WRITE, 0, CREATE_ALWAYS, nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(szFile, GENERIC_WRITE, 0, nullptr, CREATE_ALWAYS, 0, nullptr))); +#endif + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + auto_delete_file delonfail(hFile.get()); + + // Determine size for TGA pixel data + size_t rowPitch, slicePitch; + if (convFlags & CONV_FLAGS_888) + { + rowPitch = image.width * 3; + slicePitch = image.height * rowPitch; + } + else + { + ComputePitch(image.format, image.width, image.height, rowPitch, slicePitch, CP_FLAGS_NONE); + } + + if (slicePitch < 65535) + { + // For small images, it is better to create an in-memory file and write it out + Blob blob; + + hr = SaveToTGAMemory(image, blob); + if (FAILED(hr)) + return hr; + + // Write blob + const DWORD bytesToWrite = static_cast(blob.GetBufferSize()); + DWORD bytesWritten; + if (!WriteFile(hFile.get(), blob.GetBufferPointer(), bytesToWrite, &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != bytesToWrite) + { + return E_FAIL; + } + } + else + { + // Otherwise, write the image one scanline at a time... + std::unique_ptr temp(new (std::nothrow) uint8_t[rowPitch]); + if (!temp) + return E_OUTOFMEMORY; + + // Write header + DWORD bytesWritten; + if (!WriteFile(hFile.get(), &tga_header, sizeof(TGA_HEADER), &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != sizeof(TGA_HEADER)) + return E_FAIL; + + // Write pixels + auto pPixels = reinterpret_cast(image.pixels); + + for (size_t y = 0; y < image.height; ++y) + { + // Copy pixels + if (convFlags & CONV_FLAGS_888) + { + Copy24bppScanline(temp.get(), rowPitch, pPixels, image.rowPitch); + } + else if (convFlags & CONV_FLAGS_SWIZZLE) + { + _SwizzleScanline(temp.get(), rowPitch, pPixels, image.rowPitch, image.format, TEXP_SCANLINE_NONE); + } + else + { + _CopyScanline(temp.get(), rowPitch, pPixels, image.rowPitch, image.format, TEXP_SCANLINE_NONE); + } + + pPixels += image.rowPitch; + + if (!WriteFile(hFile.get(), temp.get(), static_cast(rowPitch), &bytesWritten, nullptr)) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesWritten != rowPitch) + return E_FAIL; + } + } + + delonfail.clear(); + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexUtil.cpp b/deps/DirectXTex/DirectXTex/DirectXTexUtil.cpp new file mode 100644 index 0000000..96a2386 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexUtil.cpp @@ -0,0 +1,1480 @@ +//------------------------------------------------------------------------------------- +// DirectXTexUtil.cpp +// +// DirectX Texture Library - Utilities +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +#if defined(_XBOX_ONE) && defined(_TITLE) +static_assert(XBOX_DXGI_FORMAT_R10G10B10_7E3_A2_FLOAT == DXGI_FORMAT_R10G10B10_7E3_A2_FLOAT, "Xbox One XDK mismatch detected"); +static_assert(XBOX_DXGI_FORMAT_R10G10B10_6E4_A2_FLOAT == DXGI_FORMAT_R10G10B10_6E4_A2_FLOAT, "Xbox One XDK mismatch detected"); +static_assert(XBOX_DXGI_FORMAT_D16_UNORM_S8_UINT == DXGI_FORMAT_D16_UNORM_S8_UINT, "Xbox One XDK mismatch detected"); +static_assert(XBOX_DXGI_FORMAT_R16_UNORM_X8_TYPELESS == DXGI_FORMAT_R16_UNORM_X8_TYPELESS, "Xbox One XDK mismatch detected"); +static_assert(XBOX_DXGI_FORMAT_X16_TYPELESS_G8_UINT == DXGI_FORMAT_X16_TYPELESS_G8_UINT, "Xbox One XDK mismatch detected"); +static_assert(XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM == DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM, "Xbox One XDK mismatch detected"); +static_assert(XBOX_DXGI_FORMAT_R4G4_UNORM == DXGI_FORMAT_R4G4_UNORM, "Xbox One XDK mismatch detected"); +#endif + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN10) +static_assert(WIN10_DXGI_FORMAT_P208 == DXGI_FORMAT_P208, "Windows SDK mismatch detected"); +static_assert(WIN10_DXGI_FORMAT_V208 == DXGI_FORMAT_V208, "Windows SDK mismatch detected"); +static_assert(WIN10_DXGI_FORMAT_V408 == DXGI_FORMAT_V408, "Windows SDK mismatch detected"); +#endif + +using namespace DirectX; +using Microsoft::WRL::ComPtr; + +namespace +{ + //------------------------------------------------------------------------------------- + // WIC Pixel Format Translation Data + //------------------------------------------------------------------------------------- + struct WICTranslate + { + GUID wic; + DXGI_FORMAT format; + bool srgb; + }; + + const WICTranslate g_WICFormats[] = + { + { GUID_WICPixelFormat128bppRGBAFloat, DXGI_FORMAT_R32G32B32A32_FLOAT, false }, + + { GUID_WICPixelFormat64bppRGBAHalf, DXGI_FORMAT_R16G16B16A16_FLOAT, false }, + { GUID_WICPixelFormat64bppRGBA, DXGI_FORMAT_R16G16B16A16_UNORM, true }, + + { GUID_WICPixelFormat32bppRGBA, DXGI_FORMAT_R8G8B8A8_UNORM, true }, + { GUID_WICPixelFormat32bppBGRA, DXGI_FORMAT_B8G8R8A8_UNORM, true }, // DXGI 1.1 + { GUID_WICPixelFormat32bppBGR, DXGI_FORMAT_B8G8R8X8_UNORM, true }, // DXGI 1.1 + + { GUID_WICPixelFormat32bppRGBA1010102XR, DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM, true }, // DXGI 1.1 + { GUID_WICPixelFormat32bppRGBA1010102, DXGI_FORMAT_R10G10B10A2_UNORM, true }, + + { GUID_WICPixelFormat16bppBGRA5551, DXGI_FORMAT_B5G5R5A1_UNORM, true }, + { GUID_WICPixelFormat16bppBGR565, DXGI_FORMAT_B5G6R5_UNORM, true }, + + { GUID_WICPixelFormat32bppGrayFloat, DXGI_FORMAT_R32_FLOAT, false }, + { GUID_WICPixelFormat16bppGrayHalf, DXGI_FORMAT_R16_FLOAT, false }, + { GUID_WICPixelFormat16bppGray, DXGI_FORMAT_R16_UNORM, true }, + { GUID_WICPixelFormat8bppGray, DXGI_FORMAT_R8_UNORM, true }, + + { GUID_WICPixelFormat8bppAlpha, DXGI_FORMAT_A8_UNORM, false }, + + { GUID_WICPixelFormatBlackWhite, DXGI_FORMAT_R1_UNORM, false }, + }; + + bool g_WIC2 = false; + IWICImagingFactory* g_Factory = nullptr; +} + + +//===================================================================================== +// WIC Utilities +//===================================================================================== + +_Use_decl_annotations_ +DXGI_FORMAT DirectX::_WICToDXGI(const GUID& guid) +{ + for (size_t i = 0; i < _countof(g_WICFormats); ++i) + { + if (memcmp(&g_WICFormats[i].wic, &guid, sizeof(GUID)) == 0) + return g_WICFormats[i].format; + } + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + if (g_WIC2) + { + if (memcmp(&GUID_WICPixelFormat96bppRGBFloat, &guid, sizeof(GUID)) == 0) + return DXGI_FORMAT_R32G32B32_FLOAT; + } +#endif + + return DXGI_FORMAT_UNKNOWN; +} + +_Use_decl_annotations_ +bool DirectX::_DXGIToWIC( DXGI_FORMAT format, GUID& guid, bool ignoreRGBvsBGR ) +{ + switch( format ) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + if ( ignoreRGBvsBGR ) + { + // If we are not doing conversion so don't really care about BGR vs RGB color-order, + // we can use the canonical WIC 32bppBGRA format which avoids an extra format conversion when using the WIC scaler + memcpy( &guid, &GUID_WICPixelFormat32bppBGRA, sizeof(GUID) ); + } + else + { + memcpy( &guid, &GUID_WICPixelFormat32bppRGBA, sizeof(GUID) ); + } + return true; + + case DXGI_FORMAT_D32_FLOAT: + memcpy( &guid, &GUID_WICPixelFormat32bppGrayFloat, sizeof(GUID) ); + return true; + + case DXGI_FORMAT_D16_UNORM: + memcpy( &guid, &GUID_WICPixelFormat16bppGray, sizeof(GUID) ); + return true; + + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + memcpy( &guid, &GUID_WICPixelFormat32bppBGRA, sizeof(GUID) ); + return true; + + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + memcpy( &guid, &GUID_WICPixelFormat32bppBGR, sizeof(GUID) ); + return true; + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + case DXGI_FORMAT_R32G32B32_FLOAT: + if ( g_WIC2 ) + { + memcpy( &guid, &GUID_WICPixelFormat96bppRGBFloat, sizeof(GUID) ); + return true; + } + break; +#endif + + default: + for( size_t i=0; i < _countof(g_WICFormats); ++i ) + { + if ( g_WICFormats[i].format == format ) + { + memcpy( &guid, &g_WICFormats[i].wic, sizeof(GUID) ); + return true; + } + } + break; + } + + memcpy( &guid, &GUID_NULL, sizeof(GUID) ); + return false; +} + +DWORD DirectX::_CheckWICColorSpace(_In_ const GUID& sourceGUID, _In_ const GUID& targetGUID) +{ + DWORD srgb = 0; + + for (size_t i = 0; i < _countof(g_WICFormats); ++i) + { + if (memcmp(&g_WICFormats[i].wic, &sourceGUID, sizeof(GUID)) == 0) + { + if (g_WICFormats[i].srgb) + srgb |= TEX_FILTER_SRGB_IN; + } + + if (memcmp(&g_WICFormats[i].wic, &targetGUID, sizeof(GUID)) == 0) + { + if (g_WICFormats[i].srgb) + srgb |= TEX_FILTER_SRGB_OUT; + } + } + + if ((srgb & (TEX_FILTER_SRGB_IN | TEX_FILTER_SRGB_OUT)) == (TEX_FILTER_SRGB_IN | TEX_FILTER_SRGB_OUT)) + { + srgb &= ~(TEX_FILTER_SRGB_IN | TEX_FILTER_SRGB_OUT); + } + + return srgb; +} + + +//------------------------------------------------------------------------------------- +// Public helper function to get common WIC codec GUIDs +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +REFGUID DirectX::GetWICCodec(WICCodecs codec) +{ + switch (codec) + { + case WIC_CODEC_BMP: + return GUID_ContainerFormatBmp; + + case WIC_CODEC_JPEG: + return GUID_ContainerFormatJpeg; + + case WIC_CODEC_PNG: + return GUID_ContainerFormatPng; + + case WIC_CODEC_TIFF: + return GUID_ContainerFormatTiff; + + case WIC_CODEC_GIF: + return GUID_ContainerFormatGif; + + case WIC_CODEC_WMP: + return GUID_ContainerFormatWmp; + + case WIC_CODEC_ICO: + return GUID_ContainerFormatIco; + + default: + return GUID_NULL; + } +} + + +//------------------------------------------------------------------------------------- +// Singleton function for WIC factory +//------------------------------------------------------------------------------------- +IWICImagingFactory* DirectX::GetWICFactory(bool& iswic2) +{ + if (g_Factory) + { + iswic2 = g_WIC2; + return g_Factory; + } + + static INIT_ONCE s_initOnce = INIT_ONCE_STATIC_INIT; + + InitOnceExecuteOnce(&s_initOnce, + [](PINIT_ONCE, PVOID, LPVOID *factory) -> BOOL + { +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + HRESULT hr = CoCreateInstance( + CLSID_WICImagingFactory2, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory2), + factory + ); + + if (SUCCEEDED(hr)) + { + // WIC2 is available on Windows 10, Windows 8.x, and Windows 7 SP1 with KB 2670838 installed + g_WIC2 = true; + return TRUE; + } + else + { + g_WIC2 = false; + + hr = CoCreateInstance( + CLSID_WICImagingFactory1, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + factory + ); + return SUCCEEDED(hr) ? TRUE : FALSE; + } +#else + g_WIC2 = false; + + return SUCCEEDED(CoCreateInstance( + CLSID_WICImagingFactory, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + factory)) ? TRUE : FALSE; +#endif + }, nullptr, reinterpret_cast(&g_Factory)); + + iswic2 = g_WIC2; + return g_Factory; +} + + +//------------------------------------------------------------------------------------- +// Optional initializer for WIC factory +//------------------------------------------------------------------------------------- +void DirectX::SetWICFactory(_In_opt_ IWICImagingFactory* pWIC) +{ + if (pWIC == g_Factory) + return; + + bool iswic2 = false; + if (pWIC) + { +#if(_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + ComPtr wic2; + HRESULT hr = pWIC->QueryInterface(IID_PPV_ARGS(wic2.GetAddressOf())); + if (SUCCEEDED(hr)) + { + iswic2 = true; + } +#endif + pWIC->AddRef(); + } + + g_WIC2 = iswic2; + std::swap(pWIC, g_Factory); + if (pWIC) + pWIC->Release(); +} + + + +//===================================================================================== +// DXGI Format Utilities +//===================================================================================== + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::IsPacked(DXGI_FORMAT fmt) +{ + switch (static_cast(fmt)) + { + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_YUY2: // 4:2:2 8-bit + case DXGI_FORMAT_Y210: // 4:2:2 10-bit + case DXGI_FORMAT_Y216: // 4:2:2 16-bit + return true; + + default: + return false; + } +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::IsVideo(DXGI_FORMAT fmt) +{ + switch (static_cast(fmt)) + { + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + case DXGI_FORMAT_YUY2: + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + case DXGI_FORMAT_NV11: + // These video formats can be used with the 3D pipeline through special view mappings + + case DXGI_FORMAT_420_OPAQUE: + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case DXGI_FORMAT_A8P8: + // These are limited use video formats not usable in any way by the 3D pipeline + + case WIN10_DXGI_FORMAT_P208: + case WIN10_DXGI_FORMAT_V208: + case WIN10_DXGI_FORMAT_V408: + // These video formats are for JPEG Hardware decode (DXGI 1.4) + return true; + + default: + return false; + } +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::IsPlanar(DXGI_FORMAT fmt) +{ + switch (static_cast(fmt)) + { + case DXGI_FORMAT_NV12: // 4:2:0 8-bit + case DXGI_FORMAT_P010: // 4:2:0 10-bit + case DXGI_FORMAT_P016: // 4:2:0 16-bit + case DXGI_FORMAT_420_OPAQUE:// 4:2:0 8-bit + case DXGI_FORMAT_NV11: // 4:1:1 8-bit + + case WIN10_DXGI_FORMAT_P208: // 4:2:2 8-bit + case WIN10_DXGI_FORMAT_V208: // 4:4:0 8-bit + case WIN10_DXGI_FORMAT_V408: // 4:4:4 8-bit + // These are JPEG Hardware decode formats (DXGI 1.4) + + case XBOX_DXGI_FORMAT_D16_UNORM_S8_UINT: + case XBOX_DXGI_FORMAT_R16_UNORM_X8_TYPELESS: + case XBOX_DXGI_FORMAT_X16_TYPELESS_G8_UINT: + // These are Xbox One platform specific types + return true; + + default: + return false; + } +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::IsDepthStencil(DXGI_FORMAT fmt) +{ + switch (static_cast(fmt)) + { + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_D16_UNORM: + case XBOX_DXGI_FORMAT_D16_UNORM_S8_UINT: + case XBOX_DXGI_FORMAT_R16_UNORM_X8_TYPELESS: + case XBOX_DXGI_FORMAT_X16_TYPELESS_G8_UINT: + return true; + + default: + return false; + } +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::IsTypeless(DXGI_FORMAT fmt, bool partialTypeless) +{ + switch (static_cast(fmt)) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R32G32_TYPELESS: + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R16G16_TYPELESS: + case DXGI_FORMAT_R32_TYPELESS: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_R8G8_TYPELESS: + case DXGI_FORMAT_R16_TYPELESS: + case DXGI_FORMAT_R8_TYPELESS: + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC7_TYPELESS: + return true; + + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case XBOX_DXGI_FORMAT_R16_UNORM_X8_TYPELESS: + case XBOX_DXGI_FORMAT_X16_TYPELESS_G8_UINT: + return partialTypeless; + + default: + return false; + } +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DirectX::HasAlpha(DXGI_FORMAT fmt) +{ + switch (static_cast(fmt)) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_A8P8: + case DXGI_FORMAT_B4G4R4A4_UNORM: + case XBOX_DXGI_FORMAT_R10G10B10_7E3_A2_FLOAT: + case XBOX_DXGI_FORMAT_R10G10B10_6E4_A2_FLOAT: + case XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM: + return true; + + default: + return false; + } +} + + +//------------------------------------------------------------------------------------- +// Returns bits-per-pixel for a given DXGI format, or 0 on failure +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +size_t DirectX::BitsPerPixel(DXGI_FORMAT fmt) +{ + switch (static_cast(fmt)) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + return 128; + + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return 96; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_R32G32_TYPELESS: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + return 64; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R11G11B10_FLOAT: + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_R16G16_TYPELESS: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + case DXGI_FORMAT_R32_TYPELESS: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_YUY2: + case XBOX_DXGI_FORMAT_R10G10B10_7E3_A2_FLOAT: + case XBOX_DXGI_FORMAT_R10G10B10_6E4_A2_FLOAT: + case XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM: + return 32; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + case XBOX_DXGI_FORMAT_D16_UNORM_S8_UINT: + case XBOX_DXGI_FORMAT_R16_UNORM_X8_TYPELESS: + case XBOX_DXGI_FORMAT_X16_TYPELESS_G8_UINT: + case WIN10_DXGI_FORMAT_V408: + return 24; + + case DXGI_FORMAT_R8G8_TYPELESS: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + case DXGI_FORMAT_R16_TYPELESS: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_A8P8: + case DXGI_FORMAT_B4G4R4A4_UNORM: + case WIN10_DXGI_FORMAT_P208: + case WIN10_DXGI_FORMAT_V208: + return 16; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + case DXGI_FORMAT_NV11: + return 12; + + case DXGI_FORMAT_R8_TYPELESS: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case XBOX_DXGI_FORMAT_R4G4_UNORM: + return 8; + + case DXGI_FORMAT_R1_UNORM: + return 1; + + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + return 4; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return 8; + + default: + return 0; + } +} + + +//------------------------------------------------------------------------------------- +// Returns bits-per-color-channel for a given DXGI format, or 0 on failure +// For mixed formats, it returns the largest color-depth in the format +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +size_t DirectX::BitsPerColor(DXGI_FORMAT fmt) +{ + switch (static_cast(fmt)) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + case DXGI_FORMAT_R32G32_TYPELESS: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_R32_TYPELESS: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + return 32; + + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + return 24; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_R16G16_TYPELESS: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + case DXGI_FORMAT_R16_TYPELESS: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_P016: + case DXGI_FORMAT_Y216: + case XBOX_DXGI_FORMAT_D16_UNORM_S8_UINT: + case XBOX_DXGI_FORMAT_R16_UNORM_X8_TYPELESS: + case XBOX_DXGI_FORMAT_X16_TYPELESS_G8_UINT: + return 16; + + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + return 14; + + case DXGI_FORMAT_R11G11B10_FLOAT: + return 11; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_P010: + case DXGI_FORMAT_Y210: + case XBOX_DXGI_FORMAT_R10G10B10_7E3_A2_FLOAT: + case XBOX_DXGI_FORMAT_R10G10B10_6E4_A2_FLOAT: + case XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM: + return 10; + + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_R8G8_TYPELESS: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + case DXGI_FORMAT_R8_TYPELESS: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + case DXGI_FORMAT_YUY2: + case DXGI_FORMAT_NV11: + case WIN10_DXGI_FORMAT_P208: + case WIN10_DXGI_FORMAT_V208: + case WIN10_DXGI_FORMAT_V408: + return 8; + + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return 7; + + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_B5G6R5_UNORM: + return 6; + + case DXGI_FORMAT_B5G5R5A1_UNORM: + return 5; + + case DXGI_FORMAT_B4G4R4A4_UNORM: + case XBOX_DXGI_FORMAT_R4G4_UNORM: + return 4; + + case DXGI_FORMAT_R1_UNORM: + return 1; + + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case DXGI_FORMAT_A8P8: + // Palettized formats return 0 for this function + + default: + return 0; + } +} + + +//------------------------------------------------------------------------------------- +// Computes the image row pitch in bytes, and the slice ptich (size in bytes of the image) +// based on DXGI format, width, and height +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DirectX::ComputePitch(DXGI_FORMAT fmt, size_t width, size_t height, + size_t& rowPitch, size_t& slicePitch, DWORD flags) +{ + switch (static_cast(fmt)) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + assert(IsCompressed(fmt)); + { + if (flags & CP_FLAGS_BAD_DXTN_TAILS) + { + size_t nbw = width >> 2; + size_t nbh = height >> 2; + rowPitch = std::max(1, nbw * 8); + slicePitch = std::max(1, rowPitch * nbh); + } + else + { + size_t nbw = std::max(1, (width + 3) / 4); + size_t nbh = std::max(1, (height + 3) / 4); + rowPitch = nbw * 8; + slicePitch = rowPitch * nbh; + } + } + break; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + assert(IsCompressed(fmt)); + { + if (flags & CP_FLAGS_BAD_DXTN_TAILS) + { + size_t nbw = width >> 2; + size_t nbh = height >> 2; + rowPitch = std::max(1, nbw * 16); + slicePitch = std::max(1, rowPitch * nbh); + } + else + { + size_t nbw = std::max(1, (width + 3) / 4); + size_t nbh = std::max(1, (height + 3) / 4); + rowPitch = nbw * 16; + slicePitch = rowPitch * nbh; + } + } + break; + + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_YUY2: + assert(IsPacked(fmt)); + rowPitch = ((width + 1) >> 1) * 4; + slicePitch = rowPitch * height; + break; + + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + assert(IsPacked(fmt)); + rowPitch = ((width + 1) >> 1) * 8; + slicePitch = rowPitch * height; + break; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + assert(IsPlanar(fmt)); + rowPitch = ((width + 1) >> 1) * 2; + slicePitch = rowPitch * (height + ((height + 1) >> 1)); + break; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + case XBOX_DXGI_FORMAT_D16_UNORM_S8_UINT: + case XBOX_DXGI_FORMAT_R16_UNORM_X8_TYPELESS: + case XBOX_DXGI_FORMAT_X16_TYPELESS_G8_UINT: + assert(IsPlanar(fmt)); + rowPitch = ((width + 1) >> 1) * 4; + slicePitch = rowPitch * (height + ((height + 1) >> 1)); + break; + + case DXGI_FORMAT_NV11: + assert(IsPlanar(fmt)); + rowPitch = ((width + 3) >> 2) * 4; + slicePitch = rowPitch * height * 2; + break; + + case WIN10_DXGI_FORMAT_P208: + assert(IsPlanar(fmt)); + rowPitch = ((width + 1) >> 1) * 2; + slicePitch = rowPitch * height * 2; + break; + + case WIN10_DXGI_FORMAT_V208: + assert(IsPlanar(fmt)); + rowPitch = width; + slicePitch = rowPitch * (height + (((height + 1) >> 1) * 2)); + break; + + case WIN10_DXGI_FORMAT_V408: + assert(IsPlanar(fmt)); + rowPitch = width; + slicePitch = rowPitch * (height + ((height >> 1) * 4)); + break; + + default: + assert(IsValid(fmt)); + assert(!IsCompressed(fmt) && !IsPacked(fmt) && !IsPlanar(fmt)); + { + + size_t bpp; + + if (flags & CP_FLAGS_24BPP) + bpp = 24; + else if (flags & CP_FLAGS_16BPP) + bpp = 16; + else if (flags & CP_FLAGS_8BPP) + bpp = 8; + else + bpp = BitsPerPixel(fmt); + + if (flags & (CP_FLAGS_LEGACY_DWORD | CP_FLAGS_PARAGRAPH | CP_FLAGS_YMM | CP_FLAGS_ZMM | CP_FLAGS_PAGE4K)) + { + if (flags & CP_FLAGS_PAGE4K) + { + rowPitch = ((width * bpp + 32767) / 32768) * 4096; + slicePitch = rowPitch * height; + } + else if (flags & CP_FLAGS_ZMM) + { + rowPitch = ((width * bpp + 511) / 512) * 64; + slicePitch = rowPitch * height; + } + else if (flags & CP_FLAGS_YMM) + { + rowPitch = ((width * bpp + 255) / 256) * 32; + slicePitch = rowPitch * height; + } + else if (flags & CP_FLAGS_PARAGRAPH) + { + rowPitch = ((width * bpp + 127) / 128) * 16; + slicePitch = rowPitch * height; + } + else // DWORD alignment + { + // Special computation for some incorrectly created DDS files based on + // legacy DirectDraw assumptions about pitch alignment + rowPitch = ((width * bpp + 31) / 32) * sizeof(uint32_t); + slicePitch = rowPitch * height; + } + } + else + { + // Default byte alignment + rowPitch = (width * bpp + 7) / 8; + slicePitch = rowPitch * height; + } + } + break; + } +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +size_t DirectX::ComputeScanlines(DXGI_FORMAT fmt, size_t height) +{ + switch (static_cast(fmt)) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + assert(IsCompressed(fmt)); + return std::max(1, (height + 3) / 4); + + case DXGI_FORMAT_NV11: + case WIN10_DXGI_FORMAT_P208: + assert(IsPlanar(fmt)); + return height * 2; + + case WIN10_DXGI_FORMAT_V208: + assert(IsPlanar(fmt)); + return height + (((height + 1) >> 1) * 2); + + case WIN10_DXGI_FORMAT_V408: + assert(IsPlanar(fmt)); + return height + ((height >> 1) * 4); + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + case DXGI_FORMAT_420_OPAQUE: + case XBOX_DXGI_FORMAT_D16_UNORM_S8_UINT: + case XBOX_DXGI_FORMAT_R16_UNORM_X8_TYPELESS: + case XBOX_DXGI_FORMAT_X16_TYPELESS_G8_UINT: + assert(IsPlanar(fmt)); + return height + ((height + 1) >> 1); + + default: + assert(IsValid(fmt)); + assert(!IsCompressed(fmt) && !IsPlanar(fmt)); + return height; + } +} + + +//------------------------------------------------------------------------------------- +// Converts to an SRGB equivalent type if available +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +DXGI_FORMAT DirectX::MakeSRGB(DXGI_FORMAT fmt) +{ + switch (fmt) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + return DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + + case DXGI_FORMAT_BC1_UNORM: + return DXGI_FORMAT_BC1_UNORM_SRGB; + + case DXGI_FORMAT_BC2_UNORM: + return DXGI_FORMAT_BC2_UNORM_SRGB; + + case DXGI_FORMAT_BC3_UNORM: + return DXGI_FORMAT_BC3_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + return DXGI_FORMAT_B8G8R8A8_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + return DXGI_FORMAT_B8G8R8X8_UNORM_SRGB; + + case DXGI_FORMAT_BC7_UNORM: + return DXGI_FORMAT_BC7_UNORM_SRGB; + + default: + return fmt; + } +} + + +//------------------------------------------------------------------------------------- +// Converts to a format to an equivalent TYPELESS format if available +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +DXGI_FORMAT DirectX::MakeTypeless(DXGI_FORMAT fmt) +{ + switch (static_cast(fmt)) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + return DXGI_FORMAT_R32G32B32A32_TYPELESS; + + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return DXGI_FORMAT_R32G32B32_TYPELESS; + + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + return DXGI_FORMAT_R16G16B16A16_TYPELESS; + + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + return DXGI_FORMAT_R32G32_TYPELESS; + + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case XBOX_DXGI_FORMAT_R10G10B10_7E3_A2_FLOAT: + case XBOX_DXGI_FORMAT_R10G10B10_6E4_A2_FLOAT: + case XBOX_DXGI_FORMAT_R10G10B10_SNORM_A2_UNORM: + return DXGI_FORMAT_R10G10B10A2_TYPELESS; + + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + return DXGI_FORMAT_R8G8B8A8_TYPELESS; + + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + return DXGI_FORMAT_R16G16_TYPELESS; + + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + return DXGI_FORMAT_R32_TYPELESS; + + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + return DXGI_FORMAT_R8G8_TYPELESS; + + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + return DXGI_FORMAT_R16_TYPELESS; + + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case XBOX_DXGI_FORMAT_R4G4_UNORM: + return DXGI_FORMAT_R8_TYPELESS; + + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + return DXGI_FORMAT_BC1_TYPELESS; + + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + return DXGI_FORMAT_BC2_TYPELESS; + + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + return DXGI_FORMAT_BC3_TYPELESS; + + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + return DXGI_FORMAT_BC4_TYPELESS; + + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + return DXGI_FORMAT_BC5_TYPELESS; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + return DXGI_FORMAT_B8G8R8A8_TYPELESS; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + return DXGI_FORMAT_B8G8R8X8_TYPELESS; + + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + return DXGI_FORMAT_BC6H_TYPELESS; + + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return DXGI_FORMAT_BC7_TYPELESS; + + default: + return fmt; + } +} + + +//------------------------------------------------------------------------------------- +// Converts to a TYPELESS format to an equivalent UNORM format if available +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +DXGI_FORMAT DirectX::MakeTypelessUNORM(DXGI_FORMAT fmt) +{ + switch (fmt) + { + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + return DXGI_FORMAT_R16G16B16A16_UNORM; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + return DXGI_FORMAT_R10G10B10A2_UNORM; + + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + return DXGI_FORMAT_R8G8B8A8_UNORM; + + case DXGI_FORMAT_R16G16_TYPELESS: + return DXGI_FORMAT_R16G16_UNORM; + + case DXGI_FORMAT_R8G8_TYPELESS: + return DXGI_FORMAT_R8G8_UNORM; + + case DXGI_FORMAT_R16_TYPELESS: + return DXGI_FORMAT_R16_UNORM; + + case DXGI_FORMAT_R8_TYPELESS: + return DXGI_FORMAT_R8_UNORM; + + case DXGI_FORMAT_BC1_TYPELESS: + return DXGI_FORMAT_BC1_UNORM; + + case DXGI_FORMAT_BC2_TYPELESS: + return DXGI_FORMAT_BC2_UNORM; + + case DXGI_FORMAT_BC3_TYPELESS: + return DXGI_FORMAT_BC3_UNORM; + + case DXGI_FORMAT_BC4_TYPELESS: + return DXGI_FORMAT_BC4_UNORM; + + case DXGI_FORMAT_BC5_TYPELESS: + return DXGI_FORMAT_BC5_UNORM; + + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + return DXGI_FORMAT_B8G8R8A8_UNORM; + + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + return DXGI_FORMAT_B8G8R8X8_UNORM; + + case DXGI_FORMAT_BC7_TYPELESS: + return DXGI_FORMAT_BC7_UNORM; + + default: + return fmt; + } +} + + +//------------------------------------------------------------------------------------- +// Converts to a TYPELESS format to an equivalent FLOAT format if available +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +DXGI_FORMAT DirectX::MakeTypelessFLOAT(DXGI_FORMAT fmt) +{ + switch (fmt) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + return DXGI_FORMAT_R32G32B32A32_FLOAT; + + case DXGI_FORMAT_R32G32B32_TYPELESS: + return DXGI_FORMAT_R32G32B32_FLOAT; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + return DXGI_FORMAT_R16G16B16A16_FLOAT; + + case DXGI_FORMAT_R32G32_TYPELESS: + return DXGI_FORMAT_R32G32_FLOAT; + + case DXGI_FORMAT_R16G16_TYPELESS: + return DXGI_FORMAT_R16G16_FLOAT; + + case DXGI_FORMAT_R32_TYPELESS: + return DXGI_FORMAT_R32_FLOAT; + + case DXGI_FORMAT_R16_TYPELESS: + return DXGI_FORMAT_R16_FLOAT; + + default: + return fmt; + } +} + + +//===================================================================================== +// TexMetadata +//===================================================================================== + +_Use_decl_annotations_ +size_t TexMetadata::ComputeIndex(size_t mip, size_t item, size_t slice) const +{ + if (mip >= mipLevels) + return size_t(-1); + + switch (dimension) + { + case TEX_DIMENSION_TEXTURE1D: + case TEX_DIMENSION_TEXTURE2D: + if (slice > 0) + return size_t(-1); + + if (item >= arraySize) + return size_t(-1); + + return (item*(mipLevels)+mip); + + case TEX_DIMENSION_TEXTURE3D: + if (item > 0) + { + // No support for arrays of volumes + return size_t(-1); + } + else + { + size_t index = 0; + size_t d = depth; + + for (size_t level = 0; level < mip; ++level) + { + index += d; + if (d > 1) + d >>= 1; + } + + if (slice >= d) + return size_t(-1); + + index += slice; + + return index; + } + break; + + default: + return size_t(-1); + } +} + + +//===================================================================================== +// Blob - Bitmap image container +//===================================================================================== + +Blob& Blob::operator= (Blob&& moveFrom) +{ + if (this != &moveFrom) + { + Release(); + + m_buffer = moveFrom.m_buffer; + m_size = moveFrom.m_size; + + moveFrom.m_buffer = nullptr; + moveFrom.m_size = 0; + } + return *this; +} + +void Blob::Release() +{ + if (m_buffer) + { + _aligned_free(m_buffer); + m_buffer = nullptr; + } + + m_size = 0; +} + +_Use_decl_annotations_ +HRESULT Blob::Initialize(size_t size) +{ + if (!size) + return E_INVALIDARG; + + Release(); + + m_buffer = _aligned_malloc(size, 16); + if (!m_buffer) + { + Release(); + return E_OUTOFMEMORY; + } + + m_size = size; + + return S_OK; +} + +HRESULT Blob::Trim(size_t size) +{ + if (!size) + return E_INVALIDARG; + + if (!m_buffer) + return E_UNEXPECTED; + + if (size > m_size) + return E_INVALIDARG; + + m_size = size; + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTexWIC.cpp b/deps/DirectXTex/DirectXTex/DirectXTexWIC.cpp new file mode 100644 index 0000000..b2be015 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTexWIC.cpp @@ -0,0 +1,1317 @@ +//------------------------------------------------------------------------------------- +// DirectXTexWIC.cpp +// +// DirectX Texture Library - WIC-based file reader/writer +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//------------------------------------------------------------------------------------- + +#include "directxtexp.h" + +//------------------------------------------------------------------------------------- +// IStream support for WIC Memory routines +//------------------------------------------------------------------------------------- + +#if defined(WINAPI_FAMILY) && (WINAPI_FAMILY == WINAPI_FAMILY_APP) && (WINAPI_FAMILY != WINAPI_FAMILY_PHONE_APP) + + #include + #pragma comment(lib,"shcore.lib") + +#ifdef __cplusplus_winrt + + static inline HRESULT CreateMemoryStream( _Outptr_ IStream** stream ) + { + auto randomAccessStream = ref new ::Windows::Storage::Streams::InMemoryRandomAccessStream(); + return CreateStreamOverRandomAccessStream( randomAccessStream, IID_PPV_ARGS( stream ) ); + } + +#else + + #include + #include + +#pragma warning(push) +#pragma warning(disable : 4471) + #include +#pragma warning(pop) + + static inline HRESULT CreateMemoryStream( _Outptr_ IStream** stream ) + { + Microsoft::WRL::ComPtr abiStream; + HRESULT hr = Windows::Foundation::ActivateInstance( + Microsoft::WRL::Wrappers::HStringReference( RuntimeClass_Windows_Storage_Streams_InMemoryRandomAccessStream ).Get(), + abiStream.GetAddressOf() ); + + if (SUCCEEDED(hr)) + { + hr = CreateStreamOverRandomAccessStream( abiStream.Get(), IID_PPV_ARGS( stream ) ); + } + return hr; + } + +#endif // __cplusplus_winrt + +#else + + #pragma prefast(suppress:6387 28196, "a simple wrapper around an existing annotated function" ); + static inline HRESULT CreateMemoryStream( _Outptr_ IStream** stream ) + { + return CreateStreamOnHGlobal( 0, TRUE, stream ); + } + +#endif + +using namespace DirectX; +using Microsoft::WRL::ComPtr; + +namespace +{ + + //------------------------------------------------------------------------------------- + // WIC Pixel Format nearest conversion table + //------------------------------------------------------------------------------------- + + struct WICConvert + { + GUID source; + GUID target; + }; + + const WICConvert g_WICConvert[] = + { + // Directly support the formats listed in XnaTexUtil::g_WICFormats, so no conversion required + // Note target GUID in this conversion table must be one of those directly supported formats. + + { GUID_WICPixelFormat1bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat2bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat4bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat8bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + + { GUID_WICPixelFormat2bppGray, GUID_WICPixelFormat8bppGray }, // DXGI_FORMAT_R8_UNORM + { GUID_WICPixelFormat4bppGray, GUID_WICPixelFormat8bppGray }, // DXGI_FORMAT_R8_UNORM + + { GUID_WICPixelFormat16bppGrayFixedPoint, GUID_WICPixelFormat16bppGrayHalf }, // DXGI_FORMAT_R16_FLOAT + { GUID_WICPixelFormat32bppGrayFixedPoint, GUID_WICPixelFormat32bppGrayFloat }, // DXGI_FORMAT_R32_FLOAT + + { GUID_WICPixelFormat16bppBGR555, GUID_WICPixelFormat16bppBGRA5551 }, // DXGI_FORMAT_B5G5R5A1_UNORM + { GUID_WICPixelFormat32bppBGR101010, GUID_WICPixelFormat32bppRGBA1010102 }, // DXGI_FORMAT_R10G10B10A2_UNORM + + { GUID_WICPixelFormat24bppBGR, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat24bppRGB, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat32bppPBGRA, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat32bppPRGBA, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + + { GUID_WICPixelFormat48bppRGB, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat48bppBGR, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppBGRA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPRGBA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPBGRA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + + { GUID_WICPixelFormat48bppRGBFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat48bppBGRFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBAFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppBGRAFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat48bppRGBHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + + { GUID_WICPixelFormat128bppPRGBAFloat, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBFloat, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBAFixedPoint, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBFixedPoint, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat32bppRGBE, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + + { GUID_WICPixelFormat32bppCMYK, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat64bppCMYK, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat40bppCMYKAlpha, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat80bppCMYKAlpha, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + + #if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + { GUID_WICPixelFormat32bppRGB, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat64bppRGB, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPRGBAHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + #endif + + // We don't support n-channel formats + }; + + //------------------------------------------------------------------------------------- + // Returns the DXGI format and optionally the WIC pixel GUID to convert to + //------------------------------------------------------------------------------------- + DXGI_FORMAT DetermineFormat( + _In_ const WICPixelFormatGUID& pixelFormat, + DWORD flags, + bool iswic2, + _Out_opt_ WICPixelFormatGUID* pConvert) + { + if (pConvert) + memset(pConvert, 0, sizeof(WICPixelFormatGUID)); + + DXGI_FORMAT format = _WICToDXGI(pixelFormat); + + if (format == DXGI_FORMAT_UNKNOWN) + { + if (memcmp(&GUID_WICPixelFormat96bppRGBFixedPoint, &pixelFormat, sizeof(WICPixelFormatGUID)) == 0) + { +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + if (iswic2) + { + if (pConvert) + memcpy(pConvert, &GUID_WICPixelFormat96bppRGBFloat, sizeof(WICPixelFormatGUID)); + format = DXGI_FORMAT_R32G32B32_FLOAT; + } + else +#else + UNREFERENCED_PARAMETER(iswic2); +#endif + { + if (pConvert) + memcpy(pConvert, &GUID_WICPixelFormat128bppRGBAFloat, sizeof(WICPixelFormatGUID)); + format = DXGI_FORMAT_R32G32B32A32_FLOAT; + } + } + else + { + for (size_t i = 0; i < _countof(g_WICConvert); ++i) + { + if (memcmp(&g_WICConvert[i].source, &pixelFormat, sizeof(WICPixelFormatGUID)) == 0) + { + if (pConvert) + memcpy(pConvert, &g_WICConvert[i].target, sizeof(WICPixelFormatGUID)); + + format = _WICToDXGI(g_WICConvert[i].target); + assert(format != DXGI_FORMAT_UNKNOWN); + break; + } + } + } + } + + // Handle special cases based on flags + switch (format) + { + case DXGI_FORMAT_B8G8R8A8_UNORM: // BGRA + case DXGI_FORMAT_B8G8R8X8_UNORM: // BGRX + if (flags & WIC_FLAGS_FORCE_RGB) + { + format = DXGI_FORMAT_R8G8B8A8_UNORM; + if (pConvert) + memcpy(pConvert, &GUID_WICPixelFormat32bppRGBA, sizeof(WICPixelFormatGUID)); + } + break; + + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + if (flags & WIC_FLAGS_NO_X2_BIAS) + { + format = DXGI_FORMAT_R10G10B10A2_UNORM; + if (pConvert) + memcpy(pConvert, &GUID_WICPixelFormat32bppRGBA1010102, sizeof(WICPixelFormatGUID)); + } + break; + + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_B5G6R5_UNORM: + if (flags & WIC_FLAGS_NO_16BPP) + { + format = DXGI_FORMAT_R8G8B8A8_UNORM; + if (pConvert) + memcpy(pConvert, &GUID_WICPixelFormat32bppRGBA, sizeof(WICPixelFormatGUID)); + } + break; + + case DXGI_FORMAT_R1_UNORM: + if (!(flags & WIC_FLAGS_ALLOW_MONO)) + { + // By default we want to promote a black & white to gresycale since R1 is not a generally supported D3D format + format = DXGI_FORMAT_R8_UNORM; + if (pConvert) + memcpy(pConvert, &GUID_WICPixelFormat8bppGray, sizeof(WICPixelFormatGUID)); + } + break; + + default: + break; + } + + return format; + } + + + //------------------------------------------------------------------------------------- + // Determines metadata for image + //------------------------------------------------------------------------------------- + HRESULT DecodeMetadata( + DWORD flags, + bool iswic2, + _In_ IWICBitmapDecoder *decoder, + _In_ IWICBitmapFrameDecode *frame, + _Out_ TexMetadata& metadata, + _Out_opt_ WICPixelFormatGUID* pConvert, + _In_opt_ std::function getMQR) + { + if (!decoder || !frame) + return E_POINTER; + + memset(&metadata, 0, sizeof(TexMetadata)); + metadata.depth = 1; + metadata.mipLevels = 1; + metadata.dimension = TEX_DIMENSION_TEXTURE2D; + + UINT w, h; + HRESULT hr = frame->GetSize(&w, &h); + if (FAILED(hr)) + return hr; + + metadata.width = w; + metadata.height = h; + + if (flags & WIC_FLAGS_ALL_FRAMES) + { + UINT fcount; + hr = decoder->GetFrameCount(&fcount); + if (FAILED(hr)) + return hr; + + metadata.arraySize = fcount; + } + else + metadata.arraySize = 1; + + WICPixelFormatGUID pixelFormat; + hr = frame->GetPixelFormat(&pixelFormat); + if (FAILED(hr)) + return hr; + + metadata.format = DetermineFormat(pixelFormat, flags, iswic2, pConvert); + if (metadata.format == DXGI_FORMAT_UNKNOWN) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + if (!(flags & WIC_FLAGS_IGNORE_SRGB)) + { + GUID containerFormat; + hr = decoder->GetContainerFormat(&containerFormat); + if (FAILED(hr)) + return hr; + + ComPtr metareader; + hr = frame->GetMetadataQueryReader(metareader.GetAddressOf()); + if (SUCCEEDED(hr)) + { + // Check for sRGB colorspace metadata + bool sRGB = false; + + PROPVARIANT value; + PropVariantInit(&value); + + if (memcmp(&containerFormat, &GUID_ContainerFormatPng, sizeof(GUID)) == 0) + { + // Check for sRGB chunk + if (SUCCEEDED(metareader->GetMetadataByName(L"/sRGB/RenderingIntent", &value)) && value.vt == VT_UI1) + { + sRGB = true; + } + } +#if defined(_XBOX_ONE) && defined(_TITLE) + else if (memcmp(&containerFormat, &GUID_ContainerFormatJpeg, sizeof(GUID)) == 0) + { + if (SUCCEEDED(metareader->GetMetadataByName(L"/app1/ifd/exif/{ushort=40961}", &value)) && value.vt == VT_UI2 && value.uiVal == 1) + { + sRGB = true; + } + } + else if (memcmp(&containerFormat, &GUID_ContainerFormatTiff, sizeof(GUID)) == 0) + { + if (SUCCEEDED(metareader->GetMetadataByName(L"/ifd/exif/{ushort=40961}", &value)) && value.vt == VT_UI2 && value.uiVal == 1) + { + sRGB = true; + } + } +#else + else if (SUCCEEDED(metareader->GetMetadataByName(L"System.Image.ColorSpace", &value)) && value.vt == VT_UI2 && value.uiVal == 1) + { + sRGB = true; + } +#endif + + (void)PropVariantClear(&value); + + if (sRGB) + metadata.format = MakeSRGB(metadata.format); + } + else if (hr == WINCODEC_ERR_UNSUPPORTEDOPERATION) + { + // Some formats just don't support metadata (BMP, ICO, etc.), so ignore this failure + hr = S_OK; + } + } + + if (getMQR) + { + ComPtr metareader; + if (SUCCEEDED(frame->GetMetadataQueryReader(metareader.GetAddressOf()))) + { + getMQR(metareader.Get()); + } + } + + return hr; + } + + + //------------------------------------------------------------------------------------- + // Decodes a single frame + //------------------------------------------------------------------------------------- + HRESULT DecodeSingleFrame( + DWORD flags, + const TexMetadata& metadata, + const WICPixelFormatGUID& convertGUID, + _In_ IWICBitmapFrameDecode *frame, + _Inout_ ScratchImage& image) + { + if (!frame) + return E_POINTER; + + HRESULT hr = image.Initialize2D(metadata.format, metadata.width, metadata.height, 1, 1); + if (FAILED(hr)) + return hr; + + const Image *img = image.GetImage(0, 0, 0); + if (!img) + return E_POINTER; + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + if (memcmp(&convertGUID, &GUID_NULL, sizeof(GUID)) == 0) + { + hr = frame->CopyPixels(0, static_cast(img->rowPitch), static_cast(img->slicePitch), img->pixels); + if (FAILED(hr)) + return hr; + } + else + { + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID pixelFormat; + hr = frame->GetPixelFormat(&pixelFormat); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pixelFormat, convertGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(frame, convertGUID, _GetWICDither(flags), nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(0, static_cast(img->rowPitch), static_cast(img->slicePitch), img->pixels); + if (FAILED(hr)) + return hr; + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Decodes an image array, resizing/format converting as needed + //------------------------------------------------------------------------------------- + HRESULT DecodeMultiframe( + DWORD flags, + const TexMetadata& metadata, + _In_ IWICBitmapDecoder *decoder, + _Inout_ ScratchImage& image) + { + if (!decoder) + return E_POINTER; + + HRESULT hr = image.Initialize2D(metadata.format, metadata.width, metadata.height, metadata.arraySize, 1); + if (FAILED(hr)) + return hr; + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + WICPixelFormatGUID sourceGUID; + if (!_DXGIToWIC(metadata.format, sourceGUID)) + return E_FAIL; + + for (size_t index = 0; index < metadata.arraySize; ++index) + { + const Image* img = image.GetImage(0, index, 0); + if (!img) + return E_POINTER; + + ComPtr frame; + hr = decoder->GetFrame(static_cast(index), frame.GetAddressOf()); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID pfGuid; + hr = frame->GetPixelFormat(&pfGuid); + if (FAILED(hr)) + return hr; + + UINT w, h; + hr = frame->GetSize(&w, &h); + if (FAILED(hr)) + return hr; + + if (w == metadata.width && h == metadata.height) + { + // This frame does not need resized + if (memcmp(&pfGuid, &sourceGUID, sizeof(WICPixelFormatGUID)) == 0) + { + hr = frame->CopyPixels(0, static_cast(img->rowPitch), static_cast(img->slicePitch), img->pixels); + if (FAILED(hr)) + return hr; + } + else + { + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pfGuid, sourceGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(frame.Get(), sourceGUID, _GetWICDither(flags), nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(0, static_cast(img->rowPitch), static_cast(img->slicePitch), img->pixels); + if (FAILED(hr)) + return hr; + } + } + else + { + // This frame needs resizing + ComPtr scaler; + hr = pWIC->CreateBitmapScaler(scaler.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = scaler->Initialize(frame.Get(), static_cast(metadata.width), static_cast(metadata.height), _GetWICInterp(flags)); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID pfScaler; + hr = scaler->GetPixelFormat(&pfScaler); + if (FAILED(hr)) + return hr; + + if (memcmp(&pfScaler, &sourceGUID, sizeof(WICPixelFormatGUID)) == 0) + { + hr = scaler->CopyPixels(0, static_cast(img->rowPitch), static_cast(img->slicePitch), img->pixels); + if (FAILED(hr)) + return hr; + } + else + { + // The WIC bitmap scaler is free to return a different pixel format than the source image, so here we + // convert it to our desired format + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pfScaler, sourceGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(scaler.Get(), sourceGUID, _GetWICDither(flags), nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(0, static_cast(img->rowPitch), static_cast(img->slicePitch), img->pixels); + if (FAILED(hr)) + return hr; + } + } + } + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Encodes image metadata + //------------------------------------------------------------------------------------- + HRESULT EncodeMetadata( + _In_ IWICBitmapFrameEncode* frame, + const GUID& containerFormat, + DXGI_FORMAT format) + { + if (!frame) + return E_POINTER; + + ComPtr metawriter; + HRESULT hr = frame->GetMetadataQueryWriter(metawriter.GetAddressOf()); + if (SUCCEEDED(hr)) + { + PROPVARIANT value; + PropVariantInit(&value); + + bool sRGB = IsSRGB(format); + + value.vt = VT_LPSTR; + value.pszVal = const_cast("DirectXTex"); + + if (memcmp(&containerFormat, &GUID_ContainerFormatPng, sizeof(GUID)) == 0) + { + // Set Software name + (void)metawriter->SetMetadataByName(L"/tEXt/{str=Software}", &value); + + // Set sRGB chunk + if (sRGB) + { + value.vt = VT_UI1; + value.bVal = 0; + (void)metawriter->SetMetadataByName(L"/sRGB/RenderingIntent", &value); + } + } +#if defined(_XBOX_ONE) && defined(_TITLE) + else if (memcmp(&containerFormat, &GUID_ContainerFormatJpeg, sizeof(GUID)) == 0) + { + // Set Software name + (void)metawriter->SetMetadataByName(L"/app1/ifd/{ushort=305}", &value); + + if (sRGB) + { + // Set EXIF Colorspace of sRGB + value.vt = VT_UI2; + value.uiVal = 1; + (void)metawriter->SetMetadataByName(L"/app1/ifd/exif/{ushort=40961}", &value); + } + } + else if (memcmp(&containerFormat, &GUID_ContainerFormatTiff, sizeof(GUID)) == 0) + { + // Set Software name + (void)metawriter->SetMetadataByName(L"/ifd/{ushort=305}", &value); + + if (sRGB) + { + // Set EXIF Colorspace of sRGB + value.vt = VT_UI2; + value.uiVal = 1; + (void)metawriter->SetMetadataByName(L"/ifd/exif/{ushort=40961}", &value); + } + } +#else + else + { + // Set Software name + (void)metawriter->SetMetadataByName(L"System.ApplicationName", &value); + + if (sRGB) + { + // Set EXIF Colorspace of sRGB + value.vt = VT_UI2; + value.uiVal = 1; + (void)metawriter->SetMetadataByName(L"System.Image.ColorSpace", &value); + } + } +#endif + } + else if (hr == WINCODEC_ERR_UNSUPPORTEDOPERATION) + { + // Some formats just don't support metadata (BMP, ICO, etc.), so ignore this failure + hr = S_OK; + } + + return hr; + } + + + //------------------------------------------------------------------------------------- + // Encodes a single frame + //------------------------------------------------------------------------------------- + HRESULT EncodeImage( + const Image& image, + DWORD flags, + _In_ REFGUID containerFormat, + _In_ IWICBitmapFrameEncode* frame, + _In_opt_ IPropertyBag2* props, + _In_opt_ const GUID* targetFormat) + { + if (!frame) + return E_INVALIDARG; + + if (!image.pixels) + return E_POINTER; + + WICPixelFormatGUID pfGuid; + if (!_DXGIToWIC(image.format, pfGuid)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + HRESULT hr = frame->Initialize(props); + if (FAILED(hr)) + return hr; + + if ((image.width > UINT32_MAX) || (image.height > UINT32_MAX)) + return E_INVALIDARG; + + hr = frame->SetSize(static_cast(image.width), static_cast(image.height)); + if (FAILED(hr)) + return hr; + + hr = frame->SetResolution(72, 72); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID targetGuid = (targetFormat) ? (*targetFormat) : pfGuid; + hr = frame->SetPixelFormat(&targetGuid); + if (FAILED(hr)) + return hr; + + if (targetFormat && memcmp(targetFormat, &targetGuid, sizeof(WICPixelFormatGUID)) != 0) + { + // Requested output pixel format is not supported by the WIC codec + return E_FAIL; + } + + hr = EncodeMetadata(frame, containerFormat, image.format); + if (FAILED(hr)) + return hr; + + if (memcmp(&targetGuid, &pfGuid, sizeof(WICPixelFormatGUID)) != 0) + { + // Conversion required to write + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr source; + hr = pWIC->CreateBitmapFromMemory(static_cast(image.width), static_cast(image.height), pfGuid, + static_cast(image.rowPitch), static_cast(image.slicePitch), + image.pixels, source.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pfGuid, targetGuid, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(source.Get(), targetGuid, _GetWICDither(flags), nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + WICRect rect = { 0, 0, static_cast(image.width), static_cast(image.height) }; + hr = frame->WriteSource(FC.Get(), &rect); + if (FAILED(hr)) + return hr; + } + else + { + // No conversion required + hr = frame->WritePixels(static_cast(image.height), static_cast(image.rowPitch), static_cast(image.slicePitch), + reinterpret_cast(image.pixels)); + if (FAILED(hr)) + return hr; + } + + hr = frame->Commit(); + if (FAILED(hr)) + return hr; + + return S_OK; + } + + HRESULT EncodeSingleFrame( + const Image& image, + DWORD flags, + _In_ REFGUID containerFormat, + _Inout_ IStream* stream, + _In_opt_ const GUID* targetFormat, + _In_opt_ std::function setCustomProps) + { + if (!stream) + return E_INVALIDARG; + + // Initialize WIC + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr encoder; + HRESULT hr = pWIC->CreateEncoder(containerFormat, 0, encoder.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = encoder->Initialize(stream, WICBitmapEncoderNoCache); + if (FAILED(hr)) + return hr; + + ComPtr frame; + ComPtr props; + hr = encoder->CreateNewFrame(frame.GetAddressOf(), props.GetAddressOf()); + if (FAILED(hr)) + return hr; + + if (memcmp(&containerFormat, &GUID_ContainerFormatBmp, sizeof(WICPixelFormatGUID)) == 0 && iswic2) + { + // Opt-in to the WIC2 support for writing 32-bit Windows BMP files with an alpha channel + PROPBAG2 option = { 0 }; + option.pstrName = const_cast(L"EnableV5Header32bppBGRA"); + + VARIANT varValue; + varValue.vt = VT_BOOL; + varValue.boolVal = VARIANT_TRUE; + (void)props->Write(1, &option, &varValue); + } + + if (setCustomProps) + { + setCustomProps(props.Get()); + } + + hr = EncodeImage(image, flags, containerFormat, frame.Get(), props.Get(), targetFormat); + if (FAILED(hr)) + return hr; + + hr = encoder->Commit(); + if (FAILED(hr)) + return hr; + + return S_OK; + } + + + //------------------------------------------------------------------------------------- + // Encodes an image array + //------------------------------------------------------------------------------------- + HRESULT EncodeMultiframe( + _In_reads_(nimages) const Image* images, + size_t nimages, + DWORD flags, + _In_ REFGUID containerFormat, + _Inout_ IStream* stream, + _In_opt_ const GUID* targetFormat, + _In_opt_ std::function setCustomProps) + { + if (!stream || nimages < 2) + return E_INVALIDARG; + + if (!images) + return E_POINTER; + + // Initialize WIC + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr encoder; + HRESULT hr = pWIC->CreateEncoder(containerFormat, 0, encoder.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr einfo; + hr = encoder->GetEncoderInfo(einfo.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL mframe = FALSE; + hr = einfo->DoesSupportMultiframe(&mframe); + if (FAILED(hr)) + return hr; + + if (!mframe) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + hr = encoder->Initialize(stream, WICBitmapEncoderNoCache); + if (FAILED(hr)) + return hr; + + for (size_t index = 0; index < nimages; ++index) + { + ComPtr frame; + ComPtr props; + hr = encoder->CreateNewFrame(frame.GetAddressOf(), props.GetAddressOf()); + if (FAILED(hr)) + return hr; + + if (setCustomProps) + { + setCustomProps(props.Get()); + } + + hr = EncodeImage(images[index], flags, containerFormat, frame.Get(), props.Get(), targetFormat); + if (FAILED(hr)) + return hr; + } + + hr = encoder->Commit(); + if (FAILED(hr)) + return hr; + + return S_OK; + } +} + + +//===================================================================================== +// Entry-points +//===================================================================================== + +//------------------------------------------------------------------------------------- +// Obtain metadata from WIC-supported file in memory +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::GetMetadataFromWICMemory( + const void* pSource, + size_t size, + DWORD flags, + TexMetadata& metadata, + std::function getMQR) +{ + if (!pSource || size == 0) + return E_INVALIDARG; + + if (size > UINT32_MAX) + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + // Create input stream for memory + ComPtr stream; + HRESULT hr = pWIC->CreateStream(stream.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = stream->InitializeFromMemory(reinterpret_cast(const_cast(pSource)), + static_cast(size)); + if (FAILED(hr)) + return hr; + + // Initialize WIC + ComPtr decoder; + hr = pWIC->CreateDecoderFromStream(stream.Get(), 0, WICDecodeMetadataCacheOnDemand, decoder.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr frame; + hr = decoder->GetFrame(0, frame.GetAddressOf()); + if (FAILED(hr)) + return hr; + + // Get metadata + hr = DecodeMetadata(flags, iswic2, decoder.Get(), frame.Get(), metadata, nullptr, getMQR); + if (FAILED(hr)) + return hr; + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Obtain metadata from WIC-supported file on disk +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::GetMetadataFromWICFile( + const wchar_t* szFile, + DWORD flags, + TexMetadata& metadata, + std::function getMQR) +{ + if (!szFile) + return E_INVALIDARG; + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + // Initialize WIC + ComPtr decoder; + HRESULT hr = pWIC->CreateDecoderFromFilename(szFile, 0, GENERIC_READ, WICDecodeMetadataCacheOnDemand, decoder.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr frame; + hr = decoder->GetFrame(0, frame.GetAddressOf()); + if (FAILED(hr)) + return hr; + + // Get metadata + hr = DecodeMetadata(flags, iswic2, decoder.Get(), frame.Get(), metadata, nullptr, getMQR); + if (FAILED(hr)) + return hr; + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Load a WIC-supported file in memory +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadFromWICMemory( + const void* pSource, + size_t size, + DWORD flags, + TexMetadata* metadata, + ScratchImage& image, + std::function getMQR) +{ + if (!pSource || size == 0) + return E_INVALIDARG; + + if (size > UINT32_MAX) + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + image.Release(); + + // Create input stream for memory + ComPtr stream; + HRESULT hr = pWIC->CreateStream(stream.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = stream->InitializeFromMemory(reinterpret_cast(const_cast(pSource)), static_cast(size)); + if (FAILED(hr)) + return hr; + + // Initialize WIC + ComPtr decoder; + hr = pWIC->CreateDecoderFromStream(stream.Get(), 0, WICDecodeMetadataCacheOnDemand, decoder.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr frame; + hr = decoder->GetFrame(0, frame.GetAddressOf()); + if (FAILED(hr)) + return hr; + + // Get metadata + TexMetadata mdata; + WICPixelFormatGUID convertGUID = { 0 }; + hr = DecodeMetadata(flags, iswic2, decoder.Get(), frame.Get(), mdata, &convertGUID, getMQR); + if (FAILED(hr)) + return hr; + + if ((mdata.arraySize > 1) && (flags & WIC_FLAGS_ALL_FRAMES)) + { + hr = DecodeMultiframe(flags, mdata, decoder.Get(), image); + } + else + { + hr = DecodeSingleFrame(flags, mdata, convertGUID, frame.Get(), image); + } + + if (FAILED(hr)) + { + image.Release(); + return hr; + } + + if (metadata) + memcpy(metadata, &mdata, sizeof(TexMetadata)); + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Load a WIC-supported file from disk +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadFromWICFile( + const wchar_t* szFile, + DWORD flags, + TexMetadata* metadata, + ScratchImage& image, + std::function getMQR) +{ + if (!szFile) + return E_INVALIDARG; + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + image.Release(); + + // Initialize WIC + ComPtr decoder; + HRESULT hr = pWIC->CreateDecoderFromFilename(szFile, 0, GENERIC_READ, WICDecodeMetadataCacheOnDemand, decoder.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr frame; + hr = decoder->GetFrame(0, frame.GetAddressOf()); + if (FAILED(hr)) + return hr; + + // Get metadata + TexMetadata mdata; + WICPixelFormatGUID convertGUID = { 0 }; + hr = DecodeMetadata(flags, iswic2, decoder.Get(), frame.Get(), mdata, &convertGUID, getMQR); + if (FAILED(hr)) + return hr; + + if ((mdata.arraySize > 1) && (flags & WIC_FLAGS_ALL_FRAMES)) + { + hr = DecodeMultiframe(flags, mdata, decoder.Get(), image); + } + else + { + hr = DecodeSingleFrame(flags, mdata, convertGUID, frame.Get(), image); + } + + if (FAILED(hr)) + { + image.Release(); + return hr; + } + + if (metadata) + memcpy(metadata, &mdata, sizeof(TexMetadata)); + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Save a WIC-supported file to memory +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveToWICMemory( + const Image& image, + DWORD flags, + REFGUID containerFormat, + Blob& blob, + const GUID* targetFormat, + std::function setCustomProps) +{ + if (!image.pixels) + return E_POINTER; + + blob.Release(); + + ComPtr stream; + HRESULT hr = CreateMemoryStream(stream.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = EncodeSingleFrame(image, flags, containerFormat, stream.Get(), targetFormat, setCustomProps); + if (FAILED(hr)) + return hr; + + // Copy stream data into blob + STATSTG stat; + hr = stream->Stat(&stat, STATFLAG_NONAME); + if (FAILED(hr)) + return hr; + + if (stat.cbSize.HighPart > 0) + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + + hr = blob.Initialize(stat.cbSize.LowPart); + if (FAILED(hr)) + return hr; + + LARGE_INTEGER li = { { 0 } }; + hr = stream->Seek(li, STREAM_SEEK_SET, 0); + if (FAILED(hr)) + return hr; + + DWORD bytesRead; + hr = stream->Read(blob.GetBufferPointer(), static_cast(blob.GetBufferSize()), &bytesRead); + if (FAILED(hr)) + return hr; + + if (bytesRead != blob.GetBufferSize()) + return E_FAIL; + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT DirectX::SaveToWICMemory( + const Image* images, + size_t nimages, + DWORD flags, + REFGUID containerFormat, + Blob& blob, + const GUID* targetFormat, + std::function setCustomProps) +{ + if (!images || nimages == 0) + return E_INVALIDARG; + + blob.Release(); + + ComPtr stream; + HRESULT hr = CreateMemoryStream(stream.GetAddressOf()); + if (FAILED(hr)) + return hr; + + if (nimages > 1) + hr = EncodeMultiframe(images, nimages, flags, containerFormat, stream.Get(), targetFormat, setCustomProps); + else + hr = EncodeSingleFrame(images[0], flags, containerFormat, stream.Get(), targetFormat, setCustomProps); + + if (FAILED(hr)) + return hr; + + // Copy stream data into blob + STATSTG stat; + hr = stream->Stat(&stat, STATFLAG_NONAME); + if (FAILED(hr)) + return hr; + + if (stat.cbSize.HighPart > 0) + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + + hr = blob.Initialize(stat.cbSize.LowPart); + if (FAILED(hr)) + return hr; + + LARGE_INTEGER li = { { 0 } }; + hr = stream->Seek(li, STREAM_SEEK_SET, 0); + if (FAILED(hr)) + return hr; + + DWORD bytesRead; + hr = stream->Read(blob.GetBufferPointer(), static_cast(blob.GetBufferSize()), &bytesRead); + if (FAILED(hr)) + return hr; + + if (bytesRead != blob.GetBufferSize()) + return E_FAIL; + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +// Save a WIC-supported file to disk +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveToWICFile( + const Image& image, + DWORD flags, + REFGUID containerFormat, + const wchar_t* szFile, + const GUID* targetFormat, + std::function setCustomProps) +{ + if (!szFile) + return E_INVALIDARG; + + if (!image.pixels) + return E_POINTER; + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr stream; + HRESULT hr = pWIC->CreateStream(stream.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = stream->InitializeFromFilename(szFile, GENERIC_WRITE); + if (FAILED(hr)) + return hr; + + hr = EncodeSingleFrame(image, flags, containerFormat, stream.Get(), targetFormat, setCustomProps); + if (FAILED(hr)) + { + stream.Reset(); + DeleteFileW(szFile); + return hr; + } + + return S_OK; +} + +_Use_decl_annotations_ +HRESULT DirectX::SaveToWICFile( + const Image* images, + size_t nimages, + DWORD flags, + REFGUID containerFormat, + const wchar_t* szFile, + const GUID* targetFormat, + std::function setCustomProps) +{ + if (!szFile || !images || nimages == 0) + return E_INVALIDARG; + + bool iswic2 = false; + IWICImagingFactory* pWIC = GetWICFactory(iswic2); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr stream; + HRESULT hr = pWIC->CreateStream(stream.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = stream->InitializeFromFilename(szFile, GENERIC_WRITE); + if (FAILED(hr)) + return hr; + + if (nimages > 1) + hr = EncodeMultiframe(images, nimages, flags, containerFormat, stream.Get(), targetFormat, setCustomProps); + else + hr = EncodeSingleFrame(images[0], flags, containerFormat, stream.Get(), targetFormat, setCustomProps); + + if (FAILED(hr)) + { + stream.Reset(); + DeleteFileW(szFile); + return hr; + } + + return S_OK; +} diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2013.vcxproj b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2013.vcxproj new file mode 100644 index 0000000..41f0be8 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2013.vcxproj @@ -0,0 +1,457 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DirectXTex + {371B9FA9-4C90-4AC6-A123-ACED756D6C77} + DirectXTex + Win32Proj + $(VCTargetsPath11) + + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;_DEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;_DEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;PROFILE;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;PROFILE;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Document + + + Document + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2013.vcxproj.filters b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2013.vcxproj.filters new file mode 100644 index 0000000..1c9c27e --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2013.vcxproj.filters @@ -0,0 +1,163 @@ + + + + + {1b82e2dc-aea9-4897-8c7e-7ff2aa1ea8c8} + + + {d342dfd3-2538-4c06-98aa-9f8f79a9abee} + + + {1d9a21fa-9b40-40bd-a0d2-777ca8e2a4ca} + + + {30730940-319b-4b9d-bc3c-f4f00029cafb} + + + {ca7fdb2a-e99b-4b62-a803-629281c5ebe9} + + + + + Header Files + + + Header Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files + + + + + Source Files\Shaders + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015.vcxproj b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015.vcxproj new file mode 100644 index 0000000..122b5b6 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015.vcxproj @@ -0,0 +1,450 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DirectXTex + {371B9FA9-4C90-4AC6-A123-ACED756D6C77} + DirectXTex + Win32Proj + + + + StaticLibrary + Unicode + v140 + + + StaticLibrary + Unicode + v140 + + + StaticLibrary + Unicode + v140 + + + StaticLibrary + Unicode + v140 + + + StaticLibrary + Unicode + v140 + + + StaticLibrary + Unicode + v140 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;_DEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;_DEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;PROFILE;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;PROFILE;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + Document + + + Document + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015.vcxproj.filters b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015.vcxproj.filters new file mode 100644 index 0000000..693d4d1 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015.vcxproj.filters @@ -0,0 +1,163 @@ + + + + + {68652706-b700-4472-9af7-a56a482bd896} + + + {9b7fcbc5-2533-4b88-b75b-d4803e55fa7c} + + + {eb989628-e889-44bf-837a-05c9f09b258e} + + + {a674c059-ed12-4d51-b5b3-44c34ce565da} + + + {c0d1c51b-c157-45b8-9169-af3cc2c4f4b6} + + + + + Header Files + + + Header Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files + + + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015_Win10.vcxproj b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015_Win10.vcxproj new file mode 100644 index 0000000..96a9e7b --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015_Win10.vcxproj @@ -0,0 +1,457 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DirectXTex + {371B9FA9-4C90-4AC6-A123-ACED756D6C77} + DirectXTex + Win32Proj + 10.0.14393.0 + + + + StaticLibrary + Unicode + v140 + + + StaticLibrary + Unicode + v140 + + + StaticLibrary + Unicode + v140 + + + StaticLibrary + Unicode + v140 + + + StaticLibrary + Unicode + v140 + + + StaticLibrary + Unicode + v140 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2015_Win10\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;_DEBUG;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;_DEBUG;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;PROFILE;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;PROFILE;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Document + + + Document + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015_Win10.vcxproj.filters b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015_Win10.vcxproj.filters new file mode 100644 index 0000000..0b3fb32 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2015_Win10.vcxproj.filters @@ -0,0 +1,169 @@ + + + + + {68652706-b700-4472-9af7-a56a482bd896} + + + {9b7fcbc5-2533-4b88-b75b-d4803e55fa7c} + + + {d665bb3f-6d2a-415d-83f5-abd5c813962b} + + + {b8e74ae5-5bcf-404a-b18b-df14ecd31b2d} + + + {34309123-96a2-4472-b288-885f1fd2ac6c} + + + + + Header Files + + + Header Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files + + + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017.vcxproj b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017.vcxproj new file mode 100644 index 0000000..f4f9be2 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017.vcxproj @@ -0,0 +1,457 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DirectXTex + {371B9FA9-4C90-4AC6-A123-ACED756D6C77} + DirectXTex + Win32Proj + 10.0.15063.0 + + + + StaticLibrary + Unicode + v141 + + + StaticLibrary + Unicode + v141 + + + StaticLibrary + Unicode + v141 + + + StaticLibrary + Unicode + v141 + + + StaticLibrary + Unicode + v141 + + + StaticLibrary + Unicode + v141 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + StreamingSIMDExtensions2 + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;_DEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4996 + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;_DEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4996 + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4996 + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4996 + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;PROFILE;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4996 + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;PROFILE;_LIB;_WIN7_PLATFORM_UPDATE;_WIN32_WINNT=0x0600;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4996 + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + Document + + + Document + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017.vcxproj.filters b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017.vcxproj.filters new file mode 100644 index 0000000..693d4d1 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017.vcxproj.filters @@ -0,0 +1,163 @@ + + + + + {68652706-b700-4472-9af7-a56a482bd896} + + + {9b7fcbc5-2533-4b88-b75b-d4803e55fa7c} + + + {eb989628-e889-44bf-837a-05c9f09b258e} + + + {a674c059-ed12-4d51-b5b3-44c34ce565da} + + + {c0d1c51b-c157-45b8-9169-af3cc2c4f4b6} + + + + + Header Files + + + Header Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files + + + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017_Win10.vcxproj b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017_Win10.vcxproj new file mode 100644 index 0000000..e776d5e --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017_Win10.vcxproj @@ -0,0 +1,457 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DirectXTex + {371B9FA9-4C90-4AC6-A123-ACED756D6C77} + DirectXTex + Win32Proj + 10.0.14393.0 + + + + StaticLibrary + Unicode + v141 + + + StaticLibrary + Unicode + v141 + + + StaticLibrary + Unicode + v141 + + + StaticLibrary + Unicode + v141 + + + StaticLibrary + Unicode + v141 + + + StaticLibrary + Unicode + v141 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + StreamingSIMDExtensions2 + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;_DEBUG;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;_DEBUG;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;PROFILE;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + /permissive- %(AdditionalOptions) + _UNICODE;UNICODE;WIN32;NDEBUG;PROFILE;_LIB;_WIN32_WINNT=0x0A00;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Document + + + Document + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017_Win10.vcxproj.filters b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017_Win10.vcxproj.filters new file mode 100644 index 0000000..0b3fb32 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Desktop_2017_Win10.vcxproj.filters @@ -0,0 +1,169 @@ + + + + + {68652706-b700-4472-9af7-a56a482bd896} + + + {9b7fcbc5-2533-4b88-b75b-d4803e55fa7c} + + + {d665bb3f-6d2a-415d-83f5-abd5c813962b} + + + {b8e74ae5-5bcf-404a-b18b-df14ecd31b2d} + + + {34309123-96a2-4472-b288-885f1fd2ac6c} + + + + + Header Files + + + Header Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files + + + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Windows10.vcxproj b/deps/DirectXTex/DirectXTex/DirectXTex_Windows10.vcxproj new file mode 100644 index 0000000..a1a7f94 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Windows10.vcxproj @@ -0,0 +1,316 @@ + + + + + Debug + ARM + + + Debug + Win32 + + + Debug + x64 + + + Release + ARM + + + Release + Win32 + + + Release + x64 + + + + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Document + + + Document + + + + {fb3f52b5-bfe8-43fd-836f-363735dab738} + StaticLibrary + DirectXTex + DirectXTex + en-US + 14.0 + true + Windows Store + 10.0.15063.0 + 10.0.14393.0 + 10.0 + + + + StaticLibrary + true + v141 + + + StaticLibrary + true + v141 + + + StaticLibrary + true + v141 + + + StaticLibrary + false + v141 + + + StaticLibrary + false + v141 + + + StaticLibrary + false + v141 + + + + + + + + + + + + + + + + + + + + + + + + + + + + Bin\Windows10\$(Platform)\$(Configuration)\ + Bin\Windows10\$(Platform)\$(Configuration)\ + DirectXTex + false + + + Bin\Windows10\$(Platform)\$(Configuration)\ + Bin\Windows10\$(Platform)\$(Configuration)\ + DirectXTex + false + + + Bin\Windows10\$(Platform)\$(Configuration)\ + Bin\Windows10\$(Platform)\$(Configuration)\ + DirectXTex + false + + + Bin\Windows10\$(Platform)\$(Configuration)\ + Bin\Windows10\$(Platform)\$(Configuration)\ + DirectXTex + false + + + Bin\Windows10\$(Platform)\$(Configuration)\ + Bin\Windows10\$(Platform)\$(Configuration)\ + DirectXTex + false + + + Bin\Windows10\$(Platform)\$(Configuration)\ + Bin\Windows10\$(Platform)\$(Configuration)\ + DirectXTex + false + + + + Use + false + true + Fast + StreamingSIMDExtensions2 + $(IntDir)$(TargetName).pdb + EnableAllWarnings + DirectXTexP.h + _CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + /permissive- %(AdditionalOptions) + + + Console + false + false + + + + + Use + false + true + Fast + StreamingSIMDExtensions2 + $(IntDir)$(TargetName).pdb + EnableAllWarnings + DirectXTexP.h + _CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + /permissive- %(AdditionalOptions) + + + Console + false + false + + + + + Use + false + true + Fast + $(IntDir)$(TargetName).pdb + EnableAllWarnings + DirectXTexP.h + _CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + /permissive- %(AdditionalOptions) + + + Console + false + false + + + + + Use + false + true + Fast + $(IntDir)$(TargetName).pdb + EnableAllWarnings + DirectXTexP.h + _CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + /permissive- %(AdditionalOptions) + + + Console + false + false + + + + + Use + false + true + Fast + $(IntDir)$(TargetName).pdb + EnableAllWarnings + DirectXTexP.h + _CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + /permissive- %(AdditionalOptions) + + + Console + false + false + + + + + Use + false + true + Fast + $(IntDir)$(TargetName).pdb + EnableAllWarnings + DirectXTexP.h + _CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + /permissive- %(AdditionalOptions) + + + Console + false + false + + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Windows10.vcxproj.filters b/deps/DirectXTex/DirectXTex/DirectXTex_Windows10.vcxproj.filters new file mode 100644 index 0000000..83c5bb1 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Windows10.vcxproj.filters @@ -0,0 +1,184 @@ + + + + + {f4d68f4f-adbe-40a1-b052-f2e4cae3b5ae} + + + {b42472b0-7a63-47b0-b77f-4ffe492471a0} + + + {1838e3e6-1f80-4713-9a98-41ea7e654d12} + + + {7c13ba68-1ec8-4710-a8dd-cd973621b725} + + + {fbc9373c-d511-4fd1-a7b8-d55df1b27d2e} + + + + + {f4d68f4f-adbe-40a1-b052-f2e4cae3b5ae} + + + {b42472b0-7a63-47b0-b77f-4ffe492471a0} + + + {1838e3e6-1f80-4713-9a98-41ea7e654d12} + + + {7c13ba68-1ec8-4710-a8dd-cd973621b725} + + + {fbc9373c-d511-4fd1-a7b8-d55df1b27d2e} + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Header Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Header Files + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Windows81.vcxproj b/deps/DirectXTex/DirectXTex/DirectXTex_Windows81.vcxproj new file mode 100644 index 0000000..9741a4f --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Windows81.vcxproj @@ -0,0 +1,676 @@ + + + + + Debug + ARM + + + Debug + Win32 + + + Debug + x64 + + + Profile + ARM + + + Profile + Win32 + + + Profile + x64 + + + Release + ARM + + + Release + Win32 + + + Release + x64 + + + + DirectXTex + {371B9FA9-4C90-4AC6-A123-ACED756D6C77} + DirectXTex + Win32Proj + $(VCTargetsPath11) + en-US + 12.0 + true + Windows Store + 8.1 + + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + StaticLibrary + Unicode + v120 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Bin\Windows81\$(Platform)\$(Configuration)\ + Bin\Windows81\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Windows81\$(Platform)\$(Configuration)\ + Bin\Windows81\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Windows81\$(Platform)\$(Configuration)\ + Bin\Windows81\$(Platform)\$(Configuration)\ + DirectXTex + true + true + + + Bin\Windows81\$(Platform)\$(Configuration)\ + Bin\Windows81\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Windows81\$(Platform)\$(Configuration)\ + Bin\Windows81\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Windows81\$(Platform)\$(Configuration)\ + Bin\Windows81\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Windows81\$(Platform)\$(Configuration)\ + Bin\Windows81\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Windows81\$(Platform)\$(Configuration)\ + Bin\Windows81\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + Bin\Windows81\$(Platform)\$(Configuration)\ + Bin\Windows81\$(Platform)\$(Configuration)\ + DirectXTex + false + true + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;_DEBUG;_LIB;%(PreprocessorDefinitions) + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4628 + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + /IGNORE:4264 %(AdditionalOptions) + + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;_DEBUG;_LIB;%(PreprocessorDefinitions) + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4628 + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + /IGNORE:4264 %(AdditionalOptions) + + + + + EnableAllWarnings + Disabled + MultiThreadedDebugDLL + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;_DEBUG;_LIB;%(PreprocessorDefinitions) + EnableFastChecks + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4628 + + + %(AdditionalOptions) + %(AdditionalDependencies) + Windows + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + /IGNORE:4264 %(AdditionalOptions) + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;NDEBUG;_LIB;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4628 + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + /IGNORE:4264 %(AdditionalOptions) + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;NDEBUG;_LIB;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4628 + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + /IGNORE:4264 %(AdditionalOptions) + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;NDEBUG;_LIB;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4628 + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + /IGNORE:4264 %(AdditionalOptions) + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;NDEBUG;PROFILE;_LIB;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4628 + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + /IGNORE:4264 %(AdditionalOptions) + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;NDEBUG;PROFILE;_LIB;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4628 + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + /IGNORE:4264 %(AdditionalOptions) + + + + + EnableAllWarnings + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + %(AdditionalOptions) + _UNICODE;UNICODE;NDEBUG;PROFILE;_LIB;%(PreprocessorDefinitions) + Use + DirectXTexP.h + $(IntDir)$(TargetName).pdb + 4628 + + + %(AdditionalOptions) + %(AdditionalDependencies) + true + Windows + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + /IGNORE:4264 %(AdditionalOptions) + + + + + Document + + + Document + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_Windows81.vcxproj.filters b/deps/DirectXTex/DirectXTex/DirectXTex_Windows81.vcxproj.filters new file mode 100644 index 0000000..db38ee6 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_Windows81.vcxproj.filters @@ -0,0 +1,163 @@ + + + + + {c99f7f80-93a7-4692-8567-779ebabe625b} + + + {586313f2-be7d-4c9c-aa53-09f565530df1} + + + {582e299d-9d25-4208-b5d3-c2eac13e3df0} + + + {e51b4bb7-ec1f-4a4c-8ca7-0da6ceb16465} + + + {53dd160e-d654-4210-ad80-ba533a55a740} + + + + + Header Files + + + Header Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files + + + Source Files + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_WindowsPhone81.vcxproj b/deps/DirectXTex/DirectXTex/DirectXTex_WindowsPhone81.vcxproj new file mode 100644 index 0000000..cabc65b --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_WindowsPhone81.vcxproj @@ -0,0 +1,220 @@ + + + + + Debug + Win32 + + + Release + Win32 + + + Debug + ARM + + + Release + ARM + + + + {5709aa1f-d4e3-4138-bdd6-55c8daf3d983} + Win32Proj + DirectXTex + DirectXTex + en-US + 12.0 + true + Windows Phone + 8.1 + + + + StaticLibrary + true + v120_wp81 + + + StaticLibrary + false + v120_wp81 + + + StaticLibrary + true + v120_wp81 + + + StaticLibrary + false + v120_wp81 + + + + + + + + + + + + + + + + + + Bin\WindowsPhone81\$(Platform)\$(Configuration)\ + Bin\WindowsPhone81\$(Platform)\$(Configuration)\ + DirectXTex + + + Bin\WindowsPhone81\$(Platform)\$(Configuration)\ + Bin\WindowsPhone81\$(Platform)\$(Configuration)\ + DirectXTex + + + Bin\WindowsPhone81\$(Platform)\$(Configuration)\ + Bin\WindowsPhone81\$(Platform)\$(Configuration)\ + DirectXTex + + + Bin\WindowsPhone81\$(Platform)\$(Configuration)\ + Bin\WindowsPhone81\$(Platform)\$(Configuration)\ + DirectXTex + + + + Use + false + true + DirectXTexP.h + $(IntDir)$(TargetName).pdb + Fast + StreamingSIMDExtensions2 + EnableAllWarnings + + + Console + false + false + + + + + Use + false + true + DirectXTexP.h + $(IntDir)$(TargetName).pdb + Fast + StreamingSIMDExtensions2 + EnableAllWarnings + + + Console + false + false + + + + + Use + false + true + DirectXTexP.h + $(IntDir)$(TargetName).pdb + Fast + EnableAllWarnings + + + Console + false + false + + + + + Use + false + true + DirectXTexP.h + $(IntDir)$(TargetName).pdb + Fast + EnableAllWarnings + + + Console + false + false + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + + + + + + Document + + + Document + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_WindowsPhone81.vcxproj.filters b/deps/DirectXTex/DirectXTex/DirectXTex_WindowsPhone81.vcxproj.filters new file mode 100644 index 0000000..c232e02 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_WindowsPhone81.vcxproj.filters @@ -0,0 +1,161 @@ + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Header Files + + + Header Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + {ae44e5d8-5e05-47c8-92f5-0d6464fff56b} + + + {dc9e6b8b-d350-4f63-895f-790dbd53c33e} + + + {226c7e42-76b6-499d-a4f6-df6ca1643037} + + + {4e237727-0b49-48ae-aae4-2b525ec1e124} + + + {67066457-5e0a-49d3-893a-0ae08a4c0ed5} + + + + + Source Files\Shaders + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2015.vcxproj b/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2015.vcxproj new file mode 100644 index 0000000..0cd492b --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2015.vcxproj @@ -0,0 +1,233 @@ + + + + + Release + Durango + + + Profile + Durango + + + Debug + Durango + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + + + + + + Document + + + Document + + + + DirectXTex + {879b5023-53b7-4108-aeae-f019c2e9410d} + en-US + Win32Proj + title + + v140 + 14.0 + Native + + + + StaticLibrary + v140 + false + Unicode + false + false + + + StaticLibrary + v140 + false + Unicode + false + false + + + StaticLibrary + v140 + true + Unicode + false + false + + + + + + + + + + + + + + + + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkLibPath) + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkIncludeRoot) + $(Console_SdkRoot)bin;$(VCInstallDir)bin\x86_amd64;$(VCInstallDir)bin;$(WindowsSDK_ExecutablePath_x86);$(VSInstallDir)Common7\Tools\bin;$(VSInstallDir)Common7\tools;$(VSInstallDir)Common7\ide;$(ProgramFiles)\HTML Help Workshop;$(MSBuildToolsPath32);$(FxCopDir);$(PATH); + Bin\XboxOneXDK_2015\$(Platform)\$(Configuration)\ + Bin\XboxOneXDK_2015\$(Platform)\$(Configuration)\ + DirectXTex + + + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkLibPath) + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkIncludeRoot) + $(Console_SdkRoot)bin;$(VCInstallDir)bin\x86_amd64;$(VCInstallDir)bin;$(WindowsSDK_ExecutablePath_x86);$(VSInstallDir)Common7\Tools\bin;$(VSInstallDir)Common7\tools;$(VSInstallDir)Common7\ide;$(ProgramFiles)\HTML Help Workshop;$(MSBuildToolsPath32);$(FxCopDir);$(PATH); + Bin\XboxOneXDK_2015\$(Platform)\$(Configuration)\ + Bin\XboxOneXDK_2015\$(Platform)\$(Configuration)\ + DirectXTex + + + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkLibPath) + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkIncludeRoot) + $(Console_SdkRoot)bin;$(VCInstallDir)bin\x86_amd64;$(VCInstallDir)bin;$(WindowsSDK_ExecutablePath_x86);$(VSInstallDir)Common7\Tools\bin;$(VSInstallDir)Common7\tools;$(VSInstallDir)Common7\ide;$(ProgramFiles)\HTML Help Workshop;$(MSBuildToolsPath32);$(FxCopDir);$(PATH); + Bin\XboxOneXDK_2015\$(Platform)\$(Configuration)\ + Bin\XboxOneXDK_2015\$(Platform)\$(Configuration)\ + DirectXTex + + + + d3d11_x.lib;combase.lib;kernelx.lib;toolhelpx.lib;uuid.lib; + + + true + Windows + true + true + false + + + Use + DirectXTexP.h + $(Console_SdkPackagesRoot);$(Console_SdkWindowsMetadataPath);%(AdditionalUsingDirectories) + MaxSpeed + NDEBUG;__WRL_NO_DEFAULT_LIB__;_LIB;%(PreprocessorDefinitions) + EnableAllWarnings + true + true + false + $(IntDir)$(TargetName).pdb + + + + + pixEvt.lib;d3d11_x.lib;combase.lib;kernelx.lib;toolhelpx.lib;uuid.lib; + + + true + Windows + true + true + false + + + Use + DirectXTexP.h + $(Console_SdkPackagesRoot);$(Console_SdkWindowsMetadataPath);%(AdditionalUsingDirectories) + MaxSpeed + NDEBUG;__WRL_NO_DEFAULT_LIB__;_LIB;PROFILE;%(PreprocessorDefinitions) + EnableAllWarnings + true + true + false + $(IntDir)$(TargetName).pdb + + + + + d3d11_x.lib;combase.lib;kernelx.lib;toolhelpx.lib;uuid.lib; + Windows + true + false + + + DirectXTexP.h + Use + false + $(Console_SdkPackagesRoot);$(Console_SdkWindowsMetadataPath);%(AdditionalUsingDirectories) + EnableAllWarnings + Disabled + _DEBUG;__WRL_NO_DEFAULT_LIB__;_LIB;%(PreprocessorDefinitions) + false + $(IntDir)$(TargetName).pdb + + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2015.vcxproj.filters b/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2015.vcxproj.filters new file mode 100644 index 0000000..c06b901 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2015.vcxproj.filters @@ -0,0 +1,166 @@ + + + + + {4FC737F1-C7A5-4376-A066-2A32D752A2FF} + cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx + + + {93995380-89BD-4b04-88EB-625FBE52EBFB} + h;hpp;hxx;hm;inl;inc;xsd + + + {c60baf7a-25a9-4215-842d-8d49d65d538e} + + + {c4ad5fdf-0988-4c92-9558-0cd1f3bdb13d} + + + {367c58a1-fc2c-45ca-b564-e7cf8daa85f1} + + + + + Header Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Header Files + + + Source Files\Shaders + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2017.vcxproj b/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2017.vcxproj new file mode 100644 index 0000000..0a021d3 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2017.vcxproj @@ -0,0 +1,231 @@ + + + + + Release + Durango + + + Profile + Durango + + + Debug + Durango + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + + + + + + Document + + + Document + + + + DirectXTex + {879b5023-53b7-4108-aeae-f019c2e9410d} + en-US + Win32Proj + title + + v141 + 14.0 + Native + + + + StaticLibrary + v141 + false + Unicode + false + false + + + StaticLibrary + v141 + false + Unicode + false + false + + + StaticLibrary + v141 + true + Unicode + false + false + + + + + + + + + + + + + + + + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkLibPath) + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkIncludeRoot) + $(Console_SdkRoot)bin;$(VCInstallDir)bin\x86_amd64;$(VCInstallDir)bin;$(WindowsSDK_ExecutablePath_x86);$(VSInstallDir)Common7\Tools\bin;$(VSInstallDir)Common7\tools;$(VSInstallDir)Common7\ide;$(ProgramFiles)\HTML Help Workshop;$(MSBuildToolsPath32);$(FxCopDir);$(PATH); + Bin\XboxOneXDK_2017\$(Platform)\$(Configuration)\ + Bin\XboxOneXDK_2017\$(Platform)\$(Configuration)\ + DirectXTex + + + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkLibPath) + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkIncludeRoot) + $(Console_SdkRoot)bin;$(VCInstallDir)bin\x86_amd64;$(VCInstallDir)bin;$(WindowsSDK_ExecutablePath_x86);$(VSInstallDir)Common7\Tools\bin;$(VSInstallDir)Common7\tools;$(VSInstallDir)Common7\ide;$(ProgramFiles)\HTML Help Workshop;$(MSBuildToolsPath32);$(FxCopDir);$(PATH); + Bin\XboxOneXDK_2017\$(Platform)\$(Configuration)\ + Bin\XboxOneXDK_2017\$(Platform)\$(Configuration)\ + DirectXTex + + + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkLibPath) + $(Console_SdkLibPath);$(Console_SdkWindowsMetadataPath) + $(Console_SdkIncludeRoot) + $(Console_SdkRoot)bin;$(VCInstallDir)bin\x86_amd64;$(VCInstallDir)bin;$(WindowsSDK_ExecutablePath_x86);$(VSInstallDir)Common7\Tools\bin;$(VSInstallDir)Common7\tools;$(VSInstallDir)Common7\ide;$(ProgramFiles)\HTML Help Workshop;$(MSBuildToolsPath32);$(FxCopDir);$(PATH); + Bin\XboxOneXDK_2017\$(Platform)\$(Configuration)\ + Bin\XboxOneXDK_2017\$(Platform)\$(Configuration)\ + DirectXTex + + + + d3d11_x.lib;combase.lib;kernelx.lib;toolhelpx.lib;uuid.lib; + + + true + Windows + true + true + false + + + Use + DirectXTexP.h + $(Console_SdkPackagesRoot);$(Console_SdkWindowsMetadataPath);%(AdditionalUsingDirectories) + MaxSpeed + NDEBUG;__WRL_NO_DEFAULT_LIB__;_LIB;%(PreprocessorDefinitions) + EnableAllWarnings + true + true + false + $(IntDir)$(TargetName).pdb + + + + + pixEvt.lib;d3d11_x.lib;combase.lib;kernelx.lib;toolhelpx.lib;uuid.lib; + + + true + Windows + true + true + false + + + Use + DirectXTexP.h + $(Console_SdkPackagesRoot);$(Console_SdkWindowsMetadataPath);%(AdditionalUsingDirectories) + MaxSpeed + NDEBUG;__WRL_NO_DEFAULT_LIB__;_LIB;PROFILE;%(PreprocessorDefinitions) + EnableAllWarnings + true + true + false + $(IntDir)$(TargetName).pdb + + + + + d3d11_x.lib;combase.lib;kernelx.lib;toolhelpx.lib;uuid.lib; + Windows + true + false + + + DirectXTexP.h + Use + false + $(Console_SdkPackagesRoot);$(Console_SdkWindowsMetadataPath);%(AdditionalUsingDirectories) + EnableAllWarnings + Disabled + _DEBUG;__WRL_NO_DEFAULT_LIB__;_LIB;%(PreprocessorDefinitions) + false + $(IntDir)$(TargetName).pdb + + + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2017.vcxproj.filters b/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2017.vcxproj.filters new file mode 100644 index 0000000..c06b901 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/DirectXTex_XboxOneXDK_2017.vcxproj.filters @@ -0,0 +1,166 @@ + + + + + {4FC737F1-C7A5-4376-A066-2A32D752A2FF} + cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx + + + {93995380-89BD-4b04-88EB-625FBE52EBFB} + h;hpp;hxx;hm;inl;inc;xsd + + + {c60baf7a-25a9-4215-842d-8d49d65d538e} + + + {c4ad5fdf-0988-4c92-9558-0cd1f3bdb13d} + + + {367c58a1-fc2c-45ca-b564-e7cf8daa85f1} + + + + + Header Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Header Files + + + Source Files\Shaders + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders\Compiled + + + Source Files\Shaders + + + Source Files\Shaders + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + Source Files\Shaders\Symbols + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/Filters.h b/deps/DirectXTex/DirectXTex/Filters.h new file mode 100644 index 0000000..582c48c --- /dev/null +++ b/deps/DirectXTex/DirectXTex/Filters.h @@ -0,0 +1,423 @@ +//------------------------------------------------------------------------------------- +// filters.h +// +// Utility header with helpers for implementing image filters +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +//------------------------------------------------------------------------------------- + +#pragma once + +#include +#include + +#include + +#include "scoped.h" + +namespace DirectX +{ + +//------------------------------------------------------------------------------------- +// Box filtering helpers +//------------------------------------------------------------------------------------- + +XMGLOBALCONST XMVECTORF32 g_boxScale = { { { 0.25f, 0.25f, 0.25f, 0.25f } } }; +XMGLOBALCONST XMVECTORF32 g_boxScale3D = { { { 0.125f, 0.125f, 0.125f, 0.125f } } }; + +#define AVERAGE4( res, p0, p1, p2, p3 ) \ +{ \ + XMVECTOR v = XMVectorAdd( (p0), (p1) ); \ + v = XMVectorAdd( v, (p2) ); \ + v = XMVectorAdd( v, (p3) ); \ + res = XMVectorMultiply( v, g_boxScale ); \ +} + +#define AVERAGE8( res, p0, p1, p2, p3, p4, p5, p6, p7) \ +{ \ + XMVECTOR v = XMVectorAdd( (p0), (p1) ); \ + v = XMVectorAdd( v, (p2) ); \ + v = XMVectorAdd( v, (p3) ); \ + v = XMVectorAdd( v, (p4) ); \ + v = XMVectorAdd( v, (p5) ); \ + v = XMVectorAdd( v, (p6) ); \ + v = XMVectorAdd( v, (p7) ); \ + res = XMVectorMultiply( v, g_boxScale3D ); \ +} + + +//------------------------------------------------------------------------------------- +// Linear filtering helpers +//------------------------------------------------------------------------------------- + +struct LinearFilter +{ + size_t u0; + float weight0; + size_t u1; + float weight1; +}; + +inline void _CreateLinearFilter(_In_ size_t source, _In_ size_t dest, _In_ bool wrap, _Out_writes_(dest) LinearFilter* lf) +{ + assert(source > 0); + assert(dest > 0); + assert(lf != 0); + + float scale = float(source) / float(dest); + + // Mirror is the same case as clamp for linear + + for (size_t u = 0; u < dest; ++u) + { + float srcB = (float(u) + 0.5f) * scale + 0.5f; + + ptrdiff_t isrcB = ptrdiff_t(srcB); + ptrdiff_t isrcA = isrcB - 1; + + if (isrcA < 0) + { + isrcA = (wrap) ? (source - 1) : 0; + } + + if (size_t(isrcB) >= source) + { + isrcB = (wrap) ? 0 : (source - 1); + } + + float weight = 1.0f + float(isrcB) - srcB; + + auto& entry = lf[u]; + entry.u0 = size_t(isrcA); + entry.weight0 = weight; + + entry.u1 = size_t(isrcB); + entry.weight1 = 1.0f - weight; + } +} + +#define BILINEAR_INTERPOLATE( res, x, y, r0, r1 ) \ + res = ( y.weight0 * ( (r0)[ x.u0 ] * x.weight0 + (r0)[ x.u1 ] * x.weight1 ) ) \ + + ( y.weight1 * ( (r1)[ x.u0 ] * x.weight0 + (r1)[ x.u1 ] * x.weight1 ) ) + +#define TRILINEAR_INTERPOLATE( res, x, y, z, r0, r1, r2, r3 ) \ + res = ( z.weight0 * ( ( y.weight0 * ( (r0)[ x.u0 ] * x.weight0 + (r0)[ x.u1 ] * x.weight1 ) ) \ + + ( y.weight1 * ( (r1)[ x.u0 ] * x.weight0 + (r1)[ x.u1 ] * x.weight1 ) ) ) ) \ + + ( z.weight1 * ( ( y.weight0 * ( (r2)[ x.u0 ] * x.weight0 + (r2)[ x.u1 ] * x.weight1 ) ) \ + + ( y.weight1 * ( (r3)[ x.u0 ] * x.weight0 + (r3)[ x.u1 ] * x.weight1 ) ) ) ) + + +//------------------------------------------------------------------------------------- +// Cubic filtering helpers +//------------------------------------------------------------------------------------- + +XMGLOBALCONST XMVECTORF32 g_cubicThird = { { { 1.f / 3.f, 1.f / 3.f, 1.f / 3.f, 1.f / 3.f } } }; +XMGLOBALCONST XMVECTORF32 g_cubicSixth = { { { 1.f / 6.f, 1.f / 6.f, 1.f / 6.f, 1.f / 6.f } } }; +XMGLOBALCONST XMVECTORF32 g_cubicHalf = { { { 1.f / 2.f, 1.f / 2.f, 1.f / 2.f, 1.f / 2.f } } }; + +inline ptrdiff_t bounduvw(ptrdiff_t u, ptrdiff_t maxu, bool wrap, bool mirror) +{ + if (wrap) + { + if (u < 0) + { + u = maxu + u + 1; + } + else if (u > maxu) + { + u = u - maxu - 1; + } + } + else if (mirror) + { + if (u < 0) + { + u = (-u) - 1; + } + else if (u > maxu) + { + u = maxu - (u - maxu - 1); + } + } + + // Handles clamp, but also a safety factor for degenerate images for wrap/mirror + u = std::min(u, maxu); + u = std::max(u, 0); + + return u; +} + +struct CubicFilter +{ + size_t u0; + size_t u1; + size_t u2; + size_t u3; + float x; +}; + +inline void _CreateCubicFilter(_In_ size_t source, _In_ size_t dest, _In_ bool wrap, _In_ bool mirror, _Out_writes_(dest) CubicFilter* cf) +{ + assert(source > 0); + assert(dest > 0); + assert(cf != 0); + + float scale = float(source) / float(dest); + + for (size_t u = 0; u < dest; ++u) + { + float srcB = (float(u) + 0.5f) * scale - 0.5f; + + ptrdiff_t isrcB = bounduvw(ptrdiff_t(srcB), source - 1, wrap, mirror); + ptrdiff_t isrcA = bounduvw(isrcB - 1, source - 1, wrap, mirror); + ptrdiff_t isrcC = bounduvw(isrcB + 1, source - 1, wrap, mirror); + ptrdiff_t isrcD = bounduvw(isrcB + 2, source - 1, wrap, mirror); + + auto& entry = cf[u]; + entry.u0 = size_t(isrcA); + entry.u1 = size_t(isrcB); + entry.u2 = size_t(isrcC); + entry.u3 = size_t(isrcD); + + float x = srcB - float(isrcB); + entry.x = x; + } +} + +#define CUBIC_INTERPOLATE( res, dx, p0, p1, p2, p3 ) \ +{ \ + XMVECTOR a0 = (p1); \ + XMVECTOR d0 = (p0) - a0; \ + XMVECTOR d2 = (p2) - a0; \ + XMVECTOR d3 = (p3) - a0; \ + XMVECTOR a1 = d2 - g_cubicThird*d0 - g_cubicSixth*d3; \ + XMVECTOR a2 = g_cubicHalf*d0 + g_cubicHalf*d2; \ + XMVECTOR a3 = g_cubicSixth*d3 - g_cubicSixth*d0 - g_cubicHalf*d2; \ + XMVECTOR vdx = XMVectorReplicate( dx ); \ + XMVECTOR vdx2 = vdx * vdx; \ + XMVECTOR vdx3 = vdx2 * vdx; \ + res = a0 + a1*vdx + a2*vdx2 + a3*vdx3; \ +} + + +//------------------------------------------------------------------------------------- +// Triangle filtering helpers +//------------------------------------------------------------------------------------- + +namespace TriangleFilter +{ + struct FilterTo + { + size_t u; + float weight; + }; + + struct FilterFrom + { + size_t count; + size_t sizeInBytes; + FilterTo to[1]; // variable-sized array + }; + + struct Filter + { + size_t sizeInBytes; + size_t totalSize; + FilterFrom from[1]; // variable-sized array + }; + + struct TriangleRow + { + size_t remaining; + TriangleRow* next; + ScopedAlignedArrayXMVECTOR scanline; + + TriangleRow() : remaining(0), next(nullptr) {} + }; + + static const size_t TF_FILTER_SIZE = sizeof(Filter) - sizeof(FilterFrom); + static const size_t TF_FROM_SIZE = sizeof(FilterFrom) - sizeof(FilterTo); + static const size_t TF_TO_SIZE = sizeof(FilterTo); + + static const float TF_EPSILON = 0.00001f; + + inline HRESULT _Create(_In_ size_t source, _In_ size_t dest, _In_ bool wrap, _Inout_ std::unique_ptr& tf) + { + assert(source > 0); + assert(dest > 0); + + float scale = float(dest) / float(source); + float scaleInv = 0.5f / scale; + + // Determine storage required for filter and allocate memory if needed + size_t totalSize = TF_FILTER_SIZE + TF_FROM_SIZE + TF_TO_SIZE; + float repeat = (wrap) ? 1.f : 0.f; + + for (size_t u = 0; u < source; ++u) + { + float src = float(u) - 0.5f; + float destMin = src * scale; + float destMax = destMin + scale; + + totalSize += TF_FROM_SIZE + TF_TO_SIZE + size_t(destMax - destMin + repeat + 1.f) * TF_TO_SIZE * 2; + } + + uint8_t* pFilter = nullptr; + + if (tf) + { + // See if existing filter memory block is large enough to reuse + if (tf->totalSize >= totalSize) + { + pFilter = reinterpret_cast(tf.get()); + } + else + { + // Need to reallocate filter memory block + tf.reset(nullptr); + } + } + + if (!tf) + { + // Allocate filter memory block + pFilter = new (std::nothrow) uint8_t[totalSize]; + if (!pFilter) + return E_OUTOFMEMORY; + + tf.reset(reinterpret_cast(pFilter)); + tf->totalSize = totalSize; + } + + assert(pFilter != 0); + _Analysis_assume_(pFilter != 0); + + // Filter setup + size_t sizeInBytes = TF_FILTER_SIZE; + size_t accumU = 0; + float accumWeight = 0.f; + + for (size_t u = 0; u < source; ++u) + { + // Setup from entry + size_t sizeFrom = sizeInBytes; + auto pFrom = reinterpret_cast(pFilter + sizeInBytes); + sizeInBytes += TF_FROM_SIZE; + + if (sizeInBytes > totalSize) + return E_FAIL; + + size_t toCount = 0; + + // Perform two passes to capture the influences from both sides + for (size_t j = 0; j < 2; ++j) + { + float src = float(u + j) - 0.5f; + + float destMin = src * scale; + float destMax = destMin + scale; + + if (!wrap) + { + // Clamp + if (destMin < 0.f) + destMin = 0.f; + if (destMax > float(dest)) + destMax = float(dest); + } + + for (auto k = static_cast(floorf(destMin)); float(k) < destMax; ++k) + { + float d0 = float(k); + float d1 = d0 + 1.f; + + size_t u0; + if (k < 0) + { + // Handle wrap + u0 = size_t(k + ptrdiff_t(dest)); + } + else if (k >= ptrdiff_t(dest)) + { + // Handle wrap + u0 = size_t(k - ptrdiff_t(dest)); + } + else + { + u0 = size_t(k); + } + + // Save previous accumulated weight (if any) + if (u0 != accumU) + { + if (accumWeight > TF_EPSILON) + { + auto pTo = reinterpret_cast(pFilter + sizeInBytes); + sizeInBytes += TF_TO_SIZE; + ++toCount; + + if (sizeInBytes > totalSize) + return E_FAIL; + + pTo->u = accumU; + pTo->weight = accumWeight; + } + + accumWeight = 0.f; + accumU = u0; + } + + // Clip destination + if (d0 < destMin) + d0 = destMin; + if (d1 > destMax) + d1 = destMax; + + // Calculate average weight over destination pixel + + float weight; + if (!wrap && src < 0.f) + weight = 1.f; + else if (!wrap && ((src + 1.f) >= float(source))) + weight = 0.f; + else + weight = (d0 + d1) * scaleInv - src; + + accumWeight += (d1 - d0) * (j ? (1.f - weight) : weight); + } + } + + // Store accumulated weight + if (accumWeight > TF_EPSILON) + { + auto pTo = reinterpret_cast(pFilter + sizeInBytes); + sizeInBytes += TF_TO_SIZE; + ++toCount; + + if (sizeInBytes > totalSize) + return E_FAIL; + + pTo->u = accumU; + pTo->weight = accumWeight; + } + + accumWeight = 0.f; + + // Finalize from entry + pFrom->count = toCount; + pFrom->sizeInBytes = sizeInBytes - sizeFrom; + } + + tf->sizeInBytes = sizeInBytes; + + return S_OK; + } + +}; // namespace TriangleFilter + +}; // namespace DirectX \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/Shaders/BC6HEncode.hlsl b/deps/DirectXTex/DirectXTex/Shaders/BC6HEncode.hlsl new file mode 100644 index 0000000..227796e --- /dev/null +++ b/deps/DirectXTex/DirectXTex/Shaders/BC6HEncode.hlsl @@ -0,0 +1,2566 @@ +//-------------------------------------------------------------------------------------- +// File: BC6HEncode.hlsl +// +// The Compute Shader for BC6H Encoder +// +// Copyright (c) Microsoft Corporation. All rights reserved. +//-------------------------------------------------------------------------------------- + +#define REF_DEVICE + +#define UINTLENGTH 32 +#define NCHANNELS 3 +#define SIGNED_F16 96 +#define UNSIGNED_F16 95 +#define MAX_FLOAT asfloat(0x7F7FFFFF) +#define MIN_FLOAT asfloat(0xFF7FFFFF) +#define MAX_INT asint(0x7FFFFFFF) +#define MIN_INT asint(0x80000000) + +cbuffer cbCS : register( b0 ) +{ + uint g_tex_width; + uint g_num_block_x; + uint g_format; //either SIGNED_F16 for DXGI_FORMAT_BC6H_SF16 or UNSIGNED_F16 for DXGI_FORMAT_BC6H_UF16 + uint g_mode_id; + uint g_start_block_id; + uint g_num_total_blocks; +}; + +static const uint candidateModeMemory[14] = { 0x00, 0x01, 0x02, 0x06, 0x0A, 0x0E, 0x12, 0x16, 0x1A, 0x1E, 0x03, 0x07, 0x0B, 0x0F }; +static const uint candidateModeFlag[14] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14 }; +static const bool candidateModeTransformed[14] = { true, true, true, true, true, true, true, true, true, false, false, true, true, true }; +static const uint4 candidateModePrec[14] = { uint4(10,5,5,5), uint4(7,6,6,6), + uint4(11,5,4,4), uint4(11,4,5,4), uint4(11,4,4,5), uint4(9,5,5,5), + uint4(8,6,5,5), uint4(8,5,6,5), uint4(8,5,5,6), uint4(6,6,6,6), + uint4(10,10,10,10), uint4(11,9,9,9), uint4(12,8,8,8), uint4(16,4,4,4) }; + +/*static const uint4x4 candidateSection[32] = +{ + {0,0,1,1, 0,0,1,1, 0,0,1,1, 0,0,1,1}, {0,0,0,1, 0,0,0,1, 0,0,0,1, 0,0,0,1}, {0,1,1,1, 0,1,1,1, 0,1,1,1, 0,1,1,1}, {0,0,0,1, 0,0,1,1, 0,0,1,1, 0,1,1,1}, + {0,0,0,0, 0,0,0,1, 0,0,0,1, 0,0,1,1}, {0,0,1,1, 0,1,1,1, 0,1,1,1, 1,1,1,1}, {0,0,0,1, 0,0,1,1, 0,1,1,1, 1,1,1,1}, {0,0,0,0, 0,0,0,1, 0,0,1,1, 0,1,1,1}, + {0,0,0,0, 0,0,0,0, 0,0,0,1, 0,0,1,1}, {0,0,1,1, 0,1,1,1, 1,1,1,1, 1,1,1,1}, {0,0,0,0, 0,0,0,1, 0,1,1,1, 1,1,1,1}, {0,0,0,0, 0,0,0,0, 0,0,0,1, 0,1,1,1}, + {0,0,0,1, 0,1,1,1, 1,1,1,1, 1,1,1,1}, {0,0,0,0, 0,0,0,0, 1,1,1,1, 1,1,1,1}, {0,0,0,0, 1,1,1,1, 1,1,1,1, 1,1,1,1}, {0,0,0,0, 0,0,0,0, 0,0,0,0, 1,1,1,1}, + {0,0,0,0, 1,0,0,0, 1,1,1,0, 1,1,1,1}, {0,1,1,1, 0,0,0,1, 0,0,0,0, 0,0,0,0}, {0,0,0,0, 0,0,0,0, 1,0,0,0, 1,1,1,0}, {0,1,1,1, 0,0,1,1, 0,0,0,1, 0,0,0,0}, + {0,0,1,1, 0,0,0,1, 0,0,0,0, 0,0,0,0}, {0,0,0,0, 1,0,0,0, 1,1,0,0, 1,1,1,0}, {0,0,0,0, 0,0,0,0, 1,0,0,0, 1,1,0,0}, {0,1,1,1, 0,0,1,1, 0,0,1,1, 0,0,0,1}, + {0,0,1,1, 0,0,0,1, 0,0,0,1, 0,0,0,0}, {0,0,0,0, 1,0,0,0, 1,0,0,0, 1,1,0,0}, {0,1,1,0, 0,1,1,0, 0,1,1,0, 0,1,1,0}, {0,0,1,1, 0,1,1,0, 0,1,1,0, 1,1,0,0}, + {0,0,0,1, 0,1,1,1, 1,1,1,0, 1,0,0,0}, {0,0,0,0, 1,1,1,1, 1,1,1,1, 0,0,0,0}, {0,1,1,1, 0,0,0,1, 1,0,0,0, 1,1,1,0}, {0,0,1,1, 1,0,0,1, 1,0,0,1, 1,1,0,0} +};*/ + +static const uint candidateSectionBit[32] = +{ + 0xCCCC, 0x8888, 0xEEEE, 0xECC8, + 0xC880, 0xFEEC, 0xFEC8, 0xEC80, + 0xC800, 0xFFEC, 0xFE80, 0xE800, + 0xFFE8, 0xFF00, 0xFFF0, 0xF000, + 0xF710, 0x008E, 0x7100, 0x08CE, + 0x008C, 0x7310, 0x3100, 0x8CCE, + 0x088C, 0x3110, 0x6666, 0x366C, + 0x17E8, 0x0FF0, 0x718E, 0x399C +}; + +static const uint candidateFixUpIndex1D[32] = +{ + 15,15,15,15, + 15,15,15,15, + 15,15,15,15, + 15,15,15,15, + 15, 2, 8, 2, + 2, 8, 8,15, + 2, 8, 2, 2, + 8, 8, 2, 2 +}; + +//0, 9, 18, 27, 37, 46, 55, 64 +static const uint aStep1[64] = {0,0,0,0,0,1,1,1, + 1,1,1,1,1,1,2,2, + 2,2,2,2,2,2,2,3, + 3,3,3,3,3,3,3,3, + 3,4,4,4,4,4,4,4, + 4,4,5,5,5,5,5,5, + 5,5,5,6,6,6,6,6, + 6,6,6,6,7,7,7,7}; + +//0, 4, 9, 13, 17, 21, 26, 30, 34, 38, 43, 47, 51, 55, 60, 64 +static const uint aStep2[64] = { 0, 0, 0, 1, 1, 1, 1, 2, + 2, 2, 2, 2, 3, 3, 3, 3, + 4, 4, 4, 4, 5, 5, 5, 5, + 6, 6, 6, 6, 6, 7, 7, 7, + 7, 8, 8, 8, 8, 9, 9, 9, + 9,10,10,10,10,10,11,11, + 11,11,12,12,12,12,13,13, + 13,13,14,14,14,14,15,15}; + +static const float3 RGB2LUM = float3(0.2126f, 0.7152f, 0.0722f); + +#define THREAD_GROUP_SIZE 64 +#define BLOCK_SIZE_Y 4 +#define BLOCK_SIZE_X 4 +#define BLOCK_SIZE (BLOCK_SIZE_Y * BLOCK_SIZE_X) + + +//Forward declaration +uint3 float2half( float3 pixel_f ); +int3 start_quantize( uint3 pixel_h ); +void quantize( inout int2x3 endPoint, uint prec ); +void finish_quantize_0( inout int bBadQuantize, inout int2x3 endPoint, uint4 prec, bool transformed ); +void finish_quantize_1( inout int bBadQuantize, inout int2x3 endPoint, uint4 prec, bool transformed ); +void finish_quantize( out bool bBadQuantize, inout int2x3 endPoint, uint4 prec, bool transformed ); + +void start_unquantize( inout int2x3 endPoint[2], uint4 prec, bool transformed ); +void start_unquantize( inout int2x3 endPoint, uint4 prec, bool transformed ); +void unquantize( inout int2x3 color, uint prec ); +uint3 finish_unquantize( int3 color ); +void generate_palette_unquantized8( out uint3 palette, int3 low, int3 high, int i ); +void generate_palette_unquantized16( out uint3 palette, int3 low, int3 high, int i ); +float3 half2float(uint3 color_h ); + +void block_package( inout uint4 block, int2x3 endPoint[2], uint mode_type, uint partition_index ); +void block_package( inout uint4 block, int2x3 endPoint, uint mode_type ); + +void swap(inout int3 lhs, inout int3 rhs) +{ + int3 tmp = lhs; + lhs = rhs; + rhs = tmp; +} + +Texture2D g_Input : register( t0 ); +StructuredBuffer g_InBuff : register( t1 ); + +RWStructuredBuffer g_OutBuff : register( u0 ); + +struct SharedData +{ + float3 pixel; + int3 pixel_ph; + float3 pixel_hr; + float pixel_lum; + float error; + uint best_mode; + uint best_partition; + int3 endPoint_low; + int3 endPoint_high; + float endPoint_lum_low; + float endPoint_lum_high; +}; + +groupshared SharedData shared_temp[THREAD_GROUP_SIZE]; + +[numthreads( THREAD_GROUP_SIZE, 1, 1 )] +void TryModeG10CS( uint GI : SV_GroupIndex, uint3 groupID : SV_GroupID ) +{ + const uint MAX_USED_THREAD = 16; + uint BLOCK_IN_GROUP = THREAD_GROUP_SIZE / MAX_USED_THREAD; + uint blockInGroup = GI / MAX_USED_THREAD; + uint blockID = g_start_block_id + groupID.x * BLOCK_IN_GROUP + blockInGroup; + uint threadBase = blockInGroup * MAX_USED_THREAD; + uint threadInBlock = GI - threadBase; + +#ifndef REF_DEVICE + if (blockID >= g_num_total_blocks) + { + return; + } +#endif + + uint block_y = blockID / g_num_block_x; + uint block_x = blockID - block_y * g_num_block_x; + uint base_x = block_x * BLOCK_SIZE_X; + uint base_y = block_y * BLOCK_SIZE_Y; + + if (threadInBlock < 16) + { + shared_temp[GI].pixel = g_Input.Load( uint3( base_x + threadInBlock % 4, base_y + threadInBlock / 4, 0 ) ).rgb; + uint3 pixel_h = float2half( shared_temp[GI].pixel ); + shared_temp[GI].pixel_hr = half2float(pixel_h); + shared_temp[GI].pixel_lum = dot(shared_temp[GI].pixel_hr, RGB2LUM); + shared_temp[GI].pixel_ph = start_quantize( pixel_h ); + + shared_temp[GI].endPoint_low = shared_temp[GI].pixel_ph; + shared_temp[GI].endPoint_high = shared_temp[GI].pixel_ph; + shared_temp[GI].endPoint_lum_low = shared_temp[GI].pixel_lum; + shared_temp[GI].endPoint_lum_high = shared_temp[GI].pixel_lum; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (threadInBlock < 8) + { + if (shared_temp[GI].endPoint_lum_low > shared_temp[GI + 8].endPoint_lum_low) + { + shared_temp[GI].endPoint_low = shared_temp[GI + 8].endPoint_low; + shared_temp[GI].endPoint_lum_low = shared_temp[GI + 8].endPoint_lum_low; + } + if (shared_temp[GI].endPoint_lum_high < shared_temp[GI + 8].endPoint_lum_high) + { + shared_temp[GI].endPoint_high = shared_temp[GI + 8].endPoint_high; + shared_temp[GI].endPoint_lum_high = shared_temp[GI + 8].endPoint_lum_high; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 4) + { + if (shared_temp[GI].endPoint_lum_low > shared_temp[GI + 4].endPoint_lum_low) + { + shared_temp[GI].endPoint_low = shared_temp[GI + 4].endPoint_low; + shared_temp[GI].endPoint_lum_low = shared_temp[GI + 4].endPoint_lum_low; + } + if (shared_temp[GI].endPoint_lum_high < shared_temp[GI + 4].endPoint_lum_high) + { + shared_temp[GI].endPoint_high = shared_temp[GI + 4].endPoint_high; + shared_temp[GI].endPoint_lum_high = shared_temp[GI + 4].endPoint_lum_high; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 2) + { + if (shared_temp[GI].endPoint_lum_low > shared_temp[GI + 2].endPoint_lum_low) + { + shared_temp[GI].endPoint_low = shared_temp[GI + 2].endPoint_low; + shared_temp[GI].endPoint_lum_low = shared_temp[GI + 2].endPoint_lum_low; + } + if (shared_temp[GI].endPoint_lum_high < shared_temp[GI + 2].endPoint_lum_high) + { + shared_temp[GI].endPoint_high = shared_temp[GI + 2].endPoint_high; + shared_temp[GI].endPoint_lum_high = shared_temp[GI + 2].endPoint_lum_high; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 1) + { + if (shared_temp[GI].endPoint_lum_low > shared_temp[GI + 1].endPoint_lum_low) + { + shared_temp[GI].endPoint_low = shared_temp[GI + 1].endPoint_low; + shared_temp[GI].endPoint_lum_low = shared_temp[GI + 1].endPoint_lum_low; + } + if (shared_temp[GI].endPoint_lum_high < shared_temp[GI + 1].endPoint_lum_high) + { + shared_temp[GI].endPoint_high = shared_temp[GI + 1].endPoint_high; + shared_temp[GI].endPoint_lum_high = shared_temp[GI + 1].endPoint_lum_high; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + //ergod mode_type 11:14 + if ( threadInBlock == 0 ) + { + int2x3 endPoint; + // find_axis + endPoint[0] = shared_temp[threadBase + 0].endPoint_low; + endPoint[1] = shared_temp[threadBase + 0].endPoint_high; + + //compute_index + float3 span = endPoint[1] - endPoint[0];// fixed a bug in v0.2 + float span_norm_sqr = dot( span, span );// fixed a bug in v0.2 + float dotProduct = dot( span, shared_temp[threadBase + 0].pixel_ph - endPoint[0] );// fixed a bug in v0.2 + if ( span_norm_sqr > 0 && dotProduct >= 0 && uint( dotProduct * 63.49999 / span_norm_sqr ) > 32 ) + { + swap(endPoint[0], endPoint[1]); + + shared_temp[GI].endPoint_low = endPoint[0]; + shared_temp[GI].endPoint_high = endPoint[1]; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (threadInBlock < 4) + { + int2x3 endPoint; + endPoint[0] = shared_temp[threadBase + 0].endPoint_low; + endPoint[1] = shared_temp[threadBase + 0].endPoint_high; + + float3 span = endPoint[1] - endPoint[0]; + float span_norm_sqr = dot( span, span ); + + uint4 prec = candidateModePrec[threadInBlock + 10]; + int2x3 endPoint_q = endPoint; + quantize( endPoint_q, prec.x ); + + bool transformed = candidateModeTransformed[threadInBlock + 10]; + if (transformed) + { + endPoint_q[1] -= endPoint_q[0]; + } + + bool bBadQuantize; + finish_quantize( bBadQuantize, endPoint_q, prec, transformed ); + + start_unquantize( endPoint_q, prec, transformed ); + + unquantize( endPoint_q, prec.x ); + + float error = 0; + [loop]for ( uint j = 0; j < 16; j ++ ) + { + float dotProduct = dot( span, shared_temp[threadBase + j].pixel_ph - endPoint[0] );// fixed a bug in v0.2 + uint index = ( span_norm_sqr <= 0 || dotProduct <= 0 ) ? 0 + : ( ( dotProduct < span_norm_sqr ) ? aStep2[ uint( dotProduct * 63.49999 / span_norm_sqr ) ] : aStep2[63] ); + + uint3 pixel_rh; + generate_palette_unquantized16( pixel_rh, endPoint_q[0], endPoint_q[1], index ); + float3 pixel_r = half2float( pixel_rh ); + pixel_r -= shared_temp[threadBase + j].pixel_hr; + error += dot(pixel_r, pixel_r); + } + if ( bBadQuantize ) + error = 1e20f; + + shared_temp[GI].error = error; + shared_temp[GI].best_mode = candidateModeFlag[threadInBlock + 10]; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (threadInBlock < 2) + { + if ( shared_temp[GI].error > shared_temp[GI + 2].error ) + { + shared_temp[GI].error = shared_temp[GI + 2].error; + shared_temp[GI].best_mode = shared_temp[GI + 2].best_mode; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 1) + { + if ( shared_temp[GI].error > shared_temp[GI + 1].error ) + { + shared_temp[GI].error = shared_temp[GI + 1].error; + shared_temp[GI].best_mode = shared_temp[GI + 1].best_mode; + } + + g_OutBuff[blockID] = uint4(asuint(shared_temp[GI].error), shared_temp[GI].best_mode, 0, 0); + } +} + +[numthreads( THREAD_GROUP_SIZE, 1, 1 )] +void TryModeLE10CS( uint GI : SV_GroupIndex, uint3 groupID : SV_GroupID ) +{ + const uint MAX_USED_THREAD = 32; + uint BLOCK_IN_GROUP = THREAD_GROUP_SIZE / MAX_USED_THREAD; + uint blockInGroup = GI / MAX_USED_THREAD; + uint blockID = g_start_block_id + groupID.x * BLOCK_IN_GROUP + blockInGroup; + uint threadBase = blockInGroup * MAX_USED_THREAD; + uint threadInBlock = GI - threadBase; + +#ifndef REF_DEVICE + if (blockID >= g_num_total_blocks) + { + return; + } + + if (asfloat(g_InBuff[blockID].x) < 1e-6f) + { + g_OutBuff[blockID] = g_InBuff[blockID]; + return; + } +#endif + + uint block_y = blockID / g_num_block_x; + uint block_x = blockID - block_y * g_num_block_x; + uint base_x = block_x * BLOCK_SIZE_X; + uint base_y = block_y * BLOCK_SIZE_Y; + + if (threadInBlock < 16) + { + shared_temp[GI].pixel = g_Input.Load( uint3( base_x + threadInBlock % 4, base_y + threadInBlock / 4, 0 ) ).rgb; + uint3 pixel_h = float2half( shared_temp[GI].pixel ); + shared_temp[GI].pixel_hr = half2float(pixel_h); + shared_temp[GI].pixel_lum = dot(shared_temp[GI].pixel_hr, RGB2LUM); + shared_temp[GI].pixel_ph = start_quantize( pixel_h ); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + //ergod mode_type 1:10 + if (threadInBlock < 32) + { + // find_axis + int2x3 endPoint[2]; + endPoint[0][0] = MAX_INT; + endPoint[0][1] = MIN_INT; + endPoint[1][0] = MAX_INT; + endPoint[1][1] = MIN_INT; + + float2 endPoint_lum[2]; + endPoint_lum[0][0] = MAX_FLOAT; + endPoint_lum[0][1] = MIN_FLOAT; + endPoint_lum[1][0] = MAX_FLOAT; + endPoint_lum[1][1] = MIN_FLOAT; + + uint bit = candidateSectionBit[threadInBlock]; + for ( uint i = 0; i < 16; i ++ ) + { + int3 pixel_ph = shared_temp[threadBase + i].pixel_ph; + float pixel_lum = shared_temp[threadBase + i].pixel_lum; + if ( (bit >> i) & 1 ) //It gets error when using "candidateSection" as "endPoint_ph" index + { + if (endPoint_lum[1][0] > pixel_lum) + { + endPoint[1][0] = pixel_ph; + endPoint_lum[1][0] = pixel_lum; + } + if (endPoint_lum[1][1] < pixel_lum) + { + endPoint[1][1] = pixel_ph; + endPoint_lum[1][1] = pixel_lum; + } + } + else + { + if (endPoint_lum[0][0] > pixel_lum) + { + endPoint[0][0] = pixel_ph; + endPoint_lum[0][0] = pixel_lum; + } + if (endPoint_lum[0][1] < pixel_lum) + { + endPoint[0][1] = pixel_ph; + endPoint_lum[0][1] = pixel_lum; + } + } + } + + //compute_index + float3 span[2];// fixed a bug in v0.2 + float span_norm_sqr[2];// fixed a bug in v0.2 + [unroll] + for (uint p = 0; p < 2; ++ p) + { + span[p] = endPoint[p][1] - endPoint[p][0]; + span_norm_sqr[p] = dot( span[p], span[p] ); + + float dotProduct = dot( span[p], shared_temp[threadBase + (0 == p ? 0 : candidateFixUpIndex1D[threadInBlock])].pixel_ph - endPoint[p][0] );// fixed a bug in v0.2 + if ( span_norm_sqr[p] > 0 && dotProduct >= 0 && uint( dotProduct * 63.49999 / span_norm_sqr[p] ) > 32 ) + { + span[p] = -span[p]; + swap(endPoint[p][0], endPoint[p][1]); + } + } + + uint4 prec = candidateModePrec[g_mode_id]; + int2x3 endPoint_q[2] = endPoint; + quantize( endPoint_q[0], prec.x ); + quantize( endPoint_q[1], prec.x ); + + bool transformed = candidateModeTransformed[g_mode_id]; + if (transformed) + { + endPoint_q[0][1] -= endPoint_q[0][0]; + endPoint_q[1][0] -= endPoint_q[0][0]; + endPoint_q[1][1] -= endPoint_q[0][0]; + } + + int bBadQuantize = 0; + finish_quantize_0( bBadQuantize, endPoint_q[0], prec, transformed ); + finish_quantize_1( bBadQuantize, endPoint_q[1], prec, transformed ); + + start_unquantize( endPoint_q, prec, transformed ); + + unquantize( endPoint_q[0], prec.x ); + unquantize( endPoint_q[1], prec.x ); + + float error = 0; + for ( uint j = 0; j < 16; j ++ ) + { + uint3 pixel_rh; + if ((bit >> j) & 1) + { + float dotProduct = dot( span[1], shared_temp[threadBase + j].pixel_ph - endPoint[1][0] );// fixed a bug in v0.2 + uint index = ( span_norm_sqr[1] <= 0 || dotProduct <= 0 ) ? 0 + : ( ( dotProduct < span_norm_sqr[1] ) ? aStep1[ uint( dotProduct * 63.49999 / span_norm_sqr[1] ) ] : aStep1[63] ); + generate_palette_unquantized8( pixel_rh, endPoint_q[1][0], endPoint_q[1][1], index ); + } + else + { + float dotProduct = dot( span[0], shared_temp[threadBase + j].pixel_ph - endPoint[0][0] );// fixed a bug in v0.2 + uint index = ( span_norm_sqr[0] <= 0 || dotProduct <= 0 ) ? 0 + : ( ( dotProduct < span_norm_sqr[0] ) ? aStep1[ uint( dotProduct * 63.49999 / span_norm_sqr[0] ) ] : aStep1[63] ); + generate_palette_unquantized8( pixel_rh, endPoint_q[0][0], endPoint_q[0][1], index ); + } + + float3 pixel_r = half2float( pixel_rh ); + pixel_r -= shared_temp[threadBase + j].pixel_hr; + error += dot(pixel_r, pixel_r); + } + if ( bBadQuantize ) + error = 1e20f; + + shared_temp[GI].error = error; + shared_temp[GI].best_mode = candidateModeFlag[g_mode_id]; + shared_temp[GI].best_partition = threadInBlock; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (threadInBlock < 16) + { + if ( shared_temp[GI].error > shared_temp[GI + 16].error ) + { + shared_temp[GI].error = shared_temp[GI + 16].error; + shared_temp[GI].best_mode = shared_temp[GI + 16].best_mode; + shared_temp[GI].best_partition = shared_temp[GI + 16].best_partition; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 8) + { + if ( shared_temp[GI].error > shared_temp[GI + 8].error ) + { + shared_temp[GI].error = shared_temp[GI + 8].error; + shared_temp[GI].best_mode = shared_temp[GI + 8].best_mode; + shared_temp[GI].best_partition = shared_temp[GI + 8].best_partition; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 4) + { + if ( shared_temp[GI].error > shared_temp[GI + 4].error ) + { + shared_temp[GI].error = shared_temp[GI + 4].error; + shared_temp[GI].best_mode = shared_temp[GI + 4].best_mode; + shared_temp[GI].best_partition = shared_temp[GI + 4].best_partition; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 2) + { + if ( shared_temp[GI].error > shared_temp[GI + 2].error ) + { + shared_temp[GI].error = shared_temp[GI + 2].error; + shared_temp[GI].best_mode = shared_temp[GI + 2].best_mode; + shared_temp[GI].best_partition = shared_temp[GI + 2].best_partition; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 1) + { + if ( shared_temp[GI].error > shared_temp[GI + 1].error ) + { + shared_temp[GI].error = shared_temp[GI + 1].error; + shared_temp[GI].best_mode = shared_temp[GI + 1].best_mode; + shared_temp[GI].best_partition = shared_temp[GI + 1].best_partition; + } + + if (asfloat(g_InBuff[blockID].x) > shared_temp[GI].error) + { + g_OutBuff[blockID] = uint4(asuint(shared_temp[GI].error), shared_temp[GI].best_mode, shared_temp[GI].best_partition, 0); + } + else + { + g_OutBuff[blockID] = g_InBuff[blockID]; + } + } +} + +[numthreads( THREAD_GROUP_SIZE, 1, 1 )] +void EncodeBlockCS(uint GI : SV_GroupIndex, uint3 groupID : SV_GroupID) +{ + const uint MAX_USED_THREAD = 32; + uint BLOCK_IN_GROUP = THREAD_GROUP_SIZE / MAX_USED_THREAD; + uint blockInGroup = GI / MAX_USED_THREAD; + uint blockID = g_start_block_id + groupID.x * BLOCK_IN_GROUP + blockInGroup; + uint threadBase = blockInGroup * MAX_USED_THREAD; + uint threadInBlock = GI - threadBase; + +#ifndef REF_DEVICE + if (blockID >= g_num_total_blocks) + { + return; + } +#endif + + uint block_y = blockID / g_num_block_x; + uint block_x = blockID - block_y * g_num_block_x; + uint base_x = block_x * BLOCK_SIZE_X; + uint base_y = block_y * BLOCK_SIZE_Y; + + if (threadInBlock < 16) + { + shared_temp[GI].pixel = g_Input.Load( uint3( base_x + threadInBlock % 4, base_y + threadInBlock / 4, 0 ) ).rgb; + shared_temp[GI].pixel_lum = dot(shared_temp[GI].pixel, RGB2LUM); + uint3 pixel_h = float2half( shared_temp[GI].pixel ); + shared_temp[GI].pixel_ph = start_quantize( pixel_h ); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + uint best_mode = g_InBuff[blockID].y; + uint best_partition = g_InBuff[blockID].z; + + uint4 block = 0; + + if (threadInBlock < 32) + { + int2x3 endPoint; + endPoint[0] = MAX_INT; + endPoint[1] = MIN_INT; + + float2 endPoint_lum; + endPoint_lum[0] = MAX_FLOAT; + endPoint_lum[1] = MIN_FLOAT; + + int2 endPoint_lum_index; + endPoint_lum_index[0] = -1; + endPoint_lum_index[1] = -1; + + int3 pixel_ph = shared_temp[threadBase + (threadInBlock & 0xF)].pixel_ph; + float pixel_lum = shared_temp[threadBase + (threadInBlock & 0xF)].pixel_lum; + if (threadInBlock < 16) + { + if (best_mode > 10) + { + endPoint[0] = endPoint[1] = pixel_ph; + endPoint_lum[0] = endPoint_lum[1] = pixel_lum; + } + else + { + uint bits = candidateSectionBit[best_partition]; + if (0 == ((bits >> threadInBlock) & 1)) + { + endPoint[0] = endPoint[1] = pixel_ph; + endPoint_lum[0] = endPoint_lum[1] = pixel_lum; + } + } + } + else + { + if (best_mode <= 10) + { + uint bits = candidateSectionBit[best_partition]; + if (1 == ((bits >> (threadInBlock & 0xF)) & 1)) + { + endPoint[0] = endPoint[1] = pixel_ph; + endPoint_lum[0] = endPoint_lum[1] = pixel_lum; + } + } + } + + shared_temp[GI].endPoint_low = endPoint[0]; + shared_temp[GI].endPoint_high = endPoint[1]; + + shared_temp[GI].endPoint_lum_low = endPoint_lum[0]; + shared_temp[GI].endPoint_lum_high = endPoint_lum[1]; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if ((threadInBlock & 0xF) < 8) + { + if (shared_temp[GI].endPoint_lum_low > shared_temp[GI + 8].endPoint_lum_low) + { + shared_temp[GI].endPoint_low = shared_temp[GI + 8].endPoint_low; + shared_temp[GI].endPoint_lum_low = shared_temp[GI + 8].endPoint_lum_low; + } + if (shared_temp[GI].endPoint_lum_high < shared_temp[GI + 8].endPoint_lum_high) + { + shared_temp[GI].endPoint_high = shared_temp[GI + 8].endPoint_high; + shared_temp[GI].endPoint_lum_high = shared_temp[GI + 8].endPoint_lum_high; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if ((threadInBlock & 0xF) < 4) + { + if (shared_temp[GI].endPoint_lum_low > shared_temp[GI + 4].endPoint_lum_low) + { + shared_temp[GI].endPoint_low = shared_temp[GI + 4].endPoint_low; + shared_temp[GI].endPoint_lum_low = shared_temp[GI + 4].endPoint_lum_low; + } + if (shared_temp[GI].endPoint_lum_high < shared_temp[GI + 4].endPoint_lum_high) + { + shared_temp[GI].endPoint_high = shared_temp[GI + 4].endPoint_high; + shared_temp[GI].endPoint_lum_high = shared_temp[GI + 4].endPoint_lum_high; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if ((threadInBlock & 0xF) < 2) + { + if (shared_temp[GI].endPoint_lum_low > shared_temp[GI + 2].endPoint_lum_low) + { + shared_temp[GI].endPoint_low = shared_temp[GI + 2].endPoint_low; + shared_temp[GI].endPoint_lum_low = shared_temp[GI + 2].endPoint_lum_low; + } + if (shared_temp[GI].endPoint_lum_high < shared_temp[GI + 2].endPoint_lum_high) + { + shared_temp[GI].endPoint_high = shared_temp[GI + 2].endPoint_high; + shared_temp[GI].endPoint_lum_high = shared_temp[GI + 2].endPoint_lum_high; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if ((threadInBlock & 0xF) < 1) + { + if (shared_temp[GI].endPoint_lum_low > shared_temp[GI + 1].endPoint_lum_low) + { + shared_temp[GI].endPoint_low = shared_temp[GI + 1].endPoint_low; + shared_temp[GI].endPoint_lum_low = shared_temp[GI + 1].endPoint_lum_low; + } + if (shared_temp[GI].endPoint_lum_high < shared_temp[GI + 1].endPoint_lum_high) + { + shared_temp[GI].endPoint_high = shared_temp[GI + 1].endPoint_high; + shared_temp[GI].endPoint_lum_high = shared_temp[GI + 1].endPoint_lum_high; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (threadInBlock < 2) + { + // find_axis + int2x3 endPoint; + endPoint[0] = shared_temp[threadBase + threadInBlock * 16].endPoint_low; + endPoint[1] = shared_temp[threadBase + threadInBlock * 16].endPoint_high; + + uint fixup = 0; + if ((1 == threadInBlock) && (best_mode <= 10)) + { + fixup = candidateFixUpIndex1D[best_partition]; + } + + float3 span = endPoint[1] - endPoint[0]; + float span_norm_sqr = dot( span, span ); + float dotProduct = dot( span, shared_temp[threadBase + fixup].pixel_ph - endPoint[0] ); + if ( span_norm_sqr > 0 && dotProduct >= 0 && uint( dotProduct * 63.49999 / span_norm_sqr ) > 32 ) + { + swap(endPoint[0], endPoint[1]); + } + + shared_temp[GI].endPoint_low = endPoint[0]; + shared_temp[GI].endPoint_high = endPoint[1]; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (threadInBlock < 16) + { + uint bits; + if (best_mode > 10) + { + bits = 0; + } + else + { + bits = candidateSectionBit[best_partition]; + } + + float3 span; + float dotProduct; + if ((bits >> threadInBlock) & 1) + { + span = shared_temp[threadBase + 1].endPoint_high - shared_temp[threadBase + 1].endPoint_low; + dotProduct = dot( span, shared_temp[threadBase + threadInBlock].pixel_ph - shared_temp[threadBase + 1].endPoint_low ); + } + else + { + span = shared_temp[threadBase + 0].endPoint_high - shared_temp[threadBase + 0].endPoint_low; + dotProduct = dot( span, shared_temp[threadBase + threadInBlock].pixel_ph - shared_temp[threadBase + 0].endPoint_low ); + } + float span_norm_sqr = dot( span, span ); + + if (best_mode > 10) + { + uint index = ( span_norm_sqr <= 0 || dotProduct <= 0 ) ? 0 + : ( ( dotProduct < span_norm_sqr ) ? aStep2[ uint( dotProduct * 63.49999 / span_norm_sqr ) ] : aStep2[63] ); + if (threadInBlock == 0) + { + block.z |= index << 1; + } + else if (threadInBlock < 8) + { + block.z |= index << (threadInBlock * 4); + } + else + { + block.w |= index << ((threadInBlock - 8) * 4); + } + } + else + { + uint index = ( span_norm_sqr <= 0 || dotProduct <= 0 ) ? 0 + : ( ( dotProduct < span_norm_sqr ) ? aStep1[ uint( dotProduct * 63.49999 / span_norm_sqr ) ] : aStep1[63] ); + + uint fixup = candidateFixUpIndex1D[best_partition]; + int2 offset = int2((fixup != 2), (fixup == 15)); + + if (threadInBlock == 0) + { + block.z |= index << 18; + } + else if (threadInBlock < 3) + { + block.z |= index << (20 + (threadInBlock - 1) * 3); + } + else if (threadInBlock < 5) + { + block.z |= index << (25 + (threadInBlock - 3) * 3 + offset.x); + } + else if (threadInBlock == 5) + { + block.w |= index >> !offset.x; + if (!offset.x) + { + block.z |= index << 31; + } + } + else if (threadInBlock < 9) + { + block.w |= index << (2 + (threadInBlock - 6) * 3 + offset.x); + } + else + { + block.w |= index << (11 + (threadInBlock - 9) * 3 + offset.y); + } + } + + shared_temp[GI].pixel_hr.xy = asfloat(block.zw); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 8) + { + shared_temp[GI].pixel_hr.xy = asfloat(asuint(shared_temp[GI].pixel_hr.xy) | asuint(shared_temp[GI + 8].pixel_hr.xy)); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 4) + { + shared_temp[GI].pixel_hr.xy = asfloat(asuint(shared_temp[GI].pixel_hr.xy) | asuint(shared_temp[GI + 4].pixel_hr.xy)); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 2) + { + shared_temp[GI].pixel_hr.xy = asfloat(asuint(shared_temp[GI].pixel_hr.xy) | asuint(shared_temp[GI + 2].pixel_hr.xy)); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 1) + { + shared_temp[GI].pixel_hr.xy = asfloat(asuint(shared_temp[GI].pixel_hr.xy) | asuint(shared_temp[GI + 1].pixel_hr.xy)); + + block.zw = asuint(shared_temp[GI].pixel_hr.xy); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + bool transformed = candidateModeTransformed[best_mode - 1]; + uint4 prec = candidateModePrec[best_mode - 1]; + if (threadInBlock == 2) + { + int2x3 endPoint_q; + endPoint_q[0] = shared_temp[threadBase + 0].endPoint_low; + endPoint_q[1] = shared_temp[threadBase + 0].endPoint_high; + + quantize( endPoint_q, prec.x ); + if (transformed) + { + endPoint_q[1] -= endPoint_q[0]; + } + + shared_temp[GI].endPoint_low = endPoint_q[0]; + shared_temp[GI].endPoint_high = endPoint_q[1]; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock == 3) + { + int3 ep0 = shared_temp[threadBase + 2].endPoint_low; + int2x3 endPoint_q; + endPoint_q[0] = shared_temp[threadBase + 1].endPoint_low; + endPoint_q[1] = shared_temp[threadBase + 1].endPoint_high; + + if (best_mode <= 10) + { + quantize( endPoint_q, prec.x ); + if (transformed) + { + endPoint_q[0] -= ep0; + endPoint_q[1] -= ep0; + } + + shared_temp[GI].endPoint_low = endPoint_q[0]; + shared_temp[GI].endPoint_high = endPoint_q[1]; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (threadInBlock < 2) + { + int2x3 endPoint_q; + endPoint_q[0] = shared_temp[threadBase + threadInBlock + 2].endPoint_low; + endPoint_q[1] = shared_temp[threadBase + threadInBlock + 2].endPoint_high; + + int bBadQuantize = 0; + if (threadInBlock == 0) + { + if (best_mode > 10) + { + finish_quantize( bBadQuantize, endPoint_q, prec, transformed ); + } + else + { + finish_quantize_0( bBadQuantize, endPoint_q, prec, transformed ); + } + } + else // if (threadInBlock == 1) + { + if (best_mode <= 10) + { + finish_quantize_1( bBadQuantize, endPoint_q, prec, transformed ); + } + } + + shared_temp[GI].endPoint_low = endPoint_q[0]; + shared_temp[GI].endPoint_high = endPoint_q[1]; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if ( threadInBlock == 0 ) + { + int2x3 endPoint_q[2]; + endPoint_q[0][0] = shared_temp[threadBase + 0].endPoint_low; + endPoint_q[0][1] = shared_temp[threadBase + 0].endPoint_high; + endPoint_q[1][0] = shared_temp[threadBase + 1].endPoint_low; + endPoint_q[1][1] = shared_temp[threadBase + 1].endPoint_high; + + if ( best_mode > 10 ) + { + block_package( block, endPoint_q[0], best_mode ); + } + else + { + block_package( block, endPoint_q, best_mode, best_partition ); + } + + g_OutBuff[blockID] = block; + } +} + +uint float2half1( float f ) +{ + uint Result; + + uint IValue = asuint(f); + uint Sign = (IValue & 0x80000000U) >> 16U; + IValue = IValue & 0x7FFFFFFFU; + + if (IValue > 0x47FFEFFFU) + { + // The number is too large to be represented as a half. Saturate to infinity. + Result = 0x7FFFU; + } + else + { + if (IValue < 0x38800000U) + { + // The number is too small to be represented as a normalized half. + // Convert it to a denormalized value. + uint Shift = 113U - (IValue >> 23U); + IValue = (0x800000U | (IValue & 0x7FFFFFU)) >> Shift; + } + else + { + // Rebias the exponent to represent the value as a normalized half. + IValue += 0xC8000000U; + } + + Result = ((IValue + 0x0FFFU + ((IValue >> 13U) & 1U)) >> 13U)&0x7FFFU; + } + return (Result|Sign); +} + +uint3 float2half( float3 endPoint_f ) +{ + //uint3 sign = asuint(endPoint_f) & 0x80000000; + //uint3 expo = asuint(endPoint_f) & 0x7F800000; + //uint3 base = asuint(endPoint_f) & 0x007FFFFF; + //return ( expo < 0x33800000 ) ? 0 + // //0x33800000 indicating 2^-24, which is minimal denormalized number that half can present + // : ( ( expo < 0x38800000 ) ? ( sign >> 16 ) | ( ( base + 0x00800000 ) >> ( 23 - ( ( expo - 0x33800000 ) >> 23 ) ) )//fixed a bug in v0.2 + // //0x38800000 indicating 2^-14, which is minimal normalized number that half can present, so need to use denormalized half presentation + // : ( ( expo == 0x7F800000 || expo > 0x47000000 ) ? ( ( sign >> 16 ) | 0x7bff ) + // // treat NaN as INF, treat INF (including NaN) as the maximum/minimum number that half can present + // // 0x47000000 indicating 2^15, which is maximum exponent that half can present, so cut to 0x7bff which is the maximum half number + // : ( ( sign >> 16 ) | ( ( ( expo - 0x38000000 ) | base ) >> 13 ) ) ) ); + + + return uint3( float2half1( endPoint_f.x ), float2half1( endPoint_f.y ), float2half1( endPoint_f.z ) ); +} +int3 start_quantize( uint3 pixel_h ) +{ + if ( g_format == UNSIGNED_F16 ) + { + return asint( ( pixel_h << 6 ) / 31 ); + } + else + { + return ( pixel_h < 0x8000 ) ? ( ( pixel_h == 0x7bff ) ? 0x7fff : asint( ( pixel_h << 5 ) / 31 ) )// fixed a bug in v0.2 + : ( ( pixel_h == 0x7bff ) ? 0xffff8001 : -asint( ( ( 0x00007fff & pixel_h ) << 5 ) / 31 ) );// fixed a bug in v0.2 + } +} +void quantize( inout int2x3 endPoint, uint prec ) +{ + int iprec = asint( prec ); + if ( g_format == UNSIGNED_F16 ) + { + endPoint = ( ( iprec >= 15 ) | ( endPoint == 0 ) ) ? endPoint + : ( ( endPoint == asint(0xFFFF) ) ? ( ( 1 << iprec ) - 1 ) + : ( ( ( endPoint << iprec ) + asint(0x0000) ) >> 16 ) ); + } + else + { + endPoint = ( ( iprec >= 16 ) | ( endPoint == 0 ) ) ? endPoint + : ( ( endPoint >= 0 ) ? ( ( endPoint == asint(0x7FFF) ) ? ( ( 1 << ( iprec - 1 ) ) - 1 ) : ( ( ( endPoint << ( iprec - 1 ) ) + asint(0x0000) ) >> 15 ) ) + : ( ( -endPoint == asint(0x7FFF) ) ? -( ( 1 << ( iprec - 1 ) ) - 1 ) : -( ( ( -endPoint << ( iprec - 1 ) ) + asint(0x0000) ) >> 15 ) ) ); + } +} +void finish_quantize_0( inout int bBadQuantize, inout int2x3 endPoint, uint4 prec, bool transformed ) +{ + if ( transformed ) + { + bool3 bBadComponent = ( endPoint[1] >= 0 ) ? ( endPoint[1] >= ( 1 << ( prec.yzw - 1 ) ) ) + : ( -endPoint[1] > ( 1 << ( prec.yzw - 1 ) ) ); + bBadQuantize |= any(bBadComponent); + + endPoint[0] = endPoint[0] & ( ( 1 << prec.x ) - 1 ); + endPoint[1] = ( endPoint[1] >= 0 ) ? ( ( endPoint[1] >= ( 1 << ( prec.yzw - 1 ) ) ) ? ( ( 1 << ( prec.yzw - 1 ) ) - 1 ) : endPoint[1] ) + : ( ( -endPoint[1] > ( 1 << ( prec.yzw - 1 ) ) ) ? ( 1 << ( prec.yzw - 1 ) ) : ( endPoint[1] & ( ( 1 << prec.yzw ) - 1 ) ) ); + } + else + { + endPoint &= ( ( 1 << prec.x ) - 1 ); + } +} +void finish_quantize_1( inout int bBadQuantize, inout int2x3 endPoint, uint4 prec, bool transformed ) +{ + if ( transformed ) + { + bool2x3 bBadComponent; + bBadComponent[0] = ( endPoint[0] >= 0 ) ? ( endPoint[0] >= ( 1 << ( prec.yzw - 1 ) ) ) + : ( -endPoint[0] > ( 1 << ( prec.yzw - 1 ) ) ); + bBadComponent[1] = ( endPoint[1] >= 0 ) ? ( endPoint[1] >= ( 1 << ( prec.yzw - 1 ) ) ) + : ( -endPoint[1] > ( 1 << ( prec.yzw - 1 ) ) ); + bBadQuantize |= any(bBadComponent); + + endPoint[0] = ( endPoint[0] >= 0 ) ? ( ( endPoint[0] >= ( 1 << ( prec.yzw - 1 ) ) ) ? ( ( 1 << ( prec.yzw - 1 ) ) - 1 ) : endPoint[0] ) + : ( ( -endPoint[0] > ( 1 << ( prec.yzw - 1 ) ) ) ? ( 1 << ( prec.yzw - 1 ) ) : ( endPoint[0] & ( ( 1 << prec.yzw ) - 1 ) ) ); + endPoint[1] = ( endPoint[1] >= 0 ) ? ( ( endPoint[1] >= ( 1 << ( prec.yzw - 1 ) ) ) ? ( ( 1 << ( prec.yzw - 1 ) ) - 1 ) : endPoint[1] ) + : ( ( -endPoint[1] > ( 1 << ( prec.yzw - 1 ) ) ) ? ( 1 << ( prec.yzw - 1 ) ) : ( endPoint[1] & ( ( 1 << prec.yzw ) - 1 ) ) ); + } + else + { + endPoint &= ( ( 1 << prec.x ) - 1 ); + } +} +void finish_quantize( out bool bBadQuantize, inout int2x3 endPoint, uint4 prec, bool transformed ) +{ + if ( transformed ) + { + bool3 bBadComponent; + bBadComponent = ( endPoint[1] >= 0 ) ? ( endPoint[1] >= ( 1 << ( prec.yzw - 1 ) ) ) + : ( -endPoint[1] > ( 1 << ( prec.yzw - 1 ) ) ); + bBadQuantize = any( bBadComponent ); + + endPoint[0] = endPoint[0] & ( ( 1 << prec.x ) - 1 ); + endPoint[1] = ( endPoint[1] >= 0 ) ? ( ( endPoint[1] >= ( 1 << ( prec.yzw - 1 ) ) ) ? ( ( 1 << ( prec.yzw - 1 ) ) - 1 ) : endPoint[1] ) + : ( ( -endPoint[1] > ( 1 << ( prec.yzw - 1 ) ) ) ? ( 1 << ( prec.yzw - 1 ) ) : ( endPoint[1] & ( ( 1 << prec.yzw ) - 1 ) ) ); + } + else + { + endPoint &= ( ( 1 << prec.x ) - 1 ); + + bBadQuantize = 0; + } +} + +void SIGN_EXTEND( uint3 prec, inout int3 color ) +{ + uint3 p = 1 << (prec - 1); + color = (color & p) ? (color & (p - 1)) - p : color; +} + +void sign_extend( bool transformed, uint4 prec, inout int2x3 endPoint ) +{ + if ( g_format == SIGNED_F16 ) + SIGN_EXTEND( prec.x, endPoint[0] ); + if ( g_format == SIGNED_F16 || transformed ) + SIGN_EXTEND( prec.yzw, endPoint[1] ); +} + +void sign_extend( bool transformed, uint4 prec, inout int2x3 endPoint[2] ) +{ + if ( g_format == SIGNED_F16 ) + SIGN_EXTEND( prec.x, endPoint[0][0] ); + if ( g_format == SIGNED_F16 || transformed ) + { + SIGN_EXTEND( prec.yzw, endPoint[0][1] ); + SIGN_EXTEND( prec.yzw, endPoint[1][0] ); + SIGN_EXTEND( prec.yzw, endPoint[1][1] ); + } +} +void start_unquantize( inout int2x3 endPoint[2], uint4 prec, bool transformed ) +{ + sign_extend( transformed, prec, endPoint ); + if ( transformed ) + { + endPoint[0][1] += endPoint[0][0]; + endPoint[1][0] += endPoint[0][0]; + endPoint[1][1] += endPoint[0][0]; + } +} +void start_unquantize( inout int2x3 endPoint, uint4 prec, bool transformed ) +{ + sign_extend( transformed, prec, endPoint ); + if ( transformed ) + endPoint[1] += endPoint[0]; +} +void unquantize( inout int2x3 color, uint prec ) +{ + int iprec = asint( prec ); + if (g_format == UNSIGNED_F16 ) + { + if (prec < 15) + { + color = (color != 0) ? (color == ((1 << iprec) - 1) ? 0xFFFF : (((color << 16) + 0x8000) >> iprec)) : color; + } + } + else + { + if (prec < 16) + { + uint2x3 s = color >= 0 ? 0 : 1; + color = abs(color); + color = (color != 0) ? (color >= ((1 << (iprec - 1)) - 1) ? 0x7FFF : (((color << 15) + 0x4000) >> (iprec - 1))) : color; + color = s > 0 ? -color : color; + } + } +} +uint3 finish_unquantize( int3 color ) +{ + if ( g_format == UNSIGNED_F16 ) + color = ( color * 31 ) >> 6; + else + { + color = ( color < 0 ) ? -( ( -color * 31 ) >> 5 ) : ( color * 31 ) >> 5; + color = ( color < 0 ) ? ( ( -color ) | 0x8000 ) : color; + } + return asuint(color); +} +void generate_palette_unquantized8( out uint3 palette, int3 low, int3 high, int i ) +{ + static const int aWeight3[] = {0, 9, 18, 27, 37, 46, 55, 64}; + + int3 tmp = ( low * ( 64 - aWeight3[i] ) + high * aWeight3[i] + 32 ) >> 6; + palette = finish_unquantize( tmp ); +} +void generate_palette_unquantized16( out uint3 palette, int3 low, int3 high, int i ) +{ + static const int aWeight4[] = {0, 4, 9, 13, 17, 21, 26, 30, 34, 38, 43, 47, 51, 55, 60, 64}; + + int3 tmp = ( low * ( 64 - aWeight4[i] ) + high * aWeight4[i] + 32 ) >> 6; + palette = finish_unquantize( tmp ); +} + +float half2float1( uint Value ) +{ + uint Mantissa = (uint)(Value & 0x03FF); + + uint Exponent; + if ((Value & 0x7C00) != 0) // The value is normalized + { + Exponent = (uint)((Value >> 10) & 0x1F); + } + else if (Mantissa != 0) // The value is denormalized + { + // Normalize the value in the resulting float + Exponent = 1; + + do + { + Exponent--; + Mantissa <<= 1; + } while ((Mantissa & 0x0400) == 0); + + Mantissa &= 0x03FF; + } + else // The value is zero + { + Exponent = (uint)(-112); + } + + uint Result = ((Value & 0x8000) << 16) | // Sign + ((Exponent + 112) << 23) | // Exponent + (Mantissa << 13); // Mantissa + + return asfloat(Result); +} + +float3 half2float(uint3 color_h ) +{ + //uint3 sign = color_h & 0x8000; + //uint3 expo = color_h & 0x7C00; + //uint3 base = color_h & 0x03FF; + //return ( expo == 0 ) ? asfloat( ( sign << 16 ) | asuint( float3(base) / 16777216 ) ) //16777216 = 2^24 + // : asfloat( ( sign << 16 ) | ( ( ( expo + 0x1C000 ) | base ) << 13 ) ); //0x1C000 = 0x1FC00 - 0x3C00 + + return float3( half2float1( color_h.x ), half2float1( color_h.y ), half2float1( color_h.z ) ); +} + +void block_package( inout uint4 block, int2x3 endPoint[2], uint mode_type, uint partition_index ) // for mode 1 - 10 +{ + block.xy = 0; + block.z &= 0xFFFC0000; + + //block.z |= (partition_index & 0x1f) << 13; + + if ( mode_type == candidateModeFlag[0]) + { + /*block.x = candidateModeMemory[0]; + block.x |= ( ( endPoint[0][0].r << 5 ) & 0x00007FE0 ) | ( ( endPoint[0][0].g << 15 ) & 0x01FF8000 ) | ( ( endPoint[0][0].b << 25 ) & 0xFE000000 ); + block.x |= ( endPoint[1][0].g >> 2 ) & 0x00000004; + block.x |= ( endPoint[1][0].b >> 1 ) & 0x00000008; + block.x |= endPoint[1][1].b & 0x00000010; + block.y |= ( ( endPoint[0][0].b >> 7 ) & 0x00000007 ); + block.y |= ( ( endPoint[0][1].r << 3 ) & 0x000000F8 ) | ( ( endPoint[0][1].g << 13 ) & 0x0003E000 ) | ( ( endPoint[0][1].b << 23 ) & 0x0F800000 ); + block.yz |= ( endPoint[1][0].gr << uint2(9, 1) ) & uint2(0x00001E00, 0x0000003E); + block.y |= ( endPoint[1][0].b << 29 ) & 0xE0000000; + block.y |= ( ( endPoint[1][1].g << 4 ) & 0x00000100 ); + block.yz |= ( endPoint[1][1].gr << uint2(19, 7) ) & uint2(0x00780000, 0x00000F80); + block.yz |= ( ( endPoint[1][1].b << uint2(27, 9) ) & uint2(0x10000000, 0x00001000) ) | ( ( endPoint[1][1].b << uint2(18, 4) ) & uint2(0x00040000, 0x00000040) ); + block.z |= ( endPoint[1][0].b >> 3 ) & 0x00000001;*/ + + block.x |= ((candidateModeMemory[0] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[0] >> 1) & 1) << 1; + block.x |= ((endPoint[1][0].g >> 4) & 1) << 2; + block.x |= ((endPoint[1][0].b >> 4) & 1) << 3; + block.x |= ((endPoint[1][1].b >> 4) & 1) << 4; + block.x |= ((endPoint[0][0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0][0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0][0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0][0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0][0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0][0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0][0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0][0].r >> 7) & 1) << 12; + block.x |= ((endPoint[0][0].r >> 8) & 1) << 13; + block.x |= ((endPoint[0][0].r >> 9) & 1) << 14; + block.x |= ((endPoint[0][0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0][0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0][0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0][0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0][0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0][0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0][0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0][0].g >> 7) & 1) << 22; + block.x |= ((endPoint[0][0].g >> 8) & 1) << 23; + block.x |= ((endPoint[0][0].g >> 9) & 1) << 24; + block.x |= ((endPoint[0][0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0][0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0][0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0][0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0][0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0][0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0][0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0][0].b >> 7) & 1) << 0; + block.y |= ((endPoint[0][0].b >> 8) & 1) << 1; + block.y |= ((endPoint[0][0].b >> 9) & 1) << 2; + block.y |= ((endPoint[0][1].r >> 0) & 1) << 3; + block.y |= ((endPoint[0][1].r >> 1) & 1) << 4; + block.y |= ((endPoint[0][1].r >> 2) & 1) << 5; + block.y |= ((endPoint[0][1].r >> 3) & 1) << 6; + block.y |= ((endPoint[0][1].r >> 4) & 1) << 7; + block.y |= ((endPoint[1][1].g >> 4) & 1) << 8; + block.y |= ((endPoint[1][0].g >> 0) & 1) << 9; + block.y |= ((endPoint[1][0].g >> 1) & 1) << 10; + block.y |= ((endPoint[1][0].g >> 2) & 1) << 11; + block.y |= ((endPoint[1][0].g >> 3) & 1) << 12; + block.y |= ((endPoint[0][1].g >> 0) & 1) << 13; + block.y |= ((endPoint[0][1].g >> 1) & 1) << 14; + block.y |= ((endPoint[0][1].g >> 2) & 1) << 15; + block.y |= ((endPoint[0][1].g >> 3) & 1) << 16; + block.y |= ((endPoint[0][1].g >> 4) & 1) << 17; + block.y |= ((endPoint[1][1].b >> 0) & 1) << 18; + block.y |= ((endPoint[1][1].g >> 0) & 1) << 19; + block.y |= ((endPoint[1][1].g >> 1) & 1) << 20; + block.y |= ((endPoint[1][1].g >> 2) & 1) << 21; + block.y |= ((endPoint[1][1].g >> 3) & 1) << 22; + block.y |= ((endPoint[0][1].b >> 0) & 1) << 23; + block.y |= ((endPoint[0][1].b >> 1) & 1) << 24; + block.y |= ((endPoint[0][1].b >> 2) & 1) << 25; + block.y |= ((endPoint[0][1].b >> 3) & 1) << 26; + block.y |= ((endPoint[0][1].b >> 4) & 1) << 27; + block.y |= ((endPoint[1][1].b >> 1) & 1) << 28; + block.y |= ((endPoint[1][0].b >> 0) & 1) << 29; + block.y |= ((endPoint[1][0].b >> 1) & 1) << 30; + block.y |= ((endPoint[1][0].b >> 2) & 1) << 31; + block.z |= ((endPoint[1][0].b >> 3) & 1) << 0; + block.z |= ((endPoint[1][0].r >> 0) & 1) << 1; + block.z |= ((endPoint[1][0].r >> 1) & 1) << 2; + block.z |= ((endPoint[1][0].r >> 2) & 1) << 3; + block.z |= ((endPoint[1][0].r >> 3) & 1) << 4; + block.z |= ((endPoint[1][0].r >> 4) & 1) << 5; + block.z |= ((endPoint[1][1].b >> 2) & 1) << 6; + block.z |= ((endPoint[1][1].r >> 0) & 1) << 7; + block.z |= ((endPoint[1][1].r >> 1) & 1) << 8; + block.z |= ((endPoint[1][1].r >> 2) & 1) << 9; + block.z |= ((endPoint[1][1].r >> 3) & 1) << 10; + block.z |= ((endPoint[1][1].r >> 4) & 1) << 11; + block.z |= ((endPoint[1][1].b >> 3) & 1) << 12; + block.z |= ((partition_index >> 0) & 1) << 13; + block.z |= ((partition_index >> 1) & 1) << 14; + block.z |= ((partition_index >> 2) & 1) << 15; + block.z |= ((partition_index >> 3) & 1) << 16; + block.z |= ((partition_index >> 4) & 1) << 17; + } + else if ( mode_type == candidateModeFlag[1]) + { + /*block.x = candidateModeMemory[1]; + block.x |= ( ( endPoint[0][0].r << 5 ) & 0x00000FE0 ) | ( ( endPoint[0][0].g << 15 ) & 0x003F8000 ) | ( ( endPoint[0][0].b << 25 ) & 0xFE000000 ); + block.y |= ( ( endPoint[0][1].r << 3 ) & 0x000001F8 ) | ( ( endPoint[0][1].g << 13 ) & 0x0007E000 ) | ( ( endPoint[0][1].b << 23 ) & 0x1F800000 ); + block.x |= ( ( endPoint[1][0].g >> 3 ) & 0x00000004 ) | ( ( endPoint[1][0].g << 20 ) & 0x01000000 ); + block.x |= ( endPoint[1][1].g >> 1 ) & 0x00000018; + block.x |= ( ( endPoint[1][1].b << 21 ) & 0x00800000 ) | ( ( endPoint[1][1].b << 12 ) & 0x00003000 ); + block.x |= ( ( endPoint[1][0].b << 17 ) & 0x00400000 ) | ( ( endPoint[1][0].b << 10 ) & 0x00004000 ); + block.yz |= ( endPoint[1][0].gr << uint2(9, 1) ) & uint2(0x00001E00, 0x0000007E); + block.y |= ( endPoint[1][0].b << 29 ) & 0xE0000000; + block.yz |= ( endPoint[1][1].gr << uint2(19, 7) ) & uint2(0x00780000, 0x00001F80); + block.y |= ( ( endPoint[1][1].b >> 4 ) & 0x00000002 ) | ( ( endPoint[1][1].b >> 2 ) & 0x00000004 ) | ( ( endPoint[1][1].b >> 3 ) & 0x00000001 ); + block.z |= ( endPoint[1][0].b >> 3 ) & 0x00000001;*/ + + block.x |= ((candidateModeMemory[1] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[1] >> 1) & 1) << 1; + block.x |= ((endPoint[1][0].g >> 5) & 1) << 2; + block.x |= ((endPoint[1][1].g >> 4) & 1) << 3; + block.x |= ((endPoint[1][1].g >> 5) & 1) << 4; + block.x |= ((endPoint[0][0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0][0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0][0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0][0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0][0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0][0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0][0].r >> 6) & 1) << 11; + block.x |= ((endPoint[1][1].b >> 0) & 1) << 12; + block.x |= ((endPoint[1][1].b >> 1) & 1) << 13; + block.x |= ((endPoint[1][0].b >> 4) & 1) << 14; + block.x |= ((endPoint[0][0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0][0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0][0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0][0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0][0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0][0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0][0].g >> 6) & 1) << 21; + block.x |= ((endPoint[1][0].b >> 5) & 1) << 22; + block.x |= ((endPoint[1][1].b >> 2) & 1) << 23; + block.x |= ((endPoint[1][0].g >> 4) & 1) << 24; + block.x |= ((endPoint[0][0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0][0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0][0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0][0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0][0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0][0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0][0].b >> 6) & 1) << 31; + block.y |= ((endPoint[1][1].b >> 3) & 1) << 0; + block.y |= ((endPoint[1][1].b >> 5) & 1) << 1; + block.y |= ((endPoint[1][1].b >> 4) & 1) << 2; + block.y |= ((endPoint[0][1].r >> 0) & 1) << 3; + block.y |= ((endPoint[0][1].r >> 1) & 1) << 4; + block.y |= ((endPoint[0][1].r >> 2) & 1) << 5; + block.y |= ((endPoint[0][1].r >> 3) & 1) << 6; + block.y |= ((endPoint[0][1].r >> 4) & 1) << 7; + block.y |= ((endPoint[0][1].r >> 5) & 1) << 8; + block.y |= ((endPoint[1][0].g >> 0) & 1) << 9; + block.y |= ((endPoint[1][0].g >> 1) & 1) << 10; + block.y |= ((endPoint[1][0].g >> 2) & 1) << 11; + block.y |= ((endPoint[1][0].g >> 3) & 1) << 12; + block.y |= ((endPoint[0][1].g >> 0) & 1) << 13; + block.y |= ((endPoint[0][1].g >> 1) & 1) << 14; + block.y |= ((endPoint[0][1].g >> 2) & 1) << 15; + block.y |= ((endPoint[0][1].g >> 3) & 1) << 16; + block.y |= ((endPoint[0][1].g >> 4) & 1) << 17; + block.y |= ((endPoint[0][1].g >> 5) & 1) << 18; + block.y |= ((endPoint[1][1].g >> 0) & 1) << 19; + block.y |= ((endPoint[1][1].g >> 1) & 1) << 20; + block.y |= ((endPoint[1][1].g >> 2) & 1) << 21; + block.y |= ((endPoint[1][1].g >> 3) & 1) << 22; + block.y |= ((endPoint[0][1].b >> 0) & 1) << 23; + block.y |= ((endPoint[0][1].b >> 1) & 1) << 24; + block.y |= ((endPoint[0][1].b >> 2) & 1) << 25; + block.y |= ((endPoint[0][1].b >> 3) & 1) << 26; + block.y |= ((endPoint[0][1].b >> 4) & 1) << 27; + block.y |= ((endPoint[0][1].b >> 5) & 1) << 28; + block.y |= ((endPoint[1][0].b >> 0) & 1) << 29; + block.y |= ((endPoint[1][0].b >> 1) & 1) << 30; + block.y |= ((endPoint[1][0].b >> 2) & 1) << 31; + block.z |= ((endPoint[1][0].b >> 3) & 1) << 0; + block.z |= ((endPoint[1][0].r >> 0) & 1) << 1; + block.z |= ((endPoint[1][0].r >> 1) & 1) << 2; + block.z |= ((endPoint[1][0].r >> 2) & 1) << 3; + block.z |= ((endPoint[1][0].r >> 3) & 1) << 4; + block.z |= ((endPoint[1][0].r >> 4) & 1) << 5; + block.z |= ((endPoint[1][0].r >> 5) & 1) << 6; + block.z |= ((endPoint[1][1].r >> 0) & 1) << 7; + block.z |= ((endPoint[1][1].r >> 1) & 1) << 8; + block.z |= ((endPoint[1][1].r >> 2) & 1) << 9; + block.z |= ((endPoint[1][1].r >> 3) & 1) << 10; + block.z |= ((endPoint[1][1].r >> 4) & 1) << 11; + block.z |= ((endPoint[1][1].r >> 5) & 1) << 12; + block.z |= ((partition_index >> 0) & 1) << 13; + block.z |= ((partition_index >> 1) & 1) << 14; + block.z |= ((partition_index >> 2) & 1) << 15; + block.z |= ((partition_index >> 3) & 1) << 16; + block.z |= ((partition_index >> 4) & 1) << 17; + } + else if ( mode_type == candidateModeFlag[2]) + { + /*block.x = candidateModeMemory[2]; + block.x |= ( ( endPoint[0][0].r << 5 ) & 0x00007FE0 ) | ( ( endPoint[0][0].g << 15 ) & 0x01FF8000 ) | ( ( endPoint[0][0].b << 25 ) & 0xFE000000 ); + block.y |= ( endPoint[0][0].r >> 2 ) & 0x00000100; + block.y |= ( endPoint[0][0].g << 7 ) & 0x00020000; + block.y |= ( ( endPoint[0][0].b << 17 ) & 0x08000000 ) | ( ( endPoint[0][0].b >> 7 ) & 0x00000007 ); + block.y |= ( ( endPoint[0][1].r << 3 ) & 0x000000F8 ) | ( ( endPoint[0][1].g << 13 ) & 0x0001E000 ) | ( ( endPoint[0][1].b << 23 ) & 0x07800000 ); + block.yz |= ( endPoint[1][0].gr << uint2(9, 1) ) & uint2(0x00001E00, 0x0000003E); + block.y |= ( endPoint[1][0].b << 29 ) & 0xE0000000; + block.yz |= ( endPoint[1][1].gr << uint2(19, 7) ) & uint2(0x00780000, 0x00000F80); + block.yz |= ( ( endPoint[1][1].b << uint2(27, 9) ) & uint2(0x10000000, 0x00001000) ) | ( ( endPoint[1][1].b << uint2(18, 4) ) & uint2(0x00040000, 0x00000040) ); + block.z |= ( endPoint[1][0].b >> 3 ) & 0x00000001;*/ + + block.x |= ((candidateModeMemory[2] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[2] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[2] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[2] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[2] >> 4) & 1) << 4; + block.x |= ((endPoint[0][0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0][0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0][0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0][0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0][0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0][0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0][0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0][0].r >> 7) & 1) << 12; + block.x |= ((endPoint[0][0].r >> 8) & 1) << 13; + block.x |= ((endPoint[0][0].r >> 9) & 1) << 14; + block.x |= ((endPoint[0][0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0][0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0][0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0][0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0][0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0][0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0][0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0][0].g >> 7) & 1) << 22; + block.x |= ((endPoint[0][0].g >> 8) & 1) << 23; + block.x |= ((endPoint[0][0].g >> 9) & 1) << 24; + block.x |= ((endPoint[0][0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0][0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0][0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0][0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0][0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0][0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0][0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0][0].b >> 7) & 1) << 0; + block.y |= ((endPoint[0][0].b >> 8) & 1) << 1; + block.y |= ((endPoint[0][0].b >> 9) & 1) << 2; + block.y |= ((endPoint[0][1].r >> 0) & 1) << 3; + block.y |= ((endPoint[0][1].r >> 1) & 1) << 4; + block.y |= ((endPoint[0][1].r >> 2) & 1) << 5; + block.y |= ((endPoint[0][1].r >> 3) & 1) << 6; + block.y |= ((endPoint[0][1].r >> 4) & 1) << 7; + block.y |= ((endPoint[0][0].r >> 10) & 1) << 8; + block.y |= ((endPoint[1][0].g >> 0) & 1) << 9; + block.y |= ((endPoint[1][0].g >> 1) & 1) << 10; + block.y |= ((endPoint[1][0].g >> 2) & 1) << 11; + block.y |= ((endPoint[1][0].g >> 3) & 1) << 12; + block.y |= ((endPoint[0][1].g >> 0) & 1) << 13; + block.y |= ((endPoint[0][1].g >> 1) & 1) << 14; + block.y |= ((endPoint[0][1].g >> 2) & 1) << 15; + block.y |= ((endPoint[0][1].g >> 3) & 1) << 16; + block.y |= ((endPoint[0][0].g >> 10) & 1) << 17; + block.y |= ((endPoint[1][1].b >> 0) & 1) << 18; + block.y |= ((endPoint[1][1].g >> 0) & 1) << 19; + block.y |= ((endPoint[1][1].g >> 1) & 1) << 20; + block.y |= ((endPoint[1][1].g >> 2) & 1) << 21; + block.y |= ((endPoint[1][1].g >> 3) & 1) << 22; + block.y |= ((endPoint[0][1].b >> 0) & 1) << 23; + block.y |= ((endPoint[0][1].b >> 1) & 1) << 24; + block.y |= ((endPoint[0][1].b >> 2) & 1) << 25; + block.y |= ((endPoint[0][1].b >> 3) & 1) << 26; + block.y |= ((endPoint[0][0].b >> 10) & 1) << 27; + block.y |= ((endPoint[1][1].b >> 1) & 1) << 28; + block.y |= ((endPoint[1][0].b >> 0) & 1) << 29; + block.y |= ((endPoint[1][0].b >> 1) & 1) << 30; + block.y |= ((endPoint[1][0].b >> 2) & 1) << 31; + block.z |= ((endPoint[1][0].b >> 3) & 1) << 0; + block.z |= ((endPoint[1][0].r >> 0) & 1) << 1; + block.z |= ((endPoint[1][0].r >> 1) & 1) << 2; + block.z |= ((endPoint[1][0].r >> 2) & 1) << 3; + block.z |= ((endPoint[1][0].r >> 3) & 1) << 4; + block.z |= ((endPoint[1][0].r >> 4) & 1) << 5; + block.z |= ((endPoint[1][1].b >> 2) & 1) << 6; + block.z |= ((endPoint[1][1].r >> 0) & 1) << 7; + block.z |= ((endPoint[1][1].r >> 1) & 1) << 8; + block.z |= ((endPoint[1][1].r >> 2) & 1) << 9; + block.z |= ((endPoint[1][1].r >> 3) & 1) << 10; + block.z |= ((endPoint[1][1].r >> 4) & 1) << 11; + block.z |= ((endPoint[1][1].b >> 3) & 1) << 12; + block.z |= ((partition_index >> 0) & 1) << 13; + block.z |= ((partition_index >> 1) & 1) << 14; + block.z |= ((partition_index >> 2) & 1) << 15; + block.z |= ((partition_index >> 3) & 1) << 16; + block.z |= ((partition_index >> 4) & 1) << 17; + } + else if ( mode_type == candidateModeFlag[3]) + { + /*block.x = candidateModeMemory[3]; + block.x |= ( ( endPoint[0][0].r << 5 ) & 0x00007FE0 ) | ( ( endPoint[0][0].g << 15 ) & 0x01FF8000 ) | ( ( endPoint[0][0].b << 25 ) & 0xFE000000 ); + block.y |= ( endPoint[0][0].r >> 3 ) & 0x00000080; + block.y |= ( endPoint[0][0].g << 8 ) & 0x00040000; + block.y |= ( ( endPoint[0][0].b << 17 ) & 0x08000000 ) | ( ( endPoint[0][0].b >> 7 ) & 0x00000007 ); + block.y |= ( ( endPoint[0][1].r << 3 ) & 0x00000078 ) | ( ( endPoint[0][1].g << 13 ) & 0x0003E000 ) | ( ( endPoint[0][1].b << 23 ) & 0x07800000 ); + block.yz |= ( endPoint[1][0].gr << uint2(9, 1) ) & uint2(0x00001E00, 0x0000001E); + block.y |= ( endPoint[1][0].b << 29 ) & 0xE0000000; + block.y |= ( ( endPoint[1][1].g << 4 ) & 0x00000100 ); + block.yz |= ( endPoint[1][1].gr << uint2(19, 7) ) & uint2(0x00780000, 0x00000780); + block.yz |= ( endPoint[1][1].b << uint2(27, 9) ) & uint2(0x10000000, 0x00001000); + block.z |= ( ( endPoint[1][0].g << 7 ) & 0x00000800 ); + block.z |= ( endPoint[1][0].b >> 3 ) & 0x00000001; + block.z |= ( endPoint[1][1].b << 4 ) & 0x00000040; + block.z |= ( endPoint[1][1].b << 5 ) & 0x00000020;*/ + + block.x |= ((candidateModeMemory[3] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[3] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[3] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[3] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[3] >> 4) & 1) << 4; + block.x |= ((endPoint[0][0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0][0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0][0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0][0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0][0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0][0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0][0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0][0].r >> 7) & 1) << 12; + block.x |= ((endPoint[0][0].r >> 8) & 1) << 13; + block.x |= ((endPoint[0][0].r >> 9) & 1) << 14; + block.x |= ((endPoint[0][0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0][0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0][0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0][0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0][0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0][0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0][0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0][0].g >> 7) & 1) << 22; + block.x |= ((endPoint[0][0].g >> 8) & 1) << 23; + block.x |= ((endPoint[0][0].g >> 9) & 1) << 24; + block.x |= ((endPoint[0][0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0][0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0][0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0][0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0][0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0][0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0][0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0][0].b >> 7) & 1) << 0; + block.y |= ((endPoint[0][0].b >> 8) & 1) << 1; + block.y |= ((endPoint[0][0].b >> 9) & 1) << 2; + block.y |= ((endPoint[0][1].r >> 0) & 1) << 3; + block.y |= ((endPoint[0][1].r >> 1) & 1) << 4; + block.y |= ((endPoint[0][1].r >> 2) & 1) << 5; + block.y |= ((endPoint[0][1].r >> 3) & 1) << 6; + block.y |= ((endPoint[0][0].r >> 10) & 1) << 7; + block.y |= ((endPoint[1][1].g >> 4) & 1) << 8; + block.y |= ((endPoint[1][0].g >> 0) & 1) << 9; + block.y |= ((endPoint[1][0].g >> 1) & 1) << 10; + block.y |= ((endPoint[1][0].g >> 2) & 1) << 11; + block.y |= ((endPoint[1][0].g >> 3) & 1) << 12; + block.y |= ((endPoint[0][1].g >> 0) & 1) << 13; + block.y |= ((endPoint[0][1].g >> 1) & 1) << 14; + block.y |= ((endPoint[0][1].g >> 2) & 1) << 15; + block.y |= ((endPoint[0][1].g >> 3) & 1) << 16; + block.y |= ((endPoint[0][1].g >> 4) & 1) << 17; + block.y |= ((endPoint[0][0].g >> 10) & 1) << 18; + block.y |= ((endPoint[1][1].g >> 0) & 1) << 19; + block.y |= ((endPoint[1][1].g >> 1) & 1) << 20; + block.y |= ((endPoint[1][1].g >> 2) & 1) << 21; + block.y |= ((endPoint[1][1].g >> 3) & 1) << 22; + block.y |= ((endPoint[0][1].b >> 0) & 1) << 23; + block.y |= ((endPoint[0][1].b >> 1) & 1) << 24; + block.y |= ((endPoint[0][1].b >> 2) & 1) << 25; + block.y |= ((endPoint[0][1].b >> 3) & 1) << 26; + block.y |= ((endPoint[0][0].b >> 10) & 1) << 27; + block.y |= ((endPoint[1][1].b >> 1) & 1) << 28; + block.y |= ((endPoint[1][0].b >> 0) & 1) << 29; + block.y |= ((endPoint[1][0].b >> 1) & 1) << 30; + block.y |= ((endPoint[1][0].b >> 2) & 1) << 31; + block.z |= ((endPoint[1][0].b >> 3) & 1) << 0; + block.z |= ((endPoint[1][0].r >> 0) & 1) << 1; + block.z |= ((endPoint[1][0].r >> 1) & 1) << 2; + block.z |= ((endPoint[1][0].r >> 2) & 1) << 3; + block.z |= ((endPoint[1][0].r >> 3) & 1) << 4; + block.z |= ((endPoint[1][1].b >> 0) & 1) << 5; + block.z |= ((endPoint[1][1].b >> 2) & 1) << 6; + block.z |= ((endPoint[1][1].r >> 0) & 1) << 7; + block.z |= ((endPoint[1][1].r >> 1) & 1) << 8; + block.z |= ((endPoint[1][1].r >> 2) & 1) << 9; + block.z |= ((endPoint[1][1].r >> 3) & 1) << 10; + block.z |= ((endPoint[1][0].g >> 4) & 1) << 11; + block.z |= ((endPoint[1][1].b >> 3) & 1) << 12; + block.z |= ((partition_index >> 0) & 1) << 13; + block.z |= ((partition_index >> 1) & 1) << 14; + block.z |= ((partition_index >> 2) & 1) << 15; + block.z |= ((partition_index >> 3) & 1) << 16; + block.z |= ((partition_index >> 4) & 1) << 17; + } + else if ( mode_type == candidateModeFlag[4]) + { + /*block.x = candidateModeMemory[4]; + block.x |= ( ( endPoint[0][0].r << 5 ) & 0x00007FE0 ) | ( ( endPoint[0][0].g << 15 ) & 0x01FF8000 ) | ( ( endPoint[0][0].b << 25 ) & 0xFE000000 ); + block.y |= ( endPoint[0][0].r >> 3 ) & 0x00000080; + block.y |= ( endPoint[0][0].g << 7 ) & 0x00020000; + block.y |= ( ( endPoint[0][0].b << 18 ) & 0x10000000 ) | ( ( endPoint[0][0].b >> 7 ) & 0x00000007 ); + block.y |= ( ( endPoint[0][1].r << 3 ) & 0x00000078 ) | ( ( endPoint[0][1].g << 13 ) & 0x0001E000 ) | ( ( endPoint[0][1].b << 23 ) & 0x0F800000 ); + block.y |= ( ( endPoint[1][0].g << 9 ) & 0x00001E00 ) | ( ( endPoint[1][0].b << 4 ) & 0x00000100 ); + block.y |= ( endPoint[1][0].b << 29 ) & 0xE0000000; + block.yz |= ( endPoint[1][1].gr << uint2(19, 7) ) & uint2(0x00780000, 0x00000780); + block.yz |= ( endPoint[1][1].b << uint2(18, 4) ) & uint2(0x00040000, 0x00000060); + block.z |= ( endPoint[1][0].r << 1 ) & 0x0000001E; + block.z |= ( endPoint[1][0].b >> 3 ) & 0x00000001; + block.z |= ( ( endPoint[1][1].b << 7 ) & 0x00000800 ) | ( ( endPoint[1][1].b << 9 ) & 0x00001000 );*/ + + block.x |= ((candidateModeMemory[4] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[4] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[4] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[4] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[4] >> 4) & 1) << 4; + block.x |= ((endPoint[0][0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0][0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0][0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0][0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0][0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0][0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0][0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0][0].r >> 7) & 1) << 12; + block.x |= ((endPoint[0][0].r >> 8) & 1) << 13; + block.x |= ((endPoint[0][0].r >> 9) & 1) << 14; + block.x |= ((endPoint[0][0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0][0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0][0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0][0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0][0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0][0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0][0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0][0].g >> 7) & 1) << 22; + block.x |= ((endPoint[0][0].g >> 8) & 1) << 23; + block.x |= ((endPoint[0][0].g >> 9) & 1) << 24; + block.x |= ((endPoint[0][0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0][0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0][0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0][0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0][0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0][0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0][0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0][0].b >> 7) & 1) << 0; + block.y |= ((endPoint[0][0].b >> 8) & 1) << 1; + block.y |= ((endPoint[0][0].b >> 9) & 1) << 2; + block.y |= ((endPoint[0][1].r >> 0) & 1) << 3; + block.y |= ((endPoint[0][1].r >> 1) & 1) << 4; + block.y |= ((endPoint[0][1].r >> 2) & 1) << 5; + block.y |= ((endPoint[0][1].r >> 3) & 1) << 6; + block.y |= ((endPoint[0][0].r >> 10) & 1) << 7; + block.y |= ((endPoint[1][0].b >> 4) & 1) << 8; + block.y |= ((endPoint[1][0].g >> 0) & 1) << 9; + block.y |= ((endPoint[1][0].g >> 1) & 1) << 10; + block.y |= ((endPoint[1][0].g >> 2) & 1) << 11; + block.y |= ((endPoint[1][0].g >> 3) & 1) << 12; + block.y |= ((endPoint[0][1].g >> 0) & 1) << 13; + block.y |= ((endPoint[0][1].g >> 1) & 1) << 14; + block.y |= ((endPoint[0][1].g >> 2) & 1) << 15; + block.y |= ((endPoint[0][1].g >> 3) & 1) << 16; + block.y |= ((endPoint[0][0].g >> 10) & 1) << 17; + block.y |= ((endPoint[1][1].b >> 0) & 1) << 18; + block.y |= ((endPoint[1][1].g >> 0) & 1) << 19; + block.y |= ((endPoint[1][1].g >> 1) & 1) << 20; + block.y |= ((endPoint[1][1].g >> 2) & 1) << 21; + block.y |= ((endPoint[1][1].g >> 3) & 1) << 22; + block.y |= ((endPoint[0][1].b >> 0) & 1) << 23; + block.y |= ((endPoint[0][1].b >> 1) & 1) << 24; + block.y |= ((endPoint[0][1].b >> 2) & 1) << 25; + block.y |= ((endPoint[0][1].b >> 3) & 1) << 26; + block.y |= ((endPoint[0][1].b >> 4) & 1) << 27; + block.y |= ((endPoint[0][0].b >> 10) & 1) << 28; + block.y |= ((endPoint[1][0].b >> 0) & 1) << 29; + block.y |= ((endPoint[1][0].b >> 1) & 1) << 30; + block.y |= ((endPoint[1][0].b >> 2) & 1) << 31; + block.z |= ((endPoint[1][0].b >> 3) & 1) << 0; + block.z |= ((endPoint[1][0].r >> 0) & 1) << 1; + block.z |= ((endPoint[1][0].r >> 1) & 1) << 2; + block.z |= ((endPoint[1][0].r >> 2) & 1) << 3; + block.z |= ((endPoint[1][0].r >> 3) & 1) << 4; + block.z |= ((endPoint[1][1].b >> 1) & 1) << 5; + block.z |= ((endPoint[1][1].b >> 2) & 1) << 6; + block.z |= ((endPoint[1][1].r >> 0) & 1) << 7; + block.z |= ((endPoint[1][1].r >> 1) & 1) << 8; + block.z |= ((endPoint[1][1].r >> 2) & 1) << 9; + block.z |= ((endPoint[1][1].r >> 3) & 1) << 10; + block.z |= ((endPoint[1][1].b >> 4) & 1) << 11; + block.z |= ((endPoint[1][1].b >> 3) & 1) << 12; + block.z |= ((partition_index >> 0) & 1) << 13; + block.z |= ((partition_index >> 1) & 1) << 14; + block.z |= ((partition_index >> 2) & 1) << 15; + block.z |= ((partition_index >> 3) & 1) << 16; + block.z |= ((partition_index >> 4) & 1) << 17; + } + else if ( mode_type == candidateModeFlag[5]) + { + /*block.x = candidateModeMemory[5]; + block.x |= ( ( endPoint[0][0].r << 5 ) & 0x00003FE0 ) | ( ( endPoint[0][0].g << 15 ) & 0x00FF8000 ) | ( ( endPoint[0][0].b << 25 ) & 0xFE000000); + block.y |= ( endPoint[0][0].b >> 7 ) & 0x00000003; + block.y |= ( ( endPoint[0][1].r << 3 ) & 0x000000F8 ) | ( ( endPoint[0][1].g << 13 ) & 0x0003E000 ) | ( ( endPoint[0][1].b << 23 ) & 0x0F800000 ); + block.x |= ( ( endPoint[1][0].g << 20 ) & 0x01000000 ) | ( ( endPoint[1][0].b << 10 ) & 0x00004000 ); + block.yz |= ( endPoint[1][0].gr << uint2(9, 1) ) & uint2(0x00001E00, 0x0000003E); + block.y |= ( endPoint[1][0].b << 29 ) & 0xE0000000; + block.y |= ( ( endPoint[1][1].g << 4 ) & 0x00000100 ) | ( ( endPoint[1][1].b >> 2 ) & 0x00000004 ); + block.y |= ( ( endPoint[1][1].b << 27 ) & 0x10000000 ); + block.yz |= ( endPoint[1][1].gr << uint2(19, 7) ) & uint2(0x00780000, 0x00000F80); + block.yz |= ( endPoint[1][1].b << uint2(18, 4) ) & uint2(0x00040000, 0x00000040); + block.z |= ( endPoint[1][0].b >> 3 ) & 0x00000001; + block.z |= ( ( endPoint[1][1].b << 9 ) & 0x00001000 );*/ + + block.x |= ((candidateModeMemory[5] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[5] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[5] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[5] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[5] >> 4) & 1) << 4; + block.x |= ((endPoint[0][0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0][0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0][0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0][0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0][0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0][0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0][0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0][0].r >> 7) & 1) << 12; + block.x |= ((endPoint[0][0].r >> 8) & 1) << 13; + block.x |= ((endPoint[1][0].b >> 4) & 1) << 14; + block.x |= ((endPoint[0][0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0][0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0][0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0][0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0][0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0][0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0][0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0][0].g >> 7) & 1) << 22; + block.x |= ((endPoint[0][0].g >> 8) & 1) << 23; + block.x |= ((endPoint[1][0].g >> 4) & 1) << 24; + block.x |= ((endPoint[0][0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0][0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0][0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0][0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0][0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0][0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0][0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0][0].b >> 7) & 1) << 0; + block.y |= ((endPoint[0][0].b >> 8) & 1) << 1; + block.y |= ((endPoint[1][1].b >> 4) & 1) << 2; + block.y |= ((endPoint[0][1].r >> 0) & 1) << 3; + block.y |= ((endPoint[0][1].r >> 1) & 1) << 4; + block.y |= ((endPoint[0][1].r >> 2) & 1) << 5; + block.y |= ((endPoint[0][1].r >> 3) & 1) << 6; + block.y |= ((endPoint[0][1].r >> 4) & 1) << 7; + block.y |= ((endPoint[1][1].g >> 4) & 1) << 8; + block.y |= ((endPoint[1][0].g >> 0) & 1) << 9; + block.y |= ((endPoint[1][0].g >> 1) & 1) << 10; + block.y |= ((endPoint[1][0].g >> 2) & 1) << 11; + block.y |= ((endPoint[1][0].g >> 3) & 1) << 12; + block.y |= ((endPoint[0][1].g >> 0) & 1) << 13; + block.y |= ((endPoint[0][1].g >> 1) & 1) << 14; + block.y |= ((endPoint[0][1].g >> 2) & 1) << 15; + block.y |= ((endPoint[0][1].g >> 3) & 1) << 16; + block.y |= ((endPoint[0][1].g >> 4) & 1) << 17; + block.y |= ((endPoint[1][1].b >> 0) & 1) << 18; + block.y |= ((endPoint[1][1].g >> 0) & 1) << 19; + block.y |= ((endPoint[1][1].g >> 1) & 1) << 20; + block.y |= ((endPoint[1][1].g >> 2) & 1) << 21; + block.y |= ((endPoint[1][1].g >> 3) & 1) << 22; + block.y |= ((endPoint[0][1].b >> 0) & 1) << 23; + block.y |= ((endPoint[0][1].b >> 1) & 1) << 24; + block.y |= ((endPoint[0][1].b >> 2) & 1) << 25; + block.y |= ((endPoint[0][1].b >> 3) & 1) << 26; + block.y |= ((endPoint[0][1].b >> 4) & 1) << 27; + block.y |= ((endPoint[1][1].b >> 1) & 1) << 28; + block.y |= ((endPoint[1][0].b >> 0) & 1) << 29; + block.y |= ((endPoint[1][0].b >> 1) & 1) << 30; + block.y |= ((endPoint[1][0].b >> 2) & 1) << 31; + block.z |= ((endPoint[1][0].b >> 3) & 1) << 0; + block.z |= ((endPoint[1][0].r >> 0) & 1) << 1; + block.z |= ((endPoint[1][0].r >> 1) & 1) << 2; + block.z |= ((endPoint[1][0].r >> 2) & 1) << 3; + block.z |= ((endPoint[1][0].r >> 3) & 1) << 4; + block.z |= ((endPoint[1][0].r >> 4) & 1) << 5; + block.z |= ((endPoint[1][1].b >> 2) & 1) << 6; + block.z |= ((endPoint[1][1].r >> 0) & 1) << 7; + block.z |= ((endPoint[1][1].r >> 1) & 1) << 8; + block.z |= ((endPoint[1][1].r >> 2) & 1) << 9; + block.z |= ((endPoint[1][1].r >> 3) & 1) << 10; + block.z |= ((endPoint[1][1].r >> 4) & 1) << 11; + block.z |= ((endPoint[1][1].b >> 3) & 1) << 12; + block.z |= ((partition_index >> 0) & 1) << 13; + block.z |= ((partition_index >> 1) & 1) << 14; + block.z |= ((partition_index >> 2) & 1) << 15; + block.z |= ((partition_index >> 3) & 1) << 16; + block.z |= ((partition_index >> 4) & 1) << 17; + } + else if ( mode_type == candidateModeFlag[6]) + { + /*block.x = candidateModeMemory[6]; + block.x |= ( ( endPoint[0][0].r << 5 ) & 0x00001FE0 ) | ( ( endPoint[0][0].g << 15 ) & 0x007F8000 ) | ( ( endPoint[0][0].b << 25 ) & 0xFE000000 ); + block.y |= ( endPoint[0][0].b >> 7 ) & 0x00000001; + block.y |= ( ( endPoint[0][1].r << 3 ) & 0x000001F8 ) | ( ( endPoint[0][1].g << 13 ) & 0x0003E000 ) | ( ( endPoint[0][1].b << 23 ) & 0x0F800000 ); + block.x |= ( ( endPoint[1][0].g << 20 ) & 0x01000000 ) | ( ( endPoint[1][0].b << 10 ) & 0x00004000); + block.x |= ( ( endPoint[1][1].g << 9 ) & 0x00002000 ) | ( ( endPoint[1][1].b << 21 ) & 0x00800000); + block.yz |= ( endPoint[1][0].gr << uint2(9, 1) ) & uint2(0x00001E00, 0x0000007E); + block.y |= ( endPoint[1][0].b << 29 ) & 0xE0000000; + block.yz |= ( endPoint[1][1].gr << uint2(19, 7) ) & uint2(0x00780000, 0x00001F80); + block.y |= ( ( endPoint[1][1].b >> 2 ) & 0x00000006 ); + block.y |= ( ( endPoint[1][1].b << 27 ) & 0x10000000 ) | ( ( endPoint[1][1].b << 18 ) & 0x00040000 ); + block.z |= ( endPoint[1][0].b >> 3 ) & 0x00000001;*/ + + block.x |= ((candidateModeMemory[6] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[6] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[6] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[6] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[6] >> 4) & 1) << 4; + block.x |= ((endPoint[0][0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0][0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0][0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0][0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0][0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0][0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0][0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0][0].r >> 7) & 1) << 12; + block.x |= ((endPoint[1][1].g >> 4) & 1) << 13; + block.x |= ((endPoint[1][0].b >> 4) & 1) << 14; + block.x |= ((endPoint[0][0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0][0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0][0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0][0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0][0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0][0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0][0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0][0].g >> 7) & 1) << 22; + block.x |= ((endPoint[1][1].b >> 2) & 1) << 23; + block.x |= ((endPoint[1][0].g >> 4) & 1) << 24; + block.x |= ((endPoint[0][0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0][0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0][0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0][0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0][0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0][0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0][0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0][0].b >> 7) & 1) << 0; + block.y |= ((endPoint[1][1].b >> 3) & 1) << 1; + block.y |= ((endPoint[1][1].b >> 4) & 1) << 2; + block.y |= ((endPoint[0][1].r >> 0) & 1) << 3; + block.y |= ((endPoint[0][1].r >> 1) & 1) << 4; + block.y |= ((endPoint[0][1].r >> 2) & 1) << 5; + block.y |= ((endPoint[0][1].r >> 3) & 1) << 6; + block.y |= ((endPoint[0][1].r >> 4) & 1) << 7; + block.y |= ((endPoint[0][1].r >> 5) & 1) << 8; + block.y |= ((endPoint[1][0].g >> 0) & 1) << 9; + block.y |= ((endPoint[1][0].g >> 1) & 1) << 10; + block.y |= ((endPoint[1][0].g >> 2) & 1) << 11; + block.y |= ((endPoint[1][0].g >> 3) & 1) << 12; + block.y |= ((endPoint[0][1].g >> 0) & 1) << 13; + block.y |= ((endPoint[0][1].g >> 1) & 1) << 14; + block.y |= ((endPoint[0][1].g >> 2) & 1) << 15; + block.y |= ((endPoint[0][1].g >> 3) & 1) << 16; + block.y |= ((endPoint[0][1].g >> 4) & 1) << 17; + block.y |= ((endPoint[1][1].b >> 0) & 1) << 18; + block.y |= ((endPoint[1][1].g >> 0) & 1) << 19; + block.y |= ((endPoint[1][1].g >> 1) & 1) << 20; + block.y |= ((endPoint[1][1].g >> 2) & 1) << 21; + block.y |= ((endPoint[1][1].g >> 3) & 1) << 22; + block.y |= ((endPoint[0][1].b >> 0) & 1) << 23; + block.y |= ((endPoint[0][1].b >> 1) & 1) << 24; + block.y |= ((endPoint[0][1].b >> 2) & 1) << 25; + block.y |= ((endPoint[0][1].b >> 3) & 1) << 26; + block.y |= ((endPoint[0][1].b >> 4) & 1) << 27; + block.y |= ((endPoint[1][1].b >> 1) & 1) << 28; + block.y |= ((endPoint[1][0].b >> 0) & 1) << 29; + block.y |= ((endPoint[1][0].b >> 1) & 1) << 30; + block.y |= ((endPoint[1][0].b >> 2) & 1) << 31; + block.z |= ((endPoint[1][0].b >> 3) & 1) << 0; + block.z |= ((endPoint[1][0].r >> 0) & 1) << 1; + block.z |= ((endPoint[1][0].r >> 1) & 1) << 2; + block.z |= ((endPoint[1][0].r >> 2) & 1) << 3; + block.z |= ((endPoint[1][0].r >> 3) & 1) << 4; + block.z |= ((endPoint[1][0].r >> 4) & 1) << 5; + block.z |= ((endPoint[1][0].r >> 5) & 1) << 6; + block.z |= ((endPoint[1][1].r >> 0) & 1) << 7; + block.z |= ((endPoint[1][1].r >> 1) & 1) << 8; + block.z |= ((endPoint[1][1].r >> 2) & 1) << 9; + block.z |= ((endPoint[1][1].r >> 3) & 1) << 10; + block.z |= ((endPoint[1][1].r >> 4) & 1) << 11; + block.z |= ((endPoint[1][1].r >> 5) & 1) << 12; + block.z |= ((partition_index >> 0) & 1) << 13; + block.z |= ((partition_index >> 1) & 1) << 14; + block.z |= ((partition_index >> 2) & 1) << 15; + block.z |= ((partition_index >> 3) & 1) << 16; + block.z |= ((partition_index >> 4) & 1) << 17; + } + else if ( mode_type == candidateModeFlag[7]) + { + /*block.x = candidateModeMemory[7]; + block.x |= ( ( endPoint[0][0].r << 5 ) & 0x00001FE0 ) | ( ( endPoint[0][0].g << 15 ) & 0x007F8000 ) | ( ( endPoint[0][0].b << 25 ) & 0xFE000000 ); + block.y |= ( endPoint[0][0].b >> 7 ) & 0x00000001; + block.y |= ( ( endPoint[0][1].r << 3 ) & 0x000000F8 ) | ( ( endPoint[0][1].g << 13 ) & 0x0007E000 ) | ( ( endPoint[0][1].b << 23 ) & 0x0F800000 ); + block.x |= ( ( endPoint[1][0].g << 20 ) & 0x01000000 ) | ( ( endPoint[1][0].b << 10 ) & 0x00004000 ); + block.x |= ( ( endPoint[1][0].g << 18 ) & 0x00800000 ); + block.x |= ( ( endPoint[1][1].b << 13 ) & 0x00002000 ); + block.yz |= ( endPoint[1][0].gr << uint2(9, 1) ) & uint2(0x00001E00, 0x0000003E); + block.yz |= ( endPoint[1][1].gr << uint2(19, 7) ) & uint2(0x00780000, 0x00000F80); + block.y |= ( endPoint[1][0].b << 29 ) & 0xE0000000; + block.y |= ( ( endPoint[1][1].g >> 4 ) & 0x00000002 ) | ( ( endPoint[1][1].g << 4 ) & 0x00000100 ) | ( ( endPoint[1][1].b >> 2 ) & 0x00000004 ); + block.y |= ( endPoint[1][1].b << 27 ) & 0x10000000; + block.z |= ( endPoint[1][0].b >> 3 ) & 0x00000001; + block.z |= ( ( endPoint[1][1].b << 9 ) & 0x00001000 ) | ( ( endPoint[1][1].b << 4 ) & 0x00000040 );*/ + + block.x |= ((candidateModeMemory[7] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[7] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[7] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[7] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[7] >> 4) & 1) << 4; + block.x |= ((endPoint[0][0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0][0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0][0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0][0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0][0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0][0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0][0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0][0].r >> 7) & 1) << 12; + block.x |= ((endPoint[1][1].b >> 0) & 1) << 13; + block.x |= ((endPoint[1][0].b >> 4) & 1) << 14; + block.x |= ((endPoint[0][0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0][0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0][0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0][0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0][0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0][0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0][0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0][0].g >> 7) & 1) << 22; + block.x |= ((endPoint[1][0].g >> 5) & 1) << 23; + block.x |= ((endPoint[1][0].g >> 4) & 1) << 24; + block.x |= ((endPoint[0][0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0][0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0][0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0][0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0][0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0][0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0][0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0][0].b >> 7) & 1) << 0; + block.y |= ((endPoint[1][1].g >> 5) & 1) << 1; + block.y |= ((endPoint[1][1].b >> 4) & 1) << 2; + block.y |= ((endPoint[0][1].r >> 0) & 1) << 3; + block.y |= ((endPoint[0][1].r >> 1) & 1) << 4; + block.y |= ((endPoint[0][1].r >> 2) & 1) << 5; + block.y |= ((endPoint[0][1].r >> 3) & 1) << 6; + block.y |= ((endPoint[0][1].r >> 4) & 1) << 7; + block.y |= ((endPoint[1][1].g >> 4) & 1) << 8; + block.y |= ((endPoint[1][0].g >> 0) & 1) << 9; + block.y |= ((endPoint[1][0].g >> 1) & 1) << 10; + block.y |= ((endPoint[1][0].g >> 2) & 1) << 11; + block.y |= ((endPoint[1][0].g >> 3) & 1) << 12; + block.y |= ((endPoint[0][1].g >> 0) & 1) << 13; + block.y |= ((endPoint[0][1].g >> 1) & 1) << 14; + block.y |= ((endPoint[0][1].g >> 2) & 1) << 15; + block.y |= ((endPoint[0][1].g >> 3) & 1) << 16; + block.y |= ((endPoint[0][1].g >> 4) & 1) << 17; + block.y |= ((endPoint[0][1].g >> 5) & 1) << 18; + block.y |= ((endPoint[1][1].g >> 0) & 1) << 19; + block.y |= ((endPoint[1][1].g >> 1) & 1) << 20; + block.y |= ((endPoint[1][1].g >> 2) & 1) << 21; + block.y |= ((endPoint[1][1].g >> 3) & 1) << 22; + block.y |= ((endPoint[0][1].b >> 0) & 1) << 23; + block.y |= ((endPoint[0][1].b >> 1) & 1) << 24; + block.y |= ((endPoint[0][1].b >> 2) & 1) << 25; + block.y |= ((endPoint[0][1].b >> 3) & 1) << 26; + block.y |= ((endPoint[0][1].b >> 4) & 1) << 27; + block.y |= ((endPoint[1][1].b >> 1) & 1) << 28; + block.y |= ((endPoint[1][0].b >> 0) & 1) << 29; + block.y |= ((endPoint[1][0].b >> 1) & 1) << 30; + block.y |= ((endPoint[1][0].b >> 2) & 1) << 31; + block.z |= ((endPoint[1][0].b >> 3) & 1) << 0; + block.z |= ((endPoint[1][0].r >> 0) & 1) << 1; + block.z |= ((endPoint[1][0].r >> 1) & 1) << 2; + block.z |= ((endPoint[1][0].r >> 2) & 1) << 3; + block.z |= ((endPoint[1][0].r >> 3) & 1) << 4; + block.z |= ((endPoint[1][0].r >> 4) & 1) << 5; + block.z |= ((endPoint[1][1].b >> 2) & 1) << 6; + block.z |= ((endPoint[1][1].r >> 0) & 1) << 7; + block.z |= ((endPoint[1][1].r >> 1) & 1) << 8; + block.z |= ((endPoint[1][1].r >> 2) & 1) << 9; + block.z |= ((endPoint[1][1].r >> 3) & 1) << 10; + block.z |= ((endPoint[1][1].r >> 4) & 1) << 11; + block.z |= ((endPoint[1][1].b >> 3) & 1) << 12; + block.z |= ((partition_index >> 0) & 1) << 13; + block.z |= ((partition_index >> 1) & 1) << 14; + block.z |= ((partition_index >> 2) & 1) << 15; + block.z |= ((partition_index >> 3) & 1) << 16; + block.z |= ((partition_index >> 4) & 1) << 17; + } + else if ( mode_type == candidateModeFlag[8]) + { + /*block.x = candidateModeMemory[8]; + block.x |= ( ( endPoint[0][0].r << 5 ) & 0x00001FE0 ) | ( ( endPoint[0][0].g << 15 ) & 0x007F8000 ) | ( ( endPoint[0][0].b << 25 ) & 0xFE000000 ); + block.y |= ( endPoint[0][0].b >> 7 ) & 0x00000001; + block.y |= ( ( endPoint[0][1].r << 3 ) & 0x000000F8 ) | ( ( endPoint[0][1].g << 13 ) & 0x0003E000 ) | ( ( endPoint[0][1].b << 23 ) & 0x1F800000 ); + block.x |= ( ( endPoint[1][0].g << 20 ) & 0x01000000 ) | ( ( endPoint[1][0].b << 10 ) & 0x00004000 ); + block.x |= ( ( endPoint[1][0].b << 18 ) & 0x00800000 ); + block.x |= ( endPoint[1][1].b << 12 ) & 0x00002000; + block.y |= ( endPoint[1][0].b << 29 ) & 0xE0000000; + block.y |= ( ( endPoint[1][1].g << 4 ) & 0x00000100 ) | ( ( endPoint[1][1].b >> 4 ) & 0x00000002 ) | ( ( endPoint[1][1].b >> 2 ) & 0x00000004 ); + block.yz |= ( endPoint[1][0].gr << uint2(9, 1) ) & uint2(0x00001E00, 0x0000003E); + block.yz |= ( endPoint[1][1].gr << uint2(19, 7) ) & uint2(0x00780000, 0x00000F80); + block.y |= ( endPoint[1][1].b << 18 ) & 0x00040000; + block.z |= ( endPoint[1][0].b >> 3 ) & 0x00000001; + block.z |= ( ( endPoint[1][1].b << 9 ) & 0x00001000 ) | ( ( endPoint[1][1].b << 4 ) & 0x00000040 );*/ + + block.x |= ((candidateModeMemory[8] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[8] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[8] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[8] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[8] >> 4) & 1) << 4; + block.x |= ((endPoint[0][0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0][0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0][0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0][0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0][0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0][0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0][0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0][0].r >> 7) & 1) << 12; + block.x |= ((endPoint[1][1].b >> 1) & 1) << 13; + block.x |= ((endPoint[1][0].b >> 4) & 1) << 14; + block.x |= ((endPoint[0][0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0][0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0][0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0][0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0][0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0][0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0][0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0][0].g >> 7) & 1) << 22; + block.x |= ((endPoint[1][0].b >> 5) & 1) << 23; + block.x |= ((endPoint[1][0].g >> 4) & 1) << 24; + block.x |= ((endPoint[0][0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0][0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0][0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0][0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0][0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0][0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0][0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0][0].b >> 7) & 1) << 0; + block.y |= ((endPoint[1][1].b >> 5) & 1) << 1; + block.y |= ((endPoint[1][1].b >> 4) & 1) << 2; + block.y |= ((endPoint[0][1].r >> 0) & 1) << 3; + block.y |= ((endPoint[0][1].r >> 1) & 1) << 4; + block.y |= ((endPoint[0][1].r >> 2) & 1) << 5; + block.y |= ((endPoint[0][1].r >> 3) & 1) << 6; + block.y |= ((endPoint[0][1].r >> 4) & 1) << 7; + block.y |= ((endPoint[1][1].g >> 4) & 1) << 8; + block.y |= ((endPoint[1][0].g >> 0) & 1) << 9; + block.y |= ((endPoint[1][0].g >> 1) & 1) << 10; + block.y |= ((endPoint[1][0].g >> 2) & 1) << 11; + block.y |= ((endPoint[1][0].g >> 3) & 1) << 12; + block.y |= ((endPoint[0][1].g >> 0) & 1) << 13; + block.y |= ((endPoint[0][1].g >> 1) & 1) << 14; + block.y |= ((endPoint[0][1].g >> 2) & 1) << 15; + block.y |= ((endPoint[0][1].g >> 3) & 1) << 16; + block.y |= ((endPoint[0][1].g >> 4) & 1) << 17; + block.y |= ((endPoint[1][1].b >> 0) & 1) << 18; + block.y |= ((endPoint[1][1].g >> 0) & 1) << 19; + block.y |= ((endPoint[1][1].g >> 1) & 1) << 20; + block.y |= ((endPoint[1][1].g >> 2) & 1) << 21; + block.y |= ((endPoint[1][1].g >> 3) & 1) << 22; + block.y |= ((endPoint[0][1].b >> 0) & 1) << 23; + block.y |= ((endPoint[0][1].b >> 1) & 1) << 24; + block.y |= ((endPoint[0][1].b >> 2) & 1) << 25; + block.y |= ((endPoint[0][1].b >> 3) & 1) << 26; + block.y |= ((endPoint[0][1].b >> 4) & 1) << 27; + block.y |= ((endPoint[0][1].b >> 5) & 1) << 28; + block.y |= ((endPoint[1][0].b >> 0) & 1) << 29; + block.y |= ((endPoint[1][0].b >> 1) & 1) << 30; + block.y |= ((endPoint[1][0].b >> 2) & 1) << 31; + block.z |= ((endPoint[1][0].b >> 3) & 1) << 0; + block.z |= ((endPoint[1][0].r >> 0) & 1) << 1; + block.z |= ((endPoint[1][0].r >> 1) & 1) << 2; + block.z |= ((endPoint[1][0].r >> 2) & 1) << 3; + block.z |= ((endPoint[1][0].r >> 3) & 1) << 4; + block.z |= ((endPoint[1][0].r >> 4) & 1) << 5; + block.z |= ((endPoint[1][1].b >> 2) & 1) << 6; + block.z |= ((endPoint[1][1].r >> 0) & 1) << 7; + block.z |= ((endPoint[1][1].r >> 1) & 1) << 8; + block.z |= ((endPoint[1][1].r >> 2) & 1) << 9; + block.z |= ((endPoint[1][1].r >> 3) & 1) << 10; + block.z |= ((endPoint[1][1].r >> 4) & 1) << 11; + block.z |= ((endPoint[1][1].b >> 3) & 1) << 12; + block.z |= ((partition_index >> 0) & 1) << 13; + block.z |= ((partition_index >> 1) & 1) << 14; + block.z |= ((partition_index >> 2) & 1) << 15; + block.z |= ((partition_index >> 3) & 1) << 16; + block.z |= ((partition_index >> 4) & 1) << 17; + } + else if ( mode_type == candidateModeFlag[9]) + { + /*block.x = candidateModeMemory[9]; + block.x |= ( ( endPoint[0][0].r << 5 ) & 0x000007E0 ) | ( ( endPoint[0][0].g << 15 ) & 0x001F8000 ) | ( ( endPoint[0][0].b << 25 ) & 0x7E000000 ); + block.y |= ( ( endPoint[0][1].r << 3 ) & 0x000001F8 ) | ( ( endPoint[0][1].g << 13 ) & 0x0007E000 ) | ( ( endPoint[0][1].b << 23 ) & 0x1F800000 ); + block.x |= ( ( endPoint[1][0].g << 16 ) & 0x00200000 ) | ( ( endPoint[1][0].g << 20 ) & 0x01000000 ); + block.x |= ( ( endPoint[1][0].b << 17 ) & 0x00400000 ) | ( ( endPoint[1][0].b << 10 ) & 0x00004000 ); + block.x |= ( ( endPoint[1][1].b << 21 ) & 0x00800000 ) | ( ( endPoint[1][1].b << 12 ) & 0x00003000 ); + block.x |= ( ( endPoint[1][1].g << 26 ) & 0x80000000 ) | ( ( endPoint[1][1].g << 7 ) & 0x00000800 ); + block.yz |= ( endPoint[1][0].gr << uint2(9, 1) ) & uint2(0x00001E00, 0x0000007E); + block.yz |= ( endPoint[1][1].gr << uint2(19, 7) ) & uint2(0x00780000, 0x00001F80); + block.y |= ( endPoint[1][0].b << 29 ) & 0xE0000000; + block.y |= ( ( endPoint[1][1].b >> 4 ) & 0x00000002 ) | ( ( endPoint[1][1].b >> 2 ) & 0x00000004 ) | ( ( endPoint[1][1].b >> 3 ) & 0x00000001 ); + block.z |= ( endPoint[1][0].b >> 3 ) & 0x00000001;*/ + + block.x |= ((candidateModeMemory[9] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[9] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[9] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[9] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[9] >> 4) & 1) << 4; + block.x |= ((endPoint[0][0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0][0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0][0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0][0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0][0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0][0].r >> 5) & 1) << 10; + block.x |= ((endPoint[1][1].g >> 4) & 1) << 11; + block.x |= ((endPoint[1][1].b >> 0) & 1) << 12; + block.x |= ((endPoint[1][1].b >> 1) & 1) << 13; + block.x |= ((endPoint[1][0].b >> 4) & 1) << 14; + block.x |= ((endPoint[0][0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0][0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0][0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0][0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0][0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0][0].g >> 5) & 1) << 20; + block.x |= ((endPoint[1][0].g >> 5) & 1) << 21; + block.x |= ((endPoint[1][0].b >> 5) & 1) << 22; + block.x |= ((endPoint[1][1].b >> 2) & 1) << 23; + block.x |= ((endPoint[1][0].g >> 4) & 1) << 24; + block.x |= ((endPoint[0][0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0][0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0][0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0][0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0][0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0][0].b >> 5) & 1) << 30; + block.x |= ((endPoint[1][1].g >> 5) & 1) << 31; + block.y |= ((endPoint[1][1].b >> 3) & 1) << 0; + block.y |= ((endPoint[1][1].b >> 5) & 1) << 1; + block.y |= ((endPoint[1][1].b >> 4) & 1) << 2; + block.y |= ((endPoint[0][1].r >> 0) & 1) << 3; + block.y |= ((endPoint[0][1].r >> 1) & 1) << 4; + block.y |= ((endPoint[0][1].r >> 2) & 1) << 5; + block.y |= ((endPoint[0][1].r >> 3) & 1) << 6; + block.y |= ((endPoint[0][1].r >> 4) & 1) << 7; + block.y |= ((endPoint[0][1].r >> 5) & 1) << 8; + block.y |= ((endPoint[1][0].g >> 0) & 1) << 9; + block.y |= ((endPoint[1][0].g >> 1) & 1) << 10; + block.y |= ((endPoint[1][0].g >> 2) & 1) << 11; + block.y |= ((endPoint[1][0].g >> 3) & 1) << 12; + block.y |= ((endPoint[0][1].g >> 0) & 1) << 13; + block.y |= ((endPoint[0][1].g >> 1) & 1) << 14; + block.y |= ((endPoint[0][1].g >> 2) & 1) << 15; + block.y |= ((endPoint[0][1].g >> 3) & 1) << 16; + block.y |= ((endPoint[0][1].g >> 4) & 1) << 17; + block.y |= ((endPoint[0][1].g >> 5) & 1) << 18; + block.y |= ((endPoint[1][1].g >> 0) & 1) << 19; + block.y |= ((endPoint[1][1].g >> 1) & 1) << 20; + block.y |= ((endPoint[1][1].g >> 2) & 1) << 21; + block.y |= ((endPoint[1][1].g >> 3) & 1) << 22; + block.y |= ((endPoint[0][1].b >> 0) & 1) << 23; + block.y |= ((endPoint[0][1].b >> 1) & 1) << 24; + block.y |= ((endPoint[0][1].b >> 2) & 1) << 25; + block.y |= ((endPoint[0][1].b >> 3) & 1) << 26; + block.y |= ((endPoint[0][1].b >> 4) & 1) << 27; + block.y |= ((endPoint[0][1].b >> 5) & 1) << 28; + block.y |= ((endPoint[1][0].b >> 0) & 1) << 29; + block.y |= ((endPoint[1][0].b >> 1) & 1) << 30; + block.y |= ((endPoint[1][0].b >> 2) & 1) << 31; + block.z |= ((endPoint[1][0].b >> 3) & 1) << 0; + block.z |= ((endPoint[1][0].r >> 0) & 1) << 1; + block.z |= ((endPoint[1][0].r >> 1) & 1) << 2; + block.z |= ((endPoint[1][0].r >> 2) & 1) << 3; + block.z |= ((endPoint[1][0].r >> 3) & 1) << 4; + block.z |= ((endPoint[1][0].r >> 4) & 1) << 5; + block.z |= ((endPoint[1][0].r >> 5) & 1) << 6; + block.z |= ((endPoint[1][1].r >> 0) & 1) << 7; + block.z |= ((endPoint[1][1].r >> 1) & 1) << 8; + block.z |= ((endPoint[1][1].r >> 2) & 1) << 9; + block.z |= ((endPoint[1][1].r >> 3) & 1) << 10; + block.z |= ((endPoint[1][1].r >> 4) & 1) << 11; + block.z |= ((endPoint[1][1].r >> 5) & 1) << 12; + block.z |= ((partition_index >> 0) & 1) << 13; + block.z |= ((partition_index >> 1) & 1) << 14; + block.z |= ((partition_index >> 2) & 1) << 15; + block.z |= ((partition_index >> 3) & 1) << 16; + block.z |= ((partition_index >> 4) & 1) << 17; + } +} +void block_package( inout uint4 block, int2x3 endPoint, uint mode_type ) // for mode 11 - 14 +{ + /*block.x = ( ( endPoint[0].r << 5 ) & 0x00007FE0 ) | ( ( endPoint[0].g << 15 ) & 0x01FF8000 ) | ( ( endPoint[0].b << 25 ) & 0xFE000000 ); + block.y |= ( endPoint[0].b >> 7 ) & 0x00000007;*/ + + block.xy = 0; + block.z &= 0xFFFFFFFE; + + + if ( mode_type == candidateModeFlag[10]) + { + /* block.x |= candidateModeMemory[10]; + block.y |= ( ( endPoint[1].r << 3 ) & 0x00001FF8 ) | ( ( endPoint[1].g << 13 ) & 0x007FE000 ) | ( ( endPoint[1].b << 23 ) & 0xFF800000 ); + block.z |= ( endPoint[1].b >> 9 ) & 0x00000001;*/ + + block.x |= ((candidateModeMemory[10] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[10] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[10] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[10] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[10] >> 4) & 1) << 4; + block.x |= ((endPoint[0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0].r >> 7) & 1) << 12; + block.x |= ((endPoint[0].r >> 8) & 1) << 13; + block.x |= ((endPoint[0].r >> 9) & 1) << 14; + block.x |= ((endPoint[0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0].g >> 7) & 1) << 22; + block.x |= ((endPoint[0].g >> 8) & 1) << 23; + block.x |= ((endPoint[0].g >> 9) & 1) << 24; + block.x |= ((endPoint[0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0].b >> 7) & 1) << 0; + block.y |= ((endPoint[0].b >> 8) & 1) << 1; + block.y |= ((endPoint[0].b >> 9) & 1) << 2; + block.y |= ((endPoint[1].r >> 0) & 1) << 3; + block.y |= ((endPoint[1].r >> 1) & 1) << 4; + block.y |= ((endPoint[1].r >> 2) & 1) << 5; + block.y |= ((endPoint[1].r >> 3) & 1) << 6; + block.y |= ((endPoint[1].r >> 4) & 1) << 7; + block.y |= ((endPoint[1].r >> 5) & 1) << 8; + block.y |= ((endPoint[1].r >> 6) & 1) << 9; + block.y |= ((endPoint[1].r >> 7) & 1) << 10; + block.y |= ((endPoint[1].r >> 8) & 1) << 11; + block.y |= ((endPoint[1].r >> 9) & 1) << 12; + block.y |= ((endPoint[1].g >> 0) & 1) << 13; + block.y |= ((endPoint[1].g >> 1) & 1) << 14; + block.y |= ((endPoint[1].g >> 2) & 1) << 15; + block.y |= ((endPoint[1].g >> 3) & 1) << 16; + block.y |= ((endPoint[1].g >> 4) & 1) << 17; + block.y |= ((endPoint[1].g >> 5) & 1) << 18; + block.y |= ((endPoint[1].g >> 6) & 1) << 19; + block.y |= ((endPoint[1].g >> 7) & 1) << 20; + block.y |= ((endPoint[1].g >> 8) & 1) << 21; + block.y |= ((endPoint[1].g >> 9) & 1) << 22; + block.y |= ((endPoint[1].b >> 0) & 1) << 23; + block.y |= ((endPoint[1].b >> 1) & 1) << 24; + block.y |= ((endPoint[1].b >> 2) & 1) << 25; + block.y |= ((endPoint[1].b >> 3) & 1) << 26; + block.y |= ((endPoint[1].b >> 4) & 1) << 27; + block.y |= ((endPoint[1].b >> 5) & 1) << 28; + block.y |= ((endPoint[1].b >> 6) & 1) << 29; + block.y |= ((endPoint[1].b >> 7) & 1) << 30; + block.y |= ((endPoint[1].b >> 8) & 1) << 31; + block.z |= ((endPoint[1].b >> 9) & 1) << 0; + } + else if (mode_type == candidateModeFlag[11]) + { + /*block.x |= candidateModeMemory[11]; + block.y |= ( ( endPoint[0].r << 2 ) & 0x00001000 ) | ( ( endPoint[0].g << 12 ) & 0x00400000 ); + block.y |= ( ( endPoint[1].r << 3 ) & 0x00000FF8 ) | ( ( endPoint[1].g << 13 ) & 0x003FE000 ) | ( ( endPoint[1].b << 23 ) & 0xFF800000 ); + block.z |= ( endPoint[0].b >> 10 ) & 0x00000001;*/ + + block.x |= ((candidateModeMemory[11] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[11] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[11] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[11] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[11] >> 4) & 1) << 4; + block.x |= ((endPoint[0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0].r >> 7) & 1) << 12; + block.x |= ((endPoint[0].r >> 8) & 1) << 13; + block.x |= ((endPoint[0].r >> 9) & 1) << 14; + block.x |= ((endPoint[0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0].g >> 7) & 1) << 22; + block.x |= ((endPoint[0].g >> 8) & 1) << 23; + block.x |= ((endPoint[0].g >> 9) & 1) << 24; + block.x |= ((endPoint[0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0].b >> 7) & 1) << 0; + block.y |= ((endPoint[0].b >> 8) & 1) << 1; + block.y |= ((endPoint[0].b >> 9) & 1) << 2; + block.y |= ((endPoint[1].r >> 0) & 1) << 3; + block.y |= ((endPoint[1].r >> 1) & 1) << 4; + block.y |= ((endPoint[1].r >> 2) & 1) << 5; + block.y |= ((endPoint[1].r >> 3) & 1) << 6; + block.y |= ((endPoint[1].r >> 4) & 1) << 7; + block.y |= ((endPoint[1].r >> 5) & 1) << 8; + block.y |= ((endPoint[1].r >> 6) & 1) << 9; + block.y |= ((endPoint[1].r >> 7) & 1) << 10; + block.y |= ((endPoint[1].r >> 8) & 1) << 11; + block.y |= ((endPoint[0].r >> 10) & 1) << 12; + block.y |= ((endPoint[1].g >> 0) & 1) << 13; + block.y |= ((endPoint[1].g >> 1) & 1) << 14; + block.y |= ((endPoint[1].g >> 2) & 1) << 15; + block.y |= ((endPoint[1].g >> 3) & 1) << 16; + block.y |= ((endPoint[1].g >> 4) & 1) << 17; + block.y |= ((endPoint[1].g >> 5) & 1) << 18; + block.y |= ((endPoint[1].g >> 6) & 1) << 19; + block.y |= ((endPoint[1].g >> 7) & 1) << 20; + block.y |= ((endPoint[1].g >> 8) & 1) << 21; + block.y |= ((endPoint[0].g >> 10) & 1) << 22; + block.y |= ((endPoint[1].b >> 0) & 1) << 23; + block.y |= ((endPoint[1].b >> 1) & 1) << 24; + block.y |= ((endPoint[1].b >> 2) & 1) << 25; + block.y |= ((endPoint[1].b >> 3) & 1) << 26; + block.y |= ((endPoint[1].b >> 4) & 1) << 27; + block.y |= ((endPoint[1].b >> 5) & 1) << 28; + block.y |= ((endPoint[1].b >> 6) & 1) << 29; + block.y |= ((endPoint[1].b >> 7) & 1) << 30; + block.y |= ((endPoint[1].b >> 8) & 1) << 31; + block.z |= ((endPoint[0].b >> 10) & 1) << 0; + } + else if (mode_type == candidateModeFlag[12])// violate the spec in [0].low + { + /*block.x |= candidateModeMemory[12]; + block.y |= ( ( endPoint[0].r << 2 ) & 0x00001000 ) | ( ( endPoint[0].g << 12 ) & 0x00400000 ); + block.y |= ( ( endPoint[0].r << 0 ) & 0x00000800 ) | ( ( endPoint[0].g << 10 ) & 0x00200000 ); + block.y |= ( endPoint[0].b << 20 ) & 0x80000000; + block.y |= ( ( endPoint[1].r << 3 ) & 0x000007F8 ) | ( ( endPoint[1].g << 13 ) & 0x001FE000 ) | ( ( endPoint[1].b << 23 ) & 0x7F800000 ); + block.z |= ( endPoint[0].b >> 10 ) & 0x00000001;*/ + + block.x |= ((candidateModeMemory[12] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[12] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[12] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[12] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[12] >> 4) & 1) << 4; + block.x |= ((endPoint[0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0].r >> 7) & 1) << 12; + block.x |= ((endPoint[0].r >> 8) & 1) << 13; + block.x |= ((endPoint[0].r >> 9) & 1) << 14; + block.x |= ((endPoint[0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0].g >> 7) & 1) << 22; + block.x |= ((endPoint[0].g >> 8) & 1) << 23; + block.x |= ((endPoint[0].g >> 9) & 1) << 24; + block.x |= ((endPoint[0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0].b >> 7) & 1) << 0; + block.y |= ((endPoint[0].b >> 8) & 1) << 1; + block.y |= ((endPoint[0].b >> 9) & 1) << 2; + block.y |= ((endPoint[1].r >> 0) & 1) << 3; + block.y |= ((endPoint[1].r >> 1) & 1) << 4; + block.y |= ((endPoint[1].r >> 2) & 1) << 5; + block.y |= ((endPoint[1].r >> 3) & 1) << 6; + block.y |= ((endPoint[1].r >> 4) & 1) << 7; + block.y |= ((endPoint[1].r >> 5) & 1) << 8; + block.y |= ((endPoint[1].r >> 6) & 1) << 9; + block.y |= ((endPoint[1].r >> 7) & 1) << 10; + block.y |= ((endPoint[0].r >> 11) & 1) << 11; + block.y |= ((endPoint[0].r >> 10) & 1) << 12; + block.y |= ((endPoint[1].g >> 0) & 1) << 13; + block.y |= ((endPoint[1].g >> 1) & 1) << 14; + block.y |= ((endPoint[1].g >> 2) & 1) << 15; + block.y |= ((endPoint[1].g >> 3) & 1) << 16; + block.y |= ((endPoint[1].g >> 4) & 1) << 17; + block.y |= ((endPoint[1].g >> 5) & 1) << 18; + block.y |= ((endPoint[1].g >> 6) & 1) << 19; + block.y |= ((endPoint[1].g >> 7) & 1) << 20; + block.y |= ((endPoint[0].g >> 11) & 1) << 21; + block.y |= ((endPoint[0].g >> 10) & 1) << 22; + block.y |= ((endPoint[1].b >> 0) & 1) << 23; + block.y |= ((endPoint[1].b >> 1) & 1) << 24; + block.y |= ((endPoint[1].b >> 2) & 1) << 25; + block.y |= ((endPoint[1].b >> 3) & 1) << 26; + block.y |= ((endPoint[1].b >> 4) & 1) << 27; + block.y |= ((endPoint[1].b >> 5) & 1) << 28; + block.y |= ((endPoint[1].b >> 6) & 1) << 29; + block.y |= ((endPoint[1].b >> 7) & 1) << 30; + block.y |= ((endPoint[0].b >> 11) & 1) << 31; + block.z |= ((endPoint[0].b >> 10) & 1) << 0; + } + else if (mode_type == candidateModeFlag[13]) + { + /*block.x |= candidateModeMemory[13]; + block.y |= ( ( endPoint[0].r >> 8 ) & 0x00000080 ); + block.y |= ( ( endPoint[0].r >> 6 ) & 0x00000100 ); + block.y |= ( ( endPoint[0].r >> 4 ) & 0x00000200 ); + block.y |= ( ( endPoint[0].r >> 2 ) & 0x00000400 ); + block.y |= ( ( endPoint[0].r >> 0 ) & 0x00000800 ); + block.y |= ( ( endPoint[0].r << 2 ) & 0x00001000 ); + block.y |= ( ( endPoint[0].g << 2 ) & 0x00020000 ); + block.y |= ( ( endPoint[0].g << 4 ) & 0x00040000 ); + block.y |= ( ( endPoint[0].g << 6 ) & 0x00080000 ); + block.y |= ( ( endPoint[0].g << 8 ) & 0x00100000 ); + block.y |= ( ( endPoint[0].g << 10 ) & 0x00200000 ); + block.y |= ( ( endPoint[0].g << 12 ) & 0x00400000 ); + block.y |= ( ( endPoint[0].b << 12 ) & 0x08000000 ); + block.y |= ( ( endPoint[0].b << 14 ) & 0x10000000 ); + block.y |= ( ( endPoint[0].b << 16 ) & 0x20000000 ); + block.y |= ( ( endPoint[0].b << 18 ) & 0x40000000 ); + block.y |= ( ( endPoint[0].b << 20 ) & 0x80000000 ); + block.y |= ( ( endPoint[1].r << 3 ) & 0x00000078 ) | ( ( endPoint[1].g << 13 ) & 0x0001E000 ) | ( ( endPoint[1].b << 23 ) & 0x07800000 ); + block.z |= ( endPoint[0].b >> 10 ) & 0x00000001;*/ + + block.x |= ((candidateModeMemory[13] >> 0) & 1) << 0; + block.x |= ((candidateModeMemory[13] >> 1) & 1) << 1; + block.x |= ((candidateModeMemory[13] >> 2) & 1) << 2; + block.x |= ((candidateModeMemory[13] >> 3) & 1) << 3; + block.x |= ((candidateModeMemory[13] >> 4) & 1) << 4; + block.x |= ((endPoint[0].r >> 0) & 1) << 5; + block.x |= ((endPoint[0].r >> 1) & 1) << 6; + block.x |= ((endPoint[0].r >> 2) & 1) << 7; + block.x |= ((endPoint[0].r >> 3) & 1) << 8; + block.x |= ((endPoint[0].r >> 4) & 1) << 9; + block.x |= ((endPoint[0].r >> 5) & 1) << 10; + block.x |= ((endPoint[0].r >> 6) & 1) << 11; + block.x |= ((endPoint[0].r >> 7) & 1) << 12; + block.x |= ((endPoint[0].r >> 8) & 1) << 13; + block.x |= ((endPoint[0].r >> 9) & 1) << 14; + block.x |= ((endPoint[0].g >> 0) & 1) << 15; + block.x |= ((endPoint[0].g >> 1) & 1) << 16; + block.x |= ((endPoint[0].g >> 2) & 1) << 17; + block.x |= ((endPoint[0].g >> 3) & 1) << 18; + block.x |= ((endPoint[0].g >> 4) & 1) << 19; + block.x |= ((endPoint[0].g >> 5) & 1) << 20; + block.x |= ((endPoint[0].g >> 6) & 1) << 21; + block.x |= ((endPoint[0].g >> 7) & 1) << 22; + block.x |= ((endPoint[0].g >> 8) & 1) << 23; + block.x |= ((endPoint[0].g >> 9) & 1) << 24; + block.x |= ((endPoint[0].b >> 0) & 1) << 25; + block.x |= ((endPoint[0].b >> 1) & 1) << 26; + block.x |= ((endPoint[0].b >> 2) & 1) << 27; + block.x |= ((endPoint[0].b >> 3) & 1) << 28; + block.x |= ((endPoint[0].b >> 4) & 1) << 29; + block.x |= ((endPoint[0].b >> 5) & 1) << 30; + block.x |= ((endPoint[0].b >> 6) & 1) << 31; + block.y |= ((endPoint[0].b >> 7) & 1) << 0; + block.y |= ((endPoint[0].b >> 8) & 1) << 1; + block.y |= ((endPoint[0].b >> 9) & 1) << 2; + block.y |= ((endPoint[1].r >> 0) & 1) << 3; + block.y |= ((endPoint[1].r >> 1) & 1) << 4; + block.y |= ((endPoint[1].r >> 2) & 1) << 5; + block.y |= ((endPoint[1].r >> 3) & 1) << 6; + block.y |= ((endPoint[0].r >> 15) & 1) << 7; + block.y |= ((endPoint[0].r >> 14) & 1) << 8; + block.y |= ((endPoint[0].r >> 13) & 1) << 9; + block.y |= ((endPoint[0].r >> 12) & 1) << 10; + block.y |= ((endPoint[0].r >> 11) & 1) << 11; + block.y |= ((endPoint[0].r >> 10) & 1) << 12; + block.y |= ((endPoint[1].g >> 0) & 1) << 13; + block.y |= ((endPoint[1].g >> 1) & 1) << 14; + block.y |= ((endPoint[1].g >> 2) & 1) << 15; + block.y |= ((endPoint[1].g >> 3) & 1) << 16; + block.y |= ((endPoint[0].g >> 15) & 1) << 17; + block.y |= ((endPoint[0].g >> 14) & 1) << 18; + block.y |= ((endPoint[0].g >> 13) & 1) << 19; + block.y |= ((endPoint[0].g >> 12) & 1) << 20; + block.y |= ((endPoint[0].g >> 11) & 1) << 21; + block.y |= ((endPoint[0].g >> 10) & 1) << 22; + block.y |= ((endPoint[1].b >> 0) & 1) << 23; + block.y |= ((endPoint[1].b >> 1) & 1) << 24; + block.y |= ((endPoint[1].b >> 2) & 1) << 25; + block.y |= ((endPoint[1].b >> 3) & 1) << 26; + block.y |= ((endPoint[0].b >> 15) & 1) << 27; + block.y |= ((endPoint[0].b >> 14) & 1) << 28; + block.y |= ((endPoint[0].b >> 13) & 1) << 29; + block.y |= ((endPoint[0].b >> 12) & 1) << 30; + block.y |= ((endPoint[0].b >> 11) & 1) << 31; + block.z |= ((endPoint[0].b >> 10) & 1) << 0; + } +} diff --git a/deps/DirectXTex/DirectXTex/Shaders/BC7Encode.hlsl b/deps/DirectXTex/DirectXTex/Shaders/BC7Encode.hlsl new file mode 100644 index 0000000..8f31c96 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/Shaders/BC7Encode.hlsl @@ -0,0 +1,1907 @@ +//-------------------------------------------------------------------------------------- +// File: BC7Encode.hlsl +// +// The Compute Shader for BC7 Encoder +// +// Copyright (c) Microsoft Corporation. All rights reserved. +//-------------------------------------------------------------------------------------- + +//#define REF_DEVICE + +#define CHAR_LENGTH 8 +#define NCHANNELS 4 +#define BC7_UNORM 98 +#define MAX_UINT 0xFFFFFFFF +#define MIN_UINT 0 + +static const uint candidateSectionBit[64] = //Associated to partition 0-63 +{ + 0xCCCC, 0x8888, 0xEEEE, 0xECC8, + 0xC880, 0xFEEC, 0xFEC8, 0xEC80, + 0xC800, 0xFFEC, 0xFE80, 0xE800, + 0xFFE8, 0xFF00, 0xFFF0, 0xF000, + 0xF710, 0x008E, 0x7100, 0x08CE, + 0x008C, 0x7310, 0x3100, 0x8CCE, + 0x088C, 0x3110, 0x6666, 0x366C, + 0x17E8, 0x0FF0, 0x718E, 0x399C, + 0xaaaa, 0xf0f0, 0x5a5a, 0x33cc, + 0x3c3c, 0x55aa, 0x9696, 0xa55a, + 0x73ce, 0x13c8, 0x324c, 0x3bdc, + 0x6996, 0xc33c, 0x9966, 0x660, + 0x272, 0x4e4, 0x4e40, 0x2720, + 0xc936, 0x936c, 0x39c6, 0x639c, + 0x9336, 0x9cc6, 0x817e, 0xe718, + 0xccf0, 0xfcc, 0x7744, 0xee22, +}; +static const uint candidateSectionBit2[64] = //Associated to partition 64-127 +{ + 0xaa685050, 0x6a5a5040, 0x5a5a4200, 0x5450a0a8, + 0xa5a50000, 0xa0a05050, 0x5555a0a0, 0x5a5a5050, + 0xaa550000, 0xaa555500, 0xaaaa5500, 0x90909090, + 0x94949494, 0xa4a4a4a4, 0xa9a59450, 0x2a0a4250, + 0xa5945040, 0x0a425054, 0xa5a5a500, 0x55a0a0a0, + 0xa8a85454, 0x6a6a4040, 0xa4a45000, 0x1a1a0500, + 0x0050a4a4, 0xaaa59090, 0x14696914, 0x69691400, + 0xa08585a0, 0xaa821414, 0x50a4a450, 0x6a5a0200, + 0xa9a58000, 0x5090a0a8, 0xa8a09050, 0x24242424, + 0x00aa5500, 0x24924924, 0x24499224, 0x50a50a50, + 0x500aa550, 0xaaaa4444, 0x66660000, 0xa5a0a5a0, + 0x50a050a0, 0x69286928, 0x44aaaa44, 0x66666600, + 0xaa444444, 0x54a854a8, 0x95809580, 0x96969600, + 0xa85454a8, 0x80959580, 0xaa141414, 0x96960000, + 0xaaaa1414, 0xa05050a0, 0xa0a5a5a0, 0x96000000, + 0x40804080, 0xa9a8a9a8, 0xaaaaaa44, 0x2a4a5254, +}; +static const uint2 candidateFixUpIndex1D[128] = +{ + {15, 0},{15, 0},{15, 0},{15, 0}, + {15, 0},{15, 0},{15, 0},{15, 0}, + {15, 0},{15, 0},{15, 0},{15, 0}, + {15, 0},{15, 0},{15, 0},{15, 0}, + {15, 0},{ 2, 0},{ 8, 0},{ 2, 0}, + { 2, 0},{ 8, 0},{ 8, 0},{15, 0}, + { 2, 0},{ 8, 0},{ 2, 0},{ 2, 0}, + { 8, 0},{ 8, 0},{ 2, 0},{ 2, 0}, + + {15, 0},{15, 0},{ 6, 0},{ 8, 0}, + { 2, 0},{ 8, 0},{15, 0},{15, 0}, + { 2, 0},{ 8, 0},{ 2, 0},{ 2, 0}, + { 2, 0},{15, 0},{15, 0},{ 6, 0}, + { 6, 0},{ 2, 0},{ 6, 0},{ 8, 0}, + {15, 0},{15, 0},{ 2, 0},{ 2, 0}, + {15, 0},{15, 0},{15, 0},{15, 0}, + {15, 0},{ 2, 0},{ 2, 0},{15, 0}, + //candidateFixUpIndex1D[i][1], i < 64 should not be used + + { 3,15},{ 3, 8},{15, 8},{15, 3}, + { 8,15},{ 3,15},{15, 3},{15, 8}, + { 8,15},{ 8,15},{ 6,15},{ 6,15}, + { 6,15},{ 5,15},{ 3,15},{ 3, 8}, + { 3,15},{ 3, 8},{ 8,15},{15, 3}, + { 3,15},{ 3, 8},{ 6,15},{10, 8}, + { 5, 3},{ 8,15},{ 8, 6},{ 6,10}, + { 8,15},{ 5,15},{15,10},{15, 8}, + + { 8,15},{15, 3},{ 3,15},{ 5,10}, + { 6,10},{10, 8},{ 8, 9},{15,10}, + {15, 6},{ 3,15},{15, 8},{ 5,15}, + {15, 3},{15, 6},{15, 6},{15, 8}, //The Spec doesn't mark the first fixed up index in this row, so I apply 15 for them, and seems correct + { 3,15},{15, 3},{ 5,15},{ 5,15}, + { 5,15},{ 8,15},{ 5,15},{10,15}, + { 5,15},{10,15},{ 8,15},{13,15}, + {15, 3},{12,15},{ 3,15},{ 3, 8}, +}; +static const uint2 candidateFixUpIndex1DOrdered[128] = //Same with candidateFixUpIndex1D but order the result when i >= 64 +{ + {15, 0},{15, 0},{15, 0},{15, 0}, + {15, 0},{15, 0},{15, 0},{15, 0}, + {15, 0},{15, 0},{15, 0},{15, 0}, + {15, 0},{15, 0},{15, 0},{15, 0}, + {15, 0},{ 2, 0},{ 8, 0},{ 2, 0}, + { 2, 0},{ 8, 0},{ 8, 0},{15, 0}, + { 2, 0},{ 8, 0},{ 2, 0},{ 2, 0}, + { 8, 0},{ 8, 0},{ 2, 0},{ 2, 0}, + + {15, 0},{15, 0},{ 6, 0},{ 8, 0}, + { 2, 0},{ 8, 0},{15, 0},{15, 0}, + { 2, 0},{ 8, 0},{ 2, 0},{ 2, 0}, + { 2, 0},{15, 0},{15, 0},{ 6, 0}, + { 6, 0},{ 2, 0},{ 6, 0},{ 8, 0}, + {15, 0},{15, 0},{ 2, 0},{ 2, 0}, + {15, 0},{15, 0},{15, 0},{15, 0}, + {15, 0},{ 2, 0},{ 2, 0},{15, 0}, + //candidateFixUpIndex1DOrdered[i][1], i < 64 should not be used + + { 3,15},{ 3, 8},{ 8,15},{ 3,15}, + { 8,15},{ 3,15},{ 3,15},{ 8,15}, + { 8,15},{ 8,15},{ 6,15},{ 6,15}, + { 6,15},{ 5,15},{ 3,15},{ 3, 8}, + { 3,15},{ 3, 8},{ 8,15},{ 3,15}, + { 3,15},{ 3, 8},{ 6,15},{ 8,10}, + { 3, 5},{ 8,15},{ 6, 8},{ 6,10}, + { 8,15},{ 5,15},{10,15},{ 8,15}, + + { 8,15},{ 3,15},{ 3,15},{ 5,10}, + { 6,10},{ 8,10},{ 8, 9},{10,15}, + { 6,15},{ 3,15},{ 8,15},{ 5,15}, + { 3,15},{ 6,15},{ 6,15},{ 8,15}, //The Spec doesn't mark the first fixed up index in this row, so I apply 15 for them, and seems correct + { 3,15},{ 3,15},{ 5,15},{ 5,15}, + { 5,15},{ 8,15},{ 5,15},{10,15}, + { 5,15},{10,15},{ 8,15},{13,15}, + { 3,15},{12,15},{ 3,15},{ 3, 8}, +}; +//static const uint4x4 candidateRotation[4] = +//{ +// {1,0,0,0},{0,1,0,0},{0,0,1,0},{0,0,0,1}, +// {0,0,0,1},{0,1,0,0},{0,0,1,0},{1,0,0,0}, +// {1,0,0,0},{0,0,0,1},{0,0,1,0},{0,1,0,0}, +// {1,0,0,0},{0,1,0,0},{0,0,0,1},{0,0,1,0} +//}; +//static const uint2 candidateIndexPrec[8] = {{3,0},{3,0},{2,0},{2,0}, +// {2,3}, //color index and alpha index can exchange +// {2,2},{4,4},{2,2}}; + +static const uint aWeight[3][16] = { {0, 4, 9, 13, 17, 21, 26, 30, 34, 38, 43, 47, 51, 55, 60, 64}, + {0, 9, 18, 27, 37, 46, 55, 64, 0, 0, 0, 0, 0, 0, 0, 0}, + {0, 21, 43, 64, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} }; + + //4 bit index: 0, 4, 9, 13, 17, 21, 26, 30, 34, 38, 43, 47, 51, 55, 60, 64 +static const uint aStep[3][64] = { { 0, 0, 0, 1, 1, 1, 1, 2, + 2, 2, 2, 2, 3, 3, 3, 3, + 4, 4, 4, 4, 5, 5, 5, 5, + 6, 6, 6, 6, 6, 7, 7, 7, + 7, 8, 8, 8, 8, 9, 9, 9, + 9,10,10,10,10,10,11,11, + 11,11,12,12,12,12,13,13, + 13,13,14,14,14,14,15,15 }, + //3 bit index: 0, 9, 18, 27, 37, 46, 55, 64 + { 0,0,0,0,0,1,1,1, + 1,1,1,1,1,1,2,2, + 2,2,2,2,2,2,2,3, + 3,3,3,3,3,3,3,3, + 3,4,4,4,4,4,4,4, + 4,4,5,5,5,5,5,5, + 5,5,5,6,6,6,6,6, + 6,6,6,6,7,7,7,7 }, + //2 bit index: 0, 21, 43, 64 + { 0,0,0,0,0,0,0,0, + 0,0,0,1,1,1,1,1, + 1,1,1,1,1,1,1,1, + 1,1,1,1,1,1,1,1, + 1,2,2,2,2,2,2,2, + 2,2,2,2,2,2,2,2, + 2,2,2,2,2,2,3,3, + 3,3,3,3,3,3,3,3 } }; + +cbuffer cbCS : register( b0 ) +{ + uint g_tex_width; + uint g_num_block_x; + uint g_format; + uint g_mode_id; + uint g_start_block_id; + uint g_num_total_blocks; + float g_alpha_weight; +}; + +//Forward declaration +uint2x4 compress_endpoints0( inout uint2x4 endPoint, uint2 P ); //Mode = 0 +uint2x4 compress_endpoints1( inout uint2x4 endPoint, uint2 P ); //Mode = 1 +uint2x4 compress_endpoints2( inout uint2x4 endPoint ); //Mode = 2 +uint2x4 compress_endpoints3( inout uint2x4 endPoint, uint2 P ); //Mode = 3 +uint2x4 compress_endpoints7( inout uint2x4 endPoint, uint2 P ); //Mode = 7 +uint2x4 compress_endpoints6( inout uint2x4 endPoint, uint2 P ); //Mode = 6 +uint2x4 compress_endpoints4( inout uint2x4 endPoint ); //Mode = 4 +uint2x4 compress_endpoints5( inout uint2x4 endPoint ); //Mode = 5 + +void block_package0( out uint4 block, uint partition, uint threadBase ); //Mode0 +void block_package1( out uint4 block, uint partition, uint threadBase ); //Mode1 +void block_package2( out uint4 block, uint partition, uint threadBase ); //Mode2 +void block_package3( out uint4 block, uint partition, uint threadBase ); //Mode3 +void block_package4( out uint4 block, uint rotation, uint index_selector, uint threadBase ); //Mode4 +void block_package5( out uint4 block, uint rotation, uint threadBase ); //Mode5 +void block_package6( out uint4 block, uint threadBase ); //Mode6 +void block_package7( out uint4 block, uint partition, uint threadBase ); //Mode7 + + +void swap(inout uint4 lhs, inout uint4 rhs) +{ + uint4 tmp = lhs; + lhs = rhs; + rhs = tmp; +} +void swap(inout uint3 lhs, inout uint3 rhs) +{ + uint3 tmp = lhs; + lhs = rhs; + rhs = tmp; +} +void swap(inout uint lhs, inout uint rhs) +{ + uint tmp = lhs; + lhs = rhs; + rhs = tmp; +} + +uint ComputeError(in uint4 a, in uint4 b) +{ + return dot(a.rgb, b.rgb) + g_alpha_weight * a.a*b.a; +} + +void Ensure_A_Is_Larger( inout uint4 a, inout uint4 b ) +{ + if ( a.x < b.x ) + swap( a.x, b.x ); + if ( a.y < b.y ) + swap( a.y, b.y ); + if ( a.z < b.z ) + swap( a.z, b.z ); + if ( a.w < b.w ) + swap( a.w, b.w ); +} + + +Texture2D g_Input : register( t0 ); +StructuredBuffer g_InBuff : register( t1 ); + +RWStructuredBuffer g_OutBuff : register( u0 ); + +#define THREAD_GROUP_SIZE 64 +#define BLOCK_SIZE_Y 4 +#define BLOCK_SIZE_X 4 +#define BLOCK_SIZE (BLOCK_SIZE_Y * BLOCK_SIZE_X) + +struct BufferShared +{ + uint4 pixel; + uint error; + uint mode; + uint partition; + uint index_selector; + uint rotation; + uint4 endPoint_low; + uint4 endPoint_high; + uint4 endPoint_low_quantized; + uint4 endPoint_high_quantized; +}; +groupshared BufferShared shared_temp[THREAD_GROUP_SIZE]; + +[numthreads( THREAD_GROUP_SIZE, 1, 1 )] +void TryMode456CS( uint GI : SV_GroupIndex, uint3 groupID : SV_GroupID ) // mode 4 5 6 all have 1 subset per block, and fix-up index is always index 0 +{ + // we process 4 BC blocks per thread group + const uint MAX_USED_THREAD = 16; // pixels in a BC (block compressed) block + uint BLOCK_IN_GROUP = THREAD_GROUP_SIZE / MAX_USED_THREAD; // the number of BC blocks a thread group processes = 64 / 16 = 4 + uint blockInGroup = GI / MAX_USED_THREAD; // what BC block this thread is on within this thread group + uint blockID = g_start_block_id + groupID.x * BLOCK_IN_GROUP + blockInGroup; // what global BC block this thread is on + uint threadBase = blockInGroup * MAX_USED_THREAD; // the first id of the pixel in this BC block in this thread group + uint threadInBlock = GI - threadBase; // id of the pixel in this BC block + +#ifndef REF_DEVICE + if (blockID >= g_num_total_blocks) + { + return; + } +#endif + + uint block_y = blockID / g_num_block_x; + uint block_x = blockID - block_y * g_num_block_x; + uint base_x = block_x * BLOCK_SIZE_X; + uint base_y = block_y * BLOCK_SIZE_Y; + + if (threadInBlock < 16) + { + shared_temp[GI].pixel = clamp(uint4(g_Input.Load( uint3( base_x + threadInBlock % 4, base_y + threadInBlock / 4, 0 ) ) * 255), 0, 255); + + shared_temp[GI].endPoint_low = shared_temp[GI].pixel; + shared_temp[GI].endPoint_high = shared_temp[GI].pixel; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (threadInBlock < 8) + { + shared_temp[GI].endPoint_low = min(shared_temp[GI].endPoint_low, shared_temp[GI + 8].endPoint_low); + shared_temp[GI].endPoint_high = max(shared_temp[GI].endPoint_high, shared_temp[GI + 8].endPoint_high); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 4) + { + shared_temp[GI].endPoint_low = min(shared_temp[GI].endPoint_low, shared_temp[GI + 4].endPoint_low); + shared_temp[GI].endPoint_high = max(shared_temp[GI].endPoint_high, shared_temp[GI + 4].endPoint_high); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 2) + { + shared_temp[GI].endPoint_low = min(shared_temp[GI].endPoint_low, shared_temp[GI + 2].endPoint_low); + shared_temp[GI].endPoint_high = max(shared_temp[GI].endPoint_high, shared_temp[GI + 2].endPoint_high); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 1) + { + shared_temp[GI].endPoint_low = min(shared_temp[GI].endPoint_low, shared_temp[GI + 1].endPoint_low); + shared_temp[GI].endPoint_high = max(shared_temp[GI].endPoint_high, shared_temp[GI + 1].endPoint_high); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + uint2x4 endPoint; + endPoint[0] = shared_temp[threadBase].endPoint_low; + endPoint[1] = shared_temp[threadBase].endPoint_high; + + uint error = 0xFFFFFFFF; + uint mode = 0; + uint index_selector = 0; + uint rotation = 0; + + uint2 indexPrec; + if (threadInBlock < 8) // all threads of threadInBlock < 8 will be working on trying out mode 4, since only mode 4 has index selector bit + { + if (0 == (threadInBlock & 1)) // thread 0, 2, 4, 6 + { + //2 represents 2bit index precision; 1 represents 3bit index precision + index_selector = 0; + indexPrec = uint2( 2, 1 ); + } + else // thread 1, 3, 5, 7 + { + //2 represents 2bit index precision; 1 represents 3bit index precision + index_selector = 1; + indexPrec = uint2( 1, 2 ); + } + } + else + { + //2 represents 2bit index precision + indexPrec = uint2( 2, 2 ); + } + + uint4 pixel_r; + uint color_index; + uint alpha_index; + int4 span; + int2 span_norm_sqr; + int2 dotProduct; + if (threadInBlock < 12) // Try mode 4 5 in threads 0..11 + { + // mode 4 5 have component rotation + if ((threadInBlock < 2) || (8 == threadInBlock)) // rotation = 0 in thread 0, 1 + { + rotation = 0; + } + else if ((threadInBlock < 4) || (9 == threadInBlock)) // rotation = 1 in thread 2, 3 + { + endPoint[0].ra = endPoint[0].ar; + endPoint[1].ra = endPoint[1].ar; + + rotation = 1; + } + else if ((threadInBlock < 6) || (10 == threadInBlock)) // rotation = 2 in thread 4, 5 + { + endPoint[0].ga = endPoint[0].ag; + endPoint[1].ga = endPoint[1].ag; + + rotation = 2; + } + else if ((threadInBlock < 8) || (11 == threadInBlock)) // rotation = 3 in thread 6, 7 + { + endPoint[0].ba = endPoint[0].ab; + endPoint[1].ba = endPoint[1].ab; + + rotation = 3; + } + + if (threadInBlock < 8) // try mode 4 in threads 0..7 + { + // mode 4 thread distribution + // Thread 0 1 2 3 4 5 6 7 + // Rotation 0 0 1 1 2 2 3 3 + // Index selector 0 1 0 1 0 1 0 1 + + mode = 4; + compress_endpoints4( endPoint ); + } + else // try mode 5 in threads 8..11 + { + // mode 5 thread distribution + // Thread 8 9 10 11 + // Rotation 0 1 2 3 + + mode = 5; + compress_endpoints5( endPoint ); + } + + uint4 pixel = shared_temp[threadBase + 0].pixel; + if (1 == rotation) + { + pixel.ra = pixel.ar; + } + else if (2 == rotation) + { + pixel.ga = pixel.ag; + } + else if (3 == rotation) + { + pixel.ba = pixel.ab; + } + + span = endPoint[1] - endPoint[0]; + span_norm_sqr = uint2( dot( span.rgb, span.rgb ), span.a * span.a ); + + // in mode 4 5 6, end point 0 must be closer to pixel 0 than end point 1, because of the fix-up index is always index 0 + // TODO: this shouldn't be necessary here in error calculation + /* + dotProduct = int2( dot( span.rgb, pixel.rgb - endPoint[0].rgb ), span.a * ( pixel.a - endPoint[0].a ) ); + if ( span_norm_sqr.x > 0 && dotProduct.x > 0 && uint( dotProduct.x * 63.49999 ) > uint( 32 * span_norm_sqr.x ) ) + { + span.rgb = -span.rgb; + swap(endPoint[0].rgb, endPoint[1].rgb); + } + if ( span_norm_sqr.y > 0 && dotProduct.y > 0 && uint( dotProduct.y * 63.49999 ) > uint( 32 * span_norm_sqr.y ) ) + { + span.a = -span.a; + swap(endPoint[0].a, endPoint[1].a); + } + */ + + // should be the same as above + dotProduct = int2( dot( pixel.rgb - endPoint[0].rgb, pixel.rgb - endPoint[0].rgb ), dot( pixel.rgb - endPoint[1].rgb, pixel.rgb - endPoint[1].rgb ) ); + if ( dotProduct.x > dotProduct.y ) + { + span.rgb = -span.rgb; + swap(endPoint[0].rgb, endPoint[1].rgb); + } + dotProduct = int2( dot( pixel.a - endPoint[0].a, pixel.a - endPoint[0].a ), dot( pixel.a - endPoint[1].a, pixel.a - endPoint[1].a ) ); + if ( dotProduct.x > dotProduct.y ) + { + span.a = -span.a; + swap(endPoint[0].a, endPoint[1].a); + } + + error = 0; + for ( uint i = 0; i < 16; i ++ ) + { + pixel = shared_temp[threadBase + i].pixel; + if (1 == rotation) + { + pixel.ra = pixel.ar; + } + else if (2 == rotation) + { + pixel.ga = pixel.ag; + } + else if (3 == rotation) + { + pixel.ba = pixel.ab; + } + + dotProduct.x = dot( span.rgb, pixel.rgb - endPoint[0].rgb ); + color_index = ( span_norm_sqr.x <= 0 /*endPoint[0] == endPoint[1]*/ || dotProduct.x <= 0 /*pixel == endPoint[0]*/ ) ? 0 + : ( ( dotProduct.x < span_norm_sqr.x ) ? aStep[indexPrec.x][ uint( dotProduct.x * 63.49999 / span_norm_sqr.x ) ] : aStep[indexPrec.x][63] ); + dotProduct.y = dot( span.a, pixel.a - endPoint[0].a ); + alpha_index = ( span_norm_sqr.y <= 0 || dotProduct.y <= 0 ) ? 0 + : ( ( dotProduct.y < span_norm_sqr.y ) ? aStep[indexPrec.y][ uint( dotProduct.y * 63.49999 / span_norm_sqr.y ) ] : aStep[indexPrec.y][63] ); + + // the same color_index and alpha_index should be used for reconstruction, so this should be left commented out + /*if (index_selector) + { + swap(color_index, alpha_index); + }*/ + + pixel_r.rgb = ( ( 64 - aWeight[indexPrec.x][color_index] ) * endPoint[0].rgb + + aWeight[indexPrec.x][color_index] * endPoint[1].rgb + + 32 ) >> 6; + pixel_r.a = ( ( 64 - aWeight[indexPrec.y][alpha_index] ) * endPoint[0].a + + aWeight[indexPrec.y][alpha_index] * endPoint[1].a + + 32 ) >> 6; + + Ensure_A_Is_Larger( pixel_r, pixel ); + pixel_r -= pixel; + if (1 == rotation) + { + pixel_r.ra = pixel_r.ar; + } + else if (2 == rotation) + { + pixel_r.ga = pixel_r.ag; + } + else if (3 == rotation) + { + pixel_r.ba = pixel_r.ab; + } + error += ComputeError(pixel_r, pixel_r); + } + } + else if (threadInBlock < 16) // Try mode 6 in threads 12..15, since in mode 4 5 6, only mode 6 has p bit + { + uint p = threadInBlock - 12; + + compress_endpoints6( endPoint, uint2(p >> 0, p >> 1) & 1 ); + + uint4 pixel = shared_temp[threadBase + 0].pixel; + + span = endPoint[1] - endPoint[0]; + span_norm_sqr = dot( span, span ); + dotProduct = dot( span, pixel - endPoint[0] ); + if ( span_norm_sqr.x > 0 && dotProduct.x >= 0 && uint( dotProduct.x * 63.49999 ) > uint( 32 * span_norm_sqr.x ) ) + { + span = -span; + swap(endPoint[0], endPoint[1]); + } + + error = 0; + for ( uint i = 0; i < 16; i ++ ) + { + pixel = shared_temp[threadBase + i].pixel; + + dotProduct.x = dot( span, pixel - endPoint[0] ); + color_index = ( span_norm_sqr.x <= 0 || dotProduct.x <= 0 ) ? 0 + : ( ( dotProduct.x < span_norm_sqr.x ) ? aStep[0][ uint( dotProduct.x * 63.49999 / span_norm_sqr.x ) ] : aStep[0][63] ); + + pixel_r = ( ( 64 - aWeight[0][color_index] ) * endPoint[0] + + aWeight[0][color_index] * endPoint[1] + 32 ) >> 6; + + Ensure_A_Is_Larger( pixel_r, pixel ); + pixel_r -= pixel; + error += ComputeError(pixel_r, pixel_r); + } + + mode = 6; + rotation = p; // Borrow rotation for p + } + + shared_temp[GI].error = error; + shared_temp[GI].mode = mode; + shared_temp[GI].index_selector = index_selector; + shared_temp[GI].rotation = rotation; + +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (threadInBlock < 8) + { + if ( shared_temp[GI].error > shared_temp[GI + 8].error ) + { + shared_temp[GI].error = shared_temp[GI + 8].error; + shared_temp[GI].mode = shared_temp[GI + 8].mode; + shared_temp[GI].index_selector = shared_temp[GI + 8].index_selector; + shared_temp[GI].rotation = shared_temp[GI + 8].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 4) + { + if ( shared_temp[GI].error > shared_temp[GI + 4].error ) + { + shared_temp[GI].error = shared_temp[GI + 4].error; + shared_temp[GI].mode = shared_temp[GI + 4].mode; + shared_temp[GI].index_selector = shared_temp[GI + 4].index_selector; + shared_temp[GI].rotation = shared_temp[GI + 4].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 2) + { + if ( shared_temp[GI].error > shared_temp[GI + 2].error ) + { + shared_temp[GI].error = shared_temp[GI + 2].error; + shared_temp[GI].mode = shared_temp[GI + 2].mode; + shared_temp[GI].index_selector = shared_temp[GI + 2].index_selector; + shared_temp[GI].rotation = shared_temp[GI + 2].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 1) + { + if ( shared_temp[GI].error > shared_temp[GI + 1].error ) + { + shared_temp[GI].error = shared_temp[GI + 1].error; + shared_temp[GI].mode = shared_temp[GI + 1].mode; + shared_temp[GI].index_selector = shared_temp[GI + 1].index_selector; + shared_temp[GI].rotation = shared_temp[GI + 1].rotation; + } + + g_OutBuff[blockID] = uint4(shared_temp[GI].error, (shared_temp[GI].index_selector << 31) | shared_temp[GI].mode, + 0, shared_temp[GI].rotation); // rotation is indeed rotation for mode 4 5. for mode 6, rotation is p bit + } +} + +[numthreads( THREAD_GROUP_SIZE, 1, 1 )] +void TryMode137CS( uint GI : SV_GroupIndex, uint3 groupID : SV_GroupID ) // mode 1 3 7 all have 2 subsets per block +{ + const uint MAX_USED_THREAD = 64; + uint BLOCK_IN_GROUP = THREAD_GROUP_SIZE / MAX_USED_THREAD; + uint blockInGroup = GI / MAX_USED_THREAD; + uint blockID = g_start_block_id + groupID.x * BLOCK_IN_GROUP + blockInGroup; + uint threadBase = blockInGroup * MAX_USED_THREAD; + uint threadInBlock = GI - threadBase; + + uint block_y = blockID / g_num_block_x; + uint block_x = blockID - block_y * g_num_block_x; + uint base_x = block_x * BLOCK_SIZE_X; + uint base_y = block_y * BLOCK_SIZE_Y; + + if (threadInBlock < 16) + { + shared_temp[GI].pixel = clamp(uint4(g_Input.Load( uint3( base_x + threadInBlock % 4, base_y + threadInBlock / 4, 0 ) ) * 255), 0, 255); + } + GroupMemoryBarrierWithGroupSync(); + + shared_temp[GI].error = 0xFFFFFFFF; + + uint4 pixel_r; + uint2x4 endPoint[2]; // endPoint[0..1 for subset id][0..1 for low and high in the subset] + uint2x4 endPointBackup[2]; + uint color_index; + if (threadInBlock < 64) + { + uint partition = threadInBlock; + + endPoint[0][0] = MAX_UINT; + endPoint[0][1] = MIN_UINT; + endPoint[1][0] = MAX_UINT; + endPoint[1][1] = MIN_UINT; + uint bits = candidateSectionBit[partition]; + for ( uint i = 0; i < 16; i ++ ) + { + uint4 pixel = shared_temp[threadBase + i].pixel; + if ( (( bits >> i ) & 0x01) == 1 ) + { + endPoint[1][0] = min( endPoint[1][0], pixel ); + endPoint[1][1] = max( endPoint[1][1], pixel ); + } + else + { + endPoint[0][0] = min( endPoint[0][0], pixel ); + endPoint[0][1] = max( endPoint[0][1], pixel ); + } + } + + endPointBackup[0] = endPoint[0]; + endPointBackup[1] = endPoint[1]; + + uint max_p; + if (1 == g_mode_id) + { + // in mode 1, there is only one p bit per subset + max_p = 4; + } + else + { + // in mode 3 7, there are two p bits per subset, one for each end point + max_p = 16; + } + + uint rotation = 0; + uint error = MAX_UINT; + for ( uint p = 0; p < max_p; p ++ ) + { + endPoint[0] = endPointBackup[0]; + endPoint[1] = endPointBackup[1]; + + for ( i = 0; i < 2; i ++ ) // loop through 2 subsets + { + if (g_mode_id == 1) + { + compress_endpoints1( endPoint[i], (p >> i) & 1 ); + } + else if (g_mode_id == 3) + { + compress_endpoints3( endPoint[i], uint2(p >> (i * 2 + 0), p >> (i * 2 + 1)) & 1 ); + } + else if (g_mode_id == 7) + { + compress_endpoints7( endPoint[i], uint2(p >> (i * 2 + 0), p >> (i * 2 + 1)) & 1 ); + } + } + + int4 span[2]; + span[0] = endPoint[0][1] - endPoint[0][0]; + span[1] = endPoint[1][1] - endPoint[1][0]; + + if (g_mode_id != 7) + { + span[0].w = span[1].w = 0; + } + + int span_norm_sqr[2]; + span_norm_sqr[0] = dot( span[0], span[0] ); + span_norm_sqr[1] = dot( span[1], span[1] ); + + // TODO: again, this shouldn't be necessary here in error calculation + int dotProduct = dot( span[0], shared_temp[threadBase + 0].pixel - endPoint[0][0] ); + if ( span_norm_sqr[0] > 0 && dotProduct > 0 && uint( dotProduct * 63.49999 ) > uint( 32 * span_norm_sqr[0] ) ) + { + span[0] = -span[0]; + swap(endPoint[0][0], endPoint[0][1]); + } + dotProduct = dot( span[1], shared_temp[threadBase + candidateFixUpIndex1D[partition].x].pixel - endPoint[1][0] ); + if ( span_norm_sqr[1] > 0 && dotProduct > 0 && uint( dotProduct * 63.49999 ) > uint( 32 * span_norm_sqr[1] ) ) + { + span[1] = -span[1]; + swap(endPoint[1][0], endPoint[1][1]); + } + + uint step_selector; + if (g_mode_id != 1) + { + step_selector = 2; // mode 3 7 have 2 bit index + } + else + { + step_selector = 1; // mode 1 has 3 bit index + } + + uint p_error = 0; + for ( i = 0; i < 16; i ++ ) + { + if (((bits >> i) & 0x01) == 1) + { + dotProduct = dot( span[1], shared_temp[threadBase + i].pixel - endPoint[1][0] ); + color_index = (span_norm_sqr[1] <= 0 || dotProduct <= 0) ? 0 + : ((dotProduct < span_norm_sqr[1]) ? aStep[step_selector][uint(dotProduct * 63.49999 / span_norm_sqr[1])] : aStep[step_selector][63]); + } + else + { + dotProduct = dot( span[0], shared_temp[threadBase + i].pixel - endPoint[0][0] ); + color_index = (span_norm_sqr[0] <= 0 || dotProduct <= 0) ? 0 + : ((dotProduct < span_norm_sqr[0]) ? aStep[step_selector][uint(dotProduct * 63.49999 / span_norm_sqr[0])] : aStep[step_selector][63]); + } + + uint subset_index = (bits >> i) & 0x01; + + pixel_r = ((64 - aWeight[step_selector][color_index]) * endPoint[subset_index][0] + + aWeight[step_selector][color_index] * endPoint[subset_index][1] + 32) >> 6; + if (g_mode_id != 7) + { + pixel_r.a = 255; + } + + uint4 pixel = shared_temp[threadBase + i].pixel; + Ensure_A_Is_Larger( pixel_r, pixel ); + pixel_r -= pixel; + p_error += ComputeError(pixel_r, pixel_r); + } + + if (p_error < error) + { + error = p_error; + rotation = p; + } + } + + shared_temp[GI].error = error; + shared_temp[GI].mode = g_mode_id; + shared_temp[GI].partition = partition; + shared_temp[GI].rotation = rotation; // mode 1 3 7 don't have rotation, we use rotation for p bits + } + GroupMemoryBarrierWithGroupSync(); + + if (threadInBlock < 32) + { + if ( shared_temp[GI].error > shared_temp[GI + 32].error ) + { + shared_temp[GI].error = shared_temp[GI + 32].error; + shared_temp[GI].mode = shared_temp[GI + 32].mode; + shared_temp[GI].partition = shared_temp[GI + 32].partition; + shared_temp[GI].rotation = shared_temp[GI + 32].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif +if (threadInBlock < 16) + { + if ( shared_temp[GI].error > shared_temp[GI + 16].error ) + { + shared_temp[GI].error = shared_temp[GI + 16].error; + shared_temp[GI].mode = shared_temp[GI + 16].mode; + shared_temp[GI].partition = shared_temp[GI + 16].partition; + shared_temp[GI].rotation = shared_temp[GI + 16].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 8) + { + if ( shared_temp[GI].error > shared_temp[GI + 8].error ) + { + shared_temp[GI].error = shared_temp[GI + 8].error; + shared_temp[GI].mode = shared_temp[GI + 8].mode; + shared_temp[GI].partition = shared_temp[GI + 8].partition; + shared_temp[GI].rotation = shared_temp[GI + 8].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 4) + { + if ( shared_temp[GI].error > shared_temp[GI + 4].error ) + { + shared_temp[GI].error = shared_temp[GI + 4].error; + shared_temp[GI].mode = shared_temp[GI + 4].mode; + shared_temp[GI].partition = shared_temp[GI + 4].partition; + shared_temp[GI].rotation = shared_temp[GI + 4].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 2) + { + if ( shared_temp[GI].error > shared_temp[GI + 2].error ) + { + shared_temp[GI].error = shared_temp[GI + 2].error; + shared_temp[GI].mode = shared_temp[GI + 2].mode; + shared_temp[GI].partition = shared_temp[GI + 2].partition; + shared_temp[GI].rotation = shared_temp[GI + 2].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 1) + { + if ( shared_temp[GI].error > shared_temp[GI + 1].error ) + { + shared_temp[GI].error = shared_temp[GI + 1].error; + shared_temp[GI].mode = shared_temp[GI + 1].mode; + shared_temp[GI].partition = shared_temp[GI + 1].partition; + shared_temp[GI].rotation = shared_temp[GI + 1].rotation; + } + + if (g_InBuff[blockID].x > shared_temp[GI].error) + { + g_OutBuff[blockID] = uint4(shared_temp[GI].error, shared_temp[GI].mode, shared_temp[GI].partition, shared_temp[GI].rotation); // mode 1 3 7 don't have rotation, we use rotation for p bits + } + else + { + g_OutBuff[blockID] = g_InBuff[blockID]; + } + } +} + +[numthreads( THREAD_GROUP_SIZE, 1, 1 )] +void TryMode02CS( uint GI : SV_GroupIndex, uint3 groupID : SV_GroupID ) // mode 0 2 have 3 subsets per block +{ + const uint MAX_USED_THREAD = 64; + uint BLOCK_IN_GROUP = THREAD_GROUP_SIZE / MAX_USED_THREAD; + uint blockInGroup = GI / MAX_USED_THREAD; + uint blockID = g_start_block_id + groupID.x * BLOCK_IN_GROUP + blockInGroup; + uint threadBase = blockInGroup * MAX_USED_THREAD; + uint threadInBlock = GI - threadBase; + + uint block_y = blockID / g_num_block_x; + uint block_x = blockID - block_y * g_num_block_x; + uint base_x = block_x * BLOCK_SIZE_X; + uint base_y = block_y * BLOCK_SIZE_Y; + + if (threadInBlock < 16) + { + shared_temp[GI].pixel = clamp(uint4(g_Input.Load( uint3( base_x + threadInBlock % 4, base_y + threadInBlock / 4, 0 ) ) * 255), 0, 255); + } + GroupMemoryBarrierWithGroupSync(); + + shared_temp[GI].error = 0xFFFFFFFF; + + uint num_partitions; + if (0 == g_mode_id) + { + num_partitions = 16; + } + else + { + num_partitions = 64; + } + + uint4 pixel_r; + uint2x4 endPoint[3]; // endPoint[0..1 for subset id][0..1 for low and high in the subset] + uint2x4 endPointBackup[3]; + uint color_index[16]; + if (threadInBlock < num_partitions) + { + uint partition = threadInBlock + 64; + + endPoint[0][0] = MAX_UINT; + endPoint[0][1] = MIN_UINT; + endPoint[1][0] = MAX_UINT; + endPoint[1][1] = MIN_UINT; + endPoint[2][0] = MAX_UINT; + endPoint[2][1] = MIN_UINT; + uint bits2 = candidateSectionBit2[partition - 64]; + for ( uint i = 0; i < 16; i ++ ) + { + uint4 pixel = shared_temp[threadBase + i].pixel; + uint subset_index = ( bits2 >> ( i * 2 ) ) & 0x03; + if ( subset_index == 2 ) + { + endPoint[2][0] = min( endPoint[2][0], pixel ); + endPoint[2][1] = max( endPoint[2][1], pixel ); + } + else if ( subset_index == 1 ) + { + endPoint[1][0] = min( endPoint[1][0], pixel ); + endPoint[1][1] = max( endPoint[1][1], pixel ); + } + else + { + endPoint[0][0] = min( endPoint[0][0], pixel ); + endPoint[0][1] = max( endPoint[0][1], pixel ); + } + } + + endPointBackup[0] = endPoint[0]; + endPointBackup[1] = endPoint[1]; + endPointBackup[2] = endPoint[2]; + + uint max_p; + if (0 == g_mode_id) + { + max_p = 64; // changed from 32 to 64 + } + else + { + max_p = 1; + } + + uint rotation = 0; + uint error = MAX_UINT; + for ( uint p = 0; p < max_p; p ++ ) + { + endPoint[0] = endPointBackup[0]; + endPoint[1] = endPointBackup[1]; + endPoint[2] = endPointBackup[2]; + + for ( i = 0; i < 3; i ++ ) + { + if (0 == g_mode_id) + { + compress_endpoints0( endPoint[i], uint2(p >> (i * 2 + 0), p >> (i * 2 + 1)) & 1 ); + } + else + { + compress_endpoints2( endPoint[i] ); + } + } + + uint step_selector = 1 + (2 == g_mode_id); + + int4 span[3]; + span[0] = endPoint[0][1] - endPoint[0][0]; + span[1] = endPoint[1][1] - endPoint[1][0]; + span[2] = endPoint[2][1] - endPoint[2][0]; + span[0].w = span[1].w = span[2].w = 0; + int span_norm_sqr[3]; + span_norm_sqr[0] = dot( span[0], span[0] ); + span_norm_sqr[1] = dot( span[1], span[1] ); + span_norm_sqr[2] = dot( span[2], span[2] ); + + // TODO: again, this shouldn't be necessary here in error calculation + uint ci[3] = { 0, candidateFixUpIndex1D[partition].x, candidateFixUpIndex1D[partition].y }; + for (i = 0; i < 3; i ++) + { + int dotProduct = dot( span[i], shared_temp[threadBase + ci[i]].pixel - endPoint[i][0] ); + if ( span_norm_sqr[i] > 0 && dotProduct > 0 && uint( dotProduct * 63.49999 ) > uint( 32 * span_norm_sqr[i] ) ) + { + span[i] = -span[i]; + swap(endPoint[i][0], endPoint[i][1]); + } + } + + uint p_error = 0; + for ( i = 0; i < 16; i ++ ) + { + uint subset_index = ( bits2 >> ( i * 2 ) ) & 0x03; + if ( subset_index == 2 ) + { + int dotProduct = dot( span[2], shared_temp[threadBase + i].pixel - endPoint[2][0] ); + color_index[i] = ( span_norm_sqr[2] <= 0 || dotProduct <= 0 ) ? 0 + : ( ( dotProduct < span_norm_sqr[2] ) ? aStep[step_selector][ uint( dotProduct * 63.49999 / span_norm_sqr[2] ) ] : aStep[step_selector][63] ); + } + else if ( subset_index == 1 ) + { + int dotProduct = dot( span[1], shared_temp[threadBase + i].pixel - endPoint[1][0] ); + color_index[i] = ( span_norm_sqr[1] <= 0 || dotProduct <= 0 ) ? 0 + : ( ( dotProduct < span_norm_sqr[1] ) ? aStep[step_selector][ uint( dotProduct * 63.49999 / span_norm_sqr[1] ) ] : aStep[step_selector][63] ); + } + else + { + int dotProduct = dot( span[0], shared_temp[threadBase + i].pixel - endPoint[0][0] ); + color_index[i] = ( span_norm_sqr[0] <= 0 || dotProduct <= 0 ) ? 0 + : ( ( dotProduct < span_norm_sqr[0] ) ? aStep[step_selector][ uint( dotProduct * 63.49999 / span_norm_sqr[0] ) ] : aStep[step_selector][63] ); + } + + pixel_r = ( ( 64 - aWeight[step_selector][color_index[i]] ) * endPoint[subset_index][0] + + aWeight[step_selector][color_index[i]] * endPoint[subset_index][1] + 32 ) >> 6; + pixel_r.a = 255; + + uint4 pixel = shared_temp[threadBase + i].pixel; + Ensure_A_Is_Larger( pixel_r, pixel ); + pixel_r -= pixel; + p_error += ComputeError(pixel_r, pixel_r); + } + + if (p_error < error) + { + error = p_error; + rotation = p; // Borrow rotation for p + } + } + + shared_temp[GI].error = error; + shared_temp[GI].partition = partition; + shared_temp[GI].rotation = rotation; + } + GroupMemoryBarrierWithGroupSync(); + + if (threadInBlock < 32) + { + if ( shared_temp[GI].error > shared_temp[GI + 32].error ) + { + shared_temp[GI].error = shared_temp[GI + 32].error; + shared_temp[GI].partition = shared_temp[GI + 32].partition; + shared_temp[GI].rotation = shared_temp[GI + 32].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 16) + { + if ( shared_temp[GI].error > shared_temp[GI + 16].error ) + { + shared_temp[GI].error = shared_temp[GI + 16].error; + shared_temp[GI].partition = shared_temp[GI + 16].partition; + shared_temp[GI].rotation = shared_temp[GI + 16].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 8) + { + if ( shared_temp[GI].error > shared_temp[GI + 8].error ) + { + shared_temp[GI].error = shared_temp[GI + 8].error; + shared_temp[GI].partition = shared_temp[GI + 8].partition; + shared_temp[GI].rotation = shared_temp[GI + 8].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 4) + { + if ( shared_temp[GI].error > shared_temp[GI + 4].error ) + { + shared_temp[GI].error = shared_temp[GI + 4].error; + shared_temp[GI].partition = shared_temp[GI + 4].partition; + shared_temp[GI].rotation = shared_temp[GI + 4].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 2) + { + if ( shared_temp[GI].error > shared_temp[GI + 2].error ) + { + shared_temp[GI].error = shared_temp[GI + 2].error; + shared_temp[GI].partition = shared_temp[GI + 2].partition; + shared_temp[GI].rotation = shared_temp[GI + 2].rotation; + } + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 1) + { + if ( shared_temp[GI].error > shared_temp[GI + 1].error ) + { + shared_temp[GI].error = shared_temp[GI + 1].error; + shared_temp[GI].partition = shared_temp[GI + 1].partition; + shared_temp[GI].rotation = shared_temp[GI + 1].rotation; + } + + if (g_InBuff[blockID].x > shared_temp[GI].error) + { + g_OutBuff[blockID] = uint4(shared_temp[GI].error, g_mode_id, shared_temp[GI].partition, shared_temp[GI].rotation); // rotation is actually p bit for mode 0. for mode 2, rotation is always 0 + } + else + { + g_OutBuff[blockID] = g_InBuff[blockID]; + } + } +} + +[numthreads( THREAD_GROUP_SIZE, 1, 1 )] +void EncodeBlockCS(uint GI : SV_GroupIndex, uint3 groupID : SV_GroupID) +{ + const uint MAX_USED_THREAD = 16; + uint BLOCK_IN_GROUP = THREAD_GROUP_SIZE / MAX_USED_THREAD; + uint blockInGroup = GI / MAX_USED_THREAD; + uint blockID = g_start_block_id + groupID.x * BLOCK_IN_GROUP + blockInGroup; + uint threadBase = blockInGroup * MAX_USED_THREAD; + uint threadInBlock = GI - threadBase; + +#ifndef REF_DEVICE + if (blockID >= g_num_total_blocks) + { + return; + } +#endif + + uint block_y = blockID / g_num_block_x; + uint block_x = blockID - block_y * g_num_block_x; + uint base_x = block_x * BLOCK_SIZE_X; + uint base_y = block_y * BLOCK_SIZE_Y; + + uint mode = g_InBuff[blockID].y & 0x7FFFFFFF; + uint partition = g_InBuff[blockID].z; + uint index_selector = (g_InBuff[blockID].y >> 31) & 1; + uint rotation = g_InBuff[blockID].w; + + if (threadInBlock < 16) + { + uint4 pixel = clamp(uint4(g_Input.Load( uint3( base_x + threadInBlock % 4, base_y + threadInBlock / 4, 0 ) ) * 255), 0, 255); + + if ((4 == mode) || (5 == mode)) + { + if (1 == rotation) + { + pixel.ra = pixel.ar; + } + else if (2 == rotation) + { + pixel.ga = pixel.ag; + } + else if (3 == rotation) + { + pixel.ba = pixel.ab; + } + } + + shared_temp[GI].pixel = pixel; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + uint bits = candidateSectionBit[partition]; + uint bits2 = candidateSectionBit2[partition - 64]; + + uint2x4 ep; + uint2x4 ep_quantized; + [unroll] + for (int ii = 2; ii >= 0; -- ii) + { + if (threadInBlock < 16) + { + uint2x4 ep; + ep[0] = MAX_UINT; + ep[1] = MIN_UINT; + + uint4 pixel = shared_temp[GI].pixel; + + uint subset_index = ( bits >> threadInBlock ) & 0x01; + uint subset_index2 = ( bits2 >> ( threadInBlock * 2 ) ) & 0x03; + if (0 == ii) + { + if ((0 == mode) || (2 == mode)) + { + if (0 == subset_index2) + { + ep[0] = ep[1] = pixel; + } + } + else if ((1 == mode) || (3 == mode) || (7 == mode)) + { + if (0 == subset_index) + { + ep[0] = ep[1] = pixel; + } + } + else if ((4 == mode) || (5 == mode) || (6 == mode)) + { + ep[0] = ep[1] = pixel; + } + } + else if (1 == ii) + { + if ((0 == mode) || (2 == mode)) + { + if (1 == subset_index2) + { + ep[0] = ep[1] = pixel; + } + } + else if ((1 == mode) || (3 == mode) || (7 == mode)) + { + if (1 == subset_index) + { + ep[0] = ep[1] = pixel; + } + } + } + else + { + if ((0 == mode) || (2 == mode)) + { + if (2 == subset_index2) + { + ep[0] = ep[1] = pixel; + } + } + } + + shared_temp[GI].endPoint_low = ep[0]; + shared_temp[GI].endPoint_high = ep[1]; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (threadInBlock < 8) + { + shared_temp[GI].endPoint_low = min(shared_temp[GI].endPoint_low, shared_temp[GI + 8].endPoint_low); + shared_temp[GI].endPoint_high = max(shared_temp[GI].endPoint_high, shared_temp[GI + 8].endPoint_high); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 4) + { + shared_temp[GI].endPoint_low = min(shared_temp[GI].endPoint_low, shared_temp[GI + 4].endPoint_low); + shared_temp[GI].endPoint_high = max(shared_temp[GI].endPoint_high, shared_temp[GI + 4].endPoint_high); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 2) + { + shared_temp[GI].endPoint_low = min(shared_temp[GI].endPoint_low, shared_temp[GI + 2].endPoint_low); + shared_temp[GI].endPoint_high = max(shared_temp[GI].endPoint_high, shared_temp[GI + 2].endPoint_high); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + if (threadInBlock < 1) + { + shared_temp[GI].endPoint_low = min(shared_temp[GI].endPoint_low, shared_temp[GI + 1].endPoint_low); + shared_temp[GI].endPoint_high = max(shared_temp[GI].endPoint_high, shared_temp[GI + 1].endPoint_high); + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (ii == (int)threadInBlock) + { + ep[0] = shared_temp[threadBase].endPoint_low; + ep[1] = shared_temp[threadBase].endPoint_high; + } + } + + if (threadInBlock < 3) + { + uint2 P; + if (1 == mode) + { + P = (rotation >> threadInBlock) & 1; + } + else + { + P = uint2(rotation >> (threadInBlock * 2 + 0), rotation >> (threadInBlock * 2 + 1)) & 1; + } + + if (0 == mode) + { + ep_quantized = compress_endpoints0( ep, P ); + } + else if (1 == mode) + { + ep_quantized = compress_endpoints1( ep, P ); + } + else if (2 == mode) + { + ep_quantized = compress_endpoints2( ep ); + } + else if (3 == mode) + { + ep_quantized = compress_endpoints3( ep, P ); + } + else if (4 == mode) + { + ep_quantized = compress_endpoints4( ep ); + } + else if (5 == mode) + { + ep_quantized = compress_endpoints5( ep ); + } + else if (6 == mode) + { + ep_quantized = compress_endpoints6( ep, P ); + } + else //if (7 == mode) + { + ep_quantized = compress_endpoints7( ep, P ); + } + + int4 span = ep[1] - ep[0]; + if (mode < 4) + { + span.w = 0; + } + + if ((4 == mode) || (5 == mode)) + { + if (0 == threadInBlock) + { + int2 span_norm_sqr = uint2( dot( span.rgb, span.rgb ), span.a * span.a ); + int2 dotProduct = int2( dot( span.rgb, shared_temp[threadBase + 0].pixel.rgb - ep[0].rgb ), span.a * ( shared_temp[threadBase + 0].pixel.a - ep[0].a ) ); + if ( span_norm_sqr.x > 0 && dotProduct.x > 0 && uint( dotProduct.x * 63.49999 ) > uint( 32 * span_norm_sqr.x ) ) + { + swap(ep[0].rgb, ep[1].rgb); + swap(ep_quantized[0].rgb, ep_quantized[1].rgb); + } + if ( span_norm_sqr.y > 0 && dotProduct.y > 0 && uint( dotProduct.y * 63.49999 ) > uint( 32 * span_norm_sqr.y ) ) + { + swap(ep[0].a, ep[1].a); + swap(ep_quantized[0].a, ep_quantized[1].a); + } + } + } + else //if ((0 == mode) || (2 == mode) || (1 == mode) || (3 == mode) || (7 == mode) || (6 == mode)) + { + int p; + if (0 == threadInBlock) + { + p = 0; + } + else if (1 == threadInBlock) + { + p = candidateFixUpIndex1D[partition].x; + } + else //if (2 == threadInBlock) + { + p = candidateFixUpIndex1D[partition].y; + } + + int span_norm_sqr = dot( span, span ); + int dotProduct = dot( span, shared_temp[threadBase + p].pixel - ep[0] ); + if ( span_norm_sqr > 0 && dotProduct > 0 && uint( dotProduct * 63.49999 ) > uint( 32 * span_norm_sqr ) ) + { + swap(ep[0], ep[1]); + swap(ep_quantized[0], ep_quantized[1]); + } + } + + shared_temp[GI].endPoint_low = ep[0]; + shared_temp[GI].endPoint_high = ep[1]; + shared_temp[GI].endPoint_low_quantized = ep_quantized[0]; + shared_temp[GI].endPoint_high_quantized = ep_quantized[1]; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (threadInBlock < 16) + { + uint color_index = 0; + uint alpha_index = 0; + + uint2x4 ep; + + uint2 indexPrec; + if ((0 == mode) || (1 == mode)) + { + indexPrec = 1; + } + else if (6 == mode) + { + indexPrec = 0; + } + else if (4 == mode) + { + if (0 == index_selector) + { + indexPrec = uint2(2, 1); + } + else + { + indexPrec = uint2(1, 2); + } + } + else + { + indexPrec = 2; + } + + int subset_index; + if ((0 == mode) || (2 == mode)) + { + subset_index = (bits2 >> (threadInBlock * 2)) & 0x03; + } + else if ((1 == mode) || (3 == mode) || (7 == mode)) + { + subset_index = (bits >> threadInBlock) & 0x01; + } + else + { + subset_index = 0; + } + + ep[0] = shared_temp[threadBase + subset_index].endPoint_low; + ep[1] = shared_temp[threadBase + subset_index].endPoint_high; + + int4 span = ep[1] - ep[0]; + if (mode < 4) + { + span.w = 0; + } + + if ((4 == mode) || (5 == mode)) + { + int2 span_norm_sqr; + span_norm_sqr.x = dot( span.rgb, span.rgb ); + span_norm_sqr.y = span.a * span.a; + + int dotProduct = dot( span.rgb, shared_temp[threadBase + threadInBlock].pixel.rgb - ep[0].rgb ); + color_index = ( span_norm_sqr.x <= 0 || dotProduct <= 0 ) ? 0 + : ( ( dotProduct < span_norm_sqr.x ) ? aStep[indexPrec.x][ uint( dotProduct * 63.49999 / span_norm_sqr.x ) ] : aStep[indexPrec.x][63] ); + dotProduct = dot( span.a, shared_temp[threadBase + threadInBlock].pixel.a - ep[0].a ); + alpha_index = ( span_norm_sqr.y <= 0 || dotProduct <= 0 ) ? 0 + : ( ( dotProduct < span_norm_sqr.y ) ? aStep[indexPrec.y][ uint( dotProduct * 63.49999 / span_norm_sqr.y ) ] : aStep[indexPrec.y][63] ); + + if (index_selector) + { + swap(color_index, alpha_index); + } + } + else + { + int span_norm_sqr = dot( span, span ); + + int dotProduct = dot( span, shared_temp[threadBase + threadInBlock].pixel - ep[0] ); + color_index = ( span_norm_sqr <= 0 || dotProduct <= 0 ) ? 0 + : ( ( dotProduct < span_norm_sqr ) ? aStep[indexPrec.x][ uint( dotProduct * 63.49999 / span_norm_sqr ) ] : aStep[indexPrec.x][63] ); + } + + shared_temp[GI].error = color_index; + shared_temp[GI].mode = alpha_index; + } +#ifdef REF_DEVICE + GroupMemoryBarrierWithGroupSync(); +#endif + + if (0 == threadInBlock) + { + uint4 block; + if (0 == mode) + { + block_package0( block, partition, threadBase ); + } + else if (1 == mode) + { + block_package1( block, partition, threadBase ); + } + else if (2 == mode) + { + block_package2( block, partition, threadBase ); + } + else if (3 == mode) + { + block_package3( block, partition, threadBase ); + } + else if (4 == mode) + { + block_package4( block, rotation, index_selector, threadBase ); + } + else if (5 == mode) + { + block_package5( block, rotation, threadBase ); + } + else if (6 == mode) + { + block_package6( block, threadBase ); + } + else //if (7 == mode) + { + block_package7( block, partition, threadBase ); + } + + g_OutBuff[blockID] = block; + } +} + +//uint4 truncate_and_round( uint4 color, uint bits) +//{ +// uint precisionMask = ((1 << bits) - 1) << (8 - bits); +// uint precisionHalf = (1 << (7-bits)); +// +// uint4 truncated = color & precisionMask; +// uint4 rounded = min(255, color + precisionHalf) & precisionMask; +// +// uint4 truncated_bak = truncated = truncated | (truncated >> bits); +// uint4 rounded_bak = rounded = rounded | (rounded >> bits); +// +// uint4 color_bak = color; +// +// Ensure_A_Is_Larger( rounded, color ); +// Ensure_A_Is_Larger( truncated, color_bak ); +// +// if (dot(rounded - color, rounded - color) < +// dot(truncated - color_bak, truncated - color_bak)) +// { +// return rounded_bak; +// } +// else +// { +// return truncated_bak; +// } +//} + +uint4 quantize( uint4 color, uint uPrec ) +{ + uint4 rnd = min(255, color + (1 << (7 - uPrec))); + return rnd >> (8 - uPrec); +} + +uint4 unquantize( uint4 color, uint uPrec ) +{ + color = color << (8 - uPrec); + return color | (color >> uPrec); +} + +uint2x4 compress_endpoints0( inout uint2x4 endPoint, uint2 P ) +{ + uint2x4 quantized; + for ( uint j = 0; j < 2; j ++ ) + { + quantized[j].rgb = quantize(endPoint[j].rgbb, 5).rgb & 0xFFFFFFFE; + quantized[j].rgb |= P[j]; + quantized[j].a = 0xFF; + + endPoint[j].rgb = unquantize(quantized[j].rgbb, 5).rgb; + endPoint[j].a = 0xFF; + + quantized[j] <<= 3; + } + return quantized; +} +uint2x4 compress_endpoints1( inout uint2x4 endPoint, uint2 P ) +{ + uint2x4 quantized; + for ( uint j = 0; j < 2; j ++ ) + { + quantized[j].rgb = quantize(endPoint[j].rgbb, 7).rgb & 0xFFFFFFFE; + quantized[j].rgb |= P[j]; + quantized[j].a = 0xFF; + + endPoint[j].rgb = unquantize(quantized[j].rgbb, 7).rgb; + endPoint[j].a = 0xFF; + + quantized[j] <<= 1; + } + return quantized; +} +uint2x4 compress_endpoints2( inout uint2x4 endPoint ) +{ + uint2x4 quantized; + for ( uint j = 0; j < 2; j ++ ) + { + quantized[j].rgb = quantize(endPoint[j].rgbb, 5).rgb; + quantized[j].a = 0xFF; + + endPoint[j].rgb = unquantize(quantized[j].rgbb, 5).rgb; + endPoint[j].a = 0xFF; + + quantized[j] <<= 3; + } + return quantized; +} +uint2x4 compress_endpoints3( inout uint2x4 endPoint, uint2 P ) +{ + uint2x4 quantized; + for ( uint j = 0; j < 2; j ++ ) + { + quantized[j].rgb = endPoint[j].rgb & 0xFFFFFFFE; + quantized[j].rgb |= P[j]; + quantized[j].a = 0xFF; + + endPoint[j].rgb = quantized[j].rgb; + endPoint[j].a = 0xFF; + } + return quantized; +} +uint2x4 compress_endpoints4( inout uint2x4 endPoint ) +{ + uint2x4 quantized; + for ( uint j = 0; j < 2; j ++ ) + { + quantized[j].rgb = quantize(endPoint[j].rgbb, 5).rgb; + quantized[j].a = quantize(endPoint[j].a, 6).r; + + endPoint[j].rgb = unquantize(quantized[j].rgbb, 5).rgb; + endPoint[j].a = unquantize(quantized[j].a, 6).r; + + quantized[j].rgb <<= 3; + quantized[j].a <<= 2; + } + return quantized; +} +uint2x4 compress_endpoints5( inout uint2x4 endPoint ) +{ + uint2x4 quantized; + for ( uint j = 0; j < 2; j ++ ) + { + quantized[j].rgb = quantize(endPoint[j].rgbb, 7).rgb; + quantized[j].a = endPoint[j].a; + + endPoint[j].rgb = unquantize(quantized[j].rgbb, 7).rgb; + // endPoint[j].a Alpha is full precision + + quantized[j].rgb <<= 1; + } + return quantized; +} +uint2x4 compress_endpoints6( inout uint2x4 endPoint, uint2 P ) +{ + uint2x4 quantized; + for ( uint j = 0; j < 2; j ++ ) + { + quantized[j] = endPoint[j] & 0xFFFFFFFE; + quantized[j] |= P[j]; + + endPoint[j] = quantized[j]; + } + return quantized; +} +uint2x4 compress_endpoints7( inout uint2x4 endPoint, uint2 P ) +{ + uint2x4 quantized; + for ( uint j = 0; j < 2; j ++ ) + { + quantized[j] = quantize(endPoint[j], 6) & 0xFFFFFFFE; + quantized[j] |= P[j]; + + endPoint[j] = unquantize(quantized[j], 6); + } + return quantized << 2; +} + +#define get_end_point_l(subset) shared_temp[threadBase + subset].endPoint_low_quantized +#define get_end_point_h(subset) shared_temp[threadBase + subset].endPoint_high_quantized +#define get_color_index(index) shared_temp[threadBase + index].error +#define get_alpha_index(index) shared_temp[threadBase + index].mode + +void block_package0( out uint4 block, uint partition, uint threadBase ) +{ + block.x = 0x01 | ( (partition - 64) << 1 ) + | ( ( get_end_point_l(0).r & 0xF0 ) << 1 ) | ( ( get_end_point_h(0).r & 0xF0 ) << 5 ) + | ( ( get_end_point_l(1).r & 0xF0 ) << 9 ) | ( ( get_end_point_h(1).r & 0xF0 ) << 13 ) + | ( ( get_end_point_l(2).r & 0xF0 ) << 17 ) | ( ( get_end_point_h(2).r & 0xF0 ) << 21 ) + | ( ( get_end_point_l(0).g & 0xF0 ) << 25 ); + block.y = ( ( get_end_point_l(0).g & 0xF0 ) >> 7 ) | ( ( get_end_point_h(0).g & 0xF0 ) >> 3 ) + | ( ( get_end_point_l(1).g & 0xF0 ) << 1 ) | ( ( get_end_point_h(1).g & 0xF0 ) << 5 ) + | ( ( get_end_point_l(2).g & 0xF0 ) << 9 ) | ( ( get_end_point_h(2).g & 0xF0 ) << 13 ) + | ( ( get_end_point_l(0).b & 0xF0 ) << 17 ) | ( ( get_end_point_h(0).b & 0xF0 ) << 21 ) + | ( ( get_end_point_l(1).b & 0xF0 ) << 25 ); + block.z = ( ( get_end_point_l(1).b & 0xF0 ) >> 7 ) | ( ( get_end_point_h(1).b & 0xF0 ) >> 3 ) + | ( ( get_end_point_l(2).b & 0xF0 ) << 1 ) | ( ( get_end_point_h(2).b & 0xF0 ) << 5 ) + | ( ( get_end_point_l(0).r & 0x08 ) << 10 ) | ( ( get_end_point_h(0).r & 0x08 ) << 11 ) + | ( ( get_end_point_l(1).r & 0x08 ) << 12 ) | ( ( get_end_point_h(1).r & 0x08 ) << 13 ) + | ( ( get_end_point_l(2).r & 0x08 ) << 14 ) | ( ( get_end_point_h(2).r & 0x08 ) << 15 ) + | ( get_color_index(0) << 19 ); + block.w = 0; + uint i = 1; + for ( ; i <= min( candidateFixUpIndex1DOrdered[partition][0], 4 ); i ++ ) + { + block.z |= get_color_index(i) << ( i * 3 + 18 ); + } + if ( candidateFixUpIndex1DOrdered[partition][0] < 4 ) //i = 4 + { + block.z |= get_color_index(4) << 29; + i += 1; + } + else //i = 5 + { + block.w |= ( get_color_index(4) & 0x04 ) >> 2; + for ( ; i <= candidateFixUpIndex1DOrdered[partition][0]; i ++ ) + block.w |= get_color_index(i) << ( i * 3 - 14 ); + } + for ( ; i <= candidateFixUpIndex1DOrdered[partition][1]; i ++ ) + { + block.w |= get_color_index(i) << ( i * 3 - 15 ); + } + for ( ; i < 16; i ++ ) + { + block.w |= get_color_index(i) << ( i * 3 - 16 ); + } +} +void block_package1( out uint4 block, uint partition, uint threadBase ) +{ + block.x = 0x02 | ( partition << 2 ) + | ( ( get_end_point_l(0).r & 0xFC ) << 6 ) | ( ( get_end_point_h(0).r & 0xFC ) << 12 ) + | ( ( get_end_point_l(1).r & 0xFC ) << 18 ) | ( ( get_end_point_h(1).r & 0xFC ) << 24 ); + block.y = ( ( get_end_point_l(0).g & 0xFC ) >> 2 ) | ( ( get_end_point_h(0).g & 0xFC ) << 4 ) + | ( ( get_end_point_l(1).g & 0xFC ) << 10 ) | ( ( get_end_point_h(1).g & 0xFC ) << 16 ) + | ( ( get_end_point_l(0).b & 0xFC ) << 22 ) | ( ( get_end_point_h(0).b & 0xFC ) << 28 ); + block.z = ( ( get_end_point_h(0).b & 0xFC ) >> 4 ) | ( ( get_end_point_l(1).b & 0xFC ) << 2 ) + | ( ( get_end_point_h(1).b & 0xFC ) << 8 ) + | ( ( get_end_point_l(0).r & 0x02 ) << 15 ) | ( ( get_end_point_l(1).r & 0x02 ) << 16 ) + | ( get_color_index(0) << 18 ); + if ( candidateFixUpIndex1DOrdered[partition][0] == 15 ) + { + block.w = (get_color_index(15) << 30) | (get_color_index(14) << 27) | (get_color_index(13) << 24) | (get_color_index(12) << 21) | (get_color_index(11) << 18) | (get_color_index(10) << 15) + | (get_color_index(9) << 12) | (get_color_index(8) << 9) | (get_color_index(7) << 6) | (get_color_index(6) << 3) | get_color_index(5); + block.z |= (get_color_index(4) << 29) | (get_color_index(3) << 26) | (get_color_index(2) << 23) | (get_color_index(1) << 20) | (get_color_index(0) << 18); + } + else if ( candidateFixUpIndex1DOrdered[partition][0] == 2 ) + { + block.w = (get_color_index(15) << 29) | (get_color_index(14) << 26) | (get_color_index(13) << 23) | (get_color_index(12) << 20) | (get_color_index(11) << 17) | (get_color_index(10) << 14) + | (get_color_index(9) << 11) | (get_color_index(8) << 8) | (get_color_index(7) << 5) | (get_color_index(6) << 2) | (get_color_index(5) >> 1); + block.z |= (get_color_index(5) << 31) | (get_color_index(4) << 28) | (get_color_index(3) << 25) | (get_color_index(2) << 23) | (get_color_index(1) << 20) | (get_color_index(0) << 18); + } + else if ( candidateFixUpIndex1DOrdered[partition][0] == 8 ) + { + block.w = (get_color_index(15) << 29) | (get_color_index(14) << 26) | (get_color_index(13) << 23) | (get_color_index(12) << 20) | (get_color_index(11) << 17) | (get_color_index(10) << 14) + | (get_color_index(9) << 11) | (get_color_index(8) << 9) | (get_color_index(7) << 6) | (get_color_index(6) << 3) | get_color_index(5); + block.z |= (get_color_index(4) << 29) | (get_color_index(3) << 26) | (get_color_index(2) << 23) | (get_color_index(1) << 20) | (get_color_index(0) << 18); + } + else //candidateFixUpIndex1DOrdered[partition] == 6 + { + block.w = (get_color_index(15) << 29) | (get_color_index(14) << 26) | (get_color_index(13) << 23) | (get_color_index(12) << 20) | (get_color_index(11) << 17) | (get_color_index(10) << 14) + | (get_color_index(9) << 11) | (get_color_index(8) << 8) | (get_color_index(7) << 6) | (get_color_index(6) << 4) | get_color_index(5); + block.z |= (get_color_index(4) << 29) | (get_color_index(3) << 26) | (get_color_index(2) << 23) | (get_color_index(1) << 20) | (get_color_index(0) << 18); + } +} +void block_package2( out uint4 block, uint partition, uint threadBase ) +{ + block.x = 0x04 | ( (partition - 64) << 3 ) + | ( ( get_end_point_l(0).r & 0xF8 ) << 6 ) | ( ( get_end_point_h(0).r & 0xF8 ) << 11 ) + | ( ( get_end_point_l(1).r & 0xF8 ) << 16 ) | ( ( get_end_point_h(1).r & 0xF8 ) << 21 ) + | ( ( get_end_point_l(2).r & 0xF8 ) << 26 ); + block.y = ( ( get_end_point_l(2).r & 0xF8 ) >> 6 ) | ( ( get_end_point_h(2).r & 0xF8 ) >> 1 ) + | ( ( get_end_point_l(0).g & 0xF8 ) << 4 ) | ( ( get_end_point_h(0).g & 0xF8 ) << 9 ) + | ( ( get_end_point_l(1).g & 0xF8 ) << 14 ) | ( ( get_end_point_h(1).g & 0xF8 ) << 19 ) + | ( ( get_end_point_l(2).g & 0xF8 ) << 24 ); + block.z = ( ( get_end_point_h(2).g & 0xF8 ) >> 3 ) | ( ( get_end_point_l(0).b & 0xF8 ) << 2 ) + | ( ( get_end_point_h(0).b & 0xF8 ) << 7 ) | ( ( get_end_point_l(1).b & 0xF8 ) << 12 ) + | ( ( get_end_point_h(1).b & 0xF8 ) << 17 ) | ( ( get_end_point_l(2).b & 0xF8 ) << 22 ) + | ( ( get_end_point_h(2).b & 0xF8 ) << 27 ); + block.w = ( ( get_end_point_h(2).b & 0xF8 ) >> 5 ) + | ( get_color_index(0) << 3 ); + uint i = 1; + for ( ; i <= candidateFixUpIndex1DOrdered[partition][0]; i ++ ) + { + block.w |= get_color_index(i) << ( i * 2 + 2 ); + } + for ( ; i <= candidateFixUpIndex1DOrdered[partition][1]; i ++ ) + { + block.w |= get_color_index(i) << ( i * 2 + 1 ); + } + for ( ; i < 16; i ++ ) + { + block.w |= get_color_index(i) << ( i * 2 ); + } +} +void block_package3( out uint4 block, uint partition, uint threadBase ) +{ + block.x = 0x08 | ( partition << 4 ) + | ( ( get_end_point_l(0).r & 0xFE ) << 9 ) | ( ( get_end_point_h(0).r & 0xFE ) << 16 ) + | ( ( get_end_point_l(1).r & 0xFE ) << 23 ) | ( ( get_end_point_h(1).r & 0xFE ) << 30 ); + block.y = ( ( get_end_point_h(1).r & 0xFE ) >> 2 ) | ( ( get_end_point_l(0).g & 0xFE ) << 5 ) + | ( ( get_end_point_h(0).g & 0xFE ) << 12 ) | ( ( get_end_point_l(1).g & 0xFE ) << 19 ) + | ( ( get_end_point_h(1).g & 0xFE ) << 26 ); + block.z = ( ( get_end_point_h(1).g & 0xFE ) >> 6 ) | ( ( get_end_point_l(0).b & 0xFE ) << 1 ) + | ( ( get_end_point_h(0).b & 0xFE ) << 8 ) | ( ( get_end_point_l(1).b & 0xFE ) << 15 ) + | ( ( get_end_point_h(1).b & 0xFE ) << 22 ) + | ( ( get_end_point_l(0).r & 0x01 ) << 30 ) | ( ( get_end_point_h(0).r & 0x01 ) << 31 ); + block.w = ( ( get_end_point_l(1).r & 0x01 ) << 0 ) | ( ( get_end_point_h(1).r & 0x01 ) << 1 ) + | ( get_color_index(0) << 2 ); + uint i = 1; + for ( ; i <= candidateFixUpIndex1DOrdered[partition][0]; i ++ ) + { + block.w |= get_color_index(i) << ( i * 2 + 1 ); + } + for ( ; i < 16; i ++ ) + { + block.w |= get_color_index(i) << ( i * 2 ); + } +} +void block_package4( out uint4 block, uint rotation, uint index_selector, uint threadBase ) +{ + block.x = 0x10 | ( (rotation & 3) << 5 ) | ( (index_selector & 1) << 7 ) + | ( ( get_end_point_l(0).r & 0xF8 ) << 5 ) | ( ( get_end_point_h(0).r & 0xF8 ) << 10 ) + | ( ( get_end_point_l(0).g & 0xF8 ) << 15 ) | ( ( get_end_point_h(0).g & 0xF8 ) << 20 ) + | ( ( get_end_point_l(0).b & 0xF8 ) << 25 ); + + block.y = ( ( get_end_point_l(0).b & 0xF8 ) >> 7 ) | ( ( get_end_point_h(0).b & 0xF8 ) >> 2 ) + | ( ( get_end_point_l(0).a & 0xFC ) << 4 ) | ( ( get_end_point_h(0).a & 0xFC ) << 10 ) + | ( (get_color_index(0) & 1) << 18 ) | ( get_color_index(1) << 19 ) | ( get_color_index(2) << 21 ) | ( get_color_index(3) << 23 ) + | ( get_color_index(4) << 25 ) | ( get_color_index(5) << 27 ) | ( get_color_index(6) << 29 ) | ( get_color_index(7) << 31 ); + + block.z = ( get_color_index(7) >> 1 ) | ( get_color_index(8) << 1 ) | ( get_color_index(9) << 3 ) | ( get_color_index(10)<< 5 ) + | ( get_color_index(11)<< 7 ) | ( get_color_index(12)<< 9 ) | ( get_color_index(13)<< 11 ) | ( get_color_index(14)<< 13 ) + | ( get_color_index(15)<< 15 ) | ( (get_alpha_index(0) & 3) << 17 ) | ( get_alpha_index(1) << 19 ) | ( get_alpha_index(2) << 22 ) + | ( get_alpha_index(3) << 25 ) | ( get_alpha_index(4) << 28 ) | ( get_alpha_index(5) << 31 ); + + block.w = ( get_alpha_index(5) >> 1 ) | ( get_alpha_index(6) << 2 ) | ( get_alpha_index(7) << 5 ) | ( get_alpha_index(8) << 8 ) + | ( get_alpha_index(9) << 11 ) | ( get_alpha_index(10)<< 14 ) | ( get_alpha_index(11)<< 17 ) | ( get_alpha_index(12)<< 20 ) + | ( get_alpha_index(13)<< 23 ) | ( get_alpha_index(14)<< 26 ) | ( get_alpha_index(15)<< 29 ); +} +void block_package5( out uint4 block, uint rotation, uint threadBase ) +{ + block.x = 0x20 | ( rotation << 6 ) + | ( ( get_end_point_l(0).r & 0xFE ) << 7 ) | ( ( get_end_point_h(0).r & 0xFE ) << 14 ) + | ( ( get_end_point_l(0).g & 0xFE ) << 21 ) | ( ( get_end_point_h(0).g & 0xFE ) << 28 ); + block.y = ( ( get_end_point_h(0).g & 0xFE ) >> 4 ) | ( ( get_end_point_l(0).b & 0xFE ) << 3 ) + | ( ( get_end_point_h(0).b & 0xFE ) << 10 ) | ( get_end_point_l(0).a << 18 ) | ( get_end_point_h(0).a << 26 ); + block.z = ( get_end_point_h(0).a >> 6 ) + | ( get_color_index(0) << 2 ) | ( get_color_index(1) << 3 ) | ( get_color_index(2) << 5 ) | ( get_color_index(3) << 7 ) + | ( get_color_index(4) << 9 ) | ( get_color_index(5) << 11 ) | ( get_color_index(6) << 13 ) | ( get_color_index(7) << 15 ) + | ( get_color_index(8) << 17 ) | ( get_color_index(9) << 19 ) | ( get_color_index(10)<< 21 ) | ( get_color_index(11)<< 23 ) + | ( get_color_index(12)<< 25 ) | ( get_color_index(13)<< 27 ) | ( get_color_index(14)<< 29 ) | ( get_color_index(15)<< 31 ); + block.w = ( get_color_index(15)>> 1 ) | ( get_alpha_index(0) << 1 ) | ( get_alpha_index(1) << 2 ) | ( get_alpha_index(2) << 4 ) + | ( get_alpha_index(3) << 6 ) | ( get_alpha_index(4) << 8 ) | ( get_alpha_index(5) << 10 ) | ( get_alpha_index(6) << 12 ) + | ( get_alpha_index(7) << 14 ) | ( get_alpha_index(8) << 16 ) | ( get_alpha_index(9) << 18 ) | ( get_alpha_index(10)<< 20 ) + | ( get_alpha_index(11)<< 22 ) | ( get_alpha_index(12)<< 24 ) | ( get_alpha_index(13)<< 26 ) | ( get_alpha_index(14)<< 28 ) + | ( get_alpha_index(15)<< 30 ); +} +void block_package6( out uint4 block, uint threadBase ) +{ + block.x = 0x40 + | ( ( get_end_point_l(0).r & 0xFE ) << 6 ) | ( ( get_end_point_h(0).r & 0xFE ) << 13 ) + | ( ( get_end_point_l(0).g & 0xFE ) << 20 ) | ( ( get_end_point_h(0).g & 0xFE ) << 27 ); + block.y = ( ( get_end_point_h(0).g & 0xFE ) >> 5 ) | ( ( get_end_point_l(0).b & 0xFE ) << 2 ) + | ( ( get_end_point_h(0).b & 0xFE ) << 9 ) | ( ( get_end_point_l(0).a & 0xFE ) << 16 ) + | ( ( get_end_point_h(0).a & 0xFE ) << 23 ) + | ( get_end_point_l(0).r & 0x01 ) << 31; + block.z = ( get_end_point_h(0).r & 0x01 ) + | ( get_color_index(0) << 1 ) | ( get_color_index(1) << 4 ) | ( get_color_index(2) << 8 ) | ( get_color_index(3) << 12 ) + | ( get_color_index(4) << 16 ) | ( get_color_index(5) << 20 ) | ( get_color_index(6) << 24 ) | ( get_color_index(7) << 28 ); + block.w = ( get_color_index(8) << 0 ) | ( get_color_index(9) << 4 ) | ( get_color_index(10)<< 8 ) | ( get_color_index(11)<< 12 ) + | ( get_color_index(12)<< 16 ) | ( get_color_index(13)<< 20 ) | ( get_color_index(14)<< 24 ) | ( get_color_index(15)<< 28 ); +} +void block_package7( out uint4 block, uint partition, uint threadBase ) +{ + block.x = 0x80 | ( partition << 8 ) + | ( ( get_end_point_l(0).r & 0xF8 ) << 11 ) | ( ( get_end_point_h(0).r & 0xF8 ) << 16 ) + | ( ( get_end_point_l(1).r & 0xF8 ) << 21 ) | ( ( get_end_point_h(1).r & 0xF8 ) << 26 ); + block.y = ( ( get_end_point_h(1).r & 0xF8 ) >> 6 ) | ( ( get_end_point_l(0).g & 0xF8 ) >> 1 ) + | ( ( get_end_point_h(0).g & 0xF8 ) << 4 ) | ( ( get_end_point_l(1).g & 0xF8 ) << 9 ) + | ( ( get_end_point_h(1).g & 0xF8 ) << 14 ) | ( ( get_end_point_l(0).b & 0xF8 ) << 19 ) + | ( ( get_end_point_h(0).b & 0xF8 ) << 24 ); + block.z = ( ( get_end_point_l(1).b & 0xF8 ) >> 3 ) | ( ( get_end_point_h(1).b & 0xF8 ) << 2 ) + | ( ( get_end_point_l(0).a & 0xF8 ) << 7 ) | ( ( get_end_point_h(0).a & 0xF8 ) << 12 ) + | ( ( get_end_point_l(1).a & 0xF8 ) << 17 ) | ( ( get_end_point_h(1).a & 0xF8 ) << 22 ) + | ( ( get_end_point_l(0).r & 0x04 ) << 28 ) | ( ( get_end_point_h(0).r & 0x04 ) << 29 ); + block.w = ( ( get_end_point_l(1).r & 0x04 ) >> 2 ) | ( ( get_end_point_h(1).r & 0x04 ) >> 1 ) + | ( get_color_index(0) << 2 ); + uint i = 1; + for ( ; i <= candidateFixUpIndex1DOrdered[partition][0]; i ++ ) + { + block.w |= get_color_index(i) << ( i * 2 + 1 ); + } + for ( ; i < 16; i ++ ) + { + block.w |= get_color_index(i) << ( i * 2 ); + } +} \ No newline at end of file diff --git a/deps/DirectXTex/DirectXTex/Shaders/CompileShaders.cmd b/deps/DirectXTex/DirectXTex/Shaders/CompileShaders.cmd new file mode 100644 index 0000000..76e340d --- /dev/null +++ b/deps/DirectXTex/DirectXTex/Shaders/CompileShaders.cmd @@ -0,0 +1,37 @@ +@echo off +rem THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +rem ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +rem THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +rem PARTICULAR PURPOSE. +rem +rem Copyright (c) Microsoft Corporation. All rights reserved. + +setlocal +set error=0 + +call :CompileShader BC7Encode TryMode456CS +call :CompileShader BC7Encode TryMode137CS +call :CompileShader BC7Encode TryMode02CS +call :CompileShader BC7Encode EncodeBlockCS + +call :CompileShader BC6HEncode TryModeG10CS +call :CompileShader BC6HEncode TryModeLE10CS +call :CompileShader BC6HEncode EncodeBlockCS + +echo. + +if %error% == 0 ( + echo Shaders compiled ok +) else ( + echo There were shader compilation errors! +) + +endlocal +exit /b + +:CompileShader +set fxc=fxc /nologo %1.hlsl /Tcs_4_0 /Zi /Zpc /Qstrip_reflect /Qstrip_debug /E%2 /FhCompiled\%1_%2.inc /FdCompiled\%1_%2.pdb /Vn%1_%2 +echo. +echo %fxc% +%fxc% || set error=1 +exit /b diff --git a/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC6HEncode_EncodeBlockCS.inc b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC6HEncode_EncodeBlockCS.inc new file mode 100644 index 0000000..380f63e --- /dev/null +++ b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC6HEncode_EncodeBlockCS.inc @@ -0,0 +1,22226 @@ +#if 0 +// +// Generated by Microsoft (R) D3D Shader Disassembler +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Input +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Output +cs_4_0 +dcl_globalFlags refactoringAllowed +dcl_immediateConstantBuffer { { 0x0000cccc, 15, 0, 0}, + { 0x00008888, 15, 0, 0}, + { 0x0000eeee, 15, 0, 0}, + { 0x0000ecc8, 15, 1, 0}, + { 0x0000c880, 15, 1, 0}, + { 0x0000feec, 15, 1, 1}, + { 0x0000fec8, 15, 1, 1}, + { 0x0000ec80, 15, 2, 1}, + { 0x0000c800, 15, 2, 1}, + { 0x0000ffec, 15, 2, 1}, + { 0x0000fe80, 15, 2, 1}, + { 0x0000e800, 15, 2, 1}, + { 0x0000ffe8, 15, 3, 1}, + { 0x0000ff00, 15, 3, 1}, + { 0x0000fff0, 15, 3, 2}, + { 0x0000f000, 15, 3, 2}, + { 0x0000f710, 15, 4, 2}, + { 142, 2, 4, 2}, + { 0x00007100, 8, 4, 2}, + { 2254, 2, 4, 2}, + { 140, 2, 5, 2}, + { 0x00007310, 8, 5, 2}, + { 0x00003100, 8, 5, 2}, + { 0x00008cce, 15, 5, 3}, + { 2188, 2, 6, 3}, + { 0x00003110, 8, 6, 3}, + { 0x00006666, 2, 6, 3}, + { 0x0000366c, 2, 6, 3}, + { 6120, 8, 6, 3}, + { 4080, 8, 7, 3}, + { 0x0000718e, 2, 7, 3}, + { 0x0000399c, 2, 7, 3}, + { -1, 0, 7, 3}, + { -1, 0, 8, 4}, + { -1, 0, 8, 4}, + { -1, 0, 8, 4}, + { -1, 0, 8, 4}, + { -1, 0, 9, 4}, + { -1, 0, 9, 4}, + { -1, 0, 9, 4}, + { -1, 0, 9, 4}, + { 0, 0, 10, 4}, + { 0, 0, 10, 5}, + { -1, 0, 10, 5}, + { -1, 0, 10, 5}, + { -1, 0, 10, 5}, + { 0, 0, 11, 5}, + { 0, 0, 11, 5}, + { 0, 0, 11, 5}, + { 0, 0, 11, 5}, + { 0, 0, 12, 5}, + { 0, 0, 12, 6}, + { 0, 0, 12, 6}, + { 0, 0, 12, 6}, + { 0, 0, 13, 6}, + { 0, 0, 13, 6}, + { 0, 0, 13, 6}, + { 0, 0, 13, 6}, + { 0, 0, 14, 6}, + { 0, 0, 14, 6}, + { 0, 0, 14, 7}, + { 0, 0, 14, 7}, + { 0, 0, 15, 7}, + { 0, 0, 15, 7}, + { 10, 5, 5, 5}, + { 7, 6, 6, 6}, + { 11, 5, 4, 4}, + { 11, 4, 5, 4}, + { 11, 4, 4, 5}, + { 9, 5, 5, 5}, + { 8, 6, 5, 5}, + { 8, 5, 6, 5}, + { 8, 5, 5, 6}, + { 6, 6, 6, 6}, + { 10, 10, 10, 10}, + { 11, 9, 9, 9}, + { 12, 8, 8, 8}, + { 16, 4, 4, 4} } +dcl_constantbuffer CB0[2], immediateIndexed +dcl_resource_texture2d (float,float,float,float) t0 +dcl_resource_structured t1, 16 +dcl_uav_structured u0, 16 +dcl_input vThreadIDInGroupFlattened +dcl_input vThreadGroupID.x +dcl_temps 18 +dcl_tgsm_structured g0, 84, 64 +dcl_thread_group 64, 1, 1 +ushr r0.x, vThreadIDInGroupFlattened.x, l(5) +ishl r0.y, vThreadGroupID.x, l(1) +iadd r0.y, r0.y, cb0[1].x +iadd r0.x, r0.x, r0.y +and r0.y, vThreadIDInGroupFlattened.x, l(32) +iadd r0.z, -r0.y, vThreadIDInGroupFlattened.x +ult r1.xyzw, r0.zzzz, l(16, 32, 2, 8) +if_nz r1.x + udiv r0.w, null, r0.x, cb0[0].y + imad r2.x, -r0.w, cb0[0].y, r0.x + ishl r2.x, r2.x, l(2) + ishl r0.w, r0.w, l(2) + and r2.y, r0.z, l(3) + iadd r2.x, r2.y, r2.x + ushr r3.x, r0.z, l(2) + iadd r2.y, r0.w, r3.x + mov r2.zw, l(0,0,0,0) + ld r2.xyzw, r2.xyzw, t0.xyzw + dp3 r0.w, r2.xyzx, l(0.212600, 0.715200, 0.072200, 0.000000) + store_structured g0.x, vThreadIDInGroupFlattened.x, l(36), r0.w + ushr r3.xyz, r2.xyzx, l(16) + and r3.xyz, r3.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + and r4.xyzw, r2.xxyy, l(0x7fffffff, 0x007fffff, 0x7fffffff, 0x007fffff) + ult r2.xy, l(0x47ffefff, 0x47ffefff, 0, 0), r4.xzxx + ult r5.xy, r4.xzxx, l(0x38800000, 0x38800000, 0, 0) + ushr r5.zw, r4.xxxz, l(23) + iadd r5.zw, -r5.zzzw, l(0, 0, 113, 113) + iadd r4.yw, r4.yyyw, l(0, 0x00800000, 0, 0x00800000) + ushr r6.x, r4.y, r5.z + ushr r6.y, r4.w, r5.w + iadd r4.xy, r4.xzxx, l(0xc8000000, 0xc8000000, 0, 0) + movc r4.xy, r5.xyxx, r6.xyxx, r4.xyxx + iadd r4.zw, r4.xxxy, l(0, 0, 4095, 4095) + ushr r4.xy, r4.xyxx, l(13) + and r4.xy, r4.xyxx, l(1, 1, 0, 0) + iadd r4.xy, r4.xyxx, r4.zwzz + ushr r4.xy, r4.xyxx, l(13) + and r4.xy, r4.xyxx, l(0x00007fff, 0x00007fff, 0, 0) + movc r2.xy, r2.xyxx, l(0x00007fff,0x00007fff,0,0), r4.xyxx + iadd r4.xy, r3.xyxx, r2.xyxx + and r2.xy, r2.zzzz, l(0x7fffffff, 0x007fffff, 0, 0) + ult r0.w, l(0x47ffefff), r2.x + ult r2.z, r2.x, l(0x38800000) + ushr r2.w, r2.x, l(23) + iadd r2.w, -r2.w, l(113) + iadd r2.y, r2.y, l(0x00800000) + ushr r2.y, r2.y, r2.w + iadd r2.x, r2.x, l(0xc8000000) + movc r2.x, r2.z, r2.y, r2.x + iadd r2.y, r2.x, l(4095) + ushr r2.x, r2.x, l(13) + and r2.x, r2.x, l(1) + iadd r2.x, r2.x, r2.y + ushr r2.x, r2.x, l(13) + and r2.x, r2.x, l(0x00007fff) + movc r0.w, r0.w, l(0x00007fff), r2.x + iadd r4.z, r3.z, r0.w + ieq r0.w, cb0[0].z, l(95) + ishl r2.xyz, r4.xyzx, l(6) + udiv r2.xyz, null, r2.xyzx, l(31, 31, 31, 0) + ult r3.xyz, r4.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + ieq r5.xyz, r4.xyzx, l(0x00007bff, 0x00007bff, 0x00007bff, 0) + ishl r4.xyz, r4.xyzx, l(5) + udiv r6.xyz, null, r4.xyzx, l(31, 31, 31, 0) + movc r6.xyz, r5.xyzx, l(0x00007fff,0x00007fff,0x00007fff,0), r6.xyzx + and r4.xyz, r4.xyzx, l(0x000fffe0, 0x000fffe0, 0x000fffe0, 0) + udiv r4.xyz, null, r4.xyzx, l(31, 31, 31, 0) + ineg r4.xyz, r4.xyzx + movc r4.xyz, r5.xyzx, l(0xffff8001,0xffff8001,0xffff8001,0), r4.xyzx + movc r3.xyz, r3.xyzx, r6.xyzx, r4.xyzx + movc r2.xyz, r0.wwww, r2.xyzx, r3.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(12), r2.xyzx +endif +sync_g_t +ld_structured r2.xy, r0.x, l(4), t1.xyxx +if_nz r1.y + and r0.w, r0.z, l(15) + iadd r1.y, r0.w, r0.y + ld_structured r3.xyz, r1.y, l(12), g0.xyzx + ld_structured r3.w, r1.y, l(36), g0.xxxx + if_nz r1.x + ult r1.y, l(10), r2.x + if_nz r1.y + mov r4.xyzw, r3.xyzx + mov r5.xyzw, r3.yzww + else + ushr r1.y, icb[r2.y + 0].x, r0.z + and r1.y, r1.y, l(1) + movc r4.xyzw, r1.yyyy, l(0x7fffffff,0x7fffffff,0x7fffffff,-0.000000), r3.xyzx + movc r5.xyzw, r1.yyyy, l(-0.000000,-0.000000,340282346638528860000000000000000000000.000000,-340282346638528860000000000000000000000.000000), r3.yzww + endif + else + uge r1.y, l(10), r2.x + if_nz r1.y + ushr r0.w, icb[r2.y + 0].x, r0.w + and r0.w, r0.w, l(1) + ieq r0.w, r0.w, l(1) + movc r4.xyzw, r0.wwww, r3.xyzx, l(0x7fffffff,0x7fffffff,0x7fffffff,-0.000000) + movc r5.xyzw, r0.wwww, r3.yzww, l(-0.000000,-0.000000,340282346638528860000000000000000000000.000000,-340282346638528860000000000000000000000.000000) + else + mov r4.xyzw, l(0x7fffffff,0x7fffffff,0x7fffffff,-0.000000) + mov r5.xyzw, l(-0.000000,-0.000000,340282346638528860000000000000000000000.000000,-340282346638528860000000000000000000000.000000) + endif + endif + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r4.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(68), r5.xyzw +endif +sync_g_t +and r0.w, r0.z, l(15) +ult r3.xyzw, r0.wwww, l(8, 4, 2, 1) +if_nz r3.x + ld_structured r4.x, vThreadIDInGroupFlattened.x, l(76), g0.xxxx + iadd r0.w, vThreadIDInGroupFlattened.x, l(8) + ld_structured r5.x, r0.w, l(76), g0.xxxx + lt r1.y, r5.x, r4.x + if_nz r1.y + ld_structured r4.xyz, r0.w, l(52), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(52), r4.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(76), r5.x + endif + ld_structured r4.x, vThreadIDInGroupFlattened.x, l(80), g0.xxxx + ld_structured r5.x, r0.w, l(80), g0.xxxx + lt r1.y, r4.x, r5.x + if_nz r1.y + ld_structured r4.xyz, r0.w, l(64), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(64), r4.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(80), r5.x + endif +endif +sync_g_t +if_nz r3.y + ld_structured r4.x, vThreadIDInGroupFlattened.x, l(76), g0.xxxx + iadd r0.w, vThreadIDInGroupFlattened.x, l(4) + ld_structured r5.x, r0.w, l(76), g0.xxxx + lt r1.y, r5.x, r4.x + if_nz r1.y + ld_structured r4.xyz, r0.w, l(52), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(52), r4.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(76), r5.x + endif + ld_structured r4.x, vThreadIDInGroupFlattened.x, l(80), g0.xxxx + ld_structured r5.x, r0.w, l(80), g0.xxxx + lt r1.y, r4.x, r5.x + if_nz r1.y + ld_structured r4.xyz, r0.w, l(64), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(64), r4.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(80), r5.x + endif +endif +sync_g_t +if_nz r3.z + ld_structured r4.x, vThreadIDInGroupFlattened.x, l(76), g0.xxxx + iadd r0.w, vThreadIDInGroupFlattened.x, l(2) + ld_structured r5.x, r0.w, l(76), g0.xxxx + lt r1.y, r5.x, r4.x + if_nz r1.y + ld_structured r4.xyz, r0.w, l(52), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(52), r4.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(76), r5.x + endif + ld_structured r4.x, vThreadIDInGroupFlattened.x, l(80), g0.xxxx + ld_structured r5.x, r0.w, l(80), g0.xxxx + lt r1.y, r4.x, r5.x + if_nz r1.y + ld_structured r4.xyz, r0.w, l(64), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(64), r4.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(80), r5.x + endif +endif +sync_g_t +if_nz r3.w + ld_structured r3.x, vThreadIDInGroupFlattened.x, l(76), g0.xxxx + iadd r0.w, vThreadIDInGroupFlattened.x, l(1) + ld_structured r4.x, r0.w, l(76), g0.xxxx + lt r1.y, r4.x, r3.x + if_nz r1.y + ld_structured r3.xyz, r0.w, l(52), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(52), r3.xyzx + endif + ld_structured r3.x, vThreadIDInGroupFlattened.x, l(80), g0.xxxx + ld_structured r4.x, r0.w, l(80), g0.xxxx + lt r1.y, r3.x, r4.x + if_nz r1.y + ld_structured r3.xyz, r0.w, l(64), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(64), r3.xyzx + endif +endif +sync_g_t +if_nz r1.z + ishl r0.w, r0.z, l(4) + iadd r0.w, r0.w, r0.y + ld_structured r3.xyz, r0.w, l(52), g0.xyzx + ld_structured r4.xyz, r0.w, l(64), g0.xyzx + ieq r0.w, r0.z, l(1) + uge r1.y, l(10), r2.x + and r0.w, r0.w, r1.y + if_nz r0.w + mov r0.w, icb[r2.y + 0].y + else + mov r0.w, l(0) + endif + iadd r5.xyz, -r3.xyzx, r4.xyzx + itof r5.xyz, r5.xyzx + dp3 r1.y, r5.xyzx, r5.xyzx + iadd r0.w, r0.w, r0.y + ld_structured r6.xyz, r0.w, l(12), g0.xyzx + iadd r6.xyz, -r3.xyzx, r6.xyzx + itof r6.xyz, r6.xyzx + dp3 r0.w, r5.xyzx, r6.xyzx + lt r2.z, l(0.000000), r1.y + ge r2.w, r0.w, l(0.000000) + and r2.z, r2.w, r2.z + mul r0.w, r0.w, l(63.499989) + div r0.w, r0.w, r1.y + ftou r0.w, r0.w + ult r0.w, l(32), r0.w + and r0.w, r0.w, r2.z + mov r4.w, r3.x + mov r3.w, r4.x + movc r5.xyzw, r0.wwww, r4.xyzw, r3.xyzw + movc r2.zw, r0.wwww, r3.yyyz, r4.yyyz + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r5.xyzw + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(68), r2.zwzz +endif +sync_g_t +if_nz r1.x + ult r0.w, l(10), r2.x + if_nz r0.w + mov r1.x, l(0) + else + mov r1.x, icb[r2.y + 0].x + endif + ushr r1.x, r1.x, r0.z + and r1.x, r1.x, l(1) + if_nz r1.x + iadd r1.x, r0.y, l(1) + ld_structured r3.xyz, r1.x, l(64), g0.xyzx + ld_structured r4.xyz, r1.x, l(52), g0.xyzx + iadd r3.xyz, r3.xyzx, -r4.xyzx + itof r3.xyz, r3.xyzx + ld_structured r5.xyz, vThreadIDInGroupFlattened.x, l(12), g0.xyzx + iadd r4.xyz, -r4.xyzx, r5.xyzx + itof r4.xyz, r4.xyzx + dp3 r1.x, r3.xyzx, r4.xyzx + else + ld_structured r4.xyz, r0.y, l(64), g0.xyzx + ld_structured r5.xyz, r0.y, l(52), g0.xyzx + iadd r4.xyz, r4.xyzx, -r5.xyzx + itof r3.xyz, r4.xyzx + ld_structured r4.xyz, vThreadIDInGroupFlattened.x, l(12), g0.xyzx + iadd r4.xyz, -r5.xyzx, r4.xyzx + itof r4.xyz, r4.xyzx + dp3 r1.x, r3.xyzx, r4.xyzx + endif + dp3 r1.y, r3.xyzx, r3.xyzx + if_nz r0.w + ge r0.w, l(0.000000), r1.y + ge r2.z, l(0.000000), r1.x + or r0.w, r0.w, r2.z + lt r2.z, r1.x, r1.y + mul r2.w, r1.x, l(63.499989) + div r2.w, r2.w, r1.y + ftou r2.w, r2.w + movc r2.z, r2.z, icb[r2.w + 0].z, l(15) + movc r0.w, r0.w, l(0), r2.z + ishl r3.x, r0.w, l(1) + ult r2.z, r0.z, l(8) + ishl r2.w, r0.z, l(2) + ishl r4.x, r0.w, r2.w + iadd r2.w, r2.w, l(-32) + ishl r4.w, r0.w, r2.w + mov r4.yz, l(0,0,0,0) + movc r2.zw, r2.zzzz, r4.xxxy, r4.zzzw + mov r3.y, l(0) + movc r3.xy, r0.zzzz, r2.zwzz, r3.xyxx + else + ge r0.w, l(0.000000), r1.y + ge r2.z, l(0.000000), r1.x + or r0.w, r0.w, r2.z + lt r2.z, r1.x, r1.y + mul r1.x, r1.x, l(63.499989) + div r1.x, r1.x, r1.y + ftou r1.x, r1.x + movc r1.x, r2.z, icb[r1.x + 0].w, l(7) + movc r0.w, r0.w, l(0), r1.x + if_z r0.z + ishl r3.x, r0.w, l(18) + mov r3.y, l(0) + else + ult r1.x, r0.z, l(3) + if_nz r1.x + imad r1.x, r0.z, l(3), l(17) + ishl r3.x, r0.w, r1.x + mov r3.y, l(0) + else + ine r1.x, l(2), icb[r2.y + 0].y + ieq r1.y, l(15), icb[r2.y + 0].y + and r2.zw, r1.xxxy, l(0, 0, 1, 1) + ult r1.y, r0.z, l(5) + if_nz r1.y + imad r1.y, r0.z, l(3), r2.z + iadd r1.y, r1.y, l(16) + ishl r3.x, r0.w, r1.y + mov r3.y, l(0) + else + ieq r1.y, r0.z, l(5) + movc r4.x, r1.x, l(0), l(1) + ushr r4.y, r0.w, r4.x + ishl r4.z, r0.w, l(31) + movc r4.x, r1.x, l(0), r4.z + ult r1.x, r0.z, l(9) + imad r2.zw, r0.zzzz, l(0, 0, 3, 3), r2.zzzw + iadd r2.zw, r2.zzzw, l(0, 0, -16, -16) + ishl r2.z, r0.w, r2.z + ishl r0.w, r0.w, r2.w + movc r5.y, r1.x, r2.z, r0.w + mov r5.x, l(0) + movc r3.xy, r1.yyyy, r4.xyxx, r5.xyxx + endif + endif + endif + endif + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(24), r3.xyxx +else + mov r3.xy, l(0,0,0,0) +endif +sync_g_t +if_nz r1.w + ld_structured r4.xy, vThreadIDInGroupFlattened.x, l(24), g0.xyxx + iadd r0.w, vThreadIDInGroupFlattened.x, l(8) + ld_structured r5.xy, r0.w, l(24), g0.xyxx + or r1.xy, r4.xyxx, r5.xyxx + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(24), r1.xyxx +endif +sync_g_t +ult r1.xy, r0.zzzz, l(4, 1, 0, 0) +if_nz r1.x + ld_structured r4.xy, vThreadIDInGroupFlattened.x, l(24), g0.xyxx + iadd r0.w, vThreadIDInGroupFlattened.x, l(4) + ld_structured r5.xy, r0.w, l(24), g0.xyxx + or r1.xw, r4.xxxy, r5.xxxy + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(24), r1.xwxx +endif +sync_g_t +if_nz r1.z + ld_structured r4.xy, vThreadIDInGroupFlattened.x, l(24), g0.xyxx + iadd r0.w, vThreadIDInGroupFlattened.x, l(2) + ld_structured r5.xy, r0.w, l(24), g0.xyxx + or r1.xw, r4.xxxy, r5.xxxy + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(24), r1.xwxx +endif +sync_g_t +if_nz r1.y + ld_structured r4.xy, vThreadIDInGroupFlattened.x, l(24), g0.xyxx + iadd r0.w, vThreadIDInGroupFlattened.x, l(1) + ld_structured r5.xy, r0.w, l(24), g0.xyxx + or r3.xy, r4.xyxx, r5.xyxx +endif +sync_g_t +iadd r0.w, r2.x, l(-1) +ieq r1.xy, r0.zzzz, l(2, 3, 0, 0) +if_nz r1.x + ld_structured r4.xyz, r0.y, l(52), g0.xyzx + ld_structured r5.xyz, r0.y, l(64), g0.xyzx + ieq r1.x, cb0[0].z, l(95) + if_nz r1.x + ige r1.x, icb[r0.w + 64].x, l(15) + and r1.x, r1.x, l(1) + movc r6.xyz, r4.xyzx, l(0,0,0,0), l(1,1,1,0) + movc r7.xyz, r5.xyzx, l(0,0,0,0), l(1,1,1,0) + or r6.xyz, r1.xxxx, r6.xyzx + or r7.xyz, r1.xxxx, r7.xyzx + ieq r8.xyz, r4.xyzx, l(0x0000ffff, 0x0000ffff, 0x0000ffff, 0) + ieq r9.xyz, r5.xyzx, l(0x0000ffff, 0x0000ffff, 0x0000ffff, 0) + ishl r1.x, l(1), icb[r0.w + 64].x + iadd r1.x, r1.x, l(-1) + ishl r10.xyz, r4.xyzx, icb[r0.w + 64].x + ishl r11.xyz, r5.xyzx, icb[r0.w + 64].x + ishr r10.xyz, r10.xyzx, l(16) + ishr r11.xyz, r11.xyzx, l(16) + movc r8.xyz, r8.xyzx, r1.xxxx, r10.xyzx + movc r9.xyz, r9.xyzx, r1.xxxx, r11.xyzx + movc r6.xyz, r6.xyzx, r4.xyzx, r8.xyzx + movc r7.xyz, r7.xyzx, r5.xyzx, r9.xyzx + else + ige r1.x, icb[r0.w + 64].x, l(16) + and r1.x, r1.x, l(1) + movc r8.xyz, r4.xyzx, l(0,0,0,0), l(1,1,1,0) + movc r9.xyz, r5.xyzx, l(0,0,0,0), l(1,1,1,0) + or r8.xyz, r1.xxxx, r8.xyzx + or r9.xyz, r1.xxxx, r9.xyzx + ige r10.xyz, r4.xyzx, l(0, 0, 0, 0) + ige r11.xyz, r5.xyzx, l(0, 0, 0, 0) + ieq r12.xyz, r4.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ieq r13.xyz, r5.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + iadd r1.x, l(-1), icb[r0.w + 64].x + ishl r1.w, l(1), r1.x + iadd r2.z, r1.w, l(-1) + ishl r14.xyz, r4.xyzx, r1.x + ishl r15.xyz, r5.xyzx, r1.x + ishr r14.xyz, r14.xyzx, l(15) + ishr r15.xyz, r15.xyzx, l(15) + movc r12.xyz, r12.xyzx, r2.zzzz, r14.xyzx + movc r13.xyz, r13.xyzx, r2.zzzz, r15.xyzx + ineg r14.xyz, r4.xyzx + ineg r15.xyz, r5.xyzx + ieq r16.xyz, r14.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ieq r17.xyz, r15.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + iadd r1.w, -r1.w, l(1) + ishl r14.xyz, r14.xyzx, r1.x + ishl r15.xyz, r15.xyzx, r1.x + ishr r14.xyz, r14.xyzx, l(15) + ishr r15.xyz, r15.xyzx, l(15) + ineg r14.xyz, r14.xyzx + ineg r15.xyz, r15.xyzx + movc r14.xyz, r16.xyzx, r1.wwww, r14.xyzx + movc r15.xyz, r17.xyzx, r1.wwww, r15.xyzx + movc r10.xyz, r10.xyzx, r12.xyzx, r14.xyzx + movc r11.xyz, r11.xyzx, r13.xyzx, r15.xyzx + movc r6.xyz, r8.xyzx, r4.xyzx, r10.xyzx + movc r7.xyz, r9.xyzx, r5.xyzx, r11.xyzx + endif + iadd r4.xyz, -r6.xyzx, r7.xyzx + movc r4.xyz, icb[r0.w + 32].xxxx, r4.xyzx, r7.xyzx + mov r6.w, r4.x + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r6.xyzw + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(68), r4.yzyy +endif +sync_g_t +if_nz r1.y + iadd r1.xy, r0.yyyy, l(2, 1, 0, 0) + ld_structured r4.xyz, r1.x, l(52), g0.xyzx + ld_structured r5.xyz, r1.y, l(52), g0.xyzx + ld_structured r6.xyz, r1.y, l(64), g0.xyzx + uge r1.x, l(10), r2.x + if_nz r1.x + ieq r1.x, cb0[0].z, l(95) + if_nz r1.x + ige r1.x, icb[r0.w + 64].x, l(15) + and r1.x, r1.x, l(1) + movc r7.xyz, r5.xyzx, l(0,0,0,0), l(1,1,1,0) + movc r8.xyz, r6.xyzx, l(0,0,0,0), l(1,1,1,0) + or r7.xyz, r1.xxxx, r7.xyzx + or r1.xyw, r1.xxxx, r8.xyxz + ieq r8.xyz, r5.xyzx, l(0x0000ffff, 0x0000ffff, 0x0000ffff, 0) + ieq r9.xyz, r6.xyzx, l(0x0000ffff, 0x0000ffff, 0x0000ffff, 0) + ishl r2.z, l(1), icb[r0.w + 64].x + iadd r2.z, r2.z, l(-1) + ishl r10.xyz, r5.xyzx, icb[r0.w + 64].x + ishl r11.xyz, r6.xyzx, icb[r0.w + 64].x + ishr r10.xyz, r10.xyzx, l(16) + ishr r11.xyz, r11.xyzx, l(16) + movc r8.xyz, r8.xyzx, r2.zzzz, r10.xyzx + movc r9.xyz, r9.xyzx, r2.zzzz, r11.xyzx + movc r7.xyz, r7.xyzx, r5.xyzx, r8.xyzx + movc r1.xyw, r1.xyxw, r6.xyxz, r9.xyxz + else + ige r2.z, icb[r0.w + 64].x, l(16) + and r2.z, r2.z, l(1) + movc r8.xyz, r5.xyzx, l(0,0,0,0), l(1,1,1,0) + movc r9.xyz, r6.xyzx, l(0,0,0,0), l(1,1,1,0) + or r8.xyz, r2.zzzz, r8.xyzx + or r9.xyz, r2.zzzz, r9.xyzx + ige r10.xyz, r5.xyzx, l(0, 0, 0, 0) + ige r11.xyz, r6.xyzx, l(0, 0, 0, 0) + ieq r12.xyz, r5.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ieq r13.xyz, r6.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + iadd r2.z, l(-1), icb[r0.w + 64].x + ishl r2.w, l(1), r2.z + iadd r4.w, r2.w, l(-1) + ishl r14.xyz, r5.xyzx, r2.z + ishl r15.xyz, r6.xyzx, r2.z + ishr r14.xyz, r14.xyzx, l(15) + ishr r15.xyz, r15.xyzx, l(15) + movc r12.xyz, r12.xyzx, r4.wwww, r14.xyzx + movc r13.xyz, r13.xyzx, r4.wwww, r15.xyzx + ineg r14.xyz, r5.xyzx + ineg r15.xyz, r6.xyzx + ieq r16.xyz, r14.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ieq r17.xyz, r15.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + iadd r2.w, -r2.w, l(1) + ishl r14.xyz, r14.xyzx, r2.z + ishl r15.xyz, r15.xyzx, r2.z + ishr r14.xyz, r14.xyzx, l(15) + ishr r15.xyz, r15.xyzx, l(15) + ineg r14.xyz, r14.xyzx + ineg r15.xyz, r15.xyzx + movc r14.xyz, r16.xyzx, r2.wwww, r14.xyzx + movc r15.xyz, r17.xyzx, r2.wwww, r15.xyzx + movc r10.xyz, r10.xyzx, r12.xyzx, r14.xyzx + movc r11.xyz, r11.xyzx, r13.xyzx, r15.xyzx + movc r7.xyz, r8.xyzx, r5.xyzx, r10.xyzx + movc r1.xyw, r9.xyxz, r6.xyxz, r11.xyxz + endif + iadd r5.xyz, -r4.xyzx, r7.xyzx + iadd r4.xyz, -r4.xyzx, r1.xywx + mov r5.w, r4.x + mov r7.w, r1.x + movc r5.xyzw, icb[r0.w + 32].xxxx, r5.xyzw, r7.xyzw + movc r1.xy, icb[r0.w + 32].xxxx, r4.yzyy, r1.ywyy + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r5.xyzw + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(68), r1.xyxx + endif +endif +sync_g_t +if_nz r1.z + iadd r1.x, vThreadIDInGroupFlattened.x, l(2) + ld_structured r4.xyz, r1.x, l(52), g0.xyzx + ld_structured r1.xyz, r1.x, l(64), g0.yzxx + if_z r0.z + ult r1.w, l(10), r2.x + if_nz r1.w + ishl r5.x, l(1), icb[r0.w + 64].x + ishl r5.y, l(1), icb[r0.w + 64].y + ishl r5.z, l(1), icb[r0.w + 64].z + ishl r5.w, l(1), icb[r0.w + 64].w + ige r6.xyz, r1.zxyz, l(0, 0, 0, 0) + iadd r7.xyz, l(-1, -1, -1, 0), icb[r0.w + 64].yzwy + ishl r8.x, l(1), r7.x + ishl r8.y, l(1), r7.y + ishl r8.z, l(1), r7.z + ige r7.xyz, r1.zxyz, r8.xyzx + iadd r9.xyz, r8.xyzx, l(-1, -1, -1, 0) + movc r7.xyz, r7.xyzx, r9.xyzx, r1.zxyz + ineg r9.xyz, r1.zxyz + ilt r9.xyz, r8.xyzx, r9.xyzx + iadd r5.xyzw, r5.xyzw, l(-1, -1, -1, -1) + and r5.yzw, r1.zzxy, r5.yyzw + movc r5.yzw, r9.xxyz, r8.xxyz, r5.yyzw + movc r5.yzw, r6.xxyz, r7.xxyz, r5.yyzw + mov r4.w, r1.z + and r6.xyzw, r4.xyzw, r5.xxxx + and r2.zw, r1.xxxy, r5.xxxx + mov r7.xyz, r6.xyzx + mov r7.w, r5.y + movc r4.xyzw, icb[r0.w + 32].xxxx, r7.xyzw, r6.xyzw + movc r1.xy, icb[r0.w + 32].xxxx, r5.zwzz, r2.zwzz + else + if_nz icb[r0.w + 32].x + ishl r5.x, l(1), icb[r0.w + 64].x + ishl r5.y, l(1), icb[r0.w + 64].y + ishl r5.z, l(1), icb[r0.w + 64].z + ishl r5.w, l(1), icb[r0.w + 64].w + iadd r5.xyzw, r5.xyzw, l(-1, -1, -1, -1) + and r4.xyz, r4.xyzx, r5.xxxx + ige r6.xyz, r1.zxyz, l(0, 0, 0, 0) + iadd r7.xyz, l(-1, -1, -1, 0), icb[r0.w + 64].yzwy + ishl r8.x, l(1), r7.x + ishl r8.y, l(1), r7.y + ishl r8.z, l(1), r7.z + ige r7.xyz, r1.zxyz, r8.xyzx + iadd r9.xyz, r8.xyzx, l(-1, -1, -1, 0) + movc r7.xyz, r7.xyzx, r9.xyzx, r1.zxyz + ineg r9.xyz, r1.zxyz + ilt r9.xyz, r8.xyzx, r9.xyzx + and r5.xyz, r1.zxyz, r5.yzwy + movc r5.xyz, r9.xyzx, r8.xyzx, r5.xyzx + movc r1.xyz, r6.yzxy, r7.yzxy, r5.yzxy + mov r4.w, r1.z + else + ishl r1.w, l(1), icb[r0.w + 64].x + iadd r1.w, r1.w, l(-1) + mov r4.w, r1.z + and r4.xyzw, r1.wwww, r4.xyzw + and r1.xy, r1.wwww, r1.xyxx + endif + endif + else + uge r1.w, l(10), r2.x + if_nz r1.w + if_nz icb[r0.w + 32].x + ige r5.xyz, r4.xyzx, l(0, 0, 0, 0) + iadd r6.xyz, l(-1, -1, -1, 0), icb[r0.w + 64].yzwy + ishl r7.x, l(1), r6.x + ishl r7.y, l(1), r6.y + ishl r7.z, l(1), r6.z + ige r6.xyz, r4.xyzx, r7.xyzx + iadd r8.xyz, r7.xyzx, l(-1, -1, -1, 0) + movc r6.xyz, r6.xyzx, r8.xyzx, r4.xyzx + ineg r9.xyz, r4.xyzx + ilt r9.xyz, r7.xyzx, r9.xyzx + ishl r10.x, l(1), icb[r0.w + 64].y + ishl r10.y, l(1), icb[r0.w + 64].z + ishl r10.z, l(1), icb[r0.w + 64].w + iadd r10.xyz, r10.xyzx, l(-1, -1, -1, 0) + and r11.xyz, r4.xyzx, r10.xyzx + movc r9.xyz, r9.xyzx, r7.xyzx, r11.xyzx + movc r4.xyz, r5.xyzx, r6.xyzx, r9.xyzx + ige r5.xyz, r1.zxyz, l(0, 0, 0, 0) + ige r6.xyz, r1.zxyz, r7.xyzx + movc r6.xyz, r6.xyzx, r8.xyzx, r1.zxyz + ineg r8.xyz, r1.zxyz + ilt r8.xyz, r7.xyzx, r8.xyzx + and r9.xyz, r1.zxyz, r10.xyzx + movc r7.xyz, r8.xyzx, r7.xyzx, r9.xyzx + movc r1.xyz, r5.yzxy, r6.yzxy, r7.yzxy + mov r4.w, r1.z + else + ishl r0.w, l(1), icb[r0.w + 64].x + iadd r0.w, r0.w, l(-1) + mov r4.w, r1.z + and r4.xyzw, r0.wwww, r4.xyzw + and r1.xy, r0.wwww, r1.xyxx + endif + else + mov r4.w, r1.z + endif + endif + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r4.xyzw + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(68), r1.xyxx +endif +sync_g_t +if_z r0.z + ld_structured r1.xyzw, r0.y, l(52), g0.xyzw + ld_structured r4.xy, r0.y, l(68), g0.xyxx + ult r0.z, l(10), r2.x + if_nz r0.z + and r3.w, r3.x, l(-2) + ieq r0.z, r2.x, l(11) + if_nz r0.z + ishl r5.x, r1.x, l(5) + ishl r5.y, r1.y, l(15) + ishl r5.z, r1.z, l(25) + ishl r5.w, r1.w, l(3) + and r5.xyzw, r5.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.z, r5.x, l(3) + ishr r0.w, r1.x, l(1) + ishr r2.z, r1.x, l(2) + ishr r2.w, r1.x, l(3) + ishr r4.z, r1.x, l(4) + ishl r6.x, r0.w, l(6) + ishl r6.y, r2.z, l(7) + ishl r6.z, r2.w, l(8) + ishl r6.w, r4.z, l(9) + and r6.xyzw, r6.xyzw, l(64, 128, 256, 512) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.x, l(5) + ishr r2.z, r1.x, l(6) + ishr r2.w, r1.x, l(7) + ishr r4.z, r1.x, l(8) + ishl r6.x, r0.w, l(10) + ishl r6.y, r2.z, l(11) + ishl r6.z, r2.w, l(12) + ishl r6.w, r4.z, l(13) + and r6.xyzw, r6.xyzw, l(1024, 2048, 4096, 8192) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.x, l(9) + ishr r2.z, r1.y, l(1) + ishr r2.w, r1.y, l(2) + ishr r4.z, r1.y, l(3) + ishl r6.x, r0.w, l(14) + ishl r6.y, r2.z, l(16) + ishl r6.z, r2.w, l(17) + ishl r6.w, r4.z, l(18) + and r6.xyzw, r6.xyzw, l(0x00004000, 0x00010000, 0x00020000, 0x00040000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.y, l(4) + ishr r2.z, r1.y, l(5) + ishr r2.w, r1.y, l(6) + ishr r4.z, r1.y, l(7) + ishl r6.x, r0.w, l(19) + ishl r6.y, r2.z, l(20) + ishl r6.z, r2.w, l(21) + ishl r6.w, r4.z, l(22) + and r6.xyzw, r6.xyzw, l(0x00080000, 0x00100000, 0x00200000, 0x00400000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.y, l(8) + ishr r2.z, r1.y, l(9) + ishr r2.w, r1.z, l(1) + ishr r4.z, r1.z, l(2) + ishl r6.x, r0.w, l(23) + ishl r6.y, r2.z, l(24) + ishl r6.z, r2.w, l(26) + ishl r6.w, r4.z, l(27) + and r6.xyzw, r6.xyzw, l(0x00800000, 0x01000000, 0x04000000, 0x08000000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.z, l(3) + ishr r2.z, r1.z, l(4) + ishr r2.w, r1.z, l(5) + ishr r4.z, r1.z, l(6) + ishl r5.x, r0.w, l(28) + ishl r5.y, r2.z, l(29) + ishl r5.z, r2.w, l(30) + ishl r0.w, r4.z, l(31) + and r5.xyz, r5.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r3.x, r0.w, r0.z + ishr r0.z, r1.z, l(7) + ishr r0.w, r1.z, l(8) + ishr r2.z, r1.z, l(9) + ishr r2.w, r1.w, l(1) + and r0.z, r0.z, l(1) + ishl r5.x, r0.w, l(1) + ishl r5.y, r2.z, l(2) + ishl r5.z, r2.w, l(4) + and r5.xyz, r5.xyzx, l(2, 4, 16, 0) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.w, r0.z + iadd r0.z, r5.z, r0.z + ishr r0.w, r1.w, l(2) + ishr r2.z, r1.w, l(3) + ishr r2.w, r1.w, l(4) + ishr r4.z, r1.w, l(5) + ishl r5.x, r0.w, l(5) + ishl r5.y, r2.z, l(6) + ishl r5.z, r2.w, l(7) + ishl r5.w, r4.z, l(8) + and r5.xyzw, r5.xyzw, l(32, 64, 128, 256) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r1.w, l(6) + ishr r2.z, r1.w, l(7) + ishr r2.w, r1.w, l(8) + ishr r4.z, r1.w, l(9) + ishl r5.x, r0.w, l(9) + ishl r5.y, r2.z, l(10) + ishl r5.z, r2.w, l(11) + ishl r5.w, r4.z, l(12) + and r5.xyzw, r5.xyzw, l(512, 1024, 2048, 4096) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishl r5.x, r4.x, l(13) + ishl r5.y, r4.y, l(23) + and r2.zw, r5.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.z, r0.z, r2.z + ishr r0.w, r4.x, l(1) + ishr r2.z, r4.x, l(2) + ishr r4.z, r4.x, l(3) + ishr r4.w, r4.x, l(4) + ishl r5.x, r0.w, l(14) + ishl r5.y, r2.z, l(15) + ishl r5.z, r4.z, l(16) + ishl r5.w, r4.w, l(17) + and r5.xyzw, r5.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r4.x, l(5) + ishr r2.z, r4.x, l(6) + ishr r4.z, r4.x, l(7) + ishr r4.w, r4.x, l(8) + ishl r5.x, r0.w, l(18) + ishl r5.y, r2.z, l(19) + ishl r5.z, r4.z, l(20) + ishl r5.w, r4.w, l(21) + and r5.xyzw, r5.xyzw, l(0x00040000, 0x00080000, 0x00100000, 0x00200000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r4.x, l(9) + ishr r2.z, r4.y, l(1) + ishr r4.z, r4.y, l(2) + ishr r4.w, r4.y, l(3) + ishl r5.x, r0.w, l(22) + ishl r5.y, r2.z, l(24) + ishl r5.z, r4.z, l(25) + ishl r5.w, r4.w, l(26) + and r5.xyzw, r5.xyzw, l(0x00400000, 0x01000000, 0x02000000, 0x04000000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r2.w, r0.z + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r4.y, l(4) + ishr r2.z, r4.y, l(5) + ishr r2.w, r4.y, l(6) + ishr r4.z, r4.y, l(7) + ishl r5.x, r0.w, l(27) + ishl r5.y, r2.z, l(28) + ishl r5.z, r2.w, l(29) + ishl r5.w, r4.z, l(30) + and r5.xyzw, r5.xyzw, l(0x08000000, 0x10000000, 0x20000000, 0x40000000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r4.y, l(8) + ishr r2.z, r4.y, l(9) + ishl r0.w, r0.w, l(31) + iadd r3.z, r0.w, r0.z + and r0.z, r2.z, l(1) + iadd r3.w, r0.z, r3.w + else + ieq r0.z, r2.x, l(12) + if_nz r0.z + ishl r5.x, r1.x, l(5) + ishl r5.y, r1.y, l(15) + ishl r5.z, r1.z, l(25) + ishl r5.w, r1.w, l(3) + and r5.xyzw, r5.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.z, r5.x, l(7) + ishr r0.w, r1.x, l(1) + ishr r2.z, r1.x, l(2) + ishr r2.w, r1.x, l(3) + ishr r4.z, r1.x, l(4) + ishl r6.x, r0.w, l(6) + ishl r6.y, r2.z, l(7) + ishl r6.z, r2.w, l(8) + ishl r6.w, r4.z, l(9) + and r6.xyzw, r6.xyzw, l(64, 128, 256, 512) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.x, l(5) + ishr r2.z, r1.x, l(6) + ishr r2.w, r1.x, l(7) + ishr r4.z, r1.x, l(8) + ishl r6.x, r0.w, l(10) + ishl r6.y, r2.z, l(11) + ishl r6.z, r2.w, l(12) + ishl r6.w, r4.z, l(13) + and r6.xyzw, r6.xyzw, l(1024, 2048, 4096, 8192) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.x, l(9) + ishr r2.z, r1.y, l(1) + ishr r2.w, r1.y, l(2) + ishr r4.z, r1.y, l(3) + ishl r6.x, r0.w, l(14) + ishl r6.y, r2.z, l(16) + ishl r6.z, r2.w, l(17) + ishl r6.w, r4.z, l(18) + and r6.xyzw, r6.xyzw, l(0x00004000, 0x00010000, 0x00020000, 0x00040000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.y, l(4) + ishr r2.z, r1.y, l(5) + ishr r2.w, r1.y, l(6) + ishr r4.z, r1.y, l(7) + ishl r6.x, r0.w, l(19) + ishl r6.y, r2.z, l(20) + ishl r6.z, r2.w, l(21) + ishl r6.w, r4.z, l(22) + and r6.xyzw, r6.xyzw, l(0x00080000, 0x00100000, 0x00200000, 0x00400000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.y, l(8) + ishr r2.z, r1.y, l(9) + ishr r2.w, r1.z, l(1) + ishr r4.z, r1.z, l(2) + ishl r6.x, r0.w, l(23) + ishl r6.y, r2.z, l(24) + ishl r6.z, r2.w, l(26) + ishl r6.w, r4.z, l(27) + and r6.xyzw, r6.xyzw, l(0x00800000, 0x01000000, 0x04000000, 0x08000000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.z, l(3) + ishr r2.z, r1.z, l(4) + ishr r2.w, r1.z, l(5) + ishr r4.z, r1.z, l(6) + ishl r5.x, r0.w, l(28) + ishl r5.y, r2.z, l(29) + ishl r5.z, r2.w, l(30) + ishl r0.w, r4.z, l(31) + and r5.xyz, r5.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r3.x, r0.w, r0.z + ishr r0.z, r1.z, l(7) + ishr r0.w, r1.z, l(8) + ishr r2.z, r1.z, l(9) + ishr r2.w, r1.w, l(1) + and r0.z, r0.z, l(1) + ishl r5.x, r0.w, l(1) + ishl r5.y, r2.z, l(2) + ishl r5.z, r2.w, l(4) + and r5.xyz, r5.xyzx, l(2, 4, 16, 0) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.w, r0.z + iadd r0.z, r5.z, r0.z + ishr r0.w, r1.w, l(2) + ishr r2.z, r1.w, l(3) + ishr r2.w, r1.w, l(4) + ishr r4.z, r1.w, l(5) + ishl r5.x, r0.w, l(5) + ishl r5.y, r2.z, l(6) + ishl r5.z, r2.w, l(7) + ishl r5.w, r4.z, l(8) + and r5.xyzw, r5.xyzw, l(32, 64, 128, 256) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r1.w, l(6) + ishr r2.z, r1.w, l(7) + ishr r2.w, r1.w, l(8) + ishr r4.z, r1.x, l(10) + ishl r5.x, r0.w, l(9) + ishl r5.y, r2.z, l(10) + ishl r5.z, r2.w, l(11) + ishl r5.w, r4.z, l(12) + and r5.xyzw, r5.xyzw, l(512, 1024, 2048, 4096) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishl r5.x, r4.x, l(13) + ishl r5.y, r4.y, l(23) + and r2.zw, r5.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.z, r0.z, r2.z + ishr r0.w, r4.x, l(1) + ishr r2.z, r4.x, l(2) + ishr r4.z, r4.x, l(3) + ishr r4.w, r4.x, l(4) + ishl r5.x, r0.w, l(14) + ishl r5.y, r2.z, l(15) + ishl r5.z, r4.z, l(16) + ishl r5.w, r4.w, l(17) + and r5.xyzw, r5.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r4.x, l(5) + ishr r2.z, r4.x, l(6) + ishr r4.z, r4.x, l(7) + ishr r4.w, r4.x, l(8) + ishl r5.x, r0.w, l(18) + ishl r5.y, r2.z, l(19) + ishl r5.z, r4.z, l(20) + ishl r5.w, r4.w, l(21) + and r5.xyzw, r5.xyzw, l(0x00040000, 0x00080000, 0x00100000, 0x00200000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r4.zw, r1.yyyz, l(10) + ishl r0.w, r4.z, l(22) + and r0.w, r0.w, l(0x00400000) + iadd r0.z, r0.w, r0.z + iadd r0.z, r2.w, r0.z + ishr r0.w, r4.y, l(1) + ishr r2.z, r4.y, l(2) + ishr r2.w, r4.y, l(3) + ishr r4.z, r4.y, l(4) + ishl r5.x, r0.w, l(24) + ishl r5.y, r2.z, l(25) + ishl r5.z, r2.w, l(26) + ishl r5.w, r4.z, l(27) + and r5.xyzw, r5.xyzw, l(0x01000000, 0x02000000, 0x04000000, 0x08000000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r4.y, l(5) + ishr r2.z, r4.y, l(6) + ishr r2.w, r4.y, l(7) + ishr r4.z, r4.y, l(8) + ishl r5.x, r0.w, l(28) + ishl r5.y, r2.z, l(29) + ishl r5.z, r2.w, l(30) + ishl r0.w, r4.z, l(31) + and r5.xyz, r5.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r3.z, r0.w, r0.z + and r0.z, r4.w, l(1) + iadd r3.w, r0.z, r3.w + else + ieq r0.z, r2.x, l(13) + if_nz r0.z + ishl r5.x, r1.x, l(5) + ishl r5.y, r1.y, l(15) + ishl r5.z, r1.z, l(25) + ishl r5.w, r1.w, l(3) + and r5.xyzw, r5.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.z, r5.x, l(11) + ishr r0.w, r1.x, l(1) + ishr r2.z, r1.x, l(2) + ishr r2.w, r1.x, l(3) + ishr r4.z, r1.x, l(4) + ishl r6.x, r0.w, l(6) + ishl r6.y, r2.z, l(7) + ishl r6.z, r2.w, l(8) + ishl r6.w, r4.z, l(9) + and r6.xyzw, r6.xyzw, l(64, 128, 256, 512) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.x, l(5) + ishr r2.z, r1.x, l(6) + ishr r2.w, r1.x, l(7) + ishr r4.z, r1.x, l(8) + ishl r6.x, r0.w, l(10) + ishl r6.y, r2.z, l(11) + ishl r6.z, r2.w, l(12) + ishl r6.w, r4.z, l(13) + and r6.xyzw, r6.xyzw, l(1024, 2048, 4096, 8192) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.x, l(9) + ishr r2.z, r1.y, l(1) + ishr r2.w, r1.y, l(2) + ishr r4.z, r1.y, l(3) + ishl r6.x, r0.w, l(14) + ishl r6.y, r2.z, l(16) + ishl r6.z, r2.w, l(17) + ishl r6.w, r4.z, l(18) + and r6.xyzw, r6.xyzw, l(0x00004000, 0x00010000, 0x00020000, 0x00040000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.y, l(4) + ishr r2.z, r1.y, l(5) + ishr r2.w, r1.y, l(6) + ishr r4.z, r1.y, l(7) + ishl r6.x, r0.w, l(19) + ishl r6.y, r2.z, l(20) + ishl r6.z, r2.w, l(21) + ishl r6.w, r4.z, l(22) + and r6.xyzw, r6.xyzw, l(0x00080000, 0x00100000, 0x00200000, 0x00400000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.y, l(8) + ishr r2.z, r1.y, l(9) + ishr r2.w, r1.z, l(1) + ishr r4.z, r1.z, l(2) + ishl r6.x, r0.w, l(23) + ishl r6.y, r2.z, l(24) + ishl r6.z, r2.w, l(26) + ishl r6.w, r4.z, l(27) + and r6.xyzw, r6.xyzw, l(0x00800000, 0x01000000, 0x04000000, 0x08000000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.z, l(3) + ishr r2.z, r1.z, l(4) + ishr r2.w, r1.z, l(5) + ishr r4.z, r1.z, l(6) + ishl r5.x, r0.w, l(28) + ishl r5.y, r2.z, l(29) + ishl r5.z, r2.w, l(30) + ishl r0.w, r4.z, l(31) + and r5.xyz, r5.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r3.x, r0.w, r0.z + ishr r0.z, r1.z, l(7) + ishr r0.w, r1.z, l(8) + ishr r2.z, r1.z, l(9) + ishr r2.w, r1.w, l(1) + and r0.z, r0.z, l(1) + ishl r5.x, r0.w, l(1) + ishl r5.y, r2.z, l(2) + ishl r5.z, r2.w, l(4) + and r5.xyz, r5.xyzx, l(2, 4, 16, 0) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.w, r0.z + iadd r0.z, r5.z, r0.z + ishr r0.w, r1.w, l(2) + ishr r2.z, r1.w, l(3) + ishr r2.w, r1.w, l(4) + ishr r4.z, r1.w, l(5) + ishl r5.x, r0.w, l(5) + ishl r5.y, r2.z, l(6) + ishl r5.z, r2.w, l(7) + ishl r5.w, r4.z, l(8) + and r5.xyzw, r5.xyzw, l(32, 64, 128, 256) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r1.w, l(6) + ishr r2.z, r1.w, l(7) + ishr r2.w, r1.x, l(10) + ishr r4.z, r1.y, l(11) + ishl r5.x, r0.w, l(9) + ishl r5.y, r2.z, l(10) + ishl r5.z, r2.w, l(12) + ishl r5.w, r4.z, l(21) + and r5.xyzw, r5.xyzw, l(512, 1024, 4096, 0x00200000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + and r0.w, r1.x, l(2048) + iadd r0.z, r0.w, r0.z + iadd r0.z, r5.z, r0.z + ishl r5.x, r4.x, l(13) + ishl r5.y, r4.y, l(23) + and r2.zw, r5.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.z, r0.z, r2.z + ishr r0.w, r4.x, l(1) + ishr r2.z, r4.x, l(2) + ishr r4.z, r4.x, l(3) + ishr r4.w, r4.x, l(4) + ishl r6.x, r0.w, l(14) + ishl r6.y, r2.z, l(15) + ishl r6.z, r4.z, l(16) + ishl r6.w, r4.w, l(17) + and r6.xyzw, r6.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r4.x, l(5) + ishr r2.z, r4.x, l(6) + ishr r4.z, r4.x, l(7) + ishr r4.w, r4.y, l(1) + ishl r6.x, r0.w, l(18) + ishl r6.y, r2.z, l(19) + ishl r6.z, r4.z, l(20) + ishl r6.w, r4.w, l(24) + and r6.xyzw, r6.xyzw, l(0x00040000, 0x00080000, 0x00100000, 0x01000000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r4.zw, r1.yyyz, l(10) + ishr r0.w, r1.z, l(11) + ishl r2.z, r4.z, l(22) + ishl r0.w, r0.w, l(31) + and r2.z, r2.z, l(0x00400000) + iadd r0.z, r0.z, r2.z + iadd r0.z, r2.w, r0.z + iadd r0.z, r6.w, r0.z + ishr r2.z, r4.y, l(2) + ishr r2.w, r4.y, l(3) + ishr r4.z, r4.y, l(4) + ishr r5.x, r4.y, l(5) + ishl r6.x, r2.z, l(25) + ishl r6.y, r2.w, l(26) + ishl r6.z, r4.z, l(27) + ishl r6.w, r5.x, l(28) + and r5.xyzw, r6.xyzw, l(0x02000000, 0x04000000, 0x08000000, 0x10000000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r2.z, r4.y, l(6) + ishr r2.w, r4.y, l(7) + ishl r5.x, r2.z, l(29) + ishl r5.y, r2.w, l(30) + and r2.zw, r5.xxxy, l(0, 0, 0x20000000, 0x40000000) + iadd r0.z, r0.z, r2.z + iadd r0.z, r2.w, r0.z + iadd r3.z, r0.w, r0.z + and r0.z, r4.w, l(1) + iadd r3.w, r0.z, r3.w + else + ieq r0.z, r2.x, l(14) + if_nz r0.z + ishl r5.x, r1.x, l(5) + ishl r5.y, r1.y, l(15) + ishl r5.z, r1.z, l(25) + ishl r5.w, r1.w, l(3) + and r5.xyzw, r5.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.z, r5.x, l(15) + ishr r0.w, r1.x, l(1) + ishr r2.z, r1.x, l(2) + ishr r2.w, r1.x, l(3) + ishr r4.z, r1.x, l(4) + ishl r6.x, r0.w, l(6) + ishl r6.y, r2.z, l(7) + ishl r6.z, r2.w, l(8) + ishl r6.w, r4.z, l(9) + and r6.xyzw, r6.xyzw, l(64, 128, 256, 512) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.x, l(5) + ishr r2.z, r1.x, l(6) + ishr r2.w, r1.x, l(7) + ishr r4.z, r1.x, l(8) + ishl r6.x, r0.w, l(10) + ishl r6.y, r2.z, l(11) + ishl r6.z, r2.w, l(12) + ishl r6.w, r4.z, l(13) + and r6.xyzw, r6.xyzw, l(1024, 2048, 4096, 8192) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.x, l(9) + ishr r2.z, r1.y, l(1) + ishr r2.w, r1.y, l(2) + ishr r4.z, r1.y, l(3) + ishl r6.x, r0.w, l(14) + ishl r6.y, r2.z, l(16) + ishl r6.z, r2.w, l(17) + ishl r6.w, r4.z, l(18) + and r6.xyzw, r6.xyzw, l(0x00004000, 0x00010000, 0x00020000, 0x00040000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.y, l(4) + ishr r2.z, r1.y, l(5) + ishr r2.w, r1.y, l(6) + ishr r4.z, r1.y, l(7) + ishl r6.x, r0.w, l(19) + ishl r6.y, r2.z, l(20) + ishl r6.z, r2.w, l(21) + ishl r6.w, r4.z, l(22) + and r6.xyzw, r6.xyzw, l(0x00080000, 0x00100000, 0x00200000, 0x00400000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.y, l(8) + ishr r2.z, r1.y, l(9) + ishr r2.w, r1.z, l(1) + ishr r4.z, r1.z, l(2) + ishl r6.x, r0.w, l(23) + ishl r6.y, r2.z, l(24) + ishl r6.z, r2.w, l(26) + ishl r6.w, r4.z, l(27) + and r6.xyzw, r6.xyzw, l(0x00800000, 0x01000000, 0x04000000, 0x08000000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r1.z, l(3) + ishr r2.z, r1.z, l(4) + ishr r2.w, r1.z, l(5) + ishr r4.z, r1.z, l(6) + ishl r5.x, r0.w, l(28) + ishl r5.y, r2.z, l(29) + ishl r5.z, r2.w, l(30) + ishl r0.w, r4.z, l(31) + and r5.xyz, r5.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r3.x, r0.w, r0.z + ishr r0.z, r1.z, l(7) + ishr r0.w, r1.z, l(8) + ishr r2.z, r1.z, l(9) + ishr r2.w, r1.w, l(1) + and r0.z, r0.z, l(1) + ishl r5.x, r0.w, l(1) + ishl r5.y, r2.z, l(2) + ishl r5.z, r2.w, l(4) + and r5.xyz, r5.xyzx, l(2, 4, 16, 0) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.w, r0.z + iadd r0.z, r5.z, r0.z + ishr r0.w, r1.w, l(2) + ishr r2.z, r1.w, l(3) + ishr r2.w, r1.x, l(15) + ishr r4.z, r1.x, l(14) + ishl r5.x, r0.w, l(5) + ishl r5.y, r2.z, l(6) + ishl r5.z, r2.w, l(7) + ishl r5.w, r4.z, l(8) + and r5.xyzw, r5.xyzw, l(32, 64, 128, 256) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r1.x, l(13) + ishr r2.z, r1.x, l(12) + ishr r2.w, r1.x, l(10) + ishr r4.z, r1.y, l(15) + ishl r5.x, r0.w, l(9) + ishl r5.y, r2.z, l(10) + ishl r5.z, r2.w, l(12) + ishl r5.w, r4.z, l(17) + and r5.xyzw, r5.xyzw, l(512, 1024, 4096, 0x00020000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + and r0.w, r1.x, l(2048) + iadd r0.z, r0.w, r0.z + iadd r0.z, r5.z, r0.z + ishl r5.x, r4.x, l(13) + ishl r5.y, r4.y, l(23) + and r2.zw, r5.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.z, r0.z, r2.z + ishr r4.zw, r4.xxxy, l(1) + ishr r0.w, r4.x, l(2) + ishr r2.z, r4.x, l(3) + ishl r6.x, r4.z, l(14) + ishl r6.y, r0.w, l(15) + ishl r6.z, r2.z, l(16) + ishl r6.w, r4.w, l(24) + and r6.xyzw, r6.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x01000000) + iadd r0.z, r0.z, r6.x + iadd r0.z, r6.y, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r1.y, l(14) + ishr r2.z, r1.y, l(13) + ishr r4.z, r1.y, l(12) + ishr r4.w, r1.y, l(11) + ishl r5.x, r0.w, l(18) + ishl r5.y, r2.z, l(19) + ishl r5.z, r4.z, l(20) + ishl r5.w, r4.w, l(21) + and r5.xyzw, r5.xyzw, l(0x00040000, 0x00080000, 0x00100000, 0x00200000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r1.y, l(10) + ishr r2.z, r1.z, l(15) + ishr r4.z, r1.z, l(14) + ishr r4.w, r1.z, l(13) + ishl r5.x, r0.w, l(22) + ishl r5.y, r2.z, l(27) + ishl r5.z, r4.z, l(28) + ishl r5.w, r4.w, l(29) + and r5.xyzw, r5.xyzw, l(0x00400000, 0x08000000, 0x10000000, 0x20000000) + iadd r0.z, r0.z, r5.x + iadd r0.z, r2.w, r0.z + iadd r0.z, r6.w, r0.z + ishr r0.w, r4.y, l(2) + ishr r2.z, r4.y, l(3) + ishl r6.x, r0.w, l(25) + ishl r6.y, r2.z, l(26) + and r2.zw, r6.xxxy, l(0, 0, 0x02000000, 0x04000000) + iadd r0.z, r0.z, r2.z + iadd r0.z, r2.w, r0.z + iadd r0.z, r5.y, r0.z + iadd r0.z, r5.z, r0.z + iadd r0.z, r5.w, r0.z + ishr r0.w, r1.z, l(12) + ishr r2.z, r1.z, l(11) + ishr r2.w, r1.z, l(10) + ishl r0.w, r0.w, l(30) + ishl r2.z, r2.z, l(31) + and r0.w, r0.w, l(0x40000000) + iadd r0.z, r0.w, r0.z + iadd r3.z, r2.z, r0.z + and r0.z, r2.w, l(1) + iadd r3.w, r0.z, r3.w + else + mov r3.xz, l(0,0,0,0) + endif + endif + endif + endif + else + iadd r0.y, r0.y, l(1) + ld_structured r5.xyzw, r0.y, l(52), g0.xyzw + ld_structured r6.xy, r0.y, l(68), g0.xyxx + and r3.w, r3.x, l(0xfffc0000) + ieq r0.y, r2.x, l(1) + if_nz r0.y + ishr r0.yz, r5.yyzy, l(4) + ishr r0.w, r5.y, l(1) + ishr r2.z, r5.y, l(2) + ishl r7.x, r0.y, l(2) + ishl r7.y, r0.z, l(3) + ishl r7.z, r0.w, l(10) + ishl r7.w, r2.z, l(11) + and r7.xyzw, r7.xyzw, l(4, 8, 1024, 2048) + iadd r0.y, r7.y, r7.x + and r0.z, r6.y, l(16) + iadd r0.y, r0.z, r0.y + ishl r8.x, r1.x, l(5) + ishl r8.y, r1.y, l(15) + ishl r8.z, r1.z, l(25) + ishl r8.w, r1.w, l(3) + and r8.xyzw, r8.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.y, r0.y, r8.x + ishr r0.z, r1.x, l(1) + ishr r0.w, r1.x, l(2) + ishr r2.z, r1.x, l(3) + ishr r2.w, r1.x, l(4) + ishl r9.x, r0.z, l(6) + ishl r9.y, r0.w, l(7) + ishl r9.z, r2.z, l(8) + ishl r9.w, r2.w, l(9) + and r9.xyzw, r9.xyzw, l(64, 128, 256, 512) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.z, r1.x, l(5) + ishr r0.w, r1.x, l(6) + ishr r2.z, r1.x, l(7) + ishr r2.w, r1.x, l(8) + ishl r9.x, r0.z, l(10) + ishl r9.y, r0.w, l(11) + ishl r9.z, r2.z, l(12) + ishl r9.w, r2.w, l(13) + and r9.xyzw, r9.xyzw, l(1024, 2048, 4096, 8192) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.z, r1.x, l(9) + ishr r0.w, r1.y, l(1) + ishr r2.z, r1.y, l(2) + ishr r2.w, r1.y, l(3) + ishl r9.x, r0.z, l(14) + ishl r9.y, r0.w, l(16) + ishl r9.z, r2.z, l(17) + ishl r9.w, r2.w, l(18) + and r9.xyzw, r9.xyzw, l(0x00004000, 0x00010000, 0x00020000, 0x00040000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.z, r1.y, l(4) + ishr r0.w, r1.y, l(5) + ishr r2.z, r1.y, l(6) + ishr r2.w, r1.y, l(7) + ishl r9.x, r0.z, l(19) + ishl r9.y, r0.w, l(20) + ishl r9.z, r2.z, l(21) + ishl r9.w, r2.w, l(22) + and r9.xyzw, r9.xyzw, l(0x00080000, 0x00100000, 0x00200000, 0x00400000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.z, r1.y, l(8) + ishr r0.w, r1.y, l(9) + ishr r2.z, r1.z, l(1) + ishr r2.w, r1.z, l(2) + ishl r9.x, r0.z, l(23) + ishl r9.y, r0.w, l(24) + ishl r9.z, r2.z, l(26) + ishl r9.w, r2.w, l(27) + and r9.xyzw, r9.xyzw, l(0x00800000, 0x01000000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.z, r1.z, l(3) + ishr r0.w, r1.z, l(4) + ishr r2.z, r1.z, l(5) + ishr r2.w, r1.z, l(6) + ishl r8.x, r0.z, l(28) + ishl r8.y, r0.w, l(29) + ishl r8.z, r2.z, l(30) + ishl r0.z, r2.w, l(31) + and r8.xyz, r8.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r3.x, r0.z, r0.y + ishr r0.y, r1.z, l(7) + ishr r0.z, r1.z, l(8) + ishr r0.w, r1.z, l(9) + ishr r2.z, r1.w, l(1) + and r0.y, r0.y, l(1) + ishl r8.x, r0.z, l(1) + ishl r8.y, r0.w, l(2) + ishl r8.z, r2.z, l(4) + and r8.xyz, r8.xyzx, l(2, 4, 16, 0) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.w, r0.y + iadd r0.y, r8.z, r0.y + ishr r0.z, r1.w, l(2) + ishr r0.w, r1.w, l(3) + ishr r2.z, r1.w, l(4) + ishl r8.x, r0.z, l(5) + ishl r8.y, r0.w, l(6) + ishl r8.z, r2.z, l(7) + and r8.xyz, r8.xyzx, l(32, 64, 128, 0) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + ishr r0.z, r6.x, l(4) + ishr r0.w, r6.x, l(1) + ishr r2.z, r6.x, l(2) + ishr r2.w, r6.x, l(3) + ishl r8.x, r0.z, l(8) + ishl r8.y, r0.w, l(20) + ishl r8.z, r2.z, l(21) + ishl r8.w, r2.w, l(22) + and r8.xyzw, r8.xyzw, l(256, 0x00100000, 0x00200000, 0x00400000) + iadd r0.y, r0.y, r8.x + ishl r9.x, r5.y, l(9) + ishl r9.y, r5.z, l(29) + ishl r9.z, r5.x, l(1) + ishl r9.w, r5.w, l(7) + and r9.xyzw, r9.xyzw, l(512, 0x20000000, 2, 128) + iadd r0.y, r0.y, r9.x + iadd r0.y, r7.z, r0.y + iadd r0.y, r7.w, r0.y + ishr r0.zw, r5.yyyz, l(3) + ishr r2.z, r5.z, l(1) + ishr r2.w, r5.z, l(2) + ishl r7.x, r0.z, l(12) + ishl r7.y, r2.z, l(30) + ishl r0.z, r2.w, l(31) + and r2.zw, r7.xxxy, l(0, 0, 4096, 0x40000000) + iadd r0.y, r0.y, r2.z + ishl r7.x, r4.x, l(13) + ishl r7.y, r4.y, l(23) + and r4.zw, r7.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.y, r0.y, r4.z + ishr r2.z, r4.x, l(1) + ishr r4.z, r4.x, l(2) + ishr r6.z, r4.x, l(3) + ishr r6.w, r4.x, l(4) + ishl r7.x, r2.z, l(14) + ishl r7.y, r4.z, l(15) + ishl r7.z, r6.z, l(16) + ishl r7.w, r6.w, l(17) + and r7.xyzw, r7.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r7.w, r0.y + ishl r7.x, r6.y, l(18) + ishl r7.y, r6.x, l(19) + and r6.zw, r7.xxxy, l(0, 0, 0x00040000, 0x00080000) + iadd r0.y, r0.y, r6.z + iadd r0.y, r6.w, r0.y + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + iadd r0.y, r4.w, r0.y + ishr r2.z, r4.y, l(1) + ishr r4.z, r4.y, l(2) + ishr r4.w, r4.y, l(3) + ishr r6.z, r4.y, l(4) + ishl r7.x, r2.z, l(24) + ishl r7.y, r4.z, l(25) + ishl r7.z, r4.w, l(26) + ishl r7.w, r6.z, l(27) + and r7.xyzw, r7.xyzw, l(0x01000000, 0x02000000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r7.w, r0.y + ishr r2.z, r6.y, l(1) + ishr r4.z, r6.y, l(2) + ishr r4.w, r6.y, l(3) + ishl r7.x, r2.z, l(28) + ishl r7.y, r4.z, l(6) + ishl r7.z, r4.w, l(12) + and r7.xyz, r7.xyzx, l(0x10000000, 64, 4096, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r2.w, r0.y + iadd r3.z, r0.z, r0.y + and r0.y, r0.w, l(1) + iadd r0.y, r0.y, r3.w + iadd r0.y, r9.z, r0.y + ishr r0.z, r5.x, l(1) + ishr r0.w, r5.x, l(2) + ishr r2.z, r5.x, l(3) + ishr r2.w, r5.x, l(4) + ishl r8.x, r0.z, l(2) + ishl r8.y, r0.w, l(3) + ishl r8.z, r2.z, l(4) + ishl r8.w, r2.w, l(5) + and r8.xyzw, r8.xyzw, l(4, 8, 16, 32) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.z, r5.w, l(1) + ishr r0.w, r5.w, l(2) + ishr r2.z, r5.w, l(3) + ishr r2.w, r5.w, l(4) + ishl r8.x, r0.z, l(8) + ishl r8.y, r0.w, l(9) + ishl r8.z, r2.z, l(10) + ishl r8.w, r2.w, l(11) + and r8.xyzw, r8.xyzw, l(256, 512, 1024, 2048) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + iadd r0.y, r7.z, r0.y + ishl r0.z, r2.y, l(13) + and r0.z, r0.z, l(8192) + iadd r0.y, r0.z, r0.y + ushr r0.z, r2.y, l(1) + ushr r0.w, r2.y, l(2) + ushr r2.z, r2.y, l(3) + ushr r2.w, r2.y, l(4) + ishl r7.x, r0.z, l(14) + ishl r7.y, r0.w, l(15) + ishl r7.z, r2.z, l(16) + ishl r7.w, r2.w, l(17) + and r7.xyzw, r7.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.w, r7.w, r0.y + else + ieq r0.y, r2.x, l(2) + if_nz r0.y + ishr r0.yz, r5.yyzy, l(5) + ishr r2.zw, r5.zzzy, l(4) + ishl r7.x, r0.y, l(2) + ishl r7.y, r2.z, l(14) + ishl r7.z, r0.z, l(22) + ishl r7.w, r2.w, l(24) + and r7.xyzw, r7.xyzw, l(4, 0x00004000, 0x00400000, 0x01000000) + iadd r0.y, r7.x, l(1) + ishr r0.z, r6.x, l(4) + ishr r0.w, r6.x, l(5) + ishr r2.z, r6.y, l(1) + ishr r2.w, r6.y, l(2) + ishl r8.x, r0.z, l(3) + ishl r8.y, r0.w, l(4) + ishl r8.z, r2.z, l(13) + ishl r8.w, r2.w, l(23) + and r8.xyzw, r8.xyzw, l(8, 16, 8192, 0x00800000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + ishl r9.x, r1.x, l(5) + ishl r9.y, r1.y, l(15) + ishl r9.z, r1.z, l(25) + ishl r9.w, r1.w, l(3) + and r9.xyzw, r9.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.y, r0.y, r9.x + ishr r0.z, r1.x, l(1) + ishr r0.w, r1.x, l(2) + ishr r2.z, r1.x, l(3) + ishr r2.w, r1.x, l(4) + ishl r10.x, r0.z, l(6) + ishl r10.y, r0.w, l(7) + ishl r10.z, r2.z, l(8) + ishl r10.w, r2.w, l(9) + and r10.xyzw, r10.xyzw, l(64, 128, 256, 512) + iadd r0.y, r0.y, r10.x + iadd r0.y, r10.y, r0.y + iadd r0.y, r10.z, r0.y + iadd r0.y, r10.w, r0.y + ishr r0.z, r1.x, l(5) + ishr r0.w, r1.x, l(6) + ishr r2.z, r1.y, l(1) + ishr r2.w, r1.y, l(2) + ishl r10.x, r0.z, l(10) + ishl r10.y, r0.w, l(11) + ishl r10.z, r2.z, l(16) + ishl r10.w, r2.w, l(17) + and r10.xyzw, r10.xyzw, l(1024, 2048, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r10.x + iadd r0.y, r10.y, r0.y + ishl r8.x, r6.y, l(12) + ishl r8.y, r6.x, l(19) + and r0.zw, r8.xxxy, l(0, 0, 4096, 0x00080000) + iadd r0.y, r0.z, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r9.y, r0.y + iadd r0.y, r10.z, r0.y + iadd r0.y, r10.w, r0.y + ishr r0.z, r1.y, l(3) + ishr r2.z, r1.y, l(4) + ishr r2.w, r1.y, l(5) + ishr r4.z, r1.y, l(6) + ishl r10.x, r0.z, l(18) + ishl r10.y, r2.z, l(19) + ishl r10.z, r2.w, l(20) + ishl r10.w, r4.z, l(21) + and r10.xyzw, r10.xyzw, l(0x00040000, 0x00080000, 0x00100000, 0x00200000) + iadd r0.y, r0.y, r10.x + iadd r0.y, r10.y, r0.y + iadd r0.y, r10.z, r0.y + iadd r0.y, r10.w, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r8.w, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r9.z, r0.y + ishr r0.z, r1.z, l(1) + ishr r2.z, r1.z, l(2) + ishr r2.w, r1.z, l(3) + ishr r4.z, r1.z, l(4) + ishl r7.x, r0.z, l(26) + ishl r7.y, r2.z, l(27) + ishl r7.z, r2.w, l(28) + ishl r7.w, r4.z, l(29) + and r7.xyzw, r7.xyzw, l(0x04000000, 0x08000000, 0x10000000, 0x20000000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r7.w, r0.y + ishr r0.z, r1.z, l(5) + ishr r2.z, r1.z, l(6) + ishr r2.w, r1.w, l(1) + ishr r4.z, r1.w, l(2) + ishl r7.x, r0.z, l(30) + ishl r0.z, r2.z, l(31) + ishl r7.z, r2.w, l(4) + ishl r7.w, r4.z, l(5) + and r7.xyz, r7.xzwx, l(0x40000000, 16, 32, 0) + iadd r0.y, r0.y, r7.x + iadd r3.x, r0.z, r0.y + ishr r0.y, r6.y, l(3) + ishr r0.z, r6.y, l(5) + ishr r2.z, r6.y, l(4) + ishr r2.w, r6.x, l(1) + and r0.y, r0.y, l(1) + ishl r8.x, r0.z, l(1) + ishl r8.y, r2.z, l(2) + ishl r8.z, r2.w, l(20) + and r8.xyz, r8.xyzx, l(2, 4, 0x00100000, 0) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r9.w, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r1.w, l(3) + ishr r2.z, r1.w, l(4) + ishr r2.w, r1.w, l(5) + ishl r7.x, r0.z, l(6) + ishl r7.y, r2.z, l(7) + ishl r7.z, r2.w, l(8) + and r7.xyz, r7.xyzx, l(64, 128, 256, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishl r7.x, r5.y, l(9) + ishl r7.y, r5.z, l(29) + ishl r7.z, r5.x, l(1) + ishl r7.w, r5.w, l(7) + and r7.xyzw, r7.xyzw, l(512, 0x20000000, 2, 128) + iadd r0.y, r0.y, r7.x + ishr r2.zw, r5.yyyz, l(1) + ishr r0.z, r5.y, l(2) + ishr r4.z, r5.y, l(3) + ishl r9.x, r2.z, l(10) + ishl r9.y, r0.z, l(11) + ishl r9.z, r4.z, l(12) + ishl r9.w, r2.w, l(30) + and r9.xyzw, r9.xyzw, l(1024, 2048, 4096, 0x40000000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + ishl r8.x, r4.x, l(13) + ishl r8.y, r4.y, l(23) + and r2.zw, r8.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.y, r0.y, r2.z + ishr r0.z, r4.x, l(1) + ishr r2.z, r4.x, l(2) + ishr r4.z, r4.x, l(3) + ishr r4.w, r4.x, l(4) + ishl r10.x, r0.z, l(14) + ishl r10.y, r2.z, l(15) + ishl r10.z, r4.z, l(16) + ishl r10.w, r4.w, l(17) + and r10.xyzw, r10.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r10.x + iadd r0.y, r10.y, r0.y + iadd r0.y, r10.z, r0.y + iadd r0.y, r10.w, r0.y + ishr r0.z, r4.x, l(5) + ishr r2.z, r4.y, l(1) + ishr r4.z, r4.y, l(2) + ishr r4.w, r4.y, l(3) + ishl r10.x, r0.z, l(18) + ishl r10.y, r2.z, l(24) + ishl r10.z, r4.z, l(25) + ishl r10.w, r4.w, l(26) + and r10.xyzw, r10.xyzw, l(0x00040000, 0x01000000, 0x02000000, 0x04000000) + iadd r0.y, r0.y, r10.x + iadd r0.y, r0.w, r0.y + iadd r0.y, r8.z, r0.y + ishr r0.z, r6.x, l(2) + ishr r0.w, r6.x, l(3) + ishl r8.x, r0.z, l(21) + ishl r8.y, r0.w, l(22) + and r0.zw, r8.xxxy, l(0, 0, 0x00200000, 0x00400000) + iadd r0.y, r0.z, r0.y + iadd r0.y, r0.w, r0.y + iadd r0.y, r2.w, r0.y + iadd r0.y, r10.y, r0.y + iadd r0.y, r10.z, r0.y + iadd r0.y, r10.w, r0.y + ishr r0.z, r4.y, l(4) + ishr r0.w, r4.y, l(5) + ishl r8.x, r0.z, l(27) + ishl r8.y, r0.w, l(28) + and r0.zw, r8.xxxy, l(0, 0, 0x08000000, 0x10000000) + iadd r0.y, r0.z, r0.y + iadd r0.y, r0.w, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.zw, r5.zzzx, l(2) + ishr r2.z, r5.z, l(3) + ishr r2.w, r5.x, l(1) + ishl r8.x, r0.z, l(31) + ishl r8.y, r2.w, l(2) + ishl r8.z, r0.w, l(3) + iadd r3.z, r0.y, r8.x + and r0.y, r2.z, l(1) + iadd r0.y, r0.y, r3.w + iadd r0.y, r7.z, r0.y + and r0.zw, r8.yyyz, l(0, 0, 4, 8) + iadd r0.y, r0.z, r0.y + iadd r0.y, r0.w, r0.y + ishr r0.z, r5.x, l(3) + ishr r0.w, r5.x, l(4) + ishr r2.z, r5.x, l(5) + ishr r2.w, r5.w, l(1) + ishl r8.x, r0.z, l(4) + ishl r8.y, r0.w, l(5) + ishl r8.z, r2.z, l(6) + ishl r8.w, r2.w, l(8) + and r8.xyzw, r8.xyzw, l(16, 32, 64, 256) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r5.w, l(2) + ishr r0.w, r5.w, l(3) + ishr r2.z, r5.w, l(4) + ishr r2.w, r5.w, l(5) + ishl r7.x, r0.z, l(9) + ishl r7.y, r0.w, l(10) + ishl r7.z, r2.z, l(11) + ishl r7.w, r2.w, l(12) + and r7.xyzw, r7.xyzw, l(512, 1024, 2048, 4096) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r7.w, r0.y + ishl r0.z, r2.y, l(13) + and r0.z, r0.z, l(8192) + iadd r0.y, r0.z, r0.y + ushr r0.z, r2.y, l(1) + ushr r0.w, r2.y, l(2) + ushr r2.z, r2.y, l(3) + ushr r2.w, r2.y, l(4) + ishl r7.x, r0.z, l(14) + ishl r7.y, r0.w, l(15) + ishl r7.z, r2.z, l(16) + ishl r7.w, r2.w, l(17) + and r7.xyzw, r7.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.w, r7.w, r0.y + else + ieq r0.y, r2.x, l(3) + if_nz r0.y + ishl r7.x, r1.x, l(5) + ishl r7.y, r1.y, l(15) + ishl r7.z, r1.z, l(25) + ishl r7.w, r1.w, l(3) + and r7.xyzw, r7.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.y, r7.x, l(2) + ishr r0.z, r1.x, l(1) + ishr r0.w, r1.x, l(2) + ishr r2.z, r1.x, l(3) + ishr r2.w, r1.x, l(4) + ishl r8.x, r0.z, l(6) + ishl r8.y, r0.w, l(7) + ishl r8.z, r2.z, l(8) + ishl r8.w, r2.w, l(9) + and r8.xyzw, r8.xyzw, l(64, 128, 256, 512) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.x, l(5) + ishr r0.w, r1.x, l(6) + ishr r2.z, r1.x, l(7) + ishr r2.w, r1.x, l(8) + ishl r8.x, r0.z, l(10) + ishl r8.y, r0.w, l(11) + ishl r8.z, r2.z, l(12) + ishl r8.w, r2.w, l(13) + and r8.xyzw, r8.xyzw, l(1024, 2048, 4096, 8192) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.x, l(9) + ishr r0.w, r1.y, l(1) + ishr r2.z, r1.y, l(2) + ishr r2.w, r1.y, l(3) + ishl r8.x, r0.z, l(14) + ishl r8.y, r0.w, l(16) + ishl r8.z, r2.z, l(17) + ishl r8.w, r2.w, l(18) + and r8.xyzw, r8.xyzw, l(0x00004000, 0x00010000, 0x00020000, 0x00040000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(4) + ishr r0.w, r1.y, l(5) + ishr r2.z, r1.y, l(6) + ishr r2.w, r1.y, l(7) + ishl r8.x, r0.z, l(19) + ishl r8.y, r0.w, l(20) + ishl r8.z, r2.z, l(21) + ishl r8.w, r2.w, l(22) + and r8.xyzw, r8.xyzw, l(0x00080000, 0x00100000, 0x00200000, 0x00400000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(8) + ishr r0.w, r1.y, l(9) + ishr r2.z, r1.z, l(1) + ishr r2.w, r1.z, l(2) + ishl r8.x, r0.z, l(23) + ishl r8.y, r0.w, l(24) + ishl r8.z, r2.z, l(26) + ishl r8.w, r2.w, l(27) + and r8.xyzw, r8.xyzw, l(0x00800000, 0x01000000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.z, l(3) + ishr r0.w, r1.z, l(4) + ishr r2.z, r1.z, l(5) + ishr r2.w, r1.z, l(6) + ishl r7.x, r0.z, l(28) + ishl r7.y, r0.w, l(29) + ishl r7.z, r2.z, l(30) + ishl r0.z, r2.w, l(31) + and r7.xyz, r7.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.x, r0.z, r0.y + ishr r0.y, r1.z, l(7) + ishr r0.z, r1.z, l(8) + ishr r0.w, r1.z, l(9) + ishr r2.z, r1.w, l(1) + and r0.y, r0.y, l(1) + ishl r7.x, r0.z, l(1) + ishl r7.y, r0.w, l(2) + ishl r7.z, r2.z, l(4) + and r7.xyz, r7.xyzx, l(2, 4, 16, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r1.w, l(2) + ishr r0.w, r1.w, l(3) + ishr r2.z, r1.w, l(4) + ishr r2.w, r1.x, l(10) + ishl r7.x, r0.z, l(5) + ishl r7.y, r0.w, l(6) + ishl r7.z, r2.z, l(7) + ishl r7.w, r2.w, l(8) + and r7.xyzw, r7.xyzw, l(32, 64, 128, 256) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r7.w, r0.y + ishl r7.x, r5.y, l(9) + ishl r7.y, r5.z, l(29) + ishl r7.z, r5.x, l(1) + ishl r7.w, r5.w, l(7) + and r7.xyzw, r7.xyzw, l(512, 0x20000000, 2, 128) + iadd r0.y, r0.y, r7.x + ishr r0.zw, r5.yyyz, l(1) + ishr r2.z, r5.y, l(2) + ishr r2.w, r5.y, l(3) + ishl r8.x, r0.z, l(10) + ishl r8.y, r2.z, l(11) + ishl r8.z, r2.w, l(12) + ishl r8.w, r0.w, l(30) + and r8.xyzw, r8.xyzw, l(1024, 2048, 4096, 0x40000000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + ishl r8.x, r4.x, l(13) + ishl r8.y, r4.y, l(23) + and r0.zw, r8.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.y, r0.z, r0.y + ishr r2.zw, r4.xxxy, l(1) + ishr r0.z, r4.x, l(2) + ishr r4.z, r4.x, l(3) + ishl r9.x, r2.z, l(14) + ishl r9.y, r0.z, l(15) + ishl r9.z, r4.z, l(16) + ishl r9.w, r2.w, l(24) + and r9.xyzw, r9.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x01000000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + ishr r2.zw, r1.yyyz, l(10) + ishl r8.x, r2.z, l(17) + ishl r8.y, r2.w, l(27) + and r2.zw, r8.xxxy, l(0, 0, 0x00020000, 0x08000000) + iadd r0.y, r0.y, r2.z + ishl r8.x, r6.y, l(18) + ishl r8.y, r6.x, l(19) + and r4.zw, r8.xxxy, l(0, 0, 0x00040000, 0x00080000) + iadd r0.y, r0.y, r4.z + iadd r0.y, r4.w, r0.y + ishr r4.zw, r6.xxxy, l(1) + ishr r0.z, r6.x, l(2) + ishr r2.z, r6.x, l(3) + ishl r10.x, r4.z, l(20) + ishl r10.y, r0.z, l(21) + ishl r10.z, r2.z, l(22) + ishl r10.w, r4.w, l(28) + and r10.xyzw, r10.xyzw, l(0x00100000, 0x00200000, 0x00400000, 0x10000000) + iadd r0.y, r0.y, r10.x + iadd r0.y, r10.y, r0.y + iadd r0.y, r10.z, r0.y + iadd r0.y, r0.w, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.z, r4.y, l(2) + ishr r0.w, r4.y, l(3) + ishl r8.x, r0.z, l(25) + ishl r8.y, r0.w, l(26) + and r0.zw, r8.xxxy, l(0, 0, 0x02000000, 0x04000000) + iadd r0.y, r0.z, r0.y + iadd r0.y, r0.w, r0.y + iadd r0.y, r2.w, r0.y + iadd r0.y, r10.w, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.zw, r5.zzzx, l(2) + ishr r2.z, r5.z, l(3) + ishr r2.w, r5.x, l(1) + ishl r8.x, r0.z, l(31) + ishl r8.y, r2.w, l(2) + ishl r8.z, r0.w, l(3) + iadd r3.z, r0.y, r8.x + and r0.y, r2.z, l(1) + iadd r0.y, r0.y, r3.w + iadd r0.y, r7.z, r0.y + and r0.zw, r8.yyyz, l(0, 0, 4, 8) + iadd r0.y, r0.z, r0.y + iadd r0.y, r0.w, r0.y + ishr r0.z, r5.x, l(3) + ishr r0.w, r5.x, l(4) + ishr r2.z, r5.w, l(1) + ishr r2.w, r5.w, l(2) + ishl r8.x, r0.z, l(4) + ishl r8.y, r0.w, l(5) + ishl r8.z, r2.z, l(8) + ishl r8.w, r2.w, l(9) + and r8.xyzw, r8.xyzw, l(16, 32, 256, 512) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + ishr r0.z, r6.y, l(2) + ishr r0.w, r6.y, l(3) + ishl r7.x, r0.z, l(6) + ishl r7.y, r0.w, l(12) + and r0.zw, r7.xxxy, l(0, 0, 64, 4096) + iadd r0.y, r0.z, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r5.w, l(3) + ishr r2.z, r5.w, l(4) + ishl r7.x, r0.z, l(10) + ishl r7.y, r2.z, l(11) + and r2.zw, r7.xxxy, l(0, 0, 1024, 2048) + iadd r0.y, r0.y, r2.z + iadd r0.y, r2.w, r0.y + iadd r0.y, r0.w, r0.y + ishl r0.z, r2.y, l(13) + and r0.z, r0.z, l(8192) + iadd r0.y, r0.z, r0.y + ushr r0.z, r2.y, l(1) + ushr r0.w, r2.y, l(2) + ushr r2.z, r2.y, l(3) + ushr r2.w, r2.y, l(4) + ishl r7.x, r0.z, l(14) + ishl r7.y, r0.w, l(15) + ishl r7.z, r2.z, l(16) + ishl r7.w, r2.w, l(17) + and r7.xyzw, r7.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.w, r7.w, r0.y + else + ieq r0.y, r2.x, l(4) + if_nz r0.y + ishl r7.x, r1.x, l(5) + ishl r7.y, r1.y, l(15) + ishl r7.z, r1.z, l(25) + ishl r7.w, r1.w, l(3) + and r7.xyzw, r7.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.y, r7.x, l(6) + ishr r0.z, r1.x, l(1) + ishr r0.w, r1.x, l(2) + ishr r2.z, r1.x, l(3) + ishr r2.w, r1.x, l(4) + ishl r8.x, r0.z, l(6) + ishl r8.y, r0.w, l(7) + ishl r8.z, r2.z, l(8) + ishl r8.w, r2.w, l(9) + and r8.xyzw, r8.xyzw, l(64, 128, 256, 512) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.x, l(5) + ishr r0.w, r1.x, l(6) + ishr r2.z, r1.x, l(7) + ishr r2.w, r1.x, l(8) + ishl r8.x, r0.z, l(10) + ishl r8.y, r0.w, l(11) + ishl r8.z, r2.z, l(12) + ishl r8.w, r2.w, l(13) + and r8.xyzw, r8.xyzw, l(1024, 2048, 4096, 8192) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.x, l(9) + ishr r0.w, r1.y, l(1) + ishr r2.z, r1.y, l(2) + ishr r2.w, r1.y, l(3) + ishl r8.x, r0.z, l(14) + ishl r8.y, r0.w, l(16) + ishl r8.z, r2.z, l(17) + ishl r8.w, r2.w, l(18) + and r8.xyzw, r8.xyzw, l(0x00004000, 0x00010000, 0x00020000, 0x00040000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(4) + ishr r0.w, r1.y, l(5) + ishr r2.z, r1.y, l(6) + ishr r2.w, r1.y, l(7) + ishl r8.x, r0.z, l(19) + ishl r8.y, r0.w, l(20) + ishl r8.z, r2.z, l(21) + ishl r8.w, r2.w, l(22) + and r8.xyzw, r8.xyzw, l(0x00080000, 0x00100000, 0x00200000, 0x00400000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(8) + ishr r0.w, r1.y, l(9) + ishr r2.z, r1.z, l(1) + ishr r2.w, r1.z, l(2) + ishl r8.x, r0.z, l(23) + ishl r8.y, r0.w, l(24) + ishl r8.z, r2.z, l(26) + ishl r8.w, r2.w, l(27) + and r8.xyzw, r8.xyzw, l(0x00800000, 0x01000000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.z, l(3) + ishr r0.w, r1.z, l(4) + ishr r2.z, r1.z, l(5) + ishr r2.w, r1.z, l(6) + ishl r7.x, r0.z, l(28) + ishl r7.y, r0.w, l(29) + ishl r7.z, r2.z, l(30) + ishl r0.z, r2.w, l(31) + and r7.xyz, r7.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.x, r0.z, r0.y + ishr r0.y, r1.z, l(7) + ishr r0.z, r1.z, l(8) + ishr r0.w, r1.z, l(9) + ishr r2.z, r1.w, l(1) + and r0.y, r0.y, l(1) + ishl r7.x, r0.z, l(1) + ishl r7.y, r0.w, l(2) + ishl r7.z, r2.z, l(4) + and r7.xyz, r7.xyzx, l(2, 4, 16, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r1.w, l(2) + ishr r0.w, r1.w, l(3) + ishr r2.zw, r1.xxxy, l(10) + ishl r7.x, r0.z, l(5) + ishl r7.y, r0.w, l(6) + ishl r7.z, r2.z, l(7) + ishl r7.w, r2.w, l(18) + and r7.xyzw, r7.xyzw, l(32, 64, 128, 0x00040000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r6.x, l(4) + ishr r0.w, r6.x, l(1) + ishr r2.z, r6.x, l(2) + ishr r2.w, r6.x, l(3) + ishl r8.x, r0.z, l(8) + ishl r8.y, r0.w, l(20) + ishl r8.z, r2.z, l(21) + ishl r8.w, r2.w, l(22) + and r8.xyzw, r8.xyzw, l(256, 0x00100000, 0x00200000, 0x00400000) + iadd r0.y, r0.y, r8.x + ishl r9.x, r5.y, l(9) + ishl r9.y, r5.z, l(29) + ishl r9.z, r5.x, l(1) + ishl r9.w, r5.w, l(7) + and r9.xyzw, r9.xyzw, l(512, 0x20000000, 2, 128) + iadd r0.y, r0.y, r9.x + ishr r0.zw, r5.yyyz, l(1) + ishr r2.z, r5.y, l(2) + ishr r2.w, r5.y, l(3) + ishl r10.x, r0.z, l(10) + ishl r10.y, r2.z, l(11) + ishl r10.z, r2.w, l(12) + ishl r10.w, r0.w, l(30) + and r10.xyzw, r10.xyzw, l(1024, 2048, 4096, 0x40000000) + iadd r0.y, r0.y, r10.x + iadd r0.y, r10.y, r0.y + iadd r0.y, r10.z, r0.y + ishl r7.x, r4.x, l(13) + ishl r7.y, r4.y, l(23) + and r0.zw, r7.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.y, r0.z, r0.y + ishr r0.z, r4.x, l(1) + ishr r2.z, r4.x, l(2) + ishr r2.w, r4.x, l(3) + ishr r4.z, r4.x, l(4) + ishl r11.x, r0.z, l(14) + ishl r11.y, r2.z, l(15) + ishl r11.z, r2.w, l(16) + ishl r11.w, r4.z, l(17) + and r11.xyzw, r11.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r11.x + iadd r0.y, r11.y, r0.y + iadd r0.y, r11.z, r0.y + iadd r0.y, r11.w, r0.y + iadd r0.y, r7.w, r0.y + ishl r7.x, r6.x, l(19) + ishl r7.y, r6.y, l(5) + and r2.zw, r7.xxxy, l(0, 0, 0x00080000, 32) + iadd r0.y, r0.y, r2.z + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + iadd r0.y, r0.w, r0.y + ishr r0.z, r4.y, l(1) + ishr r0.w, r4.y, l(2) + ishr r2.z, r4.y, l(3) + ishl r7.x, r0.z, l(24) + ishl r7.y, r0.w, l(25) + ishl r7.z, r2.z, l(26) + and r7.xyz, r7.xyzx, l(0x01000000, 0x02000000, 0x04000000, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r1.z, l(10) + ishl r0.z, r0.z, l(27) + and r0.z, r0.z, l(0x08000000) + iadd r0.y, r0.z, r0.y + ishr r0.z, r6.y, l(1) + ishr r0.w, r6.y, l(2) + ishr r2.z, r6.y, l(3) + ishl r7.x, r0.z, l(28) + ishl r7.y, r0.w, l(6) + ishl r7.z, r2.z, l(12) + and r7.xyz, r7.xyzx, l(0x10000000, 64, 4096, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r10.w, r0.y + ishr r0.zw, r5.zzzx, l(2) + ishr r2.z, r5.z, l(3) + ishr r4.z, r5.x, l(1) + ishl r8.x, r0.z, l(31) + ishl r8.y, r4.z, l(2) + ishl r8.z, r0.w, l(3) + iadd r3.z, r0.y, r8.x + and r0.y, r2.z, l(1) + iadd r0.y, r0.y, r3.w + iadd r0.y, r9.z, r0.y + and r0.zw, r8.yyyz, l(0, 0, 4, 8) + iadd r0.y, r0.z, r0.y + iadd r0.y, r0.w, r0.y + ishr r0.zw, r5.xxxw, l(3) + ishr r2.z, r5.w, l(1) + ishr r4.z, r5.w, l(2) + ishl r8.x, r0.z, l(4) + ishl r8.y, r2.z, l(8) + ishl r8.z, r4.z, l(9) + ishl r8.w, r0.w, l(10) + and r8.xyzw, r8.xyzw, l(16, 256, 512, 1024) + iadd r0.y, r0.y, r8.x + iadd r0.y, r2.w, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r9.w, r0.y + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r5.y, l(4) + ishl r0.z, r0.z, l(11) + and r0.z, r0.z, l(2048) + iadd r0.y, r0.z, r0.y + iadd r0.y, r7.z, r0.y + ishl r0.z, r2.y, l(13) + and r0.z, r0.z, l(8192) + iadd r0.y, r0.z, r0.y + ushr r0.z, r2.y, l(1) + ushr r0.w, r2.y, l(2) + ushr r2.z, r2.y, l(3) + ushr r2.w, r2.y, l(4) + ishl r7.x, r0.z, l(14) + ishl r7.y, r0.w, l(15) + ishl r7.z, r2.z, l(16) + ishl r7.w, r2.w, l(17) + and r7.xyzw, r7.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.w, r7.w, r0.y + else + ieq r0.y, r2.x, l(5) + if_nz r0.y + ishl r7.x, r1.x, l(5) + ishl r7.y, r1.y, l(15) + ishl r7.z, r1.z, l(25) + ishl r7.w, r1.w, l(3) + and r7.xyzw, r7.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.y, r7.x, l(10) + ishr r0.z, r1.x, l(1) + ishr r0.w, r1.x, l(2) + ishr r2.z, r1.x, l(3) + ishr r2.w, r1.x, l(4) + ishl r8.x, r0.z, l(6) + ishl r8.y, r0.w, l(7) + ishl r8.z, r2.z, l(8) + ishl r8.w, r2.w, l(9) + and r8.xyzw, r8.xyzw, l(64, 128, 256, 512) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.x, l(5) + ishr r0.w, r1.x, l(6) + ishr r2.z, r1.x, l(7) + ishr r2.w, r1.x, l(8) + ishl r8.x, r0.z, l(10) + ishl r8.y, r0.w, l(11) + ishl r8.z, r2.z, l(12) + ishl r8.w, r2.w, l(13) + and r8.xyzw, r8.xyzw, l(1024, 2048, 4096, 8192) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.x, l(9) + ishr r0.w, r1.y, l(1) + ishr r2.z, r1.y, l(2) + ishr r2.w, r1.y, l(3) + ishl r8.x, r0.z, l(14) + ishl r8.y, r0.w, l(16) + ishl r8.z, r2.z, l(17) + ishl r8.w, r2.w, l(18) + and r8.xyzw, r8.xyzw, l(0x00004000, 0x00010000, 0x00020000, 0x00040000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(4) + ishr r0.w, r1.y, l(5) + ishr r2.z, r1.y, l(6) + ishr r2.w, r1.y, l(7) + ishl r8.x, r0.z, l(19) + ishl r8.y, r0.w, l(20) + ishl r8.z, r2.z, l(21) + ishl r8.w, r2.w, l(22) + and r8.xyzw, r8.xyzw, l(0x00080000, 0x00100000, 0x00200000, 0x00400000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(8) + ishr r0.w, r1.y, l(9) + ishr r2.z, r1.z, l(1) + ishr r2.w, r1.z, l(2) + ishl r8.x, r0.z, l(23) + ishl r8.y, r0.w, l(24) + ishl r8.z, r2.z, l(26) + ishl r8.w, r2.w, l(27) + and r8.xyzw, r8.xyzw, l(0x00800000, 0x01000000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.z, l(3) + ishr r0.w, r1.z, l(4) + ishr r2.z, r1.z, l(5) + ishr r2.w, r1.z, l(6) + ishl r7.x, r0.z, l(28) + ishl r7.y, r0.w, l(29) + ishl r7.z, r2.z, l(30) + ishl r0.z, r2.w, l(31) + and r7.xyz, r7.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.x, r0.z, r0.y + ishr r0.y, r1.z, l(7) + ishr r0.z, r1.z, l(8) + ishr r0.w, r1.z, l(9) + ishr r2.z, r1.w, l(1) + and r0.y, r0.y, l(1) + ishl r7.x, r0.z, l(1) + ishl r7.y, r0.w, l(2) + ishl r7.z, r2.z, l(4) + and r7.xyz, r7.xyzx, l(2, 4, 16, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r1.w, l(2) + ishr r0.w, r1.w, l(3) + ishr r2.zw, r1.xxxy, l(10) + ishl r7.x, r0.z, l(5) + ishl r7.y, r0.w, l(6) + ishl r7.z, r2.z, l(7) + ishl r7.w, r2.w, l(17) + and r7.xyzw, r7.xyzw, l(32, 64, 128, 0x00020000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r5.z, l(4) + ishr r0.w, r5.y, l(1) + ishr r2.z, r5.y, l(2) + ishr r2.w, r5.y, l(3) + ishl r8.x, r0.z, l(8) + ishl r8.y, r0.w, l(10) + ishl r8.z, r2.z, l(11) + ishl r8.w, r2.w, l(12) + and r8.xyzw, r8.xyzw, l(256, 1024, 2048, 4096) + iadd r0.y, r0.y, r8.x + ishl r9.x, r5.y, l(9) + ishl r9.y, r5.z, l(29) + ishl r9.z, r5.x, l(1) + ishl r9.w, r5.w, l(7) + and r9.xyzw, r9.xyzw, l(512, 0x20000000, 2, 128) + iadd r0.y, r0.y, r9.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishl r7.x, r4.x, l(13) + ishl r7.y, r4.y, l(23) + and r0.zw, r7.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.y, r0.z, r0.y + ishr r2.zw, r4.xxxy, l(1) + ishr r0.z, r4.x, l(2) + ishr r4.z, r4.x, l(3) + ishl r8.x, r2.z, l(14) + ishl r8.y, r0.z, l(15) + ishl r8.z, r4.z, l(16) + ishl r8.w, r2.w, l(24) + and r8.xyzw, r8.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x01000000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r7.w, r0.y + ishl r7.x, r6.y, l(18) + ishl r7.y, r6.x, l(19) + and r2.zw, r7.xxxy, l(0, 0, 0x00040000, 0x00080000) + iadd r0.y, r0.y, r2.z + iadd r0.y, r2.w, r0.y + ishr r2.zw, r6.xxxy, l(1) + ishr r0.z, r6.x, l(2) + ishr r4.z, r6.x, l(3) + ishl r7.x, r2.z, l(20) + ishl r7.y, r0.z, l(21) + ishl r7.z, r4.z, l(22) + ishl r7.w, r2.w, l(5) + and r7.xyzw, r7.xyzw, l(0x00100000, 0x00200000, 0x00400000, 32) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r0.w, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r4.y, l(2) + ishr r0.w, r4.y, l(3) + ishr r2.z, r4.y, l(4) + ishl r7.x, r0.z, l(25) + ishl r7.y, r0.w, l(26) + ishl r7.z, r2.z, l(27) + and r7.xyz, r7.xyzx, l(0x02000000, 0x04000000, 0x08000000, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r1.z, l(10) + ishl r0.z, r0.z, l(28) + and r0.z, r0.z, l(0x10000000) + iadd r0.y, r0.z, r0.y + iadd r0.y, r9.y, r0.y + ishr r0.zw, r5.zzzx, l(1) + ishr r2.z, r5.z, l(2) + ishr r2.w, r5.z, l(3) + ishl r7.x, r0.z, l(30) + ishl r0.z, r2.z, l(31) + ishl r7.z, r0.w, l(2) + and r4.zw, r7.xxxz, l(0, 0, 0x40000000, 4) + iadd r0.y, r0.y, r4.z + iadd r3.z, r0.z, r0.y + and r0.y, r2.w, l(1) + iadd r0.y, r0.y, r3.w + iadd r0.y, r9.z, r0.y + iadd r0.y, r4.w, r0.y + ishr r0.zw, r5.xxxw, l(2) + ishr r2.z, r5.x, l(3) + ishr r2.w, r5.w, l(1) + ishl r8.x, r0.z, l(3) + ishl r8.y, r2.z, l(4) + ishl r8.z, r2.w, l(8) + ishl r8.w, r0.w, l(9) + and r8.xyzw, r8.xyzw, l(8, 16, 256, 512) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r7.w, r0.y + ishr r0.z, r6.y, l(2) + ishr r0.w, r6.y, l(4) + ishr r2.z, r6.y, l(3) + ishl r7.x, r0.z, l(6) + ishl r7.y, r0.w, l(11) + ishl r7.z, r2.z, l(12) + and r7.xyz, r7.xyzx, l(64, 2048, 4096, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r9.w, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r5.w, l(3) + ishl r0.z, r0.z, l(10) + and r0.z, r0.z, l(1024) + iadd r0.y, r0.z, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishl r0.z, r2.y, l(13) + and r0.z, r0.z, l(8192) + iadd r0.y, r0.z, r0.y + ushr r0.z, r2.y, l(1) + ushr r0.w, r2.y, l(2) + ushr r2.z, r2.y, l(3) + ushr r2.w, r2.y, l(4) + ishl r7.x, r0.z, l(14) + ishl r7.y, r0.w, l(15) + ishl r7.z, r2.z, l(16) + ishl r7.w, r2.w, l(17) + and r7.xyzw, r7.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.w, r7.w, r0.y + else + ieq r0.y, r2.x, l(6) + if_nz r0.y + ishl r7.x, r1.x, l(5) + ishl r7.y, r1.y, l(15) + ishl r7.z, r1.z, l(25) + ishl r7.w, r1.w, l(3) + and r7.xyzw, r7.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.y, r7.x, l(14) + ishr r0.z, r1.x, l(1) + ishr r0.w, r1.x, l(2) + ishr r2.z, r1.x, l(3) + ishr r2.w, r1.x, l(4) + ishl r8.x, r0.z, l(6) + ishl r8.y, r0.w, l(7) + ishl r8.z, r2.z, l(8) + ishl r8.w, r2.w, l(9) + and r8.xyzw, r8.xyzw, l(64, 128, 256, 512) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.x, l(5) + ishr r0.w, r1.x, l(6) + ishr r2.z, r1.x, l(7) + ishr r2.w, r1.x, l(8) + ishl r8.x, r0.z, l(10) + ishl r8.y, r0.w, l(11) + ishl r8.z, r2.z, l(12) + ishl r8.w, r2.w, l(13) + and r8.xyzw, r8.xyzw, l(1024, 2048, 4096, 8192) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.zw, r5.zzzy, l(4) + ishr r2.z, r5.y, l(1) + ishr r2.w, r5.y, l(2) + ishl r8.x, r0.z, l(14) + ishl r8.y, r0.w, l(24) + ishl r8.z, r2.z, l(10) + ishl r8.w, r2.w, l(11) + and r8.xyzw, r8.xyzw, l(0x00004000, 0x01000000, 1024, 2048) + iadd r0.y, r0.y, r8.x + iadd r0.y, r7.y, r0.y + ishr r0.z, r1.y, l(1) + ishr r0.w, r1.y, l(2) + ishr r2.z, r1.y, l(3) + ishr r2.w, r1.y, l(4) + ishl r9.x, r0.z, l(16) + ishl r9.y, r0.w, l(17) + ishl r9.z, r2.z, l(18) + ishl r9.w, r2.w, l(19) + and r9.xyzw, r9.xyzw, l(0x00010000, 0x00020000, 0x00040000, 0x00080000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.z, r1.y, l(5) + ishr r0.w, r1.y, l(6) + ishr r2.z, r1.y, l(7) + ishr r2.w, r1.y, l(8) + ishl r9.x, r0.z, l(20) + ishl r9.y, r0.w, l(21) + ishl r9.z, r2.z, l(22) + ishl r9.w, r2.w, l(23) + and r9.xyzw, r9.xyzw, l(0x00100000, 0x00200000, 0x00400000, 0x00800000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + iadd r0.y, r8.y, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r1.z, l(1) + ishr r0.w, r1.z, l(2) + ishr r2.z, r1.z, l(3) + ishr r2.w, r1.z, l(4) + ishl r9.x, r0.z, l(26) + ishl r9.y, r0.w, l(27) + ishl r9.z, r2.z, l(28) + ishl r9.w, r2.w, l(29) + and r9.xyzw, r9.xyzw, l(0x04000000, 0x08000000, 0x10000000, 0x20000000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.z, r1.z, l(5) + ishr r0.w, r1.z, l(6) + ishr r2.z, r1.z, l(7) + ishr r2.w, r1.z, l(8) + ishl r7.x, r0.z, l(30) + ishl r0.z, r0.w, l(31) + ishl r7.z, r2.w, l(1) + and r4.zw, r7.xxxz, l(0, 0, 0x40000000, 2) + iadd r0.y, r0.y, r4.z + iadd r3.x, r0.z, r0.y + and r0.y, r2.z, l(1) + iadd r0.y, r4.w, r0.y + ishr r0.zw, r6.yyyx, l(4) + ishr r2.z, r6.x, l(1) + ishr r2.w, r6.x, l(2) + ishl r9.x, r0.z, l(2) + ishl r9.y, r0.w, l(8) + ishl r9.z, r2.z, l(20) + ishl r9.w, r2.w, l(21) + and r9.xyzw, r9.xyzw, l(4, 256, 0x00100000, 0x00200000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r7.w, r0.y + ishr r0.z, r1.w, l(1) + ishr r0.w, r1.w, l(2) + ishr r2.z, r1.w, l(3) + ishr r2.w, r1.w, l(4) + ishl r7.x, r0.z, l(4) + ishl r7.y, r0.w, l(5) + ishl r7.z, r2.z, l(6) + ishl r7.w, r2.w, l(7) + and r7.xyzw, r7.xyzw, l(16, 32, 64, 128) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r9.y, r0.y + ishl r7.x, r5.y, l(9) + ishl r7.y, r5.z, l(29) + ishl r7.z, r5.x, l(1) + ishl r7.w, r5.w, l(7) + and r7.xyzw, r7.xyzw, l(512, 0x20000000, 2, 128) + iadd r0.y, r0.y, r7.x + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.zw, r5.yyyz, l(3) + ishr r2.z, r5.z, l(1) + ishr r2.w, r5.z, l(2) + ishl r8.x, r0.z, l(12) + ishl r8.y, r2.z, l(30) + ishl r0.z, r2.w, l(31) + and r2.zw, r8.xxxy, l(0, 0, 4096, 0x40000000) + iadd r0.y, r0.y, r2.z + ishl r8.x, r4.x, l(13) + ishl r8.y, r4.y, l(23) + and r4.zw, r8.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.y, r0.y, r4.z + ishr r2.z, r4.x, l(1) + ishr r4.z, r4.x, l(2) + ishr r6.z, r4.x, l(3) + ishr r6.w, r4.x, l(4) + ishl r8.x, r2.z, l(14) + ishl r8.y, r4.z, l(15) + ishl r8.z, r6.z, l(16) + ishl r8.w, r6.w, l(17) + and r8.xyzw, r8.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishl r8.x, r6.y, l(18) + ishl r8.y, r6.x, l(19) + and r6.zw, r8.xxxy, l(0, 0, 0x00040000, 0x00080000) + iadd r0.y, r0.y, r6.z + iadd r0.y, r6.w, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r6.zw, r6.xxxy, l(3) + ishr r2.z, r6.y, l(1) + ishr r4.z, r6.y, l(2) + ishl r8.x, r6.z, l(22) + ishl r8.y, r2.z, l(28) + ishl r8.z, r4.z, l(6) + ishl r8.w, r6.w, l(12) + and r8.xyzw, r8.xyzw, l(0x00400000, 0x10000000, 64, 4096) + iadd r0.y, r0.y, r8.x + iadd r0.y, r4.w, r0.y + ishr r2.z, r4.y, l(1) + ishr r4.z, r4.y, l(2) + ishr r4.w, r4.y, l(3) + ishr r6.z, r4.y, l(4) + ishl r9.x, r2.z, l(24) + ishl r9.y, r4.z, l(25) + ishl r9.z, r4.w, l(26) + ishl r9.w, r6.z, l(27) + and r9.xyzw, r9.xyzw, l(0x01000000, 0x02000000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + iadd r0.y, r8.y, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r2.w, r0.y + iadd r3.z, r0.z, r0.y + and r0.y, r0.w, l(1) + iadd r0.y, r0.y, r3.w + iadd r0.y, r7.z, r0.y + ishr r0.z, r5.x, l(1) + ishr r0.w, r5.x, l(2) + ishr r2.z, r5.x, l(3) + ishr r2.w, r5.x, l(4) + ishl r9.x, r0.z, l(2) + ishl r9.y, r0.w, l(3) + ishl r9.z, r2.z, l(4) + ishl r9.w, r2.w, l(5) + and r9.xyzw, r9.xyzw, l(4, 8, 16, 32) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r7.w, r0.y + ishr r0.z, r5.w, l(1) + ishr r0.w, r5.w, l(2) + ishr r2.z, r5.w, l(3) + ishr r2.w, r5.w, l(4) + ishl r7.x, r0.z, l(8) + ishl r7.y, r0.w, l(9) + ishl r7.z, r2.z, l(10) + ishl r7.w, r2.w, l(11) + and r7.xyzw, r7.xyzw, l(256, 512, 1024, 2048) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r8.w, r0.y + ishl r0.z, r2.y, l(13) + and r0.z, r0.z, l(8192) + iadd r0.y, r0.z, r0.y + ushr r0.z, r2.y, l(1) + ushr r0.w, r2.y, l(2) + ushr r2.z, r2.y, l(3) + ushr r2.w, r2.y, l(4) + ishl r7.x, r0.z, l(14) + ishl r7.y, r0.w, l(15) + ishl r7.z, r2.z, l(16) + ishl r7.w, r2.w, l(17) + and r7.xyzw, r7.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.w, r7.w, r0.y + else + ieq r0.y, r2.x, l(7) + if_nz r0.y + ishl r7.x, r1.x, l(5) + ishl r7.y, r1.y, l(15) + ishl r7.z, r1.z, l(25) + ishl r7.w, r1.w, l(3) + and r7.xyzw, r7.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.y, r7.x, l(18) + ishr r0.z, r1.x, l(1) + ishr r0.w, r1.x, l(2) + ishr r2.z, r1.x, l(3) + ishr r2.w, r1.x, l(4) + ishl r8.x, r0.z, l(6) + ishl r8.y, r0.w, l(7) + ishl r8.z, r2.z, l(8) + ishl r8.w, r2.w, l(9) + and r8.xyzw, r8.xyzw, l(64, 128, 256, 512) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.x, l(5) + ishr r0.w, r1.x, l(6) + ishr r2.z, r1.x, l(7) + ishr r2.w, r1.y, l(1) + ishl r8.x, r0.z, l(10) + ishl r8.y, r0.w, l(11) + ishl r8.z, r2.z, l(12) + ishl r8.w, r2.w, l(16) + and r8.xyzw, r8.xyzw, l(1024, 2048, 4096, 0x00010000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + ishr r0.zw, r6.xxxy, l(4) + ishr r2.z, r6.y, l(2) + ishr r2.w, r6.y, l(3) + ishl r9.x, r0.z, l(13) + ishl r9.y, r2.z, l(23) + ishl r9.z, r2.w, l(1) + ishl r9.w, r0.w, l(2) + and r9.xyzw, r9.xyzw, l(8192, 0x00800000, 2, 4) + iadd r0.y, r0.y, r9.x + ishr r0.zw, r5.zzzy, l(4) + ishr r2.z, r5.y, l(1) + ishr r2.w, r5.y, l(2) + ishl r10.x, r0.z, l(14) + ishl r10.y, r0.w, l(24) + ishl r10.z, r2.z, l(10) + ishl r10.w, r2.w, l(11) + and r10.xyzw, r10.xyzw, l(0x00004000, 0x01000000, 1024, 2048) + iadd r0.y, r0.y, r10.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(2) + ishr r0.w, r1.y, l(3) + ishr r2.z, r1.y, l(4) + ishr r2.w, r1.y, l(5) + ishl r8.x, r0.z, l(17) + ishl r8.y, r0.w, l(18) + ishl r8.z, r2.z, l(19) + ishl r8.w, r2.w, l(20) + and r8.xyzw, r8.xyzw, l(0x00020000, 0x00040000, 0x00080000, 0x00100000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(6) + ishr r0.w, r1.y, l(7) + ishr r2.z, r1.z, l(1) + ishr r2.w, r1.z, l(2) + ishl r8.x, r0.z, l(21) + ishl r8.y, r0.w, l(22) + ishl r8.z, r2.z, l(26) + ishl r8.w, r2.w, l(27) + and r8.xyzw, r8.xyzw, l(0x00200000, 0x00400000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r9.y, r0.y + iadd r0.y, r10.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.z, l(3) + ishr r0.w, r1.z, l(4) + ishr r2.z, r1.z, l(5) + ishr r2.w, r1.z, l(6) + ishl r7.x, r0.z, l(28) + ishl r7.y, r0.w, l(29) + ishl r7.z, r2.z, l(30) + ishl r0.z, r2.w, l(31) + and r7.xyz, r7.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.x, r0.z, r0.y + ishr r0.y, r1.z, l(7) + ishr r0.z, r1.w, l(1) + ishr r0.w, r1.w, l(2) + ishr r2.z, r1.w, l(3) + and r0.y, r0.y, l(1) + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + iadd r0.y, r7.w, r0.y + ishl r7.x, r0.z, l(4) + ishl r7.y, r0.w, l(5) + ishl r7.z, r2.z, l(6) + and r7.xyz, r7.xyzx, l(16, 32, 64, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r1.w, l(4) + ishr r0.w, r1.w, l(5) + ishl r7.x, r0.z, l(7) + ishl r7.y, r0.w, l(8) + and r0.zw, r7.xxxy, l(0, 0, 128, 256) + iadd r0.y, r0.z, r0.y + iadd r0.y, r0.w, r0.y + ishl r7.x, r5.y, l(9) + ishl r7.y, r5.z, l(29) + ishl r7.z, r5.x, l(1) + ishl r7.w, r5.w, l(7) + and r7.xyzw, r7.xyzw, l(512, 0x20000000, 2, 128) + iadd r0.y, r0.y, r7.x + iadd r0.y, r10.z, r0.y + iadd r0.y, r10.w, r0.y + ishr r0.zw, r5.yyyz, l(3) + ishr r2.z, r5.z, l(1) + ishr r2.w, r5.z, l(2) + ishl r8.x, r0.z, l(12) + ishl r8.y, r2.z, l(30) + ishl r0.z, r2.w, l(31) + and r2.zw, r8.xxxy, l(0, 0, 4096, 0x40000000) + iadd r0.y, r0.y, r2.z + ishl r8.x, r4.x, l(13) + ishl r8.y, r4.y, l(23) + and r4.zw, r8.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.y, r0.y, r4.z + ishr r2.z, r4.x, l(1) + ishr r4.z, r4.x, l(2) + ishr r6.z, r4.x, l(3) + ishr r6.w, r4.x, l(4) + ishl r8.x, r2.z, l(14) + ishl r8.y, r4.z, l(15) + ishl r8.z, r6.z, l(16) + ishl r8.w, r6.w, l(17) + and r8.xyzw, r8.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishl r8.x, r6.y, l(18) + ishl r8.y, r6.x, l(19) + and r6.zw, r8.xxxy, l(0, 0, 0x00040000, 0x00080000) + iadd r0.y, r0.y, r6.z + iadd r0.y, r6.w, r0.y + ishr r6.zw, r6.xxxy, l(1) + ishr r2.z, r6.x, l(2) + ishr r4.z, r6.x, l(3) + ishl r8.x, r6.z, l(20) + ishl r8.y, r2.z, l(21) + ishl r8.z, r4.z, l(22) + ishl r8.w, r6.w, l(28) + and r8.xyzw, r8.xyzw, l(0x00100000, 0x00200000, 0x00400000, 0x10000000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r4.w, r0.y + ishr r2.z, r4.y, l(1) + ishr r4.z, r4.y, l(2) + ishr r4.w, r4.y, l(3) + ishr r6.z, r4.y, l(4) + ishl r9.x, r2.z, l(24) + ishl r9.y, r4.z, l(25) + ishl r9.z, r4.w, l(26) + ishl r9.w, r6.z, l(27) + and r9.xyzw, r9.xyzw, l(0x01000000, 0x02000000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + iadd r0.y, r8.w, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r2.w, r0.y + iadd r3.z, r0.z, r0.y + and r0.y, r0.w, l(1) + iadd r0.y, r0.y, r3.w + iadd r0.y, r7.z, r0.y + ishr r0.z, r5.x, l(1) + ishr r0.w, r5.x, l(2) + ishr r2.z, r5.x, l(3) + ishr r2.w, r5.x, l(4) + ishl r8.x, r0.z, l(2) + ishl r8.y, r0.w, l(3) + ishl r8.z, r2.z, l(4) + ishl r8.w, r2.w, l(5) + and r8.xyzw, r8.xyzw, l(4, 8, 16, 32) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r5.x, l(5) + ishr r0.w, r5.w, l(1) + ishr r2.z, r5.w, l(2) + ishr r2.w, r5.w, l(3) + ishl r8.x, r0.z, l(6) + ishl r8.y, r0.w, l(8) + ishl r8.z, r2.z, l(9) + ishl r8.w, r2.w, l(10) + and r8.xyzw, r8.xyzw, l(64, 256, 512, 1024) + iadd r0.y, r0.y, r8.x + iadd r0.y, r7.w, r0.y + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r5.w, l(4) + ishr r0.w, r5.w, l(5) + ishl r7.x, r0.z, l(11) + ishl r7.y, r0.w, l(12) + and r0.zw, r7.xxxy, l(0, 0, 2048, 4096) + iadd r0.y, r0.z, r0.y + iadd r0.y, r0.w, r0.y + ishl r0.z, r2.y, l(13) + and r0.z, r0.z, l(8192) + iadd r0.y, r0.z, r0.y + ushr r0.z, r2.y, l(1) + ushr r0.w, r2.y, l(2) + ushr r2.z, r2.y, l(3) + ushr r2.w, r2.y, l(4) + ishl r7.x, r0.z, l(14) + ishl r7.y, r0.w, l(15) + ishl r7.z, r2.z, l(16) + ishl r7.w, r2.w, l(17) + and r7.xyzw, r7.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.w, r7.w, r0.y + else + ieq r0.y, r2.x, l(8) + if_nz r0.y + ishl r7.x, r1.x, l(5) + ishl r7.y, r1.y, l(15) + ishl r7.z, r1.z, l(25) + ishl r7.w, r1.w, l(3) + and r7.xyzw, r7.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.y, r7.x, l(22) + ishr r0.z, r1.x, l(1) + ishr r0.w, r1.x, l(2) + ishr r2.z, r1.x, l(3) + ishr r2.w, r1.x, l(4) + ishl r8.x, r0.z, l(6) + ishl r8.y, r0.w, l(7) + ishl r8.z, r2.z, l(8) + ishl r8.w, r2.w, l(9) + and r8.xyzw, r8.xyzw, l(64, 128, 256, 512) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.x, l(5) + ishr r0.w, r1.x, l(6) + ishr r2.z, r1.x, l(7) + ishr r2.w, r1.y, l(1) + ishl r8.x, r0.z, l(10) + ishl r8.y, r0.w, l(11) + ishl r8.z, r2.z, l(12) + ishl r8.w, r2.w, l(16) + and r8.xyzw, r8.xyzw, l(1024, 2048, 4096, 0x00010000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + ishl r8.x, r6.y, l(13) + ishl r8.y, r6.x, l(19) + and r0.zw, r8.xxxy, l(0, 0, 8192, 0x00080000) + iadd r0.y, r0.z, r0.y + ishr r2.zw, r5.zzzy, l(4) + ishr r0.z, r5.y, l(5) + ishr r4.z, r5.y, l(1) + ishl r9.x, r2.z, l(14) + ishl r9.y, r0.z, l(23) + ishl r9.z, r2.w, l(24) + ishl r9.w, r4.z, l(10) + and r9.xyzw, r9.xyzw, l(0x00004000, 0x00800000, 0x01000000, 1024) + iadd r0.y, r0.y, r9.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(2) + ishr r2.z, r1.y, l(3) + ishr r2.w, r1.y, l(4) + ishr r4.z, r1.y, l(5) + ishl r8.x, r0.z, l(17) + ishl r8.y, r2.z, l(18) + ishl r8.z, r2.w, l(19) + ishl r8.w, r4.z, l(20) + and r8.xyzw, r8.xyzw, l(0x00020000, 0x00040000, 0x00080000, 0x00100000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(6) + ishr r2.z, r1.y, l(7) + ishr r2.w, r1.z, l(1) + ishr r4.z, r1.z, l(2) + ishl r8.x, r0.z, l(21) + ishl r8.y, r2.z, l(22) + ishl r8.z, r2.w, l(26) + ishl r8.w, r4.z, l(27) + and r8.xyzw, r8.xyzw, l(0x00200000, 0x00400000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.z, l(3) + ishr r2.z, r1.z, l(4) + ishr r2.w, r1.z, l(5) + ishr r4.z, r1.z, l(6) + ishl r7.x, r0.z, l(28) + ishl r7.y, r2.z, l(29) + ishl r7.z, r2.w, l(30) + ishl r0.z, r4.z, l(31) + and r7.xyz, r7.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.x, r0.z, r0.y + ishr r0.y, r1.z, l(7) + ishr r0.z, r1.w, l(1) + ishr r2.z, r1.w, l(2) + ishr r2.w, r1.w, l(3) + and r0.y, r0.y, l(1) + ishr r4.z, r6.x, l(5) + ishr r6.zw, r6.yyyx, l(4) + ishr r4.w, r6.x, l(1) + ishl r8.x, r4.z, l(1) + ishl r8.y, r6.z, l(2) + ishl r8.z, r6.w, l(8) + ishl r8.w, r4.w, l(20) + and r8.xyzw, r8.xyzw, l(2, 4, 256, 0x00100000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r7.w, r0.y + ishl r7.x, r0.z, l(4) + ishl r7.y, r2.z, l(5) + ishl r7.z, r2.w, l(6) + and r7.xyz, r7.xyzx, l(16, 32, 64, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r1.w, l(4) + ishl r0.z, r0.z, l(7) + and r0.z, r0.z, l(128) + iadd r0.y, r0.z, r0.y + iadd r0.y, r8.z, r0.y + ishl r7.x, r5.y, l(9) + ishl r7.y, r5.z, l(29) + ishl r7.z, r5.x, l(1) + ishl r7.w, r5.w, l(7) + and r7.xyzw, r7.xyzw, l(512, 0x20000000, 2, 128) + iadd r0.y, r0.y, r7.x + iadd r0.y, r9.w, r0.y + ishr r2.zw, r5.yyyz, l(2) + ishr r0.z, r5.y, l(3) + ishr r4.z, r5.z, l(1) + ishl r8.x, r2.z, l(11) + ishl r8.y, r0.z, l(12) + ishl r8.z, r4.z, l(30) + ishl r0.z, r2.w, l(31) + and r8.xyz, r8.xyzx, l(2048, 4096, 0x40000000, 0) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + ishl r8.x, r4.x, l(13) + ishl r8.y, r4.y, l(23) + and r2.zw, r8.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.y, r0.y, r2.z + ishr r2.z, r4.x, l(1) + ishr r4.z, r4.x, l(2) + ishr r4.w, r4.x, l(3) + ishr r6.z, r4.x, l(4) + ishl r9.x, r2.z, l(14) + ishl r9.y, r4.z, l(15) + ishl r9.z, r4.w, l(16) + ishl r9.w, r6.z, l(17) + and r9.xyzw, r9.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r2.z, r4.x, l(5) + ishr r4.z, r4.y, l(1) + ishr r4.w, r4.y, l(2) + ishr r6.z, r4.y, l(3) + ishl r9.x, r2.z, l(18) + ishl r9.y, r4.z, l(24) + ishl r9.z, r4.w, l(25) + ishl r9.w, r6.z, l(26) + and r9.xyzw, r9.xyzw, l(0x00040000, 0x01000000, 0x02000000, 0x04000000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r0.w, r0.y + iadd r0.y, r8.w, r0.y + ishr r4.zw, r6.xxxy, l(2) + ishr r0.w, r6.x, l(3) + ishr r2.z, r6.y, l(1) + ishl r10.x, r4.z, l(21) + ishl r10.y, r0.w, l(22) + ishl r10.z, r2.z, l(28) + ishl r10.w, r4.w, l(6) + and r10.xyzw, r10.xyzw, l(0x00200000, 0x00400000, 0x10000000, 64) + iadd r0.y, r0.y, r10.x + iadd r0.y, r10.y, r0.y + iadd r0.y, r2.w, r0.y + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.w, r4.y, l(4) + ishl r0.w, r0.w, l(27) + and r0.w, r0.w, l(0x08000000) + iadd r0.y, r0.w, r0.y + iadd r0.y, r10.z, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r3.z, r0.z, r0.y + ishr r0.yz, r5.zzxz, l(3) + ishr r0.w, r5.x, l(1) + ishr r2.z, r5.x, l(2) + and r0.y, r0.y, l(1) + iadd r0.y, r0.y, r3.w + iadd r0.y, r7.z, r0.y + ishl r7.x, r0.w, l(2) + ishl r7.y, r2.z, l(3) + ishl r7.z, r0.z, l(4) + and r7.xyz, r7.xyzx, l(4, 8, 16, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r5.x, l(4) + ishr r0.w, r5.w, l(1) + ishr r2.z, r5.w, l(2) + ishr r2.w, r5.w, l(3) + ishl r8.x, r0.z, l(5) + ishl r8.y, r0.w, l(8) + ishl r8.z, r2.z, l(9) + ishl r8.w, r2.w, l(10) + and r8.xyzw, r8.xyzw, l(32, 256, 512, 1024) + iadd r0.y, r0.y, r8.x + iadd r0.y, r10.w, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r5.w, l(4) + ishl r0.z, r0.z, l(11) + and r0.z, r0.z, l(2048) + iadd r0.y, r0.z, r0.y + ishr r0.z, r6.y, l(3) + ishl r0.z, r0.z, l(12) + and r0.z, r0.z, l(4096) + iadd r0.y, r0.z, r0.y + ishl r0.z, r2.y, l(13) + and r0.z, r0.z, l(8192) + iadd r0.y, r0.z, r0.y + ushr r0.z, r2.y, l(1) + ushr r0.w, r2.y, l(2) + ushr r2.z, r2.y, l(3) + ushr r2.w, r2.y, l(4) + ishl r7.x, r0.z, l(14) + ishl r7.y, r0.w, l(15) + ishl r7.z, r2.z, l(16) + ishl r7.w, r2.w, l(17) + and r7.xyzw, r7.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.w, r7.w, r0.y + else + ieq r0.y, r2.x, l(9) + if_nz r0.y + ishl r7.x, r1.x, l(5) + ishl r7.y, r1.y, l(15) + ishl r7.z, r1.z, l(25) + ishl r7.w, r1.w, l(3) + and r7.xyzw, r7.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.y, r7.x, l(26) + ishr r0.z, r1.x, l(1) + ishr r0.w, r1.x, l(2) + ishr r2.z, r1.x, l(3) + ishr r2.w, r1.x, l(4) + ishl r8.x, r0.z, l(6) + ishl r8.y, r0.w, l(7) + ishl r8.z, r2.z, l(8) + ishl r8.w, r2.w, l(9) + and r8.xyzw, r8.xyzw, l(64, 128, 256, 512) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.x, l(5) + ishr r0.w, r1.x, l(6) + ishr r2.z, r1.x, l(7) + ishr r2.w, r1.y, l(1) + ishl r8.x, r0.z, l(10) + ishl r8.y, r0.w, l(11) + ishl r8.z, r2.z, l(12) + ishl r8.w, r2.w, l(16) + and r8.xyzw, r8.xyzw, l(1024, 2048, 4096, 0x00010000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + ishr r0.z, r6.y, l(1) + ishr r0.w, r6.y, l(5) + ishr r2.zw, r6.yyyx, l(4) + ishl r9.x, r0.z, l(13) + ishl r9.y, r0.w, l(1) + ishl r9.z, r2.z, l(2) + ishl r9.w, r2.w, l(8) + and r9.xyzw, r9.xyzw, l(8192, 2, 4, 256) + iadd r0.y, r0.y, r9.x + ishr r0.zw, r5.zzzy, l(4) + ishr r2.z, r5.z, l(5) + ishr r2.w, r5.y, l(1) + ishl r10.x, r0.z, l(14) + ishl r10.y, r2.z, l(23) + ishl r10.z, r0.w, l(24) + ishl r10.w, r2.w, l(10) + and r10.xyzw, r10.xyzw, l(0x00004000, 0x00800000, 0x01000000, 1024) + iadd r0.y, r0.y, r10.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(2) + ishr r0.w, r1.y, l(3) + ishr r2.z, r1.y, l(4) + ishr r2.w, r1.y, l(5) + ishl r8.x, r0.z, l(17) + ishl r8.y, r0.w, l(18) + ishl r8.z, r2.z, l(19) + ishl r8.w, r2.w, l(20) + and r8.xyzw, r8.xyzw, l(0x00020000, 0x00040000, 0x00080000, 0x00100000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.y, l(6) + ishr r0.w, r1.y, l(7) + ishr r2.z, r1.z, l(1) + ishr r2.w, r1.z, l(2) + ishl r8.x, r0.z, l(21) + ishl r8.y, r0.w, l(22) + ishl r8.z, r2.z, l(26) + ishl r8.w, r2.w, l(27) + and r8.xyzw, r8.xyzw, l(0x00200000, 0x00400000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r10.y, r0.y + iadd r0.y, r10.z, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.z, l(3) + ishr r0.w, r1.z, l(4) + ishr r2.z, r1.z, l(5) + ishr r2.w, r1.z, l(6) + ishl r7.x, r0.z, l(28) + ishl r7.y, r0.w, l(29) + ishl r7.z, r2.z, l(30) + ishl r0.z, r2.w, l(31) + and r7.xyz, r7.xyzx, l(0x10000000, 0x20000000, 0x40000000, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.x, r0.z, r0.y + ishr r0.y, r1.z, l(7) + ishr r0.z, r1.w, l(1) + ishr r0.w, r1.w, l(2) + ishr r2.z, r1.w, l(3) + and r0.y, r0.y, l(1) + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r7.w, r0.y + ishl r7.x, r0.z, l(4) + ishl r7.y, r0.w, l(5) + ishl r7.z, r2.z, l(6) + and r7.xyz, r7.xyzx, l(16, 32, 64, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r1.w, l(4) + ishl r0.z, r0.z, l(7) + and r0.z, r0.z, l(128) + iadd r0.y, r0.z, r0.y + iadd r0.y, r9.w, r0.y + ishl r7.x, r5.y, l(9) + ishl r7.y, r5.z, l(29) + ishl r7.z, r5.x, l(1) + ishl r7.w, r5.w, l(7) + and r7.xyzw, r7.xyzw, l(512, 0x20000000, 2, 128) + iadd r0.y, r0.y, r7.x + iadd r0.y, r10.w, r0.y + ishr r0.zw, r5.yyyz, l(2) + ishr r2.z, r5.y, l(3) + ishr r2.w, r5.z, l(1) + ishl r8.x, r0.z, l(11) + ishl r8.y, r2.z, l(12) + ishl r8.z, r2.w, l(30) + ishl r0.z, r0.w, l(31) + and r8.xyz, r8.xyzx, l(2048, 4096, 0x40000000, 0) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + ishl r8.x, r4.x, l(13) + ishl r8.y, r4.y, l(23) + and r2.zw, r8.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.y, r0.y, r2.z + ishr r0.w, r4.x, l(1) + ishr r2.z, r4.x, l(2) + ishr r4.z, r4.x, l(3) + ishr r4.w, r4.x, l(4) + ishl r9.x, r0.w, l(14) + ishl r9.y, r2.z, l(15) + ishl r9.z, r4.z, l(16) + ishl r9.w, r4.w, l(17) + and r9.xyzw, r9.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishl r8.x, r6.y, l(18) + ishl r8.y, r6.x, l(19) + and r4.zw, r8.xxxy, l(0, 0, 0x00040000, 0x00080000) + iadd r0.y, r0.y, r4.z + iadd r0.y, r4.w, r0.y + ishr r0.w, r6.x, l(1) + ishr r4.zw, r6.xxxy, l(2) + ishr r2.z, r6.x, l(3) + ishl r9.x, r0.w, l(20) + ishl r9.y, r4.z, l(21) + ishl r9.z, r2.z, l(22) + ishl r9.w, r4.w, l(6) + and r9.xyzw, r9.xyzw, l(0x00100000, 0x00200000, 0x00400000, 64) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r2.w, r0.y + ishr r0.w, r4.y, l(1) + ishr r2.z, r4.y, l(2) + ishr r2.w, r4.y, l(3) + ishr r4.z, r4.y, l(4) + ishl r10.x, r0.w, l(24) + ishl r10.y, r2.z, l(25) + ishl r10.z, r2.w, l(26) + ishl r10.w, r4.z, l(27) + and r10.xyzw, r10.xyzw, l(0x01000000, 0x02000000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r10.x + iadd r0.y, r10.y, r0.y + iadd r0.y, r10.z, r0.y + iadd r0.y, r10.w, r0.y + ishr r0.w, r4.y, l(5) + ishl r0.w, r0.w, l(28) + and r0.w, r0.w, l(0x10000000) + iadd r0.y, r0.w, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r3.z, r0.z, r0.y + ishr r0.yz, r5.zzxz, l(3) + ishr r0.w, r5.x, l(1) + ishr r2.z, r5.x, l(2) + and r0.y, r0.y, l(1) + iadd r0.y, r0.y, r3.w + iadd r0.y, r7.z, r0.y + ishl r7.x, r0.w, l(2) + ishl r7.y, r2.z, l(3) + ishl r7.z, r0.z, l(4) + and r7.xyz, r7.xyzx, l(4, 8, 16, 0) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + ishr r0.z, r5.x, l(4) + ishr r0.w, r5.w, l(1) + ishr r2.z, r5.w, l(2) + ishr r2.w, r5.w, l(3) + ishl r8.x, r0.z, l(5) + ishl r8.y, r0.w, l(8) + ishl r8.z, r2.z, l(9) + ishl r8.w, r2.w, l(10) + and r8.xyzw, r8.xyzw, l(32, 256, 512, 1024) + iadd r0.y, r0.y, r8.x + iadd r0.y, r9.w, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r5.w, l(4) + ishl r0.z, r0.z, l(11) + and r0.z, r0.z, l(2048) + iadd r0.y, r0.z, r0.y + ishr r0.z, r6.y, l(3) + ishl r0.z, r0.z, l(12) + and r0.z, r0.z, l(4096) + iadd r0.y, r0.z, r0.y + ishl r0.z, r2.y, l(13) + and r0.z, r0.z, l(8192) + iadd r0.y, r0.z, r0.y + ushr r0.z, r2.y, l(1) + ushr r0.w, r2.y, l(2) + ushr r2.z, r2.y, l(3) + ushr r2.w, r2.y, l(4) + ishl r7.x, r0.z, l(14) + ishl r7.y, r0.w, l(15) + ishl r7.z, r2.z, l(16) + ishl r7.w, r2.w, l(17) + and r7.xyzw, r7.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r3.w, r7.w, r0.y + else + ieq r0.y, r2.x, l(10) + if_nz r0.y + ishl r7.x, r1.x, l(5) + ishl r7.y, r1.y, l(15) + ishl r7.z, r1.z, l(25) + ishl r7.w, r1.w, l(3) + and r7.xyzw, r7.xyzw, l(32, 0x00008000, 0x02000000, 8) + iadd r0.y, r7.x, l(30) + ishr r0.z, r1.x, l(1) + ishr r0.w, r1.x, l(2) + ishr r2.x, r1.x, l(3) + ishr r2.z, r1.x, l(4) + ishl r8.x, r0.z, l(6) + ishl r8.y, r0.w, l(7) + ishl r8.z, r2.x, l(8) + ishl r8.w, r2.z, l(9) + and r8.xyzw, r8.xyzw, l(64, 128, 256, 512) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.x, l(5) + ishr r0.w, r1.y, l(1) + ishr r1.x, r1.y, l(2) + ishr r2.x, r1.y, l(3) + ishl r8.x, r0.z, l(10) + ishl r8.y, r0.w, l(16) + ishl r8.z, r1.x, l(17) + ishl r8.w, r2.x, l(18) + and r8.xyzw, r8.xyzw, l(1024, 0x00010000, 0x00020000, 0x00040000) + iadd r0.y, r0.y, r8.x + ishr r0.z, r6.x, l(4) + ishr r0.w, r6.y, l(1) + ishr r1.x, r6.y, l(2) + ishr r2.x, r6.x, l(5) + ishl r9.x, r0.z, l(11) + ishl r9.y, r0.w, l(13) + ishl r9.z, r1.x, l(23) + ishl r0.z, r2.x, l(31) + and r2.xzw, r9.xxyz, l(2048, 0, 8192, 0x00800000) + iadd r0.y, r0.y, r2.x + ishl r9.x, r6.y, l(12) + ishl r9.y, r6.x, l(19) + and r4.zw, r9.xxxy, l(0, 0, 4096, 0x00080000) + iadd r0.y, r0.y, r4.z + iadd r0.y, r2.z, r0.y + ishr r2.xz, r5.zzyz, l(4) + ishr r6.zw, r5.yyyz, l(5) + ishl r9.x, r2.x, l(14) + ishl r9.y, r6.z, l(21) + ishl r9.z, r6.w, l(22) + ishl r9.w, r2.z, l(24) + and r9.xyzw, r9.xyzw, l(0x00004000, 0x00200000, 0x00400000, 0x01000000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.w, r1.y, l(4) + ishr r1.x, r1.y, l(5) + ishr r1.y, r1.z, l(1) + ishr r2.x, r1.z, l(2) + ishl r8.x, r0.w, l(19) + ishl r8.y, r1.x, l(20) + ishl r8.z, r1.y, l(26) + ishl r8.w, r2.x, l(27) + and r8.xyzw, r8.xyzw, l(0x00080000, 0x00100000, 0x04000000, 0x08000000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r2.w, r0.y + iadd r0.y, r9.w, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r8.z, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.w, r1.z, l(3) + ishr r1.x, r1.z, l(4) + ishr r1.y, r1.z, l(5) + ishr r1.z, r1.w, l(1) + ishl r8.x, r0.w, l(28) + ishl r8.y, r1.x, l(29) + ishl r8.z, r1.y, l(30) + ishl r8.w, r1.z, l(4) + and r8.xyzw, r8.xyzw, l(0x10000000, 0x20000000, 0x40000000, 16) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + iadd r3.x, r0.z, r0.y + ishr r0.y, r6.y, l(3) + ishr r0.z, r6.y, l(5) + ishr r0.w, r6.y, l(4) + ishr r1.x, r6.x, l(1) + and r0.y, r0.y, l(1) + ishl r7.x, r0.z, l(1) + ishl r7.y, r0.w, l(2) + ishl r7.z, r1.x, l(20) + and r1.xyz, r7.xyzx, l(2, 4, 0x00100000, 0) + iadd r0.y, r0.y, r1.x + iadd r0.y, r1.y, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.z, r1.w, l(2) + ishr r0.w, r1.w, l(3) + ishr r1.x, r1.w, l(4) + ishr r1.y, r1.w, l(5) + ishl r7.x, r0.z, l(5) + ishl r7.y, r0.w, l(6) + ishl r7.z, r1.x, l(7) + ishl r7.w, r1.y, l(8) + and r7.xyzw, r7.xyzw, l(32, 64, 128, 256) + iadd r0.y, r0.y, r7.x + iadd r0.y, r7.y, r0.y + iadd r0.y, r7.z, r0.y + iadd r0.y, r7.w, r0.y + ishl r7.x, r5.y, l(9) + ishl r7.y, r5.z, l(29) + ishl r7.z, r5.x, l(1) + ishl r7.w, r5.w, l(7) + and r7.xyzw, r7.xyzw, l(512, 0x20000000, 2, 128) + iadd r0.y, r0.y, r7.x + ishr r0.zw, r5.yyyz, l(1) + ishr r1.x, r5.y, l(2) + ishr r1.y, r5.y, l(3) + ishl r8.x, r0.z, l(10) + ishl r8.y, r1.x, l(11) + ishl r8.z, r1.y, l(12) + ishl r8.w, r0.w, l(30) + and r8.xyzw, r8.xyzw, l(1024, 2048, 4096, 0x40000000) + iadd r0.y, r0.y, r8.x + iadd r0.y, r8.y, r0.y + iadd r0.y, r8.z, r0.y + ishl r1.x, r4.x, l(13) + ishl r1.y, r4.y, l(23) + and r0.zw, r1.xxxy, l(0, 0, 8192, 0x00800000) + iadd r0.y, r0.z, r0.y + ishr r0.z, r4.x, l(1) + ishr r1.x, r4.x, l(2) + ishr r1.y, r4.x, l(3) + ishr r1.w, r4.x, l(4) + ishl r9.x, r0.z, l(14) + ishl r9.y, r1.x, l(15) + ishl r9.z, r1.y, l(16) + ishl r9.w, r1.w, l(17) + and r9.xyzw, r9.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.z, r4.x, l(5) + ishr r1.x, r4.y, l(1) + ishr r1.y, r4.y, l(2) + ishr r1.w, r4.y, l(3) + ishl r9.x, r0.z, l(18) + ishl r9.y, r1.x, l(24) + ishl r9.z, r1.y, l(25) + ishl r9.w, r1.w, l(26) + and r9.xyzw, r9.xyzw, l(0x00040000, 0x01000000, 0x02000000, 0x04000000) + iadd r0.y, r0.y, r9.x + iadd r0.y, r4.w, r0.y + iadd r0.y, r1.z, r0.y + ishr r0.z, r6.x, l(2) + ishr r1.x, r6.x, l(3) + ishl r6.x, r0.z, l(21) + ishl r6.y, r1.x, l(22) + and r1.xy, r6.xyxx, l(0x00200000, 0x00400000, 0, 0) + iadd r0.y, r0.y, r1.x + iadd r0.y, r1.y, r0.y + iadd r0.y, r0.w, r0.y + iadd r0.y, r9.y, r0.y + iadd r0.y, r9.z, r0.y + iadd r0.y, r9.w, r0.y + ishr r0.z, r4.y, l(4) + ishr r0.w, r4.y, l(5) + ishl r1.x, r0.z, l(27) + ishl r1.y, r0.w, l(28) + and r0.zw, r1.xxxy, l(0, 0, 0x08000000, 0x10000000) + iadd r0.y, r0.z, r0.y + iadd r0.y, r0.w, r0.y + iadd r0.y, r7.y, r0.y + iadd r0.y, r8.w, r0.y + ishr r0.zw, r5.zzzx, l(2) + ishr r1.x, r5.z, l(3) + ishr r1.y, r5.x, l(1) + ishl r4.x, r0.z, l(31) + ishl r4.y, r1.y, l(2) + ishl r4.z, r0.w, l(3) + iadd r3.z, r0.y, r4.x + and r0.y, r1.x, l(1) + iadd r0.y, r0.y, r3.w + iadd r0.y, r7.z, r0.y + and r0.zw, r4.yyyz, l(0, 0, 4, 8) + iadd r0.y, r0.z, r0.y + iadd r0.y, r0.w, r0.y + ishr r0.z, r5.x, l(3) + ishr r0.w, r5.x, l(4) + ishr r1.x, r5.x, l(5) + ishr r1.y, r5.w, l(1) + ishl r4.x, r0.z, l(4) + ishl r4.y, r0.w, l(5) + ishl r4.z, r1.x, l(6) + ishl r4.w, r1.y, l(8) + and r1.xyzw, r4.xyzw, l(16, 32, 64, 256) + iadd r0.y, r0.y, r1.x + iadd r0.y, r1.y, r0.y + iadd r0.y, r1.z, r0.y + iadd r0.y, r7.w, r0.y + iadd r0.y, r1.w, r0.y + ishr r0.z, r5.w, l(2) + ishr r0.w, r5.w, l(3) + ishr r1.x, r5.w, l(4) + ishr r1.y, r5.w, l(5) + ishl r4.x, r0.z, l(9) + ishl r4.y, r0.w, l(10) + ishl r4.z, r1.x, l(11) + ishl r4.w, r1.y, l(12) + and r1.xyzw, r4.xyzw, l(512, 1024, 2048, 4096) + iadd r0.y, r0.y, r1.x + iadd r0.y, r1.y, r0.y + iadd r0.y, r1.z, r0.y + iadd r0.y, r1.w, r0.y + ishl r0.z, r2.y, l(13) + and r0.z, r0.z, l(8192) + iadd r0.y, r0.z, r0.y + ushr r0.z, r2.y, l(1) + ushr r0.w, r2.y, l(2) + ushr r1.x, r2.y, l(3) + ushr r1.y, r2.y, l(4) + ishl r2.x, r0.z, l(14) + ishl r2.y, r0.w, l(15) + ishl r2.z, r1.x, l(16) + ishl r2.w, r1.y, l(17) + and r1.xyzw, r2.xyzw, l(0x00004000, 0x00008000, 0x00010000, 0x00020000) + iadd r0.y, r0.y, r1.x + iadd r0.y, r1.y, r0.y + iadd r0.y, r1.z, r0.y + iadd r3.w, r1.w, r0.y + else + mov r3.xz, l(0,0,0,0) + endif + endif + endif + endif + endif + endif + endif + endif + endif + endif + endif + store_structured u0.xyzw, r0.x, l(0), r3.xzwy +endif +ret +// Approximately 0 instruction slots used +#endif + +const BYTE BC6HEncode_EncodeBlockCS[] = +{ + 68, 88, 66, 67, 106, 242, + 47, 44, 29, 251, 192, 175, + 230, 64, 141, 23, 223, 196, + 86, 63, 1, 0, 0, 0, + 28, 173, 1, 0, 3, 0, + 0, 0, 44, 0, 0, 0, + 60, 0, 0, 0, 76, 0, + 0, 0, 73, 83, 71, 78, + 8, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 79, 83, 71, 78, 8, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 83, 72, + 69, 88, 200, 172, 1, 0, + 64, 0, 5, 0, 50, 107, + 0, 0, 106, 8, 0, 1, + 53, 24, 0, 0, 58, 1, + 0, 0, 204, 204, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 136, 136, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 238, 238, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 200, 236, 0, 0, + 15, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 128, 200, 0, 0, 15, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 236, 254, + 0, 0, 15, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 200, 254, 0, 0, + 15, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 128, 236, 0, 0, 15, 0, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 0, 0, 200, + 0, 0, 15, 0, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 0, 236, 255, 0, 0, + 15, 0, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 0, + 128, 254, 0, 0, 15, 0, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 0, 0, 232, + 0, 0, 15, 0, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 0, 232, 255, 0, 0, + 15, 0, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 0, + 0, 255, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 0, 240, 255, + 0, 0, 15, 0, 0, 0, + 3, 0, 0, 0, 2, 0, + 0, 0, 0, 240, 0, 0, + 15, 0, 0, 0, 3, 0, + 0, 0, 2, 0, 0, 0, + 16, 247, 0, 0, 15, 0, + 0, 0, 4, 0, 0, 0, + 2, 0, 0, 0, 142, 0, + 0, 0, 2, 0, 0, 0, + 4, 0, 0, 0, 2, 0, + 0, 0, 0, 113, 0, 0, + 8, 0, 0, 0, 4, 0, + 0, 0, 2, 0, 0, 0, + 206, 8, 0, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 2, 0, 0, 0, 140, 0, + 0, 0, 2, 0, 0, 0, + 5, 0, 0, 0, 2, 0, + 0, 0, 16, 115, 0, 0, + 8, 0, 0, 0, 5, 0, + 0, 0, 2, 0, 0, 0, + 0, 49, 0, 0, 8, 0, + 0, 0, 5, 0, 0, 0, + 2, 0, 0, 0, 206, 140, + 0, 0, 15, 0, 0, 0, + 5, 0, 0, 0, 3, 0, + 0, 0, 140, 8, 0, 0, + 2, 0, 0, 0, 6, 0, + 0, 0, 3, 0, 0, 0, + 16, 49, 0, 0, 8, 0, + 0, 0, 6, 0, 0, 0, + 3, 0, 0, 0, 102, 102, + 0, 0, 2, 0, 0, 0, + 6, 0, 0, 0, 3, 0, + 0, 0, 108, 54, 0, 0, + 2, 0, 0, 0, 6, 0, + 0, 0, 3, 0, 0, 0, + 232, 23, 0, 0, 8, 0, + 0, 0, 6, 0, 0, 0, + 3, 0, 0, 0, 240, 15, + 0, 0, 8, 0, 0, 0, + 7, 0, 0, 0, 3, 0, + 0, 0, 142, 113, 0, 0, + 2, 0, 0, 0, 7, 0, + 0, 0, 3, 0, 0, 0, + 156, 57, 0, 0, 2, 0, + 0, 0, 7, 0, 0, 0, + 3, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 7, 0, 0, 0, 3, 0, + 0, 0, 255, 255, 255, 255, + 0, 0, 0, 0, 8, 0, + 0, 0, 4, 0, 0, 0, + 255, 255, 255, 255, 0, 0, + 0, 0, 8, 0, 0, 0, + 4, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 8, 0, 0, 0, 4, 0, + 0, 0, 255, 255, 255, 255, + 0, 0, 0, 0, 8, 0, + 0, 0, 4, 0, 0, 0, + 255, 255, 255, 255, 0, 0, + 0, 0, 9, 0, 0, 0, + 4, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 9, 0, 0, 0, 4, 0, + 0, 0, 255, 255, 255, 255, + 0, 0, 0, 0, 9, 0, + 0, 0, 4, 0, 0, 0, + 255, 255, 255, 255, 0, 0, + 0, 0, 9, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 5, 0, 0, 0, + 255, 255, 255, 255, 0, 0, + 0, 0, 10, 0, 0, 0, + 5, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 10, 0, 0, 0, 5, 0, + 0, 0, 255, 255, 255, 255, + 0, 0, 0, 0, 10, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 11, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 11, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 11, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 11, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 12, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 12, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 12, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 12, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 13, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 13, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 13, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 13, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 14, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 14, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 14, 0, + 0, 0, 7, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 14, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 7, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 7, 0, 0, 0, + 10, 0, 0, 0, 5, 0, + 0, 0, 5, 0, 0, 0, + 5, 0, 0, 0, 7, 0, + 0, 0, 6, 0, 0, 0, + 6, 0, 0, 0, 6, 0, + 0, 0, 11, 0, 0, 0, + 5, 0, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 11, 0, 0, 0, 4, 0, + 0, 0, 5, 0, 0, 0, + 4, 0, 0, 0, 11, 0, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 5, 0, + 0, 0, 9, 0, 0, 0, + 5, 0, 0, 0, 5, 0, + 0, 0, 5, 0, 0, 0, + 8, 0, 0, 0, 6, 0, + 0, 0, 5, 0, 0, 0, + 5, 0, 0, 0, 8, 0, + 0, 0, 5, 0, 0, 0, + 6, 0, 0, 0, 5, 0, + 0, 0, 8, 0, 0, 0, + 5, 0, 0, 0, 5, 0, + 0, 0, 6, 0, 0, 0, + 6, 0, 0, 0, 6, 0, + 0, 0, 6, 0, 0, 0, + 6, 0, 0, 0, 10, 0, + 0, 0, 10, 0, 0, 0, + 10, 0, 0, 0, 10, 0, + 0, 0, 11, 0, 0, 0, + 9, 0, 0, 0, 9, 0, + 0, 0, 9, 0, 0, 0, + 12, 0, 0, 0, 8, 0, + 0, 0, 8, 0, 0, 0, + 8, 0, 0, 0, 16, 0, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 89, 0, 0, 4, + 70, 142, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 88, 24, 0, 4, 0, 112, + 16, 0, 0, 0, 0, 0, + 85, 85, 0, 0, 162, 0, + 0, 4, 0, 112, 16, 0, + 1, 0, 0, 0, 16, 0, + 0, 0, 158, 0, 0, 4, + 0, 224, 17, 0, 0, 0, + 0, 0, 16, 0, 0, 0, + 95, 0, 0, 2, 0, 64, + 2, 0, 95, 0, 0, 2, + 18, 16, 2, 0, 104, 0, + 0, 2, 18, 0, 0, 0, + 160, 0, 0, 5, 0, 240, + 17, 0, 0, 0, 0, 0, + 84, 0, 0, 0, 64, 0, + 0, 0, 155, 0, 0, 4, + 64, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 6, 18, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 16, 2, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 8, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 128, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 128, 65, 0, + 0, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 79, 0, + 0, 10, 242, 0, 16, 0, + 1, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 2, 0, 0, 0, 8, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 1, 0, + 0, 0, 78, 0, 0, 9, + 130, 0, 16, 0, 0, 0, + 0, 0, 0, 208, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 26, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 35, 0, 0, 11, + 18, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 128, + 65, 0, 0, 0, 0, 0, + 0, 0, 26, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 85, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 8, 194, 0, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 45, 0, 0, 7, 242, 0, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 2, 0, + 0, 0, 70, 126, 16, 0, + 0, 0, 0, 0, 16, 0, + 0, 10, 130, 0, 16, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 208, 179, + 89, 62, 89, 23, 55, 63, + 152, 221, 147, 61, 0, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 0, 128, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 4, 0, 0, 0, + 6, 5, 16, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 127, 255, 255, + 127, 0, 255, 255, 255, 127, + 255, 255, 127, 0, 79, 0, + 0, 10, 50, 0, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 255, 239, 255, 71, + 255, 239, 255, 71, 0, 0, + 0, 0, 0, 0, 0, 0, + 134, 0, 16, 0, 4, 0, + 0, 0, 79, 0, 0, 10, + 50, 0, 16, 0, 5, 0, + 0, 0, 134, 0, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 128, 56, + 0, 0, 128, 56, 0, 0, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 194, 0, + 16, 0, 5, 0, 0, 0, + 6, 8, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 30, 0, + 0, 11, 194, 0, 16, 0, + 5, 0, 0, 0, 166, 14, + 16, 128, 65, 0, 0, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 113, 0, + 0, 0, 113, 0, 0, 0, + 30, 0, 0, 10, 162, 0, + 16, 0, 4, 0, 0, 0, + 86, 13, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 128, 0, 0, 0, 0, 0, + 0, 0, 128, 0, 85, 0, + 0, 7, 18, 0, 16, 0, + 6, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 10, 50, 0, + 16, 0, 4, 0, 0, 0, + 134, 0, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 200, 0, 0, + 0, 200, 0, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 9, 50, 0, 16, 0, + 4, 0, 0, 0, 70, 0, + 16, 0, 5, 0, 0, 0, + 70, 0, 16, 0, 6, 0, + 0, 0, 70, 0, 16, 0, + 4, 0, 0, 0, 30, 0, + 0, 10, 194, 0, 16, 0, + 4, 0, 0, 0, 6, 4, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 255, 15, 0, 0, 255, 15, + 0, 0, 85, 0, 0, 7, + 50, 0, 16, 0, 4, 0, + 0, 0, 70, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 1, 0, 0, 10, 50, 0, + 16, 0, 4, 0, 0, 0, + 70, 0, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 50, 0, 16, 0, + 4, 0, 0, 0, 70, 0, + 16, 0, 4, 0, 0, 0, + 230, 10, 16, 0, 4, 0, + 0, 0, 85, 0, 0, 7, + 50, 0, 16, 0, 4, 0, + 0, 0, 70, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 1, 0, 0, 10, 50, 0, + 16, 0, 4, 0, 0, 0, + 70, 0, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 12, 50, 0, 16, 0, + 2, 0, 0, 0, 70, 0, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 70, 0, 16, 0, + 4, 0, 0, 0, 30, 0, + 0, 7, 50, 0, 16, 0, + 4, 0, 0, 0, 70, 0, + 16, 0, 3, 0, 0, 0, + 70, 0, 16, 0, 2, 0, + 0, 0, 1, 0, 0, 10, + 50, 0, 16, 0, 2, 0, + 0, 0, 166, 10, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 255, 255, 255, 127, + 255, 255, 127, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 79, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 255, 239, + 255, 71, 10, 0, 16, 0, + 2, 0, 0, 0, 79, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 128, 56, 85, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 30, 0, 0, 8, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 128, 65, 0, + 0, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 113, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 128, 0, + 85, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 200, 55, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 255, 15, 0, 0, + 85, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 85, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 255, 127, + 0, 0, 55, 0, 0, 9, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 255, 127, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 32, 0, 0, 8, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 95, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 78, 0, 0, 11, 114, 0, + 16, 0, 2, 0, 0, 0, + 0, 208, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 31, 0, + 0, 0, 31, 0, 0, 0, + 31, 0, 0, 0, 0, 0, + 0, 0, 79, 0, 0, 10, + 114, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 128, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 255, 123, 0, 0, 255, 123, + 0, 0, 255, 123, 0, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 78, 0, 0, 11, + 114, 0, 16, 0, 6, 0, + 0, 0, 0, 208, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 31, 0, 0, 0, 31, 0, + 0, 0, 31, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 224, 255, + 15, 0, 224, 255, 15, 0, + 224, 255, 15, 0, 0, 0, + 0, 0, 78, 0, 0, 11, + 114, 0, 16, 0, 4, 0, + 0, 0, 0, 208, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 31, 0, 0, 0, 31, 0, + 0, 0, 31, 0, 0, 0, + 0, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 1, 128, 255, 255, 1, 128, + 255, 255, 1, 128, 255, 255, + 0, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 2, 0, 0, 0, + 246, 15, 16, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 21, 0, 0, 1, + 190, 24, 0, 1, 167, 0, + 0, 9, 50, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 70, 112, 16, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 130, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 31, 0, 4, 3, 10, 0, + 16, 0, 1, 0, 0, 0, + 79, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 242, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 5, 242, 0, + 16, 0, 5, 0, 0, 0, + 150, 15, 16, 0, 3, 0, + 0, 0, 18, 0, 0, 1, + 85, 0, 0, 8, 34, 0, + 16, 0, 1, 0, 0, 0, + 10, 144, 144, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 55, 0, 0, 12, 242, 0, + 16, 0, 4, 0, 0, 0, + 86, 5, 16, 0, 1, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 127, 255, 255, + 255, 127, 255, 255, 255, 127, + 0, 0, 0, 128, 70, 2, + 16, 0, 3, 0, 0, 0, + 55, 0, 0, 12, 242, 0, + 16, 0, 5, 0, 0, 0, + 86, 5, 16, 0, 1, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 128, 0, 0, + 0, 128, 255, 255, 127, 127, + 255, 255, 127, 255, 150, 15, + 16, 0, 3, 0, 0, 0, + 21, 0, 0, 1, 18, 0, + 0, 1, 80, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 1, 0, 0, 0, + 85, 0, 0, 8, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 144, 144, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 32, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 55, 0, + 0, 12, 242, 0, 16, 0, + 4, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 127, 255, 255, + 255, 127, 255, 255, 255, 127, + 0, 0, 0, 128, 55, 0, + 0, 12, 242, 0, 16, 0, + 5, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 150, 15, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 128, 0, 0, + 0, 128, 255, 255, 127, 127, + 255, 255, 127, 255, 18, 0, + 0, 1, 54, 0, 0, 8, + 242, 0, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 127, 255, 255, + 255, 127, 255, 255, 255, 127, + 0, 0, 0, 128, 54, 0, + 0, 8, 242, 0, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 128, + 0, 0, 0, 128, 255, 255, + 127, 127, 255, 255, 127, 255, + 21, 0, 0, 1, 21, 0, + 0, 1, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 68, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 21, 0, 0, 1, 190, 24, + 0, 1, 1, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 79, 0, 0, 10, 242, 0, + 16, 0, 3, 0, 0, 0, + 246, 15, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 8, 0, 0, 0, 4, 0, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 10, 0, 16, 0, + 3, 0, 0, 0, 167, 0, + 0, 8, 18, 0, 16, 0, + 4, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 49, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 114, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 76, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 21, 0, 0, 1, + 167, 0, 0, 8, 18, 0, + 16, 0, 4, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 80, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 80, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 49, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 80, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 190, 24, 0, 1, 31, 0, + 4, 3, 26, 0, 16, 0, + 3, 0, 0, 0, 167, 0, + 0, 8, 18, 0, 16, 0, + 4, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 49, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 114, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 76, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 21, 0, 0, 1, + 167, 0, 0, 8, 18, 0, + 16, 0, 4, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 80, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 80, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 49, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 80, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 190, 24, 0, 1, 31, 0, + 4, 3, 42, 0, 16, 0, + 3, 0, 0, 0, 167, 0, + 0, 8, 18, 0, 16, 0, + 4, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 49, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 114, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 76, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 21, 0, 0, 1, + 167, 0, 0, 8, 18, 0, + 16, 0, 4, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 80, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 80, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 49, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 80, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 190, 24, 0, 1, 31, 0, + 4, 3, 58, 0, 16, 0, + 3, 0, 0, 0, 167, 0, + 0, 8, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 49, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 114, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 21, 0, 0, 1, 167, 0, + 0, 8, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 80, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 80, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 49, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 64, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 114, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 21, 0, 0, 1, 21, 0, + 0, 1, 190, 24, 0, 1, + 31, 0, 4, 3, 42, 0, + 16, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 32, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 80, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 31, 0, 4, 3, + 58, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 144, 144, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 18, 0, 0, 1, + 54, 0, 0, 5, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 21, 0, 0, 1, + 30, 0, 0, 8, 114, 0, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 128, 65, 0, + 0, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 43, 0, 0, 5, + 114, 0, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 16, 0, + 0, 7, 34, 0, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 8, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 128, 65, 0, + 0, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 43, 0, 0, 5, + 114, 0, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 16, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 49, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 29, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 56, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 253, 255, 125, 66, + 14, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 28, 0, + 0, 5, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 79, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 5, 0, 0, 0, + 246, 15, 16, 0, 0, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 55, 0, 0, 9, 194, 0, + 16, 0, 2, 0, 0, 0, + 246, 15, 16, 0, 0, 0, + 0, 0, 86, 9, 16, 0, + 3, 0, 0, 0, 86, 9, + 16, 0, 4, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 168, 0, 0, 8, + 50, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 68, 0, + 0, 0, 230, 10, 16, 0, + 2, 0, 0, 0, 21, 0, + 0, 1, 190, 24, 0, 1, + 31, 0, 4, 3, 10, 0, + 16, 0, 1, 0, 0, 0, + 79, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 31, 0, + 4, 3, 58, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 18, 0, 0, 1, 54, 0, + 0, 6, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 144, + 144, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 21, 0, + 0, 1, 85, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 10, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 8, + 114, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 128, 65, 0, 0, 0, + 4, 0, 0, 0, 43, 0, + 0, 5, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 167, 0, 0, 8, 114, 0, + 16, 0, 5, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 8, + 114, 0, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 128, + 65, 0, 0, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 43, 0, + 0, 5, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 16, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 18, 0, + 0, 1, 167, 0, 0, 9, + 114, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 8, + 114, 0, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 128, 65, 0, 0, 0, + 5, 0, 0, 0, 43, 0, + 0, 5, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 167, 0, 0, 8, 114, 0, + 16, 0, 4, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 8, + 114, 0, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 128, + 65, 0, 0, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 43, 0, + 0, 5, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 16, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 21, 0, + 0, 1, 16, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 0, 0, 0, 0, + 29, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 29, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 60, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 49, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 56, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 253, 255, + 125, 66, 14, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 28, 0, 0, 5, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 55, 0, 0, 10, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 42, 144, + 144, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 79, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 224, 255, + 255, 255, 41, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 54, 0, 0, 8, 98, 0, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 55, 0, 0, 9, + 194, 0, 16, 0, 2, 0, + 0, 0, 166, 10, 16, 0, + 2, 0, 0, 0, 6, 4, + 16, 0, 4, 0, 0, 0, + 166, 14, 16, 0, 4, 0, + 0, 0, 54, 0, 0, 5, + 34, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 9, 50, 0, 16, 0, + 3, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 230, 10, 16, 0, 2, 0, + 0, 0, 70, 0, 16, 0, + 3, 0, 0, 0, 18, 0, + 0, 1, 29, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 29, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 49, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 56, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 253, 255, 125, 66, 14, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 28, 0, 0, 5, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 55, 0, + 0, 10, 18, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 58, 144, 144, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 55, 0, 0, 9, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 31, 0, 0, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 18, 0, 0, 0, + 54, 0, 0, 5, 34, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 18, 0, 0, 1, + 79, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 31, 0, + 4, 3, 10, 0, 16, 0, + 1, 0, 0, 0, 35, 0, + 0, 9, 18, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 54, 0, 0, 5, + 34, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 18, 0, + 0, 1, 39, 0, 0, 8, + 18, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 26, 144, + 144, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 32, 0, + 0, 8, 34, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 26, 144, 144, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 2, 0, 0, 0, + 6, 4, 16, 0, 1, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 79, 0, + 0, 7, 34, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 1, 0, + 0, 0, 35, 0, 0, 9, + 34, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 18, 0, 0, 1, 32, 0, + 0, 7, 34, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 55, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 55, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 79, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 35, 0, 0, 12, + 194, 0, 16, 0, 2, 0, + 0, 0, 166, 10, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 3, 0, 0, 0, + 166, 14, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 10, + 194, 0, 16, 0, 2, 0, + 0, 0, 166, 14, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 240, 255, + 255, 255, 240, 255, 255, 255, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 55, 0, 0, 9, + 34, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 9, 50, 0, 16, 0, + 3, 0, 0, 0, 86, 5, + 16, 0, 1, 0, 0, 0, + 70, 0, 16, 0, 4, 0, + 0, 0, 70, 0, 16, 0, + 5, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 21, 0, 0, 1, 21, 0, + 0, 1, 168, 0, 0, 8, + 50, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 70, 0, 16, 0, + 3, 0, 0, 0, 18, 0, + 0, 1, 54, 0, 0, 8, + 50, 0, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 21, 0, + 0, 1, 190, 24, 0, 1, + 31, 0, 4, 3, 58, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 8, 50, 0, + 16, 0, 4, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 50, 0, 16, 0, 1, 0, + 0, 0, 70, 0, 16, 0, + 4, 0, 0, 0, 70, 0, + 16, 0, 5, 0, 0, 0, + 168, 0, 0, 8, 50, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 70, 0, 16, 0, 1, 0, + 0, 0, 21, 0, 0, 1, + 190, 24, 0, 1, 79, 0, + 0, 10, 50, 0, 16, 0, + 1, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 4, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 8, + 50, 0, 16, 0, 4, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 146, 0, 16, 0, + 1, 0, 0, 0, 6, 4, + 16, 0, 4, 0, 0, 0, + 6, 4, 16, 0, 5, 0, + 0, 0, 168, 0, 0, 8, + 50, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 198, 0, 16, 0, + 1, 0, 0, 0, 21, 0, + 0, 1, 190, 24, 0, 1, + 31, 0, 4, 3, 42, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 8, 50, 0, + 16, 0, 4, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 146, 0, 16, 0, 1, 0, + 0, 0, 6, 4, 16, 0, + 4, 0, 0, 0, 6, 4, + 16, 0, 5, 0, 0, 0, + 168, 0, 0, 8, 50, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 198, 0, 16, 0, 1, 0, + 0, 0, 21, 0, 0, 1, + 190, 24, 0, 1, 31, 0, + 4, 3, 26, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 8, 50, 0, 16, 0, + 4, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 50, 0, + 16, 0, 3, 0, 0, 0, + 70, 0, 16, 0, 4, 0, + 0, 0, 70, 0, 16, 0, + 5, 0, 0, 0, 21, 0, + 0, 1, 190, 24, 0, 1, + 30, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 32, 0, + 0, 10, 50, 0, 16, 0, + 1, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 2, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 32, 0, 0, 8, + 18, 0, 16, 0, 1, 0, + 0, 0, 42, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 95, 0, 0, 0, 31, 0, + 4, 3, 10, 0, 16, 0, + 1, 0, 0, 0, 33, 0, + 0, 9, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 144, + 208, 0, 64, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 1, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 55, 0, 0, 15, + 114, 0, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 55, 0, 0, 15, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 114, 0, 16, 0, 6, 0, + 0, 0, 6, 0, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 60, 0, 0, 7, 114, 0, + 16, 0, 7, 0, 0, 0, + 6, 0, 16, 0, 1, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 32, 0, + 0, 10, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 0, 0, + 0, 0, 32, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 255, 255, + 0, 0, 0, 0, 0, 0, + 41, 0, 0, 9, 18, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 10, 144, 208, 0, + 64, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 41, 0, + 0, 9, 114, 0, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 10, 144, 208, 0, 64, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 9, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 10, 144, 208, 0, 64, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 6, 0, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 6, 0, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 18, 0, 0, 1, 33, 0, + 0, 9, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 144, + 208, 0, 64, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 1, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 55, 0, 0, 15, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 55, 0, 0, 15, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 114, 0, 16, 0, 8, 0, + 0, 0, 6, 0, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 60, 0, 0, 7, 114, 0, + 16, 0, 9, 0, 0, 0, + 6, 0, 16, 0, 1, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 33, 0, + 0, 10, 114, 0, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 33, 0, 0, 10, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 32, 0, + 0, 10, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 9, + 18, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 10, 144, + 208, 0, 64, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 41, 0, + 0, 7, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 166, 10, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 166, 10, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 15, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 16, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 32, 0, + 0, 10, 114, 0, 16, 0, + 17, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 8, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 128, + 65, 0, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 246, 15, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 17, 0, + 0, 0, 246, 15, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 21, 0, 0, 1, 30, 0, + 0, 8, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 128, 65, 0, 0, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 55, 0, 0, 11, 114, 0, + 16, 0, 4, 0, 0, 0, + 6, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 168, 0, 0, 8, 50, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 150, 5, 16, 0, 4, 0, + 0, 0, 21, 0, 0, 1, + 190, 24, 0, 1, 31, 0, + 4, 3, 26, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 10, 50, 0, 16, 0, + 1, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 6, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 80, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 31, 0, 4, 3, 10, 0, + 16, 0, 1, 0, 0, 0, + 32, 0, 0, 8, 18, 0, + 16, 0, 1, 0, 0, 0, + 42, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 95, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 1, 0, + 0, 0, 33, 0, 0, 9, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 144, 208, 0, + 64, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 1, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 55, 0, 0, 15, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 15, 114, 0, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 114, 0, + 16, 0, 7, 0, 0, 0, + 6, 0, 16, 0, 1, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 60, 0, + 0, 7, 178, 0, 16, 0, + 1, 0, 0, 0, 6, 0, + 16, 0, 1, 0, 0, 0, + 70, 8, 16, 0, 8, 0, + 0, 0, 32, 0, 0, 10, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 255, 255, + 0, 0, 0, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 0, 0, 255, 255, + 0, 0, 255, 255, 0, 0, + 0, 0, 0, 0, 41, 0, + 0, 9, 66, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 10, 144, 208, 0, 64, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 41, 0, 0, 9, + 114, 0, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 10, 144, + 208, 0, 64, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 9, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 10, 144, + 208, 0, 64, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 42, 0, 0, 7, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 166, 10, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 166, 10, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 55, 0, + 0, 9, 178, 0, 16, 0, + 1, 0, 0, 0, 70, 12, + 16, 0, 1, 0, 0, 0, + 70, 8, 16, 0, 6, 0, + 0, 0, 70, 8, 16, 0, + 9, 0, 0, 0, 18, 0, + 0, 1, 33, 0, 0, 9, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 144, 208, 0, + 64, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 55, 0, 0, 15, 114, 0, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 15, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 114, 0, + 16, 0, 8, 0, 0, 0, + 166, 10, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 60, 0, + 0, 7, 114, 0, 16, 0, + 9, 0, 0, 0, 166, 10, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 33, 0, 0, 10, + 114, 0, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 33, 0, 0, 10, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 32, 0, + 0, 10, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 32, 0, 0, 10, + 114, 0, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 9, 66, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 10, 144, 208, 0, + 64, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 41, 0, 0, 7, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 246, 15, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 246, 15, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 32, 0, + 0, 10, 114, 0, 16, 0, + 16, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 32, 0, 0, 10, + 114, 0, 16, 0, 17, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 2, 64, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 8, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 128, 65, 0, + 0, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 15, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 16, 0, 0, 0, + 246, 15, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 17, 0, 0, 0, + 246, 15, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 55, 0, + 0, 9, 178, 0, 16, 0, + 1, 0, 0, 0, 70, 8, + 16, 0, 9, 0, 0, 0, + 70, 8, 16, 0, 6, 0, + 0, 0, 70, 8, 16, 0, + 11, 0, 0, 0, 21, 0, + 0, 1, 30, 0, 0, 8, + 114, 0, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 128, + 65, 0, 0, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 8, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 128, 65, 0, 0, 0, + 4, 0, 0, 0, 70, 3, + 16, 0, 1, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 5, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 55, 0, + 0, 11, 242, 0, 16, 0, + 5, 0, 0, 0, 6, 144, + 208, 0, 32, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 55, 0, 0, 11, 50, 0, + 16, 0, 1, 0, 0, 0, + 6, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 150, 5, + 16, 0, 4, 0, 0, 0, + 214, 5, 16, 0, 1, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 168, 0, + 0, 8, 50, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 68, 0, 0, 0, 70, 0, + 16, 0, 1, 0, 0, 0, + 21, 0, 0, 1, 21, 0, + 0, 1, 190, 24, 0, 1, + 31, 0, 4, 3, 42, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 6, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 150, 240, + 17, 0, 0, 0, 0, 0, + 31, 0, 0, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 79, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 31, 0, + 4, 3, 58, 0, 16, 0, + 1, 0, 0, 0, 41, 0, + 0, 9, 18, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 10, 144, 208, 0, 64, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 9, 34, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 26, 144, 208, 0, 64, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 9, 66, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 144, 208, 0, 64, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 9, 130, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 58, 144, 208, 0, 64, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 33, 0, + 0, 10, 114, 0, 16, 0, + 6, 0, 0, 0, 38, 9, + 16, 0, 1, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 12, + 114, 0, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 0, 0, 0, 0, 150, 151, + 208, 0, 64, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 33, 0, 0, 7, + 114, 0, 16, 0, 7, 0, + 0, 0, 38, 9, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 0, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 38, 9, 16, 0, + 1, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 9, 0, 0, 0, 38, 9, + 16, 0, 1, 0, 0, 0, + 34, 0, 0, 7, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 10, 242, 0, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 1, 0, 0, 7, + 226, 0, 16, 0, 5, 0, + 0, 0, 166, 4, 16, 0, + 1, 0, 0, 0, 86, 14, + 16, 0, 5, 0, 0, 0, + 55, 0, 0, 9, 226, 0, + 16, 0, 5, 0, 0, 0, + 6, 9, 16, 0, 9, 0, + 0, 0, 6, 9, 16, 0, + 8, 0, 0, 0, 86, 14, + 16, 0, 5, 0, 0, 0, + 55, 0, 0, 9, 226, 0, + 16, 0, 5, 0, 0, 0, + 6, 9, 16, 0, 6, 0, + 0, 0, 6, 9, 16, 0, + 7, 0, 0, 0, 86, 14, + 16, 0, 5, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 0, 0, 7, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 6, 0, + 16, 0, 5, 0, 0, 0, + 1, 0, 0, 7, 194, 0, + 16, 0, 2, 0, 0, 0, + 6, 4, 16, 0, 1, 0, + 0, 0, 6, 0, 16, 0, + 5, 0, 0, 0, 54, 0, + 0, 5, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 55, 0, 0, 11, + 242, 0, 16, 0, 4, 0, + 0, 0, 6, 144, 208, 0, + 32, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 55, 0, + 0, 11, 50, 0, 16, 0, + 1, 0, 0, 0, 6, 144, + 208, 0, 32, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 230, 10, 16, 0, + 5, 0, 0, 0, 230, 10, + 16, 0, 2, 0, 0, 0, + 18, 0, 0, 1, 31, 0, + 4, 5, 10, 144, 208, 0, + 32, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 9, 18, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 10, 144, 208, 0, + 64, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 9, 34, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 26, 144, 208, 0, + 64, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 9, 66, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 144, 208, 0, + 64, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 9, 130, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 58, 144, 208, 0, + 64, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 1, 0, + 0, 7, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 6, 0, 16, 0, 5, 0, + 0, 0, 33, 0, 0, 10, + 114, 0, 16, 0, 6, 0, + 0, 0, 38, 9, 16, 0, + 1, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 12, 114, 0, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 0, 0, + 0, 0, 150, 151, 208, 0, + 64, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 33, 0, 0, 7, 114, 0, + 16, 0, 7, 0, 0, 0, + 38, 9, 16, 0, 1, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 0, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 38, 9, 16, 0, 1, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 9, 0, + 0, 0, 38, 9, 16, 0, + 1, 0, 0, 0, 34, 0, + 0, 7, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 1, 0, 0, 7, + 114, 0, 16, 0, 5, 0, + 0, 0, 38, 9, 16, 0, + 1, 0, 0, 0, 150, 7, + 16, 0, 5, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 1, 0, 0, 0, + 150, 4, 16, 0, 6, 0, + 0, 0, 150, 4, 16, 0, + 7, 0, 0, 0, 150, 4, + 16, 0, 5, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 18, 0, 0, 1, + 41, 0, 0, 9, 130, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 10, 144, 208, 0, + 64, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 5, 130, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 0, 0, 7, 242, 0, + 16, 0, 4, 0, 0, 0, + 246, 15, 16, 0, 1, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 1, 0, + 0, 7, 50, 0, 16, 0, + 1, 0, 0, 0, 246, 15, + 16, 0, 1, 0, 0, 0, + 70, 0, 16, 0, 1, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 18, 0, + 0, 1, 80, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 1, 0, 0, 0, + 31, 0, 4, 5, 10, 144, + 208, 0, 32, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 33, 0, 0, 10, + 114, 0, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 12, 114, 0, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 0, 0, + 0, 0, 150, 151, 208, 0, + 64, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 33, 0, 0, 7, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 0, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 34, 0, + 0, 7, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 41, 0, 0, 9, + 18, 0, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 26, 144, + 208, 0, 64, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 9, + 34, 0, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 144, + 208, 0, 64, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 9, + 66, 0, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 58, 144, + 208, 0, 64, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 2, 64, + 0, 0, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 0, 0, 0, 0, + 1, 0, 0, 7, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 33, 0, + 0, 10, 114, 0, 16, 0, + 5, 0, 0, 0, 38, 9, + 16, 0, 1, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 33, 0, 0, 7, + 114, 0, 16, 0, 6, 0, + 0, 0, 38, 9, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 38, 9, + 16, 0, 1, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 8, 0, 0, 0, + 38, 9, 16, 0, 1, 0, + 0, 0, 34, 0, 0, 7, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 1, 0, 0, 7, 114, 0, + 16, 0, 9, 0, 0, 0, + 38, 9, 16, 0, 1, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 1, 0, 0, 0, 150, 4, + 16, 0, 5, 0, 0, 0, + 150, 4, 16, 0, 6, 0, + 0, 0, 150, 4, 16, 0, + 7, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 18, 0, 0, 1, 41, 0, + 0, 9, 130, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 10, 144, 208, 0, 64, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 54, 0, 0, 5, + 130, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 0, + 0, 7, 242, 0, 16, 0, + 4, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 4, 0, + 0, 0, 1, 0, 0, 7, + 50, 0, 16, 0, 1, 0, + 0, 0, 246, 15, 16, 0, + 0, 0, 0, 0, 70, 0, + 16, 0, 1, 0, 0, 0, + 21, 0, 0, 1, 18, 0, + 0, 1, 54, 0, 0, 5, + 130, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 14, 16, 0, 4, 0, + 0, 0, 168, 0, 0, 8, + 50, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 68, 0, + 0, 0, 70, 0, 16, 0, + 1, 0, 0, 0, 21, 0, + 0, 1, 190, 24, 0, 1, + 31, 0, 0, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 68, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 79, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 254, 255, + 255, 255, 32, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 0, 128, 0, 0, + 0, 0, 0, 2, 8, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 64, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 4, 0, 0, 0, 8, + 0, 0, 0, 16, 0, 0, + 0, 32, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 18, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 0, 0, 0, + 4, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 8, 0, 0, 0, + 16, 0, 0, 0, 32, 0, + 0, 0, 64, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 0, 4, 0, 0, + 0, 8, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 16, 0, 0, + 0, 32, 0, 0, 0, 64, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 16, 0, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 5, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 64, 0, 0, 0, 128, 0, + 0, 0, 0, 1, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 2, 0, 0, 0, 4, + 0, 0, 0, 8, 0, 0, + 0, 16, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 2, 0, 0, 0, 6, 4, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 32, 0, 0, 0, 0, + 128, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 5, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 128, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 18, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 4, 0, 0, 0, + 8, 0, 0, 0, 16, 0, + 0, 0, 32, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 64, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 0, 4, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 27, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 8, 0, 0, + 0, 16, 0, 0, 0, 32, + 0, 0, 0, 64, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 18, 0, 0, 1, + 32, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 25, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 5, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 0, 128, 0, 0, 0, 0, + 0, 2, 8, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 64, 0, 0, 0, 128, 0, + 0, 0, 0, 1, 0, 0, + 0, 2, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 0, 4, + 0, 0, 0, 8, 0, 0, + 0, 16, 0, 0, 0, 32, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 4, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 8, 0, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 64, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 128, 0, + 0, 0, 0, 1, 0, 0, + 0, 4, 0, 0, 0, 8, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 16, 0, 0, 0, 32, + 0, 0, 0, 64, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 2, 0, 0, 0, + 4, 0, 0, 0, 16, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 32, 0, 0, 0, 64, 0, + 0, 0, 128, 0, 0, 0, + 0, 1, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 2, + 0, 0, 0, 4, 0, 0, + 0, 8, 0, 0, 0, 16, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 2, 0, + 0, 0, 6, 4, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 32, + 0, 0, 0, 0, 128, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 128, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 18, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 19, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 20, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 21, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 4, 0, 0, 0, 8, 0, + 0, 0, 16, 0, 0, 0, + 32, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 4, 0, 0, 0, + 86, 9, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 22, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 64, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 25, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 1, 0, 0, 0, 2, + 0, 0, 0, 4, 0, 0, + 0, 8, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 30, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 16, + 0, 0, 0, 32, 0, 0, + 0, 64, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 18, 0, 0, 1, 32, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 31, 0, 4, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 25, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 32, 0, 0, 0, 0, 128, + 0, 0, 0, 0, 0, 2, + 8, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 64, 0, + 0, 0, 128, 0, 0, 0, + 0, 1, 0, 0, 0, 2, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 4, 0, 0, + 0, 8, 0, 0, 0, 16, + 0, 0, 0, 32, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 18, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 0, 0, 4, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 19, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 20, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 21, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 22, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 8, 0, + 0, 0, 16, 0, 0, 0, + 32, 0, 0, 0, 64, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 27, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 0, 0, 0, + 0, 1, 0, 0, 0, 4, + 0, 0, 0, 8, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 30, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 16, + 0, 0, 0, 32, 0, 0, + 0, 64, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 2, 0, 0, 0, 4, 0, + 0, 0, 16, 0, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 64, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 5, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 2, 0, 0, + 0, 4, 0, 0, 0, 16, + 0, 0, 0, 0, 32, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 0, 8, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 2, 0, 0, 0, 6, 4, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 32, 0, 0, 0, 0, + 128, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 128, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 18, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 4, 0, 0, 0, + 8, 0, 0, 0, 16, 0, + 0, 0, 0, 1, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 4, 0, + 0, 0, 86, 9, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 22, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 64, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 2, 0, 0, + 0, 4, 0, 0, 0, 8, + 0, 0, 0, 16, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 2, 0, 0, 0, + 6, 4, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 32, + 0, 0, 0, 64, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 18, 0, 0, 1, 32, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 31, 0, 4, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 25, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 32, 0, 0, 0, 0, 128, + 0, 0, 0, 0, 0, 2, + 8, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 64, 0, + 0, 0, 128, 0, 0, 0, + 0, 1, 0, 0, 0, 2, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 4, 0, 0, + 0, 8, 0, 0, 0, 16, + 0, 0, 0, 32, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 18, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 0, 0, 4, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 19, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 20, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 21, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 22, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 8, 0, + 0, 0, 16, 0, 0, 0, + 32, 0, 0, 0, 64, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 27, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 0, 0, 0, + 0, 1, 0, 0, 0, 4, + 0, 0, 0, 8, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 30, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 16, + 0, 0, 0, 32, 0, 0, + 0, 64, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 2, 0, 0, 0, 4, 0, + 0, 0, 16, 0, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 64, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 5, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 2, 0, 0, + 0, 4, 0, 0, 0, 16, + 0, 0, 0, 0, 2, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 0, 8, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 2, 0, 0, 0, 6, 4, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 32, 0, 0, 0, 0, + 128, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 4, 0, 0, 0, + 6, 4, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 128, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 1, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 5, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 4, 0, + 0, 0, 8, 0, 0, 0, + 16, 0, 0, 0, 32, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 64, 0, 0, 0, + 0, 8, 0, 0, 0, 16, + 0, 0, 0, 32, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 25, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 2, 0, + 0, 0, 6, 4, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 2, 0, 0, 0, 4, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 64, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 18, 0, 0, 1, 54, 0, + 0, 8, 82, 0, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 21, 0, 0, 1, 21, 0, + 0, 1, 21, 0, 0, 1, + 21, 0, 0, 1, 18, 0, + 0, 1, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 68, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 252, 255, 32, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 98, 0, 16, 0, 0, 0, + 0, 0, 86, 6, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 7, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 4, 0, 0, 0, 8, 0, + 0, 0, 0, 4, 0, 0, + 0, 8, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 25, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 0, 128, 0, 0, 0, 0, + 0, 2, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 64, 0, 0, 0, 128, 0, + 0, 0, 0, 1, 0, 0, + 0, 2, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 9, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 4, + 0, 0, 0, 8, 0, 0, + 0, 16, 0, 0, 0, 32, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 4, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 8, 0, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 64, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 128, 0, + 0, 0, 0, 1, 0, 0, + 0, 4, 0, 0, 0, 8, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 16, 0, 0, 0, 32, + 0, 0, 0, 64, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 2, 0, 0, 0, + 4, 0, 0, 0, 16, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 64, 0, 0, 0, + 128, 0, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 1, + 0, 0, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 64, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 2, + 0, 0, 0, 0, 0, 32, + 2, 0, 0, 0, 128, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 0, 0, + 0, 0, 86, 9, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 30, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 2, 0, + 0, 0, 6, 4, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 16, + 0, 0, 0, 0, 0, 64, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 4, 0, 0, 0, + 6, 4, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 32, 0, 0, + 0, 0, 128, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 128, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 18, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 19, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 6, 0, + 0, 0, 6, 4, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 8, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 0, 4, 0, 0, 0, 8, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 16, 64, 0, 0, 0, + 0, 16, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 4, 0, 0, 0, + 8, 0, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 1, 0, 0, + 0, 2, 0, 0, 0, 4, + 0, 0, 0, 8, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 32, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 85, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 128, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 18, 0, 0, 1, 32, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 98, 0, 16, 0, 0, 0, + 0, 0, 86, 6, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 2, 0, 0, 0, + 166, 6, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 4, 0, 0, 0, + 0, 64, 0, 0, 0, 0, + 64, 0, 0, 0, 0, 1, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 8, 0, 0, 0, 16, 0, + 0, 0, 0, 32, 0, 0, + 0, 0, 128, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 0, 128, 0, 0, + 0, 0, 0, 2, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 10, 0, + 0, 0, 70, 14, 16, 0, + 10, 0, 0, 0, 2, 64, + 0, 0, 64, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 10, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 10, 0, 0, 0, + 70, 14, 16, 0, 10, 0, + 0, 0, 2, 64, 0, 0, + 0, 4, 0, 0, 0, 8, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 10, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 19, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 0, 0, + 0, 0, 6, 4, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 16, + 0, 0, 0, 0, 8, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 10, 0, + 0, 0, 70, 14, 16, 0, + 10, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 4, 0, + 0, 0, 8, 0, 0, 0, + 16, 0, 0, 0, 32, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 10, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 4, 0, 0, 0, 8, + 0, 0, 0, 16, 0, 0, + 0, 32, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 134, 3, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 64, + 16, 0, 0, 0, 32, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 64, 0, + 0, 0, 128, 0, 0, 0, + 0, 1, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 7, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 2, 0, 0, 0, 0, + 0, 32, 2, 0, 0, 0, + 128, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 2, 0, + 0, 0, 86, 9, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 0, 4, 0, 0, 0, 8, + 0, 0, 0, 16, 0, 0, + 0, 0, 0, 64, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 9, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 2, 0, 0, 0, + 6, 4, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 32, 0, 0, + 0, 0, 128, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 10, 0, 0, 0, 70, 14, + 16, 0, 10, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 128, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 10, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 25, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 10, 0, + 0, 0, 70, 14, 16, 0, + 10, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 1, 0, 0, + 0, 2, 0, 0, 0, 4, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 10, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 0, 0, 0, 0, 6, 4, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 32, 0, 0, 0, + 64, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 0, 0, 0, 0, + 6, 4, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 8, + 0, 0, 0, 16, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 0, 0, + 0, 0, 166, 2, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 1, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 0, 0, 0, 0, + 86, 9, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 16, 0, 0, 0, + 32, 0, 0, 0, 64, 0, + 0, 0, 0, 1, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 2, + 0, 0, 0, 4, 0, 0, + 0, 8, 0, 0, 0, 16, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 32, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 85, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 128, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 18, 0, + 0, 1, 32, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 0, 128, 0, 0, + 0, 0, 0, 2, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 64, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 4, 0, 0, 0, 8, + 0, 0, 0, 16, 0, 0, + 0, 32, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 18, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 0, 0, 0, + 4, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 8, 0, 0, 0, + 16, 0, 0, 0, 32, 0, + 0, 0, 64, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 0, 4, 0, 0, + 0, 8, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 16, 0, 0, + 0, 32, 0, 0, 0, 64, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 16, 0, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 64, 0, 0, 0, 128, 0, + 0, 0, 0, 1, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 2, 0, 0, + 0, 0, 0, 32, 2, 0, + 0, 0, 128, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 0, 0, 0, 0, 86, 9, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 4, 0, 0, + 0, 8, 0, 0, 0, 16, + 0, 0, 0, 0, 0, 64, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 0, 0, + 0, 0, 6, 4, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 32, + 0, 0, 0, 0, 128, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 2, 0, 0, 0, 6, 4, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 128, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 1, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 2, 0, 0, 0, + 86, 9, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 27, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 2, 0, 0, 0, + 6, 4, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 8, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 18, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 4, 0, 0, 0, 6, 4, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 8, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 4, 0, 0, 0, 6, 4, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 10, 0, + 0, 0, 70, 14, 16, 0, + 10, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 64, 0, 0, 0, 0, 16, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 10, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 25, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 0, 0, 0, 0, + 6, 4, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 2, + 0, 0, 0, 4, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 0, 0, 0, 0, 166, 2, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 1, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 0, 0, + 0, 0, 86, 9, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 0, 1, 0, 0, 0, 2, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 0, 0, + 0, 0, 6, 4, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 64, 0, + 0, 0, 0, 16, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 2, 0, + 0, 0, 6, 4, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 4, + 0, 0, 0, 8, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 32, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 85, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 128, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 18, 0, + 0, 1, 32, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 0, 128, 0, 0, + 0, 0, 0, 2, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 64, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 4, 0, 0, 0, 8, + 0, 0, 0, 16, 0, 0, + 0, 32, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 18, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 0, 0, 0, + 4, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 8, 0, 0, 0, + 16, 0, 0, 0, 32, 0, + 0, 0, 64, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 0, 4, 0, 0, + 0, 8, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 16, 0, 0, + 0, 32, 0, 0, 0, 64, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 16, 0, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 2, 0, + 0, 0, 6, 4, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 18, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 64, 0, 0, 0, + 128, 0, 0, 0, 0, 0, + 4, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 1, + 0, 0, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 64, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 2, + 0, 0, 0, 0, 0, 32, + 2, 0, 0, 0, 128, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 0, 0, 0, 0, + 86, 9, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 30, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 10, 0, 0, 0, 70, 14, + 16, 0, 10, 0, 0, 0, + 2, 64, 0, 0, 0, 4, + 0, 0, 0, 8, 0, 0, + 0, 16, 0, 0, 0, 0, + 0, 64, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 10, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 0, 0, 0, 0, 6, 4, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 32, 0, 0, 0, 0, + 128, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 11, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 11, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 11, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 11, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 11, 0, + 0, 0, 70, 14, 16, 0, + 11, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 128, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 11, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 11, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 11, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 11, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 2, 0, 0, 0, 6, 4, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 32, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 1, 0, 0, 0, 2, + 0, 0, 0, 4, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 8, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 16, 64, 0, + 0, 0, 0, 16, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 0, 0, 0, 0, 166, 2, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 1, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 0, 0, + 0, 0, 86, 9, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 0, 0, + 0, 0, 6, 12, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 16, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 0, 4, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 8, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 32, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 85, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 85, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 7, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 128, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 18, 0, 0, 1, + 32, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 25, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 0, 128, 0, 0, 0, 0, + 0, 2, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 64, 0, 0, 0, 128, 0, + 0, 0, 0, 1, 0, 0, + 0, 2, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 4, + 0, 0, 0, 8, 0, 0, + 0, 16, 0, 0, 0, 32, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 4, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 8, 0, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 64, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 128, 0, + 0, 0, 0, 1, 0, 0, + 0, 4, 0, 0, 0, 8, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 16, 0, 0, 0, 32, + 0, 0, 0, 64, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 2, 0, 0, 0, + 4, 0, 0, 0, 16, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 2, 0, 0, 0, + 6, 4, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 64, 0, 0, 0, 128, 0, + 0, 0, 0, 0, 2, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 1, 0, 0, + 0, 4, 0, 0, 0, 8, + 0, 0, 0, 16, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 9, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 2, 0, 0, + 0, 0, 0, 32, 2, 0, + 0, 0, 128, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 0, 0, 0, 0, + 6, 4, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 32, 0, 0, + 0, 0, 128, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 2, 0, + 0, 0, 6, 4, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 128, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 1, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 18, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 2, 0, 0, 0, 6, 4, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 8, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 2, 0, 0, 0, 6, 4, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 64, 0, 32, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 2, + 0, 0, 0, 4, 0, 0, + 0, 8, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 16, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 0, 0, + 0, 0, 166, 2, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 4, 0, + 0, 0, 6, 8, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 64, 4, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 0, 0, 0, 0, + 6, 12, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 8, 0, + 0, 0, 16, 0, 0, 0, + 0, 1, 0, 0, 0, 2, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 64, 0, 0, 0, + 0, 8, 0, 0, 0, 16, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 4, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 32, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 85, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 85, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 7, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 128, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 18, 0, 0, 1, + 32, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 25, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 0, 128, 0, 0, 0, 0, + 0, 2, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 64, 0, 0, 0, 128, 0, + 0, 0, 0, 1, 0, 0, + 0, 2, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 4, + 0, 0, 0, 8, 0, 0, + 0, 16, 0, 0, 0, 32, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 0, 0, 0, 0, + 166, 6, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 0, 0, 1, + 0, 4, 0, 0, 0, 8, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 4, 0, + 0, 0, 8, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 9, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 16, 0, 0, 0, 32, 0, + 0, 0, 64, 0, 0, 0, + 128, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 4, 0, 0, 0, 8, + 0, 0, 0, 16, 0, 0, + 0, 32, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 4, 0, 0, 0, 6, 8, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 64, 2, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 0, 0, 0, 0, + 86, 1, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 20, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 21, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 4, 0, + 0, 0, 0, 1, 0, 0, + 0, 0, 16, 0, 0, 0, + 32, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 7, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 16, 0, 0, 0, 32, 0, + 0, 0, 64, 0, 0, 0, + 128, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 2, + 0, 0, 0, 0, 0, 32, + 2, 0, 0, 0, 128, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 0, 0, + 0, 0, 86, 9, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 30, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 2, 0, + 0, 0, 6, 4, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 16, + 0, 0, 0, 0, 0, 64, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 4, 0, 0, 0, + 6, 4, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 32, 0, 0, + 0, 0, 128, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 128, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 18, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 19, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 6, 0, + 0, 0, 6, 4, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 8, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 6, 0, 0, 0, 6, 4, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 22, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 64, 0, + 0, 0, 0, 16, 64, 0, + 0, 0, 0, 16, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 25, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 1, 0, 0, 0, 2, + 0, 0, 0, 4, 0, 0, + 0, 8, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 4, 0, 0, 0, 8, 0, + 0, 0, 16, 0, 0, 0, + 32, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 9, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 7, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 1, 0, 0, 0, 2, + 0, 0, 0, 4, 0, 0, + 0, 8, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 32, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 85, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 128, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 18, 0, + 0, 1, 32, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 0, 128, 0, 0, + 0, 0, 0, 2, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 18, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 64, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 4, 0, 0, 0, 8, + 0, 0, 0, 16, 0, 0, + 0, 0, 1, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 0, 0, 0, 0, 6, 4, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 32, 0, 0, + 0, 0, 128, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 0, 0, 0, 0, 166, 6, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 10, 0, + 0, 0, 70, 14, 16, 0, + 10, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 0, 0, 1, 0, 4, + 0, 0, 0, 8, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 10, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 18, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 8, 0, 0, 0, 16, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 27, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 32, 0, 0, 0, + 64, 0, 0, 0, 0, 4, + 0, 0, 0, 8, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 16, 0, 0, 0, 32, + 0, 0, 0, 64, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 16, 0, 0, 0, + 32, 0, 0, 0, 64, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 0, 0, 0, 0, 6, 4, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 2, 0, 0, + 0, 0, 0, 32, 2, 0, + 0, 0, 128, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 0, 0, 0, 0, + 86, 9, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 2, 0, 0, 0, + 6, 4, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 16, 0, 0, + 0, 0, 0, 64, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 4, 0, 0, 0, 6, 4, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 32, 0, 0, 0, 0, + 128, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 128, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 6, 0, 0, 0, + 6, 4, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 8, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 6, 0, 0, 0, + 6, 4, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 16, 0, 0, 0, 32, 0, + 0, 0, 64, 0, 0, 0, + 0, 16, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 0, 4, 0, 0, 0, 8, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 4, 0, + 0, 0, 8, 0, 0, 0, + 16, 0, 0, 0, 32, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 64, 0, 0, 0, + 0, 1, 0, 0, 0, 2, + 0, 0, 0, 4, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 0, 0, 0, 0, + 6, 4, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 8, 0, 0, + 0, 16, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 32, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 85, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 128, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 18, 0, + 0, 1, 32, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 0, 128, 0, 0, + 0, 0, 0, 2, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 64, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 4, 0, 0, 0, 8, + 0, 0, 0, 16, 0, 0, + 0, 0, 1, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 0, 0, 0, 0, + 6, 4, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 32, 0, 0, + 0, 0, 8, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 2, 0, + 0, 0, 166, 6, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 4, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 9, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 18, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 19, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 20, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 2, 0, 0, 0, + 4, 0, 0, 0, 8, 0, + 0, 0, 16, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 21, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 22, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 32, 0, 0, 0, 64, 0, + 0, 0, 0, 4, 0, 0, + 0, 8, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 30, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 16, + 0, 0, 0, 32, 0, 0, + 0, 64, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 6, 0, 0, 0, 86, 1, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 0, 1, 0, 0, 0, 0, + 16, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 16, 0, 0, 0, + 32, 0, 0, 0, 64, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 128, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 7, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 2, 0, 0, 0, 0, + 0, 32, 2, 0, 0, 0, + 128, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 2, 0, 0, 0, + 86, 9, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 8, + 0, 0, 0, 16, 0, 0, + 0, 0, 0, 64, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 2, 0, 0, 0, + 6, 4, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 32, 0, 0, + 0, 0, 128, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 128, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 25, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 1, 0, 0, + 0, 2, 0, 0, 0, 4, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 194, 0, + 16, 0, 4, 0, 0, 0, + 6, 4, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 21, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 22, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 10, 0, 0, 0, 70, 14, + 16, 0, 10, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 32, 0, 0, 0, 64, 0, + 0, 0, 0, 16, 64, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 10, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 8, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 98, 0, 16, 0, + 0, 0, 0, 0, 166, 8, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 4, 0, + 0, 0, 8, 0, 0, 0, + 16, 0, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 0, 1, 0, 0, + 0, 2, 0, 0, 0, 4, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 8, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 16, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 32, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 85, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 85, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 7, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 128, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 18, 0, 0, 1, + 32, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 25, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 0, 128, 0, 0, 0, 0, + 0, 2, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 64, 0, 0, 0, 128, 0, + 0, 0, 0, 1, 0, 0, + 0, 2, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 4, + 0, 0, 0, 8, 0, 0, + 0, 16, 0, 0, 0, 0, + 1, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 2, 0, 0, 0, 86, 1, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 0, 32, 0, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 0, 1, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 0, 0, + 0, 0, 166, 6, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 10, 0, 0, 0, + 70, 14, 16, 0, 10, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 0, + 128, 0, 0, 0, 0, 1, + 0, 4, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 10, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 18, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 19, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 20, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 2, 0, 0, 0, + 4, 0, 0, 0, 8, 0, + 0, 0, 16, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 21, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 22, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 32, 0, 0, 0, 64, 0, + 0, 0, 0, 4, 0, 0, + 0, 8, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 30, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 16, + 0, 0, 0, 32, 0, 0, + 0, 64, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 16, 0, 0, 0, 32, 0, + 0, 0, 64, 0, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 128, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 2, + 0, 0, 0, 0, 0, 32, + 2, 0, 0, 0, 128, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 0, 0, 0, 0, 86, 9, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 30, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 8, 0, 0, + 0, 16, 0, 0, 0, 0, + 0, 64, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 2, 0, 0, 0, 6, 4, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 32, 0, 0, 0, 0, + 128, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 128, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 4, 0, 0, 0, + 6, 4, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 8, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 4, 0, 0, 0, 6, 4, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 16, 0, 0, 0, 32, 0, + 0, 0, 64, 0, 64, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 10, 0, + 0, 0, 70, 14, 16, 0, + 10, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 0, 4, 0, 0, 0, 8, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 10, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 10, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 16, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 98, 0, 16, 0, 0, 0, + 0, 0, 166, 8, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 4, 0, 0, 0, + 8, 0, 0, 0, 16, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 0, 1, 0, 0, 0, 2, + 0, 0, 0, 4, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 8, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 16, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 32, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 85, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 128, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 18, 0, 0, 1, 32, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 25, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 7, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 32, 0, 0, 0, 0, 128, + 0, 0, 0, 0, 0, 2, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 64, 0, + 0, 0, 128, 0, 0, 0, + 0, 1, 0, 0, 0, 2, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 4, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 4, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 9, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 1, 0, 0, 10, 210, 0, + 16, 0, 2, 0, 0, 0, + 6, 9, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 0, 8, 0, 0, 0, 0, + 0, 0, 0, 32, 0, 0, + 0, 0, 128, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 9, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 4, 0, 0, 0, 6, 4, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 16, 0, 0, 0, 0, + 8, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 82, 0, 16, 0, + 2, 0, 0, 0, 166, 9, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 194, 0, 16, 0, 6, 0, + 0, 0, 86, 9, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 0, 32, 0, + 0, 0, 64, 0, 0, 0, + 0, 1, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 27, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 8, 0, 0, 0, + 16, 0, 0, 0, 0, 4, + 0, 0, 0, 8, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 8, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 16, 0, 0, + 0, 32, 0, 0, 0, 64, + 16, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 42, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 42, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 64, 0, 0, 0, 128, 0, + 0, 0, 0, 1, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 2, 0, 0, + 0, 0, 0, 32, 2, 0, + 0, 0, 128, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 0, 0, 0, 0, 86, 9, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 4, 0, 0, + 0, 8, 0, 0, 0, 16, + 0, 0, 0, 0, 0, 64, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 0, 0, + 0, 0, 6, 4, 16, 0, + 1, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 32, + 0, 0, 0, 0, 128, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 42, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 9, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 128, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 9, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 42, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 34, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 18, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 4, 0, 0, 0, 0, 1, + 0, 0, 0, 2, 0, 0, + 0, 4, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 42, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 1, 0, 0, 10, 50, 0, + 16, 0, 1, 0, 0, 0, + 70, 0, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 32, 0, 0, 0, + 64, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 0, 0, + 0, 0, 6, 4, 16, 0, + 1, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 8, 0, 0, 0, 16, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 194, 0, 16, 0, + 0, 0, 0, 0, 166, 2, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 0, 0, + 0, 0, 86, 9, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 1, 0, 0, 0, 70, 14, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 64, 0, 0, 0, 0, 1, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 42, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 42, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 42, 0, + 0, 7, 34, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 1, 0, 0, 0, + 70, 14, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 0, 2, 0, 0, 0, 4, + 0, 0, 0, 8, 0, 0, + 0, 16, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 32, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 85, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 1, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 0, 64, + 0, 0, 0, 128, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 18, 0, 0, 1, 54, 0, + 0, 8, 82, 0, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 21, 0, 0, 1, 21, 0, + 0, 1, 21, 0, 0, 1, + 21, 0, 0, 1, 21, 0, + 0, 1, 21, 0, 0, 1, + 21, 0, 0, 1, 21, 0, + 0, 1, 21, 0, 0, 1, + 21, 0, 0, 1, 21, 0, + 0, 1, 168, 0, 0, 9, + 242, 224, 17, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 134, 7, 16, 0, 3, 0, + 0, 0, 21, 0, 0, 1, + 62, 0, 0, 1 +}; diff --git a/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC6HEncode_TryModeG10CS.inc b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC6HEncode_TryModeG10CS.inc new file mode 100644 index 0000000..18a4e87 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC6HEncode_TryModeG10CS.inc @@ -0,0 +1,3366 @@ +#if 0 +// +// Generated by Microsoft (R) D3D Shader Disassembler +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Input +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Output +cs_4_0 +dcl_globalFlags refactoringAllowed +dcl_immediateConstantBuffer { { 10, 5, 5, 5}, + { 7, 6, 6, 6}, + { 11, 5, 4, 4}, + { 11, 4, 5, 4}, + { 11, 4, 4, 5}, + { 9, 5, 5, 5}, + { 8, 6, 5, 5}, + { 8, 5, 6, 5}, + { 8, 5, 5, 6}, + { 6, 6, 6, 6}, + { 10, 10, 10, 10}, + { 11, 9, 9, 9}, + { 12, 8, 8, 8}, + { 16, 4, 4, 4}, + { -1, 0, 0, 0}, + { -1, 0, 4, 0}, + { -1, 0, 9, 0}, + { -1, 1, 13, 0}, + { -1, 1, 17, 0}, + { -1, 1, 21, 0}, + { -1, 1, 26, 0}, + { -1, 2, 30, 0}, + { -1, 2, 34, 0}, + { 0, 2, 38, 0}, + { 0, 2, 43, 0}, + { -1, 2, 47, 0}, + { -1, 3, 51, 0}, + { -1, 3, 55, 0}, + { 0, 3, 60, 0}, + { 0, 3, 64, 0}, + { 0, 4, 0, 0}, + { 0, 4, 0, 0}, + { 0, 4, 0, 0}, + { 0, 4, 0, 0}, + { 0, 5, 0, 0}, + { 0, 5, 0, 0}, + { 0, 5, 0, 0}, + { 0, 5, 0, 0}, + { 0, 6, 0, 0}, + { 0, 6, 0, 0}, + { 0, 6, 0, 0}, + { 0, 6, 0, 0}, + { 0, 6, 0, 0}, + { 0, 7, 0, 0}, + { 0, 7, 0, 0}, + { 0, 7, 0, 0}, + { 0, 7, 0, 0}, + { 0, 8, 0, 0}, + { 0, 8, 0, 0}, + { 0, 8, 0, 0}, + { 0, 8, 0, 0}, + { 0, 9, 0, 0}, + { 0, 9, 0, 0}, + { 0, 9, 0, 0}, + { 0, 9, 0, 0}, + { 0, 10, 0, 0}, + { 0, 10, 0, 0}, + { 0, 10, 0, 0}, + { 0, 10, 0, 0}, + { 0, 10, 0, 0}, + { 0, 11, 0, 0}, + { 0, 11, 0, 0}, + { 0, 11, 0, 0}, + { 0, 11, 0, 0}, + { 0, 12, 0, 0}, + { 0, 12, 0, 0}, + { 0, 12, 0, 0}, + { 0, 12, 0, 0}, + { 0, 13, 0, 0}, + { 0, 13, 0, 0}, + { 0, 13, 0, 0}, + { 0, 13, 0, 0}, + { 0, 14, 0, 0}, + { 0, 14, 0, 0}, + { 0, 14, 0, 0}, + { 0, 14, 0, 0}, + { 0, 15, 0, 0}, + { 0, 15, 0, 0} } +dcl_constantbuffer CB0[2], immediateIndexed +dcl_resource_texture2d (float,float,float,float) t0 +dcl_uav_structured u0, 16 +dcl_input vThreadIDInGroupFlattened +dcl_input vThreadGroupID.x +dcl_temps 19 +dcl_tgsm_structured g0, 84, 64 +dcl_thread_group 64, 1, 1 +ushr r0.x, vThreadIDInGroupFlattened.x, l(4) +ishl r0.y, vThreadGroupID.x, l(2) +iadd r0.y, r0.y, cb0[1].x +iadd r0.x, r0.x, r0.y +and r0.y, vThreadIDInGroupFlattened.x, l(48) +iadd r0.z, -r0.y, vThreadIDInGroupFlattened.x +ult r1.xyzw, r0.zzzz, l(16, 8, 4, 2) +if_nz r1.x + udiv r0.w, null, r0.x, cb0[0].y + imad r1.x, -r0.w, cb0[0].y, r0.x + ishl r1.x, r1.x, l(2) + ishl r0.w, r0.w, l(2) + and r2.x, r0.z, l(3) + iadd r2.x, r1.x, r2.x + ushr r1.x, r0.z, l(2) + iadd r2.y, r0.w, r1.x + mov r2.zw, l(0,0,0,0) + ld r2.xyzw, r2.xyzw, t0.xyzw + ushr r3.xyz, r2.xyzx, l(16) + and r3.xyz, r3.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + and r4.xyzw, r2.xxyy, l(0x7fffffff, 0x007fffff, 0x7fffffff, 0x007fffff) + ult r2.xy, l(0x47ffefff, 0x47ffefff, 0, 0), r4.xzxx + ult r5.xy, r4.xzxx, l(0x38800000, 0x38800000, 0, 0) + ushr r5.zw, r4.xxxz, l(23) + iadd r5.zw, -r5.zzzw, l(0, 0, 113, 113) + iadd r4.yw, r4.yyyw, l(0, 0x00800000, 0, 0x00800000) + ushr r6.x, r4.y, r5.z + ushr r6.y, r4.w, r5.w + iadd r4.xy, r4.xzxx, l(0xc8000000, 0xc8000000, 0, 0) + movc r4.xy, r5.xyxx, r6.xyxx, r4.xyxx + iadd r4.zw, r4.xxxy, l(0, 0, 4095, 4095) + ushr r4.xy, r4.xyxx, l(13) + and r4.xy, r4.xyxx, l(1, 1, 0, 0) + iadd r4.xy, r4.xyxx, r4.zwzz + ushr r4.xy, r4.xyxx, l(13) + and r4.xy, r4.xyxx, l(0x00007fff, 0x00007fff, 0, 0) + movc r2.xy, r2.xyxx, l(0x00007fff,0x00007fff,0,0), r4.xyxx + iadd r4.xy, r3.xyxx, r2.xyxx + and r2.xy, r2.zzzz, l(0x7fffffff, 0x007fffff, 0, 0) + ult r0.w, l(0x47ffefff), r2.x + ult r1.x, r2.x, l(0x38800000) + ushr r2.z, r2.x, l(23) + iadd r2.z, -r2.z, l(113) + iadd r2.y, r2.y, l(0x00800000) + ushr r2.y, r2.y, r2.z + iadd r2.x, r2.x, l(0xc8000000) + movc r1.x, r1.x, r2.y, r2.x + iadd r2.x, r1.x, l(4095) + ushr r1.x, r1.x, l(13) + and r1.x, r1.x, l(1) + iadd r1.x, r1.x, r2.x + ushr r1.x, r1.x, l(13) + and r1.x, r1.x, l(0x00007fff) + movc r0.w, r0.w, l(0x00007fff), r1.x + iadd r4.z, r3.z, r0.w + and r2.xyzw, r4.xxyy, l(1023, 0x00007c00, 1023, 0x00007c00) + if_nz r2.y + ushr r0.w, r4.x, l(10) + and r0.w, r0.w, l(31) + else + if_nz r2.x + ishl r1.x, r2.x, l(1) + mov r2.y, r1.x + mov r0.w, l(0) + loop + and r3.x, r2.y, l(1024) + breakc_nz r3.x + iadd r0.w, r0.w, l(-1) + ishl r2.y, r2.y, l(1) + endloop + and r2.x, r2.y, l(1022) + else + mov r2.x, l(0) + mov r0.w, l(-112) + endif + endif + ishl r3.xyz, r4.xyzx, l(16) + and r3.xyz, r3.xyzx, l(0x80000000, 0x80000000, 0x80000000, 0) + ishl r0.w, r0.w, l(23) + iadd r0.w, r0.w, l(0x38000000) + or r0.w, r0.w, r3.x + ishl r1.x, r2.x, l(13) + iadd r5.x, r0.w, r1.x + if_nz r2.w + ushr r0.w, r4.y, l(10) + and r0.w, r0.w, l(31) + else + if_nz r2.z + ishl r1.x, r2.z, l(1) + mov r2.x, r1.x + mov r0.w, l(0) + loop + and r2.y, r2.x, l(1024) + breakc_nz r2.y + iadd r0.w, r0.w, l(-1) + ishl r2.x, r2.x, l(1) + endloop + and r2.z, r2.x, l(1022) + else + mov r2.z, l(0) + mov r0.w, l(-112) + endif + endif + ishl r0.w, r0.w, l(23) + iadd r0.w, r0.w, l(0x38000000) + or r0.w, r0.w, r3.y + ishl r1.x, r2.z, l(13) + iadd r5.y, r0.w, r1.x + and r2.xy, r4.zzzz, l(1023, 0x00007c00, 0, 0) + if_nz r2.y + ushr r0.w, r4.z, l(10) + and r0.w, r0.w, l(31) + else + if_nz r2.x + ishl r1.x, r2.x, l(1) + mov r2.y, r1.x + mov r0.w, l(0) + loop + and r2.z, r2.y, l(1024) + breakc_nz r2.z + iadd r0.w, r0.w, l(-1) + ishl r2.y, r2.y, l(1) + endloop + and r2.x, r2.y, l(1022) + else + mov r2.x, l(0) + mov r0.w, l(-112) + endif + endif + ishl r0.w, r0.w, l(23) + iadd r0.w, r0.w, l(0x38000000) + or r0.w, r0.w, r3.z + ishl r1.x, r2.x, l(13) + iadd r5.z, r0.w, r1.x + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(24), r5.xyzx + dp3 r2.w, r5.xyzx, l(0.212600, 0.715200, 0.072200, 0.000000) + ieq r0.w, cb0[0].z, l(95) + ishl r3.xyz, r4.xyzx, l(6) + udiv r3.xyz, null, r3.xyzx, l(31, 31, 31, 0) + ult r5.xyz, r4.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + ieq r6.xyz, r4.xyzx, l(0x00007bff, 0x00007bff, 0x00007bff, 0) + ishl r4.xyz, r4.xyzx, l(5) + udiv r7.xyz, null, r4.xyzx, l(31, 31, 31, 0) + movc r7.xyz, r6.xyzx, l(0x00007fff,0x00007fff,0x00007fff,0), r7.xyzx + and r4.xyz, r4.xyzx, l(0x000fffe0, 0x000fffe0, 0x000fffe0, 0) + udiv r4.xyz, null, r4.xyzx, l(31, 31, 31, 0) + ineg r4.xyz, r4.xyzx + movc r4.xyz, r6.xyzx, l(0xffff8001,0xffff8001,0xffff8001,0), r4.xyzx + movc r4.xyz, r5.xyzx, r7.xyzx, r4.xyzx + movc r2.xyz, r0.wwww, r3.xyzx, r4.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(12), r2.xyzx + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r2.xyzx + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(68), r2.yzww +endif +sync_g_t +if_nz r1.y + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(76), g0.xxxx + iadd r0.w, vThreadIDInGroupFlattened.x, l(8) + ld_structured r3.x, r0.w, l(76), g0.xxxx + lt r1.x, r3.x, r2.x + if_nz r1.x + ld_structured r2.xyz, r0.w, l(52), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(52), r2.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(76), r3.x + endif + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(80), g0.xxxx + ld_structured r3.x, r0.w, l(80), g0.xxxx + lt r1.x, r2.x, r3.x + if_nz r1.x + ld_structured r2.xyz, r0.w, l(64), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(64), r2.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(80), r3.x + endif +endif +sync_g_t +if_nz r1.z + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(76), g0.xxxx + iadd r0.w, vThreadIDInGroupFlattened.x, l(4) + ld_structured r3.x, r0.w, l(76), g0.xxxx + lt r1.x, r3.x, r2.x + if_nz r1.x + ld_structured r2.xyz, r0.w, l(52), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(52), r2.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(76), r3.x + endif + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(80), g0.xxxx + ld_structured r3.x, r0.w, l(80), g0.xxxx + lt r1.x, r2.x, r3.x + if_nz r1.x + ld_structured r2.xyz, r0.w, l(64), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(64), r2.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(80), r3.x + endif +endif +sync_g_t +if_nz r1.w + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(76), g0.xxxx + iadd r0.w, vThreadIDInGroupFlattened.x, l(2) + ld_structured r3.x, r0.w, l(76), g0.xxxx + lt r1.x, r3.x, r2.x + if_nz r1.x + ld_structured r2.xyz, r0.w, l(52), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(52), r2.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(76), r3.x + endif + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(80), g0.xxxx + ld_structured r3.x, r0.w, l(80), g0.xxxx + lt r1.x, r2.x, r3.x + if_nz r1.x + ld_structured r2.xyz, r0.w, l(64), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(64), r2.xyzx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(80), r3.x + endif +endif +sync_g_t +ult r0.w, r0.z, l(1) +if_nz r0.w + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(76), g0.xxxx + iadd r1.x, vThreadIDInGroupFlattened.x, l(1) + ld_structured r3.x, r1.x, l(76), g0.xxxx + lt r1.y, r3.x, r2.x + if_nz r1.y + ld_structured r2.xyz, r1.x, l(52), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(52), r2.xyzx + endif + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(80), g0.xxxx + ld_structured r3.x, r1.x, l(80), g0.xxxx + lt r1.y, r2.x, r3.x + if_nz r1.y + ld_structured r2.xyz, r1.x, l(64), g0.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(64), r2.xyzx + endif +endif +sync_g_t +if_z r0.z + ld_structured r2.xyz, r0.y, l(52), g0.xyzx + ld_structured r3.xyz, r0.y, l(64), g0.xyzx + iadd r4.xyz, -r2.xyzx, r3.xyzx + itof r4.xyz, r4.xyzx + dp3 r1.x, r4.xyzx, r4.xyzx + ld_structured r5.xyz, r0.y, l(12), g0.xyzx + iadd r5.xyz, -r2.xyzx, r5.xyzx + itof r5.xyz, r5.xyzx + dp3 r1.y, r4.xyzx, r5.xyzx + lt r2.w, l(0.000000), r1.x + ge r4.x, r1.y, l(0.000000) + and r2.w, r2.w, r4.x + mul r1.y, r1.y, l(63.499989) + div r1.x, r1.y, r1.x + ftou r1.x, r1.x + ult r1.x, l(32), r1.x + and r1.x, r1.x, r2.w + if_nz r1.x + mov r3.w, r2.x + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r3.xyzw + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(68), r2.yzyy + endif +endif +sync_g_t +if_nz r1.z + ld_structured r2.xyz, r0.y, l(52), g0.xyzx + ld_structured r3.xyz, r0.y, l(64), g0.xyzx + ineg r1.xyz, r2.xyzx + iadd r4.xyz, r1.xyzx, r3.xyzx + itof r4.xyz, r4.xyzx + dp3 r2.w, r4.xyzx, r4.xyzx + iadd r5.yz, r0.zzzz, l(0, 10, 11, 0) + ieq r6.xy, cb0[0].zzzz, l(95, 96, 0, 0) + if_nz r6.x + ige r0.z, icb[r5.y + 0].x, l(15) + and r0.z, r0.z, l(1) + movc r7.xyz, r2.xyzx, l(0,0,0,0), l(1,1,1,0) + movc r8.xyz, r3.xyzx, l(0,0,0,0), l(1,1,1,0) + or r7.xyz, r0.zzzz, r7.xyzx + or r8.xyz, r0.zzzz, r8.xyzx + ieq r9.xyz, r2.xyzx, l(0x0000ffff, 0x0000ffff, 0x0000ffff, 0) + ieq r10.xyz, r3.xyzx, l(0x0000ffff, 0x0000ffff, 0x0000ffff, 0) + ishl r0.z, l(1), icb[r5.y + 0].x + iadd r0.z, r0.z, l(-1) + ishl r11.xyz, r2.xyzx, icb[r5.y + 0].x + ishl r12.xyz, r3.xyzx, icb[r5.y + 0].x + ishr r11.xyz, r11.xyzx, l(16) + ishr r12.xyz, r12.xyzx, l(16) + movc r9.xyz, r9.xyzx, r0.zzzz, r11.xyzx + movc r10.xyz, r10.xyzx, r0.zzzz, r12.xyzx + movc r7.xyz, r7.xyzx, r2.xyzx, r9.xyzx + movc r8.xyz, r8.xyzx, r3.xyzx, r10.xyzx + else + ige r0.z, icb[r5.y + 0].x, l(16) + and r0.z, r0.z, l(1) + movc r9.xyz, r2.xyzx, l(0,0,0,0), l(1,1,1,0) + movc r10.xyz, r3.xyzx, l(0,0,0,0), l(1,1,1,0) + or r9.xyz, r0.zzzz, r9.xyzx + or r10.xyz, r0.zzzz, r10.xyzx + ige r11.xyz, r2.xyzx, l(0, 0, 0, 0) + ige r12.xyz, r3.xyzx, l(0, 0, 0, 0) + ieq r13.xyz, r2.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ieq r14.xyz, r3.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + iadd r0.z, l(-1), icb[r5.y + 0].x + ishl r3.w, l(1), r0.z + iadd r4.w, r3.w, l(-1) + ishl r15.xyz, r2.xyzx, r0.z + ishl r16.xyz, r3.xyzx, r0.z + ishr r15.xyz, r15.xyzx, l(15) + ishr r16.xyz, r16.xyzx, l(15) + movc r13.xyz, r13.xyzx, r4.wwww, r15.xyzx + movc r14.xyz, r14.xyzx, r4.wwww, r16.xyzx + ineg r15.xyz, r3.xyzx + ieq r16.xyz, r1.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ieq r17.xyz, r15.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + iadd r3.w, -r3.w, l(1) + ishl r18.xyz, r1.xyzx, r0.z + ishl r15.xyz, r15.xyzx, r0.z + ishr r18.xyz, r18.xyzx, l(15) + ishr r15.xyz, r15.xyzx, l(15) + ineg r18.xyz, r18.xyzx + ineg r15.xyz, r15.xyzx + movc r16.xyz, r16.xyzx, r3.wwww, r18.xyzx + movc r15.xyz, r17.xyzx, r3.wwww, r15.xyzx + movc r11.xyz, r11.xyzx, r13.xyzx, r16.xyzx + movc r12.xyz, r12.xyzx, r14.xyzx, r15.xyzx + movc r7.xyz, r9.xyzx, r2.xyzx, r11.xyzx + movc r8.xyz, r10.xyzx, r3.xyzx, r12.xyzx + endif + iadd r2.xyz, -r7.xyzx, r8.xyzx + movc r2.xyz, icb[r5.y + 14].xxxx, r2.xyzx, r8.xyzx + ige r3.xyz, r2.xyzx, l(0, 0, 0, 0) + iadd r8.xyzw, l(-1, -1, -1, -1), icb[r5.y + 0].xyzw + ishl r9.x, l(1), r8.x + ishl r9.y, l(1), r8.y + ishl r9.z, l(1), r8.z + ishl r9.w, l(1), r8.w + ige r8.yzw, r2.xxyz, r9.yyzw + ineg r10.xyz, r2.xyzx + ilt r10.xyz, r9.yzwy, r10.xyzx + movc r11.xyz, r3.xyzx, r8.yzwy, r10.xyzx + or r0.z, r11.y, r11.x + or r11.x, r11.z, r0.z + ishl r12.x, l(1), icb[r5.y + 0].x + ishl r12.y, l(1), icb[r5.y + 0].y + ishl r12.z, l(1), icb[r5.y + 0].z + ishl r12.w, l(1), icb[r5.y + 0].w + iadd r12.xyzw, r12.xyzw, l(-1, -1, -1, -1) + and r7.xyz, r7.xyzx, r12.xxxx + iadd r13.xyzw, r9.yzwx, l(-1, -1, -1, -1) + movc r8.yzw, r8.yyzw, r13.xxyz, r2.xxyz + and r12.yzw, r2.xxyz, r12.yyzw + movc r10.xyz, r10.xyzx, r9.yzwy, r12.yzwy + movc r11.yzw, r3.xxyz, r8.yyzw, r10.xxyz + and r3.yzw, r2.xxyz, r12.xxxx + mov r3.x, l(0) + movc r3.xyzw, icb[r5.y + 14].xxxx, r11.xyzw, r3.xyzw + and r2.xyz, r9.xxxx, r7.xyzx + and r8.yzw, r7.xxyz, r13.wwww + iadd r8.yzw, -r9.xxxx, r8.yyzw + movc r2.xyz, r2.xyzx, r8.yzwy, r7.xyzx + movc r2.xyz, r6.yyyy, r2.xyzx, r7.xyzx + or r0.z, r6.y, icb[r5.y + 14].x + and r6.yzw, r9.yyzw, r3.yyzw + and r7.xyz, r13.xyzx, r3.yzwy + iadd r7.xyz, -r9.yzwy, r7.xyzx + movc r6.yzw, r6.yyzw, r7.xxyz, r3.yyzw + movc r3.yzw, r0.zzzz, r6.yyzw, r3.yyzw + iadd r6.yzw, r2.xxyz, r3.yyzw + movc r3.yzw, icb[r5.y + 14].xxxx, r6.yyzw, r3.yyzw + ult r6.yz, icb[r5.y + 0].xxxx, l(0, 15, 16, 0) + ieq r7.xyz, r12.xxxx, r2.xyzx + ieq r8.yzw, r12.xxxx, r3.yyzw + ishl r9.xyz, r2.xyzx, l(16) + ishl r10.xyz, r3.yzwy, l(16) + iadd r9.xyz, r9.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + iadd r10.xyz, r10.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + ushr r9.xyz, r9.xyzx, icb[r5.y + 0].x + ushr r10.xyz, r10.xyzx, icb[r5.y + 0].x + movc r7.xyz, r7.xyzx, l(0x0000ffff,0x0000ffff,0x0000ffff,0), r9.xyzx + movc r8.yzw, r8.yyzw, l(0,0x0000ffff,0x0000ffff,0x0000ffff), r10.xxyz + movc r7.xyz, r2.xyzx, r7.xyzx, l(0,0,0,0) + movc r8.yzw, r3.yyzw, r8.yyzw, l(0,0,0,0) + movc r7.xyz, r6.yyyy, r7.xyzx, r2.xyzx + movc r8.yzw, r6.yyyy, r8.yyzw, r3.yyzw + ige r9.xyz, r2.xyzx, l(0, 0, 0, 0) + ige r10.xyz, r3.yzwy, l(0, 0, 0, 0) + imax r11.xyz, -r2.xyzx, r2.xyzx + imax r12.xyz, -r3.yzwy, r3.yzwy + ige r13.xyz, r11.xyzx, r13.wwww + ige r14.xyz, r12.xyzx, r13.wwww + ishl r15.xyz, r11.xyzx, l(15) + ishl r16.xyz, r12.xyzx, l(15) + iadd r15.xyz, r15.xyzx, l(0x00004000, 0x00004000, 0x00004000, 0) + iadd r16.xyz, r16.xyzx, l(0x00004000, 0x00004000, 0x00004000, 0) + ushr r15.xyz, r15.xyzx, r8.x + ushr r16.xyz, r16.xyzx, r8.x + movc r13.xyz, r13.xyzx, l(0x00007fff,0x00007fff,0x00007fff,0), r15.xyzx + movc r14.xyz, r14.xyzx, l(0x00007fff,0x00007fff,0x00007fff,0), r16.xyzx + movc r11.xyz, r11.xyzx, r13.xyzx, l(0,0,0,0) + movc r12.xyz, r12.xyzx, r14.xyzx, l(0,0,0,0) + ineg r13.xyz, r11.xyzx + ineg r14.xyz, r12.xyzx + movc r9.xyz, r9.xyzx, r11.xyzx, r13.xyzx + movc r10.xyz, r10.xyzx, r12.xyzx, r14.xyzx + movc r2.xyz, r6.zzzz, r9.xyzx, r2.xyzx + movc r3.yzw, r6.zzzz, r10.xxyz, r3.yyzw + movc r2.xyz, r6.xxxx, r7.xyzx, r2.xyzx + movc r3.yzw, r6.xxxx, r8.yyzw, r3.yyzw + ge r0.z, l(0.000000), r2.w + mov r4.w, l(0) + mov r5.y, l(0) + loop + uge r5.w, r5.y, l(16) + breakc_nz r5.w + iadd r5.w, r0.y, r5.y + ld_structured r7.xyz, r5.w, l(12), g0.xyzx + iadd r6.yzw, r1.xxyz, r7.xxyz + itof r6.yzw, r6.yyzw + dp3 r6.y, r4.xyzx, r6.yzwy + ge r6.z, l(0.000000), r6.y + or r6.z, r0.z, r6.z + lt r6.w, r6.y, r2.w + mul r6.y, r6.y, l(63.499989) + div r6.y, r6.y, r2.w + ftou r6.y, r6.y + movc r6.y, r6.w, icb[r6.y + 14].y, l(15) + movc r6.y, r6.z, l(0), r6.y + iadd r6.z, l(64), -icb[r6.y + 14].z + imul null, r7.xyz, r3.yzwy, icb[r6.y + 14].zzzz + imad r6.yzw, r2.xxyz, r6.zzzz, r7.xxyz + iadd r6.yzw, r6.yyzw, l(0, 32, 32, 32) + ishr r6.yzw, r6.yyzw, l(6) + imul null, r7.xyz, r6.yzwy, l(31, 31, 31, 0) + ishr r8.xyz, r7.xyzx, l(6) + ilt r9.xyz, r6.yzwy, l(0, 0, 0, 0) + imul null, r6.yzw, r6.yyzw, l(0, -31, -31, -31) + ishr r6.yzw, r6.yyzw, l(5) + ineg r6.yzw, r6.yyzw + ishr r7.xyz, r7.xyzx, l(5) + movc r6.yzw, r9.xxyz, r6.yyzw, r7.xxyz + ilt r7.xyz, r6.yzwy, l(0, 0, 0, 0) + ineg r9.xyz, r6.yzwy + or r9.xyz, r9.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + movc r6.yzw, r7.xxyz, r9.xxyz, r6.yyzw + movc r6.yzw, r6.xxxx, r8.xxyz, r6.yyzw + and r7.xyzw, r6.yyzz, l(1023, 0x00007c00, 1023, 0x00007c00) + if_nz r7.y + ushr r7.y, r6.y, l(10) + and r7.y, r7.y, l(31) + else + if_nz r7.x + ishl r8.x, r7.x, l(1) + mov r8.y, r8.x + mov r7.y, l(0) + loop + and r8.z, r8.y, l(1024) + breakc_nz r8.z + iadd r7.y, r7.y, l(-1) + ishl r8.y, r8.y, l(1) + endloop + and r7.x, r8.y, l(1022) + else + mov r7.xy, l(0,-112,0,0) + endif + endif + ishl r8.xzw, r6.yyzw, l(16) + and r8.xzw, r8.xxzw, l(0x80000000, 0, 0x80000000, 0x80000000) + ishl r6.y, r7.y, l(23) + iadd r6.y, r6.y, l(0x38000000) + or r6.y, r6.y, r8.x + ishl r7.x, r7.x, l(13) + iadd r9.x, r6.y, r7.x + if_nz r7.w + ushr r6.y, r6.z, l(10) + and r6.y, r6.y, l(31) + else + if_nz r7.z + ishl r6.z, r7.z, l(1) + mov r7.x, r6.z + mov r6.y, l(0) + loop + and r7.w, r7.x, l(1024) + breakc_nz r7.w + iadd r6.y, r6.y, l(-1) + ishl r7.x, r7.x, l(1) + endloop + and r7.z, r7.x, l(1022) + else + mov r7.z, l(0) + mov r6.y, l(-112) + endif + endif + ishl r6.z, r6.y, l(23) + iadd r6.z, r6.z, l(0x38000000) + or r6.z, r6.z, r8.z + ishl r7.z, r7.z, l(13) + iadd r9.y, r6.z, r7.z + and r7.zw, r6.wwww, l(0, 0, 1023, 0x00007c00) + if_nz r7.w + ushr r6.z, r6.w, l(10) + and r6.z, r6.z, l(31) + else + if_nz r7.z + ishl r6.w, r7.z, l(1) + mov r7.w, r6.w + mov r6.z, l(0) + loop + and r8.x, r7.w, l(1024) + breakc_nz r8.x + iadd r6.z, r6.z, l(-1) + ishl r7.w, r7.w, l(1) + endloop + and r7.z, r7.w, l(1022) + else + mov r7.z, l(0) + mov r6.z, l(-112) + endif + endif + ishl r6.w, r6.z, l(23) + iadd r6.w, r6.w, l(0x38000000) + or r6.w, r6.w, r8.w + ishl r7.z, r7.z, l(13) + iadd r9.z, r6.w, r7.z + ld_structured r10.xyz, r5.w, l(24), g0.xyzx + add r8.xzw, r9.xxyz, -r10.xxyz + dp3 r5.w, r8.xzwx, r8.xzwx + add r4.w, r4.w, r5.w + iadd r5.y, r5.y, l(1) + endloop + movc r5.x, r3.x, l(100000002004087730000.000000), r4.w + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(40), r5.xzxx +endif +sync_g_t +if_nz r1.w + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(40), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(2) + ld_structured r2.yz, r0.y, l(40), g0.xxyx + lt r0.z, r2.y, r1.x + if_nz r0.z + ld_structured r2.x, r0.y, l(40), g0.xxxx + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(40), r2.xzxx + endif +endif +sync_g_t +if_nz r0.w + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(40), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(1) + ld_structured r2.yz, r0.y, l(40), g0.xxyx + lt r0.z, r2.y, r1.x + if_nz r0.z + ld_structured r2.x, r0.y, l(40), g0.xxxx + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(40), r2.xzxx + endif + ld_structured r1.xy, vThreadIDInGroupFlattened.x, l(40), g0.xyxx + mov r1.zw, l(0,0,0,0) + store_structured u0.xyzw, r0.x, l(0), r1.xyzw +endif +ret +// Approximately 0 instruction slots used +#endif + +const BYTE BC6HEncode_TryModeG10CS[] = +{ + 68, 88, 66, 67, 117, 150, + 86, 154, 76, 44, 62, 174, + 101, 82, 50, 59, 75, 244, + 89, 47, 1, 0, 0, 0, + 84, 63, 0, 0, 3, 0, + 0, 0, 44, 0, 0, 0, + 60, 0, 0, 0, 76, 0, + 0, 0, 73, 83, 71, 78, + 8, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 79, 83, 71, 78, 8, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 83, 72, + 69, 88, 0, 63, 0, 0, + 64, 0, 5, 0, 192, 15, + 0, 0, 106, 8, 0, 1, + 53, 24, 0, 0, 58, 1, + 0, 0, 10, 0, 0, 0, + 5, 0, 0, 0, 5, 0, + 0, 0, 5, 0, 0, 0, + 7, 0, 0, 0, 6, 0, + 0, 0, 6, 0, 0, 0, + 6, 0, 0, 0, 11, 0, + 0, 0, 5, 0, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 11, 0, 0, 0, + 4, 0, 0, 0, 5, 0, + 0, 0, 4, 0, 0, 0, + 11, 0, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 5, 0, 0, 0, 9, 0, + 0, 0, 5, 0, 0, 0, + 5, 0, 0, 0, 5, 0, + 0, 0, 8, 0, 0, 0, + 6, 0, 0, 0, 5, 0, + 0, 0, 5, 0, 0, 0, + 8, 0, 0, 0, 5, 0, + 0, 0, 6, 0, 0, 0, + 5, 0, 0, 0, 8, 0, + 0, 0, 5, 0, 0, 0, + 5, 0, 0, 0, 6, 0, + 0, 0, 6, 0, 0, 0, + 6, 0, 0, 0, 6, 0, + 0, 0, 6, 0, 0, 0, + 10, 0, 0, 0, 10, 0, + 0, 0, 10, 0, 0, 0, + 10, 0, 0, 0, 11, 0, + 0, 0, 9, 0, 0, 0, + 9, 0, 0, 0, 9, 0, + 0, 0, 12, 0, 0, 0, + 8, 0, 0, 0, 8, 0, + 0, 0, 8, 0, 0, 0, + 16, 0, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 255, 255, 255, 255, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 255, 255, 255, 255, 0, 0, + 0, 0, 9, 0, 0, 0, + 0, 0, 0, 0, 255, 255, + 255, 255, 1, 0, 0, 0, + 13, 0, 0, 0, 0, 0, + 0, 0, 255, 255, 255, 255, + 1, 0, 0, 0, 17, 0, + 0, 0, 0, 0, 0, 0, + 255, 255, 255, 255, 1, 0, + 0, 0, 21, 0, 0, 0, + 0, 0, 0, 0, 255, 255, + 255, 255, 1, 0, 0, 0, + 26, 0, 0, 0, 0, 0, + 0, 0, 255, 255, 255, 255, + 2, 0, 0, 0, 30, 0, + 0, 0, 0, 0, 0, 0, + 255, 255, 255, 255, 2, 0, + 0, 0, 34, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 38, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 43, 0, + 0, 0, 0, 0, 0, 0, + 255, 255, 255, 255, 2, 0, + 0, 0, 47, 0, 0, 0, + 0, 0, 0, 0, 255, 255, + 255, 255, 3, 0, 0, 0, + 51, 0, 0, 0, 0, 0, + 0, 0, 255, 255, 255, 255, + 3, 0, 0, 0, 55, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 60, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 64, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 9, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 9, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 9, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 9, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 11, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 11, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 11, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 11, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 12, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 12, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 13, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 13, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 13, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 13, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 14, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 14, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 14, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 14, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 89, 0, 0, 4, + 70, 142, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 88, 24, 0, 4, 0, 112, + 16, 0, 0, 0, 0, 0, + 85, 85, 0, 0, 158, 0, + 0, 4, 0, 224, 17, 0, + 0, 0, 0, 0, 16, 0, + 0, 0, 95, 0, 0, 2, + 0, 64, 2, 0, 95, 0, + 0, 2, 18, 16, 2, 0, + 104, 0, 0, 2, 19, 0, + 0, 0, 160, 0, 0, 5, + 0, 240, 17, 0, 0, 0, + 0, 0, 84, 0, 0, 0, + 64, 0, 0, 0, 155, 0, + 0, 4, 64, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 85, 0, 0, 6, + 18, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 16, 2, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 30, 0, 0, 8, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 128, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 48, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 128, + 65, 0, 0, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 79, 0, 0, 10, 242, 0, + 16, 0, 1, 0, 0, 0, + 166, 10, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 16, 0, 0, 0, 8, 0, + 0, 0, 4, 0, 0, 0, + 2, 0, 0, 0, 31, 0, + 4, 3, 10, 0, 16, 0, + 1, 0, 0, 0, 78, 0, + 0, 9, 130, 0, 16, 0, + 0, 0, 0, 0, 0, 208, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 26, 128, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 35, 0, + 0, 11, 18, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 128, 65, 0, 0, 0, + 0, 0, 0, 0, 26, 128, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 85, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 54, 0, 0, 8, 194, 0, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 45, 0, 0, 7, + 242, 0, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 70, 126, + 16, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 0, 128, + 0, 0, 0, 128, 0, 0, + 0, 128, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 4, 0, + 0, 0, 6, 5, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 255, 255, 255, 127, + 255, 255, 127, 0, 255, 255, + 255, 127, 255, 255, 127, 0, + 79, 0, 0, 10, 50, 0, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 255, 239, + 255, 71, 255, 239, 255, 71, + 0, 0, 0, 0, 0, 0, + 0, 0, 134, 0, 16, 0, + 4, 0, 0, 0, 79, 0, + 0, 10, 50, 0, 16, 0, + 5, 0, 0, 0, 134, 0, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 128, 56, 0, 0, 128, 56, + 0, 0, 0, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 194, 0, 16, 0, 5, 0, + 0, 0, 6, 8, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 30, 0, 0, 11, 194, 0, + 16, 0, 5, 0, 0, 0, + 166, 14, 16, 128, 65, 0, + 0, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 113, 0, 0, 0, 113, 0, + 0, 0, 30, 0, 0, 10, + 162, 0, 16, 0, 4, 0, + 0, 0, 86, 13, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 128, 0, 0, 0, + 0, 0, 0, 0, 128, 0, + 85, 0, 0, 7, 18, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 85, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 10, + 50, 0, 16, 0, 4, 0, + 0, 0, 134, 0, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 200, + 0, 0, 0, 200, 0, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 9, 50, 0, + 16, 0, 4, 0, 0, 0, + 70, 0, 16, 0, 5, 0, + 0, 0, 70, 0, 16, 0, + 6, 0, 0, 0, 70, 0, + 16, 0, 4, 0, 0, 0, + 30, 0, 0, 10, 194, 0, + 16, 0, 4, 0, 0, 0, + 6, 4, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 255, 15, 0, 0, + 255, 15, 0, 0, 85, 0, + 0, 7, 50, 0, 16, 0, + 4, 0, 0, 0, 70, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 1, 0, 0, 10, + 50, 0, 16, 0, 4, 0, + 0, 0, 70, 0, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 50, 0, + 16, 0, 4, 0, 0, 0, + 70, 0, 16, 0, 4, 0, + 0, 0, 230, 10, 16, 0, + 4, 0, 0, 0, 85, 0, + 0, 7, 50, 0, 16, 0, + 4, 0, 0, 0, 70, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 1, 0, 0, 10, + 50, 0, 16, 0, 4, 0, + 0, 0, 70, 0, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 12, 50, 0, + 16, 0, 2, 0, 0, 0, + 70, 0, 16, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 70, 0, + 16, 0, 4, 0, 0, 0, + 30, 0, 0, 7, 50, 0, + 16, 0, 4, 0, 0, 0, + 70, 0, 16, 0, 3, 0, + 0, 0, 70, 0, 16, 0, + 2, 0, 0, 0, 1, 0, + 0, 10, 50, 0, 16, 0, + 2, 0, 0, 0, 166, 10, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 127, 255, 255, 127, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 255, 239, 255, 71, 10, 0, + 16, 0, 2, 0, 0, 0, + 79, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 128, 56, 85, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 30, 0, 0, 8, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 128, + 65, 0, 0, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 113, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 128, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 200, 55, 0, + 0, 9, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 255, 15, + 0, 0, 85, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 1, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 85, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 1, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 127, 0, 0, 55, 0, + 0, 9, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 255, 127, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 2, 0, + 0, 0, 6, 5, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 255, 3, 0, 0, + 0, 124, 0, 0, 255, 3, + 0, 0, 0, 124, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 2, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 18, 0, 0, 1, + 31, 0, 4, 3, 10, 0, + 16, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 48, 0, 0, 1, + 1, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 4, 0, 0, 3, 0, + 4, 3, 10, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 41, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 22, 0, 0, 1, 1, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 254, 3, + 0, 0, 18, 0, 0, 1, + 54, 0, 0, 5, 18, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 144, 255, 255, 255, 21, 0, + 0, 1, 21, 0, 0, 1, + 41, 0, 0, 7, 114, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 128, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 56, 60, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 58, 0, 16, 0, + 2, 0, 0, 0, 85, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 18, 0, 0, 1, 31, 0, + 4, 3, 42, 0, 16, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 1, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 4, + 0, 0, 3, 0, 4, 3, + 26, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 255, 255, 255, 255, + 41, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 1, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 254, 3, 0, 0, + 18, 0, 0, 1, 54, 0, + 0, 5, 66, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 144, 255, + 255, 255, 21, 0, 0, 1, + 21, 0, 0, 1, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 56, + 60, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 0, 0, 10, 50, 0, + 16, 0, 2, 0, 0, 0, + 166, 10, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 255, 3, 0, 0, 0, 124, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 2, 0, 0, 0, 85, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 18, 0, 0, 1, 31, 0, + 4, 3, 10, 0, 16, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 54, 0, 0, 5, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 1, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 4, + 0, 0, 3, 0, 4, 3, + 42, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 255, 255, 255, 255, + 41, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 1, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 254, 3, 0, 0, + 18, 0, 0, 1, 54, 0, + 0, 5, 18, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 144, 255, + 255, 255, 21, 0, 0, 1, + 21, 0, 0, 1, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 56, + 60, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 16, 0, 0, 10, + 130, 0, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 208, 179, 89, 62, + 89, 23, 55, 63, 152, 221, + 147, 61, 0, 0, 0, 0, + 32, 0, 0, 8, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 95, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 78, 0, 0, 11, 114, 0, + 16, 0, 3, 0, 0, 0, + 0, 208, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 31, 0, + 0, 0, 31, 0, 0, 0, + 31, 0, 0, 0, 0, 0, + 0, 0, 79, 0, 0, 10, + 114, 0, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 128, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 255, 123, 0, 0, 255, 123, + 0, 0, 255, 123, 0, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 78, 0, 0, 11, + 114, 0, 16, 0, 7, 0, + 0, 0, 0, 208, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 31, 0, 0, 0, 31, 0, + 0, 0, 31, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 224, 255, + 15, 0, 224, 255, 15, 0, + 224, 255, 15, 0, 0, 0, + 0, 0, 78, 0, 0, 11, + 114, 0, 16, 0, 4, 0, + 0, 0, 0, 208, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 31, 0, 0, 0, 31, 0, + 0, 0, 31, 0, 0, 0, + 0, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 1, 128, 255, 255, 1, 128, + 255, 255, 1, 128, 255, 255, + 0, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 2, 0, 0, 0, + 246, 15, 16, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 68, 0, 0, 0, 150, 15, + 16, 0, 2, 0, 0, 0, + 21, 0, 0, 1, 190, 24, + 0, 1, 31, 0, 4, 3, + 26, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 8, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 76, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 76, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 49, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 168, 0, 0, 8, + 114, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 168, 0, + 0, 8, 18, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 21, 0, 0, 1, 167, 0, + 0, 8, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 80, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 80, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 49, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 31, 0, + 4, 3, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 64, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 114, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 80, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 190, 24, + 0, 1, 31, 0, 4, 3, + 42, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 8, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 76, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 76, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 49, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 168, 0, 0, 8, + 114, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 168, 0, + 0, 8, 18, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 21, 0, 0, 1, 167, 0, + 0, 8, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 80, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 80, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 49, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 31, 0, + 4, 3, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 64, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 114, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 80, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 190, 24, + 0, 1, 31, 0, 4, 3, + 58, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 8, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 76, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 76, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 49, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 168, 0, 0, 8, + 114, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 168, 0, + 0, 8, 18, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 21, 0, 0, 1, 167, 0, + 0, 8, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 80, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 80, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 49, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 31, 0, + 4, 3, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 64, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 114, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 80, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 190, 24, + 0, 1, 79, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 76, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 76, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 49, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 21, 0, 0, 1, + 167, 0, 0, 8, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 80, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 80, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 49, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 190, 24, + 0, 1, 31, 0, 0, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 8, + 114, 0, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 128, + 65, 0, 0, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 43, 0, + 0, 5, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 16, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 8, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 128, 65, 0, 0, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 43, 0, 0, 5, 114, 0, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 16, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 49, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 29, 0, + 0, 7, 18, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 56, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 253, 255, 125, 66, 14, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 28, 0, 0, 5, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 79, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 31, 0, 4, 3, 10, 0, + 16, 0, 1, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 14, 16, 0, + 3, 0, 0, 0, 168, 0, + 0, 8, 50, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 68, 0, 0, 0, 150, 5, + 16, 0, 2, 0, 0, 0, + 21, 0, 0, 1, 21, 0, + 0, 1, 190, 24, 0, 1, + 31, 0, 4, 3, 42, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 1, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 43, 0, 0, 5, 114, 0, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 16, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 30, 0, 0, 10, 98, 0, + 16, 0, 5, 0, 0, 0, + 166, 10, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 11, 0, 0, 0, + 0, 0, 0, 0, 32, 0, + 0, 11, 50, 0, 16, 0, + 6, 0, 0, 0, 166, 138, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 95, 0, 0, 0, + 96, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 31, 0, 4, 3, 10, 0, + 16, 0, 6, 0, 0, 0, + 33, 0, 0, 8, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 144, 144, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 55, 0, 0, 15, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 15, 114, 0, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 114, 0, + 16, 0, 7, 0, 0, 0, + 166, 10, 16, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 60, 0, + 0, 7, 114, 0, 16, 0, + 8, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 32, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 255, 255, + 0, 0, 0, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 0, 0, 255, 255, + 0, 0, 255, 255, 0, 0, + 0, 0, 0, 0, 41, 0, + 0, 8, 66, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 10, 144, 144, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 41, 0, + 0, 8, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 10, 144, 144, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 41, 0, 0, 8, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 10, 144, 144, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 42, 0, 0, 7, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 166, 10, 16, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 166, 10, 16, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 18, 0, + 0, 1, 33, 0, 0, 8, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 144, 144, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 55, 0, 0, 15, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 55, 0, 0, 15, + 114, 0, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 114, 0, 16, 0, 9, 0, + 0, 0, 166, 10, 16, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 60, 0, 0, 7, 114, 0, + 16, 0, 10, 0, 0, 0, + 166, 10, 16, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 33, 0, + 0, 10, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 33, 0, 0, 10, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 32, 0, + 0, 10, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 8, + 66, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 10, 144, + 144, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 255, 255, 255, 255, + 41, 0, 0, 7, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 16, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 42, 0, 0, 7, 114, 0, + 16, 0, 16, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 246, 15, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 246, 15, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 16, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 16, 0, 0, 0, + 70, 2, 16, 0, 1, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 32, 0, + 0, 10, 114, 0, 16, 0, + 17, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 8, + 130, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 128, + 65, 0, 0, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 18, 0, 0, 0, 70, 2, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 114, 0, + 16, 0, 18, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 18, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 16, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 246, 15, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 18, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 17, 0, + 0, 0, 246, 15, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 16, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 21, 0, 0, 1, 30, 0, + 0, 8, 114, 0, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 128, 65, 0, 0, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 55, 0, 0, 11, 114, 0, + 16, 0, 2, 0, 0, 0, + 6, 144, 208, 0, 14, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 33, 0, 0, 10, + 114, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 11, 242, 0, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 70, 158, 144, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 9, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 33, 0, 0, 7, 226, 0, + 16, 0, 8, 0, 0, 0, + 6, 9, 16, 0, 2, 0, + 0, 0, 86, 14, 16, 0, + 9, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 34, 0, 0, 7, 114, 0, + 16, 0, 10, 0, 0, 0, + 150, 7, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 150, 7, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 11, 0, 0, 0, + 10, 0, 16, 0, 11, 0, + 0, 0, 60, 0, 0, 7, + 18, 0, 16, 0, 11, 0, + 0, 0, 42, 0, 16, 0, + 11, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 8, 18, 0, + 16, 0, 12, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 10, 144, 144, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 41, 0, 0, 8, + 34, 0, 16, 0, 12, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 26, 144, + 144, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 41, 0, + 0, 8, 66, 0, 16, 0, + 12, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 144, 144, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 41, 0, 0, 8, 130, 0, + 16, 0, 12, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 58, 144, 144, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 12, 0, + 0, 0, 70, 14, 16, 0, + 12, 0, 0, 0, 2, 64, + 0, 0, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 1, 0, 0, 7, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 6, 0, 16, 0, + 12, 0, 0, 0, 30, 0, + 0, 10, 242, 0, 16, 0, + 13, 0, 0, 0, 150, 3, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 55, 0, 0, 9, + 226, 0, 16, 0, 8, 0, + 0, 0, 86, 14, 16, 0, + 8, 0, 0, 0, 6, 9, + 16, 0, 13, 0, 0, 0, + 6, 9, 16, 0, 2, 0, + 0, 0, 1, 0, 0, 7, + 226, 0, 16, 0, 12, 0, + 0, 0, 6, 9, 16, 0, + 2, 0, 0, 0, 86, 14, + 16, 0, 12, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 10, 0, + 0, 0, 150, 7, 16, 0, + 9, 0, 0, 0, 150, 7, + 16, 0, 12, 0, 0, 0, + 55, 0, 0, 9, 226, 0, + 16, 0, 11, 0, 0, 0, + 6, 9, 16, 0, 3, 0, + 0, 0, 86, 14, 16, 0, + 8, 0, 0, 0, 6, 9, + 16, 0, 10, 0, 0, 0, + 1, 0, 0, 7, 226, 0, + 16, 0, 3, 0, 0, 0, + 6, 9, 16, 0, 2, 0, + 0, 0, 6, 0, 16, 0, + 12, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 11, 242, 0, + 16, 0, 3, 0, 0, 0, + 6, 144, 208, 0, 14, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 0, 11, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 1, 0, 0, 7, + 114, 0, 16, 0, 2, 0, + 0, 0, 6, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 1, 0, 0, 7, 226, 0, + 16, 0, 8, 0, 0, 0, + 6, 9, 16, 0, 7, 0, + 0, 0, 246, 15, 16, 0, + 13, 0, 0, 0, 30, 0, + 0, 8, 226, 0, 16, 0, + 8, 0, 0, 0, 6, 0, + 16, 128, 65, 0, 0, 0, + 9, 0, 0, 0, 86, 14, + 16, 0, 8, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 150, 7, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 2, 0, 0, 0, + 86, 5, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 60, 0, 0, 9, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 10, 144, 208, 0, + 14, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 0, 0, 7, 226, 0, + 16, 0, 6, 0, 0, 0, + 86, 14, 16, 0, 9, 0, + 0, 0, 86, 14, 16, 0, + 3, 0, 0, 0, 1, 0, + 0, 7, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 150, 7, 16, 0, 3, 0, + 0, 0, 30, 0, 0, 8, + 114, 0, 16, 0, 7, 0, + 0, 0, 150, 7, 16, 128, + 65, 0, 0, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 6, 0, 0, 0, 86, 14, + 16, 0, 6, 0, 0, 0, + 6, 9, 16, 0, 7, 0, + 0, 0, 86, 14, 16, 0, + 3, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 3, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 86, 14, 16, 0, 6, 0, + 0, 0, 86, 14, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 226, 0, 16, 0, + 6, 0, 0, 0, 6, 9, + 16, 0, 2, 0, 0, 0, + 86, 14, 16, 0, 3, 0, + 0, 0, 55, 0, 0, 11, + 226, 0, 16, 0, 3, 0, + 0, 0, 6, 144, 208, 0, + 14, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 86, 14, 16, 0, 6, 0, + 0, 0, 86, 14, 16, 0, + 3, 0, 0, 0, 79, 0, + 0, 11, 98, 0, 16, 0, + 6, 0, 0, 0, 6, 144, + 144, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 16, 0, + 0, 0, 0, 0, 0, 0, + 32, 0, 0, 7, 114, 0, + 16, 0, 7, 0, 0, 0, + 6, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 32, 0, + 0, 7, 226, 0, 16, 0, + 8, 0, 0, 0, 6, 0, + 16, 0, 12, 0, 0, 0, + 86, 14, 16, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 10, 0, 0, 0, + 150, 7, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 128, + 0, 0, 0, 128, 0, 0, + 0, 128, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 2, 64, + 0, 0, 0, 128, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 8, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 10, 144, 144, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 85, 0, 0, 8, + 114, 0, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 10, 144, + 144, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 55, 0, + 0, 12, 226, 0, 16, 0, + 8, 0, 0, 0, 86, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 255, 255, + 0, 0, 6, 9, 16, 0, + 10, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 12, 226, 0, 16, 0, + 8, 0, 0, 0, 86, 14, + 16, 0, 3, 0, 0, 0, + 86, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 7, 0, 0, 0, 86, 5, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 8, 0, 0, 0, 86, 5, + 16, 0, 6, 0, 0, 0, + 86, 14, 16, 0, 8, 0, + 0, 0, 86, 14, 16, 0, + 3, 0, 0, 0, 33, 0, + 0, 10, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 33, 0, 0, 10, + 114, 0, 16, 0, 10, 0, + 0, 0, 150, 7, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 36, 0, 0, 8, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 128, 65, 0, + 0, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 36, 0, 0, 8, + 114, 0, 16, 0, 12, 0, + 0, 0, 150, 7, 16, 128, + 65, 0, 0, 0, 3, 0, + 0, 0, 150, 7, 16, 0, + 3, 0, 0, 0, 33, 0, + 0, 7, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 246, 15, 16, 0, 13, 0, + 0, 0, 33, 0, 0, 7, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 246, 15, + 16, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 16, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 64, 0, 0, 0, 64, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 16, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 64, + 0, 0, 0, 64, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 16, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 16, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 2, 0, 0, 0, 166, 10, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 3, 0, 0, 0, 166, 10, + 16, 0, 6, 0, 0, 0, + 6, 9, 16, 0, 10, 0, + 0, 0, 86, 14, 16, 0, + 3, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 2, 0, 0, 0, 6, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 3, 0, 0, 0, 6, 0, + 16, 0, 6, 0, 0, 0, + 86, 14, 16, 0, 8, 0, + 0, 0, 86, 14, 16, 0, + 3, 0, 0, 0, 29, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 80, 0, + 0, 7, 130, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 3, 0, 4, 3, + 58, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 226, 0, + 16, 0, 6, 0, 0, 0, + 6, 9, 16, 0, 1, 0, + 0, 0, 6, 9, 16, 0, + 7, 0, 0, 0, 43, 0, + 0, 5, 226, 0, 16, 0, + 6, 0, 0, 0, 86, 14, + 16, 0, 6, 0, 0, 0, + 16, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 150, 7, 16, 0, + 6, 0, 0, 0, 29, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 49, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 56, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 253, 255, + 125, 66, 14, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 28, 0, 0, 5, 34, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 55, 0, 0, 11, + 34, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 26, 144, + 208, 0, 14, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 55, 0, + 0, 9, 34, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 10, 66, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 42, 144, 208, 128, 65, 0, + 0, 0, 14, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 38, 0, 0, 10, + 0, 208, 0, 0, 114, 0, + 16, 0, 7, 0, 0, 0, + 150, 7, 16, 0, 3, 0, + 0, 0, 166, 154, 208, 0, + 14, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 35, 0, 0, 9, 226, 0, + 16, 0, 6, 0, 0, 0, + 6, 9, 16, 0, 2, 0, + 0, 0, 166, 10, 16, 0, + 6, 0, 0, 0, 6, 9, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 10, 226, 0, + 16, 0, 6, 0, 0, 0, + 86, 14, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 32, 0, + 0, 0, 32, 0, 0, 0, + 32, 0, 0, 0, 42, 0, + 0, 7, 226, 0, 16, 0, + 6, 0, 0, 0, 86, 14, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 38, 0, 0, 11, + 0, 208, 0, 0, 114, 0, + 16, 0, 7, 0, 0, 0, + 150, 7, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 31, 0, 0, 0, 31, 0, + 0, 0, 31, 0, 0, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 34, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 150, 7, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 38, 0, 0, 11, 0, 208, + 0, 0, 226, 0, 16, 0, + 6, 0, 0, 0, 86, 14, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 225, 255, 255, 255, + 225, 255, 255, 255, 225, 255, + 255, 255, 42, 0, 0, 7, + 226, 0, 16, 0, 6, 0, + 0, 0, 86, 14, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 40, 0, 0, 5, 226, 0, + 16, 0, 6, 0, 0, 0, + 86, 14, 16, 0, 6, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 55, 0, 0, 9, 226, 0, + 16, 0, 6, 0, 0, 0, + 6, 9, 16, 0, 9, 0, + 0, 0, 86, 14, 16, 0, + 6, 0, 0, 0, 6, 9, + 16, 0, 7, 0, 0, 0, + 34, 0, 0, 10, 114, 0, + 16, 0, 7, 0, 0, 0, + 150, 7, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 9, 0, 0, 0, 150, 7, + 16, 0, 6, 0, 0, 0, + 60, 0, 0, 10, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 128, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 6, 0, 0, 0, 6, 9, + 16, 0, 7, 0, 0, 0, + 6, 9, 16, 0, 9, 0, + 0, 0, 86, 14, 16, 0, + 6, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 6, 0, 0, 0, 6, 0, + 16, 0, 6, 0, 0, 0, + 6, 9, 16, 0, 8, 0, + 0, 0, 86, 14, 16, 0, + 6, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 86, 10, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 255, 3, + 0, 0, 0, 124, 0, 0, + 255, 3, 0, 0, 0, 124, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 7, 0, + 0, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 1, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 18, 0, + 0, 1, 31, 0, 4, 3, + 10, 0, 16, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 54, 0, 0, 5, 34, 0, + 16, 0, 8, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 54, 0, 0, 5, + 34, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 48, 0, + 0, 1, 1, 0, 0, 7, + 66, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 0, 4, 0, 0, + 3, 0, 4, 3, 42, 0, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 41, 0, + 0, 7, 34, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 22, 0, 0, 1, + 1, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 254, 3, 0, 0, 18, 0, + 0, 1, 54, 0, 0, 8, + 50, 0, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 144, 255, + 255, 255, 0, 0, 0, 0, + 0, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 41, 0, 0, 7, 210, 0, + 16, 0, 8, 0, 0, 0, + 86, 14, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 1, 0, + 0, 10, 210, 0, 16, 0, + 8, 0, 0, 0, 6, 14, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 128, 0, 0, 0, 0, + 0, 0, 0, 128, 0, 0, + 0, 128, 41, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 56, 60, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 31, 0, + 4, 3, 58, 0, 16, 0, + 7, 0, 0, 0, 85, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 1, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 18, 0, 0, 1, 31, 0, + 4, 3, 42, 0, 16, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 1, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 0, 4, + 0, 0, 3, 0, 4, 3, + 58, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 255, 255, 255, 255, + 41, 0, 0, 7, 18, 0, + 16, 0, 7, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 1, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 254, 3, 0, 0, + 18, 0, 0, 1, 54, 0, + 0, 5, 66, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 34, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 144, 255, + 255, 255, 21, 0, 0, 1, + 21, 0, 0, 1, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 56, + 60, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 7, 0, 0, 0, + 246, 15, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 255, 3, 0, 0, + 0, 124, 0, 0, 31, 0, + 4, 3, 58, 0, 16, 0, + 7, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 18, 0, 0, 1, 31, 0, + 4, 3, 42, 0, 16, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 54, 0, + 0, 5, 66, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 1, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 0, 4, + 0, 0, 3, 0, 4, 3, + 10, 0, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 255, 255, 255, 255, + 41, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 1, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 254, 3, 0, 0, + 18, 0, 0, 1, 54, 0, + 0, 5, 66, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 66, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 144, 255, + 255, 255, 21, 0, 0, 1, + 21, 0, 0, 1, 41, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 56, + 60, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 0, 0, 0, 8, 210, 0, + 16, 0, 8, 0, 0, 0, + 6, 9, 16, 0, 9, 0, + 0, 0, 6, 9, 16, 128, + 65, 0, 0, 0, 10, 0, + 0, 0, 16, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 134, 3, 16, 0, + 8, 0, 0, 0, 134, 3, + 16, 0, 8, 0, 0, 0, + 0, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 22, 0, 0, 1, + 55, 0, 0, 9, 18, 0, + 16, 0, 5, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 236, 120, 173, 96, 58, 0, + 16, 0, 4, 0, 0, 0, + 168, 0, 0, 8, 50, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 134, 0, 16, 0, 5, 0, + 0, 0, 21, 0, 0, 1, + 190, 24, 0, 1, 31, 0, + 4, 3, 58, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 8, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 40, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 98, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 40, 0, 0, 0, 6, 241, + 17, 0, 0, 0, 0, 0, + 49, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 40, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 50, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 40, 0, 0, 0, 134, 0, + 16, 0, 2, 0, 0, 0, + 21, 0, 0, 1, 21, 0, + 0, 1, 190, 24, 0, 1, + 31, 0, 4, 3, 58, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 98, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 6, 241, 17, 0, 0, 0, + 0, 0, 49, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 40, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 50, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 134, 0, 16, 0, 2, 0, + 0, 0, 21, 0, 0, 1, + 167, 0, 0, 8, 50, 0, + 16, 0, 1, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 54, 0, 0, 8, + 194, 0, 16, 0, 1, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 168, 0, + 0, 9, 242, 224, 17, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 70, 14, 16, 0, + 1, 0, 0, 0, 21, 0, + 0, 1, 62, 0, 0, 1 +}; diff --git a/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC6HEncode_TryModeLE10CS.inc b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC6HEncode_TryModeLE10CS.inc new file mode 100644 index 0000000..5cac112 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC6HEncode_TryModeLE10CS.inc @@ -0,0 +1,5061 @@ +#if 0 +// +// Generated by Microsoft (R) D3D Shader Disassembler +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Input +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Output +cs_4_0 +dcl_globalFlags refactoringAllowed +dcl_immediateConstantBuffer { { 0x0000cccc, 15, -1, 0}, + { 0x00008888, 15, -1, 9}, + { 0x0000eeee, 15, -1, 18}, + { 0x0000ecc8, 15, -1, 27}, + { 0x0000c880, 15, -1, 37}, + { 0x0000feec, 15, -1, 46}, + { 0x0000fec8, 15, -1, 55}, + { 0x0000ec80, 15, -1, 64}, + { 0x0000c800, 15, -1, 0}, + { 0x0000ffec, 15, 0, 0}, + { 0x0000fe80, 15, 0, 0}, + { 0x0000e800, 15, -1, 0}, + { 0x0000ffe8, 15, -1, 0}, + { 0x0000ff00, 15, -1, 0}, + { 0x0000fff0, 15, 0, 0}, + { 0x0000f000, 15, 0, 0}, + { 0x0000f710, 15, 0, 0}, + { 142, 2, 0, 0}, + { 0x00007100, 8, 0, 0}, + { 2254, 2, 0, 0}, + { 140, 2, 0, 0}, + { 0x00007310, 8, 0, 0}, + { 0x00003100, 8, 0, 0}, + { 0x00008cce, 15, 0, 0}, + { 2188, 2, 0, 0}, + { 0x00003110, 8, 0, 0}, + { 0x00006666, 2, 0, 0}, + { 0x0000366c, 2, 0, 0}, + { 6120, 8, 0, 0}, + { 4080, 8, 0, 0}, + { 0x0000718e, 2, 0, 0}, + { 0x0000399c, 2, 0, 0}, + { 10, 5, 5, 5}, + { 7, 6, 6, 6}, + { 11, 5, 4, 4}, + { 11, 4, 5, 4}, + { 11, 4, 4, 5}, + { 9, 5, 5, 5}, + { 8, 6, 5, 5}, + { 8, 5, 6, 5}, + { 8, 5, 5, 6}, + { 6, 6, 6, 6}, + { 10, 10, 10, 10}, + { 11, 9, 9, 9}, + { 12, 8, 8, 8}, + { 16, 4, 4, 4}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 7, 0, 0, 0}, + { 7, 0, 0, 0}, + { 7, 0, 0, 0}, + { 7, 0, 0, 0} } +dcl_constantbuffer CB0[2], immediateIndexed +dcl_resource_texture2d (float,float,float,float) t0 +dcl_resource_structured t1, 16 +dcl_uav_structured u0, 16 +dcl_input vThreadIDInGroupFlattened +dcl_input vThreadGroupID.x +dcl_temps 24 +dcl_indexableTemp x0[6], 4 +dcl_indexableTemp x1[2], 4 +dcl_tgsm_structured g0, 84, 64 +dcl_thread_group 64, 1, 1 +ushr r0.x, vThreadIDInGroupFlattened.x, l(5) +ishl r0.y, vThreadGroupID.x, l(1) +iadd r0.y, r0.y, cb0[1].x +iadd r0.x, r0.x, r0.y +and r0.y, vThreadIDInGroupFlattened.x, l(32) +iadd r1.z, -r0.y, vThreadIDInGroupFlattened.x +ult r2.xyzw, r1.zzzz, l(16, 32, 8, 4) +if_nz r2.x + udiv r0.z, null, r0.x, cb0[0].y + imad r0.w, -r0.z, cb0[0].y, r0.x + ishl r0.w, r0.w, l(2) + ishl r0.z, r0.z, l(2) + and r1.w, r1.z, l(3) + iadd r3.x, r0.w, r1.w + ushr r0.w, r1.z, l(2) + iadd r3.y, r0.w, r0.z + mov r3.zw, l(0,0,0,0) + ld r3.xyzw, r3.xyzw, t0.xyzw + ushr r4.xyz, r3.xyzx, l(16) + and r4.xyz, r4.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + and r5.xyzw, r3.xxyy, l(0x7fffffff, 0x007fffff, 0x7fffffff, 0x007fffff) + ult r0.zw, l(0, 0, 0x47ffefff, 0x47ffefff), r5.xxxz + ult r3.xy, r5.xzxx, l(0x38800000, 0x38800000, 0, 0) + ushr r6.xy, r5.xzxx, l(23) + iadd r6.xy, -r6.xyxx, l(113, 113, 0, 0) + iadd r5.yw, r5.yyyw, l(0, 0x00800000, 0, 0x00800000) + ushr r7.x, r5.y, r6.x + ushr r7.y, r5.w, r6.y + iadd r5.xy, r5.xzxx, l(0xc8000000, 0xc8000000, 0, 0) + movc r3.xy, r3.xyxx, r7.xyxx, r5.xyxx + iadd r5.xy, r3.xyxx, l(4095, 4095, 0, 0) + ushr r3.xy, r3.xyxx, l(13) + and r3.xy, r3.xyxx, l(1, 1, 0, 0) + iadd r3.xy, r3.xyxx, r5.xyxx + ushr r3.xy, r3.xyxx, l(13) + and r3.xy, r3.xyxx, l(0x00007fff, 0x00007fff, 0, 0) + movc r0.zw, r0.zzzw, l(0,0,0x00007fff,0x00007fff), r3.xxxy + iadd r5.xy, r4.xyxx, r0.zwzz + and r0.zw, r3.zzzz, l(0, 0, 0x7fffffff, 0x007fffff) + ult r1.w, l(0x47ffefff), r0.z + ult r3.x, r0.z, l(0x38800000) + ushr r3.y, r0.z, l(23) + iadd r3.y, -r3.y, l(113) + iadd r0.w, r0.w, l(0x00800000) + ushr r0.w, r0.w, r3.y + iadd r0.z, r0.z, l(0xc8000000) + movc r0.z, r3.x, r0.w, r0.z + iadd r0.w, r0.z, l(4095) + ushr r0.z, r0.z, l(13) + and r0.z, r0.z, l(1) + iadd r0.z, r0.z, r0.w + ushr r0.z, r0.z, l(13) + and r0.z, r0.z, l(0x00007fff) + movc r0.z, r1.w, l(0x00007fff), r0.z + iadd r5.z, r4.z, r0.z + and r3.xyzw, r5.xxyy, l(1023, 0x00007c00, 1023, 0x00007c00) + if_nz r3.y + ushr r0.z, r5.x, l(10) + and r0.z, r0.z, l(31) + else + if_nz r3.x + ishl r0.w, r3.x, l(1) + mov r1.w, r0.w + mov r0.z, l(0) + loop + and r3.y, r1.w, l(1024) + breakc_nz r3.y + iadd r0.z, r0.z, l(-1) + ishl r1.w, r1.w, l(1) + endloop + and r3.x, r1.w, l(1022) + else + mov r3.x, l(0) + mov r0.z, l(-112) + endif + endif + ishl r4.xyz, r5.xyzx, l(16) + and r4.xyz, r4.xyzx, l(0x80000000, 0x80000000, 0x80000000, 0) + ishl r0.z, r0.z, l(23) + iadd r0.z, r0.z, l(0x38000000) + or r0.z, r0.z, r4.x + ishl r0.w, r3.x, l(13) + iadd r6.x, r0.w, r0.z + if_nz r3.w + ushr r0.z, r5.y, l(10) + and r0.z, r0.z, l(31) + else + if_nz r3.z + ishl r0.w, r3.z, l(1) + mov r1.w, r0.w + mov r0.z, l(0) + loop + and r3.x, r1.w, l(1024) + breakc_nz r3.x + iadd r0.z, r0.z, l(-1) + ishl r1.w, r1.w, l(1) + endloop + and r3.z, r1.w, l(1022) + else + mov r3.z, l(0) + mov r0.z, l(-112) + endif + endif + ishl r0.z, r0.z, l(23) + iadd r0.z, r0.z, l(0x38000000) + or r0.z, r0.z, r4.y + ishl r0.w, r3.z, l(13) + iadd r6.y, r0.w, r0.z + and r0.zw, r5.zzzz, l(0, 0, 1023, 0x00007c00) + if_nz r0.w + ushr r0.w, r5.z, l(10) + and r0.w, r0.w, l(31) + else + if_nz r0.z + ishl r1.w, r0.z, l(1) + mov r3.x, r1.w + mov r0.w, l(0) + loop + and r3.y, r3.x, l(1024) + breakc_nz r3.y + iadd r0.w, r0.w, l(-1) + ishl r3.x, r3.x, l(1) + endloop + and r0.z, r3.x, l(1022) + else + mov r0.zw, l(0,0,0,-112) + endif + endif + ishl r0.w, r0.w, l(23) + iadd r0.w, r0.w, l(0x38000000) + or r0.w, r0.w, r4.z + ishl r0.z, r0.z, l(13) + iadd r6.z, r0.z, r0.w + dp3 r6.w, r6.xyzx, l(0.212600, 0.715200, 0.072200, 0.000000) + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(24), r6.xyzw + ieq r0.z, cb0[0].z, l(95) + ishl r3.xyz, r5.xyzx, l(6) + udiv r3.xyz, null, r3.xyzx, l(31, 31, 31, 0) + ult r4.xyz, r5.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + ieq r6.xyz, r5.xyzx, l(0x00007bff, 0x00007bff, 0x00007bff, 0) + ishl r5.xyz, r5.xyzx, l(5) + udiv r7.xyz, null, r5.xyzx, l(31, 31, 31, 0) + movc r7.xyz, r6.xyzx, l(0x00007fff,0x00007fff,0x00007fff,0), r7.xyzx + and r5.xyz, r5.xyzx, l(0x000fffe0, 0x000fffe0, 0x000fffe0, 0) + udiv r5.xyz, null, r5.xyzx, l(31, 31, 31, 0) + ineg r5.xyz, r5.xyzx + movc r5.xyz, r6.xyzx, l(0xffff8001,0xffff8001,0xffff8001,0), r5.xyzx + movc r4.xyz, r4.xyzx, r7.xyzx, r5.xyzx + movc r3.xyz, r0.zzzz, r3.xyzx, r4.xyzx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(12), r3.xyzx +endif +sync_g_t +if_nz r2.y + mov x0[0].x, l(0x7fffffff) + mov x0[1].x, l(0x7fffffff) + mov x0[2].x, l(0x7fffffff) + mov x0[0].y, l(-0.000000) + mov x0[1].y, l(-0.000000) + mov x0[2].y, l(-0.000000) + mov x0[3].x, l(0x7fffffff) + mov x0[4].x, l(0x7fffffff) + mov x0[5].x, l(0x7fffffff) + mov x0[3].y, l(-0.000000) + mov x0[4].y, l(-0.000000) + mov x0[5].y, l(-0.000000) + mov x1[0].x, l(340282346638528860000000000000000000000.000000) + mov x1[0].y, l(-340282346638528860000000000000000000000.000000) + mov x1[1].x, l(340282346638528860000000000000000000000.000000) + mov x1[1].y, l(-340282346638528860000000000000000000000.000000) + mov r0.z, l(0) + loop + uge r0.w, r0.z, l(16) + breakc_nz r0.w + iadd r0.w, r0.z, r0.y + ld_structured r3.xyz, r0.w, l(12), g0.xyzx + ld_structured r4.x, r0.w, l(36), g0.xxxx + ushr r0.w, icb[r1.z + 0].x, r0.z + and r0.w, r0.w, l(1) + if_nz r0.w + mov r0.w, x1[1].x + lt r1.w, r4.x, r0.w + mov r2.y, x0[3].x + movc r2.y, r1.w, r3.x, r2.y + mov x0[3].x, r2.y + mov r2.y, x0[4].x + movc r2.y, r1.w, r3.y, r2.y + mov x0[4].x, r2.y + mov r2.y, x0[5].x + movc r2.y, r1.w, r3.z, r2.y + mov x0[5].x, r2.y + movc r0.w, r1.w, r4.x, r0.w + mov x1[1].x, r0.w + mov r0.w, x1[1].y + lt r1.w, r0.w, r4.x + mov r2.y, x0[3].y + movc r2.y, r1.w, r3.x, r2.y + mov x0[3].y, r2.y + mov r2.y, x0[4].y + movc r2.y, r1.w, r3.y, r2.y + mov x0[4].y, r2.y + mov r2.y, x0[5].y + movc r2.y, r1.w, r3.z, r2.y + mov x0[5].y, r2.y + movc r0.w, r1.w, r4.x, r0.w + mov x1[1].y, r0.w + else + mov r0.w, x1[0].x + lt r1.w, r4.x, r0.w + mov r2.y, x0[0].x + movc r2.y, r1.w, r3.x, r2.y + mov x0[0].x, r2.y + mov r2.y, x0[1].x + movc r2.y, r1.w, r3.y, r2.y + mov x0[1].x, r2.y + mov r2.y, x0[2].x + movc r2.y, r1.w, r3.z, r2.y + mov x0[2].x, r2.y + movc r0.w, r1.w, r4.x, r0.w + mov x1[0].x, r0.w + mov r0.w, x1[0].y + lt r1.w, r0.w, r4.x + mov r2.y, x0[0].y + movc r2.y, r1.w, r3.x, r2.y + mov x0[0].y, r2.y + mov r2.y, x0[1].y + movc r2.y, r1.w, r3.y, r2.y + mov x0[1].y, r2.y + mov r2.y, x0[2].y + movc r2.y, r1.w, r3.z, r2.y + mov x0[2].y, r2.y + movc r0.w, r1.w, r4.x, r0.w + mov x1[0].y, r0.w + endif + iadd r0.z, r0.z, l(1) + endloop + mov r3.x, x0[0].y + mov r3.y, x0[1].y + mov r3.z, x0[2].y + mov r0.z, x0[0].x + mov r0.w, x0[1].x + mov r1.w, x0[2].x + ineg r4.xy, r0.zwzz + ineg r4.z, r1.w + iadd r5.xyz, r3.xyzx, r4.xyzx + itof r5.xyz, r5.xyzx + dp3 r2.y, r5.xyzx, r5.xyzx + ld_structured r6.xyz, r0.y, l(12), g0.xyzx + iadd r4.xyz, r4.xyzx, r6.xyzx + itof r4.xyz, r4.xyzx + dp3 r3.w, r5.xyzx, r4.xyzx + lt r4.x, l(0.000000), r2.y + ge r4.y, r3.w, l(0.000000) + and r4.x, r4.y, r4.x + mul r3.w, r3.w, l(63.499989) + div r3.w, r3.w, r2.y + ftou r3.w, r3.w + ult r3.w, l(32), r3.w + and r3.w, r3.w, r4.x + movc r4.xyz, r3.wwww, -r5.xyzx, r5.xyzx + movc r5.xy, r3.wwww, r3.xyxx, r0.zwzz + movc r5.z, r3.w, r3.z, r1.w + movc r6.xy, r3.wwww, r0.zwzz, r3.xyxx + movc r6.z, r3.w, r1.w, r3.z + mov r3.x, x0[3].y + mov r3.y, x0[4].y + mov r3.z, x0[5].y + mov r0.z, x0[3].x + mov r0.w, x0[4].x + mov r1.w, x0[5].x + ineg r7.xy, r0.zwzz + ineg r7.z, r1.w + iadd r8.xyz, r3.xyzx, r7.xyzx + itof r8.xyz, r8.xyzx + dp3 r3.w, r8.xyzx, r8.xyzx + iadd r4.w, r0.y, icb[r1.z + 0].y + ld_structured r9.xyz, r4.w, l(12), g0.xyzx + iadd r7.xyz, r7.xyzx, r9.xyzx + itof r7.xyz, r7.xyzx + dp3 r4.w, r8.xyzx, r7.xyzx + lt r5.w, l(0.000000), r3.w + ge r6.w, r4.w, l(0.000000) + and r5.w, r5.w, r6.w + mul r4.w, r4.w, l(63.499989) + div r4.w, r4.w, r3.w + ftou r4.w, r4.w + ult r4.w, l(32), r4.w + and r4.w, r4.w, r5.w + movc r7.xyz, r4.wwww, -r8.xyzx, r8.xyzx + movc r8.xy, r4.wwww, r3.xyxx, r0.zwzz + movc r8.z, r4.w, r3.z, r1.w + movc r9.xy, r4.wwww, r0.zwzz, r3.xyxx + movc r9.z, r4.w, r1.w, r3.z + ieq r0.zw, cb0[0].zzzz, l(0, 0, 95, 96) + if_nz r0.z + mov r1.w, cb0[0].w + ige r3.x, icb[r1.w + 32].x, l(15) + and r3.x, r3.x, l(1) + movc r10.xyz, r5.xyzx, l(0,0,0,0), l(1,1,1,0) + movc r11.xyz, r6.xyzx, l(0,0,0,0), l(1,1,1,0) + or r10.xyz, r3.xxxx, r10.xyzx + or r11.xyz, r3.xxxx, r11.xyzx + ieq r12.xyz, r5.xyzx, l(0x0000ffff, 0x0000ffff, 0x0000ffff, 0) + ieq r13.xyz, r6.xyzx, l(0x0000ffff, 0x0000ffff, 0x0000ffff, 0) + ishl r3.y, l(1), icb[r1.w + 32].x + iadd r3.y, r3.y, l(-1) + ishl r14.xyz, r5.xyzx, icb[r1.w + 32].x + ishl r15.xyz, r6.xyzx, icb[r1.w + 32].x + ishr r14.xyz, r14.xyzx, l(16) + ishr r15.xyz, r15.xyzx, l(16) + movc r12.xyz, r12.xyzx, r3.yyyy, r14.xyzx + movc r13.xyz, r13.xyzx, r3.yyyy, r15.xyzx + movc r10.xyz, r10.xyzx, r5.xyzx, r12.xyzx + movc r11.xyz, r11.xyzx, r6.xyzx, r13.xyzx + movc r12.xyz, r8.xyzx, l(0,0,0,0), l(1,1,1,0) + movc r13.xyz, r9.xyzx, l(0,0,0,0), l(1,1,1,0) + or r12.xyz, r3.xxxx, r12.xyzx + or r13.xyz, r3.xxxx, r13.xyzx + ieq r14.xyz, r8.xyzx, l(0x0000ffff, 0x0000ffff, 0x0000ffff, 0) + ieq r15.xyz, r9.xyzx, l(0x0000ffff, 0x0000ffff, 0x0000ffff, 0) + mov r1.w, cb0[0].w + ishl r16.xyz, r8.xyzx, icb[r1.w + 32].x + ishl r17.xyz, r9.xyzx, icb[r1.w + 32].x + ishr r16.xyz, r16.xyzx, l(16) + ishr r17.xyz, r17.xyzx, l(16) + movc r14.xyz, r14.xyzx, r3.yyyy, r16.xyzx + movc r3.xyz, r15.xyzx, r3.yyyy, r17.xyzx + movc r12.xyz, r12.xyzx, r8.xyzx, r14.xyzx + movc r3.xyz, r13.xyzx, r9.xyzx, r3.xyzx + else + mov r1.w, cb0[0].w + ige r4.w, icb[r1.w + 32].x, l(16) + and r4.w, r4.w, l(1) + movc r13.xyz, r5.xyzx, l(0,0,0,0), l(1,1,1,0) + movc r14.xyz, r6.xyzx, l(0,0,0,0), l(1,1,1,0) + or r13.xyz, r4.wwww, r13.xyzx + or r14.xyz, r4.wwww, r14.xyzx + ige r15.xyz, r5.xyzx, l(0, 0, 0, 0) + ige r16.xyz, r6.xyzx, l(0, 0, 0, 0) + ieq r17.xyz, r5.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ieq r18.xyz, r6.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + iadd r1.w, l(-1), icb[r1.w + 32].x + ishl r5.w, l(1), r1.w + iadd r6.w, r5.w, l(-1) + ishl r19.xyz, r5.xyzx, r1.w + ishl r20.xyz, r6.xyzx, r1.w + ishr r19.xyz, r19.xyzx, l(15) + ishr r20.xyz, r20.xyzx, l(15) + movc r17.xyz, r17.xyzx, r6.wwww, r19.xyzx + movc r18.xyz, r18.xyzx, r6.wwww, r20.xyzx + ineg r19.xyz, r5.xyzx + ineg r20.xyz, r6.xyzx + ieq r21.xyz, r19.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ieq r22.xyz, r20.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + iadd r5.w, -r5.w, l(1) + ishl r19.xyz, r19.xyzx, r1.w + ishl r20.xyz, r20.xyzx, r1.w + ishr r19.xyz, r19.xyzx, l(15) + ishr r20.xyz, r20.xyzx, l(15) + ineg r19.xyz, r19.xyzx + ineg r20.xyz, r20.xyzx + movc r19.xyz, r21.xyzx, r5.wwww, r19.xyzx + movc r20.xyz, r22.xyzx, r5.wwww, r20.xyzx + movc r15.xyz, r15.xyzx, r17.xyzx, r19.xyzx + movc r16.xyz, r16.xyzx, r18.xyzx, r20.xyzx + movc r10.xyz, r13.xyzx, r5.xyzx, r15.xyzx + movc r11.xyz, r14.xyzx, r6.xyzx, r16.xyzx + movc r6.xyz, r8.xyzx, l(0,0,0,0), l(1,1,1,0) + movc r13.xyz, r9.xyzx, l(0,0,0,0), l(1,1,1,0) + or r6.xyz, r4.wwww, r6.xyzx + or r13.xyz, r4.wwww, r13.xyzx + ige r14.xyz, r8.xyzx, l(0, 0, 0, 0) + ige r15.xyz, r9.xyzx, l(0, 0, 0, 0) + ieq r16.xyz, r8.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ieq r17.xyz, r9.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ishl r18.xyz, r8.xyzx, r1.w + ishl r19.xyz, r9.xyzx, r1.w + ishr r18.xyz, r18.xyzx, l(15) + ishr r19.xyz, r19.xyzx, l(15) + movc r16.xyz, r16.xyzx, r6.wwww, r18.xyzx + movc r17.xyz, r17.xyzx, r6.wwww, r19.xyzx + ineg r18.xyz, r8.xyzx + ineg r19.xyz, r9.xyzx + ieq r20.xyz, r18.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ieq r21.xyz, r19.xyzx, l(0x00007fff, 0x00007fff, 0x00007fff, 0) + ishl r18.xyz, r18.xyzx, r1.w + ishl r19.xyz, r19.xyzx, r1.w + ishr r18.xyz, r18.xyzx, l(15) + ishr r19.xyz, r19.xyzx, l(15) + ineg r18.xyz, r18.xyzx + ineg r19.xyz, r19.xyzx + movc r18.xyz, r20.xyzx, r5.wwww, r18.xyzx + movc r19.xyz, r21.xyzx, r5.wwww, r19.xyzx + movc r14.xyz, r14.xyzx, r16.xyzx, r18.xyzx + movc r15.xyz, r15.xyzx, r17.xyzx, r19.xyzx + movc r12.xyz, r6.xyzx, r8.xyzx, r14.xyzx + movc r3.xyz, r13.xyzx, r9.xyzx, r15.xyzx + endif + iadd r6.xyz, -r10.xyzx, r11.xyzx + mov r1.w, cb0[0].w + movc r6.xyz, icb[r1.w + 0].zzzz, r6.xyzx, r11.xyzx + iadd r9.xyz, -r10.xyzx, r12.xyzx + movc r9.xyz, icb[r1.w + 0].zzzz, r9.xyzx, r12.xyzx + iadd r11.xyz, -r10.xyzx, r3.xyzx + movc r3.xyz, icb[r1.w + 0].zzzz, r11.xyzx, r3.xyzx + if_nz icb[r1.w + 0].z + ige r11.xyz, r6.xyzx, l(0, 0, 0, 0) + iadd r12.xyz, l(-1, -1, -1, 0), icb[r1.w + 32].yzwy + ishl r13.x, l(1), r12.x + ishl r13.y, l(1), r12.y + ishl r13.z, l(1), r12.z + ige r12.xyz, r6.xyzx, r13.xyzx + ineg r14.xyz, r6.xyzx + ilt r14.xyz, r13.xyzx, r14.xyzx + movc r15.xyz, r11.xyzx, r12.xyzx, r14.xyzx + or r4.w, r15.y, r15.x + or r4.w, r15.z, r4.w + ishl r15.x, l(1), icb[r1.w + 32].x + ishl r15.y, l(1), icb[r1.w + 32].y + ishl r15.z, l(1), icb[r1.w + 32].z + ishl r15.w, l(1), icb[r1.w + 32].w + iadd r15.xyzw, r15.xyzw, l(-1, -1, -1, -1) + and r16.xyz, r10.xyzx, r15.xxxx + iadd r17.xyz, r13.xyzx, l(-1, -1, -1, 0) + movc r12.xyz, r12.xyzx, r17.xyzx, r6.xyzx + and r18.xyz, r6.xyzx, r15.yzwy + movc r14.xyz, r14.xyzx, r13.xyzx, r18.xyzx + movc r11.xyz, r11.xyzx, r12.xyzx, r14.xyzx + ige r12.xyz, r9.xyzx, l(0, 0, 0, 0) + ige r14.xyz, r9.xyzx, r13.xyzx + ineg r18.xyz, r9.xyzx + ilt r18.xyz, r13.xyzx, r18.xyzx + movc r19.xyz, r12.xyzx, r14.xyzx, r18.xyzx + ige r20.xyz, r3.xyzx, l(0, 0, 0, 0) + ige r21.xyz, r3.xyzx, r13.xyzx + ineg r22.xyz, r3.xyzx + ilt r22.xyz, r13.xyzx, r22.xyzx + movc r23.xyz, r20.xyzx, r21.xyzx, r22.xyzx + or r19.xyz, r19.xyzx, r23.xyzx + or r5.w, r19.y, r19.x + or r5.w, r19.z, r5.w + or r4.w, r4.w, r5.w + and r4.w, r4.w, l(1) + movc r14.xyz, r14.xyzx, r17.xyzx, r9.xyzx + and r19.xyz, r9.xyzx, r15.yzwy + movc r18.xyz, r18.xyzx, r13.xyzx, r19.xyzx + movc r12.xyz, r12.xyzx, r14.xyzx, r18.xyzx + movc r14.xyz, r21.xyzx, r17.xyzx, r3.xyzx + and r15.xyz, r3.xyzx, r15.yzwy + movc r13.xyz, r22.xyzx, r13.xyzx, r15.xyzx + movc r13.xyz, r20.xyzx, r14.xyzx, r13.xyzx + else + ishl r5.w, l(1), icb[r1.w + 32].x + iadd r5.w, r5.w, l(-1) + and r16.xyz, r5.wwww, r10.xyzx + and r11.xyz, r5.wwww, r6.xyzx + and r12.xyz, r5.wwww, r9.xyzx + and r13.xyz, r3.xyzx, r5.wwww + mov r4.w, l(0) + endif + iadd r6.xyzw, l(-1, -1, -1, -1), icb[r1.w + 32].xyzw + ishl r9.x, l(1), r6.x + ishl r9.y, l(1), r6.y + ishl r9.z, l(1), r6.z + ishl r9.w, l(1), r6.w + and r3.xyz, r9.xxxx, r16.xyzx + iadd r10.xyzw, r9.xyzw, l(-1, -1, -1, -1) + and r6.yzw, r10.xxxx, r16.xxyz + iadd r6.yzw, -r9.xxxx, r6.yyzw + movc r3.xyz, r3.xyzx, r6.yzwy, r16.xyzx + movc r3.xyz, r0.wwww, r3.xyzx, r16.xyzx + or r0.w, r0.w, icb[r1.w + 0].z + and r6.yzw, r9.yyzw, r11.xxyz + and r14.xyz, r10.yzwy, r11.xyzx + iadd r14.xyz, -r9.yzwy, r14.xyzx + movc r6.yzw, r6.yyzw, r14.xxyz, r11.xxyz + movc r6.yzw, r0.wwww, r6.yyzw, r11.xxyz + and r11.xyz, r9.yzwy, r12.xyzx + and r14.xyz, r10.yzwy, r12.xyzx + iadd r14.xyz, -r9.yzwy, r14.xyzx + movc r11.xyz, r11.xyzx, r14.xyzx, r12.xyzx + movc r11.xyz, r0.wwww, r11.xyzx, r12.xyzx + and r12.xyz, r9.yzwy, r13.xyzx + and r10.yzw, r10.yyzw, r13.xxyz + iadd r9.xyz, -r9.yzwy, r10.yzwy + movc r9.xyz, r12.xyzx, r9.xyzx, r13.xyzx + movc r9.xyz, r0.wwww, r9.xyzx, r13.xyzx + iadd r10.yzw, r3.xxyz, r6.yyzw + movc r6.yzw, icb[r1.w + 0].zzzz, r10.yyzw, r6.yyzw + iadd r10.yzw, r3.xxyz, r11.xxyz + movc r10.yzw, icb[r1.w + 0].zzzz, r10.yyzw, r11.xxyz + iadd r11.xyz, r3.xyzx, r9.xyzx + movc r9.xyz, icb[r1.w + 0].zzzz, r11.xyzx, r9.xyzx + ult r11.xy, icb[r1.w + 32].xxxx, l(15, 16, 0, 0) + ishl r0.w, l(1), icb[r1.w + 32].x + iadd r0.w, r0.w, l(-1) + ieq r12.xyz, r0.wwww, r3.xyzx + ieq r13.xyz, r0.wwww, r6.yzwy + ishl r14.xyz, r3.xyzx, l(16) + ishl r15.xyz, r6.yzwy, l(16) + iadd r14.xyz, r14.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + iadd r15.xyz, r15.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + ushr r14.xyz, r14.xyzx, icb[r1.w + 32].x + ushr r15.xyz, r15.xyzx, icb[r1.w + 32].x + movc r12.xyz, r12.xyzx, l(0x0000ffff,0x0000ffff,0x0000ffff,0), r14.xyzx + movc r13.xyz, r13.xyzx, l(0x0000ffff,0x0000ffff,0x0000ffff,0), r15.xyzx + movc r12.xyz, r3.xyzx, r12.xyzx, l(0,0,0,0) + movc r13.xyz, r6.yzwy, r13.xyzx, l(0,0,0,0) + movc r12.xyz, r11.xxxx, r12.xyzx, r3.xyzx + movc r13.xyz, r11.xxxx, r13.xyzx, r6.yzwy + ige r14.xyz, r3.xyzx, l(0, 0, 0, 0) + ige r15.xyz, r6.yzwy, l(0, 0, 0, 0) + imax r16.xyz, -r3.xyzx, r3.xyzx + imax r17.xyz, -r6.yzwy, r6.yzwy + ige r18.xyz, r16.xyzx, r10.xxxx + ige r19.xyz, r17.xyzx, r10.xxxx + ishl r20.xyz, r16.xyzx, l(15) + ishl r21.xyz, r17.xyzx, l(15) + iadd r20.xyz, r20.xyzx, l(0x00004000, 0x00004000, 0x00004000, 0) + iadd r21.xyz, r21.xyzx, l(0x00004000, 0x00004000, 0x00004000, 0) + ushr r20.xyz, r20.xyzx, r6.x + ushr r21.xyz, r21.xyzx, r6.x + movc r18.xyz, r18.xyzx, l(0x00007fff,0x00007fff,0x00007fff,0), r20.xyzx + movc r19.xyz, r19.xyzx, l(0x00007fff,0x00007fff,0x00007fff,0), r21.xyzx + movc r16.xyz, r16.xyzx, r18.xyzx, l(0,0,0,0) + movc r17.xyz, r17.xyzx, r19.xyzx, l(0,0,0,0) + ineg r18.xyz, r16.xyzx + ineg r19.xyz, r17.xyzx + movc r14.xyz, r14.xyzx, r16.xyzx, r18.xyzx + movc r15.xyz, r15.xyzx, r17.xyzx, r19.xyzx + movc r3.xyz, r11.yyyy, r14.xyzx, r3.xyzx + movc r6.yzw, r11.yyyy, r15.xxyz, r6.yyzw + movc r3.xyz, r0.zzzz, r12.xyzx, r3.xyzx + movc r6.yzw, r0.zzzz, r13.xxyz, r6.yyzw + ieq r12.xyz, r0.wwww, r10.yzwy + ieq r13.xyz, r0.wwww, r9.xyzx + ishl r14.xyz, r10.yzwy, l(16) + ishl r15.xyz, r9.xyzx, l(16) + iadd r14.xyz, r14.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + iadd r15.xyz, r15.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + ushr r14.xyz, r14.xyzx, icb[r1.w + 32].x + ushr r15.xyz, r15.xyzx, icb[r1.w + 32].x + movc r12.xyz, r12.xyzx, l(0x0000ffff,0x0000ffff,0x0000ffff,0), r14.xyzx + movc r13.xyz, r13.xyzx, l(0x0000ffff,0x0000ffff,0x0000ffff,0), r15.xyzx + movc r12.xyz, r10.yzwy, r12.xyzx, l(0,0,0,0) + movc r13.xyz, r9.xyzx, r13.xyzx, l(0,0,0,0) + movc r12.xyz, r11.xxxx, r12.xyzx, r10.yzwy + movc r11.xzw, r11.xxxx, r13.xxyz, r9.xxyz + ige r13.xyz, r10.yzwy, l(0, 0, 0, 0) + ige r14.xyz, r9.xyzx, l(0, 0, 0, 0) + imax r15.xyz, -r10.yzwy, r10.yzwy + imax r16.xyz, -r9.xyzx, r9.xyzx + ige r17.xyz, r15.xyzx, r10.xxxx + ige r18.xyz, r16.xyzx, r10.xxxx + ishl r19.xyz, r15.xyzx, l(15) + ishl r20.xyz, r16.xyzx, l(15) + iadd r19.xyz, r19.xyzx, l(0x00004000, 0x00004000, 0x00004000, 0) + iadd r20.xyz, r20.xyzx, l(0x00004000, 0x00004000, 0x00004000, 0) + ushr r19.xyz, r19.xyzx, r6.x + ushr r20.xyz, r20.xyzx, r6.x + movc r17.xyz, r17.xyzx, l(0x00007fff,0x00007fff,0x00007fff,0), r19.xyzx + movc r18.xyz, r18.xyzx, l(0x00007fff,0x00007fff,0x00007fff,0), r20.xyzx + movc r15.xyz, r15.xyzx, r17.xyzx, l(0,0,0,0) + movc r16.xyz, r16.xyzx, r18.xyzx, l(0,0,0,0) + ineg r17.xyz, r15.xyzx + ineg r18.xyz, r16.xyzx + movc r13.xyz, r13.xyzx, r15.xyzx, r17.xyzx + movc r14.xyz, r14.xyzx, r16.xyzx, r18.xyzx + movc r10.xyz, r11.yyyy, r13.xyzx, r10.yzwy + movc r9.xyz, r11.yyyy, r14.xyzx, r9.xyzx + movc r10.xyz, r0.zzzz, r12.xyzx, r10.xyzx + movc r9.xyz, r0.zzzz, r11.xzwx, r9.xyzx + ge r0.w, l(0.000000), r3.w + ge r1.w, l(0.000000), r2.y + mov r5.w, l(0) + mov r6.x, l(0) + loop + uge r7.w, r6.x, l(16) + breakc_nz r7.w + ushr r7.w, icb[r1.z + 0].x, r6.x + and r7.w, r7.w, l(1) + if_nz r7.w + iadd r7.w, r0.y, r6.x + ld_structured r11.xyz, r7.w, l(12), g0.xyzx + iadd r11.xyz, -r8.xyzx, r11.xyzx + itof r11.xyz, r11.xyzx + dp3 r7.w, r7.xyzx, r11.xyzx + ge r8.w, l(0.000000), r7.w + or r8.w, r0.w, r8.w + lt r9.w, r7.w, r3.w + mul r7.w, r7.w, l(63.499989) + div r7.w, r7.w, r3.w + ftou r7.w, r7.w + movc r7.w, r9.w, icb[r7.w + 46].x, l(7) + movc r7.w, r8.w, l(0), r7.w + iadd r8.w, l(64), -icb[r7.w + 0].w + imul null, r11.xyz, r9.xyzx, icb[r7.w + 0].wwww + imad r11.xyz, r10.xyzx, r8.wwww, r11.xyzx + iadd r11.xyz, r11.xyzx, l(32, 32, 32, 0) + ishr r11.xyz, r11.xyzx, l(6) + imul null, r12.xyz, r11.xyzx, l(31, 31, 31, 0) + ishr r13.xyz, r12.xyzx, l(6) + ilt r14.xyz, r11.xyzx, l(0, 0, 0, 0) + imul null, r11.xyz, r11.xyzx, l(-31, -31, -31, 0) + ishr r11.xyz, r11.xyzx, l(5) + ineg r11.xyz, r11.xyzx + ishr r12.xyz, r12.xyzx, l(5) + movc r11.xyz, r14.xyzx, r11.xyzx, r12.xyzx + ilt r12.xyz, r11.xyzx, l(0, 0, 0, 0) + ineg r14.xyz, r11.xyzx + or r14.xyz, r14.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + movc r11.xyz, r12.xyzx, r14.xyzx, r11.xyzx + movc r11.xyz, r0.zzzz, r13.xyzx, r11.xyzx + else + iadd r7.w, r0.y, r6.x + ld_structured r12.xyz, r7.w, l(12), g0.xyzx + iadd r12.xyz, -r5.xyzx, r12.xyzx + itof r12.xyz, r12.xyzx + dp3 r7.w, r4.xyzx, r12.xyzx + ge r8.w, l(0.000000), r7.w + or r8.w, r1.w, r8.w + lt r9.w, r7.w, r2.y + mul r7.w, r7.w, l(63.499989) + div r7.w, r7.w, r2.y + ftou r7.w, r7.w + movc r7.w, r9.w, icb[r7.w + 46].x, l(7) + movc r7.w, r8.w, l(0), r7.w + iadd r8.w, l(64), -icb[r7.w + 0].w + imul null, r12.xyz, r6.yzwy, icb[r7.w + 0].wwww + imad r12.xyz, r3.xyzx, r8.wwww, r12.xyzx + iadd r12.xyz, r12.xyzx, l(32, 32, 32, 0) + ishr r12.xyz, r12.xyzx, l(6) + imul null, r13.xyz, r12.xyzx, l(31, 31, 31, 0) + ishr r14.xyz, r13.xyzx, l(6) + ilt r15.xyz, r12.xyzx, l(0, 0, 0, 0) + imul null, r12.xyz, r12.xyzx, l(-31, -31, -31, 0) + ishr r12.xyz, r12.xyzx, l(5) + ineg r12.xyz, r12.xyzx + ishr r13.xyz, r13.xyzx, l(5) + movc r12.xyz, r15.xyzx, r12.xyzx, r13.xyzx + ilt r13.xyz, r12.xyzx, l(0, 0, 0, 0) + ineg r15.xyz, r12.xyzx + or r15.xyz, r15.xyzx, l(0x00008000, 0x00008000, 0x00008000, 0) + movc r12.xyz, r13.xyzx, r15.xyzx, r12.xyzx + movc r11.xyz, r0.zzzz, r14.xyzx, r12.xyzx + endif + and r12.xy, r11.xxxx, l(1023, 0x00007c00, 0, 0) + if_nz r12.y + ushr r7.w, r11.x, l(10) + and r7.w, r7.w, l(31) + else + if_nz r12.x + ishl r8.w, r12.x, l(1) + mov r9.w, r8.w + mov r7.w, l(0) + loop + and r10.w, r9.w, l(1024) + breakc_nz r10.w + iadd r7.w, r7.w, l(-1) + ishl r9.w, r9.w, l(1) + endloop + and r12.x, r9.w, l(1022) + else + mov r12.x, l(0) + mov r7.w, l(-112) + endif + endif + ishl r8.w, r11.x, l(16) + and r8.w, r8.w, l(0x80000000) + ishl r10.w, r7.w, l(23) + iadd r10.w, r10.w, l(0x38000000) + or r8.w, r8.w, r10.w + ishl r10.w, r12.x, l(13) + iadd r12.x, r8.w, r10.w + and r11.xw, r11.yyyy, l(1023, 0, 0, 0x00007c00) + if_nz r11.w + ushr r8.w, r11.y, l(10) + and r8.w, r8.w, l(31) + else + if_nz r11.x + ishl r10.w, r11.x, l(1) + mov r11.w, r10.w + mov r8.w, l(0) + loop + and r12.w, r11.w, l(1024) + breakc_nz r12.w + iadd r8.w, r8.w, l(-1) + ishl r11.w, r11.w, l(1) + endloop + and r11.x, r11.w, l(1022) + else + mov r11.x, l(0) + mov r8.w, l(-112) + endif + endif + ishl r10.w, r11.y, l(16) + and r10.w, r10.w, l(0x80000000) + ishl r11.y, r8.w, l(23) + iadd r11.y, r11.y, l(0x38000000) + or r10.w, r10.w, r11.y + ishl r11.x, r11.x, l(13) + iadd r12.y, r10.w, r11.x + and r11.xy, r11.zzzz, l(1023, 0x00007c00, 0, 0) + if_nz r11.y + ushr r10.w, r11.z, l(10) + and r10.w, r10.w, l(31) + else + if_nz r11.x + ishl r11.y, r11.x, l(1) + mov r12.w, r11.y + mov r10.w, l(0) + loop + and r13.x, r12.w, l(1024) + breakc_nz r13.x + iadd r10.w, r10.w, l(-1) + ishl r12.w, r12.w, l(1) + endloop + and r11.x, r12.w, l(1022) + else + mov r11.x, l(0) + mov r10.w, l(-112) + endif + endif + ishl r11.y, r11.z, l(16) + and r11.y, r11.y, l(0x80000000) + ishl r11.z, r10.w, l(23) + iadd r11.z, r11.z, l(0x38000000) + or r11.y, r11.z, r11.y + ishl r11.x, r11.x, l(13) + iadd r12.z, r11.x, r11.y + iadd r11.x, r0.y, r6.x + ld_structured r13.xyz, r11.x, l(24), g0.xyzx + add r11.xyz, r12.xyzx, -r13.xyzx + dp3 r11.x, r11.xyzx, r11.xyzx + add r5.w, r5.w, r11.x + iadd r6.x, r6.x, l(1) + endloop + movc r1.x, r4.w, l(100000002004087730000.000000), r5.w + iadd r1.y, cb0[0].w, l(1) + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(40), r1.xyzx +endif +sync_g_t +if_nz r2.x + ld_structured r3.x, vThreadIDInGroupFlattened.x, l(40), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(16) + ld_structured r4.yzw, r0.y, l(40), g0.xxyz + lt r0.z, r4.y, r3.x + if_nz r0.z + ld_structured r4.x, r0.y, l(40), g0.xxxx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(40), r4.xzwx + endif +endif +sync_g_t +if_nz r2.z + ld_structured r3.x, vThreadIDInGroupFlattened.x, l(40), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(8) + ld_structured r4.yzw, r0.y, l(40), g0.xxyz + lt r0.z, r4.y, r3.x + if_nz r0.z + ld_structured r4.x, r0.y, l(40), g0.xxxx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(40), r4.xzwx + endif +endif +sync_g_t +if_nz r2.w + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(40), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(4) + ld_structured r3.yzw, r0.y, l(40), g0.xxyz + lt r0.z, r3.y, r2.x + if_nz r0.z + ld_structured r3.x, r0.y, l(40), g0.xxxx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(40), r3.xzwx + endif +endif +sync_g_t +ult r0.yz, r1.zzzz, l(0, 2, 1, 0) +if_nz r0.y + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(40), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(2) + ld_structured r2.yzw, r0.y, l(40), g0.xxyz + lt r0.w, r2.y, r1.x + if_nz r0.w + ld_structured r2.x, r0.y, l(40), g0.xxxx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(40), r2.xzwx + endif +endif +sync_g_t +if_nz r0.z + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(40), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(1) + ld_structured r2.yzw, r0.y, l(40), g0.xxyz + lt r0.z, r2.y, r1.x + if_nz r0.z + ld_structured r2.x, r0.y, l(40), g0.xxxx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(40), r2.xzwx + endif + ld_structured r1.x, r0.x, l(0), t1.xxxx + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(40), g0.xxxx + lt r0.y, r2.x, r1.x + if_nz r0.y + ld_structured r1.xyz, vThreadIDInGroupFlattened.x, l(40), g0.xyzx + mov r1.w, l(0) + else + ld_structured r1.xyzw, r0.x, l(0), t1.xyzw + endif + store_structured u0.xyzw, r0.x, l(0), r1.xyzw +endif +ret +// Approximately 0 instruction slots used +#endif + +const BYTE BC6HEncode_TryModeLE10CS[] = +{ + 68, 88, 66, 67, 161, 2, + 137, 126, 42, 47, 246, 175, + 125, 91, 68, 30, 201, 32, + 221, 116, 1, 0, 0, 0, + 76, 96, 0, 0, 3, 0, + 0, 0, 44, 0, 0, 0, + 60, 0, 0, 0, 76, 0, + 0, 0, 73, 83, 71, 78, + 8, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 79, 83, 71, 78, 8, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 83, 72, + 69, 88, 248, 95, 0, 0, + 64, 0, 5, 0, 254, 23, + 0, 0, 106, 8, 0, 1, + 53, 24, 0, 0, 186, 1, + 0, 0, 204, 204, 0, 0, + 15, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 136, 136, 0, 0, 15, 0, + 0, 0, 255, 255, 255, 255, + 9, 0, 0, 0, 238, 238, + 0, 0, 15, 0, 0, 0, + 255, 255, 255, 255, 18, 0, + 0, 0, 200, 236, 0, 0, + 15, 0, 0, 0, 255, 255, + 255, 255, 27, 0, 0, 0, + 128, 200, 0, 0, 15, 0, + 0, 0, 255, 255, 255, 255, + 37, 0, 0, 0, 236, 254, + 0, 0, 15, 0, 0, 0, + 255, 255, 255, 255, 46, 0, + 0, 0, 200, 254, 0, 0, + 15, 0, 0, 0, 255, 255, + 255, 255, 55, 0, 0, 0, + 128, 236, 0, 0, 15, 0, + 0, 0, 255, 255, 255, 255, + 64, 0, 0, 0, 0, 200, + 0, 0, 15, 0, 0, 0, + 255, 255, 255, 255, 0, 0, + 0, 0, 236, 255, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 128, 254, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 232, + 0, 0, 15, 0, 0, 0, + 255, 255, 255, 255, 0, 0, + 0, 0, 232, 255, 0, 0, + 15, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 0, 255, 0, 0, 15, 0, + 0, 0, 255, 255, 255, 255, + 0, 0, 0, 0, 240, 255, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 240, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 16, 247, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 142, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 113, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 206, 8, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 140, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 16, 115, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 49, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 206, 140, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 140, 8, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 16, 49, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 102, 102, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 108, 54, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 232, 23, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 240, 15, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 142, 113, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 156, 57, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 5, 0, 0, 0, + 5, 0, 0, 0, 5, 0, + 0, 0, 7, 0, 0, 0, + 6, 0, 0, 0, 6, 0, + 0, 0, 6, 0, 0, 0, + 11, 0, 0, 0, 5, 0, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 11, 0, + 0, 0, 4, 0, 0, 0, + 5, 0, 0, 0, 4, 0, + 0, 0, 11, 0, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 5, 0, 0, 0, + 9, 0, 0, 0, 5, 0, + 0, 0, 5, 0, 0, 0, + 5, 0, 0, 0, 8, 0, + 0, 0, 6, 0, 0, 0, + 5, 0, 0, 0, 5, 0, + 0, 0, 8, 0, 0, 0, + 5, 0, 0, 0, 6, 0, + 0, 0, 5, 0, 0, 0, + 8, 0, 0, 0, 5, 0, + 0, 0, 5, 0, 0, 0, + 6, 0, 0, 0, 6, 0, + 0, 0, 6, 0, 0, 0, + 6, 0, 0, 0, 6, 0, + 0, 0, 10, 0, 0, 0, + 10, 0, 0, 0, 10, 0, + 0, 0, 10, 0, 0, 0, + 11, 0, 0, 0, 9, 0, + 0, 0, 9, 0, 0, 0, + 9, 0, 0, 0, 12, 0, + 0, 0, 8, 0, 0, 0, + 8, 0, 0, 0, 8, 0, + 0, 0, 16, 0, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 89, 0, + 0, 4, 70, 142, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 88, 24, 0, 4, + 0, 112, 16, 0, 0, 0, + 0, 0, 85, 85, 0, 0, + 162, 0, 0, 4, 0, 112, + 16, 0, 1, 0, 0, 0, + 16, 0, 0, 0, 158, 0, + 0, 4, 0, 224, 17, 0, + 0, 0, 0, 0, 16, 0, + 0, 0, 95, 0, 0, 2, + 0, 64, 2, 0, 95, 0, + 0, 2, 18, 16, 2, 0, + 104, 0, 0, 2, 24, 0, + 0, 0, 105, 0, 0, 4, + 0, 0, 0, 0, 6, 0, + 0, 0, 4, 0, 0, 0, + 105, 0, 0, 4, 1, 0, + 0, 0, 2, 0, 0, 0, + 4, 0, 0, 0, 160, 0, + 0, 5, 0, 240, 17, 0, + 0, 0, 0, 0, 84, 0, + 0, 0, 64, 0, 0, 0, + 155, 0, 0, 4, 64, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 85, 0, + 0, 6, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 6, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 16, + 2, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 8, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 128, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 6, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 32, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 128, 65, 0, 0, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 79, 0, 0, 10, + 242, 0, 16, 0, 2, 0, + 0, 0, 166, 10, 16, 0, + 1, 0, 0, 0, 2, 64, + 0, 0, 16, 0, 0, 0, + 32, 0, 0, 0, 8, 0, + 0, 0, 4, 0, 0, 0, + 31, 0, 4, 3, 10, 0, + 16, 0, 2, 0, 0, 0, + 78, 0, 0, 9, 66, 0, + 16, 0, 0, 0, 0, 0, + 0, 208, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 26, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 35, 0, 0, 11, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 128, 65, 0, + 0, 0, 0, 0, 0, 0, + 26, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 8, + 194, 0, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 45, 0, + 0, 7, 242, 0, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 70, 126, 16, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 128, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 5, 0, 0, 0, 6, 5, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 127, 255, 255, 127, 0, + 255, 255, 255, 127, 255, 255, + 127, 0, 79, 0, 0, 10, + 194, 0, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 255, 239, 255, 71, + 255, 239, 255, 71, 6, 8, + 16, 0, 5, 0, 0, 0, + 79, 0, 0, 10, 50, 0, + 16, 0, 3, 0, 0, 0, + 134, 0, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 56, 0, 0, + 128, 56, 0, 0, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 50, 0, 16, 0, + 6, 0, 0, 0, 134, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 30, 0, 0, 11, + 50, 0, 16, 0, 6, 0, + 0, 0, 70, 0, 16, 128, + 65, 0, 0, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 113, 0, 0, 0, 113, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 10, 162, 0, 16, 0, + 5, 0, 0, 0, 86, 13, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 128, 0, + 0, 0, 0, 0, 0, 0, + 128, 0, 85, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 85, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 10, 50, 0, 16, 0, + 5, 0, 0, 0, 134, 0, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 200, 0, 0, 0, 200, + 0, 0, 0, 0, 0, 0, + 0, 0, 55, 0, 0, 9, + 50, 0, 16, 0, 3, 0, + 0, 0, 70, 0, 16, 0, + 3, 0, 0, 0, 70, 0, + 16, 0, 7, 0, 0, 0, + 70, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 10, + 50, 0, 16, 0, 5, 0, + 0, 0, 70, 0, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 255, 15, 0, 0, + 255, 15, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 50, 0, + 16, 0, 3, 0, 0, 0, + 70, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 10, 50, 0, 16, 0, + 3, 0, 0, 0, 70, 0, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 50, 0, 16, 0, 3, 0, + 0, 0, 70, 0, 16, 0, + 3, 0, 0, 0, 70, 0, + 16, 0, 5, 0, 0, 0, + 85, 0, 0, 7, 50, 0, + 16, 0, 3, 0, 0, 0, + 70, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 1, 0, + 0, 10, 50, 0, 16, 0, + 3, 0, 0, 0, 70, 0, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 55, 0, 0, 12, + 194, 0, 16, 0, 0, 0, + 0, 0, 166, 14, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 6, 4, 16, 0, 3, 0, + 0, 0, 30, 0, 0, 7, + 50, 0, 16, 0, 5, 0, + 0, 0, 70, 0, 16, 0, + 4, 0, 0, 0, 230, 10, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 0, 0, 0, 0, + 166, 10, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 255, 255, 255, 127, + 255, 255, 127, 0, 79, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 255, 239, 255, 71, + 42, 0, 16, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 128, 56, + 85, 0, 0, 7, 34, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 30, 0, + 0, 8, 34, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 128, 65, 0, 0, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 113, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 128, 0, 85, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 200, + 55, 0, 0, 9, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 255, 15, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 255, 127, 0, 0, + 55, 0, 0, 9, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 127, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 3, 0, 0, 0, 6, 5, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 255, 3, + 0, 0, 0, 124, 0, 0, + 255, 3, 0, 0, 0, 124, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 3, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 18, 0, + 0, 1, 31, 0, 4, 3, + 10, 0, 16, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 66, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 48, 0, + 0, 1, 1, 0, 0, 7, + 34, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 0, 4, 0, 0, + 3, 0, 4, 3, 26, 0, + 16, 0, 3, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 41, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 22, 0, 0, 1, + 1, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 254, 3, 0, 0, 18, 0, + 0, 1, 54, 0, 0, 5, + 18, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 5, 66, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 144, 255, 255, 255, + 21, 0, 0, 1, 21, 0, + 0, 1, 41, 0, 0, 7, + 114, 0, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 128, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 56, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 3, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 18, 0, 0, 1, + 31, 0, 4, 3, 42, 0, + 16, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 66, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 48, 0, 0, 1, + 1, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 0, 4, 0, 0, 3, 0, + 4, 3, 10, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 41, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 22, 0, 0, 1, 1, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 254, 3, + 0, 0, 18, 0, 0, 1, + 54, 0, 0, 5, 66, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 66, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 144, 255, 255, 255, 21, 0, + 0, 1, 21, 0, 0, 1, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 56, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 0, 0, + 0, 0, 166, 10, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 255, 3, + 0, 0, 0, 124, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 18, 0, 0, 1, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 48, 0, 0, 1, + 1, 0, 0, 7, 34, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 0, 4, 0, 0, 3, 0, + 4, 3, 26, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 41, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 22, 0, 0, 1, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 254, 3, + 0, 0, 18, 0, 0, 1, + 54, 0, 0, 8, 194, 0, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 144, 255, + 255, 255, 21, 0, 0, 1, + 21, 0, 0, 1, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 56, + 60, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 16, 0, 0, 10, 130, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 208, 179, 89, 62, 89, 23, + 55, 63, 152, 221, 147, 61, + 0, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 32, 0, 0, 8, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 95, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 78, 0, 0, 11, 114, 0, + 16, 0, 3, 0, 0, 0, + 0, 208, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 31, 0, + 0, 0, 31, 0, 0, 0, + 31, 0, 0, 0, 0, 0, + 0, 0, 79, 0, 0, 10, + 114, 0, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 128, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 255, 123, 0, 0, 255, 123, + 0, 0, 255, 123, 0, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 78, 0, 0, 11, + 114, 0, 16, 0, 7, 0, + 0, 0, 0, 208, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 31, 0, 0, 0, 31, 0, + 0, 0, 31, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 224, 255, + 15, 0, 224, 255, 15, 0, + 224, 255, 15, 0, 0, 0, + 0, 0, 78, 0, 0, 11, + 114, 0, 16, 0, 5, 0, + 0, 0, 0, 208, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 31, 0, 0, 0, 31, 0, + 0, 0, 31, 0, 0, 0, + 0, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 1, 128, 255, 255, 1, 128, + 255, 255, 1, 128, 255, 255, + 0, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 3, 0, 0, 0, + 166, 10, 16, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 21, 0, 0, 1, + 190, 24, 0, 1, 31, 0, + 4, 3, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 127, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 127, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 127, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 128, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 128, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 128, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 127, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 127, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 127, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 128, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 128, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 128, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 127, 127, 54, 0, + 0, 6, 34, 48, 32, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 127, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 127, 127, 54, 0, + 0, 6, 34, 48, 32, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 127, 255, 54, 0, + 0, 5, 66, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 80, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 3, 0, 4, 3, + 58, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 85, 0, 0, 8, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 144, 144, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 48, 32, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 49, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 55, 0, + 0, 9, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 55, 0, + 0, 9, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 55, 0, + 0, 9, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 55, 0, + 0, 9, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 48, + 32, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 49, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 55, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 55, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 55, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 55, 0, 0, 9, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 18, 0, 0, 1, + 54, 0, 0, 6, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 48, 32, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 49, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 9, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 55, 0, + 0, 9, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 55, 0, + 0, 9, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 55, 0, + 0, 9, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 48, + 32, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 49, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 55, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 55, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 55, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 55, 0, 0, 9, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 21, 0, 0, 1, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 54, 0, 0, 6, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 3, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 54, 0, 0, 6, + 66, 0, 16, 0, 3, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 1, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 40, 0, 0, 5, + 50, 0, 16, 0, 4, 0, + 0, 0, 230, 10, 16, 0, + 0, 0, 0, 0, 40, 0, + 0, 5, 66, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 43, 0, + 0, 5, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 16, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 6, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 43, 0, 0, 5, + 114, 0, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 16, 0, + 0, 7, 130, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 49, 0, 0, 7, + 18, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 29, 0, 0, 7, 34, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 18, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 56, 0, 0, 7, + 130, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 253, 255, 125, 66, + 14, 0, 0, 7, 130, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 28, 0, + 0, 5, 130, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 79, 0, 0, 7, 130, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 55, 0, 0, 10, + 114, 0, 16, 0, 4, 0, + 0, 0, 246, 15, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 128, 65, 0, 0, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 55, 0, 0, 9, 50, 0, + 16, 0, 5, 0, 0, 0, + 246, 15, 16, 0, 3, 0, + 0, 0, 70, 0, 16, 0, + 3, 0, 0, 0, 230, 10, + 16, 0, 0, 0, 0, 0, + 55, 0, 0, 9, 66, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 55, 0, 0, 9, 50, 0, + 16, 0, 6, 0, 0, 0, + 246, 15, 16, 0, 3, 0, + 0, 0, 230, 10, 16, 0, + 0, 0, 0, 0, 70, 0, + 16, 0, 3, 0, 0, 0, + 55, 0, 0, 9, 66, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 1, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 40, 0, 0, 5, 50, 0, + 16, 0, 7, 0, 0, 0, + 230, 10, 16, 0, 0, 0, + 0, 0, 40, 0, 0, 5, + 66, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 43, 0, 0, 5, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 16, 0, + 0, 7, 130, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 8, + 130, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 26, 144, + 144, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 43, 0, 0, 5, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 16, 0, + 0, 7, 130, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 49, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 29, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 56, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 253, 255, 125, 66, + 14, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 28, 0, + 0, 5, 130, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 79, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 55, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 246, 15, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 128, 65, 0, 0, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 55, 0, 0, 9, 50, 0, + 16, 0, 8, 0, 0, 0, + 246, 15, 16, 0, 4, 0, + 0, 0, 70, 0, 16, 0, + 3, 0, 0, 0, 230, 10, + 16, 0, 0, 0, 0, 0, + 55, 0, 0, 9, 66, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 55, 0, 0, 9, 50, 0, + 16, 0, 9, 0, 0, 0, + 246, 15, 16, 0, 4, 0, + 0, 0, 230, 10, 16, 0, + 0, 0, 0, 0, 70, 0, + 16, 0, 3, 0, 0, 0, + 55, 0, 0, 9, 66, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 32, 0, 0, 11, 194, 0, + 16, 0, 0, 0, 0, 0, + 166, 138, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 95, 0, 0, 0, 96, 0, + 0, 0, 31, 0, 4, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 33, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 144, 208, 0, + 32, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 1, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 55, 0, 0, 15, 114, 0, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 15, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 114, 0, + 16, 0, 10, 0, 0, 0, + 6, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 60, 0, + 0, 7, 114, 0, 16, 0, + 11, 0, 0, 0, 6, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 32, 0, 0, 10, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 255, 255, + 0, 0, 0, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 0, 0, 255, 255, + 0, 0, 255, 255, 0, 0, + 0, 0, 0, 0, 41, 0, + 0, 9, 34, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 10, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 41, 0, 0, 9, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 10, 144, + 208, 0, 32, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 41, 0, 0, 9, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 10, 144, + 208, 0, 32, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 42, 0, 0, 7, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 15, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 86, 5, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 86, 5, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 55, 0, + 0, 15, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 15, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 114, 0, 16, 0, + 12, 0, 0, 0, 6, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 60, 0, 0, 7, + 114, 0, 16, 0, 13, 0, + 0, 0, 6, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 0, 0, 255, 255, + 0, 0, 255, 255, 0, 0, + 0, 0, 0, 0, 32, 0, + 0, 10, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 41, 0, 0, 9, + 114, 0, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 10, 144, + 208, 0, 32, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 41, 0, 0, 9, + 114, 0, 16, 0, 17, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 10, 144, + 208, 0, 32, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 16, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 42, 0, 0, 7, 114, 0, + 16, 0, 17, 0, 0, 0, + 70, 2, 16, 0, 17, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 86, 5, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 16, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 86, 5, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 17, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 18, 0, + 0, 1, 54, 0, 0, 6, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 33, 0, 0, 9, + 130, 0, 16, 0, 4, 0, + 0, 0, 10, 144, 208, 0, + 32, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 55, 0, 0, 15, 114, 0, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 15, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 114, 0, + 16, 0, 13, 0, 0, 0, + 246, 15, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 60, 0, + 0, 7, 114, 0, 16, 0, + 14, 0, 0, 0, 246, 15, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 33, 0, 0, 10, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 33, 0, 0, 10, 114, 0, + 16, 0, 16, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 32, 0, + 0, 10, 114, 0, 16, 0, + 17, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 32, 0, 0, 10, + 114, 0, 16, 0, 18, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 9, 130, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 10, 144, 208, 0, + 32, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 41, 0, 0, 7, + 114, 0, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 20, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 19, 0, 0, 0, 70, 2, + 16, 0, 19, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 20, 0, + 0, 0, 70, 2, 16, 0, + 20, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 17, 0, 0, 0, + 70, 2, 16, 0, 17, 0, + 0, 0, 246, 15, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 19, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 18, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 246, 15, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 20, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 19, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 20, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 32, 0, + 0, 10, 114, 0, 16, 0, + 21, 0, 0, 0, 70, 2, + 16, 0, 19, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 32, 0, 0, 10, + 114, 0, 16, 0, 22, 0, + 0, 0, 70, 2, 16, 0, + 20, 0, 0, 0, 2, 64, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 8, 130, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 128, 65, 0, + 0, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 19, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 20, 0, 0, 0, + 70, 2, 16, 0, 20, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 19, 0, 0, 0, 70, 2, + 16, 0, 19, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 20, 0, + 0, 0, 70, 2, 16, 0, + 20, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 19, 0, 0, 0, + 70, 2, 16, 0, 19, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 20, 0, + 0, 0, 70, 2, 16, 0, + 20, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 19, 0, 0, 0, 70, 2, + 16, 0, 21, 0, 0, 0, + 246, 15, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 19, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 20, 0, 0, 0, 70, 2, + 16, 0, 22, 0, 0, 0, + 246, 15, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 20, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 17, 0, + 0, 0, 70, 2, 16, 0, + 19, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 16, 0, 0, 0, 70, 2, + 16, 0, 16, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 70, 2, 16, 0, + 20, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 16, 0, 0, 0, 55, 0, + 0, 15, 114, 0, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 15, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 114, 0, 16, 0, + 6, 0, 0, 0, 246, 15, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 60, 0, 0, 7, + 114, 0, 16, 0, 13, 0, + 0, 0, 246, 15, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 33, 0, 0, 10, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 33, 0, + 0, 10, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 32, 0, 0, 10, + 114, 0, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 0, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 17, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 18, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 0, 7, 114, 0, + 16, 0, 18, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 19, 0, 0, 0, 70, 2, + 16, 0, 19, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 16, 0, 0, 0, 246, 15, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 17, 0, + 0, 0, 70, 2, 16, 0, + 17, 0, 0, 0, 246, 15, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 19, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 18, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 19, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 32, 0, 0, 10, 114, 0, + 16, 0, 20, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 32, 0, + 0, 10, 114, 0, 16, 0, + 21, 0, 0, 0, 70, 2, + 16, 0, 19, 0, 0, 0, + 2, 64, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 255, 127, 0, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 18, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 19, 0, 0, 0, + 70, 2, 16, 0, 19, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 18, 0, 0, 0, 70, 2, + 16, 0, 18, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 19, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 18, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 19, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 18, 0, 0, 0, 70, 2, + 16, 0, 20, 0, 0, 0, + 246, 15, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 19, 0, 0, 0, 70, 2, + 16, 0, 21, 0, 0, 0, + 246, 15, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 19, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 17, 0, + 0, 0, 70, 2, 16, 0, + 19, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 21, 0, + 0, 1, 30, 0, 0, 8, + 114, 0, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 128, + 65, 0, 0, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 128, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 10, 114, 0, 16, 0, + 6, 0, 0, 0, 166, 154, + 144, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 30, 0, 0, 8, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 128, + 65, 0, 0, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 55, 0, + 0, 10, 114, 0, 16, 0, + 9, 0, 0, 0, 166, 154, + 144, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 30, 0, 0, 8, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 128, + 65, 0, 0, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 55, 0, + 0, 10, 114, 0, 16, 0, + 3, 0, 0, 0, 166, 154, + 144, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 31, 0, 4, 4, + 42, 144, 144, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 33, 0, 0, 10, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 12, 114, 0, 16, 0, + 12, 0, 0, 0, 2, 64, + 0, 0, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 0, 0, 0, 0, + 150, 151, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 13, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 12, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 13, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 13, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 12, 0, 0, 0, 33, 0, + 0, 7, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 34, 0, + 0, 7, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 60, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 15, 0, 0, 0, 10, 0, + 16, 0, 15, 0, 0, 0, + 60, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 15, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 41, 0, + 0, 9, 18, 0, 16, 0, + 15, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 10, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 41, 0, + 0, 9, 34, 0, 16, 0, + 15, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 26, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 41, 0, + 0, 9, 66, 0, 16, 0, + 15, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 42, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 41, 0, + 0, 9, 130, 0, 16, 0, + 15, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 58, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 10, 242, 0, 16, 0, + 15, 0, 0, 0, 70, 14, + 16, 0, 15, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 1, 0, 0, 7, + 114, 0, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 6, 0, + 16, 0, 15, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 17, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 0, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 17, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 1, 0, + 0, 7, 114, 0, 16, 0, + 18, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 150, 7, 16, 0, 15, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 33, 0, 0, 10, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 33, 0, 0, 7, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 18, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 34, 0, 0, 7, 114, 0, + 16, 0, 18, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 19, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 33, 0, + 0, 10, 114, 0, 16, 0, + 20, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 33, 0, 0, 7, + 114, 0, 16, 0, 21, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 22, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 34, 0, 0, 7, + 114, 0, 16, 0, 22, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 22, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 23, 0, 0, 0, + 70, 2, 16, 0, 20, 0, + 0, 0, 70, 2, 16, 0, + 21, 0, 0, 0, 70, 2, + 16, 0, 22, 0, 0, 0, + 60, 0, 0, 7, 114, 0, + 16, 0, 19, 0, 0, 0, + 70, 2, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 23, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 19, 0, 0, 0, + 10, 0, 16, 0, 19, 0, + 0, 0, 60, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 19, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 60, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 17, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 1, 0, 0, 7, + 114, 0, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 150, 7, + 16, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 18, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 19, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 18, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 21, 0, + 0, 0, 70, 2, 16, 0, + 17, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 1, 0, 0, 7, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 150, 7, 16, 0, + 15, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 22, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 20, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 18, 0, + 0, 1, 41, 0, 0, 9, + 130, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 10, 144, + 208, 0, 32, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 255, 255, 255, 255, + 1, 0, 0, 7, 114, 0, + 16, 0, 16, 0, 0, 0, + 246, 15, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 1, 0, + 0, 7, 114, 0, 16, 0, + 11, 0, 0, 0, 246, 15, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 1, 0, 0, 7, + 114, 0, 16, 0, 12, 0, + 0, 0, 246, 15, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 1, 0, 0, 7, 114, 0, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 246, 15, 16, 0, + 5, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 21, 0, 0, 1, 30, 0, + 0, 12, 242, 0, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 70, 158, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 9, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 1, 0, 0, 7, + 114, 0, 16, 0, 3, 0, + 0, 0, 6, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 16, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 10, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 1, 0, + 0, 7, 226, 0, 16, 0, + 6, 0, 0, 0, 6, 0, + 16, 0, 10, 0, 0, 0, + 6, 9, 16, 0, 16, 0, + 0, 0, 30, 0, 0, 8, + 226, 0, 16, 0, 6, 0, + 0, 0, 6, 0, 16, 128, + 65, 0, 0, 0, 9, 0, + 0, 0, 86, 14, 16, 0, + 6, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 150, 7, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 16, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 3, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 16, 0, 0, 0, 60, 0, + 0, 8, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 42, 144, 144, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 0, 0, 7, 226, 0, + 16, 0, 6, 0, 0, 0, + 86, 14, 16, 0, 9, 0, + 0, 0, 6, 9, 16, 0, + 11, 0, 0, 0, 1, 0, + 0, 7, 114, 0, 16, 0, + 14, 0, 0, 0, 150, 7, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 30, 0, 0, 8, + 114, 0, 16, 0, 14, 0, + 0, 0, 150, 7, 16, 128, + 65, 0, 0, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 6, 0, 0, 0, 86, 14, + 16, 0, 6, 0, 0, 0, + 6, 9, 16, 0, 14, 0, + 0, 0, 6, 9, 16, 0, + 11, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 6, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 86, 14, 16, 0, 6, 0, + 0, 0, 6, 9, 16, 0, + 11, 0, 0, 0, 1, 0, + 0, 7, 114, 0, 16, 0, + 11, 0, 0, 0, 150, 7, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 1, 0, 0, 7, + 114, 0, 16, 0, 14, 0, + 0, 0, 150, 7, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 30, 0, 0, 8, 114, 0, + 16, 0, 14, 0, 0, 0, + 150, 7, 16, 128, 65, 0, + 0, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 11, 0, + 0, 0, 246, 15, 16, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 1, 0, 0, 7, + 114, 0, 16, 0, 12, 0, + 0, 0, 150, 7, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 1, 0, 0, 7, 226, 0, + 16, 0, 10, 0, 0, 0, + 86, 14, 16, 0, 10, 0, + 0, 0, 6, 9, 16, 0, + 13, 0, 0, 0, 30, 0, + 0, 8, 114, 0, 16, 0, + 9, 0, 0, 0, 150, 7, + 16, 128, 65, 0, 0, 0, + 9, 0, 0, 0, 150, 7, + 16, 0, 10, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 9, 0, 0, 0, + 246, 15, 16, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 30, 0, 0, 7, 226, 0, + 16, 0, 10, 0, 0, 0, + 6, 9, 16, 0, 3, 0, + 0, 0, 86, 14, 16, 0, + 6, 0, 0, 0, 55, 0, + 0, 10, 226, 0, 16, 0, + 6, 0, 0, 0, 166, 154, + 144, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 86, 14, + 16, 0, 10, 0, 0, 0, + 86, 14, 16, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 226, 0, 16, 0, 10, 0, + 0, 0, 6, 9, 16, 0, + 3, 0, 0, 0, 6, 9, + 16, 0, 11, 0, 0, 0, + 55, 0, 0, 10, 226, 0, + 16, 0, 10, 0, 0, 0, + 166, 154, 144, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 86, 14, 16, 0, 10, 0, + 0, 0, 6, 9, 16, 0, + 11, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 55, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 166, 154, 144, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 79, 0, 0, 12, 50, 0, + 16, 0, 11, 0, 0, 0, + 6, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 2, 64, + 0, 0, 15, 0, 0, 0, + 16, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 41, 0, 0, 9, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 10, 144, 208, 0, + 32, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 32, 0, + 0, 7, 114, 0, 16, 0, + 12, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 32, 0, 0, 7, + 114, 0, 16, 0, 13, 0, + 0, 0, 246, 15, 16, 0, + 0, 0, 0, 0, 150, 7, + 16, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 15, 0, 0, 0, 150, 7, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 2, 64, + 0, 0, 0, 128, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 15, 0, + 0, 0, 2, 64, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 128, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 9, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 10, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 85, 0, + 0, 9, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 10, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 13, 0, 0, 0, 150, 7, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 12, 0, 0, 0, 6, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 13, 0, 0, 0, 6, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 150, 7, 16, 0, + 6, 0, 0, 0, 33, 0, + 0, 10, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 33, 0, 0, 10, + 114, 0, 16, 0, 15, 0, + 0, 0, 150, 7, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 36, 0, 0, 8, 114, 0, + 16, 0, 16, 0, 0, 0, + 70, 2, 16, 128, 65, 0, + 0, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 36, 0, 0, 8, + 114, 0, 16, 0, 17, 0, + 0, 0, 150, 7, 16, 128, + 65, 0, 0, 0, 6, 0, + 0, 0, 150, 7, 16, 0, + 6, 0, 0, 0, 33, 0, + 0, 7, 114, 0, 16, 0, + 18, 0, 0, 0, 70, 2, + 16, 0, 16, 0, 0, 0, + 6, 0, 16, 0, 10, 0, + 0, 0, 33, 0, 0, 7, + 114, 0, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 17, 0, 0, 0, 6, 0, + 16, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 20, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 21, 0, 0, 0, 70, 2, + 16, 0, 17, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 20, 0, + 0, 0, 70, 2, 16, 0, + 20, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 64, 0, 0, 0, 64, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 21, 0, 0, 0, + 70, 2, 16, 0, 21, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 64, + 0, 0, 0, 64, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 20, 0, 0, 0, 70, 2, + 16, 0, 20, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 21, 0, + 0, 0, 70, 2, 16, 0, + 21, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 18, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 20, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 19, 0, 0, 0, + 70, 2, 16, 0, 19, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 21, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 16, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 17, 0, 0, 0, + 70, 2, 16, 0, 17, 0, + 0, 0, 70, 2, 16, 0, + 19, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 18, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 17, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 17, 0, + 0, 0, 70, 2, 16, 0, + 19, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 3, 0, 0, 0, 86, 5, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 6, 0, 0, 0, 86, 5, + 16, 0, 11, 0, 0, 0, + 6, 9, 16, 0, 15, 0, + 0, 0, 86, 14, 16, 0, + 6, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 3, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 6, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 6, 9, 16, 0, 13, 0, + 0, 0, 86, 14, 16, 0, + 6, 0, 0, 0, 32, 0, + 0, 7, 114, 0, 16, 0, + 12, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 150, 7, 16, 0, 10, 0, + 0, 0, 32, 0, 0, 7, + 114, 0, 16, 0, 13, 0, + 0, 0, 246, 15, 16, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 14, 0, 0, 0, + 150, 7, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 2, 64, + 0, 0, 0, 128, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 15, 0, + 0, 0, 2, 64, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 128, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 9, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 10, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 85, 0, + 0, 9, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 10, 144, 208, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 0, 0, 255, 255, 0, 0, + 255, 255, 0, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 12, 0, 0, 0, 150, 7, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 12, 0, 0, 0, 6, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 150, 7, 16, 0, + 10, 0, 0, 0, 55, 0, + 0, 9, 210, 0, 16, 0, + 11, 0, 0, 0, 6, 0, + 16, 0, 11, 0, 0, 0, + 6, 9, 16, 0, 13, 0, + 0, 0, 6, 9, 16, 0, + 9, 0, 0, 0, 33, 0, + 0, 10, 114, 0, 16, 0, + 13, 0, 0, 0, 150, 7, + 16, 0, 10, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 33, 0, 0, 10, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 36, 0, 0, 8, 114, 0, + 16, 0, 15, 0, 0, 0, + 150, 7, 16, 128, 65, 0, + 0, 0, 10, 0, 0, 0, + 150, 7, 16, 0, 10, 0, + 0, 0, 36, 0, 0, 8, + 114, 0, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 128, + 65, 0, 0, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 33, 0, + 0, 7, 114, 0, 16, 0, + 17, 0, 0, 0, 70, 2, + 16, 0, 15, 0, 0, 0, + 6, 0, 16, 0, 10, 0, + 0, 0, 33, 0, 0, 7, + 114, 0, 16, 0, 18, 0, + 0, 0, 70, 2, 16, 0, + 16, 0, 0, 0, 6, 0, + 16, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 19, 0, 0, 0, + 70, 2, 16, 0, 15, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 20, 0, 0, 0, 70, 2, + 16, 0, 16, 0, 0, 0, + 1, 64, 0, 0, 15, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 19, 0, 0, 0, 2, 64, + 0, 0, 0, 64, 0, 0, + 0, 64, 0, 0, 0, 64, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 20, 0, 0, 0, + 70, 2, 16, 0, 20, 0, + 0, 0, 2, 64, 0, 0, + 0, 64, 0, 0, 0, 64, + 0, 0, 0, 64, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 19, 0, 0, 0, 70, 2, + 16, 0, 19, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 20, 0, + 0, 0, 70, 2, 16, 0, + 20, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 17, 0, 0, 0, + 70, 2, 16, 0, 17, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 19, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 18, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 2, 64, 0, 0, + 255, 127, 0, 0, 255, 127, + 0, 0, 255, 127, 0, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 20, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 17, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 12, 114, 0, + 16, 0, 16, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 17, 0, 0, 0, + 70, 2, 16, 0, 15, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 18, 0, + 0, 0, 70, 2, 16, 0, + 16, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 17, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 10, 0, 0, 0, 86, 5, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 150, 7, 16, 0, + 10, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 9, 0, 0, 0, 86, 5, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 10, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 9, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 134, 3, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 29, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 29, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 48, 0, + 0, 1, 80, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 3, 0, 4, 3, 58, 0, + 16, 0, 7, 0, 0, 0, + 85, 0, 0, 8, 130, 0, + 16, 0, 7, 0, 0, 0, + 10, 144, 144, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 11, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 8, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 128, 65, 0, 0, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 43, 0, 0, 5, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 16, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 29, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 49, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 56, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 253, 255, 125, 66, 14, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 28, 0, 0, 5, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 55, 0, + 0, 11, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 10, 144, 208, 0, 46, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 55, 0, 0, 9, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 9, 130, 0, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 64, 0, + 0, 0, 58, 144, 144, 128, + 65, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 38, 0, 0, 9, 0, 208, + 0, 0, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 246, 159, 144, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 35, 0, 0, 9, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 10, 0, + 0, 0, 246, 15, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 2, 64, 0, 0, + 32, 0, 0, 0, 32, 0, + 0, 0, 32, 0, 0, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 38, 0, 0, 11, + 0, 208, 0, 0, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 2, 64, 0, 0, + 31, 0, 0, 0, 31, 0, + 0, 0, 31, 0, 0, 0, + 0, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 34, 0, 0, 10, + 114, 0, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 38, 0, 0, 11, 0, 208, + 0, 0, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 2, 64, 0, 0, 225, 255, + 255, 255, 225, 255, 255, 255, + 225, 255, 255, 255, 0, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 42, 0, 0, 7, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 34, 0, 0, 10, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 40, 0, + 0, 5, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 60, 0, 0, 10, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 2, 64, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 128, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 14, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 11, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 18, 0, + 0, 1, 30, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 12, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 8, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 128, 65, 0, + 0, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 43, 0, 0, 5, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 16, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 29, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 60, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 49, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 56, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 253, 255, 125, 66, + 14, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 28, 0, + 0, 5, 130, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 55, 0, 0, 11, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 10, 144, 208, 0, + 46, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 55, 0, 0, 9, + 130, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 30, 0, 0, 9, + 130, 0, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 58, 144, + 144, 128, 65, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 38, 0, 0, 9, + 0, 208, 0, 0, 114, 0, + 16, 0, 12, 0, 0, 0, + 150, 7, 16, 0, 6, 0, + 0, 0, 246, 159, 144, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 35, 0, 0, 9, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 246, 15, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 32, 0, 0, 0, 32, 0, + 0, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 38, 0, + 0, 11, 0, 208, 0, 0, + 114, 0, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 2, 64, + 0, 0, 31, 0, 0, 0, + 31, 0, 0, 0, 31, 0, + 0, 0, 0, 0, 0, 0, + 42, 0, 0, 7, 114, 0, + 16, 0, 14, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 34, 0, + 0, 10, 114, 0, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 38, 0, 0, 11, + 0, 208, 0, 0, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 2, 64, 0, 0, + 225, 255, 255, 255, 225, 255, + 255, 255, 225, 255, 255, 255, + 0, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 42, 0, + 0, 7, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 34, 0, 0, 10, + 114, 0, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 40, 0, 0, 5, 114, 0, + 16, 0, 15, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 60, 0, 0, 10, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 2, 64, + 0, 0, 0, 128, 0, 0, + 0, 128, 0, 0, 0, 128, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 15, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 55, 0, 0, 9, 114, 0, + 16, 0, 11, 0, 0, 0, + 166, 10, 16, 0, 0, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 21, 0, 0, 1, 1, 0, + 0, 10, 50, 0, 16, 0, + 12, 0, 0, 0, 6, 0, + 16, 0, 11, 0, 0, 0, + 2, 64, 0, 0, 255, 3, + 0, 0, 0, 124, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 12, 0, + 0, 0, 85, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 11, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 18, 0, + 0, 1, 31, 0, 4, 3, + 10, 0, 16, 0, 12, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 12, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 48, 0, + 0, 1, 1, 0, 0, 7, + 130, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 0, 4, 0, 0, + 3, 0, 4, 3, 58, 0, + 16, 0, 10, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 41, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 22, 0, 0, 1, + 1, 0, 0, 7, 18, 0, + 16, 0, 12, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 254, 3, 0, 0, 18, 0, + 0, 1, 54, 0, 0, 5, + 18, 0, 16, 0, 12, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 144, 255, 255, 255, + 21, 0, 0, 1, 21, 0, + 0, 1, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 11, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 128, 41, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 56, + 60, 0, 0, 7, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 10, 0, + 16, 0, 12, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 12, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 1, 0, 0, 10, 146, 0, + 16, 0, 11, 0, 0, 0, + 86, 5, 16, 0, 11, 0, + 0, 0, 2, 64, 0, 0, + 255, 3, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 124, 0, 0, 31, 0, + 4, 3, 58, 0, 16, 0, + 11, 0, 0, 0, 85, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 10, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 18, 0, 0, 1, 31, 0, + 4, 3, 10, 0, 16, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 10, 0, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 11, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 1, 0, + 0, 7, 130, 0, 16, 0, + 12, 0, 0, 0, 58, 0, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 0, 4, + 0, 0, 3, 0, 4, 3, + 58, 0, 16, 0, 12, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 255, 255, 255, 255, + 41, 0, 0, 7, 130, 0, + 16, 0, 11, 0, 0, 0, + 58, 0, 16, 0, 11, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 1, 0, 0, 7, + 18, 0, 16, 0, 11, 0, + 0, 0, 58, 0, 16, 0, + 11, 0, 0, 0, 1, 64, + 0, 0, 254, 3, 0, 0, + 18, 0, 0, 1, 54, 0, + 0, 5, 18, 0, 16, 0, + 11, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 144, 255, + 255, 255, 21, 0, 0, 1, + 21, 0, 0, 1, 41, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 128, + 41, 0, 0, 7, 34, 0, + 16, 0, 11, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 11, 0, 0, 0, 26, 0, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 56, 60, 0, 0, 7, + 130, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 11, 0, 0, 0, + 10, 0, 16, 0, 11, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 12, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 10, 0, 16, 0, 11, 0, + 0, 0, 1, 0, 0, 10, + 50, 0, 16, 0, 11, 0, + 0, 0, 166, 10, 16, 0, + 11, 0, 0, 0, 2, 64, + 0, 0, 255, 3, 0, 0, + 0, 124, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 11, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 11, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 18, 0, 0, 1, + 31, 0, 4, 3, 10, 0, + 16, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 11, 0, 0, 0, + 10, 0, 16, 0, 11, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 12, 0, 0, 0, 26, 0, + 16, 0, 11, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 10, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 48, 0, 0, 1, + 1, 0, 0, 7, 18, 0, + 16, 0, 13, 0, 0, 0, + 58, 0, 16, 0, 12, 0, + 0, 0, 1, 64, 0, 0, + 0, 4, 0, 0, 3, 0, + 4, 3, 10, 0, 16, 0, + 13, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 41, 0, 0, 7, + 130, 0, 16, 0, 12, 0, + 0, 0, 58, 0, 16, 0, + 12, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 22, 0, 0, 1, 1, 0, + 0, 7, 18, 0, 16, 0, + 11, 0, 0, 0, 58, 0, + 16, 0, 12, 0, 0, 0, + 1, 64, 0, 0, 254, 3, + 0, 0, 18, 0, 0, 1, + 54, 0, 0, 5, 18, 0, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 144, 255, 255, 255, 21, 0, + 0, 1, 21, 0, 0, 1, + 41, 0, 0, 7, 34, 0, + 16, 0, 11, 0, 0, 0, + 42, 0, 16, 0, 11, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 1, 0, + 0, 7, 34, 0, 16, 0, + 11, 0, 0, 0, 26, 0, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 128, 41, 0, 0, 7, + 66, 0, 16, 0, 11, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 11, 0, 0, 0, + 42, 0, 16, 0, 11, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 56, 60, 0, + 0, 7, 34, 0, 16, 0, + 11, 0, 0, 0, 42, 0, + 16, 0, 11, 0, 0, 0, + 26, 0, 16, 0, 11, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 11, 0, + 0, 0, 10, 0, 16, 0, + 11, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 12, 0, 0, 0, + 10, 0, 16, 0, 11, 0, + 0, 0, 26, 0, 16, 0, + 11, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 11, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 13, 0, + 0, 0, 10, 0, 16, 0, + 11, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 0, 0, 0, 8, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 128, 65, 0, 0, 0, + 13, 0, 0, 0, 16, 0, + 0, 7, 18, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 0, 0, 0, 7, + 130, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 10, 0, + 16, 0, 11, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 6, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 55, 0, 0, 9, + 18, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 236, 120, 173, 96, + 58, 0, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 8, + 34, 0, 16, 0, 1, 0, + 0, 0, 58, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 168, 0, + 0, 8, 114, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 40, 0, 0, 0, 70, 2, + 16, 0, 1, 0, 0, 0, + 21, 0, 0, 1, 190, 24, + 0, 1, 31, 0, 4, 3, + 10, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 8, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 40, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 167, 0, + 0, 9, 226, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 40, 0, + 0, 0, 6, 249, 17, 0, + 0, 0, 0, 0, 49, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 31, 0, 4, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 168, 0, 0, 8, + 114, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 40, 0, + 0, 0, 134, 3, 16, 0, + 4, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 190, 24, 0, 1, 31, 0, + 4, 3, 42, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 8, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 40, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 167, 0, 0, 9, 226, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 40, 0, 0, 0, 6, 249, + 17, 0, 0, 0, 0, 0, + 49, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 40, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 114, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 40, 0, 0, 0, 134, 3, + 16, 0, 4, 0, 0, 0, + 21, 0, 0, 1, 21, 0, + 0, 1, 190, 24, 0, 1, + 31, 0, 4, 3, 58, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 167, 0, 0, 9, + 226, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 6, 249, 17, 0, 0, 0, + 0, 0, 49, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 40, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 134, 3, 16, 0, 3, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 190, 24, + 0, 1, 79, 0, 0, 10, + 98, 0, 16, 0, 0, 0, + 0, 0, 166, 10, 16, 0, + 1, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 226, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 6, 249, 17, 0, 0, 0, + 0, 0, 49, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 40, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 134, 3, 16, 0, 2, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 190, 24, + 0, 1, 31, 0, 4, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 8, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 40, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 226, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 40, 0, + 0, 0, 6, 249, 17, 0, + 0, 0, 0, 0, 49, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 31, 0, 4, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 40, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 168, 0, 0, 8, + 114, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 40, 0, + 0, 0, 134, 3, 16, 0, + 2, 0, 0, 0, 21, 0, + 0, 1, 167, 0, 0, 9, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 6, 112, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 8, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 40, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 49, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 8, + 114, 0, 16, 0, 1, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 40, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 18, 0, 0, 1, 167, 0, + 0, 9, 242, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 70, 126, 16, 0, + 1, 0, 0, 0, 21, 0, + 0, 1, 168, 0, 0, 9, + 242, 224, 17, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 1, 0, + 0, 0, 21, 0, 0, 1, + 62, 0, 0, 1 +}; diff --git a/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_EncodeBlockCS.inc b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_EncodeBlockCS.inc new file mode 100644 index 0000000..bbd2d6a --- /dev/null +++ b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_EncodeBlockCS.inc @@ -0,0 +1,10151 @@ +#if 0 +// +// Generated by Microsoft (R) D3D Shader Disassembler +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Input +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Output +cs_4_0 +dcl_globalFlags refactoringAllowed +dcl_immediateConstantBuffer { { 0x0000cccc, -0.000000, 15, 0}, + { 0x00008888, 65981199646559862000000000.000000, 15, 0}, + { 0x0000eeee, 15358528172589056.000000, 15, 0}, + { 0x0000ecc8, 3584194248704.000000, 15, 0}, + { 0x0000c880, -0.000000, 15, 0}, + { 0x0000feec, -0.000000, 15, 0}, + { 0x0000fec8, 14680365989888.000000, 15, 0}, + { 0x0000ec80, 15362462362632192.000000, 15, 0}, + { 0x0000c800, -0.000000, 15, 0}, + { 0x0000ffec, -0.000000, 15, 0}, + { 0x0000fe80, -0.000000, 15, 0}, + { 0x0000e800, -0.000000, 15, 0}, + { 0x0000ffe8, -0.000000, 15, 0}, + { 0x0000ff00, -0.000000, 15, 0}, + { 0x0000fff0, -0.000000, 15, 0}, + { 0x0000f000, 0.000000, 15, 0}, + { 0x0000f710, -0.000000, 15, 0}, + { 142, 0.000000, 2, 0}, + { 0x00007100, -0.000000, 8, 0}, + { 2254, 22076467445760.000000, 2, 0}, + { 140, -0.000000, 2, 0}, + { 0x00007310, 70798013459086900000000000.000000, 8, 0}, + { 0x00003100, -0.000000, 8, 0}, + { 0x00008cce, 0.000000, 15, 0}, + { 2188, 0x0050a4a4, 2, 0}, + { 0x00003110, -0.000000, 8, 0}, + { 0x00006666, 0.000000, 2, 0}, + { 0x0000366c, 17610885206241624000000000.000000, 2, 0}, + { 6120, -0.000000, 8, 0}, + { 4080, -0.000000, 8, 0}, + { 0x0000718e, 22097854464.000000, 2, 0}, + { 0x0000399c, 65888818352238725000000000.000000, 2, 0}, + { 0x0000aaaa, -0.000000, 15, 0}, + { 0x0000f0f0, 19411582976.000000, 15, 0}, + { 0x00005a5a, -0.000000, 6, 0}, + { 0x000033cc, 0.000000, 8, 0}, + { 0x00003c3c, 0.000000, 2, 0}, + { 0x000055aa, 0.000000, 8, 0}, + { 0x00009696, 0.000000, 15, 0}, + { 0x0000a55a, 22151331840.000000, 15, 0}, + { 0x000073ce, 9304358912.000000, 2, 0}, + { 5064, -0.000000, 8, 0}, + { 0x0000324c, 271536072765004600000000.000000, 2, 0}, + { 0x00003bdc, -0.000000, 2, 0}, + { 0x00006996, 21517107200.000000, 2, 0}, + { 0x0000c33c, 12724757752857623000000000.000000, 15, 0}, + { 0x00009966, 1365.320801, 15, 0}, + { 1632, 272006464738884190000000.000000, 6, 0}, + { 626, -0.000000, 6, 0}, + { 1252, 5783798415360.000000, 2, 0}, + { 0x00004e40, -0.000000, 6, 0}, + { 0x00002720, -0.000000, 8, 0}, + { 0x0000c936, -0.000000, 15, 0}, + { 0x0000936c, -0.000000, 15, 0}, + { 0x000039c6, -0.000000, 2, 0}, + { 0x0000639c, -0.000000, 2, 0}, + { 0x00009336, -0.000000, 15, 0}, + { 0x00009cc6, -0.000000, 15, 0}, + { 0x0000817e, -0.000000, 15, 0}, + { 0x0000e718, -0.000000, 15, 0}, + { 0x0000ccf0, 4.007874, 15, 0}, + { 4044, -0.000000, 2, 0}, + { 0x00007744, -0.000000, 2, 0}, + { 0x0000ee22, 0.000000, 15, 0}, + { 0, 0, 3, 15}, + { 0, 0, 3, 8}, + { 0, 0, 15, 8}, + { 1, 0, 15, 3}, + { 1, 0, 8, 15}, + { 1, 0, 3, 15}, + { 1, 0, 15, 3}, + { 2, 0, 15, 8}, + { 2, 0, 8, 15}, + { 2, 0, 8, 15}, + { 2, 0, 6, 15}, + { 2, 0, 6, 15}, + { 3, 0, 6, 15}, + { 3, 0, 5, 15}, + { 3, 0, 3, 15}, + { 3, 0, 3, 8}, + { 4, 0, 3, 15}, + { 4, 0, 3, 8}, + { 4, 0, 8, 15}, + { 4, 0, 15, 3}, + { 5, 0, 3, 15}, + { 5, 0, 3, 8}, + { 5, 0, 6, 15}, + { 5, 0, 10, 8}, + { 6, 0, 5, 3}, + { 6, 0, 8, 15}, + { 6, 0, 8, 6}, + { 6, 0, 6, 10}, + { 6, 0, 8, 15}, + { 7, 0, 5, 15}, + { 7, 0, 15, 10}, + { 7, 0, 15, 8}, + { 7, 0, 8, 15}, + { 8, 0, 15, 3}, + { 8, 0, 3, 15}, + { 8, 0, 5, 10}, + { 8, 0, 6, 10}, + { 9, 0, 10, 8}, + { 9, 0, 8, 9}, + { 9, 0, 15, 10}, + { 9, 0, 15, 6}, + { 10, 0, 3, 15}, + { 10, 0, 15, 8}, + { 10, 0, 5, 15}, + { 10, 0, 15, 3}, + { 10, 0, 15, 6}, + { 11, 0, 15, 6}, + { 11, 0, 15, 8}, + { 11, 0, 3, 15}, + { 11, 0, 15, 3}, + { 12, 0, 5, 15}, + { 12, 0, 5, 15}, + { 12, 0, 5, 15}, + { 12, 0, 8, 15}, + { 13, 0, 5, 15}, + { 13, 0, 10, 15}, + { 13, 0, 5, 15}, + { 13, 0, 10, 15}, + { 14, 0, 8, 15}, + { 14, 0, 13, 15}, + { 14, 0, 15, 3}, + { 14, 0, 12, 15}, + { 15, 0, 3, 15}, + { 15, 0, 3, 8}, + { 0, 15, 0, 0}, + { 0, 15, 0, 0}, + { 0, 15, 0, 0}, + { 0, 15, 0, 0}, + { 0, 15, 0, 0}, + { 1, 15, 0, 0}, + { 1, 15, 0, 0}, + { 1, 15, 0, 0}, + { 1, 15, 0, 0}, + { 1, 15, 0, 0}, + { 1, 15, 0, 0}, + { 1, 15, 0, 0}, + { 1, 15, 0, 0}, + { 1, 15, 0, 0}, + { 2, 15, 0, 0}, + { 2, 15, 0, 0}, + { 2, 15, 0, 0}, + { 2, 2, 0, 0}, + { 2, 8, 0, 0}, + { 2, 2, 0, 0}, + { 2, 2, 0, 0}, + { 2, 8, 0, 0}, + { 2, 8, 0, 0}, + { 3, 15, 0, 0}, + { 3, 2, 0, 0}, + { 3, 8, 0, 0}, + { 3, 2, 0, 0}, + { 3, 2, 0, 0}, + { 3, 8, 0, 0}, + { 3, 8, 0, 0}, + { 3, 2, 0, 0}, + { 3, 2, 0, 0}, + { 3, 15, 0, 0}, + { 4, 15, 0, 0}, + { 4, 6, 0, 0}, + { 4, 8, 0, 0}, + { 4, 2, 0, 0}, + { 4, 8, 0, 0}, + { 4, 15, 0, 0}, + { 4, 15, 0, 0}, + { 4, 2, 0, 0}, + { 4, 8, 0, 0}, + { 5, 2, 0, 0}, + { 5, 2, 0, 0}, + { 5, 2, 0, 0}, + { 5, 15, 0, 0}, + { 5, 15, 0, 0}, + { 5, 6, 0, 0}, + { 5, 6, 0, 0}, + { 5, 2, 0, 0}, + { 5, 6, 0, 0}, + { 6, 8, 0, 0}, + { 6, 15, 0, 0}, + { 6, 15, 0, 0}, + { 6, 2, 0, 0}, + { 6, 2, 0, 0}, + { 6, 15, 0, 0}, + { 6, 15, 0, 0}, + { 6, 15, 0, 0}, + { 6, 15, 0, 0}, + { 7, 15, 0, 0}, + { 7, 2, 0, 0}, + { 7, 2, 0, 0}, + { 7, 15, 0, 0}, + { 0, 3, 15, 0}, + { 0, 3, 8, 0}, + { 0, 8, 15, 0}, + { 0, 3, 15, 0}, + { 0, 8, 15, 0}, + { 0, 3, 15, 0}, + { 0, 3, 15, 0}, + { 0, 8, 15, 0}, + { 0, 8, 15, 0}, + { 0, 8, 15, 0}, + { 0, 6, 15, 0}, + { 1, 6, 15, 0}, + { 1, 6, 15, 0}, + { 1, 5, 15, 0}, + { 1, 3, 15, 0}, + { 1, 3, 8, 0}, + { 1, 3, 15, 0}, + { 1, 3, 8, 0}, + { 1, 8, 15, 0}, + { 1, 3, 15, 0}, + { 1, 3, 15, 0}, + { 1, 3, 8, 0}, + { 1, 6, 15, 0}, + { 1, 8, 10, 0}, + { 1, 3, 5, 0}, + { 1, 8, 15, 0}, + { 1, 6, 8, 0}, + { 1, 6, 10, 0}, + { 1, 8, 15, 0}, + { 1, 5, 15, 0}, + { 1, 10, 15, 0}, + { 1, 8, 15, 0}, + { 1, 8, 15, 0}, + { 2, 3, 15, 0}, + { 2, 3, 15, 0}, + { 2, 5, 10, 0}, + { 2, 6, 10, 0}, + { 2, 8, 10, 0}, + { 2, 8, 9, 0}, + { 2, 10, 15, 0}, + { 2, 6, 15, 0}, + { 2, 3, 15, 0}, + { 2, 8, 15, 0}, + { 2, 5, 15, 0}, + { 2, 3, 15, 0}, + { 2, 6, 15, 0}, + { 2, 6, 15, 0}, + { 2, 8, 15, 0}, + { 2, 3, 15, 0}, + { 2, 3, 15, 0}, + { 2, 5, 15, 0}, + { 2, 5, 15, 0}, + { 2, 5, 15, 0}, + { 2, 8, 15, 0}, + { 3, 5, 15, 0}, + { 3, 10, 15, 0}, + { 3, 5, 15, 0}, + { 3, 10, 15, 0}, + { 3, 8, 15, 0}, + { 3, 13, 15, 0}, + { 3, 3, 15, 0}, + { 3, 12, 15, 0}, + { 3, 3, 15, 0}, + { 3, 3, 8, 0} } +dcl_constantbuffer CB0[2], immediateIndexed +dcl_resource_texture2d (float,float,float,float) t0 +dcl_resource_structured t1, 16 +dcl_uav_structured u0, 16 +dcl_input vThreadIDInGroupFlattened +dcl_input vThreadGroupID.x +dcl_temps 15 +dcl_tgsm_structured g0, 100, 64 +dcl_thread_group 64, 1, 1 +ushr r0.x, vThreadIDInGroupFlattened.x, l(4) +ishl r0.y, vThreadGroupID.x, l(2) +iadd r0.y, r0.y, cb0[1].x +iadd r0.x, r0.x, r0.y +uge r0.y, r0.x, cb0[1].y +if_nz r0.y + ret +endif +and r0.y, vThreadIDInGroupFlattened.x, l(48) +iadd r0.z, -r0.y, vThreadIDInGroupFlattened.x +ld_structured r1.xyz, r0.x, l(4), t1.xyzx +and r0.w, r1.x, l(0x7fffffff) +ld_structured r2.x, r0.x, l(4), t1.xxxx +ushr r1.x, r2.x, l(31) +ult r2.xyzw, r0.zzzz, l(16, 8, 4, 2) +if_nz r2.x + udiv r1.w, null, r0.x, cb0[0].y + imad r3.x, -r1.w, cb0[0].y, r0.x + ishl r3.x, r3.x, l(2) + ishl r1.w, r1.w, l(2) + and r3.y, r0.z, l(3) + iadd r3.x, r3.y, r3.x + ushr r4.x, r0.z, l(2) + iadd r3.y, r1.w, r4.x + mov r3.zw, l(0,0,0,0) + ld r3.xyzw, r3.xyzw, t0.xyzw + mul r3.xyzw, r3.xyzw, l(255.000000, 255.000000, 255.000000, 255.000000) + ftou r3.xyzw, r3.xyzw + umin r3.xyzw, r3.xyzw, l(255, 255, 255, 255) + ieq r4.xy, r0.wwww, l(4, 5, 0, 0) + or r1.w, r4.y, r4.x + ieq r4.xyz, r1.zzzz, l(1, 2, 3, 0) + movc r5.zw, r4.zzzz, r3.wwwz, r3.zzzw + mov r5.xy, r3.xyxx + movc r5.yzw, r4.yyyy, r3.wwzy, r5.yyzw + movc r4.xyzw, r4.xxxx, r3.wyzx, r5.xyzw + movc r3.xyzw, r1.wwww, r4.xyzw, r3.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(0), r3.xyzw +endif +iadd r1.w, r1.y, l(-64) +if_nz r2.x + ld_structured r3.xyzw, vThreadIDInGroupFlattened.x, l(0), g0.xyzw + ishl r4.x, r0.z, l(1) + ushr r4.x, icb[r1.w + 0].y, r4.x + and r4.x, r4.x, l(3) + ieq r4.yz, r0.wwww, l(0, 0, 2, 0) + or r4.y, r4.z, r4.y + ieq r4.x, r4.x, l(2) + movc r5.xyzw, r4.xxxx, r3.xyzw, l(-1,-1,-1,-1) + and r3.xyzw, r3.xyzw, r4.xxxx + movc r5.xyzw, r4.yyyy, r5.xyzw, l(-1,-1,-1,-1) + and r3.xyzw, r3.xyzw, r4.yyyy + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r5.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r3.xyzw +endif +if_nz r2.y + ld_structured r3.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r4.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r5.x, vThreadIDInGroupFlattened.x, l(8) + ld_structured r6.xyzw, r5.x, l(36), g0.xyzw + ld_structured r5.xyzw, r5.x, l(52), g0.xyzw + umin r3.xyzw, r3.xyzw, r6.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r3.xyzw + umax r3.xyzw, r4.xyzw, r5.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r3.xyzw +endif +if_nz r2.z + ld_structured r3.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r4.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r5.x, vThreadIDInGroupFlattened.x, l(4) + ld_structured r6.xyzw, r5.x, l(36), g0.xyzw + ld_structured r5.xyzw, r5.x, l(52), g0.xyzw + umin r3.xyzw, r3.xyzw, r6.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r3.xyzw + umax r3.xyzw, r4.xyzw, r5.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r3.xyzw +endif +if_nz r2.w + ld_structured r3.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r4.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r5.x, vThreadIDInGroupFlattened.x, l(2) + ld_structured r6.xyzw, r5.x, l(36), g0.xyzw + ld_structured r5.xyzw, r5.x, l(52), g0.xyzw + umin r3.xyzw, r3.xyzw, r6.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r3.xyzw + umax r3.xyzw, r4.xyzw, r5.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r3.xyzw +endif +ult r3.xy, r0.zzzz, l(1, 3, 0, 0) +if_nz r3.x + ld_structured r4.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r5.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r3.z, vThreadIDInGroupFlattened.x, l(1) + ld_structured r6.xyzw, r3.z, l(36), g0.xyzw + ld_structured r7.xyzw, r3.z, l(52), g0.xyzw + umin r4.xyzw, r4.xyzw, r6.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r4.xyzw + umax r4.xyzw, r5.xyzw, r7.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r4.xyzw +endif +ieq r3.zw, r0.zzzz, l(0, 0, 2, 1) +if_nz r3.z + ld_structured r4.xyzw, r0.y, l(36), g0.xyzw + ld_structured r5.xyzw, r0.y, l(52), g0.xyzw +endif +if_nz r2.x + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(0), g0.xyzw + ushr r3.z, icb[r1.y + 0].x, r0.z + and r3.z, r3.z, l(1) + ishl r7.x, r0.z, l(1) + ushr r7.x, icb[r1.w + 0].y, r7.x + and r7.x, r7.x, l(3) + ieq r8.xyzw, r0.wwww, l(0, 2, 1, 3) + ieq r7.x, r7.x, l(1) + movc r9.xyzw, r7.xxxx, r6.xyzw, l(-1,-1,-1,-1) + and r7.xyzw, r6.xyzw, r7.xxxx + or r8.xy, r8.ywyy, r8.xzxx + ieq r8.z, r0.w, l(7) + or r8.y, r8.z, r8.y + ieq r3.z, r3.z, l(1) + movc r10.xyzw, r3.zzzz, r6.xyzw, l(-1,-1,-1,-1) + and r6.xyzw, r6.xyzw, r3.zzzz + movc r10.xyzw, r8.yyyy, r10.xyzw, l(-1,-1,-1,-1) + and r6.xyzw, r6.xyzw, r8.yyyy + movc r9.xyzw, r8.xxxx, r9.xyzw, r10.xyzw + movc r6.xyzw, r8.xxxx, r7.xyzw, r6.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r9.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r6.xyzw +endif +if_nz r2.y + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r7.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r3.z, vThreadIDInGroupFlattened.x, l(8) + ld_structured r8.xyzw, r3.z, l(36), g0.xyzw + ld_structured r9.xyzw, r3.z, l(52), g0.xyzw + umin r6.xyzw, r6.xyzw, r8.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r6.xyzw + umax r6.xyzw, r7.xyzw, r9.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r6.xyzw +endif +if_nz r2.z + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r7.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r3.z, vThreadIDInGroupFlattened.x, l(4) + ld_structured r8.xyzw, r3.z, l(36), g0.xyzw + ld_structured r9.xyzw, r3.z, l(52), g0.xyzw + umin r6.xyzw, r6.xyzw, r8.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r6.xyzw + umax r6.xyzw, r7.xyzw, r9.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r6.xyzw +endif +if_nz r2.w + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r7.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r3.z, vThreadIDInGroupFlattened.x, l(2) + ld_structured r8.xyzw, r3.z, l(36), g0.xyzw + ld_structured r9.xyzw, r3.z, l(52), g0.xyzw + umin r6.xyzw, r6.xyzw, r8.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r6.xyzw + umax r6.xyzw, r7.xyzw, r9.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r6.xyzw +endif +if_nz r3.x + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r7.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r3.z, vThreadIDInGroupFlattened.x, l(1) + ld_structured r8.xyzw, r3.z, l(36), g0.xyzw + ld_structured r9.xyzw, r3.z, l(52), g0.xyzw + umin r6.xyzw, r6.xyzw, r8.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r6.xyzw + umax r6.xyzw, r7.xyzw, r9.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r6.xyzw +endif +if_nz r3.w + ld_structured r4.xyzw, r0.y, l(36), g0.xyzw + ld_structured r5.xyzw, r0.y, l(52), g0.xyzw +endif +if_nz r2.x + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(0), g0.xyzw + ushr r3.z, icb[r1.y + 0].x, r0.z + and r3.z, r3.z, l(1) + ishl r7.x, r0.z, l(1) + ushr r7.x, icb[r1.w + 0].y, r7.x + and r7.x, r7.x, l(3) + ieq r8.xyzw, r0.wwww, l(0, 2, 1, 3) + movc r9.xyzw, r7.xxxx, l(-1,-1,-1,-1), r6.xyzw + movc r7.xyzw, r7.xxxx, l(0,0,0,0), r6.xyzw + or r8.xy, r8.ywyy, r8.xzxx + ieq r10.xyzw, r0.wwww, l(7, 4, 5, 6) + or r8.y, r8.y, r10.x + movc r11.xyzw, r3.zzzz, l(-1,-1,-1,-1), r6.xyzw + movc r12.xyzw, r3.zzzz, l(0,0,0,0), r6.xyzw + or r3.z, r10.z, r10.y + or r3.z, r10.w, r3.z + movc r10.xyzw, r3.zzzz, r6.xyzw, l(-1,-1,-1,-1) + and r6.xyzw, r6.xyzw, r3.zzzz + movc r10.xyzw, r8.yyyy, r11.xyzw, r10.xyzw + movc r6.xyzw, r8.yyyy, r12.xyzw, r6.xyzw + movc r9.xyzw, r8.xxxx, r9.xyzw, r10.xyzw + movc r6.xyzw, r8.xxxx, r7.xyzw, r6.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r9.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r6.xyzw +endif +if_nz r2.y + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r7.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r2.y, vThreadIDInGroupFlattened.x, l(8) + ld_structured r8.xyzw, r2.y, l(36), g0.xyzw + ld_structured r9.xyzw, r2.y, l(52), g0.xyzw + umin r6.xyzw, r6.xyzw, r8.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r6.xyzw + umax r6.xyzw, r7.xyzw, r9.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r6.xyzw +endif +if_nz r2.z + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r7.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r2.y, vThreadIDInGroupFlattened.x, l(4) + ld_structured r8.xyzw, r2.y, l(36), g0.xyzw + ld_structured r9.xyzw, r2.y, l(52), g0.xyzw + umin r6.xyzw, r6.xyzw, r8.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r6.xyzw + umax r6.xyzw, r7.xyzw, r9.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r6.xyzw +endif +if_nz r2.w + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r7.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r2.y, vThreadIDInGroupFlattened.x, l(2) + ld_structured r8.xyzw, r2.y, l(36), g0.xyzw + ld_structured r9.xyzw, r2.y, l(52), g0.xyzw + umin r6.xyzw, r6.xyzw, r8.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r6.xyzw + umax r6.xyzw, r7.xyzw, r9.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r6.xyzw +endif +if_nz r3.x + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r7.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r2.y, vThreadIDInGroupFlattened.x, l(1) + ld_structured r8.xyzw, r2.y, l(36), g0.xyzw + ld_structured r9.xyzw, r2.y, l(52), g0.xyzw + umin r6.xyzw, r6.xyzw, r8.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r6.xyzw + umax r6.xyzw, r7.xyzw, r9.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r6.xyzw +endif +if_z r0.z + ld_structured r4.xyzw, r0.y, l(36), g0.xyzw + ld_structured r5.xyzw, r0.y, l(52), g0.xyzw +endif +if_nz r3.y + ieq r2.yzw, r0.wwww, l(0, 1, 4, 5) + ushr r3.x, r1.z, r0.z + and r3.x, r3.x, l(1) + ishl r3.y, r0.z, l(1) + ushr r6.x, r1.z, r3.y + iadd r3.y, r3.y, l(1) + ushr r6.y, r1.z, r3.y + and r3.yz, r6.xxyx, l(0, 1, 1, 0) + movc r3.xy, r2.yyyy, r3.xxxx, r3.yzyy + if_z r0.w + iadd r6.xyz, r4.xyzx, l(4, 4, 4, 0) + umin r6.xyz, r6.xyzx, l(255, 255, 255, 0) + ushr r6.xyz, r6.xyzx, l(3) + and r6.xyz, r6.xyzx, l(30, 30, 30, 0) + iadd r6.xyz, r3.xxxx, r6.xyzx + ishl r6.xyz, r6.xyzx, l(3) + ushr r7.xyz, r6.xyzx, l(5) + iadd r7.xyz, r6.xyzx, r7.xyzx + iadd r8.xyz, r5.xyzx, l(4, 4, 4, 0) + umin r8.xyz, r8.xyzx, l(255, 255, 255, 0) + ushr r8.xyz, r8.xyzx, l(3) + and r8.xyz, r8.xyzx, l(30, 30, 30, 0) + iadd r8.xyz, r3.yyyy, r8.xyzx + ishl r8.xyz, r8.xyzx, l(3) + ushr r9.xyz, r8.xyzx, l(5) + iadd r5.xyz, r8.xyzx, r9.xyzx + mov r5.w, l(255) + mov r4.xyw, l(255,2040,0,2040) + else + if_nz r2.y + iadd r9.xyz, r4.xyzx, l(1, 1, 1, 0) + umin r9.xyz, r9.xyzx, l(255, 255, 255, 0) + ushr r9.xyz, r9.xyzx, l(1) + and r9.xyz, r9.xyzx, l(126, 126, 126, 0) + iadd r9.xyz, r3.xxxx, r9.xyzx + ishl r6.xyz, r9.xyzx, l(1) + ushr r9.xyz, r6.xyzx, l(7) + iadd r7.xyz, r6.xyzx, r9.xyzx + iadd r9.xyz, r5.xyzx, l(1, 1, 1, 0) + umin r9.xyz, r9.xyzx, l(255, 255, 255, 0) + ushr r9.xyz, r9.xyzx, l(1) + and r9.xyz, r9.xyzx, l(126, 126, 126, 0) + iadd r9.xyz, r3.yyyy, r9.xyzx + ishl r8.xyz, r9.xyzx, l(1) + ushr r9.xyz, r8.xyzx, l(7) + iadd r5.xyz, r8.xyzx, r9.xyzx + mov r5.w, l(255) + mov r4.xyw, l(255,510,0,510) + else + ieq r2.y, r0.w, l(2) + if_nz r2.y + iadd r9.xyz, r4.xyzx, l(4, 4, 4, 0) + umin r9.xyz, r9.xyzx, l(255, 255, 255, 0) + and r6.xyz, r9.xyzx, l(248, 248, 248, 0) + ushr r9.xyz, r9.xyzx, l(5) + iadd r7.xyz, r6.xyzx, r9.xyzx + iadd r9.xyz, r5.xyzx, l(4, 4, 4, 0) + umin r9.xyz, r9.xyzx, l(255, 255, 255, 0) + and r8.xyz, r9.xyzx, l(248, 248, 248, 0) + ushr r9.xyz, r9.xyzx, l(5) + iadd r5.xyz, r8.xyzx, r9.xyzx + mov r5.w, l(255) + mov r4.xyw, l(255,2040,0,2040) + else + ieq r2.y, r0.w, l(3) + if_nz r2.y + and r9.xyz, r4.xyzx, l(-2, -2, -2, 0) + iadd r6.xyz, r3.xxxx, r9.xyzx + and r9.xyz, r5.xyzx, l(-2, -2, -2, 0) + iadd r8.xyz, r3.yyyy, r9.xyzx + mov r7.xyz, r6.xyzx + mov r5.xyz, r8.xyzx + mov r5.w, l(255) + mov r4.xyw, l(255,255,0,255) + else + ieq r2.y, r0.w, l(4) + if_nz r2.y + iadd r9.xyzw, r4.xyzw, l(4, 4, 4, 2) + umin r9.xyzw, r9.xyzw, l(255, 255, 255, 255) + and r6.xyzw, r9.xyzw, l(248, 248, 248, 252) + ushr r10.xyz, r9.xyzx, l(5) + ushr r10.w, r9.w, l(6) + iadd r7.xyzw, r6.xyzw, r10.xyzw + iadd r9.xyzw, r5.xyzw, l(4, 4, 4, 2) + umin r9.xyzw, r9.xyzw, l(255, 255, 255, 255) + and r4.xyzw, r9.xwzy, l(248, 252, 248, 248) + ushr r10.xyz, r9.xyzx, l(5) + ushr r10.w, r9.w, l(6) + iadd r5.xyzw, r4.xwzy, r10.xyzw + mov r8.xyz, r4.xwzx + mov r4.x, r7.w + mov r4.w, r6.w + else + ieq r2.y, r0.w, l(5) + if_nz r2.y + iadd r9.xyz, r4.xyzx, l(1, 1, 1, 0) + umin r9.xyz, r9.xyzx, l(255, 255, 255, 0) + and r6.xyz, r9.xyzx, l(254, 254, 254, 0) + ushr r9.xyz, r9.xyzx, l(7) + iadd r7.xyz, r6.xyzx, r9.xyzx + iadd r9.xyz, r5.xyzx, l(1, 1, 1, 0) + umin r9.xyz, r9.xyzx, l(255, 255, 255, 0) + and r8.xyz, r9.xyzx, l(254, 254, 254, 0) + ushr r9.xyz, r9.xyzx, l(7) + iadd r5.xyz, r8.xyzx, r9.xyzx + mov r4.x, r4.w + mov r4.y, r5.w + else + ieq r2.y, r0.w, l(6) + if_nz r2.y + and r9.xyzw, r4.xyzw, l(-2, -2, -2, -2) + iadd r6.xyzw, r3.xxxx, r9.xyzw + and r9.xyzw, r5.xyzw, l(-2, -2, -2, -2) + iadd r4.xyzw, r3.yyyy, r9.xwzy + mov r7.xyz, r6.xyzx + mov r5.xyzw, r4.xwzy + mov r8.xyz, r4.xwzx + mov r4.xw, r6.wwww + else + iadd r9.xyzw, r4.xyzw, l(2, 2, 2, 2) + umin r9.xyzw, r9.xyzw, l(255, 255, 255, 255) + ushr r9.xyzw, r9.xyzw, l(2) + and r9.xyzw, r9.xyzw, l(62, 62, 62, 62) + iadd r9.xyzw, r3.xxxx, r9.xyzw + ishl r6.xyzw, r9.xyzw, l(2) + ushr r10.xyzw, r6.xyzw, l(6) + iadd r4.xyzw, r6.wxzy, r10.wxzy + iadd r10.xyzw, r5.xyzw, l(2, 2, 2, 2) + umin r10.xyzw, r10.xyzw, l(255, 255, 255, 255) + ushr r10.xyzw, r10.xyzw, l(2) + and r10.xyzw, r10.xyzw, l(62, 62, 62, 62) + iadd r10.xyzw, r3.yyyy, r10.xwyz + ishl r8.xyzw, r10.xzwy, l(2) + ushr r11.xyzw, r8.xyzw, l(6) + iadd r5.xyzw, r8.xyzw, r11.xyzw + mov r10.x, r9.w + ishl r3.xy, r10.xyxx, l(2) + mov r7.xyz, r4.ywzy + mov r4.yw, r3.yyyx + endif + endif + endif + endif + endif + endif + endif + ineg r9.xyz, r7.xyzx + ineg r9.w, r4.x + iadd r10.xyzw, r5.xyzw, r9.xyzw + ult r2.y, r0.w, l(4) + movc r2.y, r2.y, l(0), r10.w + or r2.z, r2.w, r2.z + if_nz r2.z + if_z r0.z + imul null, r2.zw, r10.xxxy, r10.xxxy + iadd r2.z, r2.w, r2.z + imad r2.z, r10.z, r10.z, r2.z + imul null, r2.w, r2.y, r2.y + ld_structured r11.xyzw, r0.y, l(0), g0.xyzw + iadd r3.xyz, -r7.xyzx, r11.xyzx + imul null, r3.xy, r3.xyxx, r10.xyxx + iadd r3.x, r3.y, r3.x + imad r3.x, r10.z, r3.z, r3.x + iadd r3.y, -r4.x, r11.w + imul null, r3.y, r2.y, r3.y + ilt r3.z, l(0), r2.z + ilt r10.w, l(0), r3.x + and r3.z, r3.z, r10.w + itof r3.x, r3.x + mul r3.x, r3.x, l(63.499989) + ftou r3.x, r3.x + ishl r2.z, r2.z, l(5) + ult r2.z, r2.z, r3.x + and r2.z, r2.z, r3.z + movc r11.xyz, r2.zzzz, r5.xyzx, r7.xyzx + movc r5.xyz, r2.zzzz, r7.xyzx, r5.xyzx + movc r12.xyz, r2.zzzz, r8.xyzx, r6.xyzx + movc r8.xyz, r2.zzzz, r6.xyzx, r8.xyzx + ilt r2.z, l(0), r2.w + ilt r3.x, l(0), r3.y + and r2.z, r2.z, r3.x + itof r3.x, r3.y + mul r3.x, r3.x, l(63.499989) + ftou r3.x, r3.x + ishl r2.w, r2.w, l(5) + ult r2.w, r2.w, r3.x + and r2.z, r2.w, r2.z + mov r4.z, r5.w + movc r13.xyzw, r2.zzzz, r4.zxyw, r4.xzwy + mov r11.w, r13.x + mov r5.w, r13.y + mov r12.w, r13.z + mov r6.xyzw, r12.xyzw + mov r8.w, r13.w + else + mov r7.w, r4.x + mov r11.xyzw, r7.xyzw + mov r6.w, r4.w + mov r8.w, r4.y + endif + else + if_z r0.z + mov r2.z, l(0) + else + if_nz r3.w + mov r2.z, icb[r1.y + 0].z + else + mov r2.z, icb[r1.y + 0].w + endif + endif + imul null, r3.xy, r10.xyxx, r10.xyxx + iadd r2.w, r3.y, r3.x + imad r2.w, r10.z, r10.z, r2.w + imad r2.w, r2.y, r2.y, r2.w + iadd r2.z, r0.y, r2.z + ld_structured r3.xyzw, r2.z, l(0), g0.xyzw + iadd r3.xyzw, r9.xyzw, r3.xyzw + imul null, r3.xy, r3.xyxx, r10.xyxx + iadd r2.z, r3.y, r3.x + imad r2.z, r10.z, r3.z, r2.z + imad r2.y, r2.y, r3.w, r2.z + ilt r2.z, l(0), r2.w + ilt r3.x, l(0), r2.y + and r2.z, r2.z, r3.x + itof r2.y, r2.y + mul r2.y, r2.y, l(63.499989) + ftou r2.y, r2.y + ishl r2.w, r2.w, l(5) + ult r2.y, r2.w, r2.y + and r2.y, r2.y, r2.z + mov r7.w, r4.x + movc r11.xyzw, r2.yyyy, r5.xyzw, r7.xyzw + movc r5.xyzw, r2.yyyy, r7.xyzw, r5.xyzw + mov r8.w, r4.y + mov r4.xyz, r6.xyzx + movc r6.xyzw, r2.yyyy, r8.xyzw, r4.xyzw + movc r8.xyzw, r2.yyyy, r4.xyzw, r8.xyzw + endif + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r11.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r5.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(68), r6.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(84), r8.xyzw +endif +if_nz r2.x + ieq r2.xyzw, r0.wwww, l(0, 1, 6, 4) + or r3.x, r2.y, r2.x + movc r3.yz, r1.xxxx, l(0,1,2,0), l(0,2,1,0) + movc r3.yz, r2.wwww, r3.yyzy, l(0,2,2,0) + movc r3.yz, r2.zzzz, l(0,0,0,0), r3.yyzy + movc r3.xy, r3.xxxx, l(1,1,0,0), r3.yzyy + ieq r4.xyzw, r0.wwww, l(2, 3, 7, 5) + ishl r2.z, r0.z, l(1) + ushr r1.w, icb[r1.w + 0].y, r2.z + and r1.w, r1.w, l(3) + or r2.xyz, r2.xywx, r4.xywx + or r2.y, r4.z, r2.y + ushr r2.w, icb[r1.y + 0].x, r0.z + and r2.y, r2.y, r2.w + and r2.y, r2.y, l(1) + movc r1.w, r2.x, r1.w, r2.y + iadd r1.w, r0.y, r1.w + ld_structured r4.xyzw, r1.w, l(36), g0.xyzw + ld_structured r5.xyzw, r1.w, l(52), g0.xyzw + iadd r5.xyzw, -r4.xyzw, r5.xyzw + ult r1.w, r0.w, l(4) + movc r1.w, r1.w, l(0), r5.w + if_nz r2.z + imul null, r2.xy, r5.xyxx, r5.xyxx + iadd r2.x, r2.y, r2.x + imad r2.x, r5.z, r5.z, r2.x + imul null, r2.y, r1.w, r1.w + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(0), g0.xyzw + iadd r7.xyzw, -r4.xyzw, r6.xyzw + imul null, r2.zw, r5.xxxy, r7.xxxy + iadd r2.z, r2.w, r2.z + imad r2.z, r5.z, r7.z, r2.z + ige r2.w, l(0), r2.x + ige r3.z, l(0), r2.z + or r2.w, r2.w, r3.z + ilt r3.z, r2.z, r2.x + itof r2.xz, r2.xxzx + mul r2.z, r2.z, l(63.499989) + div r2.x, r2.z, r2.x + ftou r2.x, r2.x + ishl r3.yw, r3.xxxy, l(6) + iadd r2.x, r2.x, r3.y + iadd r6.xy, r3.ywyy, l(11, 11, 0, 0) + udiv null, r6.xy, r6.xyxx, l(68, 68, 0, 0) + ult r7.xy, r3.ywyy, l(1, 1, 0, 0) + movc r6.xy, r7.xyxx, l(15,15,0,0), r6.xyxx + movc r2.x, r3.z, icb[r2.x + 64].x, r6.x + movc r7.y, r2.w, l(0), r2.x + imul null, r2.x, r1.w, r7.w + ige r2.zw, l(0, 0, 0, 0), r2.yyyx + or r2.z, r2.w, r2.z + ilt r2.w, r2.x, r2.y + itof r2.xy, r2.xyxx + mul r2.x, r2.x, l(63.499989) + div r2.x, r2.x, r2.y + ftou r2.x, r2.x + iadd r2.x, r2.x, r3.w + movc r2.x, r2.w, icb[r2.x + 64].x, r6.y + movc r7.x, r2.z, l(0), r2.x + movc r2.xy, r1.xxxx, r7.xyxx, r7.yxyy + else + imul null, r2.zw, r5.xxxy, r5.xxxy + iadd r2.z, r2.w, r2.z + imad r2.z, r5.z, r5.z, r2.z + imad r2.z, r1.w, r1.w, r2.z + ld_structured r6.xyzw, vThreadIDInGroupFlattened.x, l(0), g0.xyzw + iadd r4.xyzw, -r4.xyzw, r6.xyzw + imul null, r3.yz, r4.xxyx, r5.xxyx + iadd r2.w, r3.z, r3.y + imad r2.w, r5.z, r4.z, r2.w + imad r1.w, r1.w, r4.w, r2.w + ige r2.w, l(0), r2.z + ige r3.y, l(0), r1.w + or r2.w, r2.w, r3.y + ilt r3.y, r1.w, r2.z + itof r1.w, r1.w + mul r1.w, r1.w, l(63.499989) + itof r2.z, r2.z + div r1.w, r1.w, r2.z + ftou r1.w, r1.w + ishl r2.z, r3.x, l(6) + iadd r1.w, r1.w, r2.z + iadd r3.x, r2.z, l(11) + udiv null, r3.x, r3.x, l(68) + ult r2.z, r2.z, l(1) + movc r2.z, r2.z, l(15), r3.x + movc r1.w, r3.y, icb[r1.w + 64].x, r2.z + movc r2.x, r2.w, l(0), r1.w + mov r2.y, l(0) + endif + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(16), r2.xyxx +endif +if_z r0.z + if_z r0.w + ishl r0.z, r1.y, l(1) + iadd r0.z, r0.z, l(-128) + iadd r0.z, r0.z, l(1) + ld_structured r2.xyz, r0.y, l(68), g0.xyzx + ishl r3.x, r2.x, l(1) + ishl r3.y, r2.y, l(25) + ishl r3.z, r2.z, l(17) + and r3.xyz, r3.xyzx, l(480, 0xe0000000, 0x01e00000, 0) + or r0.z, r0.z, r3.x + ld_structured r4.xyz, r0.y, l(84), g0.xyzx + ishl r5.x, r4.x, l(5) + ishl r5.y, r4.z, l(21) + and r2.xw, r5.xxxy, l(7680, 0, 0, 0x1e000000) + or r0.z, r0.z, r2.x + iadd r3.xw, r0.yyyy, l(1, 0, 0, 2) + ld_structured r5.xyz, r3.x, l(68), g0.xyzx + ishl r6.x, r5.x, l(9) + ishl r6.y, r5.y, l(1) + ishl r6.z, r5.z, l(25) + and r6.xyz, r6.xyzx, l(0x0001e000, 480, 0xe0000000, 0) + or r0.z, r0.z, r6.x + ld_structured r7.xyz, r3.x, l(84), g0.xyzx + ishl r8.x, r7.x, l(13) + ishl r8.y, r7.y, l(5) + and r4.xw, r8.xxxy, l(0x001e0000, 0, 0, 7680) + or r0.z, r0.z, r4.x + ld_structured r8.xyz, r3.w, l(68), g0.xyzx + ishl r9.x, r8.x, l(17) + ishl r9.y, r8.y, l(9) + ishl r9.z, r8.z, l(1) + and r9.xyz, r9.xyzx, l(0x01e00000, 0x0001e000, 480, 0) + or r0.z, r0.z, r9.x + ld_structured r10.xyz, r3.w, l(84), g0.xyzx + ishl r11.x, r10.x, l(21) + ishl r11.y, r10.y, l(13) + ishl r11.z, r10.z, l(5) + and r11.xyz, r11.xyzx, l(0x1e000000, 0x001e0000, 7680, 0) + or r0.z, r0.z, r11.x + or r12.x, r3.y, r0.z + ld_structured r13.xy, r0.y, l(68), g0.xyxx + ushr r0.z, r13.y, l(7) + and r0.z, r0.z, l(1) + ushr r1.w, r4.y, l(3) + and r1.w, r1.w, l(30) + iadd r0.z, r0.z, r1.w + iadd r0.z, r6.y, r0.z + iadd r0.z, r4.w, r0.z + iadd r0.z, r9.y, r0.z + iadd r0.z, r11.y, r0.z + iadd r0.z, r3.z, r0.z + iadd r0.z, r2.w, r0.z + iadd r12.y, r6.z, r0.z + ld_structured r2.x, r3.x, l(76), g0.xxxx + ushr r0.z, r2.x, l(7) + and r0.z, r0.z, l(1) + ushr r1.w, r7.z, l(3) + and r1.w, r1.w, l(30) + iadd r0.z, r0.z, r1.w + iadd r0.z, r9.z, r0.z + iadd r0.z, r11.z, r0.z + ishl r1.w, r13.x, l(10) + and r1.w, r1.w, l(8192) + iadd r0.z, r0.z, r1.w + ld_structured r2.x, r0.y, l(84), g0.xxxx + ishl r1.w, r2.x, l(11) + and r1.w, r1.w, l(0x00004000) + iadd r0.z, r0.z, r1.w + ld_structured r2.x, r3.x, l(68), g0.xxxx + ishl r1.w, r2.x, l(12) + and r1.w, r1.w, l(0x00008000) + iadd r0.z, r0.z, r1.w + ld_structured r2.x, r3.x, l(84), g0.xxxx + ishl r1.w, r2.x, l(13) + and r1.w, r1.w, l(0x00010000) + iadd r0.z, r0.z, r1.w + ld_structured r2.x, r3.w, l(68), g0.xxxx + ishl r1.w, r2.x, l(14) + and r1.w, r1.w, l(0x00020000) + iadd r0.z, r0.z, r1.w + ld_structured r2.x, r3.w, l(84), g0.xxxx + ishl r1.w, r2.x, l(15) + and r1.w, r1.w, l(0x00040000) + iadd r0.z, r0.z, r1.w + ld_structured r2.x, r0.y, l(16), g0.xxxx + ishl r1.w, r2.x, l(19) + iadd r0.z, r0.z, r1.w + umin r1.w, l(4), icb[r1.y + 128].y + mov r12.z, r0.z + mov r2.x, l(1) + loop + ult r2.y, r1.w, r2.x + breakc_nz r2.y + iadd r2.y, r0.y, r2.x + ld_structured r3.x, r2.y, l(16), g0.xxxx + imad r2.y, r2.x, l(3), l(18) + ishl r2.y, r3.x, r2.y + or r12.z, r2.y, r12.z + iadd r2.x, r2.x, l(1) + endloop + ult r0.z, icb[r1.y + 128].y, l(4) + if_nz r0.z + iadd r0.z, r0.y, l(4) + ld_structured r3.x, r0.z, l(16), g0.xxxx + ishl r0.z, r3.x, l(29) + or r12.z, r0.z, r12.z + iadd r2.z, r2.x, l(1) + mov r2.y, l(0) + else + iadd r0.z, r0.y, l(4) + ld_structured r3.x, r0.z, l(16), g0.xxxx + ushr r0.z, r3.x, l(2) + and r0.z, r0.z, l(1) + mov r2.y, r0.z + mov r2.z, r2.x + loop + ult r1.w, icb[r1.y + 128].y, r2.z + breakc_nz r1.w + iadd r1.w, r0.y, r2.z + ld_structured r3.x, r1.w, l(16), g0.xxxx + imad r1.w, r2.z, l(3), l(-14) + ishl r1.w, r3.x, r1.w + or r2.y, r1.w, r2.y + iadd r2.z, r2.z, l(1) + endloop + endif + mov r0.z, r2.y + mov r1.w, r2.z + loop + ult r2.x, icb[r1.y + 128].z, r1.w + breakc_nz r2.x + iadd r2.x, r0.y, r1.w + ld_structured r3.x, r2.x, l(16), g0.xxxx + imad r2.x, r1.w, l(3), l(-15) + ishl r2.x, r3.x, r2.x + or r0.z, r0.z, r2.x + iadd r1.w, r1.w, l(1) + endloop + mov r12.w, r0.z + mov r2.x, r1.w + loop + uge r2.y, r2.x, l(16) + breakc_nz r2.y + iadd r2.y, r0.y, r2.x + ld_structured r3.x, r2.y, l(16), g0.xxxx + imad r2.y, r2.x, l(3), l(-16) + ishl r2.y, r3.x, r2.y + or r12.w, r2.y, r12.w + iadd r2.x, r2.x, l(1) + endloop + else + ieq r0.z, r0.w, l(1) + if_nz r0.z + ishl r0.z, r1.y, l(2) + iadd r0.z, r0.z, l(2) + ld_structured r2.xyz, r0.y, l(68), g0.xyzx + ishl r3.x, r2.x, l(6) + ishl r3.y, r2.z, l(22) + and r2.xz, r3.xxyx, l(0x00003f00, 0, 0x3f000000, 0) + or r0.z, r0.z, r2.x + ld_structured r3.xyz, r0.y, l(84), g0.xyzx + ishl r4.x, r3.x, l(12) + ishl r4.y, r3.y, l(4) + ishl r4.z, r3.z, l(28) + and r3.xyz, r4.xyzx, l(0x000fc000, 4032, 0xc0000000, 0) + or r0.z, r0.z, r3.x + iadd r1.w, r0.y, l(1) + ld_structured r4.xyz, r1.w, l(68), g0.xyzx + ishl r5.x, r4.x, l(18) + ishl r5.y, r4.y, l(10) + ishl r5.z, r4.z, l(2) + and r4.xyz, r5.xyzx, l(0x03f00000, 0x0003f000, 1008, 0) + or r0.z, r0.z, r4.x + ld_structured r5.xyz, r1.w, l(84), g0.xyzx + ishl r6.x, r5.x, l(24) + ishl r6.y, r5.y, l(16) + ishl r6.z, r5.z, l(8) + and r5.xyz, r6.xyzx, l(0xfc000000, 0x00fc0000, 0x0000fc00, 0) + or r12.x, r0.z, r5.x + ushr r0.z, r2.y, l(2) + and r0.z, r0.z, l(63) + iadd r0.z, r3.y, r0.z + iadd r0.z, r4.y, r0.z + iadd r0.z, r5.y, r0.z + iadd r0.z, r2.z, r0.z + iadd r12.y, r3.z, r0.z + ld_structured r2.x, r0.y, l(92), g0.xxxx + ushr r0.z, r2.x, l(4) + and r0.z, r0.z, l(15) + iadd r0.z, r4.z, r0.z + iadd r0.z, r5.z, r0.z + ld_structured r2.x, r0.y, l(68), g0.xxxx + ishl r2.x, r2.x, l(15) + and r2.x, r2.x, l(0x00010000) + iadd r0.z, r0.z, r2.x + ld_structured r2.x, r1.w, l(68), g0.xxxx + ishl r2.x, r2.x, l(16) + and r2.x, r2.x, l(0x00020000) + iadd r0.z, r0.z, r2.x + ld_structured r2.x, r0.y, l(16), g0.xxxx + ishl r2.x, r2.x, l(18) + iadd r0.z, r0.z, r2.x + ieq r2.y, l(15), icb[r1.y + 128].y + if_nz r2.y + iadd r3.xyzw, r0.yyyy, l(15, 14, 13, 12) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.y, r4.x, l(30) + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(27) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + ishl r2.z, r4.x, l(24) + or r2.y, r2.z, r2.y + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(21) + or r2.y, r2.z, r2.y + iadd r3.xyzw, r0.yyyy, l(11, 10, 9, 8) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.z, r4.x, l(18) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(15) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + ishl r2.z, r4.x, l(12) + or r2.y, r2.z, r2.y + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(9) + or r2.y, r2.z, r2.y + iadd r3.xyzw, r0.yyyy, l(7, 6, 5, 4) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.z, r4.x, l(6) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(3) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + or r12.w, r2.y, r4.x + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.y, r3.x, l(29) + iadd r2.zw, r0.yyyy, l(0, 0, 3, 2) + ld_structured r3.x, r2.z, l(16), g0.xxxx + ishl r2.z, r3.x, l(26) + or r2.y, r2.z, r2.y + ld_structured r3.x, r2.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(23) + or r2.y, r2.z, r2.y + ld_structured r3.x, r1.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(20) + or r2.y, r2.z, r2.y + or r2.y, r2.x, r2.y + or r12.z, r0.z, r2.y + else + ieq r2.y, l(2), icb[r1.y + 128].y + if_nz r2.y + iadd r3.xyzw, r0.yyyy, l(15, 14, 13, 12) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.y, r4.x, l(29) + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(26) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + ishl r2.z, r4.x, l(23) + or r2.y, r2.z, r2.y + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(20) + or r2.y, r2.z, r2.y + iadd r3.xyzw, r0.yyyy, l(11, 10, 9, 8) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.z, r4.x, l(17) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(14) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + ishl r2.z, r4.x, l(11) + or r2.y, r2.z, r2.y + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(8) + or r2.y, r2.z, r2.y + iadd r3.xyzw, r0.yyyy, l(7, 6, 5, 4) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.z, r4.x, l(5) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(2) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + ushr r2.z, r4.x, l(1) + or r12.w, r2.z, r2.y + ishl r2.y, r4.x, l(31) + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(28) + or r2.y, r2.z, r2.y + iadd r2.zw, r0.yyyy, l(0, 0, 3, 2) + ld_structured r3.x, r2.z, l(16), g0.xxxx + ishl r2.z, r3.x, l(25) + or r2.y, r2.z, r2.y + ld_structured r3.x, r2.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(23) + or r2.y, r2.z, r2.y + ld_structured r3.x, r1.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(20) + or r2.y, r2.z, r2.y + or r2.y, r2.x, r2.y + or r12.z, r0.z, r2.y + else + ieq r2.y, l(8), icb[r1.y + 128].y + if_nz r2.y + iadd r3.xyzw, r0.yyyy, l(15, 14, 13, 12) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.y, r4.x, l(29) + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(26) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + ishl r2.z, r4.x, l(23) + or r2.y, r2.z, r2.y + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(20) + or r2.y, r2.z, r2.y + iadd r3.xyzw, r0.yyyy, l(11, 10, 9, 8) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.z, r4.x, l(17) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(14) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + ishl r2.z, r4.x, l(11) + or r2.y, r2.z, r2.y + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(9) + or r2.y, r2.z, r2.y + iadd r3.xyzw, r0.yyyy, l(7, 6, 5, 4) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.z, r4.x, l(6) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(3) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + or r12.w, r2.y, r4.x + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.y, r3.x, l(29) + iadd r2.zw, r0.yyyy, l(0, 0, 3, 2) + ld_structured r3.x, r2.z, l(16), g0.xxxx + ishl r2.z, r3.x, l(26) + or r2.y, r2.z, r2.y + ld_structured r3.x, r2.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(23) + or r2.y, r2.z, r2.y + ld_structured r3.x, r1.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(20) + or r2.y, r2.z, r2.y + or r2.y, r2.x, r2.y + or r12.z, r0.z, r2.y + else + iadd r3.xyzw, r0.yyyy, l(15, 14, 13, 12) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.y, r4.x, l(29) + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(26) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + ishl r2.z, r4.x, l(23) + or r2.y, r2.z, r2.y + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(20) + or r2.y, r2.z, r2.y + iadd r3.xyzw, r0.yyyy, l(11, 10, 9, 8) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.z, r4.x, l(17) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(14) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + ishl r2.z, r4.x, l(11) + or r2.y, r2.z, r2.y + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(8) + or r2.y, r2.z, r2.y + iadd r3.xyzw, r0.yyyy, l(7, 6, 5, 4) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r2.z, r4.x, l(6) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.y, l(16), g0.xxxx + ishl r2.z, r4.x, l(4) + or r2.y, r2.z, r2.y + ld_structured r4.x, r3.z, l(16), g0.xxxx + or r12.w, r2.y, r4.x + ld_structured r3.x, r3.w, l(16), g0.xxxx + ishl r2.y, r3.x, l(29) + iadd r2.zw, r0.yyyy, l(0, 0, 3, 2) + ld_structured r3.x, r2.z, l(16), g0.xxxx + ishl r2.z, r3.x, l(26) + or r2.y, r2.z, r2.y + ld_structured r3.x, r2.w, l(16), g0.xxxx + ishl r2.z, r3.x, l(23) + or r2.y, r2.z, r2.y + ld_structured r3.x, r1.w, l(16), g0.xxxx + ishl r1.w, r3.x, l(20) + or r1.w, r1.w, r2.y + or r1.w, r2.x, r1.w + or r12.z, r0.z, r1.w + endif + endif + endif + else + ieq r0.z, r0.w, l(2) + if_nz r0.z + ishl r0.z, r1.y, l(3) + iadd r0.z, r0.z, l(-512) + iadd r0.z, r0.z, l(4) + ld_structured r2.xyz, r0.y, l(68), g0.xyzx + ishl r3.x, r2.x, l(6) + ishl r3.y, r2.y, l(4) + ishl r3.z, r2.z, l(2) + and r3.xyz, r3.xyzx, l(0x00003e00, 3968, 992, 0) + or r0.z, r0.z, r3.x + ld_structured r4.xyz, r0.y, l(84), g0.xyzx + ishl r5.x, r4.x, l(11) + ishl r5.y, r4.y, l(9) + ishl r5.z, r4.z, l(7) + and r5.xyz, r5.xyzx, l(0x0007c000, 0x0001f000, 0x00007c00, 0) + or r0.z, r0.z, r5.x + iadd r2.xw, r0.yyyy, l(1, 0, 0, 2) + ld_structured r6.xyz, r2.x, l(68), g0.xyzx + ishl r7.x, r6.x, l(16) + ishl r7.y, r6.y, l(14) + ishl r7.z, r6.z, l(12) + and r7.xyz, r7.xyzx, l(0x00f80000, 0x003e0000, 0x000f8000, 0) + or r0.z, r0.z, r7.x + ld_structured r8.xyz, r2.x, l(84), g0.xyzx + ishl r9.x, r8.x, l(21) + ishl r9.y, r8.y, l(19) + ishl r9.z, r8.z, l(17) + and r9.xyz, r9.xyzx, l(0x1f000000, 0x07c00000, 0x01f00000, 0) + or r0.z, r0.z, r9.x + ld_structured r10.xyz, r2.w, l(68), g0.xyzx + ishl r11.x, r10.x, l(26) + ishl r11.y, r10.y, l(24) + ishl r11.z, r10.z, l(22) + and r11.xyz, r11.xyzx, l(0xe0000000, 0xf8000000, 0x3e000000, 0) + or r12.x, r0.z, r11.x + ld_structured r13.x, r2.w, l(68), g0.xxxx + ushr r0.z, r13.x, l(6) + and r0.z, r0.z, l(3) + ld_structured r13.xyz, r2.w, l(84), g0.xyzx + ushr r14.x, r13.x, l(1) + ushr r14.y, r13.y, l(3) + and r3.xw, r14.xxxy, l(124, 0, 0, 31) + iadd r0.z, r0.z, r3.x + iadd r0.z, r3.y, r0.z + iadd r0.z, r5.y, r0.z + iadd r0.z, r7.y, r0.z + iadd r0.z, r9.y, r0.z + iadd r12.y, r11.y, r0.z + iadd r0.z, r3.z, r3.w + iadd r0.z, r5.z, r0.z + iadd r0.z, r7.z, r0.z + iadd r0.z, r9.z, r0.z + iadd r0.z, r11.z, r0.z + ishl r1.w, r13.z, l(27) + and r1.w, r1.w, l(0xc0000000) + iadd r12.z, r0.z, r1.w + ld_structured r2.x, r2.w, l(92), g0.xxxx + ushr r0.z, r2.x, l(5) + and r0.z, r0.z, l(7) + ld_structured r2.x, r0.y, l(16), g0.xxxx + ishl r1.w, r2.x, l(3) + iadd r0.z, r0.z, r1.w + mov r1.w, r0.z + mov r2.x, l(1) + loop + ult r2.y, icb[r1.y + 128].y, r2.x + breakc_nz r2.y + iadd r2.y, r0.y, r2.x + ld_structured r3.x, r2.y, l(16), g0.xxxx + ishl r2.y, r2.x, l(1) + iadd r2.y, r2.y, l(2) + ishl r2.y, r3.x, r2.y + or r1.w, r1.w, r2.y + iadd r2.x, r2.x, l(1) + endloop + mov r0.z, r1.w + mov r2.y, r2.x + loop + ult r2.z, icb[r1.y + 128].z, r2.y + breakc_nz r2.z + iadd r2.z, r0.y, r2.y + ld_structured r3.x, r2.z, l(16), g0.xxxx + ishl r2.z, r2.y, l(1) + iadd r2.z, r2.z, l(1) + ishl r2.z, r3.x, r2.z + or r0.z, r0.z, r2.z + iadd r2.y, r2.y, l(1) + endloop + mov r12.w, r0.z + mov r1.w, r2.y + loop + uge r2.x, r1.w, l(16) + breakc_nz r2.x + iadd r2.x, r0.y, r1.w + ld_structured r3.x, r2.x, l(16), g0.xxxx + ishl r2.x, r1.w, l(1) + ishl r2.x, r3.x, r2.x + or r12.w, r2.x, r12.w + iadd r1.w, r1.w, l(1) + endloop + else + ieq r0.z, r0.w, l(3) + if_nz r0.z + ishl r0.z, r1.y, l(4) + iadd r0.z, r0.z, l(8) + ld_structured r2.xyz, r0.y, l(68), g0.xyzx + ishl r3.x, r2.x, l(9) + ishl r3.y, r2.y, l(5) + ishl r3.z, r2.z, l(1) + and r3.xyz, r3.xyzx, l(0x0001fc00, 8128, 508, 0) + or r0.z, r0.z, r3.x + ld_structured r4.xyz, r0.y, l(84), g0.xyzx + ishl r5.x, r4.x, l(16) + ishl r5.y, r4.y, l(12) + ishl r5.z, r4.z, l(8) + and r5.xyz, r5.xyzx, l(0x00fe0000, 0x000fe000, 0x0000fe00, 0) + or r0.z, r0.z, r5.x + iadd r1.w, r0.y, l(1) + ld_structured r6.xyz, r1.w, l(68), g0.xyzx + ishl r7.x, r6.x, l(23) + ishl r7.y, r6.y, l(19) + ishl r7.z, r6.z, l(15) + and r7.xyz, r7.xyzx, l(0x7f000000, 0x07f00000, 0x007f0000, 0) + or r0.z, r0.z, r7.x + ld_structured r8.xyz, r1.w, l(84), g0.xyzx + ishl r9.x, r8.x, l(30) + ishl r9.y, r8.y, l(26) + ishl r9.z, r8.z, l(22) + and r9.xyz, r9.xyzx, l(0x80000000, 0xf8000000, 0x3f800000, 0) + or r12.x, r0.z, r9.x + ld_structured r10.xy, r1.w, l(84), g0.xyxx + ushr r11.x, r10.x, l(2) + ushr r11.y, r10.y, l(6) + and r2.xw, r11.xxxy, l(63, 0, 0, 3) + iadd r2.xy, r3.yzyy, r2.xwxx + iadd r2.xy, r5.yzyy, r2.xyxx + iadd r2.xy, r7.yzyy, r2.xyxx + iadd r2.xy, r9.yzyy, r2.xyxx + ld_structured r3.x, r0.y, l(68), g0.xxxx + ishl r0.z, r3.x, l(30) + and r0.z, r0.z, l(0x40000000) + iadd r0.z, r0.z, r2.y + ld_structured r3.x, r0.y, l(84), g0.xxxx + ishl r2.y, r3.x, l(31) + iadd r12.z, r0.z, r2.y + ld_structured r3.x, r1.w, l(68), g0.xxxx + and r0.z, r3.x, l(1) + ld_structured r3.x, r1.w, l(84), g0.xxxx + ishl r1.w, r3.x, l(1) + and r1.w, r1.w, l(2) + iadd r0.z, r0.z, r1.w + ld_structured r3.x, r0.y, l(16), g0.xxxx + ishl r1.w, r3.x, l(2) + iadd r0.z, r0.z, r1.w + mov r1.w, r0.z + mov r2.y, l(1) + loop + ult r2.z, icb[r1.y + 128].y, r2.y + breakc_nz r2.z + iadd r2.z, r0.y, r2.y + ld_structured r3.x, r2.z, l(16), g0.xxxx + ishl r2.z, r2.y, l(1) + iadd r2.z, r2.z, l(1) + ishl r2.z, r3.x, r2.z + or r1.w, r1.w, r2.z + iadd r2.y, r2.y, l(1) + endloop + mov r12.w, r1.w + mov r0.z, r2.y + loop + uge r2.z, r0.z, l(16) + breakc_nz r2.z + iadd r2.z, r0.z, r0.y + ld_structured r3.x, r2.z, l(16), g0.xxxx + ishl r2.z, r0.z, l(1) + ishl r2.z, r3.x, r2.z + or r12.w, r2.z, r12.w + iadd r0.z, r0.z, l(1) + endloop + mov r12.y, r2.x + else + ieq r0.z, r0.w, l(4) + if_nz r0.z + ishl r0.z, r1.z, l(5) + and r0.z, r0.z, l(96) + iadd r0.z, r0.z, l(16) + ishl r1.x, r1.x, l(7) + iadd r0.z, r0.z, r1.x + ld_structured r2.xyzw, r0.y, l(68), g0.xyzw + ishl r3.x, r2.x, l(5) + ishl r3.y, r2.y, l(15) + ishl r3.z, r2.z, l(25) + ishl r3.w, r2.w, l(4) + and r2.xyzw, r3.xyzw, l(7936, 0x007c0000, 0xf0000000, 4032) + iadd r0.z, r0.z, r2.x + ld_structured r3.xyzw, r0.y, l(84), g0.xyzw + ishl r4.xz, r3.xxwx, l(10) + ishl r4.y, r3.y, l(20) + and r3.xyw, r4.xyxz, l(0x0003e000, 0x0f800000, 0, 0x0003f000) + iadd r0.z, r0.z, r3.x + iadd r0.z, r2.y, r0.z + iadd r0.z, r3.y, r0.z + iadd r12.x, r2.z, r0.z + ld_structured r4.x, r0.y, l(76), g0.xxxx + ushr r0.z, r4.x, l(7) + and r0.z, r0.z, l(1) + ushr r1.x, r3.z, l(2) + and r1.x, r1.x, l(62) + iadd r0.z, r0.z, r1.x + iadd r0.z, r2.w, r0.z + iadd r0.z, r3.w, r0.z + ld_structured r2.xy, r0.y, l(16), g0.xyxx + ishl r3.x, r2.x, l(18) + ishl r3.y, r2.y, l(17) + and r1.xw, r3.xxxy, l(0x00040000, 0, 0, 0x00060000) + iadd r0.z, r0.z, r1.x + iadd r2.xyzw, r0.yyyy, l(1, 2, 3, 4) + ld_structured r3.xy, r2.x, l(16), g0.xyxx + ishl r3.xy, r3.xyxx, l(19) + iadd r0.z, r0.z, r3.x + ld_structured r4.xy, r2.y, l(16), g0.xyxx + ishl r1.x, r4.x, l(21) + ishl r2.x, r4.y, l(22) + or r0.z, r0.z, r1.x + ld_structured r4.xy, r2.z, l(16), g0.xyxx + ishl r1.x, r4.x, l(23) + ishl r2.y, r4.y, l(25) + or r0.z, r0.z, r1.x + ld_structured r4.xy, r2.w, l(16), g0.xyxx + ishl r1.x, r4.x, l(25) + ishl r2.z, r4.y, l(28) + or r0.z, r0.z, r1.x + iadd r4.xyzw, r0.yyyy, l(5, 6, 7, 8) + ld_structured r5.xy, r4.x, l(16), g0.xyxx + ishl r1.x, r5.x, l(27) + ishl r2.w, r5.y, l(31) + or r0.z, r0.z, r1.x + ld_structured r5.xy, r4.y, l(16), g0.xyxx + ishl r1.x, r5.x, l(29) + ishl r3.x, r5.y, l(2) + or r0.z, r0.z, r1.x + ld_structured r5.xy, r4.z, l(16), g0.xyxx + ishl r1.x, r5.x, l(31) + ishl r3.z, r5.y, l(5) + or r12.y, r0.z, r1.x + ld_structured r5.x, r4.z, l(16), g0.xxxx + ushr r0.z, r5.x, l(1) + ld_structured r5.xy, r4.w, l(16), g0.xyxx + ishl r1.x, r5.x, l(1) + ishl r3.w, r5.y, l(8) + or r0.z, r0.z, r1.x + iadd r5.xyzw, r0.yyyy, l(9, 10, 11, 12) + ld_structured r6.xy, r5.x, l(16), g0.xyxx + ishl r1.x, r6.x, l(3) + ishl r4.y, r6.y, l(11) + or r0.z, r0.z, r1.x + ld_structured r6.xy, r5.y, l(16), g0.xyxx + ishl r1.x, r6.x, l(5) + ishl r4.z, r6.y, l(14) + or r0.z, r0.z, r1.x + ld_structured r6.xy, r5.z, l(16), g0.xyxx + ishl r1.x, r6.x, l(7) + ishl r4.w, r6.y, l(17) + or r0.z, r0.z, r1.x + ld_structured r5.xy, r5.w, l(16), g0.xyxx + ishl r1.x, r5.x, l(9) + ishl r5.x, r5.y, l(20) + or r0.z, r0.z, r1.x + iadd r5.yzw, r0.yyyy, l(0, 13, 14, 15) + ld_structured r6.xy, r5.y, l(16), g0.xyxx + ishl r1.x, r6.x, l(11) + ishl r5.y, r6.y, l(23) + or r0.z, r0.z, r1.x + ld_structured r6.xy, r5.z, l(16), g0.xyxx + ishl r1.x, r6.x, l(13) + ishl r5.z, r6.y, l(26) + or r0.z, r0.z, r1.x + ld_structured r6.xy, r5.w, l(16), g0.xyxx + ishl r1.x, r6.x, l(15) + ishl r5.w, r6.y, l(29) + or r0.z, r0.z, r1.x + or r0.z, r1.w, r0.z + or r0.z, r3.y, r0.z + or r0.z, r2.x, r0.z + or r0.z, r2.y, r0.z + or r0.z, r2.z, r0.z + or r12.z, r2.w, r0.z + ld_structured r2.x, r4.x, l(20), g0.xxxx + ushr r0.z, r2.x, l(1) + or r0.z, r3.x, r0.z + or r0.z, r3.z, r0.z + or r0.z, r3.w, r0.z + or r0.z, r4.y, r0.z + or r0.z, r4.z, r0.z + or r0.z, r4.w, r0.z + or r0.z, r5.x, r0.z + or r0.z, r5.y, r0.z + or r0.z, r5.z, r0.z + or r12.w, r5.w, r0.z + else + ieq r0.z, r0.w, l(5) + if_nz r0.z + ishl r0.z, r1.z, l(6) + iadd r0.z, r0.z, l(32) + ld_structured r2.xyzw, r0.y, l(68), g0.xyzw + ishl r3.x, r2.x, l(7) + ishl r3.y, r2.y, l(21) + ishl r3.z, r2.z, l(3) + ishl r1.x, r2.w, l(18) + and r2.xyz, r3.xyzx, l(0x00007f00, 0x1fc00000, 2032, 0) + or r0.z, r0.z, r2.x + ld_structured r3.xyzw, r0.y, l(84), g0.xyzw + ishl r4.x, r3.x, l(14) + ishl r4.y, r3.y, l(28) + ishl r4.z, r3.z, l(10) + ishl r1.z, r3.w, l(26) + and r3.xyz, r4.xyzx, l(0x003f8000, 0xe0000000, 0x0003f800, 0) + or r0.z, r0.z, r3.x + or r0.z, r2.y, r0.z + or r12.x, r3.y, r0.z + ld_structured r4.x, r0.y, l(88), g0.xxxx + ushr r0.z, r4.x, l(4) + and r0.z, r0.z, l(15) + iadd r0.z, r2.z, r0.z + iadd r0.z, r3.z, r0.z + iadd r0.z, r1.x, r0.z + or r12.y, r1.z, r0.z + ld_structured r2.x, r0.y, l(96), g0.xxxx + ushr r0.z, r2.x, l(6) + ld_structured r2.xy, r0.y, l(16), g0.xyxx + ishl r1.x, r2.x, l(2) + ishl r1.z, r2.y, l(1) + or r0.z, r0.z, r1.x + iadd r2.xyzw, r0.yyyy, l(1, 2, 3, 4) + ld_structured r3.xy, r2.x, l(16), g0.xyxx + ishl r1.x, r3.x, l(3) + ishl r1.w, r3.y, l(2) + or r0.z, r0.z, r1.x + ld_structured r3.xy, r2.y, l(16), g0.xyxx + ishl r1.x, r3.x, l(5) + ishl r2.x, r3.y, l(4) + or r0.z, r0.z, r1.x + ld_structured r3.xy, r2.z, l(16), g0.xyxx + ishl r1.x, r3.x, l(7) + ishl r2.y, r3.y, l(6) + or r0.z, r0.z, r1.x + ld_structured r3.xy, r2.w, l(16), g0.xyxx + ishl r1.x, r3.x, l(9) + ishl r2.z, r3.y, l(8) + or r0.z, r0.z, r1.x + iadd r3.xyzw, r0.yyyy, l(5, 6, 7, 8) + ld_structured r4.xy, r3.x, l(16), g0.xyxx + ishl r1.x, r4.x, l(11) + ishl r2.w, r4.y, l(10) + or r0.z, r0.z, r1.x + ld_structured r4.xy, r3.y, l(16), g0.xyxx + ishl r1.x, r4.x, l(13) + ishl r3.x, r4.y, l(12) + or r0.z, r0.z, r1.x + ld_structured r4.xy, r3.z, l(16), g0.xyxx + ishl r1.x, r4.x, l(15) + ishl r3.y, r4.y, l(14) + or r0.z, r0.z, r1.x + ld_structured r4.xy, r3.w, l(16), g0.xyxx + ishl r1.x, r4.x, l(17) + ishl r3.z, r4.y, l(16) + or r0.z, r0.z, r1.x + iadd r4.xyzw, r0.yyyy, l(9, 10, 11, 12) + ld_structured r5.xy, r4.x, l(16), g0.xyxx + ishl r1.x, r5.x, l(19) + ishl r3.w, r5.y, l(18) + or r0.z, r0.z, r1.x + ld_structured r5.xy, r4.y, l(16), g0.xyxx + ishl r1.x, r5.x, l(21) + ishl r4.x, r5.y, l(20) + or r0.z, r0.z, r1.x + ld_structured r5.xy, r4.z, l(16), g0.xyxx + ishl r1.x, r5.x, l(23) + ishl r4.y, r5.y, l(22) + or r0.z, r0.z, r1.x + ld_structured r5.xy, r4.w, l(16), g0.xyxx + ishl r1.x, r5.x, l(25) + ishl r4.z, r5.y, l(24) + or r0.z, r0.z, r1.x + iadd r5.xyz, r0.yyyy, l(13, 14, 15, 0) + ld_structured r6.xy, r5.x, l(16), g0.xyxx + ishl r1.x, r6.x, l(27) + ishl r4.w, r6.y, l(26) + or r0.z, r0.z, r1.x + ld_structured r6.xy, r5.y, l(16), g0.xyxx + ishl r1.x, r6.x, l(29) + ishl r5.x, r6.y, l(28) + or r0.z, r0.z, r1.x + ld_structured r6.xy, r5.z, l(16), g0.xyxx + ishl r1.x, r6.x, l(31) + ishl r5.y, r6.y, l(30) + or r12.z, r0.z, r1.x + ld_structured r6.x, r5.z, l(16), g0.xxxx + ushr r0.z, r6.x, l(1) + or r0.z, r1.z, r0.z + or r0.z, r1.w, r0.z + or r0.z, r2.x, r0.z + or r0.z, r2.y, r0.z + or r0.z, r2.z, r0.z + or r0.z, r2.w, r0.z + or r0.z, r3.x, r0.z + or r0.z, r3.y, r0.z + or r0.z, r3.z, r0.z + or r0.z, r3.w, r0.z + or r0.z, r4.x, r0.z + or r0.z, r4.y, r0.z + or r0.z, r4.z, r0.z + or r0.z, r4.w, r0.z + or r0.z, r5.x, r0.z + or r12.w, r5.y, r0.z + else + ieq r0.z, r0.w, l(6) + if_nz r0.z + ld_structured r2.xyzw, r0.y, l(68), g0.xyzw + ishl r3.x, r2.x, l(6) + ishl r3.y, r2.y, l(20) + ishl r3.z, r2.z, l(2) + ishl r3.w, r2.w, l(16) + and r2.xyzw, r3.xyzw, l(0x00003f80, 0x0fe00000, 1016, 0x00fe0000) + iadd r0.z, r2.x, l(64) + ld_structured r3.xyzw, r0.y, l(84), g0.xyzw + ishl r4.x, r3.x, l(13) + ishl r4.y, r3.y, l(27) + ishl r4.z, r3.z, l(9) + ishl r4.w, r3.w, l(23) + and r3.xyzw, r4.xyzw, l(0x001fc000, 0xf0000000, 0x0001fc00, 0x7f000000) + iadd r0.z, r0.z, r3.x + iadd r0.z, r2.y, r0.z + iadd r12.x, r3.y, r0.z + ld_structured r4.xy, r0.y, l(84), g0.xyxx + ushr r0.z, r4.y, l(5) + and r0.z, r0.z, l(7) + iadd r0.z, r2.z, r0.z + iadd r0.z, r3.z, r0.z + iadd r0.z, r2.w, r0.z + iadd r0.z, r3.w, r0.z + ld_structured r2.x, r0.y, l(68), g0.xxxx + ishl r0.w, r2.x, l(31) + iadd r12.y, r0.w, r0.z + and r0.z, r4.x, l(1) + ld_structured r2.x, r0.y, l(16), g0.xxxx + ishl r0.w, r2.x, l(1) + iadd r0.z, r0.w, r0.z + iadd r2.xyzw, r0.yyyy, l(1, 2, 3, 4) + ld_structured r3.x, r2.x, l(16), g0.xxxx + ishl r0.w, r3.x, l(4) + or r0.z, r0.w, r0.z + ld_structured r3.x, r2.y, l(16), g0.xxxx + ishl r0.w, r3.x, l(8) + or r0.z, r0.w, r0.z + ld_structured r3.x, r2.z, l(16), g0.xxxx + ishl r0.w, r3.x, l(12) + or r0.z, r0.w, r0.z + ld_structured r2.x, r2.w, l(16), g0.xxxx + ishl r0.w, r2.x, l(16) + or r0.z, r0.w, r0.z + iadd r2.xyzw, r0.yyyy, l(5, 6, 7, 8) + ld_structured r3.x, r2.x, l(16), g0.xxxx + ishl r0.w, r3.x, l(20) + or r0.z, r0.w, r0.z + ld_structured r3.x, r2.y, l(16), g0.xxxx + ishl r0.w, r3.x, l(24) + or r0.z, r0.w, r0.z + ld_structured r3.x, r2.z, l(16), g0.xxxx + ishl r0.w, r3.x, l(28) + or r12.z, r0.w, r0.z + ld_structured r2.x, r2.w, l(16), g0.xxxx + iadd r3.xyzw, r0.yyyy, l(9, 10, 11, 12) + ld_structured r4.x, r3.x, l(16), g0.xxxx + ishl r0.z, r4.x, l(4) + or r0.z, r0.z, r2.x + ld_structured r2.x, r3.y, l(16), g0.xxxx + ishl r0.w, r2.x, l(8) + or r0.z, r0.w, r0.z + ld_structured r2.x, r3.z, l(16), g0.xxxx + ishl r0.w, r2.x, l(12) + or r0.z, r0.w, r0.z + ld_structured r2.x, r3.w, l(16), g0.xxxx + ishl r0.w, r2.x, l(16) + or r0.z, r0.w, r0.z + iadd r1.xzw, r0.yyyy, l(13, 0, 14, 15) + ld_structured r2.x, r1.x, l(16), g0.xxxx + ishl r0.w, r2.x, l(20) + or r0.z, r0.w, r0.z + ld_structured r2.x, r1.z, l(16), g0.xxxx + ishl r0.w, r2.x, l(24) + or r0.z, r0.w, r0.z + ld_structured r2.x, r1.w, l(16), g0.xxxx + ishl r0.w, r2.x, l(28) + or r12.w, r0.w, r0.z + else + ishl r0.z, r1.y, l(8) + iadd r0.z, r0.z, l(128) + ld_structured r2.xyzw, r0.y, l(68), g0.xyzw + ishl r3.x, r2.x, l(11) + ishl r3.y, r2.z, l(19) + ishl r3.z, r2.w, l(7) + and r1.xzw, r3.xxyz, l(0x0007c000, 0, 0x07c00000, 0x00007c00) + or r0.z, r0.z, r1.x + ld_structured r3.xyzw, r0.y, l(84), g0.xyzw + ishl r4.x, r3.x, l(16) + ishl r4.y, r3.y, l(4) + ishl r4.z, r3.z, l(24) + ishl r4.w, r3.w, l(12) + and r4.xyzw, r4.xyzw, l(0x00f80000, 3968, 0xf8000000, 0x000f8000) + or r0.z, r0.z, r4.x + iadd r0.w, r0.y, l(1) + ld_structured r5.xyzw, r0.w, l(68), g0.xyzw + ishl r6.x, r5.x, l(21) + ishl r6.y, r5.y, l(9) + ishl r6.z, r5.w, l(17) + and r6.xyz, r6.xyzx, l(0x1f000000, 0x0001f000, 0x01f00000, 0) + or r0.z, r0.z, r6.x + ld_structured r7.xyzw, r0.w, l(84), g0.xyzw + ishl r8.x, r7.x, l(26) + ishl r8.y, r7.y, l(14) + ishl r8.z, r7.z, l(2) + ishl r8.w, r7.w, l(22) + and r8.xyzw, r8.xyzw, l(0xe0000000, 0x003e0000, 992, 0x3e000000) + or r12.x, r0.z, r8.x + ld_structured r9.x, r0.w, l(84), g0.xxxx + ushr r10.x, r9.x, l(6) + ushr r10.y, r9.x, l(1) + and r6.xw, r10.xxxy, l(3, 0, 0, 2) + ushr r0.z, r2.y, l(1) + and r0.z, r0.z, l(124) + iadd r0.z, r0.z, r6.x + iadd r0.z, r4.y, r0.z + iadd r0.z, r6.y, r0.z + iadd r0.z, r8.y, r0.z + iadd r0.z, r1.z, r0.z + iadd r12.y, r4.z, r0.z + ushr r0.z, r5.z, l(3) + and r0.z, r0.z, l(31) + iadd r0.z, r8.z, r0.z + iadd r0.z, r1.w, r0.z + iadd r0.z, r4.w, r0.z + iadd r0.z, r6.z, r0.z + iadd r0.z, r8.w, r0.z + ld_structured r2.x, r0.y, l(68), g0.xxxx + ishl r1.x, r2.x, l(28) + and r1.x, r1.x, l(0x40000000) + iadd r0.z, r0.z, r1.x + ld_structured r2.x, r0.y, l(84), g0.xxxx + ishl r1.x, r2.x, l(29) + and r1.x, r1.x, l(0x80000000) + iadd r12.z, r0.z, r1.x + ld_structured r2.x, r0.w, l(68), g0.xxxx + ushr r0.z, r2.x, l(2) + and r0.z, r0.z, l(1) + iadd r0.z, r6.w, r0.z + ld_structured r2.x, r0.y, l(16), g0.xxxx + ishl r0.w, r2.x, l(2) + iadd r0.z, r0.w, r0.z + mov r0.w, r0.z + mov r1.x, l(1) + loop + ult r1.z, icb[r1.y + 128].y, r1.x + breakc_nz r1.z + iadd r1.z, r0.y, r1.x + ld_structured r2.x, r1.z, l(16), g0.xxxx + ishl r1.z, r1.x, l(1) + iadd r1.z, r1.z, l(1) + ishl r1.z, r2.x, r1.z + or r0.w, r0.w, r1.z + iadd r1.x, r1.x, l(1) + endloop + mov r12.w, r0.w + mov r0.z, r1.x + loop + uge r1.y, r0.z, l(16) + breakc_nz r1.y + iadd r1.y, r0.z, r0.y + ld_structured r2.x, r1.y, l(16), g0.xxxx + ishl r1.y, r0.z, l(1) + ishl r1.y, r2.x, r1.y + or r12.w, r1.y, r12.w + iadd r0.z, r0.z, l(1) + endloop + endif + endif + endif + endif + endif + endif + endif + store_structured u0.xyzw, r0.x, l(0), r12.xyzw +endif +ret +// Approximately 0 instruction slots used +#endif + +const BYTE BC7Encode_EncodeBlockCS[] = +{ + 68, 88, 66, 67, 38, 175, + 165, 204, 73, 182, 127, 102, + 182, 246, 162, 152, 80, 235, + 28, 253, 1, 0, 0, 0, + 200, 193, 0, 0, 3, 0, + 0, 0, 44, 0, 0, 0, + 60, 0, 0, 0, 76, 0, + 0, 0, 73, 83, 71, 78, + 8, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 79, 83, 71, 78, 8, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 83, 72, + 69, 88, 116, 193, 0, 0, + 64, 0, 5, 0, 93, 48, + 0, 0, 106, 8, 0, 1, + 53, 24, 0, 0, 2, 4, + 0, 0, 204, 204, 0, 0, + 80, 80, 104, 170, 15, 0, + 0, 0, 0, 0, 0, 0, + 136, 136, 0, 0, 64, 80, + 90, 106, 15, 0, 0, 0, + 0, 0, 0, 0, 238, 238, + 0, 0, 0, 66, 90, 90, + 15, 0, 0, 0, 0, 0, + 0, 0, 200, 236, 0, 0, + 168, 160, 80, 84, 15, 0, + 0, 0, 0, 0, 0, 0, + 128, 200, 0, 0, 0, 0, + 165, 165, 15, 0, 0, 0, + 0, 0, 0, 0, 236, 254, + 0, 0, 80, 80, 160, 160, + 15, 0, 0, 0, 0, 0, + 0, 0, 200, 254, 0, 0, + 160, 160, 85, 85, 15, 0, + 0, 0, 0, 0, 0, 0, + 128, 236, 0, 0, 80, 80, + 90, 90, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 200, + 0, 0, 0, 0, 85, 170, + 15, 0, 0, 0, 0, 0, + 0, 0, 236, 255, 0, 0, + 0, 85, 85, 170, 15, 0, + 0, 0, 0, 0, 0, 0, + 128, 254, 0, 0, 0, 85, + 170, 170, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 232, + 0, 0, 144, 144, 144, 144, + 15, 0, 0, 0, 0, 0, + 0, 0, 232, 255, 0, 0, + 148, 148, 148, 148, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 255, 0, 0, 164, 164, + 164, 164, 15, 0, 0, 0, + 0, 0, 0, 0, 240, 255, + 0, 0, 80, 148, 165, 169, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 240, 0, 0, + 80, 66, 10, 42, 15, 0, + 0, 0, 0, 0, 0, 0, + 16, 247, 0, 0, 64, 80, + 148, 165, 15, 0, 0, 0, + 0, 0, 0, 0, 142, 0, + 0, 0, 84, 80, 66, 10, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 113, 0, 0, + 0, 165, 165, 165, 8, 0, + 0, 0, 0, 0, 0, 0, + 206, 8, 0, 0, 160, 160, + 160, 85, 2, 0, 0, 0, + 0, 0, 0, 0, 140, 0, + 0, 0, 84, 84, 168, 168, + 2, 0, 0, 0, 0, 0, + 0, 0, 16, 115, 0, 0, + 64, 64, 106, 106, 8, 0, + 0, 0, 0, 0, 0, 0, + 0, 49, 0, 0, 0, 80, + 164, 164, 8, 0, 0, 0, + 0, 0, 0, 0, 206, 140, + 0, 0, 0, 5, 26, 26, + 15, 0, 0, 0, 0, 0, + 0, 0, 140, 8, 0, 0, + 164, 164, 80, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 16, 49, 0, 0, 144, 144, + 165, 170, 8, 0, 0, 0, + 0, 0, 0, 0, 102, 102, + 0, 0, 20, 105, 105, 20, + 2, 0, 0, 0, 0, 0, + 0, 0, 108, 54, 0, 0, + 0, 20, 105, 105, 2, 0, + 0, 0, 0, 0, 0, 0, + 232, 23, 0, 0, 160, 133, + 133, 160, 8, 0, 0, 0, + 0, 0, 0, 0, 240, 15, + 0, 0, 20, 20, 130, 170, + 8, 0, 0, 0, 0, 0, + 0, 0, 142, 113, 0, 0, + 80, 164, 164, 80, 2, 0, + 0, 0, 0, 0, 0, 0, + 156, 57, 0, 0, 0, 2, + 90, 106, 2, 0, 0, 0, + 0, 0, 0, 0, 170, 170, + 0, 0, 0, 128, 165, 169, + 15, 0, 0, 0, 0, 0, + 0, 0, 240, 240, 0, 0, + 168, 160, 144, 80, 15, 0, + 0, 0, 0, 0, 0, 0, + 90, 90, 0, 0, 80, 144, + 160, 168, 6, 0, 0, 0, + 0, 0, 0, 0, 204, 51, + 0, 0, 36, 36, 36, 36, + 8, 0, 0, 0, 0, 0, + 0, 0, 60, 60, 0, 0, + 0, 85, 170, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 170, 85, 0, 0, 36, 73, + 146, 36, 8, 0, 0, 0, + 0, 0, 0, 0, 150, 150, + 0, 0, 36, 146, 73, 36, + 15, 0, 0, 0, 0, 0, + 0, 0, 90, 165, 0, 0, + 80, 10, 165, 80, 15, 0, + 0, 0, 0, 0, 0, 0, + 206, 115, 0, 0, 80, 165, + 10, 80, 2, 0, 0, 0, + 0, 0, 0, 0, 200, 19, + 0, 0, 68, 68, 170, 170, + 8, 0, 0, 0, 0, 0, + 0, 0, 76, 50, 0, 0, + 0, 0, 102, 102, 2, 0, + 0, 0, 0, 0, 0, 0, + 220, 59, 0, 0, 160, 165, + 160, 165, 2, 0, 0, 0, + 0, 0, 0, 0, 150, 105, + 0, 0, 160, 80, 160, 80, + 2, 0, 0, 0, 0, 0, + 0, 0, 60, 195, 0, 0, + 40, 105, 40, 105, 15, 0, + 0, 0, 0, 0, 0, 0, + 102, 153, 0, 0, 68, 170, + 170, 68, 15, 0, 0, 0, + 0, 0, 0, 0, 96, 6, + 0, 0, 0, 102, 102, 102, + 6, 0, 0, 0, 0, 0, + 0, 0, 114, 2, 0, 0, + 68, 68, 68, 170, 6, 0, + 0, 0, 0, 0, 0, 0, + 228, 4, 0, 0, 168, 84, + 168, 84, 2, 0, 0, 0, + 0, 0, 0, 0, 64, 78, + 0, 0, 128, 149, 128, 149, + 6, 0, 0, 0, 0, 0, + 0, 0, 32, 39, 0, 0, + 0, 150, 150, 150, 8, 0, + 0, 0, 0, 0, 0, 0, + 54, 201, 0, 0, 168, 84, + 84, 168, 15, 0, 0, 0, + 0, 0, 0, 0, 108, 147, + 0, 0, 128, 149, 149, 128, + 15, 0, 0, 0, 0, 0, + 0, 0, 198, 57, 0, 0, + 20, 20, 20, 170, 2, 0, + 0, 0, 0, 0, 0, 0, + 156, 99, 0, 0, 0, 0, + 150, 150, 2, 0, 0, 0, + 0, 0, 0, 0, 54, 147, + 0, 0, 20, 20, 170, 170, + 15, 0, 0, 0, 0, 0, + 0, 0, 198, 156, 0, 0, + 160, 80, 80, 160, 15, 0, + 0, 0, 0, 0, 0, 0, + 126, 129, 0, 0, 160, 165, + 165, 160, 15, 0, 0, 0, + 0, 0, 0, 0, 24, 231, + 0, 0, 0, 0, 0, 150, + 15, 0, 0, 0, 0, 0, + 0, 0, 240, 204, 0, 0, + 128, 64, 128, 64, 15, 0, + 0, 0, 0, 0, 0, 0, + 204, 15, 0, 0, 168, 169, + 168, 169, 2, 0, 0, 0, + 0, 0, 0, 0, 68, 119, + 0, 0, 68, 170, 170, 170, + 2, 0, 0, 0, 0, 0, + 0, 0, 34, 238, 0, 0, + 84, 82, 74, 42, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 8, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 3, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 8, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 15, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 15, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 15, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 8, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 8, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 3, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 8, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 15, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 8, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 3, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 6, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 10, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 7, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 15, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 10, 0, 0, 0, 7, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 8, 0, + 0, 0, 7, 0, 0, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 3, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 10, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 10, 0, 0, 0, 9, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 0, 0, 8, 0, + 0, 0, 9, 0, 0, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 9, 0, 0, 0, + 9, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 10, 0, 0, 0, 9, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 6, 0, + 0, 0, 10, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 10, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 8, 0, 0, 0, 10, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 15, 0, + 0, 0, 10, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 10, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 6, 0, 0, 0, 11, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 6, 0, + 0, 0, 11, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 8, 0, 0, 0, + 11, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 11, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 3, 0, + 0, 0, 12, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 15, 0, 0, 0, + 12, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 15, 0, + 0, 0, 12, 0, 0, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 13, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 13, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 0, 0, 15, 0, + 0, 0, 13, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 15, 0, 0, 0, + 13, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 15, 0, 0, 0, 14, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 14, 0, 0, 0, + 0, 0, 0, 0, 13, 0, + 0, 0, 15, 0, 0, 0, + 14, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 3, 0, 0, 0, 14, 0, + 0, 0, 0, 0, 0, 0, + 12, 0, 0, 0, 15, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 6, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 6, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 5, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 3, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 6, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 8, 0, 0, 0, + 10, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 6, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 6, 0, 0, 0, 10, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 10, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 5, 0, 0, 0, + 10, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 6, 0, 0, 0, 10, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 8, 0, + 0, 0, 10, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 9, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 10, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 6, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 5, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 6, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 6, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 5, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 5, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 5, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 10, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 10, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 13, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 12, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 3, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 89, 0, 0, 4, 70, 142, + 32, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 88, 24, + 0, 4, 0, 112, 16, 0, + 0, 0, 0, 0, 85, 85, + 0, 0, 162, 0, 0, 4, + 0, 112, 16, 0, 1, 0, + 0, 0, 16, 0, 0, 0, + 158, 0, 0, 4, 0, 224, + 17, 0, 0, 0, 0, 0, + 16, 0, 0, 0, 95, 0, + 0, 2, 0, 64, 2, 0, + 95, 0, 0, 2, 18, 16, + 2, 0, 104, 0, 0, 2, + 15, 0, 0, 0, 160, 0, + 0, 5, 0, 240, 17, 0, + 0, 0, 0, 0, 100, 0, + 0, 0, 64, 0, 0, 0, + 155, 0, 0, 4, 64, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 85, 0, + 0, 6, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 6, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 16, + 2, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 30, 0, + 0, 8, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 128, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 80, 0, + 0, 8, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 26, 128, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 0, 0, 0, 0, + 62, 0, 0, 1, 21, 0, + 0, 1, 1, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 48, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 128, + 65, 0, 0, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 70, 114, + 16, 0, 1, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 127, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 6, 112, 16, 0, + 1, 0, 0, 0, 85, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 79, 0, 0, 10, + 242, 0, 16, 0, 2, 0, + 0, 0, 166, 10, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 16, 0, 0, 0, + 8, 0, 0, 0, 4, 0, + 0, 0, 2, 0, 0, 0, + 31, 0, 4, 3, 10, 0, + 16, 0, 2, 0, 0, 0, + 78, 0, 0, 9, 130, 0, + 16, 0, 1, 0, 0, 0, + 0, 208, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 26, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 35, 0, 0, 11, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 128, 65, 0, + 0, 0, 1, 0, 0, 0, + 26, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 7, 34, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 85, 0, 0, 7, 18, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 54, 0, 0, 8, + 194, 0, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 45, 0, + 0, 7, 242, 0, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 70, 126, 16, 0, 0, 0, + 0, 0, 56, 0, 0, 10, + 242, 0, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 127, 67, + 0, 0, 127, 67, 0, 0, + 127, 67, 0, 0, 127, 67, + 28, 0, 0, 5, 242, 0, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 84, 0, 0, 10, + 242, 0, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 32, 0, 0, 10, 50, 0, + 16, 0, 4, 0, 0, 0, + 246, 15, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 4, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 32, 0, 0, 10, + 114, 0, 16, 0, 4, 0, + 0, 0, 166, 10, 16, 0, + 1, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 9, 194, 0, + 16, 0, 5, 0, 0, 0, + 166, 10, 16, 0, 4, 0, + 0, 0, 246, 11, 16, 0, + 3, 0, 0, 0, 166, 14, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 5, 50, 0, + 16, 0, 5, 0, 0, 0, + 70, 0, 16, 0, 3, 0, + 0, 0, 55, 0, 0, 9, + 226, 0, 16, 0, 5, 0, + 0, 0, 86, 5, 16, 0, + 4, 0, 0, 0, 246, 6, + 16, 0, 3, 0, 0, 0, + 86, 14, 16, 0, 5, 0, + 0, 0, 55, 0, 0, 9, + 242, 0, 16, 0, 4, 0, + 0, 0, 6, 0, 16, 0, + 4, 0, 0, 0, 118, 2, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 55, 0, 0, 9, + 242, 0, 16, 0, 3, 0, + 0, 0, 246, 15, 16, 0, + 1, 0, 0, 0, 70, 14, + 16, 0, 4, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 70, 14, 16, 0, + 3, 0, 0, 0, 21, 0, + 0, 1, 30, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 192, 255, 255, 255, + 31, 0, 4, 3, 10, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 3, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 8, 18, 0, + 16, 0, 4, 0, 0, 0, + 26, 144, 144, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 0, 0, 7, + 18, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 32, 0, 0, 10, 98, 0, + 16, 0, 4, 0, 0, 0, + 246, 15, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 32, 0, 0, 7, + 18, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 55, 0, 0, 12, 242, 0, + 16, 0, 5, 0, 0, 0, + 6, 0, 16, 0, 4, 0, + 0, 0, 70, 14, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 1, 0, 0, 7, 242, 0, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 6, 0, 16, 0, + 4, 0, 0, 0, 55, 0, + 0, 12, 242, 0, 16, 0, + 5, 0, 0, 0, 86, 5, + 16, 0, 4, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 1, 0, + 0, 7, 242, 0, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 86, 5, 16, 0, 4, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 21, 0, 0, 1, 31, 0, + 4, 3, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 3, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 4, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 18, 0, 16, 0, 5, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 84, 0, 0, 7, + 242, 0, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 83, 0, 0, 7, + 242, 0, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 21, 0, 0, 1, + 31, 0, 4, 3, 42, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 3, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 4, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 18, 0, 16, 0, + 5, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 6, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 5, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 84, 0, + 0, 7, 242, 0, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 14, 16, 0, + 3, 0, 0, 0, 83, 0, + 0, 7, 242, 0, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 4, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 14, 16, 0, + 3, 0, 0, 0, 21, 0, + 0, 1, 31, 0, 4, 3, + 58, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 3, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 4, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 18, 0, + 16, 0, 5, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 6, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 5, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 84, 0, 0, 7, 242, 0, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 83, 0, 0, 7, 242, 0, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 0, 4, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 21, 0, 0, 1, 79, 0, + 0, 10, 50, 0, 16, 0, + 3, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 3, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 4, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 5, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 66, 0, + 16, 0, 3, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 84, 0, 0, 7, 242, 0, + 16, 0, 4, 0, 0, 0, + 70, 14, 16, 0, 4, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 14, + 16, 0, 4, 0, 0, 0, + 83, 0, 0, 7, 242, 0, + 16, 0, 4, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 14, + 16, 0, 4, 0, 0, 0, + 21, 0, 0, 1, 32, 0, + 0, 10, 194, 0, 16, 0, + 3, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 0, 31, 0, 4, 3, + 42, 0, 16, 0, 3, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 21, 0, 0, 1, + 31, 0, 4, 3, 10, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 6, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 85, 0, 0, 8, + 66, 0, 16, 0, 3, 0, + 0, 0, 10, 144, 144, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 8, 18, 0, + 16, 0, 7, 0, 0, 0, + 26, 144, 144, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 1, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 32, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 246, 15, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 32, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 55, 0, 0, 12, + 242, 0, 16, 0, 9, 0, + 0, 0, 6, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 1, 0, 0, 7, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 6, 0, + 16, 0, 7, 0, 0, 0, + 60, 0, 0, 7, 50, 0, + 16, 0, 8, 0, 0, 0, + 214, 5, 16, 0, 8, 0, + 0, 0, 134, 0, 16, 0, + 8, 0, 0, 0, 32, 0, + 0, 7, 66, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 32, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 55, 0, + 0, 12, 242, 0, 16, 0, + 10, 0, 0, 0, 166, 10, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 1, 0, + 0, 7, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 166, 10, 16, 0, 3, 0, + 0, 0, 55, 0, 0, 12, + 242, 0, 16, 0, 10, 0, + 0, 0, 86, 5, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 10, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 1, 0, 0, 7, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 86, 5, + 16, 0, 8, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 9, 0, 0, 0, + 6, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 10, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 6, 0, 0, 0, + 6, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 21, 0, + 0, 1, 31, 0, 4, 3, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 6, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 7, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 66, 0, + 16, 0, 3, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 84, 0, 0, 7, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 83, 0, 0, 7, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 21, 0, 0, 1, 31, 0, + 4, 3, 42, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 6, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 7, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 66, 0, 16, 0, 3, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 84, 0, 0, 7, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 83, 0, 0, 7, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 21, 0, 0, 1, + 31, 0, 4, 3, 58, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 6, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 7, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 66, 0, 16, 0, + 3, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 84, 0, + 0, 7, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 83, 0, + 0, 7, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 21, 0, + 0, 1, 31, 0, 4, 3, + 10, 0, 16, 0, 3, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 6, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 7, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 66, 0, + 16, 0, 3, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 84, 0, 0, 7, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 83, 0, 0, 7, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 21, 0, 0, 1, 31, 0, + 4, 3, 58, 0, 16, 0, + 3, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 21, 0, + 0, 1, 31, 0, 4, 3, + 10, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 6, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 85, 0, + 0, 8, 66, 0, 16, 0, + 3, 0, 0, 0, 10, 144, + 144, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 85, 0, 0, 8, + 18, 0, 16, 0, 7, 0, + 0, 0, 26, 144, 144, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 1, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 32, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 246, 15, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 0, 3, 0, 0, 0, + 55, 0, 0, 12, 242, 0, + 16, 0, 9, 0, 0, 0, + 6, 0, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 70, 14, + 16, 0, 6, 0, 0, 0, + 55, 0, 0, 12, 242, 0, + 16, 0, 7, 0, 0, 0, + 6, 0, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 60, 0, 0, 7, 50, 0, + 16, 0, 8, 0, 0, 0, + 214, 5, 16, 0, 8, 0, + 0, 0, 134, 0, 16, 0, + 8, 0, 0, 0, 32, 0, + 0, 10, 242, 0, 16, 0, + 10, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 7, 0, + 0, 0, 4, 0, 0, 0, + 5, 0, 0, 0, 6, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 10, 0, 0, 0, + 55, 0, 0, 12, 242, 0, + 16, 0, 11, 0, 0, 0, + 166, 10, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 70, 14, + 16, 0, 6, 0, 0, 0, + 55, 0, 0, 12, 242, 0, + 16, 0, 12, 0, 0, 0, + 166, 10, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 10, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 55, 0, 0, 12, + 242, 0, 16, 0, 10, 0, + 0, 0, 166, 10, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 255, 255, 255, 255, + 255, 255, 1, 0, 0, 7, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 166, 10, + 16, 0, 3, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 10, 0, 0, 0, + 86, 5, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 11, 0, 0, 0, 70, 14, + 16, 0, 10, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 6, 0, 0, 0, + 86, 5, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 12, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 9, 0, 0, 0, + 6, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 10, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 6, 0, 0, 0, + 6, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 21, 0, + 0, 1, 31, 0, 4, 3, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 6, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 7, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 84, 0, 0, 7, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 83, 0, 0, 7, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 21, 0, 0, 1, 31, 0, + 4, 3, 42, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 6, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 7, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 84, 0, 0, 7, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 83, 0, 0, 7, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 21, 0, 0, 1, + 31, 0, 4, 3, 58, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 6, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 7, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 8, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 84, 0, + 0, 7, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 83, 0, + 0, 7, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 21, 0, + 0, 1, 31, 0, 4, 3, + 10, 0, 16, 0, 3, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 6, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 7, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 84, 0, 0, 7, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 83, 0, 0, 7, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 21, 0, 0, 1, 31, 0, + 0, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 21, 0, + 0, 1, 31, 0, 4, 3, + 26, 0, 16, 0, 3, 0, + 0, 0, 32, 0, 0, 10, + 226, 0, 16, 0, 2, 0, + 0, 0, 246, 15, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 4, 0, + 0, 0, 5, 0, 0, 0, + 85, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 7, 18, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 1, 0, 0, 10, 98, 0, + 16, 0, 3, 0, 0, 0, + 6, 1, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 9, 50, 0, 16, 0, + 3, 0, 0, 0, 86, 5, + 16, 0, 2, 0, 0, 0, + 6, 0, 16, 0, 3, 0, + 0, 0, 150, 5, 16, 0, + 3, 0, 0, 0, 31, 0, + 0, 3, 58, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 84, 0, 0, 10, + 114, 0, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 30, 0, + 0, 0, 30, 0, 0, 0, + 30, 0, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 6, 0, + 0, 0, 6, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 84, 0, + 0, 10, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 30, 0, 0, 0, 30, 0, + 0, 0, 30, 0, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 8, 0, 0, 0, 86, 5, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 255, 0, 0, 0, 54, 0, + 0, 8, 178, 0, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 248, 7, 0, 0, 0, 0, + 0, 0, 248, 7, 0, 0, + 18, 0, 0, 1, 31, 0, + 4, 3, 26, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 84, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 126, 0, + 0, 0, 126, 0, 0, 0, + 126, 0, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 9, 0, + 0, 0, 6, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 84, 0, + 0, 10, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 126, 0, 0, 0, 126, 0, + 0, 0, 126, 0, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 9, 0, 0, 0, 86, 5, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 255, 0, 0, 0, 54, 0, + 0, 8, 178, 0, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 254, 1, 0, 0, 0, 0, + 0, 0, 254, 1, 0, 0, + 18, 0, 0, 1, 32, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 84, 0, 0, 10, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 248, 0, + 0, 0, 248, 0, 0, 0, + 248, 0, 0, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 84, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 248, 0, 0, 0, 248, 0, + 0, 0, 248, 0, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 255, 0, + 0, 0, 54, 0, 0, 8, + 178, 0, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 255, 0, 0, 0, 248, 7, + 0, 0, 0, 0, 0, 0, + 248, 7, 0, 0, 18, 0, + 0, 1, 32, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 254, 255, 255, 255, 254, 255, + 255, 255, 254, 255, 255, 255, + 0, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 6, 0, 0, 0, 6, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 254, 255, 255, 255, + 254, 255, 255, 255, 254, 255, + 255, 255, 0, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 8, 0, 0, 0, + 86, 5, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 54, 0, + 0, 5, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 54, 0, 0, 5, 114, 0, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 255, 0, 0, 0, 54, 0, + 0, 8, 178, 0, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 0, 0, + 0, 0, 255, 0, 0, 0, + 18, 0, 0, 1, 32, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 2, 0, 0, 0, + 84, 0, 0, 10, 242, 0, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 6, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 248, 0, + 0, 0, 248, 0, 0, 0, + 248, 0, 0, 0, 252, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 10, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 2, 0, 0, 0, + 84, 0, 0, 10, 242, 0, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 4, 0, 0, 0, 198, 6, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 248, 0, + 0, 0, 252, 0, 0, 0, + 248, 0, 0, 0, 248, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 5, 0, 0, 0, 198, 6, + 16, 0, 4, 0, 0, 0, + 70, 14, 16, 0, 10, 0, + 0, 0, 54, 0, 0, 5, + 114, 0, 16, 0, 8, 0, + 0, 0, 198, 2, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 18, 0, 0, 1, + 32, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 84, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 254, 0, 0, 0, 254, 0, + 0, 0, 254, 0, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 84, 0, + 0, 10, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 254, 0, 0, 0, + 254, 0, 0, 0, 254, 0, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 18, 0, 0, 1, 32, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 254, 255, 255, 255, + 254, 255, 255, 255, 254, 255, + 255, 255, 254, 255, 255, 255, + 30, 0, 0, 7, 242, 0, + 16, 0, 6, 0, 0, 0, + 6, 0, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 254, 255, + 255, 255, 254, 255, 255, 255, + 254, 255, 255, 255, 254, 255, + 255, 255, 30, 0, 0, 7, + 242, 0, 16, 0, 4, 0, + 0, 0, 86, 5, 16, 0, + 3, 0, 0, 0, 198, 6, + 16, 0, 9, 0, 0, 0, + 54, 0, 0, 5, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 54, 0, 0, 5, + 242, 0, 16, 0, 5, 0, + 0, 0, 198, 6, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 5, 114, 0, 16, 0, + 8, 0, 0, 0, 198, 2, + 16, 0, 4, 0, 0, 0, + 54, 0, 0, 5, 146, 0, + 16, 0, 4, 0, 0, 0, + 246, 15, 16, 0, 6, 0, + 0, 0, 18, 0, 0, 1, + 30, 0, 0, 10, 242, 0, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 2, 0, 0, 0, 2, 0, + 0, 0, 2, 0, 0, 0, + 2, 0, 0, 0, 84, 0, + 0, 10, 242, 0, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 85, 0, 0, 7, + 242, 0, 16, 0, 9, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 62, 0, 0, 0, 62, 0, + 0, 0, 62, 0, 0, 0, + 62, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 9, 0, 0, 0, 6, 0, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 242, 0, 16, 0, 6, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 85, 0, 0, 7, 242, 0, + 16, 0, 10, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 4, 0, 0, 0, 54, 6, + 16, 0, 6, 0, 0, 0, + 54, 6, 16, 0, 10, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 10, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 2, 0, 0, 0, + 2, 0, 0, 0, 2, 0, + 0, 0, 2, 0, 0, 0, + 84, 0, 0, 10, 242, 0, + 16, 0, 10, 0, 0, 0, + 70, 14, 16, 0, 10, 0, + 0, 0, 2, 64, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 85, 0, + 0, 7, 242, 0, 16, 0, + 10, 0, 0, 0, 70, 14, + 16, 0, 10, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 10, 0, + 0, 0, 70, 14, 16, 0, + 10, 0, 0, 0, 2, 64, + 0, 0, 62, 0, 0, 0, + 62, 0, 0, 0, 62, 0, + 0, 0, 62, 0, 0, 0, + 30, 0, 0, 7, 242, 0, + 16, 0, 10, 0, 0, 0, + 86, 5, 16, 0, 3, 0, + 0, 0, 198, 9, 16, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 242, 0, 16, 0, + 8, 0, 0, 0, 134, 7, + 16, 0, 10, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 85, 0, 0, 7, + 242, 0, 16, 0, 11, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 11, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 50, 0, + 16, 0, 3, 0, 0, 0, + 70, 0, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 5, 114, 0, 16, 0, + 7, 0, 0, 0, 214, 6, + 16, 0, 4, 0, 0, 0, + 54, 0, 0, 5, 162, 0, + 16, 0, 4, 0, 0, 0, + 86, 1, 16, 0, 3, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 21, 0, + 0, 1, 21, 0, 0, 1, + 21, 0, 0, 1, 21, 0, + 0, 1, 21, 0, 0, 1, + 40, 0, 0, 5, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 40, 0, 0, 5, + 130, 0, 16, 0, 9, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 10, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 9, 0, + 0, 0, 79, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 55, 0, 0, 9, 34, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 2, 0, 0, 0, 31, 0, + 0, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 194, 0, 16, 0, 2, 0, + 0, 0, 6, 4, 16, 0, + 10, 0, 0, 0, 6, 4, + 16, 0, 10, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 35, 0, + 0, 9, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 11, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 8, 114, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 128, 65, 0, + 0, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 38, 0, 0, 8, + 0, 208, 0, 0, 50, 0, + 16, 0, 3, 0, 0, 0, + 70, 0, 16, 0, 3, 0, + 0, 0, 70, 0, 16, 0, + 10, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 35, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 30, 0, 0, 8, + 34, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 128, + 65, 0, 0, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 11, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 34, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 34, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 34, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 43, 0, 0, 5, 18, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 56, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 253, 255, 125, 66, + 28, 0, 0, 5, 18, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 79, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 11, 0, + 0, 0, 166, 10, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 5, 0, + 0, 0, 166, 10, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 12, 0, + 0, 0, 166, 10, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 8, 0, + 0, 0, 166, 10, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 34, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 34, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 43, 0, 0, 5, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 56, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 253, 255, + 125, 66, 28, 0, 0, 5, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 79, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 5, 66, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 13, 0, 0, 0, + 166, 10, 16, 0, 2, 0, + 0, 0, 38, 13, 16, 0, + 4, 0, 0, 0, 134, 7, + 16, 0, 4, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 11, 0, 0, 0, + 10, 0, 16, 0, 13, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 13, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 12, 0, 0, 0, 42, 0, + 16, 0, 13, 0, 0, 0, + 54, 0, 0, 5, 242, 0, + 16, 0, 6, 0, 0, 0, + 70, 14, 16, 0, 12, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 13, 0, 0, 0, 18, 0, + 0, 1, 54, 0, 0, 5, + 130, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 5, 242, 0, 16, 0, + 11, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 21, 0, + 0, 1, 18, 0, 0, 1, + 31, 0, 0, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 66, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 18, 0, 0, 1, + 31, 0, 4, 3, 58, 0, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 144, 144, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 18, 0, 0, 1, 54, 0, + 0, 6, 66, 0, 16, 0, + 2, 0, 0, 0, 58, 144, + 144, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 38, 0, 0, 8, 0, 208, + 0, 0, 50, 0, 16, 0, + 3, 0, 0, 0, 70, 0, + 16, 0, 10, 0, 0, 0, + 70, 0, 16, 0, 10, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 35, 0, 0, 9, 130, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 35, 0, 0, 9, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 38, 0, 0, 8, + 0, 208, 0, 0, 50, 0, + 16, 0, 3, 0, 0, 0, + 70, 0, 16, 0, 3, 0, + 0, 0, 70, 0, 16, 0, + 10, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 35, 0, 0, 9, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 35, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 34, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 34, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 43, 0, 0, 5, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 56, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 253, 255, + 125, 66, 28, 0, 0, 5, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 79, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 11, 0, 0, 0, + 86, 5, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 0, 7, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 5, 0, 0, 0, + 86, 5, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 7, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 54, 0, 0, 5, + 114, 0, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 55, 0, + 0, 9, 242, 0, 16, 0, + 6, 0, 0, 0, 86, 5, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 55, 0, + 0, 9, 242, 0, 16, 0, + 8, 0, 0, 0, 86, 5, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 4, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 21, 0, + 0, 1, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 14, 16, 0, + 11, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 21, 0, + 0, 1, 31, 0, 4, 3, + 10, 0, 16, 0, 2, 0, + 0, 0, 32, 0, 0, 10, + 242, 0, 16, 0, 2, 0, + 0, 0, 246, 15, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 6, 0, + 0, 0, 4, 0, 0, 0, + 60, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 55, 0, + 0, 15, 98, 0, 16, 0, + 3, 0, 0, 0, 6, 0, + 16, 0, 1, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 12, 98, 0, 16, 0, + 3, 0, 0, 0, 246, 15, + 16, 0, 2, 0, 0, 0, + 86, 6, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 12, 98, 0, 16, 0, + 3, 0, 0, 0, 166, 10, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 86, 6, 16, 0, + 3, 0, 0, 0, 55, 0, + 0, 12, 50, 0, 16, 0, + 3, 0, 0, 0, 6, 0, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 150, 5, 16, 0, + 3, 0, 0, 0, 32, 0, + 0, 10, 242, 0, 16, 0, + 4, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 2, 0, + 0, 0, 3, 0, 0, 0, + 7, 0, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 8, 130, 0, + 16, 0, 1, 0, 0, 0, + 26, 144, 144, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 60, 0, 0, 7, 114, 0, + 16, 0, 2, 0, 0, 0, + 70, 3, 16, 0, 2, 0, + 0, 0, 70, 3, 16, 0, + 4, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 85, 0, 0, 8, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 144, 144, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 55, 0, 0, 9, 130, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 8, 242, 0, 16, 0, + 5, 0, 0, 0, 70, 14, + 16, 128, 65, 0, 0, 0, + 4, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 79, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 55, 0, + 0, 9, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 2, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 50, 0, 16, 0, 2, 0, + 0, 0, 70, 0, 16, 0, + 5, 0, 0, 0, 70, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 35, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 6, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 8, + 242, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 128, + 65, 0, 0, 0, 4, 0, + 0, 0, 70, 14, 16, 0, + 6, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 194, 0, 16, 0, 2, 0, + 0, 0, 6, 4, 16, 0, + 5, 0, 0, 0, 6, 4, + 16, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 35, 0, + 0, 9, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 33, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 33, 0, 0, 7, + 66, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 60, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 34, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 43, 0, 0, 5, + 82, 0, 16, 0, 2, 0, + 0, 0, 6, 2, 16, 0, + 2, 0, 0, 0, 56, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 253, 255, + 125, 66, 14, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 28, 0, 0, 5, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 162, 0, 16, 0, 3, 0, + 0, 0, 6, 4, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 10, 50, 0, 16, 0, + 6, 0, 0, 0, 214, 5, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 11, 0, + 0, 0, 11, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 78, 0, 0, 11, + 0, 208, 0, 0, 50, 0, + 16, 0, 6, 0, 0, 0, + 70, 0, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 68, 0, 0, 0, 68, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 79, 0, + 0, 10, 50, 0, 16, 0, + 7, 0, 0, 0, 214, 5, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 55, 0, 0, 12, + 50, 0, 16, 0, 6, 0, + 0, 0, 70, 0, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 15, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 70, 0, 16, 0, 6, 0, + 0, 0, 55, 0, 0, 11, + 18, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 10, 144, + 208, 0, 64, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 55, 0, + 0, 9, 34, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 18, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 33, 0, 0, 10, 194, 0, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 86, 1, 16, 0, + 2, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 34, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 43, 0, 0, 5, 50, 0, + 16, 0, 2, 0, 0, 0, + 70, 0, 16, 0, 2, 0, + 0, 0, 56, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 253, 255, 125, 66, + 14, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 28, 0, + 0, 5, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 55, 0, + 0, 11, 18, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 10, 144, 208, 0, 64, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 55, 0, 0, 9, 18, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 55, 0, 0, 9, 50, 0, + 16, 0, 2, 0, 0, 0, + 6, 0, 16, 0, 1, 0, + 0, 0, 70, 0, 16, 0, + 7, 0, 0, 0, 22, 5, + 16, 0, 7, 0, 0, 0, + 18, 0, 0, 1, 38, 0, + 0, 8, 0, 208, 0, 0, + 194, 0, 16, 0, 2, 0, + 0, 0, 6, 4, 16, 0, + 5, 0, 0, 0, 6, 4, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 35, 0, + 0, 9, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 35, 0, + 0, 9, 66, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 6, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 8, 242, 0, + 16, 0, 4, 0, 0, 0, + 70, 14, 16, 128, 65, 0, + 0, 0, 4, 0, 0, 0, + 70, 14, 16, 0, 6, 0, + 0, 0, 38, 0, 0, 8, + 0, 208, 0, 0, 98, 0, + 16, 0, 3, 0, 0, 0, + 6, 1, 16, 0, 4, 0, + 0, 0, 6, 1, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 35, 0, 0, 9, + 130, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 35, 0, 0, 9, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 33, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 33, 0, 0, 7, 34, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 34, 0, 0, 7, + 34, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 43, 0, 0, 5, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 56, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 253, 255, 125, 66, + 43, 0, 0, 5, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 14, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 28, 0, 0, 5, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 78, 0, 0, 8, + 0, 208, 0, 0, 18, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 68, 0, 0, 0, 79, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 55, 0, 0, 9, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 55, 0, 0, 11, + 130, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 10, 144, + 208, 0, 64, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 55, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 21, 0, 0, 1, 168, 0, + 0, 8, 50, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 0, + 16, 0, 2, 0, 0, 0, + 21, 0, 0, 1, 31, 0, + 0, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 31, 0, + 0, 3, 58, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 128, 255, 255, 255, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 68, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 224, 1, + 0, 0, 0, 0, 0, 224, + 0, 0, 224, 1, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 84, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 1, 0, 0, 10, + 146, 0, 16, 0, 2, 0, + 0, 0, 6, 4, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 30, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 30, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 10, 146, 0, 16, 0, + 3, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 25, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 224, 1, 0, + 224, 1, 0, 0, 0, 0, + 0, 224, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 13, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 1, 0, 0, 10, 146, 0, + 16, 0, 4, 0, 0, 0, + 6, 4, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 30, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 30, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 9, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 224, 1, + 0, 224, 1, 0, 224, 1, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 9, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 11, 0, 0, 0, 10, 0, + 16, 0, 10, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 11, 0, + 0, 0, 26, 0, 16, 0, + 10, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 11, 0, 0, 0, + 42, 0, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 30, 0, 0, 30, 0, + 0, 30, 0, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 11, 0, 0, 0, + 60, 0, 0, 7, 18, 0, + 16, 0, 12, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 13, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 68, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 13, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 11, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 12, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 76, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 30, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 11, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 13, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 0, 32, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 84, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 0, 64, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 0, 128, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 84, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 1, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 2, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 84, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 4, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 84, 0, + 0, 9, 130, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 26, 144, 208, 0, 128, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 66, 0, 16, 0, + 12, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 18, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 48, 0, 0, 1, + 79, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 3, 0, + 4, 3, 26, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 35, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 12, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 12, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 22, 0, 0, 1, + 79, 0, 0, 9, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 144, 208, 0, 128, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 12, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 12, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 18, 0, 0, 1, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 48, 0, 0, 1, + 79, 0, 0, 9, 130, 0, + 16, 0, 1, 0, 0, 0, + 26, 144, 208, 0, 128, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 3, 0, 4, 3, 58, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 35, 0, + 0, 9, 130, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 242, 255, 255, 255, 41, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 21, 0, 0, 1, + 54, 0, 0, 5, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 48, 0, + 0, 1, 79, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 42, 144, 208, 0, + 128, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 3, 0, 4, 3, + 10, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 35, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 241, 255, 255, 255, + 41, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 22, 0, 0, 1, 54, 0, + 0, 5, 130, 0, 16, 0, + 12, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 18, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 48, 0, 0, 1, + 80, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 3, 0, + 4, 3, 26, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 35, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 240, 255, + 255, 255, 41, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 60, 0, 0, 7, 130, 0, + 16, 0, 12, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 12, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 22, 0, 0, 1, + 18, 0, 0, 1, 32, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 31, 0, 4, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 68, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 1, 0, 0, 10, 82, 0, + 16, 0, 2, 0, 0, 0, + 6, 1, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 63, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 63, + 0, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 84, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 192, 15, 0, + 192, 15, 0, 0, 0, 0, + 0, 192, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 18, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 240, 3, + 0, 240, 3, 0, 240, 3, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 6, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 252, 0, 0, 252, 0, + 0, 252, 0, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 18, 0, 16, 0, 12, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 63, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 12, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 92, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 1, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 1, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 1, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 2, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 18, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 32, 0, + 0, 9, 34, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 26, 144, 208, 0, 128, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 10, 242, 0, 16, 0, + 3, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 15, 0, + 0, 0, 14, 0, 0, 0, + 13, 0, 0, 0, 12, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 3, 0, 0, 0, + 86, 5, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 11, 0, 0, 0, 10, 0, + 0, 0, 9, 0, 0, 0, + 8, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 3, 0, 0, 0, + 86, 5, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 7, 0, 0, 0, 6, 0, + 0, 0, 5, 0, 0, 0, + 4, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 130, 0, 16, 0, 12, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 30, 0, + 0, 10, 194, 0, 16, 0, + 2, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 12, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 18, 0, + 0, 1, 32, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 26, 144, + 208, 0, 128, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 3, 0, + 0, 0, 86, 5, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 15, 0, 0, 0, + 14, 0, 0, 0, 13, 0, + 0, 0, 12, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 20, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 10, 242, 0, 16, 0, + 3, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 11, 0, + 0, 0, 10, 0, 0, 0, + 9, 0, 0, 0, 8, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 14, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 10, 242, 0, 16, 0, + 3, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 7, 0, + 0, 0, 6, 0, 0, 0, + 5, 0, 0, 0, 4, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 12, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 10, + 194, 0, 16, 0, 2, 0, + 0, 0, 86, 5, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 25, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 12, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 18, 0, 0, 1, + 32, 0, 0, 9, 34, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 26, 144, 208, 0, + 128, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 3, 0, 0, 0, + 86, 5, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 15, 0, 0, 0, 14, 0, + 0, 0, 13, 0, 0, 0, + 12, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 3, 0, + 0, 0, 86, 5, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 11, 0, 0, 0, + 10, 0, 0, 0, 9, 0, + 0, 0, 8, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 11, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 3, 0, + 0, 0, 86, 5, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 7, 0, 0, 0, + 6, 0, 0, 0, 5, 0, + 0, 0, 4, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 12, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 30, 0, 0, 10, 194, 0, + 16, 0, 2, 0, 0, 0, + 86, 5, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 20, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 12, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 18, 0, 0, 1, 30, 0, + 0, 10, 242, 0, 16, 0, + 3, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 15, 0, + 0, 0, 14, 0, 0, 0, + 13, 0, 0, 0, 12, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 29, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 3, 0, 0, 0, + 86, 5, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 11, 0, 0, 0, 10, 0, + 0, 0, 9, 0, 0, 0, + 8, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 3, 0, 0, 0, + 86, 5, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 7, 0, 0, 0, 6, 0, + 0, 0, 5, 0, 0, 0, + 4, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 130, 0, 16, 0, 12, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 30, 0, + 0, 10, 194, 0, 16, 0, + 2, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 60, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 12, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 21, 0, 0, 1, 18, 0, + 0, 1, 32, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 254, + 255, 255, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 68, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 62, 0, 0, 128, 15, + 0, 0, 224, 3, 0, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 84, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 0, 192, 7, 0, + 0, 240, 1, 0, 0, 124, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 30, 0, + 0, 10, 146, 0, 16, 0, + 2, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 7, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 248, 0, + 0, 0, 62, 0, 0, 128, + 15, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 9, 0, 0, 0, 10, 0, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 31, 0, 0, 192, 7, + 0, 0, 240, 1, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 68, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 11, 0, 0, 0, + 10, 0, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 11, 0, 0, 0, 26, 0, + 16, 0, 10, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 11, 0, + 0, 0, 42, 0, 16, 0, + 10, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 224, 0, 0, + 0, 248, 0, 0, 0, 62, + 0, 0, 0, 0, 60, 0, + 0, 7, 18, 0, 16, 0, + 12, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 11, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 13, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 13, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 13, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 18, 0, 16, 0, + 14, 0, 0, 0, 10, 0, + 16, 0, 13, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 14, 0, + 0, 0, 26, 0, 16, 0, + 13, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 10, 146, 0, + 16, 0, 3, 0, 0, 0, + 6, 4, 16, 0, 14, 0, + 0, 0, 2, 64, 0, 0, + 124, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 31, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 12, 0, 0, 0, + 26, 0, 16, 0, 11, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 11, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 13, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 192, 30, 0, 0, 7, + 66, 0, 16, 0, 12, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 92, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 18, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 48, 0, 0, 1, + 79, 0, 0, 9, 34, 0, + 16, 0, 2, 0, 0, 0, + 26, 144, 208, 0, 128, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 3, 0, 4, 3, 26, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 22, 0, 0, 1, 54, 0, + 0, 5, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 54, 0, 0, 5, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 48, 0, 0, 1, + 79, 0, 0, 9, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 144, 208, 0, 128, 0, + 0, 0, 26, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 3, 0, 4, 3, 42, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 22, 0, 0, 1, 54, 0, + 0, 5, 130, 0, 16, 0, + 12, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 48, 0, 0, 1, + 80, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 3, 0, + 4, 3, 10, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 12, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 12, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 22, 0, 0, 1, 18, 0, + 0, 1, 32, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 167, 0, 0, 9, + 114, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 70, 242, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 0, 252, 1, 0, + 192, 31, 0, 0, 252, 1, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 5, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 254, 0, 0, 224, 15, 0, + 0, 254, 0, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 114, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 68, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 19, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 7, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 127, 0, 0, 240, 7, + 0, 0, 127, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 84, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 9, 0, 0, 0, + 10, 0, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 30, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 9, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 22, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 9, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 128, 0, 0, + 0, 248, 0, 0, 128, 63, + 0, 0, 0, 0, 60, 0, + 0, 7, 18, 0, 16, 0, + 12, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 9, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 84, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 18, 0, 16, 0, 11, 0, + 0, 0, 10, 0, 16, 0, + 10, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 85, 0, 0, 7, 34, 0, + 16, 0, 11, 0, 0, 0, + 26, 0, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 1, 0, + 0, 10, 146, 0, 16, 0, + 2, 0, 0, 0, 6, 4, + 16, 0, 11, 0, 0, 0, + 2, 64, 0, 0, 63, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 30, 0, 0, 7, + 50, 0, 16, 0, 2, 0, + 0, 0, 150, 5, 16, 0, + 3, 0, 0, 0, 198, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 50, 0, + 16, 0, 2, 0, 0, 0, + 150, 5, 16, 0, 5, 0, + 0, 0, 70, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 50, 0, 16, 0, + 2, 0, 0, 0, 150, 5, + 16, 0, 7, 0, 0, 0, + 70, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 50, 0, 16, 0, 2, 0, + 0, 0, 150, 5, 16, 0, + 9, 0, 0, 0, 70, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 68, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 30, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 64, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 84, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 12, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 84, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 48, 0, 0, 1, 79, 0, + 0, 9, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 144, + 208, 0, 128, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 3, 0, + 4, 3, 42, 0, 16, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 60, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 54, 0, 0, 5, + 130, 0, 16, 0, 12, 0, + 0, 0, 58, 0, 16, 0, + 1, 0, 0, 0, 54, 0, + 0, 5, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 48, 0, 0, 1, 80, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 3, 0, 4, 3, + 42, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 60, 0, 0, 7, + 130, 0, 16, 0, 12, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 12, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 54, 0, 0, 5, + 34, 0, 16, 0, 12, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 18, 0, + 0, 1, 32, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 96, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 25, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 31, 0, 0, 0, 0, + 124, 0, 0, 0, 0, 240, + 192, 15, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 84, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 82, 0, 16, 0, 4, 0, + 0, 0, 6, 3, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 1, 0, + 0, 10, 178, 0, 16, 0, + 3, 0, 0, 0, 70, 8, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 0, 224, + 3, 0, 0, 0, 128, 15, + 0, 0, 0, 0, 0, 240, + 3, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 12, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 76, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 85, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 62, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 1, 0, 0, 10, 146, 0, + 16, 0, 1, 0, 0, 0, + 6, 4, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 2, 0, + 0, 0, 86, 5, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 3, 0, + 0, 0, 4, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 50, 0, + 16, 0, 3, 0, 0, 0, + 70, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 22, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 25, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 4, 0, + 0, 0, 86, 5, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 5, 0, 0, 0, + 6, 0, 0, 0, 7, 0, + 0, 0, 8, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 5, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 29, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 31, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 12, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 10, 242, 0, 16, 0, + 5, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 9, 0, + 0, 0, 10, 0, 0, 0, + 11, 0, 0, 0, 12, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 6, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 17, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 9, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 30, 0, 0, 10, + 226, 0, 16, 0, 5, 0, + 0, 0, 86, 5, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 13, 0, 0, 0, 14, 0, + 0, 0, 15, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 11, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 23, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 13, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 12, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 12, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 18, 0, 0, 1, + 32, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 68, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 21, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 18, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 0, 127, + 0, 0, 0, 0, 192, 31, + 240, 7, 0, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 84, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 10, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 26, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 0, 128, + 63, 0, 0, 0, 0, 224, + 0, 248, 3, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 18, 0, 16, 0, + 12, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 88, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 15, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 34, 0, 16, 0, + 12, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 96, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 2, 0, 0, 0, + 86, 5, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 2, 0, + 0, 0, 3, 0, 0, 0, + 4, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 10, 242, 0, 16, 0, + 3, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 5, 0, + 0, 0, 6, 0, 0, 0, + 7, 0, 0, 0, 8, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 10, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 14, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 50, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 17, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 4, 0, + 0, 0, 86, 5, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 9, 0, 0, 0, + 10, 0, 0, 0, 11, 0, + 0, 0, 12, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 5, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 18, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 21, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 23, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 22, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 25, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 5, 0, 0, 0, + 86, 5, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 13, 0, 0, 0, 14, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 6, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 27, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 26, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 6, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 30, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 12, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 130, 0, 16, 0, 12, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 18, 0, 0, 1, 32, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 31, 0, 4, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 20, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 128, 63, 0, 0, 0, 0, + 224, 15, 248, 3, 0, 0, + 0, 0, 254, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 64, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 84, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 27, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 9, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 23, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 0, 192, 31, 0, 0, 0, + 0, 240, 0, 252, 1, 0, + 0, 0, 0, 127, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 12, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 50, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 70, 240, 17, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 68, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 12, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 2, 0, 0, 0, + 86, 5, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 2, 0, + 0, 0, 3, 0, 0, 0, + 4, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 12, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 2, 0, 0, 0, + 86, 5, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 5, 0, 0, 0, 6, 0, + 0, 0, 7, 0, 0, 0, + 8, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 20, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 12, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 10, 242, 0, 16, 0, + 3, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 9, 0, + 0, 0, 10, 0, 0, 0, + 11, 0, 0, 0, 12, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 12, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 10, 210, 0, 16, 0, + 1, 0, 0, 0, 86, 5, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 13, 0, + 0, 0, 0, 0, 0, 0, + 14, 0, 0, 0, 15, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 20, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 60, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 12, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 18, 0, 0, 1, + 41, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 128, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 11, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 3, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 19, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 1, 0, 0, 10, + 210, 0, 16, 0, 1, 0, + 0, 0, 6, 9, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 0, 192, 7, 0, + 0, 0, 0, 0, 0, 0, + 192, 7, 0, 124, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 12, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 4, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 248, 0, + 128, 15, 0, 0, 0, 0, + 0, 248, 0, 128, 15, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 68, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 21, 0, 0, 0, + 41, 0, 0, 7, 34, 0, + 16, 0, 6, 0, 0, 0, + 26, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 9, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 1, 64, 0, 0, 17, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 31, + 0, 240, 1, 0, 0, 0, + 240, 1, 0, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 26, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 8, 0, + 0, 0, 26, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 22, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 224, + 0, 0, 62, 0, 224, 3, + 0, 0, 0, 0, 0, 62, + 60, 0, 0, 7, 18, 0, + 16, 0, 12, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 8, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 18, 0, 16, 0, + 10, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 10, 0, + 0, 0, 10, 0, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 10, 146, 0, + 16, 0, 6, 0, 0, 0, + 6, 4, 16, 0, 10, 0, + 0, 0, 2, 64, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 124, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 12, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 31, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 68, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 28, 0, + 0, 0, 1, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 64, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 84, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 29, 0, + 0, 0, 1, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 128, + 30, 0, 0, 7, 66, 0, + 16, 0, 12, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 68, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 48, 0, + 0, 1, 79, 0, 0, 9, + 66, 0, 16, 0, 1, 0, + 0, 0, 26, 144, 208, 0, + 128, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 3, 0, 4, 3, + 42, 0, 16, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 66, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 66, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 1, 0, 0, 0, + 60, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 22, 0, 0, 1, + 54, 0, 0, 5, 130, 0, + 16, 0, 12, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 48, 0, + 0, 1, 80, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 3, 0, 4, 3, 26, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 1, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 34, 0, 16, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 60, 0, 0, 7, 130, 0, + 16, 0, 12, 0, 0, 0, + 26, 0, 16, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 12, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 22, 0, 0, 1, + 21, 0, 0, 1, 21, 0, + 0, 1, 21, 0, 0, 1, + 21, 0, 0, 1, 21, 0, + 0, 1, 21, 0, 0, 1, + 21, 0, 0, 1, 168, 0, + 0, 9, 242, 224, 17, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 70, 14, 16, 0, + 12, 0, 0, 0, 21, 0, + 0, 1, 62, 0, 0, 1 +}; diff --git a/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_TryMode02CS.inc b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_TryMode02CS.inc new file mode 100644 index 0000000..5f627d3 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_TryMode02CS.inc @@ -0,0 +1,3823 @@ +#if 0 +// +// Generated by Microsoft (R) D3D Shader Disassembler +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Input +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Output +cs_4_0 +dcl_globalFlags refactoringAllowed +dcl_immediateConstantBuffer { { -0.000000, 15, 0, 0}, + { 65981199646559862000000000.000000, 15, 0, 0}, + { 15358528172589056.000000, 15, 0, 0}, + { 3584194248704.000000, 15, 0, 1}, + { -0.000000, 15, 0, 1}, + { -0.000000, 15, 0, 1}, + { 14680365989888.000000, 15, 0, 1}, + { 15362462362632192.000000, 15, 0, 2}, + { -0.000000, 15, 0, 2}, + { -0.000000, 15, 0, 2}, + { -0.000000, 15, 0, 2}, + { -0.000000, 15, 0, 2}, + { -0.000000, 15, 0, 3}, + { -0.000000, 15, 0, 3}, + { -0.000000, 15, 0, 3}, + { 0.000000, 15, 0, 3}, + { -0.000000, 15, 0, 4}, + { 0.000000, 2, 0, 4}, + { -0.000000, 8, 0, 4}, + { 22076467445760.000000, 2, 0, 4}, + { -0.000000, 2, 0, 5}, + { 70798013459086900000000000.000000, 8, 0, 5}, + { -0.000000, 8, 0, 5}, + { 0.000000, 15, 0, 5}, + { 0x0050a4a4, 2, 0, 6}, + { -0.000000, 8, 0, 6}, + { 0.000000, 2, 0, 6}, + { 17610885206241624000000000.000000, 2, 0, 6}, + { -0.000000, 8, 0, 6}, + { -0.000000, 8, 0, 7}, + { 22097854464.000000, 2, 0, 7}, + { 65888818352238725000000000.000000, 2, 0, 7}, + { -0.000000, 15, 0, 7}, + { 19411582976.000000, 15, 0, 8}, + { -0.000000, 6, 0, 8}, + { 0.000000, 8, 0, 8}, + { 0.000000, 2, 0, 8}, + { 0.000000, 8, 0, 9}, + { 0.000000, 15, 0, 9}, + { 22151331840.000000, 15, 0, 9}, + { 9304358912.000000, 2, 0, 9}, + { -0.000000, 8, 0, 10}, + { 271536072765004600000000.000000, 2, 0, 10}, + { -0.000000, 2, 0, 10}, + { 21517107200.000000, 2, 0, 10}, + { 12724757752857623000000000.000000, 15, 0, 10}, + { 1365.320801, 15, 0, 11}, + { 272006464738884190000000.000000, 6, 0, 11}, + { -0.000000, 6, 0, 11}, + { 5783798415360.000000, 2, 0, 11}, + { -0.000000, 6, 0, 12}, + { -0.000000, 8, 0, 12}, + { -0.000000, 15, 0, 12}, + { -0.000000, 15, 0, 12}, + { -0.000000, 2, 0, 13}, + { -0.000000, 2, 0, 13}, + { -0.000000, 15, 0, 13}, + { -0.000000, 15, 0, 13}, + { -0.000000, 15, 0, 14}, + { -0.000000, 15, 0, 14}, + { 4.007874, 15, 0, 14}, + { -0.000000, 2, 0, 14}, + { -0.000000, 2, 0, 15}, + { 0.000000, 15, 0, 15}, + { 0, 3, 15, 0}, + { 4, 3, 8, 0}, + { 9, 15, 8, 0}, + { 13, 15, 3, 0}, + { 17, 8, 15, 0}, + { 21, 3, 15, 1}, + { 26, 15, 3, 1}, + { 30, 15, 8, 1}, + { 34, 8, 15, 1}, + { 38, 8, 15, 1}, + { 43, 6, 15, 1}, + { 47, 6, 15, 1}, + { 51, 6, 15, 1}, + { 55, 5, 15, 1}, + { 60, 3, 15, 2}, + { 64, 3, 8, 2}, + { 0, 3, 15, 2}, + { 9, 3, 8, 2}, + { 18, 8, 15, 2}, + { 27, 15, 3, 2}, + { 37, 3, 15, 2}, + { 46, 3, 8, 2}, + { 55, 6, 15, 2}, + { 64, 10, 8, 3}, + { 0, 5, 3, 3}, + { 0, 8, 15, 3}, + { 0, 8, 6, 3}, + { 0, 6, 10, 3}, + { 0, 8, 15, 3}, + { 0, 5, 15, 3}, + { 0, 15, 10, 3}, + { 0, 15, 8, 3}, + { 0, 8, 15, 3}, + { 21, 15, 3, 4}, + { 43, 3, 15, 4}, + { 64, 5, 10, 4}, + { 0, 6, 10, 4}, + { 0, 10, 8, 4}, + { 0, 8, 9, 4}, + { 0, 15, 10, 4}, + { 0, 15, 6, 4}, + { 0, 3, 15, 4}, + { 0, 15, 8, 5}, + { 0, 5, 15, 5}, + { 0, 15, 3, 5}, + { 0, 15, 6, 5}, + { 0, 15, 6, 5}, + { 0, 15, 8, 5}, + { 0, 3, 15, 5}, + { 0, 15, 3, 5}, + { 0, 5, 15, 5}, + { 0, 5, 15, 6}, + { 0, 5, 15, 6}, + { 0, 8, 15, 6}, + { 0, 5, 15, 6}, + { 0, 10, 15, 6}, + { 0, 5, 15, 6}, + { 0, 10, 15, 6}, + { 0, 8, 15, 6}, + { 0, 13, 15, 6}, + { 0, 15, 3, 7}, + { 0, 12, 15, 7}, + { 0, 3, 15, 7}, + { 0, 3, 8, 7}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3} } +dcl_constantbuffer CB0[2], immediateIndexed +dcl_resource_texture2d (float,float,float,float) t0 +dcl_resource_structured t1, 16 +dcl_uav_structured u0, 16 +dcl_input vThreadIDInGroupFlattened +dcl_input vThreadGroupID.x +dcl_temps 29 +dcl_indexableTemp x0[12], 4 +dcl_indexableTemp x1[3], 4 +dcl_indexableTemp x2[3], 4 +dcl_indexableTemp x3[3], 4 +dcl_tgsm_structured g0, 100, 64 +dcl_thread_group 64, 1, 1 +iadd r0.x, vThreadGroupID.x, cb0[1].x +ult r1.xyzw, vThreadIDInGroupFlattened.xxxx, l(16, 32, 8, 4) +if_nz r1.x + udiv r0.y, null, r0.x, cb0[0].y + imad r0.z, -r0.y, cb0[0].y, r0.x + ishl r0.z, r0.z, l(2) + ishl r0.y, r0.y, l(2) + and r0.w, vThreadIDInGroupFlattened.x, l(3) + iadd r2.x, r0.w, r0.z + ushr r0.z, vThreadIDInGroupFlattened.x, l(2) + iadd r2.y, r0.z, r0.y + mov r2.zw, l(0,0,0,0) + ld r2.xyzw, r2.xyzw, t0.xyzw + mul r2.xyzw, r2.xyzw, l(255.000000, 255.000000, 255.000000, 255.000000) + ftou r2.xyzw, r2.xyzw + umin r2.xyzw, r2.xyzw, l(255, 255, 255, 255) + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(0), r2.xyzw +endif +sync_g_t +store_structured g0.x, vThreadIDInGroupFlattened.x, l(16), l(-1) +movc r0.y, cb0[0].w, l(64), l(16) +ult r0.y, vThreadIDInGroupFlattened.x, r0.y +if_nz r0.y + iadd r0.y, vThreadIDInGroupFlattened.x, l(64) + mov x0[0].x, l(-1) + mov x0[1].x, l(-1) + mov x0[2].x, l(-1) + mov x0[0].y, l(0) + mov x0[1].y, l(0) + mov x0[2].y, l(0) + mov x0[4].x, l(-1) + mov x0[5].x, l(-1) + mov x0[6].x, l(-1) + mov x0[4].y, l(0) + mov x0[5].y, l(0) + mov x0[6].y, l(0) + mov x0[8].x, l(-1) + mov x0[9].x, l(-1) + mov x0[10].x, l(-1) + mov x0[8].y, l(0) + mov x0[9].y, l(0) + mov x0[10].y, l(0) + iadd r0.z, r0.y, l(-64) + mov r0.w, l(0) + loop + uge r2.x, r0.w, l(16) + breakc_nz r2.x + ld_structured r2.xyz, r0.w, l(0), g0.xyzx + ishl r2.w, r0.w, l(1) + ushr r2.w, icb[r0.z + 0].x, r2.w + and r2.w, r2.w, l(3) + ieq r3.x, r2.w, l(2) + if_nz r3.x + mov r3.x, x0[8].x + mov r3.y, x0[9].x + mov r3.z, x0[10].x + umin r3.xyz, r2.xyzx, r3.xyzx + mov x0[8].x, r3.x + mov x0[9].x, r3.y + mov x0[10].x, r3.z + mov r3.x, x0[8].y + mov r3.y, x0[9].y + mov r3.z, x0[10].y + umax r3.xyz, r2.xyzx, r3.xyzx + mov x0[8].y, r3.x + mov x0[9].y, r3.y + mov x0[10].y, r3.z + else + ieq r2.w, r2.w, l(1) + if_nz r2.w + mov r3.x, x0[4].x + mov r3.y, x0[5].x + mov r3.z, x0[6].x + umin r3.xyz, r2.xyzx, r3.xyzx + mov x0[4].x, r3.x + mov x0[5].x, r3.y + mov x0[6].x, r3.z + mov r3.x, x0[4].y + mov r3.y, x0[5].y + mov r3.z, x0[6].y + umax r3.xyz, r2.xyzx, r3.xyzx + mov x0[4].y, r3.x + mov x0[5].y, r3.y + mov x0[6].y, r3.z + else + mov r3.x, x0[0].x + mov r3.y, x0[1].x + mov r3.z, x0[2].x + umin r3.xyz, r2.xyzx, r3.xyzx + mov x0[0].x, r3.x + mov x0[1].x, r3.y + mov x0[2].x, r3.z + mov r3.x, x0[0].y + mov r3.y, x0[1].y + mov r3.z, x0[2].y + umax r2.xyz, r2.xyzx, r3.xyzx + mov x0[0].y, r2.x + mov x0[1].y, r2.y + mov x0[2].y, r2.z + endif + endif + iadd r0.w, r0.w, l(1) + endloop + mov r2.x, x0[0].x + mov r2.y, x0[1].x + mov r2.z, x0[2].x + mov r3.x, x0[0].y + mov r3.y, x0[1].y + mov r3.z, x0[2].y + mov r4.x, x0[4].x + mov r4.y, x0[5].x + mov r4.z, x0[6].x + mov r5.x, x0[4].y + mov r5.y, x0[5].y + mov r5.z, x0[6].y + mov r6.x, x0[8].x + mov r6.y, x0[9].x + mov r6.z, x0[10].x + mov r7.x, x0[8].y + mov r7.y, x0[9].y + mov r7.z, x0[10].y + movc r0.w, cb0[0].w, l(1), l(64) + iadd r2.xyz, r2.xyzx, l(4, 4, 4, 0) + umin r2.xyz, r2.xyzx, l(255, 255, 255, 0) + ushr r8.xyz, r2.xyzx, l(3) + and r8.xyz, r8.xyzx, l(30, 30, 30, 0) + iadd r3.xyz, r3.xyzx, l(4, 4, 4, 0) + umin r3.xyz, r3.xyzx, l(255, 255, 255, 0) + ushr r9.xyz, r3.xyzx, l(3) + and r9.xyz, r9.xyzx, l(30, 30, 30, 0) + and r10.xyz, r2.xyzx, l(248, 248, 248, 0) + ushr r2.xyz, r2.xyzx, l(5) + iadd r2.xyz, r2.xyzx, r10.xyzx + and r10.xyz, r3.xyzx, l(248, 248, 248, 0) + ushr r3.xyz, r3.xyzx, l(5) + iadd r3.xyz, r3.xyzx, r10.xyzx + iadd r4.xyz, r4.xyzx, l(4, 4, 4, 0) + umin r4.xyz, r4.xyzx, l(255, 255, 255, 0) + ushr r10.xyz, r4.xyzx, l(3) + and r10.xyz, r10.xyzx, l(30, 30, 30, 0) + iadd r5.xyz, r5.xyzx, l(4, 4, 4, 0) + umin r5.xyz, r5.xyzx, l(255, 255, 255, 0) + ushr r11.xyz, r5.xyzx, l(3) + and r11.xyz, r11.xyzx, l(30, 30, 30, 0) + and r12.xyz, r4.xyzx, l(248, 248, 248, 0) + ushr r4.xyz, r4.xyzx, l(5) + iadd r4.xyz, r4.xyzx, r12.xyzx + and r12.xyz, r5.xyzx, l(248, 248, 248, 0) + ushr r5.xyz, r5.xyzx, l(5) + iadd r5.xyz, r5.xyzx, r12.xyzx + iadd r6.xyz, r6.xyzx, l(4, 4, 4, 0) + umin r6.xyz, r6.xyzx, l(255, 255, 255, 0) + ushr r12.xyz, r6.xyzx, l(3) + and r12.xyz, r12.xyzx, l(30, 30, 30, 0) + iadd r7.xyz, r7.xyzx, l(4, 4, 4, 0) + umin r7.xyz, r7.xyzx, l(255, 255, 255, 0) + ushr r13.xyz, r7.xyzx, l(3) + and r13.xyz, r13.xyzx, l(30, 30, 30, 0) + and r14.xyz, r6.xyzx, l(248, 248, 248, 0) + ushr r6.xyz, r6.xyzx, l(5) + iadd r6.xyz, r6.xyzx, r14.xyzx + and r14.xyz, r7.xyzx, l(248, 248, 248, 0) + ushr r7.xyz, r7.xyzx, l(5) + iadd r7.xyz, r7.xyzx, r14.xyzx + mov r2.w, r3.z + mov r3.w, r2.y + mov r4.w, r5.z + mov r5.w, r4.y + mov r6.w, r7.z + mov r7.w, r6.y + mov r14.y, l(255) + mov r2.y, cb0[0].w + mov r15.xy, l(0,-1,0,0) + mov r16.x, l(0) + loop + uge r3.z, r16.x, r0.w + breakc_nz r3.z + ieq r3.z, r2.y, l(2) + if_z r2.y + ushr r16.y, r16.x, l(1) + and r14.zw, r16.xxxy, l(0, 0, 1, 1) + iadd r17.xyz, r8.xyzx, r14.zzzz + ishl r17.xyz, r17.xyzx, l(3) + ushr r18.xyz, r17.xyzx, l(5) + iadd r17.xzw, r17.zzxy, r18.zzxy + iadd r18.xyz, r9.xyzx, r14.wwww + ishl r18.xyz, r18.xyzx, l(3) + ushr r19.xyz, r18.xyzx, l(5) + iadd r18.xyz, r18.yxzy, r19.yxzy + mov r17.y, r18.z + mov r18.w, r17.w + mov r14.zw, r18.wwwx + mov r18.x, r17.z + else + mov r17.xy, r2.zwzz + mov r14.zw, r3.wwwy + mov r18.x, r2.x + mov r18.y, r3.x + endif + mov x0[3].xy, l(255,255,0,0) + mov x0[2].xy, r17.xyxx + mov x0[1].xy, r14.zwzz + mov x0[0].xy, r18.xyxx + if_z r2.y + ushr r19.x, r16.x, l(2) + ushr r19.y, r16.x, l(3) + and r15.zw, r19.xxxy, l(0, 0, 1, 1) + iadd r19.xyz, r10.xyzx, r15.zzzz + ishl r19.xyz, r19.xyzx, l(3) + ushr r20.xyz, r19.xyzx, l(5) + iadd r19.xzw, r19.zzxy, r20.zzxy + iadd r20.xyz, r11.xyzx, r15.wwww + ishl r20.xyz, r20.xyzx, l(3) + ushr r21.xyz, r20.xyzx, l(5) + iadd r20.xyz, r20.yxzy, r21.yxzy + mov r19.y, r20.z + mov r20.w, r19.w + mov r15.zw, r20.wwwx + mov r20.x, r19.z + else + mov r19.xy, r4.zwzz + mov r15.zw, r5.wwwy + mov r20.x, r4.x + mov r20.y, r5.x + endif + mov x0[7].xy, l(255,255,0,0) + mov x0[6].xy, r19.xyxx + mov x0[5].xy, r15.zwzz + mov x0[4].xy, r20.xyxx + if_z r2.y + ushr r21.x, r16.x, l(4) + ushr r21.y, r16.x, l(5) + and r16.zw, r21.xxxy, l(0, 0, 1, 1) + iadd r21.xyz, r12.xyzx, r16.zzzz + ishl r21.xyz, r21.xyzx, l(3) + ushr r22.xyz, r21.xyzx, l(5) + iadd r21.xzw, r21.zzxy, r22.zzxy + iadd r22.xyz, r13.xyzx, r16.wwww + ishl r22.xyz, r22.xyzx, l(3) + ushr r23.xyz, r22.xyzx, l(5) + iadd r22.xyz, r22.yxzy, r23.yxzy + mov r21.y, r22.z + mov r22.w, r21.w + mov r16.zw, r22.wwwx + mov r22.x, r21.z + else + mov r21.xy, r6.zwzz + mov r16.zw, r7.wwwy + mov r22.x, r6.x + mov r22.y, r7.x + endif + mov x0[11].xy, l(255,255,0,0) + mov x0[10].xy, r21.xyxx + mov x0[9].xy, r16.zwzz + mov x0[8].xy, r22.xyxx + ineg r23.x, r18.x + ineg r23.y, r14.z + ineg r23.z, r17.x + mov r18.z, r14.w + mov r18.w, r17.y + iadd r17.xyz, r18.yzwy, r23.xyzx + mov x1[0].xyz, r17.xyzx + ineg r18.x, r20.x + ineg r18.y, r15.z + ineg r18.z, r19.x + mov r20.z, r15.w + mov r20.w, r19.y + iadd r18.xyz, r18.xyzx, r20.yzwy + mov x1[1].xyz, r18.xyzx + ineg r19.x, r22.x + ineg r19.y, r16.z + ineg r19.z, r21.x + mov r22.z, r16.w + mov r22.w, r21.y + iadd r19.xyz, r19.xyzx, r22.yzwy + mov x1[2].xyz, r19.xyzx + mov x1[2].w, l(0) + mov x1[1].w, l(0) + mov x1[0].w, l(0) + imul null, r14.zw, r17.xxxy, r17.xxxy + iadd r4.y, r14.w, r14.z + imad r4.y, r17.z, r17.z, r4.y + mov x2[0].x, r4.y + imul null, r14.zw, r18.xxxy, r18.xxxy + iadd r5.z, r14.w, r14.z + imad r5.z, r18.z, r18.z, r5.z + mov x2[1].x, r5.z + imul null, r14.zw, r19.xxxy, r19.xxxy + iadd r6.y, r14.w, r14.z + imad r6.y, r19.z, r19.z, r6.y + mov x2[2].x, r6.y + mov x3[0].x, l(0) + mov x3[1].x, icb[r0.y + 0].y + mov x3[2].x, icb[r0.y + 0].z + mov r7.z, l(0) + loop + uge r8.w, r7.z, l(3) + breakc_nz r8.w + mov r17.xyzw, x1[r7.z + 0].xyzw + mov r8.w, x3[r7.z + 0].x + ld_structured r18.xyzw, r8.w, l(0), g0.xyzw + ishl r8.w, r7.z, l(2) + mov r9.w, x0[r8.w + 0].x + mov r10.w, x0[r8.w + 1].x + mov r11.w, x0[r8.w + 2].x + mov r12.w, x0[r8.w + 3].x + ineg r19.x, r9.w + ineg r19.y, r10.w + ineg r19.z, r11.w + ineg r19.w, r12.w + iadd r18.xyzw, r18.xyzw, r19.xyzw + imul null, r14.zw, r17.xxxy, r18.xxxy + iadd r13.w, r14.w, r14.z + imad r13.w, r17.z, r18.z, r13.w + imad r13.w, r17.w, r18.w, r13.w + mov r14.z, x2[r7.z + 0].x + ilt r14.w, l(0), r14.z + ilt r15.z, l(0), r13.w + and r14.w, r14.w, r15.z + itof r13.w, r13.w + mul r13.w, r13.w, l(63.499989) + ftou r13.w, r13.w + ishl r14.z, r14.z, l(5) + ult r13.w, r14.z, r13.w + and r13.w, r13.w, r14.w + if_nz r13.w + ineg r17.xyzw, r17.xyzw + mov x1[r7.z + 0].xyzw, r17.xyzw + mov r13.w, x0[r8.w + 0].y + mov r14.z, x0[r8.w + 1].y + mov r14.w, x0[r8.w + 2].y + mov r15.z, x0[r8.w + 3].y + mov x0[r8.w + 0].x, r13.w + mov x0[r8.w + 1].x, r14.z + mov x0[r8.w + 2].x, r14.w + mov x0[r8.w + 3].x, r15.z + mov x0[r8.w + 0].y, r9.w + mov x0[r8.w + 1].y, r10.w + mov x0[r8.w + 2].y, r11.w + mov x0[r8.w + 3].y, r12.w + endif + iadd r7.z, r7.z, l(1) + endloop + mov r17.xyzw, x1[2].xyzw + mov r7.z, x0[8].x + mov r8.w, x0[9].x + mov r9.w, x0[10].x + mov r10.w, x0[11].x + ineg r18.x, r7.z + ineg r18.y, r8.w + ineg r18.z, r9.w + ineg r18.w, r10.w + ige r11.w, l(0), r6.y + itof r12.w, r6.y + movc r19.xyz, r3.zzzz, l(128,3,32,0), l(64,7,16,0) + mov r20.xyzw, x1[1].xyzw + mov r3.z, x0[4].x + mov r13.w, x0[5].x + mov r14.z, x0[6].x + mov r14.w, x0[7].x + ineg r21.x, r3.z + ineg r21.y, r13.w + ineg r21.zw, r14.zzzw + ige r15.z, l(0), r5.z + itof r15.w, r5.z + mov r22.xyzw, x1[0].xyzw + mov r16.z, x0[0].x + mov r16.w, x0[1].x + mov r19.w, x0[2].x + mov r23.x, x0[3].x + ineg r24.xy, r16.zwzz + ineg r24.z, r19.w + ineg r24.w, r23.x + ige r23.y, l(0), r4.y + itof r23.z, r4.y + mov r23.w, l(0) + mov r16.y, l(0) + loop + uge r25.x, r23.w, l(16) + breakc_nz r25.x + ishl r25.x, r23.w, l(1) + ushr r25.x, icb[r0.z + 0].x, r25.x + and r25.x, r25.x, l(3) + ieq r25.y, r25.x, l(2) + if_nz r25.y + ld_structured r26.xyzw, r23.w, l(0), g0.xyzw + iadd r26.xyzw, r18.xyzw, r26.xyzw + imul null, r25.yz, r17.xxyx, r26.xxyx + iadd r25.y, r25.z, r25.y + imad r25.y, r17.z, r26.z, r25.y + imad r25.y, r17.w, r26.w, r25.y + ige r25.z, l(0), r25.y + or r25.z, r11.w, r25.z + ilt r25.w, r25.y, r6.y + itof r25.y, r25.y + mul r25.y, r25.y, l(63.499989) + div r25.y, r25.y, r12.w + ftou r25.y, r25.y + iadd r25.y, r19.x, r25.y + movc r25.y, r25.w, icb[r25.y + 0].w, r19.y + movc r25.y, r25.z, l(0), r25.y + else + ieq r25.z, r25.x, l(1) + if_nz r25.z + ld_structured r26.xyzw, r23.w, l(0), g0.xyzw + iadd r26.xyzw, r21.xyzw, r26.xyzw + imul null, r25.zw, r20.xxxy, r26.xxxy + iadd r25.z, r25.w, r25.z + imad r25.z, r20.z, r26.z, r25.z + imad r25.z, r20.w, r26.w, r25.z + ige r25.w, l(0), r25.z + or r25.w, r15.z, r25.w + ilt r26.x, r25.z, r5.z + itof r25.z, r25.z + mul r25.z, r25.z, l(63.499989) + div r25.z, r25.z, r15.w + ftou r25.z, r25.z + iadd r25.z, r19.x, r25.z + movc r25.z, r26.x, icb[r25.z + 0].w, r19.y + movc r25.y, r25.w, l(0), r25.z + else + ld_structured r26.xyzw, r23.w, l(0), g0.xyzw + iadd r26.xyzw, r24.xyzw, r26.xyzw + imul null, r25.zw, r22.xxxy, r26.xxxy + iadd r25.z, r25.w, r25.z + imad r25.z, r22.z, r26.z, r25.z + imad r25.z, r22.w, r26.w, r25.z + ige r25.w, l(0), r25.z + or r25.w, r23.y, r25.w + ilt r26.x, r25.z, r4.y + itof r25.z, r25.z + mul r25.z, r25.z, l(63.499989) + div r25.z, r25.z, r23.z + ftou r25.z, r25.z + iadd r25.z, r19.x, r25.z + movc r25.z, r26.x, icb[r25.z + 0].w, r19.y + movc r25.y, r25.w, l(0), r25.z + endif + endif + iadd r25.y, r19.z, r25.y + iadd r25.z, l(64), -icb[r25.y + 64].x + ishl r25.x, r25.x, l(2) + mov r26.x, x0[r25.x + 0].x + mov r26.y, x0[r25.x + 1].x + mov r26.z, x0[r25.x + 2].x + mov r27.x, x0[r25.x + 0].y + mov r27.y, x0[r25.x + 1].y + mov r27.z, x0[r25.x + 2].y + imul null, r25.xyw, r27.xyxz, icb[r25.y + 64].xxxx + imad r25.xyz, r25.zzzz, r26.xyzx, r25.xywx + iadd r25.xyz, r25.xyzx, l(32, 32, 32, 0) + ushr r25.xyw, r25.xyxz, l(6) + ld_structured r26.xyzw, r23.w, l(0), g0.xyzw + ult r27.xyz, r25.xywx, r26.xyzx + mov r25.z, r26.x + movc r27.xw, r27.xxxx, r25.zzzx, r25.xxxz + mov r25.xz, r26.yyzy + movc r25.xyzw, r27.yyzz, r25.xyzw, r25.yxwz + ult r26.x, l(255), r26.w + mov r14.x, r26.w + movc r26.xw, r26.xxxx, r14.yyyx, r14.xxxy + ineg r28.x, r27.w + ineg r28.yz, r25.yywy + ineg r28.w, r26.x + mov r26.x, r27.x + mov r26.yz, r25.xxzx + iadd r25.xyzw, r28.xyzw, r26.xyzw + imul null, r25.xy, r25.xyxx, r25.xyxx + iadd r14.x, r25.y, r25.x + imad r14.x, r25.z, r25.z, r14.x + utof r14.x, r14.x + utof r25.x, r25.w + mul r25.x, r25.x, r25.x + mad r14.x, r25.x, cb0[1].z, r14.x + ftou r14.x, r14.x + iadd r16.y, r14.x, r16.y + iadd r23.w, r23.w, l(1) + endloop + ult r3.z, r16.y, r15.y + movc r15.xy, r3.zzzz, r16.xyxx, r15.xyxx + iadd r16.x, r16.x, l(1) + endloop + store_structured g0.x, vThreadIDInGroupFlattened.x, l(16), r15.y + store_structured g0.x, vThreadIDInGroupFlattened.x, l(24), r0.y + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r15.x +endif +sync_g_t +if_nz r1.y + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(32) + ld_structured r3.x, r0.y, l(16), g0.xxxx + ld_structured r4.x, r0.y, l(24), g0.xxxx + ld_structured r5.x, r0.y, l(32), g0.xxxx + ult r0.y, r3.x, r2.x + if_nz r0.y + store_structured g0.x, vThreadIDInGroupFlattened.x, l(16), r3.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(24), r4.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r5.x + endif +endif +if_nz r1.x + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(16) + ld_structured r3.x, r0.y, l(16), g0.xxxx + ld_structured r4.x, r0.y, l(24), g0.xxxx + ld_structured r5.x, r0.y, l(32), g0.xxxx + ult r0.y, r3.x, r2.x + if_nz r0.y + store_structured g0.x, vThreadIDInGroupFlattened.x, l(16), r3.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(24), r4.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r5.x + endif +endif +if_nz r1.z + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(8) + ld_structured r3.x, r0.y, l(16), g0.xxxx + ld_structured r4.x, r0.y, l(24), g0.xxxx + ld_structured r5.x, r0.y, l(32), g0.xxxx + ult r0.y, r3.x, r2.x + if_nz r0.y + store_structured g0.x, vThreadIDInGroupFlattened.x, l(16), r3.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(24), r4.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r5.x + endif +endif +if_nz r1.w + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(4) + ld_structured r2.x, r0.y, l(16), g0.xxxx + ld_structured r3.x, r0.y, l(24), g0.xxxx + ld_structured r4.x, r0.y, l(32), g0.xxxx + ult r0.y, r2.x, r1.x + if_nz r0.y + store_structured g0.x, vThreadIDInGroupFlattened.x, l(16), r2.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(24), r3.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r4.x + endif +endif +ult r0.yz, vThreadIDInGroupFlattened.xxxx, l(0, 2, 1, 0) +if_nz r0.y + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(2) + ld_structured r2.x, r0.y, l(16), g0.xxxx + ld_structured r3.x, r0.y, l(24), g0.xxxx + ld_structured r4.x, r0.y, l(32), g0.xxxx + ult r0.y, r2.x, r1.x + if_nz r0.y + store_structured g0.x, vThreadIDInGroupFlattened.x, l(16), r2.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(24), r3.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r4.x + endif +endif +if_nz r0.z + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(1) + ld_structured r2.x, r0.y, l(16), g0.xxxx + ld_structured r3.x, r0.y, l(24), g0.xxxx + ld_structured r4.x, r0.y, l(32), g0.xxxx + ult r0.y, r2.x, r1.x + if_nz r0.y + store_structured g0.x, vThreadIDInGroupFlattened.x, l(16), r2.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(24), r3.x + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r4.x + endif + ld_structured r1.x, r0.x, l(0), t1.xxxx + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + ult r0.y, r2.x, r1.x + if_nz r0.y + ld_structured r2.z, vThreadIDInGroupFlattened.x, l(24), g0.xxxx + ld_structured r2.w, vThreadIDInGroupFlattened.x, l(32), g0.xxxx + mov r2.y, cb0[0].w + else + ld_structured r2.xyzw, r0.x, l(0), t1.xyzw + endif + store_structured u0.xyzw, r0.x, l(0), r2.xyzw +endif +ret +// Approximately 0 instruction slots used +#endif + +const BYTE BC7Encode_TryMode02CS[] = +{ + 68, 88, 66, 67, 122, 4, + 188, 46, 162, 127, 38, 170, + 88, 175, 162, 101, 250, 119, + 32, 234, 1, 0, 0, 0, + 172, 70, 0, 0, 3, 0, + 0, 0, 44, 0, 0, 0, + 60, 0, 0, 0, 76, 0, + 0, 0, 73, 83, 71, 78, + 8, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 79, 83, 71, 78, 8, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 83, 72, + 69, 88, 88, 70, 0, 0, + 64, 0, 5, 0, 150, 17, + 0, 0, 106, 8, 0, 1, + 53, 24, 0, 0, 2, 3, + 0, 0, 80, 80, 104, 170, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 64, 80, 90, 106, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 66, + 90, 90, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 168, 160, 80, 84, + 15, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 165, 165, 15, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 80, 80, + 160, 160, 15, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 160, 160, 85, 85, + 15, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 80, 80, 90, 90, 15, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 85, 170, 15, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 85, 85, 170, + 15, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 85, 170, 170, 15, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 144, 144, + 144, 144, 15, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 148, 148, 148, 148, + 15, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 164, 164, 164, 164, 15, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 80, 148, + 165, 169, 15, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 80, 66, 10, 42, + 15, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 64, 80, 148, 165, 15, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 84, 80, + 66, 10, 2, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 165, 165, 165, + 8, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 160, 160, 160, 85, 2, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 84, 84, + 168, 168, 2, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 64, 64, 106, 106, + 8, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 0, 80, 164, 164, 8, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 0, 5, + 26, 26, 15, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 164, 164, 80, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 144, 144, 165, 170, 8, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 20, 105, + 105, 20, 2, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 0, 20, 105, 105, + 2, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 160, 133, 133, 160, 8, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 20, 20, + 130, 170, 8, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 80, 164, 164, 80, + 2, 0, 0, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 0, 2, 90, 106, 2, 0, + 0, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 0, 128, + 165, 169, 15, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 168, 160, 144, 80, + 15, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 80, 144, 160, 168, 6, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 36, 36, + 36, 36, 8, 0, 0, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 0, 85, 170, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 36, 73, 146, 36, 8, 0, + 0, 0, 0, 0, 0, 0, + 9, 0, 0, 0, 36, 146, + 73, 36, 15, 0, 0, 0, + 0, 0, 0, 0, 9, 0, + 0, 0, 80, 10, 165, 80, + 15, 0, 0, 0, 0, 0, + 0, 0, 9, 0, 0, 0, + 80, 165, 10, 80, 2, 0, + 0, 0, 0, 0, 0, 0, + 9, 0, 0, 0, 68, 68, + 170, 170, 8, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 0, 0, 102, 102, + 2, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 160, 165, 160, 165, 2, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 0, 0, 160, 80, + 160, 80, 2, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 40, 105, 40, 105, + 15, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 68, 170, 170, 68, 15, 0, + 0, 0, 0, 0, 0, 0, + 11, 0, 0, 0, 0, 102, + 102, 102, 6, 0, 0, 0, + 0, 0, 0, 0, 11, 0, + 0, 0, 68, 68, 68, 170, + 6, 0, 0, 0, 0, 0, + 0, 0, 11, 0, 0, 0, + 168, 84, 168, 84, 2, 0, + 0, 0, 0, 0, 0, 0, + 11, 0, 0, 0, 128, 149, + 128, 149, 6, 0, 0, 0, + 0, 0, 0, 0, 12, 0, + 0, 0, 0, 150, 150, 150, + 8, 0, 0, 0, 0, 0, + 0, 0, 12, 0, 0, 0, + 168, 84, 84, 168, 15, 0, + 0, 0, 0, 0, 0, 0, + 12, 0, 0, 0, 128, 149, + 149, 128, 15, 0, 0, 0, + 0, 0, 0, 0, 12, 0, + 0, 0, 20, 20, 20, 170, + 2, 0, 0, 0, 0, 0, + 0, 0, 13, 0, 0, 0, + 0, 0, 150, 150, 2, 0, + 0, 0, 0, 0, 0, 0, + 13, 0, 0, 0, 20, 20, + 170, 170, 15, 0, 0, 0, + 0, 0, 0, 0, 13, 0, + 0, 0, 160, 80, 80, 160, + 15, 0, 0, 0, 0, 0, + 0, 0, 13, 0, 0, 0, + 160, 165, 165, 160, 15, 0, + 0, 0, 0, 0, 0, 0, + 14, 0, 0, 0, 0, 0, + 0, 150, 15, 0, 0, 0, + 0, 0, 0, 0, 14, 0, + 0, 0, 128, 64, 128, 64, + 15, 0, 0, 0, 0, 0, + 0, 0, 14, 0, 0, 0, + 168, 169, 168, 169, 2, 0, + 0, 0, 0, 0, 0, 0, + 14, 0, 0, 0, 68, 170, + 170, 170, 2, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 84, 82, 74, 42, + 15, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 3, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 9, 0, 0, 0, + 15, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 13, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 17, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 21, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 1, 0, 0, 0, + 26, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 0, 15, 0, 0, 0, + 8, 0, 0, 0, 1, 0, + 0, 0, 34, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 1, 0, 0, 0, + 38, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 1, 0, 0, 0, 43, 0, + 0, 0, 6, 0, 0, 0, + 15, 0, 0, 0, 1, 0, + 0, 0, 47, 0, 0, 0, + 6, 0, 0, 0, 15, 0, + 0, 0, 1, 0, 0, 0, + 51, 0, 0, 0, 6, 0, + 0, 0, 15, 0, 0, 0, + 1, 0, 0, 0, 55, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 1, 0, + 0, 0, 60, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 2, 0, 0, 0, + 64, 0, 0, 0, 3, 0, + 0, 0, 8, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 2, 0, + 0, 0, 9, 0, 0, 0, + 3, 0, 0, 0, 8, 0, + 0, 0, 2, 0, 0, 0, + 18, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 2, 0, 0, 0, 27, 0, + 0, 0, 15, 0, 0, 0, + 3, 0, 0, 0, 2, 0, + 0, 0, 37, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 2, 0, 0, 0, + 46, 0, 0, 0, 3, 0, + 0, 0, 8, 0, 0, 0, + 2, 0, 0, 0, 55, 0, + 0, 0, 6, 0, 0, 0, + 15, 0, 0, 0, 2, 0, + 0, 0, 64, 0, 0, 0, + 10, 0, 0, 0, 8, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 3, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 6, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 10, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 10, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 8, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 21, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 4, 0, 0, 0, 43, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 4, 0, + 0, 0, 64, 0, 0, 0, + 5, 0, 0, 0, 10, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 10, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 8, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 9, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 10, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 6, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 8, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 3, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 6, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 6, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 8, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 3, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 15, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 15, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 15, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 15, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 15, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 15, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 13, 0, 0, 0, 15, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 12, 0, 0, 0, + 15, 0, 0, 0, 7, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 7, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 8, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 89, 0, 0, 4, + 70, 142, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 88, 24, 0, 4, 0, 112, + 16, 0, 0, 0, 0, 0, + 85, 85, 0, 0, 162, 0, + 0, 4, 0, 112, 16, 0, + 1, 0, 0, 0, 16, 0, + 0, 0, 158, 0, 0, 4, + 0, 224, 17, 0, 0, 0, + 0, 0, 16, 0, 0, 0, + 95, 0, 0, 2, 0, 64, + 2, 0, 95, 0, 0, 2, + 18, 16, 2, 0, 104, 0, + 0, 2, 29, 0, 0, 0, + 105, 0, 0, 4, 0, 0, + 0, 0, 12, 0, 0, 0, + 4, 0, 0, 0, 105, 0, + 0, 4, 1, 0, 0, 0, + 3, 0, 0, 0, 4, 0, + 0, 0, 105, 0, 0, 4, + 2, 0, 0, 0, 3, 0, + 0, 0, 4, 0, 0, 0, + 105, 0, 0, 4, 3, 0, + 0, 0, 3, 0, 0, 0, + 4, 0, 0, 0, 160, 0, + 0, 5, 0, 240, 17, 0, + 0, 0, 0, 0, 100, 0, + 0, 0, 64, 0, 0, 0, + 155, 0, 0, 4, 64, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 16, + 2, 0, 10, 128, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 79, 0, 0, 9, + 242, 0, 16, 0, 1, 0, + 0, 0, 6, 64, 2, 0, + 2, 64, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 8, 0, 0, 0, 4, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 1, 0, + 0, 0, 78, 0, 0, 9, + 34, 0, 16, 0, 0, 0, + 0, 0, 0, 208, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 26, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 35, 0, 0, 11, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 128, + 65, 0, 0, 0, 0, 0, + 0, 0, 26, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 6, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 85, 0, + 0, 6, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 8, + 194, 0, 16, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 45, 0, + 0, 7, 242, 0, 16, 0, + 2, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 70, 126, 16, 0, 0, 0, + 0, 0, 56, 0, 0, 10, + 242, 0, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 127, 67, + 0, 0, 127, 67, 0, 0, + 127, 67, 0, 0, 127, 67, + 28, 0, 0, 5, 242, 0, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 2, 0, + 0, 0, 84, 0, 0, 10, + 242, 0, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 2, 0, + 0, 0, 21, 0, 0, 1, + 190, 24, 0, 1, 168, 0, + 0, 8, 18, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 1, 64, + 0, 0, 255, 255, 255, 255, + 55, 0, 0, 10, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 64, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 79, 0, + 0, 6, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 192, 255, + 255, 255, 54, 0, 0, 5, + 130, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 48, 0, + 0, 1, 80, 0, 0, 7, + 18, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 3, 0, 4, 3, 10, 0, + 16, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 114, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 70, 242, + 17, 0, 0, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 85, 0, + 0, 8, 130, 0, 16, 0, + 2, 0, 0, 0, 10, 144, + 144, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 32, 0, + 0, 7, 18, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 18, 0, 16, 0, 3, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 3, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 9, 0, + 0, 0, 54, 0, 0, 6, + 66, 0, 16, 0, 3, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 84, 0, 0, 7, + 114, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 10, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 9, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 83, 0, 0, 7, 114, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 18, 0, + 0, 1, 32, 0, 0, 7, + 130, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 2, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 3, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 3, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 3, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 84, 0, 0, 7, 114, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 0, 16, 0, + 3, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 3, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 66, 0, 16, 0, + 3, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 83, 0, + 0, 7, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 18, 0, 0, 1, + 54, 0, 0, 6, 18, 0, + 16, 0, 3, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 3, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 3, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 84, 0, 0, 7, 114, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 0, 16, 0, + 3, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 3, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 66, 0, 16, 0, + 3, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 83, 0, + 0, 7, 114, 0, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 30, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 22, 0, 0, 1, + 54, 0, 0, 6, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 4, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 4, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 5, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 5, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 5, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 6, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 6, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 9, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 6, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 7, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 7, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 9, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 7, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 55, 0, 0, 10, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 84, 0, 0, 10, + 114, 0, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 30, 0, + 0, 0, 30, 0, 0, 0, + 30, 0, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 84, 0, 0, 10, 114, 0, + 16, 0, 3, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 9, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 30, 0, 0, 0, + 30, 0, 0, 0, 30, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 248, 0, 0, 0, 248, 0, + 0, 0, 248, 0, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 2, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 248, 0, 0, 0, 248, 0, + 0, 0, 248, 0, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 3, 0, + 0, 0, 70, 2, 16, 0, + 3, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 84, 0, + 0, 10, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 10, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 10, 0, + 0, 0, 2, 64, 0, 0, + 30, 0, 0, 0, 30, 0, + 0, 0, 30, 0, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 84, 0, 0, 10, + 114, 0, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 2, 64, 0, 0, 30, 0, + 0, 0, 30, 0, 0, 0, + 30, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 248, 0, 0, 0, + 248, 0, 0, 0, 248, 0, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 4, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 248, 0, 0, 0, + 248, 0, 0, 0, 248, 0, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 5, 0, 0, 0, 70, 2, + 16, 0, 5, 0, 0, 0, + 70, 2, 16, 0, 12, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 84, 0, 0, 10, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 12, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 12, 0, + 0, 0, 70, 2, 16, 0, + 12, 0, 0, 0, 2, 64, + 0, 0, 30, 0, 0, 0, + 30, 0, 0, 0, 30, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 4, 0, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 84, 0, + 0, 10, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 2, 64, 0, 0, + 30, 0, 0, 0, 30, 0, + 0, 0, 30, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 2, 64, 0, 0, 248, 0, + 0, 0, 248, 0, 0, 0, + 248, 0, 0, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 248, 0, + 0, 0, 248, 0, 0, 0, + 248, 0, 0, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 4, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 14, 0, 0, 0, 1, 64, + 0, 0, 255, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 2, 0, 0, 0, + 58, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 8, 50, 0, + 16, 0, 15, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 255, 255, 255, 255, + 0, 0, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 16, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 48, 0, + 0, 1, 80, 0, 0, 7, + 66, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 16, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 3, 0, 4, 3, 42, 0, + 16, 0, 3, 0, 0, 0, + 32, 0, 0, 7, 66, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 31, 0, + 0, 3, 26, 0, 16, 0, + 2, 0, 0, 0, 85, 0, + 0, 7, 34, 0, 16, 0, + 16, 0, 0, 0, 10, 0, + 16, 0, 16, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 14, 0, + 0, 0, 6, 4, 16, 0, + 16, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 17, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 166, 10, 16, 0, + 14, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 17, 0, 0, 0, 70, 2, + 16, 0, 17, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 18, 0, + 0, 0, 70, 2, 16, 0, + 17, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 210, 0, + 16, 0, 17, 0, 0, 0, + 166, 4, 16, 0, 17, 0, + 0, 0, 166, 4, 16, 0, + 18, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 18, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 246, 15, 16, 0, 14, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 18, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 19, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 18, 0, 0, 0, 22, 6, + 16, 0, 18, 0, 0, 0, + 22, 6, 16, 0, 19, 0, + 0, 0, 54, 0, 0, 5, + 34, 0, 16, 0, 17, 0, + 0, 0, 42, 0, 16, 0, + 18, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 18, 0, 0, 0, 58, 0, + 16, 0, 17, 0, 0, 0, + 54, 0, 0, 5, 194, 0, + 16, 0, 14, 0, 0, 0, + 246, 3, 16, 0, 18, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 18, 0, + 0, 0, 42, 0, 16, 0, + 17, 0, 0, 0, 18, 0, + 0, 1, 54, 0, 0, 5, + 50, 0, 16, 0, 17, 0, + 0, 0, 230, 10, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 5, 194, 0, 16, 0, + 14, 0, 0, 0, 246, 7, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 5, 18, 0, + 16, 0, 18, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 5, + 34, 0, 16, 0, 18, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 21, 0, + 0, 1, 54, 0, 0, 9, + 50, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 6, + 50, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 70, 0, 16, 0, 17, 0, + 0, 0, 54, 0, 0, 6, + 50, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 230, 10, 16, 0, 14, 0, + 0, 0, 54, 0, 0, 6, + 50, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 70, 0, 16, 0, 18, 0, + 0, 0, 31, 0, 0, 3, + 26, 0, 16, 0, 2, 0, + 0, 0, 85, 0, 0, 7, + 18, 0, 16, 0, 19, 0, + 0, 0, 10, 0, 16, 0, + 16, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 85, 0, 0, 7, 34, 0, + 16, 0, 19, 0, 0, 0, + 10, 0, 16, 0, 16, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 15, 0, 0, 0, 6, 4, + 16, 0, 19, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 166, 10, + 16, 0, 15, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 19, 0, 0, 0, + 70, 2, 16, 0, 19, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 20, 0, 0, 0, 70, 2, + 16, 0, 19, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 210, 0, 16, 0, 19, 0, + 0, 0, 166, 4, 16, 0, + 19, 0, 0, 0, 166, 4, + 16, 0, 20, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 20, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 246, 15, 16, 0, + 15, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 20, 0, 0, 0, 70, 2, + 16, 0, 20, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 21, 0, + 0, 0, 70, 2, 16, 0, + 20, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 20, 0, 0, 0, + 22, 6, 16, 0, 20, 0, + 0, 0, 22, 6, 16, 0, + 21, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 19, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 19, 0, + 0, 0, 54, 0, 0, 5, + 194, 0, 16, 0, 15, 0, + 0, 0, 246, 3, 16, 0, + 20, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 20, 0, 0, 0, 42, 0, + 16, 0, 19, 0, 0, 0, + 18, 0, 0, 1, 54, 0, + 0, 5, 50, 0, 16, 0, + 19, 0, 0, 0, 230, 10, + 16, 0, 4, 0, 0, 0, + 54, 0, 0, 5, 194, 0, + 16, 0, 15, 0, 0, 0, + 246, 7, 16, 0, 5, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 20, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 20, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 21, 0, 0, 1, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 50, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 70, 0, 16, 0, + 19, 0, 0, 0, 54, 0, + 0, 6, 50, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 230, 10, 16, 0, + 15, 0, 0, 0, 54, 0, + 0, 6, 50, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 70, 0, 16, 0, + 20, 0, 0, 0, 31, 0, + 0, 3, 26, 0, 16, 0, + 2, 0, 0, 0, 85, 0, + 0, 7, 18, 0, 16, 0, + 21, 0, 0, 0, 10, 0, + 16, 0, 16, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 21, 0, + 0, 0, 10, 0, 16, 0, + 16, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 16, 0, 0, 0, + 6, 4, 16, 0, 21, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 21, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 166, 10, 16, 0, 16, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 21, 0, + 0, 0, 70, 2, 16, 0, + 21, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 22, 0, 0, 0, + 70, 2, 16, 0, 21, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 210, 0, 16, 0, + 21, 0, 0, 0, 166, 4, + 16, 0, 21, 0, 0, 0, + 166, 4, 16, 0, 22, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 22, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 246, 15, + 16, 0, 16, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 22, 0, 0, 0, + 70, 2, 16, 0, 22, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 23, 0, 0, 0, 70, 2, + 16, 0, 22, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 22, 0, + 0, 0, 22, 6, 16, 0, + 22, 0, 0, 0, 22, 6, + 16, 0, 23, 0, 0, 0, + 54, 0, 0, 5, 34, 0, + 16, 0, 21, 0, 0, 0, + 42, 0, 16, 0, 22, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 22, 0, + 0, 0, 58, 0, 16, 0, + 21, 0, 0, 0, 54, 0, + 0, 5, 194, 0, 16, 0, + 16, 0, 0, 0, 246, 3, + 16, 0, 22, 0, 0, 0, + 54, 0, 0, 5, 18, 0, + 16, 0, 22, 0, 0, 0, + 42, 0, 16, 0, 21, 0, + 0, 0, 18, 0, 0, 1, + 54, 0, 0, 5, 50, 0, + 16, 0, 21, 0, 0, 0, + 230, 10, 16, 0, 6, 0, + 0, 0, 54, 0, 0, 5, + 194, 0, 16, 0, 16, 0, + 0, 0, 246, 7, 16, 0, + 7, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 22, 0, 0, 0, 10, 0, + 16, 0, 6, 0, 0, 0, + 54, 0, 0, 5, 34, 0, + 16, 0, 22, 0, 0, 0, + 10, 0, 16, 0, 7, 0, + 0, 0, 21, 0, 0, 1, + 54, 0, 0, 9, 50, 48, + 32, 0, 0, 0, 0, 0, + 11, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 50, 48, + 32, 0, 0, 0, 0, 0, + 10, 0, 0, 0, 70, 0, + 16, 0, 21, 0, 0, 0, + 54, 0, 0, 6, 50, 48, + 32, 0, 0, 0, 0, 0, + 9, 0, 0, 0, 230, 10, + 16, 0, 16, 0, 0, 0, + 54, 0, 0, 6, 50, 48, + 32, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 70, 0, + 16, 0, 22, 0, 0, 0, + 40, 0, 0, 5, 18, 0, + 16, 0, 23, 0, 0, 0, + 10, 0, 16, 0, 18, 0, + 0, 0, 40, 0, 0, 5, + 34, 0, 16, 0, 23, 0, + 0, 0, 42, 0, 16, 0, + 14, 0, 0, 0, 40, 0, + 0, 5, 66, 0, 16, 0, + 23, 0, 0, 0, 10, 0, + 16, 0, 17, 0, 0, 0, + 54, 0, 0, 5, 66, 0, + 16, 0, 18, 0, 0, 0, + 58, 0, 16, 0, 14, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 18, 0, + 0, 0, 26, 0, 16, 0, + 17, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 17, 0, 0, 0, 150, 7, + 16, 0, 18, 0, 0, 0, + 70, 2, 16, 0, 23, 0, + 0, 0, 54, 0, 0, 6, + 114, 48, 32, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 70, 2, 16, 0, 17, 0, + 0, 0, 40, 0, 0, 5, + 18, 0, 16, 0, 18, 0, + 0, 0, 10, 0, 16, 0, + 20, 0, 0, 0, 40, 0, + 0, 5, 34, 0, 16, 0, + 18, 0, 0, 0, 42, 0, + 16, 0, 15, 0, 0, 0, + 40, 0, 0, 5, 66, 0, + 16, 0, 18, 0, 0, 0, + 10, 0, 16, 0, 19, 0, + 0, 0, 54, 0, 0, 5, + 66, 0, 16, 0, 20, 0, + 0, 0, 58, 0, 16, 0, + 15, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 20, 0, 0, 0, 26, 0, + 16, 0, 19, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 18, 0, 0, 0, + 70, 2, 16, 0, 18, 0, + 0, 0, 150, 7, 16, 0, + 20, 0, 0, 0, 54, 0, + 0, 6, 114, 48, 32, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 70, 2, 16, 0, + 18, 0, 0, 0, 40, 0, + 0, 5, 18, 0, 16, 0, + 19, 0, 0, 0, 10, 0, + 16, 0, 22, 0, 0, 0, + 40, 0, 0, 5, 34, 0, + 16, 0, 19, 0, 0, 0, + 42, 0, 16, 0, 16, 0, + 0, 0, 40, 0, 0, 5, + 66, 0, 16, 0, 19, 0, + 0, 0, 10, 0, 16, 0, + 21, 0, 0, 0, 54, 0, + 0, 5, 66, 0, 16, 0, + 22, 0, 0, 0, 58, 0, + 16, 0, 16, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 22, 0, 0, 0, + 26, 0, 16, 0, 21, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 19, 0, + 0, 0, 70, 2, 16, 0, + 19, 0, 0, 0, 150, 7, + 16, 0, 22, 0, 0, 0, + 54, 0, 0, 6, 114, 48, + 32, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 19, 0, 0, 0, + 54, 0, 0, 6, 130, 48, + 32, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 130, 48, + 32, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 130, 48, + 32, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 194, 0, 16, 0, + 14, 0, 0, 0, 6, 4, + 16, 0, 17, 0, 0, 0, + 6, 4, 16, 0, 17, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 42, 0, + 16, 0, 14, 0, 0, 0, + 35, 0, 0, 9, 34, 0, + 16, 0, 4, 0, 0, 0, + 42, 0, 16, 0, 17, 0, + 0, 0, 42, 0, 16, 0, + 17, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 194, 0, 16, 0, + 14, 0, 0, 0, 6, 4, + 16, 0, 18, 0, 0, 0, + 6, 4, 16, 0, 18, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 42, 0, + 16, 0, 14, 0, 0, 0, + 35, 0, 0, 9, 66, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 18, 0, + 0, 0, 42, 0, 16, 0, + 18, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 2, 0, 0, 0, + 1, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 194, 0, 16, 0, + 14, 0, 0, 0, 6, 4, + 16, 0, 19, 0, 0, 0, + 6, 4, 16, 0, 19, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 42, 0, + 16, 0, 14, 0, 0, 0, + 35, 0, 0, 9, 34, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 19, 0, + 0, 0, 42, 0, 16, 0, + 19, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 2, 0, 0, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 7, 18, 48, + 32, 0, 3, 0, 0, 0, + 1, 0, 0, 0, 26, 144, + 144, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 7, 18, 48, 32, 0, + 3, 0, 0, 0, 2, 0, + 0, 0, 42, 144, 144, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 66, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 48, 0, + 0, 1, 80, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 3, 0, 4, 3, 58, 0, + 16, 0, 8, 0, 0, 0, + 54, 0, 0, 7, 242, 0, + 16, 0, 17, 0, 0, 0, + 70, 62, 32, 4, 1, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 54, 0, + 0, 7, 130, 0, 16, 0, + 8, 0, 0, 0, 10, 48, + 32, 4, 3, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 18, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 54, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 10, 48, 32, 4, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 54, 0, + 0, 8, 130, 0, 16, 0, + 10, 0, 0, 0, 10, 48, + 32, 6, 0, 0, 0, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 54, 0, 0, 8, 130, 0, + 16, 0, 11, 0, 0, 0, + 10, 48, 32, 6, 0, 0, + 0, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 54, 0, 0, 8, + 130, 0, 16, 0, 12, 0, + 0, 0, 10, 48, 32, 6, + 0, 0, 0, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 40, 0, + 0, 5, 18, 0, 16, 0, + 19, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 40, 0, 0, 5, 34, 0, + 16, 0, 19, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 40, 0, 0, 5, + 66, 0, 16, 0, 19, 0, + 0, 0, 58, 0, 16, 0, + 11, 0, 0, 0, 40, 0, + 0, 5, 130, 0, 16, 0, + 19, 0, 0, 0, 58, 0, + 16, 0, 12, 0, 0, 0, + 30, 0, 0, 7, 242, 0, + 16, 0, 18, 0, 0, 0, + 70, 14, 16, 0, 18, 0, + 0, 0, 70, 14, 16, 0, + 19, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 194, 0, 16, 0, 14, 0, + 0, 0, 6, 4, 16, 0, + 17, 0, 0, 0, 6, 4, + 16, 0, 18, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 13, 0, 0, 0, + 58, 0, 16, 0, 14, 0, + 0, 0, 42, 0, 16, 0, + 14, 0, 0, 0, 35, 0, + 0, 9, 130, 0, 16, 0, + 13, 0, 0, 0, 42, 0, + 16, 0, 17, 0, 0, 0, + 42, 0, 16, 0, 18, 0, + 0, 0, 58, 0, 16, 0, + 13, 0, 0, 0, 35, 0, + 0, 9, 130, 0, 16, 0, + 13, 0, 0, 0, 58, 0, + 16, 0, 17, 0, 0, 0, + 58, 0, 16, 0, 18, 0, + 0, 0, 58, 0, 16, 0, + 13, 0, 0, 0, 54, 0, + 0, 7, 66, 0, 16, 0, + 14, 0, 0, 0, 10, 48, + 32, 4, 2, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 34, 0, 0, 7, + 130, 0, 16, 0, 14, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 14, 0, 0, 0, + 34, 0, 0, 7, 66, 0, + 16, 0, 15, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 13, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 14, 0, 0, 0, + 42, 0, 16, 0, 15, 0, + 0, 0, 43, 0, 0, 5, + 130, 0, 16, 0, 13, 0, + 0, 0, 58, 0, 16, 0, + 13, 0, 0, 0, 56, 0, + 0, 7, 130, 0, 16, 0, + 13, 0, 0, 0, 58, 0, + 16, 0, 13, 0, 0, 0, + 1, 64, 0, 0, 253, 255, + 125, 66, 28, 0, 0, 5, + 130, 0, 16, 0, 13, 0, + 0, 0, 58, 0, 16, 0, + 13, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 14, 0, 0, 0, 42, 0, + 16, 0, 14, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 79, 0, 0, 7, + 130, 0, 16, 0, 13, 0, + 0, 0, 42, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 13, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 13, 0, 0, 0, + 58, 0, 16, 0, 13, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 31, 0, + 4, 3, 58, 0, 16, 0, + 13, 0, 0, 0, 40, 0, + 0, 5, 242, 0, 16, 0, + 17, 0, 0, 0, 70, 14, + 16, 0, 17, 0, 0, 0, + 54, 0, 0, 7, 242, 48, + 32, 4, 1, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 17, 0, 0, 0, 54, 0, + 0, 7, 130, 0, 16, 0, + 13, 0, 0, 0, 26, 48, + 32, 4, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 54, 0, 0, 8, + 66, 0, 16, 0, 14, 0, + 0, 0, 26, 48, 32, 6, + 0, 0, 0, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 54, 0, + 0, 8, 130, 0, 16, 0, + 14, 0, 0, 0, 26, 48, + 32, 6, 0, 0, 0, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 54, 0, 0, 8, 66, 0, + 16, 0, 15, 0, 0, 0, + 26, 48, 32, 6, 0, 0, + 0, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 54, 0, 0, 7, + 18, 48, 32, 4, 0, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 13, 0, 0, 0, + 54, 0, 0, 8, 18, 48, + 32, 6, 0, 0, 0, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 14, 0, + 0, 0, 54, 0, 0, 8, + 18, 48, 32, 6, 0, 0, + 0, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 54, 0, + 0, 8, 18, 48, 32, 6, + 0, 0, 0, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 42, 0, + 16, 0, 15, 0, 0, 0, + 54, 0, 0, 7, 34, 48, + 32, 4, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 54, 0, + 0, 8, 34, 48, 32, 6, + 0, 0, 0, 0, 1, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 54, 0, 0, 8, 34, 48, + 32, 6, 0, 0, 0, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 11, 0, + 0, 0, 54, 0, 0, 8, + 34, 48, 32, 6, 0, 0, + 0, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 12, 0, 0, 0, 21, 0, + 0, 1, 30, 0, 0, 7, + 66, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 22, 0, 0, 1, 54, 0, + 0, 6, 242, 0, 16, 0, + 17, 0, 0, 0, 70, 62, + 32, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 66, 0, 16, 0, + 7, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 8, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 9, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 9, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 10, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 10, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 11, 0, 0, 0, 40, 0, + 0, 5, 18, 0, 16, 0, + 18, 0, 0, 0, 42, 0, + 16, 0, 7, 0, 0, 0, + 40, 0, 0, 5, 34, 0, + 16, 0, 18, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 40, 0, 0, 5, + 66, 0, 16, 0, 18, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 40, 0, + 0, 5, 130, 0, 16, 0, + 18, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 33, 0, 0, 7, 130, 0, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 6, 0, 0, 0, 43, 0, + 0, 5, 130, 0, 16, 0, + 12, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 55, 0, 0, 15, 114, 0, + 16, 0, 19, 0, 0, 0, + 166, 10, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 128, 0, 0, 0, 3, 0, + 0, 0, 32, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 64, 0, 0, 0, + 7, 0, 0, 0, 16, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 242, 0, + 16, 0, 20, 0, 0, 0, + 70, 62, 32, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 3, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 13, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 14, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 14, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 40, 0, 0, 5, 18, 0, + 16, 0, 21, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 40, 0, 0, 5, + 34, 0, 16, 0, 21, 0, + 0, 0, 58, 0, 16, 0, + 13, 0, 0, 0, 40, 0, + 0, 5, 194, 0, 16, 0, + 21, 0, 0, 0, 166, 14, + 16, 0, 14, 0, 0, 0, + 33, 0, 0, 7, 66, 0, + 16, 0, 15, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 43, 0, + 0, 5, 130, 0, 16, 0, + 15, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 54, 0, 0, 6, 242, 0, + 16, 0, 22, 0, 0, 0, + 70, 62, 32, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 16, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 16, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 19, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 23, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 40, 0, 0, 5, 50, 0, + 16, 0, 24, 0, 0, 0, + 230, 10, 16, 0, 16, 0, + 0, 0, 40, 0, 0, 5, + 66, 0, 16, 0, 24, 0, + 0, 0, 58, 0, 16, 0, + 19, 0, 0, 0, 40, 0, + 0, 5, 130, 0, 16, 0, + 24, 0, 0, 0, 10, 0, + 16, 0, 23, 0, 0, 0, + 33, 0, 0, 7, 34, 0, + 16, 0, 23, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 43, 0, + 0, 5, 66, 0, 16, 0, + 23, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 23, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 34, 0, 16, 0, 16, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 48, 0, + 0, 1, 80, 0, 0, 7, + 18, 0, 16, 0, 25, 0, + 0, 0, 58, 0, 16, 0, + 23, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 3, 0, 4, 3, 10, 0, + 16, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 25, 0, 0, 0, + 58, 0, 16, 0, 23, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 85, 0, + 0, 8, 18, 0, 16, 0, + 25, 0, 0, 0, 10, 144, + 144, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 25, 0, 0, 0, + 1, 0, 0, 7, 18, 0, + 16, 0, 25, 0, 0, 0, + 10, 0, 16, 0, 25, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 32, 0, + 0, 7, 34, 0, 16, 0, + 25, 0, 0, 0, 10, 0, + 16, 0, 25, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 25, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 26, 0, + 0, 0, 58, 0, 16, 0, + 23, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 242, 0, 16, 0, 26, 0, + 0, 0, 70, 14, 16, 0, + 18, 0, 0, 0, 70, 14, + 16, 0, 26, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 98, 0, 16, 0, + 25, 0, 0, 0, 6, 1, + 16, 0, 17, 0, 0, 0, + 6, 1, 16, 0, 26, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 25, 0, + 0, 0, 42, 0, 16, 0, + 25, 0, 0, 0, 26, 0, + 16, 0, 25, 0, 0, 0, + 35, 0, 0, 9, 34, 0, + 16, 0, 25, 0, 0, 0, + 42, 0, 16, 0, 17, 0, + 0, 0, 42, 0, 16, 0, + 26, 0, 0, 0, 26, 0, + 16, 0, 25, 0, 0, 0, + 35, 0, 0, 9, 34, 0, + 16, 0, 25, 0, 0, 0, + 58, 0, 16, 0, 17, 0, + 0, 0, 58, 0, 16, 0, + 26, 0, 0, 0, 26, 0, + 16, 0, 25, 0, 0, 0, + 33, 0, 0, 7, 66, 0, + 16, 0, 25, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 25, 0, 0, 0, 60, 0, + 0, 7, 66, 0, 16, 0, + 25, 0, 0, 0, 58, 0, + 16, 0, 11, 0, 0, 0, + 42, 0, 16, 0, 25, 0, + 0, 0, 34, 0, 0, 7, + 130, 0, 16, 0, 25, 0, + 0, 0, 26, 0, 16, 0, + 25, 0, 0, 0, 26, 0, + 16, 0, 6, 0, 0, 0, + 43, 0, 0, 5, 34, 0, + 16, 0, 25, 0, 0, 0, + 26, 0, 16, 0, 25, 0, + 0, 0, 56, 0, 0, 7, + 34, 0, 16, 0, 25, 0, + 0, 0, 26, 0, 16, 0, + 25, 0, 0, 0, 1, 64, + 0, 0, 253, 255, 125, 66, + 14, 0, 0, 7, 34, 0, + 16, 0, 25, 0, 0, 0, + 26, 0, 16, 0, 25, 0, + 0, 0, 58, 0, 16, 0, + 12, 0, 0, 0, 28, 0, + 0, 5, 34, 0, 16, 0, + 25, 0, 0, 0, 26, 0, + 16, 0, 25, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 25, 0, 0, 0, + 10, 0, 16, 0, 19, 0, + 0, 0, 26, 0, 16, 0, + 25, 0, 0, 0, 55, 0, + 0, 10, 34, 0, 16, 0, + 25, 0, 0, 0, 58, 0, + 16, 0, 25, 0, 0, 0, + 58, 144, 144, 0, 26, 0, + 16, 0, 25, 0, 0, 0, + 26, 0, 16, 0, 19, 0, + 0, 0, 55, 0, 0, 9, + 34, 0, 16, 0, 25, 0, + 0, 0, 42, 0, 16, 0, + 25, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 25, 0, + 0, 0, 18, 0, 0, 1, + 32, 0, 0, 7, 66, 0, + 16, 0, 25, 0, 0, 0, + 10, 0, 16, 0, 25, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 25, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 26, 0, 0, 0, 58, 0, + 16, 0, 23, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 26, 0, 0, 0, 70, 14, + 16, 0, 21, 0, 0, 0, + 70, 14, 16, 0, 26, 0, + 0, 0, 38, 0, 0, 8, + 0, 208, 0, 0, 194, 0, + 16, 0, 25, 0, 0, 0, + 6, 4, 16, 0, 20, 0, + 0, 0, 6, 4, 16, 0, + 26, 0, 0, 0, 30, 0, + 0, 7, 66, 0, 16, 0, + 25, 0, 0, 0, 58, 0, + 16, 0, 25, 0, 0, 0, + 42, 0, 16, 0, 25, 0, + 0, 0, 35, 0, 0, 9, + 66, 0, 16, 0, 25, 0, + 0, 0, 42, 0, 16, 0, + 20, 0, 0, 0, 42, 0, + 16, 0, 26, 0, 0, 0, + 42, 0, 16, 0, 25, 0, + 0, 0, 35, 0, 0, 9, + 66, 0, 16, 0, 25, 0, + 0, 0, 58, 0, 16, 0, + 20, 0, 0, 0, 58, 0, + 16, 0, 26, 0, 0, 0, + 42, 0, 16, 0, 25, 0, + 0, 0, 33, 0, 0, 7, + 130, 0, 16, 0, 25, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 25, 0, 0, 0, + 60, 0, 0, 7, 130, 0, + 16, 0, 25, 0, 0, 0, + 42, 0, 16, 0, 15, 0, + 0, 0, 58, 0, 16, 0, + 25, 0, 0, 0, 34, 0, + 0, 7, 18, 0, 16, 0, + 26, 0, 0, 0, 42, 0, + 16, 0, 25, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 43, 0, 0, 5, + 66, 0, 16, 0, 25, 0, + 0, 0, 42, 0, 16, 0, + 25, 0, 0, 0, 56, 0, + 0, 7, 66, 0, 16, 0, + 25, 0, 0, 0, 42, 0, + 16, 0, 25, 0, 0, 0, + 1, 64, 0, 0, 253, 255, + 125, 66, 14, 0, 0, 7, + 66, 0, 16, 0, 25, 0, + 0, 0, 42, 0, 16, 0, + 25, 0, 0, 0, 58, 0, + 16, 0, 15, 0, 0, 0, + 28, 0, 0, 5, 66, 0, + 16, 0, 25, 0, 0, 0, + 42, 0, 16, 0, 25, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 25, 0, + 0, 0, 10, 0, 16, 0, + 19, 0, 0, 0, 42, 0, + 16, 0, 25, 0, 0, 0, + 55, 0, 0, 10, 66, 0, + 16, 0, 25, 0, 0, 0, + 10, 0, 16, 0, 26, 0, + 0, 0, 58, 144, 144, 0, + 42, 0, 16, 0, 25, 0, + 0, 0, 26, 0, 16, 0, + 19, 0, 0, 0, 55, 0, + 0, 9, 34, 0, 16, 0, + 25, 0, 0, 0, 58, 0, + 16, 0, 25, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 25, 0, 0, 0, 18, 0, + 0, 1, 167, 0, 0, 9, + 242, 0, 16, 0, 26, 0, + 0, 0, 58, 0, 16, 0, + 23, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 242, 0, 16, 0, 26, 0, + 0, 0, 70, 14, 16, 0, + 24, 0, 0, 0, 70, 14, + 16, 0, 26, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 194, 0, 16, 0, + 25, 0, 0, 0, 6, 4, + 16, 0, 22, 0, 0, 0, + 6, 4, 16, 0, 26, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 25, 0, + 0, 0, 58, 0, 16, 0, + 25, 0, 0, 0, 42, 0, + 16, 0, 25, 0, 0, 0, + 35, 0, 0, 9, 66, 0, + 16, 0, 25, 0, 0, 0, + 42, 0, 16, 0, 22, 0, + 0, 0, 42, 0, 16, 0, + 26, 0, 0, 0, 42, 0, + 16, 0, 25, 0, 0, 0, + 35, 0, 0, 9, 66, 0, + 16, 0, 25, 0, 0, 0, + 58, 0, 16, 0, 22, 0, + 0, 0, 58, 0, 16, 0, + 26, 0, 0, 0, 42, 0, + 16, 0, 25, 0, 0, 0, + 33, 0, 0, 7, 130, 0, + 16, 0, 25, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 25, 0, 0, 0, 60, 0, + 0, 7, 130, 0, 16, 0, + 25, 0, 0, 0, 26, 0, + 16, 0, 23, 0, 0, 0, + 58, 0, 16, 0, 25, 0, + 0, 0, 34, 0, 0, 7, + 18, 0, 16, 0, 26, 0, + 0, 0, 42, 0, 16, 0, + 25, 0, 0, 0, 26, 0, + 16, 0, 4, 0, 0, 0, + 43, 0, 0, 5, 66, 0, + 16, 0, 25, 0, 0, 0, + 42, 0, 16, 0, 25, 0, + 0, 0, 56, 0, 0, 7, + 66, 0, 16, 0, 25, 0, + 0, 0, 42, 0, 16, 0, + 25, 0, 0, 0, 1, 64, + 0, 0, 253, 255, 125, 66, + 14, 0, 0, 7, 66, 0, + 16, 0, 25, 0, 0, 0, + 42, 0, 16, 0, 25, 0, + 0, 0, 42, 0, 16, 0, + 23, 0, 0, 0, 28, 0, + 0, 5, 66, 0, 16, 0, + 25, 0, 0, 0, 42, 0, + 16, 0, 25, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 25, 0, 0, 0, + 10, 0, 16, 0, 19, 0, + 0, 0, 42, 0, 16, 0, + 25, 0, 0, 0, 55, 0, + 0, 10, 66, 0, 16, 0, + 25, 0, 0, 0, 10, 0, + 16, 0, 26, 0, 0, 0, + 58, 144, 144, 0, 42, 0, + 16, 0, 25, 0, 0, 0, + 26, 0, 16, 0, 19, 0, + 0, 0, 55, 0, 0, 9, + 34, 0, 16, 0, 25, 0, + 0, 0, 58, 0, 16, 0, + 25, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 25, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 30, 0, + 0, 7, 34, 0, 16, 0, + 25, 0, 0, 0, 42, 0, + 16, 0, 19, 0, 0, 0, + 26, 0, 16, 0, 25, 0, + 0, 0, 30, 0, 0, 10, + 66, 0, 16, 0, 25, 0, + 0, 0, 1, 64, 0, 0, + 64, 0, 0, 0, 10, 144, + 208, 128, 65, 0, 0, 0, + 64, 0, 0, 0, 26, 0, + 16, 0, 25, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 25, 0, 0, 0, + 10, 0, 16, 0, 25, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 7, 18, 0, 16, 0, + 26, 0, 0, 0, 10, 48, + 32, 4, 0, 0, 0, 0, + 10, 0, 16, 0, 25, 0, + 0, 0, 54, 0, 0, 8, + 34, 0, 16, 0, 26, 0, + 0, 0, 10, 48, 32, 6, + 0, 0, 0, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 25, 0, 0, 0, 54, 0, + 0, 8, 66, 0, 16, 0, + 26, 0, 0, 0, 10, 48, + 32, 6, 0, 0, 0, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 25, 0, 0, 0, + 54, 0, 0, 7, 18, 0, + 16, 0, 27, 0, 0, 0, + 26, 48, 32, 4, 0, 0, + 0, 0, 10, 0, 16, 0, + 25, 0, 0, 0, 54, 0, + 0, 8, 34, 0, 16, 0, + 27, 0, 0, 0, 26, 48, + 32, 6, 0, 0, 0, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 25, 0, 0, 0, + 54, 0, 0, 8, 66, 0, + 16, 0, 27, 0, 0, 0, + 26, 48, 32, 6, 0, 0, + 0, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 25, 0, + 0, 0, 38, 0, 0, 10, + 0, 208, 0, 0, 178, 0, + 16, 0, 25, 0, 0, 0, + 70, 8, 16, 0, 27, 0, + 0, 0, 6, 144, 208, 0, + 64, 0, 0, 0, 26, 0, + 16, 0, 25, 0, 0, 0, + 35, 0, 0, 9, 114, 0, + 16, 0, 25, 0, 0, 0, + 166, 10, 16, 0, 25, 0, + 0, 0, 70, 2, 16, 0, + 26, 0, 0, 0, 70, 3, + 16, 0, 25, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 25, 0, 0, 0, + 70, 2, 16, 0, 25, 0, + 0, 0, 2, 64, 0, 0, + 32, 0, 0, 0, 32, 0, + 0, 0, 32, 0, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 178, 0, 16, 0, + 25, 0, 0, 0, 70, 8, + 16, 0, 25, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 26, 0, + 0, 0, 58, 0, 16, 0, + 23, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 114, 0, 16, 0, 27, 0, + 0, 0, 70, 3, 16, 0, + 25, 0, 0, 0, 70, 2, + 16, 0, 26, 0, 0, 0, + 54, 0, 0, 5, 66, 0, + 16, 0, 25, 0, 0, 0, + 10, 0, 16, 0, 26, 0, + 0, 0, 55, 0, 0, 9, + 146, 0, 16, 0, 27, 0, + 0, 0, 6, 0, 16, 0, + 27, 0, 0, 0, 166, 2, + 16, 0, 25, 0, 0, 0, + 6, 8, 16, 0, 25, 0, + 0, 0, 54, 0, 0, 5, + 82, 0, 16, 0, 25, 0, + 0, 0, 86, 6, 16, 0, + 26, 0, 0, 0, 55, 0, + 0, 9, 242, 0, 16, 0, + 25, 0, 0, 0, 86, 10, + 16, 0, 27, 0, 0, 0, + 70, 14, 16, 0, 25, 0, + 0, 0, 22, 11, 16, 0, + 25, 0, 0, 0, 79, 0, + 0, 7, 18, 0, 16, 0, + 26, 0, 0, 0, 1, 64, + 0, 0, 255, 0, 0, 0, + 58, 0, 16, 0, 26, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 14, 0, + 0, 0, 58, 0, 16, 0, + 26, 0, 0, 0, 55, 0, + 0, 9, 146, 0, 16, 0, + 26, 0, 0, 0, 6, 0, + 16, 0, 26, 0, 0, 0, + 86, 1, 16, 0, 14, 0, + 0, 0, 6, 4, 16, 0, + 14, 0, 0, 0, 40, 0, + 0, 5, 18, 0, 16, 0, + 28, 0, 0, 0, 58, 0, + 16, 0, 27, 0, 0, 0, + 40, 0, 0, 5, 98, 0, + 16, 0, 28, 0, 0, 0, + 86, 7, 16, 0, 25, 0, + 0, 0, 40, 0, 0, 5, + 130, 0, 16, 0, 28, 0, + 0, 0, 10, 0, 16, 0, + 26, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 26, 0, 0, 0, 10, 0, + 16, 0, 27, 0, 0, 0, + 54, 0, 0, 5, 98, 0, + 16, 0, 26, 0, 0, 0, + 6, 2, 16, 0, 25, 0, + 0, 0, 30, 0, 0, 7, + 242, 0, 16, 0, 25, 0, + 0, 0, 70, 14, 16, 0, + 28, 0, 0, 0, 70, 14, + 16, 0, 26, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 50, 0, 16, 0, + 25, 0, 0, 0, 70, 0, + 16, 0, 25, 0, 0, 0, + 70, 0, 16, 0, 25, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 14, 0, + 0, 0, 26, 0, 16, 0, + 25, 0, 0, 0, 10, 0, + 16, 0, 25, 0, 0, 0, + 35, 0, 0, 9, 18, 0, + 16, 0, 14, 0, 0, 0, + 42, 0, 16, 0, 25, 0, + 0, 0, 42, 0, 16, 0, + 25, 0, 0, 0, 10, 0, + 16, 0, 14, 0, 0, 0, + 86, 0, 0, 5, 18, 0, + 16, 0, 14, 0, 0, 0, + 10, 0, 16, 0, 14, 0, + 0, 0, 86, 0, 0, 5, + 18, 0, 16, 0, 25, 0, + 0, 0, 58, 0, 16, 0, + 25, 0, 0, 0, 56, 0, + 0, 7, 18, 0, 16, 0, + 25, 0, 0, 0, 10, 0, + 16, 0, 25, 0, 0, 0, + 10, 0, 16, 0, 25, 0, + 0, 0, 50, 0, 0, 10, + 18, 0, 16, 0, 14, 0, + 0, 0, 10, 0, 16, 0, + 25, 0, 0, 0, 42, 128, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 14, 0, 0, 0, + 28, 0, 0, 5, 18, 0, + 16, 0, 14, 0, 0, 0, + 10, 0, 16, 0, 14, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 16, 0, + 0, 0, 10, 0, 16, 0, + 14, 0, 0, 0, 26, 0, + 16, 0, 16, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 23, 0, 0, 0, + 58, 0, 16, 0, 23, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 79, 0, 0, 7, + 66, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 16, 0, 0, 0, 26, 0, + 16, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 50, 0, + 16, 0, 15, 0, 0, 0, + 166, 10, 16, 0, 3, 0, + 0, 0, 70, 0, 16, 0, + 16, 0, 0, 0, 70, 0, + 16, 0, 15, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 16, 0, 0, 0, + 10, 0, 16, 0, 16, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 26, 0, 16, 0, + 15, 0, 0, 0, 168, 0, + 0, 8, 18, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 10, 0, 16, 0, 15, 0, + 0, 0, 21, 0, 0, 1, + 190, 24, 0, 1, 31, 0, + 4, 3, 26, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 8, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 32, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 79, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 18, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 31, 0, 4, 3, 10, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 168, 0, + 0, 8, 18, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 32, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 21, 0, 0, 1, 21, 0, + 0, 1, 31, 0, 4, 3, + 42, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 8, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 79, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 0, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 168, 0, + 0, 8, 18, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 10, 0, 16, 0, 5, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 31, 0, + 4, 3, 58, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 8, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 32, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 79, 0, 0, 7, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 18, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 79, 0, 0, 9, 98, 0, + 16, 0, 0, 0, 0, 0, + 6, 64, 2, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 168, 0, + 0, 8, 18, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 32, 0, 0, 0, 10, 0, + 16, 0, 4, 0, 0, 0, + 21, 0, 0, 1, 21, 0, + 0, 1, 31, 0, 4, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 8, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 24, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 79, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 0, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 168, 0, + 0, 8, 18, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 24, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 168, 0, 0, 8, 18, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 21, 0, 0, 1, + 167, 0, 0, 9, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 6, 112, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 24, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 8, + 130, 0, 16, 0, 2, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 128, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 18, 0, + 0, 1, 167, 0, 0, 9, + 242, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 126, 16, 0, 1, 0, + 0, 0, 21, 0, 0, 1, + 168, 0, 0, 9, 242, 224, + 17, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 21, 0, 0, 1, 62, 0, + 0, 1 +}; diff --git a/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_TryMode137CS.inc b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_TryMode137CS.inc new file mode 100644 index 0000000..9a78e45 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_TryMode137CS.inc @@ -0,0 +1,3961 @@ +#if 0 +// +// Generated by Microsoft (R) D3D Shader Disassembler +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Input +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Output +cs_4_0 +dcl_globalFlags refactoringAllowed +dcl_immediateConstantBuffer { { 0x0000cccc, 15, 0, 0}, + { 0x00008888, 15, 0, 0}, + { 0x0000eeee, 15, 0, 0}, + { 0x0000ecc8, 15, 0, 1}, + { 0x0000c880, 15, 0, 1}, + { 0x0000feec, 15, 0, 1}, + { 0x0000fec8, 15, 0, 1}, + { 0x0000ec80, 15, 0, 2}, + { 0x0000c800, 15, 0, 2}, + { 0x0000ffec, 15, 0, 2}, + { 0x0000fe80, 15, 0, 2}, + { 0x0000e800, 15, 0, 2}, + { 0x0000ffe8, 15, 0, 3}, + { 0x0000ff00, 15, 0, 3}, + { 0x0000fff0, 15, 0, 3}, + { 0x0000f000, 15, 0, 3}, + { 0x0000f710, 15, 0, 4}, + { 142, 2, 0, 4}, + { 0x00007100, 8, 0, 4}, + { 2254, 2, 0, 4}, + { 140, 2, 0, 5}, + { 0x00007310, 8, 0, 5}, + { 0x00003100, 8, 0, 5}, + { 0x00008cce, 15, 0, 5}, + { 2188, 2, 0, 6}, + { 0x00003110, 8, 0, 6}, + { 0x00006666, 2, 0, 6}, + { 0x0000366c, 2, 0, 6}, + { 6120, 8, 0, 6}, + { 4080, 8, 0, 7}, + { 0x0000718e, 2, 0, 7}, + { 0x0000399c, 2, 0, 7}, + { 0x0000aaaa, 15, 0, 7}, + { 0x0000f0f0, 15, 0, 8}, + { 0x00005a5a, 6, 0, 8}, + { 0x000033cc, 8, 0, 8}, + { 0x00003c3c, 2, 0, 8}, + { 0x000055aa, 8, 0, 9}, + { 0x00009696, 15, 0, 9}, + { 0x0000a55a, 15, 0, 9}, + { 0x000073ce, 2, 0, 9}, + { 5064, 8, 0, 10}, + { 0x0000324c, 2, 0, 10}, + { 0x00003bdc, 2, 0, 10}, + { 0x00006996, 2, 0, 10}, + { 0x0000c33c, 15, 0, 10}, + { 0x00009966, 15, 0, 11}, + { 1632, 6, 0, 11}, + { 626, 6, 0, 11}, + { 1252, 2, 0, 11}, + { 0x00004e40, 6, 0, 12}, + { 0x00002720, 8, 0, 12}, + { 0x0000c936, 15, 0, 12}, + { 0x0000936c, 15, 0, 12}, + { 0x000039c6, 2, 0, 13}, + { 0x0000639c, 2, 0, 13}, + { 0x00009336, 15, 0, 13}, + { 0x00009cc6, 15, 0, 13}, + { 0x0000817e, 15, 0, 14}, + { 0x0000e718, 15, 0, 14}, + { 0x0000ccf0, 15, 0, 14}, + { 4044, 2, 0, 14}, + { 0x00007744, 2, 0, 15}, + { 0x0000ee22, 15, 0, 15}, + { 0, 3, 15, 0}, + { 4, 3, 8, 0}, + { 9, 15, 8, 0}, + { 13, 15, 3, 0}, + { 17, 8, 15, 0}, + { 21, 3, 15, 1}, + { 26, 15, 3, 1}, + { 30, 15, 8, 1}, + { 34, 8, 15, 1}, + { 38, 8, 15, 1}, + { 43, 6, 15, 1}, + { 47, 6, 15, 1}, + { 51, 6, 15, 1}, + { 55, 5, 15, 1}, + { 60, 3, 15, 2}, + { 64, 3, 8, 2}, + { 0, 3, 15, 2}, + { 9, 3, 8, 2}, + { 18, 8, 15, 2}, + { 27, 15, 3, 2}, + { 37, 3, 15, 2}, + { 46, 3, 8, 2}, + { 55, 6, 15, 2}, + { 64, 10, 8, 3}, + { 0, 5, 3, 3}, + { 0, 8, 15, 3}, + { 0, 8, 6, 3}, + { 0, 6, 10, 3}, + { 0, 8, 15, 3}, + { 0, 5, 15, 3}, + { 0, 15, 10, 3}, + { 0, 15, 8, 3}, + { 0, 8, 15, 3}, + { 21, 15, 3, 4}, + { 43, 3, 15, 4}, + { 64, 5, 10, 4}, + { 0, 6, 10, 4}, + { 0, 10, 8, 4}, + { 0, 8, 9, 4}, + { 0, 15, 10, 4}, + { 0, 15, 6, 4}, + { 0, 3, 15, 4}, + { 0, 15, 8, 5}, + { 0, 5, 15, 5}, + { 0, 15, 3, 5}, + { 0, 15, 6, 5}, + { 0, 15, 6, 5}, + { 0, 15, 8, 5}, + { 0, 3, 15, 5}, + { 0, 15, 3, 5}, + { 0, 5, 15, 5}, + { 0, 5, 15, 6}, + { 0, 5, 15, 6}, + { 0, 8, 15, 6}, + { 0, 5, 15, 6}, + { 0, 10, 15, 6}, + { 0, 5, 15, 6}, + { 0, 10, 15, 6}, + { 0, 8, 15, 6}, + { 0, 13, 15, 6}, + { 0, 15, 3, 7}, + { 0, 12, 15, 7}, + { 0, 3, 15, 7}, + { 0, 3, 8, 7}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 1}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 2}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3}, + { 0, 0, 0, 3} } +dcl_constantbuffer CB0[2], immediateIndexed +dcl_resource_texture2d (float,float,float,float) t0 +dcl_resource_structured t1, 16 +dcl_uav_structured u0, 16 +dcl_input vThreadIDInGroupFlattened +dcl_input vThreadGroupID.x +dcl_temps 29 +dcl_indexableTemp x0[8], 4 +dcl_tgsm_structured g0, 100, 64 +dcl_thread_group 64, 1, 1 +iadd r0.x, vThreadGroupID.x, cb0[1].x +ult r1.xyzw, vThreadIDInGroupFlattened.xxxx, l(16, 32, 8, 4) +if_nz r1.x + udiv r0.y, null, r0.x, cb0[0].y + imad r0.z, -r0.y, cb0[0].y, r0.x + ishl r0.z, r0.z, l(2) + ishl r0.y, r0.y, l(2) + and r0.w, vThreadIDInGroupFlattened.x, l(3) + iadd r2.x, r0.w, r0.z + ushr r0.z, vThreadIDInGroupFlattened.x, l(2) + iadd r2.y, r0.z, r0.y + mov r2.zw, l(0,0,0,0) + ld r2.xyzw, r2.xyzw, t0.xyzw + mul r2.xyzw, r2.xyzw, l(255.000000, 255.000000, 255.000000, 255.000000) + ftou r2.xyzw, r2.xyzw + umin r2.xyzw, r2.xyzw, l(255, 255, 255, 255) + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(0), r2.xyzw +endif +sync_g_t +mov x0[0].x, l(-1) +mov x0[1].x, l(-1) +mov x0[2].x, l(-1) +mov x0[3].x, l(-1) +mov x0[0].y, l(0) +mov x0[1].y, l(0) +mov x0[2].y, l(0) +mov x0[3].y, l(0) +mov x0[4].x, l(-1) +mov x0[5].x, l(-1) +mov x0[6].x, l(-1) +mov x0[7].x, l(-1) +mov x0[4].y, l(0) +mov x0[5].y, l(0) +mov x0[6].y, l(0) +mov x0[7].y, l(0) +mov r0.y, l(0) +loop + uge r0.z, r0.y, l(16) + breakc_nz r0.z + ld_structured r2.xyzw, r0.y, l(0), g0.xyzw + mov r0.z, vThreadIDInGroupFlattened.x + ushr r0.z, icb[r0.z + 0].x, r0.y + and r0.z, r0.z, l(1) + ieq r0.z, r0.z, l(1) + if_nz r0.z + mov r3.x, x0[4].x + mov r3.y, x0[5].x + mov r3.z, x0[6].x + mov r3.w, x0[7].x + umin r3.xyzw, r2.xyzw, r3.xyzw + mov x0[4].x, r3.x + mov x0[5].x, r3.y + mov x0[6].x, r3.z + mov x0[7].x, r3.w + mov r3.x, x0[4].y + mov r3.y, x0[5].y + mov r3.z, x0[6].y + mov r3.w, x0[7].y + umax r3.xyzw, r2.xyzw, r3.xyzw + mov x0[4].y, r3.x + mov x0[5].y, r3.y + mov x0[6].y, r3.z + mov x0[7].y, r3.w + else + mov r3.x, x0[0].x + mov r3.y, x0[1].x + mov r3.z, x0[2].x + mov r3.w, x0[3].x + umin r3.xyzw, r2.xyzw, r3.xyzw + mov x0[0].x, r3.x + mov x0[1].x, r3.y + mov x0[2].x, r3.z + mov x0[3].x, r3.w + mov r3.x, x0[0].y + mov r3.y, x0[1].y + mov r3.z, x0[2].y + mov r3.w, x0[3].y + umax r2.xyzw, r2.xyzw, r3.xyzw + mov x0[0].y, r2.x + mov x0[1].y, r2.y + mov x0[2].y, r2.z + mov x0[3].y, r2.w + endif + iadd r0.y, r0.y, l(1) +endloop +mov r2.x, x0[0].x +mov r2.y, x0[1].x +mov r2.z, x0[2].x +mov r2.w, x0[3].x +mov r3.x, x0[0].y +mov r3.y, x0[1].y +mov r3.z, x0[2].y +mov r3.w, x0[3].y +mov r4.x, x0[4].x +mov r4.y, x0[5].x +mov r4.z, x0[6].x +mov r4.w, x0[7].x +mov r5.x, x0[4].y +mov r5.y, x0[5].y +mov r5.z, x0[6].y +mov r5.w, x0[7].y +ieq r0.y, cb0[0].w, l(1) +movc r0.y, r0.y, l(4), l(16) +iadd r6.xyz, r2.xyzx, l(1, 1, 1, 0) +umin r6.xyz, r6.xyzx, l(255, 255, 255, 0) +ushr r6.xyz, r6.xyzx, l(1) +and r6.xyz, r6.xyzx, l(126, 126, 126, 0) +iadd r7.xyz, r3.xyzx, l(1, 1, 1, 0) +umin r7.xyz, r7.xyzx, l(255, 255, 255, 0) +ushr r7.xyz, r7.xyzx, l(1) +and r7.xyz, r7.xyzx, l(126, 126, 126, 0) +iadd r8.xyz, r4.xyzx, l(1, 1, 1, 0) +and r9.xyz, r2.xyzx, l(-2, -2, -2, 0) +and r10.xyz, r3.xyzx, l(-2, -2, -2, 0) +umin r8.xyz, r8.xyzx, l(255, 255, 255, 0) +iadd r11.xyzw, r2.xyzw, l(2, 2, 2, 2) +umin r11.xyzw, r11.xyzw, l(255, 255, 255, 255) +ushr r11.xyzw, r11.xyzw, l(2) +and r11.xyzw, r11.xyzw, l(62, 62, 62, 62) +iadd r12.xyzw, r3.xyzw, l(2, 2, 2, 2) +umin r12.xyzw, r12.xyzw, l(255, 255, 255, 255) +ushr r12.xyzw, r12.xyzw, l(2) +and r12.xyzw, r12.xyzw, l(62, 62, 62, 62) +ushr r8.xyz, r8.xyzx, l(1) +and r8.xyz, r8.xyzx, l(126, 126, 126, 0) +iadd r13.xyz, r5.xyzx, l(1, 1, 1, 0) +umin r13.xyz, r13.xyzx, l(255, 255, 255, 0) +ushr r13.xyz, r13.xyzx, l(1) +and r13.xyz, r13.xyzx, l(126, 126, 126, 0) +and r14.xyz, r4.xyzx, l(-2, -2, -2, 0) +and r15.xyz, r5.xyzx, l(-2, -2, -2, 0) +iadd r16.xyzw, r4.xyzw, l(2, 2, 2, 2) +umin r16.xyzw, r16.xyzw, l(255, 255, 255, 255) +ushr r16.xyzw, r16.xyzw, l(2) +and r16.xyzw, r16.xyzw, l(62, 62, 62, 62) +iadd r17.xyzw, r5.xyzw, l(2, 2, 2, 2) +umin r17.xyzw, r17.xyzw, l(255, 255, 255, 255) +ushr r17.xyzw, r17.xyzw, l(2) +and r17.xyzw, r17.xyzw, l(62, 62, 62, 62) +mov r0.z, cb0[0].w +mov r0.w, l(0) +mov r18.y, l(-1) +mov r19.x, l(0) +loop + uge r6.w, r19.x, r0.y + breakc_nz r6.w + mov x0[0].x, r2.x + mov x0[1].x, r2.y + mov x0[2].x, r2.z + mov x0[3].x, r2.w + mov x0[0].y, r3.x + mov x0[1].y, r3.y + mov x0[2].y, r3.z + mov x0[3].y, r3.w + mov x0[4].x, r4.x + mov x0[5].x, r4.y + mov x0[6].x, r4.z + mov x0[7].x, r4.w + mov x0[4].y, r5.x + mov x0[5].y, r5.y + mov x0[6].y, r5.z + mov x0[7].y, r5.w + ieq r6.w, r0.z, l(1) + if_nz r6.w + and r6.w, r19.x, l(1) + iadd r20.xyz, r6.wwww, r6.xyzx + ishl r20.xyz, r20.xyzx, l(1) + ushr r21.xyz, r20.xyzx, l(7) + iadd r20.xyz, r20.xyzx, r21.xyzx + iadd r21.xyz, r6.wwww, r7.xyzx + ishl r21.xyz, r21.xyzx, l(1) + ushr r22.xyz, r21.xyzx, l(7) + iadd r21.xyz, r21.xyzx, r22.xyzx + mov x0[0].x, r20.x + mov x0[1].x, r20.y + mov x0[2].x, r20.z + mov x0[3].x, l(255) + mov x0[0].y, r21.x + mov x0[1].y, r21.y + mov x0[2].y, r21.z + mov x0[3].y, l(255) + ushr r6.w, r19.x, l(1) + and r6.w, r6.w, l(1) + iadd r20.xyz, r6.wwww, r8.xyzx + ishl r20.xyz, r20.xyzx, l(1) + ushr r21.xyz, r20.xyzx, l(7) + iadd r20.xyz, r20.xyzx, r21.xyzx + iadd r21.xyz, r6.wwww, r13.xyzx + ishl r21.xyz, r21.xyzx, l(1) + ushr r22.xyz, r21.xyzx, l(7) + iadd r21.xyz, r21.xyzx, r22.xyzx + mov x0[4].x, r20.x + mov x0[5].x, r20.y + mov x0[6].x, r20.z + mov x0[7].x, l(255) + mov x0[4].y, r21.x + mov x0[5].y, r21.y + mov x0[6].y, r21.z + mov x0[7].y, l(255) + else + ieq r6.w, r0.z, l(3) + if_nz r6.w + ushr r19.y, r19.x, l(1) + and r19.zw, r19.xxxy, l(0, 0, 1, 1) + iadd r20.xyz, r9.xyzx, r19.zzzz + iadd r21.xyz, r10.xyzx, r19.wwww + mov x0[0].x, r20.x + mov x0[1].x, r20.y + mov x0[2].x, r20.z + mov x0[3].x, l(255) + mov x0[0].y, r21.x + mov x0[1].y, r21.y + mov x0[2].y, r21.z + mov x0[3].y, l(255) + else + ieq r7.w, r0.z, l(7) + if_nz r7.w + ushr r19.y, r19.x, l(1) + and r19.zw, r19.xxxy, l(0, 0, 1, 1) + iadd r20.xyzw, r11.xyzw, r19.zzzz + ishl r20.xyzw, r20.xyzw, l(2) + ushr r21.xyzw, r20.xyzw, l(6) + iadd r20.xyzw, r20.xyzw, r21.xyzw + iadd r21.xyzw, r12.xyzw, r19.wwww + ishl r21.xyzw, r21.xyzw, l(2) + ushr r22.xyzw, r21.xyzw, l(6) + iadd r21.xyzw, r21.xyzw, r22.xyzw + mov x0[0].x, r20.x + mov x0[1].x, r20.y + mov x0[2].x, r20.z + mov x0[3].x, r20.w + mov x0[0].y, r21.x + mov x0[1].y, r21.y + mov x0[2].y, r21.z + mov x0[3].y, r21.w + endif + endif + if_nz r6.w + ushr r20.x, r19.x, l(2) + ushr r20.y, r19.x, l(3) + and r19.zw, r20.xxxy, l(0, 0, 1, 1) + iadd r20.xyz, r14.xyzx, r19.zzzz + iadd r21.xyz, r15.xyzx, r19.wwww + mov x0[4].x, r20.x + mov x0[5].x, r20.y + mov x0[6].x, r20.z + mov x0[7].x, l(255) + mov x0[4].y, r21.x + mov x0[5].y, r21.y + mov x0[6].y, r21.z + mov x0[7].y, l(255) + else + ieq r6.w, r0.z, l(7) + if_nz r6.w + ushr r20.x, r19.x, l(2) + ushr r20.y, r19.x, l(3) + and r19.zw, r20.xxxy, l(0, 0, 1, 1) + iadd r20.xyzw, r16.xyzw, r19.zzzz + ishl r20.xyzw, r20.xyzw, l(2) + ushr r21.xyzw, r20.xyzw, l(6) + iadd r20.xyzw, r20.xyzw, r21.xyzw + iadd r21.xyzw, r17.xyzw, r19.wwww + ishl r21.xyzw, r21.xyzw, l(2) + ushr r22.xyzw, r21.xyzw, l(6) + iadd r21.xyzw, r21.xyzw, r22.xyzw + mov x0[4].x, r20.x + mov x0[5].x, r20.y + mov x0[6].x, r20.z + mov x0[7].x, r20.w + mov x0[4].y, r21.x + mov x0[5].y, r21.y + mov x0[6].y, r21.z + mov x0[7].y, r21.w + endif + endif + endif + mov r20.x, x0[0].y + mov r20.y, x0[1].y + mov r20.z, x0[2].y + mov r20.w, x0[3].y + mov r6.w, x0[0].x + mov r7.w, x0[1].x + mov r8.w, x0[2].x + mov r9.w, x0[3].x + ineg r21.x, r6.w + ineg r21.y, r7.w + ineg r21.z, r8.w + ineg r21.w, r9.w + iadd r22.xyzw, r20.xyzw, r21.xyzw + mov r23.x, x0[4].y + mov r23.y, x0[5].y + mov r23.z, x0[6].y + mov r23.w, x0[7].y + mov r10.w, x0[4].x + mov r13.w, x0[5].x + mov r14.w, x0[6].x + mov r15.w, x0[7].x + ineg r24.x, r10.w + ineg r24.y, r13.w + ineg r24.z, r14.w + ineg r24.w, r15.w + iadd r23.xyzw, r23.xyzw, r24.xyzw + ine r19.zw, r0.zzzz, l(0, 0, 7, 1) + movc r23.w, r19.z, l(0), r23.w + movc r22.w, r19.z, l(0), r22.w + imul null, r24.xy, r22.xyxx, r22.xyxx + iadd r10.w, r24.y, r24.x + imad r10.w, r22.z, r22.z, r10.w + imad r10.w, r22.w, r22.w, r10.w + imul null, r24.xy, r23.xyxx, r23.xyxx + iadd r13.w, r24.y, r24.x + imad r13.w, r23.z, r23.z, r13.w + imad r13.w, r23.w, r23.w, r13.w + ld_structured r24.xyzw, l(0), l(0), g0.xyzw + iadd r21.xyzw, r21.xyzw, r24.xyzw + imul null, r21.xy, r21.xyxx, r22.xyxx + iadd r14.w, r21.y, r21.x + imad r14.w, r22.z, r21.z, r14.w + imad r14.w, r22.w, r21.w, r14.w + ilt r15.w, l(0), r10.w + ilt r18.w, l(0), r14.w + and r15.w, r15.w, r18.w + itof r14.w, r14.w + mul r14.w, r14.w, l(63.499989) + ftou r14.w, r14.w + ishl r18.w, r10.w, l(5) + ult r14.w, r18.w, r14.w + and r14.w, r14.w, r15.w + ineg r21.xyzw, r22.xyzw + movc r21.xyzw, r14.wwww, r21.xyzw, r22.xyzw + movc r15.w, r14.w, r20.x, r6.w + mov x0[0].x, r15.w + mov r18.w, x0[1].x + movc r18.w, r14.w, r20.y, r18.w + mov x0[1].x, r18.w + mov r20.x, x0[2].x + movc r20.x, r14.w, r20.z, r20.x + mov x0[2].x, r20.x + mov r20.y, x0[3].x + movc r20.y, r14.w, r20.w, r20.y + mov x0[3].x, r20.y + mov r20.z, x0[0].y + movc r6.w, r14.w, r6.w, r20.z + mov x0[0].y, r6.w + mov r6.w, x0[1].y + movc r6.w, r14.w, r7.w, r6.w + mov x0[1].y, r6.w + mov r6.w, x0[2].y + movc r6.w, r14.w, r8.w, r6.w + mov x0[2].y, r6.w + mov r6.w, x0[3].y + movc r6.w, r14.w, r9.w, r6.w + mov x0[3].y, r6.w + mov r6.w, vThreadIDInGroupFlattened.x + mov r7.w, icb[r6.w + 0].y + ld_structured r22.xyzw, r7.w, l(0), g0.xyzw + mov r7.w, x0[4].x + mov r8.w, x0[5].x + mov r9.w, x0[6].x + mov r14.w, x0[7].x + ineg r24.x, r7.w + ineg r24.y, r8.w + ineg r24.z, r9.w + ineg r24.w, r14.w + iadd r22.xyzw, r22.xyzw, r24.xyzw + imul null, r20.zw, r22.xxxy, r23.xxxy + iadd r20.z, r20.w, r20.z + imad r20.z, r23.z, r22.z, r20.z + imad r20.z, r23.w, r22.w, r20.z + ilt r20.w, l(0), r13.w + ilt r22.x, l(0), r20.z + and r20.w, r20.w, r22.x + itof r20.z, r20.z + mul r20.z, r20.z, l(63.499989) + ftou r20.z, r20.z + ishl r22.x, r13.w, l(5) + ult r20.z, r22.x, r20.z + and r20.z, r20.z, r20.w + ineg r22.xyzw, r23.xyzw + movc r22.xyzw, r20.zzzz, r22.xyzw, r23.xyzw + mov r20.w, x0[4].y + mov r23.x, x0[5].y + mov r23.y, x0[6].y + mov r23.z, x0[7].y + movc r20.w, r20.z, r20.w, r7.w + mov x0[4].x, r20.w + mov r23.w, x0[5].x + movc r23.x, r20.z, r23.x, r23.w + mov x0[5].x, r23.x + mov r23.w, x0[6].x + movc r23.y, r20.z, r23.y, r23.w + mov x0[6].x, r23.y + mov r23.w, x0[7].x + movc r23.z, r20.z, r23.z, r23.w + mov x0[7].x, r23.z + mov r23.w, x0[4].y + movc r7.w, r20.z, r7.w, r23.w + mov x0[4].y, r7.w + mov r7.w, x0[5].y + movc r7.w, r20.z, r8.w, r7.w + mov x0[5].y, r7.w + mov r7.w, x0[6].y + movc r7.w, r20.z, r9.w, r7.w + mov x0[6].y, r7.w + mov r7.w, x0[7].y + movc r7.w, r20.z, r14.w, r7.w + mov x0[7].y, r7.w + ineg r24.x, r20.w + ineg r24.yzw, r23.xxyz + ige r7.w, l(0), r13.w + itof r8.w, r13.w + movc r23.xyz, r19.wwww, l(32,128,3,0), l(16,64,7,0) + ineg r25.x, r15.w + ineg r25.y, r18.w + ineg r25.zw, r20.xxxy + ige r9.w, l(0), r10.w + itof r14.w, r10.w + mov r15.w, l(0) + mov r19.y, l(0) + loop + uge r18.w, r15.w, l(16) + breakc_nz r18.w + ushr r18.w, icb[r6.w + 0].x, r15.w + and r18.w, r18.w, l(1) + ieq r19.w, r18.w, l(1) + if_nz r19.w + ld_structured r20.xyzw, r15.w, l(0), g0.xyzw + iadd r20.xyzw, r24.xyzw, r20.xyzw + imul null, r20.xy, r20.xyxx, r22.xyxx + iadd r19.w, r20.y, r20.x + imad r19.w, r22.z, r20.z, r19.w + imad r19.w, r22.w, r20.w, r19.w + ige r20.x, l(0), r19.w + or r20.x, r7.w, r20.x + ilt r20.y, r19.w, r13.w + itof r19.w, r19.w + mul r19.w, r19.w, l(63.499989) + div r19.w, r19.w, r8.w + ftou r19.w, r19.w + iadd r19.w, r19.w, r23.y + movc r19.w, r20.y, icb[r19.w + 0].w, r23.z + movc r19.w, r20.x, l(0), r19.w + else + ld_structured r20.xyzw, r15.w, l(0), g0.xyzw + iadd r20.xyzw, r25.xyzw, r20.xyzw + imul null, r20.xy, r20.xyxx, r21.xyxx + iadd r20.x, r20.y, r20.x + imad r20.x, r21.z, r20.z, r20.x + imad r20.x, r21.w, r20.w, r20.x + ige r20.y, l(0), r20.x + or r20.y, r9.w, r20.y + ilt r20.z, r20.x, r10.w + itof r20.x, r20.x + mul r20.x, r20.x, l(63.499989) + div r20.x, r20.x, r14.w + ftou r20.x, r20.x + iadd r20.x, r20.x, r23.y + movc r20.x, r20.z, icb[r20.x + 0].w, r23.z + movc r19.w, r20.y, l(0), r20.x + endif + iadd r19.w, r19.w, r23.x + iadd r20.x, l(64), -icb[r19.w + 64].x + ishl r18.w, r18.w, l(2) + mov r26.x, x0[r18.w + 0].x + mov r26.y, x0[r18.w + 1].x + mov r26.z, x0[r18.w + 2].x + mov r26.w, x0[r18.w + 3].x + mov r27.x, x0[r18.w + 0].y + mov r27.y, x0[r18.w + 1].y + mov r27.z, x0[r18.w + 2].y + mov r27.w, x0[r18.w + 3].y + imul null, r27.xyzw, r27.xyzw, icb[r19.w + 64].xxxx + imad r20.xyzw, r20.xxxx, r26.xyzw, r27.xyzw + iadd r20.xyzw, r20.xyzw, l(32, 32, 32, 32) + ushr r20.xyzw, r20.xzyw, l(6) + movc r20.w, r19.z, l(255), r20.w + ld_structured r26.xyzw, r15.w, l(0), g0.xyzw + ult r27.xyz, r20.xzyx, r26.xyzx + mov r28.xz, r26.xxyx + mov r28.yw, r20.xxxz + movc r28.xyzw, r27.xxyy, r28.xyzw, r28.yxwz + mov r20.xz, r26.zzwz + movc r20.xy, r27.zzzz, r20.xyxx, r20.yxyy + ult r18.w, r20.w, r26.w + movc r26.xw, r18.wwww, r20.wwwz, r20.zzzw + ineg r27.xy, r28.ywyy + ineg r27.z, r20.y + ineg r27.w, r26.x + mov r26.xy, r28.xzxx + mov r26.z, r20.x + iadd r20.xyzw, r27.xyzw, r26.xyzw + imul null, r20.xy, r20.xyxx, r20.xyxx + iadd r18.w, r20.y, r20.x + imad r18.w, r20.z, r20.z, r18.w + utof r18.w, r18.w + utof r19.w, r20.w + mul r19.w, r19.w, r19.w + mad r18.w, r19.w, cb0[1].z, r18.w + ftou r18.w, r18.w + iadd r19.y, r18.w, r19.y + iadd r15.w, r15.w, l(1) + endloop + ult r6.w, r19.y, r18.y + mov r18.x, r0.w + movc r18.xy, r6.wwww, r19.xyxx, r18.xyxx + iadd r19.x, r19.x, l(1) + mov r0.w, r18.x +endloop +mov r18.x, cb0[0].w +mov r18.z, vThreadIDInGroupFlattened.x +store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(16), r18.yxzy +store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r0.w +sync_g_t +if_nz r1.y + iadd r0.y, vThreadIDInGroupFlattened.x, l(32) + ld_structured r2.yzw, r0.y, l(16), g0.xxyz + ld_structured r3.x, r0.y, l(32), g0.xxxx + ult r0.z, r2.y, r18.y + if_nz r0.z + ld_structured r2.x, r0.y, l(16), g0.xxxx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(16), r2.xzwx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r3.x + endif +endif +if_nz r1.x + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(16) + ld_structured r3.yzw, r0.y, l(16), g0.xxyz + ld_structured r4.x, r0.y, l(32), g0.xxxx + ult r0.z, r3.y, r2.x + if_nz r0.z + ld_structured r3.x, r0.y, l(16), g0.xxxx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(16), r3.xzwx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r4.x + endif +endif +if_nz r1.z + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(8) + ld_structured r3.yzw, r0.y, l(16), g0.xxyz + ld_structured r4.x, r0.y, l(32), g0.xxxx + ult r0.z, r3.y, r2.x + if_nz r0.z + ld_structured r3.x, r0.y, l(16), g0.xxxx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(16), r3.xzwx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r4.x + endif +endif +if_nz r1.w + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(4) + ld_structured r2.yzw, r0.y, l(16), g0.xxyz + ld_structured r3.x, r0.y, l(32), g0.xxxx + ult r0.z, r2.y, r1.x + if_nz r0.z + ld_structured r2.x, r0.y, l(16), g0.xxxx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(16), r2.xzwx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r3.x + endif +endif +ult r0.yz, vThreadIDInGroupFlattened.xxxx, l(0, 2, 1, 0) +if_nz r0.y + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(2) + ld_structured r2.yzw, r0.y, l(16), g0.xxyz + ld_structured r3.x, r0.y, l(32), g0.xxxx + ult r0.w, r2.y, r1.x + if_nz r0.w + ld_structured r2.x, r0.y, l(16), g0.xxxx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(16), r2.xzwx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r3.x + endif +endif +if_nz r0.z + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(1) + ld_structured r2.yzw, r0.y, l(16), g0.xxyz + ld_structured r3.x, r0.y, l(32), g0.xxxx + ult r0.z, r2.y, r1.x + if_nz r0.z + ld_structured r2.x, r0.y, l(16), g0.xxxx + store_structured g0.xyz, vThreadIDInGroupFlattened.x, l(16), r2.xzwx + store_structured g0.x, vThreadIDInGroupFlattened.x, l(32), r3.x + endif + ld_structured r1.x, r0.x, l(0), t1.xxxx + ld_structured r2.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + ult r0.y, r2.x, r1.x + if_nz r0.y + ld_structured r1.xyz, vThreadIDInGroupFlattened.x, l(16), g0.xyzx + ld_structured r1.w, vThreadIDInGroupFlattened.x, l(32), g0.xxxx + else + ld_structured r1.xyzw, r0.x, l(0), t1.xyzw + endif + store_structured u0.xyzw, r0.x, l(0), r1.xyzw +endif +ret +// Approximately 0 instruction slots used +#endif + +const BYTE BC7Encode_TryMode137CS[] = +{ + 68, 88, 66, 67, 24, 142, + 44, 233, 135, 73, 185, 32, + 139, 70, 101, 2, 121, 203, + 167, 180, 1, 0, 0, 0, + 144, 73, 0, 0, 3, 0, + 0, 0, 44, 0, 0, 0, + 60, 0, 0, 0, 76, 0, + 0, 0, 73, 83, 71, 78, + 8, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 79, 83, 71, 78, 8, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 83, 72, + 69, 88, 60, 73, 0, 0, + 64, 0, 5, 0, 79, 18, + 0, 0, 106, 8, 0, 1, + 53, 24, 0, 0, 2, 3, + 0, 0, 204, 204, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 136, 136, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 238, 238, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 200, 236, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 128, 200, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 236, 254, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 200, 254, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 128, 236, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 200, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 236, 255, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 128, 254, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 232, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 232, 255, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 255, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 240, 255, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 240, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 16, 247, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 142, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 113, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 206, 8, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 140, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 16, 115, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 0, 49, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 206, 140, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 140, 8, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 16, 49, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 102, 102, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 108, 54, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 232, 23, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 240, 15, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 142, 113, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 156, 57, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 170, 170, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 240, 240, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 90, 90, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 204, 51, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 60, 60, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 170, 85, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 9, 0, 0, 0, 150, 150, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 9, 0, + 0, 0, 90, 165, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 9, 0, 0, 0, + 206, 115, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 9, 0, 0, 0, 200, 19, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 76, 50, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 220, 59, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 0, 0, 150, 105, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 60, 195, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 102, 153, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 11, 0, 0, 0, 96, 6, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 11, 0, + 0, 0, 114, 2, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 11, 0, 0, 0, + 228, 4, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 11, 0, 0, 0, 64, 78, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 12, 0, + 0, 0, 32, 39, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 12, 0, 0, 0, + 54, 201, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 12, 0, 0, 0, 108, 147, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 12, 0, + 0, 0, 198, 57, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 13, 0, 0, 0, + 156, 99, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 13, 0, 0, 0, 54, 147, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 13, 0, + 0, 0, 198, 156, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 13, 0, 0, 0, + 126, 129, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 14, 0, 0, 0, 24, 231, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 14, 0, + 0, 0, 240, 204, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 14, 0, 0, 0, + 204, 15, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 14, 0, 0, 0, 68, 119, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 34, 238, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 3, 0, 0, 0, + 8, 0, 0, 0, 0, 0, + 0, 0, 9, 0, 0, 0, + 15, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 13, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 17, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 0, 0, + 0, 0, 21, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 1, 0, 0, 0, + 26, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 0, 15, 0, 0, 0, + 8, 0, 0, 0, 1, 0, + 0, 0, 34, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 1, 0, 0, 0, + 38, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 1, 0, 0, 0, 43, 0, + 0, 0, 6, 0, 0, 0, + 15, 0, 0, 0, 1, 0, + 0, 0, 47, 0, 0, 0, + 6, 0, 0, 0, 15, 0, + 0, 0, 1, 0, 0, 0, + 51, 0, 0, 0, 6, 0, + 0, 0, 15, 0, 0, 0, + 1, 0, 0, 0, 55, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 1, 0, + 0, 0, 60, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 2, 0, 0, 0, + 64, 0, 0, 0, 3, 0, + 0, 0, 8, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 2, 0, + 0, 0, 9, 0, 0, 0, + 3, 0, 0, 0, 8, 0, + 0, 0, 2, 0, 0, 0, + 18, 0, 0, 0, 8, 0, + 0, 0, 15, 0, 0, 0, + 2, 0, 0, 0, 27, 0, + 0, 0, 15, 0, 0, 0, + 3, 0, 0, 0, 2, 0, + 0, 0, 37, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 2, 0, 0, 0, + 46, 0, 0, 0, 3, 0, + 0, 0, 8, 0, 0, 0, + 2, 0, 0, 0, 55, 0, + 0, 0, 6, 0, 0, 0, + 15, 0, 0, 0, 2, 0, + 0, 0, 64, 0, 0, 0, + 10, 0, 0, 0, 8, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 3, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 6, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 10, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 10, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 8, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 21, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 4, 0, 0, 0, 43, 0, + 0, 0, 3, 0, 0, 0, + 15, 0, 0, 0, 4, 0, + 0, 0, 64, 0, 0, 0, + 5, 0, 0, 0, 10, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 10, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 8, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 9, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 10, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 6, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 8, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 3, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 6, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 6, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 8, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 15, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 3, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 15, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 15, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 15, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 15, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 15, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 15, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 15, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 15, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 15, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 13, 0, 0, 0, 15, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 3, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 12, 0, 0, 0, + 15, 0, 0, 0, 7, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 15, 0, + 0, 0, 7, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 8, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 89, 0, 0, 4, + 70, 142, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 88, 24, 0, 4, 0, 112, + 16, 0, 0, 0, 0, 0, + 85, 85, 0, 0, 162, 0, + 0, 4, 0, 112, 16, 0, + 1, 0, 0, 0, 16, 0, + 0, 0, 158, 0, 0, 4, + 0, 224, 17, 0, 0, 0, + 0, 0, 16, 0, 0, 0, + 95, 0, 0, 2, 0, 64, + 2, 0, 95, 0, 0, 2, + 18, 16, 2, 0, 104, 0, + 0, 2, 29, 0, 0, 0, + 105, 0, 0, 4, 0, 0, + 0, 0, 8, 0, 0, 0, + 4, 0, 0, 0, 160, 0, + 0, 5, 0, 240, 17, 0, + 0, 0, 0, 0, 100, 0, + 0, 0, 64, 0, 0, 0, + 155, 0, 0, 4, 64, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 16, + 2, 0, 10, 128, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 79, 0, 0, 9, + 242, 0, 16, 0, 1, 0, + 0, 0, 6, 64, 2, 0, + 2, 64, 0, 0, 16, 0, + 0, 0, 32, 0, 0, 0, + 8, 0, 0, 0, 4, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 1, 0, + 0, 0, 78, 0, 0, 9, + 34, 0, 16, 0, 0, 0, + 0, 0, 0, 208, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 26, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 35, 0, 0, 11, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 128, + 65, 0, 0, 0, 0, 0, + 0, 0, 26, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 6, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 85, 0, + 0, 6, 66, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 8, + 194, 0, 16, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 45, 0, + 0, 7, 242, 0, 16, 0, + 2, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 70, 126, 16, 0, 0, 0, + 0, 0, 56, 0, 0, 10, + 242, 0, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 127, 67, + 0, 0, 127, 67, 0, 0, + 127, 67, 0, 0, 127, 67, + 28, 0, 0, 5, 242, 0, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 2, 0, + 0, 0, 84, 0, 0, 10, + 242, 0, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 2, 0, + 0, 0, 21, 0, 0, 1, + 190, 24, 0, 1, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 255, 255, 255, 255, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 80, 0, + 0, 7, 66, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 3, 0, 4, 3, + 42, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 54, 0, 0, 4, + 66, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 85, 0, 0, 8, 66, 0, + 16, 0, 0, 0, 0, 0, + 10, 144, 144, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 32, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 3, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 66, 0, 16, 0, + 3, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 3, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 84, 0, + 0, 7, 242, 0, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 3, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 54, 0, 0, 6, + 66, 0, 16, 0, 3, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 3, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 83, 0, 0, 7, + 242, 0, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 3, 0, 0, 0, + 18, 0, 0, 1, 54, 0, + 0, 6, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 3, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 66, 0, 16, 0, + 3, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 3, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 84, 0, + 0, 7, 242, 0, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 3, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 54, 0, 0, 6, + 66, 0, 16, 0, 3, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 3, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 83, 0, 0, 7, + 242, 0, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 21, 0, 0, 1, 30, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 22, 0, 0, 1, + 54, 0, 0, 6, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 2, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 2, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 2, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 3, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 4, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 4, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 4, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 4, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 54, 0, 0, 6, 18, 0, + 16, 0, 5, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 54, 0, 0, 6, 34, 0, + 16, 0, 5, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 54, 0, 0, 6, 66, 0, + 16, 0, 5, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 5, 0, 0, 0, + 26, 48, 32, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 32, 0, 0, 8, 34, 0, + 16, 0, 0, 0, 0, 0, + 58, 128, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 55, 0, 0, 9, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 84, 0, 0, 10, 114, 0, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 6, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 126, 0, 0, 0, + 126, 0, 0, 0, 126, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 84, 0, + 0, 10, 114, 0, 16, 0, + 7, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 126, 0, 0, 0, 126, 0, + 0, 0, 126, 0, 0, 0, + 0, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 9, 0, + 0, 0, 70, 2, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 254, 255, 255, 255, + 254, 255, 255, 255, 254, 255, + 255, 255, 0, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 254, 255, 255, 255, 254, 255, + 255, 255, 254, 255, 255, 255, + 0, 0, 0, 0, 84, 0, + 0, 10, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 0, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 11, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 2, 0, 0, 0, + 2, 0, 0, 0, 2, 0, + 0, 0, 2, 0, 0, 0, + 84, 0, 0, 10, 242, 0, + 16, 0, 11, 0, 0, 0, + 70, 14, 16, 0, 11, 0, + 0, 0, 2, 64, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 85, 0, + 0, 7, 242, 0, 16, 0, + 11, 0, 0, 0, 70, 14, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 10, + 242, 0, 16, 0, 11, 0, + 0, 0, 70, 14, 16, 0, + 11, 0, 0, 0, 2, 64, + 0, 0, 62, 0, 0, 0, + 62, 0, 0, 0, 62, 0, + 0, 0, 62, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 12, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 2, 0, 0, 0, 2, 0, + 0, 0, 2, 0, 0, 0, + 2, 0, 0, 0, 84, 0, + 0, 10, 242, 0, 16, 0, + 12, 0, 0, 0, 70, 14, + 16, 0, 12, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 85, 0, 0, 7, + 242, 0, 16, 0, 12, 0, + 0, 0, 70, 14, 16, 0, + 12, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 12, 0, 0, 0, + 70, 14, 16, 0, 12, 0, + 0, 0, 2, 64, 0, 0, + 62, 0, 0, 0, 62, 0, + 0, 0, 62, 0, 0, 0, + 62, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 126, 0, 0, 0, + 126, 0, 0, 0, 126, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 114, 0, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 84, 0, + 0, 10, 114, 0, 16, 0, + 13, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 13, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 13, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 2, 64, 0, 0, + 126, 0, 0, 0, 126, 0, + 0, 0, 126, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 14, 0, 0, 0, 70, 2, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 254, 255, + 255, 255, 254, 255, 255, 255, + 254, 255, 255, 255, 0, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 2, 16, 0, + 5, 0, 0, 0, 2, 64, + 0, 0, 254, 255, 255, 255, + 254, 255, 255, 255, 254, 255, + 255, 255, 0, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 16, 0, 0, 0, + 70, 14, 16, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 2, 0, 0, 0, 2, 0, + 0, 0, 2, 0, 0, 0, + 2, 0, 0, 0, 84, 0, + 0, 10, 242, 0, 16, 0, + 16, 0, 0, 0, 70, 14, + 16, 0, 16, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 85, 0, 0, 7, + 242, 0, 16, 0, 16, 0, + 0, 0, 70, 14, 16, 0, + 16, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 16, 0, 0, 0, + 70, 14, 16, 0, 16, 0, + 0, 0, 2, 64, 0, 0, + 62, 0, 0, 0, 62, 0, + 0, 0, 62, 0, 0, 0, + 62, 0, 0, 0, 30, 0, + 0, 10, 242, 0, 16, 0, + 17, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 2, 64, 0, 0, 2, 0, + 0, 0, 2, 0, 0, 0, + 2, 0, 0, 0, 2, 0, + 0, 0, 84, 0, 0, 10, + 242, 0, 16, 0, 17, 0, + 0, 0, 70, 14, 16, 0, + 17, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 85, 0, 0, 7, 242, 0, + 16, 0, 17, 0, 0, 0, + 70, 14, 16, 0, 17, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 17, 0, 0, 0, 70, 14, + 16, 0, 17, 0, 0, 0, + 2, 64, 0, 0, 62, 0, + 0, 0, 62, 0, 0, 0, + 62, 0, 0, 0, 62, 0, + 0, 0, 54, 0, 0, 6, + 66, 0, 16, 0, 0, 0, + 0, 0, 58, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 18, 0, 0, 0, 1, 64, + 0, 0, 255, 255, 255, 255, + 54, 0, 0, 5, 18, 0, + 16, 0, 19, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 48, 0, 0, 1, + 80, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 10, 0, 16, 0, 19, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 3, 0, + 4, 3, 58, 0, 16, 0, + 6, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 5, 0, 0, 0, 32, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 31, 0, 4, 3, + 58, 0, 16, 0, 6, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 19, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 20, 0, 0, 0, + 246, 15, 16, 0, 6, 0, + 0, 0, 70, 2, 16, 0, + 6, 0, 0, 0, 41, 0, + 0, 7, 114, 0, 16, 0, + 20, 0, 0, 0, 70, 2, + 16, 0, 20, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 21, 0, + 0, 0, 70, 2, 16, 0, + 20, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 20, 0, 0, 0, + 70, 2, 16, 0, 20, 0, + 0, 0, 70, 2, 16, 0, + 21, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 21, 0, 0, 0, 246, 15, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 21, 0, + 0, 0, 70, 2, 16, 0, + 21, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 22, 0, 0, 0, + 70, 2, 16, 0, 21, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 21, 0, 0, 0, 70, 2, + 16, 0, 21, 0, 0, 0, + 70, 2, 16, 0, 22, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 255, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 21, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 26, 0, 16, 0, 21, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 21, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 1, 64, 0, 0, 255, 0, + 0, 0, 85, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 19, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 6, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 20, 0, 0, 0, 246, 15, + 16, 0, 6, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 41, 0, 0, 7, + 114, 0, 16, 0, 20, 0, + 0, 0, 70, 2, 16, 0, + 20, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 21, 0, 0, 0, + 70, 2, 16, 0, 20, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 20, 0, 0, 0, 70, 2, + 16, 0, 20, 0, 0, 0, + 70, 2, 16, 0, 21, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 21, 0, + 0, 0, 246, 15, 16, 0, + 6, 0, 0, 0, 70, 2, + 16, 0, 13, 0, 0, 0, + 41, 0, 0, 7, 114, 0, + 16, 0, 21, 0, 0, 0, + 70, 2, 16, 0, 21, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 22, 0, 0, 0, 70, 2, + 16, 0, 21, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 21, 0, + 0, 0, 70, 2, 16, 0, + 21, 0, 0, 0, 70, 2, + 16, 0, 22, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 20, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 20, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 255, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 10, 0, + 16, 0, 21, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 26, 0, + 16, 0, 21, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 21, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 255, 0, 0, 0, + 18, 0, 0, 1, 32, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 31, 0, 4, 3, + 58, 0, 16, 0, 6, 0, + 0, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 19, 0, + 0, 0, 10, 0, 16, 0, + 19, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 19, 0, 0, 0, + 6, 4, 16, 0, 19, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 20, 0, 0, 0, 70, 2, + 16, 0, 9, 0, 0, 0, + 166, 10, 16, 0, 19, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 21, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 246, 15, + 16, 0, 19, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 20, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 20, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 255, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 21, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 21, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 21, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 1, 64, + 0, 0, 255, 0, 0, 0, + 18, 0, 0, 1, 32, 0, + 0, 7, 130, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 7, 0, + 0, 0, 31, 0, 4, 3, + 58, 0, 16, 0, 7, 0, + 0, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 19, 0, + 0, 0, 10, 0, 16, 0, + 19, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 19, 0, 0, 0, + 6, 4, 16, 0, 19, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 20, 0, 0, 0, 70, 14, + 16, 0, 11, 0, 0, 0, + 166, 10, 16, 0, 19, 0, + 0, 0, 41, 0, 0, 7, + 242, 0, 16, 0, 20, 0, + 0, 0, 70, 14, 16, 0, + 20, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 85, 0, 0, 7, 242, 0, + 16, 0, 21, 0, 0, 0, + 70, 14, 16, 0, 20, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 20, 0, 0, 0, 70, 14, + 16, 0, 20, 0, 0, 0, + 70, 14, 16, 0, 21, 0, + 0, 0, 30, 0, 0, 7, + 242, 0, 16, 0, 21, 0, + 0, 0, 70, 14, 16, 0, + 12, 0, 0, 0, 246, 15, + 16, 0, 19, 0, 0, 0, + 41, 0, 0, 7, 242, 0, + 16, 0, 21, 0, 0, 0, + 70, 14, 16, 0, 21, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 85, 0, + 0, 7, 242, 0, 16, 0, + 22, 0, 0, 0, 70, 14, + 16, 0, 21, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 30, 0, 0, 7, + 242, 0, 16, 0, 21, 0, + 0, 0, 70, 14, 16, 0, + 21, 0, 0, 0, 70, 14, + 16, 0, 22, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 20, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 20, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 20, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 21, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 21, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 21, 0, 0, 0, + 54, 0, 0, 6, 34, 48, + 32, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 21, 0, 0, 0, + 21, 0, 0, 1, 21, 0, + 0, 1, 31, 0, 4, 3, + 58, 0, 16, 0, 6, 0, + 0, 0, 85, 0, 0, 7, + 18, 0, 16, 0, 20, 0, + 0, 0, 10, 0, 16, 0, + 19, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 85, 0, 0, 7, 34, 0, + 16, 0, 20, 0, 0, 0, + 10, 0, 16, 0, 19, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 10, 194, 0, 16, 0, + 19, 0, 0, 0, 6, 4, + 16, 0, 20, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 20, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 166, 10, + 16, 0, 19, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 21, 0, 0, 0, + 70, 2, 16, 0, 15, 0, + 0, 0, 246, 15, 16, 0, + 19, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 20, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 20, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 20, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 255, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 21, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 21, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 21, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 255, 0, 0, 0, 18, 0, + 0, 1, 32, 0, 0, 7, + 130, 0, 16, 0, 6, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 6, 0, 0, 0, + 85, 0, 0, 7, 18, 0, + 16, 0, 20, 0, 0, 0, + 10, 0, 16, 0, 19, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 85, 0, + 0, 7, 34, 0, 16, 0, + 20, 0, 0, 0, 10, 0, + 16, 0, 19, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 19, 0, + 0, 0, 6, 4, 16, 0, + 20, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 30, 0, 0, 7, 242, 0, + 16, 0, 20, 0, 0, 0, + 70, 14, 16, 0, 16, 0, + 0, 0, 166, 10, 16, 0, + 19, 0, 0, 0, 41, 0, + 0, 7, 242, 0, 16, 0, + 20, 0, 0, 0, 70, 14, + 16, 0, 20, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 85, 0, 0, 7, + 242, 0, 16, 0, 21, 0, + 0, 0, 70, 14, 16, 0, + 20, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 242, 0, + 16, 0, 20, 0, 0, 0, + 70, 14, 16, 0, 20, 0, + 0, 0, 70, 14, 16, 0, + 21, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 21, 0, 0, 0, 70, 14, + 16, 0, 17, 0, 0, 0, + 246, 15, 16, 0, 19, 0, + 0, 0, 41, 0, 0, 7, + 242, 0, 16, 0, 21, 0, + 0, 0, 70, 14, 16, 0, + 21, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 85, 0, 0, 7, 242, 0, + 16, 0, 22, 0, 0, 0, + 70, 14, 16, 0, 21, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 21, 0, 0, 0, 70, 14, + 16, 0, 21, 0, 0, 0, + 70, 14, 16, 0, 22, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 10, 0, 16, 0, 21, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 21, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 21, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 21, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 21, 0, + 0, 1, 54, 0, 0, 6, + 18, 0, 16, 0, 20, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 20, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 54, 0, 0, 6, + 66, 0, 16, 0, 20, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 20, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 6, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 7, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 8, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 9, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 40, 0, 0, 5, + 18, 0, 16, 0, 21, 0, + 0, 0, 58, 0, 16, 0, + 6, 0, 0, 0, 40, 0, + 0, 5, 34, 0, 16, 0, + 21, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 40, 0, 0, 5, 66, 0, + 16, 0, 21, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 40, 0, 0, 5, + 130, 0, 16, 0, 21, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 22, 0, 0, 0, 70, 14, + 16, 0, 20, 0, 0, 0, + 70, 14, 16, 0, 21, 0, + 0, 0, 54, 0, 0, 6, + 18, 0, 16, 0, 23, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 23, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 54, 0, 0, 6, + 66, 0, 16, 0, 23, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 23, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 10, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 13, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 14, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 15, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 40, 0, 0, 5, + 18, 0, 16, 0, 24, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 40, 0, + 0, 5, 34, 0, 16, 0, + 24, 0, 0, 0, 58, 0, + 16, 0, 13, 0, 0, 0, + 40, 0, 0, 5, 66, 0, + 16, 0, 24, 0, 0, 0, + 58, 0, 16, 0, 14, 0, + 0, 0, 40, 0, 0, 5, + 130, 0, 16, 0, 24, 0, + 0, 0, 58, 0, 16, 0, + 15, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 23, 0, 0, 0, 70, 14, + 16, 0, 23, 0, 0, 0, + 70, 14, 16, 0, 24, 0, + 0, 0, 39, 0, 0, 10, + 194, 0, 16, 0, 19, 0, + 0, 0, 166, 10, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 1, 0, 0, 0, + 55, 0, 0, 9, 130, 0, + 16, 0, 23, 0, 0, 0, + 42, 0, 16, 0, 19, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 23, 0, 0, 0, + 55, 0, 0, 9, 130, 0, + 16, 0, 22, 0, 0, 0, + 42, 0, 16, 0, 19, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 22, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 50, 0, 16, 0, + 24, 0, 0, 0, 70, 0, + 16, 0, 22, 0, 0, 0, + 70, 0, 16, 0, 22, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 24, 0, 0, 0, 10, 0, + 16, 0, 24, 0, 0, 0, + 35, 0, 0, 9, 130, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 22, 0, + 0, 0, 42, 0, 16, 0, + 22, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 35, 0, 0, 9, 130, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 22, 0, + 0, 0, 58, 0, 16, 0, + 22, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 50, 0, 16, 0, + 24, 0, 0, 0, 70, 0, + 16, 0, 23, 0, 0, 0, + 70, 0, 16, 0, 23, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 13, 0, + 0, 0, 26, 0, 16, 0, + 24, 0, 0, 0, 10, 0, + 16, 0, 24, 0, 0, 0, + 35, 0, 0, 9, 130, 0, + 16, 0, 13, 0, 0, 0, + 42, 0, 16, 0, 23, 0, + 0, 0, 42, 0, 16, 0, + 23, 0, 0, 0, 58, 0, + 16, 0, 13, 0, 0, 0, + 35, 0, 0, 9, 130, 0, + 16, 0, 13, 0, 0, 0, + 58, 0, 16, 0, 23, 0, + 0, 0, 58, 0, 16, 0, + 23, 0, 0, 0, 58, 0, + 16, 0, 13, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 24, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 242, 0, + 16, 0, 21, 0, 0, 0, + 70, 14, 16, 0, 21, 0, + 0, 0, 70, 14, 16, 0, + 24, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 50, 0, 16, 0, 21, 0, + 0, 0, 70, 0, 16, 0, + 21, 0, 0, 0, 70, 0, + 16, 0, 22, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 14, 0, 0, 0, + 26, 0, 16, 0, 21, 0, + 0, 0, 10, 0, 16, 0, + 21, 0, 0, 0, 35, 0, + 0, 9, 130, 0, 16, 0, + 14, 0, 0, 0, 42, 0, + 16, 0, 22, 0, 0, 0, + 42, 0, 16, 0, 21, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 35, 0, + 0, 9, 130, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 22, 0, 0, 0, + 58, 0, 16, 0, 21, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 34, 0, + 0, 7, 130, 0, 16, 0, + 15, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 34, 0, 0, 7, + 130, 0, 16, 0, 18, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 14, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 15, 0, 0, 0, + 58, 0, 16, 0, 15, 0, + 0, 0, 58, 0, 16, 0, + 18, 0, 0, 0, 43, 0, + 0, 5, 130, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 14, 0, 0, 0, + 56, 0, 0, 7, 130, 0, + 16, 0, 14, 0, 0, 0, + 58, 0, 16, 0, 14, 0, + 0, 0, 1, 64, 0, 0, + 253, 255, 125, 66, 28, 0, + 0, 5, 130, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 14, 0, 0, 0, + 41, 0, 0, 7, 130, 0, + 16, 0, 18, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 79, 0, + 0, 7, 130, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 18, 0, 0, 0, + 58, 0, 16, 0, 14, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 14, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 15, 0, 0, 0, + 40, 0, 0, 5, 242, 0, + 16, 0, 21, 0, 0, 0, + 70, 14, 16, 0, 22, 0, + 0, 0, 55, 0, 0, 9, + 242, 0, 16, 0, 21, 0, + 0, 0, 246, 15, 16, 0, + 14, 0, 0, 0, 70, 14, + 16, 0, 21, 0, 0, 0, + 70, 14, 16, 0, 22, 0, + 0, 0, 55, 0, 0, 9, + 130, 0, 16, 0, 15, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 10, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 15, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 18, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 55, 0, 0, 9, + 130, 0, 16, 0, 18, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 26, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 18, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 18, 0, + 0, 0, 54, 0, 0, 6, + 18, 0, 16, 0, 20, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 55, 0, 0, 9, + 18, 0, 16, 0, 20, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 10, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 34, 0, 16, 0, 20, 0, + 0, 0, 10, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 55, 0, 0, 9, + 34, 0, 16, 0, 20, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 20, 0, 0, 0, + 26, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 18, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 66, 0, 16, 0, 20, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 55, 0, 0, 9, + 130, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 42, 0, 16, 0, 20, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 6, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 55, 0, 0, 9, + 130, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 7, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 6, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 55, 0, 0, 9, + 130, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 54, 0, 0, 6, + 130, 0, 16, 0, 6, 0, + 0, 0, 26, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 55, 0, 0, 9, + 130, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 54, 0, 0, 6, + 34, 48, 32, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 54, 0, 0, 4, + 130, 0, 16, 0, 6, 0, + 0, 0, 10, 64, 2, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 7, 0, 0, 0, + 26, 144, 144, 0, 58, 0, + 16, 0, 6, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 22, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 7, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 8, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 9, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 54, 0, 0, 6, 130, 0, + 16, 0, 14, 0, 0, 0, + 10, 48, 32, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 40, 0, 0, 5, 18, 0, + 16, 0, 24, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 40, 0, 0, 5, + 34, 0, 16, 0, 24, 0, + 0, 0, 58, 0, 16, 0, + 8, 0, 0, 0, 40, 0, + 0, 5, 66, 0, 16, 0, + 24, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 40, 0, 0, 5, 130, 0, + 16, 0, 24, 0, 0, 0, + 58, 0, 16, 0, 14, 0, + 0, 0, 30, 0, 0, 7, + 242, 0, 16, 0, 22, 0, + 0, 0, 70, 14, 16, 0, + 22, 0, 0, 0, 70, 14, + 16, 0, 24, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 194, 0, 16, 0, + 20, 0, 0, 0, 6, 4, + 16, 0, 22, 0, 0, 0, + 6, 4, 16, 0, 23, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 20, 0, + 0, 0, 58, 0, 16, 0, + 20, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 35, 0, 0, 9, 66, 0, + 16, 0, 20, 0, 0, 0, + 42, 0, 16, 0, 23, 0, + 0, 0, 42, 0, 16, 0, + 22, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 35, 0, 0, 9, 66, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 23, 0, + 0, 0, 58, 0, 16, 0, + 22, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 34, 0, 0, 7, 130, 0, + 16, 0, 20, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 13, 0, 0, 0, 34, 0, + 0, 7, 18, 0, 16, 0, + 22, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 20, 0, + 0, 0, 1, 0, 0, 7, + 130, 0, 16, 0, 20, 0, + 0, 0, 58, 0, 16, 0, + 20, 0, 0, 0, 10, 0, + 16, 0, 22, 0, 0, 0, + 43, 0, 0, 5, 66, 0, + 16, 0, 20, 0, 0, 0, + 42, 0, 16, 0, 20, 0, + 0, 0, 56, 0, 0, 7, + 66, 0, 16, 0, 20, 0, + 0, 0, 42, 0, 16, 0, + 20, 0, 0, 0, 1, 64, + 0, 0, 253, 255, 125, 66, + 28, 0, 0, 5, 66, 0, + 16, 0, 20, 0, 0, 0, + 42, 0, 16, 0, 20, 0, + 0, 0, 41, 0, 0, 7, + 18, 0, 16, 0, 22, 0, + 0, 0, 58, 0, 16, 0, + 13, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 79, 0, 0, 7, 66, 0, + 16, 0, 20, 0, 0, 0, + 10, 0, 16, 0, 22, 0, + 0, 0, 42, 0, 16, 0, + 20, 0, 0, 0, 1, 0, + 0, 7, 66, 0, 16, 0, + 20, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 20, 0, + 0, 0, 40, 0, 0, 5, + 242, 0, 16, 0, 22, 0, + 0, 0, 70, 14, 16, 0, + 23, 0, 0, 0, 55, 0, + 0, 9, 242, 0, 16, 0, + 22, 0, 0, 0, 166, 10, + 16, 0, 20, 0, 0, 0, + 70, 14, 16, 0, 22, 0, + 0, 0, 70, 14, 16, 0, + 23, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 20, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 0, 16, 0, + 23, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 34, 0, 16, 0, + 23, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 54, 0, + 0, 6, 66, 0, 16, 0, + 23, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 55, 0, + 0, 9, 130, 0, 16, 0, + 20, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 20, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 20, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 23, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 55, 0, + 0, 9, 18, 0, 16, 0, + 23, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 10, 0, 16, 0, 23, 0, + 0, 0, 58, 0, 16, 0, + 23, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 10, 0, 16, 0, + 23, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 23, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 55, 0, + 0, 9, 34, 0, 16, 0, + 23, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 26, 0, 16, 0, 23, 0, + 0, 0, 58, 0, 16, 0, + 23, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 26, 0, 16, 0, + 23, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 23, 0, 0, 0, 10, 48, + 32, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 55, 0, + 0, 9, 66, 0, 16, 0, + 23, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 42, 0, 16, 0, 23, 0, + 0, 0, 58, 0, 16, 0, + 23, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 23, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 23, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 55, 0, + 0, 9, 130, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 23, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 7, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 55, 0, + 0, 9, 130, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 7, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 55, 0, + 0, 9, 130, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 130, 0, 16, 0, + 7, 0, 0, 0, 26, 48, + 32, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 55, 0, + 0, 9, 130, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 14, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 34, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 40, 0, + 0, 5, 18, 0, 16, 0, + 24, 0, 0, 0, 58, 0, + 16, 0, 20, 0, 0, 0, + 40, 0, 0, 5, 226, 0, + 16, 0, 24, 0, 0, 0, + 6, 9, 16, 0, 23, 0, + 0, 0, 33, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 13, 0, 0, 0, + 43, 0, 0, 5, 130, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 13, 0, + 0, 0, 55, 0, 0, 15, + 114, 0, 16, 0, 23, 0, + 0, 0, 246, 15, 16, 0, + 19, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 128, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 16, 0, + 0, 0, 64, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 40, 0, 0, 5, + 18, 0, 16, 0, 25, 0, + 0, 0, 58, 0, 16, 0, + 15, 0, 0, 0, 40, 0, + 0, 5, 34, 0, 16, 0, + 25, 0, 0, 0, 58, 0, + 16, 0, 18, 0, 0, 0, + 40, 0, 0, 5, 194, 0, + 16, 0, 25, 0, 0, 0, + 6, 4, 16, 0, 20, 0, + 0, 0, 33, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 43, 0, 0, 5, 130, 0, + 16, 0, 14, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 15, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 19, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 80, 0, + 0, 7, 130, 0, 16, 0, + 18, 0, 0, 0, 58, 0, + 16, 0, 15, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 3, 0, 4, 3, + 58, 0, 16, 0, 18, 0, + 0, 0, 85, 0, 0, 8, + 130, 0, 16, 0, 18, 0, + 0, 0, 10, 144, 144, 0, + 58, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 15, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 18, 0, 0, 0, 58, 0, + 16, 0, 18, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 32, 0, 0, 7, + 130, 0, 16, 0, 19, 0, + 0, 0, 58, 0, 16, 0, + 18, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 19, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 15, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 7, 242, 0, + 16, 0, 20, 0, 0, 0, + 70, 14, 16, 0, 24, 0, + 0, 0, 70, 14, 16, 0, + 20, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 50, 0, 16, 0, 20, 0, + 0, 0, 70, 0, 16, 0, + 20, 0, 0, 0, 70, 0, + 16, 0, 22, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 19, 0, 0, 0, + 26, 0, 16, 0, 20, 0, + 0, 0, 10, 0, 16, 0, + 20, 0, 0, 0, 35, 0, + 0, 9, 130, 0, 16, 0, + 19, 0, 0, 0, 42, 0, + 16, 0, 22, 0, 0, 0, + 42, 0, 16, 0, 20, 0, + 0, 0, 58, 0, 16, 0, + 19, 0, 0, 0, 35, 0, + 0, 9, 130, 0, 16, 0, + 19, 0, 0, 0, 58, 0, + 16, 0, 22, 0, 0, 0, + 58, 0, 16, 0, 20, 0, + 0, 0, 58, 0, 16, 0, + 19, 0, 0, 0, 33, 0, + 0, 7, 18, 0, 16, 0, + 20, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 19, 0, + 0, 0, 60, 0, 0, 7, + 18, 0, 16, 0, 20, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 10, 0, + 16, 0, 20, 0, 0, 0, + 34, 0, 0, 7, 34, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 19, 0, + 0, 0, 58, 0, 16, 0, + 13, 0, 0, 0, 43, 0, + 0, 5, 130, 0, 16, 0, + 19, 0, 0, 0, 58, 0, + 16, 0, 19, 0, 0, 0, + 56, 0, 0, 7, 130, 0, + 16, 0, 19, 0, 0, 0, + 58, 0, 16, 0, 19, 0, + 0, 0, 1, 64, 0, 0, + 253, 255, 125, 66, 14, 0, + 0, 7, 130, 0, 16, 0, + 19, 0, 0, 0, 58, 0, + 16, 0, 19, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 28, 0, 0, 5, + 130, 0, 16, 0, 19, 0, + 0, 0, 58, 0, 16, 0, + 19, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 19, 0, 0, 0, 58, 0, + 16, 0, 19, 0, 0, 0, + 26, 0, 16, 0, 23, 0, + 0, 0, 55, 0, 0, 10, + 130, 0, 16, 0, 19, 0, + 0, 0, 26, 0, 16, 0, + 20, 0, 0, 0, 58, 144, + 144, 0, 58, 0, 16, 0, + 19, 0, 0, 0, 42, 0, + 16, 0, 23, 0, 0, 0, + 55, 0, 0, 9, 130, 0, + 16, 0, 19, 0, 0, 0, + 10, 0, 16, 0, 20, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 19, 0, 0, 0, + 18, 0, 0, 1, 167, 0, + 0, 9, 242, 0, 16, 0, + 20, 0, 0, 0, 58, 0, + 16, 0, 15, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 20, 0, 0, 0, 70, 14, + 16, 0, 25, 0, 0, 0, + 70, 14, 16, 0, 20, 0, + 0, 0, 38, 0, 0, 8, + 0, 208, 0, 0, 50, 0, + 16, 0, 20, 0, 0, 0, + 70, 0, 16, 0, 20, 0, + 0, 0, 70, 0, 16, 0, + 21, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 20, 0, 0, 0, 26, 0, + 16, 0, 20, 0, 0, 0, + 10, 0, 16, 0, 20, 0, + 0, 0, 35, 0, 0, 9, + 18, 0, 16, 0, 20, 0, + 0, 0, 42, 0, 16, 0, + 21, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 10, 0, 16, 0, 20, 0, + 0, 0, 35, 0, 0, 9, + 18, 0, 16, 0, 20, 0, + 0, 0, 58, 0, 16, 0, + 21, 0, 0, 0, 58, 0, + 16, 0, 20, 0, 0, 0, + 10, 0, 16, 0, 20, 0, + 0, 0, 33, 0, 0, 7, + 34, 0, 16, 0, 20, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 20, 0, 0, 0, + 60, 0, 0, 7, 34, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 20, 0, 0, 0, 34, 0, + 0, 7, 66, 0, 16, 0, + 20, 0, 0, 0, 10, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 43, 0, 0, 5, + 18, 0, 16, 0, 20, 0, + 0, 0, 10, 0, 16, 0, + 20, 0, 0, 0, 56, 0, + 0, 7, 18, 0, 16, 0, + 20, 0, 0, 0, 10, 0, + 16, 0, 20, 0, 0, 0, + 1, 64, 0, 0, 253, 255, + 125, 66, 14, 0, 0, 7, + 18, 0, 16, 0, 20, 0, + 0, 0, 10, 0, 16, 0, + 20, 0, 0, 0, 58, 0, + 16, 0, 14, 0, 0, 0, + 28, 0, 0, 5, 18, 0, + 16, 0, 20, 0, 0, 0, + 10, 0, 16, 0, 20, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 20, 0, + 0, 0, 10, 0, 16, 0, + 20, 0, 0, 0, 26, 0, + 16, 0, 23, 0, 0, 0, + 55, 0, 0, 10, 18, 0, + 16, 0, 20, 0, 0, 0, + 42, 0, 16, 0, 20, 0, + 0, 0, 58, 144, 144, 0, + 10, 0, 16, 0, 20, 0, + 0, 0, 42, 0, 16, 0, + 23, 0, 0, 0, 55, 0, + 0, 9, 130, 0, 16, 0, + 19, 0, 0, 0, 26, 0, + 16, 0, 20, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 20, 0, 0, 0, 21, 0, + 0, 1, 30, 0, 0, 7, + 130, 0, 16, 0, 19, 0, + 0, 0, 58, 0, 16, 0, + 19, 0, 0, 0, 10, 0, + 16, 0, 23, 0, 0, 0, + 30, 0, 0, 10, 18, 0, + 16, 0, 20, 0, 0, 0, + 1, 64, 0, 0, 64, 0, + 0, 0, 10, 144, 208, 128, + 65, 0, 0, 0, 64, 0, + 0, 0, 58, 0, 16, 0, + 19, 0, 0, 0, 41, 0, + 0, 7, 130, 0, 16, 0, + 18, 0, 0, 0, 58, 0, + 16, 0, 18, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 54, 0, 0, 7, + 18, 0, 16, 0, 26, 0, + 0, 0, 10, 48, 32, 4, + 0, 0, 0, 0, 58, 0, + 16, 0, 18, 0, 0, 0, + 54, 0, 0, 8, 34, 0, + 16, 0, 26, 0, 0, 0, + 10, 48, 32, 6, 0, 0, + 0, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 18, 0, + 0, 0, 54, 0, 0, 8, + 66, 0, 16, 0, 26, 0, + 0, 0, 10, 48, 32, 6, + 0, 0, 0, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 18, 0, 0, 0, 54, 0, + 0, 8, 130, 0, 16, 0, + 26, 0, 0, 0, 10, 48, + 32, 6, 0, 0, 0, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 18, 0, 0, 0, + 54, 0, 0, 7, 18, 0, + 16, 0, 27, 0, 0, 0, + 26, 48, 32, 4, 0, 0, + 0, 0, 58, 0, 16, 0, + 18, 0, 0, 0, 54, 0, + 0, 8, 34, 0, 16, 0, + 27, 0, 0, 0, 26, 48, + 32, 6, 0, 0, 0, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 18, 0, 0, 0, + 54, 0, 0, 8, 66, 0, + 16, 0, 27, 0, 0, 0, + 26, 48, 32, 6, 0, 0, + 0, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 18, 0, + 0, 0, 54, 0, 0, 8, + 130, 0, 16, 0, 27, 0, + 0, 0, 26, 48, 32, 6, + 0, 0, 0, 0, 3, 0, + 0, 0, 58, 0, 16, 0, + 18, 0, 0, 0, 38, 0, + 0, 10, 0, 208, 0, 0, + 242, 0, 16, 0, 27, 0, + 0, 0, 70, 14, 16, 0, + 27, 0, 0, 0, 6, 144, + 208, 0, 64, 0, 0, 0, + 58, 0, 16, 0, 19, 0, + 0, 0, 35, 0, 0, 9, + 242, 0, 16, 0, 20, 0, + 0, 0, 6, 0, 16, 0, + 20, 0, 0, 0, 70, 14, + 16, 0, 26, 0, 0, 0, + 70, 14, 16, 0, 27, 0, + 0, 0, 30, 0, 0, 10, + 242, 0, 16, 0, 20, 0, + 0, 0, 70, 14, 16, 0, + 20, 0, 0, 0, 2, 64, + 0, 0, 32, 0, 0, 0, + 32, 0, 0, 0, 32, 0, + 0, 0, 32, 0, 0, 0, + 85, 0, 0, 7, 242, 0, + 16, 0, 20, 0, 0, 0, + 134, 13, 16, 0, 20, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 55, 0, + 0, 9, 130, 0, 16, 0, + 20, 0, 0, 0, 42, 0, + 16, 0, 19, 0, 0, 0, + 1, 64, 0, 0, 255, 0, + 0, 0, 58, 0, 16, 0, + 20, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 26, 0, 0, 0, 58, 0, + 16, 0, 15, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 79, 0, + 0, 7, 114, 0, 16, 0, + 27, 0, 0, 0, 134, 1, + 16, 0, 20, 0, 0, 0, + 70, 2, 16, 0, 26, 0, + 0, 0, 54, 0, 0, 5, + 82, 0, 16, 0, 28, 0, + 0, 0, 6, 1, 16, 0, + 26, 0, 0, 0, 54, 0, + 0, 5, 162, 0, 16, 0, + 28, 0, 0, 0, 6, 8, + 16, 0, 20, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 28, 0, 0, 0, + 6, 5, 16, 0, 27, 0, + 0, 0, 70, 14, 16, 0, + 28, 0, 0, 0, 22, 11, + 16, 0, 28, 0, 0, 0, + 54, 0, 0, 5, 82, 0, + 16, 0, 20, 0, 0, 0, + 166, 11, 16, 0, 26, 0, + 0, 0, 55, 0, 0, 9, + 50, 0, 16, 0, 20, 0, + 0, 0, 166, 10, 16, 0, + 27, 0, 0, 0, 70, 0, + 16, 0, 20, 0, 0, 0, + 22, 5, 16, 0, 20, 0, + 0, 0, 79, 0, 0, 7, + 130, 0, 16, 0, 18, 0, + 0, 0, 58, 0, 16, 0, + 20, 0, 0, 0, 58, 0, + 16, 0, 26, 0, 0, 0, + 55, 0, 0, 9, 146, 0, + 16, 0, 26, 0, 0, 0, + 246, 15, 16, 0, 18, 0, + 0, 0, 246, 11, 16, 0, + 20, 0, 0, 0, 166, 14, + 16, 0, 20, 0, 0, 0, + 40, 0, 0, 5, 50, 0, + 16, 0, 27, 0, 0, 0, + 214, 5, 16, 0, 28, 0, + 0, 0, 40, 0, 0, 5, + 66, 0, 16, 0, 27, 0, + 0, 0, 26, 0, 16, 0, + 20, 0, 0, 0, 40, 0, + 0, 5, 130, 0, 16, 0, + 27, 0, 0, 0, 10, 0, + 16, 0, 26, 0, 0, 0, + 54, 0, 0, 5, 50, 0, + 16, 0, 26, 0, 0, 0, + 134, 0, 16, 0, 28, 0, + 0, 0, 54, 0, 0, 5, + 66, 0, 16, 0, 26, 0, + 0, 0, 10, 0, 16, 0, + 20, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 20, 0, 0, 0, 70, 14, + 16, 0, 27, 0, 0, 0, + 70, 14, 16, 0, 26, 0, + 0, 0, 38, 0, 0, 8, + 0, 208, 0, 0, 50, 0, + 16, 0, 20, 0, 0, 0, + 70, 0, 16, 0, 20, 0, + 0, 0, 70, 0, 16, 0, + 20, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 18, 0, 0, 0, 26, 0, + 16, 0, 20, 0, 0, 0, + 10, 0, 16, 0, 20, 0, + 0, 0, 35, 0, 0, 9, + 130, 0, 16, 0, 18, 0, + 0, 0, 42, 0, 16, 0, + 20, 0, 0, 0, 42, 0, + 16, 0, 20, 0, 0, 0, + 58, 0, 16, 0, 18, 0, + 0, 0, 86, 0, 0, 5, + 130, 0, 16, 0, 18, 0, + 0, 0, 58, 0, 16, 0, + 18, 0, 0, 0, 86, 0, + 0, 5, 130, 0, 16, 0, + 19, 0, 0, 0, 58, 0, + 16, 0, 20, 0, 0, 0, + 56, 0, 0, 7, 130, 0, + 16, 0, 19, 0, 0, 0, + 58, 0, 16, 0, 19, 0, + 0, 0, 58, 0, 16, 0, + 19, 0, 0, 0, 50, 0, + 0, 10, 130, 0, 16, 0, + 18, 0, 0, 0, 58, 0, + 16, 0, 19, 0, 0, 0, + 42, 128, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 58, 0, 16, 0, 18, 0, + 0, 0, 28, 0, 0, 5, + 130, 0, 16, 0, 18, 0, + 0, 0, 58, 0, 16, 0, + 18, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 19, 0, 0, 0, 58, 0, + 16, 0, 18, 0, 0, 0, + 26, 0, 16, 0, 19, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 15, 0, + 0, 0, 58, 0, 16, 0, + 15, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 22, 0, 0, 1, 79, 0, + 0, 7, 130, 0, 16, 0, + 6, 0, 0, 0, 26, 0, + 16, 0, 19, 0, 0, 0, + 26, 0, 16, 0, 18, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 18, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 55, 0, + 0, 9, 50, 0, 16, 0, + 18, 0, 0, 0, 246, 15, + 16, 0, 6, 0, 0, 0, + 70, 0, 16, 0, 19, 0, + 0, 0, 70, 0, 16, 0, + 18, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 19, 0, 0, 0, 10, 0, + 16, 0, 19, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 18, 0, 0, 0, 22, 0, + 0, 1, 54, 0, 0, 6, + 18, 0, 16, 0, 18, 0, + 0, 0, 58, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 54, 0, 0, 4, + 66, 0, 16, 0, 18, 0, + 0, 0, 10, 64, 2, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 22, 6, 16, 0, 18, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 190, 24, + 0, 1, 31, 0, 4, 3, + 26, 0, 16, 0, 1, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 167, 0, 0, 9, + 226, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 249, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 18, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 134, 3, 16, 0, 2, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 31, 0, 4, 3, 10, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 167, 0, 0, 9, + 226, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 249, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 134, 3, 16, 0, 3, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 31, 0, 4, 3, 42, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 2, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 8, 0, + 0, 0, 167, 0, 0, 9, + 226, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 249, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 4, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 3, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 134, 3, 16, 0, 3, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 10, 0, 16, 0, + 4, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 31, 0, 4, 3, 58, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 167, 0, 0, 9, + 226, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 249, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 134, 3, 16, 0, 2, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 79, 0, 0, 9, 98, 0, + 16, 0, 0, 0, 0, 0, + 6, 64, 2, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 226, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 249, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 58, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 134, 3, 16, 0, 2, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 21, 0, + 0, 1, 21, 0, 0, 1, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 18, 0, + 16, 0, 1, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 226, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 6, 249, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 18, 0, 16, 0, 3, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 32, 0, 0, 0, + 6, 240, 17, 0, 0, 0, + 0, 0, 79, 0, 0, 7, + 66, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 31, 0, 4, 3, 42, 0, + 16, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 18, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 168, 0, 0, 8, 114, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 134, 3, 16, 0, 2, 0, + 0, 0, 168, 0, 0, 8, + 18, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 21, 0, + 0, 1, 167, 0, 0, 9, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 6, 112, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 8, + 18, 0, 16, 0, 2, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 79, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 31, 0, 4, 3, + 26, 0, 16, 0, 0, 0, + 0, 0, 167, 0, 0, 8, + 114, 0, 16, 0, 1, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 70, 242, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 8, 130, 0, 16, 0, + 1, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 32, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 18, 0, 0, 1, 167, 0, + 0, 9, 242, 0, 16, 0, + 1, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 70, 126, 16, 0, + 1, 0, 0, 0, 21, 0, + 0, 1, 168, 0, 0, 9, + 242, 224, 17, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 1, 0, + 0, 0, 21, 0, 0, 1, + 62, 0, 0, 1 +}; diff --git a/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_TryMode456CS.inc b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_TryMode456CS.inc new file mode 100644 index 0000000..d828ae1 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/Shaders/Compiled/BC7Encode_TryMode456CS.inc @@ -0,0 +1,3026 @@ +#if 0 +// +// Generated by Microsoft (R) D3D Shader Disassembler +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Input +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// no Output +cs_4_0 +dcl_globalFlags refactoringAllowed +dcl_immediateConstantBuffer { { 0, 0, 0, 0}, + { 0, 4, 0, 0}, + { 0, 9, 0, 0}, + { 1, 13, 0, 0}, + { 1, 17, 0, 0}, + { 1, 21, 0, 0}, + { 1, 26, 0, 0}, + { 2, 30, 0, 0}, + { 2, 34, 0, 0}, + { 2, 38, 0, 0}, + { 2, 43, 0, 0}, + { 2, 47, 0, 0}, + { 3, 51, 0, 0}, + { 3, 55, 0, 0}, + { 3, 60, 0, 0}, + { 3, 64, 0, 0}, + { 4, 0, 0, 0}, + { 4, 9, 0, 0}, + { 4, 18, 0, 0}, + { 4, 27, 0, 0}, + { 5, 37, 0, 0}, + { 5, 46, 0, 0}, + { 5, 55, 0, 0}, + { 5, 64, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 7, 0, 0, 0}, + { 7, 0, 0, 0}, + { 7, 0, 0, 0}, + { 7, 0, 0, 0}, + { 8, 21, 0, 0}, + { 8, 43, 0, 0}, + { 8, 64, 0, 0}, + { 8, 0, 0, 0}, + { 9, 0, 0, 0}, + { 9, 0, 0, 0}, + { 9, 0, 0, 0}, + { 9, 0, 0, 0}, + { 10, 0, 0, 0}, + { 10, 0, 0, 0}, + { 10, 0, 0, 0}, + { 10, 0, 0, 0}, + { 10, 0, 0, 0}, + { 11, 0, 0, 0}, + { 11, 0, 0, 0}, + { 11, 0, 0, 0}, + { 11, 0, 0, 0}, + { 12, 0, 0, 0}, + { 12, 0, 0, 0}, + { 12, 0, 0, 0}, + { 12, 0, 0, 0}, + { 13, 0, 0, 0}, + { 13, 0, 0, 0}, + { 13, 0, 0, 0}, + { 13, 0, 0, 0}, + { 14, 0, 0, 0}, + { 14, 0, 0, 0}, + { 14, 0, 0, 0}, + { 14, 0, 0, 0}, + { 15, 0, 0, 0}, + { 15, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 4, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 5, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 6, 0, 0, 0}, + { 7, 0, 0, 0}, + { 7, 0, 0, 0}, + { 7, 0, 0, 0}, + { 7, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 0, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 1, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 2, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0}, + { 3, 0, 0, 0} } +dcl_constantbuffer CB0[2], immediateIndexed +dcl_resource_texture2d (float,float,float,float) t0 +dcl_uav_structured u0, 16 +dcl_input vThreadIDInGroupFlattened +dcl_input vThreadGroupID.x +dcl_temps 19 +dcl_tgsm_structured g0, 100, 64 +dcl_thread_group 64, 1, 1 +ushr r0.x, vThreadIDInGroupFlattened.x, l(4) +ishl r0.y, vThreadGroupID.x, l(2) +iadd r0.y, r0.y, cb0[1].x +iadd r0.x, r0.x, r0.y +uge r0.y, r0.x, cb0[1].y +if_nz r0.y + ret +endif +and r0.y, vThreadIDInGroupFlattened.x, l(48) +iadd r0.z, -r0.y, vThreadIDInGroupFlattened.x +ult r1.xyzw, r0.zzzz, l(16, 8, 4, 2) +if_nz r1.x + udiv r0.w, null, r0.x, cb0[0].y + imad r2.x, -r0.w, cb0[0].y, r0.x + ishl r2.x, r2.x, l(2) + ishl r0.w, r0.w, l(2) + and r2.y, r0.z, l(3) + iadd r2.x, r2.y, r2.x + ushr r3.x, r0.z, l(2) + iadd r2.y, r0.w, r3.x + mov r2.zw, l(0,0,0,0) + ld r2.xyzw, r2.xyzw, t0.xyzw + mul r2.xyzw, r2.xyzw, l(255.000000, 255.000000, 255.000000, 255.000000) + ftou r2.xyzw, r2.xyzw + umin r2.xyzw, r2.xyzw, l(255, 255, 255, 255) + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(0), r2.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r2.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r2.xyzw +endif +if_nz r1.y + ld_structured r2.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r3.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r0.w, vThreadIDInGroupFlattened.x, l(8) + ld_structured r4.xyzw, r0.w, l(36), g0.xyzw + ld_structured r5.xyzw, r0.w, l(52), g0.xyzw + umin r2.xyzw, r2.xyzw, r4.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r2.xyzw + umax r2.xyzw, r3.xyzw, r5.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r2.xyzw +endif +if_nz r1.z + ld_structured r2.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r3.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r0.w, vThreadIDInGroupFlattened.x, l(4) + ld_structured r4.xyzw, r0.w, l(36), g0.xyzw + ld_structured r5.xyzw, r0.w, l(52), g0.xyzw + umin r2.xyzw, r2.xyzw, r4.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r2.xyzw + umax r2.xyzw, r3.xyzw, r5.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r2.xyzw +endif +if_nz r1.w + ld_structured r2.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r3.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r0.w, vThreadIDInGroupFlattened.x, l(2) + ld_structured r4.xyzw, r0.w, l(36), g0.xyzw + ld_structured r5.xyzw, r0.w, l(52), g0.xyzw + umin r2.xyzw, r2.xyzw, r4.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r2.xyzw + umax r2.xyzw, r3.xyzw, r5.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r2.xyzw +endif +ult r2.xy, r0.zzzz, l(1, 12, 0, 0) +if_nz r2.x + ld_structured r3.xyzw, vThreadIDInGroupFlattened.x, l(36), g0.xyzw + ld_structured r4.xyzw, vThreadIDInGroupFlattened.x, l(52), g0.xyzw + iadd r0.w, vThreadIDInGroupFlattened.x, l(1) + ld_structured r5.xyzw, r0.w, l(36), g0.xyzw + ld_structured r6.xyzw, r0.w, l(52), g0.xyzw + umin r3.xyzw, r3.xyzw, r5.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(36), r3.xyzw + umax r3.xyzw, r4.xyzw, r6.xyzw + store_structured g0.xyzw, vThreadIDInGroupFlattened.x, l(52), r3.xyzw +endif +ld_structured r3.xyzw, r0.y, l(0), g0.xyzw +ld_structured r4.xyzw, r0.y, l(36), g0.xyzw +ld_structured r5.xyzw, r0.y, l(52), g0.xyzw +and r0.w, r0.z, l(1) +movc r6.xyz, r0.wwww, l(1,1,2,0), l(0,2,1,0) +movc r6.xyz, r1.yyyy, r6.xyzx, l(0,2,2,0) +if_nz r2.y + ieq r7.xyzw, r0.zzzz, l(8, 9, 10, 11) + ult r0.w, r0.z, l(6) + or r0.w, r7.z, r0.w + or r2.yzw, r1.wwzy, r7.xxyw + mov r7.y, r4.z + mov r7.w, r5.z + mov r7.x, l(3) + mov r8.x, r4.w + mov r8.y, r5.w + mov r8.z, l(0) + movc r9.xyz, r2.wwww, r7.ywxy, r8.xyzx + movc r10.yw, r2.wwww, r8.xxxy, r7.yyyw + mov r11.x, r4.y + mov r11.y, r5.y + mov r11.z, l(2) + movc r9.xyz, r0.wwww, r11.xyzx, r9.xyzx + mov r7.xz, r8.xxyx + mov r10.xz, r11.xxyx + movc r7.xyzw, r0.wwww, r7.xzwy, r10.xzwy + mov r10.x, r4.x + mov r10.yz, r7.xxwx + movc r11.xyz, r2.zzzz, r4.wyzw, r10.xyzx + mov r10.y, r5.x + mov r10.z, l(1) + movc r9.xyz, r2.zzzz, r10.xyzx, r9.xyzx + mov r7.x, r10.y + movc r7.xyz, r2.zzzz, r5.wyzw, r7.xyzx + movc r10.xyz, r2.yyyy, r4.xyzx, r11.xyzx + movc r7.xyz, r2.yyyy, r5.xyzx, r7.xyzx + movc r2.yzw, r2.yyyy, r8.xxyz, r9.xxyz + if_nz r1.y + iadd r8.xyz, r10.xyzx, l(4, 4, 4, 0) + umin r8.xyz, r8.xyzx, l(255, 255, 255, 0) + iadd r9.xy, r2.yzyy, l(2, 2, 0, 0) + umin r9.xy, r9.xyxx, l(255, 255, 0, 0) + and r11.xyz, r8.xyzx, l(248, 248, 248, 0) + ushr r8.xyz, r8.xyzx, l(5) + iadd r8.xyz, r8.xyzx, r11.xyzx + and r9.zw, r9.xxxy, l(0, 0, 252, 252) + ushr r9.xy, r9.xyxx, l(6) + iadd r11.xyz, r7.xyzx, l(4, 4, 4, 0) + umin r11.xyz, r11.xyzx, l(255, 255, 255, 0) + and r12.xyz, r11.xyzx, l(248, 248, 248, 0) + ushr r11.xyz, r11.xyzx, l(5) + iadd r11.xyz, r11.xyzx, r12.xyzx + iadd r9.xy, r9.xyxx, r9.zwzz + mov r11.w, r9.y + mov r12.y, l(4) + else + iadd r10.xyz, r10.xyzx, l(1, 1, 1, 0) + umin r10.xyz, r10.xyzx, l(255, 255, 255, 0) + and r13.xyz, r10.xyzx, l(254, 254, 254, 0) + ushr r10.xyz, r10.xyzx, l(7) + iadd r8.xyz, r10.xyzx, r13.xyzx + iadd r7.xyz, r7.xyzx, l(1, 1, 1, 0) + umin r7.xyz, r7.xyzx, l(255, 255, 255, 0) + and r10.xyz, r7.xyzx, l(254, 254, 254, 0) + ushr r7.xyz, r7.xyzx, l(7) + iadd r11.xyz, r7.xyzx, r10.xyzx + mov r9.x, r2.y + mov r11.w, r2.z + mov r12.y, l(5) + endif + ieq r7.xyz, r2.wwww, l(1, 2, 3, 0) + movc r10.zw, r7.zzzz, r3.wwwz, r3.zzzw + mov r10.xy, r3.xyxx + movc r10.yzw, r7.yyyy, r3.wwzy, r10.yyzw + movc r10.xyzw, r7.xxxx, r3.wyzx, r10.xyzw + ineg r13.xyz, r8.xyzx + ineg r13.w, r9.x + iadd r14.xyzw, r11.xyzw, r13.xyzw + imul null, r15.xyz, r14.xywx, r14.xywx + iadd r0.w, r15.y, r15.x + imad r0.w, r14.z, r14.z, r0.w + iadd r13.xyzw, r10.xyzw, r13.xyzw + imul null, r13.xyw, r13.xyxw, r13.xyxw + iadd r2.y, r13.y, r13.x + imad r2.y, r13.z, r13.z, r2.y + iadd r10.xyzw, -r11.xyzw, r10.xyzw + imul null, r10.xyw, r10.xyxw, r10.xyxw + iadd r2.z, r10.y, r10.x + imad r2.z, r10.z, r10.z, r2.z + ilt r2.y, r2.z, r2.y + ineg r16.xyzw, r14.xyzw + movc r10.xyz, r2.yyyy, r11.xyzx, r8.xyzx + movc r8.xyz, r2.yyyy, r8.xyzx, r11.xyzx + movc r11.xyz, r2.yyyy, r16.xyzx, r14.xyzx + ilt r2.y, r10.w, r13.w + mov r9.y, r11.w + mov r9.z, r16.w + mov r9.w, r14.w + movc r9.xyz, r2.yyyy, r9.yxzy, r9.xywx + ige r2.y, l(0), r0.w + itof r2.z, r0.w + ishl r12.zw, r6.yyyz, l(6) + ishl r6.yz, r6.yyzy, l(4) + iadd r13.xy, r12.zwzz, l(11, 11, 0, 0) + ige r7.w, l(0), r15.z + itof r8.w, r15.z + udiv null, r13.xy, r13.xyxx, l(68, 68, 0, 0) + mov r13.zw, l(0,0,0,0) + loop + uge r9.w, r13.w, l(16) + breakc_nz r9.w + iadd r9.w, r0.y, r13.w + ld_structured r14.xyzw, r9.w, l(0), g0.xyzw + movc r16.zw, r7.zzzz, r14.wwwz, r14.zzzw + mov r16.xy, r14.xyxx + movc r16.yzw, r7.yyyy, r14.wwzy, r16.yyzw + movc r14.xyzw, r7.xxxx, r14.wyzx, r16.xyzw + iadd r15.xyw, -r10.xyxz, r14.xyxz + imul null, r15.xy, r11.xyxx, r15.xyxx + iadd r9.w, r15.y, r15.x + imad r9.w, r11.z, r15.w, r9.w + ige r10.w, l(0), r9.w + or r10.w, r2.y, r10.w + ilt r11.w, r9.w, r0.w + itof r9.w, r9.w + mul r9.w, r9.w, l(63.499989) + div r9.w, r9.w, r2.z + ftou r9.w, r9.w + iadd r9.w, r9.w, r12.z + movc r9.w, r11.w, icb[r9.w + 0].x, r13.x + movc r9.w, r10.w, l(0), r9.w + iadd r10.w, -r9.x, r14.w + imul null, r10.w, r9.z, r10.w + ige r11.w, l(0), r10.w + or r11.w, r7.w, r11.w + ilt r15.x, r10.w, r15.z + itof r10.w, r10.w + mul r10.w, r10.w, l(63.499989) + div r10.w, r10.w, r8.w + ftou r10.w, r10.w + iadd r10.w, r10.w, r12.w + movc r10.w, r15.x, icb[r10.w + 0].x, r13.y + movc r10.w, r11.w, l(0), r10.w + iadd r9.w, r6.y, r9.w + iadd r11.w, l(64), -icb[r9.w + 0].y + imul null, r15.xyw, r8.xyxz, icb[r9.w + 0].yyyy + imad r15.xyw, r11.wwww, r10.xyxz, r15.xyxw + iadd r15.xyw, r15.xyxw, l(32, 32, 0, 32) + ushr r16.xyw, r15.xyxw, l(6) + iadd r9.w, r6.z, r10.w + iadd r10.w, l(64), -icb[r9.w + 0].y + imul null, r9.w, r9.y, icb[r9.w + 0].y + imad r9.w, r10.w, r9.x, r9.w + iadd r9.w, r9.w, l(32) + ushr r15.y, r9.w, l(6) + ult r17.xyz, r16.xywx, r14.xyzx + mov r16.z, r14.x + movc r17.xw, r17.xxxx, r16.zzzx, r16.xxxz + mov r16.xz, r14.yyzy + movc r16.xyzw, r17.yyzz, r16.xyzw, r16.yxwz + ult r9.w, r15.y, r14.w + mov r15.x, r14.w + movc r14.xy, r9.wwww, r15.xyxx, r15.yxyy + ineg r18.w, r17.w + ineg r18.yz, r16.yywy + ineg r18.x, r14.y + mov r14.w, r17.x + mov r14.yz, r16.xxzx + iadd r14.xyzw, r18.xyzw, r14.xyzw + movc r16.zw, r7.zzzz, r14.xxxz, r14.zzzx + mov r16.xy, r14.wyww + movc r16.yzw, r7.yyyy, r14.xxzy, r16.yyzw + movc r14.xyzw, r7.xxxx, r14.xyzw, r16.xyzw + imul null, r14.xy, r14.xyxx, r14.xyxx + iadd r9.w, r14.y, r14.x + imad r9.w, r14.z, r14.z, r9.w + utof r9.w, r9.w + utof r10.w, r14.w + mul r10.w, r10.w, r10.w + mad r9.w, r10.w, cb0[1].z, r9.w + ftou r9.w, r9.w + iadd r13.z, r9.w, r13.z + iadd r13.w, r13.w, l(1) + endloop + mov r12.x, r13.z + mov r6.w, r2.w +else + if_nz r1.x + iadd r7.x, r0.z, l(-12) + ushr r7.y, r7.x, l(1) + and r0.zw, r7.xxxy, l(0, 0, 1, 1) + and r4.xyzw, r4.xyzw, l(-2, -2, -2, -2) + iadd r4.xyzw, r0.zzzz, r4.xyzw + and r5.xyzw, r5.xyzw, l(-2, -2, -2, -2) + iadd r5.xyzw, r0.wwww, r5.xyzw + iadd r8.xyzw, -r4.xyzw, r5.xyzw + imul null, r0.zw, r8.xxxy, r8.xxxy + iadd r0.z, r0.w, r0.z + imad r0.z, r8.z, r8.z, r0.z + imad r0.z, r8.w, r8.w, r0.z + iadd r3.xyzw, r3.xyzw, -r4.xyzw + imul null, r2.yz, r3.xxyx, r8.xxyx + iadd r0.w, r2.z, r2.y + imad r0.w, r8.z, r3.z, r0.w + imad r0.w, r8.w, r3.w, r0.w + ilt r1.x, l(0), r0.z + ige r2.y, r0.w, l(0) + and r1.x, r1.x, r2.y + itof r0.w, r0.w + mul r0.w, r0.w, l(63.499989) + ftou r0.w, r0.w + ishl r2.y, r0.z, l(5) + ult r0.w, r2.y, r0.w + and r0.w, r0.w, r1.x + ineg r3.xyzw, r8.xyzw + movc r9.xyzw, r0.wwww, r5.xyzw, r4.xyzw + movc r4.xyzw, r0.wwww, r4.xyzw, r5.xyzw + movc r3.xyzw, r0.wwww, r3.xyzw, r8.xyzw + ige r0.w, l(0), r0.z + itof r1.x, r0.z + mov r12.xy, l(0,0,0,0) + loop + uge r2.y, r12.y, l(16) + breakc_nz r2.y + iadd r2.y, r0.y, r12.y + ld_structured r5.xyzw, r2.y, l(0), g0.xyzw + iadd r8.xyzw, -r9.xyzw, r5.xyzw + imul null, r2.yz, r3.xxyx, r8.xxyx + iadd r2.y, r2.z, r2.y + imad r2.y, r3.z, r8.z, r2.y + imad r2.y, r3.w, r8.w, r2.y + ige r2.z, l(0), r2.y + or r2.z, r0.w, r2.z + ilt r2.w, r2.y, r0.z + itof r2.y, r2.y + mul r2.y, r2.y, l(63.499989) + div r2.y, r2.y, r1.x + ftou r2.y, r2.y + movc r2.y, r2.w, icb[r2.y + 0].x, l(15) + movc r2.y, r2.z, l(0), r2.y + iadd r2.z, l(64), -icb[r2.y + 0].y + imul null, r8.xyzw, r4.xyzw, icb[r2.y + 0].yyyy + imad r8.xyzw, r2.zzzz, r9.xyzw, r8.xyzw + iadd r8.xyzw, r8.xyzw, l(32, 32, 32, 32) + ushr r8.xyzw, r8.xzyw, l(6) + ult r10.xyzw, r8.xzyw, r5.xyzw + mov r11.xz, r5.xxyx + mov r11.yw, r8.xxxz + movc r11.xyzw, r10.xxyy, r11.xyzw, r11.yxwz + mov r8.xz, r5.zzwz + movc r5.xyzw, r10.zwzw, r8.ywxz, r8.xzyw + ineg r8.xy, r11.ywyy + ineg r8.zw, r5.xxxy + mov r5.xy, r11.xzxx + iadd r5.xyzw, r8.xyzw, r5.xyzw + imul null, r2.yz, r5.xxyx, r5.xxyx + iadd r2.y, r2.z, r2.y + imad r2.y, r5.z, r5.z, r2.y + utof r2.y, r2.y + utof r2.z, r5.w + mul r2.z, r2.z, r2.z + mad r2.y, r2.z, cb0[1].z, r2.y + ftou r2.y, r2.y + iadd r12.x, r2.y, r12.x + iadd r12.y, r12.y, l(1) + endloop + mov r12.y, l(6) + mov r6.w, r7.x + else + mov r12.xy, l(-1,0,0,0) + mov r6.w, l(0) + endif +endif +store_structured g0.xy, vThreadIDInGroupFlattened.x, l(16), r12.xyxx +store_structured g0.xy, vThreadIDInGroupFlattened.x, l(28), r6.xwxx +if_nz r1.y + iadd r0.y, vThreadIDInGroupFlattened.x, l(8) + ld_structured r3.yz, r0.y, l(16), g0.xxyx + ld_structured r4.xy, r0.y, l(28), g0.xyxx + ult r0.z, r3.y, r12.x + if_nz r0.z + ld_structured r3.x, r0.y, l(16), g0.xxxx + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(16), r3.xzxx + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(28), r4.xyxx + endif +endif +if_nz r1.z + ld_structured r3.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(4) + ld_structured r4.yz, r0.y, l(16), g0.xxyx + ld_structured r5.xy, r0.y, l(28), g0.xyxx + ult r0.z, r4.y, r3.x + if_nz r0.z + ld_structured r4.x, r0.y, l(16), g0.xxxx + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(16), r4.xzxx + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(28), r5.xyxx + endif +endif +if_nz r1.w + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(2) + ld_structured r3.yz, r0.y, l(16), g0.xxyx + ld_structured r4.xy, r0.y, l(28), g0.xyxx + ult r0.z, r3.y, r1.x + if_nz r0.z + ld_structured r3.x, r0.y, l(16), g0.xxxx + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(16), r3.xzxx + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(28), r4.xyxx + endif +endif +if_nz r2.x + ld_structured r1.x, vThreadIDInGroupFlattened.x, l(16), g0.xxxx + iadd r0.y, vThreadIDInGroupFlattened.x, l(1) + ld_structured r2.yz, r0.y, l(16), g0.xxyx + ld_structured r3.xy, r0.y, l(28), g0.xyxx + ult r0.z, r2.y, r1.x + if_nz r0.z + ld_structured r2.x, r0.y, l(16), g0.xxxx + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(16), r2.xzxx + store_structured g0.xy, vThreadIDInGroupFlattened.x, l(28), r3.xyxx + endif + ld_structured r1.xw, vThreadIDInGroupFlattened.x, l(28), g0.xxxy + ishl r0.y, r1.x, l(31) + ld_structured r1.xy, vThreadIDInGroupFlattened.x, l(16), g0.xyxx + or r1.y, r0.y, r1.y + mov r1.z, l(0) + store_structured u0.xyzw, r0.x, l(0), r1.xyzw +endif +ret +// Approximately 0 instruction slots used +#endif + +const BYTE BC7Encode_TryMode456CS[] = +{ + 68, 88, 66, 67, 193, 29, + 43, 212, 231, 175, 144, 60, + 211, 12, 231, 93, 197, 161, + 15, 183, 1, 0, 0, 0, + 56, 56, 0, 0, 3, 0, + 0, 0, 44, 0, 0, 0, + 60, 0, 0, 0, 76, 0, + 0, 0, 73, 83, 71, 78, + 8, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 79, 83, 71, 78, 8, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 83, 72, + 69, 88, 228, 55, 0, 0, + 64, 0, 5, 0, 249, 13, + 0, 0, 106, 8, 0, 1, + 53, 24, 0, 0, 2, 3, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 9, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 13, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 17, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 21, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 26, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 30, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 34, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 38, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 43, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 47, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 51, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 55, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 60, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 64, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 9, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 18, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 27, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 37, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 46, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 55, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 64, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 21, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 8, 0, 0, 0, 43, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 64, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 9, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 9, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 9, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 9, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 10, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 11, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 11, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 11, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 11, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 12, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 12, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 13, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 13, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 13, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 13, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 14, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 14, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 14, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 14, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 4, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 7, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 89, 0, 0, 4, + 70, 142, 32, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 88, 24, 0, 4, 0, 112, + 16, 0, 0, 0, 0, 0, + 85, 85, 0, 0, 158, 0, + 0, 4, 0, 224, 17, 0, + 0, 0, 0, 0, 16, 0, + 0, 0, 95, 0, 0, 2, + 0, 64, 2, 0, 95, 0, + 0, 2, 18, 16, 2, 0, + 104, 0, 0, 2, 19, 0, + 0, 0, 160, 0, 0, 5, + 0, 240, 17, 0, 0, 0, + 0, 0, 100, 0, 0, 0, + 64, 0, 0, 0, 155, 0, + 0, 4, 64, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 85, 0, 0, 6, + 18, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 41, 0, 0, 6, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 16, 2, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 30, 0, 0, 8, + 34, 0, 16, 0, 0, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 10, 128, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 80, 0, 0, 8, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 26, 128, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 0, 0, 0, 0, 62, 0, + 0, 1, 21, 0, 0, 1, + 1, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 48, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 128, 65, 0, + 0, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 79, 0, + 0, 10, 242, 0, 16, 0, + 1, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 16, 0, + 0, 0, 8, 0, 0, 0, + 4, 0, 0, 0, 2, 0, + 0, 0, 31, 0, 4, 3, + 10, 0, 16, 0, 1, 0, + 0, 0, 78, 0, 0, 9, + 130, 0, 16, 0, 0, 0, + 0, 0, 0, 208, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 26, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 35, 0, 0, 11, + 18, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 128, + 65, 0, 0, 0, 0, 0, + 0, 0, 26, 128, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 41, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 41, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 1, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 10, 0, 16, 0, 2, 0, + 0, 0, 85, 0, 0, 7, + 18, 0, 16, 0, 3, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 54, 0, + 0, 8, 194, 0, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 45, 0, 0, 7, 242, 0, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 2, 0, + 0, 0, 70, 126, 16, 0, + 0, 0, 0, 0, 56, 0, + 0, 10, 242, 0, 16, 0, + 2, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 0, 0, + 127, 67, 0, 0, 127, 67, + 0, 0, 127, 67, 0, 0, + 127, 67, 28, 0, 0, 5, + 242, 0, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 84, 0, + 0, 10, 242, 0, 16, 0, + 2, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 14, 16, 0, 2, 0, + 0, 0, 21, 0, 0, 1, + 31, 0, 4, 3, 26, 0, + 16, 0, 1, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 2, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 3, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 30, 0, + 0, 6, 130, 0, 16, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 4, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 242, 0, 16, 0, + 5, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 84, 0, + 0, 7, 242, 0, 16, 0, + 2, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 4, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 83, 0, + 0, 7, 242, 0, 16, 0, + 2, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 168, 0, 0, 8, + 242, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 52, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 21, 0, + 0, 1, 31, 0, 4, 3, + 42, 0, 16, 0, 1, 0, + 0, 0, 167, 0, 0, 8, + 242, 0, 16, 0, 2, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 36, 0, + 0, 0, 70, 254, 17, 0, + 0, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 3, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 130, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 4, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 5, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 84, 0, 0, 7, 242, 0, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 83, 0, 0, 7, 242, 0, + 16, 0, 2, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 168, 0, + 0, 8, 242, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 14, + 16, 0, 2, 0, 0, 0, + 21, 0, 0, 1, 31, 0, + 4, 3, 58, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 2, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 3, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 4, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 84, 0, 0, 7, + 242, 0, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 2, 0, 0, 0, 70, 14, + 16, 0, 4, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 14, 16, 0, 2, 0, + 0, 0, 83, 0, 0, 7, + 242, 0, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 14, 16, 0, 2, 0, + 0, 0, 21, 0, 0, 1, + 79, 0, 0, 10, 50, 0, + 16, 0, 2, 0, 0, 0, + 166, 10, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 31, 0, + 4, 3, 10, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 8, 242, 0, 16, 0, + 3, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 8, 242, 0, + 16, 0, 4, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 6, + 130, 0, 16, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 5, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 167, 0, 0, 9, + 242, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 254, 17, 0, 0, 0, + 0, 0, 84, 0, 0, 7, + 242, 0, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 36, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 83, 0, 0, 7, + 242, 0, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 70, 14, + 16, 0, 6, 0, 0, 0, + 168, 0, 0, 8, 242, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 52, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 21, 0, 0, 1, + 167, 0, 0, 9, 242, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 36, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 52, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 1, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 55, 0, + 0, 15, 114, 0, 16, 0, + 6, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 55, 0, + 0, 12, 114, 0, 16, 0, + 6, 0, 0, 0, 86, 5, + 16, 0, 1, 0, 0, 0, + 70, 2, 16, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 2, 0, 0, 0, 32, 0, + 0, 10, 242, 0, 16, 0, + 7, 0, 0, 0, 166, 10, + 16, 0, 0, 0, 0, 0, + 2, 64, 0, 0, 8, 0, + 0, 0, 9, 0, 0, 0, + 10, 0, 0, 0, 11, 0, + 0, 0, 79, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 60, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 7, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 60, 0, + 0, 7, 226, 0, 16, 0, + 2, 0, 0, 0, 246, 6, + 16, 0, 1, 0, 0, 0, + 6, 13, 16, 0, 7, 0, + 0, 0, 54, 0, 0, 5, + 34, 0, 16, 0, 7, 0, + 0, 0, 42, 0, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 54, 0, 0, 5, 18, 0, + 16, 0, 7, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 8, 0, 0, 0, 58, 0, + 16, 0, 5, 0, 0, 0, + 54, 0, 0, 5, 66, 0, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 9, 0, + 0, 0, 246, 15, 16, 0, + 2, 0, 0, 0, 214, 4, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 55, 0, 0, 9, + 162, 0, 16, 0, 10, 0, + 0, 0, 246, 15, 16, 0, + 2, 0, 0, 0, 6, 4, + 16, 0, 8, 0, 0, 0, + 86, 13, 16, 0, 7, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 11, 0, + 0, 0, 26, 0, 16, 0, + 4, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 11, 0, 0, 0, 26, 0, + 16, 0, 5, 0, 0, 0, + 54, 0, 0, 5, 66, 0, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 2, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 9, 0, + 0, 0, 246, 15, 16, 0, + 0, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 54, 0, 0, 5, + 82, 0, 16, 0, 7, 0, + 0, 0, 6, 1, 16, 0, + 8, 0, 0, 0, 54, 0, + 0, 5, 82, 0, 16, 0, + 10, 0, 0, 0, 6, 1, + 16, 0, 11, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 7, 0, 0, 0, + 246, 15, 16, 0, 0, 0, + 0, 0, 134, 7, 16, 0, + 7, 0, 0, 0, 134, 7, + 16, 0, 10, 0, 0, 0, + 54, 0, 0, 5, 18, 0, + 16, 0, 10, 0, 0, 0, + 10, 0, 16, 0, 4, 0, + 0, 0, 54, 0, 0, 5, + 98, 0, 16, 0, 10, 0, + 0, 0, 6, 3, 16, 0, + 7, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 11, 0, 0, 0, 166, 10, + 16, 0, 2, 0, 0, 0, + 118, 14, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 54, 0, + 0, 5, 34, 0, 16, 0, + 10, 0, 0, 0, 10, 0, + 16, 0, 5, 0, 0, 0, + 54, 0, 0, 5, 66, 0, + 16, 0, 10, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 9, 0, + 0, 0, 166, 10, 16, 0, + 2, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 9, 0, + 0, 0, 54, 0, 0, 5, + 18, 0, 16, 0, 7, 0, + 0, 0, 26, 0, 16, 0, + 10, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 7, 0, 0, 0, 166, 10, + 16, 0, 2, 0, 0, 0, + 118, 14, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 10, 0, 0, 0, 86, 5, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 4, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 7, 0, 0, 0, 86, 5, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 5, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 55, 0, + 0, 9, 226, 0, 16, 0, + 2, 0, 0, 0, 86, 5, + 16, 0, 2, 0, 0, 0, + 6, 9, 16, 0, 8, 0, + 0, 0, 6, 9, 16, 0, + 9, 0, 0, 0, 31, 0, + 4, 3, 26, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 2, 64, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 84, 0, 0, 10, + 114, 0, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 0, 0, 0, 0, + 30, 0, 0, 10, 50, 0, + 16, 0, 9, 0, 0, 0, + 150, 5, 16, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 2, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 84, 0, + 0, 10, 50, 0, 16, 0, + 9, 0, 0, 0, 70, 0, + 16, 0, 9, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 2, 64, + 0, 0, 248, 0, 0, 0, + 248, 0, 0, 0, 248, 0, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 8, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 1, 0, 0, 10, + 194, 0, 16, 0, 9, 0, + 0, 0, 6, 4, 16, 0, + 9, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 252, 0, + 0, 0, 252, 0, 0, 0, + 85, 0, 0, 7, 50, 0, + 16, 0, 9, 0, 0, 0, + 70, 0, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 30, 0, + 0, 10, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 4, 0, + 0, 0, 4, 0, 0, 0, + 4, 0, 0, 0, 0, 0, + 0, 0, 84, 0, 0, 10, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 2, 64, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 10, 114, 0, + 16, 0, 12, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 2, 64, 0, 0, + 248, 0, 0, 0, 248, 0, + 0, 0, 248, 0, 0, 0, + 0, 0, 0, 0, 85, 0, + 0, 7, 114, 0, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 11, 0, 0, 0, + 1, 64, 0, 0, 5, 0, + 0, 0, 30, 0, 0, 7, + 114, 0, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 70, 2, + 16, 0, 12, 0, 0, 0, + 30, 0, 0, 7, 50, 0, + 16, 0, 9, 0, 0, 0, + 70, 0, 16, 0, 9, 0, + 0, 0, 230, 10, 16, 0, + 9, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 11, 0, 0, 0, 26, 0, + 16, 0, 9, 0, 0, 0, + 54, 0, 0, 5, 34, 0, + 16, 0, 12, 0, 0, 0, + 1, 64, 0, 0, 4, 0, + 0, 0, 18, 0, 0, 1, + 30, 0, 0, 10, 114, 0, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 10, 0, + 0, 0, 2, 64, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 84, 0, + 0, 10, 114, 0, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 2, 64, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 255, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 10, + 114, 0, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 2, 64, + 0, 0, 254, 0, 0, 0, + 254, 0, 0, 0, 254, 0, + 0, 0, 0, 0, 0, 0, + 85, 0, 0, 7, 114, 0, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 30, 0, + 0, 7, 114, 0, 16, 0, + 8, 0, 0, 0, 70, 2, + 16, 0, 10, 0, 0, 0, + 70, 2, 16, 0, 13, 0, + 0, 0, 30, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 84, 0, 0, 10, 114, 0, + 16, 0, 7, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 255, 0, 0, 0, 255, 0, + 0, 0, 255, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 10, 114, 0, 16, 0, + 10, 0, 0, 0, 70, 2, + 16, 0, 7, 0, 0, 0, + 2, 64, 0, 0, 254, 0, + 0, 0, 254, 0, 0, 0, + 254, 0, 0, 0, 0, 0, + 0, 0, 85, 0, 0, 7, + 114, 0, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 7, 0, 0, 0, + 30, 0, 0, 7, 114, 0, + 16, 0, 11, 0, 0, 0, + 70, 2, 16, 0, 7, 0, + 0, 0, 70, 2, 16, 0, + 10, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 9, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 11, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 54, 0, 0, 5, + 34, 0, 16, 0, 12, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 21, 0, + 0, 1, 32, 0, 0, 10, + 114, 0, 16, 0, 7, 0, + 0, 0, 246, 15, 16, 0, + 2, 0, 0, 0, 2, 64, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 55, 0, 0, 9, 194, 0, + 16, 0, 10, 0, 0, 0, + 166, 10, 16, 0, 7, 0, + 0, 0, 246, 11, 16, 0, + 3, 0, 0, 0, 166, 14, + 16, 0, 3, 0, 0, 0, + 54, 0, 0, 5, 50, 0, + 16, 0, 10, 0, 0, 0, + 70, 0, 16, 0, 3, 0, + 0, 0, 55, 0, 0, 9, + 226, 0, 16, 0, 10, 0, + 0, 0, 86, 5, 16, 0, + 7, 0, 0, 0, 246, 6, + 16, 0, 3, 0, 0, 0, + 86, 14, 16, 0, 10, 0, + 0, 0, 55, 0, 0, 9, + 242, 0, 16, 0, 10, 0, + 0, 0, 6, 0, 16, 0, + 7, 0, 0, 0, 118, 2, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 0, 10, 0, + 0, 0, 40, 0, 0, 5, + 114, 0, 16, 0, 13, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 40, 0, + 0, 5, 130, 0, 16, 0, + 13, 0, 0, 0, 10, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 7, 242, 0, + 16, 0, 14, 0, 0, 0, + 70, 14, 16, 0, 11, 0, + 0, 0, 70, 14, 16, 0, + 13, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 114, 0, 16, 0, 15, 0, + 0, 0, 70, 3, 16, 0, + 14, 0, 0, 0, 70, 3, + 16, 0, 14, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 15, 0, + 0, 0, 10, 0, 16, 0, + 15, 0, 0, 0, 35, 0, + 0, 9, 130, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 14, 0, 0, 0, + 42, 0, 16, 0, 14, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 242, 0, 16, 0, + 13, 0, 0, 0, 70, 14, + 16, 0, 10, 0, 0, 0, + 70, 14, 16, 0, 13, 0, + 0, 0, 38, 0, 0, 8, + 0, 208, 0, 0, 178, 0, + 16, 0, 13, 0, 0, 0, + 70, 12, 16, 0, 13, 0, + 0, 0, 70, 12, 16, 0, + 13, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 13, 0, 0, 0, + 10, 0, 16, 0, 13, 0, + 0, 0, 35, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 13, 0, 0, 0, 42, 0, + 16, 0, 13, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 8, + 242, 0, 16, 0, 10, 0, + 0, 0, 70, 14, 16, 128, + 65, 0, 0, 0, 11, 0, + 0, 0, 70, 14, 16, 0, + 10, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 178, 0, 16, 0, 10, 0, + 0, 0, 70, 12, 16, 0, + 10, 0, 0, 0, 70, 12, + 16, 0, 10, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 10, 0, + 0, 0, 10, 0, 16, 0, + 10, 0, 0, 0, 35, 0, + 0, 9, 66, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 34, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 40, 0, 0, 5, + 242, 0, 16, 0, 16, 0, + 0, 0, 70, 14, 16, 0, + 14, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 10, 0, 0, 0, 86, 5, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 11, 0, + 0, 0, 70, 2, 16, 0, + 8, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 8, 0, 0, 0, 86, 5, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 8, 0, + 0, 0, 70, 2, 16, 0, + 11, 0, 0, 0, 55, 0, + 0, 9, 114, 0, 16, 0, + 11, 0, 0, 0, 86, 5, + 16, 0, 2, 0, 0, 0, + 70, 2, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 34, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 13, 0, + 0, 0, 54, 0, 0, 5, + 34, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 11, 0, 0, 0, 54, 0, + 0, 5, 66, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 16, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 14, 0, + 0, 0, 55, 0, 0, 9, + 114, 0, 16, 0, 9, 0, + 0, 0, 86, 5, 16, 0, + 2, 0, 0, 0, 22, 6, + 16, 0, 9, 0, 0, 0, + 70, 3, 16, 0, 9, 0, + 0, 0, 33, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 43, 0, 0, 5, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 194, 0, 16, 0, 12, 0, + 0, 0, 86, 9, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 98, 0, + 16, 0, 6, 0, 0, 0, + 86, 6, 16, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 30, 0, + 0, 10, 50, 0, 16, 0, + 13, 0, 0, 0, 230, 10, + 16, 0, 12, 0, 0, 0, + 2, 64, 0, 0, 11, 0, + 0, 0, 11, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 33, 0, 0, 7, + 130, 0, 16, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 15, 0, 0, 0, + 43, 0, 0, 5, 130, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 15, 0, + 0, 0, 78, 0, 0, 11, + 0, 208, 0, 0, 50, 0, + 16, 0, 13, 0, 0, 0, + 70, 0, 16, 0, 13, 0, + 0, 0, 2, 64, 0, 0, + 68, 0, 0, 0, 68, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 8, 194, 0, 16, 0, + 13, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 80, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 13, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 3, 0, 4, 3, + 58, 0, 16, 0, 9, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 13, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 14, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 55, 0, 0, 9, 194, 0, + 16, 0, 16, 0, 0, 0, + 166, 10, 16, 0, 7, 0, + 0, 0, 246, 11, 16, 0, + 14, 0, 0, 0, 166, 14, + 16, 0, 14, 0, 0, 0, + 54, 0, 0, 5, 50, 0, + 16, 0, 16, 0, 0, 0, + 70, 0, 16, 0, 14, 0, + 0, 0, 55, 0, 0, 9, + 226, 0, 16, 0, 16, 0, + 0, 0, 86, 5, 16, 0, + 7, 0, 0, 0, 246, 6, + 16, 0, 14, 0, 0, 0, + 86, 14, 16, 0, 16, 0, + 0, 0, 55, 0, 0, 9, + 242, 0, 16, 0, 14, 0, + 0, 0, 6, 0, 16, 0, + 7, 0, 0, 0, 118, 2, + 16, 0, 14, 0, 0, 0, + 70, 14, 16, 0, 16, 0, + 0, 0, 30, 0, 0, 8, + 178, 0, 16, 0, 15, 0, + 0, 0, 70, 8, 16, 128, + 65, 0, 0, 0, 10, 0, + 0, 0, 70, 8, 16, 0, + 14, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 50, 0, 16, 0, 15, 0, + 0, 0, 70, 0, 16, 0, + 11, 0, 0, 0, 70, 0, + 16, 0, 15, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 15, 0, + 0, 0, 10, 0, 16, 0, + 15, 0, 0, 0, 35, 0, + 0, 9, 130, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 11, 0, 0, 0, + 58, 0, 16, 0, 15, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 33, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 60, 0, 0, 7, + 130, 0, 16, 0, 10, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 34, 0, 0, 7, 130, 0, + 16, 0, 11, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 43, 0, + 0, 5, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 56, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 253, 255, 125, 66, 14, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 28, 0, 0, 5, + 130, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 12, 0, + 0, 0, 55, 0, 0, 10, + 130, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 11, 0, 0, 0, 10, 144, + 144, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 10, 0, + 16, 0, 13, 0, 0, 0, + 55, 0, 0, 9, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 30, 0, 0, 8, 130, 0, + 16, 0, 10, 0, 0, 0, + 10, 0, 16, 128, 65, 0, + 0, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 14, 0, + 0, 0, 38, 0, 0, 8, + 0, 208, 0, 0, 130, 0, + 16, 0, 10, 0, 0, 0, + 42, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 33, 0, + 0, 7, 130, 0, 16, 0, + 11, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 60, 0, 0, 7, + 130, 0, 16, 0, 11, 0, + 0, 0, 58, 0, 16, 0, + 7, 0, 0, 0, 58, 0, + 16, 0, 11, 0, 0, 0, + 34, 0, 0, 7, 18, 0, + 16, 0, 15, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 42, 0, 16, 0, + 15, 0, 0, 0, 43, 0, + 0, 5, 130, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 56, 0, 0, 7, 130, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 253, 255, 125, 66, 14, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 28, 0, 0, 5, + 130, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 12, 0, + 0, 0, 55, 0, 0, 10, + 130, 0, 16, 0, 10, 0, + 0, 0, 10, 0, 16, 0, + 15, 0, 0, 0, 10, 144, + 144, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 26, 0, + 16, 0, 13, 0, 0, 0, + 55, 0, 0, 9, 130, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 11, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 26, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 9, 130, 0, 16, 0, + 11, 0, 0, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 26, 144, 144, 128, 65, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 38, 0, + 0, 9, 0, 208, 0, 0, + 178, 0, 16, 0, 15, 0, + 0, 0, 70, 8, 16, 0, + 8, 0, 0, 0, 86, 149, + 144, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 35, 0, + 0, 9, 178, 0, 16, 0, + 15, 0, 0, 0, 246, 15, + 16, 0, 11, 0, 0, 0, + 70, 8, 16, 0, 10, 0, + 0, 0, 70, 12, 16, 0, + 15, 0, 0, 0, 30, 0, + 0, 10, 178, 0, 16, 0, + 15, 0, 0, 0, 70, 12, + 16, 0, 15, 0, 0, 0, + 2, 64, 0, 0, 32, 0, + 0, 0, 32, 0, 0, 0, + 0, 0, 0, 0, 32, 0, + 0, 0, 85, 0, 0, 7, + 178, 0, 16, 0, 16, 0, + 0, 0, 70, 12, 16, 0, + 15, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 6, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 30, 0, + 0, 9, 130, 0, 16, 0, + 10, 0, 0, 0, 1, 64, + 0, 0, 64, 0, 0, 0, + 26, 144, 144, 128, 65, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 38, 0, + 0, 9, 0, 208, 0, 0, + 130, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 9, 0, 0, 0, 26, 144, + 144, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 35, 0, + 0, 9, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 10, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 30, 0, + 0, 7, 130, 0, 16, 0, + 9, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 1, 64, 0, 0, 32, 0, + 0, 0, 85, 0, 0, 7, + 34, 0, 16, 0, 15, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 79, 0, 0, 7, 114, 0, + 16, 0, 17, 0, 0, 0, + 70, 3, 16, 0, 16, 0, + 0, 0, 70, 2, 16, 0, + 14, 0, 0, 0, 54, 0, + 0, 5, 66, 0, 16, 0, + 16, 0, 0, 0, 10, 0, + 16, 0, 14, 0, 0, 0, + 55, 0, 0, 9, 146, 0, + 16, 0, 17, 0, 0, 0, + 6, 0, 16, 0, 17, 0, + 0, 0, 166, 2, 16, 0, + 16, 0, 0, 0, 6, 8, + 16, 0, 16, 0, 0, 0, + 54, 0, 0, 5, 82, 0, + 16, 0, 16, 0, 0, 0, + 86, 6, 16, 0, 14, 0, + 0, 0, 55, 0, 0, 9, + 242, 0, 16, 0, 16, 0, + 0, 0, 86, 10, 16, 0, + 17, 0, 0, 0, 70, 14, + 16, 0, 16, 0, 0, 0, + 22, 11, 16, 0, 16, 0, + 0, 0, 79, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 15, 0, 0, 0, 58, 0, + 16, 0, 14, 0, 0, 0, + 54, 0, 0, 5, 18, 0, + 16, 0, 15, 0, 0, 0, + 58, 0, 16, 0, 14, 0, + 0, 0, 55, 0, 0, 9, + 50, 0, 16, 0, 14, 0, + 0, 0, 246, 15, 16, 0, + 9, 0, 0, 0, 70, 0, + 16, 0, 15, 0, 0, 0, + 22, 5, 16, 0, 15, 0, + 0, 0, 40, 0, 0, 5, + 130, 0, 16, 0, 18, 0, + 0, 0, 58, 0, 16, 0, + 17, 0, 0, 0, 40, 0, + 0, 5, 98, 0, 16, 0, + 18, 0, 0, 0, 86, 7, + 16, 0, 16, 0, 0, 0, + 40, 0, 0, 5, 18, 0, + 16, 0, 18, 0, 0, 0, + 26, 0, 16, 0, 14, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 14, 0, + 0, 0, 10, 0, 16, 0, + 17, 0, 0, 0, 54, 0, + 0, 5, 98, 0, 16, 0, + 14, 0, 0, 0, 6, 2, + 16, 0, 16, 0, 0, 0, + 30, 0, 0, 7, 242, 0, + 16, 0, 14, 0, 0, 0, + 70, 14, 16, 0, 18, 0, + 0, 0, 70, 14, 16, 0, + 14, 0, 0, 0, 55, 0, + 0, 9, 194, 0, 16, 0, + 16, 0, 0, 0, 166, 10, + 16, 0, 7, 0, 0, 0, + 6, 8, 16, 0, 14, 0, + 0, 0, 166, 2, 16, 0, + 14, 0, 0, 0, 54, 0, + 0, 5, 50, 0, 16, 0, + 16, 0, 0, 0, 118, 15, + 16, 0, 14, 0, 0, 0, + 55, 0, 0, 9, 226, 0, + 16, 0, 16, 0, 0, 0, + 86, 5, 16, 0, 7, 0, + 0, 0, 6, 6, 16, 0, + 14, 0, 0, 0, 86, 14, + 16, 0, 16, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 14, 0, 0, 0, + 6, 0, 16, 0, 7, 0, + 0, 0, 70, 14, 16, 0, + 14, 0, 0, 0, 70, 14, + 16, 0, 16, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 50, 0, 16, 0, + 14, 0, 0, 0, 70, 0, + 16, 0, 14, 0, 0, 0, + 70, 0, 16, 0, 14, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 9, 0, + 0, 0, 26, 0, 16, 0, + 14, 0, 0, 0, 10, 0, + 16, 0, 14, 0, 0, 0, + 35, 0, 0, 9, 130, 0, + 16, 0, 9, 0, 0, 0, + 42, 0, 16, 0, 14, 0, + 0, 0, 42, 0, 16, 0, + 14, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 86, 0, 0, 5, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 86, 0, 0, 5, + 130, 0, 16, 0, 10, 0, + 0, 0, 58, 0, 16, 0, + 14, 0, 0, 0, 56, 0, + 0, 7, 130, 0, 16, 0, + 10, 0, 0, 0, 58, 0, + 16, 0, 10, 0, 0, 0, + 58, 0, 16, 0, 10, 0, + 0, 0, 50, 0, 0, 10, + 130, 0, 16, 0, 9, 0, + 0, 0, 58, 0, 16, 0, + 10, 0, 0, 0, 42, 128, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 58, 0, + 16, 0, 9, 0, 0, 0, + 28, 0, 0, 5, 130, 0, + 16, 0, 9, 0, 0, 0, + 58, 0, 16, 0, 9, 0, + 0, 0, 30, 0, 0, 7, + 66, 0, 16, 0, 13, 0, + 0, 0, 58, 0, 16, 0, + 9, 0, 0, 0, 42, 0, + 16, 0, 13, 0, 0, 0, + 30, 0, 0, 7, 130, 0, + 16, 0, 13, 0, 0, 0, + 58, 0, 16, 0, 13, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 22, 0, + 0, 1, 54, 0, 0, 5, + 18, 0, 16, 0, 12, 0, + 0, 0, 42, 0, 16, 0, + 13, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 6, 0, 0, 0, 58, 0, + 16, 0, 2, 0, 0, 0, + 18, 0, 0, 1, 31, 0, + 4, 3, 10, 0, 16, 0, + 1, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 7, 0, 0, 0, 42, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 244, 255, + 255, 255, 85, 0, 0, 7, + 34, 0, 16, 0, 7, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 10, 194, 0, + 16, 0, 0, 0, 0, 0, + 6, 4, 16, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 10, 242, 0, 16, 0, + 4, 0, 0, 0, 70, 14, + 16, 0, 4, 0, 0, 0, + 2, 64, 0, 0, 254, 255, + 255, 255, 254, 255, 255, 255, + 254, 255, 255, 255, 254, 255, + 255, 255, 30, 0, 0, 7, + 242, 0, 16, 0, 4, 0, + 0, 0, 166, 10, 16, 0, + 0, 0, 0, 0, 70, 14, + 16, 0, 4, 0, 0, 0, + 1, 0, 0, 10, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 254, 255, 255, 255, 254, 255, + 255, 255, 254, 255, 255, 255, + 254, 255, 255, 255, 30, 0, + 0, 7, 242, 0, 16, 0, + 5, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 30, 0, 0, 8, + 242, 0, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 128, + 65, 0, 0, 0, 4, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 194, 0, 16, 0, 0, 0, + 0, 0, 6, 4, 16, 0, + 8, 0, 0, 0, 6, 4, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 35, 0, + 0, 9, 66, 0, 16, 0, + 0, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 35, 0, + 0, 9, 66, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 8, 242, 0, 16, 0, + 3, 0, 0, 0, 70, 14, + 16, 0, 3, 0, 0, 0, + 70, 14, 16, 128, 65, 0, + 0, 0, 4, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 98, 0, 16, 0, + 2, 0, 0, 0, 6, 1, + 16, 0, 3, 0, 0, 0, + 6, 1, 16, 0, 8, 0, + 0, 0, 30, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 35, 0, 0, 9, 130, 0, + 16, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 8, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 35, 0, 0, 9, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 8, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 34, 0, 0, 7, 18, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 33, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 7, + 18, 0, 16, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 43, 0, 0, 5, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 56, 0, 0, 7, + 130, 0, 16, 0, 0, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 253, 255, 125, 66, + 28, 0, 0, 5, 130, 0, + 16, 0, 0, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 5, 0, 0, 0, + 79, 0, 0, 7, 130, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 0, 0, 0, 0, 1, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 58, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 1, 0, + 0, 0, 40, 0, 0, 5, + 242, 0, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 55, 0, + 0, 9, 242, 0, 16, 0, + 9, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 70, 14, 16, 0, + 4, 0, 0, 0, 55, 0, + 0, 9, 242, 0, 16, 0, + 4, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 4, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 55, 0, + 0, 9, 242, 0, 16, 0, + 3, 0, 0, 0, 246, 15, + 16, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 3, 0, + 0, 0, 70, 14, 16, 0, + 8, 0, 0, 0, 33, 0, + 0, 7, 130, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 43, 0, 0, 5, + 18, 0, 16, 0, 1, 0, + 0, 0, 42, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 8, 50, 0, 16, 0, + 12, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 80, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 12, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 3, 0, 4, 3, + 26, 0, 16, 0, 2, 0, + 0, 0, 30, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 12, 0, 0, 0, + 167, 0, 0, 9, 242, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 70, 254, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 8, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 128, 65, 0, + 0, 0, 9, 0, 0, 0, + 70, 14, 16, 0, 5, 0, + 0, 0, 38, 0, 0, 8, + 0, 208, 0, 0, 98, 0, + 16, 0, 2, 0, 0, 0, + 6, 1, 16, 0, 3, 0, + 0, 0, 6, 1, 16, 0, + 8, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 35, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 3, 0, 0, 0, 42, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 35, 0, 0, 9, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 3, 0, 0, 0, 58, 0, + 16, 0, 8, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 33, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 60, 0, 0, 7, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 0, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 34, 0, + 0, 7, 130, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 0, 0, + 0, 0, 43, 0, 0, 5, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 56, 0, + 0, 7, 34, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 253, 255, + 125, 66, 14, 0, 0, 7, + 34, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 10, 0, + 16, 0, 1, 0, 0, 0, + 28, 0, 0, 5, 34, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 55, 0, 0, 10, + 34, 0, 16, 0, 2, 0, + 0, 0, 58, 0, 16, 0, + 2, 0, 0, 0, 10, 144, + 144, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 15, 0, 0, 0, + 55, 0, 0, 9, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 9, 66, 0, + 16, 0, 2, 0, 0, 0, + 1, 64, 0, 0, 64, 0, + 0, 0, 26, 144, 144, 128, + 65, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 38, 0, 0, 9, 0, 208, + 0, 0, 242, 0, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 4, 0, 0, 0, + 86, 149, 144, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 35, 0, 0, 9, 242, 0, + 16, 0, 8, 0, 0, 0, + 166, 10, 16, 0, 2, 0, + 0, 0, 70, 14, 16, 0, + 9, 0, 0, 0, 70, 14, + 16, 0, 8, 0, 0, 0, + 30, 0, 0, 10, 242, 0, + 16, 0, 8, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 32, 0, 0, 0, 32, 0, + 0, 0, 32, 0, 0, 0, + 32, 0, 0, 0, 85, 0, + 0, 7, 242, 0, 16, 0, + 8, 0, 0, 0, 134, 13, + 16, 0, 8, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 79, 0, 0, 7, + 242, 0, 16, 0, 10, 0, + 0, 0, 134, 13, 16, 0, + 8, 0, 0, 0, 70, 14, + 16, 0, 5, 0, 0, 0, + 54, 0, 0, 5, 82, 0, + 16, 0, 11, 0, 0, 0, + 6, 1, 16, 0, 5, 0, + 0, 0, 54, 0, 0, 5, + 162, 0, 16, 0, 11, 0, + 0, 0, 6, 8, 16, 0, + 8, 0, 0, 0, 55, 0, + 0, 9, 242, 0, 16, 0, + 11, 0, 0, 0, 6, 5, + 16, 0, 10, 0, 0, 0, + 70, 14, 16, 0, 11, 0, + 0, 0, 22, 11, 16, 0, + 11, 0, 0, 0, 54, 0, + 0, 5, 82, 0, 16, 0, + 8, 0, 0, 0, 166, 11, + 16, 0, 5, 0, 0, 0, + 55, 0, 0, 9, 242, 0, + 16, 0, 5, 0, 0, 0, + 230, 14, 16, 0, 10, 0, + 0, 0, 214, 8, 16, 0, + 8, 0, 0, 0, 134, 13, + 16, 0, 8, 0, 0, 0, + 40, 0, 0, 5, 50, 0, + 16, 0, 8, 0, 0, 0, + 214, 5, 16, 0, 11, 0, + 0, 0, 40, 0, 0, 5, + 194, 0, 16, 0, 8, 0, + 0, 0, 6, 4, 16, 0, + 5, 0, 0, 0, 54, 0, + 0, 5, 50, 0, 16, 0, + 5, 0, 0, 0, 134, 0, + 16, 0, 11, 0, 0, 0, + 30, 0, 0, 7, 242, 0, + 16, 0, 5, 0, 0, 0, + 70, 14, 16, 0, 8, 0, + 0, 0, 70, 14, 16, 0, + 5, 0, 0, 0, 38, 0, + 0, 8, 0, 208, 0, 0, + 98, 0, 16, 0, 2, 0, + 0, 0, 6, 1, 16, 0, + 5, 0, 0, 0, 6, 1, + 16, 0, 5, 0, 0, 0, + 30, 0, 0, 7, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 35, 0, + 0, 9, 34, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 5, 0, 0, 0, + 42, 0, 16, 0, 5, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 86, 0, + 0, 5, 34, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 86, 0, 0, 5, 66, 0, + 16, 0, 2, 0, 0, 0, + 58, 0, 16, 0, 5, 0, + 0, 0, 56, 0, 0, 7, + 66, 0, 16, 0, 2, 0, + 0, 0, 42, 0, 16, 0, + 2, 0, 0, 0, 42, 0, + 16, 0, 2, 0, 0, 0, + 50, 0, 0, 10, 34, 0, + 16, 0, 2, 0, 0, 0, + 42, 0, 16, 0, 2, 0, + 0, 0, 42, 128, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 2, 0, 0, 0, 28, 0, + 0, 5, 34, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 2, 0, 0, 0, + 30, 0, 0, 7, 18, 0, + 16, 0, 12, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 12, 0, 0, 0, 30, 0, + 0, 7, 34, 0, 16, 0, + 12, 0, 0, 0, 26, 0, + 16, 0, 12, 0, 0, 0, + 1, 64, 0, 0, 1, 0, + 0, 0, 22, 0, 0, 1, + 54, 0, 0, 5, 34, 0, + 16, 0, 12, 0, 0, 0, + 1, 64, 0, 0, 6, 0, + 0, 0, 54, 0, 0, 5, + 130, 0, 16, 0, 6, 0, + 0, 0, 10, 0, 16, 0, + 7, 0, 0, 0, 18, 0, + 0, 1, 54, 0, 0, 8, + 50, 0, 16, 0, 12, 0, + 0, 0, 2, 64, 0, 0, + 255, 255, 255, 255, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 5, 130, 0, 16, 0, + 6, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 21, 0, 0, 1, 21, 0, + 0, 1, 168, 0, 0, 8, + 50, 240, 17, 0, 0, 0, + 0, 0, 10, 64, 2, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 70, 0, 16, 0, + 12, 0, 0, 0, 168, 0, + 0, 8, 50, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 198, 0, + 16, 0, 6, 0, 0, 0, + 31, 0, 4, 3, 26, 0, + 16, 0, 1, 0, 0, 0, + 30, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 8, 0, 0, 0, + 167, 0, 0, 9, 98, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 241, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 79, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 12, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 50, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 134, 0, + 16, 0, 3, 0, 0, 0, + 168, 0, 0, 8, 50, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 70, 0, 16, 0, 4, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 31, 0, + 4, 3, 42, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 8, 18, 0, 16, 0, + 3, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 4, 0, 0, 0, + 167, 0, 0, 9, 98, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 241, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 5, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 79, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 4, 0, + 0, 0, 10, 0, 16, 0, + 3, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 4, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 50, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 134, 0, + 16, 0, 4, 0, 0, 0, + 168, 0, 0, 8, 50, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 70, 0, 16, 0, 5, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 31, 0, + 4, 3, 58, 0, 16, 0, + 1, 0, 0, 0, 167, 0, + 0, 8, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 2, 0, 0, 0, + 167, 0, 0, 9, 98, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 241, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 4, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 79, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 3, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 3, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 50, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 134, 0, + 16, 0, 3, 0, 0, 0, + 168, 0, 0, 8, 50, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 70, 0, 16, 0, 4, 0, + 0, 0, 21, 0, 0, 1, + 21, 0, 0, 1, 31, 0, + 4, 3, 10, 0, 16, 0, + 2, 0, 0, 0, 167, 0, + 0, 8, 18, 0, 16, 0, + 1, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 240, + 17, 0, 0, 0, 0, 0, + 30, 0, 0, 6, 34, 0, + 16, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 167, 0, 0, 9, 98, 0, + 16, 0, 2, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 6, 241, + 17, 0, 0, 0, 0, 0, + 167, 0, 0, 9, 50, 0, + 16, 0, 3, 0, 0, 0, + 26, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 28, 0, 0, 0, 70, 240, + 17, 0, 0, 0, 0, 0, + 79, 0, 0, 7, 66, 0, + 16, 0, 0, 0, 0, 0, + 26, 0, 16, 0, 2, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 31, 0, + 4, 3, 42, 0, 16, 0, + 0, 0, 0, 0, 167, 0, + 0, 9, 18, 0, 16, 0, + 2, 0, 0, 0, 26, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 16, 0, + 0, 0, 6, 240, 17, 0, + 0, 0, 0, 0, 168, 0, + 0, 8, 50, 240, 17, 0, + 0, 0, 0, 0, 10, 64, + 2, 0, 1, 64, 0, 0, + 16, 0, 0, 0, 134, 0, + 16, 0, 2, 0, 0, 0, + 168, 0, 0, 8, 50, 240, + 17, 0, 0, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 70, 0, 16, 0, 3, 0, + 0, 0, 21, 0, 0, 1, + 167, 0, 0, 8, 146, 0, + 16, 0, 1, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 28, 0, 0, 0, + 6, 244, 17, 0, 0, 0, + 0, 0, 41, 0, 0, 7, + 34, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 1, 0, 0, 0, 1, 64, + 0, 0, 31, 0, 0, 0, + 167, 0, 0, 8, 50, 0, + 16, 0, 1, 0, 0, 0, + 10, 64, 2, 0, 1, 64, + 0, 0, 16, 0, 0, 0, + 70, 240, 17, 0, 0, 0, + 0, 0, 60, 0, 0, 7, + 34, 0, 16, 0, 1, 0, + 0, 0, 26, 0, 16, 0, + 0, 0, 0, 0, 26, 0, + 16, 0, 1, 0, 0, 0, + 54, 0, 0, 5, 66, 0, + 16, 0, 1, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 0, 0, 168, 0, 0, 9, + 242, 224, 17, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 1, 0, + 0, 0, 21, 0, 0, 1, + 62, 0, 0, 1 +}; diff --git a/deps/DirectXTex/DirectXTex/d3dx12.h b/deps/DirectXTex/DirectXTex/d3dx12.h new file mode 100644 index 0000000..89febc4 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/d3dx12.h @@ -0,0 +1,2552 @@ +//********************************************************* +// +// Copyright (c) Microsoft. All rights reserved. +// This code is licensed under the MIT License (MIT). +// THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY +// IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR +// PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. +// +//********************************************************* + +#ifndef __D3DX12_H__ +#define __D3DX12_H__ + +#include "d3d12.h" + +#if defined( __cplusplus ) + +struct CD3DX12_DEFAULT {}; +extern const DECLSPEC_SELECTANY CD3DX12_DEFAULT D3D12_DEFAULT; + +//------------------------------------------------------------------------------------------------ +inline bool operator==( const D3D12_VIEWPORT& l, const D3D12_VIEWPORT& r ) +{ + return l.TopLeftX == r.TopLeftX && l.TopLeftY == r.TopLeftY && l.Width == r.Width && + l.Height == r.Height && l.MinDepth == r.MinDepth && l.MaxDepth == r.MaxDepth; +} + +//------------------------------------------------------------------------------------------------ +inline bool operator!=( const D3D12_VIEWPORT& l, const D3D12_VIEWPORT& r ) +{ return !( l == r ); } + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_RECT : public D3D12_RECT +{ + CD3DX12_RECT() + {} + explicit CD3DX12_RECT( const D3D12_RECT& o ) : + D3D12_RECT( o ) + {} + explicit CD3DX12_RECT( + LONG Left, + LONG Top, + LONG Right, + LONG Bottom ) + { + left = Left; + top = Top; + right = Right; + bottom = Bottom; + } + ~CD3DX12_RECT() {} + operator const D3D12_RECT&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_VIEWPORT : public D3D12_VIEWPORT +{ + CD3DX12_VIEWPORT() + {} + explicit CD3DX12_VIEWPORT( const D3D12_VIEWPORT& o ) : + D3D12_VIEWPORT( o ) + {} + explicit CD3DX12_VIEWPORT( + FLOAT topLeftX, + FLOAT topLeftY, + FLOAT width, + FLOAT height, + FLOAT minDepth = D3D12_MIN_DEPTH, + FLOAT maxDepth = D3D12_MAX_DEPTH ) + { + TopLeftX = topLeftX; + TopLeftY = topLeftY; + Width = width; + Height = height; + MinDepth = minDepth; + MaxDepth = maxDepth; + } + explicit CD3DX12_VIEWPORT( + _In_ ID3D12Resource* pResource, + UINT mipSlice = 0, + FLOAT topLeftX = 0.0f, + FLOAT topLeftY = 0.0f, + FLOAT minDepth = D3D12_MIN_DEPTH, + FLOAT maxDepth = D3D12_MAX_DEPTH ) + { + D3D12_RESOURCE_DESC Desc = pResource->GetDesc(); + const UINT64 SubresourceWidth = Desc.Width >> mipSlice; + const UINT64 SubresourceHeight = Desc.Height >> mipSlice; + switch (Desc.Dimension) + { + case D3D12_RESOURCE_DIMENSION_BUFFER: + TopLeftX = topLeftX; + TopLeftY = 0.0f; + Width = Desc.Width - topLeftX; + Height = 1.0f; + break; + case D3D12_RESOURCE_DIMENSION_TEXTURE1D: + TopLeftX = topLeftX; + TopLeftY = 0.0f; + Width = (SubresourceWidth ? SubresourceWidth : 1.0f) - topLeftX; + Height = 1.0f; + break; + case D3D12_RESOURCE_DIMENSION_TEXTURE2D: + case D3D12_RESOURCE_DIMENSION_TEXTURE3D: + TopLeftX = topLeftX; + TopLeftY = topLeftY; + Width = (SubresourceWidth ? SubresourceWidth : 1.0f) - topLeftX; + Height = (SubresourceHeight ? SubresourceHeight: 1.0f) - topLeftY; + break; + default: break; + } + + MinDepth = minDepth; + MaxDepth = maxDepth; + } + ~CD3DX12_VIEWPORT() {} + operator const D3D12_VIEWPORT&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_BOX : public D3D12_BOX +{ + CD3DX12_BOX() + {} + explicit CD3DX12_BOX( const D3D12_BOX& o ) : + D3D12_BOX( o ) + {} + explicit CD3DX12_BOX( + LONG Left, + LONG Right ) + { + left = Left; + top = 0; + front = 0; + right = Right; + bottom = 1; + back = 1; + } + explicit CD3DX12_BOX( + LONG Left, + LONG Top, + LONG Right, + LONG Bottom ) + { + left = Left; + top = Top; + front = 0; + right = Right; + bottom = Bottom; + back = 1; + } + explicit CD3DX12_BOX( + LONG Left, + LONG Top, + LONG Front, + LONG Right, + LONG Bottom, + LONG Back ) + { + left = Left; + top = Top; + front = Front; + right = Right; + bottom = Bottom; + back = Back; + } + ~CD3DX12_BOX() {} + operator const D3D12_BOX&() const { return *this; } +}; +inline bool operator==( const D3D12_BOX& l, const D3D12_BOX& r ) +{ + return l.left == r.left && l.top == r.top && l.front == r.front && + l.right == r.right && l.bottom == r.bottom && l.back == r.back; +} +inline bool operator!=( const D3D12_BOX& l, const D3D12_BOX& r ) +{ return !( l == r ); } + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_DEPTH_STENCIL_DESC : public D3D12_DEPTH_STENCIL_DESC +{ + CD3DX12_DEPTH_STENCIL_DESC() + {} + explicit CD3DX12_DEPTH_STENCIL_DESC( const D3D12_DEPTH_STENCIL_DESC& o ) : + D3D12_DEPTH_STENCIL_DESC( o ) + {} + explicit CD3DX12_DEPTH_STENCIL_DESC( CD3DX12_DEFAULT ) + { + DepthEnable = TRUE; + DepthWriteMask = D3D12_DEPTH_WRITE_MASK_ALL; + DepthFunc = D3D12_COMPARISON_FUNC_LESS; + StencilEnable = FALSE; + StencilReadMask = D3D12_DEFAULT_STENCIL_READ_MASK; + StencilWriteMask = D3D12_DEFAULT_STENCIL_WRITE_MASK; + const D3D12_DEPTH_STENCILOP_DESC defaultStencilOp = + { D3D12_STENCIL_OP_KEEP, D3D12_STENCIL_OP_KEEP, D3D12_STENCIL_OP_KEEP, D3D12_COMPARISON_FUNC_ALWAYS }; + FrontFace = defaultStencilOp; + BackFace = defaultStencilOp; + } + explicit CD3DX12_DEPTH_STENCIL_DESC( + BOOL depthEnable, + D3D12_DEPTH_WRITE_MASK depthWriteMask, + D3D12_COMPARISON_FUNC depthFunc, + BOOL stencilEnable, + UINT8 stencilReadMask, + UINT8 stencilWriteMask, + D3D12_STENCIL_OP frontStencilFailOp, + D3D12_STENCIL_OP frontStencilDepthFailOp, + D3D12_STENCIL_OP frontStencilPassOp, + D3D12_COMPARISON_FUNC frontStencilFunc, + D3D12_STENCIL_OP backStencilFailOp, + D3D12_STENCIL_OP backStencilDepthFailOp, + D3D12_STENCIL_OP backStencilPassOp, + D3D12_COMPARISON_FUNC backStencilFunc ) + { + DepthEnable = depthEnable; + DepthWriteMask = depthWriteMask; + DepthFunc = depthFunc; + StencilEnable = stencilEnable; + StencilReadMask = stencilReadMask; + StencilWriteMask = stencilWriteMask; + FrontFace.StencilFailOp = frontStencilFailOp; + FrontFace.StencilDepthFailOp = frontStencilDepthFailOp; + FrontFace.StencilPassOp = frontStencilPassOp; + FrontFace.StencilFunc = frontStencilFunc; + BackFace.StencilFailOp = backStencilFailOp; + BackFace.StencilDepthFailOp = backStencilDepthFailOp; + BackFace.StencilPassOp = backStencilPassOp; + BackFace.StencilFunc = backStencilFunc; + } + ~CD3DX12_DEPTH_STENCIL_DESC() {} + operator const D3D12_DEPTH_STENCIL_DESC&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +// Requires the Windows 10 Creators Update SDK (15063) +#if defined(NTDDI_WIN10_RS2) && (NTDDI_VERSION >= NTDDI_WIN10_RS2) +struct CD3DX12_DEPTH_STENCIL_DESC1 : public D3D12_DEPTH_STENCIL_DESC1 +{ + CD3DX12_DEPTH_STENCIL_DESC1() + {} + explicit CD3DX12_DEPTH_STENCIL_DESC1( const D3D12_DEPTH_STENCIL_DESC1& o ) : + D3D12_DEPTH_STENCIL_DESC1( o ) + {} + explicit CD3DX12_DEPTH_STENCIL_DESC1( const D3D12_DEPTH_STENCIL_DESC& o ) + { + DepthEnable = o.DepthEnable; + DepthWriteMask = o.DepthWriteMask; + DepthFunc = o.DepthFunc; + StencilEnable = o.StencilEnable; + StencilReadMask = o.StencilReadMask; + StencilWriteMask = o.StencilWriteMask; + FrontFace.StencilFailOp = o.FrontFace.StencilFailOp; + FrontFace.StencilDepthFailOp = o.FrontFace.StencilDepthFailOp; + FrontFace.StencilPassOp = o.FrontFace.StencilPassOp; + FrontFace.StencilFunc = o.FrontFace.StencilFunc; + BackFace.StencilFailOp = o.BackFace.StencilFailOp; + BackFace.StencilDepthFailOp = o.BackFace.StencilDepthFailOp; + BackFace.StencilPassOp = o.BackFace.StencilPassOp; + BackFace.StencilFunc = o.BackFace.StencilFunc; + DepthBoundsTestEnable = FALSE; + } + explicit CD3DX12_DEPTH_STENCIL_DESC1( CD3DX12_DEFAULT ) + { + DepthEnable = TRUE; + DepthWriteMask = D3D12_DEPTH_WRITE_MASK_ALL; + DepthFunc = D3D12_COMPARISON_FUNC_LESS; + StencilEnable = FALSE; + StencilReadMask = D3D12_DEFAULT_STENCIL_READ_MASK; + StencilWriteMask = D3D12_DEFAULT_STENCIL_WRITE_MASK; + const D3D12_DEPTH_STENCILOP_DESC defaultStencilOp = + { D3D12_STENCIL_OP_KEEP, D3D12_STENCIL_OP_KEEP, D3D12_STENCIL_OP_KEEP, D3D12_COMPARISON_FUNC_ALWAYS }; + FrontFace = defaultStencilOp; + BackFace = defaultStencilOp; + DepthBoundsTestEnable = FALSE; + } + explicit CD3DX12_DEPTH_STENCIL_DESC1( + BOOL depthEnable, + D3D12_DEPTH_WRITE_MASK depthWriteMask, + D3D12_COMPARISON_FUNC depthFunc, + BOOL stencilEnable, + UINT8 stencilReadMask, + UINT8 stencilWriteMask, + D3D12_STENCIL_OP frontStencilFailOp, + D3D12_STENCIL_OP frontStencilDepthFailOp, + D3D12_STENCIL_OP frontStencilPassOp, + D3D12_COMPARISON_FUNC frontStencilFunc, + D3D12_STENCIL_OP backStencilFailOp, + D3D12_STENCIL_OP backStencilDepthFailOp, + D3D12_STENCIL_OP backStencilPassOp, + D3D12_COMPARISON_FUNC backStencilFunc, + BOOL depthBoundsTestEnable ) + { + DepthEnable = depthEnable; + DepthWriteMask = depthWriteMask; + DepthFunc = depthFunc; + StencilEnable = stencilEnable; + StencilReadMask = stencilReadMask; + StencilWriteMask = stencilWriteMask; + FrontFace.StencilFailOp = frontStencilFailOp; + FrontFace.StencilDepthFailOp = frontStencilDepthFailOp; + FrontFace.StencilPassOp = frontStencilPassOp; + FrontFace.StencilFunc = frontStencilFunc; + BackFace.StencilFailOp = backStencilFailOp; + BackFace.StencilDepthFailOp = backStencilDepthFailOp; + BackFace.StencilPassOp = backStencilPassOp; + BackFace.StencilFunc = backStencilFunc; + DepthBoundsTestEnable = depthBoundsTestEnable; + } + ~CD3DX12_DEPTH_STENCIL_DESC1() {} + operator const D3D12_DEPTH_STENCIL_DESC1&() const { return *this; } + operator const D3D12_DEPTH_STENCIL_DESC() const + { + D3D12_DEPTH_STENCIL_DESC D; + D.DepthEnable = DepthEnable; + D.DepthWriteMask = DepthWriteMask; + D.DepthFunc = DepthFunc; + D.StencilEnable = StencilEnable; + D.StencilReadMask = StencilReadMask; + D.StencilWriteMask = StencilWriteMask; + D.FrontFace.StencilFailOp = FrontFace.StencilFailOp; + D.FrontFace.StencilDepthFailOp = FrontFace.StencilDepthFailOp; + D.FrontFace.StencilPassOp = FrontFace.StencilPassOp; + D.FrontFace.StencilFunc = FrontFace.StencilFunc; + D.BackFace.StencilFailOp = BackFace.StencilFailOp; + D.BackFace.StencilDepthFailOp = BackFace.StencilDepthFailOp; + D.BackFace.StencilPassOp = BackFace.StencilPassOp; + D.BackFace.StencilFunc = BackFace.StencilFunc; + return D; + } +}; +#endif + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_BLEND_DESC : public D3D12_BLEND_DESC +{ + CD3DX12_BLEND_DESC() + {} + explicit CD3DX12_BLEND_DESC( const D3D12_BLEND_DESC& o ) : + D3D12_BLEND_DESC( o ) + {} + explicit CD3DX12_BLEND_DESC( CD3DX12_DEFAULT ) + { + AlphaToCoverageEnable = FALSE; + IndependentBlendEnable = FALSE; + const D3D12_RENDER_TARGET_BLEND_DESC defaultRenderTargetBlendDesc = + { + FALSE,FALSE, + D3D12_BLEND_ONE, D3D12_BLEND_ZERO, D3D12_BLEND_OP_ADD, + D3D12_BLEND_ONE, D3D12_BLEND_ZERO, D3D12_BLEND_OP_ADD, + D3D12_LOGIC_OP_NOOP, + D3D12_COLOR_WRITE_ENABLE_ALL, + }; + for (UINT i = 0; i < D3D12_SIMULTANEOUS_RENDER_TARGET_COUNT; ++i) + RenderTarget[ i ] = defaultRenderTargetBlendDesc; + } + ~CD3DX12_BLEND_DESC() {} + operator const D3D12_BLEND_DESC&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_RASTERIZER_DESC : public D3D12_RASTERIZER_DESC +{ + CD3DX12_RASTERIZER_DESC() + {} + explicit CD3DX12_RASTERIZER_DESC( const D3D12_RASTERIZER_DESC& o ) : + D3D12_RASTERIZER_DESC( o ) + {} + explicit CD3DX12_RASTERIZER_DESC( CD3DX12_DEFAULT ) + { + FillMode = D3D12_FILL_MODE_SOLID; + CullMode = D3D12_CULL_MODE_BACK; + FrontCounterClockwise = FALSE; + DepthBias = D3D12_DEFAULT_DEPTH_BIAS; + DepthBiasClamp = D3D12_DEFAULT_DEPTH_BIAS_CLAMP; + SlopeScaledDepthBias = D3D12_DEFAULT_SLOPE_SCALED_DEPTH_BIAS; + DepthClipEnable = TRUE; + MultisampleEnable = FALSE; + AntialiasedLineEnable = FALSE; + ForcedSampleCount = 0; + ConservativeRaster = D3D12_CONSERVATIVE_RASTERIZATION_MODE_OFF; + } + explicit CD3DX12_RASTERIZER_DESC( + D3D12_FILL_MODE fillMode, + D3D12_CULL_MODE cullMode, + BOOL frontCounterClockwise, + INT depthBias, + FLOAT depthBiasClamp, + FLOAT slopeScaledDepthBias, + BOOL depthClipEnable, + BOOL multisampleEnable, + BOOL antialiasedLineEnable, + UINT forcedSampleCount, + D3D12_CONSERVATIVE_RASTERIZATION_MODE conservativeRaster) + { + FillMode = fillMode; + CullMode = cullMode; + FrontCounterClockwise = frontCounterClockwise; + DepthBias = depthBias; + DepthBiasClamp = depthBiasClamp; + SlopeScaledDepthBias = slopeScaledDepthBias; + DepthClipEnable = depthClipEnable; + MultisampleEnable = multisampleEnable; + AntialiasedLineEnable = antialiasedLineEnable; + ForcedSampleCount = forcedSampleCount; + ConservativeRaster = conservativeRaster; + } + ~CD3DX12_RASTERIZER_DESC() {} + operator const D3D12_RASTERIZER_DESC&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_RESOURCE_ALLOCATION_INFO : public D3D12_RESOURCE_ALLOCATION_INFO +{ + CD3DX12_RESOURCE_ALLOCATION_INFO() + {} + explicit CD3DX12_RESOURCE_ALLOCATION_INFO( const D3D12_RESOURCE_ALLOCATION_INFO& o ) : + D3D12_RESOURCE_ALLOCATION_INFO( o ) + {} + CD3DX12_RESOURCE_ALLOCATION_INFO( + UINT64 size, + UINT64 alignment ) + { + SizeInBytes = size; + Alignment = alignment; + } + operator const D3D12_RESOURCE_ALLOCATION_INFO&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_HEAP_PROPERTIES : public D3D12_HEAP_PROPERTIES +{ + CD3DX12_HEAP_PROPERTIES() + {} + explicit CD3DX12_HEAP_PROPERTIES(const D3D12_HEAP_PROPERTIES &o) : + D3D12_HEAP_PROPERTIES(o) + {} + CD3DX12_HEAP_PROPERTIES( + D3D12_CPU_PAGE_PROPERTY cpuPageProperty, + D3D12_MEMORY_POOL memoryPoolPreference, + UINT creationNodeMask = 1, + UINT nodeMask = 1 ) + { + Type = D3D12_HEAP_TYPE_CUSTOM; + CPUPageProperty = cpuPageProperty; + MemoryPoolPreference = memoryPoolPreference; + CreationNodeMask = creationNodeMask; + VisibleNodeMask = nodeMask; + } + explicit CD3DX12_HEAP_PROPERTIES( + D3D12_HEAP_TYPE type, + UINT creationNodeMask = 1, + UINT nodeMask = 1 ) + { + Type = type; + CPUPageProperty = D3D12_CPU_PAGE_PROPERTY_UNKNOWN; + MemoryPoolPreference = D3D12_MEMORY_POOL_UNKNOWN; + CreationNodeMask = creationNodeMask; + VisibleNodeMask = nodeMask; + } + operator const D3D12_HEAP_PROPERTIES&() const { return *this; } + bool IsCPUAccessible() const + { + return Type == D3D12_HEAP_TYPE_UPLOAD || Type == D3D12_HEAP_TYPE_READBACK || (Type == D3D12_HEAP_TYPE_CUSTOM && + (CPUPageProperty == D3D12_CPU_PAGE_PROPERTY_WRITE_COMBINE || CPUPageProperty == D3D12_CPU_PAGE_PROPERTY_WRITE_BACK)); + } +}; +inline bool operator==( const D3D12_HEAP_PROPERTIES& l, const D3D12_HEAP_PROPERTIES& r ) +{ + return l.Type == r.Type && l.CPUPageProperty == r.CPUPageProperty && + l.MemoryPoolPreference == r.MemoryPoolPreference && + l.CreationNodeMask == r.CreationNodeMask && + l.VisibleNodeMask == r.VisibleNodeMask; +} +inline bool operator!=( const D3D12_HEAP_PROPERTIES& l, const D3D12_HEAP_PROPERTIES& r ) +{ return !( l == r ); } + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_HEAP_DESC : public D3D12_HEAP_DESC +{ + CD3DX12_HEAP_DESC() + {} + explicit CD3DX12_HEAP_DESC(const D3D12_HEAP_DESC &o) : + D3D12_HEAP_DESC(o) + {} + CD3DX12_HEAP_DESC( + UINT64 size, + D3D12_HEAP_PROPERTIES properties, + UINT64 alignment = 0, + D3D12_HEAP_FLAGS flags = D3D12_HEAP_FLAG_NONE ) + { + SizeInBytes = size; + Properties = properties; + Alignment = alignment; + Flags = flags; + } + CD3DX12_HEAP_DESC( + UINT64 size, + D3D12_HEAP_TYPE type, + UINT64 alignment = 0, + D3D12_HEAP_FLAGS flags = D3D12_HEAP_FLAG_NONE ) + { + SizeInBytes = size; + Properties = CD3DX12_HEAP_PROPERTIES( type ); + Alignment = alignment; + Flags = flags; + } + CD3DX12_HEAP_DESC( + UINT64 size, + D3D12_CPU_PAGE_PROPERTY cpuPageProperty, + D3D12_MEMORY_POOL memoryPoolPreference, + UINT64 alignment = 0, + D3D12_HEAP_FLAGS flags = D3D12_HEAP_FLAG_NONE ) + { + SizeInBytes = size; + Properties = CD3DX12_HEAP_PROPERTIES( cpuPageProperty, memoryPoolPreference ); + Alignment = alignment; + Flags = flags; + } + CD3DX12_HEAP_DESC( + const D3D12_RESOURCE_ALLOCATION_INFO& resAllocInfo, + D3D12_HEAP_PROPERTIES properties, + D3D12_HEAP_FLAGS flags = D3D12_HEAP_FLAG_NONE ) + { + SizeInBytes = resAllocInfo.SizeInBytes; + Properties = properties; + Alignment = resAllocInfo.Alignment; + Flags = flags; + } + CD3DX12_HEAP_DESC( + const D3D12_RESOURCE_ALLOCATION_INFO& resAllocInfo, + D3D12_HEAP_TYPE type, + D3D12_HEAP_FLAGS flags = D3D12_HEAP_FLAG_NONE ) + { + SizeInBytes = resAllocInfo.SizeInBytes; + Properties = CD3DX12_HEAP_PROPERTIES( type ); + Alignment = resAllocInfo.Alignment; + Flags = flags; + } + CD3DX12_HEAP_DESC( + const D3D12_RESOURCE_ALLOCATION_INFO& resAllocInfo, + D3D12_CPU_PAGE_PROPERTY cpuPageProperty, + D3D12_MEMORY_POOL memoryPoolPreference, + D3D12_HEAP_FLAGS flags = D3D12_HEAP_FLAG_NONE ) + { + SizeInBytes = resAllocInfo.SizeInBytes; + Properties = CD3DX12_HEAP_PROPERTIES( cpuPageProperty, memoryPoolPreference ); + Alignment = resAllocInfo.Alignment; + Flags = flags; + } + operator const D3D12_HEAP_DESC&() const { return *this; } + bool IsCPUAccessible() const + { return static_cast< const CD3DX12_HEAP_PROPERTIES* >( &Properties )->IsCPUAccessible(); } +}; +inline bool operator==( const D3D12_HEAP_DESC& l, const D3D12_HEAP_DESC& r ) +{ + return l.SizeInBytes == r.SizeInBytes && + l.Properties == r.Properties && + l.Alignment == r.Alignment && + l.Flags == r.Flags; +} +inline bool operator!=( const D3D12_HEAP_DESC& l, const D3D12_HEAP_DESC& r ) +{ return !( l == r ); } + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_CLEAR_VALUE : public D3D12_CLEAR_VALUE +{ + CD3DX12_CLEAR_VALUE() + {} + explicit CD3DX12_CLEAR_VALUE(const D3D12_CLEAR_VALUE &o) : + D3D12_CLEAR_VALUE(o) + {} + CD3DX12_CLEAR_VALUE( + DXGI_FORMAT format, + const FLOAT color[4] ) + { + Format = format; + memcpy( Color, color, sizeof( Color ) ); + } + CD3DX12_CLEAR_VALUE( + DXGI_FORMAT format, + FLOAT depth, + UINT8 stencil ) + { + Format = format; + /* Use memcpy to preserve NAN values */ + memcpy( &DepthStencil.Depth, &depth, sizeof( depth ) ); + DepthStencil.Stencil = stencil; + } + operator const D3D12_CLEAR_VALUE&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_RANGE : public D3D12_RANGE +{ + CD3DX12_RANGE() + {} + explicit CD3DX12_RANGE(const D3D12_RANGE &o) : + D3D12_RANGE(o) + {} + CD3DX12_RANGE( + SIZE_T begin, + SIZE_T end ) + { + Begin = begin; + End = end; + } + operator const D3D12_RANGE&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +// Requires the Windows 10 Creators Update SDK (15063) +#if defined(NTDDI_WIN10_RS2) && (NTDDI_VERSION >= NTDDI_WIN10_RS2) +struct CD3DX12_RANGE_UINT64 : public D3D12_RANGE_UINT64 +{ + CD3DX12_RANGE_UINT64() + {} + explicit CD3DX12_RANGE_UINT64(const D3D12_RANGE_UINT64 &o) : + D3D12_RANGE_UINT64(o) + {} + CD3DX12_RANGE_UINT64( + UINT64 begin, + UINT64 end ) + { + Begin = begin; + End = end; + } + operator const D3D12_RANGE_UINT64&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_SUBRESOURCE_RANGE_UINT64 : public D3D12_SUBRESOURCE_RANGE_UINT64 +{ + CD3DX12_SUBRESOURCE_RANGE_UINT64() + {} + explicit CD3DX12_SUBRESOURCE_RANGE_UINT64(const D3D12_SUBRESOURCE_RANGE_UINT64 &o) : + D3D12_SUBRESOURCE_RANGE_UINT64(o) + {} + CD3DX12_SUBRESOURCE_RANGE_UINT64( + UINT subresource, + const D3D12_RANGE_UINT64& range ) + { + Subresource = subresource; + Range = range; + } + CD3DX12_SUBRESOURCE_RANGE_UINT64( + UINT subresource, + UINT64 begin, + UINT64 end ) + { + Subresource = subresource; + Range.Begin = begin; + Range.End = end; + } + operator const D3D12_SUBRESOURCE_RANGE_UINT64&() const { return *this; } +}; +#endif + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_SHADER_BYTECODE : public D3D12_SHADER_BYTECODE +{ + CD3DX12_SHADER_BYTECODE() + {} + explicit CD3DX12_SHADER_BYTECODE(const D3D12_SHADER_BYTECODE &o) : + D3D12_SHADER_BYTECODE(o) + {} + CD3DX12_SHADER_BYTECODE( + _In_ ID3DBlob* pShaderBlob ) + { + pShaderBytecode = pShaderBlob->GetBufferPointer(); + BytecodeLength = pShaderBlob->GetBufferSize(); + } + CD3DX12_SHADER_BYTECODE( + const void* _pShaderBytecode, + SIZE_T bytecodeLength ) + { + pShaderBytecode = _pShaderBytecode; + BytecodeLength = bytecodeLength; + } + operator const D3D12_SHADER_BYTECODE&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_TILED_RESOURCE_COORDINATE : public D3D12_TILED_RESOURCE_COORDINATE +{ + CD3DX12_TILED_RESOURCE_COORDINATE() + {} + explicit CD3DX12_TILED_RESOURCE_COORDINATE(const D3D12_TILED_RESOURCE_COORDINATE &o) : + D3D12_TILED_RESOURCE_COORDINATE(o) + {} + CD3DX12_TILED_RESOURCE_COORDINATE( + UINT x, + UINT y, + UINT z, + UINT subresource ) + { + X = x; + Y = y; + Z = z; + Subresource = subresource; + } + operator const D3D12_TILED_RESOURCE_COORDINATE&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_TILE_REGION_SIZE : public D3D12_TILE_REGION_SIZE +{ + CD3DX12_TILE_REGION_SIZE() + {} + explicit CD3DX12_TILE_REGION_SIZE(const D3D12_TILE_REGION_SIZE &o) : + D3D12_TILE_REGION_SIZE(o) + {} + CD3DX12_TILE_REGION_SIZE( + UINT numTiles, + BOOL useBox, + UINT width, + UINT16 height, + UINT16 depth ) + { + NumTiles = numTiles; + UseBox = useBox; + Width = width; + Height = height; + Depth = depth; + } + operator const D3D12_TILE_REGION_SIZE&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_SUBRESOURCE_TILING : public D3D12_SUBRESOURCE_TILING +{ + CD3DX12_SUBRESOURCE_TILING() + {} + explicit CD3DX12_SUBRESOURCE_TILING(const D3D12_SUBRESOURCE_TILING &o) : + D3D12_SUBRESOURCE_TILING(o) + {} + CD3DX12_SUBRESOURCE_TILING( + UINT widthInTiles, + UINT16 heightInTiles, + UINT16 depthInTiles, + UINT startTileIndexInOverallResource ) + { + WidthInTiles = widthInTiles; + HeightInTiles = heightInTiles; + DepthInTiles = depthInTiles; + StartTileIndexInOverallResource = startTileIndexInOverallResource; + } + operator const D3D12_SUBRESOURCE_TILING&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_TILE_SHAPE : public D3D12_TILE_SHAPE +{ + CD3DX12_TILE_SHAPE() + {} + explicit CD3DX12_TILE_SHAPE(const D3D12_TILE_SHAPE &o) : + D3D12_TILE_SHAPE(o) + {} + CD3DX12_TILE_SHAPE( + UINT widthInTexels, + UINT heightInTexels, + UINT depthInTexels ) + { + WidthInTexels = widthInTexels; + HeightInTexels = heightInTexels; + DepthInTexels = depthInTexels; + } + operator const D3D12_TILE_SHAPE&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_RESOURCE_BARRIER : public D3D12_RESOURCE_BARRIER +{ + CD3DX12_RESOURCE_BARRIER() + {} + explicit CD3DX12_RESOURCE_BARRIER(const D3D12_RESOURCE_BARRIER &o) : + D3D12_RESOURCE_BARRIER(o) + {} + static inline CD3DX12_RESOURCE_BARRIER Transition( + _In_ ID3D12Resource* pResource, + D3D12_RESOURCE_STATES stateBefore, + D3D12_RESOURCE_STATES stateAfter, + UINT subresource = D3D12_RESOURCE_BARRIER_ALL_SUBRESOURCES, + D3D12_RESOURCE_BARRIER_FLAGS flags = D3D12_RESOURCE_BARRIER_FLAG_NONE) + { + CD3DX12_RESOURCE_BARRIER result; + ZeroMemory(&result, sizeof(result)); + D3D12_RESOURCE_BARRIER &barrier = result; + result.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; + result.Flags = flags; + barrier.Transition.pResource = pResource; + barrier.Transition.StateBefore = stateBefore; + barrier.Transition.StateAfter = stateAfter; + barrier.Transition.Subresource = subresource; + return result; + } + static inline CD3DX12_RESOURCE_BARRIER Aliasing( + _In_ ID3D12Resource* pResourceBefore, + _In_ ID3D12Resource* pResourceAfter) + { + CD3DX12_RESOURCE_BARRIER result; + ZeroMemory(&result, sizeof(result)); + D3D12_RESOURCE_BARRIER &barrier = result; + result.Type = D3D12_RESOURCE_BARRIER_TYPE_ALIASING; + barrier.Aliasing.pResourceBefore = pResourceBefore; + barrier.Aliasing.pResourceAfter = pResourceAfter; + return result; + } + static inline CD3DX12_RESOURCE_BARRIER UAV( + _In_ ID3D12Resource* pResource) + { + CD3DX12_RESOURCE_BARRIER result; + ZeroMemory(&result, sizeof(result)); + D3D12_RESOURCE_BARRIER &barrier = result; + result.Type = D3D12_RESOURCE_BARRIER_TYPE_UAV; + barrier.UAV.pResource = pResource; + return result; + } + operator const D3D12_RESOURCE_BARRIER&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_PACKED_MIP_INFO : public D3D12_PACKED_MIP_INFO +{ + CD3DX12_PACKED_MIP_INFO() + {} + explicit CD3DX12_PACKED_MIP_INFO(const D3D12_PACKED_MIP_INFO &o) : + D3D12_PACKED_MIP_INFO(o) + {} + CD3DX12_PACKED_MIP_INFO( + UINT8 numStandardMips, + UINT8 numPackedMips, + UINT numTilesForPackedMips, + UINT startTileIndexInOverallResource ) + { + NumStandardMips = numStandardMips; + NumPackedMips = numPackedMips; + NumTilesForPackedMips = numTilesForPackedMips; + StartTileIndexInOverallResource = startTileIndexInOverallResource; + } + operator const D3D12_PACKED_MIP_INFO&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_SUBRESOURCE_FOOTPRINT : public D3D12_SUBRESOURCE_FOOTPRINT +{ + CD3DX12_SUBRESOURCE_FOOTPRINT() + {} + explicit CD3DX12_SUBRESOURCE_FOOTPRINT(const D3D12_SUBRESOURCE_FOOTPRINT &o) : + D3D12_SUBRESOURCE_FOOTPRINT(o) + {} + CD3DX12_SUBRESOURCE_FOOTPRINT( + DXGI_FORMAT format, + UINT width, + UINT height, + UINT depth, + UINT rowPitch ) + { + Format = format; + Width = width; + Height = height; + Depth = depth; + RowPitch = rowPitch; + } + explicit CD3DX12_SUBRESOURCE_FOOTPRINT( + const D3D12_RESOURCE_DESC& resDesc, + UINT rowPitch ) + { + Format = resDesc.Format; + Width = UINT( resDesc.Width ); + Height = resDesc.Height; + Depth = (resDesc.Dimension == D3D12_RESOURCE_DIMENSION_TEXTURE3D ? resDesc.DepthOrArraySize : 1); + RowPitch = rowPitch; + } + operator const D3D12_SUBRESOURCE_FOOTPRINT&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_TEXTURE_COPY_LOCATION : public D3D12_TEXTURE_COPY_LOCATION +{ + CD3DX12_TEXTURE_COPY_LOCATION() + {} + explicit CD3DX12_TEXTURE_COPY_LOCATION(const D3D12_TEXTURE_COPY_LOCATION &o) : + D3D12_TEXTURE_COPY_LOCATION(o) + {} + CD3DX12_TEXTURE_COPY_LOCATION(ID3D12Resource* pRes) { pResource = pRes; } + CD3DX12_TEXTURE_COPY_LOCATION(ID3D12Resource* pRes, D3D12_PLACED_SUBRESOURCE_FOOTPRINT const& Footprint) + { + pResource = pRes; + Type = D3D12_TEXTURE_COPY_TYPE_PLACED_FOOTPRINT; + PlacedFootprint = Footprint; + } + CD3DX12_TEXTURE_COPY_LOCATION(ID3D12Resource* pRes, UINT Sub) + { + pResource = pRes; + Type = D3D12_TEXTURE_COPY_TYPE_SUBRESOURCE_INDEX; + SubresourceIndex = Sub; + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_DESCRIPTOR_RANGE : public D3D12_DESCRIPTOR_RANGE +{ + CD3DX12_DESCRIPTOR_RANGE() { } + explicit CD3DX12_DESCRIPTOR_RANGE(const D3D12_DESCRIPTOR_RANGE &o) : + D3D12_DESCRIPTOR_RANGE(o) + {} + CD3DX12_DESCRIPTOR_RANGE( + D3D12_DESCRIPTOR_RANGE_TYPE rangeType, + UINT numDescriptors, + UINT baseShaderRegister, + UINT registerSpace = 0, + UINT offsetInDescriptorsFromTableStart = + D3D12_DESCRIPTOR_RANGE_OFFSET_APPEND) + { + Init(rangeType, numDescriptors, baseShaderRegister, registerSpace, offsetInDescriptorsFromTableStart); + } + + inline void Init( + D3D12_DESCRIPTOR_RANGE_TYPE rangeType, + UINT numDescriptors, + UINT baseShaderRegister, + UINT registerSpace = 0, + UINT offsetInDescriptorsFromTableStart = + D3D12_DESCRIPTOR_RANGE_OFFSET_APPEND) + { + Init(*this, rangeType, numDescriptors, baseShaderRegister, registerSpace, offsetInDescriptorsFromTableStart); + } + + static inline void Init( + _Out_ D3D12_DESCRIPTOR_RANGE &range, + D3D12_DESCRIPTOR_RANGE_TYPE rangeType, + UINT numDescriptors, + UINT baseShaderRegister, + UINT registerSpace = 0, + UINT offsetInDescriptorsFromTableStart = + D3D12_DESCRIPTOR_RANGE_OFFSET_APPEND) + { + range.RangeType = rangeType; + range.NumDescriptors = numDescriptors; + range.BaseShaderRegister = baseShaderRegister; + range.RegisterSpace = registerSpace; + range.OffsetInDescriptorsFromTableStart = offsetInDescriptorsFromTableStart; + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_ROOT_DESCRIPTOR_TABLE : public D3D12_ROOT_DESCRIPTOR_TABLE +{ + CD3DX12_ROOT_DESCRIPTOR_TABLE() {} + explicit CD3DX12_ROOT_DESCRIPTOR_TABLE(const D3D12_ROOT_DESCRIPTOR_TABLE &o) : + D3D12_ROOT_DESCRIPTOR_TABLE(o) + {} + CD3DX12_ROOT_DESCRIPTOR_TABLE( + UINT numDescriptorRanges, + _In_reads_opt_(numDescriptorRanges) const D3D12_DESCRIPTOR_RANGE* _pDescriptorRanges) + { + Init(numDescriptorRanges, _pDescriptorRanges); + } + + inline void Init( + UINT numDescriptorRanges, + _In_reads_opt_(numDescriptorRanges) const D3D12_DESCRIPTOR_RANGE* _pDescriptorRanges) + { + Init(*this, numDescriptorRanges, _pDescriptorRanges); + } + + static inline void Init( + _Out_ D3D12_ROOT_DESCRIPTOR_TABLE &rootDescriptorTable, + UINT numDescriptorRanges, + _In_reads_opt_(numDescriptorRanges) const D3D12_DESCRIPTOR_RANGE* _pDescriptorRanges) + { + rootDescriptorTable.NumDescriptorRanges = numDescriptorRanges; + rootDescriptorTable.pDescriptorRanges = _pDescriptorRanges; + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_ROOT_CONSTANTS : public D3D12_ROOT_CONSTANTS +{ + CD3DX12_ROOT_CONSTANTS() {} + explicit CD3DX12_ROOT_CONSTANTS(const D3D12_ROOT_CONSTANTS &o) : + D3D12_ROOT_CONSTANTS(o) + {} + CD3DX12_ROOT_CONSTANTS( + UINT num32BitValues, + UINT shaderRegister, + UINT registerSpace = 0) + { + Init(num32BitValues, shaderRegister, registerSpace); + } + + inline void Init( + UINT num32BitValues, + UINT shaderRegister, + UINT registerSpace = 0) + { + Init(*this, num32BitValues, shaderRegister, registerSpace); + } + + static inline void Init( + _Out_ D3D12_ROOT_CONSTANTS &rootConstants, + UINT num32BitValues, + UINT shaderRegister, + UINT registerSpace = 0) + { + rootConstants.Num32BitValues = num32BitValues; + rootConstants.ShaderRegister = shaderRegister; + rootConstants.RegisterSpace = registerSpace; + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_ROOT_DESCRIPTOR : public D3D12_ROOT_DESCRIPTOR +{ + CD3DX12_ROOT_DESCRIPTOR() {} + explicit CD3DX12_ROOT_DESCRIPTOR(const D3D12_ROOT_DESCRIPTOR &o) : + D3D12_ROOT_DESCRIPTOR(o) + {} + CD3DX12_ROOT_DESCRIPTOR( + UINT shaderRegister, + UINT registerSpace = 0) + { + Init(shaderRegister, registerSpace); + } + + inline void Init( + UINT shaderRegister, + UINT registerSpace = 0) + { + Init(*this, shaderRegister, registerSpace); + } + + static inline void Init(_Out_ D3D12_ROOT_DESCRIPTOR &table, UINT shaderRegister, UINT registerSpace = 0) + { + table.ShaderRegister = shaderRegister; + table.RegisterSpace = registerSpace; + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_ROOT_PARAMETER : public D3D12_ROOT_PARAMETER +{ + CD3DX12_ROOT_PARAMETER() {} + explicit CD3DX12_ROOT_PARAMETER(const D3D12_ROOT_PARAMETER &o) : + D3D12_ROOT_PARAMETER(o) + {} + + static inline void InitAsDescriptorTable( + _Out_ D3D12_ROOT_PARAMETER &rootParam, + UINT numDescriptorRanges, + _In_reads_(numDescriptorRanges) const D3D12_DESCRIPTOR_RANGE* pDescriptorRanges, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + rootParam.ParameterType = D3D12_ROOT_PARAMETER_TYPE_DESCRIPTOR_TABLE; + rootParam.ShaderVisibility = visibility; + CD3DX12_ROOT_DESCRIPTOR_TABLE::Init(rootParam.DescriptorTable, numDescriptorRanges, pDescriptorRanges); + } + + static inline void InitAsConstants( + _Out_ D3D12_ROOT_PARAMETER &rootParam, + UINT num32BitValues, + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + rootParam.ParameterType = D3D12_ROOT_PARAMETER_TYPE_32BIT_CONSTANTS; + rootParam.ShaderVisibility = visibility; + CD3DX12_ROOT_CONSTANTS::Init(rootParam.Constants, num32BitValues, shaderRegister, registerSpace); + } + + static inline void InitAsConstantBufferView( + _Out_ D3D12_ROOT_PARAMETER &rootParam, + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + rootParam.ParameterType = D3D12_ROOT_PARAMETER_TYPE_CBV; + rootParam.ShaderVisibility = visibility; + CD3DX12_ROOT_DESCRIPTOR::Init(rootParam.Descriptor, shaderRegister, registerSpace); + } + + static inline void InitAsShaderResourceView( + _Out_ D3D12_ROOT_PARAMETER &rootParam, + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + rootParam.ParameterType = D3D12_ROOT_PARAMETER_TYPE_SRV; + rootParam.ShaderVisibility = visibility; + CD3DX12_ROOT_DESCRIPTOR::Init(rootParam.Descriptor, shaderRegister, registerSpace); + } + + static inline void InitAsUnorderedAccessView( + _Out_ D3D12_ROOT_PARAMETER &rootParam, + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + rootParam.ParameterType = D3D12_ROOT_PARAMETER_TYPE_UAV; + rootParam.ShaderVisibility = visibility; + CD3DX12_ROOT_DESCRIPTOR::Init(rootParam.Descriptor, shaderRegister, registerSpace); + } + + inline void InitAsDescriptorTable( + UINT numDescriptorRanges, + _In_reads_(numDescriptorRanges) const D3D12_DESCRIPTOR_RANGE* pDescriptorRanges, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + InitAsDescriptorTable(*this, numDescriptorRanges, pDescriptorRanges, visibility); + } + + inline void InitAsConstants( + UINT num32BitValues, + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + InitAsConstants(*this, num32BitValues, shaderRegister, registerSpace, visibility); + } + + inline void InitAsConstantBufferView( + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + InitAsConstantBufferView(*this, shaderRegister, registerSpace, visibility); + } + + inline void InitAsShaderResourceView( + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + InitAsShaderResourceView(*this, shaderRegister, registerSpace, visibility); + } + + inline void InitAsUnorderedAccessView( + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + InitAsUnorderedAccessView(*this, shaderRegister, registerSpace, visibility); + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_STATIC_SAMPLER_DESC : public D3D12_STATIC_SAMPLER_DESC +{ + CD3DX12_STATIC_SAMPLER_DESC() {} + explicit CD3DX12_STATIC_SAMPLER_DESC(const D3D12_STATIC_SAMPLER_DESC &o) : + D3D12_STATIC_SAMPLER_DESC(o) + {} + CD3DX12_STATIC_SAMPLER_DESC( + UINT shaderRegister, + D3D12_FILTER filter = D3D12_FILTER_ANISOTROPIC, + D3D12_TEXTURE_ADDRESS_MODE addressU = D3D12_TEXTURE_ADDRESS_MODE_WRAP, + D3D12_TEXTURE_ADDRESS_MODE addressV = D3D12_TEXTURE_ADDRESS_MODE_WRAP, + D3D12_TEXTURE_ADDRESS_MODE addressW = D3D12_TEXTURE_ADDRESS_MODE_WRAP, + FLOAT mipLODBias = 0, + UINT maxAnisotropy = 16, + D3D12_COMPARISON_FUNC comparisonFunc = D3D12_COMPARISON_FUNC_LESS_EQUAL, + D3D12_STATIC_BORDER_COLOR borderColor = D3D12_STATIC_BORDER_COLOR_OPAQUE_WHITE, + FLOAT minLOD = 0.f, + FLOAT maxLOD = D3D12_FLOAT32_MAX, + D3D12_SHADER_VISIBILITY shaderVisibility = D3D12_SHADER_VISIBILITY_ALL, + UINT registerSpace = 0) + { + Init( + shaderRegister, + filter, + addressU, + addressV, + addressW, + mipLODBias, + maxAnisotropy, + comparisonFunc, + borderColor, + minLOD, + maxLOD, + shaderVisibility, + registerSpace); + } + + static inline void Init( + _Out_ D3D12_STATIC_SAMPLER_DESC &samplerDesc, + UINT shaderRegister, + D3D12_FILTER filter = D3D12_FILTER_ANISOTROPIC, + D3D12_TEXTURE_ADDRESS_MODE addressU = D3D12_TEXTURE_ADDRESS_MODE_WRAP, + D3D12_TEXTURE_ADDRESS_MODE addressV = D3D12_TEXTURE_ADDRESS_MODE_WRAP, + D3D12_TEXTURE_ADDRESS_MODE addressW = D3D12_TEXTURE_ADDRESS_MODE_WRAP, + FLOAT mipLODBias = 0, + UINT maxAnisotropy = 16, + D3D12_COMPARISON_FUNC comparisonFunc = D3D12_COMPARISON_FUNC_LESS_EQUAL, + D3D12_STATIC_BORDER_COLOR borderColor = D3D12_STATIC_BORDER_COLOR_OPAQUE_WHITE, + FLOAT minLOD = 0.f, + FLOAT maxLOD = D3D12_FLOAT32_MAX, + D3D12_SHADER_VISIBILITY shaderVisibility = D3D12_SHADER_VISIBILITY_ALL, + UINT registerSpace = 0) + { + samplerDesc.ShaderRegister = shaderRegister; + samplerDesc.Filter = filter; + samplerDesc.AddressU = addressU; + samplerDesc.AddressV = addressV; + samplerDesc.AddressW = addressW; + samplerDesc.MipLODBias = mipLODBias; + samplerDesc.MaxAnisotropy = maxAnisotropy; + samplerDesc.ComparisonFunc = comparisonFunc; + samplerDesc.BorderColor = borderColor; + samplerDesc.MinLOD = minLOD; + samplerDesc.MaxLOD = maxLOD; + samplerDesc.ShaderVisibility = shaderVisibility; + samplerDesc.RegisterSpace = registerSpace; + } + inline void Init( + UINT shaderRegister, + D3D12_FILTER filter = D3D12_FILTER_ANISOTROPIC, + D3D12_TEXTURE_ADDRESS_MODE addressU = D3D12_TEXTURE_ADDRESS_MODE_WRAP, + D3D12_TEXTURE_ADDRESS_MODE addressV = D3D12_TEXTURE_ADDRESS_MODE_WRAP, + D3D12_TEXTURE_ADDRESS_MODE addressW = D3D12_TEXTURE_ADDRESS_MODE_WRAP, + FLOAT mipLODBias = 0, + UINT maxAnisotropy = 16, + D3D12_COMPARISON_FUNC comparisonFunc = D3D12_COMPARISON_FUNC_LESS_EQUAL, + D3D12_STATIC_BORDER_COLOR borderColor = D3D12_STATIC_BORDER_COLOR_OPAQUE_WHITE, + FLOAT minLOD = 0.f, + FLOAT maxLOD = D3D12_FLOAT32_MAX, + D3D12_SHADER_VISIBILITY shaderVisibility = D3D12_SHADER_VISIBILITY_ALL, + UINT registerSpace = 0) + { + Init( + *this, + shaderRegister, + filter, + addressU, + addressV, + addressW, + mipLODBias, + maxAnisotropy, + comparisonFunc, + borderColor, + minLOD, + maxLOD, + shaderVisibility, + registerSpace); + } + +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_ROOT_SIGNATURE_DESC : public D3D12_ROOT_SIGNATURE_DESC +{ + CD3DX12_ROOT_SIGNATURE_DESC() {} + explicit CD3DX12_ROOT_SIGNATURE_DESC(const D3D12_ROOT_SIGNATURE_DESC &o) : + D3D12_ROOT_SIGNATURE_DESC(o) + {} + CD3DX12_ROOT_SIGNATURE_DESC( + UINT numParameters, + _In_reads_opt_(numParameters) const D3D12_ROOT_PARAMETER* _pParameters, + UINT numStaticSamplers = 0, + _In_reads_opt_(numStaticSamplers) const D3D12_STATIC_SAMPLER_DESC* _pStaticSamplers = NULL, + D3D12_ROOT_SIGNATURE_FLAGS flags = D3D12_ROOT_SIGNATURE_FLAG_NONE) + { + Init(numParameters, _pParameters, numStaticSamplers, _pStaticSamplers, flags); + } + CD3DX12_ROOT_SIGNATURE_DESC(CD3DX12_DEFAULT) + { + Init(0, NULL, 0, NULL, D3D12_ROOT_SIGNATURE_FLAG_NONE); + } + + inline void Init( + UINT numParameters, + _In_reads_opt_(numParameters) const D3D12_ROOT_PARAMETER* _pParameters, + UINT numStaticSamplers = 0, + _In_reads_opt_(numStaticSamplers) const D3D12_STATIC_SAMPLER_DESC* _pStaticSamplers = NULL, + D3D12_ROOT_SIGNATURE_FLAGS flags = D3D12_ROOT_SIGNATURE_FLAG_NONE) + { + Init(*this, numParameters, _pParameters, numStaticSamplers, _pStaticSamplers, flags); + } + + static inline void Init( + _Out_ D3D12_ROOT_SIGNATURE_DESC &desc, + UINT numParameters, + _In_reads_opt_(numParameters) const D3D12_ROOT_PARAMETER* _pParameters, + UINT numStaticSamplers = 0, + _In_reads_opt_(numStaticSamplers) const D3D12_STATIC_SAMPLER_DESC* _pStaticSamplers = NULL, + D3D12_ROOT_SIGNATURE_FLAGS flags = D3D12_ROOT_SIGNATURE_FLAG_NONE) + { + desc.NumParameters = numParameters; + desc.pParameters = _pParameters; + desc.NumStaticSamplers = numStaticSamplers; + desc.pStaticSamplers = _pStaticSamplers; + desc.Flags = flags; + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_DESCRIPTOR_RANGE1 : public D3D12_DESCRIPTOR_RANGE1 +{ + CD3DX12_DESCRIPTOR_RANGE1() { } + explicit CD3DX12_DESCRIPTOR_RANGE1(const D3D12_DESCRIPTOR_RANGE1 &o) : + D3D12_DESCRIPTOR_RANGE1(o) + {} + CD3DX12_DESCRIPTOR_RANGE1( + D3D12_DESCRIPTOR_RANGE_TYPE rangeType, + UINT numDescriptors, + UINT baseShaderRegister, + UINT registerSpace = 0, + D3D12_DESCRIPTOR_RANGE_FLAGS flags = D3D12_DESCRIPTOR_RANGE_FLAG_NONE, + UINT offsetInDescriptorsFromTableStart = + D3D12_DESCRIPTOR_RANGE_OFFSET_APPEND) + { + Init(rangeType, numDescriptors, baseShaderRegister, registerSpace, flags, offsetInDescriptorsFromTableStart); + } + + inline void Init( + D3D12_DESCRIPTOR_RANGE_TYPE rangeType, + UINT numDescriptors, + UINT baseShaderRegister, + UINT registerSpace = 0, + D3D12_DESCRIPTOR_RANGE_FLAGS flags = D3D12_DESCRIPTOR_RANGE_FLAG_NONE, + UINT offsetInDescriptorsFromTableStart = + D3D12_DESCRIPTOR_RANGE_OFFSET_APPEND) + { + Init(*this, rangeType, numDescriptors, baseShaderRegister, registerSpace, flags, offsetInDescriptorsFromTableStart); + } + + static inline void Init( + _Out_ D3D12_DESCRIPTOR_RANGE1 &range, + D3D12_DESCRIPTOR_RANGE_TYPE rangeType, + UINT numDescriptors, + UINT baseShaderRegister, + UINT registerSpace = 0, + D3D12_DESCRIPTOR_RANGE_FLAGS flags = D3D12_DESCRIPTOR_RANGE_FLAG_NONE, + UINT offsetInDescriptorsFromTableStart = + D3D12_DESCRIPTOR_RANGE_OFFSET_APPEND) + { + range.RangeType = rangeType; + range.NumDescriptors = numDescriptors; + range.BaseShaderRegister = baseShaderRegister; + range.RegisterSpace = registerSpace; + range.Flags = flags; + range.OffsetInDescriptorsFromTableStart = offsetInDescriptorsFromTableStart; + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_ROOT_DESCRIPTOR_TABLE1 : public D3D12_ROOT_DESCRIPTOR_TABLE1 +{ + CD3DX12_ROOT_DESCRIPTOR_TABLE1() {} + explicit CD3DX12_ROOT_DESCRIPTOR_TABLE1(const D3D12_ROOT_DESCRIPTOR_TABLE1 &o) : + D3D12_ROOT_DESCRIPTOR_TABLE1(o) + {} + CD3DX12_ROOT_DESCRIPTOR_TABLE1( + UINT numDescriptorRanges, + _In_reads_opt_(numDescriptorRanges) const D3D12_DESCRIPTOR_RANGE1* _pDescriptorRanges) + { + Init(numDescriptorRanges, _pDescriptorRanges); + } + + inline void Init( + UINT numDescriptorRanges, + _In_reads_opt_(numDescriptorRanges) const D3D12_DESCRIPTOR_RANGE1* _pDescriptorRanges) + { + Init(*this, numDescriptorRanges, _pDescriptorRanges); + } + + static inline void Init( + _Out_ D3D12_ROOT_DESCRIPTOR_TABLE1 &rootDescriptorTable, + UINT numDescriptorRanges, + _In_reads_opt_(numDescriptorRanges) const D3D12_DESCRIPTOR_RANGE1* _pDescriptorRanges) + { + rootDescriptorTable.NumDescriptorRanges = numDescriptorRanges; + rootDescriptorTable.pDescriptorRanges = _pDescriptorRanges; + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_ROOT_DESCRIPTOR1 : public D3D12_ROOT_DESCRIPTOR1 +{ + CD3DX12_ROOT_DESCRIPTOR1() {} + explicit CD3DX12_ROOT_DESCRIPTOR1(const D3D12_ROOT_DESCRIPTOR1 &o) : + D3D12_ROOT_DESCRIPTOR1(o) + {} + CD3DX12_ROOT_DESCRIPTOR1( + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_ROOT_DESCRIPTOR_FLAGS flags = D3D12_ROOT_DESCRIPTOR_FLAG_NONE) + { + Init(shaderRegister, registerSpace, flags); + } + + inline void Init( + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_ROOT_DESCRIPTOR_FLAGS flags = D3D12_ROOT_DESCRIPTOR_FLAG_NONE) + { + Init(*this, shaderRegister, registerSpace, flags); + } + + static inline void Init( + _Out_ D3D12_ROOT_DESCRIPTOR1 &table, + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_ROOT_DESCRIPTOR_FLAGS flags = D3D12_ROOT_DESCRIPTOR_FLAG_NONE) + { + table.ShaderRegister = shaderRegister; + table.RegisterSpace = registerSpace; + table.Flags = flags; + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_ROOT_PARAMETER1 : public D3D12_ROOT_PARAMETER1 +{ + CD3DX12_ROOT_PARAMETER1() {} + explicit CD3DX12_ROOT_PARAMETER1(const D3D12_ROOT_PARAMETER1 &o) : + D3D12_ROOT_PARAMETER1(o) + {} + + static inline void InitAsDescriptorTable( + _Out_ D3D12_ROOT_PARAMETER1 &rootParam, + UINT numDescriptorRanges, + _In_reads_(numDescriptorRanges) const D3D12_DESCRIPTOR_RANGE1* pDescriptorRanges, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + rootParam.ParameterType = D3D12_ROOT_PARAMETER_TYPE_DESCRIPTOR_TABLE; + rootParam.ShaderVisibility = visibility; + CD3DX12_ROOT_DESCRIPTOR_TABLE1::Init(rootParam.DescriptorTable, numDescriptorRanges, pDescriptorRanges); + } + + static inline void InitAsConstants( + _Out_ D3D12_ROOT_PARAMETER1 &rootParam, + UINT num32BitValues, + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + rootParam.ParameterType = D3D12_ROOT_PARAMETER_TYPE_32BIT_CONSTANTS; + rootParam.ShaderVisibility = visibility; + CD3DX12_ROOT_CONSTANTS::Init(rootParam.Constants, num32BitValues, shaderRegister, registerSpace); + } + + static inline void InitAsConstantBufferView( + _Out_ D3D12_ROOT_PARAMETER1 &rootParam, + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_ROOT_DESCRIPTOR_FLAGS flags = D3D12_ROOT_DESCRIPTOR_FLAG_NONE, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + rootParam.ParameterType = D3D12_ROOT_PARAMETER_TYPE_CBV; + rootParam.ShaderVisibility = visibility; + CD3DX12_ROOT_DESCRIPTOR1::Init(rootParam.Descriptor, shaderRegister, registerSpace, flags); + } + + static inline void InitAsShaderResourceView( + _Out_ D3D12_ROOT_PARAMETER1 &rootParam, + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_ROOT_DESCRIPTOR_FLAGS flags = D3D12_ROOT_DESCRIPTOR_FLAG_NONE, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + rootParam.ParameterType = D3D12_ROOT_PARAMETER_TYPE_SRV; + rootParam.ShaderVisibility = visibility; + CD3DX12_ROOT_DESCRIPTOR1::Init(rootParam.Descriptor, shaderRegister, registerSpace, flags); + } + + static inline void InitAsUnorderedAccessView( + _Out_ D3D12_ROOT_PARAMETER1 &rootParam, + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_ROOT_DESCRIPTOR_FLAGS flags = D3D12_ROOT_DESCRIPTOR_FLAG_NONE, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + rootParam.ParameterType = D3D12_ROOT_PARAMETER_TYPE_UAV; + rootParam.ShaderVisibility = visibility; + CD3DX12_ROOT_DESCRIPTOR1::Init(rootParam.Descriptor, shaderRegister, registerSpace, flags); + } + + inline void InitAsDescriptorTable( + UINT numDescriptorRanges, + _In_reads_(numDescriptorRanges) const D3D12_DESCRIPTOR_RANGE1* pDescriptorRanges, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + InitAsDescriptorTable(*this, numDescriptorRanges, pDescriptorRanges, visibility); + } + + inline void InitAsConstants( + UINT num32BitValues, + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + InitAsConstants(*this, num32BitValues, shaderRegister, registerSpace, visibility); + } + + inline void InitAsConstantBufferView( + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_ROOT_DESCRIPTOR_FLAGS flags = D3D12_ROOT_DESCRIPTOR_FLAG_NONE, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + InitAsConstantBufferView(*this, shaderRegister, registerSpace, flags, visibility); + } + + inline void InitAsShaderResourceView( + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_ROOT_DESCRIPTOR_FLAGS flags = D3D12_ROOT_DESCRIPTOR_FLAG_NONE, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + InitAsShaderResourceView(*this, shaderRegister, registerSpace, flags, visibility); + } + + inline void InitAsUnorderedAccessView( + UINT shaderRegister, + UINT registerSpace = 0, + D3D12_ROOT_DESCRIPTOR_FLAGS flags = D3D12_ROOT_DESCRIPTOR_FLAG_NONE, + D3D12_SHADER_VISIBILITY visibility = D3D12_SHADER_VISIBILITY_ALL) + { + InitAsUnorderedAccessView(*this, shaderRegister, registerSpace, flags, visibility); + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_VERSIONED_ROOT_SIGNATURE_DESC : public D3D12_VERSIONED_ROOT_SIGNATURE_DESC +{ + CD3DX12_VERSIONED_ROOT_SIGNATURE_DESC() {} + explicit CD3DX12_VERSIONED_ROOT_SIGNATURE_DESC(const D3D12_VERSIONED_ROOT_SIGNATURE_DESC &o) : + D3D12_VERSIONED_ROOT_SIGNATURE_DESC(o) + {} + explicit CD3DX12_VERSIONED_ROOT_SIGNATURE_DESC(const D3D12_ROOT_SIGNATURE_DESC &o) + { + Version = D3D_ROOT_SIGNATURE_VERSION_1_0; + Desc_1_0 = o; + } + explicit CD3DX12_VERSIONED_ROOT_SIGNATURE_DESC(const D3D12_ROOT_SIGNATURE_DESC1 &o) + { + Version = D3D_ROOT_SIGNATURE_VERSION_1_1; + Desc_1_1 = o; + } + CD3DX12_VERSIONED_ROOT_SIGNATURE_DESC( + UINT numParameters, + _In_reads_opt_(numParameters) const D3D12_ROOT_PARAMETER* _pParameters, + UINT numStaticSamplers = 0, + _In_reads_opt_(numStaticSamplers) const D3D12_STATIC_SAMPLER_DESC* _pStaticSamplers = NULL, + D3D12_ROOT_SIGNATURE_FLAGS flags = D3D12_ROOT_SIGNATURE_FLAG_NONE) + { + Init_1_0(numParameters, _pParameters, numStaticSamplers, _pStaticSamplers, flags); + } + CD3DX12_VERSIONED_ROOT_SIGNATURE_DESC( + UINT numParameters, + _In_reads_opt_(numParameters) const D3D12_ROOT_PARAMETER1* _pParameters, + UINT numStaticSamplers = 0, + _In_reads_opt_(numStaticSamplers) const D3D12_STATIC_SAMPLER_DESC* _pStaticSamplers = NULL, + D3D12_ROOT_SIGNATURE_FLAGS flags = D3D12_ROOT_SIGNATURE_FLAG_NONE) + { + Init_1_1(numParameters, _pParameters, numStaticSamplers, _pStaticSamplers, flags); + } + CD3DX12_VERSIONED_ROOT_SIGNATURE_DESC(CD3DX12_DEFAULT) + { + Init_1_1(0, NULL, 0, NULL, D3D12_ROOT_SIGNATURE_FLAG_NONE); + } + + inline void Init_1_0( + UINT numParameters, + _In_reads_opt_(numParameters) const D3D12_ROOT_PARAMETER* _pParameters, + UINT numStaticSamplers = 0, + _In_reads_opt_(numStaticSamplers) const D3D12_STATIC_SAMPLER_DESC* _pStaticSamplers = NULL, + D3D12_ROOT_SIGNATURE_FLAGS flags = D3D12_ROOT_SIGNATURE_FLAG_NONE) + { + Init_1_0(*this, numParameters, _pParameters, numStaticSamplers, _pStaticSamplers, flags); + } + + static inline void Init_1_0( + _Out_ D3D12_VERSIONED_ROOT_SIGNATURE_DESC &desc, + UINT numParameters, + _In_reads_opt_(numParameters) const D3D12_ROOT_PARAMETER* _pParameters, + UINT numStaticSamplers = 0, + _In_reads_opt_(numStaticSamplers) const D3D12_STATIC_SAMPLER_DESC* _pStaticSamplers = NULL, + D3D12_ROOT_SIGNATURE_FLAGS flags = D3D12_ROOT_SIGNATURE_FLAG_NONE) + { + desc.Version = D3D_ROOT_SIGNATURE_VERSION_1_0; + desc.Desc_1_0.NumParameters = numParameters; + desc.Desc_1_0.pParameters = _pParameters; + desc.Desc_1_0.NumStaticSamplers = numStaticSamplers; + desc.Desc_1_0.pStaticSamplers = _pStaticSamplers; + desc.Desc_1_0.Flags = flags; + } + + inline void Init_1_1( + UINT numParameters, + _In_reads_opt_(numParameters) const D3D12_ROOT_PARAMETER1* _pParameters, + UINT numStaticSamplers = 0, + _In_reads_opt_(numStaticSamplers) const D3D12_STATIC_SAMPLER_DESC* _pStaticSamplers = NULL, + D3D12_ROOT_SIGNATURE_FLAGS flags = D3D12_ROOT_SIGNATURE_FLAG_NONE) + { + Init_1_1(*this, numParameters, _pParameters, numStaticSamplers, _pStaticSamplers, flags); + } + + static inline void Init_1_1( + _Out_ D3D12_VERSIONED_ROOT_SIGNATURE_DESC &desc, + UINT numParameters, + _In_reads_opt_(numParameters) const D3D12_ROOT_PARAMETER1* _pParameters, + UINT numStaticSamplers = 0, + _In_reads_opt_(numStaticSamplers) const D3D12_STATIC_SAMPLER_DESC* _pStaticSamplers = NULL, + D3D12_ROOT_SIGNATURE_FLAGS flags = D3D12_ROOT_SIGNATURE_FLAG_NONE) + { + desc.Version = D3D_ROOT_SIGNATURE_VERSION_1_1; + desc.Desc_1_1.NumParameters = numParameters; + desc.Desc_1_1.pParameters = _pParameters; + desc.Desc_1_1.NumStaticSamplers = numStaticSamplers; + desc.Desc_1_1.pStaticSamplers = _pStaticSamplers; + desc.Desc_1_1.Flags = flags; + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_CPU_DESCRIPTOR_HANDLE : public D3D12_CPU_DESCRIPTOR_HANDLE +{ + CD3DX12_CPU_DESCRIPTOR_HANDLE() {} + explicit CD3DX12_CPU_DESCRIPTOR_HANDLE(const D3D12_CPU_DESCRIPTOR_HANDLE &o) : + D3D12_CPU_DESCRIPTOR_HANDLE(o) + {} + CD3DX12_CPU_DESCRIPTOR_HANDLE(CD3DX12_DEFAULT) { ptr = 0; } + CD3DX12_CPU_DESCRIPTOR_HANDLE(_In_ const D3D12_CPU_DESCRIPTOR_HANDLE &other, INT offsetScaledByIncrementSize) + { + InitOffsetted(other, offsetScaledByIncrementSize); + } + CD3DX12_CPU_DESCRIPTOR_HANDLE(_In_ const D3D12_CPU_DESCRIPTOR_HANDLE &other, INT offsetInDescriptors, UINT descriptorIncrementSize) + { + InitOffsetted(other, offsetInDescriptors, descriptorIncrementSize); + } + CD3DX12_CPU_DESCRIPTOR_HANDLE& Offset(INT offsetInDescriptors, UINT descriptorIncrementSize) + { + ptr += offsetInDescriptors * descriptorIncrementSize; + return *this; + } + CD3DX12_CPU_DESCRIPTOR_HANDLE& Offset(INT offsetScaledByIncrementSize) + { + ptr += offsetScaledByIncrementSize; + return *this; + } + bool operator==(_In_ const D3D12_CPU_DESCRIPTOR_HANDLE& other) const + { + return (ptr == other.ptr); + } + bool operator!=(_In_ const D3D12_CPU_DESCRIPTOR_HANDLE& other) const + { + return (ptr != other.ptr); + } + CD3DX12_CPU_DESCRIPTOR_HANDLE &operator=(const D3D12_CPU_DESCRIPTOR_HANDLE &other) + { + ptr = other.ptr; + return *this; + } + + inline void InitOffsetted(_In_ const D3D12_CPU_DESCRIPTOR_HANDLE &base, INT offsetScaledByIncrementSize) + { + InitOffsetted(*this, base, offsetScaledByIncrementSize); + } + + inline void InitOffsetted(_In_ const D3D12_CPU_DESCRIPTOR_HANDLE &base, INT offsetInDescriptors, UINT descriptorIncrementSize) + { + InitOffsetted(*this, base, offsetInDescriptors, descriptorIncrementSize); + } + + static inline void InitOffsetted(_Out_ D3D12_CPU_DESCRIPTOR_HANDLE &handle, _In_ const D3D12_CPU_DESCRIPTOR_HANDLE &base, INT offsetScaledByIncrementSize) + { + handle.ptr = base.ptr + offsetScaledByIncrementSize; + } + + static inline void InitOffsetted(_Out_ D3D12_CPU_DESCRIPTOR_HANDLE &handle, _In_ const D3D12_CPU_DESCRIPTOR_HANDLE &base, INT offsetInDescriptors, UINT descriptorIncrementSize) + { + handle.ptr = base.ptr + offsetInDescriptors * descriptorIncrementSize; + } +}; + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_GPU_DESCRIPTOR_HANDLE : public D3D12_GPU_DESCRIPTOR_HANDLE +{ + CD3DX12_GPU_DESCRIPTOR_HANDLE() {} + explicit CD3DX12_GPU_DESCRIPTOR_HANDLE(const D3D12_GPU_DESCRIPTOR_HANDLE &o) : + D3D12_GPU_DESCRIPTOR_HANDLE(o) + {} + CD3DX12_GPU_DESCRIPTOR_HANDLE(CD3DX12_DEFAULT) { ptr = 0; } + CD3DX12_GPU_DESCRIPTOR_HANDLE(_In_ const D3D12_GPU_DESCRIPTOR_HANDLE &other, INT offsetScaledByIncrementSize) + { + InitOffsetted(other, offsetScaledByIncrementSize); + } + CD3DX12_GPU_DESCRIPTOR_HANDLE(_In_ const D3D12_GPU_DESCRIPTOR_HANDLE &other, INT offsetInDescriptors, UINT descriptorIncrementSize) + { + InitOffsetted(other, offsetInDescriptors, descriptorIncrementSize); + } + CD3DX12_GPU_DESCRIPTOR_HANDLE& Offset(INT offsetInDescriptors, UINT descriptorIncrementSize) + { + ptr += offsetInDescriptors * descriptorIncrementSize; + return *this; + } + CD3DX12_GPU_DESCRIPTOR_HANDLE& Offset(INT offsetScaledByIncrementSize) + { + ptr += offsetScaledByIncrementSize; + return *this; + } + inline bool operator==(_In_ const D3D12_GPU_DESCRIPTOR_HANDLE& other) const + { + return (ptr == other.ptr); + } + inline bool operator!=(_In_ const D3D12_GPU_DESCRIPTOR_HANDLE& other) const + { + return (ptr != other.ptr); + } + CD3DX12_GPU_DESCRIPTOR_HANDLE &operator=(const D3D12_GPU_DESCRIPTOR_HANDLE &other) + { + ptr = other.ptr; + return *this; + } + + inline void InitOffsetted(_In_ const D3D12_GPU_DESCRIPTOR_HANDLE &base, INT offsetScaledByIncrementSize) + { + InitOffsetted(*this, base, offsetScaledByIncrementSize); + } + + inline void InitOffsetted(_In_ const D3D12_GPU_DESCRIPTOR_HANDLE &base, INT offsetInDescriptors, UINT descriptorIncrementSize) + { + InitOffsetted(*this, base, offsetInDescriptors, descriptorIncrementSize); + } + + static inline void InitOffsetted(_Out_ D3D12_GPU_DESCRIPTOR_HANDLE &handle, _In_ const D3D12_GPU_DESCRIPTOR_HANDLE &base, INT offsetScaledByIncrementSize) + { + handle.ptr = base.ptr + offsetScaledByIncrementSize; + } + + static inline void InitOffsetted(_Out_ D3D12_GPU_DESCRIPTOR_HANDLE &handle, _In_ const D3D12_GPU_DESCRIPTOR_HANDLE &base, INT offsetInDescriptors, UINT descriptorIncrementSize) + { + handle.ptr = base.ptr + offsetInDescriptors * descriptorIncrementSize; + } +}; + +//------------------------------------------------------------------------------------------------ +inline UINT D3D12CalcSubresource( UINT MipSlice, UINT ArraySlice, UINT PlaneSlice, UINT MipLevels, UINT ArraySize ) +{ + return MipSlice + ArraySlice * MipLevels + PlaneSlice * MipLevels * ArraySize; +} + +//------------------------------------------------------------------------------------------------ +template +inline void D3D12DecomposeSubresource( UINT Subresource, UINT MipLevels, UINT ArraySize, _Out_ T& MipSlice, _Out_ U& ArraySlice, _Out_ V& PlaneSlice ) +{ + MipSlice = static_cast(Subresource % MipLevels); + ArraySlice = static_cast((Subresource / MipLevels) % ArraySize); + PlaneSlice = static_cast(Subresource / (MipLevels * ArraySize)); +} + +//------------------------------------------------------------------------------------------------ +inline UINT8 D3D12GetFormatPlaneCount( + _In_ ID3D12Device* pDevice, + DXGI_FORMAT Format + ) +{ + D3D12_FEATURE_DATA_FORMAT_INFO formatInfo = {Format}; + if (FAILED(pDevice->CheckFeatureSupport(D3D12_FEATURE_FORMAT_INFO, &formatInfo, sizeof(formatInfo)))) + { + return 0; + } + return formatInfo.PlaneCount; +} + +//------------------------------------------------------------------------------------------------ +struct CD3DX12_RESOURCE_DESC : public D3D12_RESOURCE_DESC +{ + CD3DX12_RESOURCE_DESC() + {} + explicit CD3DX12_RESOURCE_DESC( const D3D12_RESOURCE_DESC& o ) : + D3D12_RESOURCE_DESC( o ) + {} + CD3DX12_RESOURCE_DESC( + D3D12_RESOURCE_DIMENSION dimension, + UINT64 alignment, + UINT64 width, + UINT height, + UINT16 depthOrArraySize, + UINT16 mipLevels, + DXGI_FORMAT format, + UINT sampleCount, + UINT sampleQuality, + D3D12_TEXTURE_LAYOUT layout, + D3D12_RESOURCE_FLAGS flags ) + { + Dimension = dimension; + Alignment = alignment; + Width = width; + Height = height; + DepthOrArraySize = depthOrArraySize; + MipLevels = mipLevels; + Format = format; + SampleDesc.Count = sampleCount; + SampleDesc.Quality = sampleQuality; + Layout = layout; + Flags = flags; + } + static inline CD3DX12_RESOURCE_DESC Buffer( + const D3D12_RESOURCE_ALLOCATION_INFO& resAllocInfo, + D3D12_RESOURCE_FLAGS flags = D3D12_RESOURCE_FLAG_NONE ) + { + return CD3DX12_RESOURCE_DESC( D3D12_RESOURCE_DIMENSION_BUFFER, resAllocInfo.Alignment, resAllocInfo.SizeInBytes, + 1, 1, 1, DXGI_FORMAT_UNKNOWN, 1, 0, D3D12_TEXTURE_LAYOUT_ROW_MAJOR, flags ); + } + static inline CD3DX12_RESOURCE_DESC Buffer( + UINT64 width, + D3D12_RESOURCE_FLAGS flags = D3D12_RESOURCE_FLAG_NONE, + UINT64 alignment = 0 ) + { + return CD3DX12_RESOURCE_DESC( D3D12_RESOURCE_DIMENSION_BUFFER, alignment, width, 1, 1, 1, + DXGI_FORMAT_UNKNOWN, 1, 0, D3D12_TEXTURE_LAYOUT_ROW_MAJOR, flags ); + } + static inline CD3DX12_RESOURCE_DESC Tex1D( + DXGI_FORMAT format, + UINT64 width, + UINT16 arraySize = 1, + UINT16 mipLevels = 0, + D3D12_RESOURCE_FLAGS flags = D3D12_RESOURCE_FLAG_NONE, + D3D12_TEXTURE_LAYOUT layout = D3D12_TEXTURE_LAYOUT_UNKNOWN, + UINT64 alignment = 0 ) + { + return CD3DX12_RESOURCE_DESC( D3D12_RESOURCE_DIMENSION_TEXTURE1D, alignment, width, 1, arraySize, + mipLevels, format, 1, 0, layout, flags ); + } + static inline CD3DX12_RESOURCE_DESC Tex2D( + DXGI_FORMAT format, + UINT64 width, + UINT height, + UINT16 arraySize = 1, + UINT16 mipLevels = 0, + UINT sampleCount = 1, + UINT sampleQuality = 0, + D3D12_RESOURCE_FLAGS flags = D3D12_RESOURCE_FLAG_NONE, + D3D12_TEXTURE_LAYOUT layout = D3D12_TEXTURE_LAYOUT_UNKNOWN, + UINT64 alignment = 0 ) + { + return CD3DX12_RESOURCE_DESC( D3D12_RESOURCE_DIMENSION_TEXTURE2D, alignment, width, height, arraySize, + mipLevels, format, sampleCount, sampleQuality, layout, flags ); + } + static inline CD3DX12_RESOURCE_DESC Tex3D( + DXGI_FORMAT format, + UINT64 width, + UINT height, + UINT16 depth, + UINT16 mipLevels = 0, + D3D12_RESOURCE_FLAGS flags = D3D12_RESOURCE_FLAG_NONE, + D3D12_TEXTURE_LAYOUT layout = D3D12_TEXTURE_LAYOUT_UNKNOWN, + UINT64 alignment = 0 ) + { + return CD3DX12_RESOURCE_DESC( D3D12_RESOURCE_DIMENSION_TEXTURE3D, alignment, width, height, depth, + mipLevels, format, 1, 0, layout, flags ); + } + inline UINT16 Depth() const + { return (Dimension == D3D12_RESOURCE_DIMENSION_TEXTURE3D ? DepthOrArraySize : 1); } + inline UINT16 ArraySize() const + { return (Dimension != D3D12_RESOURCE_DIMENSION_TEXTURE3D ? DepthOrArraySize : 1); } + inline UINT8 PlaneCount(_In_ ID3D12Device* pDevice) const + { return D3D12GetFormatPlaneCount(pDevice, Format); } + inline UINT Subresources(_In_ ID3D12Device* pDevice) const + { return MipLevels * ArraySize() * PlaneCount(pDevice); } + inline UINT CalcSubresource(UINT MipSlice, UINT ArraySlice, UINT PlaneSlice) + { return D3D12CalcSubresource(MipSlice, ArraySlice, PlaneSlice, MipLevels, ArraySize()); } + operator const D3D12_RESOURCE_DESC&() const { return *this; } +}; +inline bool operator==( const D3D12_RESOURCE_DESC& l, const D3D12_RESOURCE_DESC& r ) +{ + return l.Dimension == r.Dimension && + l.Alignment == r.Alignment && + l.Width == r.Width && + l.Height == r.Height && + l.DepthOrArraySize == r.DepthOrArraySize && + l.MipLevels == r.MipLevels && + l.Format == r.Format && + l.SampleDesc.Count == r.SampleDesc.Count && + l.SampleDesc.Quality == r.SampleDesc.Quality && + l.Layout == r.Layout && + l.Flags == r.Flags; +} +inline bool operator!=( const D3D12_RESOURCE_DESC& l, const D3D12_RESOURCE_DESC& r ) +{ return !( l == r ); } + +//------------------------------------------------------------------------------------------------ +// Row-by-row memcpy +inline void MemcpySubresource( + _In_ const D3D12_MEMCPY_DEST* pDest, + _In_ const D3D12_SUBRESOURCE_DATA* pSrc, + SIZE_T RowSizeInBytes, + UINT NumRows, + UINT NumSlices) +{ + for (UINT z = 0; z < NumSlices; ++z) + { + BYTE* pDestSlice = reinterpret_cast(pDest->pData) + pDest->SlicePitch * z; + const BYTE* pSrcSlice = reinterpret_cast(pSrc->pData) + pSrc->SlicePitch * z; + for (UINT y = 0; y < NumRows; ++y) + { + memcpy(pDestSlice + pDest->RowPitch * y, + pSrcSlice + pSrc->RowPitch * y, + RowSizeInBytes); + } + } +} + +//------------------------------------------------------------------------------------------------ +// Returns required size of a buffer to be used for data upload +inline UINT64 GetRequiredIntermediateSize( + _In_ ID3D12Resource* pDestinationResource, + _In_range_(0,D3D12_REQ_SUBRESOURCES) UINT FirstSubresource, + _In_range_(0,D3D12_REQ_SUBRESOURCES-FirstSubresource) UINT NumSubresources) +{ + D3D12_RESOURCE_DESC Desc = pDestinationResource->GetDesc(); + UINT64 RequiredSize = 0; + + ID3D12Device* pDevice; + pDestinationResource->GetDevice(__uuidof(*pDevice), reinterpret_cast(&pDevice)); + pDevice->GetCopyableFootprints(&Desc, FirstSubresource, NumSubresources, 0, nullptr, nullptr, nullptr, &RequiredSize); + pDevice->Release(); + + return RequiredSize; +} + +//------------------------------------------------------------------------------------------------ +// All arrays must be populated (e.g. by calling GetCopyableFootprints) +inline UINT64 UpdateSubresources( + _In_ ID3D12GraphicsCommandList* pCmdList, + _In_ ID3D12Resource* pDestinationResource, + _In_ ID3D12Resource* pIntermediate, + _In_range_(0,D3D12_REQ_SUBRESOURCES) UINT FirstSubresource, + _In_range_(0,D3D12_REQ_SUBRESOURCES-FirstSubresource) UINT NumSubresources, + UINT64 RequiredSize, + _In_reads_(NumSubresources) const D3D12_PLACED_SUBRESOURCE_FOOTPRINT* pLayouts, + _In_reads_(NumSubresources) const UINT* pNumRows, + _In_reads_(NumSubresources) const UINT64* pRowSizesInBytes, + _In_reads_(NumSubresources) const D3D12_SUBRESOURCE_DATA* pSrcData) +{ + // Minor validation + D3D12_RESOURCE_DESC IntermediateDesc = pIntermediate->GetDesc(); + D3D12_RESOURCE_DESC DestinationDesc = pDestinationResource->GetDesc(); + if (IntermediateDesc.Dimension != D3D12_RESOURCE_DIMENSION_BUFFER || + IntermediateDesc.Width < RequiredSize + pLayouts[0].Offset || + RequiredSize > (SIZE_T)-1 || + (DestinationDesc.Dimension == D3D12_RESOURCE_DIMENSION_BUFFER && + (FirstSubresource != 0 || NumSubresources != 1))) + { + return 0; + } + + BYTE* pData; + HRESULT hr = pIntermediate->Map(0, NULL, reinterpret_cast(&pData)); + if (FAILED(hr)) + { + return 0; + } + + for (UINT i = 0; i < NumSubresources; ++i) + { + if (pRowSizesInBytes[i] > (SIZE_T)-1) return 0; + D3D12_MEMCPY_DEST DestData = { pData + pLayouts[i].Offset, pLayouts[i].Footprint.RowPitch, pLayouts[i].Footprint.RowPitch * pNumRows[i] }; + MemcpySubresource(&DestData, &pSrcData[i], (SIZE_T)pRowSizesInBytes[i], pNumRows[i], pLayouts[i].Footprint.Depth); + } + pIntermediate->Unmap(0, NULL); + + if (DestinationDesc.Dimension == D3D12_RESOURCE_DIMENSION_BUFFER) + { + CD3DX12_BOX SrcBox( UINT( pLayouts[0].Offset ), UINT( pLayouts[0].Offset + pLayouts[0].Footprint.Width ) ); + pCmdList->CopyBufferRegion( + pDestinationResource, 0, pIntermediate, pLayouts[0].Offset, pLayouts[0].Footprint.Width); + } + else + { + for (UINT i = 0; i < NumSubresources; ++i) + { + CD3DX12_TEXTURE_COPY_LOCATION Dst(pDestinationResource, i + FirstSubresource); + CD3DX12_TEXTURE_COPY_LOCATION Src(pIntermediate, pLayouts[i]); + pCmdList->CopyTextureRegion(&Dst, 0, 0, 0, &Src, nullptr); + } + } + return RequiredSize; +} + +//------------------------------------------------------------------------------------------------ +// Heap-allocating UpdateSubresources implementation +inline UINT64 UpdateSubresources( + _In_ ID3D12GraphicsCommandList* pCmdList, + _In_ ID3D12Resource* pDestinationResource, + _In_ ID3D12Resource* pIntermediate, + UINT64 IntermediateOffset, + _In_range_(0,D3D12_REQ_SUBRESOURCES) UINT FirstSubresource, + _In_range_(0,D3D12_REQ_SUBRESOURCES-FirstSubresource) UINT NumSubresources, + _In_reads_(NumSubresources) D3D12_SUBRESOURCE_DATA* pSrcData) +{ + UINT64 RequiredSize = 0; + UINT64 MemToAlloc = static_cast(sizeof(D3D12_PLACED_SUBRESOURCE_FOOTPRINT) + sizeof(UINT) + sizeof(UINT64)) * NumSubresources; + if (MemToAlloc > SIZE_MAX) + { + return 0; + } + void* pMem = HeapAlloc(GetProcessHeap(), 0, static_cast(MemToAlloc)); + if (pMem == NULL) + { + return 0; + } + D3D12_PLACED_SUBRESOURCE_FOOTPRINT* pLayouts = reinterpret_cast(pMem); + UINT64* pRowSizesInBytes = reinterpret_cast(pLayouts + NumSubresources); + UINT* pNumRows = reinterpret_cast(pRowSizesInBytes + NumSubresources); + + D3D12_RESOURCE_DESC Desc = pDestinationResource->GetDesc(); + ID3D12Device* pDevice; + pDestinationResource->GetDevice(__uuidof(*pDevice), reinterpret_cast(&pDevice)); + pDevice->GetCopyableFootprints(&Desc, FirstSubresource, NumSubresources, IntermediateOffset, pLayouts, pNumRows, pRowSizesInBytes, &RequiredSize); + pDevice->Release(); + + UINT64 Result = UpdateSubresources(pCmdList, pDestinationResource, pIntermediate, FirstSubresource, NumSubresources, RequiredSize, pLayouts, pNumRows, pRowSizesInBytes, pSrcData); + HeapFree(GetProcessHeap(), 0, pMem); + return Result; +} + +//------------------------------------------------------------------------------------------------ +// Stack-allocating UpdateSubresources implementation +template +inline UINT64 UpdateSubresources( + _In_ ID3D12GraphicsCommandList* pCmdList, + _In_ ID3D12Resource* pDestinationResource, + _In_ ID3D12Resource* pIntermediate, + UINT64 IntermediateOffset, + _In_range_(0, MaxSubresources) UINT FirstSubresource, + _In_range_(1, MaxSubresources - FirstSubresource) UINT NumSubresources, + _In_reads_(NumSubresources) D3D12_SUBRESOURCE_DATA* pSrcData) +{ + UINT64 RequiredSize = 0; + D3D12_PLACED_SUBRESOURCE_FOOTPRINT Layouts[MaxSubresources]; + UINT NumRows[MaxSubresources]; + UINT64 RowSizesInBytes[MaxSubresources]; + + D3D12_RESOURCE_DESC Desc = pDestinationResource->GetDesc(); + ID3D12Device* pDevice; + pDestinationResource->GetDevice(__uuidof(*pDevice), reinterpret_cast(&pDevice)); + pDevice->GetCopyableFootprints(&Desc, FirstSubresource, NumSubresources, IntermediateOffset, Layouts, NumRows, RowSizesInBytes, &RequiredSize); + pDevice->Release(); + + return UpdateSubresources(pCmdList, pDestinationResource, pIntermediate, FirstSubresource, NumSubresources, RequiredSize, Layouts, NumRows, RowSizesInBytes, pSrcData); +} + +//------------------------------------------------------------------------------------------------ +inline bool D3D12IsLayoutOpaque( D3D12_TEXTURE_LAYOUT Layout ) +{ return Layout == D3D12_TEXTURE_LAYOUT_UNKNOWN || Layout == D3D12_TEXTURE_LAYOUT_64KB_UNDEFINED_SWIZZLE; } + +//------------------------------------------------------------------------------------------------ +template +inline ID3D12CommandList * const * CommandListCast(t_CommandListType * const * pp) +{ + // This cast is useful for passing strongly typed command list pointers into + // ExecuteCommandLists. + // This cast is valid as long as the const-ness is respected. D3D12 APIs do + // respect the const-ness of their arguments. + return reinterpret_cast(pp); +} + +//------------------------------------------------------------------------------------------------ +// D3D12 exports a new method for serializing root signatures in the Windows 10 Anniversary Update. +// To help enable root signature 1.1 features when they are available and not require maintaining +// two code paths for building root signatures, this helper method reconstructs a 1.0 signature when +// 1.1 is not supported. +inline HRESULT D3DX12SerializeVersionedRootSignature( + _In_ const D3D12_VERSIONED_ROOT_SIGNATURE_DESC* pRootSignatureDesc, + D3D_ROOT_SIGNATURE_VERSION MaxVersion, + _Outptr_ ID3DBlob** ppBlob, + _Always_(_Outptr_opt_result_maybenull_) ID3DBlob** ppErrorBlob) +{ + if (ppErrorBlob != NULL) + { + *ppErrorBlob = NULL; + } + + switch (MaxVersion) + { + case D3D_ROOT_SIGNATURE_VERSION_1_0: + switch (pRootSignatureDesc->Version) + { + case D3D_ROOT_SIGNATURE_VERSION_1_0: + return D3D12SerializeRootSignature(&pRootSignatureDesc->Desc_1_0, D3D_ROOT_SIGNATURE_VERSION_1, ppBlob, ppErrorBlob); + + case D3D_ROOT_SIGNATURE_VERSION_1_1: + { + HRESULT hr = S_OK; + const D3D12_ROOT_SIGNATURE_DESC1& desc_1_1 = pRootSignatureDesc->Desc_1_1; + + const SIZE_T ParametersSize = sizeof(D3D12_ROOT_PARAMETER) * desc_1_1.NumParameters; + void* pParameters = (ParametersSize > 0) ? HeapAlloc(GetProcessHeap(), 0, ParametersSize) : NULL; + if (ParametersSize > 0 && pParameters == NULL) + { + hr = E_OUTOFMEMORY; + } + D3D12_ROOT_PARAMETER* pParameters_1_0 = reinterpret_cast(pParameters); + + if (SUCCEEDED(hr)) + { + for (UINT n = 0; n < desc_1_1.NumParameters; n++) + { + __analysis_assume(ParametersSize == sizeof(D3D12_ROOT_PARAMETER) * desc_1_1.NumParameters); + pParameters_1_0[n].ParameterType = desc_1_1.pParameters[n].ParameterType; + pParameters_1_0[n].ShaderVisibility = desc_1_1.pParameters[n].ShaderVisibility; + + switch (desc_1_1.pParameters[n].ParameterType) + { + case D3D12_ROOT_PARAMETER_TYPE_32BIT_CONSTANTS: + pParameters_1_0[n].Constants.Num32BitValues = desc_1_1.pParameters[n].Constants.Num32BitValues; + pParameters_1_0[n].Constants.RegisterSpace = desc_1_1.pParameters[n].Constants.RegisterSpace; + pParameters_1_0[n].Constants.ShaderRegister = desc_1_1.pParameters[n].Constants.ShaderRegister; + break; + + case D3D12_ROOT_PARAMETER_TYPE_CBV: + case D3D12_ROOT_PARAMETER_TYPE_SRV: + case D3D12_ROOT_PARAMETER_TYPE_UAV: + pParameters_1_0[n].Descriptor.RegisterSpace = desc_1_1.pParameters[n].Descriptor.RegisterSpace; + pParameters_1_0[n].Descriptor.ShaderRegister = desc_1_1.pParameters[n].Descriptor.ShaderRegister; + break; + + case D3D12_ROOT_PARAMETER_TYPE_DESCRIPTOR_TABLE: + const D3D12_ROOT_DESCRIPTOR_TABLE1& table_1_1 = desc_1_1.pParameters[n].DescriptorTable; + + const SIZE_T DescriptorRangesSize = sizeof(D3D12_DESCRIPTOR_RANGE) * table_1_1.NumDescriptorRanges; + void* pDescriptorRanges = (DescriptorRangesSize > 0 && SUCCEEDED(hr)) ? HeapAlloc(GetProcessHeap(), 0, DescriptorRangesSize) : NULL; + if (DescriptorRangesSize > 0 && pDescriptorRanges == NULL) + { + hr = E_OUTOFMEMORY; + } + D3D12_DESCRIPTOR_RANGE* pDescriptorRanges_1_0 = reinterpret_cast(pDescriptorRanges); + + if (SUCCEEDED(hr)) + { + for (UINT x = 0; x < table_1_1.NumDescriptorRanges; x++) + { + __analysis_assume(DescriptorRangesSize == sizeof(D3D12_DESCRIPTOR_RANGE) * table_1_1.NumDescriptorRanges); + pDescriptorRanges_1_0[x].BaseShaderRegister = table_1_1.pDescriptorRanges[x].BaseShaderRegister; + pDescriptorRanges_1_0[x].NumDescriptors = table_1_1.pDescriptorRanges[x].NumDescriptors; + pDescriptorRanges_1_0[x].OffsetInDescriptorsFromTableStart = table_1_1.pDescriptorRanges[x].OffsetInDescriptorsFromTableStart; + pDescriptorRanges_1_0[x].RangeType = table_1_1.pDescriptorRanges[x].RangeType; + pDescriptorRanges_1_0[x].RegisterSpace = table_1_1.pDescriptorRanges[x].RegisterSpace; + } + } + + D3D12_ROOT_DESCRIPTOR_TABLE& table_1_0 = pParameters_1_0[n].DescriptorTable; + table_1_0.NumDescriptorRanges = table_1_1.NumDescriptorRanges; + table_1_0.pDescriptorRanges = pDescriptorRanges_1_0; + } + } + } + + if (SUCCEEDED(hr)) + { + CD3DX12_ROOT_SIGNATURE_DESC desc_1_0(desc_1_1.NumParameters, pParameters_1_0, desc_1_1.NumStaticSamplers, desc_1_1.pStaticSamplers, desc_1_1.Flags); + hr = D3D12SerializeRootSignature(&desc_1_0, D3D_ROOT_SIGNATURE_VERSION_1, ppBlob, ppErrorBlob); + } + + if (pParameters) + { + for (UINT n = 0; n < desc_1_1.NumParameters; n++) + { + if (desc_1_1.pParameters[n].ParameterType == D3D12_ROOT_PARAMETER_TYPE_DESCRIPTOR_TABLE) + { + HeapFree(GetProcessHeap(), 0, reinterpret_cast(const_cast(pParameters_1_0[n].DescriptorTable.pDescriptorRanges))); + } + } + HeapFree(GetProcessHeap(), 0, pParameters); + } + return hr; + } + } + break; + + case D3D_ROOT_SIGNATURE_VERSION_1_1: + return D3D12SerializeVersionedRootSignature(pRootSignatureDesc, ppBlob, ppErrorBlob); + } + + return E_INVALIDARG; +} + +//------------------------------------------------------------------------------------------------ +// Requires the Windows 10 Creators Update SDK (15063) +#if defined(NTDDI_WIN10_RS2) && (NTDDI_VERSION >= NTDDI_WIN10_RS2) +struct CD3DX12_RT_FORMAT_ARRAY : public D3D12_RT_FORMAT_ARRAY +{ + CD3DX12_RT_FORMAT_ARRAY() {} + explicit CD3DX12_RT_FORMAT_ARRAY(const D3D12_RT_FORMAT_ARRAY& o) + : D3D12_RT_FORMAT_ARRAY(o) + {} + explicit CD3DX12_RT_FORMAT_ARRAY(const DXGI_FORMAT* pFormats, UINT NumFormats) + { + NumRenderTargets = NumFormats; + memcpy(RTFormats, pFormats, sizeof(RTFormats)); + // assumes ARRAY_SIZE(pFormats) == ARRAY_SIZE(RTFormats) + } + operator const D3D12_RT_FORMAT_ARRAY&() const { return *this; } +}; + +//------------------------------------------------------------------------------------------------ +// Pipeline State Stream Helpers +//------------------------------------------------------------------------------------------------ + +//------------------------------------------------------------------------------------------------ +// Stream Subobjects, i.e. elements of a stream + +#pragma warning(push) +#pragma warning(disable : 4324) +template +class alignas(void*) CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT +{ +private: + D3D12_PIPELINE_STATE_SUBOBJECT_TYPE _Type; + InnerStructType _Inner; +public: + CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT() : _Type(Type), _Inner(DefaultArg()) {} + CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT(InnerStructType const& i) : _Type(Type), _Inner(i) {} + CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT& operator=(InnerStructType const& i) { _Inner = i; return *this; } + operator InnerStructType() const { return _Inner; } +}; +#pragma warning(pop) +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_PIPELINE_STATE_FLAGS, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_FLAGS> CD3DX12_PIPELINE_STATE_STREAM_FLAGS; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< UINT, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_NODE_MASK> CD3DX12_PIPELINE_STATE_STREAM_NODE_MASK; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< ID3D12RootSignature*, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_ROOT_SIGNATURE> CD3DX12_PIPELINE_STATE_STREAM_ROOT_SIGNATURE; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_INPUT_LAYOUT_DESC, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_INPUT_LAYOUT> CD3DX12_PIPELINE_STATE_STREAM_INPUT_LAYOUT; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_INDEX_BUFFER_STRIP_CUT_VALUE, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_IB_STRIP_CUT_VALUE> CD3DX12_PIPELINE_STATE_STREAM_IB_STRIP_CUT_VALUE; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_PRIMITIVE_TOPOLOGY_TYPE, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_PRIMITIVE_TOPOLOGY> CD3DX12_PIPELINE_STATE_STREAM_PRIMITIVE_TOPOLOGY; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_SHADER_BYTECODE, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_VS> CD3DX12_PIPELINE_STATE_STREAM_VS; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_SHADER_BYTECODE, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_GS> CD3DX12_PIPELINE_STATE_STREAM_GS; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_STREAM_OUTPUT_DESC, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_STREAM_OUTPUT> CD3DX12_PIPELINE_STATE_STREAM_STREAM_OUTPUT; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_SHADER_BYTECODE, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_HS> CD3DX12_PIPELINE_STATE_STREAM_HS; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_SHADER_BYTECODE, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_DS> CD3DX12_PIPELINE_STATE_STREAM_DS; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_SHADER_BYTECODE, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_PS> CD3DX12_PIPELINE_STATE_STREAM_PS; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_SHADER_BYTECODE, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_CS> CD3DX12_PIPELINE_STATE_STREAM_CS; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< CD3DX12_BLEND_DESC, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_BLEND, CD3DX12_DEFAULT> CD3DX12_PIPELINE_STATE_STREAM_BLEND_DESC; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< CD3DX12_DEPTH_STENCIL_DESC, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_DEPTH_STENCIL, CD3DX12_DEFAULT> CD3DX12_PIPELINE_STATE_STREAM_DEPTH_STENCIL; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< CD3DX12_DEPTH_STENCIL_DESC1, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_DEPTH_STENCIL1, CD3DX12_DEFAULT> CD3DX12_PIPELINE_STATE_STREAM_DEPTH_STENCIL1; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< DXGI_FORMAT, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_DEPTH_STENCIL_FORMAT> CD3DX12_PIPELINE_STATE_STREAM_DEPTH_STENCIL_FORMAT; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< CD3DX12_RASTERIZER_DESC, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_RASTERIZER, CD3DX12_DEFAULT> CD3DX12_PIPELINE_STATE_STREAM_RASTERIZER; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_RT_FORMAT_ARRAY, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_RENDER_TARGET_FORMATS> CD3DX12_PIPELINE_STATE_STREAM_RENDER_TARGET_FORMATS; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< DXGI_SAMPLE_DESC, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_SAMPLE_DESC> CD3DX12_PIPELINE_STATE_STREAM_SAMPLE_DESC; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< UINT, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_SAMPLE_MASK> CD3DX12_PIPELINE_STATE_STREAM_SAMPLE_MASK; +typedef CD3DX12_PIPELINE_STATE_STREAM_SUBOBJECT< D3D12_CACHED_PIPELINE_STATE, D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_CACHED_PSO> CD3DX12_PIPELINE_STATE_STREAM_CACHED_PSO; + +//------------------------------------------------------------------------------------------------ +// Stream Parser Helpers + +struct ID3DX12PipelineParserCallbacks +{ + // Subobject Callbacks + virtual void FlagsCb(D3D12_PIPELINE_STATE_FLAGS) {} + virtual void NodeMaskCb(UINT) {} + virtual void RootSignatureCb(ID3D12RootSignature*) {} + virtual void InputLayoutCb(const D3D12_INPUT_LAYOUT_DESC&) {} + virtual void IBStripCutValueCb(D3D12_INDEX_BUFFER_STRIP_CUT_VALUE) {} + virtual void PrimitiveTopologyTypeCb(D3D12_PRIMITIVE_TOPOLOGY_TYPE) {} + virtual void VSCb(const D3D12_SHADER_BYTECODE&) {} + virtual void GSCb(const D3D12_SHADER_BYTECODE&) {} + virtual void StreamOutputCb(const D3D12_STREAM_OUTPUT_DESC&) {} + virtual void HSCb(const D3D12_SHADER_BYTECODE&) {} + virtual void DSCb(const D3D12_SHADER_BYTECODE&) {} + virtual void PSCb(const D3D12_SHADER_BYTECODE&) {} + virtual void CSCb(const D3D12_SHADER_BYTECODE&) {} + virtual void BlendStateCb(const D3D12_BLEND_DESC&) {} + virtual void DepthStencilStateCb(const D3D12_DEPTH_STENCIL_DESC&) {} + virtual void DepthStencilState1Cb(const D3D12_DEPTH_STENCIL_DESC1&) {} + virtual void DSVFormatCb(DXGI_FORMAT) {} + virtual void RasterizerStateCb(const D3D12_RASTERIZER_DESC&) {} + virtual void RTVFormatsCb(const D3D12_RT_FORMAT_ARRAY&) {} + virtual void SampleDescCb(const DXGI_SAMPLE_DESC&) {} + virtual void SampleMaskCb(UINT) {} + virtual void CachedPSOCb(const D3D12_CACHED_PIPELINE_STATE&) {} + + // Error Callbacks + virtual void ErrorBadInputParameter(UINT /*ParameterIndex*/) {} + virtual void ErrorDuplicateSubobject(D3D12_PIPELINE_STATE_SUBOBJECT_TYPE /*DuplicateType*/) {} + virtual void ErrorUnknownSubobject(UINT /*UnknownTypeValue*/) {} + +}; + +struct CD3DX12_PIPELINE_STATE_STREAM +{ + CD3DX12_PIPELINE_STATE_STREAM() {} + CD3DX12_PIPELINE_STATE_STREAM(const D3D12_GRAPHICS_PIPELINE_STATE_DESC& Desc) + : Flags(Desc.Flags) + , NodeMask(Desc.NodeMask) + , pRootSignature(Desc.pRootSignature) + , InputLayout(Desc.InputLayout) + , IBStripCutValue(Desc.IBStripCutValue) + , PrimitiveTopologyType(Desc.PrimitiveTopologyType) + , VS(Desc.VS) + , GS(Desc.GS) + , StreamOutput(Desc.StreamOutput) + , HS(Desc.HS) + , DS(Desc.DS) + , PS(Desc.PS) + , BlendState(CD3DX12_BLEND_DESC(Desc.BlendState)) + , DepthStencilState(CD3DX12_DEPTH_STENCIL_DESC1(Desc.DepthStencilState)) + , DSVFormat(Desc.DSVFormat) + , RasterizerState(CD3DX12_RASTERIZER_DESC(Desc.RasterizerState)) + , RTVFormats(CD3DX12_RT_FORMAT_ARRAY(Desc.RTVFormats, Desc.NumRenderTargets)) + , SampleDesc(Desc.SampleDesc) + , SampleMask(Desc.SampleMask) + , CachedPSO(Desc.CachedPSO) + {} + CD3DX12_PIPELINE_STATE_STREAM(const D3D12_COMPUTE_PIPELINE_STATE_DESC& Desc) + : Flags(Desc.Flags) + , NodeMask(Desc.NodeMask) + , pRootSignature(Desc.pRootSignature) + , CS(CD3DX12_SHADER_BYTECODE(Desc.CS)) + , CachedPSO(Desc.CachedPSO) + {} + CD3DX12_PIPELINE_STATE_STREAM_FLAGS Flags; + CD3DX12_PIPELINE_STATE_STREAM_NODE_MASK NodeMask; + CD3DX12_PIPELINE_STATE_STREAM_ROOT_SIGNATURE pRootSignature; + CD3DX12_PIPELINE_STATE_STREAM_INPUT_LAYOUT InputLayout; + CD3DX12_PIPELINE_STATE_STREAM_IB_STRIP_CUT_VALUE IBStripCutValue; + CD3DX12_PIPELINE_STATE_STREAM_PRIMITIVE_TOPOLOGY PrimitiveTopologyType; + CD3DX12_PIPELINE_STATE_STREAM_VS VS; + CD3DX12_PIPELINE_STATE_STREAM_GS GS; + CD3DX12_PIPELINE_STATE_STREAM_STREAM_OUTPUT StreamOutput; + CD3DX12_PIPELINE_STATE_STREAM_HS HS; + CD3DX12_PIPELINE_STATE_STREAM_DS DS; + CD3DX12_PIPELINE_STATE_STREAM_PS PS; + CD3DX12_PIPELINE_STATE_STREAM_CS CS; + CD3DX12_PIPELINE_STATE_STREAM_BLEND_DESC BlendState; + CD3DX12_PIPELINE_STATE_STREAM_DEPTH_STENCIL1 DepthStencilState; + CD3DX12_PIPELINE_STATE_STREAM_DEPTH_STENCIL_FORMAT DSVFormat; + CD3DX12_PIPELINE_STATE_STREAM_RASTERIZER RasterizerState; + CD3DX12_PIPELINE_STATE_STREAM_RENDER_TARGET_FORMATS RTVFormats; + CD3DX12_PIPELINE_STATE_STREAM_SAMPLE_DESC SampleDesc; + CD3DX12_PIPELINE_STATE_STREAM_SAMPLE_MASK SampleMask; + CD3DX12_PIPELINE_STATE_STREAM_CACHED_PSO CachedPSO; + D3D12_GRAPHICS_PIPELINE_STATE_DESC GraphicsDescV0() const + { + D3D12_GRAPHICS_PIPELINE_STATE_DESC D; + D.Flags = this->Flags; + D.NodeMask = this->NodeMask; + D.pRootSignature = this->pRootSignature; + D.InputLayout = this->InputLayout; + D.IBStripCutValue = this->IBStripCutValue; + D.PrimitiveTopologyType = this->PrimitiveTopologyType; + D.VS = this->VS; + D.GS = this->GS; + D.StreamOutput = this->StreamOutput; + D.HS = this->HS; + D.DS = this->DS; + D.PS = this->PS; + D.BlendState = this->BlendState; + D.DepthStencilState = CD3DX12_DEPTH_STENCIL_DESC1(D3D12_DEPTH_STENCIL_DESC1(this->DepthStencilState)); + D.DSVFormat = this->DSVFormat; + D.RasterizerState = this->RasterizerState; + D.NumRenderTargets = D3D12_RT_FORMAT_ARRAY(this->RTVFormats).NumRenderTargets; + memcpy(D.RTVFormats, D3D12_RT_FORMAT_ARRAY(this->RTVFormats).RTFormats, sizeof(D.RTVFormats)); + D.SampleDesc = this->SampleDesc; + D.SampleMask = this->SampleMask; + D.CachedPSO = this->CachedPSO; + return D; + } + D3D12_COMPUTE_PIPELINE_STATE_DESC ComputeDescV0() const + { + D3D12_COMPUTE_PIPELINE_STATE_DESC D; + D.Flags = this->Flags; + D.NodeMask = this->NodeMask; + D.pRootSignature = this->pRootSignature; + D.CS = this->CS; + D.CachedPSO = this->CachedPSO; + return D; + } +}; + +struct CD3DX12_PIPELINE_STATE_STREAM_PARSE_HELPER : public ID3DX12PipelineParserCallbacks +{ + CD3DX12_PIPELINE_STATE_STREAM PipelineStream; + + // ID3DX12PipelineParserCallbacks + void FlagsCb(D3D12_PIPELINE_STATE_FLAGS Flags) {PipelineStream.Flags = Flags;} + void NodeMaskCb(UINT NodeMask) {PipelineStream.NodeMask = NodeMask;} + void RootSignatureCb(ID3D12RootSignature* pRootSignature) {PipelineStream.pRootSignature = pRootSignature;} + void InputLayoutCb(const D3D12_INPUT_LAYOUT_DESC& InputLayout) {PipelineStream.InputLayout = InputLayout;} + void IBStripCutValueCb(D3D12_INDEX_BUFFER_STRIP_CUT_VALUE IBStripCutValue) {PipelineStream.IBStripCutValue = IBStripCutValue;} + void PrimitiveTopologyTypeCb(D3D12_PRIMITIVE_TOPOLOGY_TYPE PrimitiveTopologyType) {PipelineStream.PrimitiveTopologyType = PrimitiveTopologyType;} + void VSCb(const D3D12_SHADER_BYTECODE& VS) {PipelineStream.VS = VS;} + void GSCb(const D3D12_SHADER_BYTECODE& GS) {PipelineStream.GS = GS;} + void StreamOutputCb(const D3D12_STREAM_OUTPUT_DESC& StreamOutput) {PipelineStream.StreamOutput = StreamOutput;} + void HSCb(const D3D12_SHADER_BYTECODE& HS) {PipelineStream.HS = HS;} + void DSCb(const D3D12_SHADER_BYTECODE& DS) {PipelineStream.DS = DS;} + void PSCb(const D3D12_SHADER_BYTECODE& PS) {PipelineStream.PS = PS;} + void CSCb(const D3D12_SHADER_BYTECODE& CS) {PipelineStream.CS = CS;} + void BlendStateCb(const D3D12_BLEND_DESC& BlendState) {PipelineStream.BlendState = CD3DX12_BLEND_DESC(BlendState);} + void DepthStencilStateCb(const D3D12_DEPTH_STENCIL_DESC& DepthStencilState) {PipelineStream.DepthStencilState = CD3DX12_DEPTH_STENCIL_DESC1(DepthStencilState);} + void DepthStencilState1Cb(const D3D12_DEPTH_STENCIL_DESC1& DepthStencilState) {PipelineStream.DepthStencilState = CD3DX12_DEPTH_STENCIL_DESC1(DepthStencilState);} + void DSVFormatCb(DXGI_FORMAT DSVFormat) {PipelineStream.DSVFormat = DSVFormat;} + void RasterizerStateCb(const D3D12_RASTERIZER_DESC& RasterizerState) {PipelineStream.RasterizerState = CD3DX12_RASTERIZER_DESC(RasterizerState);} + void RTVFormatsCb(const D3D12_RT_FORMAT_ARRAY& RTVFormats) {PipelineStream.RTVFormats = RTVFormats;} + void SampleDescCb(const DXGI_SAMPLE_DESC& SampleDesc) {PipelineStream.SampleDesc = SampleDesc;} + void SampleMaskCb(UINT SampleMask) {PipelineStream.SampleMask = SampleMask;} + void CachedPSOCb(const D3D12_CACHED_PIPELINE_STATE& CachedPSO) {PipelineStream.CachedPSO = CachedPSO;} + void ErrorBadInputParameter(UINT) {} + void ErrorDuplicateSubobject(D3D12_PIPELINE_STATE_SUBOBJECT_TYPE) {} + void ErrorUnknownSubobject(UINT) {} +}; + +inline D3D12_PIPELINE_STATE_SUBOBJECT_TYPE D3DX12GetBaseSubobjectType(D3D12_PIPELINE_STATE_SUBOBJECT_TYPE SubobjectType) +{ + switch (SubobjectType) + { + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_DEPTH_STENCIL1: + return D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_DEPTH_STENCIL; + default: + return SubobjectType; + } +} + +inline HRESULT D3DX12ParsePipelineStream(const D3D12_PIPELINE_STATE_STREAM_DESC& Desc, ID3DX12PipelineParserCallbacks* pCallbacks) +{ + if (Desc.SizeInBytes == 0 || Desc.pPipelineStateSubobjectStream == nullptr) + { + pCallbacks->ErrorBadInputParameter(1); // first parameter issue + return E_INVALIDARG; + } + + if (pCallbacks == nullptr) + { + pCallbacks->ErrorBadInputParameter(2); // second parameter issue + return E_INVALIDARG; + } + + bool SubobjectSeen[D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_MAX_VALID] = {0}; + for (SIZE_T CurOffset = 0, SizeOfSubobject = 0; CurOffset < Desc.SizeInBytes; CurOffset += SizeOfSubobject) + { + BYTE* pStream = static_cast(Desc.pPipelineStateSubobjectStream)+CurOffset; + auto SubobjectType = *reinterpret_cast(pStream); + if (SubobjectType >= D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_MAX_VALID) + { + pCallbacks->ErrorUnknownSubobject(SubobjectType); + return E_INVALIDARG; + } + if (SubobjectSeen[D3DX12GetBaseSubobjectType(SubobjectType)]) + { + pCallbacks->ErrorDuplicateSubobject(SubobjectType); + return E_INVALIDARG; // disallow subobject duplicates in a stream + } + SubobjectSeen[SubobjectType] = true; + switch (SubobjectType) + { + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_ROOT_SIGNATURE: + pCallbacks->RootSignatureCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::pRootSignature); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_VS: + pCallbacks->VSCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::VS); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_PS: + pCallbacks->PSCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::PS); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_DS: + pCallbacks->DSCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::DS); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_HS: + pCallbacks->HSCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::HS); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_GS: + pCallbacks->GSCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::GS); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_CS: + pCallbacks->CSCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::CS); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_STREAM_OUTPUT: + pCallbacks->StreamOutputCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::StreamOutput); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_BLEND: + pCallbacks->BlendStateCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::BlendState); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_SAMPLE_MASK: + pCallbacks->SampleMaskCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::SampleMask); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_RASTERIZER: + pCallbacks->RasterizerStateCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::RasterizerState); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_DEPTH_STENCIL: + pCallbacks->DepthStencilStateCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM_DEPTH_STENCIL); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_DEPTH_STENCIL1: + pCallbacks->DepthStencilState1Cb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::DepthStencilState); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_INPUT_LAYOUT: + pCallbacks->InputLayoutCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::InputLayout); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_IB_STRIP_CUT_VALUE: + pCallbacks->IBStripCutValueCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::IBStripCutValue); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_PRIMITIVE_TOPOLOGY: + pCallbacks->PrimitiveTopologyTypeCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::PrimitiveTopologyType); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_RENDER_TARGET_FORMATS: + pCallbacks->RTVFormatsCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::RTVFormats); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_DEPTH_STENCIL_FORMAT: + pCallbacks->DSVFormatCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::DSVFormat); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_SAMPLE_DESC: + pCallbacks->SampleDescCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::SampleDesc); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_NODE_MASK: + pCallbacks->NodeMaskCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::NodeMask); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_CACHED_PSO: + pCallbacks->CachedPSOCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::CachedPSO); + break; + case D3D12_PIPELINE_STATE_SUBOBJECT_TYPE_FLAGS: + pCallbacks->FlagsCb(*reinterpret_cast(pStream)); + SizeOfSubobject = sizeof(CD3DX12_PIPELINE_STATE_STREAM::Flags); + break; + default: + pCallbacks->ErrorUnknownSubobject(SubobjectType); + return E_INVALIDARG; + break; + } + } + + return S_OK; +} +#endif + + +#endif // defined( __cplusplus ) + +#endif //__D3DX12_H__ + + + diff --git a/deps/DirectXTex/DirectXTex/scoped.h b/deps/DirectXTex/DirectXTex/scoped.h new file mode 100644 index 0000000..6e553c7 --- /dev/null +++ b/deps/DirectXTex/DirectXTex/scoped.h @@ -0,0 +1,62 @@ +//------------------------------------------------------------------------------------- +// scoped.h +// +// Utility header with helper classes for exception-safe handling of resources +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +//------------------------------------------------------------------------------------- + +#pragma once + +#include +#include +#include + +//--------------------------------------------------------------------------------- +struct aligned_deleter { void operator()(void* p) { _aligned_free(p); } }; + +typedef std::unique_ptr ScopedAlignedArrayFloat; + +typedef std::unique_ptr ScopedAlignedArrayXMVECTOR; + +//--------------------------------------------------------------------------------- +struct handle_closer { void operator()(HANDLE h) { assert(h != INVALID_HANDLE_VALUE); if (h) CloseHandle(h); } }; + +typedef std::unique_ptr ScopedHandle; + +inline HANDLE safe_handle( HANDLE h ) { return (h == INVALID_HANDLE_VALUE) ? 0 : h; } + +//--------------------------------------------------------------------------------- +struct find_closer { void operator()(HANDLE h) { assert(h != INVALID_HANDLE_VALUE); if (h) FindClose(h); } }; + +typedef std::unique_ptr ScopedFindHandle; + +//--------------------------------------------------------------------------------- +class auto_delete_file +{ +public: + auto_delete_file(HANDLE hFile) : m_handle(hFile) {} + + auto_delete_file(const auto_delete_file&) = delete; + auto_delete_file& operator=(const auto_delete_file&) = delete; + + ~auto_delete_file() + { + if (m_handle) + { + FILE_DISPOSITION_INFO info = { 0 }; + info.DeleteFile = TRUE; + (void)SetFileInformationByHandle(m_handle, FileDispositionInfo, &info, sizeof(info)); + } + } + + void clear() { m_handle = 0; } + +private: + HANDLE m_handle; +}; diff --git a/deps/DirectXTex/DirectXTex_Desktop_2013.sln b/deps/DirectXTex/DirectXTex_Desktop_2013.sln new file mode 100644 index 0000000..3dd5d29 --- /dev/null +++ b/deps/DirectXTex/DirectXTex_Desktop_2013.sln @@ -0,0 +1,99 @@ +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 2013 +VisualStudioVersion = 12.0.40629.0 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTex", "DirectXTex\DirectXTex_Desktop_2013.vcxproj", "{371B9FA9-4C90-4AC6-A123-ACED756D6C77}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "texassemble", "Texassemble\Texassemble_Desktop_2013.vcxproj", "{8F18CBD7-4116-4956-BCD8-20D688A4CBD1}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "texconv", "Texconv\Texconv_Desktop_2013.vcxproj", "{C3A65381-8FD3-4F69-B29E-654B4B0ED136}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DDSView", "DDSView\DDSView_Desktop_2013.vcxproj", "{9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Tools", "Tools", "{988C9BEB-76E0-4EFF-AA5F-92750E17C7DC}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Sample", "Sample", "{B66E9586-79BB-4CDB-9547-7857A789D71A}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "texdiag", "Texdiag\texdiag_Desktop_2013.vcxproj", "{8E31A619-F4F8-413F-A973-4EE37B1AAA5D}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Debug|x64 = Debug|x64 + Profile|Win32 = Profile|Win32 + Profile|x64 = Profile|x64 + Release|Win32 = Release|Win32 + Release|x64 = Release|x64 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.ActiveCfg = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.Build.0 = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.ActiveCfg = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.Build.0 = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.ActiveCfg = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.Build.0 = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.ActiveCfg = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.Build.0 = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.ActiveCfg = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.Build.0 = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.ActiveCfg = Release|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.Build.0 = Release|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|Win32.ActiveCfg = Debug|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|Win32.Build.0 = Debug|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|x64.ActiveCfg = Debug|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|x64.Build.0 = Debug|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|Win32.ActiveCfg = Profile|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|Win32.Build.0 = Profile|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|x64.ActiveCfg = Profile|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|x64.Build.0 = Profile|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|Win32.ActiveCfg = Release|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|Win32.Build.0 = Release|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|x64.ActiveCfg = Release|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|x64.Build.0 = Release|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|Win32.ActiveCfg = Debug|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|Win32.Build.0 = Debug|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|x64.ActiveCfg = Debug|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|x64.Build.0 = Debug|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|Win32.ActiveCfg = Profile|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|Win32.Build.0 = Profile|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|x64.ActiveCfg = Profile|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|x64.Build.0 = Profile|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|Win32.ActiveCfg = Release|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|Win32.Build.0 = Release|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|x64.ActiveCfg = Release|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|x64.Build.0 = Release|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|Win32.ActiveCfg = Debug|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|Win32.Build.0 = Debug|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|x64.ActiveCfg = Debug|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|x64.Build.0 = Debug|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|Win32.ActiveCfg = Profile|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|Win32.Build.0 = Profile|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|x64.ActiveCfg = Profile|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|x64.Build.0 = Profile|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|Win32.ActiveCfg = Release|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|Win32.Build.0 = Release|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|x64.ActiveCfg = Release|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|x64.Build.0 = Release|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|Win32.ActiveCfg = Debug|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|Win32.Build.0 = Debug|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|x64.ActiveCfg = Debug|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|x64.Build.0 = Debug|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|Win32.ActiveCfg = Profile|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|Win32.Build.0 = Profile|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|x64.ActiveCfg = Profile|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|x64.Build.0 = Profile|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|Win32.ActiveCfg = Release|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|Win32.Build.0 = Release|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|x64.ActiveCfg = Release|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|x64.Build.0 = Release|x64 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection + GlobalSection(NestedProjects) = preSolution + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1} = {988C9BEB-76E0-4EFF-AA5F-92750E17C7DC} + {C3A65381-8FD3-4F69-B29E-654B4B0ED136} = {988C9BEB-76E0-4EFF-AA5F-92750E17C7DC} + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84} = {B66E9586-79BB-4CDB-9547-7857A789D71A} + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D} = {988C9BEB-76E0-4EFF-AA5F-92750E17C7DC} + EndGlobalSection +EndGlobal diff --git a/deps/DirectXTex/DirectXTex_Desktop_2015.sln b/deps/DirectXTex/DirectXTex_Desktop_2015.sln new file mode 100644 index 0000000..53c5636 --- /dev/null +++ b/deps/DirectXTex/DirectXTex_Desktop_2015.sln @@ -0,0 +1,99 @@ +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 14 +VisualStudioVersion = 14.0.25420.1 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTex", "DirectXTex\DirectXTex_Desktop_2015.vcxproj", "{371B9FA9-4C90-4AC6-A123-ACED756D6C77}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "texassemble", "Texassemble\Texassemble_Desktop_2015.vcxproj", "{8F18CBD7-4116-4956-BCD8-20D688A4CBD1}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "texconv", "Texconv\Texconv_Desktop_2015.vcxproj", "{C3A65381-8FD3-4F69-B29E-654B4B0ED136}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DDSView", "DDSView\DDSView_Desktop_2015.vcxproj", "{9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Tools", "Tools", "{AEA1D9F7-EA95-4BF7-8E6D-0EA068077943}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Sample", "Sample", "{E14090F7-2FE9-47EE-A331-14ED71801FDE}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "texdiag", "Texdiag\texdiag_Desktop_2015.vcxproj", "{8E31A619-F4F8-413F-A973-4EE37B1AAA5D}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Debug|x64 = Debug|x64 + Profile|Win32 = Profile|Win32 + Profile|x64 = Profile|x64 + Release|Win32 = Release|Win32 + Release|x64 = Release|x64 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.ActiveCfg = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.Build.0 = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.ActiveCfg = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.Build.0 = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.ActiveCfg = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.Build.0 = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.ActiveCfg = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.Build.0 = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.ActiveCfg = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.Build.0 = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.ActiveCfg = Release|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.Build.0 = Release|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|Win32.ActiveCfg = Debug|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|Win32.Build.0 = Debug|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|x64.ActiveCfg = Debug|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|x64.Build.0 = Debug|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|Win32.ActiveCfg = Profile|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|Win32.Build.0 = Profile|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|x64.ActiveCfg = Profile|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|x64.Build.0 = Profile|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|Win32.ActiveCfg = Release|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|Win32.Build.0 = Release|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|x64.ActiveCfg = Release|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|x64.Build.0 = Release|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|Win32.ActiveCfg = Debug|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|Win32.Build.0 = Debug|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|x64.ActiveCfg = Debug|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|x64.Build.0 = Debug|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|Win32.ActiveCfg = Profile|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|Win32.Build.0 = Profile|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|x64.ActiveCfg = Profile|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|x64.Build.0 = Profile|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|Win32.ActiveCfg = Release|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|Win32.Build.0 = Release|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|x64.ActiveCfg = Release|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|x64.Build.0 = Release|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|Win32.ActiveCfg = Debug|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|Win32.Build.0 = Debug|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|x64.ActiveCfg = Debug|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|x64.Build.0 = Debug|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|Win32.ActiveCfg = Profile|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|Win32.Build.0 = Profile|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|x64.ActiveCfg = Profile|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|x64.Build.0 = Profile|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|Win32.ActiveCfg = Release|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|Win32.Build.0 = Release|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|x64.ActiveCfg = Release|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|x64.Build.0 = Release|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|Win32.ActiveCfg = Debug|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|Win32.Build.0 = Debug|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|x64.ActiveCfg = Debug|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|x64.Build.0 = Debug|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|Win32.ActiveCfg = Profile|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|Win32.Build.0 = Profile|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|x64.ActiveCfg = Profile|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|x64.Build.0 = Profile|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|Win32.ActiveCfg = Release|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|Win32.Build.0 = Release|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|x64.ActiveCfg = Release|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|x64.Build.0 = Release|x64 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection + GlobalSection(NestedProjects) = preSolution + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1} = {AEA1D9F7-EA95-4BF7-8E6D-0EA068077943} + {C3A65381-8FD3-4F69-B29E-654B4B0ED136} = {AEA1D9F7-EA95-4BF7-8E6D-0EA068077943} + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84} = {E14090F7-2FE9-47EE-A331-14ED71801FDE} + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D} = {AEA1D9F7-EA95-4BF7-8E6D-0EA068077943} + EndGlobalSection +EndGlobal diff --git a/deps/DirectXTex/DirectXTex_Desktop_2015_Win10.sln b/deps/DirectXTex/DirectXTex_Desktop_2015_Win10.sln new file mode 100644 index 0000000..f3ae491 --- /dev/null +++ b/deps/DirectXTex/DirectXTex_Desktop_2015_Win10.sln @@ -0,0 +1,33 @@ +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 14 +VisualStudioVersion = 14.0.23107.0 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTex", "DirectXTex\DirectXTex_Desktop_2015_Win10.vcxproj", "{371B9FA9-4C90-4AC6-A123-ACED756D6C77}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Debug|x64 = Debug|x64 + Profile|Win32 = Profile|Win32 + Profile|x64 = Profile|x64 + Release|Win32 = Release|Win32 + Release|x64 = Release|x64 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.ActiveCfg = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.Build.0 = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.ActiveCfg = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.Build.0 = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.ActiveCfg = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.Build.0 = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.ActiveCfg = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.Build.0 = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.ActiveCfg = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.Build.0 = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.ActiveCfg = Release|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.Build.0 = Release|x64 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/deps/DirectXTex/DirectXTex_Desktop_2017.sln b/deps/DirectXTex/DirectXTex_Desktop_2017.sln new file mode 100644 index 0000000..540177a --- /dev/null +++ b/deps/DirectXTex/DirectXTex_Desktop_2017.sln @@ -0,0 +1,99 @@ +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 2017 +VisualStudioVersion = 14.0.25420.1 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTex", "DirectXTex\DirectXTex_Desktop_2017.vcxproj", "{371B9FA9-4C90-4AC6-A123-ACED756D6C77}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "texassemble", "Texassemble\Texassemble_Desktop_2017.vcxproj", "{8F18CBD7-4116-4956-BCD8-20D688A4CBD1}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "texconv", "Texconv\Texconv_Desktop_2017.vcxproj", "{C3A65381-8FD3-4F69-B29E-654B4B0ED136}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DDSView", "DDSView\DDSView_Desktop_2017.vcxproj", "{9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Tools", "Tools", "{AEA1D9F7-EA95-4BF7-8E6D-0EA068077943}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Sample", "Sample", "{E14090F7-2FE9-47EE-A331-14ED71801FDE}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "texdiag", "Texdiag\texdiag_Desktop_2017.vcxproj", "{8E31A619-F4F8-413F-A973-4EE37B1AAA5D}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Debug|x64 = Debug|x64 + Profile|Win32 = Profile|Win32 + Profile|x64 = Profile|x64 + Release|Win32 = Release|Win32 + Release|x64 = Release|x64 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.ActiveCfg = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.Build.0 = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.ActiveCfg = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.Build.0 = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.ActiveCfg = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.Build.0 = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.ActiveCfg = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.Build.0 = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.ActiveCfg = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.Build.0 = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.ActiveCfg = Release|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.Build.0 = Release|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|Win32.ActiveCfg = Debug|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|Win32.Build.0 = Debug|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|x64.ActiveCfg = Debug|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Debug|x64.Build.0 = Debug|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|Win32.ActiveCfg = Profile|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|Win32.Build.0 = Profile|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|x64.ActiveCfg = Profile|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Profile|x64.Build.0 = Profile|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|Win32.ActiveCfg = Release|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|Win32.Build.0 = Release|Win32 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|x64.ActiveCfg = Release|x64 + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1}.Release|x64.Build.0 = Release|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|Win32.ActiveCfg = Debug|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|Win32.Build.0 = Debug|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|x64.ActiveCfg = Debug|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Debug|x64.Build.0 = Debug|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|Win32.ActiveCfg = Profile|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|Win32.Build.0 = Profile|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|x64.ActiveCfg = Profile|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Profile|x64.Build.0 = Profile|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|Win32.ActiveCfg = Release|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|Win32.Build.0 = Release|Win32 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|x64.ActiveCfg = Release|x64 + {C3A65381-8FD3-4F69-B29E-654B4B0ED136}.Release|x64.Build.0 = Release|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|Win32.ActiveCfg = Debug|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|Win32.Build.0 = Debug|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|x64.ActiveCfg = Debug|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Debug|x64.Build.0 = Debug|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|Win32.ActiveCfg = Profile|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|Win32.Build.0 = Profile|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|x64.ActiveCfg = Profile|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Profile|x64.Build.0 = Profile|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|Win32.ActiveCfg = Release|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|Win32.Build.0 = Release|Win32 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|x64.ActiveCfg = Release|x64 + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84}.Release|x64.Build.0 = Release|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|Win32.ActiveCfg = Debug|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|Win32.Build.0 = Debug|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|x64.ActiveCfg = Debug|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Debug|x64.Build.0 = Debug|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|Win32.ActiveCfg = Profile|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|Win32.Build.0 = Profile|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|x64.ActiveCfg = Profile|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Profile|x64.Build.0 = Profile|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|Win32.ActiveCfg = Release|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|Win32.Build.0 = Release|Win32 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|x64.ActiveCfg = Release|x64 + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D}.Release|x64.Build.0 = Release|x64 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection + GlobalSection(NestedProjects) = preSolution + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1} = {AEA1D9F7-EA95-4BF7-8E6D-0EA068077943} + {C3A65381-8FD3-4F69-B29E-654B4B0ED136} = {AEA1D9F7-EA95-4BF7-8E6D-0EA068077943} + {9D3EDCAD-A800-43F0-B77F-FE6E4DFA3D84} = {E14090F7-2FE9-47EE-A331-14ED71801FDE} + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D} = {AEA1D9F7-EA95-4BF7-8E6D-0EA068077943} + EndGlobalSection +EndGlobal diff --git a/deps/DirectXTex/DirectXTex_Desktop_2017_Win10.sln b/deps/DirectXTex/DirectXTex_Desktop_2017_Win10.sln new file mode 100644 index 0000000..a51448e --- /dev/null +++ b/deps/DirectXTex/DirectXTex_Desktop_2017_Win10.sln @@ -0,0 +1,33 @@ +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 2017 +VisualStudioVersion = 14.0.23107.0 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTex", "DirectXTex\DirectXTex_Desktop_2017_Win10.vcxproj", "{371B9FA9-4C90-4AC6-A123-ACED756D6C77}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Debug|x64 = Debug|x64 + Profile|Win32 = Profile|Win32 + Profile|x64 = Profile|x64 + Release|Win32 = Release|Win32 + Release|x64 = Release|x64 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.ActiveCfg = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.Build.0 = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.ActiveCfg = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.Build.0 = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.ActiveCfg = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.Build.0 = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.ActiveCfg = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.Build.0 = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.ActiveCfg = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.Build.0 = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.ActiveCfg = Release|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.Build.0 = Release|x64 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/deps/DirectXTex/DirectXTex_Windows10.sln b/deps/DirectXTex/DirectXTex_Windows10.sln new file mode 100644 index 0000000..5623847 --- /dev/null +++ b/deps/DirectXTex/DirectXTex_Windows10.sln @@ -0,0 +1,34 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 2017 +VisualStudioVersion = 14.0.22609.0 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTex", "DirectXTex\DirectXTex_Windows10.vcxproj", "{FB3F52B5-BFE8-43FD-836F-363735DAB738}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|ARM = Debug|ARM + Debug|x64 = Debug|x64 + Debug|x86 = Debug|x86 + Release|ARM = Release|ARM + Release|x64 = Release|x64 + Release|x86 = Release|x86 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Debug|ARM.ActiveCfg = Debug|ARM + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Debug|ARM.Build.0 = Debug|ARM + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Debug|x64.ActiveCfg = Debug|x64 + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Debug|x64.Build.0 = Debug|x64 + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Debug|x86.ActiveCfg = Debug|Win32 + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Debug|x86.Build.0 = Debug|Win32 + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Release|ARM.ActiveCfg = Release|ARM + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Release|ARM.Build.0 = Release|ARM + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Release|x64.ActiveCfg = Release|x64 + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Release|x64.Build.0 = Release|x64 + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Release|x86.ActiveCfg = Release|Win32 + {FB3F52B5-BFE8-43FD-836F-363735DAB738}.Release|x86.Build.0 = Release|Win32 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/deps/DirectXTex/DirectXTex_Windows81.sln b/deps/DirectXTex/DirectXTex_Windows81.sln new file mode 100644 index 0000000..e7cdb38 --- /dev/null +++ b/deps/DirectXTex/DirectXTex_Windows81.sln @@ -0,0 +1,43 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 2013 +VisualStudioVersion = 12.0.21005.1 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTex", "DirectXTex\DirectXTex_Windows81.vcxproj", "{371B9FA9-4C90-4AC6-A123-ACED756D6C77}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|ARM = Debug|ARM + Debug|Win32 = Debug|Win32 + Debug|x64 = Debug|x64 + Profile|ARM = Profile|ARM + Profile|Win32 = Profile|Win32 + Profile|x64 = Profile|x64 + Release|ARM = Release|ARM + Release|Win32 = Release|Win32 + Release|x64 = Release|x64 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|ARM.ActiveCfg = Debug|ARM + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|ARM.Build.0 = Debug|ARM + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.ActiveCfg = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|Win32.Build.0 = Debug|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.ActiveCfg = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Debug|x64.Build.0 = Debug|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|ARM.ActiveCfg = Profile|ARM + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|ARM.Build.0 = Profile|ARM + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.ActiveCfg = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|Win32.Build.0 = Profile|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.ActiveCfg = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Profile|x64.Build.0 = Profile|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|ARM.ActiveCfg = Release|ARM + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|ARM.Build.0 = Release|ARM + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.ActiveCfg = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|Win32.Build.0 = Release|Win32 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.ActiveCfg = Release|x64 + {371B9FA9-4C90-4AC6-A123-ACED756D6C77}.Release|x64.Build.0 = Release|x64 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/deps/DirectXTex/DirectXTex_WindowsPhone81.sln b/deps/DirectXTex/DirectXTex_WindowsPhone81.sln new file mode 100644 index 0000000..f361ea4 --- /dev/null +++ b/deps/DirectXTex/DirectXTex_WindowsPhone81.sln @@ -0,0 +1,28 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 2013 +VisualStudioVersion = 12.0.30324.0 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTex", "DirectXTex\DirectXTex_WindowsPhone81.vcxproj", "{5709AA1F-D4E3-4138-BDD6-55C8DAF3D983}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|ARM = Debug|ARM + Debug|Win32 = Debug|Win32 + Release|ARM = Release|ARM + Release|Win32 = Release|Win32 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {5709AA1F-D4E3-4138-BDD6-55C8DAF3D983}.Debug|ARM.ActiveCfg = Debug|ARM + {5709AA1F-D4E3-4138-BDD6-55C8DAF3D983}.Debug|ARM.Build.0 = Debug|ARM + {5709AA1F-D4E3-4138-BDD6-55C8DAF3D983}.Debug|Win32.ActiveCfg = Debug|Win32 + {5709AA1F-D4E3-4138-BDD6-55C8DAF3D983}.Debug|Win32.Build.0 = Debug|Win32 + {5709AA1F-D4E3-4138-BDD6-55C8DAF3D983}.Release|ARM.ActiveCfg = Release|ARM + {5709AA1F-D4E3-4138-BDD6-55C8DAF3D983}.Release|ARM.Build.0 = Release|ARM + {5709AA1F-D4E3-4138-BDD6-55C8DAF3D983}.Release|Win32.ActiveCfg = Release|Win32 + {5709AA1F-D4E3-4138-BDD6-55C8DAF3D983}.Release|Win32.Build.0 = Release|Win32 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/deps/DirectXTex/DirectXTex_XboxOneXDK_2015.sln b/deps/DirectXTex/DirectXTex_XboxOneXDK_2015.sln new file mode 100644 index 0000000..2e2f290 --- /dev/null +++ b/deps/DirectXTex/DirectXTex_XboxOneXDK_2015.sln @@ -0,0 +1,25 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 14 +VisualStudioVersion = 14.0.23107.0 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTex", "DirectXTex\DirectXTex_XboxOneXDK_2015.vcxproj", "{879B5023-53B7-4108-AEAE-F019C2E9410D}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Durango = Debug|Durango + Profile|Durango = Profile|Durango + Release|Durango = Release|Durango + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Debug|Durango.ActiveCfg = Debug|Durango + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Debug|Durango.Build.0 = Debug|Durango + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Profile|Durango.ActiveCfg = Profile|Durango + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Profile|Durango.Build.0 = Profile|Durango + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Release|Durango.ActiveCfg = Release|Durango + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Release|Durango.Build.0 = Release|Durango + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/deps/DirectXTex/DirectXTex_XboxOneXDK_2017.sln b/deps/DirectXTex/DirectXTex_XboxOneXDK_2017.sln new file mode 100644 index 0000000..d350cf8 --- /dev/null +++ b/deps/DirectXTex/DirectXTex_XboxOneXDK_2017.sln @@ -0,0 +1,25 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 2017 +VisualStudioVersion = 14.0.23107.0 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTex", "DirectXTex\DirectXTex_XboxOneXDK_2017.vcxproj", "{879B5023-53B7-4108-AEAE-F019C2E9410D}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Durango = Debug|Durango + Profile|Durango = Profile|Durango + Release|Durango = Release|Durango + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Debug|Durango.ActiveCfg = Debug|Durango + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Debug|Durango.Build.0 = Debug|Durango + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Profile|Durango.ActiveCfg = Profile|Durango + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Profile|Durango.Build.0 = Profile|Durango + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Release|Durango.ActiveCfg = Release|Durango + {879B5023-53B7-4108-AEAE-F019C2E9410D}.Release|Durango.Build.0 = Release|Durango + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/deps/DirectXTex/LICENSE b/deps/DirectXTex/LICENSE new file mode 100644 index 0000000..73617f0 --- /dev/null +++ b/deps/DirectXTex/LICENSE @@ -0,0 +1,21 @@ + The MIT License (MIT) + +Copyright (c) 2017 Microsoft Corp + +Permission is hereby granted, free of charge, to any person obtaining a copy of this +software and associated documentation files (the "Software"), to deal in the Software +without restriction, including without limitation the rights to use, copy, modify, +merge, publish, distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to the following +conditions: + +The above copyright notice and this permission notice shall be included in all copies +or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, +INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A +PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF +CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE +OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + diff --git a/deps/DirectXTex/ReadMe.txt b/deps/DirectXTex/ReadMe.txt new file mode 100644 index 0000000..c4ad05c --- /dev/null +++ b/deps/DirectXTex/ReadMe.txt @@ -0,0 +1,412 @@ +DIRECTX TEXTURE LIBRARY (DirectXTex) +------------------------------------ + +Copyright (c) Microsoft Corporation. All rights reserved. + +July 26, 2017 + +This package contains DirectXTex, a shared source library for reading and writing DDS +files, and performing various texture content processing operations including +resizing, format conversion, mip-map generation, block compression for Direct3D runtime +texture resources, and height-map to normal-map conversion. This library makes +use of the Windows Image Component (WIC) APIs. It also includes simple .TGA and .HDR +readers and writers since these image file formats are commonly used for texture content +processing pipelines, but are not currently supported by a built-in WIC codec. + +The source is written for Visual Studio 2013 or 2015. It is recommended that you +make use of VS 2013 Update 5 or VS 2015 Update 3 and Windows 7 Service Pack 1 or later. + +DirectXTex\ + This contains the DirectXTex library. This includes a full-featured DDS reader and writer + including legacy format conversions, a TGA reader and writer, a HDR reader and writer, + a WIC-based bitmap reader and writer (BMP, JPEG, PNG, TIFF, and HD Photo), and various + texture processing functions. This is intended primarily for tool usage. + + Note that the majority of the header files here are intended for internal implementation + of the library only (BC.h, BCDirectCompute.h, DDS.h, DirectXTexP.h, filters.h, and scoped.h). + Only DirectXTex.h is meant as a 'public' header for the library. + +Texconv\ + This DirectXTex sample is an implementation of the "texconv" command-line texture utility + from the DirectX SDK utilizing DirectXTex rather than D3DX. + + It supports the same arguments as the Texture Conversion Tool Extended (texconvex.exe) DirectX + SDK utility. The primary differences are the -10 and -11 arguments are not applicable and the + filter names (POINT, LINEAR, CUBIC, FANT or BOX, TRIANGLE, *_DITHER, *_DITHER_DIFFUSION). + This also includes support for the JPEG XR (HD Photo) bitmap format. + (see ) + + See for details. + +Texassemble\ + This DirectXTex sample is a command-line utility for creating cubemaps, volume maps, or + texture arrays from a set of individual input image files. + + See for details. + +Texdiag\ + This DirectXTex sample is a command-line utility for analyzing image contents, primarily for + debugging purposes. + + See + +DDSView\ + This DirectXTex sample is a simple Direct3D 11-based viewer for DDS files. For array textures + or volume maps, the "<" and ">" keyboard keys will show different images contained in the DDS. + The "1" through "0" keys can also be used to jump to a specific image index. + +DDSTextureLoader\ + This contains a streamlined version of the DirectX SDK sample DDSWithoutD3DX11 texture + loading code for a simple light-weight runtime DDS loader. This version only supports + Direct3D 11 or Direct3D 12 and performs no runtime pixel data conversions (i.e. 24bpp + legacy DDS files always fail). This is ideal for runtime usage, and supports the full + complement of Direct3D texture resources (1D, 2D, volume maps, cubemaps, mipmap levels, + texture arrays, BC formats, etc.). + +ScreenGrab\ + This contains screen grab modules for Direct3D 11 and Direct3D 12 primarily intended + for creating screenshots. The images are written as a DDS or as an image file format + using WIC. + +WICTextureLoader\ + This contains a Direct3D 11 and Direct3D 12 2D texture loader that uses WIC to load a + bitmap (BMP, JPEG, PNG, HD Photo, or other WIC supported file container), resize if needed + based on the current feature level (or by explicit parameter), format convert to a + DXGI_FORMAT if required, and then create a 2D texture. Note this does not support 1D textures, + volume textures, cubemaps, or texture arrays. DDSTextureLoader is recommended for fully + "precooked" textures for maximum performance and image quality, but this loader can be useful + for creating simple 2D texture from standard image files at runtime. + +NOTE: DDSTextureLoader, ScreenGrab, and WICTextureLoader are 'stand-alone' versions of the same + modules provided in the DirectX Tool Kit. + +All content and source code for this package are subject to the terms of the MIT License. +. + +Documentation is available at . + +For the latest version of DirectXTex, bug reports, etc. please visit the project site. + +http://go.microsoft.com/fwlink/?LinkId=248926 + +This project has adopted the Microsoft Open Source Code of Conduct. For more information see the +Code of Conduct FAQ or contact opencode@microsoft.com with any additional questions or comments. + +https://opensource.microsoft.com/codeofconduct/ + + +------------------------------------ +RELEASE NOTES + +* The alpha mode specification for DDS files was updated between the March 2013 and April 2013 releases. Any + DDS files created using the DDS_FLAGS_FORCE_DX10_EXT_MISC2 flag or the texconv -dx10 switch using the + March 2013 release should be refreshed. + +* Due to the underlying Windows BMP WIC codec, alpha channels are not supported for 16bpp or 32bpp BMP pixel format + files. The Windows 8.x and Windows 10 version of the Windows BMP WIC codec does support 32bpp pixel formats with + alpha when using the BITMAPV5HEADER file header. Note the updated WIC is available on Windows 7 SP1 with KB 2670838 + installed. + +* While DXGI 1.0 and DXGI 1.1 include 5:6:5 (DXGI_FORMAT_B5G6R5_UNORM) and 5:5:5:1 (DXGI_FORMAT_B5G5R5A1_UNORM) + pixel format enumerations, the DirectX 10.x and 11.0 Runtimes do not support these formats for use with Direct3D. + The DirectX 11.1 runtime, DXGI 1.2, and the WDDM 1.2 driver model fully support 16bpp formats (5:6:5, 5:5:5:1, and + 4:4:4:4). + +* WICTextureLoader cannot load .TGA or .HDR files unless the system has a 3rd party WIC codec installed. You + must use the DirectXTex library for TGA/HDR file format support without relying on an add-on WIC codec. + +* Loading of 96bpp floating-point TIFF files results in a corrupted image prior to Windows 8. This fix is available + on Windows 7 SP1 with KB 2670838 installed. + + +------------------------------------ +RELEASE HISTORY + +July 26, 2017 + Support for reading non-standard DDS files written by nVidia Texture Tools (NVTT) + Fix for ComputeMSE when using CMSE_IMAGE2_X2_BIAS + Fix for WIC writer then codec target format requires a palette + Code cleanup + +April 24, 2017 + VS 2017 project updates + Regenerated shaders using Windows 10 Creators Update SDK (15063) + Updated D3DX12 internal copy to latest version + +April 7, 2017 + VS 2017 updated for Windows Creators Update SDK (15063) + texassemble: -tonemap switch + texconv: -wicmulti switch + +January 31, 2017 + DirectX 12 versions of IsSupported, CreateTexture (PrepareUpload), and CaptureTexture + Update to DirectX 11 version of IsSupported + WIC format 40bppCMYKAlpha should be converted to RGBA8 rather than RGBA16 + DDS support for L8A8 with bitcount 8 rather than 16 + DXGI_FORMAT_R32G8X24_TYPELESS and DXGI_FORMAT_R24G8_TYPELESS should be IsDepthStencil formats + Updates to DDSTextureLoader, ScreenGrab, and WICTextureLoader + Minor code cleanup + +December 5, 2016 + Fixed over-validation in DDS header parsing + VS 2017 RC projects added + Minor code cleanup + +October 5, 2016 + *breaking change* + Renamed Evaluate to EvaluateImage, Transform to TransformImage + texdiag: new command-line tool for texture debugging + texconv: -bcmax, -bcquick, -tonemap, and -x2bias switches + texconv: overwrite writing and -y switch + texconv/texassemble: optional OpenEXR support + texassemble: command syntax with support for generating strip and cross images from cubemap + Updates to DDSTextureLoader, WICTextureLoader, and ScreenGrab + Minor code cleanup + +September 14, 2016 + HDR (RGBE Radiance) file format reader and writer + Evaluate and Transform functions for computing user-defined functions on images + Fix BC6H GPU shaders on WARP device + Fix for alignment issues on ARM devices in software compression codec + Added TEX_THRESHOLD_DEFAULT (0.5f) constant default alpha threshold value for Convert & Compress + Minor CaptureTexture optimization + texconv/texassemble: Support for .hdr file format + texconv: added -gpu switch to specify adapter to use for GPU-based compression codecs + texconv: added -badtails switch to enable loading of legacy DXTn DDS files with incomplete mipchain tails + texconv: added -c switch for old-school colorkey/chromakey transparency to alpha conversion + texconv: added -alpha switch for reverse premultiply along with TEX_PMALPHA_REVERSE flag + texconv: added wildcard support for input filename and optional -r switch for recursive search + +August 4, 2016 + CompileShader script updated to build external pdbs + Regenerated shaders using Windows 10 Anniversary Update SDK (14393) + +August 2, 2016 + Updated for VS 2015 Update 3 and Windows 10 SDK (14393) + +August 1, 2016 + Workaround for bug in XMStoreFloat3SE (impacts conversions to DXGI_FORMAT_R9G9B9E5_SHAREDEXP) + DDSTextureLoader12, WICTextureLoader12, and ScreenGrab12 for Direct3D 12 support + Minor code cleanup + +June 27, 2016 + texconv command-line tool -wicq and -wiclossless switches + Code cleanup + +April 26, 2016 + Optional callback from WIC reader functions to query additional metadata + Retired obsolete adapter code + Minor code cleanup + +February 23, 2016 + Fix to clean up partial or zero-length image files on failed write + Retired VS 2012 projects + +November 30, 2015 + texconv command-line tool -fl switch now supports 12.0 and 12.1 feature levels + Updated for VS 2015 Update 1 and Windows 10 SDK (10586) + +October 30, 2015 + DDS support for legacy bumpmap formats (V8U8, Q8W8V8U8, V16U16) + Fix for buffer overread in BC CPU compressor + Minor code cleanup + +August 18, 2015 + Added GetWICFactory and SetWICFactory + Updates for new DXGI 1.3 types + Xbox One platform updates + +July 29, 2015 + Fixed rounding problem with 32-bit RGBA/BGRA format conversions + texconv: use CPU parallel compression for BC1-BC5 (-singleproc disables) + Updated for VS 2015 and Windows 10 SDK RTM + Retired VS 2010 and Windows 8.0 Store projects + +June 18, 2015 + New BC_FLAGS_USE_3SUBSETS option for BC7 compressors; now defaults to skipping 3 subset blocks + Fixed bug with MakeTypeless and A8_UNORM + Fixed file length validation problem in LoadDDSFromFile + +March 27, 2015 + Added projects for Windows apps Technical Preview + Fixed bug with WIC-based mipmap generation for non-WIC supported formats + Fixed bug with WIC multiframe loader when resizing required + texconv: Added -nmap/-nmapamp for generating normal maps from height maps + texconv/texassemble: Updated to load multiframe WIC files (tiff, gif) + Minor code cleanup + +November 24, 2014 + Updates for Visual Studio 2015 Technical Preview + Minor code cleanup + +September 22, 2014 + Format conversion improvements and bug fixes (depth/stencil, alpha-only, float16, RGB -> 1 channel) + Fixed issue when BC decompressing non-standard compressed rowPitch images + Explicit calling-convention annotation for all 'public' functions + Code cleanup + Xbox One platform updates + +July 15, 2014 + texconv command-line tool fixes + Fixed problem with 'wide' images with CPU Compress + Updates to Xbox One platform support + +April 3, 2014 + Windows phone 8.1 platform support + +February 24, 2014 + Direct3D 11 video and Xbox One extended format support + New APIs: IsPlanar, IsPalettized, IsDepthStencil, ConvertToSinglePlane + Added 'alphaWeight' parameter to GPU Compress [breaking change] + texconv '-aw' switch to control the alpha weighting for the BC7 GPU compressor + Fixed bug with ordered dithering in non-WIC conversion codepaths + Fixed SaveToDDS* functions when using arbitrary row pitch values + +January 24, 2014 + Added sRGB flags for Compress (TEX_COMPRESS_SRGB*) + Added 'compress' flag parameter to GPU versions of Compress [breaking change] + Minor fix for potential rounding problem in GPU Compress + Code cleanup (removed DXGI_1_2_FORMATS control define; ScopedObject typedef removed) + Dropped VS 2010 support without the Windows 8.1 SDK (removed USE_XNAMATH control define) + +December 24, 2013 + texconv updated with -fl and -pow2 command-line switches + Fixed bug in Resize when doing custom filtering which occurred when exactly doubling the image size + Added move operators to ScratchImage and Blob classes + Xbox One platform support + +October 21, 2013 + Updated for Visual Studio 2013 and Windows 8.1 SDK RTM + PremultiplyAlpha updated with new 'flags' parameter and to use sRGB correct blending + Fixed colorspace conversion issue with DirectCompute compressor when compressing for BC7 SRGB + +August 13, 2013 + DirectCompute 4.0 BC6H/BC7 compressor integration + texconv utility uses DirectCompute compression by default for BC6H/BC7, -nogpu disables use of DirectCompute + +August 1, 2013 + Support for BC compression/decompression of non-power-of-2 mipmapped textures + Fixes for BC6H / BC7 codecs to better match published standard + Fix for BC4 / BC5 codecs when compressing RGB images + Minor fix for the BC1-3 codec + New optional flags for ComputeMSE to compare UNORM vs. SNORM images + New WIC loading flag added to control use of WIC metadata to return sRGB vs. non-sRGB formats + Code cleanup and /analyze fixes + Project file cleanup + Texconv utility uses parallel BC compression by default for BC6H/BC7, -singleproc disables multithreaded behavior + +July 1, 2013 + VS 2013 Preview projects added + SaveToWIC functions updated with new optional setCustomProps parameter + +June 15, 2013 + Custom filtering implementation for Resize & GenerateMipMaps(3D) - Point, Box, Linear, Cubic, and Triangle + TEX_FILTER_TRIANGLE finite low-pass triangle filter + TEX_FILTER_WRAP, TEX_FILTER_MIRROR texture semantics for custom filtering + TEX_FILTER_BOX alias for TEX_FILTER_FANT WIC + Ordered and error diffusion dithering for non-WIC conversion + sRGB gamma correct custom filtering and conversion + DDS_FLAGS_EXPAND_LUMINANCE - Reader conversion option for L8, L16, and A8L8 legacy DDS files + Added use of WIC metadata for sRGB pixel formats + Added BitsPerColor utility function + Fixed Convert threshold parameter usage + Non-power-of-2 volume map support, fixed bug with non-square volume maps + Texconv utility update with -xlum, -wrap, and -mirror options; reworked -if options for improved dithering + Texassemble utility for creating cubemaps, volume maps, and texture arrays + DDSTextureLoader and WICTextureLoader sync'd with DirectXTK versions + +April 16, 2013 + Updated alpha-mode metadata details in .DDS files + Added new control flags for Convert + Added new optional flags for ComputeMSE + Fixed conversion handling for sRGB formats + Fixed internal routines for handling R10G10B10_XR_BIAS_A2_UNORM, R9G9B9E5_SHAREDEXP, and FORMAT_R1_UNORM + Fixed WIC I/O for GUID_WICPixelFormat32bppRGBE pixel format files (HD Photo) + Fixed non-square image handling in GenerateMipMaps3D + Fixed some error handling in the DDS load code + +March 22, 2013 + Supports reading and writing alpha-mode (straight, premultiplied, etc.) metadata in .DDS files + Added build option to use WICCreateImagingFactory_Proxy instead of CoCreateInstance to obtain WIC factory + +January 29, 2013 + Added PremultiplyAlpha to DirectXTex; -pmalpha switch for texconv command-line tool + Fixed problem with forceSRGB implementation for Ex versions of CreateTexture, CreateShaderResourceView, DDSTextureLoader and WICTextureLoader + +December 11, 2012 + Ex versions of CreateTexture, CreateShaderResourceView, DDSTextureLoader and WICTextureLoader + Fixed BC2 and BC3 decompression issue for unusual color encoding case + Converted annotation to SAL2 for improved VS 2012 /analyze experience + Updated DirectXTex, DDSView, and Texconv with VS 2010 + Windows 8.0 SDK project using official 'property sheets' + +November 15, 2012 + Added support for WIC2 when available on Windows 8 and Windows 7 with KB 2670838 + Added optional targetGUID parameter to SaveWIC* APIs to influence final container pixel format choice + Fixed bug in SaveDDS* which was generating invalid DDS files for 1D dimension textures + Improved robustness of CaptureTexture when resolving MSAA source textures + Sync'd DDSTextureLoader, ScreenGrab, and WICTextureLoader standalone versions with latest DirectXTK release + +September 28, 2012 + Added ScreenGrab module for creating runtime screenshots + Renamed project files for better naming consistency + New Typeless utilities for DirectXTex + Some minor code cleanup for DirectXTex's WIC writer function + Bug fixes and new -tu/-tf options for texconv + +June 22, 2012 + Moved to using XNA Math 2.05 instead of XNA Math 2.04 for USE_XNAMATH builds + Fixed BGR vs. RGB color channel swizzle problem with 24bpp legacy .DDS files in DirectXTex + Update to DirectXTex WIC and WICTextureLoader for additional 96bpp float format handling on Windows 8 + +May 31, 2012 + Minor fix for DDSTextureLoader's retry fallback that can happen with 10level9 feature levels + Switched to use "_DEBUG" instead of "DEBUG" and cleaned up debug warnings + added Windows Store style application project files for DirectXTex + +April 20, 2012 + DirectTex's WIC-based writer opts-in for the Windows 8 BMP encoder option for writing 32 bpp RGBA files with the BITMAPV5HEADER + +March 30, 2012 + WICTextureLoader updated with Windows 8 WIC pixel formats + DirectXTex updated with limited non-power-of-2 texture support and TEX_FILTER_SEPARATE_ALPHA option + Texconv updated with '-sepalpha' command-line option + Added USE_XNAMATH control define to build DirectXTex using either XNAMath or DirectXMath + Added VS 2012 project files (which use DirectXMath instead of XNAMath and define DXGI_1_2_FORMATS) + +March 15, 2012 + Fix for resource leak in CreateShaderResourceView() Direct3D 11 helper function in DirectXTex + +March 5, 2012 + Fix for too much temp memory allocated by WICTextureLoader; cleaned up legacy 'min/max' macro usage in DirectXTex + +February 21, 2012 + WICTextureLoader updated to handle systems and device drivers without BGRA or 16bpp format support + +February 20, 2012 + Some code cleanup for DirectXTex and DDSTextureLoader + Fixed bug in 10:10:10:2 format fixup in the LoadDDSFromMemory function + Fixed bugs in "non-zero alpha" special-case handling in LoadTGAFromFile + Fixed bug in _SwizzleScanline when copying alpha channel for BGRA<->RGBA swizzling + +February 11, 2012 + Update of DDSTextureLoader to also build in Windows Store style apps; added WICTextureLoader + Added CMYK WIC pixel formats to the DirectXTex conversion table + +January 30, 2012 + Minor code-cleanup for DirectXTex to enable use of PCH through 'directxtexp.h' header + +January 24, 2011 + Some code-cleanup for DirectXTex + Added DXGI 1.2 implementation for DDSTextureLoader and DirectXTex guarded with DXGI_1_2_FORMATS compiliation define + +December 16, 2011 + Fixed x64 compilation warnings in DDSTextureLoader + +November 30, 2011 + Fixed some of the constants used in IsSupportedTexture(), + added ability to strip off top levels of mips in DDSTextureLoader, + changed DirectXTex to use CoCreateInstance rather than LoadLibrary to obtain the WIC factory, + a few minor /analyze related annotations for DirectXTex + +October 27, 2011 + Original release \ No newline at end of file diff --git a/deps/DirectXTex/ScreenGrab/ScreenGrab.cpp b/deps/DirectXTex/ScreenGrab/ScreenGrab.cpp new file mode 100644 index 0000000..b1e8c55 --- /dev/null +++ b/deps/DirectXTex/ScreenGrab/ScreenGrab.cpp @@ -0,0 +1,1196 @@ +//-------------------------------------------------------------------------------------- +// File: ScreenGrab.cpp +// +// Function for capturing a 2D texture and saving it to a file (aka a 'screenshot' +// when used on a Direct3D 11 Render Target). +// +// Note these functions are useful as a light-weight runtime screen grabber. For +// full-featured texture capture, DDS writer, and texture processing pipeline, +// see the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +// Does not capture 1D textures or 3D textures (volume maps) + +// Does not capture mipmap chains, only the top-most texture level is saved + +// For 2D array textures and cubemaps, it captures only the first image in the array + +#include "ScreenGrab.h" + +#include +#include + +#include + +#include + +#include +#include + +using Microsoft::WRL::ComPtr; + +//-------------------------------------------------------------------------------------- +// Macros +//-------------------------------------------------------------------------------------- +#ifndef MAKEFOURCC + #define MAKEFOURCC(ch0, ch1, ch2, ch3) \ + ((uint32_t)(uint8_t)(ch0) | ((uint32_t)(uint8_t)(ch1) << 8) | \ + ((uint32_t)(uint8_t)(ch2) << 16) | ((uint32_t)(uint8_t)(ch3) << 24 )) +#endif /* defined(MAKEFOURCC) */ + +//-------------------------------------------------------------------------------------- +// DDS file structure definitions +// +// See DDS.h in the 'Texconv' sample and the 'DirectXTex' library +//-------------------------------------------------------------------------------------- +namespace +{ + #pragma pack(push,1) + + #define DDS_MAGIC 0x20534444 // "DDS " + + struct DDS_PIXELFORMAT + { + uint32_t size; + uint32_t flags; + uint32_t fourCC; + uint32_t RGBBitCount; + uint32_t RBitMask; + uint32_t GBitMask; + uint32_t BBitMask; + uint32_t ABitMask; + }; + + #define DDS_FOURCC 0x00000004 // DDPF_FOURCC + #define DDS_RGB 0x00000040 // DDPF_RGB + #define DDS_RGBA 0x00000041 // DDPF_RGB | DDPF_ALPHAPIXELS + #define DDS_LUMINANCE 0x00020000 // DDPF_LUMINANCE + #define DDS_LUMINANCEA 0x00020001 // DDPF_LUMINANCE | DDPF_ALPHAPIXELS + #define DDS_ALPHA 0x00000002 // DDPF_ALPHA + #define DDS_BUMPDUDV 0x00080000 // DDPF_BUMPDUDV + + #define DDS_HEADER_FLAGS_TEXTURE 0x00001007 // DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT + #define DDS_HEADER_FLAGS_MIPMAP 0x00020000 // DDSD_MIPMAPCOUNT + #define DDS_HEADER_FLAGS_PITCH 0x00000008 // DDSD_PITCH + #define DDS_HEADER_FLAGS_LINEARSIZE 0x00080000 // DDSD_LINEARSIZE + + #define DDS_HEIGHT 0x00000002 // DDSD_HEIGHT + #define DDS_WIDTH 0x00000004 // DDSD_WIDTH + + #define DDS_SURFACE_FLAGS_TEXTURE 0x00001000 // DDSCAPS_TEXTURE + + typedef struct + { + uint32_t size; + uint32_t flags; + uint32_t height; + uint32_t width; + uint32_t pitchOrLinearSize; + uint32_t depth; // only if DDS_HEADER_FLAGS_VOLUME is set in flags + uint32_t mipMapCount; + uint32_t reserved1[11]; + DDS_PIXELFORMAT ddspf; + uint32_t caps; + uint32_t caps2; + uint32_t caps3; + uint32_t caps4; + uint32_t reserved2; + } DDS_HEADER; + + typedef struct + { + DXGI_FORMAT dxgiFormat; + uint32_t resourceDimension; + uint32_t miscFlag; // see D3D11_RESOURCE_MISC_FLAG + uint32_t arraySize; + uint32_t reserved; + } DDS_HEADER_DXT10; + + #pragma pack(pop) + + const DDS_PIXELFORMAT DDSPF_DXT1 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','1'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_DXT3 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','3'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_DXT5 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','5'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC4_UNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','4','U'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC4_SNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','4','S'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC5_UNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','5','U'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC5_SNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','5','S'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_R8G8_B8G8 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('R','G','B','G'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_G8R8_G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('G','R','G','B'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_YUY2 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('Y','U','Y','2'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_A8R8G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x00ff0000, 0x0000ff00, 0x000000ff, 0xff000000 }; + + const DDS_PIXELFORMAT DDSPF_X8R8G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00000000 }; + + const DDS_PIXELFORMAT DDSPF_A8B8G8R8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; + + const DDS_PIXELFORMAT DDSPF_G16R16 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0x0000ffff, 0xffff0000, 0x00000000, 0x00000000 }; + + const DDS_PIXELFORMAT DDSPF_R5G6B5 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 16, 0x0000f800, 0x000007e0, 0x0000001f, 0x00000000 }; + + const DDS_PIXELFORMAT DDSPF_A1R5G5B5 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x00007c00, 0x000003e0, 0x0000001f, 0x00008000 }; + + const DDS_PIXELFORMAT DDSPF_A4R4G4B4 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x00000f00, 0x000000f0, 0x0000000f, 0x0000f000 }; + + const DDS_PIXELFORMAT DDSPF_L8 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCE, 0, 8, 0xff, 0x00, 0x00, 0x00 }; + + const DDS_PIXELFORMAT DDSPF_L16 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCE, 0, 16, 0xffff, 0x0000, 0x0000, 0x0000 }; + + const DDS_PIXELFORMAT DDSPF_A8L8 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCEA, 0, 16, 0x00ff, 0x0000, 0x0000, 0xff00 }; + + const DDS_PIXELFORMAT DDSPF_A8 = + { sizeof(DDS_PIXELFORMAT), DDS_ALPHA, 0, 8, 0x00, 0x00, 0x00, 0xff }; + + const DDS_PIXELFORMAT DDSPF_V8U8 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 16, 0x00ff, 0xff00, 0x0000, 0x0000 }; + + const DDS_PIXELFORMAT DDSPF_Q8W8V8U8 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 32, 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; + + const DDS_PIXELFORMAT DDSPF_V16U16 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 32, 0x0000ffff, 0xffff0000, 0x00000000, 0x00000000 }; + + // DXGI_FORMAT_R10G10B10A2_UNORM should be written using DX10 extension to avoid D3DX 10:10:10:2 reversal issue + + // This indicates the DDS_HEADER_DXT10 extension is present (the format is in dxgiFormat) + const DDS_PIXELFORMAT DDSPF_DX10 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','1','0'), 0, 0, 0, 0, 0 }; + + //----------------------------------------------------------------------------- + struct handle_closer { void operator()(HANDLE h) { if (h) CloseHandle(h); } }; + + typedef public std::unique_ptr ScopedHandle; + + inline HANDLE safe_handle( HANDLE h ) { return (h == INVALID_HANDLE_VALUE) ? 0 : h; } + + class auto_delete_file + { + public: + auto_delete_file(HANDLE hFile) : m_handle(hFile) {} + ~auto_delete_file() + { + if (m_handle) + { + FILE_DISPOSITION_INFO info = {}; + info.DeleteFile = TRUE; + (void)SetFileInformationByHandle(m_handle, FileDispositionInfo, &info, sizeof(info)); + } + } + + void clear() { m_handle = 0; } + + private: + HANDLE m_handle; + + auto_delete_file(const auto_delete_file&) = delete; + auto_delete_file& operator=(const auto_delete_file&) = delete; + }; + + class auto_delete_file_wic + { + public: + auto_delete_file_wic(ComPtr& hFile, const wchar_t* szFile) : m_handle(hFile), m_filename(szFile) {} + ~auto_delete_file_wic() + { + if (m_filename) + { + m_handle.Reset(); + DeleteFileW(m_filename); + } + } + + void clear() { m_filename = 0; } + + private: + const wchar_t* m_filename; + ComPtr& m_handle; + + auto_delete_file_wic(const auto_delete_file_wic&) = delete; + auto_delete_file_wic& operator=(const auto_delete_file_wic&) = delete; + }; + + //-------------------------------------------------------------------------------------- + // Return the BPP for a particular format + //-------------------------------------------------------------------------------------- + size_t BitsPerPixel( _In_ DXGI_FORMAT fmt ) + { + switch( fmt ) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + return 128; + + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return 96; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_R32G32_TYPELESS: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + return 64; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R11G11B10_FLOAT: + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_R16G16_TYPELESS: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + case DXGI_FORMAT_R32_TYPELESS: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_YUY2: + return 32; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + return 24; + + case DXGI_FORMAT_R8G8_TYPELESS: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + case DXGI_FORMAT_R16_TYPELESS: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_A8P8: + case DXGI_FORMAT_B4G4R4A4_UNORM: + return 16; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + case DXGI_FORMAT_NV11: + return 12; + + case DXGI_FORMAT_R8_TYPELESS: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + return 8; + + case DXGI_FORMAT_R1_UNORM: + return 1; + + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + return 4; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return 8; + + default: + return 0; + } + } + + + //-------------------------------------------------------------------------------------- + // Determines if the format is block compressed + //-------------------------------------------------------------------------------------- + bool IsCompressed( _In_ DXGI_FORMAT fmt ) + { + switch ( fmt ) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return true; + + default: + return false; + } + } + + + //-------------------------------------------------------------------------------------- + // Get surface information for a particular format + //-------------------------------------------------------------------------------------- + void GetSurfaceInfo( + _In_ size_t width, + _In_ size_t height, + _In_ DXGI_FORMAT fmt, + _Out_opt_ size_t* outNumBytes, + _Out_opt_ size_t* outRowBytes, + _Out_opt_ size_t* outNumRows ) + { + size_t numBytes = 0; + size_t rowBytes = 0; + size_t numRows = 0; + + bool bc = false; + bool packed = false; + bool planar = false; + size_t bpe = 0; + switch (fmt) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + bc=true; + bpe = 8; + break; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + bc = true; + bpe = 16; + break; + + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_YUY2: + packed = true; + bpe = 4; + break; + + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + packed = true; + bpe = 8; + break; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + planar = true; + bpe = 2; + break; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + planar = true; + bpe = 4; + break; + } + + if (bc) + { + size_t numBlocksWide = 0; + if (width > 0) + { + numBlocksWide = std::max( 1, (width + 3) / 4 ); + } + size_t numBlocksHigh = 0; + if (height > 0) + { + numBlocksHigh = std::max( 1, (height + 3) / 4 ); + } + rowBytes = numBlocksWide * bpe; + numRows = numBlocksHigh; + numBytes = rowBytes * numBlocksHigh; + } + else if (packed) + { + rowBytes = ( ( width + 1 ) >> 1 ) * bpe; + numRows = height; + numBytes = rowBytes * height; + } + else if ( fmt == DXGI_FORMAT_NV11 ) + { + rowBytes = ( ( width + 3 ) >> 2 ) * 4; + numRows = height * 2; // Direct3D makes this simplifying assumption, although it is larger than the 4:1:1 data + numBytes = rowBytes * numRows; + } + else if (planar) + { + rowBytes = ( ( width + 1 ) >> 1 ) * bpe; + numBytes = ( rowBytes * height ) + ( ( rowBytes * height + 1 ) >> 1 ); + numRows = height + ( ( height + 1 ) >> 1 ); + } + else + { + size_t bpp = BitsPerPixel( fmt ); + rowBytes = ( width * bpp + 7 ) / 8; // round up to nearest byte + numRows = height; + numBytes = rowBytes * height; + } + + if (outNumBytes) + { + *outNumBytes = numBytes; + } + if (outRowBytes) + { + *outRowBytes = rowBytes; + } + if (outNumRows) + { + *outNumRows = numRows; + } + } + + + //-------------------------------------------------------------------------------------- + DXGI_FORMAT EnsureNotTypeless( DXGI_FORMAT fmt ) + { + // Assumes UNORM or FLOAT; doesn't use UINT or SINT + switch( fmt ) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: return DXGI_FORMAT_R32G32B32A32_FLOAT; + case DXGI_FORMAT_R32G32B32_TYPELESS: return DXGI_FORMAT_R32G32B32_FLOAT; + case DXGI_FORMAT_R16G16B16A16_TYPELESS: return DXGI_FORMAT_R16G16B16A16_UNORM; + case DXGI_FORMAT_R32G32_TYPELESS: return DXGI_FORMAT_R32G32_FLOAT; + case DXGI_FORMAT_R10G10B10A2_TYPELESS: return DXGI_FORMAT_R10G10B10A2_UNORM; + case DXGI_FORMAT_R8G8B8A8_TYPELESS: return DXGI_FORMAT_R8G8B8A8_UNORM; + case DXGI_FORMAT_R16G16_TYPELESS: return DXGI_FORMAT_R16G16_UNORM; + case DXGI_FORMAT_R32_TYPELESS: return DXGI_FORMAT_R32_FLOAT; + case DXGI_FORMAT_R8G8_TYPELESS: return DXGI_FORMAT_R8G8_UNORM; + case DXGI_FORMAT_R16_TYPELESS: return DXGI_FORMAT_R16_UNORM; + case DXGI_FORMAT_R8_TYPELESS: return DXGI_FORMAT_R8_UNORM; + case DXGI_FORMAT_BC1_TYPELESS: return DXGI_FORMAT_BC1_UNORM; + case DXGI_FORMAT_BC2_TYPELESS: return DXGI_FORMAT_BC2_UNORM; + case DXGI_FORMAT_BC3_TYPELESS: return DXGI_FORMAT_BC3_UNORM; + case DXGI_FORMAT_BC4_TYPELESS: return DXGI_FORMAT_BC4_UNORM; + case DXGI_FORMAT_BC5_TYPELESS: return DXGI_FORMAT_BC5_UNORM; + case DXGI_FORMAT_B8G8R8A8_TYPELESS: return DXGI_FORMAT_B8G8R8A8_UNORM; + case DXGI_FORMAT_B8G8R8X8_TYPELESS: return DXGI_FORMAT_B8G8R8X8_UNORM; + case DXGI_FORMAT_BC7_TYPELESS: return DXGI_FORMAT_BC7_UNORM; + default: return fmt; + } + } + + + //-------------------------------------------------------------------------------------- + HRESULT CaptureTexture( + _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + D3D11_TEXTURE2D_DESC& desc, + ComPtr& pStaging ) + { + if ( !pContext || !pSource ) + return E_INVALIDARG; + + D3D11_RESOURCE_DIMENSION resType = D3D11_RESOURCE_DIMENSION_UNKNOWN; + pSource->GetType( &resType ); + + if ( resType != D3D11_RESOURCE_DIMENSION_TEXTURE2D ) + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + + ComPtr pTexture; + HRESULT hr = pSource->QueryInterface(IID_PPV_ARGS(pTexture.GetAddressOf())); + if ( FAILED(hr) ) + return hr; + + assert( pTexture ); + + pTexture->GetDesc( &desc ); + + ComPtr d3dDevice; + pContext->GetDevice( d3dDevice.GetAddressOf() ); + + if ( desc.SampleDesc.Count > 1 ) + { + // MSAA content must be resolved before being copied to a staging texture + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + + ComPtr pTemp; + hr = d3dDevice->CreateTexture2D( &desc, 0, pTemp.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + assert( pTemp ); + + DXGI_FORMAT fmt = EnsureNotTypeless( desc.Format ); + + UINT support = 0; + hr = d3dDevice->CheckFormatSupport( fmt, &support ); + if ( FAILED(hr) ) + return hr; + + if ( !(support & D3D11_FORMAT_SUPPORT_MULTISAMPLE_RESOLVE) ) + return E_FAIL; + + for( UINT item = 0; item < desc.ArraySize; ++item ) + { + for( UINT level = 0; level < desc.MipLevels; ++level ) + { + UINT index = D3D11CalcSubresource( level, item, desc.MipLevels ); + pContext->ResolveSubresource( pTemp.Get(), index, pSource, index, fmt ); + } + } + + desc.BindFlags = 0; + desc.MiscFlags &= D3D11_RESOURCE_MISC_TEXTURECUBE; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.Usage = D3D11_USAGE_STAGING; + + hr = d3dDevice->CreateTexture2D(&desc, 0, pStaging.ReleaseAndGetAddressOf()); + if ( FAILED(hr) ) + return hr; + + assert( pStaging ); + + pContext->CopyResource( pStaging.Get(), pTemp.Get() ); + } + else if ( (desc.Usage == D3D11_USAGE_STAGING) && (desc.CPUAccessFlags & D3D11_CPU_ACCESS_READ) ) + { + // Handle case where the source is already a staging texture we can use directly + pStaging = pTexture; + } + else + { + // Otherwise, create a staging texture from the non-MSAA source + desc.BindFlags = 0; + desc.MiscFlags &= D3D11_RESOURCE_MISC_TEXTURECUBE; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.Usage = D3D11_USAGE_STAGING; + + hr = d3dDevice->CreateTexture2D(&desc, 0, pStaging.ReleaseAndGetAddressOf()); + if ( FAILED(hr) ) + return hr; + + assert( pStaging ); + + pContext->CopyResource( pStaging.Get(), pSource ); + } + + return S_OK; + } + + //-------------------------------------------------------------------------------------- + bool g_WIC2 = false; + + IWICImagingFactory* _GetWIC() + { + static INIT_ONCE s_initOnce = INIT_ONCE_STATIC_INIT; + + IWICImagingFactory* factory = nullptr; + InitOnceExecuteOnce(&s_initOnce, + [](PINIT_ONCE, PVOID, LPVOID *factory) -> BOOL + { + #if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + HRESULT hr = CoCreateInstance( + CLSID_WICImagingFactory2, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory2), + factory + ); + + if ( SUCCEEDED(hr) ) + { + // WIC2 is available on Windows 10, Windows 8.x, and Windows 7 SP1 with KB 2670838 installed + g_WIC2 = true; + return TRUE; + } + else + { + hr = CoCreateInstance( + CLSID_WICImagingFactory1, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + factory + ); + return SUCCEEDED(hr) ? TRUE : FALSE; + } + #else + return SUCCEEDED( CoCreateInstance( + CLSID_WICImagingFactory, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + factory) ) ? TRUE : FALSE; + #endif + }, nullptr, reinterpret_cast(&factory)); + + return factory; + } +} // anonymous namespace + + +//-------------------------------------------------------------------------------------- +HRESULT DirectX::SaveDDSTextureToFile( _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + _In_z_ const wchar_t* fileName ) +{ + if ( !fileName ) + return E_INVALIDARG; + + D3D11_TEXTURE2D_DESC desc = {}; + ComPtr pStaging; + HRESULT hr = CaptureTexture( pContext, pSource, desc, pStaging ); + if ( FAILED(hr) ) + return hr; + + // Create file +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile( safe_handle( CreateFile2( fileName, GENERIC_WRITE | DELETE, 0, CREATE_ALWAYS, nullptr ) ) ); +#else + ScopedHandle hFile( safe_handle( CreateFileW( fileName, GENERIC_WRITE | DELETE, 0, nullptr, CREATE_ALWAYS, 0, nullptr ) ) ); +#endif + if ( !hFile ) + return HRESULT_FROM_WIN32( GetLastError() ); + + auto_delete_file delonfail(hFile.get()); + + // Setup header + const size_t MAX_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10); + uint8_t fileHeader[ MAX_HEADER_SIZE ]; + + *reinterpret_cast(&fileHeader[0]) = DDS_MAGIC; + + auto header = reinterpret_cast( &fileHeader[0] + sizeof(uint32_t) ); + size_t headerSize = sizeof(uint32_t) + sizeof(DDS_HEADER); + memset( header, 0, sizeof(DDS_HEADER) ); + header->size = sizeof( DDS_HEADER ); + header->flags = DDS_HEADER_FLAGS_TEXTURE | DDS_HEADER_FLAGS_MIPMAP; + header->height = desc.Height; + header->width = desc.Width; + header->mipMapCount = 1; + header->caps = DDS_SURFACE_FLAGS_TEXTURE; + + // Try to use a legacy .DDS pixel format for better tools support, otherwise fallback to 'DX10' header extension + DDS_HEADER_DXT10* extHeader = nullptr; + switch( desc.Format ) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8B8G8R8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R16G16_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_G16R16, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8L8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R16_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_L16, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_L8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_A8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8_B8G8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_R8G8_B8G8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_G8R8_G8B8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_G8R8_G8B8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC1_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DXT1, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC2_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DXT3, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC3_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DXT5, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC4_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC4_UNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC4_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC4_SNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC5_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC5_UNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC5_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC5_SNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_B5G6R5_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_R5G6B5, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_B5G5R5A1_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A1R5G5B5, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_V8U8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8B8A8_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_Q8W8V8U8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R16G16_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_V16U16, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_B8G8R8A8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8R8G8B8, sizeof(DDS_PIXELFORMAT) ); break; // DXGI 1.1 + case DXGI_FORMAT_B8G8R8X8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_X8R8G8B8, sizeof(DDS_PIXELFORMAT) ); break; // DXGI 1.1 + case DXGI_FORMAT_YUY2: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_YUY2, sizeof(DDS_PIXELFORMAT) ); break; // DXGI 1.2 + case DXGI_FORMAT_B4G4R4A4_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A4R4G4B4, sizeof(DDS_PIXELFORMAT) ); break; // DXGI 1.2 + + // Legacy D3DX formats using D3DFMT enum value as FourCC + case DXGI_FORMAT_R32G32B32A32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 116; break; // D3DFMT_A32B32G32R32F + case DXGI_FORMAT_R16G16B16A16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 113; break; // D3DFMT_A16B16G16R16F + case DXGI_FORMAT_R16G16B16A16_UNORM: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 36; break; // D3DFMT_A16B16G16R16 + case DXGI_FORMAT_R16G16B16A16_SNORM: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 110; break; // D3DFMT_Q16W16V16U16 + case DXGI_FORMAT_R32G32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 115; break; // D3DFMT_G32R32F + case DXGI_FORMAT_R16G16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 112; break; // D3DFMT_G16R16F + case DXGI_FORMAT_R32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 114; break; // D3DFMT_R32F + case DXGI_FORMAT_R16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 111; break; // D3DFMT_R16F + + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case DXGI_FORMAT_A8P8: + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + + default: + memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DX10, sizeof(DDS_PIXELFORMAT) ); + + headerSize += sizeof(DDS_HEADER_DXT10); + extHeader = reinterpret_cast( reinterpret_cast(&fileHeader[0]) + sizeof(uint32_t) + sizeof(DDS_HEADER) ); + memset( extHeader, 0, sizeof(DDS_HEADER_DXT10) ); + extHeader->dxgiFormat = desc.Format; + extHeader->resourceDimension = D3D11_RESOURCE_DIMENSION_TEXTURE2D; + extHeader->arraySize = 1; + break; + } + + size_t rowPitch, slicePitch, rowCount; + GetSurfaceInfo( desc.Width, desc.Height, desc.Format, &slicePitch, &rowPitch, &rowCount ); + + if ( IsCompressed( desc.Format ) ) + { + header->flags |= DDS_HEADER_FLAGS_LINEARSIZE; + header->pitchOrLinearSize = static_cast( slicePitch ); + } + else + { + header->flags |= DDS_HEADER_FLAGS_PITCH; + header->pitchOrLinearSize = static_cast( rowPitch ); + } + + // Setup pixels + std::unique_ptr pixels( new (std::nothrow) uint8_t[ slicePitch ] ); + if (!pixels) + return E_OUTOFMEMORY; + + D3D11_MAPPED_SUBRESOURCE mapped; + hr = pContext->Map( pStaging.Get(), 0, D3D11_MAP_READ, 0, &mapped ); + if ( FAILED(hr) ) + return hr; + + auto sptr = reinterpret_cast( mapped.pData ); + if ( !sptr ) + { + pContext->Unmap( pStaging.Get(), 0 ); + return E_POINTER; + } + + uint8_t* dptr = pixels.get(); + + size_t msize = std::min( rowPitch, mapped.RowPitch ); + for( size_t h = 0; h < rowCount; ++h ) + { + memcpy_s( dptr, rowPitch, sptr, msize ); + sptr += mapped.RowPitch; + dptr += rowPitch; + } + + pContext->Unmap( pStaging.Get(), 0 ); + + // Write header & pixels + DWORD bytesWritten; + if ( !WriteFile( hFile.get(), fileHeader, static_cast( headerSize ), &bytesWritten, nullptr ) ) + return HRESULT_FROM_WIN32( GetLastError() ); + + if ( bytesWritten != headerSize ) + return E_FAIL; + + if ( !WriteFile( hFile.get(), pixels.get(), static_cast( slicePitch ), &bytesWritten, nullptr ) ) + return HRESULT_FROM_WIN32( GetLastError() ); + + if ( bytesWritten != slicePitch ) + return E_FAIL; + + delonfail.clear(); + + return S_OK; +} + +//-------------------------------------------------------------------------------------- +HRESULT DirectX::SaveWICTextureToFile( _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + _In_ REFGUID guidContainerFormat, + _In_z_ const wchar_t* fileName, + _In_opt_ const GUID* targetFormat, + _In_opt_ std::function setCustomProps ) +{ + if ( !fileName ) + return E_INVALIDARG; + + D3D11_TEXTURE2D_DESC desc = {}; + ComPtr pStaging; + HRESULT hr = CaptureTexture( pContext, pSource, desc, pStaging ); + if ( FAILED(hr) ) + return hr; + + // Determine source format's WIC equivalent + WICPixelFormatGUID pfGuid; + bool sRGB = false; + switch ( desc.Format ) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: pfGuid = GUID_WICPixelFormat128bppRGBAFloat; break; + case DXGI_FORMAT_R16G16B16A16_FLOAT: pfGuid = GUID_WICPixelFormat64bppRGBAHalf; break; + case DXGI_FORMAT_R16G16B16A16_UNORM: pfGuid = GUID_WICPixelFormat64bppRGBA; break; + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: pfGuid = GUID_WICPixelFormat32bppRGBA1010102XR; break; // DXGI 1.1 + case DXGI_FORMAT_R10G10B10A2_UNORM: pfGuid = GUID_WICPixelFormat32bppRGBA1010102; break; + case DXGI_FORMAT_B5G5R5A1_UNORM: pfGuid = GUID_WICPixelFormat16bppBGRA5551; break; + case DXGI_FORMAT_B5G6R5_UNORM: pfGuid = GUID_WICPixelFormat16bppBGR565; break; + case DXGI_FORMAT_R32_FLOAT: pfGuid = GUID_WICPixelFormat32bppGrayFloat; break; + case DXGI_FORMAT_R16_FLOAT: pfGuid = GUID_WICPixelFormat16bppGrayHalf; break; + case DXGI_FORMAT_R16_UNORM: pfGuid = GUID_WICPixelFormat16bppGray; break; + case DXGI_FORMAT_R8_UNORM: pfGuid = GUID_WICPixelFormat8bppGray; break; + case DXGI_FORMAT_A8_UNORM: pfGuid = GUID_WICPixelFormat8bppAlpha; break; + + case DXGI_FORMAT_R8G8B8A8_UNORM: + pfGuid = GUID_WICPixelFormat32bppRGBA; + break; + + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + pfGuid = GUID_WICPixelFormat32bppRGBA; + sRGB = true; + break; + + case DXGI_FORMAT_B8G8R8A8_UNORM: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGRA; + break; + + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGRA; + sRGB = true; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGR; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGR; + sRGB = true; + break; + + default: + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + + auto pWIC = _GetWIC(); + if ( !pWIC ) + return E_NOINTERFACE; + + ComPtr stream; + hr = pWIC->CreateStream( stream.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + hr = stream->InitializeFromFilename( fileName, GENERIC_WRITE ); + if ( FAILED(hr) ) + return hr; + + auto_delete_file_wic delonfail(stream, fileName); + + ComPtr encoder; + hr = pWIC->CreateEncoder( guidContainerFormat, 0, encoder.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + hr = encoder->Initialize( stream.Get(), WICBitmapEncoderNoCache ); + if ( FAILED(hr) ) + return hr; + + ComPtr frame; + ComPtr props; + hr = encoder->CreateNewFrame( frame.GetAddressOf(), props.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + if ( targetFormat && memcmp( &guidContainerFormat, &GUID_ContainerFormatBmp, sizeof(WICPixelFormatGUID) ) == 0 && g_WIC2 ) + { + // Opt-in to the WIC2 support for writing 32-bit Windows BMP files with an alpha channel + PROPBAG2 option = {}; + option.pstrName = const_cast(L"EnableV5Header32bppBGRA"); + + VARIANT varValue; + varValue.vt = VT_BOOL; + varValue.boolVal = VARIANT_TRUE; + (void)props->Write( 1, &option, &varValue ); + } + + if ( setCustomProps ) + { + setCustomProps( props.Get() ); + } + + hr = frame->Initialize( props.Get() ); + if ( FAILED(hr) ) + return hr; + + hr = frame->SetSize( desc.Width , desc.Height ); + if ( FAILED(hr) ) + return hr; + + hr = frame->SetResolution( 72, 72 ); + if ( FAILED(hr) ) + return hr; + + // Pick a target format + WICPixelFormatGUID targetGuid; + if ( targetFormat ) + { + targetGuid = *targetFormat; + } + else + { + // Screenshots don’t typically include the alpha channel of the render target + switch ( desc.Format ) + { +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + if ( g_WIC2 ) + { + targetGuid = GUID_WICPixelFormat96bppRGBFloat; + } + else + { + targetGuid = GUID_WICPixelFormat24bppBGR; + } + break; +#endif + + case DXGI_FORMAT_R16G16B16A16_UNORM: targetGuid = GUID_WICPixelFormat48bppBGR; break; + case DXGI_FORMAT_B5G5R5A1_UNORM: targetGuid = GUID_WICPixelFormat16bppBGR555; break; + case DXGI_FORMAT_B5G6R5_UNORM: targetGuid = GUID_WICPixelFormat16bppBGR565; break; + + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_A8_UNORM: + targetGuid = GUID_WICPixelFormat8bppGray; + break; + + default: + targetGuid = GUID_WICPixelFormat24bppBGR; + break; + } + } + + hr = frame->SetPixelFormat( &targetGuid ); + if ( FAILED(hr) ) + return hr; + + if ( targetFormat && memcmp( targetFormat, &targetGuid, sizeof(WICPixelFormatGUID) ) != 0 ) + { + // Requested output pixel format is not supported by the WIC codec + return E_FAIL; + } + + // Encode WIC metadata + ComPtr metawriter; + if ( SUCCEEDED( frame->GetMetadataQueryWriter( metawriter.GetAddressOf() ) ) ) + { + PROPVARIANT value; + PropVariantInit( &value ); + + value.vt = VT_LPSTR; + value.pszVal = const_cast("DirectXTK"); + + if ( memcmp( &guidContainerFormat, &GUID_ContainerFormatPng, sizeof(GUID) ) == 0 ) + { + // Set Software name + (void)metawriter->SetMetadataByName( L"/tEXt/{str=Software}", &value ); + + // Set sRGB chunk + if ( sRGB ) + { + value.vt = VT_UI1; + value.bVal = 0; + (void)metawriter->SetMetadataByName( L"/sRGB/RenderingIntent", &value ); + } + } + else + { + // Set Software name + (void)metawriter->SetMetadataByName( L"System.ApplicationName", &value ); + + if ( sRGB ) + { + // Set EXIF Colorspace of sRGB + value.vt = VT_UI2; + value.uiVal = 1; + (void)metawriter->SetMetadataByName( L"System.Image.ColorSpace", &value ); + } + } + } + + D3D11_MAPPED_SUBRESOURCE mapped; + hr = pContext->Map( pStaging.Get(), 0, D3D11_MAP_READ, 0, &mapped ); + if ( FAILED(hr) ) + return hr; + + if ( memcmp( &targetGuid, &pfGuid, sizeof(WICPixelFormatGUID) ) != 0 ) + { + // Conversion required to write + ComPtr source; + hr = pWIC->CreateBitmapFromMemory( desc.Width, desc.Height, pfGuid, + mapped.RowPitch, mapped.RowPitch * desc.Height, + reinterpret_cast( mapped.pData ), source.GetAddressOf() ); + if ( FAILED(hr) ) + { + pContext->Unmap( pStaging.Get(), 0 ); + return hr; + } + + ComPtr FC; + hr = pWIC->CreateFormatConverter( FC.GetAddressOf() ); + if ( FAILED(hr) ) + { + pContext->Unmap( pStaging.Get(), 0 ); + return hr; + } + + BOOL canConvert = FALSE; + hr = FC->CanConvert( pfGuid, targetGuid, &canConvert ); + if ( FAILED(hr) || !canConvert ) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize( source.Get(), targetGuid, WICBitmapDitherTypeNone, nullptr, 0, WICBitmapPaletteTypeMedianCut ); + if ( FAILED(hr) ) + { + pContext->Unmap( pStaging.Get(), 0 ); + return hr; + } + + WICRect rect = { 0, 0, static_cast( desc.Width ), static_cast( desc.Height ) }; + hr = frame->WriteSource( FC.Get(), &rect ); + if ( FAILED(hr) ) + { + pContext->Unmap( pStaging.Get(), 0 ); + return hr; + } + } + else + { + // No conversion required + hr = frame->WritePixels( desc.Height, mapped.RowPitch, mapped.RowPitch * desc.Height, reinterpret_cast( mapped.pData ) ); + if ( FAILED(hr) ) + return hr; + } + + pContext->Unmap( pStaging.Get(), 0 ); + + hr = frame->Commit(); + if ( FAILED(hr) ) + return hr; + + hr = encoder->Commit(); + if ( FAILED(hr) ) + return hr; + + delonfail.clear(); + + return S_OK; +} diff --git a/deps/DirectXTex/ScreenGrab/ScreenGrab.h b/deps/DirectXTex/ScreenGrab/ScreenGrab.h new file mode 100644 index 0000000..f2e7025 --- /dev/null +++ b/deps/DirectXTex/ScreenGrab/ScreenGrab.h @@ -0,0 +1,43 @@ +//-------------------------------------------------------------------------------------- +// File: ScreenGrab.h +// +// Function for capturing a 2D texture and saving it to a file (aka a 'screenshot' +// when used on a Direct3D 11 Render Target). +// +// Note these functions are useful as a light-weight runtime screen grabber. For +// full-featured texture capture, DDS writer, and texture processing pipeline, +// see the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#pragma once + +#include + +#include +#include +#include + + +namespace DirectX +{ + HRESULT SaveDDSTextureToFile( _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + _In_z_ const wchar_t* fileName ); + + HRESULT SaveWICTextureToFile( _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + _In_ REFGUID guidContainerFormat, + _In_z_ const wchar_t* fileName, + _In_opt_ const GUID* targetFormat = nullptr, + _In_opt_ std::function setCustomProps = nullptr ); +} \ No newline at end of file diff --git a/deps/DirectXTex/ScreenGrab/ScreenGrab12.cpp b/deps/DirectXTex/ScreenGrab/ScreenGrab12.cpp new file mode 100644 index 0000000..5fe8ea7 --- /dev/null +++ b/deps/DirectXTex/ScreenGrab/ScreenGrab12.cpp @@ -0,0 +1,1298 @@ +//-------------------------------------------------------------------------------------- +// File: ScreenGrab12.cpp +// +// Function for capturing a 2D texture and saving it to a file (aka a 'screenshot' +// when used on a Direct3D 12 Render Target). +// +// Note these functions are useful as a light-weight runtime screen grabber. For +// full-featured texture capture, DDS writer, and texture processing pipeline, +// see the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkID=615561 +//-------------------------------------------------------------------------------------- + +// Does not capture 1D textures or 3D textures (volume maps) + +// Does not capture mipmap chains, only the top-most texture level is saved + +// For 2D array textures and cubemaps, it captures only the first image in the array + +#include "ScreenGrab12.h" + +#include +#include +#include + +#include + +#include + +#include + +using Microsoft::WRL::ComPtr; + +//-------------------------------------------------------------------------------------- +// Macros +//-------------------------------------------------------------------------------------- +#ifndef MAKEFOURCC +#define MAKEFOURCC(ch0, ch1, ch2, ch3) \ + ((uint32_t)(uint8_t)(ch0) | ((uint32_t)(uint8_t)(ch1) << 8) | \ + ((uint32_t)(uint8_t)(ch2) << 16) | ((uint32_t)(uint8_t)(ch3) << 24 )) +#endif /* defined(MAKEFOURCC) */ + +//-------------------------------------------------------------------------------------- +// DDS file structure definitions +// +// See DDS.h in the 'Texconv' sample and the 'DirectXTex' library +//-------------------------------------------------------------------------------------- +namespace +{ + #pragma pack(push,1) + + #define DDS_MAGIC 0x20534444 // "DDS " + + struct DDS_PIXELFORMAT + { + uint32_t size; + uint32_t flags; + uint32_t fourCC; + uint32_t RGBBitCount; + uint32_t RBitMask; + uint32_t GBitMask; + uint32_t BBitMask; + uint32_t ABitMask; + }; + + #define DDS_FOURCC 0x00000004 // DDPF_FOURCC + #define DDS_RGB 0x00000040 // DDPF_RGB + #define DDS_RGBA 0x00000041 // DDPF_RGB | DDPF_ALPHAPIXELS + #define DDS_LUMINANCE 0x00020000 // DDPF_LUMINANCE + #define DDS_LUMINANCEA 0x00020001 // DDPF_LUMINANCE | DDPF_ALPHAPIXELS + #define DDS_ALPHA 0x00000002 // DDPF_ALPHA + #define DDS_BUMPDUDV 0x00080000 // DDPF_BUMPDUDV + + #define DDS_HEADER_FLAGS_TEXTURE 0x00001007 // DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT + #define DDS_HEADER_FLAGS_MIPMAP 0x00020000 // DDSD_MIPMAPCOUNT + #define DDS_HEADER_FLAGS_PITCH 0x00000008 // DDSD_PITCH + #define DDS_HEADER_FLAGS_LINEARSIZE 0x00080000 // DDSD_LINEARSIZE + + #define DDS_HEIGHT 0x00000002 // DDSD_HEIGHT + #define DDS_WIDTH 0x00000004 // DDSD_WIDTH + + #define DDS_SURFACE_FLAGS_TEXTURE 0x00001000 // DDSCAPS_TEXTURE + + typedef struct + { + uint32_t size; + uint32_t flags; + uint32_t height; + uint32_t width; + uint32_t pitchOrLinearSize; + uint32_t depth; // only if DDS_HEADER_FLAGS_VOLUME is set in flags + uint32_t mipMapCount; + uint32_t reserved1[11]; + DDS_PIXELFORMAT ddspf; + uint32_t caps; + uint32_t caps2; + uint32_t caps3; + uint32_t caps4; + uint32_t reserved2; + } DDS_HEADER; + + typedef struct + { + DXGI_FORMAT dxgiFormat; + uint32_t resourceDimension; + uint32_t miscFlag; // see D3D11_RESOURCE_MISC_FLAG + uint32_t arraySize; + uint32_t reserved; + } DDS_HEADER_DXT10; + + #pragma pack(pop) + + const DDS_PIXELFORMAT DDSPF_DXT1 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','1'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_DXT3 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','3'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_DXT5 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','5'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC4_UNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','4','U'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC4_SNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','4','S'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC5_UNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','5','U'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC5_SNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','5','S'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_R8G8_B8G8 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('R','G','B','G'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_G8R8_G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('G','R','G','B'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_YUY2 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('Y','U','Y','2'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_A8R8G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x00ff0000, 0x0000ff00, 0x000000ff, 0xff000000 }; + + const DDS_PIXELFORMAT DDSPF_X8R8G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00000000 }; + + const DDS_PIXELFORMAT DDSPF_A8B8G8R8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; + + const DDS_PIXELFORMAT DDSPF_G16R16 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0x0000ffff, 0xffff0000, 0x00000000, 0x00000000 }; + + const DDS_PIXELFORMAT DDSPF_R5G6B5 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 16, 0x0000f800, 0x000007e0, 0x0000001f, 0x00000000 }; + + const DDS_PIXELFORMAT DDSPF_A1R5G5B5 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x00007c00, 0x000003e0, 0x0000001f, 0x00008000 }; + + const DDS_PIXELFORMAT DDSPF_A4R4G4B4 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x00000f00, 0x000000f0, 0x0000000f, 0x0000f000 }; + + const DDS_PIXELFORMAT DDSPF_L8 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCE, 0, 8, 0xff, 0x00, 0x00, 0x00 }; + + const DDS_PIXELFORMAT DDSPF_L16 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCE, 0, 16, 0xffff, 0x0000, 0x0000, 0x0000 }; + + const DDS_PIXELFORMAT DDSPF_A8L8 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCEA, 0, 16, 0x00ff, 0x0000, 0x0000, 0xff00 }; + + const DDS_PIXELFORMAT DDSPF_A8 = + { sizeof(DDS_PIXELFORMAT), DDS_ALPHA, 0, 8, 0x00, 0x00, 0x00, 0xff }; + + const DDS_PIXELFORMAT DDSPF_V8U8 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 16, 0x00ff, 0xff00, 0x0000, 0x0000 }; + + const DDS_PIXELFORMAT DDSPF_Q8W8V8U8 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 32, 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; + + const DDS_PIXELFORMAT DDSPF_V16U16 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 32, 0x0000ffff, 0xffff0000, 0x00000000, 0x00000000 }; + + // DXGI_FORMAT_R10G10B10A2_UNORM should be written using DX10 extension to avoid D3DX 10:10:10:2 reversal issue + + // This indicates the DDS_HEADER_DXT10 extension is present (the format is in dxgiFormat) + const DDS_PIXELFORMAT DDSPF_DX10 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','1','0'), 0, 0, 0, 0, 0 }; + + //----------------------------------------------------------------------------- + struct handle_closer { void operator()(HANDLE h) { if (h) CloseHandle(h); } }; + + typedef public std::unique_ptr ScopedHandle; + + inline HANDLE safe_handle( HANDLE h ) { return (h == INVALID_HANDLE_VALUE) ? 0 : h; } + + class auto_delete_file + { + public: + auto_delete_file(HANDLE hFile) : m_handle(hFile) {} + ~auto_delete_file() + { + if (m_handle) + { + FILE_DISPOSITION_INFO info = {0}; + info.DeleteFile = TRUE; + (void)SetFileInformationByHandle(m_handle, FileDispositionInfo, &info, sizeof(info)); + } + } + + void clear() { m_handle = 0; } + + private: + HANDLE m_handle; + + auto_delete_file(const auto_delete_file&) = delete; + auto_delete_file& operator=(const auto_delete_file&) = delete; + }; + + class auto_delete_file_wic + { + public: + auto_delete_file_wic(ComPtr& hFile, LPCWSTR szFile) : m_handle(hFile), m_filename(szFile) {} + ~auto_delete_file_wic() + { + if (m_filename) + { + m_handle.Reset(); + DeleteFileW(m_filename); + } + } + + void clear() { m_filename = 0; } + + private: + LPCWSTR m_filename; + ComPtr& m_handle; + + auto_delete_file_wic(const auto_delete_file_wic&) = delete; + auto_delete_file_wic& operator=(const auto_delete_file_wic&) = delete; + }; + + //-------------------------------------------------------------------------------------- + // Return the BPP for a particular format + //-------------------------------------------------------------------------------------- + size_t BitsPerPixel( _In_ DXGI_FORMAT fmt ) + { + switch( fmt ) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + return 128; + + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return 96; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_R32G32_TYPELESS: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + return 64; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R11G11B10_FLOAT: + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_R16G16_TYPELESS: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + case DXGI_FORMAT_R32_TYPELESS: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_YUY2: + return 32; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + return 24; + + case DXGI_FORMAT_R8G8_TYPELESS: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + case DXGI_FORMAT_R16_TYPELESS: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_A8P8: + case DXGI_FORMAT_B4G4R4A4_UNORM: + return 16; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + case DXGI_FORMAT_NV11: + return 12; + + case DXGI_FORMAT_R8_TYPELESS: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + return 8; + + case DXGI_FORMAT_R1_UNORM: + return 1; + + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + return 4; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return 8; + + default: + return 0; + } + } + + + //-------------------------------------------------------------------------------------- + // Determines if the format is block compressed + //-------------------------------------------------------------------------------------- + bool IsCompressed( _In_ DXGI_FORMAT fmt ) + { + switch ( fmt ) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return true; + + default: + return false; + } + } + + + //-------------------------------------------------------------------------------------- + // Get surface information for a particular format + //-------------------------------------------------------------------------------------- + void GetSurfaceInfo( + _In_ size_t width, + _In_ size_t height, + _In_ DXGI_FORMAT fmt, + _Out_opt_ size_t* outNumBytes, + _Out_opt_ size_t* outRowBytes, + _Out_opt_ size_t* outNumRows ) + { + size_t numBytes = 0; + size_t rowBytes = 0; + size_t numRows = 0; + + bool bc = false; + bool packed = false; + bool planar = false; + size_t bpe = 0; + switch (fmt) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + bc=true; + bpe = 8; + break; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + bc = true; + bpe = 16; + break; + + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_YUY2: + packed = true; + bpe = 4; + break; + + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + packed = true; + bpe = 8; + break; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + planar = true; + bpe = 2; + break; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + planar = true; + bpe = 4; + break; + } + + if (bc) + { + size_t numBlocksWide = 0; + if (width > 0) + { + numBlocksWide = std::max( 1, (width + 3) / 4 ); + } + size_t numBlocksHigh = 0; + if (height > 0) + { + numBlocksHigh = std::max( 1, (height + 3) / 4 ); + } + rowBytes = numBlocksWide * bpe; + numRows = numBlocksHigh; + numBytes = rowBytes * numBlocksHigh; + } + else if (packed) + { + rowBytes = ( ( width + 1 ) >> 1 ) * bpe; + numRows = height; + numBytes = rowBytes * height; + } + else if ( fmt == DXGI_FORMAT_NV11 ) + { + rowBytes = ( ( width + 3 ) >> 2 ) * 4; + numRows = height * 2; // Direct3D makes this simplifying assumption, although it is larger than the 4:1:1 data + numBytes = rowBytes * numRows; + } + else if (planar) + { + rowBytes = ( ( width + 1 ) >> 1 ) * bpe; + numBytes = ( rowBytes * height ) + ( ( rowBytes * height + 1 ) >> 1 ); + numRows = height + ( ( height + 1 ) >> 1 ); + } + else + { + size_t bpp = BitsPerPixel( fmt ); + rowBytes = ( width * bpp + 7 ) / 8; // round up to nearest byte + numRows = height; + numBytes = rowBytes * height; + } + + if (outNumBytes) + { + *outNumBytes = numBytes; + } + if (outRowBytes) + { + *outRowBytes = rowBytes; + } + if (outNumRows) + { + *outNumRows = numRows; + } + } + + + //-------------------------------------------------------------------------------------- + DXGI_FORMAT EnsureNotTypeless( DXGI_FORMAT fmt ) + { + // Assumes UNORM or FLOAT; doesn't use UINT or SINT + switch( fmt ) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: return DXGI_FORMAT_R32G32B32A32_FLOAT; + case DXGI_FORMAT_R32G32B32_TYPELESS: return DXGI_FORMAT_R32G32B32_FLOAT; + case DXGI_FORMAT_R16G16B16A16_TYPELESS: return DXGI_FORMAT_R16G16B16A16_UNORM; + case DXGI_FORMAT_R32G32_TYPELESS: return DXGI_FORMAT_R32G32_FLOAT; + case DXGI_FORMAT_R10G10B10A2_TYPELESS: return DXGI_FORMAT_R10G10B10A2_UNORM; + case DXGI_FORMAT_R8G8B8A8_TYPELESS: return DXGI_FORMAT_R8G8B8A8_UNORM; + case DXGI_FORMAT_R16G16_TYPELESS: return DXGI_FORMAT_R16G16_UNORM; + case DXGI_FORMAT_R32_TYPELESS: return DXGI_FORMAT_R32_FLOAT; + case DXGI_FORMAT_R8G8_TYPELESS: return DXGI_FORMAT_R8G8_UNORM; + case DXGI_FORMAT_R16_TYPELESS: return DXGI_FORMAT_R16_UNORM; + case DXGI_FORMAT_R8_TYPELESS: return DXGI_FORMAT_R8_UNORM; + case DXGI_FORMAT_BC1_TYPELESS: return DXGI_FORMAT_BC1_UNORM; + case DXGI_FORMAT_BC2_TYPELESS: return DXGI_FORMAT_BC2_UNORM; + case DXGI_FORMAT_BC3_TYPELESS: return DXGI_FORMAT_BC3_UNORM; + case DXGI_FORMAT_BC4_TYPELESS: return DXGI_FORMAT_BC4_UNORM; + case DXGI_FORMAT_BC5_TYPELESS: return DXGI_FORMAT_BC5_UNORM; + case DXGI_FORMAT_B8G8R8A8_TYPELESS: return DXGI_FORMAT_B8G8R8A8_UNORM; + case DXGI_FORMAT_B8G8R8X8_TYPELESS: return DXGI_FORMAT_B8G8R8X8_UNORM; + case DXGI_FORMAT_BC7_TYPELESS: return DXGI_FORMAT_BC7_UNORM; + default: return fmt; + } + } + + + //-------------------------------------------------------------------------------------- + inline void TransitionResource( + _In_ ID3D12GraphicsCommandList* commandList, + _In_ ID3D12Resource* resource, + _In_ D3D12_RESOURCE_STATES stateBefore, + _In_ D3D12_RESOURCE_STATES stateAfter) + { + assert(commandList != 0); + assert(resource != 0); + + if (stateBefore == stateAfter) + return; + + D3D12_RESOURCE_BARRIER desc = {}; + desc.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; + desc.Transition.pResource = resource; + desc.Transition.Subresource = D3D12_RESOURCE_BARRIER_ALL_SUBRESOURCES; + desc.Transition.StateBefore = stateBefore; + desc.Transition.StateAfter = stateAfter; + + commandList->ResourceBarrier(1, &desc); + } + + + //-------------------------------------------------------------------------------------- + HRESULT CaptureTexture(_In_ ID3D12Device* device, + _In_ ID3D12CommandQueue* pCommandQ, + _In_ ID3D12Resource* pSource, + UINT64 srcPitch, + const D3D12_RESOURCE_DESC& desc, + ComPtr& pStaging, + D3D12_RESOURCE_STATES beforeState, + D3D12_RESOURCE_STATES afterState) + { + if (!pCommandQ || !pSource) + return E_INVALIDARG; + + if (desc.Dimension != D3D12_RESOURCE_DIMENSION_TEXTURE2D) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + UINT numberOfPlanes = D3D12GetFormatPlaneCount(device, desc.Format); + if (numberOfPlanes != 1) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + D3D12_HEAP_PROPERTIES sourceHeapProperties; + D3D12_HEAP_FLAGS sourceHeapFlags; + HRESULT hr = pSource->GetHeapProperties(&sourceHeapProperties, &sourceHeapFlags); + if (FAILED(hr)) + return hr; + + if (sourceHeapProperties.Type == D3D12_HEAP_TYPE_READBACK) + { + // Handle case where the source is already a staging texture we can use directly + pStaging = pSource; + return S_OK; + } + + // Create a command allocator + ComPtr commandAlloc; + hr = device->CreateCommandAllocator(D3D12_COMMAND_LIST_TYPE_DIRECT, IID_PPV_ARGS(commandAlloc.GetAddressOf())); + if (FAILED(hr)) + return hr; + + // Spin up a new command list + ComPtr commandList; + hr = device->CreateCommandList(0, D3D12_COMMAND_LIST_TYPE_DIRECT, commandAlloc.Get(), nullptr, IID_PPV_ARGS(commandList.GetAddressOf())); + if (FAILED(hr)) + return hr; + + // Create a fence + ComPtr fence; + hr = device->CreateFence(0, D3D12_FENCE_FLAG_NONE, IID_PPV_ARGS(fence.GetAddressOf())); + if (FAILED(hr)) + return hr; + + assert((srcPitch & 0xFF) == 0); + + CD3DX12_HEAP_PROPERTIES defaultHeapProperties(D3D12_HEAP_TYPE_DEFAULT); + CD3DX12_HEAP_PROPERTIES readBackHeapProperties(D3D12_HEAP_TYPE_READBACK); + + // Readback resources must be buffers + D3D12_RESOURCE_DESC bufferDesc = {}; + bufferDesc.Alignment = desc.Alignment; + bufferDesc.DepthOrArraySize = 1; + bufferDesc.Dimension = D3D12_RESOURCE_DIMENSION_BUFFER; + bufferDesc.Flags = D3D12_RESOURCE_FLAG_NONE; + bufferDesc.Format = DXGI_FORMAT_UNKNOWN; + bufferDesc.Height = 1; + bufferDesc.Width = srcPitch * desc.Height; + bufferDesc.Layout = D3D12_TEXTURE_LAYOUT_ROW_MAJOR; + bufferDesc.MipLevels = 1; + bufferDesc.SampleDesc.Count = 1; + bufferDesc.SampleDesc.Quality = 0; + + ComPtr copySource(pSource); + if (desc.SampleDesc.Count > 1) + { + // MSAA content must be resolved before being copied to a staging texture + auto descCopy = desc; + descCopy.SampleDesc.Count = 1; + descCopy.SampleDesc.Quality = 0; + + ComPtr pTemp; + hr = device->CreateCommittedResource( + &defaultHeapProperties, + D3D12_HEAP_FLAG_NONE, + &descCopy, + D3D12_RESOURCE_STATE_COPY_DEST, + nullptr, + IID_PPV_ARGS(pTemp.GetAddressOf())); + if (FAILED(hr)) + return hr; + + assert(pTemp); + + DXGI_FORMAT fmt = EnsureNotTypeless(desc.Format); + + D3D12_FEATURE_DATA_FORMAT_SUPPORT formatInfo = { fmt }; + hr = device->CheckFeatureSupport(D3D12_FEATURE_FORMAT_SUPPORT, &formatInfo, sizeof(formatInfo)); + if (FAILED(hr)) + return hr; + + if (!(formatInfo.Support1 & D3D12_FORMAT_SUPPORT1_TEXTURE2D)) + return E_FAIL; + + for (UINT item = 0; item < desc.DepthOrArraySize; ++item) + { + for (UINT level = 0; level < desc.MipLevels; ++level) + { + UINT index = D3D12CalcSubresource(level, item, 0, desc.MipLevels, desc.DepthOrArraySize); + commandList->ResolveSubresource(pTemp.Get(), index, pSource, index, fmt); + } + } + + copySource = pTemp; + } + + // Create a staging texture + hr = device->CreateCommittedResource( + &readBackHeapProperties, + D3D12_HEAP_FLAG_NONE, + &bufferDesc, + D3D12_RESOURCE_STATE_COPY_DEST, + nullptr, + IID_PPV_ARGS(pStaging.ReleaseAndGetAddressOf())); + if (FAILED(hr)) + return hr; + + assert(pStaging); + + // Transition the resource if necessary + TransitionResource(commandList.Get(), pSource, beforeState, D3D12_RESOURCE_STATE_COPY_SOURCE); + + // Get the copy target location + D3D12_PLACED_SUBRESOURCE_FOOTPRINT bufferFootprint = {}; + bufferFootprint.Footprint.Width = static_cast(desc.Width); + bufferFootprint.Footprint.Height = desc.Height; + bufferFootprint.Footprint.Depth = 1; + bufferFootprint.Footprint.RowPitch = static_cast(srcPitch); + bufferFootprint.Footprint.Format = desc.Format; + + CD3DX12_TEXTURE_COPY_LOCATION copyDest(pStaging.Get(), bufferFootprint); + CD3DX12_TEXTURE_COPY_LOCATION copySrc(copySource.Get(), 0); + + // Copy the texture + commandList->CopyTextureRegion(©Dest, 0, 0, 0, ©Src, nullptr); + + // Transition the resource to the next state + TransitionResource(commandList.Get(), pSource, D3D12_RESOURCE_STATE_COPY_SOURCE, afterState); + + hr = commandList->Close(); + if (FAILED(hr)) + return hr; + + // Execute the command list + pCommandQ->ExecuteCommandLists(1, (ID3D12CommandList**)commandList.GetAddressOf()); + + // Signal the fence + hr = pCommandQ->Signal(fence.Get(), 1); + if (FAILED(hr)) + return hr; + + // Block until the copy is complete + while (fence->GetCompletedValue() < 1) + SwitchToThread(); + + return S_OK; + } + + IWICImagingFactory2* _GetWIC() + { + static INIT_ONCE s_initOnce = INIT_ONCE_STATIC_INIT; + + IWICImagingFactory2* factory = nullptr; + (void)InitOnceExecuteOnce(&s_initOnce, + [](PINIT_ONCE, PVOID, PVOID *factory) -> BOOL + { + return SUCCEEDED( CoCreateInstance( + CLSID_WICImagingFactory2, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory2), + factory) ) ? TRUE : FALSE; + }, nullptr, reinterpret_cast(&factory)); + + return factory; + } +} // anonymous namespace + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveDDSTextureToFile( ID3D12CommandQueue* pCommandQ, + ID3D12Resource* pSource, + const wchar_t* fileName, + D3D12_RESOURCE_STATES beforeState, + D3D12_RESOURCE_STATES afterState) +{ + if ( !fileName ) + return E_INVALIDARG; + + ComPtr device; + pCommandQ->GetDevice(IID_PPV_ARGS(device.GetAddressOf())); + + // Get the size of the image + D3D12_RESOURCE_DESC desc = pSource->GetDesc(); + UINT64 totalResourceSize = 0; + UINT64 fpRowPitch = 0; + UINT fpRowCount = 0; + // Get the rowcount, pitch and size of the top mip + device->GetCopyableFootprints( + &desc, + 0, + 1, + 0, + nullptr, + &fpRowCount, + &fpRowPitch, + &totalResourceSize); + + // Round up the srcPitch to multiples of 256 + UINT64 dstRowPitch = (fpRowPitch + 255) & ~0xFF; + + ComPtr pStaging; + HRESULT hr = CaptureTexture( device.Get(), pCommandQ, pSource, dstRowPitch, desc, pStaging, beforeState, afterState ); + if ( FAILED(hr) ) + return hr; + + // Create file + ScopedHandle hFile( safe_handle( CreateFile2( fileName, GENERIC_WRITE, 0, CREATE_ALWAYS, nullptr ) ) ); + if ( !hFile ) + return HRESULT_FROM_WIN32( GetLastError() ); + + auto_delete_file delonfail(hFile.get()); + + // Setup header + const size_t MAX_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10); + uint8_t fileHeader[ MAX_HEADER_SIZE ]; + + *reinterpret_cast(&fileHeader[0]) = DDS_MAGIC; + + auto header = reinterpret_cast( &fileHeader[0] + sizeof(uint32_t) ); + size_t headerSize = sizeof(uint32_t) + sizeof(DDS_HEADER); + memset( header, 0, sizeof(DDS_HEADER) ); + header->size = sizeof( DDS_HEADER ); + header->flags = DDS_HEADER_FLAGS_TEXTURE | DDS_HEADER_FLAGS_MIPMAP; + header->height = desc.Height; + header->width = (uint32_t) desc.Width; + header->mipMapCount = 1; + header->caps = DDS_SURFACE_FLAGS_TEXTURE; + + // Try to use a legacy .DDS pixel format for better tools support, otherwise fallback to 'DX10' header extension + DDS_HEADER_DXT10* extHeader = nullptr; + switch( desc.Format ) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8B8G8R8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R16G16_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_G16R16, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8L8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R16_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_L16, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_L8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_A8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8_B8G8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_R8G8_B8G8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_G8R8_G8B8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_G8R8_G8B8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC1_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DXT1, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC2_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DXT3, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC3_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DXT5, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC4_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC4_UNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC4_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC4_SNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC5_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC5_UNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC5_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC5_SNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_B5G6R5_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_R5G6B5, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_B5G5R5A1_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A1R5G5B5, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_V8U8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8B8A8_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_Q8W8V8U8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R16G16_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_V16U16, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_B8G8R8A8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8R8G8B8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_B8G8R8X8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_X8R8G8B8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_YUY2: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_YUY2, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_B4G4R4A4_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A4R4G4B4, sizeof(DDS_PIXELFORMAT) ); break; + + // Legacy D3DX formats using D3DFMT enum value as FourCC + case DXGI_FORMAT_R32G32B32A32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 116; break; // D3DFMT_A32B32G32R32F + case DXGI_FORMAT_R16G16B16A16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 113; break; // D3DFMT_A16B16G16R16F + case DXGI_FORMAT_R16G16B16A16_UNORM: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 36; break; // D3DFMT_A16B16G16R16 + case DXGI_FORMAT_R16G16B16A16_SNORM: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 110; break; // D3DFMT_Q16W16V16U16 + case DXGI_FORMAT_R32G32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 115; break; // D3DFMT_G32R32F + case DXGI_FORMAT_R16G16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 112; break; // D3DFMT_G16R16F + case DXGI_FORMAT_R32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 114; break; // D3DFMT_R32F + case DXGI_FORMAT_R16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 111; break; // D3DFMT_R16F + + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case DXGI_FORMAT_A8P8: + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + + default: + memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DX10, sizeof(DDS_PIXELFORMAT) ); + + headerSize += sizeof(DDS_HEADER_DXT10); + extHeader = reinterpret_cast( reinterpret_cast(&fileHeader[0]) + sizeof(uint32_t) + sizeof(DDS_HEADER) ); + memset( extHeader, 0, sizeof(DDS_HEADER_DXT10) ); + extHeader->dxgiFormat = desc.Format; + extHeader->resourceDimension = D3D12_RESOURCE_DIMENSION_TEXTURE2D; + extHeader->arraySize = 1; + break; + } + + size_t rowPitch, slicePitch, rowCount; + GetSurfaceInfo( (size_t)desc.Width, desc.Height, desc.Format, &slicePitch, &rowPitch, &rowCount ); + + if ( IsCompressed( desc.Format ) ) + { + header->flags |= DDS_HEADER_FLAGS_LINEARSIZE; + header->pitchOrLinearSize = static_cast( slicePitch ); + } + else + { + header->flags |= DDS_HEADER_FLAGS_PITCH; + header->pitchOrLinearSize = static_cast( rowPitch ); + } + + // Setup pixels + std::unique_ptr pixels( new (std::nothrow) uint8_t[ slicePitch ] ); + if (!pixels) + return E_OUTOFMEMORY; + + assert(fpRowCount == rowCount); + assert(fpRowPitch == rowPitch); + + void* pMappedMemory; + D3D12_RANGE readRange = { 0, static_cast(dstRowPitch * rowCount) }; + D3D12_RANGE writeRange = { 0, 0 }; + hr = pStaging->Map(0, &readRange, &pMappedMemory ); + if ( FAILED(hr) ) + return hr; + + auto sptr = reinterpret_cast(pMappedMemory); + if ( !sptr ) + { + pStaging->Unmap(0, &writeRange); + return E_POINTER; + } + + uint8_t* dptr = pixels.get(); + + size_t msize = std::min( rowPitch, rowPitch ); + for( size_t h = 0; h < rowCount; ++h ) + { + memcpy_s( dptr, rowPitch, sptr, msize ); + sptr += dstRowPitch; + dptr += rowPitch; + } + + pStaging->Unmap( 0, &writeRange ); + + // Write header & pixels + DWORD bytesWritten; + if ( !WriteFile( hFile.get(), fileHeader, static_cast( headerSize ), &bytesWritten, nullptr ) ) + return HRESULT_FROM_WIN32( GetLastError() ); + + if ( bytesWritten != headerSize ) + return E_FAIL; + + if ( !WriteFile( hFile.get(), pixels.get(), static_cast( slicePitch ), &bytesWritten, nullptr ) ) + return HRESULT_FROM_WIN32( GetLastError() ); + + if ( bytesWritten != slicePitch ) + return E_FAIL; + + delonfail.clear(); + + return S_OK; +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveWICTextureToFile( ID3D12CommandQueue* pCommandQ, + ID3D12Resource* pSource, + REFGUID guidContainerFormat, + const wchar_t* fileName, + D3D12_RESOURCE_STATES beforeState, + D3D12_RESOURCE_STATES afterState, + const GUID* targetFormat, + std::function setCustomProps ) +{ + if ( !fileName ) + return E_INVALIDARG; + + ComPtr device; + pCommandQ->GetDevice(IID_PPV_ARGS(device.GetAddressOf())); + + // Get the size of the image + D3D12_RESOURCE_DESC desc = pSource->GetDesc(); + UINT64 totalResourceSize = 0; + UINT64 fpRowPitch = 0; + UINT fpRowCount = 0; + // Get the rowcount, pitch and size of the top mip + device->GetCopyableFootprints( + &desc, + 0, + 1, + 0, + nullptr, + &fpRowCount, + &fpRowPitch, + &totalResourceSize); + + // Round up the srcPitch to multiples of 256 + UINT64 dstRowPitch = (fpRowPitch + 255) & ~0xFF; + + ComPtr pStaging; + HRESULT hr = CaptureTexture(device.Get(), pCommandQ, pSource, dstRowPitch, desc, pStaging, beforeState, afterState); + if (FAILED(hr)) + return hr; + + // Determine source format's WIC equivalent + WICPixelFormatGUID pfGuid; + bool sRGB = false; + switch ( desc.Format ) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: pfGuid = GUID_WICPixelFormat128bppRGBAFloat; break; + case DXGI_FORMAT_R16G16B16A16_FLOAT: pfGuid = GUID_WICPixelFormat64bppRGBAHalf; break; + case DXGI_FORMAT_R16G16B16A16_UNORM: pfGuid = GUID_WICPixelFormat64bppRGBA; break; + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: pfGuid = GUID_WICPixelFormat32bppRGBA1010102XR; break; + case DXGI_FORMAT_R10G10B10A2_UNORM: pfGuid = GUID_WICPixelFormat32bppRGBA1010102; break; + case DXGI_FORMAT_B5G5R5A1_UNORM: pfGuid = GUID_WICPixelFormat16bppBGRA5551; break; + case DXGI_FORMAT_B5G6R5_UNORM: pfGuid = GUID_WICPixelFormat16bppBGR565; break; + case DXGI_FORMAT_R32_FLOAT: pfGuid = GUID_WICPixelFormat32bppGrayFloat; break; + case DXGI_FORMAT_R16_FLOAT: pfGuid = GUID_WICPixelFormat16bppGrayHalf; break; + case DXGI_FORMAT_R16_UNORM: pfGuid = GUID_WICPixelFormat16bppGray; break; + case DXGI_FORMAT_R8_UNORM: pfGuid = GUID_WICPixelFormat8bppGray; break; + case DXGI_FORMAT_A8_UNORM: pfGuid = GUID_WICPixelFormat8bppAlpha; break; + + case DXGI_FORMAT_R8G8B8A8_UNORM: + pfGuid = GUID_WICPixelFormat32bppRGBA; + break; + + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + pfGuid = GUID_WICPixelFormat32bppRGBA; + sRGB = true; + break; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + pfGuid = GUID_WICPixelFormat32bppBGRA; + break; + + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + pfGuid = GUID_WICPixelFormat32bppBGRA; + sRGB = true; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + pfGuid = GUID_WICPixelFormat32bppBGR; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + pfGuid = GUID_WICPixelFormat32bppBGR; + sRGB = true; + break; + + default: + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + + auto pWIC = _GetWIC(); + if ( !pWIC ) + return E_NOINTERFACE; + + ComPtr stream; + hr = pWIC->CreateStream( stream.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + hr = stream->InitializeFromFilename( fileName, GENERIC_WRITE ); + if ( FAILED(hr) ) + return hr; + + auto_delete_file_wic delonfail(stream, fileName); + + ComPtr encoder; + hr = pWIC->CreateEncoder( guidContainerFormat, 0, encoder.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + hr = encoder->Initialize( stream.Get(), WICBitmapEncoderNoCache ); + if ( FAILED(hr) ) + return hr; + + ComPtr frame; + ComPtr props; + hr = encoder->CreateNewFrame( frame.GetAddressOf(), props.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + if ( targetFormat && memcmp( &guidContainerFormat, &GUID_ContainerFormatBmp, sizeof(WICPixelFormatGUID) ) == 0 ) + { + // Opt-in to the WIC2 support for writing 32-bit Windows BMP files with an alpha channel + PROPBAG2 option = {}; + option.pstrName = const_cast(L"EnableV5Header32bppBGRA"); + + VARIANT varValue; + varValue.vt = VT_BOOL; + varValue.boolVal = VARIANT_TRUE; + (void)props->Write( 1, &option, &varValue ); + } + + if ( setCustomProps ) + { + setCustomProps( props.Get() ); + } + + hr = frame->Initialize( props.Get() ); + if ( FAILED(hr) ) + return hr; + + hr = frame->SetSize(static_cast(desc.Width), desc.Height ); + if ( FAILED(hr) ) + return hr; + + hr = frame->SetResolution( 72, 72 ); + if ( FAILED(hr) ) + return hr; + + // Pick a target format + WICPixelFormatGUID targetGuid; + if ( targetFormat ) + { + targetGuid = *targetFormat; + } + else + { + // Screenshots don’t typically include the alpha channel of the render target + switch ( desc.Format ) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + targetGuid = GUID_WICPixelFormat96bppRGBFloat; // WIC 2 + break; + + case DXGI_FORMAT_R16G16B16A16_UNORM: targetGuid = GUID_WICPixelFormat48bppBGR; break; + case DXGI_FORMAT_B5G5R5A1_UNORM: targetGuid = GUID_WICPixelFormat16bppBGR555; break; + case DXGI_FORMAT_B5G6R5_UNORM: targetGuid = GUID_WICPixelFormat16bppBGR565; break; + + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_A8_UNORM: + targetGuid = GUID_WICPixelFormat8bppGray; + break; + + default: + targetGuid = GUID_WICPixelFormat24bppBGR; + break; + } + } + + hr = frame->SetPixelFormat( &targetGuid ); + if ( FAILED(hr) ) + return hr; + + if ( targetFormat && memcmp( targetFormat, &targetGuid, sizeof(WICPixelFormatGUID) ) != 0 ) + { + // Requested output pixel format is not supported by the WIC codec + return E_FAIL; + } + + // Encode WIC metadata + ComPtr metawriter; + if ( SUCCEEDED( frame->GetMetadataQueryWriter( metawriter.GetAddressOf() ) ) ) + { + PROPVARIANT value; + PropVariantInit( &value ); + + value.vt = VT_LPSTR; + value.pszVal = const_cast("DirectXTK"); + + if ( memcmp( &guidContainerFormat, &GUID_ContainerFormatPng, sizeof(GUID) ) == 0 ) + { + // Set Software name + (void)metawriter->SetMetadataByName( L"/tEXt/{str=Software}", &value ); + + // Set sRGB chunk + if ( sRGB ) + { + value.vt = VT_UI1; + value.bVal = 0; + (void)metawriter->SetMetadataByName( L"/sRGB/RenderingIntent", &value ); + } + } + else + { + // Set Software name + (void)metawriter->SetMetadataByName( L"System.ApplicationName", &value ); + + if ( sRGB ) + { + // Set EXIF Colorspace of sRGB + value.vt = VT_UI2; + value.uiVal = 1; + (void)metawriter->SetMetadataByName( L"System.Image.ColorSpace", &value ); + } + } + } + + void* pMappedMemory; + D3D12_RANGE readRange = {0, static_cast(dstRowPitch * desc.Height)}; + D3D12_RANGE writeRange = {0, 0}; + hr = pStaging->Map(0, &readRange, &pMappedMemory); + if (FAILED(hr)) + return hr; + + if ( memcmp( &targetGuid, &pfGuid, sizeof(WICPixelFormatGUID) ) != 0 ) + { + // Conversion required to write + ComPtr source; + hr = pWIC->CreateBitmapFromMemory(static_cast(desc.Width), desc.Height, pfGuid, + static_cast(dstRowPitch), static_cast(dstRowPitch * desc.Height), + reinterpret_cast(pMappedMemory), source.GetAddressOf() ); + if ( FAILED(hr) ) + { + pStaging->Unmap( 0, &writeRange ); + return hr; + } + + ComPtr FC; + hr = pWIC->CreateFormatConverter( FC.GetAddressOf() ); + if ( FAILED(hr) ) + { + pStaging->Unmap(0, &writeRange); + return hr; + } + + BOOL canConvert = FALSE; + hr = FC->CanConvert( pfGuid, targetGuid, &canConvert ); + if ( FAILED(hr) || !canConvert ) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize( source.Get(), targetGuid, WICBitmapDitherTypeNone, nullptr, 0, WICBitmapPaletteTypeMedianCut ); + if ( FAILED(hr) ) + { + pStaging->Unmap(0, &writeRange); + return hr; + } + + WICRect rect = { 0, 0, static_cast( desc.Width ), static_cast( desc.Height ) }; + hr = frame->WriteSource( FC.Get(), &rect ); + if ( FAILED(hr) ) + { + pStaging->Unmap(0, &writeRange); + return hr; + } + } + else + { + // No conversion required + hr = frame->WritePixels( desc.Height, static_cast(dstRowPitch), static_cast(dstRowPitch * desc.Height), reinterpret_cast( pMappedMemory ) ); + if ( FAILED(hr) ) + return hr; + } + + pStaging->Unmap(0, &writeRange); + + hr = frame->Commit(); + if ( FAILED(hr) ) + return hr; + + hr = encoder->Commit(); + if ( FAILED(hr) ) + return hr; + + delonfail.clear(); + + return S_OK; +} diff --git a/deps/DirectXTex/ScreenGrab/ScreenGrab12.h b/deps/DirectXTex/ScreenGrab/ScreenGrab12.h new file mode 100644 index 0000000..5f218a4 --- /dev/null +++ b/deps/DirectXTex/ScreenGrab/ScreenGrab12.h @@ -0,0 +1,49 @@ +//-------------------------------------------------------------------------------------- +// File: ScreenGrab12.h +// +// Function for capturing a 2D texture and saving it to a file (aka a 'screenshot' +// when used on a Direct3D 12 Render Target). +// +// Note these functions are useful as a light-weight runtime screen grabber. For +// full-featured texture capture, DDS writer, and texture processing pipeline, +// see the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkID=615561 +//-------------------------------------------------------------------------------------- + +#pragma once + +#include + +#include +#include +#include + + +namespace DirectX +{ + HRESULT __cdecl SaveDDSTextureToFile( + _In_ ID3D12CommandQueue* pCommandQueue, + _In_ ID3D12Resource* pSource, + _In_z_ const wchar_t* fileName, + D3D12_RESOURCE_STATES beforeState = D3D12_RESOURCE_STATE_RENDER_TARGET, + D3D12_RESOURCE_STATES afterState = D3D12_RESOURCE_STATE_RENDER_TARGET); + + HRESULT __cdecl SaveWICTextureToFile( + _In_ ID3D12CommandQueue* pCommandQ, + _In_ ID3D12Resource* pSource, + REFGUID guidContainerFormat, + _In_z_ const wchar_t* fileName, + D3D12_RESOURCE_STATES beforeState = D3D12_RESOURCE_STATE_RENDER_TARGET, + D3D12_RESOURCE_STATES afterState = D3D12_RESOURCE_STATE_RENDER_TARGET, + _In_opt_ const GUID* targetFormat = nullptr, + _In_opt_ std::function setCustomProps = nullptr); +} \ No newline at end of file diff --git a/deps/DirectXTex/Texassemble/Texassemble_Desktop_2013.vcxproj b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2013.vcxproj new file mode 100644 index 0000000..9ce81e0 --- /dev/null +++ b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2013.vcxproj @@ -0,0 +1,407 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + texassemble + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1} + texassemble + Win32Proj + $(VCTargetsPath11) + + + + Application + Unicode + v120 + + + Application + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texassemble + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texassemble + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texassemble/Texassemble_Desktop_2013.vcxproj.filters b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2013.vcxproj.filters new file mode 100644 index 0000000..781df78 --- /dev/null +++ b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2013.vcxproj.filters @@ -0,0 +1,17 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texassemble/Texassemble_Desktop_2015.vcxproj b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2015.vcxproj new file mode 100644 index 0000000..1b46a69 --- /dev/null +++ b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2015.vcxproj @@ -0,0 +1,406 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + texassemble + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1} + texassemble + Win32Proj + + + + Application + Unicode + v140 + + + Application + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texassemble + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texassemble + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texassemble/Texassemble_Desktop_2015.vcxproj.filters b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2015.vcxproj.filters new file mode 100644 index 0000000..781df78 --- /dev/null +++ b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2015.vcxproj.filters @@ -0,0 +1,17 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texassemble/Texassemble_Desktop_2017.vcxproj b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2017.vcxproj new file mode 100644 index 0000000..9d55a82 --- /dev/null +++ b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2017.vcxproj @@ -0,0 +1,413 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + texassemble + {8F18CBD7-4116-4956-BCD8-20D688A4CBD1} + texassemble + Win32Proj + 10.0.15063.0 + + + + Application + Unicode + v141 + + + Application + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texassemble + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texassemble + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texassemble + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texassemble/Texassemble_Desktop_2017.vcxproj.filters b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2017.vcxproj.filters new file mode 100644 index 0000000..781df78 --- /dev/null +++ b/deps/DirectXTex/Texassemble/Texassemble_Desktop_2017.vcxproj.filters @@ -0,0 +1,17 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texassemble/directx.ico b/deps/DirectXTex/Texassemble/directx.ico new file mode 100644 index 0000000..bc43c1b Binary files /dev/null and b/deps/DirectXTex/Texassemble/directx.ico differ diff --git a/deps/DirectXTex/Texassemble/texassemble.cpp b/deps/DirectXTex/Texassemble/texassemble.cpp new file mode 100644 index 0000000..93171f6 --- /dev/null +++ b/deps/DirectXTex/Texassemble/texassemble.cpp @@ -0,0 +1,1449 @@ +//-------------------------------------------------------------------------------------- +// File: Texassemble.cpp +// +// DirectX Texture assembler for cube maps, volume maps, and arrays +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//-------------------------------------------------------------------------------------- + +#pragma warning(push) +#pragma warning(disable : 4005) +#define WIN32_LEAN_AND_MEAN +#define NOMINMAX +#define NODRAWTEXT +#define NOGDI +#define NOBITMAP +#define NOMCX +#define NOSERVICE +#define NOHELP +#pragma warning(pop) + +#include +#include +#include + +#include +#include +#include + +#include + +#include "directxtex.h" + +//Uncomment to add support for OpenEXR (.exr) +//#define USE_OPENEXR + +#ifdef USE_OPENEXR +// See for details +#include "DirectXTexEXR.h" +#endif + +using namespace DirectX; + +enum COMMANDS +{ + CMD_CUBE = 1, + CMD_VOLUME, + CMD_ARRAY, + CMD_CUBEARRAY, + CMD_H_CROSS, + CMD_V_CROSS, + CMD_H_STRIP, + CMD_V_STRIP, + CMD_MAX +}; + +enum OPTIONS +{ + OPT_RECURSIVE = 1, + OPT_WIDTH, + OPT_HEIGHT, + OPT_FORMAT, + OPT_FILTER, + OPT_SRGBI, + OPT_SRGBO, + OPT_SRGB, + OPT_OUTPUTFILE, + OPT_OVERWRITE, + OPT_USE_DX10, + OPT_NOLOGO, + OPT_SEPALPHA, + OPT_DEMUL_ALPHA, + OPT_TA_WRAP, + OPT_TA_MIRROR, + OPT_TONEMAP, + OPT_MAX +}; + +static_assert(OPT_MAX <= 32, "dwOptions is a DWORD bitfield"); + +struct SConversion +{ + wchar_t szSrc[MAX_PATH]; +}; + +struct SValue +{ + LPCWSTR pName; + DWORD dwValue; +}; + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// + +const SValue g_pCommands[] = +{ + { L"cube", CMD_CUBE }, + { L"volume", CMD_VOLUME }, + { L"array", CMD_ARRAY }, + { L"cubearray", CMD_CUBEARRAY }, + { L"h-cross", CMD_H_CROSS }, + { L"v-cross", CMD_V_CROSS }, + { L"h-strip", CMD_H_STRIP }, + { L"v-strip", CMD_V_STRIP }, + { nullptr, 0 } +}; + +const SValue g_pOptions [] = +{ + { L"r", OPT_RECURSIVE }, + { L"w", OPT_WIDTH }, + { L"h", OPT_HEIGHT }, + { L"f", OPT_FORMAT }, + { L"if", OPT_FILTER }, + { L"srgbi", OPT_SRGBI }, + { L"srgbo", OPT_SRGBO }, + { L"srgb", OPT_SRGB }, + { L"o", OPT_OUTPUTFILE }, + { L"y", OPT_OVERWRITE }, + { L"dx10", OPT_USE_DX10 }, + { L"nologo", OPT_NOLOGO }, + { L"sepalpha", OPT_SEPALPHA }, + { L"alpha", OPT_DEMUL_ALPHA }, + { L"wrap", OPT_TA_WRAP }, + { L"mirror", OPT_TA_MIRROR }, + { L"tonemap", OPT_TONEMAP }, + { nullptr, 0 } +}; + +#define DEFFMT(fmt) { L#fmt, DXGI_FORMAT_ ## fmt } + +const SValue g_pFormats [] = +{ + // List does not include _TYPELESS or depth/stencil formats + DEFFMT(R32G32B32A32_FLOAT), + DEFFMT(R32G32B32A32_UINT), + DEFFMT(R32G32B32A32_SINT), + DEFFMT(R32G32B32_FLOAT), + DEFFMT(R32G32B32_UINT), + DEFFMT(R32G32B32_SINT), + DEFFMT(R16G16B16A16_FLOAT), + DEFFMT(R16G16B16A16_UNORM), + DEFFMT(R16G16B16A16_UINT), + DEFFMT(R16G16B16A16_SNORM), + DEFFMT(R16G16B16A16_SINT), + DEFFMT(R32G32_FLOAT), + DEFFMT(R32G32_UINT), + DEFFMT(R32G32_SINT), + DEFFMT(R10G10B10A2_UNORM), + DEFFMT(R10G10B10A2_UINT), + DEFFMT(R11G11B10_FLOAT), + DEFFMT(R8G8B8A8_UNORM), + DEFFMT(R8G8B8A8_UNORM_SRGB), + DEFFMT(R8G8B8A8_UINT), + DEFFMT(R8G8B8A8_SNORM), + DEFFMT(R8G8B8A8_SINT), + DEFFMT(R16G16_FLOAT), + DEFFMT(R16G16_UNORM), + DEFFMT(R16G16_UINT), + DEFFMT(R16G16_SNORM), + DEFFMT(R16G16_SINT), + DEFFMT(R32_FLOAT), + DEFFMT(R32_UINT), + DEFFMT(R32_SINT), + DEFFMT(R8G8_UNORM), + DEFFMT(R8G8_UINT), + DEFFMT(R8G8_SNORM), + DEFFMT(R8G8_SINT), + DEFFMT(R16_FLOAT), + DEFFMT(R16_UNORM), + DEFFMT(R16_UINT), + DEFFMT(R16_SNORM), + DEFFMT(R16_SINT), + DEFFMT(R8_UNORM), + DEFFMT(R8_UINT), + DEFFMT(R8_SNORM), + DEFFMT(R8_SINT), + DEFFMT(A8_UNORM), + //DEFFMT(R1_UNORM) + DEFFMT(R9G9B9E5_SHAREDEXP), + DEFFMT(R8G8_B8G8_UNORM), + DEFFMT(G8R8_G8B8_UNORM), + DEFFMT(B5G6R5_UNORM), + DEFFMT(B5G5R5A1_UNORM), + + // DXGI 1.1 formats + DEFFMT(B8G8R8A8_UNORM), + DEFFMT(B8G8R8X8_UNORM), + DEFFMT(R10G10B10_XR_BIAS_A2_UNORM), + DEFFMT(B8G8R8A8_UNORM_SRGB), + DEFFMT(B8G8R8X8_UNORM_SRGB), + + // DXGI 1.2 formats + DEFFMT(AYUV), + DEFFMT(Y410), + DEFFMT(Y416), + DEFFMT(YUY2), + DEFFMT(Y210), + DEFFMT(Y216), + // No support for legacy paletted video formats (AI44, IA44, P8, A8P8) + DEFFMT(B4G4R4A4_UNORM), + + { nullptr, DXGI_FORMAT_UNKNOWN } +}; + +const SValue g_pFilters [] = +{ + { L"POINT", TEX_FILTER_POINT }, + { L"LINEAR", TEX_FILTER_LINEAR }, + { L"CUBIC", TEX_FILTER_CUBIC }, + { L"FANT", TEX_FILTER_FANT }, + { L"BOX", TEX_FILTER_BOX }, + { L"TRIANGLE", TEX_FILTER_TRIANGLE }, + { L"POINT_DITHER", TEX_FILTER_POINT | TEX_FILTER_DITHER }, + { L"LINEAR_DITHER", TEX_FILTER_LINEAR | TEX_FILTER_DITHER }, + { L"CUBIC_DITHER", TEX_FILTER_CUBIC | TEX_FILTER_DITHER }, + { L"FANT_DITHER", TEX_FILTER_FANT | TEX_FILTER_DITHER }, + { L"BOX_DITHER", TEX_FILTER_BOX | TEX_FILTER_DITHER }, + { L"TRIANGLE_DITHER", TEX_FILTER_TRIANGLE | TEX_FILTER_DITHER }, + { L"POINT_DITHER_DIFFUSION", TEX_FILTER_POINT | TEX_FILTER_DITHER_DIFFUSION }, + { L"LINEAR_DITHER_DIFFUSION", TEX_FILTER_LINEAR | TEX_FILTER_DITHER_DIFFUSION }, + { L"CUBIC_DITHER_DIFFUSION", TEX_FILTER_CUBIC | TEX_FILTER_DITHER_DIFFUSION }, + { L"FANT_DITHER_DIFFUSION", TEX_FILTER_FANT | TEX_FILTER_DITHER_DIFFUSION }, + { L"BOX_DITHER_DIFFUSION", TEX_FILTER_BOX | TEX_FILTER_DITHER_DIFFUSION }, + { L"TRIANGLE_DITHER_DIFFUSION", TEX_FILTER_TRIANGLE | TEX_FILTER_DITHER_DIFFUSION }, + { nullptr, TEX_FILTER_DEFAULT } +}; + +#define CODEC_DDS 0xFFFF0001 +#define CODEC_TGA 0xFFFF0002 +#define CODEC_HDR 0xFFFF0005 +#define CODEC_EXR 0xFFFF0006 + +const SValue g_pExtFileTypes [] = +{ + { L".BMP", WIC_CODEC_BMP }, + { L".JPG", WIC_CODEC_JPEG }, + { L".JPEG", WIC_CODEC_JPEG }, + { L".PNG", WIC_CODEC_PNG }, + { L".DDS", CODEC_DDS }, + { L".TGA", CODEC_TGA }, + { L".HDR", CODEC_HDR }, + { L".TIF", WIC_CODEC_TIFF }, + { L".TIFF", WIC_CODEC_TIFF }, + { L".WDP", WIC_CODEC_WMP }, + { L".HDP", WIC_CODEC_WMP }, + { L".JXR", WIC_CODEC_WMP }, +#ifdef USE_OPENEXR + { L"EXR", CODEC_EXR }, +#endif + { nullptr, CODEC_DDS } +}; + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// + +namespace +{ + inline HANDLE safe_handle(HANDLE h) { return (h == INVALID_HANDLE_VALUE) ? 0 : h; } + + struct find_closer { void operator()(HANDLE h) { assert(h != INVALID_HANDLE_VALUE); if (h) FindClose(h); } }; + + typedef public std::unique_ptr ScopedFindHandle; + +#pragma prefast(disable : 26018, "Only used with static internal arrays") + + DWORD LookupByName(const wchar_t *pName, const SValue *pArray) + { + while (pArray->pName) + { + if (!_wcsicmp(pName, pArray->pName)) + return pArray->dwValue; + + pArray++; + } + + return 0; + } + + + const wchar_t* LookupByValue(DWORD pValue, const SValue *pArray) + { + while (pArray->pName) + { + if (pValue == pArray->dwValue) + return pArray->pName; + + pArray++; + } + + return L""; + } + + + void SearchForFiles(const wchar_t* path, std::list& files, bool recursive) + { + // Process files + WIN32_FIND_DATA findData = {}; + ScopedFindHandle hFile(safe_handle(FindFirstFileExW(path, + FindExInfoBasic, &findData, + FindExSearchNameMatch, nullptr, + FIND_FIRST_EX_LARGE_FETCH))); + if (hFile) + { + for (;;) + { + if (!(findData.dwFileAttributes & (FILE_ATTRIBUTE_HIDDEN | FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_DIRECTORY))) + { + wchar_t drive[_MAX_DRIVE] = {}; + wchar_t dir[_MAX_DIR] = {}; + _wsplitpath_s(path, drive, _MAX_DRIVE, dir, _MAX_DIR, nullptr, 0, nullptr, 0); + + SConversion conv; + _wmakepath_s(conv.szSrc, drive, dir, findData.cFileName, nullptr); + files.push_back(conv); + } + + if (!FindNextFile(hFile.get(), &findData)) + break; + } + } + + // Process directories + if (recursive) + { + wchar_t searchDir[MAX_PATH] = {}; + { + wchar_t drive[_MAX_DRIVE] = {}; + wchar_t dir[_MAX_DIR] = {}; + _wsplitpath_s(path, drive, _MAX_DRIVE, dir, _MAX_DIR, nullptr, 0, nullptr, 0); + _wmakepath_s(searchDir, drive, dir, L"*", nullptr); + } + + hFile.reset(safe_handle(FindFirstFileExW(searchDir, + FindExInfoBasic, &findData, + FindExSearchLimitToDirectories, nullptr, + FIND_FIRST_EX_LARGE_FETCH))); + if (!hFile) + return; + + for (;;) + { + if (findData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) + { + if (findData.cFileName[0] != L'.') + { + wchar_t subdir[MAX_PATH] = {}; + + { + wchar_t drive[_MAX_DRIVE] = {}; + wchar_t dir[_MAX_DIR] = {}; + wchar_t fname[_MAX_FNAME] = {}; + wchar_t ext[_MAX_FNAME] = {}; + _wsplitpath_s(path, drive, dir, fname, ext); + wcscat_s(dir, findData.cFileName); + _wmakepath_s(subdir, drive, dir, fname, ext); + } + + SearchForFiles(subdir, files, recursive); + } + } + + if (!FindNextFile(hFile.get(), &findData)) + break; + } + } + } + + + void PrintFormat(DXGI_FORMAT Format) + { + for (const SValue *pFormat = g_pFormats; pFormat->pName; pFormat++) + { + if ((DXGI_FORMAT)pFormat->dwValue == Format) + { + wprintf(pFormat->pName); + break; + } + } + } + + + void PrintInfo(const TexMetadata& info) + { + wprintf(L" (%Iux%Iu", info.width, info.height); + + if (TEX_DIMENSION_TEXTURE3D == info.dimension) + wprintf(L"x%Iu", info.depth); + + if (info.mipLevels > 1) + wprintf(L",%Iu", info.mipLevels); + + if (info.arraySize > 1) + wprintf(L",%Iu", info.arraySize); + + wprintf(L" "); + PrintFormat(info.format); + + switch (info.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + wprintf((info.arraySize > 1) ? L" 1DArray" : L" 1D"); + break; + + case TEX_DIMENSION_TEXTURE2D: + if (info.IsCubemap()) + { + wprintf((info.arraySize > 6) ? L" CubeArray" : L" Cube"); + } + else + { + wprintf((info.arraySize > 1) ? L" 2DArray" : L" 2D"); + } + break; + + case TEX_DIMENSION_TEXTURE3D: + wprintf(L" 3D"); + break; + } + + switch (info.GetAlphaMode()) + { + case TEX_ALPHA_MODE_OPAQUE: + wprintf(L" \x0e0:Opaque"); + break; + case TEX_ALPHA_MODE_PREMULTIPLIED: + wprintf(L" \x0e0:PM"); + break; + case TEX_ALPHA_MODE_STRAIGHT: + wprintf(L" \x0e0:NonPM"); + break; + } + + wprintf(L")"); + } + + + void PrintList(size_t cch, const SValue *pValue) + { + while (pValue->pName) + { + size_t cchName = wcslen(pValue->pName); + + if (cch + cchName + 2 >= 80) + { + wprintf(L"\n "); + cch = 6; + } + + wprintf(L"%ls ", pValue->pName); + cch += cchName + 2; + pValue++; + } + + wprintf(L"\n"); + } + + + void PrintLogo() + { + wprintf(L"Microsoft (R) DirectX Texture Assembler (DirectXTex version)\n"); + wprintf(L"Copyright (C) Microsoft Corp. All rights reserved.\n"); +#ifdef _DEBUG + wprintf(L"*** Debug build ***\n"); +#endif + wprintf(L"\n"); + } + + + void PrintUsage() + { + PrintLogo(); + + wprintf(L"Usage: texassemble \n\n"); + wprintf(L" cube create cubemap\n"); + wprintf(L" volume create volume map\n"); + wprintf(L" array create texture array\n"); + wprintf(L" cubearray create cubemap array\n"); + wprintf(L" h-cross or v-cross create a cross image from a cubemap\n"); + wprintf(L" h-strip or v-strip create a strip image from a cubemap\n\n"); + wprintf(L" -r wildcard filename search is recursive\n"); + wprintf(L" -w width\n"); + wprintf(L" -h height\n"); + wprintf(L" -f format\n"); + wprintf(L" -if image filtering\n"); + wprintf(L" -srgb{i|o} sRGB {input, output}\n"); + wprintf(L" -o output filename\n"); + wprintf(L" -y overwrite existing output file (if any)\n"); + wprintf(L" -sepalpha resize alpha channel separately from color channels\n"); + wprintf(L" -wrap, -mirror texture addressing mode (wrap, mirror, or clamp)\n"); + wprintf(L" -alpha convert premultiplied alpha to straight alpha\n"); + wprintf(L" -dx10 Force use of 'DX10' extended header\n"); + wprintf(L" -nologo suppress copyright message\n"); + wprintf(L" -tonemap Apply a tonemap operator based on maximum luminance\n"); + + wprintf(L"\n : "); + PrintList(13, g_pFormats); + + wprintf(L"\n : "); + PrintList(13, g_pFilters); + } +} + + +//-------------------------------------------------------------------------------------- +// Entry-point +//-------------------------------------------------------------------------------------- +#pragma prefast(disable : 28198, "Command-line tool, frees all memory on exit") + +int __cdecl wmain(_In_ int argc, _In_z_count_(argc) wchar_t* argv[]) +{ + // Parameters and defaults + size_t width = 0; + size_t height = 0; + + DXGI_FORMAT format = DXGI_FORMAT_UNKNOWN; + DWORD dwFilter = TEX_FILTER_DEFAULT; + DWORD dwSRGB = 0; + DWORD dwFilterOpts = 0; + DWORD CrossFileType = WIC_CODEC_BMP; + + wchar_t szOutputFile[MAX_PATH] = { 0 }; + + // Initialize COM (needed for WIC) + HRESULT hr = hr = CoInitializeEx(nullptr, COINIT_MULTITHREADED); + if (FAILED(hr)) + { + wprintf(L"Failed to initialize COM (%08X)\n", hr); + return 1; + } + + // Process command line + if (argc < 2) + { + PrintUsage(); + return 0; + } + + DWORD dwCommand = LookupByName(argv[1], g_pCommands); + switch (dwCommand) + { + case CMD_CUBE: + case CMD_VOLUME: + case CMD_ARRAY: + case CMD_CUBEARRAY: + case CMD_H_CROSS: + case CMD_V_CROSS: + case CMD_H_STRIP: + case CMD_V_STRIP: + break; + + default: + wprintf(L"Must use one of: cube, volume, array, cubearray,\n h-cross, v-cross, h-strip, or v-strip\n\n"); + return 1; + } + + DWORD dwOptions = 0; + std::list conversion; + + for (int iArg = 2; iArg < argc; iArg++) + { + PWSTR pArg = argv[iArg]; + + if (('-' == pArg[0]) || ('/' == pArg[0])) + { + pArg++; + PWSTR pValue; + + for (pValue = pArg; *pValue && (':' != *pValue); pValue++); + + if (*pValue) + *pValue++ = 0; + + DWORD dwOption = LookupByName(pArg, g_pOptions); + + if (!dwOption || (dwOptions & (1 << dwOption))) + { + PrintUsage(); + return 1; + } + + dwOptions |= 1 << dwOption; + + // Handle options with additional value parameter + switch (dwOption) + { + case OPT_WIDTH: + case OPT_HEIGHT: + case OPT_FORMAT: + case OPT_FILTER: + case OPT_OUTPUTFILE: + if (!*pValue) + { + if ((iArg + 1 >= argc)) + { + PrintUsage(); + return 1; + } + + iArg++; + pValue = argv[iArg]; + } + } + + switch (dwOption) + { + case OPT_WIDTH: + if (swscanf_s(pValue, L"%Iu", &width) != 1) + { + wprintf(L"Invalid value specified with -w (%ls)\n", pValue); + return 1; + } + break; + + case OPT_HEIGHT: + if (swscanf_s(pValue, L"%Iu", &height) != 1) + { + wprintf(L"Invalid value specified with -h (%ls)\n", pValue); + return 1; + } + break; + + case OPT_FORMAT: + format = (DXGI_FORMAT)LookupByName(pValue, g_pFormats); + if (!format) + { + wprintf(L"Invalid value specified with -f (%ls)\n", pValue); + return 1; + } + break; + + case OPT_FILTER: + dwFilter = LookupByName(pValue, g_pFilters); + if (!dwFilter) + { + wprintf(L"Invalid value specified with -if (%ls)\n", pValue); + return 1; + } + break; + + case OPT_SRGBI: + dwSRGB |= TEX_FILTER_SRGB_IN; + break; + + case OPT_SRGBO: + dwSRGB |= TEX_FILTER_SRGB_OUT; + break; + + case OPT_SRGB: + dwSRGB |= TEX_FILTER_SRGB; + break; + + case OPT_SEPALPHA: + dwFilterOpts |= TEX_FILTER_SEPARATE_ALPHA; + break; + + case OPT_OUTPUTFILE: + { + wcscpy_s(szOutputFile, MAX_PATH, pValue); + + wchar_t ext[_MAX_EXT]; + _wsplitpath_s(szOutputFile, nullptr, 0, nullptr, 0, nullptr, 0, ext, _MAX_EXT); + + CrossFileType = LookupByName(ext, g_pExtFileTypes); + + switch (dwCommand) + { + case CMD_H_CROSS: + case CMD_V_CROSS: + case CMD_H_STRIP: + case CMD_V_STRIP: + break; + + default: + if (CrossFileType != CODEC_DDS) + { + wprintf(L"Assembled output file must be a dds\n"); + return 1; + } + } + break; + } + + case OPT_TA_WRAP: + if (dwFilterOpts & TEX_FILTER_MIRROR) + { + wprintf(L"Can't use -wrap and -mirror at same time\n\n"); + PrintUsage(); + return 1; + } + dwFilterOpts |= TEX_FILTER_WRAP; + break; + + case OPT_TA_MIRROR: + if (dwFilterOpts & TEX_FILTER_WRAP) + { + wprintf(L"Can't use -wrap and -mirror at same time\n\n"); + PrintUsage(); + return 1; + } + dwFilterOpts |= TEX_FILTER_MIRROR; + break; + } + } + else if (wcspbrk(pArg, L"?*") != nullptr) + { + size_t count = conversion.size(); + SearchForFiles(pArg, conversion, (dwOptions & (1 << OPT_RECURSIVE)) != 0); + if (conversion.size() <= count) + { + wprintf(L"No matching files found for %ls\n", pArg); + return 1; + } + } + else + { + SConversion conv; + wcscpy_s(conv.szSrc, MAX_PATH, pArg); + + conversion.push_back(conv); + } + } + + if (conversion.empty()) + { + PrintUsage(); + return 0; + } + + if (~dwOptions & (1 << OPT_NOLOGO)) + PrintLogo(); + + switch (dwCommand) + { + case CMD_H_CROSS: + case CMD_V_CROSS: + case CMD_H_STRIP: + case CMD_V_STRIP: + if (conversion.size() > 1) + { + wprintf(L"ERROR: cross/strip output only accepts 1 input file\n"); + return 1; + } + break; + } + + // Convert images + size_t images = 0; + + std::vector> loadedImages; + + for (auto pConv = conversion.begin(); pConv != conversion.end(); ++pConv) + { + wchar_t ext[_MAX_EXT]; + wchar_t fname[_MAX_FNAME]; + _wsplitpath_s(pConv->szSrc, nullptr, 0, nullptr, 0, fname, _MAX_FNAME, ext, _MAX_EXT); + + // Load source image + if (pConv != conversion.begin()) + wprintf(L"\n"); + else if (!*szOutputFile) + { + switch (dwCommand) + { + case CMD_H_CROSS: + case CMD_V_CROSS: + case CMD_H_STRIP: + case CMD_V_STRIP: + _wmakepath_s(szOutputFile, nullptr, nullptr, fname, L".bmp"); + break; + + default: + if (_wcsicmp(ext, L".dds") == 0) + { + wprintf(L"ERROR: Need to specify output file via -o\n"); + return 1; + } + + _wmakepath_s(szOutputFile, nullptr, nullptr, fname, L".dds"); + break; + } + } + + wprintf(L"reading %ls", pConv->szSrc); + fflush(stdout); + + TexMetadata info; + std::unique_ptr image(new (std::nothrow) ScratchImage); + if (!image) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + switch (dwCommand) + { + case CMD_H_CROSS: + case CMD_V_CROSS: + case CMD_H_STRIP: + case CMD_V_STRIP: + if (_wcsicmp(ext, L".dds") == 0) + { + hr = LoadFromDDSFile(pConv->szSrc, DDS_FLAGS_NONE, &info, *image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + return 1; + } + + if (!info.IsCubemap()) + { + wprintf(L"\nERROR: Input must be a cubemap\n"); + return 1; + } + else if (info.arraySize != 6) + { + wprintf(L"\nWARNING: Only the first cubemap in an array is written out as a cross/strip\n"); + } + } + else + { + wprintf(L"\nERROR: Input must be a dds of a cubemap\n"); + return 1; + } + break; + + default: + if (_wcsicmp(ext, L".dds") == 0) + { + hr = LoadFromDDSFile(pConv->szSrc, DDS_FLAGS_NONE, &info, *image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + return 1; + } + + if (info.mipLevels > 1 + || info.IsVolumemap() + || info.IsCubemap()) + { + wprintf(L"\nERROR: Can't assemble complex surfaces\n"); + return 1; + } + } + else if (_wcsicmp(ext, L".tga") == 0) + { + hr = LoadFromTGAFile(pConv->szSrc, &info, *image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + return 1; + } + } + else if (_wcsicmp(ext, L".hdr") == 0) + { + hr = LoadFromHDRFile(pConv->szSrc, &info, *image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + return 1; + } + } +#ifdef USE_OPENEXR + else if (_wcsicmp(ext, L".exr") == 0) + { + hr = LoadFromEXRFile(pConv->szSrc, &info, *image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + continue; + } + } +#endif + else + { + // WIC shares the same filter values for mode and dither + static_assert(WIC_FLAGS_DITHER == TEX_FILTER_DITHER, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_DITHER_DIFFUSION == TEX_FILTER_DITHER_DIFFUSION, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_POINT == TEX_FILTER_POINT, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_LINEAR == TEX_FILTER_LINEAR, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_CUBIC == TEX_FILTER_CUBIC, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_FANT == TEX_FILTER_FANT, "WIC_FLAGS_* & TEX_FILTER_* should match"); + + hr = LoadFromWICFile(pConv->szSrc, dwFilter | WIC_FLAGS_ALL_FRAMES, &info, *image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + return 1; + } + } + break; + } + + PrintInfo(info); + + // Convert texture + fflush(stdout); + + // --- Planar ------------------------------------------------------------------ + if (IsPlanar(info.format)) + { + auto img = image->GetImage(0, 0, 0); + assert(img); + size_t nimg = image->GetImageCount(); + + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = ConvertToSinglePlane(img, nimg, info, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [converttosingleplane] (%x)\n", hr); + continue; + } + + auto& tinfo = timage->GetMetadata(); + + info.format = tinfo.format; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + } + + // --- Decompress -------------------------------------------------------------- + if (IsCompressed(info.format)) + { + const Image* img = image->GetImage(0, 0, 0); + assert(img); + size_t nimg = image->GetImageCount(); + + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = Decompress(img, nimg, info, DXGI_FORMAT_UNKNOWN /* picks good default */, *timage.get()); + if (FAILED(hr)) + { + wprintf(L" FAILED [decompress] (%x)\n", hr); + continue; + } + + const TexMetadata& tinfo = timage->GetMetadata(); + + info.format = tinfo.format; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + } + + // --- Undo Premultiplied Alpha (if requested) --------------------------------- + if ((dwOptions & (1 << OPT_DEMUL_ALPHA)) + && HasAlpha(info.format) + && info.format != DXGI_FORMAT_A8_UNORM) + { + if (info.GetAlphaMode() == TEX_ALPHA_MODE_STRAIGHT) + { + printf("\nWARNING: Image is already using straight alpha\n"); + } + else if (!info.IsPMAlpha()) + { + printf("\nWARNING: Image is not using premultipled alpha\n"); + } + else + { + auto img = image->GetImage(0, 0, 0); + assert(img); + size_t nimg = image->GetImageCount(); + + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = PremultiplyAlpha(img, nimg, info, TEX_PMALPHA_REVERSE | dwSRGB, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [demultiply alpha] (%x)\n", hr); + continue; + } + + auto& tinfo = timage->GetMetadata(); + info.miscFlags2 = tinfo.miscFlags2; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + } + } + + // --- Resize ------------------------------------------------------------------ + if (!width) + { + width = info.width; + } + if (!height) + { + height = info.height; + } + if (info.width != width || info.height != height) + { + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = Resize(image->GetImages(), image->GetImageCount(), image->GetMetadata(), width, height, dwFilter | dwFilterOpts, *timage.get()); + if (FAILED(hr)) + { + wprintf(L" FAILED [resize] (%x)\n", hr); + return 1; + } + + const TexMetadata& tinfo = timage->GetMetadata(); + + assert(tinfo.width == width && tinfo.height == height && tinfo.mipLevels == 1); + info.width = tinfo.width; + info.height = tinfo.height; + info.mipLevels = 1; + + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.format == tinfo.format); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + } + + // --- Tonemap (if requested) -------------------------------------------------- + if (dwOptions & (1 << OPT_TONEMAP)) + { + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + // Compute max luminosity across all images + XMVECTOR maxLum = XMVectorZero(); + hr = EvaluateImage(image->GetImages(), image->GetImageCount(), image->GetMetadata(), + [&](const XMVECTOR* pixels, size_t width, size_t y) + { + UNREFERENCED_PARAMETER(y); + + for (size_t j = 0; j < width; ++j) + { + static const XMVECTORF32 s_luminance = { 0.3f, 0.59f, 0.11f, 0.f }; + + XMVECTOR v = *pixels++; + + v = XMVector3Dot(v, s_luminance); + + maxLum = XMVectorMax(v, maxLum); + } + }); + if (FAILED(hr)) + { + wprintf(L" FAILED [tonemap maxlum] (%x)\n", hr); + return 1; + } + + // Reinhard et al, "Photographic Tone Reproduction for Digital Images" + // http://www.cs.utah.edu/~reinhard/cdrom/ + maxLum = XMVectorMultiply(maxLum, maxLum); + + hr = TransformImage(image->GetImages(), image->GetImageCount(), image->GetMetadata(), + [&](XMVECTOR* outPixels, const XMVECTOR* inPixels, size_t width, size_t y) + { + UNREFERENCED_PARAMETER(y); + + for (size_t j = 0; j < width; ++j) + { + XMVECTOR value = inPixels[j]; + + XMVECTOR scale = XMVectorDivide( + XMVectorAdd(g_XMOne, XMVectorDivide(value, maxLum)), + XMVectorAdd(g_XMOne, value)); + XMVECTOR nvalue = XMVectorMultiply(value, scale); + + value = XMVectorSelect(value, nvalue, g_XMSelect1110); + + outPixels[j] = value; + } + }, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [tonemap apply] (%x)\n", hr); + return 1; + } + + auto& tinfo = timage->GetMetadata(); + tinfo; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.format == tinfo.format); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + } + + // --- Convert ----------------------------------------------------------------- + if (format == DXGI_FORMAT_UNKNOWN) + { + format = info.format; + } + else if (info.format != format && !IsCompressed(format)) + { + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = Convert(image->GetImages(), image->GetImageCount(), image->GetMetadata(), format, + dwFilter | dwFilterOpts | dwSRGB, TEX_THRESHOLD_DEFAULT, *timage.get()); + if (FAILED(hr)) + { + wprintf(L" FAILED [convert] (%x)\n", hr); + return 1; + } + + const TexMetadata& tinfo = timage->GetMetadata(); + + assert(tinfo.format == format); + info.format = tinfo.format; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + } + + images += info.arraySize; + loadedImages.push_back(std::move(image)); + } + + switch (dwCommand) + { + case CMD_CUBE: + if (images != 6) + { + wprintf(L"\nERROR: cube requires six images to form the faces of the cubemap\n"); + return 1; + } + break; + + case CMD_CUBEARRAY: + if ((images < 6) || (images % 6) != 0) + { + wprintf(L"cubearray requires a multiple of 6 images to form the faces of the cubemaps\n"); + return 1; + } + break; + + case CMD_H_CROSS: + case CMD_V_CROSS: + case CMD_H_STRIP: + case CMD_V_STRIP: + break; + + default: + if (images < 2) + { + wprintf(L"\nERROR: Need at least 2 images to assemble\n\n"); + return 1; + } + break; + } + + // --- Create result --------------------------------------------------------------- + switch (dwCommand) + { + case CMD_H_CROSS: + case CMD_V_CROSS: + case CMD_H_STRIP: + case CMD_V_STRIP: + { + size_t twidth = 0; + size_t theight = 0; + + switch (dwCommand) + { + case CMD_H_CROSS: + // posy + // negx posz posx negz + // negy + twidth = width * 4; + theight = height * 3; + break; + + case CMD_V_CROSS: + // posy + // posz posx negz + // negy + // negx + twidth = width * 3; + theight = height * 4; + break; + + case CMD_H_STRIP: + twidth = width * 6; + theight = height; + break; + + case CMD_V_STRIP: + twidth = width; + theight = height * 6; + } + + ScratchImage result; + hr = result.Initialize2D(format, twidth, theight, 1, 1); + if (FAILED(hr)) + { + wprintf(L"FAILED setting up result image (%x)\n", hr); + return 1; + } + + memset(result.GetPixels(), 0, result.GetPixelsSize()); + + auto src = loadedImages.cbegin(); + auto dest = result.GetImage(0, 0, 0); + + for (size_t index = 0; index < 6; ++index) + { + auto img = (*src)->GetImage(0, index, 0); + if (!img) + { + wprintf(L"FAILED: Unexpected error\n"); + return 1; + } + + Rect rect(0, 0, width, height); + + size_t offsetx = 0; + size_t offsety = 0; + + switch (dwCommand) + { + case CMD_H_CROSS: + { + // posy + // negx posz posx negz + // negy + + static const size_t s_offsetx[6] = { 2, 0, 1, 1, 1, 3 }; + static const size_t s_offsety[6] = { 1, 1, 0, 2, 1, 1 }; + + offsetx = s_offsetx[index] * width; + offsety = s_offsety[index] * height; + break; + } + + case CMD_V_CROSS: + { + // posy + // posz posx negz + // negy + // negx + + static const size_t s_offsetx[6] = { 1, 1, 1, 1, 0, 2 }; + static const size_t s_offsety[6] = { 1, 3, 0, 2, 1, 1 }; + + offsetx = s_offsetx[index] * width; + offsety = s_offsety[index] * height; + break; + } + + case CMD_H_STRIP: + // posx, negx, posy, negy, posz, negz + offsetx = index * width; + break; + + case CMD_V_STRIP: + // posx, negx, posy, negy, posz, negz + offsety = index * height; + break; + } + + hr = CopyRectangle(*img, rect, *dest, dwFilter | dwFilterOpts, offsetx, offsety); + if (FAILED(hr)) + { + wprintf(L"FAILED building result image (%x)\n", hr); + return 1; + } + } + + // Write cross/strip + wprintf(L"\nWriting %ls ", szOutputFile); + PrintInfo(result.GetMetadata()); + wprintf(L"\n"); + fflush(stdout); + + if (~dwOptions & (1 << OPT_OVERWRITE)) + { + if (GetFileAttributesW(szOutputFile) != INVALID_FILE_ATTRIBUTES) + { + wprintf(L"\nERROR: Output file already exists, use -y to overwrite\n"); + return 1; + } + } + + switch (CrossFileType) + { + case CODEC_DDS: + hr = SaveToDDSFile(*dest, DDS_FLAGS_NONE, szOutputFile); + break; + + case CODEC_TGA: + hr = SaveToTGAFile(*dest, szOutputFile); + break; + + case CODEC_HDR: + hr = SaveToHDRFile(*dest, szOutputFile); + break; + +#ifdef USE_OPENEXR + case CODEC_EXR: + hr = SaveToEXRFile(*dest, szOutputFile); + break; +#endif + + default: + hr = SaveToWICFile(*dest, WIC_FLAGS_NONE, GetWICCodec(static_cast(CrossFileType)), szOutputFile); + break; + } + + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + return 1; + } + break; + } + + default: + { + std::vector imageArray; + imageArray.reserve(images); + + for (auto it = loadedImages.cbegin(); it != loadedImages.cend(); ++it) + { + const ScratchImage* simage = it->get(); + assert(simage != 0); + for (size_t j = 0; j < simage->GetMetadata().arraySize; ++j) + { + const Image* img = simage->GetImage(0, j, 0); + assert(img != 0); + imageArray.push_back(*img); + } + } + + ScratchImage result; + switch (dwCommand) + { + case CMD_VOLUME: + hr = result.Initialize3DFromImages(&imageArray[0], imageArray.size()); + break; + + case CMD_ARRAY: + hr = result.InitializeArrayFromImages(&imageArray[0], imageArray.size(), (dwOptions & (1 << OPT_USE_DX10)) != 0); + break; + + case CMD_CUBE: + case CMD_CUBEARRAY: + hr = result.InitializeCubeFromImages(&imageArray[0], imageArray.size()); + break; + } + + if (FAILED(hr)) + { + wprintf(L"FAILED building result image (%x)\n", hr); + return 1; + } + + // Write texture + wprintf(L"\nWriting %ls ", szOutputFile); + PrintInfo(result.GetMetadata()); + wprintf(L"\n"); + fflush(stdout); + + if (~dwOptions & (1 << OPT_OVERWRITE)) + { + if (GetFileAttributesW(szOutputFile) != INVALID_FILE_ATTRIBUTES) + { + wprintf(L"\nERROR: Output file already exists, use -y to overwrite\n"); + return 1; + } + } + + hr = SaveToDDSFile(result.GetImages(), result.GetImageCount(), result.GetMetadata(), + (dwOptions & (1 << OPT_USE_DX10)) ? (DDS_FLAGS_FORCE_DX10_EXT | DDS_FLAGS_FORCE_DX10_EXT_MISC2) : DDS_FLAGS_NONE, + szOutputFile); + if (FAILED(hr)) + { + wprintf(L"\nFAILED (%x)\n", hr); + return 1; + } + break; + } + } + + return 0; +} diff --git a/deps/DirectXTex/Texassemble/texassemble.rc b/deps/DirectXTex/Texassemble/texassemble.rc new file mode 100644 index 0000000..5208ce0 --- /dev/null +++ b/deps/DirectXTex/Texassemble/texassemble.rc @@ -0,0 +1,76 @@ +// Microsoft Visual C++ generated resource script. +// +#define APSTUDIO_READONLY_SYMBOLS +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 2 resource. +// +#define IDC_STATIC -1 +#include + + + +///////////////////////////////////////////////////////////////////////////// +#undef APSTUDIO_READONLY_SYMBOLS + +///////////////////////////////////////////////////////////////////////////// +// English (U.S.) resources + +#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) +#ifdef _WIN32 +LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US +#pragma code_page(1252) +#endif //_WIN32 + +///////////////////////////////////////////////////////////////////////////// +// +// Icon +// + +// Icon with lowest ID value placed first to ensure application icon +// remains consistent on all systems. +IDI_MAIN_ICON ICON "directx.ico" + +#ifdef APSTUDIO_INVOKED +///////////////////////////////////////////////////////////////////////////// +// +// TEXTINCLUDE +// + +1 TEXTINCLUDE +BEGIN + "resource.h\0" +END + +2 TEXTINCLUDE +BEGIN + "#define IDC_STATIC -1\r\n" + "#include \r\n" + "\r\n" + "\r\n" + "\0" +END + +3 TEXTINCLUDE +BEGIN + "\r\n" + "\0" +END + +#endif // APSTUDIO_INVOKED + +#endif // English (U.S.) resources +///////////////////////////////////////////////////////////////////////////// + + + +#ifndef APSTUDIO_INVOKED +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 3 resource. +// + + +///////////////////////////////////////////////////////////////////////////// +#endif // not APSTUDIO_INVOKED + diff --git a/deps/DirectXTex/Texconv/Texconv.rc b/deps/DirectXTex/Texconv/Texconv.rc new file mode 100644 index 0000000..5208ce0 --- /dev/null +++ b/deps/DirectXTex/Texconv/Texconv.rc @@ -0,0 +1,76 @@ +// Microsoft Visual C++ generated resource script. +// +#define APSTUDIO_READONLY_SYMBOLS +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 2 resource. +// +#define IDC_STATIC -1 +#include + + + +///////////////////////////////////////////////////////////////////////////// +#undef APSTUDIO_READONLY_SYMBOLS + +///////////////////////////////////////////////////////////////////////////// +// English (U.S.) resources + +#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) +#ifdef _WIN32 +LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US +#pragma code_page(1252) +#endif //_WIN32 + +///////////////////////////////////////////////////////////////////////////// +// +// Icon +// + +// Icon with lowest ID value placed first to ensure application icon +// remains consistent on all systems. +IDI_MAIN_ICON ICON "directx.ico" + +#ifdef APSTUDIO_INVOKED +///////////////////////////////////////////////////////////////////////////// +// +// TEXTINCLUDE +// + +1 TEXTINCLUDE +BEGIN + "resource.h\0" +END + +2 TEXTINCLUDE +BEGIN + "#define IDC_STATIC -1\r\n" + "#include \r\n" + "\r\n" + "\r\n" + "\0" +END + +3 TEXTINCLUDE +BEGIN + "\r\n" + "\0" +END + +#endif // APSTUDIO_INVOKED + +#endif // English (U.S.) resources +///////////////////////////////////////////////////////////////////////////// + + + +#ifndef APSTUDIO_INVOKED +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 3 resource. +// + + +///////////////////////////////////////////////////////////////////////////// +#endif // not APSTUDIO_INVOKED + diff --git a/deps/DirectXTex/Texconv/Texconv_Desktop_2013.vcxproj b/deps/DirectXTex/Texconv/Texconv_Desktop_2013.vcxproj new file mode 100644 index 0000000..1b1354a --- /dev/null +++ b/deps/DirectXTex/Texconv/Texconv_Desktop_2013.vcxproj @@ -0,0 +1,407 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + texconv + {C3A65381-8FD3-4F69-B29E-654B4B0ED136} + texconv + Win32Proj + $(VCTargetsPath11) + + + + Application + Unicode + v120 + + + Application + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texconv + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texconv + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texconv/Texconv_Desktop_2013.vcxproj.filters b/deps/DirectXTex/Texconv/Texconv_Desktop_2013.vcxproj.filters new file mode 100644 index 0000000..50ba8f9 --- /dev/null +++ b/deps/DirectXTex/Texconv/Texconv_Desktop_2013.vcxproj.filters @@ -0,0 +1,17 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texconv/Texconv_Desktop_2015.vcxproj b/deps/DirectXTex/Texconv/Texconv_Desktop_2015.vcxproj new file mode 100644 index 0000000..0cb305d --- /dev/null +++ b/deps/DirectXTex/Texconv/Texconv_Desktop_2015.vcxproj @@ -0,0 +1,406 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + texconv + {C3A65381-8FD3-4F69-B29E-654B4B0ED136} + texconv + Win32Proj + + + + Application + Unicode + v140 + + + Application + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texconv + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texconv + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texconv/Texconv_Desktop_2015.vcxproj.filters b/deps/DirectXTex/Texconv/Texconv_Desktop_2015.vcxproj.filters new file mode 100644 index 0000000..50ba8f9 --- /dev/null +++ b/deps/DirectXTex/Texconv/Texconv_Desktop_2015.vcxproj.filters @@ -0,0 +1,17 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texconv/Texconv_Desktop_2017.vcxproj b/deps/DirectXTex/Texconv/Texconv_Desktop_2017.vcxproj new file mode 100644 index 0000000..93d6ac4 --- /dev/null +++ b/deps/DirectXTex/Texconv/Texconv_Desktop_2017.vcxproj @@ -0,0 +1,413 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + texconv + {C3A65381-8FD3-4F69-B29E-654B4B0ED136} + texconv + Win32Proj + 10.0.15063.0 + + + + Application + Unicode + v141 + + + Application + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texconv + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texconv + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texconv + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + true + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texconv/Texconv_Desktop_2017.vcxproj.filters b/deps/DirectXTex/Texconv/Texconv_Desktop_2017.vcxproj.filters new file mode 100644 index 0000000..50ba8f9 --- /dev/null +++ b/deps/DirectXTex/Texconv/Texconv_Desktop_2017.vcxproj.filters @@ -0,0 +1,17 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texconv/directx.ico b/deps/DirectXTex/Texconv/directx.ico new file mode 100644 index 0000000..bc43c1b Binary files /dev/null and b/deps/DirectXTex/Texconv/directx.ico differ diff --git a/deps/DirectXTex/Texconv/texconv.cpp b/deps/DirectXTex/Texconv/texconv.cpp new file mode 100644 index 0000000..9d7efb5 --- /dev/null +++ b/deps/DirectXTex/Texconv/texconv.cpp @@ -0,0 +1,2425 @@ +//-------------------------------------------------------------------------------------- +// File: TexConv.cpp +// +// DirectX Texture Converter +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//-------------------------------------------------------------------------------------- + +#pragma warning(push) +#pragma warning(disable : 4005) +#define WIN32_LEAN_AND_MEAN +#define NOMINMAX +#define NODRAWTEXT +#define NOGDI +#define NOBITMAP +#define NOMCX +#define NOSERVICE +#define NOHELP +#pragma warning(pop) + +#include +#include +#include + +#include +#include + +#include + +#include +#include +#include + +#include + +#include "directxtex.h" + +#include "DirectXPackedVector.h" + +//Uncomment to add support for OpenEXR (.exr) +//#define USE_OPENEXR + +#ifdef USE_OPENEXR +// See for details +#include "DirectXTexEXR.h" +#endif + +using namespace DirectX; +using namespace DirectX::PackedVector; +using Microsoft::WRL::ComPtr; + +enum OPTIONS +{ + OPT_RECURSIVE = 1, + OPT_WIDTH, + OPT_HEIGHT, + OPT_MIPLEVELS, + OPT_FORMAT, + OPT_FILTER, + OPT_SRGBI, + OPT_SRGBO, + OPT_SRGB, + OPT_PREFIX, + OPT_SUFFIX, + OPT_OUTPUTDIR, + OPT_OVERWRITE, + OPT_FILETYPE, + OPT_HFLIP, + OPT_VFLIP, + OPT_DDS_DWORD_ALIGN, + OPT_DDS_BAD_DXTN_TAILS, + OPT_USE_DX10, + OPT_NOLOGO, + OPT_TIMING, + OPT_SEPALPHA, + OPT_TYPELESS_UNORM, + OPT_TYPELESS_FLOAT, + OPT_PREMUL_ALPHA, + OPT_DEMUL_ALPHA, + OPT_EXPAND_LUMINANCE, + OPT_TA_WRAP, + OPT_TA_MIRROR, + OPT_FORCE_SINGLEPROC, + OPT_GPU, + OPT_NOGPU, + OPT_FEATURE_LEVEL, + OPT_FIT_POWEROF2, + OPT_ALPHA_WEIGHT, + OPT_NORMAL_MAP, + OPT_NORMAL_MAP_AMPLITUDE, + OPT_COMPRESS_UNIFORM, + OPT_COMPRESS_MAX, + OPT_COMPRESS_QUICK, + OPT_COMPRESS_DITHER, + OPT_WIC_QUALITY, + OPT_WIC_LOSSLESS, + OPT_WIC_MULTIFRAME, + OPT_COLORKEY, + OPT_TONEMAP, + OPT_X2_BIAS, + OPT_MAX +}; + +static_assert(OPT_MAX <= 64, "dwOptions is a DWORD64 bitfield"); + +struct SConversion +{ + wchar_t szSrc[MAX_PATH]; + wchar_t szDest[MAX_PATH]; +}; + +struct SValue +{ + LPCWSTR pName; + DWORD dwValue; +}; + + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// + +const SValue g_pOptions[] = +{ + { L"r", OPT_RECURSIVE }, + { L"w", OPT_WIDTH }, + { L"h", OPT_HEIGHT }, + { L"m", OPT_MIPLEVELS }, + { L"f", OPT_FORMAT }, + { L"if", OPT_FILTER }, + { L"srgbi", OPT_SRGBI }, + { L"srgbo", OPT_SRGBO }, + { L"srgb", OPT_SRGB }, + { L"px", OPT_PREFIX }, + { L"sx", OPT_SUFFIX }, + { L"o", OPT_OUTPUTDIR }, + { L"y", OPT_OVERWRITE }, + { L"ft", OPT_FILETYPE }, + { L"hflip", OPT_HFLIP }, + { L"vflip", OPT_VFLIP }, + { L"dword", OPT_DDS_DWORD_ALIGN }, + { L"badtails", OPT_DDS_BAD_DXTN_TAILS }, + { L"dx10", OPT_USE_DX10 }, + { L"nologo", OPT_NOLOGO }, + { L"timing", OPT_TIMING }, + { L"sepalpha", OPT_SEPALPHA }, + { L"tu", OPT_TYPELESS_UNORM }, + { L"tf", OPT_TYPELESS_FLOAT }, + { L"pmalpha", OPT_PREMUL_ALPHA }, + { L"alpha", OPT_DEMUL_ALPHA }, + { L"xlum", OPT_EXPAND_LUMINANCE }, + { L"wrap", OPT_TA_WRAP }, + { L"mirror", OPT_TA_MIRROR }, + { L"singleproc", OPT_FORCE_SINGLEPROC }, + { L"gpu", OPT_GPU }, + { L"nogpu", OPT_NOGPU }, + { L"fl", OPT_FEATURE_LEVEL }, + { L"pow2", OPT_FIT_POWEROF2 }, + { L"aw", OPT_ALPHA_WEIGHT }, + { L"nmap", OPT_NORMAL_MAP }, + { L"nmapamp", OPT_NORMAL_MAP_AMPLITUDE }, + { L"bcuniform", OPT_COMPRESS_UNIFORM }, + { L"bcmax", OPT_COMPRESS_MAX }, + { L"bcquick", OPT_COMPRESS_QUICK }, + { L"bcdither", OPT_COMPRESS_DITHER }, + { L"wicq", OPT_WIC_QUALITY }, + { L"wiclossless", OPT_WIC_LOSSLESS }, + { L"wicmulti", OPT_WIC_MULTIFRAME }, + { L"c", OPT_COLORKEY }, + { L"tonemap", OPT_TONEMAP }, + { L"x2bias", OPT_X2_BIAS }, + { nullptr, 0 } +}; + +#define DEFFMT(fmt) { L#fmt, DXGI_FORMAT_ ## fmt } + +const SValue g_pFormats[] = +{ + // List does not include _TYPELESS or depth/stencil formats + DEFFMT(R32G32B32A32_FLOAT), + DEFFMT(R32G32B32A32_UINT), + DEFFMT(R32G32B32A32_SINT), + DEFFMT(R32G32B32_FLOAT), + DEFFMT(R32G32B32_UINT), + DEFFMT(R32G32B32_SINT), + DEFFMT(R16G16B16A16_FLOAT), + DEFFMT(R16G16B16A16_UNORM), + DEFFMT(R16G16B16A16_UINT), + DEFFMT(R16G16B16A16_SNORM), + DEFFMT(R16G16B16A16_SINT), + DEFFMT(R32G32_FLOAT), + DEFFMT(R32G32_UINT), + DEFFMT(R32G32_SINT), + DEFFMT(R10G10B10A2_UNORM), + DEFFMT(R10G10B10A2_UINT), + DEFFMT(R11G11B10_FLOAT), + DEFFMT(R8G8B8A8_UNORM), + DEFFMT(R8G8B8A8_UNORM_SRGB), + DEFFMT(R8G8B8A8_UINT), + DEFFMT(R8G8B8A8_SNORM), + DEFFMT(R8G8B8A8_SINT), + DEFFMT(R16G16_FLOAT), + DEFFMT(R16G16_UNORM), + DEFFMT(R16G16_UINT), + DEFFMT(R16G16_SNORM), + DEFFMT(R16G16_SINT), + DEFFMT(R32_FLOAT), + DEFFMT(R32_UINT), + DEFFMT(R32_SINT), + DEFFMT(R8G8_UNORM), + DEFFMT(R8G8_UINT), + DEFFMT(R8G8_SNORM), + DEFFMT(R8G8_SINT), + DEFFMT(R16_FLOAT), + DEFFMT(R16_UNORM), + DEFFMT(R16_UINT), + DEFFMT(R16_SNORM), + DEFFMT(R16_SINT), + DEFFMT(R8_UNORM), + DEFFMT(R8_UINT), + DEFFMT(R8_SNORM), + DEFFMT(R8_SINT), + DEFFMT(A8_UNORM), + DEFFMT(R9G9B9E5_SHAREDEXP), + DEFFMT(R8G8_B8G8_UNORM), + DEFFMT(G8R8_G8B8_UNORM), + DEFFMT(BC1_UNORM), + DEFFMT(BC1_UNORM_SRGB), + DEFFMT(BC2_UNORM), + DEFFMT(BC2_UNORM_SRGB), + DEFFMT(BC3_UNORM), + DEFFMT(BC3_UNORM_SRGB), + DEFFMT(BC4_UNORM), + DEFFMT(BC4_SNORM), + DEFFMT(BC5_UNORM), + DEFFMT(BC5_SNORM), + DEFFMT(B5G6R5_UNORM), + DEFFMT(B5G5R5A1_UNORM), + + // DXGI 1.1 formats + DEFFMT(B8G8R8A8_UNORM), + DEFFMT(B8G8R8X8_UNORM), + DEFFMT(R10G10B10_XR_BIAS_A2_UNORM), + DEFFMT(B8G8R8A8_UNORM_SRGB), + DEFFMT(B8G8R8X8_UNORM_SRGB), + DEFFMT(BC6H_UF16), + DEFFMT(BC6H_SF16), + DEFFMT(BC7_UNORM), + DEFFMT(BC7_UNORM_SRGB), + + // DXGI 1.2 formats + DEFFMT(AYUV), + DEFFMT(Y410), + DEFFMT(Y416), + DEFFMT(YUY2), + DEFFMT(Y210), + DEFFMT(Y216), + // No support for legacy paletted video formats (AI44, IA44, P8, A8P8) + DEFFMT(B4G4R4A4_UNORM), + + { nullptr, DXGI_FORMAT_UNKNOWN } +}; + +const SValue g_pReadOnlyFormats[] = +{ + DEFFMT(R32G32B32A32_TYPELESS), + DEFFMT(R32G32B32_TYPELESS), + DEFFMT(R16G16B16A16_TYPELESS), + DEFFMT(R32G32_TYPELESS), + DEFFMT(R32G8X24_TYPELESS), + DEFFMT(D32_FLOAT_S8X24_UINT), + DEFFMT(R32_FLOAT_X8X24_TYPELESS), + DEFFMT(X32_TYPELESS_G8X24_UINT), + DEFFMT(R10G10B10A2_TYPELESS), + DEFFMT(R8G8B8A8_TYPELESS), + DEFFMT(R16G16_TYPELESS), + DEFFMT(R32_TYPELESS), + DEFFMT(D32_FLOAT), + DEFFMT(R24G8_TYPELESS), + DEFFMT(D24_UNORM_S8_UINT), + DEFFMT(R24_UNORM_X8_TYPELESS), + DEFFMT(X24_TYPELESS_G8_UINT), + DEFFMT(R8G8_TYPELESS), + DEFFMT(R16_TYPELESS), + DEFFMT(R8_TYPELESS), + DEFFMT(BC1_TYPELESS), + DEFFMT(BC2_TYPELESS), + DEFFMT(BC3_TYPELESS), + DEFFMT(BC4_TYPELESS), + DEFFMT(BC5_TYPELESS), + + // DXGI 1.1 formats + DEFFMT(B8G8R8A8_TYPELESS), + DEFFMT(B8G8R8X8_TYPELESS), + DEFFMT(BC6H_TYPELESS), + DEFFMT(BC7_TYPELESS), + + // DXGI 1.2 formats + DEFFMT(NV12), + DEFFMT(P010), + DEFFMT(P016), + DEFFMT(420_OPAQUE), + DEFFMT(NV11), + + // DXGI 1.3 formats + { L"P208", DXGI_FORMAT(130) }, + { L"V208", DXGI_FORMAT(131) }, + { L"V408", DXGI_FORMAT(132) }, + + { nullptr, DXGI_FORMAT_UNKNOWN } +}; + +const SValue g_pFilters[] = +{ + { L"POINT", TEX_FILTER_POINT }, + { L"LINEAR", TEX_FILTER_LINEAR }, + { L"CUBIC", TEX_FILTER_CUBIC }, + { L"FANT", TEX_FILTER_FANT }, + { L"BOX", TEX_FILTER_BOX }, + { L"TRIANGLE", TEX_FILTER_TRIANGLE }, + { L"POINT_DITHER", TEX_FILTER_POINT | TEX_FILTER_DITHER }, + { L"LINEAR_DITHER", TEX_FILTER_LINEAR | TEX_FILTER_DITHER }, + { L"CUBIC_DITHER", TEX_FILTER_CUBIC | TEX_FILTER_DITHER }, + { L"FANT_DITHER", TEX_FILTER_FANT | TEX_FILTER_DITHER }, + { L"BOX_DITHER", TEX_FILTER_BOX | TEX_FILTER_DITHER }, + { L"TRIANGLE_DITHER", TEX_FILTER_TRIANGLE | TEX_FILTER_DITHER }, + { L"POINT_DITHER_DIFFUSION", TEX_FILTER_POINT | TEX_FILTER_DITHER_DIFFUSION }, + { L"LINEAR_DITHER_DIFFUSION", TEX_FILTER_LINEAR | TEX_FILTER_DITHER_DIFFUSION }, + { L"CUBIC_DITHER_DIFFUSION", TEX_FILTER_CUBIC | TEX_FILTER_DITHER_DIFFUSION }, + { L"FANT_DITHER_DIFFUSION", TEX_FILTER_FANT | TEX_FILTER_DITHER_DIFFUSION }, + { L"BOX_DITHER_DIFFUSION", TEX_FILTER_BOX | TEX_FILTER_DITHER_DIFFUSION }, + { L"TRIANGLE_DITHER_DIFFUSION", TEX_FILTER_TRIANGLE | TEX_FILTER_DITHER_DIFFUSION }, + { nullptr, TEX_FILTER_DEFAULT } +}; + +#define CODEC_DDS 0xFFFF0001 +#define CODEC_TGA 0xFFFF0002 +#define CODEC_HDP 0xFFFF0003 +#define CODEC_JXR 0xFFFF0004 +#define CODEC_HDR 0xFFFF0005 +#define CODEC_EXR 0xFFFF0006 + +const SValue g_pSaveFileTypes[] = // valid formats to write to +{ + { L"BMP", WIC_CODEC_BMP }, + { L"JPG", WIC_CODEC_JPEG }, + { L"JPEG", WIC_CODEC_JPEG }, + { L"PNG", WIC_CODEC_PNG }, + { L"DDS", CODEC_DDS }, + { L"TGA", CODEC_TGA }, + { L"HDR", CODEC_HDR }, + { L"TIF", WIC_CODEC_TIFF }, + { L"TIFF", WIC_CODEC_TIFF }, + { L"WDP", WIC_CODEC_WMP }, + { L"HDP", CODEC_HDP }, + { L"JXR", CODEC_JXR }, +#ifdef USE_OPENEXR + { L"EXR", CODEC_EXR }, +#endif + { nullptr, CODEC_DDS } +}; + +const SValue g_pFeatureLevels[] = // valid feature levels for -fl for maximimum size +{ + { L"9.1", 2048 }, + { L"9.2", 2048 }, + { L"9.3", 4096 }, + { L"10.0", 8192 }, + { L"10.1", 8192 }, + { L"11.0", 16384 }, + { L"11.1", 16384 }, + { L"12.0", 16384 }, + { L"12.1", 16384 }, + { nullptr, 0 }, +}; + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// + +#pragma warning( disable : 4616 6211 ) + +namespace +{ + inline HANDLE safe_handle(HANDLE h) { return (h == INVALID_HANDLE_VALUE) ? 0 : h; } + + struct find_closer { void operator()(HANDLE h) { assert(h != INVALID_HANDLE_VALUE); if (h) FindClose(h); } }; + + typedef public std::unique_ptr ScopedFindHandle; + + inline static bool ispow2(size_t x) + { + return ((x != 0) && !(x & (x - 1))); + } + +#pragma prefast(disable : 26018, "Only used with static internal arrays") + + DWORD LookupByName(const wchar_t *pName, const SValue *pArray) + { + while (pArray->pName) + { + if (!_wcsicmp(pName, pArray->pName)) + return pArray->dwValue; + + pArray++; + } + + return 0; + } + + + const wchar_t* LookupByValue(DWORD pValue, const SValue *pArray) + { + while (pArray->pName) + { + if (pValue == pArray->dwValue) + return pArray->pName; + + pArray++; + } + + return L""; + } + + + void SearchForFiles(const wchar_t* path, std::list& files, bool recursive) + { + // Process files + WIN32_FIND_DATA findData = {}; + ScopedFindHandle hFile(safe_handle(FindFirstFileExW(path, + FindExInfoBasic, &findData, + FindExSearchNameMatch, nullptr, + FIND_FIRST_EX_LARGE_FETCH))); + if (hFile) + { + for (;;) + { + if (!(findData.dwFileAttributes & (FILE_ATTRIBUTE_HIDDEN | FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_DIRECTORY))) + { + wchar_t drive[_MAX_DRIVE] = {}; + wchar_t dir[_MAX_DIR] = {}; + _wsplitpath_s(path, drive, _MAX_DRIVE, dir, _MAX_DIR, nullptr, 0, nullptr, 0); + + SConversion conv; + _wmakepath_s(conv.szSrc, drive, dir, findData.cFileName, nullptr); + files.push_back(conv); + } + + if (!FindNextFile(hFile.get(), &findData)) + break; + } + } + + // Process directories + if (recursive) + { + wchar_t searchDir[MAX_PATH] = {}; + { + wchar_t drive[_MAX_DRIVE] = {}; + wchar_t dir[_MAX_DIR] = {}; + _wsplitpath_s(path, drive, _MAX_DRIVE, dir, _MAX_DIR, nullptr, 0, nullptr, 0); + _wmakepath_s(searchDir, drive, dir, L"*", nullptr); + } + + hFile.reset(safe_handle(FindFirstFileExW(searchDir, + FindExInfoBasic, &findData, + FindExSearchLimitToDirectories, nullptr, + FIND_FIRST_EX_LARGE_FETCH))); + if (!hFile) + return; + + for (;;) + { + if (findData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) + { + if (findData.cFileName[0] != L'.') + { + wchar_t subdir[MAX_PATH] = {}; + + { + wchar_t drive[_MAX_DRIVE] = {}; + wchar_t dir[_MAX_DIR] = {}; + wchar_t fname[_MAX_FNAME] = {}; + wchar_t ext[_MAX_FNAME] = {}; + _wsplitpath_s(path, drive, dir, fname, ext); + wcscat_s(dir, findData.cFileName); + _wmakepath_s(subdir, drive, dir, fname, ext); + } + + SearchForFiles(subdir, files, recursive); + } + } + + if (!FindNextFile(hFile.get(), &findData)) + break; + } + } + } + + + void PrintFormat(DXGI_FORMAT Format) + { + for (const SValue *pFormat = g_pFormats; pFormat->pName; pFormat++) + { + if ((DXGI_FORMAT)pFormat->dwValue == Format) + { + wprintf(pFormat->pName); + return; + } + } + + for (const SValue *pFormat = g_pReadOnlyFormats; pFormat->pName; pFormat++) + { + if ((DXGI_FORMAT)pFormat->dwValue == Format) + { + wprintf(pFormat->pName); + return; + } + } + + wprintf(L"*UNKNOWN*"); + } + + + void PrintInfo(const TexMetadata& info) + { + wprintf(L" (%Iux%Iu", info.width, info.height); + + if (TEX_DIMENSION_TEXTURE3D == info.dimension) + wprintf(L"x%Iu", info.depth); + + if (info.mipLevels > 1) + wprintf(L",%Iu", info.mipLevels); + + if (info.arraySize > 1) + wprintf(L",%Iu", info.arraySize); + + wprintf(L" "); + PrintFormat(info.format); + + switch (info.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + wprintf((info.arraySize > 1) ? L" 1DArray" : L" 1D"); + break; + + case TEX_DIMENSION_TEXTURE2D: + if (info.IsCubemap()) + { + wprintf((info.arraySize > 6) ? L" CubeArray" : L" Cube"); + } + else + { + wprintf((info.arraySize > 1) ? L" 2DArray" : L" 2D"); + } + break; + + case TEX_DIMENSION_TEXTURE3D: + wprintf(L" 3D"); + break; + } + + switch (info.GetAlphaMode()) + { + case TEX_ALPHA_MODE_OPAQUE: + wprintf(L" \x0e0:Opaque"); + break; + case TEX_ALPHA_MODE_PREMULTIPLIED: + wprintf(L" \x0e0:PM"); + break; + case TEX_ALPHA_MODE_STRAIGHT: + wprintf(L" \x0e0:NonPM"); + break; + } + + wprintf(L")"); + } + + + void PrintList(size_t cch, const SValue *pValue) + { + while (pValue->pName) + { + size_t cchName = wcslen(pValue->pName); + + if (cch + cchName + 2 >= 80) + { + wprintf(L"\n "); + cch = 6; + } + + wprintf(L"%ls ", pValue->pName); + cch += cchName + 2; + pValue++; + } + + wprintf(L"\n"); + } + + + void PrintLogo() + { + wprintf(L"Microsoft (R) DirectX Texture Converter (DirectXTex version)\n"); + wprintf(L"Copyright (C) Microsoft Corp. All rights reserved.\n"); +#ifdef _DEBUG + wprintf(L"*** Debug build ***\n"); +#endif + wprintf(L"\n"); + } + + + _Success_(return != false) + bool GetDXGIFactory(_Outptr_ IDXGIFactory1** pFactory) + { + if (!pFactory) + return false; + + *pFactory = nullptr; + + typedef HRESULT(WINAPI* pfn_CreateDXGIFactory1)(REFIID riid, _Out_ void **ppFactory); + + static pfn_CreateDXGIFactory1 s_CreateDXGIFactory1 = nullptr; + + if (!s_CreateDXGIFactory1) + { + HMODULE hModDXGI = LoadLibrary(L"dxgi.dll"); + if (!hModDXGI) + return false; + + s_CreateDXGIFactory1 = reinterpret_cast(reinterpret_cast(GetProcAddress(hModDXGI, "CreateDXGIFactory1"))); + if (!s_CreateDXGIFactory1) + return false; + } + + return SUCCEEDED(s_CreateDXGIFactory1(IID_PPV_ARGS(pFactory))); + } + + + void PrintUsage() + { + PrintLogo(); + + wprintf(L"Usage: texconv \n\n"); + wprintf(L" -r wildcard filename search is recursive\n"); + wprintf(L" -w width\n"); + wprintf(L" -h height\n"); + wprintf(L" -m miplevels\n"); + wprintf(L" -f format\n"); + wprintf(L" -if image filtering\n"); + wprintf(L" -srgb{i|o} sRGB {input, output}\n"); + wprintf(L" -px name prefix\n"); + wprintf(L" -sx name suffix\n"); + wprintf(L" -o output directory\n"); + wprintf(L" -y overwrite existing output file (if any)\n"); + wprintf(L" -ft output file type\n"); + wprintf(L" -hflip horizonal flip of source image\n"); + wprintf(L" -vflip vertical flip of source image\n"); + wprintf(L" -sepalpha resize/generate mips alpha channel separately\n"); + wprintf(L" from color channels\n"); + wprintf(L" -wrap, -mirror texture addressing mode (wrap, mirror, or clamp)\n"); + wprintf(L" -pmalpha convert final texture to use premultiplied alpha\n"); + wprintf(L" -alpha convert premultiplied alpha to straight alpha\n"); + wprintf(L" -pow2 resize to fit a power-of-2, respecting aspect ratio\n"); + wprintf( + L" -nmap converts height-map to normal-map\n" + L" options must be one or more of\n" + L" r, g, b, a, l, m, u, v, i, o\n"); + wprintf(L" -nmapamp normal map amplitude (defaults to 1.0)\n"); + wprintf(L" -fl Set maximum feature level target (defaults to 11.0)\n"); + wprintf(L"\n (DDS input only)\n"); + wprintf(L" -t{u|f} TYPELESS format is treated as UNORM or FLOAT\n"); + wprintf(L" -dword Use DWORD instead of BYTE alignment\n"); + wprintf(L" -badtails Fix for older DXTn with bad mipchain tails\n"); + wprintf(L" -xlum expand legacy L8, L16, and A8P8 formats\n"); + wprintf(L"\n (DDS output only)\n"); + wprintf(L" -dx10 Force use of 'DX10' extended header\n"); + wprintf(L"\n -nologo suppress copyright message\n"); + wprintf(L" -timing Display elapsed processing time\n\n"); +#ifdef _OPENMP + wprintf(L" -singleproc Do not use multi-threaded compression\n"); +#endif + wprintf(L" -gpu Select GPU for DirectCompute-based codecs (0 is default)\n"); + wprintf(L" -nogpu Do not use DirectCompute-based codecs\n"); + wprintf(L" -bcuniform Use uniform rather than perceptual weighting for BC1-3\n"); + wprintf(L" -bcdither Use dithering for BC1-3\n"); + wprintf(L" -bcmax Use exhaustive compression (BC7 only)\n"); + wprintf(L" -bcquick Use quick compression (BC7 only)\n"); + wprintf(L" -wicq When writing images with WIC use quality (0.0 to 1.0)\n"); + wprintf(L" -wiclossless When writing images with WIC use lossless mode\n"); + wprintf(L" -wicmulti When writing images with WIC encode multiframe images\n"); + wprintf( + L" -aw BC7 GPU compressor weighting for alpha error metric\n" + L" (defaults to 1.0)\n"); + wprintf(L" -c colorkey (a.k.a. chromakey) transparency\n"); + wprintf(L" -tonemap Apply a tonemap operator based on maximum luminance\n"); + wprintf(L" -x2bias Enable *2 - 1 conversion cases for unorm/pos-only-float\n"); + + wprintf(L"\n : "); + PrintList(13, g_pFormats); + + wprintf(L"\n : "); + PrintList(13, g_pFilters); + + wprintf(L"\n : "); + PrintList(15, g_pSaveFileTypes); + + wprintf(L"\n : "); + PrintList(13, g_pFeatureLevels); + + ComPtr dxgiFactory; + if (GetDXGIFactory(dxgiFactory.GetAddressOf())) + { + wprintf(L"\n :\n"); + + ComPtr adapter; + for (UINT adapterIndex = 0; DXGI_ERROR_NOT_FOUND != dxgiFactory->EnumAdapters(adapterIndex, adapter.ReleaseAndGetAddressOf()); ++adapterIndex) + { + DXGI_ADAPTER_DESC desc; + if (SUCCEEDED(adapter->GetDesc(&desc))) + { + wprintf(L" %u: VID:%04X, PID:%04X - %ls\n", adapterIndex, desc.VendorId, desc.DeviceId, desc.Description); + } + } + } + } + + + _Success_(return != false) + bool CreateDevice(int adapter, _Outptr_ ID3D11Device** pDevice) + { + if (!pDevice) + return false; + + *pDevice = nullptr; + + static PFN_D3D11_CREATE_DEVICE s_DynamicD3D11CreateDevice = nullptr; + + if (!s_DynamicD3D11CreateDevice) + { + HMODULE hModD3D11 = LoadLibrary(L"d3d11.dll"); + if (!hModD3D11) + return false; + + s_DynamicD3D11CreateDevice = reinterpret_cast(reinterpret_cast(GetProcAddress(hModD3D11, "D3D11CreateDevice"))); + if (!s_DynamicD3D11CreateDevice) + return false; + } + + D3D_FEATURE_LEVEL featureLevels[] = + { + D3D_FEATURE_LEVEL_11_0, + D3D_FEATURE_LEVEL_10_1, + D3D_FEATURE_LEVEL_10_0, + }; + + UINT createDeviceFlags = 0; +#ifdef _DEBUG + createDeviceFlags |= D3D11_CREATE_DEVICE_DEBUG; +#endif + + ComPtr pAdapter; + if (adapter >= 0) + { + ComPtr dxgiFactory; + if (GetDXGIFactory(dxgiFactory.GetAddressOf())) + { + if (FAILED(dxgiFactory->EnumAdapters(adapter, pAdapter.GetAddressOf()))) + { + wprintf(L"\nERROR: Invalid GPU adapter index (%d)!\n", adapter); + return false; + } + } + } + + D3D_FEATURE_LEVEL fl; + HRESULT hr = s_DynamicD3D11CreateDevice(pAdapter.Get(), + (pAdapter) ? D3D_DRIVER_TYPE_UNKNOWN : D3D_DRIVER_TYPE_HARDWARE, + nullptr, createDeviceFlags, featureLevels, _countof(featureLevels), + D3D11_SDK_VERSION, pDevice, &fl, nullptr); + if (SUCCEEDED(hr)) + { + if (fl < D3D_FEATURE_LEVEL_11_0) + { + D3D11_FEATURE_DATA_D3D10_X_HARDWARE_OPTIONS hwopts; + hr = (*pDevice)->CheckFeatureSupport(D3D11_FEATURE_D3D10_X_HARDWARE_OPTIONS, &hwopts, sizeof(hwopts)); + if (FAILED(hr)) + memset(&hwopts, 0, sizeof(hwopts)); + + if (!hwopts.ComputeShaders_Plus_RawAndStructuredBuffers_Via_Shader_4_x) + { + if (*pDevice) + { + (*pDevice)->Release(); + *pDevice = nullptr; + } + hr = HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } + } + + if (SUCCEEDED(hr)) + { + ComPtr dxgiDevice; + hr = (*pDevice)->QueryInterface(IID_PPV_ARGS(dxgiDevice.GetAddressOf())); + if (SUCCEEDED(hr)) + { + hr = dxgiDevice->GetAdapter(pAdapter.ReleaseAndGetAddressOf()); + if (SUCCEEDED(hr)) + { + DXGI_ADAPTER_DESC desc; + hr = pAdapter->GetDesc(&desc); + if (SUCCEEDED(hr)) + { + wprintf(L"\n[Using DirectCompute on \"%ls\"]\n", desc.Description); + } + } + } + + return true; + } + else + return false; + } + + + void FitPowerOf2(size_t origx, size_t origy, size_t& targetx, size_t& targety, size_t maxsize) + { + float origAR = float(origx) / float(origy); + + if (origx > origy) + { + size_t x; + for (x = maxsize; x > 1; x >>= 1) { if (x <= targetx) break; }; + targetx = x; + + float bestScore = FLT_MAX; + for (size_t y = maxsize; y > 0; y >>= 1) + { + float score = fabs((float(x) / float(y)) - origAR); + if (score < bestScore) + { + bestScore = score; + targety = y; + } + } + } + else + { + size_t y; + for (y = maxsize; y > 1; y >>= 1) { if (y <= targety) break; }; + targety = y; + + float bestScore = FLT_MAX; + for (size_t x = maxsize; x > 0; x >>= 1) + { + float score = fabs((float(x) / float(y)) - origAR); + if (score < bestScore) + { + bestScore = score; + targetx = x; + } + } + } + } +} + + +//-------------------------------------------------------------------------------------- +// Entry-point +//-------------------------------------------------------------------------------------- +#pragma prefast(disable : 28198, "Command-line tool, frees all memory on exit") + +int __cdecl wmain(_In_ int argc, _In_z_count_(argc) wchar_t* argv[]) +{ + // Parameters and defaults + size_t width = 0; + size_t height = 0; + size_t mipLevels = 0; + DXGI_FORMAT format = DXGI_FORMAT_UNKNOWN; + DWORD dwFilter = TEX_FILTER_DEFAULT; + DWORD dwSRGB = 0; + DWORD dwConvert = 0; + DWORD dwCompress = TEX_COMPRESS_DEFAULT; + DWORD dwFilterOpts = 0; + DWORD FileType = CODEC_DDS; + DWORD maxSize = 16384; + int adapter = -1; + float alphaWeight = 1.f; + DWORD dwNormalMap = 0; + float nmapAmplitude = 1.f; + float wicQuality = -1.f; + DWORD colorKey = 0; + + wchar_t szPrefix[MAX_PATH]; + wchar_t szSuffix[MAX_PATH]; + wchar_t szOutputDir[MAX_PATH]; + + szPrefix[0] = 0; + szSuffix[0] = 0; + szOutputDir[0] = 0; + + // Initialize COM (needed for WIC) + HRESULT hr = CoInitializeEx(nullptr, COINIT_MULTITHREADED); + if (FAILED(hr)) + { + wprintf(L"Failed to initialize COM (%08X)\n", hr); + return 1; + } + + // Process command line + DWORD64 dwOptions = 0; + std::list conversion; + + for (int iArg = 1; iArg < argc; iArg++) + { + PWSTR pArg = argv[iArg]; + + if (('-' == pArg[0]) || ('/' == pArg[0])) + { + pArg++; + PWSTR pValue; + + for (pValue = pArg; *pValue && (':' != *pValue); pValue++); + + if (*pValue) + *pValue++ = 0; + + DWORD dwOption = LookupByName(pArg, g_pOptions); + + if (!dwOption || (dwOptions & (DWORD64(1) << dwOption))) + { + PrintUsage(); + return 1; + } + + dwOptions |= (DWORD64(1) << dwOption); + + // Handle options with additional value parameter + switch (dwOption) + { + case OPT_WIDTH: + case OPT_HEIGHT: + case OPT_MIPLEVELS: + case OPT_FORMAT: + case OPT_FILTER: + case OPT_PREFIX: + case OPT_SUFFIX: + case OPT_OUTPUTDIR: + case OPT_FILETYPE: + case OPT_GPU: + case OPT_FEATURE_LEVEL: + case OPT_ALPHA_WEIGHT: + case OPT_NORMAL_MAP: + case OPT_NORMAL_MAP_AMPLITUDE: + case OPT_WIC_QUALITY: + case OPT_COLORKEY: + if (!*pValue) + { + if ((iArg + 1 >= argc)) + { + PrintUsage(); + return 1; + } + + iArg++; + pValue = argv[iArg]; + } + break; + } + + switch (dwOption) + { + case OPT_WIDTH: + if (swscanf_s(pValue, L"%Iu", &width) != 1) + { + wprintf(L"Invalid value specified with -w (%ls)\n", pValue); + wprintf(L"\n"); + PrintUsage(); + return 1; + } + break; + + case OPT_HEIGHT: + if (swscanf_s(pValue, L"%Iu", &height) != 1) + { + wprintf(L"Invalid value specified with -h (%ls)\n", pValue); + printf("\n"); + PrintUsage(); + return 1; + } + break; + + case OPT_MIPLEVELS: + if (swscanf_s(pValue, L"%Iu", &mipLevels) != 1) + { + wprintf(L"Invalid value specified with -m (%ls)\n", pValue); + wprintf(L"\n"); + PrintUsage(); + return 1; + } + break; + + case OPT_FORMAT: + format = (DXGI_FORMAT)LookupByName(pValue, g_pFormats); + if (!format) + { + wprintf(L"Invalid value specified with -f (%ls)\n", pValue); + wprintf(L"\n"); + PrintUsage(); + return 1; + } + break; + + case OPT_FILTER: + dwFilter = LookupByName(pValue, g_pFilters); + if (!dwFilter) + { + wprintf(L"Invalid value specified with -if (%ls)\n", pValue); + wprintf(L"\n"); + PrintUsage(); + return 1; + } + break; + + case OPT_SRGBI: + dwSRGB |= TEX_FILTER_SRGB_IN; + break; + + case OPT_SRGBO: + dwSRGB |= TEX_FILTER_SRGB_OUT; + break; + + case OPT_SRGB: + dwSRGB |= TEX_FILTER_SRGB; + break; + + case OPT_SEPALPHA: + dwFilterOpts |= TEX_FILTER_SEPARATE_ALPHA; + break; + + case OPT_PREFIX: + wcscpy_s(szPrefix, MAX_PATH, pValue); + break; + + case OPT_SUFFIX: + wcscpy_s(szSuffix, MAX_PATH, pValue); + break; + + case OPT_OUTPUTDIR: + wcscpy_s(szOutputDir, MAX_PATH, pValue); + break; + + case OPT_FILETYPE: + FileType = LookupByName(pValue, g_pSaveFileTypes); + if (!FileType) + { + wprintf(L"Invalid value specified with -ft (%ls)\n", pValue); + wprintf(L"\n"); + PrintUsage(); + return 1; + } + break; + + case OPT_PREMUL_ALPHA: + if (dwOptions & (DWORD64(1) << OPT_DEMUL_ALPHA)) + { + wprintf(L"Can't use -pmalpha and -alpha at same time\n\n"); + PrintUsage(); + return 1; + } + break; + + case OPT_DEMUL_ALPHA: + if (dwOptions & (DWORD64(1) << OPT_PREMUL_ALPHA)) + { + wprintf(L"Can't use -pmalpha and -alpha at same time\n\n"); + PrintUsage(); + return 1; + } + break; + + case OPT_TA_WRAP: + if (dwFilterOpts & TEX_FILTER_MIRROR) + { + wprintf(L"Can't use -wrap and -mirror at same time\n\n"); + PrintUsage(); + return 1; + } + dwFilterOpts |= TEX_FILTER_WRAP; + break; + + case OPT_TA_MIRROR: + if (dwFilterOpts & TEX_FILTER_WRAP) + { + wprintf(L"Can't use -wrap and -mirror at same time\n\n"); + PrintUsage(); + return 1; + } + dwFilterOpts |= TEX_FILTER_MIRROR; + break; + + case OPT_NORMAL_MAP: + { + dwNormalMap = 0; + + if (wcschr(pValue, L'l')) + { + dwNormalMap |= CNMAP_CHANNEL_LUMINANCE; + } + else if (wcschr(pValue, L'r')) + { + dwNormalMap |= CNMAP_CHANNEL_RED; + } + else if (wcschr(pValue, L'g')) + { + dwNormalMap |= CNMAP_CHANNEL_GREEN; + } + else if (wcschr(pValue, L'b')) + { + dwNormalMap |= CNMAP_CHANNEL_BLUE; + } + else if (wcschr(pValue, L'a')) + { + dwNormalMap |= CNMAP_CHANNEL_ALPHA; + } + else + { + wprintf(L"Invalid value specified for -nmap (%ls), missing l, r, g, b, or a\n\n", pValue); + PrintUsage(); + return 1; + } + + if (wcschr(pValue, L'm')) + { + dwNormalMap |= CNMAP_MIRROR; + } + else + { + if (wcschr(pValue, L'u')) + { + dwNormalMap |= CNMAP_MIRROR_U; + } + if (wcschr(pValue, L'v')) + { + dwNormalMap |= CNMAP_MIRROR_V; + } + } + + if (wcschr(pValue, L'i')) + { + dwNormalMap |= CNMAP_INVERT_SIGN; + } + + if (wcschr(pValue, L'o')) + { + dwNormalMap |= CNMAP_COMPUTE_OCCLUSION; + } + } + break; + + case OPT_NORMAL_MAP_AMPLITUDE: + if (!dwNormalMap) + { + wprintf(L"-nmapamp requires -nmap\n\n"); + PrintUsage(); + return 1; + } + else if (swscanf_s(pValue, L"%f", &nmapAmplitude) != 1) + { + wprintf(L"Invalid value specified with -nmapamp (%ls)\n\n", pValue); + PrintUsage(); + return 1; + } + else if (nmapAmplitude < 0.f) + { + wprintf(L"Normal map amplitude must be positive (%ls)\n\n", pValue); + PrintUsage(); + return 1; + } + break; + + case OPT_GPU: + if (swscanf_s(pValue, L"%d", &adapter) != 1) + { + wprintf(L"Invalid value specified with -gpu (%ls)\n\n", pValue); + PrintUsage(); + return 1; + } + else if (adapter < 0) + { + wprintf(L"Adapter index (%ls)\n\n", pValue); + PrintUsage(); + return 1; + } + break; + + case OPT_FEATURE_LEVEL: + maxSize = LookupByName(pValue, g_pFeatureLevels); + if (!maxSize) + { + wprintf(L"Invalid value specified with -fl (%ls)\n", pValue); + wprintf(L"\n"); + PrintUsage(); + return 1; + } + break; + + case OPT_ALPHA_WEIGHT: + if (swscanf_s(pValue, L"%f", &alphaWeight) != 1) + { + wprintf(L"Invalid value specified with -aw (%ls)\n", pValue); + wprintf(L"\n"); + PrintUsage(); + return 1; + } + else if (alphaWeight < 0.f) + { + wprintf(L"-aw (%ls) parameter must be positive\n", pValue); + wprintf(L"\n"); + return 1; + } + break; + + case OPT_COMPRESS_UNIFORM: + dwCompress |= TEX_COMPRESS_UNIFORM; + break; + + case OPT_COMPRESS_MAX: + if (dwCompress & TEX_COMPRESS_BC7_QUICK) + { + wprintf(L"Can't use -bcmax and -bcquick at same time\n\n"); + PrintUsage(); + return 1; + } + dwCompress |= TEX_COMPRESS_BC7_USE_3SUBSETS; + break; + + case OPT_COMPRESS_QUICK: + if (dwCompress & TEX_COMPRESS_BC7_USE_3SUBSETS) + { + wprintf(L"Can't use -bcmax and -bcquick at same time\n\n"); + PrintUsage(); + return 1; + } + dwCompress |= TEX_COMPRESS_BC7_QUICK; + break; + + case OPT_COMPRESS_DITHER: + dwCompress |= TEX_COMPRESS_DITHER; + break; + + case OPT_WIC_QUALITY: + if (swscanf_s(pValue, L"%f", &wicQuality) != 1 + || (wicQuality < 0.f) + || (wicQuality > 1.f)) + { + wprintf(L"Invalid value specified with -wicq (%ls)\n", pValue); + printf("\n"); + PrintUsage(); + return 1; + } + break; + + case OPT_COLORKEY: + if (swscanf_s(pValue, L"%x", &colorKey) != 1) + { + printf("Invalid value specified with -c (%ls)\n", pValue); + printf("\n"); + PrintUsage(); + return 1; + } + colorKey &= 0xFFFFFF; + break; + + case OPT_X2_BIAS: + dwConvert |= TEX_FILTER_FLOAT_X2BIAS; + break; + } + } + else if (wcspbrk(pArg, L"?*") != nullptr) + { + size_t count = conversion.size(); + SearchForFiles(pArg, conversion, (dwOptions & (DWORD64(1) << OPT_RECURSIVE)) != 0); + if (conversion.size() <= count) + { + wprintf(L"No matching files found for %ls\n", pArg); + return 1; + } + } + else + { + SConversion conv; + wcscpy_s(conv.szSrc, MAX_PATH, pArg); + + conv.szDest[0] = 0; + + conversion.push_back(conv); + } + } + + if (conversion.empty()) + { + PrintUsage(); + return 0; + } + + if (~dwOptions & (DWORD64(1) << OPT_NOLOGO)) + PrintLogo(); + + // Work out out filename prefix and suffix + if (szOutputDir[0] && (L'\\' != szOutputDir[wcslen(szOutputDir) - 1])) + wcscat_s(szOutputDir, MAX_PATH, L"\\"); + + if (szPrefix[0]) + wcscat_s(szOutputDir, MAX_PATH, szPrefix); + + wcscpy_s(szPrefix, MAX_PATH, szOutputDir); + + const wchar_t* fileTypeName = LookupByValue(FileType, g_pSaveFileTypes); + + if (fileTypeName) + { + wcscat_s(szSuffix, MAX_PATH, L"."); + wcscat_s(szSuffix, MAX_PATH, fileTypeName); + } + else + { + wcscat_s(szSuffix, MAX_PATH, L".unknown"); + } + + if (FileType != CODEC_DDS) + { + mipLevels = 1; + } + + LARGE_INTEGER qpcFreq; + if (!QueryPerformanceFrequency(&qpcFreq)) + { + qpcFreq.QuadPart = 0; + } + + + LARGE_INTEGER qpcStart; + if (!QueryPerformanceCounter(&qpcStart)) + { + qpcStart.QuadPart = 0; + } + + // Convert images + bool nonpow2warn = false; + bool non4bc = false; + ComPtr pDevice; + + for (auto pConv = conversion.begin(); pConv != conversion.end(); ++pConv) + { + if (pConv != conversion.begin()) + wprintf(L"\n"); + + // Load source image + wprintf(L"reading %ls", pConv->szSrc); + fflush(stdout); + + wchar_t ext[_MAX_EXT]; + wchar_t fname[_MAX_FNAME]; + _wsplitpath_s(pConv->szSrc, nullptr, 0, nullptr, 0, fname, _MAX_FNAME, ext, _MAX_EXT); + + TexMetadata info; + std::unique_ptr image(new (std::nothrow) ScratchImage); + + if (!image) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + if (_wcsicmp(ext, L".dds") == 0) + { + DWORD ddsFlags = DDS_FLAGS_NONE; + if (dwOptions & (DWORD64(1) << OPT_DDS_DWORD_ALIGN)) + ddsFlags |= DDS_FLAGS_LEGACY_DWORD; + if (dwOptions & (DWORD64(1) << OPT_EXPAND_LUMINANCE)) + ddsFlags |= DDS_FLAGS_EXPAND_LUMINANCE; + if (dwOptions & (DWORD64(1) << OPT_DDS_BAD_DXTN_TAILS)) + ddsFlags |= DDS_FLAGS_BAD_DXTN_TAILS; + + hr = LoadFromDDSFile(pConv->szSrc, ddsFlags, &info, *image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + continue; + } + + if (IsTypeless(info.format)) + { + if (dwOptions & (DWORD64(1) << OPT_TYPELESS_UNORM)) + { + info.format = MakeTypelessUNORM(info.format); + } + else if (dwOptions & (DWORD64(1) << OPT_TYPELESS_FLOAT)) + { + info.format = MakeTypelessFLOAT(info.format); + } + + if (IsTypeless(info.format)) + { + wprintf(L" FAILED due to Typeless format %d\n", info.format); + continue; + } + + image->OverrideFormat(info.format); + } + } + else if (_wcsicmp(ext, L".tga") == 0) + { + hr = LoadFromTGAFile(pConv->szSrc, &info, *image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + continue; + } + } + else if (_wcsicmp(ext, L".hdr") == 0) + { + hr = LoadFromHDRFile(pConv->szSrc, &info, *image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + continue; + } + } +#ifdef USE_OPENEXR + else if (_wcsicmp(ext, L".exr") == 0) + { + hr = LoadFromEXRFile(pConv->szSrc, &info, *image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + continue; + } + } +#endif + else + { + // WIC shares the same filter values for mode and dither + static_assert(WIC_FLAGS_DITHER == TEX_FILTER_DITHER, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_DITHER_DIFFUSION == TEX_FILTER_DITHER_DIFFUSION, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_POINT == TEX_FILTER_POINT, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_LINEAR == TEX_FILTER_LINEAR, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_CUBIC == TEX_FILTER_CUBIC, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_FANT == TEX_FILTER_FANT, "WIC_FLAGS_* & TEX_FILTER_* should match"); + + DWORD wicFlags = dwFilter; + if (FileType == CODEC_DDS) + wicFlags |= WIC_FLAGS_ALL_FRAMES; + + hr = LoadFromWICFile(pConv->szSrc, wicFlags, &info, *image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + continue; + } + } + + PrintInfo(info); + + size_t tMips = (!mipLevels && info.mipLevels > 1) ? info.mipLevels : mipLevels; + + bool sizewarn = false; + + size_t twidth = (!width) ? info.width : width; + if (twidth > maxSize) + { + if (!width) + twidth = maxSize; + else + sizewarn = true; + } + + size_t theight = (!height) ? info.height : height; + if (theight > maxSize) + { + if (!height) + theight = maxSize; + else + sizewarn = true; + } + + if (sizewarn) + { + wprintf(L"\nWARNING: Target size exceeds maximum size for feature level (%u)\n", maxSize); + } + + if (dwOptions & (DWORD64(1) << OPT_FIT_POWEROF2)) + { + FitPowerOf2(info.width, info.height, twidth, theight, maxSize); + } + + // Convert texture + wprintf(L" as"); + fflush(stdout); + + // --- Planar ------------------------------------------------------------------ + if (IsPlanar(info.format)) + { + auto img = image->GetImage(0, 0, 0); + assert(img); + size_t nimg = image->GetImageCount(); + + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = ConvertToSinglePlane(img, nimg, info, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [converttosingleplane] (%x)\n", hr); + continue; + } + + auto& tinfo = timage->GetMetadata(); + + info.format = tinfo.format; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + } + + DXGI_FORMAT tformat = (format == DXGI_FORMAT_UNKNOWN) ? info.format : format; + + // --- Decompress -------------------------------------------------------------- + std::unique_ptr cimage; + if (IsCompressed(info.format)) + { + auto img = image->GetImage(0, 0, 0); + assert(img); + size_t nimg = image->GetImageCount(); + + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = Decompress(img, nimg, info, DXGI_FORMAT_UNKNOWN /* picks good default */, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [decompress] (%x)\n", hr); + continue; + } + + auto& tinfo = timage->GetMetadata(); + + info.format = tinfo.format; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + if (FileType == CODEC_DDS) + { + // Keep the original compressed image in case we can reuse it + cimage.reset(image.release()); + image.reset(timage.release()); + } + else + { + image.swap(timage); + } + } + + // --- Undo Premultiplied Alpha (if requested) --------------------------------- + if ((dwOptions & (DWORD64(1) << OPT_DEMUL_ALPHA)) + && HasAlpha(info.format) + && info.format != DXGI_FORMAT_A8_UNORM) + { + if (info.GetAlphaMode() == TEX_ALPHA_MODE_STRAIGHT) + { + printf("\nWARNING: Image is already using straight alpha\n"); + } + else if (!info.IsPMAlpha()) + { + printf("\nWARNING: Image is not using premultipled alpha\n"); + } + else + { + auto img = image->GetImage(0, 0, 0); + assert(img); + size_t nimg = image->GetImageCount(); + + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = PremultiplyAlpha(img, nimg, info, TEX_PMALPHA_REVERSE | dwSRGB, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [demultiply alpha] (%x)\n", hr); + continue; + } + + auto& tinfo = timage->GetMetadata(); + info.miscFlags2 = tinfo.miscFlags2; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + cimage.reset(); + } + } + + // --- Flip/Rotate ------------------------------------------------------------- + if (dwOptions & ((DWORD64(1) << OPT_HFLIP) | (DWORD64(1) << OPT_VFLIP))) + { + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + DWORD dwFlags = 0; + + if (dwOptions & (DWORD64(1) << OPT_HFLIP)) + dwFlags |= TEX_FR_FLIP_HORIZONTAL; + + if (dwOptions & (DWORD64(1) << OPT_VFLIP)) + dwFlags |= TEX_FR_FLIP_VERTICAL; + + assert(dwFlags != 0); + + hr = FlipRotate(image->GetImages(), image->GetImageCount(), image->GetMetadata(), dwFlags, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [fliprotate] (%x)\n", hr); + return 1; + } + + auto& tinfo = timage->GetMetadata(); + + assert(tinfo.width == twidth && tinfo.height == theight); + + info.width = tinfo.width; + info.height = tinfo.height; + + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.format == tinfo.format); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + cimage.reset(); + } + + // --- Resize ------------------------------------------------------------------ + if (info.width != twidth || info.height != theight) + { + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = Resize(image->GetImages(), image->GetImageCount(), image->GetMetadata(), twidth, theight, dwFilter | dwFilterOpts, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [resize] (%x)\n", hr); + return 1; + } + + auto& tinfo = timage->GetMetadata(); + + assert(tinfo.width == twidth && tinfo.height == theight && tinfo.mipLevels == 1); + info.width = tinfo.width; + info.height = tinfo.height; + info.mipLevels = 1; + + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.format == tinfo.format); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + cimage.reset(); + } + + // --- Tonemap (if requested) -------------------------------------------------- + if (dwOptions & DWORD64(1) << OPT_TONEMAP) + { + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + // Compute max luminosity across all images + XMVECTOR maxLum = XMVectorZero(); + hr = EvaluateImage(image->GetImages(), image->GetImageCount(), image->GetMetadata(), + [&](const XMVECTOR* pixels, size_t width, size_t y) + { + UNREFERENCED_PARAMETER(y); + + for (size_t j = 0; j < width; ++j) + { + static const XMVECTORF32 s_luminance = { 0.3f, 0.59f, 0.11f, 0.f }; + + XMVECTOR v = *pixels++; + + v = XMVector3Dot(v, s_luminance); + + maxLum = XMVectorMax(v, maxLum); + } + }); + if (FAILED(hr)) + { + wprintf(L" FAILED [tonemap maxlum] (%x)\n", hr); + return 1; + } + + // Reinhard et al, "Photographic Tone Reproduction for Digital Images" + // http://www.cs.utah.edu/~reinhard/cdrom/ + maxLum = XMVectorMultiply(maxLum, maxLum); + + hr = TransformImage(image->GetImages(), image->GetImageCount(), image->GetMetadata(), + [&](XMVECTOR* outPixels, const XMVECTOR* inPixels, size_t width, size_t y) + { + UNREFERENCED_PARAMETER(y); + + for (size_t j = 0; j < width; ++j) + { + XMVECTOR value = inPixels[j]; + + XMVECTOR scale = XMVectorDivide( + XMVectorAdd(g_XMOne, XMVectorDivide(value, maxLum)), + XMVectorAdd(g_XMOne, value)); + XMVECTOR nvalue = XMVectorMultiply(value, scale); + + value = XMVectorSelect(value, nvalue, g_XMSelect1110); + + outPixels[j] = value; + } + }, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [tonemap apply] (%x)\n", hr); + return 1; + } + + auto& tinfo = timage->GetMetadata(); + tinfo; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.format == tinfo.format); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + cimage.reset(); + } + + // --- Convert ----------------------------------------------------------------- + if (dwOptions & (DWORD64(1) << OPT_NORMAL_MAP)) + { + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + DXGI_FORMAT nmfmt = tformat; + if (IsCompressed(tformat)) + { + nmfmt = (dwNormalMap & CNMAP_COMPUTE_OCCLUSION) ? DXGI_FORMAT_R32G32B32A32_FLOAT : DXGI_FORMAT_R32G32B32_FLOAT; + } + + hr = ComputeNormalMap(image->GetImages(), image->GetImageCount(), image->GetMetadata(), dwNormalMap, nmapAmplitude, nmfmt, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [normalmap] (%x)\n", hr); + return 1; + } + + auto& tinfo = timage->GetMetadata(); + + assert(tinfo.format == nmfmt); + info.format = tinfo.format; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + cimage.reset(); + } + else if (info.format != tformat && !IsCompressed(tformat)) + { + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = Convert(image->GetImages(), image->GetImageCount(), image->GetMetadata(), tformat, + dwFilter | dwFilterOpts | dwSRGB | dwConvert, TEX_THRESHOLD_DEFAULT, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [convert] (%x)\n", hr); + return 1; + } + + auto& tinfo = timage->GetMetadata(); + + assert(tinfo.format == tformat); + info.format = tinfo.format; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + cimage.reset(); + } + + // --- ColorKey/ChromaKey ------------------------------------------------------ + if ((dwOptions & (DWORD64(1) << OPT_COLORKEY)) + && HasAlpha(info.format)) + { + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + XMVECTOR colorKeyValue = XMLoadColor(reinterpret_cast(&colorKey)); + + hr = TransformImage(image->GetImages(), image->GetImageCount(), image->GetMetadata(), + [&](XMVECTOR* outPixels, const XMVECTOR* inPixels, size_t width, size_t y) + { + static const XMVECTORF32 s_tolerance = { 0.2f, 0.2f, 0.2f, 0.f }; + + UNREFERENCED_PARAMETER(y); + + for (size_t j = 0; j < width; ++j) + { + XMVECTOR value = inPixels[j]; + + if (XMVector3NearEqual(value, colorKeyValue, s_tolerance)) + { + value = g_XMZero; + } + else + { + value = XMVectorSelect(g_XMOne, value, g_XMSelect1110); + } + + outPixels[j] = value; + } + }, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [colorkey] (%x)\n", hr); + return 1; + } + + auto& tinfo = timage->GetMetadata(); + tinfo; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.format == tinfo.format); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + cimage.reset(); + } + + // --- Generate mips ----------------------------------------------------------- + if (!ispow2(info.width) || !ispow2(info.height) || !ispow2(info.depth)) + { + if (info.dimension == TEX_DIMENSION_TEXTURE3D) + { + if (!tMips) + { + tMips = 1; + } + else + { + wprintf(L"\nERROR: Cannot generate mips for non-power-of-2 volume textures\n"); + return 1; + } + } + else if (!tMips || info.mipLevels != 1) + { + nonpow2warn = true; + } + } + + if ((!tMips || info.mipLevels != tMips) && (info.mipLevels != 1)) + { + // Mips generation only works on a single base image, so strip off existing mip levels + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + TexMetadata mdata = info; + mdata.mipLevels = 1; + hr = timage->Initialize(mdata); + if (FAILED(hr)) + { + wprintf(L" FAILED [copy to single level] (%x)\n", hr); + return 1; + } + + if (info.dimension == TEX_DIMENSION_TEXTURE3D) + { + for (size_t d = 0; d < info.depth; ++d) + { + hr = CopyRectangle(*image->GetImage(0, 0, d), Rect(0, 0, info.width, info.height), + *timage->GetImage(0, 0, d), TEX_FILTER_DEFAULT, 0, 0); + if (FAILED(hr)) + { + wprintf(L" FAILED [copy to single level] (%x)\n", hr); + return 1; + } + } + } + else + { + for (size_t i = 0; i < info.arraySize; ++i) + { + hr = CopyRectangle(*image->GetImage(0, i, 0), Rect(0, 0, info.width, info.height), + *timage->GetImage(0, i, 0), TEX_FILTER_DEFAULT, 0, 0); + if (FAILED(hr)) + { + wprintf(L" FAILED [copy to single level] (%x)\n", hr); + return 1; + } + } + } + + image.swap(timage); + info.mipLevels = image->GetMetadata().mipLevels; + + if (cimage && (tMips == 1)) + { + // Special case for trimming mips off compressed images and keeping the original compressed highest level mip + mdata = cimage->GetMetadata(); + mdata.mipLevels = 1; + hr = timage->Initialize(mdata); + if (FAILED(hr)) + { + wprintf(L" FAILED [copy compressed to single level] (%x)\n", hr); + return 1; + } + + if (mdata.dimension == TEX_DIMENSION_TEXTURE3D) + { + for (size_t d = 0; d < mdata.depth; ++d) + { + auto simg = cimage->GetImage(0, 0, d); + auto dimg = timage->GetImage(0, 0, d); + + memcpy_s(dimg->pixels, dimg->slicePitch, simg->pixels, simg->slicePitch); + } + } + else + { + for (size_t i = 0; i < mdata.arraySize; ++i) + { + auto simg = cimage->GetImage(0, i, 0); + auto dimg = timage->GetImage(0, i, 0); + + memcpy_s(dimg->pixels, dimg->slicePitch, simg->pixels, simg->slicePitch); + } + } + + cimage.swap(timage); + } + else + { + cimage.reset(); + } + } + + if ((!tMips || info.mipLevels != tMips) && (info.width > 1 || info.height > 1 || info.depth > 1)) + { + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + if (info.dimension == TEX_DIMENSION_TEXTURE3D) + { + hr = GenerateMipMaps3D(image->GetImages(), image->GetImageCount(), image->GetMetadata(), dwFilter | dwFilterOpts, tMips, *timage); + } + else + { + hr = GenerateMipMaps(image->GetImages(), image->GetImageCount(), image->GetMetadata(), dwFilter | dwFilterOpts, tMips, *timage); + } + if (FAILED(hr)) + { + wprintf(L" FAILED [mipmaps] (%x)\n", hr); + return 1; + } + + auto& tinfo = timage->GetMetadata(); + info.mipLevels = tinfo.mipLevels; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.format == tinfo.format); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + cimage.reset(); + } + + // --- Premultiplied alpha (if requested) -------------------------------------- + if ((dwOptions & (DWORD64(1) << OPT_PREMUL_ALPHA)) + && HasAlpha(info.format) + && info.format != DXGI_FORMAT_A8_UNORM) + { + if (info.IsPMAlpha()) + { + printf("\nWARNING: Image is already using premultiplied alpha\n"); + } + else + { + auto img = image->GetImage(0, 0, 0); + assert(img); + size_t nimg = image->GetImageCount(); + + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = PremultiplyAlpha(img, nimg, info, dwSRGB, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [premultiply alpha] (%x)\n", hr); + continue; + } + + auto& tinfo = timage->GetMetadata(); + info.miscFlags2 = tinfo.miscFlags2; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + cimage.reset(); + } + } + + // --- Compress ---------------------------------------------------------------- + if (IsCompressed(tformat) && (FileType == CODEC_DDS)) + { + if (cimage && (cimage->GetMetadata().format == tformat)) + { + // We never changed the image and it was already compressed in our desired format, use original data + image.reset(cimage.release()); + + auto& tinfo = image->GetMetadata(); + + if ((tinfo.width % 4) != 0 || (tinfo.height % 4) != 0) + { + non4bc = true; + } + + info.format = tinfo.format; + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + } + else + { + cimage.reset(); + + auto img = image->GetImage(0, 0, 0); + assert(img); + size_t nimg = image->GetImageCount(); + + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + bool bc6hbc7 = false; + switch (tformat) + { + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + bc6hbc7 = true; + + { + static bool s_tryonce = false; + + if (!s_tryonce) + { + s_tryonce = true; + + if (!(dwOptions & (DWORD64(1) << OPT_NOGPU))) + { + if (!CreateDevice(adapter, pDevice.GetAddressOf())) + wprintf(L"\nWARNING: DirectCompute is not available, using BC6H / BC7 CPU codec\n"); + } + else + { + wprintf(L"\nWARNING: using BC6H / BC7 CPU codec\n"); + } + } + } + break; + } + + DWORD cflags = dwCompress; +#ifdef _OPENMP + if (!(dwOptions & (DWORD64(1) << OPT_FORCE_SINGLEPROC))) + { + cflags |= TEX_COMPRESS_PARALLEL; + } +#endif + + if ((img->width % 4) != 0 || (img->height % 4) != 0) + { + non4bc = true; + } + + if (bc6hbc7 && pDevice) + { + hr = Compress(pDevice.Get(), img, nimg, info, tformat, dwCompress | dwSRGB, alphaWeight, *timage); + } + else + { + hr = Compress(img, nimg, info, tformat, cflags | dwSRGB, TEX_THRESHOLD_DEFAULT, *timage); + } + if (FAILED(hr)) + { + wprintf(L" FAILED [compress] (%x)\n", hr); + continue; + } + + auto& tinfo = timage->GetMetadata(); + + info.format = tinfo.format; + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + } + } + else + { + cimage.reset(); + } + + // --- Set alpha mode ---------------------------------------------------------- + if (HasAlpha(info.format) + && info.format != DXGI_FORMAT_A8_UNORM) + { + if (image->IsAlphaAllOpaque()) + { + info.SetAlphaMode(TEX_ALPHA_MODE_OPAQUE); + } + else if (info.IsPMAlpha()) + { + // Aleady set TEX_ALPHA_MODE_PREMULTIPLIED + } + else if (dwOptions & (DWORD64(1) << OPT_SEPALPHA)) + { + info.SetAlphaMode(TEX_ALPHA_MODE_CUSTOM); + } + else if (info.GetAlphaMode() == TEX_ALPHA_MODE_UNKNOWN) + { + info.SetAlphaMode(TEX_ALPHA_MODE_STRAIGHT); + } + } + else + { + info.SetAlphaMode(TEX_ALPHA_MODE_UNKNOWN); + } + + // --- Save result ------------------------------------------------------------- + { + auto img = image->GetImage(0, 0, 0); + assert(img); + size_t nimg = image->GetImageCount(); + + PrintInfo(info); + wprintf(L"\n"); + + // Figure out dest filename + wchar_t *pchSlash, *pchDot; + + wcscpy_s(pConv->szDest, MAX_PATH, szPrefix); + + pchSlash = wcsrchr(pConv->szSrc, L'\\'); + if (pchSlash != 0) + wcscat_s(pConv->szDest, MAX_PATH, pchSlash + 1); + else + wcscat_s(pConv->szDest, MAX_PATH, pConv->szSrc); + + pchSlash = wcsrchr(pConv->szDest, '\\'); + pchDot = wcsrchr(pConv->szDest, '.'); + + if (pchDot > pchSlash) + *pchDot = 0; + + wcscat_s(pConv->szDest, MAX_PATH, szSuffix); + + // Write texture + wprintf(L"writing %ls", pConv->szDest); + fflush(stdout); + + if (~dwOptions & (DWORD64(1) << OPT_OVERWRITE)) + { + if (GetFileAttributesW(pConv->szDest) != INVALID_FILE_ATTRIBUTES) + { + wprintf(L"\nERROR: Output file already exists, use -y to overwrite:\n"); + continue; + } + } + + switch (FileType) + { + case CODEC_DDS: + hr = SaveToDDSFile(img, nimg, info, + (dwOptions & (DWORD64(1) << OPT_USE_DX10)) ? (DDS_FLAGS_FORCE_DX10_EXT | DDS_FLAGS_FORCE_DX10_EXT_MISC2) : DDS_FLAGS_NONE, + pConv->szDest); + break; + + case CODEC_TGA: + hr = SaveToTGAFile(img[0], pConv->szDest); + break; + + case CODEC_HDR: + hr = SaveToHDRFile(img[0], pConv->szDest); + break; + +#ifdef USE_OPENEXR + case CODEC_EXR: + hr = SaveToEXRFile(img[0], pConv->szDest); + break; +#endif + + default: + { + WICCodecs codec = (FileType == CODEC_HDP || FileType == CODEC_JXR) ? WIC_CODEC_WMP : static_cast(FileType); + size_t nimages = (dwOptions & (DWORD64(1) << OPT_WIC_MULTIFRAME)) ? nimg : 1; + hr = SaveToWICFile(img, nimages, WIC_FLAGS_NONE, GetWICCodec(codec), pConv->szDest, nullptr, + [&](IPropertyBag2* props) + { + bool wicLossless = (dwOptions & (DWORD64(1) << OPT_WIC_LOSSLESS)) != 0; + + switch (FileType) + { + case WIC_CODEC_JPEG: + if (wicLossless || wicQuality >= 0.f) + { + PROPBAG2 options = {}; + VARIANT varValues = {}; + options.pstrName = const_cast(L"ImageQuality"); + varValues.vt = VT_R4; + varValues.fltVal = (wicLossless) ? 1.f : wicQuality; + (void)props->Write(1, &options, &varValues); + } + break; + + case WIC_CODEC_TIFF: + { + PROPBAG2 options = {}; + VARIANT varValues = {}; + if (wicLossless) + { + options.pstrName = const_cast(L"TiffCompressionMethod"); + varValues.vt = VT_UI1; + varValues.bVal = WICTiffCompressionNone; + } + else if (wicQuality >= 0.f) + { + options.pstrName = const_cast(L"CompressionQuality"); + varValues.vt = VT_R4; + varValues.fltVal = wicQuality; + } + (void)props->Write(1, &options, &varValues); + } + break; + + case WIC_CODEC_WMP: + case CODEC_HDP: + case CODEC_JXR: + { + PROPBAG2 options = {}; + VARIANT varValues = {}; + if (wicLossless) + { + options.pstrName = const_cast(L"Lossless"); + varValues.vt = VT_BOOL; + varValues.bVal = TRUE; + } + else if (wicQuality >= 0.f) + { + options.pstrName = const_cast(L"ImageQuality"); + varValues.vt = VT_R4; + varValues.fltVal = wicQuality; + } + (void)props->Write(1, &options, &varValues); + } + break; + } + }); + } + break; + } + + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + continue; + } + wprintf(L"\n"); + } + } + + if (nonpow2warn && maxSize <= 4096) + { + // Only emit this warning if ran with -fl set to a 9.x feature level + wprintf(L"\nWARNING: Not all feature levels support non-power-of-2 textures with mipmaps\n"); + } + + if (non4bc) + wprintf(L"\nWARNING: Direct3D requires BC image to be multiple of 4 in width & height\n"); + + if (dwOptions & (DWORD64(1) << OPT_TIMING)) + { + LARGE_INTEGER qpcEnd; + if (QueryPerformanceCounter(&qpcEnd)) + { + LONGLONG delta = qpcEnd.QuadPart - qpcStart.QuadPart; + wprintf(L"\n Processing time: %f seconds\n", double(delta) / double(qpcFreq.QuadPart)); + } + } + + return 0; +} diff --git a/deps/DirectXTex/Texdiag/directx.ico b/deps/DirectXTex/Texdiag/directx.ico new file mode 100644 index 0000000..bc43c1b Binary files /dev/null and b/deps/DirectXTex/Texdiag/directx.ico differ diff --git a/deps/DirectXTex/Texdiag/texdiag.cpp b/deps/DirectXTex/Texdiag/texdiag.cpp new file mode 100644 index 0000000..0792f4c --- /dev/null +++ b/deps/DirectXTex/Texdiag/texdiag.cpp @@ -0,0 +1,3731 @@ +//-------------------------------------------------------------------------------------- +// File: Texdiag.cpp +// +// DirectX Texture diagnostic tool +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +//-------------------------------------------------------------------------------------- + +#pragma warning(push) +#pragma warning(disable : 4005) +#define WIN32_LEAN_AND_MEAN +#define NOMINMAX +#define NODRAWTEXT +#define NOGDI +#define NOBITMAP +#define NOMCX +#define NOSERVICE +#define NOHELP +#pragma warning(pop) + +#include +#include +#include + +#include +#include +#include + +#include + +#include "directxtex.h" + +//Uncomment to add support for OpenEXR (.exr) +//#define USE_OPENEXR + +#ifdef USE_OPENEXR +// See for details +#include "DirectXTexEXR.h" +#endif + +using namespace DirectX; + +enum COMMANDS +{ + CMD_INFO = 1, + CMD_ANALYZE, + CMD_COMPARE, + CMD_DIFF, + CMD_DUMPBC, + CMD_MAX +}; + +enum OPTIONS +{ + OPT_RECURSIVE = 1, + OPT_FORMAT, + OPT_FILTER, + OPT_DDS_DWORD_ALIGN, + OPT_DDS_BAD_DXTN_TAILS, + OPT_OUTPUTFILE, + OPT_OVERWRITE, + OPT_NOLOGO, + OPT_TYPELESS_UNORM, + OPT_TYPELESS_FLOAT, + OPT_EXPAND_LUMINANCE, + OPT_TARGET_PIXELX, + OPT_TARGET_PIXELY, + OPT_MAX +}; + +static_assert(OPT_MAX <= 32, "dwOptions is a DWORD bitfield"); + +struct SConversion +{ + wchar_t szSrc[MAX_PATH]; +}; + +struct SValue +{ + LPCWSTR pName; + DWORD dwValue; +}; + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// + +const SValue g_pCommands[] = +{ + { L"info", CMD_INFO }, + { L"analyze", CMD_ANALYZE }, + { L"compare", CMD_COMPARE }, + { L"diff", CMD_DIFF }, + { L"dumpbc", CMD_DUMPBC }, + { nullptr, 0 } +}; + +const SValue g_pOptions[] = +{ + { L"r", OPT_RECURSIVE }, + { L"f", OPT_FORMAT }, + { L"if", OPT_FILTER }, + { L"dword", OPT_DDS_DWORD_ALIGN }, + { L"badtails", OPT_DDS_BAD_DXTN_TAILS }, + { L"nologo", OPT_NOLOGO }, + { L"o", OPT_OUTPUTFILE }, + { L"y", OPT_OVERWRITE }, + { L"tu", OPT_TYPELESS_UNORM }, + { L"tf", OPT_TYPELESS_FLOAT }, + { L"xlum", OPT_EXPAND_LUMINANCE }, + { L"targetx", OPT_TARGET_PIXELX }, + { L"targety", OPT_TARGET_PIXELY }, + { nullptr, 0 } +}; + +#define DEFFMT(fmt) { L#fmt, DXGI_FORMAT_ ## fmt } + +const SValue g_pFormats[] = +{ + // List does not include _TYPELESS, depth/stencil, or BC formats + DEFFMT(R32G32B32A32_FLOAT), + DEFFMT(R32G32B32A32_UINT), + DEFFMT(R32G32B32A32_SINT), + DEFFMT(R32G32B32_FLOAT), + DEFFMT(R32G32B32_UINT), + DEFFMT(R32G32B32_SINT), + DEFFMT(R16G16B16A16_FLOAT), + DEFFMT(R16G16B16A16_UNORM), + DEFFMT(R16G16B16A16_UINT), + DEFFMT(R16G16B16A16_SNORM), + DEFFMT(R16G16B16A16_SINT), + DEFFMT(R32G32_FLOAT), + DEFFMT(R32G32_UINT), + DEFFMT(R32G32_SINT), + DEFFMT(R10G10B10A2_UNORM), + DEFFMT(R10G10B10A2_UINT), + DEFFMT(R11G11B10_FLOAT), + DEFFMT(R8G8B8A8_UNORM), + DEFFMT(R8G8B8A8_UNORM_SRGB), + DEFFMT(R8G8B8A8_UINT), + DEFFMT(R8G8B8A8_SNORM), + DEFFMT(R8G8B8A8_SINT), + DEFFMT(R16G16_FLOAT), + DEFFMT(R16G16_UNORM), + DEFFMT(R16G16_UINT), + DEFFMT(R16G16_SNORM), + DEFFMT(R16G16_SINT), + DEFFMT(R32_FLOAT), + DEFFMT(R32_UINT), + DEFFMT(R32_SINT), + DEFFMT(R8G8_UNORM), + DEFFMT(R8G8_UINT), + DEFFMT(R8G8_SNORM), + DEFFMT(R8G8_SINT), + DEFFMT(R16_FLOAT), + DEFFMT(R16_UNORM), + DEFFMT(R16_UINT), + DEFFMT(R16_SNORM), + DEFFMT(R16_SINT), + DEFFMT(R8_UNORM), + DEFFMT(R8_UINT), + DEFFMT(R8_SNORM), + DEFFMT(R8_SINT), + DEFFMT(A8_UNORM), + DEFFMT(R9G9B9E5_SHAREDEXP), + DEFFMT(R8G8_B8G8_UNORM), + DEFFMT(G8R8_G8B8_UNORM), + DEFFMT(B5G6R5_UNORM), + DEFFMT(B5G5R5A1_UNORM), + + // DXGI 1.1 formats + DEFFMT(B8G8R8A8_UNORM), + DEFFMT(B8G8R8X8_UNORM), + DEFFMT(R10G10B10_XR_BIAS_A2_UNORM), + DEFFMT(B8G8R8A8_UNORM_SRGB), + DEFFMT(B8G8R8X8_UNORM_SRGB), + + // DXGI 1.2 formats + DEFFMT(AYUV), + DEFFMT(Y410), + DEFFMT(Y416), + DEFFMT(YUY2), + DEFFMT(Y210), + DEFFMT(Y216), + DEFFMT(B4G4R4A4_UNORM), + + { nullptr, DXGI_FORMAT_UNKNOWN } +}; + +const SValue g_pReadOnlyFormats[] = +{ + DEFFMT(R32G32B32A32_TYPELESS), + DEFFMT(R32G32B32_TYPELESS), + DEFFMT(R16G16B16A16_TYPELESS), + DEFFMT(R32G32_TYPELESS), + DEFFMT(R32G8X24_TYPELESS), + DEFFMT(D32_FLOAT_S8X24_UINT), + DEFFMT(R32_FLOAT_X8X24_TYPELESS), + DEFFMT(X32_TYPELESS_G8X24_UINT), + DEFFMT(R10G10B10A2_TYPELESS), + DEFFMT(R8G8B8A8_TYPELESS), + DEFFMT(R16G16_TYPELESS), + DEFFMT(R32_TYPELESS), + DEFFMT(D32_FLOAT), + DEFFMT(R24G8_TYPELESS), + DEFFMT(D24_UNORM_S8_UINT), + DEFFMT(R24_UNORM_X8_TYPELESS), + DEFFMT(X24_TYPELESS_G8_UINT), + DEFFMT(R8G8_TYPELESS), + DEFFMT(R16_TYPELESS), + DEFFMT(R8_TYPELESS), + DEFFMT(BC1_TYPELESS), + DEFFMT(BC1_UNORM), + DEFFMT(BC1_UNORM_SRGB), + DEFFMT(BC2_TYPELESS), + DEFFMT(BC2_UNORM), + DEFFMT(BC2_UNORM_SRGB), + DEFFMT(BC3_TYPELESS), + DEFFMT(BC3_UNORM), + DEFFMT(BC3_UNORM_SRGB), + DEFFMT(BC4_TYPELESS), + DEFFMT(BC4_UNORM), + DEFFMT(BC4_SNORM), + DEFFMT(BC5_TYPELESS), + DEFFMT(BC5_UNORM), + DEFFMT(BC5_SNORM), + + // DXGI 1.1 formats + DEFFMT(B8G8R8A8_TYPELESS), + DEFFMT(B8G8R8X8_TYPELESS), + DEFFMT(BC6H_TYPELESS), + DEFFMT(BC6H_UF16), + DEFFMT(BC6H_SF16), + DEFFMT(BC7_TYPELESS), + DEFFMT(BC7_UNORM), + DEFFMT(BC7_UNORM_SRGB), + + // DXGI 1.2 formats + DEFFMT(AI44), + DEFFMT(IA44), + DEFFMT(P8), + DEFFMT(A8P8), + DEFFMT(NV12), + DEFFMT(P010), + DEFFMT(P016), + DEFFMT(420_OPAQUE), + DEFFMT(NV11), + + // DXGI 1.3 formats + { L"P208", DXGI_FORMAT(130) }, + { L"V208", DXGI_FORMAT(131) }, + { L"V408", DXGI_FORMAT(132) }, + + // Xbox-specific formats + { L"R10G10B10_7E3_A2_FLOAT (Xbox)", DXGI_FORMAT(116) }, + { L"R10G10B10_6E4_A2_FLOAT (Xbox)", DXGI_FORMAT(117) }, + { L"D16_UNORM_S8_UINT (Xbox)", DXGI_FORMAT(118) }, + { L"R16_UNORM_X8_TYPELESS (Xbox)", DXGI_FORMAT(119) }, + { L"X16_TYPELESS_G8_UINT (Xbox)", DXGI_FORMAT(120) }, + { L"R10G10B10_SNORM_A2_UNORM (Xbox)", DXGI_FORMAT(189) }, + { L"R4G4_UNORM (Xbox)", DXGI_FORMAT(190) }, + + { nullptr, DXGI_FORMAT_UNKNOWN } +}; + +const SValue g_pFilters[] = +{ + { L"POINT", TEX_FILTER_POINT }, + { L"LINEAR", TEX_FILTER_LINEAR }, + { L"CUBIC", TEX_FILTER_CUBIC }, + { L"FANT", TEX_FILTER_FANT }, + { L"BOX", TEX_FILTER_BOX }, + { L"TRIANGLE", TEX_FILTER_TRIANGLE }, + { L"POINT_DITHER", TEX_FILTER_POINT | TEX_FILTER_DITHER }, + { L"LINEAR_DITHER", TEX_FILTER_LINEAR | TEX_FILTER_DITHER }, + { L"CUBIC_DITHER", TEX_FILTER_CUBIC | TEX_FILTER_DITHER }, + { L"FANT_DITHER", TEX_FILTER_FANT | TEX_FILTER_DITHER }, + { L"BOX_DITHER", TEX_FILTER_BOX | TEX_FILTER_DITHER }, + { L"TRIANGLE_DITHER", TEX_FILTER_TRIANGLE | TEX_FILTER_DITHER }, + { L"POINT_DITHER_DIFFUSION", TEX_FILTER_POINT | TEX_FILTER_DITHER_DIFFUSION }, + { L"LINEAR_DITHER_DIFFUSION", TEX_FILTER_LINEAR | TEX_FILTER_DITHER_DIFFUSION }, + { L"CUBIC_DITHER_DIFFUSION", TEX_FILTER_CUBIC | TEX_FILTER_DITHER_DIFFUSION }, + { L"FANT_DITHER_DIFFUSION", TEX_FILTER_FANT | TEX_FILTER_DITHER_DIFFUSION }, + { L"BOX_DITHER_DIFFUSION", TEX_FILTER_BOX | TEX_FILTER_DITHER_DIFFUSION }, + { L"TRIANGLE_DITHER_DIFFUSION", TEX_FILTER_TRIANGLE | TEX_FILTER_DITHER_DIFFUSION }, + { nullptr, TEX_FILTER_DEFAULT } +}; + +#define CODEC_DDS 0xFFFF0001 +#define CODEC_TGA 0xFFFF0002 +#define CODEC_HDR 0xFFFF0005 +#define CODEC_EXR 0xFFFF0006 + +const SValue g_pExtFileTypes[] = +{ + { L".BMP", WIC_CODEC_BMP }, + { L".JPG", WIC_CODEC_JPEG }, + { L".JPEG", WIC_CODEC_JPEG }, + { L".PNG", WIC_CODEC_PNG }, + { L".DDS", CODEC_DDS }, + { L".TGA", CODEC_TGA }, + { L".HDR", CODEC_HDR }, + { L".TIF", WIC_CODEC_TIFF }, + { L".TIFF", WIC_CODEC_TIFF }, + { L".WDP", WIC_CODEC_WMP }, + { L".HDP", WIC_CODEC_WMP }, + { L".JXR", WIC_CODEC_WMP }, +#ifdef USE_OPENEXR + { L"EXR", CODEC_EXR }, +#endif + { nullptr, CODEC_DDS } +}; + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// + +namespace +{ + inline HANDLE safe_handle(HANDLE h) { return (h == INVALID_HANDLE_VALUE) ? 0 : h; } + + struct find_closer { void operator()(HANDLE h) { assert(h != INVALID_HANDLE_VALUE); if (h) FindClose(h); } }; + + typedef public std::unique_ptr ScopedFindHandle; + +#pragma prefast(disable : 26018, "Only used with static internal arrays") + + DWORD LookupByName(const wchar_t *pName, const SValue *pArray) + { + while (pArray->pName) + { + if (!_wcsicmp(pName, pArray->pName)) + return pArray->dwValue; + + pArray++; + } + + return 0; + } + + + const wchar_t* LookupByValue(DWORD pValue, const SValue *pArray) + { + while (pArray->pName) + { + if (pValue == pArray->dwValue) + return pArray->pName; + + pArray++; + } + + return L""; + } + + + void SearchForFiles(const wchar_t* path, std::list& files, bool recursive) + { + // Process files + WIN32_FIND_DATA findData = {}; + ScopedFindHandle hFile(safe_handle(FindFirstFileExW(path, + FindExInfoBasic, &findData, + FindExSearchNameMatch, nullptr, + FIND_FIRST_EX_LARGE_FETCH))); + if (hFile) + { + for (;;) + { + if (!(findData.dwFileAttributes & (FILE_ATTRIBUTE_HIDDEN | FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_DIRECTORY))) + { + wchar_t drive[_MAX_DRIVE] = {}; + wchar_t dir[_MAX_DIR] = {}; + _wsplitpath_s(path, drive, _MAX_DRIVE, dir, _MAX_DIR, nullptr, 0, nullptr, 0); + + SConversion conv; + _wmakepath_s(conv.szSrc, drive, dir, findData.cFileName, nullptr); + files.push_back(conv); + } + + if (!FindNextFile(hFile.get(), &findData)) + break; + } + } + + // Process directories + if (recursive) + { + wchar_t searchDir[MAX_PATH] = {}; + { + wchar_t drive[_MAX_DRIVE] = {}; + wchar_t dir[_MAX_DIR] = {}; + _wsplitpath_s(path, drive, _MAX_DRIVE, dir, _MAX_DIR, nullptr, 0, nullptr, 0); + _wmakepath_s(searchDir, drive, dir, L"*", nullptr); + } + + hFile.reset(safe_handle(FindFirstFileExW(searchDir, + FindExInfoBasic, &findData, + FindExSearchLimitToDirectories, nullptr, + FIND_FIRST_EX_LARGE_FETCH))); + if (!hFile) + return; + + for (;;) + { + if (findData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) + { + if (findData.cFileName[0] != L'.') + { + wchar_t subdir[MAX_PATH] = {}; + + { + wchar_t drive[_MAX_DRIVE] = {}; + wchar_t dir[_MAX_DIR] = {}; + wchar_t fname[_MAX_FNAME] = {}; + wchar_t ext[_MAX_FNAME] = {}; + _wsplitpath_s(path, drive, dir, fname, ext); + wcscat_s(dir, findData.cFileName); + _wmakepath_s(subdir, drive, dir, fname, ext); + } + + SearchForFiles(subdir, files, recursive); + } + } + + if (!FindNextFile(hFile.get(), &findData)) + break; + } + } + } + + + void PrintFormat(DXGI_FORMAT Format) + { + for (const SValue *pFormat = g_pFormats; pFormat->pName; pFormat++) + { + if ((DXGI_FORMAT)pFormat->dwValue == Format) + { + wprintf(pFormat->pName); + break; + } + } + + for (const SValue *pFormat = g_pReadOnlyFormats; pFormat->pName; pFormat++) + { + if ((DXGI_FORMAT)pFormat->dwValue == Format) + { + wprintf(pFormat->pName); + return; + } + } + + wprintf(L"*UNKNOWN*"); + } + + + void PrintList(size_t cch, const SValue *pValue) + { + while (pValue->pName) + { + size_t cchName = wcslen(pValue->pName); + + if (cch + cchName + 2 >= 80) + { + wprintf(L"\n "); + cch = 6; + } + + wprintf(L"%ls ", pValue->pName); + cch += cchName + 2; + pValue++; + } + + wprintf(L"\n"); + } + + + void PrintLogo() + { + wprintf(L"Microsoft (R) DirectX Texture Diagnostic Tool\n"); + wprintf(L"Copyright (C) Microsoft Corp. All rights reserved.\n"); +#ifdef _DEBUG + wprintf(L"*** Debug build ***\n"); +#endif + wprintf(L"\n"); + } + + + void PrintUsage() + { + PrintLogo(); + + wprintf(L"Usage: texdiag \n\n"); + wprintf(L" info Output image metadata\n"); + wprintf(L" analyze Analyze and summarize image information\n"); + wprintf(L" compare Compare two images with MSE error metric\n"); + wprintf(L" diff Generate difference image from two images\n"); + wprintf(L" dumpbc Dump out compressed blocks (DDS BC only)\n\n"); + wprintf(L" -r wildcard filename search is recursive\n"); + wprintf(L" -if image filtering\n"); + wprintf(L"\n (DDS input only)\n"); + wprintf(L" -t{u|f} TYPELESS format is treated as UNORM or FLOAT\n"); + wprintf(L" -dword Use DWORD instead of BYTE alignment\n"); + wprintf(L" -badtails Fix for older DXTn with bad mipchain tails\n"); + wprintf(L" -xlum expand legacy L8, L16, and A8P8 formats\n"); + wprintf(L"\n (diff only)\n"); + wprintf(L" -f format\n"); + wprintf(L" -o output filename\n"); + wprintf(L" -y overwrite existing output file (if any)\n"); + wprintf(L"\n (dumpbc only)\n"); + wprintf(L" -targetx dump pixels at location x (defaults to all)\n"); + wprintf(L" -targety dump pixels at location y (defaults to all)\n"); + wprintf(L"\n -nologo suppress copyright message\n"); + + wprintf(L"\n : "); + PrintList(13, g_pFormats); + + wprintf(L"\n : "); + PrintList(13, g_pFilters); + } + + HRESULT LoadImage(const wchar_t *fileName, DWORD dwOptions, DWORD dwFilter, TexMetadata& info, std::unique_ptr& image) + { + if (!fileName) + return E_INVALIDARG; + + image.reset(new (std::nothrow) ScratchImage); + if (!image) + return E_OUTOFMEMORY; + + wchar_t ext[_MAX_EXT]; + _wsplitpath_s(fileName, nullptr, 0, nullptr, 0, nullptr, 0, ext, _MAX_EXT); + + if (_wcsicmp(ext, L".dds") == 0) + { + DWORD ddsFlags = DDS_FLAGS_NONE; + if (dwOptions & (1 << OPT_DDS_DWORD_ALIGN)) + ddsFlags |= DDS_FLAGS_LEGACY_DWORD; + if (dwOptions & (1 << OPT_EXPAND_LUMINANCE)) + ddsFlags |= DDS_FLAGS_EXPAND_LUMINANCE; + if (dwOptions & (1 << OPT_DDS_BAD_DXTN_TAILS)) + ddsFlags |= DDS_FLAGS_BAD_DXTN_TAILS; + + HRESULT hr = LoadFromDDSFile(fileName, ddsFlags, &info, *image); + if (FAILED(hr)) + return hr; + + if (IsTypeless(info.format)) + { + if (dwOptions & (1 << OPT_TYPELESS_UNORM)) + { + info.format = MakeTypelessUNORM(info.format); + } + else if (dwOptions & (1 << OPT_TYPELESS_FLOAT)) + { + info.format = MakeTypelessFLOAT(info.format); + } + + if (IsTypeless(info.format)) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + image->OverrideFormat(info.format); + } + + return S_OK; + } + else if (_wcsicmp(ext, L".tga") == 0) + { + return LoadFromTGAFile(fileName, &info, *image); + } + else if (_wcsicmp(ext, L".hdr") == 0) + { + return LoadFromHDRFile(fileName, &info, *image); + } +#ifdef USE_OPENEXR + else if (_wcsicmp(ext, L".exr") == 0) + { + return LoadFromEXRFile(fileName, &info, *image); + } +#endif + else + { + // WIC shares the same filter values for mode and dither + static_assert(WIC_FLAGS_DITHER == TEX_FILTER_DITHER, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_DITHER_DIFFUSION == TEX_FILTER_DITHER_DIFFUSION, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_POINT == TEX_FILTER_POINT, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_LINEAR == TEX_FILTER_LINEAR, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_CUBIC == TEX_FILTER_CUBIC, "WIC_FLAGS_* & TEX_FILTER_* should match"); + static_assert(WIC_FLAGS_FILTER_FANT == TEX_FILTER_FANT, "WIC_FLAGS_* & TEX_FILTER_* should match"); + + return LoadFromWICFile(fileName, dwFilter | WIC_FLAGS_ALL_FRAMES, &info, *image); + } + } + + HRESULT SaveImage(const Image* image, const wchar_t *fileName, DWORD codec) + { + switch (codec) + { + case CODEC_DDS: + return SaveToDDSFile(*image, DDS_FLAGS_NONE, fileName); + + case CODEC_TGA: + return SaveToTGAFile(*image, fileName); + + case CODEC_HDR: + return SaveToHDRFile(*image, fileName); + +#ifdef USE_OPENEXR + case CODEC_EXR: + return SaveToEXRFile(*image, fileName); +#endif + + default: + return SaveToWICFile(*image, WIC_FLAGS_NONE, GetWICCodec(static_cast(codec)), fileName); + } + } + + //-------------------------------------------------------------------------------------- + struct AnalyzeData + { + XMFLOAT4 imageMin; + XMFLOAT4 imageMax; + XMFLOAT4 imageAvg; + XMFLOAT4 imageVariance; + XMFLOAT4 imageStdDev; + float luminance; + size_t specials_x; + size_t specials_y; + size_t specials_z; + size_t specials_w; + + void Print() + { + wprintf(L"\t Minimum - (%f %f %f %f)\n", imageMin.x, imageMin.y, imageMin.z, imageMin.w); + wprintf(L"\t Average - (%f %f %f %f)\n", imageAvg.x, imageAvg.y, imageAvg.z, imageAvg.w); + wprintf(L"\t Maximum - (%f %f %f %f)\n", imageMax.x, imageMax.y, imageMax.z, imageMax.w); + wprintf(L"\t Variance - (%f %f %f %f)\n", imageVariance.x, imageVariance.y, imageVariance.z, imageVariance.w); + wprintf(L"\t Std Dev - (%f %f %f %f)\n", imageStdDev.x, imageStdDev.y, imageStdDev.z, imageStdDev.w); + + wprintf(L"\tLuminance - %f (maximum)\n", luminance); + + if ((specials_x > 0) || (specials_y > 0) || (specials_z > 0) || (specials_w > 0)) + { + wprintf(L" FP specials - (%Iu %Iu %Iu %Iu)\n", specials_x, specials_y, specials_z, specials_w); + } + } + }; + + HRESULT Analyze(const Image& image, _Out_ AnalyzeData& result) + { + memset(&result, 0, sizeof(AnalyzeData)); + + // First pass + XMVECTOR minv = g_XMFltMax; + XMVECTOR maxv = XMVectorNegate(g_XMFltMax); + XMVECTOR acc = g_XMZero; + XMVECTOR luminance = g_XMZero; + + size_t totalPixels = 0; + + HRESULT hr = EvaluateImage(image, [&](const XMVECTOR * pixels, size_t width, size_t y) + { + static const XMVECTORF32 s_luminance = { 0.3f, 0.59f, 0.11f, 0.f }; + + UNREFERENCED_PARAMETER(y); + + for (size_t x = 0; x < width; ++x) + { + XMVECTOR v = *pixels++; + luminance = XMVectorMax(luminance, XMVector3Dot(v, s_luminance) ); + minv = XMVectorMin(minv, v); + maxv = XMVectorMax(maxv, v); + acc = XMVectorAdd(v, acc); + ++totalPixels; + + XMFLOAT4 f; + XMStoreFloat4(&f, v); + if (!_finite(f.x)) + { + ++result.specials_x; + } + + if (!_finite(f.y)) + { + ++result.specials_y; + } + + if (!_finite(f.z)) + { + ++result.specials_z; + } + + if (!_finite(f.w)) + { + ++result.specials_w; + } + } + }); + if (FAILED(hr)) + return hr; + + if (!totalPixels) + return S_FALSE; + + result.luminance = XMVectorGetX(luminance); + XMStoreFloat4(&result.imageMin, minv); + XMStoreFloat4(&result.imageMax, maxv); + + XMVECTOR pixelv = XMVectorReplicate(float(totalPixels)); + XMVECTOR avgv = XMVectorDivide(acc, pixelv); + XMStoreFloat4(&result.imageAvg, avgv); + + // Second pass + acc = g_XMZero; + + hr = EvaluateImage(image, [&](const XMVECTOR * pixels, size_t width, size_t y) + { + UNREFERENCED_PARAMETER(y); + + for (size_t x = 0; x < width; ++x) + { + XMVECTOR v = *pixels++; + + XMVECTOR diff = XMVectorSubtract(v, avgv); + acc = XMVectorMultiplyAdd(diff, diff, acc); + } + }); + if (FAILED(hr)) + return hr; + + XMStoreFloat4(&result.imageVariance, acc); + + XMVECTOR stddev = XMVectorSqrt(acc); + + XMStoreFloat4(&result.imageStdDev, stddev); + + return S_OK; + } + + + //-------------------------------------------------------------------------------------- + struct AnalyzeBCData + { + size_t blocks; + size_t blockHist[15]; + + void Print(DXGI_FORMAT fmt) + { + wprintf(L"\t Compression - "); + PrintFormat(fmt); + wprintf(L"\n\t Total blocks - %Iu\n", blocks); + + switch (fmt) + { + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + wprintf(L"\t 4 color blocks - %Iu\n", blockHist[0]); + wprintf(L"\t 3 color blocks - %Iu\n", blockHist[1]); + break; + + // BC2 only has a single 'type' of block + + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + wprintf(L"\t 8 alpha blocks - %Iu\n", blockHist[0]); + wprintf(L"\t 6 alpha blocks - %Iu\n", blockHist[1]); + break; + + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + wprintf(L"\t 8 red blocks - %Iu\n", blockHist[0]); + wprintf(L"\t 6 red blocks - %Iu\n", blockHist[1]); + break; + + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + wprintf(L"\t 8 red blocks - %Iu\n", blockHist[0]); + wprintf(L"\t 6 red blocks - %Iu\n", blockHist[1]); + wprintf(L"\t 8 green blocks - %Iu\n", blockHist[2]); + wprintf(L"\t 6 green blocks - %Iu\n", blockHist[3]); + break; + + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + for (size_t j = 1; j <= 14; ++j) + { + if (blockHist[j] > 0) + wprintf(L"\t Mode %02Iu blocks - %Iu\n", j, blockHist[j]); + } + if (blockHist[0] > 0) + wprintf(L"\tReserved mode blcks - %Iu\n", blockHist[0]); + break; + + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + for (size_t j = 0; j <= 7; ++j) + { + if (blockHist[j] > 0) + wprintf(L"\t Mode %02Iu blocks - %Iu\n", j, blockHist[j]); + } + if (blockHist[8] > 0) + wprintf(L"\tReserved mode blcks - %Iu\n", blockHist[8]); + break; + } + } + }; + +#pragma pack(push,1) + struct BC1Block + { + uint16_t rgb[2]; // 565 colors + uint32_t bitmap; // 2bpp rgb bitmap + }; + + struct BC2Block + { + uint32_t bitmap[2]; // 4bpp alpha bitmap + BC1Block bc1; // BC1 rgb data + }; + + struct BC3Block + { + uint8_t alpha[2]; // alpha values + uint8_t bitmap[6]; // 3bpp alpha bitmap + BC1Block bc1; // BC1 rgb data + }; + + struct BC4UBlock + { + uint8_t red_0; + uint8_t red_1; + uint8_t indices[6]; + }; + + struct BC4SBlock + { + int8_t red_0; + int8_t red_1; + uint8_t indices[6]; + }; + + struct BC5UBlock + { + BC4UBlock u; + BC4UBlock v; + }; + + struct BC5SBlock + { + BC4SBlock u; + BC4SBlock v; + }; +#pragma pack(pop) + + HRESULT AnalyzeBC(const Image& image, _Out_ AnalyzeBCData& result) + { + memset(&result, 0, sizeof(AnalyzeBCData)); + + size_t sbpp; + switch (image.format) + { + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + sbpp = 8; + break; + + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + sbpp = 16; + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + const uint8_t *pSrc = image.pixels; + const size_t rowPitch = image.rowPitch; + + for (size_t h = 0; h < image.height; h += 4) + { + const uint8_t *sptr = pSrc; + + for (size_t count = 0; count < rowPitch; count += sbpp) + { + switch (image.format) + { + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + { + auto block = reinterpret_cast(sptr); + + if (block->rgb[0] <= block->rgb[1]) + { + // Transparent block + ++result.blockHist[1]; + } + else + { + // Opaque block + ++result.blockHist[0]; + } + } + break; + + // BC2 only has a single 'type' of block + + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + { + auto block = reinterpret_cast(sptr); + + if (block->alpha[0] > block->alpha[1]) + { + // 8 alpha block + ++result.blockHist[0]; + } + else + { + // 6 alpha block + ++result.blockHist[1]; + } + } + break; + + case DXGI_FORMAT_BC4_UNORM: + { + auto block = reinterpret_cast(sptr); + + if (block->red_0 > block->red_1) + { + // 8 red block + ++result.blockHist[0]; + } + else + { + // 6 red block + ++result.blockHist[1]; + } + } + break; + + case DXGI_FORMAT_BC4_SNORM: + { + auto block = reinterpret_cast(sptr); + + if (block->red_0 > block->red_1) + { + // 8 red block + ++result.blockHist[0]; + } + else + { + // 6 red block + ++result.blockHist[1]; + } + } + break; + + case DXGI_FORMAT_BC5_UNORM: + { + auto block = reinterpret_cast(sptr); + + if (block->u.red_0 > block->u.red_1) + { + // 8 red block + ++result.blockHist[0]; + } + else + { + // 6 red block + ++result.blockHist[1]; + } + + if (block->v.red_0 > block->v.red_1) + { + // 8 green block + ++result.blockHist[2]; + } + else + { + // 6 green block + ++result.blockHist[3]; + } + } + break; + + case DXGI_FORMAT_BC5_SNORM: + { + auto block = reinterpret_cast(sptr); + + if (block->u.red_0 > block->u.red_1) + { + // 8 red block + ++result.blockHist[0]; + } + else + { + // 6 red block + ++result.blockHist[1]; + } + + if (block->v.red_0 > block->v.red_1) + { + // 8 green block + ++result.blockHist[2]; + } + else + { + // 6 green block + ++result.blockHist[3]; + } + } + break; + + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + switch (*sptr & 0x03) + { + case 0x00: + // Mode 1 (2 bits, 00) + ++result.blockHist[1]; + break; + + case 0x01: + // Mode 2 (2 bits, 01) + ++result.blockHist[2]; + break; + + default: + switch (*sptr & 0x1F) + { + case 0x02: + // Mode 3 (5 bits, 00010) + ++result.blockHist[3]; + break; + + case 0x06: + // Mode 4 (5 bits, 00110) + ++result.blockHist[4]; + break; + + case 0x0A: + // Mode 5 (5 bits, 01010) + ++result.blockHist[5]; + break; + + case 0x0E: + // Mode 6 (5 bits, 01110) + ++result.blockHist[6]; + break; + + case 0x12: + // Mode 7 (5 bits, 10010) + ++result.blockHist[7]; + break; + + case 0x16: + // Mode 8 (5 bits, 10110) + ++result.blockHist[8]; + break; + + case 0x1A: + // Mode 9 (5 bits, 11010) + ++result.blockHist[9]; + break; + + case 0x1E: + // Mode 10 (5 bits, 11110) + ++result.blockHist[10]; + break; + + case 0x03: + // Mode 11 (5 bits, 00011) + ++result.blockHist[11]; + break; + + case 0x07: + // Mode 12 (5 bits, 00111) + ++result.blockHist[12]; + break; + + case 0x0B: + // Mode 13 (5 bits, 01011) + ++result.blockHist[13]; + break; + + case 0x0F: + // Mode 14 (5 bits, 01111) + ++result.blockHist[14]; + break; + + case 0x13: // Reserved mode (5 bits, 10011) + case 0x17: // Reserved mode (5 bits, 10111) + case 0x1B: // Reserved mode (5 bits, 11011) + case 0x1F: // Reserved mode (5 bits, 11111) + default: + ++result.blockHist[0]; + break; + } + break; + } + break; + + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + if (*sptr & 0x01) + { + // Mode 0 (1) + ++result.blockHist[0]; + } + else if (*sptr & 0x02) + { + // Mode 1 (01) + ++result.blockHist[1]; + } + else if (*sptr & 0x04) + { + // Mode 2 (001) + ++result.blockHist[2]; + } + else if (*sptr & 0x08) + { + // Mode 3 (0001) + ++result.blockHist[3]; + } + else if (*sptr & 0x10) + { + // Mode 4 (00001) + ++result.blockHist[4]; + } + else if (*sptr & 0x20) + { + // Mode 5 (000001) + ++result.blockHist[5]; + } + else if (*sptr & 0x40) + { + // Mode 6 (0000001) + ++result.blockHist[6]; + } + else if (*sptr & 0x80) + { + // Mode 7 (00000001) + ++result.blockHist[7]; + } + else + { + // Reserved mode 8 (00000000) + ++result.blockHist[8]; + } + break; + } + + sptr += sbpp; + ++result.blocks; + } + + pSrc += rowPitch; + } + + return S_OK; + } + + + //-------------------------------------------------------------------------------------- + HRESULT Difference(const Image& image1, const Image& image2, DWORD dwFilter, DXGI_FORMAT format, ScratchImage& result) + { + if (!image1.pixels || !image2.pixels) + return E_POINTER; + + if (image1.width != image2.width + || image1.height != image2.height) + return E_FAIL; + + ScratchImage tempA; + const Image* imageA = &image1; + if (IsCompressed(image1.format)) + { + HRESULT hr = Decompress(image1, DXGI_FORMAT_R32G32B32A32_FLOAT, tempA); + if (FAILED(hr)) + return hr; + + imageA = tempA.GetImage(0, 0, 0); + } + + ScratchImage tempB; + const Image* imageB = &image2; + if (image2.format != DXGI_FORMAT_R32G32B32A32_FLOAT) + { + if (IsCompressed(image2.format)) + { + HRESULT hr = Decompress(image2, DXGI_FORMAT_R32G32B32A32_FLOAT, tempB); + if (FAILED(hr)) + return hr; + + imageB = tempB.GetImage(0,0,0); + } + else + { + HRESULT hr = Convert(image2, DXGI_FORMAT_R32G32B32A32_FLOAT, dwFilter, TEX_THRESHOLD_DEFAULT, tempB); + if (FAILED(hr)) + return hr; + + imageB = tempB.GetImage(0, 0, 0); + } + } + + if (!imageA || !imageB) + return E_POINTER; + + ScratchImage diffImage; + HRESULT hr = TransformImage(*imageA, [&](XMVECTOR* outPixels, const XMVECTOR * inPixels, size_t width, size_t y) + { + auto *inPixelsB = reinterpret_cast(imageB->pixels + (y*imageB->rowPitch)); + + for (size_t x = 0; x < width; ++x) + { + XMVECTOR v1 = *inPixels++; + XMVECTOR v2 = *inPixelsB++; + + v1 = XMVectorSubtract(v1, v2); + v1 = XMVectorAbs(v1); + + v1 = XMVectorSelect( g_XMIdentityR3, v1, g_XMSelect1110); + + *outPixels++ = v1; + } + }, (format == DXGI_FORMAT_R32G32B32A32_FLOAT) ? result : diffImage); + if (FAILED(hr)) + return hr; + + if (format == DXGI_FORMAT_R32G32B32A32_FLOAT) + return S_OK; + + return Convert(diffImage.GetImages(), diffImage.GetImageCount(), diffImage.GetMetadata(), format, dwFilter, TEX_THRESHOLD_DEFAULT, result); + } + + + //-------------------------------------------------------------------------------------- + // Partition, Shape, Fixup + const uint8_t g_aFixUp[3][64][3] = + { + { // No fix-ups for 1st subset for BC6H or BC7 + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 }, + { 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 },{ 0, 0, 0 } + }, + + { // BC6H/BC7 Partition Set Fixups for 2 Subsets + { 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0,15, 0 },{ 0, 2, 0 },{ 0, 8, 0 },{ 0, 2, 0 }, + { 0, 2, 0 },{ 0, 8, 0 },{ 0, 8, 0 },{ 0,15, 0 }, + { 0, 2, 0 },{ 0, 8, 0 },{ 0, 2, 0 },{ 0, 2, 0 }, + { 0, 8, 0 },{ 0, 8, 0 },{ 0, 2, 0 },{ 0, 2, 0 }, + + // BC7 Partition Set Fixups for 2 Subsets (second-half) + { 0,15, 0 },{ 0,15, 0 },{ 0, 6, 0 },{ 0, 8, 0 }, + { 0, 2, 0 },{ 0, 8, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0, 2, 0 },{ 0, 8, 0 },{ 0, 2, 0 },{ 0, 2, 0 }, + { 0, 2, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0, 6, 0 }, + { 0, 6, 0 },{ 0, 2, 0 },{ 0, 6, 0 },{ 0, 8, 0 }, + { 0,15, 0 },{ 0,15, 0 },{ 0, 2, 0 },{ 0, 2, 0 }, + { 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 },{ 0,15, 0 }, + { 0,15, 0 },{ 0, 2, 0 },{ 0, 2, 0 },{ 0,15, 0 } + }, + + { // BC7 Partition Set Fixups for 3 Subsets + { 0, 3,15 },{ 0, 3, 8 },{ 0,15, 8 },{ 0,15, 3 }, + { 0, 8,15 },{ 0, 3,15 },{ 0,15, 3 },{ 0,15, 8 }, + { 0, 8,15 },{ 0, 8,15 },{ 0, 6,15 },{ 0, 6,15 }, + { 0, 6,15 },{ 0, 5,15 },{ 0, 3,15 },{ 0, 3, 8 }, + { 0, 3,15 },{ 0, 3, 8 },{ 0, 8,15 },{ 0,15, 3 }, + { 0, 3,15 },{ 0, 3, 8 },{ 0, 6,15 },{ 0,10, 8 }, + { 0, 5, 3 },{ 0, 8,15 },{ 0, 8, 6 },{ 0, 6,10 }, + { 0, 8,15 },{ 0, 5,15 },{ 0,15,10 },{ 0,15, 8 }, + { 0, 8,15 },{ 0,15, 3 },{ 0, 3,15 },{ 0, 5,10 }, + { 0, 6,10 },{ 0,10, 8 },{ 0, 8, 9 },{ 0,15,10 }, + { 0,15, 6 },{ 0, 3,15 },{ 0,15, 8 },{ 0, 5,15 }, + { 0,15, 3 },{ 0,15, 6 },{ 0,15, 6 },{ 0,15, 8 }, + { 0, 3,15 },{ 0,15, 3 },{ 0, 5,15 },{ 0, 5,15 }, + { 0, 5,15 },{ 0, 8,15 },{ 0, 5,15 },{ 0,10,15 }, + { 0, 5,15 },{ 0,10,15 },{ 0, 8,15 },{ 0,13,15 }, + { 0,15, 3 },{ 0,12,15 },{ 0, 3,15 },{ 0, 3, 8 } + } + }; + + inline static bool IsFixUpOffset(_In_range_(0, 2) size_t uPartitions, _In_range_(0, 63) uint64_t uShape, _In_range_(0, 15) size_t uOffset) + { + for (size_t p = 0; p <= uPartitions; p++) + { + if (uOffset == g_aFixUp[uPartitions][uShape][p]) + { + return true; + } + } + return false; + } + + //-------------------------------------------------------------------------------------- +#define SIGN_EXTEND(x,nb) ((((x)&(1<<((nb)-1)))?((~0)<<(nb)):0)|(x)) + +#define NUM_PIXELS_PER_BLOCK 16 + + void Print565(uint16_t rgb) + { + float r = (float)((rgb >> 11) & 31) * (1.0f / 31.0f); + float g = (float)((rgb >> 5) & 63) * (1.0f / 63.0f); + float b = (float)((rgb >> 0) & 31) * (1.0f / 31.0f); + + wprintf(L"(R: %.3f, G: %.3f, B: %.3f)", r, g, b); + } + + void PrintIndex2bpp(uint32_t bitmap) + { + for (size_t j = 0; j < NUM_PIXELS_PER_BLOCK; ++j, bitmap >>= 2) + { + wprintf(L"%u%ls", bitmap & 0x3, ((j < (NUM_PIXELS_PER_BLOCK - 1)) && ((j % 4) == 3)) ? L" | " : L" "); + } + } + + void PrintIndex2bpp(uint64_t bitmap, size_t parts, uint64_t shape) + { + for (size_t j = 0; j < NUM_PIXELS_PER_BLOCK; ++j) + { + if (IsFixUpOffset(parts, shape, j)) + { + wprintf(L"%I64u%ls", bitmap & 0x1, ((j < (NUM_PIXELS_PER_BLOCK - 1)) && ((j % 4) == 3)) ? L" | " : L" "); + bitmap >>= 1; + } + else + { + wprintf(L"%I64u%ls", bitmap & 0x3, ((j < (NUM_PIXELS_PER_BLOCK - 1)) && ((j % 4) == 3)) ? L" | " : L" "); + bitmap >>= 2; + } + } + } + + void PrintIndex3bpp(uint64_t bitmap, size_t parts, uint64_t shape) + { + for (size_t j = 0; j < NUM_PIXELS_PER_BLOCK; ++j) + { + if (IsFixUpOffset(parts, shape, j)) + { + wprintf(L"%I64u%ls", bitmap & 0x3, ((j < (NUM_PIXELS_PER_BLOCK - 1)) && ((j % 4) == 3)) ? L" | " : L" "); + bitmap >>= 2; + } + else + { + wprintf(L"%I64u%ls", bitmap & 0x7, ((j < (NUM_PIXELS_PER_BLOCK - 1)) && ((j % 4) == 3)) ? L" | " : L" "); + bitmap >>= 3; + } + } + } + + void PrintIndex4bpp(uint64_t bitmap, size_t parts, uint64_t shape) + { + for (size_t j = 0; j < NUM_PIXELS_PER_BLOCK; ++j) + { + if (IsFixUpOffset(parts, shape, j)) + { + wprintf(L"%I64X%ls", bitmap & 0x7, ((j < (NUM_PIXELS_PER_BLOCK - 1)) && ((j % 4) == 3)) ? L" | " : L" "); + bitmap >>= 3; + } + else + { + wprintf(L"%I64X%ls", bitmap & 0xF, ((j < (NUM_PIXELS_PER_BLOCK - 1)) && ((j % 4) == 3)) ? L" | " : L" "); + bitmap >>= 4; + } + } + } + + void PrintIndex3bpp(const uint8_t data[6]) + { + uint32_t bitmap = data[0] | (data[1] << 8) | (data[2] << 16); + + size_t j = 0; + for (; j < (NUM_PIXELS_PER_BLOCK / 2); ++j, bitmap >>= 3) + { + wprintf(L"%u%ls", bitmap & 0x7, ((j % 4) == 3) ? L" | " : L" "); + } + + bitmap = data[3] | (data[4] << 8) | (data[5] << 16); + + for (; j < NUM_PIXELS_PER_BLOCK; ++j, bitmap >>= 3) + { + wprintf(L"%u%ls", bitmap & 0x7, ((j < (NUM_PIXELS_PER_BLOCK - 1)) && ((j % 4) == 3)) ? L" | " : L" "); + } + } + + const wchar_t* GetRotBits(uint64_t rot) + { + switch (rot) + { + case 1: return L" (R<->A)"; + case 2: return L" (G<->A)"; + case 3: return L" (B<->A)"; + default: return L""; + } + } + + HRESULT DumpBCImage(const Image& image, int pixelx, int pixely) + { + size_t sbpp; + switch (image.format) + { + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + sbpp = 8; + break; + + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + sbpp = 16; + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + const uint8_t *pSrc = image.pixels; + const size_t rowPitch = image.rowPitch; + + size_t nblock = 0; + for (size_t h = 0; h < image.height; h += 4, pSrc += rowPitch) + { + if (pixely >= 0) + { + if ((pixely < int(h)) || (pixely >= int(h + 4))) + continue; + } + + const uint8_t *sptr = pSrc; + + size_t w = 0; + for (size_t count = 0; count < rowPitch; count += sbpp, w += 4, ++nblock, sptr += sbpp) + { + if (pixelx >= 0) + { + if ((pixelx < int(w)) || (pixelx >= int(w + 4))) + continue; + } + + wprintf(L" Block %Iu (pixel: %Iu x %Iu)\n", nblock, w, h); + switch (image.format) + { + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + { + auto block = reinterpret_cast(sptr); + + if (block->rgb[0] <= block->rgb[1]) + { + // Transparent block + wprintf(L"\tTransparent - E0: "); + } + else + { + // Opaque block + wprintf(L"\t Opaque - E0: "); + } + + Print565(block->rgb[0]); + wprintf(L"\n\t E1: "); + Print565(block->rgb[1]); + wprintf(L"\n\t Index: "); + PrintIndex2bpp(block->bitmap); + wprintf(L"\n"); + } + break; + + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + { + auto block = reinterpret_cast(sptr); + + wprintf(L"\tColor - E0: "); + Print565(block->bc1.rgb[0]); + wprintf(L"\n\t E1: "); + Print565(block->bc1.rgb[1]); + wprintf(L"\n\t Index: "); + PrintIndex2bpp(block->bc1.bitmap); + wprintf(L"\n"); + + wprintf(L"\tAlpha - "); + + size_t j = 0; + uint32_t bitmap = block->bitmap[0]; + for (; j < (NUM_PIXELS_PER_BLOCK / 2); ++j, bitmap >>= 4) + { + wprintf(L"%X%ls", bitmap & 0xF, ((j % 4) == 3) ? L" | " : L" "); + } + + bitmap = block->bitmap[1]; + for (; j < NUM_PIXELS_PER_BLOCK; ++j, bitmap >>= 4) + { + wprintf(L"%X%ls", bitmap & 0xF, ((j < (NUM_PIXELS_PER_BLOCK - 1)) && ((j % 4) == 3)) ? L" | " : L" "); + } + + wprintf(L"\n"); + } + break; + + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + { + auto block = reinterpret_cast(sptr); + + wprintf(L"\tColor - E0: "); + Print565(block->bc1.rgb[0]); + wprintf(L"\n\t E1: "); + Print565(block->bc1.rgb[1]); + wprintf(L"\n\t Index: "); + PrintIndex2bpp(block->bc1.bitmap); + wprintf(L"\n"); + + wprintf(L"\tAlpha - E0: %0.3f E1: %0.3f (%u)\n\t Index: ", + float((float)block->alpha[0] / 255.f), + float((float)block->alpha[1] / 255.f), (block->alpha[0] > block->alpha[1]) ? 8 : 6); + + PrintIndex3bpp(block->bitmap); + + wprintf(L"\n"); + } + break; + + case DXGI_FORMAT_BC4_UNORM: + { + auto block = reinterpret_cast(sptr); + + wprintf(L"\t E0: %0.3f E1: %0.3f (%u)\n\tIndex: ", + float((float)block->red_0 / 255.f), + float((float)block->red_1 / 255.f), (block->red_0 > block->red_1) ? 8 : 6); + + PrintIndex3bpp(block->indices); + + wprintf(L"\n"); + } + break; + + case DXGI_FORMAT_BC4_SNORM: + { + auto block = reinterpret_cast(sptr); + + wprintf(L"\t E0: %0.3f E1: %0.3f (%u)\n\tIndex: ", + float((float)block->red_0 / 127.f), + float((float)block->red_1 / 127.f), (block->red_0 > block->red_1) ? 8 : 6); + + PrintIndex3bpp(block->indices); + + wprintf(L"\n"); + } + break; + + case DXGI_FORMAT_BC5_UNORM: + { + auto block = reinterpret_cast(sptr); + + wprintf(L"\tU - E0: %0.3f E1: %0.3f (%u)\n\t Index: ", + float((float)block->u.red_0 / 255.f), + float((float)block->u.red_1 / 255.f), (block->u.red_0 > block->u.red_1) ? 8 : 6); + + PrintIndex3bpp(block->u.indices); + + wprintf(L"\n"); + + wprintf(L"\tV - E0: %0.3f E1: %0.3f (%u)\n\t Index: ", + float((float)block->v.red_0 / 255.f), + float((float)block->v.red_1 / 255.f), (block->v.red_0 > block->v.red_1) ? 8 : 6); + + PrintIndex3bpp(block->v.indices); + + wprintf(L"\n"); + } + break; + + case DXGI_FORMAT_BC5_SNORM: + { + auto block = reinterpret_cast(sptr); + + wprintf(L"\tU - E0: %0.3f E1: %0.3f (%u)\n\t Index: ", + float((float)block->u.red_0 / 127.f), + float((float)block->u.red_1 / 127.f), (block->u.red_0 > block->u.red_1) ? 8 : 6); + + PrintIndex3bpp(block->u.indices); + + wprintf(L"\n"); + + wprintf(L"\tV - E0: %0.3f E1: %0.3f (%u)\n\t Index: ", + float((float)block->v.red_0 / 127.f), + float((float)block->v.red_1 / 127.f), (block->v.red_0 > block->v.red_1) ? 8 : 6); + + PrintIndex3bpp(block->v.indices); + + wprintf(L"\n"); + } + break; + + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + // http://msdn.microsoft.com/en-us/library/windows/desktop/hh308952.aspx#decoding_the_bc6h_format + + switch (*sptr & 0x03) + { + case 0x00: + // Mode 1 (2 bits, 00) + { + struct bc6h_mode1 + { + uint64_t mode : 2; // { M, 0}, { M, 1} + uint64_t gy4 : 1; // {GY, 4} + uint64_t by4 : 1; // {BY, 4} + uint64_t bz4 : 1; // {BZ, 4} + uint64_t rw : 10; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9} + uint64_t gw : 10; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9} + uint64_t bw : 10; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9} + uint64_t rx : 5; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4} + uint64_t gz4 : 1; // {GZ, 4} + uint64_t gy : 4; // {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3} + uint64_t gx : 5; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4} + uint64_t bz0 : 1; // {BZ, 0}, + uint64_t gz : 4; // {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3} + uint64_t bx : 5; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4} + uint64_t bz1 : 1; // {BZ, 1} + uint64_t by : 3; // {BY, 0}, {BY, 1}, {BY, 2} + uint64_t by3 : 1; // {BY, 3} + uint64_t ry : 5; // {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4} + uint64_t bz2 : 1; // {BZ, 2} + uint64_t rz : 5; // {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4} + uint64_t bz3 : 1; // {BZ, 3} + uint64_t d : 5; // { D, 0}, { D, 1}, { D, 2}, { D, 3}, { D, 4} + uint64_t indices : 46; + }; + static_assert(sizeof(bc6h_mode1) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw), int(m->gw), int(m->bw)); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + XMINT3 e1_A(int(m->ry), + int(m->gy | (m->gy4 << 4)), + int(m->by | (m->by3 << 3) | (m->by4 << 4))); + XMINT3 e1_B(int(m->rz), + int(m->gz | (m->gz4 << 4)), + int(m->bz0 | (m->bz1 << 1) | (m->bz2 << 2) | (m->bz3 << 3) | (m->bz4 << 4))); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 10); + e0_A.y = SIGN_EXTEND(e0_A.y, 10); + e0_A.z = SIGN_EXTEND(e0_A.z, 10); + + e0_B.x = SIGN_EXTEND(e0_B.x, 5); + e0_B.y = SIGN_EXTEND(e0_B.y, 5); + e0_B.z = SIGN_EXTEND(e0_B.z, 5); + + e1_A.x = SIGN_EXTEND(e1_A.x, 5); + e1_A.y = SIGN_EXTEND(e1_A.y, 5); + e1_A.z = SIGN_EXTEND(e1_A.z, 5); + + e1_B.x = SIGN_EXTEND(e1_B.x, 5); + e1_B.y = SIGN_EXTEND(e1_B.y, 5); + e1_B.z = SIGN_EXTEND(e1_B.z, 5); + } + + wprintf(L"\tMode 1 - [10 5 5 5] shape %I64u\n", m->d); + wprintf(L"\t E0(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E0(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t E1(A): (%04X, %04X, %04X)\n", e1_A.x & 0xFFFF, e1_A.y & 0xFFFF, e1_A.z & 0xFFFF); + wprintf(L"\t E1(B): (%04X, %04X, %04X)\n", e1_B.x & 0xFFFF, e1_B.y & 0xFFFF, e1_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex3bpp(m->indices, 1, m->d); + wprintf(L"\n"); + } + break; + + case 0x01: + // Mode 2 (2 bits, 01) + { + struct bc6h_mode2 + { + uint64_t mode : 2; // { M, 0}, { M, 1} + uint64_t gy5 : 1; // {GY, 5} + uint64_t gz45 : 2; // {GZ, 4}, {GZ, 5} + uint64_t rw : 7; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6} + uint64_t bz : 2; // {BZ, 0}, {BZ, 1} + uint64_t by4 : 1; // {BY, 4}, + uint64_t gw : 7; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6} + uint64_t by5 : 1; // {BY, 5} + uint64_t bz2 : 1; // {BZ, 2} + uint64_t gy4 : 1; // {GY, 4} + uint64_t bw : 7; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6} + uint64_t bz3 : 1; // {BZ, 3} + uint64_t bz5 : 1; // {BZ, 5} + uint64_t bz4 : 1; // {BZ, 4} + uint64_t rx : 6; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, {RX, 5} + uint64_t gy : 4; // {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3} + uint64_t gx : 6; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, {GX, 5} + uint64_t gz : 4; // {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3} + uint64_t bx : 5; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, {BX, 5} + uint64_t by : 4; // {BY, 0}, {BY, 1}, {BY, 2}, {BY, 3} + uint64_t ry : 6; // {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, {RY, 5} + uint64_t rz : 6; // {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4}, {RZ, 5}, + uint64_t d : 5; // { D, 0}, { D, 1}, { D, 2}, { D, 3}, { D, 4} + uint64_t indices : 46; + + }; + static_assert(sizeof(bc6h_mode2) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw), int(m->gw), int(m->bw)); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + XMINT3 e1_A(int(m->ry), + int(m->gy | (m->gy4 << 4) | (m->gy5 << 5)), + int(m->by | (m->by4 << 4) | (m->by5 << 5))); + XMINT3 e1_B(int(m->rz), + int(m->gz | (m->gz45 << 4)), + int(m->bz | (m->bz2 << 2) | (m->bz3 << 3) | (m->bz4 << 4) | (m->bz5 << 5))); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 7); + e0_A.y = SIGN_EXTEND(e0_A.y, 7); + e0_A.z = SIGN_EXTEND(e0_A.z, 7); + + e0_B.x = SIGN_EXTEND(e0_B.x, 6); + e0_B.y = SIGN_EXTEND(e0_B.y, 6); + e0_B.z = SIGN_EXTEND(e0_B.z, 6); + + e1_A.x = SIGN_EXTEND(e1_A.x, 6); + e1_A.y = SIGN_EXTEND(e1_A.y, 6); + e1_A.z = SIGN_EXTEND(e1_A.z, 6); + + e1_B.x = SIGN_EXTEND(e1_B.x, 6); + e1_B.y = SIGN_EXTEND(e1_B.y, 6); + e1_B.z = SIGN_EXTEND(e1_B.z, 6); + } + + wprintf(L"\tMode 2 - [7 6 6 6] shape %I64u\n", m->d); + wprintf(L"\t E0(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E0(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t E1(A): (%04X, %04X, %04X)\n", e1_A.x & 0xFFFF, e1_A.y & 0xFFFF, e1_A.z & 0xFFFF); + wprintf(L"\t E1(B): (%04X, %04X, %04X)\n", e1_B.x & 0xFFFF, e1_B.y & 0xFFFF, e1_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex3bpp(m->indices, 1, m->d); + wprintf(L"\n"); + } + break; + + default: + switch (*sptr & 0x1F) + { + case 0x02: + // Mode 3 (5 bits, 00010) + { + struct bc6h_mode3 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 10; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9} + uint64_t gw : 10; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9} + uint64_t bw : 10; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9} + uint64_t rx : 5; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4} + uint64_t rw10 : 1; // {RW,10} + uint64_t gy : 4; // {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3} + uint64_t gx : 4; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3} + uint64_t gw10 : 1; // {GW,10} + uint64_t bz0 : 1; // {BZ, 0} + uint64_t gz : 4; // {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3} + uint64_t bx : 4; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3} + uint64_t bw10 : 1; // {BW,10} + uint64_t bz1 : 1; // {BZ, 1} + uint64_t by : 3; // {BY, 0}, {BY, 1}, {BY, 2} + uint64_t by3 : 1; // {BY, 3} + uint64_t ry : 5; // {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4} + uint64_t bz2 : 1; // {BZ, 2} + uint64_t rz : 5; // {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4} + uint64_t bz3 : 1; // {BZ, 3} + uint64_t d : 5; // { D, 0}, { D, 1}, { D, 2}, { D, 3}, { D, 4} + uint64_t indices : 46; + + }; + static_assert(sizeof(bc6h_mode3) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw | (m->rw10 << 10)), + int(m->gw | (m->gw10 << 10)), + int(m->bw | (m->bw10 << 10))); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + XMINT3 e1_A(int(m->ry), int(m->gy), + int(m->by | (m->by3 << 3))); + XMINT3 e1_B(int(m->rz), + int(m->gz), + int(m->bz0 | (m->bz1 << 1) | (m->bz2 << 2) | (m->bz3 << 3))); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 11); + e0_A.y = SIGN_EXTEND(e0_A.y, 11); + e0_A.z = SIGN_EXTEND(e0_A.z, 11); + + e0_B.x = SIGN_EXTEND(e0_B.x, 5); + e0_B.y = SIGN_EXTEND(e0_B.y, 4); + e0_B.z = SIGN_EXTEND(e0_B.z, 4); + + e1_A.x = SIGN_EXTEND(e1_A.x, 5); + e1_A.y = SIGN_EXTEND(e1_A.y, 4); + e1_A.z = SIGN_EXTEND(e1_A.z, 4); + + e1_B.x = SIGN_EXTEND(e1_B.x, 5); + e1_B.y = SIGN_EXTEND(e1_B.y, 4); + e1_B.z = SIGN_EXTEND(e1_B.z, 4); + } + + wprintf(L"\tMode 3 - [11 5 4 4] shape %I64u\n", m->d); + wprintf(L"\t E0(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E0(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t E1(A): (%04X, %04X, %04X)\n", e1_A.x & 0xFFFF, e1_A.y & 0xFFFF, e1_A.z & 0xFFFF); + wprintf(L"\t E1(B): (%04X, %04X, %04X)\n", e1_B.x & 0xFFFF, e1_B.y & 0xFFFF, e1_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex3bpp(m->indices, 1, m->d); + wprintf(L"\n"); + } + break; + + case 0x06: + // Mode 4 (5 bits, 00110) + { + struct bc6h_mode4 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 10; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9} + uint64_t gw : 10; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9} + uint64_t bw : 10; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9} + uint64_t rx : 4; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3} + uint64_t rw10 : 1; // {RW,10} + uint64_t gz4 : 1; // {GZ, 4} + uint64_t gy : 4; // {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3} + uint64_t gx : 5; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4} + uint64_t gw10 : 1; // {GW,10} + uint64_t gz : 4; // {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3} + uint64_t bx : 4; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3} + uint64_t bw10 : 1; // {BW,10} + uint64_t bz1 : 1; // {BZ, 1} + uint64_t by : 3; // {BY, 0}, {BY, 1}, {BY, 2} + uint64_t by3 : 1; // {BY, 3} + uint64_t ry : 4; // {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3} + uint64_t bz0 : 1; // {BZ, 0} + uint64_t bz2 : 1; // {BZ, 2} + uint64_t rz : 4; // {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3} + uint64_t gy4 : 1; // {GY, 4} + uint64_t bz3 : 1; // {BZ, 3} + uint64_t d : 5; // { D, 0}, { D, 1}, { D, 2}, { D, 3}, { D, 4} + uint64_t indices : 46; + + }; + static_assert(sizeof(bc6h_mode4) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw | (m->rw10 << 10)), + int(m->gw | (m->gw10 << 10)), + int(m->bw | (m->bw10 << 10))); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + XMINT3 e1_A(int(m->ry), + int(m->gy | (m->gy4 << 4)), + int(m->by | (m->by3 << 3))); + XMINT3 e1_B(int(m->rz), + int(m->gz | (m->gz4 << 4)), + int(m->bz0 | (m->bz1 << 1) | (m->bz2 << 2) | (m->bz3 << 3))); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 11); + e0_A.y = SIGN_EXTEND(e0_A.y, 11); + e0_A.z = SIGN_EXTEND(e0_A.z, 11); + + e0_B.x = SIGN_EXTEND(e0_B.x, 4); + e0_B.y = SIGN_EXTEND(e0_B.y, 5); + e0_B.z = SIGN_EXTEND(e0_B.z, 4); + + e1_A.x = SIGN_EXTEND(e1_A.x, 4); + e1_A.y = SIGN_EXTEND(e1_A.y, 5); + e1_A.z = SIGN_EXTEND(e1_A.z, 4); + + e1_B.x = SIGN_EXTEND(e1_B.x, 4); + e1_B.y = SIGN_EXTEND(e1_B.y, 5); + e1_B.z = SIGN_EXTEND(e1_B.z, 4); + } + + wprintf(L"\tMode 4 - [11 4 5 4] shape %I64u\n", m->d); + wprintf(L"\t E0(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E0(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t E1(A): (%04X, %04X, %04X)\n", e1_A.x & 0xFFFF, e1_A.y & 0xFFFF, e1_A.z & 0xFFFF); + wprintf(L"\t E1(B): (%04X, %04X, %04X)\n", e1_B.x & 0xFFFF, e1_B.y & 0xFFFF, e1_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex3bpp(m->indices, 1, m->d); + wprintf(L"\n"); + } + break; + + case 0x0A: + // Mode 5 (5 bits, 01010) + { + struct bc6h_mode5 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 10; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9} + uint64_t gw : 10; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9} + uint64_t bw : 10; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9} + uint64_t rx : 4; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3} + uint64_t rw10 : 1; // {RW,10} + uint64_t by4 : 1; // {BY, 4} + uint64_t gy : 4; // {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3} + uint64_t gx : 4; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3} + uint64_t gw10 : 1; // {GW,10} + uint64_t bz0 : 1; // {BZ, 0} + uint64_t gz : 4; // {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3} + uint64_t bx : 5; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4} + uint64_t bw10 : 1; // {BW,10} + uint64_t by : 3; // {BY, 0}, {BY, 1}, {BY, 2} + uint64_t by3 : 1; // {BY, 3} + uint64_t ry : 4; // {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3} + uint64_t bz12 : 2; // {BZ, 1}, {BZ, 2} + uint64_t rz : 5; // {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {BZ, 4} + uint64_t bz3 : 1; // {BZ, 3} + uint64_t d : 5; // { D, 0}, { D, 1}, { D, 2}, { D, 3}, { D, 4} + uint64_t indices : 46; + }; + static_assert(sizeof(bc6h_mode5) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw | (m->rw10 << 10)), + int(m->gw | (m->gw10 << 10)), + int(m->bw | (m->bw10 << 10))); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + XMINT3 e1_A(int(m->ry), int(m->gy), + int(m->by | (m->by3 << 3) | (m->by4 << 4))); + XMINT3 e1_B(int(m->rz), int(m->gz), + int(m->bz0 | (m->bz12 << 1) | (m->bz3 << 3))); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 11); + e0_A.y = SIGN_EXTEND(e0_A.y, 11); + e0_A.z = SIGN_EXTEND(e0_A.z, 11); + + e0_B.x = SIGN_EXTEND(e0_B.x, 4); + e0_B.y = SIGN_EXTEND(e0_B.y, 4); + e0_B.z = SIGN_EXTEND(e0_B.z, 5); + + e1_A.x = SIGN_EXTEND(e1_A.x, 4); + e1_A.y = SIGN_EXTEND(e1_A.y, 4); + e1_A.z = SIGN_EXTEND(e1_A.z, 5); + + e1_B.x = SIGN_EXTEND(e1_B.x, 4); + e1_B.y = SIGN_EXTEND(e1_B.y, 4); + e1_B.z = SIGN_EXTEND(e1_B.z, 5); + } + + wprintf(L"\tMode 5 - [11 4 4 5] shape %I64u\n", m->d); + wprintf(L"\t E0(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E0(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t E1(A): (%04X, %04X, %04X)\n", e1_A.x & 0xFFFF, e1_A.y & 0xFFFF, e1_A.z & 0xFFFF); + wprintf(L"\t E1(B): (%04X, %04X, %04X)\n", e1_B.x & 0xFFFF, e1_B.y & 0xFFFF, e1_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex3bpp(m->indices, 1, m->d); + wprintf(L"\n"); + } + break; + + case 0x0E: + // Mode 6 (5 bits, 01110) + { + struct bc6h_mode6 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 9; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8} + uint64_t by4 : 1; // {BY, 4} + uint64_t gw : 9; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8} + uint64_t gy4 : 1; // {GY, 4} + uint64_t bw : 9; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8} + uint64_t bz4 : 1; // {BZ, 4} + uint64_t rx : 5; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4} + uint64_t gz4 : 1; // {GZ, 4} + uint64_t gy : 4; // {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3} + uint64_t gx : 5; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4} + uint64_t bz0 : 1; // {BZ, 0} + uint64_t gz : 4; // {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3} + uint64_t bx : 5; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4} + uint64_t bz1 : 1; // {BZ, 1} + uint64_t by : 3; // {BY, 0}, {BY, 1}, {BY, 2} + uint64_t by3 : 1; // {BY, 3} + uint64_t ry : 5; // {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, + uint64_t bz2 : 1; // {BZ, 2} + uint64_t rz : 5; // {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {BZ, 4} + uint64_t bz3 : 1; // {BZ, 3} + uint64_t d : 5; // { D, 0}, { D, 1}, { D, 2}, { D, 3}, { D, 4} + uint64_t indices : 46; + }; + static_assert(sizeof(bc6h_mode6) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw), int(m->gw), int(m->bw)); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + XMINT3 e1_A(int(m->ry), + int(m->gy | (m->gy4 << 4)), + int(m->by | (m->by3 << 3) | (m->by4 << 4))); + XMINT3 e1_B(int(m->rz), + int(m->gz | (m->gz4 << 4)), + int(m->bz0 | (m->bz1 << 1) | (m->bz2 << 2) | (m->bz3 << 3) | (m->bz4 << 4))); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 9); + e0_A.y = SIGN_EXTEND(e0_A.y, 9); + e0_A.z = SIGN_EXTEND(e0_A.z, 9); + + e0_B.x = SIGN_EXTEND(e0_B.x, 5); + e0_B.y = SIGN_EXTEND(e0_B.y, 5); + e0_B.z = SIGN_EXTEND(e0_B.z, 5); + + e1_A.x = SIGN_EXTEND(e1_A.x, 5); + e1_A.y = SIGN_EXTEND(e1_A.y, 5); + e1_A.z = SIGN_EXTEND(e1_A.z, 5); + + e1_B.x = SIGN_EXTEND(e1_B.x, 5); + e1_B.y = SIGN_EXTEND(e1_B.y, 5); + e1_B.z = SIGN_EXTEND(e1_B.z, 5); + } + + wprintf(L"\tMode 6 - [9 5 5 5] shape %I64u\n", m->d); + wprintf(L"\t E0(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E0(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t E1(A): (%04X, %04X, %04X)\n", e1_A.x & 0xFFFF, e1_A.y & 0xFFFF, e1_A.z & 0xFFFF); + wprintf(L"\t E1(B): (%04X, %04X, %04X)\n", e1_B.x & 0xFFFF, e1_B.y & 0xFFFF, e1_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex3bpp(m->indices, 1, m->d); + wprintf(L"\n"); + } + break; + + case 0x12: + // Mode 7 (5 bits, 10010) + { + struct bc6h_mode7 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 8; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7} + uint64_t gz4 : 1; // {GZ, 4} + uint64_t by4 : 1; // {BY, 4} + uint64_t gw : 8; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7} + uint64_t bz2 : 1; // {BZ, 2} + uint64_t gy4 : 1; // {GY, 4} + uint64_t bw : 8; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7} + uint64_t bz3 : 1; // {BZ, 3} + uint64_t bz4 : 1; // {BZ, 4} + uint64_t rx : 6; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, {RX, 5} + uint64_t gy : 4; // {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3} + uint64_t gx : 5; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4} + uint64_t bz0 : 1; // {BZ, 0} + uint64_t gz : 4; // {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3} + uint64_t bx : 5; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4} + uint64_t bz1 : 1; // {BZ, 1} + uint64_t by : 3; // {BY, 0}, {BY, 1}, {BY, 2} + uint64_t by3 : 1; // {BY, 3} + uint64_t ry : 6; // {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, {RY, 5} + uint64_t rz : 6; // {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4}, {RZ, 5} + uint64_t d : 5; // { D, 0}, { D, 1}, { D, 2}, { D, 3}, { D, 4} + uint64_t indices : 46; + }; + static_assert(sizeof(bc6h_mode7) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw), int(m->gw), int(m->bw)); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + XMINT3 e1_A(int(m->ry), + int(m->gy | (m->gy4 << 4)), + int(m->by | (m->by3 << 3) | (m->by4 << 4))); + XMINT3 e1_B(int(m->rz), + int(m->gz | (m->gz4 << 4)), + int(m->bz0 | (m->bz1 << 1) | (m->bz2 << 2) | (m->bz3 << 3) | (m->bz4 << 4))); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 8); + e0_A.y = SIGN_EXTEND(e0_A.y, 8); + e0_A.z = SIGN_EXTEND(e0_A.z, 8); + + e0_B.x = SIGN_EXTEND(e0_B.x, 6); + e0_B.y = SIGN_EXTEND(e0_B.y, 5); + e0_B.z = SIGN_EXTEND(e0_B.z, 5); + + e1_A.x = SIGN_EXTEND(e1_A.x, 6); + e1_A.y = SIGN_EXTEND(e1_A.y, 5); + e1_A.z = SIGN_EXTEND(e1_A.z, 5); + + e1_B.x = SIGN_EXTEND(e1_B.x, 6); + e1_B.y = SIGN_EXTEND(e1_B.y, 5); + e1_B.z = SIGN_EXTEND(e1_B.z, 5); + } + + wprintf(L"\tMode 7 - [8 6 5 5] shape %I64u\n", m->d); + wprintf(L"\t E0(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E0(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t E1(A): (%04X, %04X, %04X)\n", e1_A.x & 0xFFFF, e1_A.y & 0xFFFF, e1_A.z & 0xFFFF); + wprintf(L"\t E1(B): (%04X, %04X, %04X)\n", e1_B.x & 0xFFFF, e1_B.y & 0xFFFF, e1_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex3bpp(m->indices, 1, m->d); + wprintf(L"\n"); + } + break; + + case 0x16: + // Mode 8 (5 bits, 10110) + { + struct bc6h_mode8 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 8; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7} + uint64_t bz0 : 1; // {BZ, 0} + uint64_t by4 : 1; // {BY, 4} + uint64_t gw : 8; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7} + uint64_t gy5 : 1; // {GY, 5} + uint64_t gy4 : 1; // {GY, 4} + uint64_t bw : 8; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7} + uint64_t gz5 : 1; // {GZ, 5} + uint64_t bz4 : 1; // {BZ, 4} + uint64_t rx : 5; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4} + uint64_t gz4 : 1; // {GZ, 4} + uint64_t gy : 4; // {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3} + uint64_t gx : 6; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, {GX, 5} + uint64_t gz : 4; // {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3} + uint64_t bx : 5; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4} + uint64_t bz1 : 1; // {BZ, 1} + uint64_t by : 3; // {BY, 0}, {BY, 1}, {BY, 2} + uint64_t by3 : 1; // {BY, 3} + uint64_t ry : 5; // {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4} + uint64_t bz2 : 1; // {BZ, 2} + uint64_t rz : 5; // {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4} + uint64_t bz3 : 1; // {BZ, 3} + uint64_t d : 5; // { D, 0}, { D, 1}, { D, 2}, { D, 3}, { D, 4} + uint64_t indices : 46; + }; + static_assert(sizeof(bc6h_mode8) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw), int(m->gw), int(m->bw)); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + XMINT3 e1_A(int(m->ry), + int(m->gy | (m->gy4 << 4) | (m->gy5 << 5)), + int(m->by | (m->by3 << 3) | (m->by4 << 4))); + XMINT3 e1_B(int(m->rz), + int(m->gz | (m->gz4 << 4) | (m->gz5 << 5)), + int(m->bz0 | (m->bz1 << 1) | (m->bz2 << 2) | (m->bz3 << 3) | (m->bz4 << 4))); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 8); + e0_A.y = SIGN_EXTEND(e0_A.y, 8); + e0_A.z = SIGN_EXTEND(e0_A.z, 8); + + e0_B.x = SIGN_EXTEND(e0_B.x, 5); + e0_B.y = SIGN_EXTEND(e0_B.y, 6); + e0_B.z = SIGN_EXTEND(e0_B.z, 5); + + e1_A.x = SIGN_EXTEND(e1_A.x, 5); + e1_A.y = SIGN_EXTEND(e1_A.y, 6); + e1_A.z = SIGN_EXTEND(e1_A.z, 5); + + e1_B.x = SIGN_EXTEND(e1_B.x, 5); + e1_B.y = SIGN_EXTEND(e1_B.y, 6); + e1_B.z = SIGN_EXTEND(e1_B.z, 5); + } + + wprintf(L"\tMode 8 - [8 5 6 5] shape %I64u\n", m->d); + wprintf(L"\t E0(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E0(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t E1(A): (%04X, %04X, %04X)\n", e1_A.x & 0xFFFF, e1_A.y & 0xFFFF, e1_A.z & 0xFFFF); + wprintf(L"\t E1(B): (%04X, %04X, %04X)\n", e1_B.x & 0xFFFF, e1_B.y & 0xFFFF, e1_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex3bpp(m->indices, 1, m->d); + wprintf(L"\n"); + } + break; + + case 0x1A: + // Mode 9 (5 bits, 11010) + { + struct bc6h_mode9 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 8; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7} + uint64_t bz1 : 1; // {BZ, 1} + uint64_t by4 : 1; // {BY, 4} + uint64_t gw : 8; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7} + uint64_t by5 : 1; // {BY, 5} + uint64_t gy4 : 1; // {GY, 4} + uint64_t bw : 8; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7} + uint64_t bz5 : 1; // {BZ, 5} + uint64_t bz4 : 1; // {BZ, 4} + uint64_t rx : 5; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4} + uint64_t gz4 : 1; // {GZ, 4} + uint64_t gy : 4; // {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3} + uint64_t gx : 5; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4} + uint64_t bz0 : 1; // {BZ, 0} + uint64_t gz : 4; // {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3} + uint64_t bx : 6; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, {BX, 5} + uint64_t by : 3; // {BY, 0}, {BY, 1}, {BY, 2} + uint64_t by3 : 1; // {BY, 3} + uint64_t ry : 5; // {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4} + uint64_t bz2 : 1; // {BZ, 2} + uint64_t rz : 5; // {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4} + uint64_t bz3 : 1; // {BZ, 3} + uint64_t d : 5; // { D, 0}, { D, 1}, { D, 2}, { D, 3}, { D, 4} + uint64_t indices : 46; + }; + static_assert(sizeof(bc6h_mode9) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw), int(m->gw), int(m->bw)); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + XMINT3 e1_A(int(m->ry), + int(m->gy | (m->gy4 << 4)), + int(m->by | (m->by3 << 3) | (m->by4 << 4) | (m->by5 << 5))); + XMINT3 e1_B(int(m->rz), + int(m->gz | (m->gz4 << 4)), + int(m->bz0 | (m->bz1 << 1) | (m->bz2 << 2) | (m->bz3 << 3) | (m->bz4 << 4) | (m->bz5 << 5))); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 8); + e0_A.y = SIGN_EXTEND(e0_A.y, 8); + e0_A.z = SIGN_EXTEND(e0_A.z, 8); + + e0_B.x = SIGN_EXTEND(e0_B.x, 5); + e0_B.y = SIGN_EXTEND(e0_B.y, 5); + e0_B.z = SIGN_EXTEND(e0_B.z, 6); + + e1_A.x = SIGN_EXTEND(e1_A.x, 5); + e1_A.y = SIGN_EXTEND(e1_A.y, 5); + e1_A.z = SIGN_EXTEND(e1_A.z, 6); + + e1_B.x = SIGN_EXTEND(e1_B.x, 5); + e1_B.y = SIGN_EXTEND(e1_B.y, 5); + e1_B.z = SIGN_EXTEND(e1_B.z, 6); + } + + wprintf(L"\tMode 9 - [8 5 5 6] shape %I64u\n", m->d); + wprintf(L"\t E0(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E0(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t E1(A): (%04X, %04X, %04X)\n", e1_A.x & 0xFFFF, e1_A.y & 0xFFFF, e1_A.z & 0xFFFF); + wprintf(L"\t E1(B): (%04X, %04X, %04X)\n", e1_B.x & 0xFFFF, e1_B.y & 0xFFFF, e1_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex3bpp(m->indices, 1, m->d); + wprintf(L"\n"); + } + break; + + case 0x1E: + // Mode 10 (5 bits, 11110) + { + struct bc6h_mode10 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 6; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5} + uint64_t gz4 : 1; // {GZ, 4} + uint64_t bz : 2; // {BZ, 0}, {BZ, 1} + uint64_t by4 : 1; // {BY, 4} + uint64_t gw : 6; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5} + uint64_t gy5 : 1; // {GY, 5} + uint64_t by5 : 1; // {BY, 5} + uint64_t bz2 : 1; // {BZ, 2} + uint64_t gy4 : 1; // {GY, 4} + uint64_t bw : 6; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {GZ, 5} + uint64_t bz3 : 1; // {BZ, 3} + uint64_t bz5 : 1; // {BZ, 5} + uint64_t bz4 : 1; // {BZ, 4} + uint64_t rx : 6; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, {RX, 5} + uint64_t gy : 4; // {GY, 0}, {GY, 1}, {GY, 2}, {GY, 3} + uint64_t gx : 6; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, {GX, 5} + uint64_t gz : 4; // {GZ, 0}, {GZ, 1}, {GZ, 2}, {GZ, 3} + uint64_t bx : 6; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, {BX, 5} + uint64_t by : 3; // {BY, 0}, {BY, 1}, {BY, 2} + uint64_t by3 : 1; // {BY, 3} + uint64_t ry : 6; // {RY, 0}, {RY, 1}, {RY, 2}, {RY, 3}, {RY, 4}, {RY, 5} + uint64_t rz : 6; // {RZ, 0}, {RZ, 1}, {RZ, 2}, {RZ, 3}, {RZ, 4}, {RZ, 5} + uint64_t d : 5; // { D, 0}, { D, 1}, { D, 2}, { D, 3}, { D, 4} + uint64_t indices : 46; + }; + static_assert(sizeof(bc6h_mode10) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw), int(m->gw), int(m->bw)); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + XMINT3 e1_A(int(m->ry), + int(m->gy | (m->gy4 << 4) | (m->gy5 << 5)), + int(m->by | (m->by3 << 3) | (m->by4 << 4) | (m->by5 << 5))); + XMINT3 e1_B(int(m->rz), + int(m->gz | (m->gz4 << 4)), + int(m->bz | (m->bz2 << 2) | (m->bz3 << 3) | (m->bz4 << 4) | (m->bz5 << 5))); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 6); + e0_A.y = SIGN_EXTEND(e0_A.y, 6); + e0_A.z = SIGN_EXTEND(e0_A.z, 6); + + e0_B.x = SIGN_EXTEND(e0_B.x, 6); + e0_B.y = SIGN_EXTEND(e0_B.y, 6); + e0_B.z = SIGN_EXTEND(e0_B.z, 6); + + e1_A.x = SIGN_EXTEND(e1_A.x, 6); + e1_A.y = SIGN_EXTEND(e1_A.y, 6); + e1_A.z = SIGN_EXTEND(e1_A.z, 6); + + e1_B.x = SIGN_EXTEND(e1_B.x, 6); + e1_B.y = SIGN_EXTEND(e1_B.y, 6); + e1_B.z = SIGN_EXTEND(e1_B.z, 6); + } + + wprintf(L"\tMode 10 - [6 6 6 6] shape %I64u\n", m->d); + wprintf(L"\t E0(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E0(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t E1(A): (%04X, %04X, %04X)\n", e1_A.x & 0xFFFF, e1_A.y & 0xFFFF, e1_A.z & 0xFFFF); + wprintf(L"\t E1(B): (%04X, %04X, %04X)\n", e1_B.x & 0xFFFF, e1_B.y & 0xFFFF, e1_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex3bpp(m->indices, 1, m->d); + wprintf(L"\n"); + } + break; + + case 0x03: + // Mode 11 (5 bits, 00011) + { + struct bc6h_mode11 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 10; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9} + uint64_t gw : 10; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9} + uint64_t bw : 10; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9} + uint64_t rx : 10; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, {RX, 5}, {RX, 6}, {RX, 7}, {RX, 8}, {RX, 9} + uint64_t gx : 10; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, {GX, 5}, {GX, 6}, {GX, 7}, {GX, 8}, {GX, 9} + uint64_t bx : 9; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, {BX, 5}, {BX, 6}, {BX, 7}, {BX, 8} + uint64_t bx9 : 1; // {BX, 9} + uint64_t indices : 63; + }; + static_assert(sizeof(bc6h_mode11) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw), int(m->gw), int(m->bw)); + XMINT3 e0_B(int(m->rx), int(m->gx), + int(m->bx | (m->bx9 << 9))); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 10); + e0_A.y = SIGN_EXTEND(e0_A.y, 10); + e0_A.z = SIGN_EXTEND(e0_A.z, 10); + + e0_B.x = SIGN_EXTEND(e0_B.x, 10); + e0_B.y = SIGN_EXTEND(e0_B.y, 10); + e0_B.z = SIGN_EXTEND(e0_B.z, 10); + } + + wprintf(L"\tMode 11 - [10 10]\n"); + wprintf(L"\t E(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex4bpp(m->indices, 0, 0); + wprintf(L"\n"); + } + break; + + case 0x07: + // Mode 12 (5 bits, 00111) + { + struct bc6h_mode12 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 10; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9} + uint64_t gw : 10; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9} + uint64_t bw : 10; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9} + uint64_t rx : 9; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, {RX, 5}, {RX, 6}, {RX, 7}, {RX, 8} + uint64_t rw10 : 1; // {RW,10} + uint64_t gx : 9; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, {GX, 5}, {GX, 6}, {GX, 7}, {GX, 8} + uint64_t gw10 : 1; // {GW,10} + uint64_t bx : 9; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, {BX, 5}, {BX, 6}, {BX, 7}, {BX, 8} + uint64_t bw10 : 1; // {BW,10} + uint64_t indices : 63; + }; + static_assert(sizeof(bc6h_mode12) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw | (m->rw10 << 10)), + int(m->gw | (m->gw10 << 10)), + int(m->bw | (m->bw10 << 10))); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 11); + e0_A.y = SIGN_EXTEND(e0_A.y, 11); + e0_A.z = SIGN_EXTEND(e0_A.z, 11); + + e0_B.x = SIGN_EXTEND(e0_B.x, 9); + e0_B.y = SIGN_EXTEND(e0_B.y, 9); + e0_B.z = SIGN_EXTEND(e0_B.z, 9); + } + + wprintf(L"\tMode 12 - [11 9]\n"); + wprintf(L"\t E(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex4bpp(m->indices, 0, 0); + wprintf(L"\n"); + } + break; + + case 0x0B: + // Mode 13 (5 bits, 01011) + { + struct bc6h_mode13 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 10; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9} + uint64_t gw : 10; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9} + uint64_t bw : 10; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9} + uint64_t rx : 8; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3}, {RX, 4}, {RX, 5}, {RX, 6}, {RX, 7} + uint64_t rw11 : 1; // {RW,11} + uint64_t rw10 : 1; // {RW,10} + uint64_t gx : 8; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3}, {GX, 4}, {GX, 5}, {GX, 6}, {GX, 7} + uint64_t gw11 : 1; // {GW,11} + uint64_t gw10 : 1; // {GW,10} + uint64_t bx : 8; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3}, {BX, 4}, {BX, 5}, {BX, 6}, {BX, 7} + uint64_t bw11 : 1; // {BW,11} + uint64_t bw10 : 1; // {BW,10} + uint64_t indices : 63; + }; + static_assert(sizeof(bc6h_mode13) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw | (m->rw10 << 10) | (m->rw11 << 11)), + int(m->gw | (m->gw10 << 10) | (m->gw11 << 11)), + int(m->bw | (m->bw10 << 10) | (m->bw11 << 11))); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 12); + e0_A.y = SIGN_EXTEND(e0_A.y, 12); + e0_A.z = SIGN_EXTEND(e0_A.z, 12); + + e0_B.x = SIGN_EXTEND(e0_B.x, 8); + e0_B.y = SIGN_EXTEND(e0_B.y, 8); + e0_B.z = SIGN_EXTEND(e0_B.z, 8); + } + + wprintf(L"\tMode 13 - [12 8]\n"); + wprintf(L"\t E(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex4bpp(m->indices, 0, 0); + wprintf(L"\n"); + } + break; + + case 0x0F: + // Mode 14 (5 bits, 01111) + { + struct bc6h_mode14 + { + uint64_t mode : 5; // { M, 0}, { M, 1}, { M, 2}, { M, 3}, { M, 4} + uint64_t rw : 10; // {RW, 0}, {RW, 1}, {RW, 2}, {RW, 3}, {RW, 4}, {RW, 5}, {RW, 6}, {RW, 7}, {RW, 8}, {RW, 9} + uint64_t gw : 10; // {GW, 0}, {GW, 1}, {GW, 2}, {GW, 3}, {GW, 4}, {GW, 5}, {GW, 6}, {GW, 7}, {GW, 8}, {GW, 9} + uint64_t bw : 10; // {BW, 0}, {BW, 1}, {BW, 2}, {BW, 3}, {BW, 4}, {BW, 5}, {BW, 6}, {BW, 7}, {BW, 8}, {BW, 9} + uint64_t rx : 4; // {RX, 0}, {RX, 1}, {RX, 2}, {RX, 3} + uint64_t rw15 : 1; // {RW,15} + uint64_t rw14 : 1; // {RW,14} + uint64_t rw13 : 1; // {RW,13} + uint64_t rw12 : 1; // {RW,12} + uint64_t rw11 : 1; // {RW,11} + uint64_t rw10 : 1; // {RW,10} + uint64_t gx : 4; // {GX, 0}, {GX, 1}, {GX, 2}, {GX, 3} + uint64_t gw15 : 1; // {GW,15} + uint64_t gw14 : 1; // {GW,14} + uint64_t gw13 : 1; // {GW,13} + uint64_t gw12 : 1; // {GW,12} + uint64_t gw11 : 1; // {GW,11} + uint64_t gw10 : 1; // {GW,10} + uint64_t bx : 4; // {BX, 0}, {BX, 1}, {BX, 2}, {BX, 3} + uint64_t bw15 : 1; // {BW,15} + uint64_t bw14 : 1; // {BW,14} + uint64_t bw13 : 1; // {BW,13} + uint64_t bw12 : 1; // {BW,12} + uint64_t bw11 : 1; // {BW,11} + uint64_t bw10 : 1; // {BW,10} + uint64_t indices : 63; + }; + static_assert(sizeof(bc6h_mode14) == 16, "Block size must be 16 bytes"); + + bool bSigned = (image.format == DXGI_FORMAT_BC6H_SF16) ? true : false; + + auto m = reinterpret_cast(sptr); + + XMINT3 e0_A(int(m->rw | (m->rw10 << 10) | (m->rw11 << 11) | (m->rw12 << 12) | (m->rw13 << 13) | (m->rw14 << 14) | (m->rw15 << 15)), + int(m->gw | (m->gw10 << 10) | (m->gw11 << 11) | (m->gw12 << 12) | (m->gw13 << 13) | (m->gw14 << 14) | (m->gw15 << 15)), + int(m->bw | (m->bw10 << 10) | (m->bw11 << 11) | (m->bw12 << 12) | (m->bw13 << 13) | (m->bw14 << 14) | (m->bw15 << 15))); + XMINT3 e0_B(int(m->rx), int(m->gx), int(m->bx)); + + if (bSigned) + { + e0_A.x = SIGN_EXTEND(e0_A.x, 16); + e0_A.y = SIGN_EXTEND(e0_A.y, 16); + e0_A.z = SIGN_EXTEND(e0_A.z, 16); + + e0_B.x = SIGN_EXTEND(e0_B.x, 4); + e0_B.y = SIGN_EXTEND(e0_B.y, 4); + e0_B.z = SIGN_EXTEND(e0_B.z, 4); + } + + wprintf(L"\tMode 14 - [16 4]\n"); + wprintf(L"\t E(A): (%04X, %04X, %04X)\n", e0_A.x & 0xFFFF, e0_A.y & 0xFFFF, e0_A.z & 0xFFFF); + wprintf(L"\t E(B): (%04X, %04X, %04X)\n", e0_B.x & 0xFFFF, e0_B.y & 0xFFFF, e0_B.z & 0xFFFF); + wprintf(L"\t Index: "); + PrintIndex4bpp(m->indices, 0, 0); + wprintf(L"\n"); + } + break; + + case 0x13: // Reserved mode (5 bits, 10011) + wprintf(L"\tERROR - Reserved mode 10011\n"); + break; + + case 0x17: // Reserved mode (5 bits, 10111) + wprintf(L"\tERROR - Reserved mode 10011\n"); + break; + + case 0x1B: // Reserved mode (5 bits, 11011) + wprintf(L"\tERROR - Reserved mode 11011\n"); + break; + + case 0x1F: // Reserved mode (5 bits, 11111) + wprintf(L"\tERROR - Reserved mode 11111\n"); + break; + } + break; + } + break; + + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + // http://msdn.microsoft.com/en-us/library/windows/desktop/hh308954.aspx + + if (*sptr & 0x01) + { + // Mode 0 (1) + struct bc7_mode0 + { + uint64_t mode : 1; + uint64_t part : 4; + uint64_t r0 : 4; + uint64_t r1 : 4; + uint64_t r2 : 4; + uint64_t r3 : 4; + uint64_t r4 : 4; + uint64_t r5 : 4; + uint64_t g0 : 4; + uint64_t g1 : 4; + uint64_t g2 : 4; + uint64_t g3 : 4; + uint64_t g4 : 4; + uint64_t g5 : 4; + uint64_t b0 : 4; + uint64_t b1 : 4; + uint64_t b2 : 3; + uint64_t b2n : 1; + uint64_t b3 : 4; + uint64_t b4 : 4; + uint64_t b5 : 4; + uint64_t P0 : 1; + uint64_t P1 : 1; + uint64_t P2 : 1; + uint64_t P3 : 1; + uint64_t P4 : 1; + uint64_t P5 : 1; + uint64_t index : 45; + }; + static_assert(sizeof(bc7_mode0) == 16, "Block size must be 16 bytes"); + + auto m = reinterpret_cast(sptr); + + wprintf(L"\tMode 0 - [4 4 4] partition %I64u\n", m->part); + wprintf(L"\t E0:(%0.3f, %0.3f, %0.3f)\n", float((m->r0 << 1) | m->P0) / 31.f, float((m->g0 << 1) | m->P0) / 31.f, float((m->b0 << 1) | m->P0) / 31.f); + wprintf(L"\t E1:(%0.3f, %0.3f, %0.3f)\n", float((m->r1 << 1) | m->P1) / 31.f, float((m->g1 << 1) | m->P1) / 31.f, float((m->b1 << 1) | m->P1) / 31.f); + wprintf(L"\t E2:(%0.3f, %0.3f, %0.3f)\n", float((m->r2 << 1) | m->P2) / 31.f, float((m->g2 << 1) | m->P2) / 31.f, float(((m->b2 | (m->b2n << 3)) << 1) | m->P2) / 31.f); + wprintf(L"\t E3:(%0.3f, %0.3f, %0.3f)\n", float((m->r3 << 1) | m->P3) / 31.f, float((m->g3 << 1) | m->P3) / 31.f, float((m->b3 << 1) | m->P3) / 31.f); + wprintf(L"\t E4:(%0.3f, %0.3f, %0.3f)\n", float((m->r4 << 1) | m->P4) / 31.f, float((m->g4 << 1) | m->P4) / 31.f, float((m->b4 << 1) | m->P4) / 31.f); + wprintf(L"\t E5:(%0.3f, %0.3f, %0.3f)\n", float((m->r5 << 1) | m->P5) / 31.f, float((m->g5 << 1) | m->P5) / 31.f, float((m->b5 << 1) | m->P5) / 31.f); + wprintf(L"\t Index: "); + PrintIndex2bpp(m->index, 2, m->part); + wprintf(L"\n"); + } + else if (*sptr & 0x02) + { + // Mode 1 (01) + struct bc7_mode1 + { + uint64_t mode : 2; + uint64_t part : 6; + uint64_t r0 : 6; + uint64_t r1 : 6; + uint64_t r2 : 6; + uint64_t r3 : 6; + uint64_t g0 : 6; + uint64_t g1 : 6; + uint64_t g2 : 6; + uint64_t g3 : 6; + uint64_t b0 : 6; + uint64_t b1 : 2; + uint64_t b1n : 4; + uint64_t b2 : 6; + uint64_t b3 : 6; + uint64_t P0 : 1; + uint64_t P1 : 1; + uint64_t index : 46; + }; + static_assert(sizeof(bc7_mode1) == 16, "Block size must be 16 bytes"); + + auto m = reinterpret_cast(sptr); + + wprintf(L"\tMode 1 - [6 6 6] partition %I64u\n", m->part); + wprintf(L"\t E0:(%0.3f, %0.3f, %0.3f)\n", float((m->r0 << 1) | m->P0) / 127.f, float((m->g0 << 1) | m->P0) / 127.f, float((m->b0 << 1) | m->P0) / 127.f); + wprintf(L"\t E1:(%0.3f, %0.3f, %0.3f)\n", float((m->r1 << 1) | m->P0) / 127.f, float((m->g1 << 1) | m->P0) / 127.f, float(((m->b1 | (m->b1n << 2)) << 1) | m->P0) / 127.f); + wprintf(L"\t E2:(%0.3f, %0.3f, %0.3f)\n", float((m->r2 << 1) | m->P1) / 127.f, float((m->g2 << 1) | m->P1) / 127.f, float((m->b2 << 1) | m->P1) / 127.f); + wprintf(L"\t E3:(%0.3f, %0.3f, %0.3f)\n", float((m->r3 << 1) | m->P1) / 127.f, float((m->g3 << 1) | m->P1) / 127.f, float((m->b3 << 1) | m->P1) / 127.f); + wprintf(L"\t Index: "); + PrintIndex3bpp(m->index, 1, m->part); + wprintf(L"\n"); + } + else if (*sptr & 0x04) + { + // Mode 2 (001) + struct bc7_mode2 + { + uint64_t mode : 3; + uint64_t part : 6; + uint64_t r0 : 5; + uint64_t r1 : 5; + uint64_t r2 : 5; + uint64_t r3 : 5; + uint64_t r4 : 5; + uint64_t r5 : 5; + uint64_t g0 : 5; + uint64_t g1 : 5; + uint64_t g2 : 5; + uint64_t g3 : 5; + uint64_t g4 : 5; + uint64_t g5 : 5; + uint64_t b0 : 5; + uint64_t b1 : 5; + uint64_t b2 : 5; + uint64_t b3 : 5; + uint64_t b4 : 5; + uint64_t b5 : 5; + uint64_t index : 29; + }; + static_assert(sizeof(bc7_mode2) == 16, "Block size must be 16 bytes"); + + auto m = reinterpret_cast(sptr); + + wprintf(L"\tMode 2 - [5 5 5] partition %I64u\n", m->part); + wprintf(L"\t E0:(%0.3f, %0.3f, %0.3f)\n", float(m->r0) / 31.f, float(m->g0) / 31.f, float(m->b0) / 31.f); + wprintf(L"\t E1:(%0.3f, %0.3f, %0.3f)\n", float(m->r1) / 31.f, float(m->g1) / 31.f, float(m->b1) / 31.f); + wprintf(L"\t E2:(%0.3f, %0.3f, %0.3f)\n", float(m->r2) / 31.f, float(m->g2) / 31.f, float(m->b2) / 31.f); + wprintf(L"\t E3:(%0.3f, %0.3f, %0.3f)\n", float(m->r3) / 31.f, float(m->g3) / 31.f, float(m->b3) / 31.f); + wprintf(L"\t E4:(%0.3f, %0.3f, %0.3f)\n", float(m->r4) / 31.f, float(m->g4) / 31.f, float(m->b4) / 31.f); + wprintf(L"\t E5:(%0.3f, %0.3f, %0.3f)\n", float(m->r5) / 31.f, float(m->g5) / 31.f, float(m->b5) / 31.f); + wprintf(L"\t Index: "); + PrintIndex2bpp(m->index, 2, m->part); + wprintf(L"\n"); + } + else if (*sptr & 0x08) + { + // Mode 3 (0001) + struct bc7_mode3 + { + uint64_t mode : 4; + uint64_t part : 6; + uint64_t r0 : 7; + uint64_t r1 : 7; + uint64_t r2 : 7; + uint64_t r3 : 7; + uint64_t g0 : 7; + uint64_t g1 : 7; + uint64_t g2 : 7; + uint64_t g3 : 5; + uint64_t g3n : 2; + uint64_t b0 : 7; + uint64_t b1 : 7; + uint64_t b2 : 7; + uint64_t b3 : 7; + uint64_t P0 : 1; + uint64_t P1 : 1; + uint64_t P2 : 1; + uint64_t P3 : 1; + uint64_t index : 30; + }; + static_assert(sizeof(bc7_mode3) == 16, "Block size must be 16 bytes"); + + auto m = reinterpret_cast(sptr); + + wprintf(L"\tMode 3 - [7 7 7] partition %I64u\n", m->part); + wprintf(L"\t E0:(%0.3f, %0.3f, %0.3f)\n", float((m->r0 << 1) | m->P0) / 255.f, float((m->g0 << 1) | m->P0) / 255.f, float((m->b0 << 1) | m->P0) / 255.f); + wprintf(L"\t E1:(%0.3f, %0.3f, %0.3f)\n", float((m->r1 << 1) | m->P1) / 255.f, float((m->g1 << 1) | m->P1) / 255.f, float((m->b1 << 1) | m->P1) / 255.f); + wprintf(L"\t E2:(%0.3f, %0.3f, %0.3f)\n", float((m->r2 << 1) | m->P2) / 255.f, float((m->g2 << 1) | m->P2) / 255.f, float((m->b2 << 1) | m->P2) / 255.f); + wprintf(L"\t E3:(%0.3f, %0.3f, %0.3f)\n", float((m->r3 << 1) | m->P3) / 255.f, float(((m->g3 | (m->g3n << 5)) << 1) | m->P3) / 255.f, float((m->b3 << 1) | m->P3) / 255.f); + wprintf(L"\t Index: "); + PrintIndex2bpp(m->index, 1, m->part); + wprintf(L"\n"); + } + else if (*sptr & 0x10) + { + // Mode 4 (00001) + struct bc7_mode4 + { + uint64_t mode : 5; + uint64_t rot : 2; + uint64_t idx : 1; + uint64_t r0 : 5; + uint64_t r1 : 5; + uint64_t g0 : 5; + uint64_t g1 : 5; + uint64_t b0 : 5; + uint64_t b1 : 5; + uint64_t a0 : 6; + uint64_t a1 : 6; + uint64_t color_index : 14; + uint64_t color_indexn : 17; + uint64_t alpha_index : 47; + }; + static_assert(sizeof(bc7_mode4) == 16, "Block size must be 16 bytes"); + + auto m = reinterpret_cast(sptr); + + wprintf(L"\tMode 4 - [5 5 5 A6] indx mode %ls, rot-bits %I64u%ls\n", m->idx ? L"3-bit" : L"2-bit", m->rot, GetRotBits(m->rot)); + wprintf(L"\t C0:(%0.3f, %0.3f, %0.3f)\n", float(m->r0) / 31.f, float(m->g0) / 31.f, float(m->b0) / 31.f); + wprintf(L"\t C1:(%0.3f, %0.3f, %0.3f)\n", float(m->r1) / 31.f, float(m->g1) / 31.f, float(m->b1) / 31.f); + wprintf(L"\t A0:(%0.3f)\n", float(m->a0) / 63.f); + wprintf(L"\t A1:(%0.3f)\n", float(m->a1) / 63.f); + wprintf(L"\t Colors: "); + + uint64_t color_index = m->color_index | (m->color_indexn << 14); + if (m->idx) + PrintIndex3bpp(color_index, 0, 0); + else + PrintIndex2bpp(color_index, 0, 0); + wprintf(L"\n"); + wprintf(L"\t Alpha: "); + PrintIndex3bpp(m->alpha_index, 0, 0); + wprintf(L"\n"); + } + else if (*sptr & 0x20) + { + // Mode 5 (000001) + struct bc7_mode5 + { + uint64_t mode : 6; + uint64_t rot : 2; + uint64_t r0 : 7; + uint64_t r1 : 7; + uint64_t g0 : 7; + uint64_t g1 : 7; + uint64_t b0 : 7; + uint64_t b1 : 7; + uint64_t a0 : 8; + uint64_t a1 : 6; + uint64_t a1n : 2; + uint64_t color_index : 31; + uint64_t alpha_index : 31; + }; + static_assert(sizeof(bc7_mode5) == 16, "Block size must be 16 bytes"); + + auto m = reinterpret_cast(sptr); + + wprintf(L"\tMode 5 - [7 7 7 A8] rot-bits %I64u%ls\n", m->rot, GetRotBits(m->rot)); + wprintf(L"\t C0:(%0.3f, %0.3f, %0.3f)\n", float(m->r0) / 127.f, float(m->g0) / 127.f, float(m->b0) / 127.f); + wprintf(L"\t C1:(%0.3f, %0.3f, %0.3f)\n", float(m->r1) / 127.f, float(m->g1) / 127.f, float(m->b1) / 127.f); + wprintf(L"\t A0:(%0.3f)\n", float(m->a0) / 255.f); + wprintf(L"\t A1:(%0.3f)\n", float(m->a1 | (m->a1n << 6)) / 255.f); + wprintf(L"\t Colors: "); + PrintIndex2bpp(m->color_index, 0, 0); + wprintf(L"\n"); + wprintf(L"\t Alpha: "); + PrintIndex2bpp(m->alpha_index, 0, 0); + wprintf(L"\n"); + } + else if (*sptr & 0x40) + { + // Mode 6 (0000001) + struct bc7_mode6 + { + uint64_t mode : 7; + uint64_t r0 : 7; + uint64_t r1 : 7; + uint64_t g0 : 7; + uint64_t g1 : 7; + uint64_t b0 : 7; + uint64_t b1 : 7; + uint64_t a0 : 7; + uint64_t a1 : 7; + uint64_t P0 : 1; + uint64_t P1 : 1; + uint64_t index : 63; + + }; + static_assert(sizeof(bc7_mode6) == 16, "Block size must be 16 bytes"); + + auto m = reinterpret_cast(sptr); + + wprintf(L"\tMode 6 - [7 7 7 A7]\n"); + wprintf(L"\t C0:(%0.3f, %0.3f, %0.3f)\n", float((m->r0 << 1) | m->P0) / 255.f, float((m->g0 << 1) | m->P0) / 255.f, float((m->b0 << 1) | m->P0) / 255.f); + wprintf(L"\t C1:(%0.3f, %0.3f, %0.3f)\n", float((m->r1 << 1) | m->P1) / 255.f, float((m->g1 << 1) | m->P1) / 255.f, float((m->b1 << 1) | m->P1) / 255.f); + wprintf(L"\t A0:(%0.3f)\n", float((m->a0 << 1) | m->P0) / 255.f); + wprintf(L"\t A1:(%0.3f)\n", float((m->a1 << 1) | m->P1) / 255.f); + wprintf(L"\t Index: "); + PrintIndex4bpp(m->index, 0, 0); + wprintf(L"\n"); + } + else if (*sptr & 0x80) + { + // Mode 7 (00000001) + struct bc7_mode7 + { + uint64_t mode : 8; + uint64_t part : 6; + uint64_t r0 : 5; + uint64_t r1 : 5; + uint64_t r2 : 5; + uint64_t r3 : 5; + uint64_t g0 : 5; + uint64_t g1 : 5; + uint64_t g2 : 5; + uint64_t g3 : 5; + uint64_t b0 : 5; + uint64_t b1 : 5; + uint64_t b2 : 5; + uint64_t b3 : 5; + uint64_t a0 : 5; + uint64_t a1 : 5; + uint64_t a2 : 5; + uint64_t a3 : 5; + uint64_t P0 : 1; + uint64_t P1 : 1; + uint64_t P2 : 1; + uint64_t P3 : 1; + uint64_t index : 30; + + }; + static_assert(sizeof(bc7_mode7) == 16, "Block size must be 16 bytes"); + + auto m = reinterpret_cast(sptr); + + wprintf(L"\tMode 7 - [5 5 5 A5] partition %I64u\n", m->part); + wprintf(L"\t C0:(%0.3f, %0.3f, %0.3f)\n", float((m->r0 << 1) | m->P0) / 63.f, float((m->g0 << 1) | m->P0) / 63.f, float((m->b0 << 1) | m->P0) / 63.f); + wprintf(L"\t C1:(%0.3f, %0.3f, %0.3f)\n", float((m->r1 << 1) | m->P1) / 63.f, float((m->g1 << 1) | m->P1) / 63.f, float((m->b1 << 1) | m->P1) / 63.f); + wprintf(L"\t C2:(%0.3f, %0.3f, %0.3f)\n", float((m->r2 << 1) | m->P2) / 63.f, float((m->g2 << 1) | m->P2) / 63.f, float((m->b2 << 1) | m->P2) / 63.f); + wprintf(L"\t C3:(%0.3f, %0.3f, %0.3f)\n", float((m->r3 << 1) | m->P3) / 63.f, float((m->g3 << 1) | m->P3) / 63.f, float((m->b3 << 1) | m->P3) / 63.f); + wprintf(L"\t A0:(%0.3f)\n", float((m->a0 << 1) | m->P0) / 63.f); + wprintf(L"\t A1:(%0.3f)\n", float((m->a1 << 1) | m->P1) / 63.f); + wprintf(L"\t A2:(%0.3f)\n", float((m->a2 << 1) | m->P2) / 63.f); + wprintf(L"\t A3:(%0.3f)\n", float((m->a3 << 1) | m->P3) / 63.f); + wprintf(L"\t Index: "); + PrintIndex4bpp(m->index, 1, m->part); + wprintf(L"\n"); + } + else + { + // Reserved mode 8 (00000000) + wprintf(L"\tERROR - Reserved mode 8\n"); + } + break; + } + } + } + + return S_OK; + } +} + + +//-------------------------------------------------------------------------------------- +// Entry-point +//-------------------------------------------------------------------------------------- +#pragma prefast(disable : 28198, "Command-line tool, frees all memory on exit") + +int __cdecl wmain(_In_ int argc, _In_z_count_(argc) wchar_t* argv[]) +{ + // Parameters and defaults + DWORD dwFilter = TEX_FILTER_DEFAULT; + int pixelx = -1; + int pixely = -1; + DXGI_FORMAT diffFormat = DXGI_FORMAT_B8G8R8A8_UNORM; + DWORD diffFileType = WIC_CODEC_BMP; + wchar_t szOutputFile[MAX_PATH] = { 0 }; + + // Initialize COM (needed for WIC) + HRESULT hr = hr = CoInitializeEx(nullptr, COINIT_MULTITHREADED); + if (FAILED(hr)) + { + wprintf(L"Failed to initialize COM (%08X)\n", hr); + return 1; + } + + // Process command line + if (argc < 2) + { + PrintUsage(); + return 0; + } + + DWORD dwCommand = LookupByName(argv[1], g_pCommands); + switch (dwCommand) + { + case CMD_INFO: + case CMD_ANALYZE: + case CMD_COMPARE: + case CMD_DIFF: + case CMD_DUMPBC: + break; + + default: + wprintf(L"Must use one of: info, analyze, compare, diff, or dumpbc\n\n"); + return 1; + } + + DWORD dwOptions = 0; + std::list conversion; + + for (int iArg = 2; iArg < argc; iArg++) + { + PWSTR pArg = argv[iArg]; + + if (('-' == pArg[0]) || ('/' == pArg[0])) + { + pArg++; + PWSTR pValue; + + for (pValue = pArg; *pValue && (':' != *pValue); pValue++); + + if (*pValue) + *pValue++ = 0; + + DWORD dwOption = LookupByName(pArg, g_pOptions); + + if (!dwOption || (dwOptions & (1 << dwOption))) + { + PrintUsage(); + return 1; + } + + dwOptions |= 1 << dwOption; + + // Handle options with additional value parameter + switch (dwOption) + { + case OPT_FILTER: + case OPT_FORMAT: + case OPT_OUTPUTFILE: + case OPT_TARGET_PIXELX: + case OPT_TARGET_PIXELY: + if (!*pValue) + { + if ((iArg + 1 >= argc)) + { + PrintUsage(); + return 1; + } + + iArg++; + pValue = argv[iArg]; + } + break; + } + + switch (dwOption) + { + case OPT_FORMAT: + if (dwCommand != CMD_DIFF) + { + wprintf(L"-f only valid for use with diff command\n"); + return 1; + } + else + { + diffFormat = (DXGI_FORMAT)LookupByName(pValue, g_pFormats); + if (!diffFormat) + { + wprintf(L"Invalid value specified with -f (%ls)\n", pValue); + return 1; + } + } + break; + + case OPT_FILTER: + dwFilter = LookupByName(pValue, g_pFilters); + if (!dwFilter) + { + wprintf(L"Invalid value specified with -if (%ls)\n", pValue); + return 1; + } + break; + + case OPT_OUTPUTFILE: + if (dwCommand != CMD_DIFF) + { + wprintf(L"-o only valid for use with diff command\n"); + return 1; + } + else + { + wcscpy_s(szOutputFile, MAX_PATH, pValue); + + wchar_t ext[_MAX_EXT]; + _wsplitpath_s(szOutputFile, nullptr, 0, nullptr, 0, nullptr, 0, ext, _MAX_EXT); + + diffFileType = LookupByName(ext, g_pExtFileTypes); + } + break; + + case OPT_TARGET_PIXELX: + if (dwCommand != CMD_DUMPBC) + { + wprintf(L"-targetx only valid with dumpbc command\n"); + return 1; + } + else if (swscanf_s(pValue, L"%d", &pixelx) != 1) + { + wprintf(L"Invalid value for pixel x location (%ls)\n", pValue); + return 1; + } + break; + + case OPT_TARGET_PIXELY: + if (dwCommand != CMD_DUMPBC) + { + wprintf(L"-targety only valid with dumpbc command\n"); + return 1; + } + else if (swscanf_s(pValue, L"%d", &pixely) != 1) + { + wprintf(L"Invalid value for pixel y location (%ls)\n", pValue); + return 1; + } + break; + } + } + else if (wcspbrk(pArg, L"?*") != nullptr) + { + size_t count = conversion.size(); + SearchForFiles(pArg, conversion, (dwOptions & (1 << OPT_RECURSIVE)) != 0); + if (conversion.size() <= count) + { + wprintf(L"No matching files found for %ls\n", pArg); + return 1; + } + } + else + { + SConversion conv; + wcscpy_s(conv.szSrc, MAX_PATH, pArg); + + conversion.push_back(conv); + } + } + + if (conversion.empty()) + { + PrintUsage(); + return 0; + } + + if (~dwOptions & (1 << OPT_NOLOGO)) + PrintLogo(); + + switch (dwCommand) + { + case CMD_COMPARE: + case CMD_DIFF: + // --- Compare/Diff ------------------------------------------------------------ + if (conversion.size() != 2) + { + wprintf(L"ERROR: compare/diff needs exactly two images\n"); + return 1; + } + else + { + auto pImage1 = conversion.cbegin(); + + wprintf(L"1: %ls", pImage1->szSrc); + fflush(stdout); + + TexMetadata info1; + std::unique_ptr image1; + hr = LoadImage(pImage1->szSrc, dwOptions, dwFilter, info1, image1); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + return 1; + } + + auto pImage2 = conversion.cbegin(); + std::advance(pImage2, 1); + + wprintf(L"\n2: %ls", pImage2->szSrc); + fflush(stdout); + + TexMetadata info2; + std::unique_ptr image2; + hr = LoadImage(pImage2->szSrc, dwOptions, dwFilter, info2, image2); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + return 1; + } + + wprintf(L"\n"); + fflush(stdout); + + if (info1.height != info2.height + || info1.width != info2.width) + { + wprintf(L"ERROR: Can only compare/diff images of the same width & height\n"); + return 1; + } + + if (dwCommand == CMD_DIFF) + { + if (!*szOutputFile) + { + wchar_t ext[_MAX_EXT]; + wchar_t fname[_MAX_FNAME]; + _wsplitpath_s(pImage1->szSrc, nullptr, 0, nullptr, 0, fname, _MAX_FNAME, ext, _MAX_EXT); + if (_wcsicmp(ext, L".bmp") == 0) + { + wprintf(L"ERROR: Need to specify output file via -o\n"); + return 1; + } + + _wmakepath_s(szOutputFile, nullptr, nullptr, fname, L".bmp"); + } + + if (image1->GetImageCount() > 1 || image2->GetImageCount() > 1) + wprintf(L"WARNING: ignoring all images but first one in each file\n"); + + ScratchImage diffImage; + hr = Difference(*image1->GetImage(0, 0, 0), *image2->GetImage(0, 0, 0), dwFilter, diffFormat, diffImage); + if (FAILED(hr)) + { + wprintf(L"Failed diffing images (%08X)\n", hr); + return 1; + } + + if (~dwOptions & (1 << OPT_OVERWRITE)) + { + if (GetFileAttributesW(szOutputFile) != INVALID_FILE_ATTRIBUTES) + { + wprintf(L"\nERROR: Output file already exists, use -y to overwrite\n"); + return 1; + } + } + + hr = SaveImage(diffImage.GetImage(0, 0, 0), szOutputFile, diffFileType); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + return 1; + } + + wprintf(L"Difference %ls\n", szOutputFile); + } + else if ((info1.depth == 1 + && info1.arraySize == 1 + && info1.mipLevels == 1) + || info1.depth != info2.depth + || info1.arraySize != info2.arraySize + || info1.mipLevels != info2.mipLevels + || image1->GetImageCount() != image2->GetImageCount()) + { + // Compare single image + if (image1->GetImageCount() > 1 || image2->GetImageCount() > 1) + wprintf(L"WARNING: ignoring all images but first one in each file\n"); + + float mse, mseV[4]; + hr = ComputeMSE(*image1->GetImage(0, 0, 0), *image2->GetImage(0, 0, 0), mse, mseV); + if (FAILED(hr)) + { + wprintf(L"Failed comparing images (%08X)\n", hr); + return 1; + } + + wprintf(L"Result: %f (%f %f %f %f) PSNR %f dB\n", mse, mseV[0], mseV[1], mseV[2], mseV[3], + 10.f * log10f(3.f / (mseV[0] + mseV[1] + mseV[2]))); + } + else + { + // Compare all images + float min_mse = FLT_MAX; + float min_mseV[4] = { FLT_MAX, FLT_MAX, FLT_MAX, FLT_MAX }; + + float max_mse = -FLT_MAX; + float max_mseV[4] = { -FLT_MAX, -FLT_MAX, -FLT_MAX, -FLT_MAX }; + + double sum_mse = 0; + double sum_mseV[4] = { 0, 0, 0, 0 }; + + size_t total_images = 0; + + if (info1.depth > 1) + { + wprintf(L"Results by mip (%3Iu) and slice (%3Iu)\n\n", info1.mipLevels, info1.depth); + + size_t depth = info1.depth; + for (size_t mip = 0; mip < info1.mipLevels; ++mip) + { + for (size_t slice = 0; slice < depth; ++slice) + { + const Image* img1 = image1->GetImage(mip, 0, slice); + const Image* img2 = image2->GetImage(mip, 0, slice); + + if (!img1 + || !img2 + || img1->height != img2->height + || img1->width != img2->width) + { + wprintf(L"ERROR: Unexpected mismatch at slice %3Iu, mip %3Iu\n", slice, mip); + return 1; + } + else + { + float mse, mseV[4]; + hr = ComputeMSE(*img1, *img2, mse, mseV); + if (FAILED(hr)) + { + wprintf(L"Failed comparing images at slice %3Iu, mip %3Iu (%08X)\n", slice, mip, hr); + return 1; + } + + min_mse = std::min(min_mse, mse); + max_mse = std::max(max_mse, mse); + sum_mse += mse; + + for (size_t j = 0; j < 4; ++j) + { + min_mseV[j] = std::min(min_mseV[j], mseV[j]); + max_mseV[j] = std::max(max_mseV[j], mseV[j]); + sum_mseV[j] += mseV[j]; + } + + ++total_images; + + wprintf(L"[%3Iu,%3Iu]: %f (%f %f %f %f) PSNR %f dB\n", mip, slice, mse, mseV[0], mseV[1], mseV[2], mseV[3], + 10.f * log10f(3.f / (mseV[0] + mseV[1] + mseV[2]))); + } + } + + if (depth > 1) + depth >>= 1; + } + } + else + { + wprintf(L"Results by item (%3Iu) and mip (%3Iu)\n\n", info1.arraySize, info1.mipLevels); + + for (size_t item = 0; item < info1.arraySize; ++item) + { + for (size_t mip = 0; mip < info1.mipLevels; ++mip) + { + const Image* img1 = image1->GetImage(mip, item, 0); + const Image* img2 = image2->GetImage(mip, item, 0); + + if (!img1 + || !img2 + || img1->height != img2->height + || img1->width != img2->width) + { + wprintf(L"ERROR: Unexpected mismatch at item %3Iu, mip %3Iu\n", item, mip); + return 1; + } + else + { + float mse, mseV[4]; + hr = ComputeMSE(*img1, *img2, mse, mseV); + if (FAILED(hr)) + { + wprintf(L"Failed comparing images at item %3Iu, mip %3Iu (%08X)\n", item, mip, hr); + return 1; + } + + min_mse = std::min(min_mse, mse); + max_mse = std::max(max_mse, mse); + sum_mse += mse; + + for (size_t j = 0; j < 4; ++j) + { + min_mseV[j] = std::min(min_mseV[j], mseV[j]); + max_mseV[j] = std::max(max_mseV[j], mseV[j]); + sum_mseV[j] += mseV[j]; + } + + ++total_images; + + wprintf(L"[%3Iu,%3Iu]: %f (%f %f %f %f) PSNR %f dB\n", item, mip, mse, mseV[0], mseV[1], mseV[2], mseV[3], + 10.f * log10f(3.f / (mseV[0] + mseV[1] + mseV[2]))); + } + } + } + } + + // Output multi-image stats + if (total_images > 1) + { + wprintf(L"\n Minimum MSE: %f (%f %f %f %f) PSNR %f dB\n", min_mse, min_mseV[0], min_mseV[1], min_mseV[2], min_mseV[3], + 10.f * log10f(3.f / (min_mseV[0] + min_mseV[1] + min_mseV[2]))); + double total_mseV0 = sum_mseV[0] / double(total_images); + double total_mseV1 = sum_mseV[1] / double(total_images); + double total_mseV2 = max_mseV[2] / double(total_images); + wprintf(L" Average MSE: %f (%f %f %f %f) PSNR %f dB\n", sum_mse / double(total_images), + total_mseV0, + total_mseV1, + total_mseV2, + sum_mseV[3] / double(total_images), + 10.0 * log10(3.0 / (total_mseV0 + total_mseV1 + total_mseV2))); + wprintf(L" Maximum MSE: %f (%f %f %f %f) PSNR %f dB\n", max_mse, max_mseV[0], max_mseV[1], max_mseV[2], max_mseV[3], + 10.f * log10f(3.f / (max_mseV[0] + max_mseV[1] + max_mseV[2]))); + } + } + } + break; + + default: + for (auto pConv = conversion.cbegin(); pConv != conversion.cend(); ++pConv) + { + // Load source image + if (pConv != conversion.begin()) + wprintf(L"\n"); + + wprintf(L"%ls", pConv->szSrc); + fflush(stdout); + + TexMetadata info; + std::unique_ptr image; + hr = LoadImage(pConv->szSrc, dwOptions, dwFilter, info, image); + if (FAILED(hr)) + { + wprintf(L" FAILED (%x)\n", hr); + return 1; + } + + wprintf(L"\n"); + fflush(stdout); + + if (dwCommand == CMD_INFO) + { + // --- Info ---------------------------------------------------------------- + wprintf(L" width = %Iu\n", info.width); + wprintf(L" height = %Iu\n", info.height); + wprintf(L" depth = %Iu\n", info.depth); + wprintf(L" mipLevels = %Iu\n", info.mipLevels); + wprintf(L" arraySize = %Iu\n", info.arraySize); + wprintf(L" format = "); + PrintFormat(info.format); + wprintf(L"\n dimension = "); + switch (info.dimension) + { + case TEX_DIMENSION_TEXTURE1D: + wprintf((info.arraySize > 1) ? L"1DArray\n" : L"1D\n"); + break; + + case TEX_DIMENSION_TEXTURE2D: + if (info.IsCubemap()) + { + wprintf((info.arraySize > 6) ? L"CubeArray\n" : L"Cube\n"); + } + else + { + wprintf((info.arraySize > 1) ? L"2DArray\n" : L"2D\n"); + } + break; + + case TEX_DIMENSION_TEXTURE3D: + wprintf(L" 3D"); + break; + } + + wprintf(L" alpha mode = "); + switch (info.GetAlphaMode()) + { + case TEX_ALPHA_MODE_OPAQUE: + wprintf(L"Opaque"); + break; + case TEX_ALPHA_MODE_PREMULTIPLIED: + wprintf(L"Premultiplied"); + break; + case TEX_ALPHA_MODE_STRAIGHT: + wprintf(L"Straight"); + break; + default: + wprintf(L"Unknown"); + break; + } + + wprintf(L"\n images = %Iu\n", image->GetImageCount()); + + auto sizeInKb = static_cast(image->GetPixelsSize() / 1024); + + wprintf(L" pixel size = %u (KB)\n\n", sizeInKb); + } + else if (dwCommand == CMD_DUMPBC) + { + // --- Dump BC ------------------------------------------------------------- + if (!IsCompressed(info.format)) + { + wprintf(L"ERROR: dumpbc only operates on BC format DDS files\n"); + return 1; + } + + if (pixelx >= (int)info.width + || pixely >= (int)info.height) + { + wprintf(L"WARNING: Specified pixel location (%d x %d) is out of range for image (%Iu x %Iu)\n", pixelx, pixely, info.width, info.height); + continue; + } + + wprintf(L"Compression: "); + PrintFormat(info.format); + wprintf(L"\n"); + + if (info.depth > 1) + { + wprintf(L"Results by mip (%3Iu) and slice (%3Iu)\n", info.mipLevels, info.depth); + + size_t depth = info.depth; + for (size_t mip = 0; mip < info.mipLevels; ++mip) + { + for (size_t slice = 0; slice < depth; ++slice) + { + const Image* img = image->GetImage(mip, 0, slice); + + if (!img) + { + wprintf(L"ERROR: Unexpected error at slice %3Iu, mip %3Iu\n", slice, mip); + return 1; + } + else + { + wprintf(L"\n[%3Iu, %3Iu]:\n", mip, slice); + + hr = DumpBCImage(*img, pixelx, pixely); + if (FAILED(hr)) + { + wprintf(L"ERROR: Failed dumping image at slice %3Iu, mip %3Iu (%08X)\n", slice, mip, hr); + return 1; + } + } + } + + if (depth > 1) + depth >>= 1; + + if (pixelx > 0) + pixelx >>= 1; + + if (pixely > 0) + pixely >>= 1; + } + } + else + { + wprintf(L"Results by item (%3Iu) and mip (%3Iu)\n", info.arraySize, info.mipLevels); + + for (size_t item = 0; item < info.arraySize; ++item) + { + int tpixelx = pixelx; + int tpixely = pixely; + + for (size_t mip = 0; mip < info.mipLevels; ++mip) + { + const Image* img = image->GetImage(mip, item, 0); + + if (!img) + { + wprintf(L"ERROR: Unexpected error at item %3Iu, mip %3Iu\n", item, mip); + return 1; + } + else + { + if (image->GetImageCount() > 1) + { + wprintf(L"\n[%3Iu, %3Iu]:\n", item, mip); + } + hr = DumpBCImage(*img, tpixelx, tpixely); + if (FAILED(hr)) + { + wprintf(L"ERROR: Failed dumping image at item %3Iu, mip %3Iu (%08X)\n", item, mip, hr); + return 1; + } + } + + if (tpixelx > 0) + tpixelx >>= 1; + + if (tpixely > 0) + tpixely >>= 1; + } + } + } + } + else + { + // --- Analyze ------------------------------------------------------------- + if (IsPlanar(info.format)) + { + auto img = image->GetImage(0, 0, 0); + assert(img); + size_t nimg = image->GetImageCount(); + + std::unique_ptr timage(new (std::nothrow) ScratchImage); + if (!timage) + { + wprintf(L"\nERROR: Memory allocation failed\n"); + return 1; + } + + hr = ConvertToSinglePlane(img, nimg, info, *timage); + if (FAILED(hr)) + { + wprintf(L" FAILED [converttosingleplane] (%x)\n", hr); + continue; + } + + auto& tinfo = timage->GetMetadata(); + + info.format = tinfo.format; + + assert(info.width == tinfo.width); + assert(info.height == tinfo.height); + assert(info.depth == tinfo.depth); + assert(info.arraySize == tinfo.arraySize); + assert(info.mipLevels == tinfo.mipLevels); + assert(info.miscFlags == tinfo.miscFlags); + assert(info.dimension == tinfo.dimension); + + image.swap(timage); + } + + if (info.depth > 1) + { + wprintf(L"Results by mip (%3Iu) and slice (%3Iu)\n\n", info.mipLevels, info.depth); + + size_t depth = info.depth; + for (size_t mip = 0; mip < info.mipLevels; ++mip) + { + for (size_t slice = 0; slice < depth; ++slice) + { + const Image* img = image->GetImage(mip, 0, slice); + + if (!img) + { + wprintf(L"ERROR: Unexpected error at slice %3Iu, mip %3Iu\n", slice, mip); + return 1; + } + else + { + AnalyzeData data; + hr = Analyze(*img, data); + if (FAILED(hr)) + { + wprintf(L"ERROR: Failed analyzing image at slice %3Iu, mip %3Iu (%08X)\n", slice, mip, hr); + return 1; + } + + wprintf(L"Result slice %3Iu, mip %3Iu:\n", slice, mip); + data.Print(); + } + + if (IsCompressed(info.format)) + { + AnalyzeBCData data; + hr = AnalyzeBC(*img, data); + if (FAILED(hr)) + { + wprintf(L"ERROR: Failed analyzing BC image at slice %3Iu, mip %3Iu (%08X)\n", slice, mip, hr); + return 1; + } + + data.Print(img->format); + } + wprintf(L"\n"); + } + + if (depth > 1) + depth >>= 1; + } + } + else + { + wprintf(L"Results by item (%3Iu) and mip (%3Iu)\n\n", info.arraySize, info.mipLevels); + + for (size_t item = 0; item < info.arraySize; ++item) + { + for (size_t mip = 0; mip < info.mipLevels; ++mip) + { + const Image* img = image->GetImage(mip, item, 0); + + if (!img) + { + wprintf(L"ERROR: Unexpected error at item %3Iu, mip %3Iu\n", item, mip); + return 1; + } + else + { + AnalyzeData data; + hr = Analyze(*img, data); + if (FAILED(hr)) + { + wprintf(L"ERROR: Failed analyzing image at item %3Iu, mip %3Iu (%08X)\n", item, mip, hr); + return 1; + } + + if (image->GetImageCount() > 1) + { + wprintf(L"Result item %3Iu, mip %3Iu:\n", item, mip); + } + data.Print(); + } + + if (IsCompressed(info.format)) + { + AnalyzeBCData data; + hr = AnalyzeBC(*img, data); + if (FAILED(hr)) + { + wprintf(L"ERROR: Failed analyzing BC image at item %3Iu, mip %3Iu (%08X)\n", item, mip, hr); + return 1; + } + + data.Print(img->format); + } + wprintf(L"\n"); + } + } + } + } + } + break; + } + + return 0; +} diff --git a/deps/DirectXTex/Texdiag/texdiag.rc b/deps/DirectXTex/Texdiag/texdiag.rc new file mode 100644 index 0000000..5208ce0 --- /dev/null +++ b/deps/DirectXTex/Texdiag/texdiag.rc @@ -0,0 +1,76 @@ +// Microsoft Visual C++ generated resource script. +// +#define APSTUDIO_READONLY_SYMBOLS +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 2 resource. +// +#define IDC_STATIC -1 +#include + + + +///////////////////////////////////////////////////////////////////////////// +#undef APSTUDIO_READONLY_SYMBOLS + +///////////////////////////////////////////////////////////////////////////// +// English (U.S.) resources + +#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) +#ifdef _WIN32 +LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US +#pragma code_page(1252) +#endif //_WIN32 + +///////////////////////////////////////////////////////////////////////////// +// +// Icon +// + +// Icon with lowest ID value placed first to ensure application icon +// remains consistent on all systems. +IDI_MAIN_ICON ICON "directx.ico" + +#ifdef APSTUDIO_INVOKED +///////////////////////////////////////////////////////////////////////////// +// +// TEXTINCLUDE +// + +1 TEXTINCLUDE +BEGIN + "resource.h\0" +END + +2 TEXTINCLUDE +BEGIN + "#define IDC_STATIC -1\r\n" + "#include \r\n" + "\r\n" + "\r\n" + "\0" +END + +3 TEXTINCLUDE +BEGIN + "\r\n" + "\0" +END + +#endif // APSTUDIO_INVOKED + +#endif // English (U.S.) resources +///////////////////////////////////////////////////////////////////////////// + + + +#ifndef APSTUDIO_INVOKED +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 3 resource. +// + + +///////////////////////////////////////////////////////////////////////////// +#endif // not APSTUDIO_INVOKED + diff --git a/deps/DirectXTex/Texdiag/texdiag_Desktop_2013.vcxproj b/deps/DirectXTex/Texdiag/texdiag_Desktop_2013.vcxproj new file mode 100644 index 0000000..7ef793d --- /dev/null +++ b/deps/DirectXTex/Texdiag/texdiag_Desktop_2013.vcxproj @@ -0,0 +1,407 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + texdiag + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D} + texdiag + Win32Proj + $(VCTargetsPath11) + + + + Application + Unicode + v120 + + + Application + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + Application + true + Unicode + v120 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texdiag + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texdiag + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + Bin\Desktop_2013\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texdiag/texdiag_Desktop_2013.vcxproj.filters b/deps/DirectXTex/Texdiag/texdiag_Desktop_2013.vcxproj.filters new file mode 100644 index 0000000..3a2f907 --- /dev/null +++ b/deps/DirectXTex/Texdiag/texdiag_Desktop_2013.vcxproj.filters @@ -0,0 +1,17 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texdiag/texdiag_Desktop_2015.vcxproj b/deps/DirectXTex/Texdiag/texdiag_Desktop_2015.vcxproj new file mode 100644 index 0000000..83e5f78 --- /dev/null +++ b/deps/DirectXTex/Texdiag/texdiag_Desktop_2015.vcxproj @@ -0,0 +1,406 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + texdiag + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D} + texdiag + Win32Proj + + + + Application + Unicode + v140 + + + Application + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + Application + true + Unicode + v140 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texdiag + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texdiag + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + Bin\Desktop_2015\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texdiag/texdiag_Desktop_2015.vcxproj.filters b/deps/DirectXTex/Texdiag/texdiag_Desktop_2015.vcxproj.filters new file mode 100644 index 0000000..3a2f907 --- /dev/null +++ b/deps/DirectXTex/Texdiag/texdiag_Desktop_2015.vcxproj.filters @@ -0,0 +1,17 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texdiag/texdiag_Desktop_2017.vcxproj b/deps/DirectXTex/Texdiag/texdiag_Desktop_2017.vcxproj new file mode 100644 index 0000000..29129fe --- /dev/null +++ b/deps/DirectXTex/Texdiag/texdiag_Desktop_2017.vcxproj @@ -0,0 +1,413 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + texdiag + {8E31A619-F4F8-413F-A973-4EE37B1AAA5D} + texdiag + Win32Proj + 10.0.15063.0 + + + + Application + Unicode + v141 + + + Application + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + Application + true + Unicode + v141 + + + + + + + + + + + + + + + + + + + + + + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texdiag + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texdiag + true + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + Bin\Desktop_2017\$(Platform)\$(Configuration)\ + texdiag + false + true + $(ExecutablePath) + $(IncludePath) + $(LibraryPath) + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EditAndContinue + EnableFastChecks + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + false + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + EnableFastChecks + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + Console + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + StreamingSIMDExtensions2 + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX86 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + MultiThreadedDLL + false + true + true + Fast + Sync + ..\DirectXTex;%(AdditionalIncludeDirectories) + /permissive- %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_CONSOLE;D3DXFX_LARGEADDRESS_HANDLE;_WIN32_WINNT=0x0600;%(PreprocessorDefinitions) + 4996 + + + %(AdditionalOptions) + ole32.lib;windowscodecs.lib;uuid.lib;%(AdditionalDependencies) + true + Console + true + true + true + true + true + MachineX64 + AsInvoker + %(DelayLoadDLLs) + + + false + + + + + + + + + + + + + + + + + + + {371b9fa9-4c90-4ac6-a123-aced756d6c77} + + + + + + + \ No newline at end of file diff --git a/deps/DirectXTex/Texdiag/texdiag_Desktop_2017.vcxproj.filters b/deps/DirectXTex/Texdiag/texdiag_Desktop_2017.vcxproj.filters new file mode 100644 index 0000000..3a2f907 --- /dev/null +++ b/deps/DirectXTex/Texdiag/texdiag_Desktop_2017.vcxproj.filters @@ -0,0 +1,17 @@ + + + + + {8e114980-c1a3-4ada-ad7c-83caadf5daeb} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + Resource Files + + + \ No newline at end of file diff --git a/deps/DirectXTex/WICTextureLoader/WICTextureLoader.cpp b/deps/DirectXTex/WICTextureLoader/WICTextureLoader.cpp new file mode 100644 index 0000000..260f44e --- /dev/null +++ b/deps/DirectXTex/WICTextureLoader/WICTextureLoader.cpp @@ -0,0 +1,934 @@ +//-------------------------------------------------------------------------------------- +// File: WICTextureLoader.cpp +// +// Function for loading a WIC image and creating a Direct3D runtime texture for it +// (auto-generating mipmaps if possible) +// +// Note: Assumes application has already called CoInitializeEx +// +// Warning: CreateWICTexture* functions are not thread-safe if given a d3dContext instance for +// auto-gen mipmap support. +// +// Note these functions are useful for images created as simple 2D textures. For +// more complex resources, DDSTextureLoader is an excellent light-weight runtime loader. +// For a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +// We could load multi-frame images (TIFF/GIF) into a texture array. +// For now, we just load the first frame (note: DirectXTex supports multi-frame images) + +#include "WICTextureLoader.h" + +#include +#include + +#include + +#include + +#include +#include + +#if !defined(NO_D3D11_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) +#pragma comment(lib,"dxguid.lib") +#endif + +using namespace DirectX; +using Microsoft::WRL::ComPtr; + +namespace +{ + //-------------------------------------------------------------------------------------- + template + inline void SetDebugObjectName(_In_ ID3D11DeviceChild* resource, _In_ const char(&name)[TNameLength]) + { +#if !defined(NO_D3D11_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) + resource->SetPrivateData(WKPDID_D3DDebugObjectName, TNameLength - 1, name); +#else + UNREFERENCED_PARAMETER(resource); + UNREFERENCED_PARAMETER(name); +#endif + } + + //------------------------------------------------------------------------------------- + // WIC Pixel Format Translation Data + //------------------------------------------------------------------------------------- + struct WICTranslate + { + GUID wic; + DXGI_FORMAT format; + }; + + const WICTranslate g_WICFormats[] = + { + { GUID_WICPixelFormat128bppRGBAFloat, DXGI_FORMAT_R32G32B32A32_FLOAT }, + + { GUID_WICPixelFormat64bppRGBAHalf, DXGI_FORMAT_R16G16B16A16_FLOAT }, + { GUID_WICPixelFormat64bppRGBA, DXGI_FORMAT_R16G16B16A16_UNORM }, + + { GUID_WICPixelFormat32bppRGBA, DXGI_FORMAT_R8G8B8A8_UNORM }, + { GUID_WICPixelFormat32bppBGRA, DXGI_FORMAT_B8G8R8A8_UNORM }, // DXGI 1.1 + { GUID_WICPixelFormat32bppBGR, DXGI_FORMAT_B8G8R8X8_UNORM }, // DXGI 1.1 + + { GUID_WICPixelFormat32bppRGBA1010102XR, DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM }, // DXGI 1.1 + { GUID_WICPixelFormat32bppRGBA1010102, DXGI_FORMAT_R10G10B10A2_UNORM }, + + { GUID_WICPixelFormat16bppBGRA5551, DXGI_FORMAT_B5G5R5A1_UNORM }, + { GUID_WICPixelFormat16bppBGR565, DXGI_FORMAT_B5G6R5_UNORM }, + + { GUID_WICPixelFormat32bppGrayFloat, DXGI_FORMAT_R32_FLOAT }, + { GUID_WICPixelFormat16bppGrayHalf, DXGI_FORMAT_R16_FLOAT }, + { GUID_WICPixelFormat16bppGray, DXGI_FORMAT_R16_UNORM }, + { GUID_WICPixelFormat8bppGray, DXGI_FORMAT_R8_UNORM }, + + { GUID_WICPixelFormat8bppAlpha, DXGI_FORMAT_A8_UNORM }, + }; + + //------------------------------------------------------------------------------------- + // WIC Pixel Format nearest conversion table + //------------------------------------------------------------------------------------- + + struct WICConvert + { + GUID source; + GUID target; + }; + + const WICConvert g_WICConvert[] = + { + // Note target GUID in this conversion table must be one of those directly supported formats (above). + + { GUID_WICPixelFormatBlackWhite, GUID_WICPixelFormat8bppGray }, // DXGI_FORMAT_R8_UNORM + + { GUID_WICPixelFormat1bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat2bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat4bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat8bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + + { GUID_WICPixelFormat2bppGray, GUID_WICPixelFormat8bppGray }, // DXGI_FORMAT_R8_UNORM + { GUID_WICPixelFormat4bppGray, GUID_WICPixelFormat8bppGray }, // DXGI_FORMAT_R8_UNORM + + { GUID_WICPixelFormat16bppGrayFixedPoint, GUID_WICPixelFormat16bppGrayHalf }, // DXGI_FORMAT_R16_FLOAT + { GUID_WICPixelFormat32bppGrayFixedPoint, GUID_WICPixelFormat32bppGrayFloat }, // DXGI_FORMAT_R32_FLOAT + + { GUID_WICPixelFormat16bppBGR555, GUID_WICPixelFormat16bppBGRA5551 }, // DXGI_FORMAT_B5G5R5A1_UNORM + + { GUID_WICPixelFormat32bppBGR101010, GUID_WICPixelFormat32bppRGBA1010102 }, // DXGI_FORMAT_R10G10B10A2_UNORM + + { GUID_WICPixelFormat24bppBGR, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat24bppRGB, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat32bppPBGRA, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat32bppPRGBA, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + + { GUID_WICPixelFormat48bppRGB, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat48bppBGR, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppBGRA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPRGBA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPBGRA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + + { GUID_WICPixelFormat48bppRGBFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat48bppBGRFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBAFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppBGRAFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat48bppRGBHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + + { GUID_WICPixelFormat128bppPRGBAFloat, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBFloat, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBAFixedPoint, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBFixedPoint, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat32bppRGBE, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + + { GUID_WICPixelFormat32bppCMYK, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat64bppCMYK, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat40bppCMYKAlpha, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat80bppCMYKAlpha, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + + #if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + { GUID_WICPixelFormat32bppRGB, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat64bppRGB, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPRGBAHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + #endif + + // We don't support n-channel formats + }; + + bool g_WIC2 = false; + + //-------------------------------------------------------------------------------------- + IWICImagingFactory* _GetWIC() + { + static INIT_ONCE s_initOnce = INIT_ONCE_STATIC_INIT; + + IWICImagingFactory* factory = nullptr; + InitOnceExecuteOnce(&s_initOnce, + [](PINIT_ONCE, PVOID, PVOID *factory) -> BOOL + { +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + HRESULT hr = CoCreateInstance( + CLSID_WICImagingFactory2, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory2), + factory + ); + + if (SUCCEEDED(hr)) + { + // WIC2 is available on Windows 10, Windows 8.x, and Windows 7 SP1 with KB 2670838 installed + g_WIC2 = true; + return TRUE; + } + else + { + hr = CoCreateInstance( + CLSID_WICImagingFactory1, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + factory + ); + return SUCCEEDED(hr) ? TRUE : FALSE; + } +#else + return SUCCEEDED(CoCreateInstance( + CLSID_WICImagingFactory, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + factory)) ? TRUE : FALSE; +#endif + }, nullptr, reinterpret_cast(&factory)); + + return factory; + } + + //--------------------------------------------------------------------------------- + DXGI_FORMAT _WICToDXGI(const GUID& guid) + { + for (size_t i = 0; i < _countof(g_WICFormats); ++i) + { + if (memcmp(&g_WICFormats[i].wic, &guid, sizeof(GUID)) == 0) + return g_WICFormats[i].format; + } + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + if (g_WIC2) + { + if (memcmp(&GUID_WICPixelFormat96bppRGBFloat, &guid, sizeof(GUID)) == 0) + return DXGI_FORMAT_R32G32B32_FLOAT; + } +#endif + + return DXGI_FORMAT_UNKNOWN; + } + + //--------------------------------------------------------------------------------- + size_t _WICBitsPerPixel(REFGUID targetGuid) + { + auto pWIC = _GetWIC(); + if (!pWIC) + return 0; + + ComPtr cinfo; + if (FAILED(pWIC->CreateComponentInfo(targetGuid, cinfo.GetAddressOf()))) + return 0; + + WICComponentType type; + if (FAILED(cinfo->GetComponentType(&type))) + return 0; + + if (type != WICPixelFormat) + return 0; + + ComPtr pfinfo; + if (FAILED(cinfo.As(&pfinfo))) + return 0; + + UINT bpp; + if (FAILED(pfinfo->GetBitsPerPixel(&bpp))) + return 0; + + return bpp; + } + + + //-------------------------------------------------------------------------------------- + DXGI_FORMAT MakeSRGB(_In_ DXGI_FORMAT format) + { + switch (format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + return DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + + case DXGI_FORMAT_BC1_UNORM: + return DXGI_FORMAT_BC1_UNORM_SRGB; + + case DXGI_FORMAT_BC2_UNORM: + return DXGI_FORMAT_BC2_UNORM_SRGB; + + case DXGI_FORMAT_BC3_UNORM: + return DXGI_FORMAT_BC3_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + return DXGI_FORMAT_B8G8R8A8_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + return DXGI_FORMAT_B8G8R8X8_UNORM_SRGB; + + case DXGI_FORMAT_BC7_UNORM: + return DXGI_FORMAT_BC7_UNORM_SRGB; + + default: + return format; + } + } + + + //--------------------------------------------------------------------------------- + HRESULT CreateTextureFromWIC(_In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_ IWICBitmapFrameDecode *frame, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ unsigned int loadFlags, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView) + { + UINT width, height; + HRESULT hr = frame->GetSize(&width, &height); + if (FAILED(hr)) + return hr; + + assert(width > 0 && height > 0); + + if (!maxsize) + { + // This is a bit conservative because the hardware could support larger textures than + // the Feature Level defined minimums, but doing it this way is much easier and more + // performant for WIC than the 'fail and retry' model used by DDSTextureLoader + + switch (d3dDevice->GetFeatureLevel()) + { + case D3D_FEATURE_LEVEL_9_1: + case D3D_FEATURE_LEVEL_9_2: + maxsize = 2048 /*D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + + case D3D_FEATURE_LEVEL_9_3: + maxsize = 4096 /*D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + + case D3D_FEATURE_LEVEL_10_0: + case D3D_FEATURE_LEVEL_10_1: + maxsize = 8192 /*D3D10_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + + default: + maxsize = D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION; + break; + } + } + + assert(maxsize > 0); + + UINT twidth, theight; + if (width > maxsize || height > maxsize) + { + float ar = static_cast(height) / static_cast(width); + if (width > height) + { + twidth = static_cast(maxsize); + theight = std::max(1, static_cast(static_cast(maxsize) * ar)); + } + else + { + theight = static_cast(maxsize); + twidth = std::max(1, static_cast(static_cast(maxsize) / ar)); + } + assert(twidth <= maxsize && theight <= maxsize); + } + else + { + twidth = width; + theight = height; + } + + // Determine format + WICPixelFormatGUID pixelFormat; + hr = frame->GetPixelFormat(&pixelFormat); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID convertGUID; + memcpy(&convertGUID, &pixelFormat, sizeof(WICPixelFormatGUID)); + + size_t bpp = 0; + + DXGI_FORMAT format = _WICToDXGI(pixelFormat); + if (format == DXGI_FORMAT_UNKNOWN) + { + if (memcmp(&GUID_WICPixelFormat96bppRGBFixedPoint, &pixelFormat, sizeof(WICPixelFormatGUID)) == 0) + { +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + if (g_WIC2) + { + memcpy(&convertGUID, &GUID_WICPixelFormat96bppRGBFloat, sizeof(WICPixelFormatGUID)); + format = DXGI_FORMAT_R32G32B32_FLOAT; + bpp = 96; + } + else +#endif + { + memcpy(&convertGUID, &GUID_WICPixelFormat128bppRGBAFloat, sizeof(WICPixelFormatGUID)); + format = DXGI_FORMAT_R32G32B32A32_FLOAT; + bpp = 128; + } + } + else + { + for (size_t i = 0; i < _countof(g_WICConvert); ++i) + { + if (memcmp(&g_WICConvert[i].source, &pixelFormat, sizeof(WICPixelFormatGUID)) == 0) + { + memcpy(&convertGUID, &g_WICConvert[i].target, sizeof(WICPixelFormatGUID)); + + format = _WICToDXGI(g_WICConvert[i].target); + assert(format != DXGI_FORMAT_UNKNOWN); + bpp = _WICBitsPerPixel(convertGUID); + break; + } + } + } + + if (format == DXGI_FORMAT_UNKNOWN) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + else + { + bpp = _WICBitsPerPixel(pixelFormat); + } + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + if ((format == DXGI_FORMAT_R32G32B32_FLOAT) && d3dContext != 0 && textureView != 0) + { + // Special case test for optional device support for autogen mipchains for R32G32B32_FLOAT + UINT fmtSupport = 0; + hr = d3dDevice->CheckFormatSupport(DXGI_FORMAT_R32G32B32_FLOAT, &fmtSupport); + if (FAILED(hr) || !(fmtSupport & D3D11_FORMAT_SUPPORT_MIP_AUTOGEN)) + { + // Use R32G32B32A32_FLOAT instead which is required for Feature Level 10.0 and up + memcpy(&convertGUID, &GUID_WICPixelFormat128bppRGBAFloat, sizeof(WICPixelFormatGUID)); + format = DXGI_FORMAT_R32G32B32A32_FLOAT; + bpp = 128; + } + } +#endif + + if (!bpp) + return E_FAIL; + + // Handle sRGB formats + if (loadFlags & WIC_LOADER_FORCE_SRGB) + { + format = MakeSRGB(format); + } + else if (!(loadFlags & WIC_LOADER_IGNORE_SRGB)) + { + ComPtr metareader; + if (SUCCEEDED(frame->GetMetadataQueryReader(metareader.GetAddressOf()))) + { + GUID containerFormat; + if (SUCCEEDED(metareader->GetContainerFormat(&containerFormat))) + { + // Check for sRGB colorspace metadata + bool sRGB = false; + + PROPVARIANT value; + PropVariantInit(&value); + + if (memcmp(&containerFormat, &GUID_ContainerFormatPng, sizeof(GUID)) == 0) + { + // Check for sRGB chunk + if (SUCCEEDED(metareader->GetMetadataByName(L"/sRGB/RenderingIntent", &value)) && value.vt == VT_UI1) + { + sRGB = true; + } + } + else if (SUCCEEDED(metareader->GetMetadataByName(L"System.Image.ColorSpace", &value)) && value.vt == VT_UI2 && value.uiVal == 1) + { + sRGB = true; + } + + (void)PropVariantClear(&value); + + if (sRGB) + format = MakeSRGB(format); + } + } + } + + // Verify our target format is supported by the current device + // (handles WDDM 1.0 or WDDM 1.1 device driver cases as well as DirectX 11.0 Runtime without 16bpp format support) + UINT support = 0; + hr = d3dDevice->CheckFormatSupport(format, &support); + if (FAILED(hr) || !(support & D3D11_FORMAT_SUPPORT_TEXTURE2D)) + { + // Fallback to RGBA 32-bit format which is supported by all devices + memcpy(&convertGUID, &GUID_WICPixelFormat32bppRGBA, sizeof(WICPixelFormatGUID)); + format = DXGI_FORMAT_R8G8B8A8_UNORM; + bpp = 32; + } + + // Allocate temporary memory for image + size_t rowPitch = (twidth * bpp + 7) / 8; + size_t imageSize = rowPitch * theight; + + std::unique_ptr temp(new (std::nothrow) uint8_t[imageSize]); + if (!temp) + return E_OUTOFMEMORY; + + // Load image data + if (memcmp(&convertGUID, &pixelFormat, sizeof(GUID)) == 0 + && twidth == width + && theight == height) + { + // No format conversion or resize needed + hr = frame->CopyPixels(0, static_cast(rowPitch), static_cast(imageSize), temp.get()); + if (FAILED(hr)) + return hr; + } + else if (twidth != width || theight != height) + { + // Resize + auto pWIC = _GetWIC(); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr scaler; + hr = pWIC->CreateBitmapScaler(scaler.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = scaler->Initialize(frame, twidth, theight, WICBitmapInterpolationModeFant); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID pfScaler; + hr = scaler->GetPixelFormat(&pfScaler); + if (FAILED(hr)) + return hr; + + if (memcmp(&convertGUID, &pfScaler, sizeof(GUID)) == 0) + { + // No format conversion needed + hr = scaler->CopyPixels(0, static_cast(rowPitch), static_cast(imageSize), temp.get()); + if (FAILED(hr)) + return hr; + } + else + { + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pfScaler, convertGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(scaler.Get(), convertGUID, WICBitmapDitherTypeErrorDiffusion, nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(0, static_cast(rowPitch), static_cast(imageSize), temp.get()); + if (FAILED(hr)) + return hr; + } + } + else + { + // Format conversion but no resize + auto pWIC = _GetWIC(); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pixelFormat, convertGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(frame, convertGUID, WICBitmapDitherTypeErrorDiffusion, nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(0, static_cast(rowPitch), static_cast(imageSize), temp.get()); + if (FAILED(hr)) + return hr; + } + + // See if format is supported for auto-gen mipmaps (varies by feature level) + bool autogen = false; + if (d3dContext != 0 && textureView != 0) // Must have context and shader-view to auto generate mipmaps + { + UINT fmtSupport = 0; + hr = d3dDevice->CheckFormatSupport(format, &fmtSupport); + if (SUCCEEDED(hr) && (fmtSupport & D3D11_FORMAT_SUPPORT_MIP_AUTOGEN)) + { + autogen = true; + } + } + + // Create texture + D3D11_TEXTURE2D_DESC desc; + desc.Width = twidth; + desc.Height = theight; + desc.MipLevels = (autogen) ? 0 : 1; + desc.ArraySize = 1; + desc.Format = format; + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Usage = usage; + desc.CPUAccessFlags = cpuAccessFlags; + + if (autogen) + { + desc.BindFlags = bindFlags | D3D11_BIND_RENDER_TARGET; + desc.MiscFlags = miscFlags | D3D11_RESOURCE_MISC_GENERATE_MIPS; + } + else + { + desc.BindFlags = bindFlags; + desc.MiscFlags = miscFlags; + } + + D3D11_SUBRESOURCE_DATA initData; + initData.pSysMem = temp.get(); + initData.SysMemPitch = static_cast(rowPitch); + initData.SysMemSlicePitch = static_cast(imageSize); + + ID3D11Texture2D* tex = nullptr; + hr = d3dDevice->CreateTexture2D(&desc, (autogen) ? nullptr : &initData, &tex); + if (SUCCEEDED(hr) && tex != 0) + { + if (textureView != 0) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc = {}; + SRVDesc.Format = desc.Format; + + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + SRVDesc.Texture2D.MipLevels = (autogen) ? -1 : 1; + + hr = d3dDevice->CreateShaderResourceView(tex, &SRVDesc, textureView); + if (FAILED(hr)) + { + tex->Release(); + return hr; + } + + if (autogen) + { + assert(d3dContext != 0); + d3dContext->UpdateSubresource(tex, 0, nullptr, temp.get(), static_cast(rowPitch), static_cast(imageSize)); + d3dContext->GenerateMips(*textureView); + } + } + + if (texture != 0) + { + *texture = tex; + } + else + { + SetDebugObjectName(tex, "WICTextureLoader"); + tex->Release(); + } + } + + return hr; + } +} // anonymous namespace + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromMemory(ID3D11Device* d3dDevice, + const uint8_t* wicData, + size_t wicDataSize, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize) +{ + return CreateWICTextureFromMemoryEx(d3dDevice, nullptr, wicData, wicDataSize, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, WIC_LOADER_DEFAULT, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromMemory(ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const uint8_t* wicData, + size_t wicDataSize, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize) +{ + return CreateWICTextureFromMemoryEx(d3dDevice, d3dContext, wicData, wicDataSize, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, WIC_LOADER_DEFAULT, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromMemoryEx(ID3D11Device* d3dDevice, + const uint8_t* wicData, + size_t wicDataSize, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + unsigned int loadFlags, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView) +{ + return CreateWICTextureFromMemoryEx(d3dDevice, nullptr, wicData, wicDataSize, maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, loadFlags, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromMemoryEx(ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const uint8_t* wicData, + size_t wicDataSize, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + unsigned int loadFlags, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView) +{ + if (texture) + { + *texture = nullptr; + } + if (textureView) + { + *textureView = nullptr; + } + + if (!d3dDevice || !wicData || (!texture && !textureView)) + return E_INVALIDARG; + + if (!wicDataSize) + return E_FAIL; + + if (wicDataSize > UINT32_MAX) + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + + auto pWIC = _GetWIC(); + if (!pWIC) + return E_NOINTERFACE; + + // Create input stream for memory + ComPtr stream; + HRESULT hr = pWIC->CreateStream(stream.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = stream->InitializeFromMemory(const_cast(wicData), static_cast(wicDataSize)); + if (FAILED(hr)) + return hr; + + // Initialize WIC + ComPtr decoder; + hr = pWIC->CreateDecoderFromStream(stream.Get(), 0, WICDecodeMetadataCacheOnDemand, decoder.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr frame; + hr = decoder->GetFrame(0, frame.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = CreateTextureFromWIC(d3dDevice, d3dContext, frame.Get(), maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, loadFlags, + texture, textureView); + if (FAILED(hr)) + return hr; + + if (texture != 0 && *texture != 0) + { + SetDebugObjectName(*texture, "WICTextureLoader"); + } + + if (textureView != 0 && *textureView != 0) + { + SetDebugObjectName(*textureView, "WICTextureLoader"); + } + + return hr; +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromFile(ID3D11Device* d3dDevice, + const wchar_t* fileName, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize) +{ + return CreateWICTextureFromFileEx(d3dDevice, nullptr, fileName, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, WIC_LOADER_DEFAULT, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromFile(ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const wchar_t* fileName, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize) +{ + return CreateWICTextureFromFileEx(d3dDevice, d3dContext, fileName, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, WIC_LOADER_DEFAULT, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromFileEx(ID3D11Device* d3dDevice, + const wchar_t* fileName, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + unsigned int loadFlags, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView) +{ + return CreateWICTextureFromFileEx(d3dDevice, nullptr, fileName, maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, loadFlags, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromFileEx(ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const wchar_t* fileName, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + unsigned int loadFlags, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView) +{ + if (texture) + { + *texture = nullptr; + } + if (textureView) + { + *textureView = nullptr; + } + + if (!d3dDevice || !fileName || (!texture && !textureView)) + return E_INVALIDARG; + + auto pWIC = _GetWIC(); + if (!pWIC) + return E_NOINTERFACE; + + // Initialize WIC + ComPtr decoder; + HRESULT hr = pWIC->CreateDecoderFromFilename(fileName, 0, GENERIC_READ, WICDecodeMetadataCacheOnDemand, decoder.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr frame; + hr = decoder->GetFrame(0, frame.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = CreateTextureFromWIC(d3dDevice, d3dContext, frame.Get(), maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, loadFlags, + texture, textureView); + +#if !defined(NO_D3D11_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) + if (SUCCEEDED(hr)) + { + if (texture != 0 || textureView != 0) + { + char strFileA[MAX_PATH]; + int result = WideCharToMultiByte(CP_ACP, + WC_NO_BEST_FIT_CHARS, + fileName, + -1, + strFileA, + MAX_PATH, + nullptr, + FALSE + ); + if (result > 0) + { + const char* pstrName = strrchr(strFileA, '\\'); + if (!pstrName) + { + pstrName = strFileA; + } + else + { + pstrName++; + } + + if (texture != 0 && *texture != 0) + { + (*texture)->SetPrivateData(WKPDID_D3DDebugObjectName, + static_cast(strnlen_s(pstrName, MAX_PATH)), + pstrName + ); + } + + if (textureView != 0 && *textureView != 0) + { + (*textureView)->SetPrivateData(WKPDID_D3DDebugObjectName, + static_cast(strnlen_s(pstrName, MAX_PATH)), + pstrName + ); + } + } + } + } +#endif + + return hr; +} diff --git a/deps/DirectXTex/WICTextureLoader/WICTextureLoader.h b/deps/DirectXTex/WICTextureLoader/WICTextureLoader.h new file mode 100644 index 0000000..736bf5d --- /dev/null +++ b/deps/DirectXTex/WICTextureLoader/WICTextureLoader.h @@ -0,0 +1,130 @@ +//-------------------------------------------------------------------------------------- +// File: WICTextureLoader.h +// +// Function for loading a WIC image and creating a Direct3D runtime texture for it +// (auto-generating mipmaps if possible) +// +// Note: Assumes application has already called CoInitializeEx +// +// Warning: CreateWICTexture* functions are not thread-safe if given a d3dContext instance for +// auto-gen mipmap support. +// +// Note these functions are useful for images created as simple 2D textures. For +// more complex resources, DDSTextureLoader is an excellent light-weight runtime loader. +// For a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#pragma once + +#include +#include + + +namespace DirectX +{ + enum WIC_LOADER_FLAGS + { + WIC_LOADER_DEFAULT = 0, + WIC_LOADER_FORCE_SRGB = 0x1, + WIC_LOADER_IGNORE_SRGB = 0x2, + }; + + // Standard version + HRESULT CreateWICTextureFromMemory( + _In_ ID3D11Device* d3dDevice, + _In_reads_bytes_(wicDataSize) const uint8_t* wicData, + _In_ size_t wicDataSize, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0); + + HRESULT CreateWICTextureFromFile( + _In_ ID3D11Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0); + + // Standard version with optional auto-gen mipmap support + HRESULT CreateWICTextureFromMemory( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_reads_bytes_(wicDataSize) const uint8_t* wicData, + _In_ size_t wicDataSize, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0); + + HRESULT CreateWICTextureFromFile( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_z_ const wchar_t* szFileName, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0); + + // Extended version + HRESULT CreateWICTextureFromMemoryEx( + _In_ ID3D11Device* d3dDevice, + _In_reads_bytes_(wicDataSize) const uint8_t* wicData, + _In_ size_t wicDataSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ unsigned int loadFlags, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView); + + HRESULT CreateWICTextureFromFileEx( + _In_ ID3D11Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ unsigned int loadFlags, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView); + + // Extended version with optional auto-gen mipmap support + HRESULT CreateWICTextureFromMemoryEx( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_reads_bytes_(wicDataSize) const uint8_t* wicData, + _In_ size_t wicDataSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ unsigned int loadFlags, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView); + + HRESULT CreateWICTextureFromFileEx( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_z_ const wchar_t* szFileName, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ unsigned int loadFlags, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView); +} \ No newline at end of file diff --git a/deps/DirectXTex/WICTextureLoader/WICTextureLoader12.cpp b/deps/DirectXTex/WICTextureLoader/WICTextureLoader12.cpp new file mode 100644 index 0000000..ddba7f8 --- /dev/null +++ b/deps/DirectXTex/WICTextureLoader/WICTextureLoader12.cpp @@ -0,0 +1,704 @@ +//-------------------------------------------------------------------------------------- +// File: WICTextureLoader12.cpp +// +// Function for loading a WIC image and creating a Direct3D 12 runtime texture for it +// (auto-generating mipmaps if possible) +// +// Note: Assumes application has already called CoInitializeEx +// +// Note these functions are useful for images created as simple 2D textures. For +// more complex resources, DDSTextureLoader is an excellent light-weight runtime loader. +// For a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkID=615561 +//-------------------------------------------------------------------------------------- + +// We could load multi-frame images (TIFF/GIF) into a texture array. +// For now, we just load the first frame (note: DirectXTex supports multi-frame images) + +#include "WICTextureLoader12.h" + +#include +#include + +#include + +#include + +#include + +using namespace DirectX; +using Microsoft::WRL::ComPtr; + +namespace +{ + //------------------------------------------------------------------------------------- + // WIC Pixel Format Translation Data + //------------------------------------------------------------------------------------- + struct WICTranslate + { + GUID wic; + DXGI_FORMAT format; + }; + + const WICTranslate g_WICFormats[] = + { + { GUID_WICPixelFormat128bppRGBAFloat, DXGI_FORMAT_R32G32B32A32_FLOAT }, + + { GUID_WICPixelFormat64bppRGBAHalf, DXGI_FORMAT_R16G16B16A16_FLOAT }, + { GUID_WICPixelFormat64bppRGBA, DXGI_FORMAT_R16G16B16A16_UNORM }, + + { GUID_WICPixelFormat32bppRGBA, DXGI_FORMAT_R8G8B8A8_UNORM }, + { GUID_WICPixelFormat32bppBGRA, DXGI_FORMAT_B8G8R8A8_UNORM }, + { GUID_WICPixelFormat32bppBGR, DXGI_FORMAT_B8G8R8X8_UNORM }, + + { GUID_WICPixelFormat32bppRGBA1010102XR, DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM }, + { GUID_WICPixelFormat32bppRGBA1010102, DXGI_FORMAT_R10G10B10A2_UNORM }, + + { GUID_WICPixelFormat16bppBGRA5551, DXGI_FORMAT_B5G5R5A1_UNORM }, + { GUID_WICPixelFormat16bppBGR565, DXGI_FORMAT_B5G6R5_UNORM }, + + { GUID_WICPixelFormat32bppGrayFloat, DXGI_FORMAT_R32_FLOAT }, + { GUID_WICPixelFormat16bppGrayHalf, DXGI_FORMAT_R16_FLOAT }, + { GUID_WICPixelFormat16bppGray, DXGI_FORMAT_R16_UNORM }, + { GUID_WICPixelFormat8bppGray, DXGI_FORMAT_R8_UNORM }, + + { GUID_WICPixelFormat8bppAlpha, DXGI_FORMAT_A8_UNORM }, + + { GUID_WICPixelFormat96bppRGBFloat, DXGI_FORMAT_R32G32B32_FLOAT }, + }; + + //------------------------------------------------------------------------------------- + // WIC Pixel Format nearest conversion table + //------------------------------------------------------------------------------------- + + struct WICConvert + { + GUID source; + GUID target; + }; + + const WICConvert g_WICConvert[] = + { + // Note target GUID in this conversion table must be one of those directly supported formats (above). + + { GUID_WICPixelFormatBlackWhite, GUID_WICPixelFormat8bppGray }, // DXGI_FORMAT_R8_UNORM + + { GUID_WICPixelFormat1bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat2bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat4bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat8bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + + { GUID_WICPixelFormat2bppGray, GUID_WICPixelFormat8bppGray }, // DXGI_FORMAT_R8_UNORM + { GUID_WICPixelFormat4bppGray, GUID_WICPixelFormat8bppGray }, // DXGI_FORMAT_R8_UNORM + + { GUID_WICPixelFormat16bppGrayFixedPoint, GUID_WICPixelFormat16bppGrayHalf }, // DXGI_FORMAT_R16_FLOAT + { GUID_WICPixelFormat32bppGrayFixedPoint, GUID_WICPixelFormat32bppGrayFloat }, // DXGI_FORMAT_R32_FLOAT + + { GUID_WICPixelFormat16bppBGR555, GUID_WICPixelFormat16bppBGRA5551 }, // DXGI_FORMAT_B5G5R5A1_UNORM + + { GUID_WICPixelFormat32bppBGR101010, GUID_WICPixelFormat32bppRGBA1010102 }, // DXGI_FORMAT_R10G10B10A2_UNORM + + { GUID_WICPixelFormat24bppBGR, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat24bppRGB, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat32bppPBGRA, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat32bppPRGBA, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + + { GUID_WICPixelFormat48bppRGB, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat48bppBGR, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppBGRA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPRGBA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPBGRA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + + { GUID_WICPixelFormat48bppRGBFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat48bppBGRFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBAFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppBGRAFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat48bppRGBHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + + { GUID_WICPixelFormat128bppPRGBAFloat, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBFloat, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBAFixedPoint, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBFixedPoint, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat32bppRGBE, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + + { GUID_WICPixelFormat32bppCMYK, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat64bppCMYK, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat40bppCMYKAlpha, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat80bppCMYKAlpha, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + + { GUID_WICPixelFormat32bppRGB, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat64bppRGB, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPRGBAHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + + { GUID_WICPixelFormat96bppRGBFixedPoint, GUID_WICPixelFormat96bppRGBFloat }, // DXGI_FORMAT_R32G32B32_FLOAT + + // We don't support n-channel formats + }; + + IWICImagingFactory2* _GetWIC() + { + static INIT_ONCE s_initOnce = INIT_ONCE_STATIC_INIT; + + IWICImagingFactory2* factory = nullptr; + (void)InitOnceExecuteOnce(&s_initOnce, + [](PINIT_ONCE, PVOID, PVOID *factory) -> BOOL + { + return SUCCEEDED( CoCreateInstance( + CLSID_WICImagingFactory2, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory2), + factory) ) ? TRUE : FALSE; + }, nullptr, reinterpret_cast(&factory)); + + return factory; + } + + //--------------------------------------------------------------------------------- + template + inline void SetDebugObjectName(_In_ ID3D12DeviceChild* resource, _In_z_ const wchar_t(&name)[TNameLength]) + { + #if !defined(NO_D3D12_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) + resource->SetName(name); + #else + UNREFERENCED_PARAMETER(resource); + UNREFERENCED_PARAMETER(name); + #endif + } + + inline uint32_t CountMips(uint32_t width, uint32_t height) + { + if (width == 0 || height == 0) + return 0; + + uint32_t count = 1; + while (width > 1 || height > 1) + { + width >>= 1; + height >>= 1; + count++; + } + return count; + } + + //-------------------------------------------------------------------------------------- + DXGI_FORMAT MakeSRGB(_In_ DXGI_FORMAT format) + { + switch (format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + return DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + + case DXGI_FORMAT_BC1_UNORM: + return DXGI_FORMAT_BC1_UNORM_SRGB; + + case DXGI_FORMAT_BC2_UNORM: + return DXGI_FORMAT_BC2_UNORM_SRGB; + + case DXGI_FORMAT_BC3_UNORM: + return DXGI_FORMAT_BC3_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + return DXGI_FORMAT_B8G8R8A8_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + return DXGI_FORMAT_B8G8R8X8_UNORM_SRGB; + + case DXGI_FORMAT_BC7_UNORM: + return DXGI_FORMAT_BC7_UNORM_SRGB; + + default: + return format; + } + } + + //--------------------------------------------------------------------------------- + DXGI_FORMAT _WICToDXGI(const GUID& guid) + { + for (size_t i = 0; i < _countof(g_WICFormats); ++i) + { + if (memcmp(&g_WICFormats[i].wic, &guid, sizeof(GUID)) == 0) + return g_WICFormats[i].format; + } + + return DXGI_FORMAT_UNKNOWN; + } + + //--------------------------------------------------------------------------------- + size_t _WICBitsPerPixel(REFGUID targetGuid) + { + auto pWIC = _GetWIC(); + if (!pWIC) + return 0; + + ComPtr cinfo; + if (FAILED(pWIC->CreateComponentInfo(targetGuid, cinfo.GetAddressOf()))) + return 0; + + WICComponentType type; + if (FAILED(cinfo->GetComponentType(&type))) + return 0; + + if (type != WICPixelFormat) + return 0; + + ComPtr pfinfo; + if (FAILED(cinfo.As(&pfinfo))) + return 0; + + UINT bpp; + if (FAILED(pfinfo->GetBitsPerPixel(&bpp))) + return 0; + + return bpp; + } + + //--------------------------------------------------------------------------------- + HRESULT CreateTextureFromWIC(_In_ ID3D12Device* d3dDevice, + _In_ IWICBitmapFrameDecode *frame, + size_t maxsize, + D3D12_RESOURCE_FLAGS resFlags, + unsigned int loadFlags, + _Outptr_ ID3D12Resource** texture, + std::unique_ptr& decodedData, + D3D12_SUBRESOURCE_DATA& subresource) + { + UINT width, height; + HRESULT hr = frame->GetSize(&width, &height); + if (FAILED(hr)) + return hr; + + assert(width > 0 && height > 0); + + if (!maxsize) + { + maxsize = D3D12_REQ_TEXTURE2D_U_OR_V_DIMENSION; + } + + assert(maxsize > 0); + + UINT twidth, theight; + if (width > maxsize || height > maxsize) + { + float ar = static_cast(height) / static_cast(width); + if (width > height) + { + twidth = static_cast(maxsize); + theight = std::max(1, static_cast(static_cast(maxsize) * ar)); + } + else + { + theight = static_cast(maxsize); + twidth = std::max(1, static_cast(static_cast(maxsize) / ar)); + } + assert(twidth <= maxsize && theight <= maxsize); + } + else + { + twidth = width; + theight = height; + } + + // Determine format + WICPixelFormatGUID pixelFormat; + hr = frame->GetPixelFormat(&pixelFormat); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID convertGUID; + memcpy(&convertGUID, &pixelFormat, sizeof(WICPixelFormatGUID)); + + size_t bpp = 0; + + DXGI_FORMAT format = _WICToDXGI(pixelFormat); + if (format == DXGI_FORMAT_UNKNOWN) + { + for (size_t i = 0; i < _countof(g_WICConvert); ++i) + { + if (memcmp(&g_WICConvert[i].source, &pixelFormat, sizeof(WICPixelFormatGUID)) == 0) + { + memcpy(&convertGUID, &g_WICConvert[i].target, sizeof(WICPixelFormatGUID)); + + format = _WICToDXGI(g_WICConvert[i].target); + assert(format != DXGI_FORMAT_UNKNOWN); + bpp = _WICBitsPerPixel(convertGUID); + break; + } + } + + if (format == DXGI_FORMAT_UNKNOWN) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + else + { + bpp = _WICBitsPerPixel(pixelFormat); + } + + if (!bpp) + return E_FAIL; + + // Handle sRGB formats + if (loadFlags & WIC_LOADER_FORCE_SRGB) + { + format = MakeSRGB(format); + } + else if (!(loadFlags & WIC_LOADER_IGNORE_SRGB)) + { + ComPtr metareader; + if (SUCCEEDED(frame->GetMetadataQueryReader(metareader.GetAddressOf()))) + { + GUID containerFormat; + if (SUCCEEDED(metareader->GetContainerFormat(&containerFormat))) + { + // Check for sRGB colorspace metadata + bool sRGB = false; + + PROPVARIANT value; + PropVariantInit(&value); + + if (memcmp(&containerFormat, &GUID_ContainerFormatPng, sizeof(GUID)) == 0) + { + // Check for sRGB chunk + if (SUCCEEDED(metareader->GetMetadataByName(L"/sRGB/RenderingIntent", &value)) && value.vt == VT_UI1) + { + sRGB = true; + } + } + else if (SUCCEEDED(metareader->GetMetadataByName(L"System.Image.ColorSpace", &value)) && value.vt == VT_UI2 && value.uiVal == 1) + { + sRGB = true; + } + + (void)PropVariantClear(&value); + + if (sRGB) + format = MakeSRGB(format); + } + } + } + + // Allocate memory for decoded image + size_t rowPitch = (twidth * bpp + 7) / 8; + size_t imageSize = rowPitch * theight; + + decodedData.reset(new (std::nothrow) uint8_t[imageSize]); + if (!decodedData) + return E_OUTOFMEMORY; + + // Load image data + if (memcmp(&convertGUID, &pixelFormat, sizeof(GUID)) == 0 + && twidth == width + && theight == height) + { + // No format conversion or resize needed + hr = frame->CopyPixels(0, static_cast(rowPitch), static_cast(imageSize), decodedData.get()); + if (FAILED(hr)) + return hr; + } + else if (twidth != width || theight != height) + { + // Resize + auto pWIC = _GetWIC(); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr scaler; + hr = pWIC->CreateBitmapScaler(scaler.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = scaler->Initialize(frame, twidth, theight, WICBitmapInterpolationModeFant); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID pfScaler; + hr = scaler->GetPixelFormat(&pfScaler); + if (FAILED(hr)) + return hr; + + if (memcmp(&convertGUID, &pfScaler, sizeof(GUID)) == 0) + { + // No format conversion needed + hr = scaler->CopyPixels(0, static_cast(rowPitch), static_cast(imageSize), decodedData.get()); + if (FAILED(hr)) + return hr; + } + else + { + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pfScaler, convertGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(scaler.Get(), convertGUID, WICBitmapDitherTypeErrorDiffusion, nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(0, static_cast(rowPitch), static_cast(imageSize), decodedData.get()); + if (FAILED(hr)) + return hr; + } + } + else + { + // Format conversion but no resize + auto pWIC = _GetWIC(); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pixelFormat, convertGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(frame, convertGUID, WICBitmapDitherTypeErrorDiffusion, nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(0, static_cast(rowPitch), static_cast(imageSize), decodedData.get()); + if (FAILED(hr)) + return hr; + } + + // Count the number of mips + uint32_t mipCount = (loadFlags & (WIC_LOADER_MIP_AUTOGEN|WIC_LOADER_MIP_RESERVE)) ? CountMips(twidth, theight) : 1; + + // Create texture + D3D12_RESOURCE_DESC desc = {}; + desc.Width = twidth; + desc.Height = theight; + desc.MipLevels = (uint16_t)mipCount; + desc.DepthOrArraySize = 1; + desc.Format = format; + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Flags = resFlags; + desc.Dimension = D3D12_RESOURCE_DIMENSION_TEXTURE2D; + + CD3DX12_HEAP_PROPERTIES defaultHeapProperties(D3D12_HEAP_TYPE_DEFAULT); + + ID3D12Resource* tex = nullptr; + hr = d3dDevice->CreateCommittedResource( + &defaultHeapProperties, + D3D12_HEAP_FLAG_NONE, + &desc, + D3D12_RESOURCE_STATE_COPY_DEST, + nullptr, + IID_PPV_ARGS(&tex)); + + if (FAILED(hr)) + { + return hr; + } + + _Analysis_assume_(tex != 0); + + subresource.pData = decodedData.get(); + subresource.RowPitch = rowPitch; + subresource.SlicePitch = imageSize; + + *texture = tex; + return hr; + } +} // anonymous namespace + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadWICTextureFromMemory( + ID3D12Device* d3dDevice, + const uint8_t* wicData, + size_t wicDataSize, + ID3D12Resource** texture, + std::unique_ptr& decodedData, + D3D12_SUBRESOURCE_DATA& subresource, + size_t maxsize) +{ + return LoadWICTextureFromMemoryEx( + d3dDevice, + wicData, + wicDataSize, + maxsize, + D3D12_RESOURCE_FLAG_NONE, + WIC_LOADER_DEFAULT, + texture, + decodedData, + subresource); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadWICTextureFromMemoryEx( + ID3D12Device* d3dDevice, + const uint8_t* wicData, + size_t wicDataSize, + size_t maxsize, + D3D12_RESOURCE_FLAGS resFlags, + unsigned int loadFlags, + ID3D12Resource** texture, + std::unique_ptr& decodedData, + D3D12_SUBRESOURCE_DATA& subresource) +{ + if ( texture ) + { + *texture = nullptr; + } + + if (!d3dDevice || !wicData || !texture) + return E_INVALIDARG; + + if ( !wicDataSize ) + return E_FAIL; + + if ( wicDataSize > UINT32_MAX ) + return HRESULT_FROM_WIN32( ERROR_FILE_TOO_LARGE ); + + auto pWIC = _GetWIC(); + if ( !pWIC ) + return E_NOINTERFACE; + + // Create input stream for memory + ComPtr stream; + HRESULT hr = pWIC->CreateStream( stream.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + hr = stream->InitializeFromMemory( const_cast( wicData ), static_cast( wicDataSize ) ); + if ( FAILED(hr) ) + return hr; + + // Initialize WIC + ComPtr decoder; + hr = pWIC->CreateDecoderFromStream( stream.Get(), 0, WICDecodeMetadataCacheOnDemand, decoder.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + ComPtr frame; + hr = decoder->GetFrame( 0, frame.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + hr = CreateTextureFromWIC( d3dDevice, + frame.Get(), maxsize, + resFlags, loadFlags, + texture, decodedData, subresource); + if ( FAILED(hr)) + return hr; + + _Analysis_assume_(*texture != nullptr); + SetDebugObjectName(*texture, L"WICTextureLoader"); + + return hr; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadWICTextureFromFile( + ID3D12Device* d3dDevice, + const wchar_t* fileName, + ID3D12Resource** texture, + std::unique_ptr& wicData, + D3D12_SUBRESOURCE_DATA& subresource, + size_t maxsize) +{ + return LoadWICTextureFromFileEx( + d3dDevice, + fileName, + maxsize, + D3D12_RESOURCE_FLAG_NONE, + WIC_LOADER_DEFAULT, + texture, + wicData, + subresource); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::LoadWICTextureFromFileEx( + ID3D12Device* d3dDevice, + const wchar_t* fileName, + size_t maxsize, + D3D12_RESOURCE_FLAGS resFlags, + unsigned int loadFlags, + ID3D12Resource** texture, + std::unique_ptr& decodedData, + D3D12_SUBRESOURCE_DATA& subresource) +{ + if ( texture ) + { + *texture = nullptr; + } + + if (!d3dDevice || !fileName || !texture ) + return E_INVALIDARG; + + auto pWIC = _GetWIC(); + if ( !pWIC ) + return E_NOINTERFACE; + + // Initialize WIC + ComPtr decoder; + HRESULT hr = pWIC->CreateDecoderFromFilename( fileName, 0, GENERIC_READ, WICDecodeMetadataCacheOnDemand, decoder.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + ComPtr frame; + hr = decoder->GetFrame( 0, frame.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + hr = CreateTextureFromWIC( d3dDevice, frame.Get(), maxsize, + resFlags, loadFlags, + texture, decodedData, subresource ); + +#if !defined(NO_D3D12_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) + if ( SUCCEEDED(hr) ) + { + const wchar_t* pstrName = wcsrchr(fileName, '\\' ); + if (!pstrName) + { + pstrName = fileName; + } + else + { + pstrName++; + } + + if (texture != 0 && *texture != 0) + { + (*texture)->SetName(pstrName); + } + } +#endif + + return hr; +} diff --git a/deps/DirectXTex/WICTextureLoader/WICTextureLoader12.h b/deps/DirectXTex/WICTextureLoader/WICTextureLoader12.h new file mode 100644 index 0000000..00a0212 --- /dev/null +++ b/deps/DirectXTex/WICTextureLoader/WICTextureLoader12.h @@ -0,0 +1,82 @@ +//-------------------------------------------------------------------------------------- +// File: WICTextureLoader12.h +// +// Function for loading a WIC image and creating a Direct3D runtime texture for it +// (auto-generating mipmaps if possible) +// +// Note: Assumes application has already called CoInitializeEx +// +// Note these functions are useful for images created as simple 2D textures. For +// more complex resources, DDSTextureLoader is an excellent light-weight runtime loader. +// For a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkID=615561 +//-------------------------------------------------------------------------------------- + +#pragma once + +#include +#include +#include + + +namespace DirectX +{ + enum WIC_LOADER_FLAGS + { + WIC_LOADER_DEFAULT = 0, + WIC_LOADER_FORCE_SRGB = 0x1, + WIC_LOADER_IGNORE_SRGB = 0x2, + WIC_LOADER_MIP_AUTOGEN = 0x4, + WIC_LOADER_MIP_RESERVE = 0x8, + }; + + // Standard version + HRESULT __cdecl LoadWICTextureFromMemory( + _In_ ID3D12Device* d3dDevice, + _In_reads_bytes_(wicDataSize) const uint8_t* wicData, + size_t wicDataSize, + _Outptr_ ID3D12Resource** texture, + std::unique_ptr& decodedData, + D3D12_SUBRESOURCE_DATA& subresource, + size_t maxsize = 0); + + HRESULT __cdecl LoadWICTextureFromFile( + _In_ ID3D12Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _Outptr_ ID3D12Resource** texture, + std::unique_ptr& decodedData, + D3D12_SUBRESOURCE_DATA& subresource, + size_t maxsize = 0); + + // Extended version + HRESULT __cdecl LoadWICTextureFromMemoryEx( + _In_ ID3D12Device* d3dDevice, + _In_reads_bytes_(wicDataSize) const uint8_t* wicData, + size_t wicDataSize, + size_t maxsize, + D3D12_RESOURCE_FLAGS resFlags, + unsigned int loadFlags, + _Outptr_ ID3D12Resource** texture, + std::unique_ptr& decodedData, + D3D12_SUBRESOURCE_DATA& subresource); + + HRESULT __cdecl LoadWICTextureFromFileEx( + _In_ ID3D12Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + size_t maxsize, + D3D12_RESOURCE_FLAGS resFlags, + unsigned int loadFlags, + _Outptr_ ID3D12Resource** texture, + std::unique_ptr& decodedData, + D3D12_SUBRESOURCE_DATA& subresource); +} \ No newline at end of file diff --git a/src/FileTypeDDS/FileTypeDDS.sln b/src/FileTypeDDS/FileTypeDDS.sln deleted file mode 100644 index a12a48f..0000000 --- a/src/FileTypeDDS/FileTypeDDS.sln +++ /dev/null @@ -1,22 +0,0 @@ - -Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio 2013 -VisualStudioVersion = 12.0.40629.0 -MinimumVisualStudioVersion = 10.0.40219.1 -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "FileTypeDDS", "FileTypeDDS\FileTypeDDS.vcxproj", "{AEC443D7-D4C8-4191-A09A-7CCE99CD1F90}" -EndProject -Global - GlobalSection(SolutionConfigurationPlatforms) = preSolution - Debug|Win32 = Debug|Win32 - Release|Win32 = Release|Win32 - EndGlobalSection - GlobalSection(ProjectConfigurationPlatforms) = postSolution - {AEC443D7-D4C8-4191-A09A-7CCE99CD1F90}.Debug|Win32.ActiveCfg = Debug|Win32 - {AEC443D7-D4C8-4191-A09A-7CCE99CD1F90}.Debug|Win32.Build.0 = Debug|Win32 - {AEC443D7-D4C8-4191-A09A-7CCE99CD1F90}.Release|Win32.ActiveCfg = Release|Win32 - {AEC443D7-D4C8-4191-A09A-7CCE99CD1F90}.Release|Win32.Build.0 = Release|Win32 - EndGlobalSection - GlobalSection(SolutionProperties) = preSolution - HideSolutionNode = FALSE - EndGlobalSection -EndGlobal diff --git a/src/FileTypeDDS/FileTypeDDS/AssemblyInfo.cpp b/src/FileTypeDDS/FileTypeDDS/AssemblyInfo.cpp deleted file mode 100644 index bbafeb5..0000000 --- a/src/FileTypeDDS/FileTypeDDS/AssemblyInfo.cpp +++ /dev/null @@ -1,38 +0,0 @@ -#include "stdafx.h" - -using namespace System; -using namespace System::Reflection; -using namespace System::Runtime::CompilerServices; -using namespace System::Runtime::InteropServices; -using namespace System::Security::Permissions; - -// -// General Information about an assembly is controlled through the following -// set of attributes. Change these attribute values to modify the information -// associated with an assembly. -// -[assembly:AssemblyTitleAttribute(L"FileTypeDDS")]; -[assembly:AssemblyDescriptionAttribute(L"")]; -[assembly:AssemblyConfigurationAttribute(L"")]; -[assembly:AssemblyCompanyAttribute(L"")]; -[assembly:AssemblyProductAttribute(L"FileTypeDDS")]; -[assembly:AssemblyCopyrightAttribute(L"Copyright (c) 2017")]; -[assembly:AssemblyTrademarkAttribute(L"")]; -[assembly:AssemblyCultureAttribute(L"")]; - -// -// Version information for an assembly consists of the following four values: -// -// Major Version -// Minor Version -// Build Number -// Revision -// -// You can specify all the value or you can default the Revision and Build Numbers -// by using the '*' as shown below: - -[assembly:AssemblyVersionAttribute("1.0.*")]; - -[assembly:ComVisible(false)]; - -[assembly:CLSCompliantAttribute(true)]; \ No newline at end of file diff --git a/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.cpp b/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.cpp deleted file mode 100644 index 617d79a..0000000 --- a/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.cpp +++ /dev/null @@ -1,5 +0,0 @@ -#include "stdafx.h" - -// The class we are implementing -#include "FileTypeDDS.h" - diff --git a/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.h b/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.h deleted file mode 100644 index 453b2e8..0000000 --- a/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.h +++ /dev/null @@ -1,12 +0,0 @@ -#pragma once - -using namespace System; - -namespace FileTypeDDS -{ - - public ref class Class1 - { - // TODO: Add your methods for this class here. - }; -} diff --git a/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.vcxproj b/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.vcxproj deleted file mode 100644 index dc39625..0000000 --- a/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.vcxproj +++ /dev/null @@ -1,93 +0,0 @@ - - - - - Debug - Win32 - - - Release - Win32 - - - - {AEC443D7-D4C8-4191-A09A-7CCE99CD1F90} - v4.5 - ManagedCProj - FileTypeDDS - - - - DynamicLibrary - true - v120 - true - Unicode - - - DynamicLibrary - false - v120 - true - Unicode - - - - - - - - - - - - - true - - - false - - - - Level3 - Disabled - WIN32;_DEBUG;%(PreprocessorDefinitions) - Use - - - true - - - - - - Level3 - WIN32;NDEBUG;%(PreprocessorDefinitions) - Use - - - true - - - - - - - - - - - - - - - - - Create - Create - - - - - - \ No newline at end of file diff --git a/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.vcxproj.filters b/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.vcxproj.filters deleted file mode 100644 index 628ec9b..0000000 --- a/src/FileTypeDDS/FileTypeDDS/FileTypeDDS.vcxproj.filters +++ /dev/null @@ -1,36 +0,0 @@ - - - - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - {93995380-89BD-4b04-88EB-625FBE52EBFB} - h;hh;hpp;hxx;hm;inl;inc;xsd - - - {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} - rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms - - - - - Header Files - - - Header Files - - - - - Source Files - - - Source Files - - - Source Files - - - \ No newline at end of file diff --git a/src/FileTypeDDS/FileTypeDDS/Stdafx.cpp b/src/FileTypeDDS/FileTypeDDS/Stdafx.cpp deleted file mode 100644 index fd4f341..0000000 --- a/src/FileTypeDDS/FileTypeDDS/Stdafx.cpp +++ /dev/null @@ -1 +0,0 @@ -#include "stdafx.h" diff --git a/src/FileTypeDDS/FileTypeDDS/Stdafx.h b/src/FileTypeDDS/FileTypeDDS/Stdafx.h deleted file mode 100644 index 45dcbb0..0000000 --- a/src/FileTypeDDS/FileTypeDDS/Stdafx.h +++ /dev/null @@ -1,3 +0,0 @@ -#pragma once - -