1/* 2 * Copyright 2013, Ingo Weinhold, ingo_weinhold@gmx.de. 3 * Distributed under the terms of the MIT License. 4 */ 5 6 7#include <debug_hex_dump.h> 8 9#include <ctype.h> 10#include <stdio.h> 11 12 13namespace BKernel { 14 15 16// #pragma mark - HexDumpDataProvider 17 18 19HexDumpDataProvider::~HexDumpDataProvider() 20{ 21} 22 23 24bool 25HexDumpDataProvider::GetAddressString(char* buffer, size_t bufferSize) const 26{ 27 return false; 28} 29 30 31// #pragma mark - HexDumpBufferDataProvider 32 33 34HexDumpBufferDataProvider::HexDumpBufferDataProvider(const void* data, 35 size_t dataSize) 36 : 37 fData((const uint8*)data), 38 fDataSize(dataSize) 39{ 40} 41 42 43bool 44HexDumpBufferDataProvider::HasMoreData() const 45{ 46 return fDataSize > 0; 47} 48 49 50uint8 51HexDumpBufferDataProvider::NextByte() 52{ 53 if (fDataSize == 0) 54 return '\0'; 55 56 fDataSize--; 57 return *fData++; 58} 59 60 61bool 62HexDumpBufferDataProvider::GetAddressString(char* buffer, 63 size_t bufferSize) const 64{ 65 snprintf(buffer, bufferSize, "%p", fData); 66 return true; 67} 68 69 70// #pragma mark - 71 72 73void 74print_hex_dump(HexDumpDataProvider& data, size_t maxBytes, uint32 flags) 75{ 76 static const size_t kBytesPerBlock = 4; 77 static const size_t kBytesPerLine = 16; 78 79 size_t i = 0; 80 for (; i < maxBytes && data.HasMoreData();) { 81 if (i > 0) 82 kputs("\n"); 83 84 // print address 85 uint8 buffer[kBytesPerLine]; 86 if ((flags & HEX_DUMP_FLAG_OMIT_ADDRESS) == 0 87 && data.GetAddressString((char*)buffer, sizeof(buffer))) { 88 kputs((char*)buffer); 89 kputs(": "); 90 } 91 92 // get the line data 93 size_t bytesInLine = 0; 94 for (; i < maxBytes && bytesInLine < kBytesPerLine 95 && data.HasMoreData(); 96 i++) { 97 buffer[bytesInLine++] = data.NextByte(); 98 } 99 100 // print hex representation 101 for (size_t k = 0; k < bytesInLine; k++) { 102 if (k > 0 && k % kBytesPerBlock == 0) 103 kputs(" "); 104 kprintf("%02x", buffer[k]); 105 } 106 107 // pad to align the text representation, if line is incomplete 108 if (bytesInLine < kBytesPerLine) { 109 int missingBytes = int(kBytesPerLine - bytesInLine); 110 kprintf("%*s", 111 2 * missingBytes + int(missingBytes / kBytesPerBlock), ""); 112 } 113 114 // print character representation 115 kputs(" "); 116 for (size_t k = 0; k < bytesInLine; k++) 117 kprintf("%c", isprint(buffer[k]) ? buffer[k] : '.'); 118 } 119 120 if (i > 0) 121 kputs("\n"); 122} 123 124 125void 126print_hex_dump(const void* data, size_t maxBytes, uint32 flags) 127{ 128 HexDumpBufferDataProvider dataProvider(data, maxBytes); 129 print_hex_dump(dataProvider, maxBytes, flags); 130} 131 132 133} // namespace BKernel 134