aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSchanzenbach, Martin <mschanzenbach@posteo.de>2019-05-29 11:17:49 +0200
committerSchanzenbach, Martin <mschanzenbach@posteo.de>2019-05-29 11:17:49 +0200
commite3a229625e138820d7a2d891c0b038d3f4d8f875 (patch)
treeb1f1420f9f0cf3fa9168c06a653c9592aa07a6ff
parent4e3c1c6b12ae5e4ba025413a95f126c3774e3d3a (diff)
downloadgnunet-e3a229625e138820d7a2d891c0b038d3f4d8f875.tar.gz
gnunet-e3a229625e138820d7a2d891c0b038d3f4d8f875.zip
fix #5734
-rw-r--r--src/gns/Makefile.am1
-rwxr-xr-xsrc/gns/test_gns_caa_lookup.sh37
-rw-r--r--src/gnsrecord/plugin_gnsrecord_dns.c1031
-rw-r--r--src/include/gnunet_dnsparser_lib.h23
4 files changed, 559 insertions, 533 deletions
diff --git a/src/gns/Makefile.am b/src/gns/Makefile.am
index 6ebbbcaff..f51e571ec 100644
--- a/src/gns/Makefile.am
+++ b/src/gns/Makefile.am
@@ -280,6 +280,7 @@ check_SCRIPTS = \
280 test_gns_config_lookup.sh \ 280 test_gns_config_lookup.sh \
281 test_gns_ipv6_lookup.sh\ 281 test_gns_ipv6_lookup.sh\
282 test_gns_txt_lookup.sh\ 282 test_gns_txt_lookup.sh\
283 test_gns_caa_lookup.sh\
283 test_gns_mx_lookup.sh \ 284 test_gns_mx_lookup.sh \
284 test_gns_gns2dns_lookup.sh \ 285 test_gns_gns2dns_lookup.sh \
285 test_gns_gns2dns_cname_lookup.sh \ 286 test_gns_gns2dns_cname_lookup.sh \
diff --git a/src/gns/test_gns_caa_lookup.sh b/src/gns/test_gns_caa_lookup.sh
new file mode 100755
index 000000000..e5219bcd5
--- /dev/null
+++ b/src/gns/test_gns_caa_lookup.sh
@@ -0,0 +1,37 @@
1#!/bin/sh
2# This file is in the public domain.
3trap "gnunet-arm -e -c test_gns_lookup.conf" SIGINT
4
5LOCATION=$(which gnunet-config)
6if [ -z $LOCATION ]
7then
8 LOCATION="gnunet-config"
9fi
10$LOCATION --version 1> /dev/null
11if test $? != 0
12then
13 echo "GNUnet command line tools cannot be found, check environmental variables PATH and GNUNET_PREFIX"
14 exit 77
15fi
16
17rm -rf `gnunet-config -c test_gns_lookup.conf -f -s paths -o GNUNET_TEST_HOME`
18which timeout > /dev/null 2>&1 && DO_TIMEOUT="timeout 30"
19TEST_CAA="0 issue ca.example.net; policy=ev"
20MY_EGO="myego"
21LABEL="testcaa"
22gnunet-arm -s -c test_gns_lookup.conf
23gnunet-identity -C $MY_EGO -c test_gns_lookup.conf
24gnunet-namestore -p -z $MY_EGO -a -n $LABEL -t CAA -V "$TEST_CAA" -e never -c test_gns_lookup.conf
25RES_CAA=`$DO_TIMEOUT gnunet-gns --raw -u $LABEL.$MY_EGO -t CAA -c test_gns_lookup.conf`
26gnunet-namestore -z $MY_EGO -d -n $LABEL -t CAA -V "$TEST_CAA" -e never -c test_gns_lookup.conf
27gnunet-identity -D $MY_EGO -c test_gns_lookup.conf
28gnunet-arm -e -c test_gns_lookup.conf
29rm -rf `gnunet-config -c test_gns_lookup.conf -f -s paths -o GNUNET_TEST_HOME`
30
31if [ "$RES_CAA" = "$TEST_CAA" ]
32then
33 exit 0
34else
35 echo "Failed to resolve to proper CAA, got '$RES_CAA'."
36 exit 1
37fi
diff --git a/src/gnsrecord/plugin_gnsrecord_dns.c b/src/gnsrecord/plugin_gnsrecord_dns.c
index 881dcec6b..52c19b445 100644
--- a/src/gnsrecord/plugin_gnsrecord_dns.c
+++ b/src/gnsrecord/plugin_gnsrecord_dns.c
@@ -44,7 +44,7 @@ dns_value_to_string (void *cls,
44 const void *data, 44 const void *data,
45 size_t data_size) 45 size_t data_size)
46{ 46{
47 char* result; 47 char *result;
48 char tmp[INET6_ADDRSTRLEN]; 48 char tmp[INET6_ADDRSTRLEN];
49 49
50 switch (type) 50 switch (type)
@@ -55,144 +55,120 @@ dns_value_to_string (void *cls,
55 if (NULL == inet_ntop (AF_INET, data, tmp, sizeof (tmp))) 55 if (NULL == inet_ntop (AF_INET, data, tmp, sizeof (tmp)))
56 return NULL; 56 return NULL;
57 return GNUNET_strdup (tmp); 57 return GNUNET_strdup (tmp);
58 case GNUNET_DNSPARSER_TYPE_NS: 58 case GNUNET_DNSPARSER_TYPE_NS: {
59 { 59 char *ns;
60 char *ns; 60 size_t off;
61 size_t off;
62 61
63 off = 0; 62 off = 0;
64 ns = GNUNET_DNSPARSER_parse_name (data, 63 ns = GNUNET_DNSPARSER_parse_name (data, data_size, &off);
65 data_size, 64 if ((NULL == ns) || (off != data_size))
66 &off);
67 if ( (NULL == ns) ||
68 (off != data_size) )
69 {
70 GNUNET_break_op (0);
71 GNUNET_free_non_null (ns);
72 return NULL;
73 }
74 return ns;
75 }
76 case GNUNET_DNSPARSER_TYPE_CNAME:
77 { 65 {
78 char *cname; 66 GNUNET_break_op (0);
79 size_t off; 67 GNUNET_free_non_null (ns);
80 68 return NULL;
81 off = 0;
82 cname = GNUNET_DNSPARSER_parse_name (data,
83 data_size,
84 &off);
85 if ( (NULL == cname) ||
86 (off != data_size) )
87 {
88 GNUNET_break_op (0);
89 GNUNET_free_non_null (cname);
90 return NULL;
91 }
92 return cname;
93 } 69 }
94 case GNUNET_DNSPARSER_TYPE_SOA: 70 return ns;
95 { 71 }
96 struct GNUNET_DNSPARSER_SoaRecord *soa; 72 case GNUNET_DNSPARSER_TYPE_CNAME: {
97 size_t off; 73 char *cname;
74 size_t off;
98 75
99 off = 0; 76 off = 0;
100 soa = GNUNET_DNSPARSER_parse_soa (data, 77 cname = GNUNET_DNSPARSER_parse_name (data, data_size, &off);
101 data_size, 78 if ((NULL == cname) || (off != data_size))
102 &off); 79 {
103 if ( (NULL == soa) || 80 GNUNET_break_op (0);
104 (off != data_size) ) 81 GNUNET_free_non_null (cname);
105 { 82 return NULL;
106 GNUNET_break_op (0);
107 if (NULL != soa)
108 GNUNET_DNSPARSER_free_soa (soa);
109 return NULL;
110 }
111 GNUNET_asprintf (&result,
112 "rname=%s mname=%s %lu,%lu,%lu,%lu,%lu",
113 soa->rname,
114 soa->mname,
115 soa->serial,
116 soa->refresh,
117 soa->retry,
118 soa->expire,
119 soa->minimum_ttl);
120 GNUNET_DNSPARSER_free_soa (soa);
121 return result;
122 } 83 }
123 case GNUNET_DNSPARSER_TYPE_PTR: 84 return cname;
85 }
86 case GNUNET_DNSPARSER_TYPE_SOA: {
87 struct GNUNET_DNSPARSER_SoaRecord *soa;
88 size_t off;
89
90 off = 0;
91 soa = GNUNET_DNSPARSER_parse_soa (data, data_size, &off);
92 if ((NULL == soa) || (off != data_size))
124 { 93 {
125 char *ptr; 94 GNUNET_break_op (0);
126 size_t off; 95 if (NULL != soa)
96 GNUNET_DNSPARSER_free_soa (soa);
97 return NULL;
98 }
99 GNUNET_asprintf (&result,
100 "rname=%s mname=%s %lu,%lu,%lu,%lu,%lu",
101 soa->rname,
102 soa->mname,
103 soa->serial,
104 soa->refresh,
105 soa->retry,
106 soa->expire,
107 soa->minimum_ttl);
108 GNUNET_DNSPARSER_free_soa (soa);
109 return result;
110 }
111 case GNUNET_DNSPARSER_TYPE_PTR: {
112 char *ptr;
113 size_t off;
127 114
128 off = 0; 115 off = 0;
129 ptr = GNUNET_DNSPARSER_parse_name (data, 116 ptr = GNUNET_DNSPARSER_parse_name (data, data_size, &off);
130 data_size, 117 if ((NULL == ptr) || (off != data_size))
131 &off); 118 {
132 if ( (NULL == ptr) || 119 GNUNET_break_op (0);
133 (off != data_size) ) 120 GNUNET_free_non_null (ptr);
134 { 121 return NULL;
135 GNUNET_break_op (0);
136 GNUNET_free_non_null (ptr);
137 return NULL;
138 }
139 return ptr;
140 } 122 }
141 case GNUNET_DNSPARSER_TYPE_CERT: 123 return ptr;
124 }
125 case GNUNET_DNSPARSER_TYPE_CERT: {
126 struct GNUNET_DNSPARSER_CertRecord *cert;
127 size_t off;
128 char *base64;
129 int len;
130
131 off = 0;
132 cert = GNUNET_DNSPARSER_parse_cert (data, data_size, &off);
133 if ((NULL == cert) || (off != data_size))
142 { 134 {
143 struct GNUNET_DNSPARSER_CertRecord *cert; 135 GNUNET_break_op (0);
144 size_t off;
145 char *base64;
146 int len;
147
148 off = 0;
149 cert = GNUNET_DNSPARSER_parse_cert (data,
150 data_size,
151 &off);
152 if ( (NULL == cert) ||
153 (off != data_size) )
154 {
155 GNUNET_break_op (0);
156 GNUNET_DNSPARSER_free_cert (cert);
157 return NULL;
158 }
159 len = GNUNET_STRINGS_base64_encode (cert->certificate_data,
160 cert->certificate_size,
161 &base64);
162 GNUNET_asprintf (&result,
163 "%u %u %u %.*s",
164 cert->cert_type,
165 cert->cert_tag,
166 cert->algorithm,
167 len,
168 base64);
169 GNUNET_free (base64);
170 GNUNET_DNSPARSER_free_cert (cert); 136 GNUNET_DNSPARSER_free_cert (cert);
171 return result; 137 return NULL;
172 } 138 }
173 case GNUNET_DNSPARSER_TYPE_MX: 139 len = GNUNET_STRINGS_base64_encode (cert->certificate_data,
174 { 140 cert->certificate_size,
175 struct GNUNET_DNSPARSER_MxRecord *mx; 141 &base64);
176 size_t off; 142 GNUNET_asprintf (&result,
143 "%u %u %u %.*s",
144 cert->cert_type,
145 cert->cert_tag,
146 cert->algorithm,
147 len,
148 base64);
149 GNUNET_free (base64);
150 GNUNET_DNSPARSER_free_cert (cert);
151 return result;
152 }
153 case GNUNET_DNSPARSER_TYPE_MX: {
154 struct GNUNET_DNSPARSER_MxRecord *mx;
155 size_t off;
177 156
178 off = 0; 157 off = 0;
179 mx = GNUNET_DNSPARSER_parse_mx (data, 158 mx = GNUNET_DNSPARSER_parse_mx (data, data_size, &off);
180 data_size, 159 if ((NULL == mx) || (off != data_size))
181 &off); 160 {
182 if ( (NULL == mx) || 161 GNUNET_break_op (0);
183 (off != data_size) )
184 {
185 GNUNET_break_op (0);
186 GNUNET_DNSPARSER_free_mx (mx);
187 return NULL;
188 }
189 GNUNET_asprintf (&result,
190 "%u,%s",
191 (unsigned int) mx->preference,
192 mx->mxhost);
193 GNUNET_DNSPARSER_free_mx (mx); 162 GNUNET_DNSPARSER_free_mx (mx);
194 return result; 163 return NULL;
195 } 164 }
165 GNUNET_asprintf (&result,
166 "%u,%s",
167 (unsigned int) mx->preference,
168 mx->mxhost);
169 GNUNET_DNSPARSER_free_mx (mx);
170 return result;
171 }
196 case GNUNET_DNSPARSER_TYPE_TXT: 172 case GNUNET_DNSPARSER_TYPE_TXT:
197 return GNUNET_strndup (data, data_size); 173 return GNUNET_strndup (data, data_size);
198 case GNUNET_DNSPARSER_TYPE_AAAA: 174 case GNUNET_DNSPARSER_TYPE_AAAA:
@@ -201,57 +177,81 @@ dns_value_to_string (void *cls,
201 if (NULL == inet_ntop (AF_INET6, data, tmp, sizeof (tmp))) 177 if (NULL == inet_ntop (AF_INET6, data, tmp, sizeof (tmp)))
202 return NULL; 178 return NULL;
203 return GNUNET_strdup (tmp); 179 return GNUNET_strdup (tmp);
204 case GNUNET_DNSPARSER_TYPE_SRV: 180 case GNUNET_DNSPARSER_TYPE_SRV: {
205 { 181 struct GNUNET_DNSPARSER_SrvRecord *srv;
206 struct GNUNET_DNSPARSER_SrvRecord *srv; 182 size_t off;
207 size_t off;
208 183
209 off = 0; 184 off = 0;
210 srv = GNUNET_DNSPARSER_parse_srv (data, 185 srv = GNUNET_DNSPARSER_parse_srv (data, data_size, &off);
211 data_size, 186 if ((NULL == srv) || (off != data_size))
212 &off); 187 {
213 if ( (NULL == srv) || 188 GNUNET_break_op (0);
214 (off != data_size) ) 189 if (NULL != srv)
215 { 190 GNUNET_DNSPARSER_free_srv (srv);
216 GNUNET_break_op (0); 191 return NULL;
217 if (NULL != srv)
218 GNUNET_DNSPARSER_free_srv (srv);
219 return NULL;
220 }
221 GNUNET_asprintf (&result,
222 "%d %d %d %s",
223 srv->priority,
224 srv->weight,
225 srv->port,
226 srv->target);
227 GNUNET_DNSPARSER_free_srv (srv);
228 return result;
229 } 192 }
230 case GNUNET_DNSPARSER_TYPE_TLSA: 193 GNUNET_asprintf (&result,
194 "%d %d %d %s",
195 srv->priority,
196 srv->weight,
197 srv->port,
198 srv->target);
199 GNUNET_DNSPARSER_free_srv (srv);
200 return result;
201 }
202 case GNUNET_DNSPARSER_TYPE_TLSA: {
203 const struct GNUNET_TUN_DnsTlsaRecord *tlsa;
204 char *tlsa_str;
205 char *hex;
206
207 if (data_size < sizeof (struct GNUNET_TUN_DnsTlsaRecord))
208 return NULL; /* malformed */
209 tlsa = data;
210 hex =
211 GNUNET_DNSPARSER_bin_to_hex (&tlsa[1],
212 data_size -
213 sizeof (struct GNUNET_TUN_DnsTlsaRecord));
214 if (0 == GNUNET_asprintf (&tlsa_str,
215 "%u %u %u %s",
216 (unsigned int) tlsa->usage,
217 (unsigned int) tlsa->selector,
218 (unsigned int) tlsa->matching_type,
219 hex))
231 { 220 {
232 const struct GNUNET_TUN_DnsTlsaRecord *tlsa;
233 char *tlsa_str;
234 char *hex;
235
236 if (data_size < sizeof (struct GNUNET_TUN_DnsTlsaRecord))
237 return NULL; /* malformed */
238 tlsa = data;
239 hex = GNUNET_DNSPARSER_bin_to_hex (&tlsa[1],
240 data_size - sizeof (struct GNUNET_TUN_DnsTlsaRecord));
241 if (0 == GNUNET_asprintf (&tlsa_str,
242 "%u %u %u %s",
243 (unsigned int) tlsa->usage,
244 (unsigned int) tlsa->selector,
245 (unsigned int) tlsa->matching_type,
246 hex))
247 {
248 GNUNET_free (hex);
249 GNUNET_free (tlsa_str);
250 return NULL;
251 }
252 GNUNET_free (hex); 221 GNUNET_free (hex);
253 return tlsa_str; 222 GNUNET_free (tlsa_str);
223 return NULL;
254 } 224 }
225 GNUNET_free (hex);
226 return tlsa_str;
227 }
228 case GNUNET_DNSPARSER_TYPE_CAA: { //RFC6844
229 const struct GNUNET_DNSPARSER_CaaRecord *caa;
230 char tag[15]; // between 1 and 15 bytes
231 char value[data_size];
232 char *caa_str;
233 if (data_size < sizeof (struct GNUNET_DNSPARSER_CaaRecord))
234 return NULL; /* malformed */
235 caa = data;
236 if ((1 > caa->tag_len) || (15 < caa->tag_len))
237 return NULL; /* malformed */
238 memset (tag, 0, sizeof (tag));
239 memset (value, 0, data_size);
240 memcpy (tag, &caa[1], caa->tag_len);
241 memcpy (value,
242 (char *) &caa[1] + caa->tag_len,
243 data_size - caa->tag_len - 2);
244 if (0 == GNUNET_asprintf (&caa_str,
245 "%u %s %s",
246 (unsigned int) caa->flags,
247 tag,
248 value))
249 {
250 GNUNET_free (caa_str);
251 return NULL;
252 }
253 return caa_str;
254 }
255 default: 255 default:
256 return NULL; 256 return NULL;
257 } 257 }
@@ -267,27 +267,25 @@ dns_value_to_string (void *cls,
267static unsigned int 267static unsigned int
268rfc4398_mnemonic_to_value (const char *mnemonic) 268rfc4398_mnemonic_to_value (const char *mnemonic)
269{ 269{
270 static struct { 270 static struct
271 {
271 const char *mnemonic; 272 const char *mnemonic;
272 unsigned int val; 273 unsigned int val;
273 } table[] = { 274 } table[] = {{"PKIX", 1},
274 { "PKIX", 1 }, 275 {"SPKI", 2},
275 { "SPKI", 2 }, 276 {"PGP", 3},
276 { "PGP", 3 }, 277 {"IPKIX", 4},
277 { "IPKIX", 4 }, 278 {"ISPKI", 5},
278 { "ISPKI", 5 }, 279 {"IPGP", 6},
279 { "IPGP", 6 }, 280 {"ACPKIX", 7},
280 { "ACPKIX", 7}, 281 {"IACPKIX", 8},
281 { "IACPKIX", 8}, 282 {"URI", 253},
282 { "URI", 253}, 283 {"OID", 254},
283 { "OID", 254}, 284 {NULL, 0}};
284 { NULL, 0 }
285 };
286 unsigned int i; 285 unsigned int i;
287 286
288 for (i=0;NULL != table[i].mnemonic;i++) 287 for (i = 0; NULL != table[i].mnemonic; i++)
289 if (0 == strcasecmp (mnemonic, 288 if (0 == strcasecmp (mnemonic, table[i].mnemonic))
290 table[i].mnemonic))
291 return table[i].val; 289 return table[i].val;
292 return 0; 290 return 0;
293} 291}
@@ -302,25 +300,23 @@ rfc4398_mnemonic_to_value (const char *mnemonic)
302static unsigned int 300static unsigned int
303rfc4034_mnemonic_to_value (const char *mnemonic) 301rfc4034_mnemonic_to_value (const char *mnemonic)
304{ 302{
305 static struct { 303 static struct
304 {
306 const char *mnemonic; 305 const char *mnemonic;
307 unsigned int val; 306 unsigned int val;
308 } table[] = { 307 } table[] = {{"RSAMD5", 1},
309 { "RSAMD5", 1 }, 308 {"DH", 2},
310 { "DH", 2 }, 309 {"DSA", 3},
311 { "DSA", 3 }, 310 {"ECC", 4},
312 { "ECC", 4 }, 311 {"RSASHA1", 5},
313 { "RSASHA1", 5 }, 312 {"INDIRECT", 252},
314 { "INDIRECT", 252 }, 313 {"PRIVATEDNS", 253},
315 { "PRIVATEDNS", 253 }, 314 {"PRIVATEOID", 254},
316 { "PRIVATEOID", 254 }, 315 {NULL, 0}};
317 { NULL, 0 }
318 };
319 unsigned int i; 316 unsigned int i;
320 317
321 for (i=0;NULL != table[i].mnemonic;i++) 318 for (i = 0; NULL != table[i].mnemonic; i++)
322 if (0 == strcasecmp (mnemonic, 319 if (0 == strcasecmp (mnemonic, table[i].mnemonic))
323 table[i].mnemonic))
324 return table[i].val; 320 return table[i].val;
325 return 0; 321 return 0;
326} 322}
@@ -356,7 +352,7 @@ dns_string_to_value (void *cls,
356 if (1 != inet_pton (AF_INET, s, &value_a)) 352 if (1 != inet_pton (AF_INET, s, &value_a))
357 { 353 {
358 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 354 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
359 _("Unable to parse IPv4 address `%s'\n"), 355 _ ("Unable to parse IPv4 address `%s'\n"),
360 s); 356 s);
361 return GNUNET_SYSERR; 357 return GNUNET_SYSERR;
362 } 358 }
@@ -364,294 +360,253 @@ dns_string_to_value (void *cls,
364 GNUNET_memcpy (*data, &value_a, sizeof (value_a)); 360 GNUNET_memcpy (*data, &value_a, sizeof (value_a));
365 *data_size = sizeof (value_a); 361 *data_size = sizeof (value_a);
366 return GNUNET_OK; 362 return GNUNET_OK;
367 case GNUNET_DNSPARSER_TYPE_NS: 363 case GNUNET_DNSPARSER_TYPE_NS: {
368 { 364 char nsbuf[256];
369 char nsbuf[256]; 365 size_t off;
370 size_t off;
371 366
372 off = 0; 367 off = 0;
373 if (GNUNET_OK != 368 if (GNUNET_OK !=
374 GNUNET_DNSPARSER_builder_add_name (nsbuf, 369 GNUNET_DNSPARSER_builder_add_name (nsbuf, sizeof (nsbuf), &off, s))
375 sizeof (nsbuf), 370 {
376 &off, 371 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
377 s)) 372 _ ("Failed to serialize NS record with value `%s'\n"),
378 { 373 s);
379 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 374 return GNUNET_SYSERR;
380 _("Failed to serialize NS record with value `%s'\n"),
381 s);
382 return GNUNET_SYSERR;
383 }
384 *data_size = off;
385 *data = GNUNET_malloc (off);
386 GNUNET_memcpy (*data, nsbuf, off);
387 return GNUNET_OK;
388 } 375 }
389 case GNUNET_DNSPARSER_TYPE_CNAME: 376 *data_size = off;
377 *data = GNUNET_malloc (off);
378 GNUNET_memcpy (*data, nsbuf, off);
379 return GNUNET_OK;
380 }
381 case GNUNET_DNSPARSER_TYPE_CNAME: {
382 char cnamebuf[256];
383 size_t off;
384
385 off = 0;
386 if (GNUNET_OK != GNUNET_DNSPARSER_builder_add_name (cnamebuf,
387 sizeof (cnamebuf),
388 &off,
389 s))
390 { 390 {
391 char cnamebuf[256]; 391 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
392 size_t off; 392 _ ("Failed to serialize CNAME record with value `%s'\n"),
393 393 s);
394 off = 0; 394 return GNUNET_SYSERR;
395 if (GNUNET_OK !=
396 GNUNET_DNSPARSER_builder_add_name (cnamebuf,
397 sizeof (cnamebuf),
398 &off,
399 s))
400 {
401 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
402 _("Failed to serialize CNAME record with value `%s'\n"),
403 s);
404 return GNUNET_SYSERR;
405 }
406 *data_size = off;
407 *data = GNUNET_malloc (off);
408 GNUNET_memcpy (*data, cnamebuf, off);
409 return GNUNET_OK;
410 } 395 }
411 case GNUNET_DNSPARSER_TYPE_CERT: 396 *data_size = off;
397 *data = GNUNET_malloc (off);
398 GNUNET_memcpy (*data, cnamebuf, off);
399 return GNUNET_OK;
400 }
401 case GNUNET_DNSPARSER_TYPE_CERT: {
402 char *sdup;
403 const char *typep;
404 const char *keyp;
405 const char *algp;
406 const char *certp;
407 unsigned int type;
408 unsigned int key;
409 unsigned int alg;
410 size_t cert_size;
411 char *cert_data;
412 struct GNUNET_DNSPARSER_CertRecord cert;
413
414 sdup = GNUNET_strdup (s);
415 typep = strtok (sdup, " ");
416 if ((NULL == typep) ||
417 ((0 == (type = rfc4398_mnemonic_to_value (typep))) &&
418 ((1 != SSCANF (typep, "%u", &type)) || (type > UINT16_MAX))))
412 { 419 {
413 char *sdup;
414 const char *typep;
415 const char *keyp;
416 const char *algp;
417 const char *certp;
418 unsigned int type;
419 unsigned int key;
420 unsigned int alg;
421 size_t cert_size;
422 char *cert_data;
423 struct GNUNET_DNSPARSER_CertRecord cert;
424
425 sdup = GNUNET_strdup (s);
426 typep = strtok (sdup, " ");
427 if ( (NULL == typep) ||
428 ( (0 == (type = rfc4398_mnemonic_to_value (typep))) &&
429 ( (1 != SSCANF (typep,
430 "%u",
431 &type)) ||
432 (type > UINT16_MAX) ) ) )
433 {
434 GNUNET_free (sdup);
435 return GNUNET_SYSERR;
436 }
437 keyp = strtok (NULL, " ");
438 if ( (NULL == keyp) ||
439 (1 != SSCANF (keyp,
440 "%u",
441 &key)) ||
442 (key > UINT16_MAX) )
443 {
444 GNUNET_free (sdup);
445 return GNUNET_SYSERR;
446 }
447 alg = 0;
448 algp = strtok (NULL, " ");
449 if ( (NULL == algp) ||
450 ( (0 == (type = rfc4034_mnemonic_to_value (typep))) &&
451 ( (1 != sscanf (algp,
452 "%u",
453 &alg)) ||
454 (alg > UINT8_MAX) ) ) )
455 {
456 GNUNET_free (sdup);
457 return GNUNET_SYSERR;
458 }
459 certp = strtok (NULL, " ");
460 if ( (NULL == certp) ||
461 (0 == strlen (certp) ) )
462 {
463 GNUNET_free (sdup);
464 return GNUNET_SYSERR;
465 }
466 cert_size = GNUNET_STRINGS_base64_decode (certp,
467 strlen (certp),
468 (void **) &cert_data);
469 GNUNET_free (sdup); 420 GNUNET_free (sdup);
470 cert.cert_type = type; 421 return GNUNET_SYSERR;
471 cert.cert_tag = key;
472 cert.algorithm = alg;
473 cert.certificate_size = cert_size;
474 cert.certificate_data = cert_data;
475 {
476 char certbuf[cert_size + sizeof (struct GNUNET_TUN_DnsCertRecord)];
477 size_t off;
478
479 off = 0;
480 if (GNUNET_OK !=
481 GNUNET_DNSPARSER_builder_add_cert (certbuf,
482 sizeof (certbuf),
483 &off,
484 &cert))
485 {
486 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
487 _("Failed to serialize CERT record with %u bytes\n"),
488 (unsigned int) cert_size);
489 GNUNET_free (cert_data);
490 return GNUNET_SYSERR;
491 }
492 *data_size = off;
493 *data = GNUNET_malloc (off);
494 GNUNET_memcpy (*data, certbuf, off);
495 }
496 GNUNET_free (cert_data);
497 return GNUNET_OK;
498 } 422 }
499 case GNUNET_DNSPARSER_TYPE_SOA: 423 keyp = strtok (NULL, " ");
424 if ((NULL == keyp) || (1 != SSCANF (keyp, "%u", &key)) ||
425 (key > UINT16_MAX))
500 { 426 {
501 struct GNUNET_DNSPARSER_SoaRecord soa; 427 GNUNET_free (sdup);
502 char soabuf[540]; 428 return GNUNET_SYSERR;
503 char soa_rname[253 + 1]; 429 }
504 char soa_mname[253 + 1]; 430 alg = 0;
505 unsigned int soa_serial; 431 algp = strtok (NULL, " ");
506 unsigned int soa_refresh; 432 if ((NULL == algp) ||
507 unsigned int soa_retry; 433 ((0 == (type = rfc4034_mnemonic_to_value (typep))) &&
508 unsigned int soa_expire; 434 ((1 != sscanf (algp, "%u", &alg)) || (alg > UINT8_MAX))))
509 unsigned int soa_min; 435 {
510 size_t off; 436 GNUNET_free (sdup);
511 437 return GNUNET_SYSERR;
512 if (7 != SSCANF (s, 438 }
513 "rname=%253s mname=%253s %u,%u,%u,%u,%u", 439 certp = strtok (NULL, " ");
514 soa_rname, 440 if ((NULL == certp) || (0 == strlen (certp)))
515 soa_mname, 441 {
516 &soa_serial, 442 GNUNET_free (sdup);
517 &soa_refresh, 443 return GNUNET_SYSERR;
518 &soa_retry,
519 &soa_expire,
520 &soa_min))
521 {
522 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
523 _("Unable to parse SOA record `%s'\n"),
524 s);
525 return GNUNET_SYSERR;
526 }
527 soa.mname = soa_mname;
528 soa.rname = soa_rname;
529 soa.serial = (uint32_t) soa_serial;
530 soa.refresh =(uint32_t) soa_refresh;
531 soa.retry = (uint32_t) soa_retry;
532 soa.expire = (uint32_t) soa_expire;
533 soa.minimum_ttl = (uint32_t) soa_min;
534 off = 0;
535 if (GNUNET_OK !=
536 GNUNET_DNSPARSER_builder_add_soa (soabuf,
537 sizeof (soabuf),
538 &off,
539 &soa))
540 {
541 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
542 _("Failed to serialize SOA record with mname `%s' and rname `%s'\n"),
543 soa_mname,
544 soa_rname);
545 return GNUNET_SYSERR;
546 }
547 *data_size = off;
548 *data = GNUNET_malloc (off);
549 GNUNET_memcpy (*data, soabuf, off);
550 return GNUNET_OK;
551 } 444 }
552 case GNUNET_DNSPARSER_TYPE_PTR: 445 cert_size = GNUNET_STRINGS_base64_decode (certp,
446 strlen (certp),
447 (void **) &cert_data);
448 GNUNET_free (sdup);
449 cert.cert_type = type;
450 cert.cert_tag = key;
451 cert.algorithm = alg;
452 cert.certificate_size = cert_size;
453 cert.certificate_data = cert_data;
553 { 454 {
554 char ptrbuf[256]; 455 char certbuf[cert_size + sizeof (struct GNUNET_TUN_DnsCertRecord)];
555 size_t off; 456 size_t off;
556 457
557 off = 0; 458 off = 0;
558 if (GNUNET_OK != 459 if (GNUNET_OK != GNUNET_DNSPARSER_builder_add_cert (certbuf,
559 GNUNET_DNSPARSER_builder_add_name (ptrbuf, 460 sizeof (certbuf),
560 sizeof (ptrbuf), 461 &off,
561 &off, 462 &cert))
562 s))
563 { 463 {
564 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 464 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
565 _("Failed to serialize PTR record with value `%s'\n"), 465 _ ("Failed to serialize CERT record with %u bytes\n"),
566 s); 466 (unsigned int) cert_size);
567 return GNUNET_SYSERR; 467 GNUNET_free (cert_data);
468 return GNUNET_SYSERR;
568 } 469 }
569 *data_size = off; 470 *data_size = off;
570 *data = GNUNET_malloc (off); 471 *data = GNUNET_malloc (off);
571 GNUNET_memcpy (*data, ptrbuf, off); 472 GNUNET_memcpy (*data, certbuf, off);
572 return GNUNET_OK;
573 } 473 }
574 case GNUNET_DNSPARSER_TYPE_MX: 474 GNUNET_free (cert_data);
475 return GNUNET_OK;
476 }
477 case GNUNET_DNSPARSER_TYPE_SOA: {
478 struct GNUNET_DNSPARSER_SoaRecord soa;
479 char soabuf[540];
480 char soa_rname[253 + 1];
481 char soa_mname[253 + 1];
482 unsigned int soa_serial;
483 unsigned int soa_refresh;
484 unsigned int soa_retry;
485 unsigned int soa_expire;
486 unsigned int soa_min;
487 size_t off;
488
489 if (7 != SSCANF (s,
490 "rname=%253s mname=%253s %u,%u,%u,%u,%u",
491 soa_rname,
492 soa_mname,
493 &soa_serial,
494 &soa_refresh,
495 &soa_retry,
496 &soa_expire,
497 &soa_min))
575 { 498 {
576 struct GNUNET_DNSPARSER_MxRecord mx; 499 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
577 char mxbuf[258]; 500 _ ("Unable to parse SOA record `%s'\n"),
578 char mxhost[253 + 1]; 501 s);
579 unsigned int mx_pref;
580 size_t off;
581
582 if (2 != SSCANF(s,
583 "%u,%253s",
584 &mx_pref,
585 mxhost))
586 {
587 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
588 _("Unable to parse MX record `%s'\n"),
589 s);
590 return GNUNET_SYSERR; 502 return GNUNET_SYSERR;
591 } 503 }
592 mx.preference = (uint16_t) mx_pref; 504 soa.mname = soa_mname;
593 mx.mxhost = mxhost; 505 soa.rname = soa_rname;
594 off = 0; 506 soa.serial = (uint32_t) soa_serial;
507 soa.refresh = (uint32_t) soa_refresh;
508 soa.retry = (uint32_t) soa_retry;
509 soa.expire = (uint32_t) soa_expire;
510 soa.minimum_ttl = (uint32_t) soa_min;
511 off = 0;
512 if (GNUNET_OK !=
513 GNUNET_DNSPARSER_builder_add_soa (soabuf, sizeof (soabuf), &off, &soa))
514 {
515 GNUNET_log (
516 GNUNET_ERROR_TYPE_ERROR,
517 _ ("Failed to serialize SOA record with mname `%s' and rname `%s'\n"),
518 soa_mname,
519 soa_rname);
520 return GNUNET_SYSERR;
521 }
522 *data_size = off;
523 *data = GNUNET_malloc (off);
524 GNUNET_memcpy (*data, soabuf, off);
525 return GNUNET_OK;
526 }
527 case GNUNET_DNSPARSER_TYPE_PTR: {
528 char ptrbuf[256];
529 size_t off;
595 530
596 if (GNUNET_OK != 531 off = 0;
597 GNUNET_DNSPARSER_builder_add_mx (mxbuf, 532 if (GNUNET_OK !=
598 sizeof (mxbuf), 533 GNUNET_DNSPARSER_builder_add_name (ptrbuf, sizeof (ptrbuf), &off, s))
599 &off, 534 {
600 &mx)) 535 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
601 { 536 _ ("Failed to serialize PTR record with value `%s'\n"),
602 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 537 s);
603 _("Failed to serialize MX record with hostname `%s'\n"), 538 return GNUNET_SYSERR;
604 mxhost);
605 return GNUNET_SYSERR;
606 }
607 *data_size = off;
608 *data = GNUNET_malloc (off);
609 GNUNET_memcpy (*data, mxbuf, off);
610 return GNUNET_OK;
611 } 539 }
612 case GNUNET_DNSPARSER_TYPE_SRV: 540 *data_size = off;
541 *data = GNUNET_malloc (off);
542 GNUNET_memcpy (*data, ptrbuf, off);
543 return GNUNET_OK;
544 }
545 case GNUNET_DNSPARSER_TYPE_MX: {
546 struct GNUNET_DNSPARSER_MxRecord mx;
547 char mxbuf[258];
548 char mxhost[253 + 1];
549 unsigned int mx_pref;
550 size_t off;
551
552 if (2 != SSCANF (s, "%u,%253s", &mx_pref, mxhost))
613 { 553 {
614 struct GNUNET_DNSPARSER_SrvRecord srv; 554 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
615 char srvbuf[270]; 555 _ ("Unable to parse MX record `%s'\n"),
616 char srvtarget[253 + 1]; 556 s);
617 unsigned int priority; 557 return GNUNET_SYSERR;
618 unsigned int weight; 558 }
619 unsigned int port; 559 mx.preference = (uint16_t) mx_pref;
620 size_t off; 560 mx.mxhost = mxhost;
561 off = 0;
621 562
622 if (4 != SSCANF(s, 563 if (GNUNET_OK !=
623 "%u %u %u %253s", 564 GNUNET_DNSPARSER_builder_add_mx (mxbuf, sizeof (mxbuf), &off, &mx))
624 &priority, 565 {
625 &weight, 566 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
626 &port, 567 _ ("Failed to serialize MX record with hostname `%s'\n"),
627 srvtarget)) 568 mxhost);
628 { 569 return GNUNET_SYSERR;
629 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 570 }
630 _("Unable to parse SRV record `%s'\n"), 571 *data_size = off;
631 s); 572 *data = GNUNET_malloc (off);
632 return GNUNET_SYSERR; 573 GNUNET_memcpy (*data, mxbuf, off);
633 } 574 return GNUNET_OK;
634 srv.priority = (uint16_t) priority; 575 }
635 srv.weight = (uint16_t) weight; 576 case GNUNET_DNSPARSER_TYPE_SRV: {
636 srv.port = (uint16_t) port; 577 struct GNUNET_DNSPARSER_SrvRecord srv;
637 srv.target = srvtarget; 578 char srvbuf[270];
638 off = 0; 579 char srvtarget[253 + 1];
639 if (GNUNET_OK != 580 unsigned int priority;
640 GNUNET_DNSPARSER_builder_add_srv (srvbuf, 581 unsigned int weight;
641 sizeof (srvbuf), 582 unsigned int port;
642 &off, 583 size_t off;
643 &srv)) 584
644 { 585 if (4 != SSCANF (s, "%u %u %u %253s", &priority, &weight, &port, srvtarget))
645 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 586 {
646 _("Failed to serialize SRV record with target `%s'\n"), 587 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
647 srvtarget); 588 _ ("Unable to parse SRV record `%s'\n"),
648 return GNUNET_SYSERR; 589 s);
649 } 590 return GNUNET_SYSERR;
650 *data_size = off;
651 *data = GNUNET_malloc (off);
652 GNUNET_memcpy (*data, srvbuf, off);
653 return GNUNET_OK;
654 } 591 }
592 srv.priority = (uint16_t) priority;
593 srv.weight = (uint16_t) weight;
594 srv.port = (uint16_t) port;
595 srv.target = srvtarget;
596 off = 0;
597 if (GNUNET_OK !=
598 GNUNET_DNSPARSER_builder_add_srv (srvbuf, sizeof (srvbuf), &off, &srv))
599 {
600 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
601 _ ("Failed to serialize SRV record with target `%s'\n"),
602 srvtarget);
603 return GNUNET_SYSERR;
604 }
605 *data_size = off;
606 *data = GNUNET_malloc (off);
607 GNUNET_memcpy (*data, srvbuf, off);
608 return GNUNET_OK;
609 }
655 case GNUNET_DNSPARSER_TYPE_TXT: 610 case GNUNET_DNSPARSER_TYPE_TXT:
656 *data = GNUNET_strdup (s); 611 *data = GNUNET_strdup (s);
657 *data_size = strlen (s); 612 *data_size = strlen (s);
@@ -660,55 +615,70 @@ dns_string_to_value (void *cls,
660 if (1 != inet_pton (AF_INET6, s, &value_aaaa)) 615 if (1 != inet_pton (AF_INET6, s, &value_aaaa))
661 { 616 {
662 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 617 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
663 _("Unable to parse IPv6 address `%s'\n"), 618 _ ("Unable to parse IPv6 address `%s'\n"),
664 s); 619 s);
665 return GNUNET_SYSERR; 620 return GNUNET_SYSERR;
666 } 621 }
667 *data = GNUNET_new (struct in6_addr); 622 *data = GNUNET_new (struct in6_addr);
668 *data_size = sizeof (struct in6_addr); 623 *data_size = sizeof (struct in6_addr);
669 GNUNET_memcpy (*data, &value_aaaa, sizeof (value_aaaa)); 624 GNUNET_memcpy (*data, &value_aaaa, sizeof (value_aaaa));
670 return GNUNET_OK; 625 return GNUNET_OK;
671 case GNUNET_DNSPARSER_TYPE_TLSA: 626 case GNUNET_DNSPARSER_TYPE_TLSA: {
627 unsigned int usage;
628 unsigned int selector;
629 unsigned int matching_type;
630 size_t slen = strlen (s) + 1;
631 char hex[slen];
632
633 if (4 != SSCANF (s, "%u %u %u %s", &usage, &selector, &matching_type, hex))
672 { 634 {
673 unsigned int usage; 635 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
674 unsigned int selector; 636 _ ("Unable to parse TLSA record string `%s'\n"),
675 unsigned int matching_type; 637 s);
676 size_t slen = strlen (s) + 1; 638 *data_size = 0;
677 char hex[slen]; 639 return GNUNET_SYSERR;
678 640 }
679 if (4 != SSCANF (s,
680 "%u %u %u %s",
681 &usage,
682 &selector,
683 &matching_type,
684 hex))
685 {
686 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
687 _("Unable to parse TLSA record string `%s'\n"),
688 s);
689 *data_size = 0;
690 return GNUNET_SYSERR;
691 }
692 641
693 *data_size = sizeof (struct GNUNET_TUN_DnsTlsaRecord) + strlen (hex) / 2; 642 *data_size = sizeof (struct GNUNET_TUN_DnsTlsaRecord) + strlen (hex) / 2;
694 *data = tlsa = GNUNET_malloc (*data_size); 643 *data = tlsa = GNUNET_malloc (*data_size);
695 tlsa->usage = (uint8_t) usage; 644 tlsa->usage = (uint8_t) usage;
696 tlsa->selector = (uint8_t) selector; 645 tlsa->selector = (uint8_t) selector;
697 tlsa->matching_type = (uint8_t) matching_type; 646 tlsa->matching_type = (uint8_t) matching_type;
698 if (strlen (hex) / 2 != 647 if (strlen (hex) / 2 != GNUNET_DNSPARSER_hex_to_bin (hex, &tlsa[1]))
699 GNUNET_DNSPARSER_hex_to_bin (hex, 648 {
700 &tlsa[1])) 649 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
701 { 650 _ ("Unable to parse TLSA record string `%s'\n"),
702 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 651 s);
703 _("Unable to parse TLSA record string `%s'\n"), 652 GNUNET_free (*data);
704 s); 653 *data = NULL;
705 GNUNET_free (*data); 654 *data_size = 0;
706 *data = NULL; 655 return GNUNET_SYSERR;
707 *data_size = 0;
708 return GNUNET_SYSERR;
709 }
710 return GNUNET_OK;
711 } 656 }
657 return GNUNET_OK;
658 }
659 case GNUNET_DNSPARSER_TYPE_CAA: { //RFC6844
660 struct GNUNET_DNSPARSER_CaaRecord *caa;
661 unsigned int flags;
662 char tag[15]; //Max tag length 15
663 char value[strlen (s)]; //Should be more than enough
664
665 if (3 != SSCANF (s, "%u %s %[^\n]", &flags, tag, value))
666 {
667 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
668 _ ("Unable to parse CAA record string `%s'\n"),
669 s);
670 *data_size = 0;
671 return GNUNET_SYSERR;
672 }
673 *data_size = sizeof (struct GNUNET_DNSPARSER_CaaRecord) + strlen (tag) +
674 strlen (value);
675 *data = caa = GNUNET_malloc (*data_size);
676 caa->flags = flags;
677 memcpy (&caa[1], tag, strlen (tag));
678 caa->tag_len = strlen (tag);
679 memcpy ((char *) &caa[1] + caa->tag_len, value, strlen (value));
680 return GNUNET_OK;
681 }
712 default: 682 default:
713 return GNUNET_SYSERR; 683 return GNUNET_SYSERR;
714 } 684 }
@@ -719,23 +689,23 @@ dns_string_to_value (void *cls,
719 * Mapping of record type numbers to human-readable 689 * Mapping of record type numbers to human-readable
720 * record type names. 690 * record type names.
721 */ 691 */
722static struct { 692static struct
693{
723 const char *name; 694 const char *name;
724 uint32_t number; 695 uint32_t number;
725} name_map[] = { 696} name_map[] = {{"A", GNUNET_DNSPARSER_TYPE_A},
726 { "A", GNUNET_DNSPARSER_TYPE_A }, 697 {"NS", GNUNET_DNSPARSER_TYPE_NS},
727 { "NS", GNUNET_DNSPARSER_TYPE_NS }, 698 {"CNAME", GNUNET_DNSPARSER_TYPE_CNAME},
728 { "CNAME", GNUNET_DNSPARSER_TYPE_CNAME }, 699 {"SOA", GNUNET_DNSPARSER_TYPE_SOA},
729 { "SOA", GNUNET_DNSPARSER_TYPE_SOA }, 700 {"PTR", GNUNET_DNSPARSER_TYPE_PTR},
730 { "PTR", GNUNET_DNSPARSER_TYPE_PTR }, 701 {"MX", GNUNET_DNSPARSER_TYPE_MX},
731 { "MX", GNUNET_DNSPARSER_TYPE_MX }, 702 {"TXT", GNUNET_DNSPARSER_TYPE_TXT},
732 { "TXT", GNUNET_DNSPARSER_TYPE_TXT }, 703 {"AAAA", GNUNET_DNSPARSER_TYPE_AAAA},
733 { "AAAA", GNUNET_DNSPARSER_TYPE_AAAA }, 704 {"SRV", GNUNET_DNSPARSER_TYPE_SRV},
734 { "SRV", GNUNET_DNSPARSER_TYPE_SRV }, 705 {"TLSA", GNUNET_DNSPARSER_TYPE_TLSA},
735 { "TLSA", GNUNET_DNSPARSER_TYPE_TLSA }, 706 {"CERT", GNUNET_DNSPARSER_TYPE_CERT},
736 { "CERT", GNUNET_DNSPARSER_TYPE_CERT }, 707 {"CAA", GNUNET_DNSPARSER_TYPE_CAA},
737 { NULL, UINT32_MAX } 708 {NULL, UINT32_MAX}};
738};
739 709
740 710
741/** 711/**
@@ -746,14 +716,13 @@ static struct {
746 * @return corresponding number, UINT32_MAX on error 716 * @return corresponding number, UINT32_MAX on error
747 */ 717 */
748static uint32_t 718static uint32_t
749dns_typename_to_number (void *cls, 719dns_typename_to_number (void *cls, const char *dns_typename)
750 const char *dns_typename)
751{ 720{
752 unsigned int i; 721 unsigned int i;
753 722
754 i=0; 723 i = 0;
755 while ( (NULL != name_map[i].name) && 724 while ((NULL != name_map[i].name) &&
756 (0 != strcasecmp (dns_typename, name_map[i].name)) ) 725 (0 != strcasecmp (dns_typename, name_map[i].name)))
757 i++; 726 i++;
758 return name_map[i].number; 727 return name_map[i].number;
759} 728}
@@ -767,14 +736,12 @@ dns_typename_to_number (void *cls,
767 * @return corresponding typestring, NULL on error 736 * @return corresponding typestring, NULL on error
768 */ 737 */
769static const char * 738static const char *
770dns_number_to_typename (void *cls, 739dns_number_to_typename (void *cls, uint32_t type)
771 uint32_t type)
772{ 740{
773 unsigned int i; 741 unsigned int i;
774 742
775 i=0; 743 i = 0;
776 while ( (NULL != name_map[i].name) && 744 while ((NULL != name_map[i].name) && (type != name_map[i].number))
777 (type != name_map[i].number) )
778 i++; 745 i++;
779 return name_map[i].name; 746 return name_map[i].name;
780} 747}
diff --git a/src/include/gnunet_dnsparser_lib.h b/src/include/gnunet_dnsparser_lib.h
index 04b09fbc4..6f81c8e04 100644
--- a/src/include/gnunet_dnsparser_lib.h
+++ b/src/include/gnunet_dnsparser_lib.h
@@ -11,7 +11,7 @@
11 WITHOUT ANY WARRANTY; without even the implied warranty of 11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Affero General Public License for more details. 13 Affero General Public License for more details.
14 14
15 You should have received a copy of the GNU Affero General Public License 15 You should have received a copy of the GNU Affero General Public License
16 along with this program. If not, see <http://www.gnu.org/licenses/>. 16 along with this program. If not, see <http://www.gnu.org/licenses/>.
17 17
@@ -86,6 +86,7 @@
86#define GNUNET_DNSPARSER_TYPE_TSIG 250 86#define GNUNET_DNSPARSER_TYPE_TSIG 250
87#define GNUNET_DNSPARSER_TYPE_ALL 255 87#define GNUNET_DNSPARSER_TYPE_ALL 255
88#define GNUNET_DNSPARSER_TYPE_URI 256 88#define GNUNET_DNSPARSER_TYPE_URI 256
89#define GNUNET_DNSPARSER_TYPE_CAA 257
89#define GNUNET_DNSPARSER_TYPE_TA 32768 90#define GNUNET_DNSPARSER_TYPE_TA 32768
90 91
91/** 92/**
@@ -399,6 +400,26 @@ struct GNUNET_DNSPARSER_SoaRecord
399 400
400 401
401/** 402/**
403 * Information from CAA records (RFC 6844).
404 * The tag is followed by the tag_len.
405 * The value is followed by the tag for (d - tag_len - 2) bytes
406 */
407struct GNUNET_DNSPARSER_CaaRecord
408{
409 /**
410 * The flags of the CAA record.
411 */
412 uint8_t flags;
413
414 /**
415 * The length of the tag.
416 */
417 uint8_t tag_len;
418};
419
420
421
422/**
402 * Binary record information (unparsed). 423 * Binary record information (unparsed).
403 */ 424 */
404struct GNUNET_DNSPARSER_RawRecord 425struct GNUNET_DNSPARSER_RawRecord