00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #include "config.h"
00020
00021 #include <isc/result.h>
00022 #include <isc/string.h>
00023 #include <isc/types.h>
00024 #include <isc/base64.h>
00025
00026 #include <dns/nsec3.h>
00027 #include <dns/private.h>
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045 #define REMOVE(x) (((x) & DNS_NSEC3FLAG_REMOVE) != 0)
00046 #define CREATE(x) (((x) & DNS_NSEC3FLAG_CREATE) != 0)
00047 #define INITIAL(x) (((x) & DNS_NSEC3FLAG_INITIAL) != 0)
00048 #define NONSEC(x) (((x) & DNS_NSEC3FLAG_NONSEC) != 0)
00049
00050 #define CHECK(x) do { \
00051 result = (x); \
00052 if (result != ISC_R_SUCCESS) \
00053 goto failure; \
00054 } while (0)
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064 static isc_boolean_t
00065 ignore(dns_rdata_t *param, dns_rdataset_t *privateset) {
00066 isc_result_t result;
00067
00068 for (result = dns_rdataset_first(privateset);
00069 result == ISC_R_SUCCESS;
00070 result = dns_rdataset_next(privateset)) {
00071 unsigned char buf[DNS_NSEC3PARAM_BUFFERSIZE];
00072 dns_rdata_t private = DNS_RDATA_INIT;
00073 dns_rdata_t rdata = DNS_RDATA_INIT;
00074
00075 dns_rdataset_current(privateset, &private);
00076 if (!dns_nsec3param_fromprivate(&private, &rdata,
00077 buf, sizeof(buf)))
00078 continue;
00079
00080
00081
00082
00083 if (CREATE(rdata.data[1]))
00084 return (ISC_FALSE);
00085 if (rdata.data[0] != param->data[0] ||
00086 rdata.data[2] != param->data[2] ||
00087 rdata.data[3] != param->data[3] ||
00088 rdata.data[4] != param->data[4] ||
00089 memcmp(&rdata.data[5], ¶m->data[5], param->data[4]))
00090 continue;
00091
00092
00093
00094
00095
00096 if (NONSEC(rdata.data[1]))
00097 return (ISC_FALSE);
00098 return (ISC_TRUE);
00099 }
00100 return (ISC_FALSE);
00101 }
00102
00103 isc_result_t
00104 dns_private_chains(dns_db_t *db, dns_dbversion_t *ver,
00105 dns_rdatatype_t privatetype,
00106 isc_boolean_t *build_nsec, isc_boolean_t *build_nsec3)
00107 {
00108 dns_dbnode_t *node;
00109 dns_rdataset_t nsecset, nsec3paramset, privateset;
00110 isc_boolean_t nsec3chain;
00111 isc_boolean_t signing;
00112 isc_result_t result;
00113 unsigned char buf[DNS_NSEC3PARAM_BUFFERSIZE];
00114 unsigned int count;
00115
00116 node = NULL;
00117 dns_rdataset_init(&nsecset);
00118 dns_rdataset_init(&nsec3paramset);
00119 dns_rdataset_init(&privateset);
00120
00121 CHECK(dns_db_getoriginnode(db, &node));
00122
00123 result = dns_db_findrdataset(db, node, ver, dns_rdatatype_nsec,
00124 0, (isc_stdtime_t) 0, &nsecset, NULL);
00125
00126 if (result != ISC_R_SUCCESS && result != ISC_R_NOTFOUND)
00127 goto failure;
00128
00129 result = dns_db_findrdataset(db, node, ver, dns_rdatatype_nsec3param,
00130 0, (isc_stdtime_t) 0, &nsec3paramset,
00131 NULL);
00132 if (result != ISC_R_SUCCESS && result != ISC_R_NOTFOUND)
00133 goto failure;
00134
00135 if (dns_rdataset_isassociated(&nsecset) &&
00136 dns_rdataset_isassociated(&nsec3paramset)) {
00137 if (build_nsec != NULL)
00138 *build_nsec = ISC_TRUE;
00139 if (build_nsec3 != NULL)
00140 *build_nsec3 = ISC_TRUE;
00141 goto success;
00142 }
00143
00144 if (privatetype != (dns_rdatatype_t)0) {
00145 result = dns_db_findrdataset(db, node, ver, privatetype,
00146 0, (isc_stdtime_t) 0,
00147 &privateset, NULL);
00148 if (result != ISC_R_SUCCESS && result != ISC_R_NOTFOUND)
00149 goto failure;
00150 }
00151
00152
00153
00154
00155 if (dns_rdataset_isassociated(&nsecset)) {
00156 if (build_nsec != NULL)
00157 *build_nsec = ISC_TRUE;
00158 if (build_nsec3 != NULL)
00159 *build_nsec3 = ISC_FALSE;
00160 if (!dns_rdataset_isassociated(&privateset))
00161 goto success;
00162 for (result = dns_rdataset_first(&privateset);
00163 result == ISC_R_SUCCESS;
00164 result = dns_rdataset_next(&privateset)) {
00165 dns_rdata_t private = DNS_RDATA_INIT;
00166 dns_rdata_t rdata = DNS_RDATA_INIT;
00167
00168 dns_rdataset_current(&privateset, &private);
00169 if (!dns_nsec3param_fromprivate(&private, &rdata,
00170 buf, sizeof(buf)))
00171 continue;
00172 if (REMOVE(rdata.data[1]))
00173 continue;
00174 if (build_nsec3 != NULL)
00175 *build_nsec3 = ISC_TRUE;
00176 break;
00177 }
00178 goto success;
00179 }
00180
00181 if (dns_rdataset_isassociated(&nsec3paramset)) {
00182 if (build_nsec3 != NULL)
00183 *build_nsec3 = ISC_TRUE;
00184 if (build_nsec != NULL)
00185 *build_nsec = ISC_FALSE;
00186 if (!dns_rdataset_isassociated(&privateset))
00187 goto success;
00188
00189
00190
00191
00192 for (result = dns_rdataset_first(&privateset);
00193 result == ISC_R_SUCCESS;
00194 result = dns_rdataset_next(&privateset)) {
00195 dns_rdata_t private = DNS_RDATA_INIT;
00196 dns_rdata_t rdata = DNS_RDATA_INIT;
00197
00198 dns_rdataset_current(&privateset, &private);
00199 if (!dns_nsec3param_fromprivate(&private, &rdata,
00200 buf, sizeof(buf)))
00201 continue;
00202 if (CREATE(rdata.data[1]))
00203 goto success;
00204 }
00205
00206
00207
00208
00209
00210 count = 0;
00211 for (result = dns_rdataset_first(&nsec3paramset);
00212 result == ISC_R_SUCCESS;
00213 result = dns_rdataset_next(&nsec3paramset)) {
00214 dns_rdata_t rdata = DNS_RDATA_INIT;
00215
00216
00217
00218
00219
00220 if (++count > 1)
00221 goto success;
00222 dns_rdataset_current(&nsec3paramset, &rdata);
00223 if (ignore(&rdata, &privateset))
00224 continue;
00225
00226
00227
00228
00229 goto success;
00230 }
00231
00232
00233
00234
00235
00236 if (build_nsec != NULL)
00237 *build_nsec = ISC_TRUE;
00238 goto success;
00239 }
00240
00241 if (build_nsec != NULL)
00242 *build_nsec = ISC_FALSE;
00243 if (build_nsec3 != NULL)
00244 *build_nsec3 = ISC_FALSE;
00245 if (!dns_rdataset_isassociated(&privateset))
00246 goto success;
00247
00248 signing = ISC_FALSE;
00249 nsec3chain = ISC_FALSE;
00250
00251 for (result = dns_rdataset_first(&privateset);
00252 result == ISC_R_SUCCESS;
00253 result = dns_rdataset_next(&privateset)) {
00254 dns_rdata_t rdata = DNS_RDATA_INIT;
00255 dns_rdata_t private = DNS_RDATA_INIT;
00256
00257 dns_rdataset_current(&privateset, &private);
00258 if (!dns_nsec3param_fromprivate(&private, &rdata,
00259 buf, sizeof(buf))) {
00260
00261
00262
00263
00264 if (private.length == 5 && private.data[0] != 0 &&
00265 private.data[3] == 0 && private.data[4] == 0)
00266 signing = ISC_TRUE;
00267 } else {
00268 if (CREATE(rdata.data[1]))
00269 nsec3chain = ISC_TRUE;
00270 }
00271 }
00272
00273 if (signing) {
00274 if (nsec3chain) {
00275 if (build_nsec3 != NULL)
00276 *build_nsec3 = ISC_TRUE;
00277 } else {
00278 if (build_nsec != NULL)
00279 *build_nsec = ISC_TRUE;
00280 }
00281 }
00282
00283 success:
00284 result = ISC_R_SUCCESS;
00285 failure:
00286 if (dns_rdataset_isassociated(&nsecset))
00287 dns_rdataset_disassociate(&nsecset);
00288 if (dns_rdataset_isassociated(&nsec3paramset))
00289 dns_rdataset_disassociate(&nsec3paramset);
00290 if (dns_rdataset_isassociated(&privateset))
00291 dns_rdataset_disassociate(&privateset);
00292 if (node != NULL)
00293 dns_db_detachnode(db, &node);
00294 return (result);
00295 }
00296
00297 isc_result_t
00298 dns_private_totext(dns_rdata_t *private, isc_buffer_t *buf) {
00299 isc_result_t result;
00300
00301 if (private->length < 5)
00302 return (ISC_R_NOTFOUND);
00303
00304 if (private->data[0] == 0) {
00305 unsigned char nsec3buf[DNS_NSEC3PARAM_BUFFERSIZE];
00306 unsigned char newbuf[DNS_NSEC3PARAM_BUFFERSIZE];
00307 dns_rdata_t rdata = DNS_RDATA_INIT;
00308 dns_rdata_nsec3param_t nsec3param;
00309 isc_boolean_t delete, init, nonsec;
00310 isc_buffer_t b;
00311
00312 if (!dns_nsec3param_fromprivate(private, &rdata, nsec3buf,
00313 sizeof(nsec3buf)))
00314 CHECK(ISC_R_FAILURE);
00315
00316 CHECK(dns_rdata_tostruct(&rdata, &nsec3param, NULL));
00317
00318 delete = ISC_TF((nsec3param.flags & DNS_NSEC3FLAG_REMOVE) != 0);
00319 init = ISC_TF((nsec3param.flags & DNS_NSEC3FLAG_INITIAL) != 0);
00320 nonsec = ISC_TF((nsec3param.flags & DNS_NSEC3FLAG_NONSEC) != 0);
00321
00322 nsec3param.flags &= ~(DNS_NSEC3FLAG_CREATE|
00323 DNS_NSEC3FLAG_REMOVE|
00324 DNS_NSEC3FLAG_INITIAL|
00325 DNS_NSEC3FLAG_NONSEC);
00326
00327 if (init)
00328 isc_buffer_putstr(buf, "Pending NSEC3 chain ");
00329 else if (delete)
00330 isc_buffer_putstr(buf, "Removing NSEC3 chain ");
00331 else
00332 isc_buffer_putstr(buf, "Creating NSEC3 chain ");
00333
00334 dns_rdata_reset(&rdata);
00335 isc_buffer_init(&b, newbuf, sizeof(newbuf));
00336 CHECK(dns_rdata_fromstruct(&rdata, dns_rdataclass_in,
00337 dns_rdatatype_nsec3param,
00338 &nsec3param, &b));
00339
00340 CHECK(dns_rdata_totext(&rdata, NULL, buf));
00341
00342 if (delete && !nonsec)
00343 isc_buffer_putstr(buf, " / creating NSEC chain");
00344 } else if (private->length == 5) {
00345 unsigned char alg = private->data[0];
00346 dns_keytag_t keyid = (private->data[2] | private->data[1] << 8);
00347 char keybuf[BUFSIZ], algbuf[DNS_SECALG_FORMATSIZE];
00348 isc_boolean_t delete = ISC_TF(private->data[3] != 0);
00349 isc_boolean_t complete = ISC_TF(private->data[4] != 0);
00350
00351 if (delete && complete)
00352 isc_buffer_putstr(buf, "Done removing signatures for ");
00353 else if (delete)
00354 isc_buffer_putstr(buf, "Removing signatures for ");
00355 else if (complete)
00356 isc_buffer_putstr(buf, "Done signing with ");
00357 else
00358 isc_buffer_putstr(buf, "Signing with ");
00359
00360 dns_secalg_format(alg, algbuf, sizeof(algbuf));
00361 sprintf(keybuf, "key %d/%s", keyid, algbuf);
00362 isc_buffer_putstr(buf, keybuf);
00363 } else
00364 return (ISC_R_NOTFOUND);
00365
00366 isc_buffer_putuint8(buf, 0);
00367 result = ISC_R_SUCCESS;
00368 failure:
00369 return (result);
00370 }