Coverage Report

Created: 2026-10-28 06:55

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/bind9/lib/dns/rdata/generic/nsec3param_51.c
Line
Count
Source
1
/*
2
 * Copyright (C) Internet Systems Consortium, Inc. ("ISC")
3
 *
4
 * SPDX-License-Identifier: MPL-2.0
5
 *
6
 * This Source Code Form is subject to the terms of the Mozilla Public
7
 * License, v. 2.0. If a copy of the MPL was not distributed with this
8
 * file, you can obtain one at https://mozilla.org/MPL/2.0/.
9
 *
10
 * See the COPYRIGHT file distributed with this work for additional
11
 * information regarding copyright ownership.
12
 */
13
14
/*
15
 * Copyright (C) 2004  Nominet, Ltd.
16
 *
17
 * Permission to use, copy, modify, and distribute this software for any
18
 * purpose with or without fee is hereby granted, provided that the above
19
 * copyright notice and this permission notice appear in all copies.
20
 *
21
 * THE SOFTWARE IS PROVIDED "AS IS" AND NOMINET DISCLAIMS ALL WARRANTIES WITH
22
 * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
23
 * AND FITNESS.  IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
24
 * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
25
 * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
26
 * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
27
 * PERFORMANCE OF THIS SOFTWARE.
28
 */
29
30
/* RFC 5155 */
31
32
#ifndef RDATA_GENERIC_NSEC3PARAM_51_C
33
#define RDATA_GENERIC_NSEC3PARAM_51_C
34
35
#include <isc/base32.h>
36
#include <isc/iterated_hash.h>
37
38
10.9k
#define RRTYPE_NSEC3PARAM_ATTRIBUTES (DNS_RDATATYPEATTR_DNSSEC)
39
40
static isc_result_t
41
1.10k
fromtext_nsec3param(ARGS_FROMTEXT) {
42
1.10k
  isc_token_t token;
43
1.10k
  unsigned int flags = 0;
44
1.10k
  unsigned char hashalg;
45
46
1.10k
  REQUIRE(type == dns_rdatatype_nsec3param);
47
48
1.10k
  UNUSED(type);
49
1.10k
  UNUSED(rdclass);
50
1.10k
  UNUSED(callbacks);
51
1.10k
  UNUSED(origin);
52
1.10k
  UNUSED(options);
53
54
  /* Hash. */
55
1.10k
  RETERR(isc_lex_getmastertoken(lexer, &token, isc_tokentype_string,
56
1.10k
              false));
57
1.09k
  RETTOK(dns_hashalg_fromtext(&hashalg, &token.value.as_textregion));
58
1.03k
  RETERR(uint8_tobuffer(hashalg, target));
59
60
  /* Flags. */
61
1.03k
  RETERR(isc_lex_getmastertoken(lexer, &token, isc_tokentype_number,
62
1.03k
              false));
63
1.02k
  flags = token.value.as_ulong;
64
1.02k
  if (flags > 255U) {
65
74
    RETTOK(ISC_R_RANGE);
66
74
  }
67
946
  RETERR(uint8_tobuffer(flags, target));
68
69
  /* Iterations. */
70
946
  RETERR(isc_lex_getmastertoken(lexer, &token, isc_tokentype_number,
71
946
              false));
72
931
  if (token.value.as_ulong > 0xffffU) {
73
21
    RETTOK(ISC_R_RANGE);
74
21
  }
75
910
  RETERR(uint16_tobuffer(token.value.as_ulong, target));
76
77
  /* Salt. */
78
910
  RETERR(isc_lex_getmastertoken(lexer, &token, isc_tokentype_string,
79
910
              false));
80
885
  if (token.value.as_textregion.length > (255 * 2)) {
81
2
    RETTOK(DNS_R_TEXTTOOLONG);
82
2
  }
83
883
  if (strcmp(DNS_AS_STR(token), "-") == 0) {
84
265
    RETERR(uint8_tobuffer(0, target));
85
618
  } else {
86
618
    RETERR(uint8_tobuffer(strlen(DNS_AS_STR(token)) / 2, target));
87
618
    RETERR(isc_hex_decodestring(DNS_AS_STR(token), target));
88
613
  }
89
90
878
  return ISC_R_SUCCESS;
91
883
}
92
93
static isc_result_t
94
1.58k
totext_nsec3param(ARGS_TOTEXT) {
95
1.58k
  isc_region_t sr;
96
1.58k
  unsigned int i, j;
97
1.58k
  unsigned char hash;
98
1.58k
  unsigned char flags;
99
1.58k
  char buf[sizeof("65535 ")];
100
1.58k
  uint32_t iterations;
101
102
1.58k
  REQUIRE(rdata->type == dns_rdatatype_nsec3param);
103
1.58k
  REQUIRE(rdata->length != 0);
104
105
1.58k
  UNUSED(tctx);
106
107
1.58k
  dns_rdata_toregion(rdata, &sr);
108
109
1.58k
  hash = uint8_fromregion(&sr);
110
1.58k
  isc_region_consume(&sr, 1);
111
112
1.58k
  flags = uint8_fromregion(&sr);
113
1.58k
  isc_region_consume(&sr, 1);
114
115
1.58k
  iterations = uint16_fromregion(&sr);
116
1.58k
  isc_region_consume(&sr, 2);
117
118
1.58k
  snprintf(buf, sizeof(buf), "%u ", hash);
119
1.58k
  RETERR(str_totext(buf, target));
120
121
1.58k
  snprintf(buf, sizeof(buf), "%u ", flags);
122
1.58k
  RETERR(str_totext(buf, target));
123
124
1.58k
  snprintf(buf, sizeof(buf), "%u ", iterations);
125
1.58k
  RETERR(str_totext(buf, target));
126
127
1.58k
  j = uint8_fromregion(&sr);
128
1.58k
  isc_region_consume(&sr, 1);
129
1.58k
  INSIST(j <= sr.length);
130
131
1.58k
  if (j != 0) {
132
1.01k
    i = sr.length;
133
1.01k
    sr.length = j;
134
1.01k
    RETERR(isc_hex_totext(&sr, 1, "", target));
135
1.01k
    sr.length = i - j;
136
1.01k
  } else {
137
564
    RETERR(str_totext("-", target));
138
564
  }
139
140
1.58k
  return ISC_R_SUCCESS;
141
1.58k
}
142
143
static isc_result_t
144
1.98k
fromwire_nsec3param(ARGS_FROMWIRE) {
145
1.98k
  isc_region_t sr, rr;
146
1.98k
  unsigned int saltlen;
147
148
1.98k
  REQUIRE(type == dns_rdatatype_nsec3param);
149
150
1.98k
  UNUSED(type);
151
1.98k
  UNUSED(rdclass);
152
1.98k
  UNUSED(dctx);
153
154
1.98k
  isc_buffer_activeregion(source, &sr);
155
1.98k
  rr = sr;
156
157
  /* hash(1), flags(1), iterations(2), saltlen(1) */
158
1.98k
  if (sr.length < 5U) {
159
17
    RETERR(DNS_R_FORMERR);
160
0
  }
161
1.96k
  saltlen = sr.base[4];
162
1.96k
  isc_region_consume(&sr, 5);
163
164
1.96k
  if (sr.length != saltlen) {
165
100
    RETERR(DNS_R_FORMERR);
166
0
  }
167
1.86k
  isc_region_consume(&sr, saltlen);
168
1.86k
  RETERR(mem_tobuffer(target, rr.base, rr.length));
169
1.84k
  isc_buffer_forward(source, rr.length);
170
1.84k
  return ISC_R_SUCCESS;
171
1.86k
}
172
173
static int
174
71.9k
compare_nsec3param(ARGS_COMPARE) {
175
71.9k
  isc_region_t r1;
176
71.9k
  isc_region_t r2;
177
178
71.9k
  REQUIRE(rdata1->type == rdata2->type);
179
71.9k
  REQUIRE(rdata1->rdclass == rdata2->rdclass);
180
71.9k
  REQUIRE(rdata1->type == dns_rdatatype_nsec3param);
181
71.9k
  REQUIRE(rdata1->length != 0);
182
71.9k
  REQUIRE(rdata2->length != 0);
183
184
71.9k
  dns_rdata_toregion(rdata1, &r1);
185
71.9k
  dns_rdata_toregion(rdata2, &r2);
186
71.9k
  return isc_region_compare(&r1, &r2);
187
71.9k
}
188
189
static isc_result_t
190
0
fromstruct_nsec3param(ARGS_FROMSTRUCT) {
191
0
  dns_rdata_nsec3param_t *nsec3param = source;
192
193
0
  REQUIRE(type == dns_rdatatype_nsec3param);
194
0
  REQUIRE(nsec3param != NULL);
195
0
  REQUIRE(nsec3param->common.rdtype == type);
196
0
  REQUIRE(nsec3param->common.rdclass == rdclass);
197
198
0
  UNUSED(type);
199
0
  UNUSED(rdclass);
200
201
0
  RETERR(uint8_tobuffer(nsec3param->hash, target));
202
0
  RETERR(uint8_tobuffer(nsec3param->flags, target));
203
0
  RETERR(uint16_tobuffer(nsec3param->iterations, target));
204
0
  RETERR(uint8_tobuffer(nsec3param->salt.length, target));
205
0
  RETERR(mem_tobuffer(target, nsec3param->salt.base,
206
0
          nsec3param->salt.length));
207
0
  return ISC_R_SUCCESS;
208
0
}
209
210
static isc_result_t
211
19
tostruct_nsec3param(ARGS_TOSTRUCT) {
212
19
  isc_region_t region;
213
19
  dns_rdata_nsec3param_t *nsec3param = target;
214
215
19
  REQUIRE(rdata->type == dns_rdatatype_nsec3param);
216
19
  REQUIRE(nsec3param != NULL);
217
19
  REQUIRE(rdata->length != 0);
218
219
19
  DNS_RDATACOMMON_INIT(nsec3param, rdata->type, rdata->rdclass);
220
221
19
  region.base = rdata->data;
222
19
  region.length = rdata->length;
223
19
  nsec3param->hash = uint8_consume_fromregion(&region);
224
19
  nsec3param->flags = uint8_consume_fromregion(&region);
225
19
  nsec3param->iterations = uint16_consume_fromregion(&region);
226
227
19
  nsec3param->salt.length = uint8_consume_fromregion(&region);
228
19
  INSIST(nsec3param->salt.length == region.length);
229
19
  nsec3param->salt.base = region.base;
230
19
  isc_region_consume(&region, nsec3param->salt.length);
231
232
19
  return ISC_R_SUCCESS;
233
19
}
234
235
static isc_result_t
236
0
additionaldata_nsec3param(ARGS_ADDLDATA) {
237
0
  REQUIRE(rdata->type == dns_rdatatype_nsec3param);
238
239
0
  UNUSED(rdata);
240
0
  UNUSED(owner);
241
0
  UNUSED(add);
242
0
  UNUSED(arg);
243
244
0
  return ISC_R_SUCCESS;
245
0
}
246
247
static isc_result_t
248
0
digest_nsec3param(ARGS_DIGEST) {
249
0
  isc_region_t r;
250
251
0
  REQUIRE(rdata->type == dns_rdatatype_nsec3param);
252
253
0
  dns_rdata_toregion(rdata, &r);
254
0
  return (digest)(arg, &r);
255
0
}
256
257
static bool
258
0
checkowner_nsec3param(ARGS_CHECKOWNER) {
259
0
  REQUIRE(type == dns_rdatatype_nsec3param);
260
261
0
  UNUSED(name);
262
0
  UNUSED(type);
263
0
  UNUSED(rdclass);
264
0
  UNUSED(wildcard);
265
266
0
  return true;
267
0
}
268
269
static bool
270
0
checknames_nsec3param(ARGS_CHECKNAMES) {
271
0
  REQUIRE(rdata->type == dns_rdatatype_nsec3param);
272
273
0
  UNUSED(rdata);
274
0
  UNUSED(owner);
275
0
  UNUSED(bad);
276
277
0
  return true;
278
0
}
279
280
static int
281
0
casecompare_nsec3param(ARGS_COMPARE) {
282
0
  return compare_nsec3param(rdata1, rdata2);
283
0
}
284
285
#endif /* RDATA_GENERIC_NSEC3PARAM_51_C */