1 /* convert.c - Hex conversion functions.
2 * Copyright (C) 2006, 2008 Free Software Foundation, Inc.
4 * This file is part of GnuPG.
6 * This file is free software; you can redistribute it and/or modify
7 * it under the terms of either
9 * - the GNU Lesser General Public License as published by the Free
10 * Software Foundation; either version 3 of the License, or (at
11 * your option) any later version.
15 * - the GNU General Public License as published by the Free
16 * Software Foundation; either version 2 of the License, or (at
17 * your option) any later version.
19 * or both in parallel, as here.
21 * This file is distributed in the hope that it will be useful,
22 * but WITHOUT ANY WARRANTY; without even the implied warranty of
23 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24 * GNU General Public License for more details.
26 * You should have received a copy of the GNU General Public License
27 * along with this program; if not, see <https://www.gnu.org/licenses/>.
38 #define tohex(n) ((n) < 10 ? ((n) + '0') : (((n) - 10) + 'A'))
41 /* Convert STRING consisting of hex characters into its binary
42 representation and store that at BUFFER. BUFFER needs to be of
43 LENGTH bytes. The function checks that the STRING will convert
44 exactly to LENGTH bytes. The string is delimited by either end of
45 string or a white space character. The function returns -1 on
46 error or the length of the parsed string. */
48 hex2bin (const char *string, void *buffer, size_t length)
51 const char *s = string;
53 for (i=0; i < length; )
55 if (!hexdigitp (s) || !hexdigitp (s+1))
56 return -1; /* Invalid hex digits. */
57 ((unsigned char*)buffer)[i++] = xtoi_2 (s);
60 if (*s && (!isascii (*s) || !isspace (*s)) )
61 return -1; /* Not followed by Nul or white space. */
63 return -1; /* Not of expected length. */
65 s++; /* Skip the delimiter. */
70 /* Convert STRING consisting of hex characters into its binary representation
71 and store that at BUFFER. BUFFER needs to be of LENGTH bytes. The
72 function check that the STRING will convert exactly to LENGTH
73 bytes. Colons between the hex digits are allowed, if one colon
74 has been given a colon is expected very 2 characters. The string
75 is delimited by either end of string or a white space character.
76 The function returns -1 on error or the length of the parsed
79 hexcolon2bin (const char *string, void *buffer, size_t length)
82 const char *s = string;
85 for (i=0; i < length; )
87 if (i==1 && *s == ':') /* Skip colons between hex digits. */
92 else if (need_colon && *s == ':')
95 return -1; /* Colon expected. */
96 if (!hexdigitp (s) || !hexdigitp (s+1))
97 return -1; /* Invalid hex digits. */
98 ((unsigned char*)buffer)[i++] = xtoi_2 (s);
102 return -1; /* Trailing colons are not allowed. */
103 if (*s && (!isascii (*s) || !isspace (*s)) )
104 return -1; /* Not followed by Nul or white space. */
106 return -1; /* Not of expected length. */
108 s++; /* Skip the delimiter. */
115 do_bin2hex (const void *buffer, size_t length, char *stringbuf, int with_colon)
117 const unsigned char *s;
122 /* Not really correct for with_colon but we don't care about the
124 size_t n = with_colon? 3:2;
125 size_t nbytes = n * length + 1;
126 if (length && (nbytes-1) / n != length)
128 gpg_err_set_errno (ENOMEM);
131 stringbuf = xtrymalloc (nbytes);
136 for (s = buffer, p = stringbuf; length; length--, s++)
138 if (with_colon && s != buffer)
140 *p++ = tohex ((*s>>4)&15);
141 *p++ = tohex (*s&15);
149 /* Convert LENGTH bytes of data in BUFFER into hex encoding and store
150 that at the provided STRINGBUF. STRINGBUF must be allocated of at
151 least (2*LENGTH+1) bytes or be NULL so that the function mallocs an
152 appropriate buffer. Returns STRINGBUF or NULL on error (which may
153 only occur if STRINGBUF has been NULL and the internal malloc
156 bin2hex (const void *buffer, size_t length, char *stringbuf)
158 return do_bin2hex (buffer, length, stringbuf, 0);
161 /* Convert LENGTH bytes of data in BUFFER into hex encoding and store
162 that at the provided STRINGBUF. STRINGBUF must be allocated of at
163 least (3*LENGTH+1) bytes or be NULL so that the function mallocs an
164 appropriate buffer. Returns STRINGBUF or NULL on error (which may
165 only occur if STRINGBUF has been NULL and the internal malloc
168 bin2hexcolon (const void *buffer, size_t length, char *stringbuf)
170 return do_bin2hex (buffer, length, stringbuf, 1);
175 /* Convert HEXSTRING consisting of hex characters into string and
176 store that at BUFFER. HEXSTRING is either delimited by end of
177 string or a white space character. The function makes sure that
178 the resulting string in BUFFER is terminated by a Nul byte. Note
179 that the returned string may include embedded Nul bytes; the extra
180 Nul byte at the end is used to make sure tha the result can always
181 be used as a C-string.
183 BUFSIZE is the available length of BUFFER; if the converted result
184 plus a possible required extra Nul character does not fit into this
185 buffer, the function returns NULL and won't change the existing
186 content of BUFFER. In-place conversion is possible as long as
187 BUFFER points to HEXSTRING.
189 If BUFFER is NULL and BUFSIZE is 0 the function scans HEXSTRING but
190 does not store anything. This may be used to find the end of
193 On success the function returns a pointer to the next character
194 after HEXSTRING (which is either end-of-string or a the next white
195 space). If BUFLEN is not NULL the number of valid vytes in BUFFER
196 is stored there (an extra Nul byte is not counted); this will even
197 be done if BUFFER has been passed as NULL. */
199 hex2str (const char *hexstring, char *buffer, size_t bufsize, size_t *buflen)
201 const char *s = hexstring;
208 for (s=hexstring, count=0; hexdigitp (s) && hexdigitp (s+1); s += 2, count++)
210 if (*s && (!isascii (*s) || !isspace (*s)) )
212 gpg_err_set_errno (EINVAL);
213 return NULL; /* Not followed by Nul or white space. */
215 /* We need to append a nul character. However we don't want that if
216 the hexstring already ends with "00". */
217 need_nul = ((s == hexstring) || !(s[-2] == '0' && s[-1] == '0'));
225 gpg_err_set_errno (EINVAL);
226 return NULL; /* Too long. */
229 for (s=hexstring, idx=0; hexdigitp (s) && hexdigitp (s+1); s += 2)
230 ((unsigned char*)buffer)[idx++] = xtoi_2 (s);
236 *buflen = count - need_nul;
241 /* Same as hex2str but this function allocated a new string. Returns
242 NULL on error. If R_COUNT is not NULL, the number of scanned bytes
243 will be stored there. ERRNO is set on error. */
245 hex2str_alloc (const char *hexstring, size_t *r_count)
251 tail = hex2str (hexstring, NULL, 0, &nbytes);
259 *r_count = tail - hexstring;
260 result = xtrymalloc (nbytes+1);
263 if (!hex2str (hexstring, result, nbytes+1, NULL))