rr_functions.c
Go to the documentation of this file.
1 /*
2  * rr_function.c
3  *
4  * function that operate on specific rr types
5  *
6  * (c) NLnet Labs, 2004-2006
7  * See the file LICENSE for the license
8  */
9 
10 /*
11  * These come strait from perldoc Net::DNS::RR::xxx
12  * first the read variant, then the write. This is
13  * not complete.
14  */
15 
16 #include <ldns/config.h>
17 
18 #include <ldns/ldns.h>
19 
20 #include <limits.h>
21 #include <strings.h>
22 
30 static ldns_rdf *
31 ldns_rr_function(ldns_rr_type type, const ldns_rr *rr, size_t pos)
32 {
33  if (!rr || ldns_rr_get_type(rr) != type) {
34  return NULL;
35  }
36  return ldns_rr_rdf(rr, pos);
37 }
38 
47 static bool
48 ldns_rr_set_function(ldns_rr_type type, ldns_rr *rr, ldns_rdf *rdf, size_t pos)
49 {
50  ldns_rdf *pop;
51  if (!rr || ldns_rr_get_type(rr) != type) {
52  return false;
53  }
54  pop = ldns_rr_set_rdf(rr, rdf, pos);
55  ldns_rdf_deep_free(pop);
56  return true;
57 }
58 
59 /* A/AAAA records */
60 ldns_rdf *
62 {
63  /* 2 types to check, cannot use the macro */
64  if (!r || (ldns_rr_get_type(r) != LDNS_RR_TYPE_A &&
66  return NULL;
67  }
68  return ldns_rr_rdf(r, 0);
69 }
70 
71 bool
73 {
74  /* 2 types to check, cannot use the macro... */
75  ldns_rdf *pop;
76  if (!r || (ldns_rr_get_type(r) != LDNS_RR_TYPE_A &&
78  return false;
79  }
80  pop = ldns_rr_set_rdf(r, f, 0);
81  if (pop) {
82  LDNS_FREE(pop);
83  return true;
84  } else {
85  return false;
86  }
87 }
88 
89 /* NS record */
90 ldns_rdf *
92 {
93  return ldns_rr_function(LDNS_RR_TYPE_NS, r, 0);
94 }
95 
96 /* MX record */
97 ldns_rdf *
99 {
100  return ldns_rr_function(LDNS_RR_TYPE_MX, r, 0);
101 }
102 
103 ldns_rdf *
105 {
106  return ldns_rr_function(LDNS_RR_TYPE_MX, r, 1);
107 }
108 
109 /* RRSIG record */
110 ldns_rdf *
112 {
113  return ldns_rr_function(LDNS_RR_TYPE_RRSIG, r, 0);
114 }
115 
116 bool
118 {
119  return ldns_rr_set_function(LDNS_RR_TYPE_RRSIG, r, f, 0);
120 }
121 
122 ldns_rdf *
124 {
125  return ldns_rr_function(LDNS_RR_TYPE_RRSIG, r, 1);
126 }
127 
128 bool
130 {
131  return ldns_rr_set_function(LDNS_RR_TYPE_RRSIG, r, f, 1);
132 }
133 
134 ldns_rdf *
136 {
137  return ldns_rr_function(LDNS_RR_TYPE_RRSIG, r, 2);
138 }
139 
140 bool
142 {
143  return ldns_rr_set_function(LDNS_RR_TYPE_RRSIG, r, f, 2);
144 }
145 
146 ldns_rdf *
148 {
149  return ldns_rr_function(LDNS_RR_TYPE_RRSIG, r, 3);
150 }
151 
152 bool
154 {
155  return ldns_rr_set_function(LDNS_RR_TYPE_RRSIG, r, f, 3);
156 }
157 
158 ldns_rdf *
160 {
161  return ldns_rr_function(LDNS_RR_TYPE_RRSIG, r, 4);
162 }
163 
164 bool
166 {
167  return ldns_rr_set_function(LDNS_RR_TYPE_RRSIG, r, f, 4);
168 }
169 
170 ldns_rdf *
172 {
173  return ldns_rr_function(LDNS_RR_TYPE_RRSIG, r, 5);
174 }
175 
176 bool
178 {
179  return ldns_rr_set_function(LDNS_RR_TYPE_RRSIG, r, f, 5);
180 }
181 
182 ldns_rdf *
184 {
185  return ldns_rr_function(LDNS_RR_TYPE_RRSIG, r, 6);
186 }
187 
188 bool
190 {
191  return ldns_rr_set_function(LDNS_RR_TYPE_RRSIG, r, f, 6);
192 }
193 
194 ldns_rdf *
196 {
197  return ldns_rr_function(LDNS_RR_TYPE_RRSIG, r, 7);
198 }
199 
200 bool
202 {
203  return ldns_rr_set_function(LDNS_RR_TYPE_RRSIG, r, f, 7);
204 }
205 
206 ldns_rdf *
208 {
209  return ldns_rr_function(LDNS_RR_TYPE_RRSIG, r, 8);
210 }
211 
212 bool
214 {
215  return ldns_rr_set_function(LDNS_RR_TYPE_RRSIG, r, f, 8);
216 }
217 
218 /* DNSKEY record */
219 ldns_rdf *
221 {
222  return ldns_rr_function(LDNS_RR_TYPE_DNSKEY, r, 0);
223 }
224 
225 bool
227 {
228  return ldns_rr_set_function(LDNS_RR_TYPE_DNSKEY, r, f, 0);
229 }
230 
231 ldns_rdf *
233 {
234  return ldns_rr_function(LDNS_RR_TYPE_DNSKEY, r, 1);
235 }
236 
237 bool
239 {
240  return ldns_rr_set_function(LDNS_RR_TYPE_DNSKEY, r, f, 1);
241 }
242 
243 ldns_rdf *
245 {
246  return ldns_rr_function(LDNS_RR_TYPE_DNSKEY, r, 2);
247 }
248 
249 bool
251 {
252  return ldns_rr_set_function(LDNS_RR_TYPE_DNSKEY, r, f, 2);
253 }
254 
255 ldns_rdf *
257 {
258  return ldns_rr_function(LDNS_RR_TYPE_DNSKEY, r, 3);
259 }
260 
261 bool
263 {
264  return ldns_rr_set_function(LDNS_RR_TYPE_DNSKEY, r, f, 3);
265 }
266 
267 size_t
268 ldns_rr_dnskey_key_size_raw(const unsigned char* keydata,
269  const size_t len,
270  const ldns_algorithm alg)
271 {
272 #ifdef USE_DSA
273  /* for DSA keys */
274  uint8_t t;
275 #endif /* USE_DSA */
276 
277  /* for RSA keys */
278  uint16_t exp;
279  uint16_t int16;
280 
281  switch ((ldns_signing_algorithm)alg) {
282 #ifdef USE_DSA
283  case LDNS_SIGN_DSA:
284  case LDNS_SIGN_DSA_NSEC3:
285  if (len > 0) {
286  t = keydata[0];
287  return (64 + t*8)*8;
288  } else {
289  return 0;
290  }
291  break;
292 #endif /* USE_DSA */
293  case LDNS_SIGN_RSAMD5:
294  case LDNS_SIGN_RSASHA1:
296 #ifdef USE_SHA2
297  case LDNS_SIGN_RSASHA256:
298  case LDNS_SIGN_RSASHA512:
299 #endif
300  if (len > 0) {
301  if (keydata[0] == 0) {
302  /* big exponent */
303  if (len > 3) {
304  memmove(&int16, keydata + 1, 2);
305  exp = ntohs(int16);
306  return (len - exp - 3)*8;
307  } else {
308  return 0;
309  }
310  } else {
311  exp = keydata[0];
312  return (len-exp-1)*8;
313  }
314  } else {
315  return 0;
316  }
317  break;
318 #ifdef USE_GOST
319  case LDNS_SIGN_ECC_GOST:
320  return 512;
321 #endif
322 #ifdef USE_ECDSA
324  return 256;
326  return 384;
327 #endif
328 #ifdef USE_ED25519
329  case LDNS_SIGN_ED25519:
330  return 256;
331 #endif
332 #ifdef USE_ED448
333  case LDNS_SIGN_ED448:
334  return 456;
335 #endif
336  case LDNS_SIGN_HMACMD5:
337  return len;
338  default:
339  return 0;
340  }
341 }
342 
343 size_t
345 {
346  if (!key || !ldns_rr_dnskey_key(key)
347  || !ldns_rr_dnskey_algorithm(key)) {
348  return 0;
349  }
350  return ldns_rr_dnskey_key_size_raw((unsigned char*)ldns_rdf_data(ldns_rr_dnskey_key(key)),
353  );
354 }
355 
356 uint32_t ldns_soa_serial_identity(uint32_t ATTR_UNUSED(unused), void *data)
357 {
358  return (uint32_t) (intptr_t) data;
359 }
360 
361 uint32_t ldns_soa_serial_increment(uint32_t s, void *ATTR_UNUSED(unused))
362 {
363  return ldns_soa_serial_increment_by(s, (void *)1);
364 }
365 
366 uint32_t ldns_soa_serial_increment_by(uint32_t s, void *data)
367 {
368  return s + (intptr_t) data;
369 }
370 
371 uint32_t ldns_soa_serial_datecounter(uint32_t s, void *data)
372 {
373  struct tm tm;
374  char s_str[11];
375  int32_t new_s;
376  time_t t = data ? (time_t) (intptr_t) data : ldns_time(NULL);
377 
378  (void) strftime(s_str, 11, "%Y%m%d00", localtime_r(&t, &tm));
379  new_s = (int32_t) atoi(s_str);
380  return new_s - ((int32_t) s) <= 0 ? s+1 : ((uint32_t) new_s);
381 }
382 
383 uint32_t ldns_soa_serial_unixtime(uint32_t s, void *data)
384 {
385  int32_t new_s = data ? (int32_t) (intptr_t) data
386  : (int32_t) ldns_time(NULL);
387  return new_s - ((int32_t) s) <= 0 ? s+1 : ((uint32_t) new_s);
388 }
389 
390 void
392 {
394 }
395 
396 void
398 {
399  ldns_rr_soa_increment_func_data(soa, f, NULL);
400 }
401 
402 void
404  ldns_soa_serial_increment_func_t f, void *data)
405 {
406  ldns_rdf *prev_soa_serial_rdf;
407  if ( !soa || !f || ldns_rr_get_type(soa) != LDNS_RR_TYPE_SOA
408  || !ldns_rr_rdf(soa, 2)) {
409  return;
410  }
411  prev_soa_serial_rdf = ldns_rr_set_rdf(
412  soa
415  , (*f)( ldns_rdf2native_int32(
416  ldns_rr_rdf(soa, 2))
417  , data
418  )
419  )
420  , 2
421  );
422  LDNS_FREE(prev_soa_serial_rdf);
423 }
424 
425 void
428 {
429  ldns_rr_soa_increment_func_data(soa, f, (void *) (intptr_t) data);
430 }
431 
ldns_rdf * ldns_rr_rdf(const ldns_rr *rr, size_t nr)
returns the rdata field member counter.
Definition: rr.c:901
bool ldns_rr_rrsig_set_sig(ldns_rr *r, ldns_rdf *f)
sets the signature data of a LDNS_RR_TYPE_RRSIG rr
Definition: rr_functions.c:213
void ldns_rr_soa_increment_func_data(ldns_rr *soa, ldns_soa_serial_increment_func_t f, void *data)
Increment the serial number of the given SOA with the given function passing it the given data argume...
Definition: rr_functions.c:403
size_t ldns_rdf_size(const ldns_rdf *rd)
returns the size of the rdf.
Definition: rdata.c:24
bool ldns_rr_rrsig_set_algorithm(ldns_rr *r, ldns_rdf *f)
sets the algorithm of a LDNS_RR_TYPE_RRSIG rr
Definition: rr_functions.c:129
uint32_t ldns_soa_serial_datecounter(uint32_t s, void *data)
Function to be used with ldns_rr_soa_increment_func or ldns_rr_soa_increment_func_int to set the soa ...
Definition: rr_functions.c:371
ldns_rdf * ldns_rr_rrsig_origttl(const ldns_rr *r)
returns the original TTL of a LDNS_RR_TYPE_RRSIG RR
Definition: rr_functions.c:147
bool ldns_rr_rrsig_set_signame(ldns_rr *r, ldns_rdf *f)
sets the signers name of a LDNS_RR_TYPE_RRSIG rr
Definition: rr_functions.c:201
uint32_t ldns_soa_serial_unixtime(uint32_t s, void *data)
Function to be used with ldns_rr_soa_increment_func or ldns_rr_soa_increment_func_int to set the soa ...
Definition: rr_functions.c:383
@ LDNS_RDF_TYPE_INT32
32 bits
Definition: rdata.h:56
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
@ LDNS_SIGN_HMACMD5
Definition: keys.h:111
ldns_rdf * ldns_native2rdf_int32(ldns_rdf_type type, uint32_t value)
returns an rdf that contains the given int32 value.
Definition: rdata.c:147
Resource Record.
Definition: rr.h:309
#define LDNS_FREE(ptr)
Definition: util.h:60
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_rr_rrsig_set_keytag(ldns_rr *r, ldns_rdf *f)
sets the keytag of a LDNS_RR_TYPE_RRSIG rr
Definition: rr_functions.c:189
ldns_rdf * ldns_rr_dnskey_algorithm(const ldns_rr *r)
returns the algorithm of a LDNS_RR_TYPE_DNSKEY rr
Definition: rr_functions.c:244
ldns_rdf * ldns_rr_a_address(const ldns_rr *r)
returns the address of a LDNS_RR_TYPE_A rr
Definition: rr_functions.c:61
@ LDNS_SIGN_ED25519
Definition: keys.h:106
@ LDNS_SIGN_ECDSAP256SHA256
Definition: keys.h:103
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
uint32_t ldns_soa_serial_increment(uint32_t s, void *unused __attribute__((unused)))
Definition: rr_functions.c:361
void ldns_rr_soa_increment_func_int(ldns_rr *soa, ldns_soa_serial_increment_func_t f, int data)
Increment the serial number of the given SOA with the given function using data as an argument for th...
Definition: rr_functions.c:426
@ LDNS_SIGN_ECC_GOST
Definition: keys.h:102
@ LDNS_SIGN_RSASHA1
Definition: keys.h:92
bool ldns_rr_dnskey_set_algorithm(ldns_rr *r, ldns_rdf *f)
sets the algorithm of a LDNS_RR_TYPE_DNSKEY rr
Definition: rr_functions.c:250
uint8_t ldns_rdf2native_int8(const ldns_rdf *rd)
returns the native uint8_t representation from the rdf.
Definition: rdata.c:70
ldns_rdf * ldns_rr_rrsig_sig(const ldns_rr *r)
returns the signature data of a LDNS_RR_TYPE_RRSIG RR
Definition: rr_functions.c:207
@ LDNS_SIGN_RSASHA512
Definition: keys.h:98
@ LDNS_RR_TYPE_NS
an authoritative name server
Definition: rr.h:82
enum ldns_enum_rr_type ldns_rr_type
Definition: rr.h:243
@ LDNS_RR_TYPE_SOA
marks the start of a zone of authority
Definition: rr.h:90
uint32_t ldns_soa_serial_increment_by(uint32_t s, void *data)
Function to be used with dns_rr_soa_increment_func_int, to increment the soa serial number with a cer...
Definition: rr_functions.c:366
void ldns_rdf_deep_free(ldns_rdf *rd)
frees a rdf structure and frees the data.
Definition: rdata.c:230
uint32_t ldns_rdf2native_int32(const ldns_rdf *rd)
returns the native uint32_t representation from the rdf.
Definition: rdata.c:98
bool ldns_rr_rrsig_set_typecovered(ldns_rr *r, ldns_rdf *f)
sets the typecovered of a LDNS_RR_TYPE_RRSIG rr
Definition: rr_functions.c:117
bool ldns_rr_rrsig_set_origttl(ldns_rr *r, ldns_rdf *f)
sets the original TTL of a LDNS_RR_TYPE_RRSIG rr
Definition: rr_functions.c:153
ldns_rdf * ldns_rr_ns_nsdname(const ldns_rr *r)
returns the name of a LDNS_RR_TYPE_NS rr
Definition: rr_functions.c:91
#define ATTR_UNUSED(x)
Definition: common.h:72
void ldns_rr_soa_increment(ldns_rr *soa)
Increment the serial number of the given SOA by one.
Definition: rr_functions.c:391
ldns_rdf * ldns_rr_dnskey_protocol(const ldns_rr *r)
returns the protocol of a LDNS_RR_TYPE_DNSKEY rr
Definition: rr_functions.c:232
@ LDNS_SIGN_DSA
Definition: keys.h:94
Resource record data field.
Definition: rdata.h:195
uint32_t(* ldns_soa_serial_increment_func_t)(uint32_t, void *)
The type of function to be passed to ldns_rr_soa_increment_func, ldns_rr_soa_increment_func_data or l...
Definition: rr_functions.h:266
uint8_t * ldns_rdf_data(const ldns_rdf *rd)
returns the data of the rdf.
Definition: rdata.c:38
bool ldns_rr_a_set_address(ldns_rr *r, ldns_rdf *f)
sets the address of a LDNS_RR_TYPE_A rr
Definition: rr_functions.c:72
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_rdf * ldns_rr_dnskey_flags(const ldns_rr *r)
returns the flags of a LDNS_RR_TYPE_DNSKEY rr
Definition: rr_functions.c:220
enum ldns_enum_algorithm ldns_algorithm
Definition: keys.h:72
uint32_t ldns_soa_serial_identity(uint32_t unused __attribute__((unused)), void *data)
Definition: rr_functions.c:356
@ LDNS_RR_TYPE_RRSIG
DNSSEC.
Definition: rr.h:170
void ldns_rr_soa_increment_func(ldns_rr *soa, ldns_soa_serial_increment_func_t f)
Increment the serial number of the given SOA with the given function.
Definition: rr_functions.c:397
@ LDNS_RR_TYPE_A
a host address
Definition: rr.h:80
ldns_rdf * ldns_rr_set_rdf(ldns_rr *rr, const ldns_rdf *f, size_t position)
sets a rdf member, it will be set on the position given.
Definition: rr.c:832
bool ldns_rr_rrsig_set_inception(ldns_rr *r, ldns_rdf *f)
sets the inception date of a LDNS_RR_TYPE_RRSIG rr
Definition: rr_functions.c:177
@ LDNS_SIGN_DSA_NSEC3
Definition: keys.h:100
size_t ldns_rr_dnskey_key_size_raw(const unsigned char *keydata, const size_t len, const ldns_algorithm alg)
get the length of the keydata in bits
Definition: rr_functions.c:268
ldns_rdf * ldns_rr_rrsig_algorithm(const ldns_rr *r)
returns the algorithm of a LDNS_RR_TYPE_RRSIG RR
Definition: rr_functions.c:123
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
@ LDNS_RR_TYPE_DNSKEY
Definition: rr.h:172
bool ldns_rr_dnskey_set_key(ldns_rr *r, ldns_rdf *f)
sets the key data of a LDNS_RR_TYPE_DNSKEY rr
Definition: rr_functions.c:262
bool ldns_rr_dnskey_set_flags(ldns_rr *r, ldns_rdf *f)
sets the flags of a LDNS_RR_TYPE_DNSKEY rr
Definition: rr_functions.c:226
@ LDNS_SIGN_RSASHA256
Definition: keys.h:97
@ LDNS_SIGN_RSAMD5
Definition: keys.h:91
size_t ldns_rr_dnskey_key_size(const ldns_rr *key)
get the length of the keydata in bits
Definition: rr_functions.c:344
ldns_rdf * ldns_rr_dnskey_key(const ldns_rr *r)
returns the key data of a LDNS_RR_TYPE_DNSKEY rr
Definition: rr_functions.c:256
enum ldns_enum_signing_algorithm ldns_signing_algorithm
Definition: keys.h:118
bool ldns_rr_rrsig_set_labels(ldns_rr *r, ldns_rdf *f)
sets the number of labels of a LDNS_RR_TYPE_RRSIG rr
Definition: rr_functions.c:141
@ LDNS_RR_TYPE_MX
mail exchange
Definition: rr.h:108
@ LDNS_SIGN_RSASHA1_NSEC3
Definition: keys.h:96
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
bool ldns_rr_dnskey_set_protocol(ldns_rr *r, ldns_rdf *f)
sets the protocol of a LDNS_RR_TYPE_DNSKEY rr
Definition: rr_functions.c:238
bool ldns_rr_rrsig_set_expiration(ldns_rr *r, ldns_rdf *f)
sets the expiration date of a LDNS_RR_TYPE_RRSIG rr
Definition: rr_functions.c:165
@ LDNS_RR_TYPE_AAAA
ipv6 address
Definition: rr.h:134
ldns_rdf * ldns_rr_mx_preference(const ldns_rr *r)
returns the mx pref.
Definition: rr_functions.c:98
@ LDNS_SIGN_ED448
Definition: keys.h:109
@ LDNS_SIGN_ECDSAP384SHA384
Definition: keys.h:104
ldns_rdf * ldns_rr_mx_exchange(const ldns_rr *r)
returns the mx host of a LDNS_RR_TYPE_MX rr
Definition: rr_functions.c:104
ldns_rr_type ldns_rr_get_type(const ldns_rr *rr)
returns the type of the rr.
Definition: rr.c:935