1#pragma once
2#include <string>
3
4
5/// Maps 0..15 to 0..9A..F or 0..9a..f correspondingly.
6
7extern const char * const hex_digit_to_char_uppercase_table;
8extern const char * const hex_digit_to_char_lowercase_table;
9
10inline char hexDigitUppercase(unsigned char c)
11{
12 return hex_digit_to_char_uppercase_table[c];
13}
14
15inline char hexDigitLowercase(unsigned char c)
16{
17 return hex_digit_to_char_lowercase_table[c];
18}
19
20
21#include <cstring>
22#include <cstddef>
23
24#include <common/Types.h>
25
26
27/// Maps 0..255 to 00..FF or 00..ff correspondingly
28
29extern const char * const hex_byte_to_char_uppercase_table;
30extern const char * const hex_byte_to_char_lowercase_table;
31
32inline void writeHexByteUppercase(UInt8 byte, void * out)
33{
34 memcpy(out, &hex_byte_to_char_uppercase_table[static_cast<size_t>(byte) * 2], 2);
35}
36
37inline void writeHexByteLowercase(UInt8 byte, void * out)
38{
39 memcpy(out, &hex_byte_to_char_lowercase_table[static_cast<size_t>(byte) * 2], 2);
40}
41
42
43/// Produces hex representation of an unsigned int with leading zeros (for checksums)
44template <typename TUInt>
45inline void writeHexUIntImpl(TUInt uint_, char * out, const char * const table)
46{
47 union
48 {
49 TUInt value;
50 UInt8 uint8[sizeof(TUInt)];
51 };
52
53 value = uint_;
54
55 /// Use little endian
56 for (size_t i = 0; i < sizeof(TUInt); ++i)
57 memcpy(out + i * 2, &table[static_cast<size_t>(uint8[sizeof(TUInt) - 1 - i]) * 2], 2);
58}
59
60template <typename TUInt>
61inline void writeHexUIntUppercase(TUInt uint_, char * out)
62{
63 writeHexUIntImpl(uint_, out, hex_byte_to_char_uppercase_table);
64}
65
66template <typename TUInt>
67inline void writeHexUIntLowercase(TUInt uint_, char * out)
68{
69 writeHexUIntImpl(uint_, out, hex_byte_to_char_lowercase_table);
70}
71
72template <typename TUInt>
73std::string getHexUIntUppercase(TUInt uint_)
74{
75 std::string res(sizeof(TUInt) * 2, '\0');
76 writeHexUIntUppercase(uint_, res.data());
77 return res;
78}
79
80template <typename TUInt>
81std::string getHexUIntLowercase(TUInt uint_)
82{
83 std::string res(sizeof(TUInt) * 2, '\0');
84 writeHexUIntLowercase(uint_, res.data());
85 return res;
86}
87
88
89/// Maps 0..9, A..F, a..f to 0..15. Other chars are mapped to implementation specific value.
90
91extern const char * const hex_char_to_digit_table;
92
93inline char unhex(char c)
94{
95 return hex_char_to_digit_table[static_cast<UInt8>(c)];
96}
97
98inline char unhex2(const char * data)
99{
100 return
101 static_cast<UInt8>(unhex(data[0])) * 0x10
102 + static_cast<UInt8>(unhex(data[1]));
103}
104
105inline UInt16 unhex4(const char * data)
106{
107 return
108 static_cast<UInt16>(unhex(data[0])) * 0x1000
109 + static_cast<UInt16>(unhex(data[1])) * 0x100
110 + static_cast<UInt16>(unhex(data[2])) * 0x10
111 + static_cast<UInt16>(unhex(data[3]));
112}
113