diff --git a/include/bx/config.h b/include/bx/config.h index fbf6e43..16b077f 100644 --- a/include/bx/config.h +++ b/include/bx/config.h @@ -30,7 +30,7 @@ || BX_PLATFORM_QNX \ || BX_PLATFORM_RPI \ || BX_PLATFORM_WINDOWS \ - || BX_PLATFORM_WINRT \ + || BX_PLATFORM_WINRT \ ? 1 : 0) #endif // BX_CONFIG_CRT_FILE_READER_WRITER diff --git a/include/bx/readerwriter.h b/include/bx/readerwriter.h index bd22c6a..c5eb043 100644 --- a/include/bx/readerwriter.h +++ b/include/bx/readerwriter.h @@ -6,6 +6,7 @@ #ifndef BX_READERWRITER_H_HEADER_GUARD #define BX_READERWRITER_H_HEADER_GUARD +#include // va_list #include #include @@ -122,6 +123,29 @@ namespace bx return result; } + /// Write formated string. + inline int32_t writePrintf(WriterI* _writer, const char* _format, ...) + { + va_list argList; + va_start(argList, _format); + + char temp[2048]; + char* out = temp; + int32_t max = sizeof(temp); + int32_t len = vsnprintf(out, max, _format, argList); + if (len > max) + { + out = (char*)alloca(len); + len = vsnprintf(out, len, _format, argList); + } + + int32_t size = write(_writer, out, len); + + va_end(argList); + + return size; + } + /// Skip _offset bytes forward. inline int64_t skip(SeekerI* _seeker, int64_t _offset) { diff --git a/makefile b/makefile index 719e201..0020436 100644 --- a/makefile +++ b/makefile @@ -27,7 +27,7 @@ all: $(GENIE) --gcc=nacl gmake $(GENIE) --gcc=nacl-arm gmake $(GENIE) --gcc=pnacl gmake - $(GENIE) --gcc=mingw gmake + $(GENIE) --gcc=mingw-gcc gmake $(GENIE) --gcc=linux-gcc gmake $(GENIE) --gcc=osx gmake $(GENIE) --gcc=ios-arm gmake diff --git a/scripts/bin2c.lua b/scripts/bin2c.lua new file mode 100644 index 0000000..c41a535 --- /dev/null +++ b/scripts/bin2c.lua @@ -0,0 +1,19 @@ +-- +-- Copyright 2010-2013 Branimir Karadzic. All rights reserved. +-- License: http://www.opensource.org/licenses/BSD-2-Clause +-- + +project "bin2c" + uuid "60eaa654-7d06-11e4-be8e-880965202986" + kind "ConsoleApp" + + includedirs { + "../include", + } + + files { + "../tools/bin2c/**.cpp", + "../tools/bin2c/**.h", + } + + configuration {} diff --git a/scripts/genie.lua b/scripts/genie.lua index 918de54..bbeb363 100644 --- a/scripts/genie.lua +++ b/scripts/genie.lua @@ -33,6 +33,7 @@ end dofile "bx.lua" dofile "unittest++.lua" +dofile "bin2c.lua" project "bx.test" uuid "8a653da8-23d6-11e3-acb4-887628d43830" diff --git a/tools/bin2c/bin2c.cpp b/tools/bin2c/bin2c.cpp new file mode 100644 index 0000000..646cb3a --- /dev/null +++ b/tools/bin2c/bin2c.cpp @@ -0,0 +1,170 @@ +/* + * Copyright 2011-2014 Branimir Karadzic. All rights reserved. + * License: http://www.opensource.org/licenses/BSD-2-Clause + */ + +#include +#include + +#include +#include +#include + +class Bin2cWriter : public bx::WriterI +{ +public: + Bin2cWriter(bx::WriterI* _writer, const char* _name) + : m_writer(_writer) + , m_name(_name) + { + } + + virtual ~Bin2cWriter() + { + } + + virtual int32_t write(const void* _data, int32_t _size) BX_OVERRIDE + { + const char* data = (const char*)_data; + m_buffer.insert(m_buffer.end(), data, data+_size); + return _size; + } + + void finish() + { +#define HEX_DUMP_WIDTH 16 +#define HEX_DUMP_SPACE_WIDTH 96 +#define HEX_DUMP_FORMAT "%-" BX_STRINGIZE(HEX_DUMP_SPACE_WIDTH) "." BX_STRINGIZE(HEX_DUMP_SPACE_WIDTH) "s" + const uint8_t* data = &m_buffer[0]; + uint32_t size = (uint32_t)m_buffer.size(); + + bx::writePrintf(m_writer, "static const uint8_t %s[%d] =\n{\n", m_name.c_str(), size); + + if (NULL != data) + { + char hex[HEX_DUMP_SPACE_WIDTH+1]; + char ascii[HEX_DUMP_WIDTH+1]; + uint32_t hexPos = 0; + uint32_t asciiPos = 0; + for (uint32_t ii = 0; ii < size; ++ii) + { + bx::snprintf(&hex[hexPos], sizeof(hex)-hexPos, "0x%02x, ", data[asciiPos]); + hexPos += 6; + + ascii[asciiPos] = isprint(data[asciiPos]) && data[asciiPos] != '\\' ? data[asciiPos] : '.'; + asciiPos++; + + if (HEX_DUMP_WIDTH == asciiPos) + { + ascii[asciiPos] = '\0'; + bx::writePrintf(m_writer, "\t" HEX_DUMP_FORMAT "// %s\n", hex, ascii); + data += asciiPos; + hexPos = 0; + asciiPos = 0; + } + } + + if (0 != asciiPos) + { + ascii[asciiPos] = '\0'; + bx::writePrintf(m_writer, "\t" HEX_DUMP_FORMAT "// %s\n", hex, ascii); + } + } + + bx::writePrintf(m_writer, "};\n"); +#undef HEX_DUMP_WIDTH +#undef HEX_DUMP_SPACE_WIDTH +#undef HEX_DUMP_FORMAT + + m_buffer.clear(); + } + + bx::WriterI* m_writer; + std::string m_filePath; + std::string m_name; + typedef std::vector Buffer; + Buffer m_buffer; +}; + +void help(const char* _error = NULL) +{ + if (NULL != _error) + { + fprintf(stderr, "Error:\n%s\n\n", _error); + } + + fprintf(stderr + , "bin2c, binary to C\n" + "Copyright 2011-2014 Branimir Karadzic. All rights reserved.\n" + "License: http://www.opensource.org/licenses/BSD-2-Clause\n\n" + ); + + fprintf(stderr + , "Usage: bin2c -f -o -n \n" + + "\n" + "Options:\n" + " -f Input file path.\n" + " -o Output file path.\n" + " -n Array name.\n" + + "\n" + "For additional information, see https://github.com/bkaradzic/bx\n" + ); +} + + +int main(int _argc, const char* _argv[]) +{ + bx::CommandLine cmdLine(_argc, _argv); + + if (cmdLine.hasArg('h', "help") ) + { + help(); + return EXIT_FAILURE; + } + + const char* filePath = cmdLine.findOption('f'); + if (NULL == filePath) + { + help("Input file name must be specified."); + return EXIT_FAILURE; + } + + const char* outFilePath = cmdLine.findOption('o'); + if (NULL == outFilePath) + { + help("Output file name must be specified."); + return EXIT_FAILURE; + } + + const char* name = cmdLine.findOption('n'); + if (NULL == name) + { + name = "data"; + } + + void* data = NULL; + size_t size = 0; + + bx::CrtFileReader fr; + if (0 == bx::open(&fr, filePath) ) + { + size = (size_t)bx::getSize(&fr); + data = malloc(size); + bx::read(&fr, data, size); + + bx::CrtFileWriter fw; + if (0 == bx::open(&fw, outFilePath) ) + { + Bin2cWriter writer(&fw, name); + bx::write(&writer, data, size); + writer.finish(); + bx::close(&fw); + } + + free(data); + } + + return 0; +}