1 /*
2 * packet.c
3 *
4 * dns packet implementation
5 *
6 * a Net::DNS like library for C
7 *
8 * (c) NLnet Labs, 2004-2006
9 *
10 * See the file LICENSE for the license
11 */
12
13 #include <ldns/config.h>
14
15 #include <ldns/ldns.h>
16 #include <ldns/internal.h>
17
18 #include <strings.h>
19 #include <limits.h>
20
21 #ifdef HAVE_SSL
22 #include <openssl/rand.h>
23 #endif
24
25 /* Access functions
26 * do this as functions to get type checking
27 */
28
29 #define LDNS_EDNS_MASK_DO_BIT 0x8000
30 #define LDNS_EDNS_MASK_UNASSIGNED (0xFFFF & ~LDNS_EDNS_MASK_DO_BIT)
31
32 /* TODO defines for 3600 */
33 /* convert to and from numerical flag values */
34 ldns_lookup_table ldns_edns_flags[] = {
35 { 3600, "do"},
36 { 0, NULL}
37 };
38
39 /* read */
40 uint16_t
ldns_pkt_id(const ldns_pkt * packet)41 ldns_pkt_id(const ldns_pkt *packet)
42 {
43 return packet->_header->_id;
44 }
45
46 bool
ldns_pkt_qr(const ldns_pkt * packet)47 ldns_pkt_qr(const ldns_pkt *packet)
48 {
49 return packet->_header->_qr;
50 }
51
52 bool
ldns_pkt_aa(const ldns_pkt * packet)53 ldns_pkt_aa(const ldns_pkt *packet)
54 {
55 return packet->_header->_aa;
56 }
57
58 bool
ldns_pkt_tc(const ldns_pkt * packet)59 ldns_pkt_tc(const ldns_pkt *packet)
60 {
61 return packet->_header->_tc;
62 }
63
64 bool
ldns_pkt_rd(const ldns_pkt * packet)65 ldns_pkt_rd(const ldns_pkt *packet)
66 {
67 return packet->_header->_rd;
68 }
69
70 bool
ldns_pkt_cd(const ldns_pkt * packet)71 ldns_pkt_cd(const ldns_pkt *packet)
72 {
73 return packet->_header->_cd;
74 }
75
76 bool
ldns_pkt_ra(const ldns_pkt * packet)77 ldns_pkt_ra(const ldns_pkt *packet)
78 {
79 return packet->_header->_ra;
80 }
81
82 bool
ldns_pkt_ad(const ldns_pkt * packet)83 ldns_pkt_ad(const ldns_pkt *packet)
84 {
85 return packet->_header->_ad;
86 }
87
88 ldns_pkt_opcode
ldns_pkt_get_opcode(const ldns_pkt * packet)89 ldns_pkt_get_opcode(const ldns_pkt *packet)
90 {
91 return packet->_header->_opcode;
92 }
93
94 ldns_pkt_rcode
ldns_pkt_get_rcode(const ldns_pkt * packet)95 ldns_pkt_get_rcode(const ldns_pkt *packet)
96 {
97 return packet->_header->_rcode;
98 }
99
100 uint16_t
ldns_pkt_qdcount(const ldns_pkt * packet)101 ldns_pkt_qdcount(const ldns_pkt *packet)
102 {
103 return packet->_header->_qdcount;
104 }
105
106 uint16_t
ldns_pkt_ancount(const ldns_pkt * packet)107 ldns_pkt_ancount(const ldns_pkt *packet)
108 {
109 return packet->_header->_ancount;
110 }
111
112 uint16_t
ldns_pkt_nscount(const ldns_pkt * packet)113 ldns_pkt_nscount(const ldns_pkt *packet)
114 {
115 return packet->_header->_nscount;
116 }
117
118 uint16_t
ldns_pkt_arcount(const ldns_pkt * packet)119 ldns_pkt_arcount(const ldns_pkt *packet)
120 {
121 return packet->_header->_arcount;
122 }
123
124 ldns_rr_list *
ldns_pkt_question(const ldns_pkt * packet)125 ldns_pkt_question(const ldns_pkt *packet)
126 {
127 return packet->_question;
128 }
129
130 ldns_rr_list *
ldns_pkt_answer(const ldns_pkt * packet)131 ldns_pkt_answer(const ldns_pkt *packet)
132 {
133 return packet->_answer;
134 }
135
136 ldns_rr_list *
ldns_pkt_authority(const ldns_pkt * packet)137 ldns_pkt_authority(const ldns_pkt *packet)
138 {
139 return packet->_authority;
140 }
141
142 ldns_rr_list *
ldns_pkt_additional(const ldns_pkt * packet)143 ldns_pkt_additional(const ldns_pkt *packet)
144 {
145 return packet->_additional;
146 }
147
148 /* return ALL section concatenated */
149 ldns_rr_list *
ldns_pkt_all(const ldns_pkt * packet)150 ldns_pkt_all(const ldns_pkt *packet)
151 {
152 ldns_rr_list *all, *prev_all;
153
154 all = ldns_rr_list_cat_clone(
155 ldns_pkt_question(packet),
156 ldns_pkt_answer(packet));
157 prev_all = all;
158 all = ldns_rr_list_cat_clone(all,
159 ldns_pkt_authority(packet));
160 ldns_rr_list_deep_free(prev_all);
161 prev_all = all;
162 all = ldns_rr_list_cat_clone(all,
163 ldns_pkt_additional(packet));
164 ldns_rr_list_deep_free(prev_all);
165 return all;
166 }
167
168 ldns_rr_list *
ldns_pkt_all_noquestion(const ldns_pkt * packet)169 ldns_pkt_all_noquestion(const ldns_pkt *packet)
170 {
171 ldns_rr_list *all, *all2;
172
173 all = ldns_rr_list_cat_clone(
174 ldns_pkt_answer(packet),
175 ldns_pkt_authority(packet));
176 all2 = ldns_rr_list_cat_clone(all,
177 ldns_pkt_additional(packet));
178
179 ldns_rr_list_deep_free(all);
180 return all2;
181 }
182
183 size_t
ldns_pkt_size(const ldns_pkt * packet)184 ldns_pkt_size(const ldns_pkt *packet)
185 {
186 return packet->_size;
187 }
188
189 uint32_t
ldns_pkt_querytime(const ldns_pkt * packet)190 ldns_pkt_querytime(const ldns_pkt *packet)
191 {
192 return packet->_querytime;
193 }
194
195 ldns_rdf *
ldns_pkt_answerfrom(const ldns_pkt * packet)196 ldns_pkt_answerfrom(const ldns_pkt *packet)
197 {
198 return packet->_answerfrom;
199 }
200
201 struct timeval
ldns_pkt_timestamp(const ldns_pkt * packet)202 ldns_pkt_timestamp(const ldns_pkt *packet)
203 {
204 return packet->timestamp;
205 }
206
207 uint16_t
ldns_pkt_edns_udp_size(const ldns_pkt * packet)208 ldns_pkt_edns_udp_size(const ldns_pkt *packet)
209 {
210 return packet->_edns_udp_size;
211 }
212
213 uint8_t
ldns_pkt_edns_extended_rcode(const ldns_pkt * packet)214 ldns_pkt_edns_extended_rcode(const ldns_pkt *packet)
215 {
216 return packet->_edns_extended_rcode;
217 }
218
219 uint8_t
ldns_pkt_edns_version(const ldns_pkt * packet)220 ldns_pkt_edns_version(const ldns_pkt *packet)
221 {
222 return packet->_edns_version;
223 }
224
225 uint16_t
ldns_pkt_edns_z(const ldns_pkt * packet)226 ldns_pkt_edns_z(const ldns_pkt *packet)
227 {
228 return packet->_edns_z;
229 }
230
231 bool
ldns_pkt_edns_do(const ldns_pkt * packet)232 ldns_pkt_edns_do(const ldns_pkt *packet)
233 {
234 return (packet->_edns_z & LDNS_EDNS_MASK_DO_BIT);
235 }
236
237 void
ldns_pkt_set_edns_do(ldns_pkt * packet,bool value)238 ldns_pkt_set_edns_do(ldns_pkt *packet, bool value)
239 {
240 if (value) {
241 packet->_edns_z = packet->_edns_z | LDNS_EDNS_MASK_DO_BIT;
242 } else {
243 packet->_edns_z = packet->_edns_z & ~LDNS_EDNS_MASK_DO_BIT;
244 }
245 }
246
247 uint16_t
ldns_pkt_edns_unassigned(const ldns_pkt * packet)248 ldns_pkt_edns_unassigned(const ldns_pkt *packet)
249 {
250 return (packet->_edns_z & LDNS_EDNS_MASK_UNASSIGNED);
251 }
252
253 void
ldns_pkt_set_edns_unassigned(ldns_pkt * packet,uint16_t value)254 ldns_pkt_set_edns_unassigned(ldns_pkt *packet, uint16_t value)
255 {
256 packet->_edns_z = (packet->_edns_z & ~LDNS_EDNS_MASK_UNASSIGNED)
257 | (value & LDNS_EDNS_MASK_UNASSIGNED);
258 }
259
260 ldns_rdf *
ldns_pkt_edns_data(const ldns_pkt * packet)261 ldns_pkt_edns_data(const ldns_pkt *packet)
262 {
263 return packet->_edns_data;
264 }
265
266 /* return only those rr that share the ownername */
267 ldns_rr_list *
ldns_pkt_rr_list_by_name(const ldns_pkt * packet,const ldns_rdf * ownername,ldns_pkt_section sec)268 ldns_pkt_rr_list_by_name(const ldns_pkt *packet,
269 const ldns_rdf *ownername,
270 ldns_pkt_section sec)
271 {
272 ldns_rr_list *rrs;
273 ldns_rr_list *ret;
274 uint16_t i;
275
276 if (!packet) {
277 return NULL;
278 }
279
280 rrs = ldns_pkt_get_section_clone(packet, sec);
281 ret = NULL;
282
283 for(i = 0; i < ldns_rr_list_rr_count(rrs); i++) {
284 if (ldns_dname_compare(ldns_rr_owner(
285 ldns_rr_list_rr(rrs, i)),
286 ownername) == 0) {
287 /* owner names match */
288 if (ret == NULL) {
289 ret = ldns_rr_list_new();
290 }
291 ldns_rr_list_push_rr(ret,
292 ldns_rr_clone(
293 ldns_rr_list_rr(rrs, i))
294 );
295 }
296 }
297
298 ldns_rr_list_deep_free(rrs);
299
300 return ret;
301 }
302
303 /* return only those rr that share a type */
304 ldns_rr_list *
ldns_pkt_rr_list_by_type(const ldns_pkt * packet,ldns_rr_type type,ldns_pkt_section sec)305 ldns_pkt_rr_list_by_type(const ldns_pkt *packet,
306 ldns_rr_type type,
307 ldns_pkt_section sec)
308 {
309 ldns_rr_list *rrs;
310 ldns_rr_list *new;
311 uint16_t i;
312
313 if(!packet) {
314 return NULL;
315 }
316
317 rrs = ldns_pkt_get_section_clone(packet, sec);
318 new = ldns_rr_list_new();
319
320 for(i = 0; i < ldns_rr_list_rr_count(rrs); i++) {
321 if (type == ldns_rr_get_type(ldns_rr_list_rr(rrs, i))) {
322 /* types match */
323 ldns_rr_list_push_rr(new,
324 ldns_rr_clone(
325 ldns_rr_list_rr(rrs, i))
326 );
327 }
328 }
329 ldns_rr_list_deep_free(rrs);
330
331 if (ldns_rr_list_rr_count(new) == 0) {
332 ldns_rr_list_free(new);
333 return NULL;
334 } else {
335 return new;
336 }
337 }
338
339 /* return only those rrs that share name and type */
340 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)341 ldns_pkt_rr_list_by_name_and_type(const ldns_pkt *packet,
342 const ldns_rdf *ownername,
343 ldns_rr_type type,
344 ldns_pkt_section sec)
345 {
346 ldns_rr_list *rrs;
347 ldns_rr_list *new;
348 ldns_rr_list *ret;
349 uint16_t i;
350
351 if(!packet) {
352 return NULL;
353 }
354
355 rrs = ldns_pkt_get_section_clone(packet, sec);
356 new = ldns_rr_list_new();
357 ret = NULL;
358
359 for(i = 0; i < ldns_rr_list_rr_count(rrs); i++) {
360 if (type == ldns_rr_get_type(ldns_rr_list_rr(rrs, i)) &&
361 ldns_dname_compare(ldns_rr_owner(ldns_rr_list_rr(rrs, i)),
362 ownername
363 ) == 0
364 ) {
365 /* types match */
366 ldns_rr_list_push_rr(new, ldns_rr_clone(ldns_rr_list_rr(rrs, i)));
367 ret = new;
368 }
369 }
370 ldns_rr_list_deep_free(rrs);
371 if (!ret) {
372 ldns_rr_list_free(new);
373 }
374 return ret;
375 }
376
377 bool
ldns_pkt_rr(const ldns_pkt * pkt,ldns_pkt_section sec,const ldns_rr * rr)378 ldns_pkt_rr(const ldns_pkt *pkt, ldns_pkt_section sec, const ldns_rr *rr)
379 {
380 bool result = false;
381
382 switch (sec) {
383 case LDNS_SECTION_QUESTION:
384 return ldns_rr_list_contains_rr(ldns_pkt_question(pkt), rr);
385 case LDNS_SECTION_ANSWER:
386 return ldns_rr_list_contains_rr(ldns_pkt_answer(pkt), rr);
387 case LDNS_SECTION_AUTHORITY:
388 return ldns_rr_list_contains_rr(ldns_pkt_authority(pkt), rr);
389 case LDNS_SECTION_ADDITIONAL:
390 return ldns_rr_list_contains_rr(ldns_pkt_additional(pkt), rr);
391 case LDNS_SECTION_ANY:
392 result = ldns_rr_list_contains_rr(ldns_pkt_question(pkt), rr);
393 /* fallthrough */
394 case LDNS_SECTION_ANY_NOQUESTION:
395 result = result
396 || ldns_rr_list_contains_rr(ldns_pkt_answer(pkt), rr)
397 || ldns_rr_list_contains_rr(ldns_pkt_authority(pkt), rr)
398 || ldns_rr_list_contains_rr(ldns_pkt_additional(pkt), rr);
399 }
400
401 return result;
402 }
403
404 uint16_t
ldns_pkt_section_count(const ldns_pkt * packet,ldns_pkt_section s)405 ldns_pkt_section_count(const ldns_pkt *packet, ldns_pkt_section s)
406 {
407 switch(s) {
408 case LDNS_SECTION_QUESTION:
409 return ldns_pkt_qdcount(packet);
410 case LDNS_SECTION_ANSWER:
411 return ldns_pkt_ancount(packet);
412 case LDNS_SECTION_AUTHORITY:
413 return ldns_pkt_nscount(packet);
414 case LDNS_SECTION_ADDITIONAL:
415 return ldns_pkt_arcount(packet);
416 case LDNS_SECTION_ANY:
417 return ldns_pkt_qdcount(packet) +
418 ldns_pkt_ancount(packet) +
419 ldns_pkt_nscount(packet) +
420 ldns_pkt_arcount(packet);
421 case LDNS_SECTION_ANY_NOQUESTION:
422 return ldns_pkt_ancount(packet) +
423 ldns_pkt_nscount(packet) +
424 ldns_pkt_arcount(packet);
425 default:
426 return 0;
427 }
428 }
429
430 bool
ldns_pkt_empty(ldns_pkt * p)431 ldns_pkt_empty(ldns_pkt *p)
432 {
433 if (!p) {
434 return true; /* NULL is empty? */
435 }
436 if (ldns_pkt_section_count(p, LDNS_SECTION_ANY) > 0) {
437 return false;
438 } else {
439 return true;
440 }
441 }
442
443
444 ldns_rr_list *
ldns_pkt_get_section_clone(const ldns_pkt * packet,ldns_pkt_section s)445 ldns_pkt_get_section_clone(const ldns_pkt *packet, ldns_pkt_section s)
446 {
447 switch(s) {
448 case LDNS_SECTION_QUESTION:
449 return ldns_rr_list_clone(ldns_pkt_question(packet));
450 case LDNS_SECTION_ANSWER:
451 return ldns_rr_list_clone(ldns_pkt_answer(packet));
452 case LDNS_SECTION_AUTHORITY:
453 return ldns_rr_list_clone(ldns_pkt_authority(packet));
454 case LDNS_SECTION_ADDITIONAL:
455 return ldns_rr_list_clone(ldns_pkt_additional(packet));
456 case LDNS_SECTION_ANY:
457 /* these are already clones */
458 return ldns_pkt_all(packet);
459 case LDNS_SECTION_ANY_NOQUESTION:
460 return ldns_pkt_all_noquestion(packet);
461 default:
462 return NULL;
463 }
464 }
465
ldns_pkt_tsig(const ldns_pkt * pkt)466 ldns_rr *ldns_pkt_tsig(const ldns_pkt *pkt) {
467 return pkt->_tsig_rr;
468 }
469
470 /* write */
471 void
ldns_pkt_set_id(ldns_pkt * packet,uint16_t id)472 ldns_pkt_set_id(ldns_pkt *packet, uint16_t id)
473 {
474 packet->_header->_id = id;
475 }
476
477 void
ldns_pkt_set_random_id(ldns_pkt * packet)478 ldns_pkt_set_random_id(ldns_pkt *packet)
479 {
480 uint16_t rid = ldns_get_random();
481 ldns_pkt_set_id(packet, rid);
482 }
483
484
485 void
ldns_pkt_set_qr(ldns_pkt * packet,bool qr)486 ldns_pkt_set_qr(ldns_pkt *packet, bool qr)
487 {
488 packet->_header->_qr = qr;
489 }
490
491 void
ldns_pkt_set_aa(ldns_pkt * packet,bool aa)492 ldns_pkt_set_aa(ldns_pkt *packet, bool aa)
493 {
494 packet->_header->_aa = aa;
495 }
496
497 void
ldns_pkt_set_tc(ldns_pkt * packet,bool tc)498 ldns_pkt_set_tc(ldns_pkt *packet, bool tc)
499 {
500 packet->_header->_tc = tc;
501 }
502
503 void
ldns_pkt_set_rd(ldns_pkt * packet,bool rd)504 ldns_pkt_set_rd(ldns_pkt *packet, bool rd)
505 {
506 packet->_header->_rd = rd;
507 }
508
509 void
ldns_pkt_set_additional(ldns_pkt * p,ldns_rr_list * rr)510 ldns_pkt_set_additional(ldns_pkt *p, ldns_rr_list *rr)
511 {
512 p->_additional = rr;
513 }
514
515 void
ldns_pkt_set_question(ldns_pkt * p,ldns_rr_list * rr)516 ldns_pkt_set_question(ldns_pkt *p, ldns_rr_list *rr)
517 {
518 p->_question = rr;
519 }
520
521 void
ldns_pkt_set_answer(ldns_pkt * p,ldns_rr_list * rr)522 ldns_pkt_set_answer(ldns_pkt *p, ldns_rr_list *rr)
523 {
524 p->_answer = rr;
525 }
526
527 void
ldns_pkt_set_authority(ldns_pkt * p,ldns_rr_list * rr)528 ldns_pkt_set_authority(ldns_pkt *p, ldns_rr_list *rr)
529 {
530 p->_authority = rr;
531 }
532
533 void
ldns_pkt_set_cd(ldns_pkt * packet,bool cd)534 ldns_pkt_set_cd(ldns_pkt *packet, bool cd)
535 {
536 packet->_header->_cd = cd;
537 }
538
539 void
ldns_pkt_set_ra(ldns_pkt * packet,bool ra)540 ldns_pkt_set_ra(ldns_pkt *packet, bool ra)
541 {
542 packet->_header->_ra = ra;
543 }
544
545 void
ldns_pkt_set_ad(ldns_pkt * packet,bool ad)546 ldns_pkt_set_ad(ldns_pkt *packet, bool ad)
547 {
548 packet->_header->_ad = ad;
549 }
550
551 void
ldns_pkt_set_opcode(ldns_pkt * packet,ldns_pkt_opcode opcode)552 ldns_pkt_set_opcode(ldns_pkt *packet, ldns_pkt_opcode opcode)
553 {
554 packet->_header->_opcode = opcode;
555 }
556
557 void
ldns_pkt_set_rcode(ldns_pkt * packet,uint8_t rcode)558 ldns_pkt_set_rcode(ldns_pkt *packet, uint8_t rcode)
559 {
560 packet->_header->_rcode = rcode;
561 }
562
563 void
ldns_pkt_set_qdcount(ldns_pkt * packet,uint16_t qdcount)564 ldns_pkt_set_qdcount(ldns_pkt *packet, uint16_t qdcount)
565 {
566 packet->_header->_qdcount = qdcount;
567 }
568
569 void
ldns_pkt_set_ancount(ldns_pkt * packet,uint16_t ancount)570 ldns_pkt_set_ancount(ldns_pkt *packet, uint16_t ancount)
571 {
572 packet->_header->_ancount = ancount;
573 }
574
575 void
ldns_pkt_set_nscount(ldns_pkt * packet,uint16_t nscount)576 ldns_pkt_set_nscount(ldns_pkt *packet, uint16_t nscount)
577 {
578 packet->_header->_nscount = nscount;
579 }
580
581 void
ldns_pkt_set_arcount(ldns_pkt * packet,uint16_t arcount)582 ldns_pkt_set_arcount(ldns_pkt *packet, uint16_t arcount)
583 {
584 packet->_header->_arcount = arcount;
585 }
586
587 void
ldns_pkt_set_querytime(ldns_pkt * packet,uint32_t time)588 ldns_pkt_set_querytime(ldns_pkt *packet, uint32_t time)
589 {
590 packet->_querytime = time;
591 }
592
593 void
ldns_pkt_set_answerfrom(ldns_pkt * packet,ldns_rdf * answerfrom)594 ldns_pkt_set_answerfrom(ldns_pkt *packet, ldns_rdf *answerfrom)
595 {
596 packet->_answerfrom = answerfrom;
597 }
598
599 void
ldns_pkt_set_timestamp(ldns_pkt * packet,struct timeval timeval)600 ldns_pkt_set_timestamp(ldns_pkt *packet, struct timeval timeval)
601 {
602 packet->timestamp.tv_sec = timeval.tv_sec;
603 packet->timestamp.tv_usec = timeval.tv_usec;
604 }
605
606 void
ldns_pkt_set_size(ldns_pkt * packet,size_t s)607 ldns_pkt_set_size(ldns_pkt *packet, size_t s)
608 {
609 packet->_size = s;
610 }
611
612 void
ldns_pkt_set_edns_udp_size(ldns_pkt * packet,uint16_t s)613 ldns_pkt_set_edns_udp_size(ldns_pkt *packet, uint16_t s)
614 {
615 packet->_edns_udp_size = s;
616 }
617
618 void
ldns_pkt_set_edns_extended_rcode(ldns_pkt * packet,uint8_t c)619 ldns_pkt_set_edns_extended_rcode(ldns_pkt *packet, uint8_t c)
620 {
621 packet->_edns_extended_rcode = c;
622 }
623
624 void
ldns_pkt_set_edns_version(ldns_pkt * packet,uint8_t v)625 ldns_pkt_set_edns_version(ldns_pkt *packet, uint8_t v)
626 {
627 packet->_edns_version = v;
628 }
629
630 void
ldns_pkt_set_edns_z(ldns_pkt * packet,uint16_t z)631 ldns_pkt_set_edns_z(ldns_pkt *packet, uint16_t z)
632 {
633 packet->_edns_z = z;
634 }
635
636 void
ldns_pkt_set_edns_data(ldns_pkt * packet,ldns_rdf * data)637 ldns_pkt_set_edns_data(ldns_pkt *packet, ldns_rdf *data)
638 {
639 packet->_edns_data = data;
640 }
641
642 void
ldns_pkt_set_edns_option_list(ldns_pkt * packet,ldns_edns_option_list * list)643 ldns_pkt_set_edns_option_list(ldns_pkt *packet, ldns_edns_option_list *list)
644 {
645 if (packet->_edns_list)
646 ldns_edns_option_list_deep_free(packet->_edns_list);
647 packet->_edns_list = list;
648 }
649
650
651 void
ldns_pkt_set_section_count(ldns_pkt * packet,ldns_pkt_section s,uint16_t count)652 ldns_pkt_set_section_count(ldns_pkt *packet, ldns_pkt_section s, uint16_t count)
653 {
654 switch(s) {
655 case LDNS_SECTION_QUESTION:
656 ldns_pkt_set_qdcount(packet, count);
657 break;
658 case LDNS_SECTION_ANSWER:
659 ldns_pkt_set_ancount(packet, count);
660 break;
661 case LDNS_SECTION_AUTHORITY:
662 ldns_pkt_set_nscount(packet, count);
663 break;
664 case LDNS_SECTION_ADDITIONAL:
665 ldns_pkt_set_arcount(packet, count);
666 break;
667 case LDNS_SECTION_ANY:
668 case LDNS_SECTION_ANY_NOQUESTION:
669 break;
670 }
671 }
672
ldns_pkt_set_tsig(ldns_pkt * pkt,ldns_rr * rr)673 void ldns_pkt_set_tsig(ldns_pkt *pkt, ldns_rr *rr)
674 {
675 pkt->_tsig_rr = rr;
676 }
677
678 bool
ldns_pkt_push_rr(ldns_pkt * packet,ldns_pkt_section section,ldns_rr * rr)679 ldns_pkt_push_rr(ldns_pkt *packet, ldns_pkt_section section, ldns_rr *rr)
680 {
681 switch(section) {
682 case LDNS_SECTION_QUESTION:
683 if (!ldns_rr_list_push_rr(ldns_pkt_question(packet), rr)) {
684 return false;
685 }
686 ldns_pkt_set_qdcount(packet, ldns_pkt_qdcount(packet) + 1);
687 break;
688 case LDNS_SECTION_ANSWER:
689 if (!ldns_rr_list_push_rr(ldns_pkt_answer(packet), rr)) {
690 return false;
691 }
692 ldns_pkt_set_ancount(packet, ldns_pkt_ancount(packet) + 1);
693 break;
694 case LDNS_SECTION_AUTHORITY:
695 if (!ldns_rr_list_push_rr(ldns_pkt_authority(packet), rr)) {
696 return false;
697 }
698 ldns_pkt_set_nscount(packet, ldns_pkt_nscount(packet) + 1);
699 break;
700 case LDNS_SECTION_ADDITIONAL:
701 if (!ldns_rr_list_push_rr(ldns_pkt_additional(packet), rr)) {
702 return false;
703 }
704 ldns_pkt_set_arcount(packet, ldns_pkt_arcount(packet) + 1);
705 break;
706 case LDNS_SECTION_ANY:
707 case LDNS_SECTION_ANY_NOQUESTION:
708 /* shouldn't this error? */
709 break;
710 }
711 return true;
712 }
713
714 bool
ldns_pkt_safe_push_rr(ldns_pkt * pkt,ldns_pkt_section sec,ldns_rr * rr)715 ldns_pkt_safe_push_rr(ldns_pkt *pkt, ldns_pkt_section sec, ldns_rr *rr)
716 {
717
718 /* check to see if its there */
719 if (ldns_pkt_rr(pkt, sec, rr)) {
720 /* already there */
721 return false;
722 }
723 return ldns_pkt_push_rr(pkt, sec, rr);
724 }
725
726 bool
ldns_pkt_push_rr_list(ldns_pkt * p,ldns_pkt_section s,ldns_rr_list * list)727 ldns_pkt_push_rr_list(ldns_pkt *p, ldns_pkt_section s, ldns_rr_list *list)
728 {
729 size_t i;
730 for(i = 0; i < ldns_rr_list_rr_count(list); i++) {
731 if (!ldns_pkt_push_rr(p, s, ldns_rr_list_rr(list, i))) {
732 return false;
733 }
734 }
735 return true;
736 }
737
738 bool
ldns_pkt_safe_push_rr_list(ldns_pkt * p,ldns_pkt_section s,ldns_rr_list * list)739 ldns_pkt_safe_push_rr_list(ldns_pkt *p, ldns_pkt_section s, ldns_rr_list *list)
740 {
741 size_t i;
742 for(i = 0; i < ldns_rr_list_rr_count(list); i++) {
743 if (!ldns_pkt_safe_push_rr(p, s, ldns_rr_list_rr(list, i))) {
744 return false;
745 }
746 }
747 return true;
748 }
749
750 bool
ldns_pkt_edns(const ldns_pkt * pkt)751 ldns_pkt_edns(const ldns_pkt *pkt)
752 {
753 return (ldns_pkt_edns_udp_size(pkt) > 0 ||
754 ldns_pkt_edns_extended_rcode(pkt) > 0 ||
755 ldns_pkt_edns_data(pkt) ||
756 ldns_pkt_edns_do(pkt) ||
757 pkt->_edns_list ||
758 pkt->_edns_present
759 );
760 }
761
762 ldns_edns_option_list*
pkt_edns_data2edns_option_list(const ldns_rdf * edns_data)763 pkt_edns_data2edns_option_list(const ldns_rdf *edns_data)
764 {
765 size_t pos = 0;
766 ldns_edns_option_list* edns_list;
767 size_t max;
768 const uint8_t* wire;
769
770 if (!edns_data)
771 return NULL;
772
773 max = ldns_rdf_size(edns_data);
774 wire = ldns_rdf_data(edns_data);
775 if (!max)
776 return NULL;
777
778 if (!(edns_list = ldns_edns_option_list_new()))
779 return NULL;
780
781 while (pos < max) {
782 ldns_edns_option* edns;
783 uint8_t *data;
784
785 if (pos + 4 > max) { /* make sure the header is */
786 ldns_edns_option_list_deep_free(edns_list);
787 return NULL;
788 }
789 ldns_edns_option_code code = ldns_read_uint16(&wire[pos]);
790 size_t size = ldns_read_uint16(&wire[pos+2]);
791 pos += 4;
792
793 if (pos + size > max) { /* make sure the size fits the data */
794 ldns_edns_option_list_deep_free(edns_list);
795 return NULL;
796 }
797 data = LDNS_XMALLOC(uint8_t, size);
798
799 if (!data) {
800 ldns_edns_option_list_deep_free(edns_list);
801 return NULL;
802 }
803 memcpy(data, &wire[pos], size);
804 pos += size;
805
806 edns = ldns_edns_new(code, size, data);
807
808 if (!edns) {
809 ldns_edns_option_list_deep_free(edns_list);
810 return NULL;
811 }
812 if (!ldns_edns_option_list_push(edns_list, edns)) {
813 ldns_edns_option_list_deep_free(edns_list);
814 return NULL;
815 }
816 }
817 return edns_list;
818
819 }
820
821 ldns_edns_option_list*
ldns_pkt_edns_get_option_list(ldns_pkt * packet)822 ldns_pkt_edns_get_option_list(ldns_pkt *packet)
823 {
824 /* return the list if it already exists */
825 if (packet->_edns_list != NULL)
826 return packet->_edns_list;
827
828 /* if the list doesn't exists, we create it by parsing the
829 * packet->_edns_data
830 */
831 if (!ldns_pkt_edns_data(packet))
832 return NULL;
833
834 return ( packet->_edns_list
835 = pkt_edns_data2edns_option_list(ldns_pkt_edns_data(packet)));
836 }
837
838
839 /* Create/destroy/convert functions
840 */
841 ldns_pkt *
ldns_pkt_new(void)842 ldns_pkt_new(void)
843 {
844 ldns_pkt *packet;
845 packet = LDNS_MALLOC(ldns_pkt);
846 if (!packet) {
847 return NULL;
848 }
849
850 packet->_header = LDNS_MALLOC(ldns_hdr);
851 if (!packet->_header) {
852 LDNS_FREE(packet);
853 return NULL;
854 }
855
856 packet->_question = ldns_rr_list_new();
857 packet->_answer = ldns_rr_list_new();
858 packet->_authority = ldns_rr_list_new();
859 packet->_additional = ldns_rr_list_new();
860
861 /* default everything to false */
862 ldns_pkt_set_qr(packet, false);
863 ldns_pkt_set_aa(packet, false);
864 ldns_pkt_set_tc(packet, false);
865 ldns_pkt_set_rd(packet, false);
866 ldns_pkt_set_ra(packet, false);
867 ldns_pkt_set_ad(packet, false);
868 ldns_pkt_set_cd(packet, false);
869
870 ldns_pkt_set_opcode(packet, LDNS_PACKET_QUERY);
871 ldns_pkt_set_rcode(packet, 0);
872 ldns_pkt_set_id(packet, 0);
873 ldns_pkt_set_size(packet, 0);
874 ldns_pkt_set_querytime(packet, 0);
875 memset(&packet->timestamp, 0, sizeof(packet->timestamp));
876 ldns_pkt_set_answerfrom(packet, NULL);
877 ldns_pkt_set_section_count(packet, LDNS_SECTION_QUESTION, 0);
878 ldns_pkt_set_section_count(packet, LDNS_SECTION_ANSWER, 0);
879 ldns_pkt_set_section_count(packet, LDNS_SECTION_AUTHORITY, 0);
880 ldns_pkt_set_section_count(packet, LDNS_SECTION_ADDITIONAL, 0);
881
882 ldns_pkt_set_edns_udp_size(packet, 0);
883 ldns_pkt_set_edns_extended_rcode(packet, 0);
884 ldns_pkt_set_edns_version(packet, 0);
885 ldns_pkt_set_edns_z(packet, 0);
886 ldns_pkt_set_edns_data(packet, NULL);
887 packet->_edns_list = NULL;
888 packet->_edns_present = false;
889
890 ldns_pkt_set_tsig(packet, NULL);
891
892 return packet;
893 }
894
895 void
ldns_pkt_free(ldns_pkt * packet)896 ldns_pkt_free(ldns_pkt *packet)
897 {
898 if (packet) {
899 LDNS_FREE(packet->_header);
900 ldns_rr_list_deep_free(packet->_question);
901 ldns_rr_list_deep_free(packet->_answer);
902 ldns_rr_list_deep_free(packet->_authority);
903 ldns_rr_list_deep_free(packet->_additional);
904 ldns_rr_free(packet->_tsig_rr);
905 ldns_rdf_deep_free(packet->_edns_data);
906 ldns_edns_option_list_deep_free(packet->_edns_list);
907 ldns_rdf_deep_free(packet->_answerfrom);
908 LDNS_FREE(packet);
909 }
910 }
911
912 bool
ldns_pkt_set_flags(ldns_pkt * packet,uint16_t flags)913 ldns_pkt_set_flags(ldns_pkt *packet, uint16_t flags)
914 {
915 if (!packet) {
916 return false;
917 }
918 if ((flags & LDNS_QR) == LDNS_QR) {
919 ldns_pkt_set_qr(packet, true);
920 }
921 if ((flags & LDNS_AA) == LDNS_AA) {
922 ldns_pkt_set_aa(packet, true);
923 }
924 if ((flags & LDNS_RD) == LDNS_RD) {
925 ldns_pkt_set_rd(packet, true);
926 }
927 if ((flags & LDNS_TC) == LDNS_TC) {
928 ldns_pkt_set_tc(packet, true);
929 }
930 if ((flags & LDNS_CD) == LDNS_CD) {
931 ldns_pkt_set_cd(packet, true);
932 }
933 if ((flags & LDNS_RA) == LDNS_RA) {
934 ldns_pkt_set_ra(packet, true);
935 }
936 if ((flags & LDNS_AD) == LDNS_AD) {
937 ldns_pkt_set_ad(packet, true);
938 }
939 return true;
940 }
941
942
943 static ldns_rr*
ldns_pkt_authsoa(const ldns_rdf * rr_name,ldns_rr_class rr_class)944 ldns_pkt_authsoa(const ldns_rdf* rr_name, ldns_rr_class rr_class)
945 {
946 ldns_rr* soa_rr = ldns_rr_new();
947 ldns_rdf *owner_rdf;
948 ldns_rdf *mname_rdf;
949 ldns_rdf *rname_rdf;
950 ldns_rdf *serial_rdf;
951 ldns_rdf *refresh_rdf;
952 ldns_rdf *retry_rdf;
953 ldns_rdf *expire_rdf;
954 ldns_rdf *minimum_rdf;
955
956 if (!soa_rr) {
957 return NULL;
958 }
959 owner_rdf = ldns_rdf_clone(rr_name);
960 if (!owner_rdf) {
961 ldns_rr_free(soa_rr);
962 return NULL;
963 }
964
965 ldns_rr_set_owner(soa_rr, owner_rdf);
966 ldns_rr_set_type(soa_rr, LDNS_RR_TYPE_SOA);
967 ldns_rr_set_class(soa_rr, rr_class);
968 ldns_rr_set_question(soa_rr, false);
969
970 if (ldns_str2rdf_dname(&mname_rdf, ".") != LDNS_STATUS_OK) {
971 ldns_rr_free(soa_rr);
972 return NULL;
973 } else {
974 ldns_rr_push_rdf(soa_rr, mname_rdf);
975 }
976 if (ldns_str2rdf_dname(&rname_rdf, ".") != LDNS_STATUS_OK) {
977 ldns_rr_free(soa_rr);
978 return NULL;
979 } else {
980 ldns_rr_push_rdf(soa_rr, rname_rdf);
981 }
982 serial_rdf = ldns_native2rdf_int32(LDNS_RDF_TYPE_INT32, 0);
983 if (!serial_rdf) {
984 ldns_rr_free(soa_rr);
985 return NULL;
986 } else {
987 ldns_rr_push_rdf(soa_rr, serial_rdf);
988 }
989 refresh_rdf = ldns_native2rdf_int32(LDNS_RDF_TYPE_INT32, 0);
990 if (!refresh_rdf) {
991 ldns_rr_free(soa_rr);
992 return NULL;
993 } else {
994 ldns_rr_push_rdf(soa_rr, refresh_rdf);
995 }
996 retry_rdf = ldns_native2rdf_int32(LDNS_RDF_TYPE_INT32, 0);
997 if (!retry_rdf) {
998 ldns_rr_free(soa_rr);
999 return NULL;
1000 } else {
1001 ldns_rr_push_rdf(soa_rr, retry_rdf);
1002 }
1003 expire_rdf = ldns_native2rdf_int32(LDNS_RDF_TYPE_INT32, 0);
1004 if (!expire_rdf) {
1005 ldns_rr_free(soa_rr);
1006 return NULL;
1007 } else {
1008 ldns_rr_push_rdf(soa_rr, expire_rdf);
1009 }
1010 minimum_rdf = ldns_native2rdf_int32(LDNS_RDF_TYPE_INT32, 0);
1011 if (!minimum_rdf) {
1012 ldns_rr_free(soa_rr);
1013 return NULL;
1014 } else {
1015 ldns_rr_push_rdf(soa_rr, minimum_rdf);
1016 }
1017 return soa_rr;
1018 }
1019
1020
1021 static ldns_status
ldns_pkt_query_new_frm_str_internal(ldns_pkt ** p,const char * name,ldns_rr_type rr_type,ldns_rr_class rr_class,uint16_t flags,ldns_rr * authsoa_rr)1022 ldns_pkt_query_new_frm_str_internal(ldns_pkt **p, const char *name,
1023 ldns_rr_type rr_type, ldns_rr_class rr_class, uint16_t flags,
1024 ldns_rr* authsoa_rr)
1025 {
1026 ldns_pkt *packet;
1027 ldns_rr *question_rr;
1028 ldns_rdf *name_rdf;
1029
1030 packet = ldns_pkt_new();
1031 if (!packet) {
1032 return LDNS_STATUS_MEM_ERR;
1033 }
1034
1035 if (!ldns_pkt_set_flags(packet, flags)) {
1036 ldns_pkt_free(packet);
1037 return LDNS_STATUS_ERR;
1038 }
1039
1040 question_rr = ldns_rr_new();
1041 if (!question_rr) {
1042 ldns_pkt_free(packet);
1043 return LDNS_STATUS_MEM_ERR;
1044 }
1045
1046 if (rr_type == 0) {
1047 rr_type = LDNS_RR_TYPE_A;
1048 }
1049 if (rr_class == 0) {
1050 rr_class = LDNS_RR_CLASS_IN;
1051 }
1052
1053 if (ldns_str2rdf_dname(&name_rdf, name) == LDNS_STATUS_OK) {
1054 ldns_rr_set_owner(question_rr, name_rdf);
1055 ldns_rr_set_type(question_rr, rr_type);
1056 ldns_rr_set_class(question_rr, rr_class);
1057 ldns_rr_set_question(question_rr, true);
1058
1059 ldns_pkt_push_rr(packet, LDNS_SECTION_QUESTION, question_rr);
1060 } else {
1061 ldns_rr_free(question_rr);
1062 ldns_pkt_free(packet);
1063 return LDNS_STATUS_ERR;
1064 }
1065
1066 if (authsoa_rr) {
1067 ldns_pkt_push_rr(packet, LDNS_SECTION_AUTHORITY, authsoa_rr);
1068 }
1069
1070 packet->_tsig_rr = NULL;
1071 ldns_pkt_set_answerfrom(packet, NULL);
1072 if (p) {
1073 *p = packet;
1074 return LDNS_STATUS_OK;
1075 } else {
1076 ldns_pkt_free(packet);
1077 return LDNS_STATUS_NULL;
1078 }
1079 }
1080
1081 ldns_status
ldns_pkt_query_new_frm_str(ldns_pkt ** p,const char * name,ldns_rr_type rr_type,ldns_rr_class rr_class,uint16_t flags)1082 ldns_pkt_query_new_frm_str(ldns_pkt **p, const char *name,
1083 ldns_rr_type rr_type, ldns_rr_class rr_class, uint16_t flags)
1084 {
1085 return ldns_pkt_query_new_frm_str_internal(p, name, rr_type,
1086 rr_class, flags, NULL);
1087 }
1088
1089 ldns_status
ldns_pkt_ixfr_request_new_frm_str(ldns_pkt ** p,const char * name,ldns_rr_class rr_class,uint16_t flags,ldns_rr * soa)1090 ldns_pkt_ixfr_request_new_frm_str(ldns_pkt **p, const char *name,
1091 ldns_rr_class rr_class, uint16_t flags, ldns_rr *soa)
1092 {
1093 ldns_rr* authsoa_rr = soa;
1094 if (!authsoa_rr) {
1095 ldns_rdf *name_rdf;
1096 if (ldns_str2rdf_dname(&name_rdf, name) == LDNS_STATUS_OK) {
1097 authsoa_rr = ldns_pkt_authsoa(name_rdf, rr_class);
1098 }
1099 ldns_rdf_free(name_rdf);
1100 }
1101 return ldns_pkt_query_new_frm_str_internal(p, name, LDNS_RR_TYPE_IXFR,
1102 rr_class, flags, authsoa_rr);
1103 }
1104
1105 static ldns_pkt *
ldns_pkt_query_new_internal(ldns_rdf * rr_name,ldns_rr_type rr_type,ldns_rr_class rr_class,uint16_t flags,ldns_rr * authsoa_rr)1106 ldns_pkt_query_new_internal(ldns_rdf *rr_name, ldns_rr_type rr_type,
1107 ldns_rr_class rr_class, uint16_t flags, ldns_rr* authsoa_rr)
1108 {
1109 ldns_pkt *packet;
1110 ldns_rr *question_rr;
1111
1112 packet = ldns_pkt_new();
1113 if (!packet) {
1114 return NULL;
1115 }
1116
1117 if (!ldns_pkt_set_flags(packet, flags)) {
1118 return NULL;
1119 }
1120
1121 question_rr = ldns_rr_new();
1122 if (!question_rr) {
1123 ldns_pkt_free(packet);
1124 return NULL;
1125 }
1126
1127 if (rr_type == 0) {
1128 rr_type = LDNS_RR_TYPE_A;
1129 }
1130 if (rr_class == 0) {
1131 rr_class = LDNS_RR_CLASS_IN;
1132 }
1133
1134 ldns_rr_set_owner(question_rr, rr_name);
1135 ldns_rr_set_type(question_rr, rr_type);
1136 ldns_rr_set_class(question_rr, rr_class);
1137 ldns_rr_set_question(question_rr, true);
1138 ldns_pkt_push_rr(packet, LDNS_SECTION_QUESTION, question_rr);
1139
1140 if (authsoa_rr) {
1141 ldns_pkt_push_rr(packet, LDNS_SECTION_AUTHORITY, authsoa_rr);
1142 }
1143
1144 packet->_tsig_rr = NULL;
1145 return packet;
1146 }
1147
1148 ldns_pkt *
ldns_pkt_query_new(ldns_rdf * rr_name,ldns_rr_type rr_type,ldns_rr_class rr_class,uint16_t flags)1149 ldns_pkt_query_new(ldns_rdf *rr_name, ldns_rr_type rr_type,
1150 ldns_rr_class rr_class, uint16_t flags)
1151 {
1152 return ldns_pkt_query_new_internal(rr_name, rr_type,
1153 rr_class, flags, NULL);
1154 }
1155
1156 ldns_pkt *
ldns_pkt_ixfr_request_new(ldns_rdf * rr_name,ldns_rr_class rr_class,uint16_t flags,ldns_rr * soa)1157 ldns_pkt_ixfr_request_new(ldns_rdf *rr_name, ldns_rr_class rr_class,
1158 uint16_t flags, ldns_rr* soa)
1159 {
1160 ldns_rr* authsoa_rr = soa;
1161 if (!authsoa_rr) {
1162 authsoa_rr = ldns_pkt_authsoa(rr_name, rr_class);
1163 }
1164 return ldns_pkt_query_new_internal(rr_name, LDNS_RR_TYPE_IXFR,
1165 rr_class, flags, authsoa_rr);
1166 }
1167
1168 ldns_pkt_type
ldns_pkt_reply_type(const ldns_pkt * p)1169 ldns_pkt_reply_type(const ldns_pkt *p)
1170 {
1171 ldns_rr_list *tmp;
1172
1173 if (!p) {
1174 return LDNS_PACKET_UNKNOWN;
1175 }
1176
1177 if (ldns_pkt_get_rcode(p) == LDNS_RCODE_NXDOMAIN) {
1178 return LDNS_PACKET_NXDOMAIN;
1179 }
1180
1181 if (ldns_pkt_ancount(p) == 0 && ldns_pkt_arcount(p) == 0
1182 && ldns_pkt_nscount(p) == 1) {
1183
1184 /* check for SOA */
1185 tmp = ldns_pkt_rr_list_by_type(p, LDNS_RR_TYPE_SOA,
1186 LDNS_SECTION_AUTHORITY);
1187 if (tmp) {
1188 ldns_rr_list_deep_free(tmp);
1189 return LDNS_PACKET_NODATA;
1190 } else {
1191 /* I have no idea ... */
1192 }
1193 }
1194
1195 if (ldns_pkt_ancount(p) == 0 && ldns_pkt_nscount(p) > 0) {
1196 tmp = ldns_pkt_rr_list_by_type(p, LDNS_RR_TYPE_NS,
1197 LDNS_SECTION_AUTHORITY);
1198 if (tmp) {
1199 /* there are nameservers here */
1200 ldns_rr_list_deep_free(tmp);
1201 return LDNS_PACKET_REFERRAL;
1202 } else {
1203 /* I have no idea */
1204 }
1205 ldns_rr_list_deep_free(tmp);
1206 }
1207
1208 /* if we cannot determine the packet type, we say it's an
1209 * answer...
1210 */
1211 return LDNS_PACKET_ANSWER;
1212 }
1213
1214 ldns_pkt *
ldns_pkt_clone(const ldns_pkt * pkt)1215 ldns_pkt_clone(const ldns_pkt *pkt)
1216 {
1217 ldns_pkt *new_pkt;
1218
1219 if (!pkt) {
1220 return NULL;
1221 }
1222 new_pkt = ldns_pkt_new();
1223
1224 ldns_pkt_set_id(new_pkt, ldns_pkt_id(pkt));
1225 ldns_pkt_set_qr(new_pkt, ldns_pkt_qr(pkt));
1226 ldns_pkt_set_aa(new_pkt, ldns_pkt_aa(pkt));
1227 ldns_pkt_set_tc(new_pkt, ldns_pkt_tc(pkt));
1228 ldns_pkt_set_rd(new_pkt, ldns_pkt_rd(pkt));
1229 ldns_pkt_set_cd(new_pkt, ldns_pkt_cd(pkt));
1230 ldns_pkt_set_ra(new_pkt, ldns_pkt_ra(pkt));
1231 ldns_pkt_set_ad(new_pkt, ldns_pkt_ad(pkt));
1232 ldns_pkt_set_opcode(new_pkt, ldns_pkt_get_opcode(pkt));
1233 ldns_pkt_set_rcode(new_pkt, ldns_pkt_get_rcode(pkt));
1234 ldns_pkt_set_qdcount(new_pkt, ldns_pkt_qdcount(pkt));
1235 ldns_pkt_set_ancount(new_pkt, ldns_pkt_ancount(pkt));
1236 ldns_pkt_set_nscount(new_pkt, ldns_pkt_nscount(pkt));
1237 ldns_pkt_set_arcount(new_pkt, ldns_pkt_arcount(pkt));
1238 if (ldns_pkt_answerfrom(pkt))
1239 ldns_pkt_set_answerfrom(new_pkt,
1240 ldns_rdf_clone(ldns_pkt_answerfrom(pkt)));
1241 ldns_pkt_set_timestamp(new_pkt, ldns_pkt_timestamp(pkt));
1242 ldns_pkt_set_querytime(new_pkt, ldns_pkt_querytime(pkt));
1243 ldns_pkt_set_size(new_pkt, ldns_pkt_size(pkt));
1244 ldns_pkt_set_tsig(new_pkt, ldns_rr_clone(ldns_pkt_tsig(pkt)));
1245
1246 ldns_pkt_set_edns_udp_size(new_pkt, ldns_pkt_edns_udp_size(pkt));
1247 ldns_pkt_set_edns_extended_rcode(new_pkt,
1248 ldns_pkt_edns_extended_rcode(pkt));
1249 ldns_pkt_set_edns_version(new_pkt, ldns_pkt_edns_version(pkt));
1250 new_pkt->_edns_present = pkt->_edns_present;
1251 ldns_pkt_set_edns_z(new_pkt, ldns_pkt_edns_z(pkt));
1252 if(ldns_pkt_edns_data(pkt))
1253 ldns_pkt_set_edns_data(new_pkt,
1254 ldns_rdf_clone(ldns_pkt_edns_data(pkt)));
1255 ldns_pkt_set_edns_do(new_pkt, ldns_pkt_edns_do(pkt));
1256 if (pkt->_edns_list)
1257 ldns_pkt_set_edns_option_list(new_pkt,
1258 ldns_edns_option_list_clone(pkt->_edns_list));
1259
1260 ldns_rr_list_deep_free(new_pkt->_question);
1261 ldns_rr_list_deep_free(new_pkt->_answer);
1262 ldns_rr_list_deep_free(new_pkt->_authority);
1263 ldns_rr_list_deep_free(new_pkt->_additional);
1264 new_pkt->_question = ldns_rr_list_clone(ldns_pkt_question(pkt));
1265 new_pkt->_answer = ldns_rr_list_clone(ldns_pkt_answer(pkt));
1266 new_pkt->_authority = ldns_rr_list_clone(ldns_pkt_authority(pkt));
1267 new_pkt->_additional = ldns_rr_list_clone(ldns_pkt_additional(pkt));
1268 return new_pkt;
1269 }
1270