From af921463602dafb6d277520cbb6e8b668799778b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Branimir=20Karad=C5=BEi=C4=87?= Date: Sun, 19 Feb 2017 17:51:38 -0800 Subject: [PATCH] Added custom allocator to ImageContainer. --- src/bgfx.cpp | 43 +----------- src/image.cpp | 81 ++++++++++++++-------- src/image.h | 36 +++++----- tools/texturec/texturec.cpp | 135 +++++++++++++++++++----------------- 4 files changed, 143 insertions(+), 152 deletions(-) diff --git a/src/bgfx.cpp b/src/bgfx.cpp index d9e74ff05..4f859923f 100644 --- a/src/bgfx.cpp +++ b/src/bgfx.cpp @@ -3113,48 +3113,7 @@ error: void calcTextureSize(TextureInfo& _info, uint16_t _width, uint16_t _height, uint16_t _depth, bool _cubeMap, bool _hasMips, uint16_t _numLayers, TextureFormat::Enum _format) { - const ImageBlockInfo& blockInfo = getBlockInfo(_format); - const uint8_t bpp = blockInfo.bitsPerPixel; - const uint16_t blockWidth = blockInfo.blockWidth; - const uint16_t blockHeight = blockInfo.blockHeight; - const uint16_t minBlockX = blockInfo.minBlockX; - const uint16_t minBlockY = blockInfo.minBlockY; - - _width = bx::uint16_max(blockWidth * minBlockX, ( (_width + blockWidth - 1) / blockWidth)*blockWidth); - _height = bx::uint16_max(blockHeight * minBlockY, ( (_height + blockHeight - 1) / blockHeight)*blockHeight); - _depth = bx::uint16_max(1, _depth); - const uint8_t numMips = calcNumMips(_hasMips, _width, _height, _depth); - const uint32_t sides = _cubeMap ? 6 : 1; - - uint32_t width = _width; - uint32_t height = _height; - uint32_t depth = _depth; - uint32_t size = 0; - - for (uint32_t lod = 0; lod < numMips; ++lod) - { - width = bx::uint32_max(blockWidth * minBlockX, ( (width + blockWidth - 1) / blockWidth )*blockWidth); - height = bx::uint32_max(blockHeight * minBlockY, ( (height + blockHeight - 1) / blockHeight)*blockHeight); - depth = bx::uint32_max(1, depth); - - size += width*height*depth*bpp/8 * sides; - - width >>= 1; - height >>= 1; - depth >>= 1; - } - - size *= _numLayers; - - _info.format = _format; - _info.width = _width; - _info.height = _height; - _info.depth = _depth; - _info.numMips = numMips; - _info.numLayers = _numLayers; - _info.cubeMap = _cubeMap; - _info.storageSize = size; - _info.bitsPerPixel = bpp; + imageGetSize(&_info, _width, _height, _depth, _cubeMap, _hasMips, _numLayers, _format); } TextureHandle createTexture(const Memory* _mem, uint32_t _flags, uint8_t _skip, TextureInfo* _info) diff --git a/src/image.cpp b/src/image.cpp index 46d83e469..91408eef4 100644 --- a/src/image.cpp +++ b/src/image.cpp @@ -263,7 +263,7 @@ namespace bgfx return uint8_t(numMips); } - uint32_t imageGetSize(TextureFormat::Enum _format, uint16_t _width, uint16_t _height, uint16_t _depth, uint16_t _numLayers, bool _cubeMap, uint8_t _numMips) + uint32_t imageGetSize(TextureInfo* _info, uint16_t _width, uint16_t _height, uint16_t _depth, bool _cubeMap, bool _hasMips, uint16_t _numLayers, TextureFormat::Enum _format) { const ImageBlockInfo& blockInfo = getBlockInfo(_format); const uint8_t bpp = blockInfo.bitsPerPixel; @@ -272,17 +272,18 @@ namespace bgfx const uint16_t minBlockX = blockInfo.minBlockX; const uint16_t minBlockY = blockInfo.minBlockY; - _width = bx::uint16_max(blockWidth * minBlockX, ( (_width + blockWidth - 1) / blockWidth)*blockWidth); - _height = bx::uint16_max(blockHeight * minBlockY, ( (_height + blockHeight - 1) / blockHeight)*blockHeight); - _depth = bx::uint16_max(1, _depth); + _width = bx::uint16_max(blockWidth * minBlockX, ( (_width + blockWidth - 1) / blockWidth)*blockWidth); + _height = bx::uint16_max(blockHeight * minBlockY, ( (_height + blockHeight - 1) / blockHeight)*blockHeight); + _depth = bx::uint16_max(1, _depth); + const uint8_t numMips = calcNumMips(_hasMips, _width, _height, _depth); + const uint32_t sides = _cubeMap ? 6 : 1; uint32_t width = _width; uint32_t height = _height; uint32_t depth = _depth; - uint32_t sides = _cubeMap ? 6 : 1; uint32_t size = 0; - for (uint32_t lod = 0; lod < _numMips; ++lod) + for (uint32_t lod = 0; lod < numMips; ++lod) { width = bx::uint32_max(blockWidth * minBlockX, ( (width + blockWidth - 1) / blockWidth )*blockWidth); height = bx::uint32_max(blockHeight * minBlockY, ( (height + blockHeight - 1) / blockHeight)*blockHeight); @@ -295,7 +296,22 @@ namespace bgfx depth >>= 1; } - return size * _numLayers; + size *= _numLayers; + + if (NULL != _info) + { + _info->format = _format; + _info->width = _width; + _info->height = _height; + _info->depth = _depth; + _info->numMips = numMips; + _info->numLayers = _numLayers; + _info->cubeMap = _cubeMap; + _info->storageSize = size; + _info->bitsPerPixel = bpp; + } + + return size; } void imageSolid(void* _dst, uint32_t _width, uint32_t _height, uint32_t _solid) @@ -1607,7 +1623,7 @@ namespace bgfx } } - const Memory* imageAlloc(ImageContainer& _imageContainer, TextureFormat::Enum _format, uint16_t _width, uint16_t _height, uint16_t _depth, uint16_t _numLayers, bool _cubeMap, bool _generateMips) + ImageContainer* imageAlloc(bx::AllocatorI* _allocator, TextureFormat::Enum _format, uint16_t _width, uint16_t _height, uint16_t _depth, uint16_t _numLayers, bool _cubeMap, bool _hasMips) { const ImageBlockInfo& blockInfo = getBlockInfo(_format); const uint16_t blockWidth = blockInfo.blockWidth; @@ -1620,31 +1636,33 @@ namespace bgfx _depth = bx::uint16_max(1, _depth); _numLayers = bx::uint16_max(1, _numLayers); - const uint8_t numMips = _generateMips ? imageGetNumMips(_format, _width, _height) : 1; - uint32_t size = imageGetSize(_format, _width, _height, _depth, _numLayers, _cubeMap, numMips); - const Memory* image = alloc(size); + const uint8_t numMips = _hasMips ? imageGetNumMips(_format, _width, _height) : 1; + uint32_t size = imageGetSize(NULL, _width, _height, _depth, _cubeMap, _hasMips, _numLayers, _format); - _imageContainer.m_data = image->data; - _imageContainer.m_format = _format; - _imageContainer.m_size = image->size; - _imageContainer.m_offset = 0; - _imageContainer.m_width = _width; - _imageContainer.m_height = _height; - _imageContainer.m_depth = _depth; - _imageContainer.m_numLayers = _numLayers; - _imageContainer.m_numMips = numMips; - _imageContainer.m_hasAlpha = false; - _imageContainer.m_cubeMap = _cubeMap; - _imageContainer.m_ktx = false; - _imageContainer.m_ktxLE = false; - _imageContainer.m_srgb = false; + ImageContainer* imageContainer = (ImageContainer*)BX_ALLOC(_allocator, size + sizeof(ImageContainer) ); - return image; + imageContainer->m_allocator = _allocator; + imageContainer->m_data = imageContainer + 1; + imageContainer->m_format = _format; + imageContainer->m_size = size; + imageContainer->m_offset = 0; + imageContainer->m_width = _width; + imageContainer->m_height = _height; + imageContainer->m_depth = _depth; + imageContainer->m_numLayers = _numLayers; + imageContainer->m_numMips = numMips; + imageContainer->m_hasAlpha = false; + imageContainer->m_cubeMap = _cubeMap; + imageContainer->m_ktx = false; + imageContainer->m_ktxLE = false; + imageContainer->m_srgb = false; + + return imageContainer; } - void imageFree(const Memory* _memory) + void imageFree(ImageContainer* _imageContainer) { - release(_memory); + BX_FREE(_imageContainer->m_allocator, _imageContainer); } // DDS @@ -1988,6 +2006,7 @@ namespace bgfx } } + _imageContainer.m_allocator = NULL; _imageContainer.m_data = NULL; _imageContainer.m_size = 0; _imageContainer.m_offset = (uint32_t)bx::seek(_reader); @@ -2297,6 +2316,7 @@ namespace bgfx } } + _imageContainer.m_allocator = NULL; _imageContainer.m_data = NULL; _imageContainer.m_size = 0; _imageContainer.m_offset = (uint32_t)offset; @@ -2447,6 +2467,7 @@ namespace bgfx } } + _imageContainer.m_allocator = NULL; _imageContainer.m_data = NULL; _imageContainer.m_size = 0; _imageContainer.m_offset = (uint32_t)offset; @@ -2489,6 +2510,7 @@ namespace bgfx _imageContainer.m_format = tc.m_format; _imageContainer.m_offset = UINT32_MAX; + _imageContainer.m_allocator = NULL; if (NULL == tc.m_mem) { _imageContainer.m_data = NULL; @@ -2872,7 +2894,8 @@ namespace bgfx default: if (isCompressed(_format) ) { - void* temp = BX_ALLOC(_allocator, imageGetSize(_format, uint16_t(_pitch/4), uint16_t(_height) ) ); + uint32_t size = imageGetSize(NULL, uint16_t(_pitch/4), uint16_t(_height), 0, false, false, 1, _format); + void* temp = BX_ALLOC(_allocator, size); imageDecodeToRgba8(temp, _src, _width, _height, _pitch, _format); imageRgba8ToRgba32f(_dst, _width, _height, _pitch, temp); BX_FREE(_allocator, temp); diff --git a/src/image.h b/src/image.h index 619fee778..282e5264a 100644 --- a/src/image.h +++ b/src/image.h @@ -12,8 +12,11 @@ namespace bgfx { struct ImageContainer { - void* m_data; + bx::AllocatorI* m_allocator; + void* m_data; + TextureFormat::Enum m_format; + uint32_t m_size; uint32_t m_offset; uint32_t m_width; @@ -87,18 +90,19 @@ namespace bgfx , uint16_t _width , uint16_t _height , uint16_t _depth = 0 - ); + ); /// Returns image size. uint32_t imageGetSize( - TextureFormat::Enum _format + TextureInfo* _info , uint16_t _width , uint16_t _height - , uint16_t _depth = 0 - , uint16_t _numLayers = 1 - , bool _cubeMap = false - , uint8_t _numMips = 1 - ); + , uint16_t _depth + , bool _cubeMap + , bool _hasMips + , uint16_t _numLayers + , TextureFormat::Enum _format + ); /// void imageSolid(void* _dst, uint32_t _width, uint32_t _height, uint32_t _solid); @@ -143,19 +147,19 @@ namespace bgfx bool imageConvert(void* _dst, TextureFormat::Enum _dstFormat, const void* _src, TextureFormat::Enum _srcFormat, uint32_t _width, uint32_t _height); /// - const Memory* imageAlloc( - ImageContainer& _imageContainer + ImageContainer* imageAlloc( + bx::AllocatorI* _allocator , TextureFormat::Enum _format , uint16_t _width , uint16_t _height - , uint16_t _depth = 0 - , uint16_t _numLayers = 1 - , bool _cubeMap = false - , bool _generateMips = false - ); + , uint16_t _depth + , uint16_t _numLayers + , bool _cubeMap + , bool _hasMips + ); /// - void imageFree(const Memory* _memory); + void imageFree(ImageContainer* _imageContainer); /// void imageWriteTga(bx::WriterI* _writer, uint32_t _width, uint32_t _height, uint32_t _pitch, const void* _src, bool _grayscale, bool _yflip, bx::Error* _err = NULL); diff --git a/tools/texturec/texturec.cpp b/tools/texturec/texturec.cpp index e1c60ca1d..3dd106a4b 100644 --- a/tools/texturec/texturec.cpp +++ b/tools/texturec/texturec.cpp @@ -3,14 +3,14 @@ * License: https://github.com/bkaradzic/bgfx#license-bsd-2-clause */ -#include -#include -#include +#include +#include +#include -// Just hacking DDS loading code in here. -#include "bgfx_p.h" +#include #include "image.h" + #include #include #include @@ -78,29 +78,6 @@ BX_PRAGMA_DIAGNOSTIC_POP() namespace bgfx { - const Memory* alloc(uint32_t _size) - { - Memory* mem = (Memory*)::realloc(NULL, sizeof(Memory) + _size); - mem->size = _size; - mem->data = (uint8_t*)mem + sizeof(Memory); - return mem; - } - - const Memory* makeRef(const void* _data, uint32_t _size, ReleaseFn _releaseFn, void* _userData) - { - BX_UNUSED(_releaseFn, _userData); - Memory* mem = (Memory*)::realloc(NULL, sizeof(Memory) ); - mem->size = _size; - mem->data = (uint8_t*)_data; - return mem; - } - - void release(const Memory* _mem) - { - Memory* mem = const_cast(_mem); - ::free(mem); - } - bool imageParse(ImageContainer& _imageContainer, const void* _data, uint32_t _size, void** _out) { *_out = NULL; @@ -570,6 +547,10 @@ int main(int _argc, const char* _argv[]) } BX_UNUSED(sdf, edge); + const bool mips = cmdLine.hasArg('m', "mips"); + const bool normalMap = cmdLine.hasArg('n', "normalmap"); + const bool iqa = cmdLine.hasArg('\0', "iqa"); + bx::CrtFileReader reader; if (!bx::open(&reader, inputFileName) ) { @@ -577,35 +558,33 @@ int main(int _argc, const char* _argv[]) return EXIT_FAILURE; } - const bool mips = cmdLine.hasArg('m', "mips"); - const bool normalMap = cmdLine.hasArg('n', "normalmap"); - const bool iqa = cmdLine.hasArg('\0', "iqa"); + bx::CrtAllocator allocator; - const bgfx::Memory* mem; - { - uint32_t size = (uint32_t)bx::getSize(&reader); - mem = bgfx::alloc(size); - bx::read(&reader, mem->data, mem->size); - bx::close(&reader); - } + uint32_t inputSize = (uint32_t)bx::getSize(&reader); + uint8_t* inputData = (uint8_t*)BX_ALLOC(&allocator, inputSize); + + bx::read(&reader, inputData, inputSize); + bx::close(&reader); { using namespace bgfx; uint8_t* decodedImage = NULL; - ImageContainer imageContainer; + ImageContainer input; - bool loaded = imageParse(imageContainer, mem->data, mem->size, (void**)&decodedImage); + bool loaded = imageParse(input, inputData, inputSize, (void**)&decodedImage); if (NULL != decodedImage) { - release(mem); - mem = makeRef(imageContainer.m_data, imageContainer.m_size); + BX_FREE(&allocator, inputData); + + inputData = (uint8_t*)input.m_data; + inputSize = input.m_size; } if (loaded) { const char* type = cmdLine.findOption('t'); - bgfx::TextureFormat::Enum format = imageContainer.m_format; + bgfx::TextureFormat::Enum format = input.m_format; if (NULL != type) { @@ -618,11 +597,10 @@ int main(int _argc, const char* _argv[]) } } - bx::CrtAllocator allocator; - const Memory* output = NULL; + ImageContainer* output = NULL; ImageMip mip; - if (imageGetRawData(imageContainer, 0, 0, mem->data, mem->size, mip) ) + if (imageGetRawData(input, 0, 0, inputData, inputSize, mip) ) { uint8_t numMips = mips ? imageGetNumMips(format, mip.m_width, mip.m_height) @@ -633,10 +611,10 @@ int main(int _argc, const char* _argv[]) if (normalMap) { - output = imageAlloc(imageContainer, format, mip.m_width, mip.m_height, 0, 1, false, mips); + output = imageAlloc(&allocator, format, mip.m_width, mip.m_height, 0, 1, false, mips); ImageMip dstMip; - imageGetRawData(imageContainer, 0, 0, NULL, 0, dstMip); + imageGetRawData(*output, 0, 0, NULL, 0, dstMip); if (mip.m_width != dstMip.m_width && mip.m_height != dstMip.m_height) @@ -651,7 +629,16 @@ int main(int _argc, const char* _argv[]) return EXIT_FAILURE; } - uint32_t size = imageGetSize(TextureFormat::RGBA32F, dstMip.m_width, dstMip.m_height); + uint32_t size = imageGetSize( + NULL + , dstMip.m_width + , dstMip.m_height + , 0 + , false + , false + , 1 + , TextureFormat::RGBA32F + ); temp = BX_ALLOC(&allocator, size); float* rgba = (float*)temp; float* rgbaDst = (float*)BX_ALLOC(&allocator, size); @@ -682,25 +669,25 @@ int main(int _argc, const char* _argv[]) } imageRgba32f11to01(rgbaDst, dstMip.m_width, dstMip.m_height, dstMip.m_width*16, rgba); - imageEncodeFromRgba32f(&allocator, output->data, rgbaDst, dstMip.m_width, dstMip.m_height, format); + imageEncodeFromRgba32f(&allocator, output->m_data, rgbaDst, dstMip.m_width, dstMip.m_height, format); for (uint8_t lod = 1; lod < numMips; ++lod) { imageRgba32fDownsample2x2NormalMap(rgba, dstMip.m_width, dstMip.m_height, dstMip.m_width*16, rgba); imageRgba32f11to01(rgbaDst, dstMip.m_width, dstMip.m_height, dstMip.m_width*16, rgba); - imageGetRawData(imageContainer, 0, lod, output->data, output->size, dstMip); + imageGetRawData(*output, 0, lod, output->m_data, output->m_size, dstMip); uint8_t* data = const_cast(dstMip.m_data); imageEncodeFromRgba32f(&allocator, data, rgbaDst, dstMip.m_width, dstMip.m_height, format); } BX_FREE(&allocator, rgbaDst); } - else if (8 != getBlockInfo(imageContainer.m_format).rBits) + else if (8 != getBlockInfo(input.m_format).rBits) { - output = imageAlloc(imageContainer, format, mip.m_width, mip.m_height, 0, 1, false, mips); + output = imageAlloc(&allocator, format, mip.m_width, mip.m_height, 0, 1, false, mips); ImageMip dstMip; - imageGetRawData(imageContainer, 0, 0, NULL, 0, dstMip); + imageGetRawData(*output, 0, 0, NULL, 0, dstMip); if (mip.m_width != dstMip.m_width && mip.m_height != dstMip.m_height) @@ -715,7 +702,16 @@ int main(int _argc, const char* _argv[]) return EXIT_FAILURE; } - uint32_t size = imageGetSize(TextureFormat::RGBA32F, dstMip.m_width, dstMip.m_height); + uint32_t size = imageGetSize( + NULL + , dstMip.m_width + , dstMip.m_height + , 0 + , false + , false + , 1 + , TextureFormat::RGBA32F + ); temp = BX_ALLOC(&allocator, size); float* rgba = (float*)temp; float* rgbaDst = (float*)BX_ALLOC(&allocator, size); @@ -728,7 +724,7 @@ int main(int _argc, const char* _argv[]) , mip.m_width*mip.m_bpp/8 , mip.m_format ); - imageEncodeFromRgba32f(&allocator, output->data, rgba, dstMip.m_width, dstMip.m_height, format); + imageEncodeFromRgba32f(&allocator, output->m_data, rgba, dstMip.m_width, dstMip.m_height, format); imageRgba32fToLinear(rgba , mip.m_width @@ -740,7 +736,7 @@ int main(int _argc, const char* _argv[]) for (uint8_t lod = 1; lod < numMips; ++lod) { imageRgba32fLinearDownsample2x2(rgba, dstMip.m_width, dstMip.m_height, dstMip.m_width*16, rgba); - imageGetRawData(imageContainer, 0, lod, output->data, output->size, dstMip); + imageGetRawData(*output, 0, lod, output->m_data, output->m_size, dstMip); uint8_t* data = const_cast(dstMip.m_data); imageRgba32fToGamma(rgbaDst @@ -757,10 +753,10 @@ int main(int _argc, const char* _argv[]) } else { - output = imageAlloc(imageContainer, format, mip.m_width, mip.m_height, 0, 1, false, mips); + output = imageAlloc(&allocator, format, mip.m_width, mip.m_height, 0, 1, false, mips); ImageMip dstMip; - imageGetRawData(imageContainer, 0, 0, NULL, 0, dstMip); + imageGetRawData(*output, 0, 0, NULL, 0, dstMip); if (mip.m_width != dstMip.m_width && mip.m_height != dstMip.m_height) @@ -775,7 +771,16 @@ int main(int _argc, const char* _argv[]) return EXIT_FAILURE; } - uint32_t size = imageGetSize(TextureFormat::RGBA8, dstMip.m_width, dstMip.m_height); + uint32_t size = imageGetSize( + NULL + , dstMip.m_width + , dstMip.m_height + , 0 + , false + , false + , 1 + , TextureFormat::RGBA8 + ); temp = BX_ALLOC(&allocator, size); memset(temp, 0, size); uint8_t* rgba = (uint8_t*)temp; @@ -795,12 +800,12 @@ int main(int _argc, const char* _argv[]) memcpy(ref, rgba, size); } - imageEncodeFromRgba8(output->data, rgba, dstMip.m_width, dstMip.m_height, format); + imageEncodeFromRgba8(output->m_data, rgba, dstMip.m_width, dstMip.m_height, format); for (uint8_t lod = 1; lod < numMips; ++lod) { imageRgba8Downsample2x2(rgba, dstMip.m_width, dstMip.m_height, dstMip.m_width*4, rgba); - imageGetRawData(imageContainer, 0, lod, output->data, output->size, dstMip); + imageGetRawData(*output, 0, lod, output->m_data, output->m_size, dstMip); uint8_t* data = const_cast(dstMip.m_data); imageEncodeFromRgba8(data, rgba, dstMip.m_width, dstMip.m_height, format); } @@ -808,7 +813,7 @@ int main(int _argc, const char* _argv[]) if (NULL != ref) { imageDecodeToRgba8(rgba - , output->data + , output->m_data , mip.m_width , mip.m_height , mip.m_width*mip.m_bpp/8 @@ -850,7 +855,7 @@ int main(int _argc, const char* _argv[]) { if (NULL != bx::stristr(outputFileName, ".ktx") ) { - imageWriteKtx(&writer, imageContainer, output->data, output->size); + imageWriteKtx(&writer, *output, output->m_data, output->m_size); } bx::close(&writer); @@ -875,7 +880,7 @@ int main(int _argc, const char* _argv[]) return EXIT_FAILURE; } - release(mem); + BX_FREE(&allocator, inputData); } return EXIT_SUCCESS;