ARB
awt_hexdump.hxx
Go to the documentation of this file.
1 // ================================================================= //
2 // //
3 // File : awt_hexdump.hxx //
4 // Purpose : //
5 // //
6 // Coded by Ralf Westram (coder@reallysoft.de) in September 2011 //
7 // Institute of Microbiology (Technical University Munich) //
8 // http://www.arb-home.de/ //
9 // //
10 // ================================================================= //
11 
12 #ifndef AWT_HEXDUMP_HXX
13 #define AWT_HEXDUMP_HXX
14 
15 #ifndef AWT_HXX
16 #include "awt.hxx"
17 #endif
18 
19 #ifndef AW_ROOT_HXX
20 #include <aw_root.hxx>
21 #endif
22 #ifndef ARB_STRBUF_H
23 #include <arb_strbuf.h>
24 #endif
25 #ifndef _GLIBCXX_CCTYPE
26 #include <cctype>
27 #endif
28 
29 // -------------------
30 // hex dumper
31 
32 CONSTEXPR_INLINE char nibble2hex(unsigned char c) { return "0123456789ABCDEF"[c&0x0f]; }
33 inline void dump_hexbyte(GBS_strstruct& buf, unsigned char c) { buf.put(nibble2hex(c>>4)); buf.put(nibble2hex(c)); }
34 
35 class MemDump {
36  bool show_offset; // prefix every line with position info ?
37  bool hex; // dump hex ?
38  bool ascii; // dump ascii ?
39 
40  size_t width; // > 0 -> wrap lines every XXX positions
41  size_t separate; // > 0 -> separate by one additional space after every XXX bytes
42  bool space; // true -> space hex bytes
43 
44  bool is_separate_position(size_t pos) const { return separate && pos && !(pos%separate); }
45 
46  void dump_sep(GBS_strstruct& buf) const { buf.cat(" | "); }
47  void dump_offset(GBS_strstruct& buf, size_t off) const {
48  if (show_offset) {
49  dump_hexbyte(buf, off>>8);
50  dump_hexbyte(buf, off&0xff);
51  if (hex||ascii) dump_sep(buf);
52  }
53  }
54  void dump_hex(GBS_strstruct& buf, const char *mem, size_t off, size_t count, bool padded) const {
55  size_t i;
56  for (i = 0; i<count; ++i) {
57  if (is_separate_position(i)) buf.put(' ');
58  dump_hexbyte(buf, mem[off+i]);
59  if (space) buf.put(' ');
60  }
61  if (padded) {
62  for (; i<width; ++i) {
63  buf.nput(' ', 2+space+is_separate_position(i));
64  }
65  }
66  buf.cut_tail(space);
67  }
68  void dump_ascii(GBS_strstruct& buf, const char *mem, size_t off, size_t count) const {
69  for (size_t i = 0; i<count; ++i) {
70  if (is_separate_position(i)) buf.put(' ');
71  buf.put(isprint(mem[off+i]) ? mem[off+i] : '.');
72  }
73  }
74  void dump_line(GBS_strstruct& buf, const char *mem, size_t off, size_t count) const {
75  dump_offset(buf, off);
76  if (hex) {
77  dump_hex(buf, mem, off, count, ascii);
78  if (ascii) dump_sep(buf);
79  }
80  if (ascii) dump_ascii(buf, mem, off, count);
81  buf.put('\n');
82  }
83  void dump_wrapped(GBS_strstruct& buf, const char *mem, size_t size) const {
85  size_t off = 0;
86  while (size) {
87  size_t count = size<width ? size : width;
88  dump_line(buf, mem, off, count);
89  size -= count;
90  off += count;
91  }
92  }
93 
94 public:
95 
96  MemDump(bool show_offset_, bool hex_, bool ascii_, size_t width_ = 0, size_t separate_ = 0, bool space_ = true)
97  : show_offset(show_offset_),
98  hex(hex_),
99  ascii(ascii_),
100  width(width_),
101  separate(separate_),
102  space(space_)
103  {}
104 
105  bool wrapped() const { return width; }
106 
107  size_t mem_needed_for_dump(size_t bytes) const {
108  size_t sections = show_offset+hex+ascii;
109 
110  if (!sections) return 1;
111 
112  size_t perByte = hex*3+ascii;
113  size_t extraPerLine = (sections-1)*3+1;
114  size_t lines = width ? bytes/width+1 : 1;
115 
116  return bytes*perByte + lines*extraPerLine + 50;
117  }
118 
119  void dump_to(GBS_strstruct& buf, const char *mem, size_t size) const {
120  if (size) {
121  if (wrapped()) dump_wrapped(buf, mem, size);
122  else { // one-line dump
123  MemDump mod(*this);
124  mod.width = size;
125  mod.dump_wrapped(buf, mem, size);
126  }
127  }
128  }
129 };
130 
131 
132 
133 #else
134 #error awt_hexdump.hxx included twice
135 #endif // AWT_HEXDUMP_HXX
void cut_tail(size_t byte_count)
Definition: arb_strbuf.h:145
#define awt_assert(cond)
Definition: awt.hxx:28
void nput(char c, size_t count)
Definition: arb_strbuf.h:180
void cat(const char *from)
Definition: arb_strbuf.h:199
bool wrapped() const
CONSTEXPR_INLINE char nibble2hex(unsigned char c)
Definition: awt_hexdump.hxx:32
size_t mem_needed_for_dump(size_t bytes) const
#define CONSTEXPR_INLINE
Definition: cxxforward.h:111
void dump_to(GBS_strstruct &buf, const char *mem, size_t size) const
MemDump(bool show_offset_, bool hex_, bool ascii_, size_t width_=0, size_t separate_=0, bool space_=true)
Definition: awt_hexdump.hxx:96
void dump_hexbyte(GBS_strstruct &buf, unsigned char c)
Definition: awt_hexdump.hxx:33
void put(char c)
Definition: arb_strbuf.h:174