1 // Copyright (2013) Jann Horn <jann@thejh.net>
2 // This code is licensed under the AGPLv3.
4 HEADER #include <sys/types.h>
8 static inline char hexchar(unsigned char c) {
9 if (c >= 10) return c+'a'-10;
13 // If `in_len` is -1, it means that `in` is a null-terminated string.
14 // `out` must have space for `in_len*2+1` bytes.
15 PUBLIC_FN void hex_encode(char *in, ssize_t in_len, char *out) {
16 if (in_len == -1) in_len = strlen(in);
18 char *in_end = in+in_len;
20 unsigned char c = *(unsigned char *)(in++);
21 *(out++) = hexchar(c>>4);
22 *(out++) = hexchar(c&0xf);
27 static inline unsigned char unhexchar(char c) {
28 if (c >= '0' && c <= '9') return c-'0';
29 if (c >= 'a' && c <= 'f') return c-'a'+10;
30 if (c >= 'A' && c <= 'F') return c-'A'+10;
34 // Returns number of decoded bytes or -1(error).
35 // Does not null-terminate output.
36 PUBLIC_FN ssize_t hex_decode(char *in, ssize_t in_len, char *out) {
38 if (in_len == -1) in_len = strlen(in);
40 if (in_len&1) return -1; /* n%2 must be 0 */
41 char *in_end = in + in_len;
43 unsigned char hi = unhexchar(*(in++));
44 unsigned char lo = unhexchar(*(in++));
45 if (hi == 255 || lo == 255) return -1;
46 *(out++) = (hi<<4) | lo;