This source file includes following definitions.
- hex_to_bin
- hex2bin
- bin2hex
- hex_dump_to_buffer
- print_hex_dump
1
2
3
4
5
6 #include <linux/types.h>
7 #include <linux/ctype.h>
8 #include <linux/errno.h>
9 #include <linux/kernel.h>
10 #include <linux/export.h>
11 #include <asm/unaligned.h>
12
13 const char hex_asc[] = "0123456789abcdef";
14 EXPORT_SYMBOL(hex_asc);
15 const char hex_asc_upper[] = "0123456789ABCDEF";
16 EXPORT_SYMBOL(hex_asc_upper);
17
18
19
20
21
22
23
24
25 int hex_to_bin(char ch)
26 {
27 if ((ch >= '0') && (ch <= '9'))
28 return ch - '0';
29 ch = tolower(ch);
30 if ((ch >= 'a') && (ch <= 'f'))
31 return ch - 'a' + 10;
32 return -1;
33 }
34 EXPORT_SYMBOL(hex_to_bin);
35
36
37
38
39
40
41
42
43
44 int hex2bin(u8 *dst, const char *src, size_t count)
45 {
46 while (count--) {
47 int hi = hex_to_bin(*src++);
48 int lo = hex_to_bin(*src++);
49
50 if ((hi < 0) || (lo < 0))
51 return -EINVAL;
52
53 *dst++ = (hi << 4) | lo;
54 }
55 return 0;
56 }
57 EXPORT_SYMBOL(hex2bin);
58
59
60
61
62
63
64
65 char *bin2hex(char *dst, const void *src, size_t count)
66 {
67 const unsigned char *_src = src;
68
69 while (count--)
70 dst = hex_byte_pack(dst, *_src++);
71 return dst;
72 }
73 EXPORT_SYMBOL(bin2hex);
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105 int hex_dump_to_buffer(const void *buf, size_t len, int rowsize, int groupsize,
106 char *linebuf, size_t linebuflen, bool ascii)
107 {
108 const u8 *ptr = buf;
109 int ngroups;
110 u8 ch;
111 int j, lx = 0;
112 int ascii_column;
113 int ret;
114
115 if (rowsize != 16 && rowsize != 32)
116 rowsize = 16;
117
118 if (len > rowsize)
119 len = rowsize;
120 if (!is_power_of_2(groupsize) || groupsize > 8)
121 groupsize = 1;
122 if ((len % groupsize) != 0)
123 groupsize = 1;
124
125 ngroups = len / groupsize;
126 ascii_column = rowsize * 2 + rowsize / groupsize + 1;
127
128 if (!linebuflen)
129 goto overflow1;
130
131 if (!len)
132 goto nil;
133
134 if (groupsize == 8) {
135 const u64 *ptr8 = buf;
136
137 for (j = 0; j < ngroups; j++) {
138 ret = snprintf(linebuf + lx, linebuflen - lx,
139 "%s%16.16llx", j ? " " : "",
140 get_unaligned(ptr8 + j));
141 if (ret >= linebuflen - lx)
142 goto overflow1;
143 lx += ret;
144 }
145 } else if (groupsize == 4) {
146 const u32 *ptr4 = buf;
147
148 for (j = 0; j < ngroups; j++) {
149 ret = snprintf(linebuf + lx, linebuflen - lx,
150 "%s%8.8x", j ? " " : "",
151 get_unaligned(ptr4 + j));
152 if (ret >= linebuflen - lx)
153 goto overflow1;
154 lx += ret;
155 }
156 } else if (groupsize == 2) {
157 const u16 *ptr2 = buf;
158
159 for (j = 0; j < ngroups; j++) {
160 ret = snprintf(linebuf + lx, linebuflen - lx,
161 "%s%4.4x", j ? " " : "",
162 get_unaligned(ptr2 + j));
163 if (ret >= linebuflen - lx)
164 goto overflow1;
165 lx += ret;
166 }
167 } else {
168 for (j = 0; j < len; j++) {
169 if (linebuflen < lx + 2)
170 goto overflow2;
171 ch = ptr[j];
172 linebuf[lx++] = hex_asc_hi(ch);
173 if (linebuflen < lx + 2)
174 goto overflow2;
175 linebuf[lx++] = hex_asc_lo(ch);
176 if (linebuflen < lx + 2)
177 goto overflow2;
178 linebuf[lx++] = ' ';
179 }
180 if (j)
181 lx--;
182 }
183 if (!ascii)
184 goto nil;
185
186 while (lx < ascii_column) {
187 if (linebuflen < lx + 2)
188 goto overflow2;
189 linebuf[lx++] = ' ';
190 }
191 for (j = 0; j < len; j++) {
192 if (linebuflen < lx + 2)
193 goto overflow2;
194 ch = ptr[j];
195 linebuf[lx++] = (isascii(ch) && isprint(ch)) ? ch : '.';
196 }
197 nil:
198 linebuf[lx] = '\0';
199 return lx;
200 overflow2:
201 linebuf[lx++] = '\0';
202 overflow1:
203 return ascii ? ascii_column + len : (groupsize * 2 + 1) * ngroups - 1;
204 }
205 EXPORT_SYMBOL(hex_dump_to_buffer);
206
207 #ifdef CONFIG_PRINTK
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239 void print_hex_dump(const char *level, const char *prefix_str, int prefix_type,
240 int rowsize, int groupsize,
241 const void *buf, size_t len, bool ascii)
242 {
243 const u8 *ptr = buf;
244 int i, linelen, remaining = len;
245 unsigned char linebuf[32 * 3 + 2 + 32 + 1];
246
247 if (rowsize != 16 && rowsize != 32)
248 rowsize = 16;
249
250 for (i = 0; i < len; i += rowsize) {
251 linelen = min(remaining, rowsize);
252 remaining -= rowsize;
253
254 hex_dump_to_buffer(ptr + i, linelen, rowsize, groupsize,
255 linebuf, sizeof(linebuf), ascii);
256
257 switch (prefix_type) {
258 case DUMP_PREFIX_ADDRESS:
259 printk("%s%s%p: %s\n",
260 level, prefix_str, ptr + i, linebuf);
261 break;
262 case DUMP_PREFIX_OFFSET:
263 printk("%s%s%.8x: %s\n", level, prefix_str, i, linebuf);
264 break;
265 default:
266 printk("%s%s%s\n", level, prefix_str, linebuf);
267 break;
268 }
269 }
270 }
271 EXPORT_SYMBOL(print_hex_dump);
272
273 #endif