Stuff ► Code Snippets ► Hexadecimal Output (C++)
You are viewing an old version of the ionflux.org website! Please visit the new version here.

Hexadecimal Output (C++)

I often want to take a look at data which has been generated by some code I have written, but which is not readable very well by humans. In the worst case, it may even contain characters which are not printable at all. For these situations, I have written some nice little functions which display arbitrary byte data in hexadecimal notation, much like in a hexadecimal editor. It is also possible to view the hexadecimal representation side by side with the readable characters.

Byte to Hexadecimal String Converter

This snippet does the simple task of converting a string of bytes to a string of hexadecimal numbers.

#include <string> #include <sstream> #include <iomanip> std::string make_hex(const std::string& inputData) { std::ostringstream buffer; buffer << std::uppercase << std::right << std::setfill('0') << std::hex; for (unsigned int i = 0; i < inputData.size(); i++) buffer << std::setw(2) << int(static_cast<unsigned char>(inputData[i])); return buffer.str(); }

Make Readable Text

Some characters can be considered readable, even in a soup of random bytes. This piece of code replaces those characters which are not considered readable by a replacement. The other characters are appended unchanged. If UTF-8 encoding is available (see the code snippets in the previous section on how to do this), the version below will display much more characters. They may not all be readable, but they do look interesting. ;-)

#include <string> #include <sstream> std::string make_readable(const std::string& inputData, const std::string& replacement = ".") { std::ostringstream buffer; unsigned char currentChar; for (unsigned int i = 0; i < inputData.size(); i++) { currentChar = static_cast<unsigned char>(inputData[i]); if (((currentChar >= 32) && (currentChar <= 126)) || (currentChar >= 160)) buffer << inputData[i]; else buffer << replacement; } return buffer.str(); } // This requires the uint_to_utf8() function from the previous section. std::string make_readable(const std::string& inputData, const std::string& replacement = ".") { std::ostringstream buffer; unsigned int currentChar; for (unsigned int i = 0; i < inputData.size(); i++) { currentChar = static_cast<unsigned int>( static_cast<unsigned char>(inputData[i])); if ((currentChar >= 32) && (currentChar <= 126)) buffer << inputData[i]; else if (currentChar >= 127) buffer << uint_to_utf8(currentChar); else buffer << replacement; } return buffer.str(); }

Make Nice Hexadecimal Output

Now we are ready to do some really nice things with the hexadecimal string and the readable representation of the data. The following function creates a column layout with arranges the bytes properly beside the readable characters. The version below fills in some defaults and puts everything together for a hex view which is really simple to use at any time when data needs to be inspected closely.

#include <string> #include <sstream> std::string make_nice_hex(const std::string& hex, const std::string& readable, int bytesPerLine, int groupBytes) { std::ostringstream buffer; std::string paddedHex(hex); std::string paddedReadable(readable); if ((paddedHex.size() % 2) != 0) paddedHex.append(" "); while (((paddedHex.size() / 2) % bytesPerLine) != 0) paddedHex.append(" "); unsigned int bytes = paddedHex.size() / 2; while (paddedReadable.size() < bytes) paddedReadable.append(" "); int readablePos = 0; for (unsigned int i = 0; i < bytes; i++) { buffer << paddedHex.substr(2 * i, 2) << " "; if ((((i + 1) % groupBytes) == 0) && (((i + 1) % bytesPerLine) != 0)) buffer << " "; if (((i + 1) % bytesPerLine) == 0) { buffer << " " << paddedReadable.substr(readablePos, bytesPerLine) << "n"; readablePos += bytesPerLine; } } return buffer.str(); } std::string make_nice_hex(const std::string& data, int bytesPerLine = 20, int groupBytes = 10) { return make_nice_hex(make_hex(data), make_readable(data, "."), bytesPerLine, groupBytes); }
© 2006-2007 Jörn P. Meier  •  Impressum  •  Datenschutz  •  Contact: webmaster@ionflux.org  •  Last update: 2009-04-27  •  Version 2.0  •  Language: en | de