3 * Where all the hard work is done
6 * See the file LICENSE for the license
11 #include <ldns/ldns.h>
14 * Converts a hex string to binary data
15 * len is the length of the string
16 * buf is the buffer to store the result in
17 * offset is the starting position in the result buffer
19 * This function returns the length of the result
22 hexstr2bin(char *hexstr
, int len
, uint8_t *buf
, size_t offset
, size_t buf_len
)
34 for (i
=0; i
<len
; i
++) {
37 /* case insensitive, skip spaces */
39 if (c
>= '0' && c
<= '9') {
41 } else if (c
>= 'a' && c
<= 'z') {
42 int8
+= (c
& 0x0f) + 9;
43 } else if (c
>= 'A' && c
<= 'Z') {
44 int8
+= (c
& 0x0f) + 9;
53 if (bufpos
+ offset
+ 1 <= buf_len
) {
54 buf
[bufpos
+offset
] = int8
;
59 error("Buffer too small in hexstr2bin");
68 packetbuffromfile(char *filename
, uint8_t *wire
)
75 * 1 = comment (skip to end of line)
76 * 2 = unprintable character found, read binary data directly
79 uint8_t *hexbuf
= xmalloc(LDNS_MAX_PACKETLEN
);
83 if (strncmp(filename
, "-", 2) == 0) {
86 fp
= fopen(filename
, "r");
89 perror("Unable to open file for reading");
94 /*verbose("Opened %s\n", filename);*/
97 while (c
!= EOF
&& hexbufpos
< LDNS_MAX_PACKETLEN
) {
98 if (state
< 2 && !isascii(c
)) {
99 /*verbose("non ascii character found in file: (%d) switching to raw mode\n", c);*/
104 if ( (c
>= '0' && c
<= '9') ||
105 (c
>= 'a' && c
<= 'f') ||
106 (c
>= 'A' && c
<= 'F') )
108 hexbuf
[hexbufpos
] = (uint8_t) c
;
110 } else if (c
== ';') {
112 } else if (c
== ' ' || c
== '\t' || c
== '\n') {
113 /* skip whitespace */
117 if (c
== '\n' || c
== EOF
) {
122 hexbuf
[hexbufpos
] = (uint8_t) c
;
131 if (have_drill_opt && drill_opt->verbose) {
132 verbose("END OF FILE REACHED\n");
135 verbose("%s\n", hexbuf);
137 verbose("Not printing wire because it contains non ascii data\n");
142 if (hexbufpos
>= LDNS_MAX_PACKETLEN
) {
143 /*verbose("packet size reached\n");*/
146 /* lenient mode: length must be multiple of 2 */
147 if (hexbufpos
% 2 != 0) {
148 hexbuf
[hexbufpos
] = (uint8_t) '0';
153 wirelen
= hexstr2bin((char *) hexbuf
,
159 memcpy(wire
, hexbuf
, (size_t) hexbufpos
);
160 wirelen
= (size_t) hexbufpos
;
170 read_hex_buffer(char *filename
)
174 ldns_buffer
*result_buffer
= NULL
;
177 wire
= xmalloc(LDNS_MAX_PACKETLEN
);
179 wiresize
= packetbuffromfile(filename
, wire
);
181 result_buffer
= LDNS_MALLOC(ldns_buffer
);
182 ldns_buffer_new_frm_data(result_buffer
, wire
, wiresize
);
183 ldns_buffer_set_position(result_buffer
, ldns_buffer_capacity(result_buffer
));
186 return result_buffer
;
190 read_hex_pkt(char *filename
)
195 ldns_pkt
*pkt
= NULL
;
197 ldns_status status
= LDNS_STATUS_ERR
;
199 wire
= xmalloc(LDNS_MAX_PACKETLEN
);
201 wiresize
= packetbuffromfile(filename
, wire
);
204 status
= ldns_wire2pkt(&pkt
, wire
, wiresize
);
209 if (status
== LDNS_STATUS_OK
) {
212 fprintf(stderr
, "Error parsing hex file: %s\n",
213 ldns_get_errorstr_by_id(status
));
219 dump_hex(const ldns_pkt
*pkt
, const char *filename
)
221 uint8_t *wire
= NULL
;
226 fp
= fopen(filename
, "w");
229 error("Unable to open %s for writing", filename
);
233 status
= ldns_pkt2wire(&wire
, pkt
, &size
);
235 if (status
!= LDNS_STATUS_OK
) {
236 error("Unable to convert packet: error code %u", status
);
242 for (i
= 1; i
< 20; i
++) {
243 fprintf(fp
, " %2u", (unsigned int) i
);
247 for (i
= 1; i
< 20; i
++) {
251 for (i
= 0; i
< size
; i
++) {
252 if (i
% 20 == 0 && i
> 0) {
253 fprintf(fp
, "\t;\t%4u-%4u\n", (unsigned int) i
-19, (unsigned int) i
);
255 fprintf(fp
, " %02x", (unsigned int)wire
[i
]);