ldns  1.7.0
dnssec_verify.c
Go to the documentation of this file.
1 #include <ldns/config.h>
2 
3 #include <ldns/ldns.h>
4 
5 #include <strings.h>
6 #include <time.h>
7 
8 #ifdef HAVE_SSL
9 /* this entire file is rather useless when you don't have
10  * crypto...
11  */
12 #include <openssl/ssl.h>
13 #include <openssl/evp.h>
14 #include <openssl/rand.h>
15 #include <openssl/err.h>
16 #include <openssl/md5.h>
17 
20 {
22  if(!nc) return NULL;
23  /*
24  * not needed anymore because CALLOC initalizes everything to zero.
25 
26  nc->rrset = NULL;
27  nc->parent_type = 0;
28  nc->parent = NULL;
29  nc->signatures = NULL;
30  nc->packet_rcode = 0;
31  nc->packet_qtype = 0;
32  nc->packet_nodata = false;
33 
34  */
35  return nc;
36 }
37 
38 void
40 {
41  LDNS_FREE(chain);
42 }
43 
44 void
46 {
49  if (chain->parent) {
51  }
52  LDNS_FREE(chain);
53 }
54 
55 void
57  const ldns_dnssec_data_chain *chain)
58 {
59  ldns_lookup_table *rcode;
60  const ldns_rr_descriptor *rr_descriptor;
61  if (chain) {
62  ldns_dnssec_data_chain_print_fmt(out, fmt, chain->parent);
63  if (ldns_rr_list_rr_count(chain->rrset) > 0) {
65  (int) chain->packet_rcode);
66  if (rcode) {
67  fprintf(out, ";; rcode: %s\n", rcode->name);
68  }
69 
70  rr_descriptor = ldns_rr_descript(chain->packet_qtype);
71  if (rr_descriptor && rr_descriptor->_name) {
72  fprintf(out, ";; qtype: %s\n", rr_descriptor->_name);
73  } else if (chain->packet_qtype != 0) {
74  fprintf(out, "TYPE%u",
75  chain->packet_qtype);
76  }
77  if (chain->packet_nodata) {
78  fprintf(out, ";; NODATA response\n");
79  }
80  fprintf(out, "rrset:\n");
81  ldns_rr_list_print_fmt(out, fmt, chain->rrset);
82  fprintf(out, "sigs:\n");
83  ldns_rr_list_print_fmt(out, fmt, chain->signatures);
84  fprintf(out, "---\n");
85  } else {
86  fprintf(out, "<no data>\n");
87  }
88  }
89 }
90 void
92 {
94  out, ldns_output_format_default, chain);
95 }
96 
97 
98 static void
99 ldns_dnssec_build_data_chain_dnskey(ldns_resolver *res,
100  uint16_t qflags,
101  const ldns_pkt *pkt,
102  ldns_rr_list *signatures,
103  ldns_dnssec_data_chain *new_chain,
104  ldns_rdf *key_name,
105  ldns_rr_class c) {
106  ldns_rr_list *keys;
107  ldns_pkt *my_pkt;
108  if (signatures && ldns_rr_list_rr_count(signatures) > 0) {
109  new_chain->signatures = ldns_rr_list_clone(signatures);
110  new_chain->parent_type = 0;
111 
113  pkt,
114  key_name,
117  );
118  if (!keys) {
119  my_pkt = ldns_resolver_query(res,
120  key_name,
122  c,
123  qflags);
124  if (my_pkt) {
126  my_pkt,
127  key_name,
130  );
131  new_chain->parent = ldns_dnssec_build_data_chain(res,
132  qflags,
133  keys,
134  my_pkt,
135  NULL);
137  ldns_pkt_free(my_pkt);
138  }
139  } else {
140  new_chain->parent = ldns_dnssec_build_data_chain(res,
141  qflags,
142  keys,
143  pkt,
144  NULL);
146  }
148  }
149 }
150 
151 static void
152 ldns_dnssec_build_data_chain_other(ldns_resolver *res,
153  uint16_t qflags,
154  ldns_dnssec_data_chain *new_chain,
155  ldns_rdf *key_name,
156  ldns_rr_class c,
157  ldns_rr_list *dss)
158 {
159  /* 'self-signed', parent is a DS */
160 
161  /* okay, either we have other keys signing the current one,
162  * or the current
163  * one should have a DS record in the parent zone.
164  * How do we find this out? Try both?
165  *
166  * request DNSKEYS for current zone,
167  * add all signatures to current level
168  */
169  ldns_pkt *my_pkt;
170  ldns_rr_list *signatures2;
171 
172  new_chain->parent_type = 1;
173 
174  my_pkt = ldns_resolver_query(res,
175  key_name,
177  c,
178  qflags);
179  if (my_pkt) {
181  key_name,
184  );
185  if (dss) {
186  new_chain->parent = ldns_dnssec_build_data_chain(res,
187  qflags,
188  dss,
189  my_pkt,
190  NULL);
191  new_chain->parent->packet_qtype = LDNS_RR_TYPE_DS;
193  }
194  ldns_pkt_free(my_pkt);
195  }
196 
197  my_pkt = ldns_resolver_query(res,
198  key_name,
200  c,
201  qflags);
202  if (my_pkt) {
203  signatures2 = ldns_pkt_rr_list_by_name_and_type(my_pkt,
204  key_name,
207  if (signatures2) {
208  if (new_chain->signatures) {
209  printf("There were already sigs!\n");
211  printf("replacing the old sigs\n");
212  }
213  new_chain->signatures = signatures2;
214  }
215  ldns_pkt_free(my_pkt);
216  }
217 }
218 
219 static ldns_dnssec_data_chain *
220 ldns_dnssec_build_data_chain_nokeyname(ldns_resolver *res,
221  uint16_t qflags,
222  ldns_rr *orig_rr,
223  const ldns_rr_list *rrset,
224  ldns_dnssec_data_chain *new_chain)
225 {
226  ldns_rdf *possible_parent_name;
227  ldns_pkt *my_pkt;
228  /* apparently we were not able to find a signing key, so
229  we assume the chain ends here
230  */
231  /* try parents for auth denial of DS */
232  if (orig_rr) {
233  possible_parent_name = ldns_rr_owner(orig_rr);
234  } else if (rrset && ldns_rr_list_rr_count(rrset) > 0) {
235  possible_parent_name = ldns_rr_owner(ldns_rr_list_rr(rrset, 0));
236  } else {
237  /* no information to go on, give up */
238  return new_chain;
239  }
240 
241  my_pkt = ldns_resolver_query(res,
242  possible_parent_name,
245  qflags);
246  if (!my_pkt) {
247  return new_chain;
248  }
249 
250  if (ldns_pkt_ancount(my_pkt) > 0) {
251  /* add error, no sigs but DS in parent */
252  /*ldns_pkt_print(stdout, my_pkt);*/
253  ldns_pkt_free(my_pkt);
254  } else {
255  /* are there signatures? */
256  new_chain->parent = ldns_dnssec_build_data_chain(res,
257  qflags,
258  NULL,
259  my_pkt,
260  NULL);
261 
262  new_chain->parent->packet_qtype = LDNS_RR_TYPE_DS;
263 
264  }
265  return new_chain;
266 }
267 
268 
271  uint16_t qflags,
272  const ldns_rr_list *rrset,
273  const ldns_pkt *pkt,
274  ldns_rr *orig_rr)
275 {
276  ldns_rr_list *signatures = NULL;
277  ldns_rr_list *dss = NULL;
278 
279  ldns_rr_list *my_rrset;
280 
281  ldns_pkt *my_pkt;
282 
283  ldns_rdf *name = NULL, *key_name = NULL;
284  ldns_rr_type type = 0;
285  ldns_rr_class c = 0;
286 
287  bool other_rrset = false;
288 
290 
291  assert(pkt != NULL);
292 
293  if (!ldns_dnssec_pkt_has_rrsigs(pkt)) {
294  /* hmm. no dnssec data in the packet. go up to try and deny
295  * DS? */
296  return new_chain;
297  }
298 
299  if (orig_rr) {
300  new_chain->rrset = ldns_rr_list_new();
301  ldns_rr_list_push_rr(new_chain->rrset, orig_rr);
302  new_chain->parent = ldns_dnssec_build_data_chain(res,
303  qflags,
304  rrset,
305  pkt,
306  NULL);
307  new_chain->packet_rcode = ldns_pkt_get_rcode(pkt);
308  new_chain->packet_qtype = ldns_rr_get_type(orig_rr);
309  if (ldns_pkt_ancount(pkt) == 0) {
310  new_chain->packet_nodata = true;
311  }
312  return new_chain;
313  }
314 
315  if (!rrset || ldns_rr_list_rr_count(rrset) < 1) {
316  /* hmm, no data, do we have denial? only works if pkt was given,
317  otherwise caller has to do the check himself */
318  new_chain->packet_nodata = true;
319  if (pkt) {
320  my_rrset = ldns_pkt_rr_list_by_type(pkt,
323  );
324  if (my_rrset) {
325  if (ldns_rr_list_rr_count(my_rrset) > 0) {
326  type = LDNS_RR_TYPE_NSEC;
327  other_rrset = true;
328  } else {
329  ldns_rr_list_deep_free(my_rrset);
330  my_rrset = NULL;
331  }
332  } else {
333  /* nothing, try nsec3 */
334  my_rrset = ldns_pkt_rr_list_by_type(pkt,
337  if (my_rrset) {
338  if (ldns_rr_list_rr_count(my_rrset) > 0) {
339  type = LDNS_RR_TYPE_NSEC3;
340  other_rrset = true;
341  } else {
342  ldns_rr_list_deep_free(my_rrset);
343  my_rrset = NULL;
344  }
345  } else {
346  /* nothing, stop */
347  /* try parent zone? for denied insecure? */
348  return new_chain;
349  }
350  }
351  } else {
352  return new_chain;
353  }
354  } else {
355  my_rrset = (ldns_rr_list *) rrset;
356  }
357 
358  if (my_rrset && ldns_rr_list_rr_count(my_rrset) > 0) {
359  new_chain->rrset = ldns_rr_list_clone(my_rrset);
360  name = ldns_rr_owner(ldns_rr_list_rr(my_rrset, 0));
361  type = ldns_rr_get_type(ldns_rr_list_rr(my_rrset, 0));
362  c = ldns_rr_get_class(ldns_rr_list_rr(my_rrset, 0));
363  }
364 
365  if (other_rrset) {
366  ldns_rr_list_deep_free(my_rrset);
367  }
368 
369  /* normally there will only be 1 signature 'set'
370  but there can be more than 1 denial (wildcards)
371  so check for NSEC
372  */
373  if (type == LDNS_RR_TYPE_NSEC || type == LDNS_RR_TYPE_NSEC3) {
374  /* just throw in all signatures, the tree builder must sort
375  this out */
376  if (pkt) {
377  signatures = ldns_dnssec_pkt_get_rrsigs_for_type(pkt, type);
378  } else {
379  my_pkt = ldns_resolver_query(res, name, type, c, qflags);
380  if (my_pkt) {
381  signatures = ldns_dnssec_pkt_get_rrsigs_for_type(pkt, type);
382  ldns_pkt_free(my_pkt);
383  }
384  }
385  } else {
386  if (pkt) {
387  signatures =
389  name,
390  type);
391  }
392  if (!signatures) {
393  my_pkt = ldns_resolver_query(res, name, type, c, qflags);
394  if (my_pkt) {
395  signatures =
397  name,
398  type);
399  ldns_pkt_free(my_pkt);
400  }
401  }
402  }
403 
404  if (signatures && ldns_rr_list_rr_count(signatures) > 0) {
405  key_name = ldns_rr_rdf(ldns_rr_list_rr(signatures, 0), 7);
406  }
407  if (!key_name) {
408  if (signatures) {
409  ldns_rr_list_deep_free(signatures);
410  }
411  return ldns_dnssec_build_data_chain_nokeyname(res,
412  qflags,
413  orig_rr,
414  rrset,
415  new_chain);
416  }
417  if (type != LDNS_RR_TYPE_DNSKEY) {
418  ldns_dnssec_build_data_chain_dnskey(res,
419  qflags,
420  pkt,
421  signatures,
422  new_chain,
423  key_name,
424  c
425  );
426  } else {
427  ldns_dnssec_build_data_chain_other(res,
428  qflags,
429  new_chain,
430  key_name,
431  c,
432  dss
433  );
434  }
435  if (signatures) {
436  ldns_rr_list_deep_free(signatures);
437  }
438  return new_chain;
439 }
440 
443 {
445  1);
446  if(!new_tree) return NULL;
447  new_tree->rr = NULL;
448  new_tree->rrset = NULL;
449  new_tree->parent_count = 0;
450 
451  return new_tree;
452 }
453 
454 void
456 {
457  size_t i;
458  if (tree) {
459  for (i = 0; i < tree->parent_count; i++) {
461  }
462  }
463  LDNS_FREE(tree);
464 }
465 
466 size_t
468 {
469  size_t result = 0;
470  size_t parent = 0;
471  size_t i;
472 
473  for (i = 0; i < tree->parent_count; i++) {
474  parent = ldns_dnssec_trust_tree_depth(tree->parents[i]);
475  if (parent > result) {
476  result = parent;
477  }
478  }
479  return 1 + result;
480 }
481 
482 /* TODO ldns_ */
483 static void
484 print_tabs(FILE *out, size_t nr, uint8_t *map, size_t treedepth)
485 {
486  size_t i;
487  for (i = 0; i < nr; i++) {
488  if (i == nr - 1) {
489  fprintf(out, "|---");
490  } else if (map && i < treedepth && map[i] == 1) {
491  fprintf(out, "| ");
492  } else {
493  fprintf(out, " ");
494  }
495  }
496 }
497 
498 static void
499 ldns_dnssec_trust_tree_print_sm_fmt(FILE *out,
500  const ldns_output_format *fmt,
502  size_t tabs,
503  bool extended,
504  uint8_t *sibmap,
505  size_t treedepth)
506 {
507  size_t i;
508  const ldns_rr_descriptor *descriptor;
509  bool mapset = false;
510 
511  if (!sibmap) {
512  treedepth = ldns_dnssec_trust_tree_depth(tree);
513  sibmap = LDNS_XMALLOC(uint8_t, treedepth);
514  if(!sibmap)
515  return; /* mem err */
516  memset(sibmap, 0, treedepth);
517  mapset = true;
518  }
519 
520  if (tree) {
521  if (tree->rr) {
522  print_tabs(out, tabs, sibmap, treedepth);
523  ldns_rdf_print(out, ldns_rr_owner(tree->rr));
524  descriptor = ldns_rr_descript(ldns_rr_get_type(tree->rr));
525 
526  if (descriptor->_name) {
527  fprintf(out, " (%s", descriptor->_name);
528  } else {
529  fprintf(out, " (TYPE%d",
530  ldns_rr_get_type(tree->rr));
531  }
532  if (tabs > 0) {
533  if (ldns_rr_get_type(tree->rr) == LDNS_RR_TYPE_DNSKEY) {
534  fprintf(out, " keytag: %u",
535  (unsigned int) ldns_calc_keytag(tree->rr));
536  fprintf(out, " alg: ");
537  ldns_rdf_print(out, ldns_rr_rdf(tree->rr, 2));
538  fprintf(out, " flags: ");
539  ldns_rdf_print(out, ldns_rr_rdf(tree->rr, 0));
540  } else if (ldns_rr_get_type(tree->rr) == LDNS_RR_TYPE_DS) {
541  fprintf(out, " keytag: ");
542  ldns_rdf_print(out, ldns_rr_rdf(tree->rr, 0));
543  fprintf(out, " digest type: ");
544  ldns_rdf_print(out, ldns_rr_rdf(tree->rr, 2));
545  }
546  if (ldns_rr_get_type(tree->rr) == LDNS_RR_TYPE_NSEC) {
547  fprintf(out, " ");
548  ldns_rdf_print(out, ldns_rr_rdf(tree->rr, 0));
549  fprintf(out, " ");
550  ldns_rdf_print(out, ldns_rr_rdf(tree->rr, 1));
551  }
552  }
553 
554  fprintf(out, ")\n");
555  for (i = 0; i < tree->parent_count; i++) {
556  if (tree->parent_count > 1 && i < tree->parent_count - 1) {
557  sibmap[tabs] = 1;
558  } else {
559  sibmap[tabs] = 0;
560  }
561  /* only print errors */
562  if (ldns_rr_get_type(tree->parents[i]->rr) ==
564  ldns_rr_get_type(tree->parents[i]->rr) ==
566  if (tree->parent_status[i] == LDNS_STATUS_OK) {
567  print_tabs(out, tabs + 1, sibmap, treedepth);
568  if (tabs == 0 &&
569  ldns_rr_get_type(tree->rr) == LDNS_RR_TYPE_NS &&
570  ldns_rr_rd_count(tree->rr) > 0) {
571  fprintf(out, "Existence of DS is denied by:\n");
572  } else {
573  fprintf(out, "Existence is denied by:\n");
574  }
575  } else {
576  /* NS records aren't signed */
577  if (ldns_rr_get_type(tree->rr) == LDNS_RR_TYPE_NS) {
578  fprintf(out, "Existence of DS is denied by:\n");
579  } else {
580  print_tabs(out, tabs + 1, sibmap, treedepth);
581  fprintf(out,
582  "Error in denial of existence: %s\n",
584  tree->parent_status[i]));
585  }
586  }
587  } else
588  if (tree->parent_status[i] != LDNS_STATUS_OK) {
589  print_tabs(out, tabs + 1, sibmap, treedepth);
590  fprintf(out,
591  "%s:\n",
593  tree->parent_status[i]));
594  if (tree->parent_status[i]
595  == LDNS_STATUS_SSL_ERR) {
596  printf("; SSL Error: ");
597  ERR_load_crypto_strings();
598  ERR_print_errors_fp(stdout);
599  printf("\n");
600  }
601  ldns_rr_print_fmt(out, fmt,
602  tree->
603  parent_signature[i]);
604  printf("For RRset:\n");
605  ldns_rr_list_print_fmt(out, fmt,
606  tree->rrset);
607  printf("With key:\n");
608  ldns_rr_print_fmt(out, fmt,
609  tree->parents[i]->rr);
610  }
611  ldns_dnssec_trust_tree_print_sm_fmt(out, fmt,
612  tree->parents[i],
613  tabs+1,
614  extended,
615  sibmap,
616  treedepth);
617  }
618  } else {
619  print_tabs(out, tabs, sibmap, treedepth);
620  fprintf(out, "<no data>\n");
621  }
622  } else {
623  fprintf(out, "<null pointer>\n");
624  }
625 
626  if (mapset) {
627  LDNS_FREE(sibmap);
628  }
629 }
630 
631 void
634  size_t tabs,
635  bool extended)
636 {
637  ldns_dnssec_trust_tree_print_sm_fmt(out, fmt,
638  tree, tabs, extended, NULL, 0);
639 }
640 
641 void
644  size_t tabs,
645  bool extended)
646 {
648  tree, tabs, extended);
649 }
650 
651 
654  const ldns_dnssec_trust_tree *parent,
655  const ldns_rr *signature,
656  const ldns_status parent_status)
657 {
658  if (tree
659  && parent
661  /*
662  printf("Add parent for: ");
663  ldns_rr_print(stdout, tree->rr);
664  printf("parent: ");
665  ldns_rr_print(stdout, parent->rr);
666  */
667  tree->parents[tree->parent_count] =
668  (ldns_dnssec_trust_tree *) parent;
669  tree->parent_status[tree->parent_count] = parent_status;
670  tree->parent_signature[tree->parent_count] = (ldns_rr *) signature;
671  tree->parent_count++;
672  return LDNS_STATUS_OK;
673  } else {
674  return LDNS_STATUS_ERR;
675  }
676 }
677 
678 /* if rr is null, take the first from the rrset */
681  ldns_dnssec_data_chain *data_chain,
682  ldns_rr *rr,
683  time_t check_time
684  )
685 {
686  ldns_rr_list *cur_rrset;
687  ldns_rr_list *cur_sigs;
688  ldns_rr *cur_rr = NULL;
689  ldns_rr *cur_sig_rr;
690  size_t i, j;
691 
693  if(!new_tree)
694  return NULL;
695 
696  if (data_chain && data_chain->rrset) {
697  cur_rrset = data_chain->rrset;
698 
699  cur_sigs = data_chain->signatures;
700 
701  if (rr) {
702  cur_rr = rr;
703  }
704 
705  if (!cur_rr && ldns_rr_list_rr_count(cur_rrset) > 0) {
706  cur_rr = ldns_rr_list_rr(cur_rrset, 0);
707  }
708 
709  if (cur_rr) {
710  new_tree->rr = cur_rr;
711  new_tree->rrset = cur_rrset;
712  /* there are three possibilities:
713  1 - 'normal' rrset, signed by a key
714  2 - dnskey signed by other dnskey
715  3 - dnskey proven by higher level DS
716  (data denied by nsec is a special case that can
717  occur in multiple places)
718 
719  */
720  if (cur_sigs) {
721  for (i = 0; i < ldns_rr_list_rr_count(cur_sigs); i++) {
722  /* find the appropriate key in the parent list */
723  cur_sig_rr = ldns_rr_list_rr(cur_sigs, i);
724 
725  if (ldns_rr_get_type(cur_rr) == LDNS_RR_TYPE_NSEC) {
726  if (ldns_dname_compare(ldns_rr_owner(cur_sig_rr),
727  ldns_rr_owner(cur_rr)))
728  {
729  /* find first that does match */
730 
731  for (j = 0;
732  j < ldns_rr_list_rr_count(cur_rrset) &&
733  ldns_dname_compare(ldns_rr_owner(cur_sig_rr),ldns_rr_owner(cur_rr)) != 0;
734  j++) {
735  cur_rr = ldns_rr_list_rr(cur_rrset, j);
736 
737  }
738  if (ldns_dname_compare(ldns_rr_owner(cur_sig_rr),
739  ldns_rr_owner(cur_rr)))
740  {
741  break;
742  }
743  }
744 
745  }
746  /* option 1 */
747  if (data_chain->parent) {
749  new_tree,
750  data_chain,
751  cur_sig_rr,
752  check_time);
753  }
754 
755  /* option 2 */
757  new_tree,
758  data_chain,
759  cur_rr,
760  cur_sig_rr,
761  check_time);
762  }
763 
765  new_tree, data_chain,
766  cur_rr, check_time);
767  } else {
768  /* no signatures? maybe it's nsec data */
769 
770  /* just add every rr from parent as new parent */
772  new_tree, data_chain, check_time);
773  }
774  }
775  }
776 
777  return new_tree;
778 }
779 
782 {
783  return ldns_dnssec_derive_trust_tree_time(data_chain, rr, ldns_time(NULL));
784 }
785 
786 void
788  ldns_dnssec_trust_tree *new_tree,
789  ldns_dnssec_data_chain *data_chain,
790  ldns_rr *cur_sig_rr,
791  time_t check_time)
792 {
793  size_t i, j;
794  ldns_rr_list *cur_rrset = ldns_rr_list_clone(data_chain->rrset);
795  ldns_dnssec_trust_tree *cur_parent_tree;
796  ldns_rr *cur_parent_rr;
797  uint16_t cur_keytag;
798  ldns_rr_list *tmp_rrset = NULL;
799  ldns_status cur_status;
800 
801  cur_keytag = ldns_rdf2native_int16(ldns_rr_rrsig_keytag(cur_sig_rr));
802 
803  for (j = 0; j < ldns_rr_list_rr_count(data_chain->parent->rrset); j++) {
804  cur_parent_rr = ldns_rr_list_rr(data_chain->parent->rrset, j);
805  if (ldns_rr_get_type(cur_parent_rr) == LDNS_RR_TYPE_DNSKEY) {
806  if (ldns_calc_keytag(cur_parent_rr) == cur_keytag) {
807 
808  /* TODO: check wildcard nsec too */
809  if (cur_rrset && ldns_rr_list_rr_count(cur_rrset) > 0) {
810  tmp_rrset = cur_rrset;
811  if (ldns_rr_get_type(ldns_rr_list_rr(cur_rrset, 0))
812  == LDNS_RR_TYPE_NSEC ||
813  ldns_rr_get_type(ldns_rr_list_rr(cur_rrset, 0))
814  == LDNS_RR_TYPE_NSEC3) {
815  /* might contain different names!
816  sort and split */
817  ldns_rr_list_sort(cur_rrset);
818  assert(tmp_rrset == cur_rrset);
819  tmp_rrset = ldns_rr_list_pop_rrset(cur_rrset);
820 
821  /* with nsecs, this might be the wrong one */
822  while (tmp_rrset &&
823  ldns_rr_list_rr_count(cur_rrset) > 0 &&
826  tmp_rrset, 0)),
827  ldns_rr_owner(cur_sig_rr)) != 0) {
828  ldns_rr_list_deep_free(tmp_rrset);
829  tmp_rrset =
830  ldns_rr_list_pop_rrset(cur_rrset);
831  }
832  }
833  cur_status = ldns_verify_rrsig_time(
834  tmp_rrset,
835  cur_sig_rr,
836  cur_parent_rr,
837  check_time);
838  if (tmp_rrset && tmp_rrset != cur_rrset
839  ) {
841  tmp_rrset);
842  tmp_rrset = NULL;
843  }
844  /* avoid dupes */
845  for (i = 0; i < new_tree->parent_count; i++) {
846  if (cur_parent_rr == new_tree->parents[i]->rr) {
847  goto done;
848  }
849  }
850 
851  cur_parent_tree =
853  data_chain->parent,
854  cur_parent_rr,
855  check_time);
856  (void)ldns_dnssec_trust_tree_add_parent(new_tree,
857  cur_parent_tree,
858  cur_sig_rr,
859  cur_status);
860  }
861  }
862  }
863  }
864  done:
865  ldns_rr_list_deep_free(cur_rrset);
866 }
867 
868 void
870  ldns_dnssec_data_chain *data_chain,
871  ldns_rr *cur_sig_rr)
872 {
874  new_tree, data_chain, cur_sig_rr, ldns_time(NULL));
875 }
876 
877 void
879  ldns_dnssec_trust_tree *new_tree,
880  ldns_dnssec_data_chain *data_chain,
881  ldns_rr *cur_rr,
882  ldns_rr *cur_sig_rr,
883  time_t check_time)
884 {
885  size_t j;
886  ldns_rr_list *cur_rrset = data_chain->rrset;
887  ldns_dnssec_trust_tree *cur_parent_tree;
888  ldns_rr *cur_parent_rr;
889  uint16_t cur_keytag;
890  ldns_status cur_status;
891 
892  cur_keytag = ldns_rdf2native_int16(ldns_rr_rrsig_keytag(cur_sig_rr));
893 
894  for (j = 0; j < ldns_rr_list_rr_count(cur_rrset); j++) {
895  cur_parent_rr = ldns_rr_list_rr(cur_rrset, j);
896  if (cur_parent_rr != cur_rr &&
897  ldns_rr_get_type(cur_parent_rr) == LDNS_RR_TYPE_DNSKEY) {
898  if (ldns_calc_keytag(cur_parent_rr) == cur_keytag
899  ) {
900  cur_parent_tree = ldns_dnssec_trust_tree_new();
901  cur_parent_tree->rr = cur_parent_rr;
902  cur_parent_tree->rrset = cur_rrset;
903  cur_status = ldns_verify_rrsig_time(
904  cur_rrset, cur_sig_rr,
905  cur_parent_rr, check_time);
906  (void) ldns_dnssec_trust_tree_add_parent(new_tree,
907  cur_parent_tree, cur_sig_rr, cur_status);
908  }
909  }
910  }
911 }
912 
913 void
915  ldns_dnssec_data_chain *data_chain,
916  ldns_rr *cur_rr,
917  ldns_rr *cur_sig_rr)
918 {
920  new_tree, data_chain, cur_rr, cur_sig_rr, ldns_time(NULL));
921 }
922 
923 void
925  ldns_dnssec_trust_tree *new_tree,
926  ldns_dnssec_data_chain *data_chain,
927  ldns_rr *cur_rr,
928  time_t check_time)
929 {
930  size_t j, h;
931  ldns_rr_list *cur_rrset = data_chain->rrset;
932  ldns_dnssec_trust_tree *cur_parent_tree;
933  ldns_rr *cur_parent_rr;
934 
935  /* try the parent to see whether there are DSs there */
936  if (ldns_rr_get_type(cur_rr) == LDNS_RR_TYPE_DNSKEY &&
937  data_chain->parent &&
938  data_chain->parent->rrset
939  ) {
940  for (j = 0;
941  j < ldns_rr_list_rr_count(data_chain->parent->rrset);
942  j++) {
943  cur_parent_rr = ldns_rr_list_rr(data_chain->parent->rrset, j);
944  if (ldns_rr_get_type(cur_parent_rr) == LDNS_RR_TYPE_DS) {
945  for (h = 0; h < ldns_rr_list_rr_count(cur_rrset); h++) {
946  cur_rr = ldns_rr_list_rr(cur_rrset, h);
947  if (ldns_rr_compare_ds(cur_rr, cur_parent_rr)) {
948  cur_parent_tree =
950  data_chain->parent,
951  cur_parent_rr,
952  check_time);
954  new_tree,
955  cur_parent_tree,
956  NULL,
958  } else {
959  /*ldns_rr_print(stdout, cur_parent_rr);*/
960  }
961  }
962  }
963  }
964  }
965 }
966 
967 void
969  ldns_dnssec_data_chain *data_chain,
970  ldns_rr *cur_rr)
971 {
973  new_tree, data_chain, cur_rr, ldns_time(NULL));
974 }
975 
976 void
978  ldns_dnssec_trust_tree *new_tree,
979  ldns_dnssec_data_chain *data_chain,
980  time_t check_time)
981 {
982  size_t i;
983  ldns_rr_list *cur_rrset;
984  ldns_rr *cur_parent_rr;
985  ldns_dnssec_trust_tree *cur_parent_tree;
986  ldns_status result;
987 
988  if (data_chain->parent && data_chain->parent->rrset) {
989  cur_rrset = data_chain->parent->rrset;
990  /* nsec? */
991  if (cur_rrset && ldns_rr_list_rr_count(cur_rrset) > 0) {
992  if (ldns_rr_get_type(ldns_rr_list_rr(cur_rrset, 0)) ==
995  new_tree->rr,
996  cur_rrset,
997  data_chain->parent->signatures,
998  data_chain->packet_rcode,
999  data_chain->packet_qtype,
1000  data_chain->packet_nodata);
1001  } else if (ldns_rr_get_type(ldns_rr_list_rr(cur_rrset, 0)) ==
1003  result = ldns_dnssec_verify_denial(
1004  new_tree->rr,
1005  cur_rrset,
1006  data_chain->parent->signatures);
1007  } else {
1008  /* unsigned zone, unsigned parent */
1009  result = LDNS_STATUS_OK;
1010  }
1011  } else {
1013  }
1014  for (i = 0; i < ldns_rr_list_rr_count(cur_rrset); i++) {
1015  cur_parent_rr = ldns_rr_list_rr(cur_rrset, i);
1016  cur_parent_tree =
1018  data_chain->parent,
1019  cur_parent_rr,
1020  check_time);
1021  (void) ldns_dnssec_trust_tree_add_parent(new_tree,
1022  cur_parent_tree, NULL, result);
1023  }
1024  }
1025 }
1026 
1027 void
1029  ldns_dnssec_data_chain *data_chain)
1030 {
1032  new_tree, data_chain, ldns_time(NULL));
1033 }
1034 
1035 /*
1036  * returns OK if there is a path from tree to key with only OK
1037  * the (first) error in between otherwise
1038  * or NOT_FOUND if the key wasn't present at all
1039  */
1042  ldns_rr_list *trusted_keys)
1043 {
1044  size_t i;
1046  bool equal;
1047  ldns_status parent_result;
1048 
1049  if (tree && trusted_keys && ldns_rr_list_rr_count(trusted_keys) > 0)
1050  { if (tree->rr) {
1051  for (i = 0; i < ldns_rr_list_rr_count(trusted_keys); i++) {
1052  equal = ldns_rr_compare_ds(
1053  tree->rr,
1054  ldns_rr_list_rr(trusted_keys, i));
1055  if (equal) {
1056  result = LDNS_STATUS_OK;
1057  return result;
1058  }
1059  }
1060  }
1061  for (i = 0; i < tree->parent_count; i++) {
1062  parent_result =
1064  trusted_keys);
1065  if (parent_result != LDNS_STATUS_CRYPTO_NO_DNSKEY) {
1066  if (tree->parent_status[i] != LDNS_STATUS_OK) {
1067  result = tree->parent_status[i];
1068  } else {
1069  if (tree->rr &&
1070  ldns_rr_get_type(tree->rr)
1071  == LDNS_RR_TYPE_NSEC &&
1072  parent_result == LDNS_STATUS_OK
1073  ) {
1074  result =
1076  } else {
1077  result = parent_result;
1078  }
1079  }
1080  }
1081  }
1082  } else {
1083  result = LDNS_STATUS_ERR;
1084  }
1085 
1086  return result;
1087 }
1088 
1091  const ldns_rr_list *rrset,
1092  const ldns_rr_list *rrsig,
1093  const ldns_rr_list *keys,
1094  time_t check_time,
1095  ldns_rr_list *good_keys
1096  )
1097 {
1098  uint16_t i;
1099  ldns_status verify_result = LDNS_STATUS_ERR;
1100 
1101  if (!rrset || !rrsig || !keys) {
1102  return LDNS_STATUS_ERR;
1103  }
1104 
1105  if (ldns_rr_list_rr_count(rrset) < 1) {
1106  return LDNS_STATUS_ERR;
1107  }
1108 
1109  if (ldns_rr_list_rr_count(rrsig) < 1) {
1111  }
1112 
1113  if (ldns_rr_list_rr_count(keys) < 1) {
1114  verify_result = LDNS_STATUS_CRYPTO_NO_TRUSTED_DNSKEY;
1115  } else {
1116  for (i = 0; i < ldns_rr_list_rr_count(rrsig); i++) {
1118  rrset, ldns_rr_list_rr(rrsig, i),
1119  keys, check_time, good_keys);
1120  /* try a little to get more descriptive error */
1121  if(s == LDNS_STATUS_OK) {
1122  verify_result = LDNS_STATUS_OK;
1123  } else if(verify_result == LDNS_STATUS_ERR)
1124  verify_result = s;
1125  else if(s != LDNS_STATUS_ERR && verify_result ==
1127  verify_result = s;
1128  }
1129  }
1130  return verify_result;
1131 }
1132 
1134 ldns_verify(ldns_rr_list *rrset, ldns_rr_list *rrsig, const ldns_rr_list *keys,
1135  ldns_rr_list *good_keys)
1136 {
1137  return ldns_verify_time(rrset, rrsig, keys, ldns_time(NULL), good_keys);
1138 }
1139 
1142  const ldns_rr_list *keys, ldns_rr_list *good_keys)
1143 {
1144  uint16_t i;
1145  ldns_status verify_result = LDNS_STATUS_ERR;
1146 
1147  if (!rrset || !rrsig || !keys) {
1148  return LDNS_STATUS_ERR;
1149  }
1150 
1151  if (ldns_rr_list_rr_count(rrset) < 1) {
1152  return LDNS_STATUS_ERR;
1153  }
1154 
1155  if (ldns_rr_list_rr_count(rrsig) < 1) {
1157  }
1158 
1159  if (ldns_rr_list_rr_count(keys) < 1) {
1160  verify_result = LDNS_STATUS_CRYPTO_NO_TRUSTED_DNSKEY;
1161  } else {
1162  for (i = 0; i < ldns_rr_list_rr_count(rrsig); i++) {
1164  ldns_rr_list_rr(rrsig, i), keys, good_keys);
1165 
1166  /* try a little to get more descriptive error */
1167  if (s == LDNS_STATUS_OK) {
1168  verify_result = LDNS_STATUS_OK;
1169  } else if (verify_result == LDNS_STATUS_ERR) {
1170  verify_result = s;
1171  } else if (s != LDNS_STATUS_ERR && verify_result ==
1173  verify_result = s;
1174  }
1175  }
1176  }
1177  return verify_result;
1178 }
1179 
1180 ldns_rr_list *
1182  const ldns_rdf *domain,
1183  const ldns_rr_list *keys,
1184  time_t check_time,
1185  ldns_status *status)
1186 {
1187  ldns_rr_list * trusted_keys = NULL;
1188  ldns_rr_list * ds_keys = NULL;
1189  ldns_rdf * prev_parent_domain;
1190  ldns_rdf * parent_domain;
1191  ldns_rr_list * parent_keys = NULL;
1192 
1193  if (res && domain && keys) {
1194 
1195  if ((trusted_keys = ldns_validate_domain_dnskey_time(res,
1196  domain, keys, check_time))) {
1197  *status = LDNS_STATUS_OK;
1198  } else {
1199  /* No trusted keys in this domain, we'll have to find some in the parent domain */
1201 
1202  parent_domain = ldns_dname_left_chop(domain);
1203  while (parent_domain && /* Fail if we are at the root*/
1204  ldns_rdf_size(parent_domain) > 0) {
1205 
1206  if ((parent_keys =
1208  parent_domain,
1209  keys,
1210  check_time,
1211  status))) {
1212  /* Check DS records */
1213  if ((ds_keys =
1215  domain,
1216  parent_keys,
1217  check_time))) {
1218  trusted_keys =
1220  res,
1221  domain,
1222  ds_keys,
1223  check_time,
1224  status);
1225  ldns_rr_list_deep_free(ds_keys);
1226  } else {
1227  /* No valid DS at the parent -- fail */
1229  }
1230  ldns_rr_list_deep_free(parent_keys);
1231  break;
1232  } else {
1233  parent_domain = ldns_dname_left_chop((
1234  prev_parent_domain
1235  = parent_domain
1236  ));
1237  ldns_rdf_deep_free(prev_parent_domain);
1238  }
1239  }
1240  if (parent_domain) {
1241  ldns_rdf_deep_free(parent_domain);
1242  }
1243  }
1244  }
1245  return trusted_keys;
1246 }
1247 
1248 ldns_rr_list *
1250  const ldns_rdf *domain,
1251  const ldns_rr_list *keys,
1252  ldns_status *status)
1253 {
1255  res, domain, keys, ldns_time(NULL), status);
1256 }
1257 
1258 ldns_rr_list *
1260  const ldns_resolver * res,
1261  const ldns_rdf * domain,
1262  const ldns_rr_list * keys,
1263  time_t check_time
1264  )
1265 {
1266  ldns_pkt * keypkt;
1267  ldns_rr * cur_key;
1268  uint16_t key_i; uint16_t key_j; uint16_t key_k;
1269  uint16_t sig_i; ldns_rr * cur_sig;
1270 
1271  ldns_rr_list * domain_keys = NULL;
1272  ldns_rr_list * domain_sigs = NULL;
1273  ldns_rr_list * trusted_keys = NULL;
1274 
1275  /* Fetch keys for the domain */
1276  keypkt = ldns_resolver_query(res, domain,
1278  if (keypkt) {
1279  domain_keys = ldns_pkt_rr_list_by_type(keypkt,
1282  domain_sigs = ldns_pkt_rr_list_by_type(keypkt,
1285 
1286  /* Try to validate the record using our keys */
1287  for (key_i=0; key_i< ldns_rr_list_rr_count(domain_keys); key_i++) {
1288 
1289  cur_key = ldns_rr_list_rr(domain_keys, key_i);
1290  for (key_j=0; key_j<ldns_rr_list_rr_count(keys); key_j++) {
1291  if (ldns_rr_compare_ds(ldns_rr_list_rr(keys, key_j),
1292  cur_key)) {
1293 
1294  /* Current key is trusted -- validate */
1295  trusted_keys = ldns_rr_list_new();
1296 
1297  for (sig_i=0;
1298  sig_i<ldns_rr_list_rr_count(domain_sigs);
1299  sig_i++) {
1300  cur_sig = ldns_rr_list_rr(domain_sigs, sig_i);
1301  /* Avoid non-matching sigs */
1303  ldns_rr_rrsig_keytag(cur_sig))
1304  == ldns_calc_keytag(cur_key)) {
1306  domain_keys,
1307  cur_sig,
1308  cur_key,
1309  check_time)
1310  == LDNS_STATUS_OK) {
1311 
1312  /* Push the whole rrset
1313  -- we can't do much more */
1314  for (key_k=0;
1315  key_k<ldns_rr_list_rr_count(
1316  domain_keys);
1317  key_k++) {
1319  trusted_keys,
1320  ldns_rr_clone(
1322  domain_keys,
1323  key_k)));
1324  }
1325 
1326  ldns_rr_list_deep_free(domain_keys);
1327  ldns_rr_list_deep_free(domain_sigs);
1328  ldns_pkt_free(keypkt);
1329  return trusted_keys;
1330  }
1331  }
1332  }
1333 
1334  /* Only push our trusted key */
1335  ldns_rr_list_push_rr(trusted_keys,
1336  ldns_rr_clone(cur_key));
1337  }
1338  }
1339  }
1340 
1341  ldns_rr_list_deep_free(domain_keys);
1342  ldns_rr_list_deep_free(domain_sigs);
1343  ldns_pkt_free(keypkt);
1344 
1345  } else {
1346  /* LDNS_STATUS_CRYPTO_NO_DNSKEY */
1347  }
1348 
1349  return trusted_keys;
1350 }
1351 
1352 ldns_rr_list *
1354  const ldns_rdf * domain,
1355  const ldns_rr_list * keys)
1356 {
1358  res, domain, keys, ldns_time(NULL));
1359 }
1360 
1361 ldns_rr_list *
1363  const ldns_resolver *res,
1364  const ldns_rdf * domain,
1365  const ldns_rr_list * keys,
1366  time_t check_time)
1367 {
1368  ldns_pkt * dspkt;
1369  uint16_t key_i;
1370  ldns_rr_list * rrset = NULL;
1371  ldns_rr_list * sigs = NULL;
1372  ldns_rr_list * trusted_keys = NULL;
1373 
1374  /* Fetch DS for the domain */
1375  dspkt = ldns_resolver_query(res, domain,
1377  if (dspkt) {
1378  rrset = ldns_pkt_rr_list_by_type(dspkt,
1381  sigs = ldns_pkt_rr_list_by_type(dspkt,
1384 
1385  /* Validate sigs */
1386  if (ldns_verify_time(rrset, sigs, keys, check_time, NULL)
1387  == LDNS_STATUS_OK) {
1388  trusted_keys = ldns_rr_list_new();
1389  for (key_i=0; key_i<ldns_rr_list_rr_count(rrset); key_i++) {
1390  ldns_rr_list_push_rr(trusted_keys,
1392  key_i)
1393  )
1394  );
1395  }
1396  }
1397 
1398  ldns_rr_list_deep_free(rrset);
1399  ldns_rr_list_deep_free(sigs);
1400  ldns_pkt_free(dspkt);
1401 
1402  } else {
1403  /* LDNS_STATUS_CRYPTO_NO_DS */
1404  }
1405 
1406  return trusted_keys;
1407 }
1408 
1409 ldns_rr_list *
1411  const ldns_rdf * domain,
1412  const ldns_rr_list * keys)
1413 {
1414  return ldns_validate_domain_ds_time(res, domain, keys, ldns_time(NULL));
1415 }
1416 
1419  ldns_resolver *res,
1420  ldns_rr_list *rrset,
1421  ldns_rr_list * rrsigs,
1422  time_t check_time,
1423  ldns_rr_list * validating_keys
1424  )
1425 {
1426  uint16_t sig_i; uint16_t key_i;
1427  ldns_rr * cur_sig; ldns_rr * cur_key;
1428  ldns_rr_list * trusted_keys = NULL;
1429  ldns_status result = LDNS_STATUS_ERR;
1430 
1431  if (!res || !rrset || !rrsigs) {
1432  return LDNS_STATUS_ERR;
1433  }
1434 
1435  if (ldns_rr_list_rr_count(rrset) < 1) {
1436  return LDNS_STATUS_ERR;
1437  }
1438 
1439  if (ldns_rr_list_rr_count(rrsigs) < 1) {
1441  }
1442 
1443  /* Look at each sig */
1444  for (sig_i=0; sig_i < ldns_rr_list_rr_count(rrsigs); sig_i++) {
1445 
1446  cur_sig = ldns_rr_list_rr(rrsigs, sig_i);
1447  /* Get a valid signer key and validate the sig */
1448  if ((trusted_keys = ldns_fetch_valid_domain_keys_time(
1449  res,
1450  ldns_rr_rrsig_signame(cur_sig),
1452  check_time,
1453  &result))) {
1454 
1455  for (key_i = 0;
1456  key_i < ldns_rr_list_rr_count(trusted_keys);
1457  key_i++) {
1458  cur_key = ldns_rr_list_rr(trusted_keys, key_i);
1459 
1460  if ((result = ldns_verify_rrsig_time(rrset,
1461  cur_sig,
1462  cur_key,
1463  check_time))
1464  == LDNS_STATUS_OK) {
1465  if (validating_keys) {
1466  ldns_rr_list_push_rr(validating_keys,
1467  ldns_rr_clone(cur_key));
1468  }
1469  ldns_rr_list_deep_free(trusted_keys);
1470  return LDNS_STATUS_OK;
1471  }
1472  }
1473  }
1474  }
1475 
1476  ldns_rr_list_deep_free(trusted_keys);
1477  return result;
1478 }
1479 
1482  ldns_resolver *res,
1483  ldns_rr_list *rrset,
1484  ldns_rr_list * rrsigs,
1485  ldns_rr_list * validating_keys)
1486 {
1487  return ldns_verify_trusted_time(
1488  res, rrset, rrsigs, ldns_time(NULL), validating_keys);
1489 }
1490 
1491 
1494  ldns_rr_list *nsecs,
1495  ldns_rr_list *rrsigs)
1496 {
1497  ldns_rdf *rr_name;
1498  ldns_rdf *wildcard_name;
1499  ldns_rdf *chopped_dname;
1500  ldns_rr *cur_nsec;
1501  size_t i;
1502  ldns_status result;
1503  /* needed for wildcard check on exact match */
1504  ldns_rr *rrsig;
1505  bool name_covered = false;
1506  bool type_covered = false;
1507  bool wildcard_covered = false;
1508  bool wildcard_type_covered = false;
1509 
1510  wildcard_name = ldns_dname_new_frm_str("*");
1511  rr_name = ldns_rr_owner(rr);
1512  chopped_dname = ldns_dname_left_chop(rr_name);
1513  result = ldns_dname_cat(wildcard_name, chopped_dname);
1514  ldns_rdf_deep_free(chopped_dname);
1515  if (result != LDNS_STATUS_OK) {
1516  return result;
1517  }
1518 
1519  for (i = 0; i < ldns_rr_list_rr_count(nsecs); i++) {
1520  cur_nsec = ldns_rr_list_rr(nsecs, i);
1521  if (ldns_dname_compare(rr_name, ldns_rr_owner(cur_nsec)) == 0) {
1522  /* see section 5.4 of RFC4035, if the label count of the NSEC's
1523  RRSIG is equal, then it is proven that wildcard expansion
1524  could not have been used to match the request */
1526  ldns_rr_owner(cur_nsec),
1527  ldns_rr_get_type(cur_nsec),
1528  rrsigs);
1529  if (rrsig && ldns_rdf2native_int8(ldns_rr_rrsig_labels(rrsig))
1530  == ldns_dname_label_count(rr_name)) {
1531  wildcard_covered = true;
1532  }
1533 
1535  ldns_rr_get_type(rr))) {
1536  type_covered = true;
1537  }
1538  }
1539  if (ldns_nsec_covers_name(cur_nsec, rr_name)) {
1540  name_covered = true;
1541  }
1542 
1543  if (ldns_dname_compare(wildcard_name,
1544  ldns_rr_owner(cur_nsec)) == 0) {
1546  ldns_rr_get_type(rr))) {
1547  wildcard_type_covered = true;
1548  }
1549  }
1550 
1551  if (ldns_nsec_covers_name(cur_nsec, wildcard_name)) {
1552  wildcard_covered = true;
1553  }
1554 
1555  }
1556 
1557  ldns_rdf_deep_free(wildcard_name);
1558 
1559  if (type_covered || !name_covered) {
1561  }
1562 
1563  if (wildcard_type_covered || !wildcard_covered) {
1565  }
1566 
1567  return LDNS_STATUS_OK;
1568 }
1569 
1572  , ldns_rr_list *nsecs
1573  , ATTR_UNUSED(ldns_rr_list *rrsigs)
1574  , ldns_pkt_rcode packet_rcode
1575  , ldns_rr_type packet_qtype
1576  , bool packet_nodata
1577  , ldns_rr **match
1578  )
1579 {
1580  ldns_rdf *closest_encloser;
1581  ldns_rdf *wildcard;
1582  ldns_rdf *hashed_wildcard_name;
1583  bool wildcard_covered = false;
1584  ldns_rdf *zone_name;
1585  ldns_rdf *hashed_name;
1586  /* self assignment to suppress uninitialized warning */
1587  ldns_rdf *next_closer = next_closer;
1588  ldns_rdf *hashed_next_closer;
1589  size_t i;
1591 
1592  if (match) {
1593  *match = NULL;
1594  }
1595 
1596  zone_name = ldns_dname_left_chop(ldns_rr_owner(ldns_rr_list_rr(nsecs,0)));
1597 
1598  /* section 8.4 */
1599  if (packet_rcode == LDNS_RCODE_NXDOMAIN) {
1600  closest_encloser = ldns_dnssec_nsec3_closest_encloser(
1601  ldns_rr_owner(rr),
1602  ldns_rr_get_type(rr),
1603  nsecs);
1604  if(!closest_encloser) {
1606  goto done;
1607  }
1608 
1609  wildcard = ldns_dname_new_frm_str("*");
1610  (void) ldns_dname_cat(wildcard, closest_encloser);
1611 
1612  for (i = 0; i < ldns_rr_list_rr_count(nsecs); i++) {
1613  hashed_wildcard_name =
1615  wildcard
1616  );
1617  (void) ldns_dname_cat(hashed_wildcard_name, zone_name);
1618 
1619  if (ldns_nsec_covers_name(ldns_rr_list_rr(nsecs, i),
1620  hashed_wildcard_name)) {
1621  wildcard_covered = true;
1622  if (match) {
1623  *match = ldns_rr_list_rr(nsecs, i);
1624  }
1625  }
1626  ldns_rdf_deep_free(hashed_wildcard_name);
1627  }
1628 
1629  if (! wildcard_covered) {
1631  } else {
1632  result = LDNS_STATUS_OK;
1633  }
1634  ldns_rdf_deep_free(closest_encloser);
1635  ldns_rdf_deep_free(wildcard);
1636 
1637  } else if (packet_nodata && packet_qtype != LDNS_RR_TYPE_DS) {
1638  /* section 8.5 */
1639  hashed_name = ldns_nsec3_hash_name_frm_nsec3(
1640  ldns_rr_list_rr(nsecs, 0),
1641  ldns_rr_owner(rr));
1642  (void) ldns_dname_cat(hashed_name, zone_name);
1643  for (i = 0; i < ldns_rr_list_rr_count(nsecs); i++) {
1644  if (ldns_dname_compare(hashed_name,
1645  ldns_rr_owner(ldns_rr_list_rr(nsecs, i)))
1646  == 0) {
1649  packet_qtype)
1650  &&
1653  LDNS_RR_TYPE_CNAME)) {
1654  result = LDNS_STATUS_OK;
1655  if (match) {
1656  *match = ldns_rr_list_rr(nsecs, i);
1657  }
1658  goto done;
1659  }
1660  }
1661  }
1663  /* wildcard no data? section 8.7 */
1664  closest_encloser = ldns_dnssec_nsec3_closest_encloser(
1665  ldns_rr_owner(rr),
1666  ldns_rr_get_type(rr),
1667  nsecs);
1668  if(!closest_encloser) {
1669  result = LDNS_STATUS_NSEC3_ERR;
1670  goto done;
1671  }
1672  wildcard = ldns_dname_new_frm_str("*");
1673  (void) ldns_dname_cat(wildcard, closest_encloser);
1674  for (i = 0; i < ldns_rr_list_rr_count(nsecs); i++) {
1675  hashed_wildcard_name =
1677  wildcard);
1678  (void) ldns_dname_cat(hashed_wildcard_name, zone_name);
1679 
1680  if (ldns_dname_compare(hashed_wildcard_name,
1681  ldns_rr_owner(ldns_rr_list_rr(nsecs, i)))
1682  == 0) {
1685  packet_qtype)
1686  &&
1689  LDNS_RR_TYPE_CNAME)) {
1690  result = LDNS_STATUS_OK;
1691  if (match) {
1692  *match = ldns_rr_list_rr(nsecs, i);
1693  }
1694  }
1695  }
1696  ldns_rdf_deep_free(hashed_wildcard_name);
1697  if (result == LDNS_STATUS_OK) {
1698  break;
1699  }
1700  }
1701  ldns_rdf_deep_free(closest_encloser);
1702  ldns_rdf_deep_free(wildcard);
1703  } else if (packet_nodata && packet_qtype == LDNS_RR_TYPE_DS) {
1704  /* section 8.6 */
1705  /* note: up to XXX this is the same as for 8.5 */
1706  hashed_name = ldns_nsec3_hash_name_frm_nsec3(ldns_rr_list_rr(nsecs,
1707  0),
1708  ldns_rr_owner(rr)
1709  );
1710  (void) ldns_dname_cat(hashed_name, zone_name);
1711  for (i = 0; i < ldns_rr_list_rr_count(nsecs); i++) {
1712  if (ldns_dname_compare(hashed_name,
1714  i)))
1715  == 0) {
1719  &&
1722  LDNS_RR_TYPE_CNAME)) {
1723  result = LDNS_STATUS_OK;
1724  if (match) {
1725  *match = ldns_rr_list_rr(nsecs, i);
1726  }
1727  goto done;
1728  }
1729  }
1730  }
1731 
1732  /* XXX see note above */
1734 
1735  closest_encloser = ldns_dnssec_nsec3_closest_encloser(
1736  ldns_rr_owner(rr),
1737  ldns_rr_get_type(rr),
1738  nsecs);
1739  if(!closest_encloser) {
1740  result = LDNS_STATUS_NSEC3_ERR;
1741  goto done;
1742  }
1743  /* Now check if we have a Opt-Out NSEC3 that covers the "next closer"*/
1744 
1745  if (ldns_dname_label_count(closest_encloser) + 1
1747 
1748  /* Query name *is* the "next closer". */
1749  hashed_next_closer = hashed_name;
1750  } else {
1751 
1752  /* "next closer" has less labels than the query name.
1753  * Create the name and hash it.
1754  */
1755  next_closer = ldns_dname_clone_from(
1756  ldns_rr_owner(rr),
1758  - (ldns_dname_label_count(closest_encloser) + 1)
1759  );
1760  hashed_next_closer = ldns_nsec3_hash_name_frm_nsec3(
1761  ldns_rr_list_rr(nsecs, 0),
1762  next_closer
1763  );
1764  (void) ldns_dname_cat(hashed_next_closer, zone_name);
1765  }
1766  /* Find the NSEC3 that covers the "next closer" */
1767  for (i = 0; i < ldns_rr_list_rr_count(nsecs); i++) {
1768  if (ldns_nsec_covers_name(ldns_rr_list_rr(nsecs, i),
1769  hashed_next_closer) &&
1770  ldns_nsec3_optout(ldns_rr_list_rr(nsecs, i))) {
1771 
1772  result = LDNS_STATUS_OK;
1773  if (match) {
1774  *match = ldns_rr_list_rr(nsecs, i);
1775  }
1776  break;
1777  }
1778  }
1779  if (ldns_dname_label_count(closest_encloser) + 1
1781 
1782  /* "next closer" has less labels than the query name.
1783  * Dispose of the temporary variables that held that name.
1784  */
1785  ldns_rdf_deep_free(hashed_next_closer);
1786  ldns_rdf_deep_free(next_closer);
1787  }
1788  ldns_rdf_deep_free(closest_encloser);
1789  }
1790 
1791  done:
1792  ldns_rdf_deep_free(zone_name);
1793  return result;
1794 }
1795 
1798  ldns_rr_list *nsecs,
1799  ldns_rr_list *rrsigs,
1800  ldns_pkt_rcode packet_rcode,
1801  ldns_rr_type packet_qtype,
1802  bool packet_nodata)
1803 {
1805  rr, nsecs, rrsigs, packet_rcode,
1806  packet_qtype, packet_nodata, NULL
1807  );
1808 }
1809 
1810 #ifdef USE_GOST
1811 EVP_PKEY*
1812 ldns_gost2pkey_raw(const unsigned char* key, size_t keylen)
1813 {
1814  /* prefix header for X509 encoding */
1815  uint8_t asn[37] = { 0x30, 0x63, 0x30, 0x1c, 0x06, 0x06, 0x2a, 0x85,
1816  0x03, 0x02, 0x02, 0x13, 0x30, 0x12, 0x06, 0x07, 0x2a, 0x85,
1817  0x03, 0x02, 0x02, 0x23, 0x01, 0x06, 0x07, 0x2a, 0x85, 0x03,
1818  0x02, 0x02, 0x1e, 0x01, 0x03, 0x43, 0x00, 0x04, 0x40};
1819  unsigned char encoded[37+64];
1820  const unsigned char* pp;
1821  if(keylen != 64) {
1822  /* key wrong size */
1823  return NULL;
1824  }
1825 
1826  /* create evp_key */
1827  memmove(encoded, asn, 37);
1828  memmove(encoded+37, key, 64);
1829  pp = (unsigned char*)&encoded[0];
1830 
1831  return d2i_PUBKEY(NULL, &pp, (int)sizeof(encoded));
1832 }
1833 
1834 static ldns_status
1835 ldns_verify_rrsig_gost_raw(const unsigned char* sig, size_t siglen,
1836  const ldns_buffer* rrset, const unsigned char* key, size_t keylen)
1837 {
1838  EVP_PKEY *evp_key;
1839  ldns_status result;
1840 
1841  (void) ldns_key_EVP_load_gost_id();
1842  evp_key = ldns_gost2pkey_raw(key, keylen);
1843  if(!evp_key) {
1844  /* could not convert key */
1845  return LDNS_STATUS_CRYPTO_BOGUS;
1846  }
1847 
1848  /* verify signature */
1849  result = ldns_verify_rrsig_evp_raw(sig, siglen, rrset,
1850  evp_key, EVP_get_digestbyname("md_gost94"));
1851  EVP_PKEY_free(evp_key);
1852 
1853  return result;
1854 }
1855 #endif
1856 
1857 #ifdef USE_ED25519
1858 EVP_PKEY*
1859 ldns_ed255192pkey_raw(const unsigned char* key, size_t keylen)
1860 {
1861  const unsigned char* pp = key; /* pp gets modified by o2i() */
1862  EVP_PKEY *evp_key;
1863  EC_KEY *ec;
1864  if(keylen != 32)
1865  return NULL; /* wrong length */
1866  ec = EC_KEY_new_by_curve_name(NID_X25519);
1867  if(!ec) return NULL;
1868  if(!o2i_ECPublicKey(&ec, &pp, (int)keylen)) {
1869  EC_KEY_free(ec);
1870  return NULL;
1871  }
1872  evp_key = EVP_PKEY_new();
1873  if(!evp_key) {
1874  EC_KEY_free(ec);
1875  return NULL;
1876  }
1877  if (!EVP_PKEY_assign_EC_KEY(evp_key, ec)) {
1878  EVP_PKEY_free(evp_key);
1879  EC_KEY_free(ec);
1880  return NULL;
1881  }
1882  return evp_key;
1883 }
1884 
1885 static ldns_status
1886 ldns_verify_rrsig_ed25519_raw(unsigned char* sig, size_t siglen,
1887  ldns_buffer* rrset, unsigned char* key, size_t keylen)
1888 {
1889  EVP_PKEY *evp_key;
1890  ldns_status result;
1891 
1892  evp_key = ldns_ed255192pkey_raw(key, keylen);
1893  if(!evp_key) {
1894  /* could not convert key */
1895  return LDNS_STATUS_CRYPTO_BOGUS;
1896  }
1897  result = ldns_verify_rrsig_evp_raw(sig, siglen, rrset, evp_key,
1898  EVP_sha512());
1899  EVP_PKEY_free(evp_key);
1900  return result;
1901 }
1902 #endif /* USE_ED25519 */
1903 
1904 #ifdef USE_ED448
1905 EVP_PKEY*
1906 ldns_ed4482pkey_raw(const unsigned char* key, size_t keylen)
1907 {
1908  const unsigned char* pp = key; /* pp gets modified by o2i() */
1909  EVP_PKEY *evp_key;
1910  EC_KEY *ec;
1911  if(keylen != 57)
1912  return NULL; /* wrong length */
1913  ec = EC_KEY_new_by_curve_name(NID_X448);
1914  if(!ec) return NULL;
1915  if(!o2i_ECPublicKey(&ec, &pp, (int)keylen)) {
1916  EC_KEY_free(ec);
1917  return NULL;
1918  }
1919  evp_key = EVP_PKEY_new();
1920  if(!evp_key) {
1921  EC_KEY_free(ec);
1922  return NULL;
1923  }
1924  if (!EVP_PKEY_assign_EC_KEY(evp_key, ec)) {
1925  EVP_PKEY_free(evp_key);
1926  EC_KEY_free(ec);
1927  return NULL;
1928  }
1929  return evp_key;
1930 }
1931 
1932 static ldns_status
1933 ldns_verify_rrsig_ed448_raw(unsigned char* sig, size_t siglen,
1934  ldns_buffer* rrset, unsigned char* key, size_t keylen)
1935 {
1936  EVP_PKEY *evp_key;
1937  ldns_status result;
1938 
1939  evp_key = ldns_ed4482pkey_raw(key, keylen);
1940  if(!evp_key) {
1941  /* could not convert key */
1942  return LDNS_STATUS_CRYPTO_BOGUS;
1943  }
1944  result = ldns_verify_rrsig_evp_raw(sig, siglen, rrset, evp_key,
1945  EVP_sha512());
1946  EVP_PKEY_free(evp_key);
1947  return result;
1948 }
1949 #endif /* USE_ED448 */
1950 
1951 #ifdef USE_ECDSA
1952 EVP_PKEY*
1953 ldns_ecdsa2pkey_raw(const unsigned char* key, size_t keylen, uint8_t algo)
1954 {
1955  unsigned char buf[256+2]; /* sufficient for 2*384/8+1 */
1956  const unsigned char* pp = buf;
1957  EVP_PKEY *evp_key;
1958  EC_KEY *ec;
1959  /* check length, which uncompressed must be 2 bignums */
1960  if(algo == LDNS_ECDSAP256SHA256) {
1961  if(keylen != 2*256/8) return NULL;
1962  ec = EC_KEY_new_by_curve_name(NID_X9_62_prime256v1);
1963  } else if(algo == LDNS_ECDSAP384SHA384) {
1964  if(keylen != 2*384/8) return NULL;
1965  ec = EC_KEY_new_by_curve_name(NID_secp384r1);
1966  } else ec = NULL;
1967  if(!ec) return NULL;
1968  if(keylen+1 > sizeof(buf))
1969  return NULL; /* sanity check */
1970  /* prepend the 0x02 (from docs) (or actually 0x04 from implementation
1971  * of openssl) for uncompressed data */
1972  buf[0] = POINT_CONVERSION_UNCOMPRESSED;
1973  memmove(buf+1, key, keylen);
1974  if(!o2i_ECPublicKey(&ec, &pp, (int)keylen+1)) {
1975  EC_KEY_free(ec);
1976  return NULL;
1977  }
1978  evp_key = EVP_PKEY_new();
1979  if(!evp_key) {
1980  EC_KEY_free(ec);
1981  return NULL;
1982  }
1983  if (!EVP_PKEY_assign_EC_KEY(evp_key, ec)) {
1984  EVP_PKEY_free(evp_key);
1985  EC_KEY_free(ec);
1986  return NULL;
1987  }
1988  return evp_key;
1989 }
1990 
1991 static ldns_status
1992 ldns_verify_rrsig_ecdsa_raw(unsigned char* sig, size_t siglen,
1993  ldns_buffer* rrset, unsigned char* key, size_t keylen, uint8_t algo)
1994 {
1995  EVP_PKEY *evp_key;
1996  ldns_status result;
1997  const EVP_MD *d;
1998 
1999  evp_key = ldns_ecdsa2pkey_raw(key, keylen, algo);
2000  if(!evp_key) {
2001  /* could not convert key */
2002  return LDNS_STATUS_CRYPTO_BOGUS;
2003  }
2004  if(algo == LDNS_ECDSAP256SHA256)
2005  d = EVP_sha256();
2006  else d = EVP_sha384(); /* LDNS_ECDSAP384SHA384 */
2007  result = ldns_verify_rrsig_evp_raw(sig, siglen, rrset, evp_key, d);
2008  EVP_PKEY_free(evp_key);
2009  return result;
2010 }
2011 #endif
2012 
2015  ldns_buffer *key_buf, uint8_t algo)
2016 {
2018  (unsigned char*)ldns_buffer_begin(rawsig_buf),
2019  ldns_buffer_position(rawsig_buf),
2020  verify_buf,
2021  (unsigned char*)ldns_buffer_begin(key_buf),
2022  ldns_buffer_position(key_buf), algo);
2023 }
2024 
2026 ldns_verify_rrsig_buffers_raw(unsigned char* sig, size_t siglen,
2027  ldns_buffer *verify_buf, unsigned char* key, size_t keylen,
2028  uint8_t algo)
2029 {
2030  /* check for right key */
2031  switch(algo) {
2032 #ifdef USE_DSA
2033  case LDNS_DSA:
2034  case LDNS_DSA_NSEC3:
2035  return ldns_verify_rrsig_dsa_raw(sig,
2036  siglen,
2037  verify_buf,
2038  key,
2039  keylen);
2040  break;
2041 #endif
2042  case LDNS_RSASHA1:
2043  case LDNS_RSASHA1_NSEC3:
2044  return ldns_verify_rrsig_rsasha1_raw(sig,
2045  siglen,
2046  verify_buf,
2047  key,
2048  keylen);
2049  break;
2050 #ifdef USE_SHA2
2051  case LDNS_RSASHA256:
2053  siglen,
2054  verify_buf,
2055  key,
2056  keylen);
2057  break;
2058  case LDNS_RSASHA512:
2060  siglen,
2061  verify_buf,
2062  key,
2063  keylen);
2064  break;
2065 #endif
2066 #ifdef USE_GOST
2067  case LDNS_ECC_GOST:
2068  return ldns_verify_rrsig_gost_raw(sig, siglen, verify_buf,
2069  key, keylen);
2070  break;
2071 #endif
2072 #ifdef USE_ECDSA
2073  case LDNS_ECDSAP256SHA256:
2074  case LDNS_ECDSAP384SHA384:
2075  return ldns_verify_rrsig_ecdsa_raw(sig, siglen, verify_buf,
2076  key, keylen, algo);
2077  break;
2078 #endif
2079 #ifdef USE_ED25519
2080  case LDNS_ED25519:
2081  return ldns_verify_rrsig_ed25519_raw(sig, siglen, verify_buf,
2082  key, keylen);
2083  break;
2084 #endif
2085 #ifdef USE_ED448
2086  case LDNS_ED448:
2087  return ldns_verify_rrsig_ed448_raw(sig, siglen, verify_buf,
2088  key, keylen);
2089  break;
2090 #endif
2091  case LDNS_RSAMD5:
2092  return ldns_verify_rrsig_rsamd5_raw(sig,
2093  siglen,
2094  verify_buf,
2095  key,
2096  keylen);
2097  break;
2098  default:
2099  /* do you know this alg?! */
2101  }
2102 }
2103 
2104 
2112 static void
2113 ldns_rrset_use_signature_ttl(ldns_rr_list* rrset_clone, const ldns_rr* rrsig)
2114 {
2115  uint32_t orig_ttl;
2116  uint16_t i;
2117  uint8_t label_count;
2118  ldns_rdf *wildcard_name;
2119  ldns_rdf *wildcard_chopped;
2120  ldns_rdf *wildcard_chopped_tmp;
2121 
2122  if ((rrsig == NULL) || ldns_rr_rd_count(rrsig) < 4) {
2123  return;
2124  }
2125 
2126  orig_ttl = ldns_rdf2native_int32( ldns_rr_rdf(rrsig, 3));
2127  label_count = ldns_rdf2native_int8(ldns_rr_rdf(rrsig, 2));
2128 
2129  for(i = 0; i < ldns_rr_list_rr_count(rrset_clone); i++) {
2130  if (label_count <
2132  ldns_rr_owner(ldns_rr_list_rr(rrset_clone, i)))) {
2133  (void) ldns_str2rdf_dname(&wildcard_name, "*");
2134  wildcard_chopped = ldns_rdf_clone(ldns_rr_owner(
2135  ldns_rr_list_rr(rrset_clone, i)));
2136  while (label_count < ldns_dname_label_count(wildcard_chopped)) {
2137  wildcard_chopped_tmp = ldns_dname_left_chop(
2138  wildcard_chopped);
2139  ldns_rdf_deep_free(wildcard_chopped);
2140  wildcard_chopped = wildcard_chopped_tmp;
2141  }
2142  (void) ldns_dname_cat(wildcard_name, wildcard_chopped);
2143  ldns_rdf_deep_free(wildcard_chopped);
2145  rrset_clone, i)));
2146  ldns_rr_set_owner(ldns_rr_list_rr(rrset_clone, i),
2147  wildcard_name);
2148  }
2149  ldns_rr_set_ttl(ldns_rr_list_rr(rrset_clone, i), orig_ttl);
2150  /* convert to lowercase */
2151  ldns_rr2canonical(ldns_rr_list_rr(rrset_clone, i));
2152  }
2153 }
2154 
2161 static ldns_status
2162 ldns_rrsig2rawsig_buffer(ldns_buffer* rawsig_buf, const ldns_rr* rrsig)
2163 {
2164  uint8_t sig_algo;
2165 
2166  if (rrsig == NULL) {
2168  }
2169  if (ldns_rr_rdf(rrsig, 1) == NULL) {
2171  }
2172  sig_algo = ldns_rdf2native_int8(ldns_rr_rdf(rrsig, 1));
2173  /* check for known and implemented algo's now (otherwise
2174  * the function could return a wrong error
2175  */
2176  /* create a buffer with signature rdata */
2177  /* for some algorithms we need other data than for others... */
2178  /* (the DSA API wants DER encoding for instance) */
2179 
2180  switch(sig_algo) {
2181  case LDNS_RSAMD5:
2182  case LDNS_RSASHA1:
2183  case LDNS_RSASHA1_NSEC3:
2184 #ifdef USE_SHA2
2185  case LDNS_RSASHA256:
2186  case LDNS_RSASHA512:
2187 #endif
2188 #ifdef USE_GOST
2189  case LDNS_ECC_GOST:
2190 #endif
2191  if (ldns_rr_rdf(rrsig, 8) == NULL) {
2193  }
2194  if (ldns_rdf2buffer_wire(rawsig_buf, ldns_rr_rdf(rrsig, 8))
2195  != LDNS_STATUS_OK) {
2196  return LDNS_STATUS_MEM_ERR;
2197  }
2198  break;
2199 #ifdef USE_DSA
2200  case LDNS_DSA:
2201  case LDNS_DSA_NSEC3:
2202  /* EVP takes rfc2459 format, which is a tad longer than dns format */
2203  if (ldns_rr_rdf(rrsig, 8) == NULL) {
2205  }
2207  rawsig_buf, ldns_rr_rdf(rrsig, 8))
2208  != LDNS_STATUS_OK) {
2209  /*
2210  if (ldns_rdf2buffer_wire(rawsig_buf,
2211  ldns_rr_rdf(rrsig, 8)) != LDNS_STATUS_OK) {
2212  */
2213  return LDNS_STATUS_MEM_ERR;
2214  }
2215  break;
2216 #endif
2217 #ifdef USE_ECDSA
2218  case LDNS_ECDSAP256SHA256:
2219  case LDNS_ECDSAP384SHA384:
2220  /* EVP produces an ASN prefix on the signature, which is
2221  * not used in the DNS */
2222  if (ldns_rr_rdf(rrsig, 8) == NULL) {
2224  }
2226  rawsig_buf, ldns_rr_rdf(rrsig, 8))
2227  != LDNS_STATUS_OK) {
2228  return LDNS_STATUS_MEM_ERR;
2229  }
2230  break;
2231 #endif
2232 #ifdef USE_ED25519
2233  case LDNS_ED25519:
2234  /* EVP produces an ASN prefix on the signature, which is
2235  * not used in the DNS */
2236  if (ldns_rr_rdf(rrsig, 8) == NULL) {
2238  }
2240  rawsig_buf, ldns_rr_rdf(rrsig, 8)) != LDNS_STATUS_OK) {
2241  return LDNS_STATUS_MEM_ERR;
2242  }
2243  break;
2244 #endif
2245 #ifdef USE_ED448
2246  case LDNS_ED448:
2247  /* EVP produces an ASN prefix on the signature, which is
2248  * not used in the DNS */
2249  if (ldns_rr_rdf(rrsig, 8) == NULL) {
2251  }
2253  rawsig_buf, ldns_rr_rdf(rrsig, 8)) != LDNS_STATUS_OK) {
2254  return LDNS_STATUS_MEM_ERR;
2255  }
2256  break;
2257 #endif
2258  case LDNS_DH:
2259  case LDNS_ECC:
2260  case LDNS_INDIRECT:
2262  default:
2264  }
2265  return LDNS_STATUS_OK;
2266 }
2267 
2274 static ldns_status
2275 ldns_rrsig_check_timestamps(const ldns_rr* rrsig, time_t now)
2276 {
2277  int32_t inception, expiration;
2278 
2279  /* check the signature time stamps */
2280  inception = (int32_t)ldns_rdf2native_time_t(
2281  ldns_rr_rrsig_inception(rrsig));
2282  expiration = (int32_t)ldns_rdf2native_time_t(
2283  ldns_rr_rrsig_expiration(rrsig));
2284 
2285  if (expiration - inception < 0) {
2286  /* bad sig, expiration before inception?? Tsssg */
2288  }
2289  if (((int32_t) now) - inception < 0) {
2290  /* bad sig, inception date has not yet come to pass */
2292  }
2293  if (expiration - ((int32_t) now) < 0) {
2294  /* bad sig, expiration date has passed */
2296  }
2297  return LDNS_STATUS_OK;
2298 }
2299 
2308 static ldns_status
2309 ldns_prepare_for_verify(ldns_buffer* rawsig_buf, ldns_buffer* verify_buf,
2310  ldns_rr_list* rrset_clone, const ldns_rr* rrsig)
2311 {
2312  ldns_status result;
2313 
2314  /* canonicalize the sig */
2316 
2317  /* check if the typecovered is equal to the type checked */
2319  ldns_rr_get_type(ldns_rr_list_rr(rrset_clone, 0)))
2321 
2322  /* create a buffer with b64 signature rdata */
2323  result = ldns_rrsig2rawsig_buffer(rawsig_buf, rrsig);
2324  if(result != LDNS_STATUS_OK)
2325  return result;
2326 
2327  /* use TTL from signature. Use wildcard names for wildcards */
2328  /* also canonicalizes rrset_clone */
2329  ldns_rrset_use_signature_ttl(rrset_clone, rrsig);
2330 
2331  /* sort the rrset in canonical order */
2332  ldns_rr_list_sort(rrset_clone);
2333 
2334  /* put the signature rr (without the b64) to the verify_buf */
2335  if (ldns_rrsig2buffer_wire(verify_buf, rrsig) != LDNS_STATUS_OK)
2336  return LDNS_STATUS_MEM_ERR;
2337 
2338  /* add the rrset in verify_buf */
2339  if(ldns_rr_list2buffer_wire(verify_buf, rrset_clone)
2340  != LDNS_STATUS_OK)
2341  return LDNS_STATUS_MEM_ERR;
2342 
2343  return LDNS_STATUS_OK;
2344 }
2345 
2355 static ldns_status
2356 ldns_verify_test_sig_key(ldns_buffer* rawsig_buf, ldns_buffer* verify_buf,
2357  const ldns_rr* rrsig, ldns_rr* key)
2358 {
2359  uint8_t sig_algo;
2360 
2361  if (rrsig == NULL) {
2363  }
2364  if (ldns_rr_rdf(rrsig, 1) == NULL) {
2366  }
2367  sig_algo = ldns_rdf2native_int8(ldns_rr_rdf(rrsig, 1));
2368 
2369  /* before anything, check if the keytags match */
2370  if (ldns_calc_keytag(key)
2371  ==
2373  ) {
2375  ldns_status result = LDNS_STATUS_ERR;
2376 
2377  /* put the key-data in a buffer, that's the third rdf, with
2378  * the base64 encoded key data */
2379  if (ldns_rr_rdf(key, 3) == NULL) {
2380  ldns_buffer_free(key_buf);
2382  }
2383  if (ldns_rdf2buffer_wire(key_buf, ldns_rr_rdf(key, 3))
2384  != LDNS_STATUS_OK) {
2385  ldns_buffer_free(key_buf);
2386  /* returning is bad might screw up
2387  good keys later in the list
2388  what to do? */
2389  return LDNS_STATUS_ERR;
2390  }
2391 
2392  if (ldns_rr_rdf(key, 2) == NULL) {
2394  }
2395  else if (sig_algo == ldns_rdf2native_int8(
2396  ldns_rr_rdf(key, 2))) {
2397  result = ldns_verify_rrsig_buffers(rawsig_buf,
2398  verify_buf, key_buf, sig_algo);
2399  } else {
2400  /* No keys with the corresponding algorithm are found */
2402  }
2403 
2404  ldns_buffer_free(key_buf);
2405  return result;
2406  }
2407  else {
2408  /* No keys with the corresponding keytag are found */
2410  }
2411 }
2412 
2413 /*
2414  * to verify:
2415  * - create the wire fmt of the b64 key rdata
2416  * - create the wire fmt of the sorted rrset
2417  * - create the wire fmt of the b64 sig rdata
2418  * - create the wire fmt of the sig without the b64 rdata
2419  * - cat the sig data (without b64 rdata) to the rrset
2420  * - verify the rrset+sig, with the b64 data and the b64 key data
2421  */
2424  const ldns_rr_list *rrset,
2425  const ldns_rr *rrsig,
2426  const ldns_rr_list *keys,
2427  time_t check_time,
2428  ldns_rr_list *good_keys)
2429 {
2430  ldns_status result;
2431  ldns_rr_list *valid = ldns_rr_list_new();
2432  if (!valid)
2433  return LDNS_STATUS_MEM_ERR;
2434 
2435  result = ldns_verify_rrsig_keylist_notime(rrset, rrsig, keys, valid);
2436  if(result != LDNS_STATUS_OK) {
2437  ldns_rr_list_free(valid);
2438  return result;
2439  }
2440 
2441  /* check timestamps last; its OK except time */
2442  result = ldns_rrsig_check_timestamps(rrsig, check_time);
2443  if(result != LDNS_STATUS_OK) {
2444  ldns_rr_list_free(valid);
2445  return result;
2446  }
2447 
2448  ldns_rr_list_cat(good_keys, valid);
2449  ldns_rr_list_free(valid);
2450  return LDNS_STATUS_OK;
2451 }
2452 
2453 /*
2454  * to verify:
2455  * - create the wire fmt of the b64 key rdata
2456  * - create the wire fmt of the sorted rrset
2457  * - create the wire fmt of the b64 sig rdata
2458  * - create the wire fmt of the sig without the b64 rdata
2459  * - cat the sig data (without b64 rdata) to the rrset
2460  * - verify the rrset+sig, with the b64 data and the b64 key data
2461  */
2464  ldns_rr *rrsig,
2465  const ldns_rr_list *keys,
2466  ldns_rr_list *good_keys)
2467 {
2469  rrset, rrsig, keys, ldns_time(NULL), good_keys);
2470 }
2471 
2474  const ldns_rr *rrsig,
2475  const ldns_rr_list *keys,
2476  ldns_rr_list *good_keys)
2477 {
2478  ldns_buffer *rawsig_buf;
2479  ldns_buffer *verify_buf;
2480  uint16_t i;
2481  ldns_status result, status;
2482  ldns_rr_list *rrset_clone;
2483  ldns_rr_list *validkeys;
2484 
2485  if (!rrset) {
2486  return LDNS_STATUS_ERR;
2487  }
2488 
2489  validkeys = ldns_rr_list_new();
2490  if (!validkeys) {
2491  return LDNS_STATUS_MEM_ERR;
2492  }
2493 
2494  /* clone the rrset so that we can fiddle with it */
2495  rrset_clone = ldns_rr_list_clone(rrset);
2496 
2497  /* create the buffers which will certainly hold the raw data */
2498  rawsig_buf = ldns_buffer_new(LDNS_MAX_PACKETLEN);
2499  verify_buf = ldns_buffer_new(LDNS_MAX_PACKETLEN);
2500 
2501  result = ldns_prepare_for_verify(rawsig_buf, verify_buf,
2502  rrset_clone, rrsig);
2503  if(result != LDNS_STATUS_OK) {
2504  ldns_buffer_free(verify_buf);
2505  ldns_buffer_free(rawsig_buf);
2506  ldns_rr_list_deep_free(rrset_clone);
2507  ldns_rr_list_free(validkeys);
2508  return result;
2509  }
2510 
2512  for(i = 0; i < ldns_rr_list_rr_count(keys); i++) {
2513  status = ldns_verify_test_sig_key(rawsig_buf, verify_buf,
2514  rrsig, ldns_rr_list_rr(keys, i));
2515  if (status == LDNS_STATUS_OK) {
2516  /* one of the keys has matched, don't break
2517  * here, instead put the 'winning' key in
2518  * the validkey list and return the list
2519  * later */
2520  if (!ldns_rr_list_push_rr(validkeys,
2521  ldns_rr_list_rr(keys,i))) {
2522  /* couldn't push the key?? */
2523  ldns_buffer_free(rawsig_buf);
2524  ldns_buffer_free(verify_buf);
2525  ldns_rr_list_deep_free(rrset_clone);
2526  ldns_rr_list_free(validkeys);
2527  return LDNS_STATUS_MEM_ERR;
2528  }
2529 
2530  result = status;
2531  }
2532 
2534  result = status;
2535  }
2536  }
2537 
2538  /* no longer needed */
2539  ldns_rr_list_deep_free(rrset_clone);
2540  ldns_buffer_free(rawsig_buf);
2541  ldns_buffer_free(verify_buf);
2542 
2543  if (ldns_rr_list_rr_count(validkeys) == 0) {
2544  /* no keys were added, return last error */
2545  ldns_rr_list_free(validkeys);
2546  return result;
2547  }
2548 
2549  /* do not check timestamps */
2550 
2551  ldns_rr_list_cat(good_keys, validkeys);
2552  ldns_rr_list_free(validkeys);
2553  return LDNS_STATUS_OK;
2554 }
2555 
2558  ldns_rr_list *rrset,
2559  ldns_rr *rrsig,
2560  ldns_rr *key,
2561  time_t check_time)
2562 {
2563  ldns_buffer *rawsig_buf;
2564  ldns_buffer *verify_buf;
2565  ldns_status result;
2566  ldns_rr_list *rrset_clone;
2567 
2568  if (!rrset) {
2569  return LDNS_STATUS_NO_DATA;
2570  }
2571  /* clone the rrset so that we can fiddle with it */
2572  rrset_clone = ldns_rr_list_clone(rrset);
2573  /* create the buffers which will certainly hold the raw data */
2574  rawsig_buf = ldns_buffer_new(LDNS_MAX_PACKETLEN);
2575  verify_buf = ldns_buffer_new(LDNS_MAX_PACKETLEN);
2576 
2577  result = ldns_prepare_for_verify(rawsig_buf, verify_buf,
2578  rrset_clone, rrsig);
2579  if(result != LDNS_STATUS_OK) {
2580  ldns_rr_list_deep_free(rrset_clone);
2581  ldns_buffer_free(rawsig_buf);
2582  ldns_buffer_free(verify_buf);
2583  return result;
2584  }
2585  result = ldns_verify_test_sig_key(rawsig_buf, verify_buf,
2586  rrsig, key);
2587  /* no longer needed */
2588  ldns_rr_list_deep_free(rrset_clone);
2589  ldns_buffer_free(rawsig_buf);
2590  ldns_buffer_free(verify_buf);
2591 
2592  /* check timestamp last, apart from time its OK */
2593  if(result == LDNS_STATUS_OK)
2594  result = ldns_rrsig_check_timestamps(rrsig, check_time);
2595 
2596  return result;
2597 }
2598 
2601 {
2602  return ldns_verify_rrsig_time(rrset, rrsig, key, ldns_time(NULL));
2603 }
2604 
2605 
2608  ldns_buffer *rrset,
2609  EVP_PKEY *key,
2610  const EVP_MD *digest_type)
2611 {
2613  (unsigned char*)ldns_buffer_begin(sig),
2614  ldns_buffer_position(sig),
2615  rrset,
2616  key,
2617  digest_type);
2618 }
2619 
2621 ldns_verify_rrsig_evp_raw(const unsigned char *sig, size_t siglen,
2622  const ldns_buffer *rrset, EVP_PKEY *key, const EVP_MD *digest_type)
2623 {
2624  EVP_MD_CTX *ctx;
2625  int res;
2626 
2627 #ifdef HAVE_EVP_MD_CTX_NEW
2628  ctx = EVP_MD_CTX_new();
2629 #else
2630  ctx = (EVP_MD_CTX*)malloc(sizeof(*ctx));
2631  if(ctx) EVP_MD_CTX_init(ctx);
2632 #endif
2633  if(!ctx)
2634  return LDNS_STATUS_MEM_ERR;
2635 
2636  EVP_VerifyInit(ctx, digest_type);
2637  EVP_VerifyUpdate(ctx,
2638  ldns_buffer_begin(rrset),
2639  ldns_buffer_position(rrset));
2640  res = EVP_VerifyFinal(ctx, sig, (unsigned int) siglen, key);
2641 
2642  EVP_MD_CTX_destroy(ctx);
2643 
2644  if (res == 1) {
2645  return LDNS_STATUS_OK;
2646  } else if (res == 0) {
2647  return LDNS_STATUS_CRYPTO_BOGUS;
2648  }
2649  /* TODO how to communicate internal SSL error?
2650  let caller use ssl's get_error() */
2651  return LDNS_STATUS_SSL_ERR;
2652 }
2653 
2656 {
2658  (unsigned char*) ldns_buffer_begin(sig),
2659  ldns_buffer_position(sig),
2660  rrset,
2661  (unsigned char*) ldns_buffer_begin(key),
2662  ldns_buffer_position(key));
2663 }
2664 
2667 {
2669  (unsigned char*)ldns_buffer_begin(sig),
2670  ldns_buffer_position(sig),
2671  rrset,
2672  (unsigned char*) ldns_buffer_begin(key),
2673  ldns_buffer_position(key));
2674 }
2675 
2678 {
2680  (unsigned char*)ldns_buffer_begin(sig),
2681  ldns_buffer_position(sig),
2682  rrset,
2683  (unsigned char*) ldns_buffer_begin(key),
2684  ldns_buffer_position(key));
2685 }
2686 
2688 ldns_verify_rrsig_dsa_raw(unsigned char* sig, size_t siglen,
2689  ldns_buffer* rrset, unsigned char* key, size_t keylen)
2690 {
2691 #ifdef USE_DSA
2692  EVP_PKEY *evp_key;
2693  ldns_status result;
2694 
2695  evp_key = EVP_PKEY_new();
2696  if (EVP_PKEY_assign_DSA(evp_key, ldns_key_buf2dsa_raw(key, keylen))) {
2697  result = ldns_verify_rrsig_evp_raw(sig,
2698  siglen,
2699  rrset,
2700  evp_key,
2701 # ifdef HAVE_EVP_DSS1
2702  EVP_dss1()
2703 # else
2704  EVP_sha1()
2705 # endif
2706  );
2707  } else {
2708  result = LDNS_STATUS_SSL_ERR;
2709  }
2710  EVP_PKEY_free(evp_key);
2711  return result;
2712 #else
2713  (void)sig; (void)siglen; (void)rrset; (void)key; (void)keylen;
2715 #endif
2716 }
2717 
2719 ldns_verify_rrsig_rsasha1_raw(unsigned char* sig, size_t siglen,
2720  ldns_buffer* rrset, unsigned char* key, size_t keylen)
2721 {
2722  EVP_PKEY *evp_key;
2723  ldns_status result;
2724 
2725  evp_key = EVP_PKEY_new();
2726  if (EVP_PKEY_assign_RSA(evp_key, ldns_key_buf2rsa_raw(key, keylen))) {
2727  result = ldns_verify_rrsig_evp_raw(sig,
2728  siglen,
2729  rrset,
2730  evp_key,
2731  EVP_sha1());
2732  } else {
2733  result = LDNS_STATUS_SSL_ERR;
2734  }
2735  EVP_PKEY_free(evp_key);
2736 
2737  return result;
2738 }
2739 
2742  size_t siglen,
2743  ldns_buffer* rrset,
2744  unsigned char* key,
2745  size_t keylen)
2746 {
2747 #ifdef USE_SHA2
2748  EVP_PKEY *evp_key;
2749  ldns_status result;
2750 
2751  evp_key = EVP_PKEY_new();
2752  if (EVP_PKEY_assign_RSA(evp_key, ldns_key_buf2rsa_raw(key, keylen))) {
2753  result = ldns_verify_rrsig_evp_raw(sig,
2754  siglen,
2755  rrset,
2756  evp_key,
2757  EVP_sha256());
2758  } else {
2759  result = LDNS_STATUS_SSL_ERR;
2760  }
2761  EVP_PKEY_free(evp_key);
2762 
2763  return result;
2764 #else
2765  /* touch these to prevent compiler warnings */
2766  (void) sig;
2767  (void) siglen;
2768  (void) rrset;
2769  (void) key;
2770  (void) keylen;
2772 #endif
2773 }
2774 
2777  size_t siglen,
2778  ldns_buffer* rrset,
2779  unsigned char* key,
2780  size_t keylen)
2781 {
2782 #ifdef USE_SHA2
2783  EVP_PKEY *evp_key;
2784  ldns_status result;
2785 
2786  evp_key = EVP_PKEY_new();
2787  if (EVP_PKEY_assign_RSA(evp_key, ldns_key_buf2rsa_raw(key, keylen))) {
2788  result = ldns_verify_rrsig_evp_raw(sig,
2789  siglen,
2790  rrset,
2791  evp_key,
2792  EVP_sha512());
2793  } else {
2794  result = LDNS_STATUS_SSL_ERR;
2795  }
2796  EVP_PKEY_free(evp_key);
2797 
2798  return result;
2799 #else
2800  /* touch these to prevent compiler warnings */
2801  (void) sig;
2802  (void) siglen;
2803  (void) rrset;
2804  (void) key;
2805  (void) keylen;
2807 #endif
2808 }
2809 
2810 
2812 ldns_verify_rrsig_rsamd5_raw(unsigned char* sig,
2813  size_t siglen,
2814  ldns_buffer* rrset,
2815  unsigned char* key,
2816  size_t keylen)
2817 {
2818  EVP_PKEY *evp_key;
2819  ldns_status result;
2820 
2821  evp_key = EVP_PKEY_new();
2822  if (EVP_PKEY_assign_RSA(evp_key, ldns_key_buf2rsa_raw(key, keylen))) {
2823  result = ldns_verify_rrsig_evp_raw(sig,
2824  siglen,
2825  rrset,
2826  evp_key,
2827  EVP_md5());
2828  } else {
2829  result = LDNS_STATUS_SSL_ERR;
2830  }
2831  EVP_PKEY_free(evp_key);
2832 
2833  return result;
2834 }
2835 
2836 #endif
ldns_rdf * ldns_rr_rdf(const ldns_rr *rr, size_t nr)
returns the rdata field member counter.
Definition: rr.c:895
implementation of buffers to ease operations
Definition: buffer.h:50
ldns_rdf * ldns_rr_rrsig_labels(const ldns_rr *r)
returns the number of labels of a LDNS_RR_TYPE_RRSIG RR
Definition: rr_functions.c:135
bool ldns_nsec_covers_name(const ldns_rr *nsec, const ldns_rdf *name)
Checks coverage of NSEC(3) RR name span Remember that nsec and name must both be in canonical form (i...
Definition: dnssec.c:1499
void ldns_dnssec_derive_trust_tree_normal_rrset_time(ldns_dnssec_trust_tree *new_tree, ldns_dnssec_data_chain *data_chain, ldns_rr *cur_sig_rr, time_t check_time)
Sub function for derive_trust_tree that is used for a &#39;normal&#39; rrset.
ldns_rr * ldns_rr_clone(const ldns_rr *rr)
clones a rr and all its data
Definition: rr.c:1385
void ldns_rdf_deep_free(ldns_rdf *rd)
frees a rdf structure and frees the data.
Definition: rdata.c:230
ldns_dnssec_trust_tree * ldns_dnssec_trust_tree_new(void)
Creates a new (empty) dnssec_trust_tree structure.
uint8_t ldns_dname_label_count(const ldns_rdf *r)
count the number of labels inside a LDNS_RDF_DNAME type rdf.
Definition: dname.c:214
bool ldns_rr_compare_ds(const ldns_rr *orr1, const ldns_rr *orr2)
returns true of the given rr&#39;s are equal.
Definition: rr.c:1695
void ldns_rr2canonical(ldns_rr *rr)
converts each dname in a rr to its canonical form.
Definition: rr.c:1766
the canonical name for an alias
Definition: rr.h:91
RSA * ldns_key_buf2rsa_raw(const unsigned char *key, size_t len)
Like ldns_key_buf2rsa, but uses raw buffer.
Definition: dnssec.c:414
ldns_rr_type ldns_rdf2rr_type(const ldns_rdf *rd)
convert an rdf of type LDNS_RDF_TYPE_TYPE to an actual LDNS_RR_TYPE.
Definition: rr.c:2687
DNSSEC.
Definition: rr.h:173
ldns_status ldns_verify_trusted_time(ldns_resolver *res, ldns_rr_list *rrset, ldns_rr_list *rrsigs, time_t check_time, ldns_rr_list *validating_keys)
Verifies a list of signatures for one RRset using a valid trust path.
ldns_rr_list * ldns_pkt_rr_list_by_name_and_type(const ldns_pkt *packet, const ldns_rdf *ownername, ldns_rr_type type, ldns_pkt_section sec)
return all the rr with a specific type and type from a packet.
Definition: packet.c:326
int ldns_dname_compare(const ldns_rdf *dname1, const ldns_rdf *dname2)
Compares the two dname rdf&#39;s according to the algorithm for ordering in RFC4034 Section 6...
Definition: dname.c:359
ldns_status ldns_verify_rrsig_evp(ldns_buffer *sig, ldns_buffer *rrset, EVP_PKEY *key, const EVP_MD *digest_type)
verifies a buffer with signature data for a buffer with rrset data with an EVP_PKEY ...
bool ldns_dnssec_pkt_has_rrsigs(const ldns_pkt *pkt)
Checks whether the packet contains rrsigs.
Definition: dnssec.c:198
DNS stub resolver structure.
Definition: resolver.h:59
ldns_rdf * ldns_rr_rrsig_inception(const ldns_rr *r)
returns the inception time of a LDNS_RR_TYPE_RRSIG RR
Definition: rr_functions.c:171
enum ldns_enum_rr_class ldns_rr_class
Definition: rr.h:64
bool ldns_rr_list_push_rr(ldns_rr_list *rr_list, const ldns_rr *rr)
pushes an rr to an rrlist.
Definition: rr.c:1118
ldns_pkt * ldns_resolver_query(const ldns_resolver *r, const ldns_rdf *name, ldns_rr_type t, ldns_rr_class c, uint16_t flags)
Send a query to a nameserver.
Definition: resolver.c:1161
List or Set of Resource Records.
Definition: rr.h:330
ldns_status ldns_str2rdf_dname(ldns_rdf **d, const char *str)
convert a dname string into wireformat
Definition: str2host.c:311
ldns_status ldns_convert_ed448_rrsig_rdf2asn1(ldns_buffer *target_buffer, const ldns_rdf *sig_rdf)
Converts the RRSIG signature RDF (from DNS) to a buffer with the signature in ASN1 format as openssl ...
ldns_pkt_rcode ldns_pkt_get_rcode(const ldns_pkt *packet)
Return the packet&#39;s respons code.
Definition: packet.c:93
Output format specifier.
Definition: host2str.h:86
uint8_t ldns_rdf2native_int8(const ldns_rdf *rd)
returns the native uint8_t representation from the rdf.
Definition: rdata.c:70
ldns_status ldns_verify_rrsig_buffers(ldns_buffer *rawsig_buf, ldns_buffer *verify_buf, ldns_buffer *key_buf, uint8_t algo)
Verifies the already processed data in the buffers This function should probably not be used directly...
ldns_status ldns_verify_time(const ldns_rr_list *rrset, const ldns_rr_list *rrsig, const ldns_rr_list *keys, time_t check_time, ldns_rr_list *good_keys)
Verifies a list of signatures for one rrset.
void ldns_dnssec_derive_trust_tree_ds_rrset(ldns_dnssec_trust_tree *new_tree, ldns_dnssec_data_chain *data_chain, ldns_rr *cur_rr)
Sub function for derive_trust_tree that is used for DS rrsets.
#define LDNS_RD
Definition: packet.h:30
void ldns_dnssec_trust_tree_print(FILE *out, ldns_dnssec_trust_tree *tree, size_t tabs, bool extended)
ldns_status ldns_dnssec_verify_denial(ldns_rr *rr, ldns_rr_list *nsecs, ldns_rr_list *rrsigs)
denial is not just a river in egypt
Definition: keys.h:48
ldns_status ldns_rr_list2buffer_wire(ldns_buffer *buffer, const ldns_rr_list *rr_list)
Copies the rr_list data to the buffer in wire format.
Definition: host2wire.c:146
#define LDNS_CALLOC(type, count)
Definition: util.h:53
#define LDNS_XMALLOC(type, count)
Definition: util.h:51
void ldns_dnssec_derive_trust_tree_normal_rrset(ldns_dnssec_trust_tree *new_tree, ldns_dnssec_data_chain *data_chain, ldns_rr *cur_sig_rr)
Sub function for derive_trust_tree that is used for a &#39;normal&#39; rrset.
size_t ldns_rdf_size(const ldns_rdf *rd)
returns the size of the rdf.
Definition: rdata.c:24
ldns_status ldns_convert_dsa_rrsig_rdf2asn1(ldns_buffer *target_buffer, const ldns_rdf *sig_rdf)
Converts the RRSIG signature RDF (in rfc2536 format) to a buffer with the signature in rfc2459 format...
Definition: dnssec.c:1795
void ldns_dnssec_data_chain_deep_free(ldns_dnssec_data_chain *chain)
Frees a dnssec_data_chain structure, and all data contained therein.
Definition: dnssec_verify.c:45
ldns_lookup_table ldns_rcodes[]
Response codes.
Definition: host2str.c:98
ldns_rr_list * ldns_fetch_valid_domain_keys_time(const ldns_resolver *res, const ldns_rdf *domain, const ldns_rr_list *keys, time_t check_time, ldns_status *status)
Tries to build an authentication chain from the given keys down to the queried domain.
void ldns_rr_list_deep_free(ldns_rr_list *rr_list)
frees an rr_list structure and all rrs contained therein.
Definition: rr.c:1006
void ldns_buffer_free(ldns_buffer *buffer)
frees the buffer.
Definition: buffer.c:137
ldns_rr_list * ldns_validate_domain_ds(const ldns_resolver *res, const ldns_rdf *domain, const ldns_rr_list *keys)
Validates the DS RRset for the given domain using the provided trusted keys.
ldns_status ldns_verify_rrsig_rsasha1_raw(unsigned char *sig, size_t siglen, ldns_buffer *rrset, unsigned char *key, size_t keylen)
Like ldns_verify_rrsig_rsasha1, but uses raw signature and key data.
void ldns_dnssec_derive_trust_tree_ds_rrset_time(ldns_dnssec_trust_tree *new_tree, ldns_dnssec_data_chain *data_chain, ldns_rr *cur_rr, time_t check_time)
Sub function for derive_trust_tree that is used for DS rrsets.
ldns_rdf * ldns_dnssec_nsec3_closest_encloser(const ldns_rdf *qname, ldns_rr_type qtype __attribute__((unused)), const ldns_rr_list *nsec3s)
Definition: dnssec.c:97
ldns_rdf * ldns_rdf_clone(const ldns_rdf *rd)
clones a rdf structure.
Definition: rdata.c:222
ldns_dnssec_trust_tree * ldns_dnssec_derive_trust_tree_time(ldns_dnssec_data_chain *data_chain, ldns_rr *rr, time_t check_time)
Generates a dnssec_trust_tree for the given rr from the given data_chain.
void ldns_dname2canonical(const ldns_rdf *rd)
Put a dname into canonical fmt - ie.
Definition: dname.c:280
ldns_status ldns_convert_ed25519_rrsig_rdf2asn1(ldns_buffer *target_buffer, const ldns_rdf *sig_rdf)
Converts the RRSIG signature RDF (from DNS) to a buffer with the signature in ASN1 format as openssl ...
ldns_rr * parent_signature[10]
for debugging, add signatures too (you might want those if they contain errors)
ldns_status ldns_verify_rrsig_rsasha256_raw(unsigned char *sig, size_t siglen, ldns_buffer *rrset, unsigned char *key, size_t keylen)
Like ldns_verify_rrsig_rsasha256, but uses raw signature and key data.
ldns_rdf * ldns_rr_rrsig_keytag(const ldns_rr *r)
returns the keytag of a LDNS_RR_TYPE_RRSIG RR
Definition: rr_functions.c:183
size_t ldns_rr_rd_count(const ldns_rr *rr)
returns the rd_count of an rr structure.
Definition: rr.c:923
EVP_PKEY * ldns_ed4482pkey_raw(const unsigned char *key, size_t keylen)
Converts a holding buffer with key material to EVP PKEY in openssl.
#define LDNS_MAX_PACKETLEN
Definition: packet.h:24
ldns_status ldns_verify_notime(ldns_rr_list *rrset, ldns_rr_list *rrsig, const ldns_rr_list *keys, ldns_rr_list *good_keys)
Verifies a list of signatures for one rrset, but disregard the time.
ldns_status ldns_verify_rrsig_keylist_notime(const ldns_rr_list *rrset, const ldns_rr *rrsig, const ldns_rr_list *keys, ldns_rr_list *good_keys)
Verifies an rrsig.
ldns_rdf * ldns_dname_left_chop(const ldns_rdf *d)
chop one label off the left side of a dname.
Definition: dname.c:189
ldns_rr_list * ldns_resolver_dnssec_anchors(const ldns_resolver *r)
Get the resolver&#39;s DNSSEC anchors.
Definition: resolver.c:132
DSA * ldns_key_buf2dsa_raw(const unsigned char *key, size_t len)
Like ldns_key_buf2dsa, but uses raw buffer.
Definition: dnssec.c:337
void ldns_rr_list_free(ldns_rr_list *rr_list)
frees an rr_list structure.
Definition: rr.c:997
ldns_rr_list * ldns_pkt_rr_list_by_type(const ldns_pkt *packet, ldns_rr_type type, ldns_pkt_section sec)
return all the rr with a specific type from a packet.
Definition: packet.c:290
const ldns_rr_descriptor * ldns_rr_descript(uint16_t type)
returns the resource record descriptor for the given rr type.
Definition: rr.c:2569
void ldns_dnssec_derive_trust_tree_no_sig(ldns_dnssec_trust_tree *new_tree, ldns_dnssec_data_chain *data_chain)
Sub function for derive_trust_tree that is used when there are no signatures.
const ldns_output_format * ldns_output_format_default
The default output format record.
Definition: host2str.c:131
Resource Record.
Definition: rr.h:302
ldns_rr_list * ldns_validate_domain_dnskey_time(const ldns_resolver *res, const ldns_rdf *domain, const ldns_rr_list *keys, time_t check_time)
Validates the DNSKEY RRset for the given domain using the provided trusted keys.
ldns_status ldns_rdf2buffer_wire(ldns_buffer *buffer, const ldns_rdf *rdf)
Copies the rdata data to the buffer in wire format.
Definition: host2wire.c:99
ldns_rr_list * ldns_fetch_valid_domain_keys(const ldns_resolver *res, const ldns_rdf *domain, const ldns_rr_list *keys, ldns_status *status)
Tries to build an authentication chain from the given keys down to the queried domain.
ldns_rdf * ldns_nsec_get_bitmap(const ldns_rr *nsec)
Returns the rdata field that contains the bitmap of the covered types of the given NSEC record...
Definition: dnssec.c:84
ldns_status ldns_verify_rrsig_buffers_raw(unsigned char *sig, size_t siglen, ldns_buffer *verify_buf, unsigned char *key, size_t keylen, uint8_t algo)
Like ldns_verify_rrsig_buffers, but uses raw data.
Including this file will include all ldns files, and define some lookup tables.
ldns_rdf * ldns_dname_new_frm_str(const char *str)
creates a new dname rdf from a string.
Definition: dname.c:268
ldns_status ldns_verify_rrsig_time(ldns_rr_list *rrset, ldns_rr *rrsig, ldns_rr *key, time_t check_time)
verify an rrsig with 1 key
ldns_rr_list * ldns_dnssec_pkt_get_rrsigs_for_type(const ldns_pkt *pkt, ldns_rr_type type)
Returns a ldns_rr_list containing the signatures covering the given type.
Definition: dnssec.c:244
bool ldns_rr_list_cat(ldns_rr_list *left, const ldns_rr_list *right)
concatenates two ldns_rr_lists together.
Definition: rr.c:1022
ldns_rdf * ldns_dname_clone_from(const ldns_rdf *d, uint16_t n)
Clones the given dname from the nth label on.
Definition: dname.c:160
ldns_rr * ldns_rr_list_rr(const ldns_rr_list *rr_list, size_t nr)
returns a specific rr of an rrlist.
Definition: rr.c:976
int ldns_key_EVP_load_gost_id(void)
Get the PKEY id for GOST, loads GOST into openssl as a side effect.
Definition: keys.c:132
void ldns_rr_print_fmt(FILE *output, const ldns_output_format *fmt, const ldns_rr *rr)
Prints the data in the resource record to the given file stream (in presentation format) ...
Definition: host2str.c:2418
ldns_rr_list * ldns_validate_domain_dnskey(const ldns_resolver *res, const ldns_rdf *domain, const ldns_rr_list *keys)
Validates the DNSKEY RRset for the given domain using the provided trusted keys.
ldns_status ldns_dnssec_trust_tree_contains_keys(ldns_dnssec_trust_tree *tree, ldns_rr_list *trusted_keys)
Returns OK if there is a trusted path in the tree to one of the DNSKEY or DS RRs in the given list...
ldns_dnssec_data_chain * parent
Definition: dnssec_verify.h:25
ldns_status ldns_verify_rrsig_keylist_time(const ldns_rr_list *rrset, const ldns_rr *rrsig, const ldns_rr_list *keys, time_t check_time, ldns_rr_list *good_keys)
Verifies an rrsig.
EVP_PKEY * ldns_ecdsa2pkey_raw(const unsigned char *key, size_t keylen, uint8_t algo)
Converts a holding buffer with key material to EVP PKEY in openssl.
void ldns_dnssec_data_chain_print_fmt(FILE *out, const ldns_output_format *fmt, const ldns_dnssec_data_chain *chain)
Prints the dnssec_data_chain to the given file stream.
Definition: dnssec_verify.c:56
#define ATTR_UNUSED(x)
Definition: common.h:69
uint16_t ldns_pkt_ancount(const ldns_pkt *packet)
Return the packet&#39;s an count.
Definition: packet.c:105
ldns_dnssec_trust_tree * ldns_dnssec_derive_trust_tree(ldns_dnssec_data_chain *data_chain, ldns_rr *rr)
Generates a dnssec_trust_tree for the given rr from the given data_chain.
uint16_t ldns_rdf2native_int16(const ldns_rdf *rd)
returns the native uint16_t representation from the rdf.
Definition: rdata.c:84
time_t ldns_rdf2native_time_t(const ldns_rdf *rd)
returns the native time_t representation from the rdf.
Definition: rdata.c:112
size_t ldns_dnssec_trust_tree_depth(ldns_dnssec_trust_tree *tree)
returns the depth of the trust tree
void ldns_dnssec_data_chain_free(ldns_dnssec_data_chain *chain)
Frees a dnssec_data_chain structure.
Definition: dnssec_verify.c:39
ldns_rr_list * ldns_rr_list_new(void)
creates a new rr_list structure.
Definition: rr.c:986
void ldns_dnssec_trust_tree_free(ldns_dnssec_trust_tree *tree)
Frees the dnssec_trust_tree recursively.
ldns_lookup_table * ldns_lookup_by_id(ldns_lookup_table *table, int id)
Definition: util.c:41
ldns_status ldns_verify_rrsig_rsasha512_raw(unsigned char *sig, size_t siglen, ldns_buffer *rrset, unsigned char *key, size_t keylen)
Like ldns_verify_rrsig_rsasha512, but uses raw signature and key data.
the Internet
Definition: rr.h:50
ldns_rr_list * ldns_validate_domain_ds_time(const ldns_resolver *res, const ldns_rdf *domain, const ldns_rr_list *keys, time_t check_time)
Validates the DS RRset for the given domain using the provided trusted keys.
bool ldns_nsec3_optout(const ldns_rr *nsec3_rr)
Returns true if the opt-out flag has been set in the given NSEC3 RR.
Definition: dnssec.c:1279
uint16_t ldns_calc_keytag(const ldns_rr *key)
calculates a keytag of a key for use in DNSSEC.
Definition: dnssec.c:271
enum ldns_enum_pkt_rcode ldns_pkt_rcode
Definition: packet.h:68
Contains all information about resource record types.
Definition: rr.h:343
void ldns_dnssec_data_chain_print(FILE *out, const ldns_dnssec_data_chain *chain)
Prints the dnssec_data_chain to the given file stream.
Definition: dnssec_verify.c:91
RFC4034, RFC3658.
Definition: rr.h:167
ldns_status ldns_dnssec_verify_denial_nsec3_match(ldns_rr *rr, ldns_rr_list *nsecs, ldns_rr_list *rrsigs __attribute__((unused)), ldns_pkt_rcode packet_rcode, ldns_rr_type packet_qtype, bool packet_nodata, ldns_rr **match)
ldns_status ldns_verify_rrsig_keylist(ldns_rr_list *rrset, ldns_rr *rrsig, const ldns_rr_list *keys, ldns_rr_list *good_keys)
Verifies an rrsig.
EVP_PKEY * ldns_gost2pkey_raw(const unsigned char *key, size_t keylen)
Converts a holding buffer with key material to EVP PKEY in openssl.
ldns_rr_list * ldns_rr_list_clone(const ldns_rr_list *rrlist)
clones an rrlist.
Definition: rr.c:1416
bool ldns_nsec_bitmap_covers_type(const ldns_rdf *bitmap, ldns_rr_type type)
Check if RR type t is enumerated and set in the RR type bitmap rdf.
Definition: dnssec.c:1384
ldns_rdf * ldns_nsec3_bitmap(const ldns_rr *nsec3_rr)
Returns the bitmap specifying the covered types of the given NSEC3 RR.
Definition: dnssec.c:1349
ldns_dnssec_trust_tree * parents[10]
DNS packet.
Definition: packet.h:233
void ldns_rr_set_owner(ldns_rr *rr, ldns_rdf *owner)
sets the owner in the rr structure.
Definition: rr.c:790
void ldns_rdf_print(FILE *output, const ldns_rdf *rdf)
Prints the data in the rdata field to the given file stream (in presentation format) ...
Definition: host2str.c:2406
uint32_t ldns_rdf2native_int32(const ldns_rdf *rd)
returns the native uint32_t representation from the rdf.
Definition: rdata.c:98
ldns_rr_type ldns_rr_get_type(const ldns_rr *rr)
returns the type of the rr.
Definition: rr.c:929
ldns_rr * ldns_dnssec_get_rrsig_for_name_and_type(const ldns_rdf *name, const ldns_rr_type type, const ldns_rr_list *rrs)
Returns the first RRSIG rr that corresponds to the rrset with the given name and type.
Definition: dnssec.c:29
ldns_rdf * ldns_rr_rrsig_typecovered(const ldns_rr *r)
returns the type covered of a LDNS_RR_TYPE_RRSIG rr
Definition: rr_functions.c:111
ldns_dnssec_data_chain * ldns_dnssec_build_data_chain(ldns_resolver *res, uint16_t qflags, const ldns_rr_list *rrset, const ldns_pkt *pkt, ldns_rr *orig_rr)
Build an ldns_dnssec_data_chain, which contains all DNSSEC data that is needed to derive the trust tr...
ldns_rr_list * ldns_rr_list_pop_rrset(ldns_rr_list *rr_list)
pops the first rrset from the list, the list must be sorted, so that all rr&#39;s from each rrset are nex...
Definition: rr.c:1333
const char * name
Definition: util.h:158
void ldns_rr_set_ttl(ldns_rr *rr, uint32_t ttl)
sets the ttl in the rr structure.
Definition: rr.c:802
enum ldns_enum_status ldns_status
Definition: error.h:134
ldns_dnssec_data_chain * ldns_dnssec_data_chain_new(void)
Creates a new dnssec_chain structure.
Definition: dnssec_verify.c:19
ldns_buffer * ldns_buffer_new(size_t capacity)
creates a new buffer with the specified capacity.
Definition: buffer.c:16
Definition: keys.h:47
A general purpose lookup table.
Definition: util.h:156
ldns_status ldns_verify_rrsig_dsa_raw(unsigned char *sig, size_t siglen, ldns_buffer *rrset, unsigned char *key, size_t keylen)
Like ldns_verify_rrsig_dsa, but uses raw signature and key data.
#define LDNS_DNSSEC_TRUST_TREE_MAX_PARENTS
dnssec_verify
Definition: dnssec_verify.h:6
ldns_rdf * ldns_rr_rrsig_signame(const ldns_rr *r)
returns the signers name of a LDNS_RR_TYPE_RRSIG RR
Definition: rr_functions.c:195
void ldns_dnssec_trust_tree_print_fmt(FILE *out, const ldns_output_format *fmt, ldns_dnssec_trust_tree *tree, size_t tabs, bool extended)
EVP_PKEY * ldns_ed255192pkey_raw(const unsigned char *key, size_t keylen)
Converts a holding buffer with key material to EVP PKEY in openssl.
ldns_status ldns_dnssec_trust_tree_add_parent(ldns_dnssec_trust_tree *tree, const ldns_dnssec_trust_tree *parent, const ldns_rr *signature, const ldns_status parent_status)
Adds a trust tree as a parent for the given trust tree.
ldns_status ldns_verify_rrsig_rsasha1(ldns_buffer *sig, ldns_buffer *rrset, ldns_buffer *key)
verifies a buffer with signature data (RSASHA1) for a buffer with rrset data with a buffer with key d...
Resource record data field.
Definition: rdata.h:174
ldns_status ldns_verify_trusted(ldns_resolver *res, ldns_rr_list *rrset, ldns_rr_list *rrsigs, ldns_rr_list *validating_keys)
Verifies a list of signatures for one RRset using a valid trust path.
ldns_rdf * ldns_rr_owner(const ldns_rr *rr)
returns the owner name of an rr structure.
Definition: rr.c:905
void ldns_dnssec_derive_trust_tree_dnskey_rrset_time(ldns_dnssec_trust_tree *new_tree, ldns_dnssec_data_chain *data_chain, ldns_rr *cur_rr, ldns_rr *cur_sig_rr, time_t check_time)
Sub function for derive_trust_tree that is used for DNSKEY rrsets.
ldns_status ldns_verify_rrsig_rsamd5(ldns_buffer *sig, ldns_buffer *rrset, ldns_buffer *key)
verifies a buffer with signature data (RSAMD5) for a buffer with rrset data with a buffer with key da...
size_t ldns_rr_list_rr_count(const ldns_rr_list *rr_list)
returns the number of rr&#39;s in an rr_list.
Definition: rr.c:943
enum ldns_enum_rr_type ldns_rr_type
Definition: rr.h:239
const char * _name
Textual name of the RR type.
Definition: rr.h:348
#define LDNS_FREE(ptr)
Definition: util.h:60
ldns_status ldns_convert_ecdsa_rrsig_rdf2asn1(ldns_buffer *target_buffer, const ldns_rdf *sig_rdf)
Converts the RRSIG signature RDF (from DNS) to a buffer with the signature in ASN1 format as openssl ...
Definition: dnssec.c:1895
an authoritative name server
Definition: rr.h:85
ldns_status ldns_rrsig2buffer_wire(ldns_buffer *buffer, const ldns_rr *rr)
Converts a rrsig to wireformat BUT EXCLUDE the rrsig rdata This is needed in DNSSEC verification...
Definition: host2wire.c:284
const char * ldns_get_errorstr_by_id(ldns_status err)
look up a descriptive text by each error.
Definition: error.c:164
ldns_rr_class ldns_rr_get_class(const ldns_rr *rr)
returns the class of the rr.
Definition: rr.c:935
Definition: keys.h:49
used to get all non-question rrs from a packet
Definition: packet.h:282
ldns_status ldns_verify_rrsig(ldns_rr_list *rrset, ldns_rr *rrsig, ldns_rr *key)
verify an rrsig with 1 key
ldns_status ldns_dnssec_verify_denial_nsec3(ldns_rr *rr, ldns_rr_list *nsecs, ldns_rr_list *rrsigs, ldns_pkt_rcode packet_rcode, ldns_rr_type packet_qtype, bool packet_nodata)
#define HAVE_EVP_DSS1
Definition: config.h:87
ldns_status ldns_dname_cat(ldns_rdf *rd1, const ldns_rdf *rd2)
concatenates rd2 after rd1 (rd2 is copied, rd1 is modified)
Definition: dname.c:90
ldns_status ldns_verify_rrsig_evp_raw(const unsigned char *sig, size_t siglen, const ldns_buffer *rrset, EVP_PKEY *key, const EVP_MD *digest_type)
Like ldns_verify_rrsig_evp, but uses raw signature data.
void ldns_pkt_free(ldns_pkt *packet)
frees the packet structure and all data that it contains.
Definition: packet.c:792
void ldns_rr_list_sort(ldns_rr_list *unsorted)
sorts an rr_list (canonical wire format).
Definition: rr.c:1501
void ldns_dnssec_derive_trust_tree_no_sig_time(ldns_dnssec_trust_tree *new_tree, ldns_dnssec_data_chain *data_chain, time_t check_time)
Sub function for derive_trust_tree that is used when there are no signatures.
ldns_status ldns_verify_rrsig_rsamd5_raw(unsigned char *sig, size_t siglen, ldns_buffer *rrset, unsigned char *key, size_t keylen)
Like ldns_verify_rrsig_rsamd5, but uses raw signature and key data.
void ldns_dnssec_derive_trust_tree_dnskey_rrset(ldns_dnssec_trust_tree *new_tree, ldns_dnssec_data_chain *data_chain, ldns_rr *cur_rr, ldns_rr *cur_sig_rr)
Sub function for derive_trust_tree that is used for DNSKEY rrsets.
ldns_status ldns_verify_rrsig_dsa(ldns_buffer *sig, ldns_buffer *rrset, ldns_buffer *key)
verifies a buffer with signature data (DSA) for a buffer with rrset data with a buffer with key data...
ldns_rdf * ldns_nsec3_hash_name_frm_nsec3(const ldns_rr *nsec, const ldns_rdf *name)
Calculates the hashed name using the parameters of the given NSEC3 RR.
Definition: dnssec.c:1359
ldns_rr_list * ldns_dnssec_pkt_get_rrsigs_for_name_and_type(const ldns_pkt *pkt, const ldns_rdf *name, ldns_rr_type type)
Returns a ldns_rr_list containing the signatures covering the given name and type.
Definition: dnssec.c:217
ldns_status ldns_verify(ldns_rr_list *rrset, ldns_rr_list *rrsig, const ldns_rr_list *keys, ldns_rr_list *good_keys)
Verifies a list of signatures for one rrset.
ldns_rdf * ldns_rr_rrsig_expiration(const ldns_rr *r)
returns the expiration time of a LDNS_RR_TYPE_RRSIG RR
Definition: rr_functions.c:159
void ldns_rr_list_print_fmt(FILE *output, const ldns_output_format *fmt, const ldns_rr_list *lst)
print a rr_list to output
Definition: host2str.c:2456