OpenDNSSEC-signer 1.2.1

/build/buildd-opendnssec_1.2.1.dfsg-1-ia64-j6OroR/opendnssec-1.2.1.dfsg/signer/src/signer/se_key.c

Go to the documentation of this file.
00001 /*
00002  * $Id: se_key.c 4294 2011-01-13 19:58:29Z jakob $
00003  *
00004  * Copyright (c) 2009 NLNet Labs. All rights reserved.
00005  *
00006  * Redistribution and use in source and binary forms, with or without
00007  * modification, are permitted provided that the following conditions
00008  * are met:
00009  * 1. Redistributions of source code must retain the above copyright
00010  *    notice, this list of conditions and the following disclaimer.
00011  * 2. Redistributions in binary form must reproduce the above copyright
00012  *    notice, this list of conditions and the following disclaimer in the
00013  *    documentation and/or other materials provided with the distribution.
00014  *
00015  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
00016  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
00017  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
00018  * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
00019  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
00020  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
00021  * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
00022  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
00023  * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
00024  * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
00025  * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00026  *
00027  */
00028 
00034 #include "signer/backup.h"
00035 #include "signer/se_key.h"
00036 #include "util/file.h"
00037 #include "util/log.h"
00038 #include "util/se_malloc.h"
00039 
00040 
00045 key_type*
00046 key_create(const char* locator, uint8_t algorithm, uint32_t flags,
00047     int publish, int ksk, int zsk)
00048 {
00049     key_type* key = (key_type*) se_malloc(sizeof(key_type));
00050 
00051     se_log_assert(locator);
00052     se_log_assert(algorithm);
00053     se_log_assert(flags);
00054 
00055     key->locator = se_strdup(locator);
00056     key->dnskey = NULL;
00057     key->hsmkey = NULL;
00058     key->params = NULL;
00059     key->algorithm = algorithm;
00060     key->flags = flags;
00061     key->publish = publish;
00062     key->ksk = ksk;
00063     key->zsk = zsk;
00064     key->next = NULL;
00065     return key;
00066 }
00067 
00068 
00073 key_type*
00074 key_recover_from_backup(FILE* fd)
00075 {
00076     key_type* key = NULL;
00077     const char* locator = NULL;
00078     uint8_t algorithm = 0;
00079     uint32_t flags = 0;
00080     int publish = 0;
00081     int ksk = 0;
00082     int zsk = 0;
00083     ldns_rr* rr = NULL;
00084 
00085     se_log_assert(fd);
00086 
00087     if (!backup_read_str(fd, &locator) ||
00088         !backup_read_uint8_t(fd, &algorithm) ||
00089         !backup_read_uint32_t(fd, &flags) ||
00090         !backup_read_int(fd, &publish) ||
00091         !backup_read_int(fd, &ksk) ||
00092         !backup_read_int(fd, &zsk) ||
00093         ldns_rr_new_frm_fp(&rr, fd, NULL, NULL, NULL) != LDNS_STATUS_OK ||
00094         !backup_read_check_str(fd, ";END"))
00095     {
00096         se_log_error("key part in backup file is corrupted");
00097         if (locator) {
00098             se_free((void*)locator);
00099         }
00100         if (rr) {
00101             ldns_rr_free(rr);
00102             rr = NULL;
00103         }
00104         return NULL;
00105     }
00106 
00107     key = (key_type*) se_malloc(sizeof(key_type));
00108     key->locator = locator;
00109     key->dnskey = rr;
00110     key->hsmkey = NULL;
00111     key->params = NULL;
00112     key->algorithm = algorithm;
00113     key->flags = flags;
00114     key->publish = publish;
00115     key->ksk = ksk;
00116     key->zsk = zsk;
00117     key->next = NULL;
00118 
00119     return key;
00120 }
00121 
00122 
00127 void
00128 key_cleanup(key_type* key)
00129 {
00130     if (key) {
00131         if (key->next) {
00132             key_cleanup(key->next);
00133             key->next = NULL;
00134         }
00135         if (key->locator) {
00136             se_free((void*)key->locator);
00137             key->locator = NULL;
00138         }
00139         if (key->dnskey) {
00140             ldns_rr_free(key->dnskey);
00141             key->dnskey = NULL;
00142         }
00143         if (key->hsmkey) {
00144             hsm_key_free(key->hsmkey);
00145             key->hsmkey = NULL;
00146         }
00147         if (key->params) {
00148             hsm_sign_params_free(key->params);
00149             key->params = NULL;
00150         }
00151         se_free((void*)key);
00152     } else {
00153         se_log_warning("cleanup empty key");
00154     }
00155 }
00156 
00157 
00162 void
00163 key_print(FILE* out, key_type* key)
00164 {
00165     se_log_assert(out);
00166     if (key) {
00167         fprintf(out, "\t\t\t<Key>\n");
00168         fprintf(out, "\t\t\t\t<Flags>%u</Flags>\n", key->flags);
00169         fprintf(out, "\t\t\t\t<Algorithm>%u</Algorithm>\n", key->algorithm);
00170         if (key->locator) {
00171             fprintf(out, "\t\t\t\t<Locator>%s</Locator>\n", key->locator);
00172         }
00173         if (key->ksk) {
00174             fprintf(out, "\t\t\t\t<KSK />\n");
00175         }
00176         if (key->zsk) {
00177             fprintf(out, "\t\t\t\t<ZSK />\n");
00178         }
00179         if (key->publish) {
00180             fprintf(out, "\t\t\t\t<Publish />\n");
00181         }
00182         fprintf(out, "\t\t\t</Key>\n");
00183         fprintf(out, "\n");
00184     }
00185     return;
00186 }
00187 
00188 
00193 keylist_type*
00194 keylist_create(void)
00195 {
00196     keylist_type* kl = (keylist_type*) se_malloc(sizeof(keylist_type));
00197 
00198     se_log_debug("create key list");
00199     kl->count = 0;
00200     kl->first_key = NULL;
00201     return kl;
00202 }
00203 
00204 
00209 int
00210 keylist_add(keylist_type* kl, key_type* key)
00211 {
00212     key_type* walk = NULL;
00213 
00214     se_log_assert(kl);
00215     se_log_assert(key);
00216     se_log_debug("add key locator %s", key->locator?key->locator:"(null)");
00217 
00218     if (kl->count == 0) {
00219         kl->first_key = key;
00220     } else {
00221         walk = kl->first_key;
00222         while (walk->next) {
00223             walk = walk->next;
00224         }
00225         walk->next = key;
00226     }
00227     kl->count += 1;
00228     return 0;
00229 }
00230 
00231 
00236 int
00237 key_compare(key_type* a, key_type* b)
00238 {
00239     se_log_assert(a);
00240     se_log_assert(b);
00241     return se_strcmp(a->locator, b->locator);
00242 }
00243 
00244 
00249 int
00250 keylist_delete(keylist_type* kl, key_type* key)
00251 {
00252     key_type* walk = NULL, *prev = NULL;
00253 
00254     se_log_assert(kl);
00255     se_log_assert(key);
00256     se_log_debug("delete key locator %s", key->locator?key->locator:"(null)");
00257 
00258     walk = kl->first_key;
00259     while (walk) {
00260         if (key_compare(walk, key) == 0) {
00261             key->next = walk->next;
00262             if (!prev) {
00263                 kl->first_key = key;
00264             } else {
00265                 prev->next = key;
00266             }
00267             kl->count -= 1;
00268             return 0;
00269         }
00270         prev = walk;
00271         walk = walk->next;
00272     }
00273 
00274     se_log_error("key locator %s not found in list",
00275         key->locator?key->locator:"(null)");
00276     return 1;
00277 }
00278 
00279 
00284 key_type*
00285 keylist_lookup(keylist_type* list, const char* locator)
00286 {
00287     key_type* search = NULL;
00288     size_t i = 0;
00289 
00290     if (!list || !locator) {
00291         return NULL;
00292     }
00293 
00294     search = list->first_key;
00295     for (i=0; i < list->count; i++) {
00296         if (search) {
00297             if (se_strcmp(search->locator, locator) == 0) {
00298                 return search;
00299             }
00300             search = search->next;
00301         } else {
00302             break;
00303         }
00304     }
00305     return NULL;
00306 }
00307 
00308 
00313 int
00314 keylist_compare(keylist_type* a, keylist_type* b)
00315 {
00316     key_type* ka, *kb;
00317     int ret = 0;
00318     size_t i = 0;
00319 
00320     se_log_assert(a);
00321     se_log_assert(b);
00322 
00323     if (a->count != b->count) {
00324         return a->count - b->count;
00325     }
00326 
00327     ka = a->first_key;
00328     kb = b->first_key;
00329     for (i=0; i < a->count; i++) {
00330         if (!ka && !kb) {
00331             se_log_warning("neither key a[%i] or key b[%i] exist", i, i);
00332             return 0;
00333         }
00334         if (!ka) {
00335             se_log_warning("key a[%i] does not exist", i);
00336             return -1;
00337         }
00338         if (!kb) {
00339             se_log_warning("key b[%i] does not exist", i);
00340             return -1;
00341         }
00342 
00343         ret = key_compare(ka, kb);
00344         if (ret == 0) {
00345             ret = ka->algorithm - kb->algorithm;
00346             if (ret == 0) {
00347                  ret = ka->flags - kb->flags;
00348                  if (ret == 0) {
00349                      ret = ka->publish - kb->publish;
00350                      if (ret == 0) {
00351                          ret = ka->ksk - kb->ksk;
00352                          if (ret == 0) {
00353                              ret = ka->zsk - kb->zsk;
00354                          }
00355                      }
00356                  }
00357             }
00358         }
00359 
00360         if (ret != 0) {
00361             return ret;
00362         }
00363         ka = ka->next;
00364         kb = kb->next;
00365     }
00366 
00367     return 0;
00368 }
00369 
00370 
00375 void
00376 keylist_cleanup(keylist_type* kl)
00377 {
00378     if (kl) {
00379         se_log_debug("clean up key list");
00380         if (kl->first_key) {
00381             key_cleanup(kl->first_key);
00382         }
00383         se_free((void*)kl);
00384     } else {
00385         se_log_warning("cleanup empty key list");
00386     }
00387 }
00388 
00389 
00394 void
00395 keylist_print(FILE* out, keylist_type* kl)
00396 {
00397     key_type* walk = NULL;
00398 
00399     se_log_assert(out);
00400     if (kl) {
00401         walk = kl->first_key;
00402         while (walk) {
00403             key_print(out, walk);
00404             walk = walk->next;
00405         }
00406     }
00407     return;
00408 }