]> git.ipfire.org Git - thirdparty/FORT-validator.git/commitdiff
Store BGPsec certs info, print at configured output
authorpcarana <pc.moreno2099@gmail.com>
Fri, 19 Jul 2019 17:04:26 +0000 (12:04 -0500)
committerpcarana <pc.moreno2099@gmail.com>
Fri, 19 Jul 2019 17:04:26 +0000 (12:04 -0500)
-Use struct 'router_key' to represent BGPsec certificates.
-Use reference count of Subject Key data (ID and public key) with 'sk_info' struct.
-Add router certificates info to local DB, as part of the refactor 'roa_table' was renamed to 'db_table'.
-Add configuration parameter 'output.bgpsec', the information is printed in hexadecimal representation (there's a TODO here: maybe encode and print as base64).
-Consider BGPsec keys in deltas.
-Use a constant for SKI length, since always is the same (20 bytes/octets).

28 files changed:
src/Makefile.am
src/config.c
src/config.h
src/object/bgpsec.c
src/object/bgpsec.h
src/object/certificate.c
src/object/router_key.c [new file with mode: 0644]
src/object/router_key.h
src/output_printer.c
src/output_printer.h
src/rtr/db/db_table.c [new file with mode: 0644]
src/rtr/db/db_table.h [new file with mode: 0644]
src/rtr/db/delta.c
src/rtr/db/delta.h
src/rtr/db/roa_table.c [deleted file]
src/rtr/db/roa_table.h [deleted file]
src/rtr/db/vrps.c
src/rtr/pdu_sender.c
src/rtr/pdu_sender.h
src/slurm/slurm_loader.c
src/slurm/slurm_loader.h
src/validation_handler.c
src/validation_handler.h
test/Makefile.am
test/impersonator.c
test/rtr/db/db_table_test.c [moved from test/rtr/db/roa_table_test.c with 92% similarity]
test/rtr/db/vrps_test.c
test/rtr/pdu_handler_test.c

index 7aea1e14fd37fb9dec61285ddb22397ed472e84d..78b75eaca2486e090474496019643168b0ea2733 100644 (file)
@@ -68,7 +68,7 @@ fort_SOURCES += object/ghostbusters.h object/ghostbusters.c
 fort_SOURCES += object/manifest.h object/manifest.c
 fort_SOURCES += object/name.h object/name.c
 fort_SOURCES += object/roa.h object/roa.c
-fort_SOURCES += object/router_key.h
+fort_SOURCES += object/router_key.c object/router_key.h
 fort_SOURCES += object/signed_object.h object/signed_object.c
 fort_SOURCES += object/tal.h object/tal.c
 fort_SOURCES += object/vcard.h object/vcard.c
@@ -88,8 +88,8 @@ fort_SOURCES += rtr/primitive_reader.c rtr/primitive_reader.h
 fort_SOURCES += rtr/primitive_writer.c rtr/primitive_writer.h
 fort_SOURCES += rtr/rtr.c rtr/rtr.h
 
+fort_SOURCES += rtr/db/db_table.c rtr/db/db_table.h
 fort_SOURCES += rtr/db/delta.c rtr/db/delta.h
-fort_SOURCES += rtr/db/roa_table.c rtr/db/roa_table.h
 fort_SOURCES += rtr/db/roa.c rtr/db/roa.h
 fort_SOURCES += rtr/db/vrp.h
 fort_SOURCES += rtr/db/vrps.c rtr/db/vrps.h
index a7737683b390b02e28c9e1d0d3714a89f9495086..971b7103193040bd15054b55f78f590fdc3cca2e 100644 (file)
@@ -85,7 +85,8 @@ struct rpki_config {
        struct {
                /** File where the validated ROAs will be stored */
                char *roa;
-               /** TODO (next iteration) Add BGPsec output */
+               /** File where the validated BGPsec certs will be stored */
+               char *bgpsec;
        } output;
 };
 
@@ -346,6 +347,14 @@ static const struct option_field options[] = {
                .doc = "File where ROAs will be stored in CSV format, use '-' to print at console",
                .arg_doc = "<file>",
        },
+       {
+               .id = 6001,
+               .name = "output.bgpsec",
+               .type = &gt_string,
+               .offset = offsetof(struct rpki_config, output.bgpsec),
+               .doc = "File where BGPsec certificates will be stored in CSV format, use '-' to print at console",
+               .arg_doc = "<file>",
+       },
 
        { 0 },
 };
@@ -548,6 +557,7 @@ set_default_values(void)
        rpki_config.log.filename_format = FNF_GLOBAL;
 
        rpki_config.output.roa = NULL;
+       rpki_config.output.bgpsec = NULL;
 
        return 0;
 
@@ -815,6 +825,12 @@ config_get_output_roa(void)
        return rpki_config.output.roa;
 }
 
+char const *
+config_get_output_bgpsec(void)
+{
+       return rpki_config.output.bgpsec;
+}
+
 void
 free_rpki_config(void)
 {
index ad6a9c340edcb301f5b0ddc2c3c2c982fe5f36e7..c3d86062489517e58a8dc19c48821e0266d68db5 100644 (file)
@@ -35,6 +35,7 @@ enum filename_format config_get_filename_format(void);
 char *config_get_rsync_program(void);
 struct string_array const *config_get_rsync_args(bool);
 char const *config_get_output_roa(void);
+char const *config_get_output_bgpsec(void);
 
 /* Needed public by the JSON module */
 void *get_rpki_config_field(struct option_field const *);
index e5bc894c35635d0cc6758d785c6343d590ebc4de..d2ef8ad18a4582f075a70646fde34dd96a6892e5 100644 (file)
@@ -4,36 +4,29 @@
 #include "validation_handler.h"
 
 struct resource_params {
-       struct router_key *router_key;
-       struct resources *resources;
+       unsigned char const     *ski;
+       unsigned char const     *spk;
+       size_t                  spk_len;
+       struct resources        *resources;
 };
 
 static int
 asn_cb(unsigned long asn, void *arg)
 {
        struct resource_params *params = arg;
-       struct router_key router_key;
 
        if (!resources_contains_asn(params->resources, asn))
                return pr_err("BGPsec certificate is not allowed for ASN %lu.",
                    asn);
 
-       memcpy(&router_key, params->router_key, sizeof(*params->router_key));
-       router_key.asn = asn;
-
-       return vhandler_handle_bgpsec(&router_key);
+       return vhandler_handle_bgpsec(params->ski, asn, params->spk,
+           params->spk_len);
 }
 
 int
-handle_bgpsec(X509 *cert, unsigned char *ski, int ski_len,
-    struct resources *resources)
+handle_bgpsec(X509 *cert, unsigned char const *ski, struct resources *resources)
 {
-       /*
-        * FIXME: Store the public key, SKI, and the resources
-        */
        struct resource_params res_params;
-       struct router_key router_key;
-       ASN1_OBJECT *cert_alg;
        X509_PUBKEY *pub_key;
        unsigned char const *cert_spk;
        int cert_spk_len;
@@ -43,22 +36,17 @@ handle_bgpsec(X509 *cert, unsigned char *ski, int ski_len,
        if (pub_key == NULL)
                return crypto_err("X509_get_X509_PUBKEY() returned NULL at BGPsec");
 
-       ok = X509_PUBKEY_get0_param(&cert_alg, &cert_spk, &cert_spk_len, NULL,
+       ok = X509_PUBKEY_get0_param(NULL, &cert_spk, &cert_spk_len, NULL,
            pub_key);
        if (!ok)
                return crypto_err("X509_PUBKEY_get0_param() returned %d at BGPsec",
                    ok);
 
-       router_key.spk = cert_spk;
-       router_key.spk_len = cert_spk_len;
-       router_key.ski = ski;
-       router_key.ski_len = ski_len;
-
-       res_params.router_key = &router_key;
+       res_params.spk = cert_spk;
+       res_params.spk_len = cert_spk_len;
+       res_params.ski = ski;
        res_params.resources = resources;
 
        ok = resources_foreach_asn(resources, asn_cb, &res_params);
-       /* FIXME Maybe this should be released elsewhere.. */
-       free(ski);
        return ok;
 }
index c34eba402649e64bc3b4472e113ba4c25818b81b..e1df212620c19f21585d76972fdf49dfcf0f89db 100644 (file)
@@ -4,6 +4,6 @@
 #include <openssl/x509.h>
 #include "resource.h"
 
-int handle_bgpsec(X509 *, unsigned char *, int, struct resources *);
+int handle_bgpsec(X509 *, unsigned char const *, struct resources *);
 
 #endif /* SRC_OBJECT_BGPSEC_H_ */
index dc27a79f8d565cd6935d749ba41b6f44da19c91b..735698ab9e334de117796a028f5f61fd29521ad0 100644 (file)
@@ -42,7 +42,6 @@ struct sia_uris {
 
 struct bgpsec_ski {
        X509 *cert;
-       int *ski_len;
        unsigned char **ski_data;
 };
 
@@ -953,9 +952,9 @@ handle_ski_bgpsec(X509_EXTENSION *ext, void *arg)
        if (tmp == NULL)
                goto end;
 
-       (*params->ski_len) = ski->length;
        memcpy(tmp, ski->data, ski->length);
-       *params->ski_data = tmp;
+       tmp[ski->length] = '\0';
+       *(params->ski_data) = tmp;
 
 end:
        ASN1_OCTET_STRING_free(ski);
@@ -1457,7 +1456,7 @@ certificate_validate_extensions_ca(X509 *cert, struct rpki_uri **mft,
 
 static int
 certificate_validate_extensions_bgpsec(X509 *cert, unsigned char **ski,
-    int *ski_len, struct certificate_refs *refs, enum rpki_policy *policy)
+    struct certificate_refs *refs, enum rpki_policy *policy)
 {
        struct bgpsec_ski ski_param;
        struct extension_handler handlers[] = {
@@ -1476,7 +1475,6 @@ certificate_validate_extensions_bgpsec(X509 *cert, unsigned char **ski,
 
        ski_param.cert = cert;
        ski_param.ski_data = ski;
-       ski_param.ski_len = ski_len;
 
        return handle_extensions(handlers, X509_get0_extensions(cert));
 }
@@ -1539,7 +1537,6 @@ certificate_traverse(struct rpp *rpp_parent, struct rpki_uri *cert_uri)
        enum cert_type type;
        struct rpp *pp;
        bool mft_retry;
-       int ski_len;
        int error;
 
        state = state_retrieve();
@@ -1598,7 +1595,7 @@ certificate_traverse(struct rpp *rpp_parent, struct rpki_uri *cert_uri)
                break;
        case BGPSEC:
                error = certificate_validate_extensions_bgpsec(cert, &ski,
-                   &ski_len, &refs, &policy);
+                   &refs, &policy);
                break;
        default:
                /* Validate as a CA */
@@ -1621,9 +1618,10 @@ certificate_traverse(struct rpp *rpp_parent, struct rpki_uri *cert_uri)
 
        if (type == BGPSEC) {
                /* This is an EE, so there's no manifest to process */
-               error = handle_bgpsec(cert, ski, ski_len,
+               error = handle_bgpsec(cert, ski,
                    x509stack_peek_resources(validation_certstack(state)));
                cert = NULL; /* Ownership stolen at x509stack_push */
+               free(ski); /* No need to remember it */
                x509stack_cancel(validation_certstack(state));
 
                goto revert_refs;
diff --git a/src/object/router_key.c b/src/object/router_key.c
new file mode 100644 (file)
index 0000000..81ca810
--- /dev/null
@@ -0,0 +1,103 @@
+#include "object/router_key.h"
+
+#include <string.h>
+#include "log.h"
+
+struct sk_info {
+       unsigned char   *ski;
+       /* SKI length its constant (see RK_SKI_LEN) */
+       unsigned char   *spk;
+       size_t          spk_len;
+       unsigned int    references;
+};
+
+static int
+uchar_create(unsigned char **result, size_t size)
+{
+       unsigned char *tmp;
+
+       tmp = malloc(size + 1);
+       if (tmp == NULL)
+               return pr_enomem();
+
+       *result = tmp;
+       return 0;
+}
+
+int
+router_key_init(struct router_key *key, unsigned char const *ski,
+    uint32_t as, unsigned char const *spk, size_t spk_len)
+{
+       struct sk_info *sk;
+       int error;
+
+       sk = malloc(sizeof(struct sk_info));
+       if (sk == NULL)
+               return pr_enomem();
+
+       error = uchar_create(&sk->ski, RK_SKI_LEN);
+       if (error) {
+               free(sk);
+               return pr_enomem();
+       }
+
+       error = uchar_create(&sk->spk, spk_len);
+       if (error) {
+               free(sk->ski);
+               free(sk);
+               return pr_enomem();
+       }
+
+       memcpy(sk->ski, ski, RK_SKI_LEN);
+       sk->ski[RK_SKI_LEN] = '\0';
+       memcpy(sk->spk, spk, spk_len);
+       sk->spk[spk_len] = '\0';
+       sk->spk_len = spk_len;
+       sk->references = 1;
+
+       key->as = as;
+       key->sk = sk;
+
+       return 0;
+}
+
+void
+router_key_cleanup(struct router_key *key)
+{
+       sk_info_refput(key->sk);
+}
+
+void
+sk_info_refget(struct sk_info *sk)
+{
+       sk->references++;
+}
+
+void
+sk_info_refput(struct sk_info *sk)
+{
+       sk->references--;
+       if (sk->references == 0) {
+               free(sk->ski);
+               free(sk->spk);
+               free(sk);
+       }
+}
+
+unsigned char *
+sk_info_get_ski(struct sk_info *sk)
+{
+       return sk->ski;
+}
+
+unsigned char *
+sk_info_get_spk(struct sk_info *sk)
+{
+       return sk->spk;
+}
+
+size_t
+sk_info_get_spk_len(struct sk_info *sk)
+{
+       return sk->spk_len;
+}
index 622be74f9fdcf4f92f91d740c4e548e242108b65..a6b612da6b3155ebc163d65a1c8700211083c446 100644 (file)
@@ -1,15 +1,37 @@
 #ifndef SRC_OBJECT_ROUTER_KEY_H_
 #define SRC_OBJECT_ROUTER_KEY_H_
 
+#include <stdint.h>
+#include <stdlib.h>
+
+/*
+ * SKI is always 20 bytes long rfc6487#section-4.8.2:
+ * "The Key Identifier used for resource certificates is the 160-bit {...}"
+ */
+#define RK_SKI_LEN     20
+
+/*
+ * Subject key info with ref counter, use getters to fetch its data
+ */
+struct sk_info;
+
 /*
- * Roouter Key representation
+ * Router Key representation
  */
 struct router_key {
-       unsigned char   *ski;
-       size_t          ski_len;
-       uint32_t        asn;
-       unsigned char   *spk;
-       size_t          spk_len;
+       uint32_t        as;
+       struct sk_info  *sk;
 };
 
+int router_key_init(struct router_key *, unsigned char const *, uint32_t,
+    unsigned char const *, size_t);
+void router_key_cleanup(struct router_key *);
+
+void sk_info_refget(struct sk_info *);
+void sk_info_refput(struct sk_info *);
+
+unsigned char *sk_info_get_ski(struct sk_info *);
+unsigned char *sk_info_get_spk(struct sk_info *);
+size_t sk_info_get_spk_len(struct sk_info *);
+
 #endif /* SRC_OBJECT_ROUTER_KEY_H_ */
index 464ec920f686346bac97a150fcb0f29aee8657d3..dd327297f1e8fde168efc311acc39fd139ae0d0c 100644 (file)
@@ -23,11 +23,10 @@ strv6addr(struct in6_addr const *addr)
 }
 
 static int
-load_output_file(FILE **result, bool *fopen)
+load_output_file(char const *output, FILE **result, bool *fopen)
 {
        FILE *tmp;
        struct stat stat;
-       char const *output = config_get_output_roa();
        int error;
 
        if (output == NULL) {
@@ -42,8 +41,10 @@ load_output_file(FILE **result, bool *fopen)
        }
 
        error = file_write(output, &tmp, &stat);
-       if (error)
+       if (error) {
+               *result = NULL;
                return error;
+       }
 
        *fopen = true;
        *result = tmp;
@@ -73,29 +74,113 @@ print_roa(struct vrp const *vrp, void *arg)
        return 0;
 }
 
-void
-output_print_roas(struct roa_table *roas)
+static int
+print_to_hex(unsigned char *data, size_t len, char **out)
 {
-       FILE *out;
-       bool fopen;
+       char *tmp;
+       char *init;
+       int i;
+
+       tmp = malloc(len * 3 + 1);
+       if (tmp == NULL)
+               return pr_enomem();
+
+       init = tmp;
+       for (i = 0; i < len * 3; i+=3) {
+               *tmp = ':';
+               tmp++;
+               tmp += sprintf(tmp, "%02X", data[i/3]);
+       }
+       *tmp = '\0';
+
+       *out = init;
+       return 0;
+}
+
+/*
+ * FIXME Improve this calls, maybe base64 encode and print?
+ */
+static int
+print_router_key(struct router_key const *key, void *arg)
+{
+       FILE *out = arg;
+       char *buf1;
+       char *buf2;
        int error;
 
-       error = load_output_file(&out, &fopen);
-       if (error) {
-               pr_err("Error getting file '%s'", config_get_output_roa());
-               return;
-       }
+       error = print_to_hex(sk_info_get_ski(key->sk), RK_SKI_LEN, &buf1);
+       if (error)
+               return error;
+       error = print_to_hex(sk_info_get_spk(key->sk),
+           sk_info_get_spk_len(key->sk), &buf2);
+       if (error)
+               return error;
+       fprintf(out, "AS%u,%s,%s\n", key->as, buf1, buf2);
+       free(buf1);
+       free(buf2);
+
+       return 0;
+}
+
+static int
+open_file(char const *loc, FILE **out, bool *fopen)
+{
+       int error;
+
+       error = load_output_file(loc, out, fopen);
+       if (error)
+               return pr_err("Error getting file '%s'", loc);
 
        /* No output configured */
-       if (out == NULL)
+       if (*out == NULL)
+               return -ENOENT;
+
+       return 0;
+}
+
+static void
+print_roas(struct db_table *db)
+{
+       FILE *out;
+       bool fopen;
+       int error;
+
+       out = NULL;
+       error = open_file(config_get_output_roa(), &out, &fopen);
+       if (error)
                return;
 
        fprintf(out, "ASN,Prefix,Max prefix length\n");
-       error = roa_table_foreach_roa(roas, print_roa, out);
+       error = db_table_foreach_roa(db, print_roa, out);
        if (fopen)
                file_close(out);
-       if (error) {
+       if (error)
                pr_err("Error printing ROAs");
+}
+
+static void
+print_router_keys(struct db_table *db)
+{
+       FILE *out;
+       bool fopen;
+       int error;
+
+       out = NULL;
+       error = open_file(config_get_output_bgpsec(), &out, &fopen);
+       if (error)
                return;
-       }
+
+       fprintf(out, "ASN,SKI,SPK\n");
+       error = db_table_foreach_router_key(db, print_router_key, out);
+       if (fopen)
+               file_close(out);
+       if (error)
+               pr_err("Error printing Router Keys");
+}
+
+void
+output_print_data(struct db_table *db)
+{
+       print_roas(db);
+       print_router_keys(db);
 }
index 47fcdb2dc9ae76e5e02f6d993b042d1381e10ab2..4bb089e2da27697fddbf93b072208ee3eafb686d 100644 (file)
@@ -1,8 +1,8 @@
 #ifndef SRC_OUTPUT_PRINTER_H_
 #define SRC_OUTPUT_PRINTER_H_
 
-#include "rtr/db/roa_table.h"
+#include "rtr/db/db_table.h"
 
-void output_print_roas(struct roa_table *);
+void output_print_data(struct db_table *);
 
 #endif /* SRC_OUTPUT_PRINTER_H_ */
diff --git a/src/rtr/db/db_table.c b/src/rtr/db/db_table.c
new file mode 100644 (file)
index 0000000..7c8438f
--- /dev/null
@@ -0,0 +1,420 @@
+#include "rtr/db/db_table.h"
+
+#include <sys/types.h> /* AF_INET, AF_INET6 (needed in OpenBSD) */
+#include <sys/socket.h> /* AF_INET, AF_INET6 (needed in OpenBSD) */
+#include "data_structure/uthash_nonfatal.h"
+
+struct hashable_roa {
+       struct vrp data;
+       UT_hash_handle hh;
+};
+
+struct hashable_key {
+       struct router_key data;
+       UT_hash_handle hh;
+};
+
+struct db_table {
+       struct hashable_roa *roas;
+       struct hashable_key *router_keys;
+};
+
+struct db_table *
+db_table_create(void)
+{
+       struct db_table *table;
+
+       table = malloc(sizeof(struct db_table));
+       if (table == NULL)
+               return NULL;
+
+       table->roas = NULL;
+       table->router_keys = NULL;
+       return table;
+}
+
+void
+db_table_destroy(struct db_table *table)
+{
+       struct hashable_roa *node;
+       struct hashable_roa *tmp;
+       struct hashable_key *node_key;
+       struct hashable_key *tmp_key;
+
+       HASH_ITER(hh, table->roas, node, tmp) {
+               HASH_DEL(table->roas, node);
+               free(node);
+       }
+
+       HASH_ITER(hh, table->router_keys, node_key, tmp_key) {
+               HASH_DEL(table->router_keys, node_key);
+               router_key_cleanup(&node_key->data);
+               free(node_key);
+       }
+
+       free(table);
+}
+
+int
+db_table_foreach_roa(struct db_table *table, vrp_foreach_cb cb, void *arg)
+{
+       struct hashable_roa *node, *tmp;
+       int error;
+
+       HASH_ITER(hh, table->roas, node, tmp) {
+               error = cb(&node->data, arg);
+               if (error)
+                       return error;
+       }
+
+       return 0;
+}
+
+int
+db_table_foreach_router_key(struct db_table *table, router_key_foreach_cb cb,
+    void *arg)
+{
+       struct hashable_key *node, *tmp;
+       int error;
+
+       HASH_ITER(hh, table->router_keys, node, tmp) {
+               error = cb(&node->data, arg);
+               if (error)
+                       return error;
+       }
+
+       return 0;
+}
+
+static struct hashable_roa *
+create_roa(uint32_t asn, uint8_t max_length)
+{
+       struct hashable_roa *roa;
+
+       roa = malloc(sizeof(struct hashable_roa));
+       if (roa == NULL)
+               return NULL;
+       /* Needed by uthash */
+       memset(roa, 0, sizeof(struct hashable_roa));
+
+       roa->data.asn = asn;
+       roa->data.max_prefix_length = max_length;
+
+       return roa;
+}
+
+static int
+add_roa(struct db_table *table, struct hashable_roa *new)
+{
+       struct hashable_roa *old;
+
+       errno = 0;
+       HASH_REPLACE(hh, table->roas, data, sizeof(new->data), new, old);
+       if (errno)
+               return -pr_errno(errno, "ROA couldn't be added to hash table");
+       if (old != NULL)
+               free(old);
+
+       return 0;
+}
+
+static int
+add_router_key(struct db_table *table, struct hashable_key *new)
+{
+       struct hashable_key *old;
+
+       errno = 0;
+       HASH_REPLACE(hh, table->router_keys, data, sizeof(new->data), new, old);
+       if (errno)
+               return -pr_errno(errno, "Router Key couldn't be added to hash table");
+       if (old != NULL) {
+               router_key_cleanup(&old->data);
+               free(old);
+       }
+
+       return 0;
+}
+
+static int
+duplicate_roa(struct db_table *dst, struct hashable_roa *new)
+{
+       struct vrp vrp;
+       struct ipv4_prefix prefix4;
+       struct ipv6_prefix prefix6;
+
+       vrp = new->data;
+       switch (vrp.addr_fam) {
+       case AF_INET:
+               prefix4.addr = vrp.prefix.v4;
+               prefix4.len = vrp.prefix_length;
+               return rtrhandler_handle_roa_v4(dst, vrp.asn, &prefix4,
+                   vrp.max_prefix_length);
+       case AF_INET6:
+               prefix6.addr = vrp.prefix.v6;
+               prefix6.len = vrp.prefix_length;
+               return rtrhandler_handle_roa_v6(dst, vrp.asn, &prefix6,
+                   vrp.max_prefix_length);
+       }
+
+       pr_crit("Unknown address family: %d", vrp.addr_fam);
+}
+
+static int
+duplicate_key(struct db_table *dst, struct hashable_key *new)
+{
+       struct sk_info *sk = new->data.sk;
+
+       return rtrhandler_handle_router_key(dst, sk_info_get_ski(sk),
+           new->data.as, sk_info_get_spk(sk), sk_info_get_spk_len(sk));
+}
+
+#define MERGE_ITER(table_prop, name, err_var)                          \
+       struct hashable_##name *node_##name, *tmp_##name, *found_##name;\
+       HASH_ITER(hh, src->table_prop, node_##name, tmp_##name) {       \
+               HASH_FIND(hh, dst->table_prop, &node_##name->data,      \
+                       sizeof(node_##name->data), found_##name);       \
+               if (found_##name != NULL)                               \
+                       continue;                                       \
+               err_var = duplicate_##name(dst, node_##name);           \
+               if (err_var)                                            \
+                       return err_var;                                 \
+       }
+
+static int
+db_table_merge(struct db_table *dst, struct db_table *src)
+{
+       int error;
+
+       /** Must look for elements due to the new mem allocation */
+       MERGE_ITER(roas, roa, error)
+       MERGE_ITER(router_keys, key, error)
+
+       return 0;
+}
+
+int
+db_table_clone(struct db_table **dst, struct db_table *src)
+{
+       int error;
+
+       *dst = db_table_create();
+       if (*dst == NULL)
+               return pr_enomem();
+
+       error = db_table_merge(*dst, src);
+       if (error)
+               free(*dst);
+
+       return error;
+}
+
+void
+db_table_remove_roa(struct db_table *table, struct vrp const *del)
+{
+       struct hashable_roa *ptr;
+
+       HASH_FIND(hh, table->roas, del, sizeof(*del), ptr);
+       if (ptr != NULL) {
+               HASH_DELETE(hh, table->roas, ptr);
+               free(ptr);
+       }
+}
+
+/*
+ * FIXME and TODO: add more funcs for router keys
+ * void
+ * db_table_remove_router_key(struct db_table *table,
+ *     struct router_key const *del)
+ * {
+ *     struct hashable_key *ptr;
+ *
+ *     HASH_FIND(hh, table->router_keys, del, sizeof(*del), ptr);
+ *     if (ptr != NULL) {
+ *             HASH_DELETE(hh, table->router_keys, ptr);
+ *             router_key_cleanup(&ptr->data);
+ *             free(ptr);
+ *     }
+ * }
+ */
+
+int
+rtrhandler_handle_roa_v4(struct db_table *table, uint32_t asn,
+    struct ipv4_prefix const *prefix4, uint8_t max_length)
+{
+       struct hashable_roa *roa;
+       int error;
+
+       roa = create_roa(asn, max_length);
+       if (roa == NULL)
+               return pr_enomem();
+       roa->data.prefix.v4 = prefix4->addr;
+       roa->data.prefix_length = prefix4->len;
+       roa->data.addr_fam = AF_INET;
+
+       error = add_roa(table, roa);
+       if (error)
+               free(roa);
+       return error;
+}
+
+int
+rtrhandler_handle_roa_v6(struct db_table *table, uint32_t asn,
+    struct ipv6_prefix const *prefix6, uint8_t max_length)
+{
+       struct hashable_roa *roa;
+       int error;
+
+       roa = create_roa(asn, max_length);
+       if (roa == NULL)
+               return pr_enomem();
+       roa->data.prefix.v6 = prefix6->addr;
+       roa->data.prefix_length = prefix6->len;
+       roa->data.addr_fam = AF_INET6;
+
+       error = add_roa(table, roa);
+       if (error)
+               free(roa);
+       return error;
+}
+
+int
+rtrhandler_handle_router_key(struct db_table *table,
+    unsigned char const *ski, uint32_t as, unsigned char const *spk,
+    size_t spk_len)
+{
+       struct hashable_key *key;
+       int error;
+
+       key = malloc(sizeof(struct hashable_key));
+       if (key == NULL)
+               return pr_enomem();
+       /* Needed by uthash */
+       memset(key, 0, sizeof(struct hashable_key));
+
+       error = router_key_init(&key->data, ski, as, spk, spk_len);
+       if (error) {
+               free(key);
+               return error;
+       }
+
+       error = add_router_key(table, key);
+       if (error) {
+               router_key_cleanup(&key->data);
+               free(key);
+       }
+       return error;
+}
+
+static int
+add_roa_delta(struct deltas *deltas, struct hashable_roa *roa, int op)
+{
+       union {
+               struct v4_address v4;
+               struct v6_address v6;
+       } addr;
+
+       switch (roa->data.addr_fam) {
+       case AF_INET:
+               addr.v4.prefix.addr = roa->data.prefix.v4;
+               addr.v4.prefix.len = roa->data.prefix_length;
+               addr.v4.max_length = roa->data.max_prefix_length;
+               return deltas_add_roa_v4(deltas, roa->data.asn, &addr.v4, op);
+       case AF_INET6:
+               addr.v6.prefix.addr = roa->data.prefix.v6;
+               addr.v6.prefix.len = roa->data.prefix_length;
+               addr.v6.max_length = roa->data.max_prefix_length;
+               return deltas_add_roa_v6(deltas, roa->data.asn, &addr.v6, op);
+       }
+
+       pr_crit("Unknown address family: %d", roa->data.addr_fam);
+}
+
+/*
+ * Copies `@roas1 - roas2` into @deltas.
+ *
+ * (Places the ROAs that exist in @roas1 but not in @roas2 in @deltas.)
+ */
+static int
+add_roa_deltas(struct hashable_roa *roas1, struct hashable_roa *roas2,
+    struct deltas *deltas, int op)
+{
+       struct hashable_roa *n1; /* A node from @roas1 */
+       struct hashable_roa *n2; /* A node from @roas2 */
+       int error;
+
+       for (n1 = roas1; n1 != NULL; n1 = n1->hh.next) {
+               HASH_FIND(hh, roas2, &n1->data, sizeof(n1->data), n2);
+               if (n2 == NULL) {
+                       error = add_roa_delta(deltas, n1, op);
+                       if (error)
+                               return error;
+               }
+       }
+
+       return 0;
+}
+
+static int
+add_router_key_delta(struct deltas *deltas, struct hashable_key *key, int op)
+{
+       return deltas_add_bgpsec(deltas, &key->data, op);
+}
+
+/*
+ * Copies `@keys1 - keys2` into @deltas.
+ *
+ * (Places the Router Keys that exist in @keys1 but not in @key2 in @deltas.)
+ */
+static int
+add_router_key_deltas(struct hashable_key *keys1, struct hashable_key *keys2,
+    struct deltas *deltas, int op)
+{
+       struct hashable_key *n1; /* A node from @keys1 */
+       struct hashable_key *n2; /* A node from @keys2 */
+       int error;
+
+       for (n1 = keys1; n1 != NULL; n1 = n1->hh.next) {
+               HASH_FIND(hh, keys2, &n1->data, sizeof(n1->data), n2);
+               if (n2 == NULL) {
+                       error = add_router_key_delta(deltas, n1, op);
+                       if (error)
+                               return error;
+               }
+       }
+
+       return 0;
+}
+
+int
+compute_deltas(struct db_table *old, struct db_table *new,
+    struct deltas **result)
+{
+       struct deltas *deltas;
+       int error;
+
+       error = deltas_create(&deltas);
+       if (error)
+               return error;
+
+       error = add_roa_deltas(new->roas, old->roas, deltas, FLAG_ANNOUNCEMENT);
+       if (error)
+               goto fail;
+       error = add_roa_deltas(old->roas, new->roas, deltas, FLAG_WITHDRAWAL);
+       if (error)
+               goto fail;
+       error = add_router_key_deltas(new->router_keys, old->router_keys,
+           deltas, FLAG_ANNOUNCEMENT);
+       if (error)
+               goto fail;
+       error = add_router_key_deltas(old->router_keys, new->router_keys,
+           deltas, FLAG_WITHDRAWAL);
+       if (error)
+               goto fail;
+
+       *result = deltas;
+       return 0;
+
+fail:
+       deltas_refput(deltas);
+       return error;
+}
diff --git a/src/rtr/db/db_table.h b/src/rtr/db/db_table.h
new file mode 100644 (file)
index 0000000..178bc66
--- /dev/null
@@ -0,0 +1,28 @@
+#ifndef SRC_RTR_DB_DB_TABLE_H_
+#define SRC_RTR_DB_DB_TABLE_H_
+
+#include "rtr/db/delta.h"
+#include "rtr/db/vrp.h"
+
+struct db_table;
+
+struct db_table *db_table_create(void);
+void db_table_destroy(struct db_table *);
+
+int db_table_clone(struct db_table **, struct db_table *);
+
+int db_table_foreach_roa(struct db_table *, vrp_foreach_cb, void *);
+void db_table_remove_roa(struct db_table *, struct vrp const *);
+
+int db_table_foreach_router_key(struct db_table *, router_key_foreach_cb cb,
+    void *);
+
+int rtrhandler_handle_roa_v4(struct db_table *, uint32_t,
+    struct ipv4_prefix const *, uint8_t);
+int rtrhandler_handle_roa_v6(struct db_table *, uint32_t,
+    struct ipv6_prefix const *, uint8_t);
+int rtrhandler_handle_router_key(struct db_table *, unsigned char const *,
+    uint32_t, unsigned char const *, size_t);
+int compute_deltas(struct db_table *, struct db_table *, struct deltas **);
+
+#endif /* SRC_RTR_DB_DB_TABLE_H_ */
index 0fd087cc1e5bf27681c1391a26b50e6bf688323c..9461099f7d826581649466badc246e8ebc9182f7 100644 (file)
@@ -18,11 +18,8 @@ struct delta_v6 {
 };
 
 struct delta_bsec {
-       unsigned char *ski;
-       int *ski_len;
        uint32_t as;
-       unsigned char *spk;
-       int *spk_len;
+       struct sk_info *sk;
 };
 
 ARRAY_LIST(deltas_v6, struct delta_v6)
@@ -46,6 +43,12 @@ struct deltas {
        atomic_uint references;
 };
 
+static void
+delta_bsec_cleanup(struct delta_bsec *bsec)
+{
+       sk_info_refput(bsec->sk);
+}
+
 int
 deltas_create(struct deltas **_result)
 {
@@ -85,8 +88,9 @@ deltas_refput(struct deltas *deltas)
                deltas_v4_cleanup(&deltas->v4.removes, NULL);
                deltas_v6_cleanup(&deltas->v6.adds, NULL);
                deltas_v6_cleanup(&deltas->v6.removes, NULL);
-               deltas_bgpsec_cleanup(&deltas->bgpsec.adds, NULL);
-               deltas_bgpsec_cleanup(&deltas->bgpsec.removes, NULL);
+               deltas_bgpsec_cleanup(&deltas->bgpsec.adds, delta_bsec_cleanup);
+               deltas_bgpsec_cleanup(&deltas->bgpsec.removes,
+                   delta_bsec_cleanup);
                free(deltas);
        }
 }
@@ -132,16 +136,13 @@ deltas_add_roa_v6(struct deltas *deltas, uint32_t as, struct v6_address *addr,
 }
 
 int
-deltas_add_bgpsec(struct deltas *deltas, unsigned char *ski, int ski_len,
-    uint32_t as, unsigned char *spk, int spk_len, int op)
+deltas_add_bgpsec(struct deltas *deltas, struct router_key *key, int op)
 {
        struct delta_bsec delta = {
-               .ski = ski,
-               .ski_len = ski_len,
-               .as = as,
-               .spk = spk,
-               .spk_len = spk_len,
+               .as = key->as,
+               .sk = key->sk,
        };
+       sk_info_refget(key->sk);
 
        switch (op) {
        case FLAG_ANNOUNCEMENT:
@@ -229,12 +230,11 @@ __foreach_bgpsec(struct deltas_bgpsec *array, delta_bgpsec_foreach_cb cb,
        delta.flags = flags;
 
        ARRAYLIST_FOREACH(array, d, i) {
-               delta.router_key.ski = d->ski;
-               delta.router_key.ski_len = d->ski_len;
-               delta.router_key.asn = d->as;
-               delta.router_key.spk = d->spk;
-               delta.router_key.spk_len = d->spk_len;
+               delta.router_key.as = d->as;
+               delta.router_key.sk = d->sk;
+               sk_info_refget(d->sk);
                error = cb(&delta, arg);
+               sk_info_refput(d->sk);
                if (error)
                        return error;
        }
index 7512b31790ae93ab00b550223f19b5c2dd98ba15..7b70d6fdc2b11d0cfa4f67497cf931ced6968c4b 100644 (file)
@@ -1,6 +1,7 @@
 #ifndef SRC_DELTA_H_
 #define SRC_DELTA_H_
 
+#include "object/router_key.h"
 #include "rtr/db/roa.h"
 #include "rtr/db/vrp.h"
 
@@ -12,8 +13,7 @@ void deltas_refput(struct deltas *);
 
 int deltas_add_roa_v4(struct deltas *, uint32_t, struct v4_address *, int);
 int deltas_add_roa_v6(struct deltas *, uint32_t, struct v6_address *, int);
-int deltas_add_bgpsec(struct deltas *, unsigned char *, int, uint32_t,
-    unsigned char *, int, int);
+int deltas_add_bgpsec(struct deltas *, struct router_key *, int);
 
 bool deltas_is_empty(struct deltas *);
 int deltas_foreach(serial_t, struct deltas *, delta_vrp_foreach_cb,
diff --git a/src/rtr/db/roa_table.c b/src/rtr/db/roa_table.c
deleted file mode 100644 (file)
index 3229069..0000000
+++ /dev/null
@@ -1,282 +0,0 @@
-#include "rtr/db/roa_table.h"
-
-#include <sys/types.h> /* AF_INET, AF_INET6 (needed in OpenBSD) */
-#include <sys/socket.h> /* AF_INET, AF_INET6 (needed in OpenBSD) */
-#include "data_structure/uthash_nonfatal.h"
-
-struct hashable_roa {
-       struct vrp data;
-       UT_hash_handle hh;
-};
-
-/* FIXME Update whole roa_table logic */
-struct hashable_keys {
-       struct router_key data;
-       UT_hash_handle hh;
-};
-
-struct roa_table {
-       struct hashable_roa *roas;
-       struct hashable_keys *router_keys;
-};
-
-struct roa_table *
-roa_table_create(void)
-{
-       struct roa_table *table;
-
-       table = malloc(sizeof(struct roa_table));
-       if (table == NULL)
-               return NULL;
-
-       table->roas = NULL;
-       return table;
-}
-
-void
-roa_table_destroy(struct roa_table *table)
-{
-       struct hashable_roa *node;
-       struct hashable_roa *tmp;
-
-       HASH_ITER(hh, table->roas, node, tmp) {
-               HASH_DEL(table->roas, node);
-               free(node);
-       }
-
-       free(table);
-}
-
-int
-roa_table_foreach_roa(struct roa_table *table, vrp_foreach_cb cb, void *arg)
-{
-       struct hashable_roa *node, *tmp;
-       int error;
-
-       HASH_ITER(hh, table->roas, node, tmp) {
-               error = cb(&node->data, arg);
-               if (error)
-                       return error;
-       }
-
-       return 0;
-}
-
-static struct hashable_roa *
-create_roa(uint32_t asn, uint8_t max_length)
-{
-       struct hashable_roa *roa;
-
-       roa = malloc(sizeof(struct hashable_roa));
-       if (roa == NULL)
-               return NULL;
-       /* Needed by uthash */
-       memset(roa, 0, sizeof(struct hashable_roa));
-
-       roa->data.asn = asn;
-       roa->data.max_prefix_length = max_length;
-
-       return roa;
-}
-
-static int
-add_roa(struct roa_table *table, struct hashable_roa *new)
-{
-       struct hashable_roa *old;
-
-       errno = 0;
-       HASH_REPLACE(hh, table->roas, data, sizeof(new->data), new, old);
-       if (errno)
-               return -pr_errno(errno, "ROA couldn't be added to hash table");
-       if (old != NULL)
-               free(old);
-
-       return 0;
-}
-
-static int
-duplicate_roa(struct roa_table *dst, struct hashable_roa *new)
-{
-       struct vrp vrp;
-       struct ipv4_prefix prefix4;
-       struct ipv6_prefix prefix6;
-
-       vrp = new->data;
-       switch (vrp.addr_fam) {
-       case AF_INET:
-               prefix4.addr = vrp.prefix.v4;
-               prefix4.len = vrp.prefix_length;
-               return rtrhandler_handle_roa_v4(dst, vrp.asn, &prefix4,
-                   vrp.max_prefix_length);
-       case AF_INET6:
-               prefix6.addr = vrp.prefix.v6;
-               prefix6.len = vrp.prefix_length;
-               return rtrhandler_handle_roa_v6(dst, vrp.asn, &prefix6,
-                   vrp.max_prefix_length);
-       }
-
-       pr_crit("Unknown address family: %d", vrp.addr_fam);
-}
-
-int
-roa_table_merge(struct roa_table *dst, struct roa_table *src)
-{
-       struct hashable_roa *node, *tmp, *found;
-       int error;
-
-       /** Must look for it due to the new mem allocation */
-       HASH_ITER(hh, src->roas, node, tmp) {
-               HASH_FIND(hh, dst->roas, &node->data, sizeof(node->data),
-                   found);
-               if (found != NULL)
-                       continue;
-               error = duplicate_roa(dst, node);
-               if (error)
-                       return error;
-       }
-
-       return 0;
-}
-
-int
-roa_table_clone(struct roa_table **dst, struct roa_table *src)
-{
-       int error;
-
-       *dst = roa_table_create();
-       if (*dst == NULL)
-               return pr_enomem();
-
-       error = roa_table_merge(*dst, src);
-       if (error)
-               free(*dst);
-
-       return error;
-}
-
-void
-roa_table_remove_roa(struct roa_table *table, struct vrp const *del)
-{
-       struct hashable_roa *ptr;
-
-       HASH_FIND(hh, table->roas, del, sizeof(*del), ptr);
-       if (ptr != NULL) {
-               HASH_DELETE(hh, table->roas, ptr);
-               free(ptr);
-       }
-}
-
-int
-rtrhandler_handle_roa_v4(struct roa_table *table, uint32_t asn,
-    struct ipv4_prefix const *prefix4, uint8_t max_length)
-{
-       struct hashable_roa *roa;
-       int error;
-
-       roa = create_roa(asn, max_length);
-       if (roa == NULL)
-               return pr_enomem();
-       roa->data.prefix.v4 = prefix4->addr;
-       roa->data.prefix_length = prefix4->len;
-       roa->data.addr_fam = AF_INET;
-
-       error = add_roa(table, roa);
-       if (error)
-               free(roa);
-       return error;
-}
-
-int
-rtrhandler_handle_roa_v6(struct roa_table *table, uint32_t asn,
-    struct ipv6_prefix const *prefix6, uint8_t max_length)
-{
-       struct hashable_roa *roa;
-       int error;
-
-       roa = create_roa(asn, max_length);
-       if (roa == NULL)
-               return pr_enomem();
-       roa->data.prefix.v6 = prefix6->addr;
-       roa->data.prefix_length = prefix6->len;
-       roa->data.addr_fam = AF_INET6;
-
-       error = add_roa(table, roa);
-       if (error)
-               free(roa);
-       return error;
-}
-
-static int
-add_delta(struct deltas *deltas, struct hashable_roa *roa, int op)
-{
-       union {
-               struct v4_address v4;
-               struct v6_address v6;
-       } addr;
-
-       switch (roa->data.addr_fam) {
-       case AF_INET:
-               addr.v4.prefix.addr = roa->data.prefix.v4;
-               addr.v4.prefix.len = roa->data.prefix_length;
-               addr.v4.max_length = roa->data.max_prefix_length;
-               return deltas_add_roa_v4(deltas, roa->data.asn, &addr.v4, op);
-       case AF_INET6:
-               addr.v6.prefix.addr = roa->data.prefix.v6;
-               addr.v6.prefix.len = roa->data.prefix_length;
-               addr.v6.max_length = roa->data.max_prefix_length;
-               return deltas_add_roa_v6(deltas, roa->data.asn, &addr.v6, op);
-       }
-
-       pr_crit("Unknown address family: %d", roa->data.addr_fam);
-}
-
-/*
- * Copies `@roas1 - roas2` into @deltas.
- *
- * (Places the ROAs that exist in @roas1 but not in @roas2 in @deltas.)
- */
-static int
-add_deltas(struct hashable_roa *roas1, struct hashable_roa *roas2,
-    struct deltas *deltas, int op)
-{
-       struct hashable_roa *n1; /* A node from @roas1 */
-       struct hashable_roa *n2; /* A node from @roas2 */
-       int error;
-
-       for (n1 = roas1; n1 != NULL; n1 = n1->hh.next) {
-               HASH_FIND(hh, roas2, &n1->data, sizeof(n1->data), n2);
-               if (n2 == NULL) {
-                       error = add_delta(deltas, n1, op);
-                       if (error)
-                               return error;
-               }
-       }
-
-       return 0;
-}
-
-int
-compute_deltas(struct roa_table *old, struct roa_table *new,
-    struct deltas **result)
-{
-       struct deltas *deltas;
-       int error;
-
-       error = deltas_create(&deltas);
-       if (error)
-               return error;
-
-       error = add_deltas(new->roas, old->roas, deltas, FLAG_ANNOUNCEMENT);
-       if (error)
-               goto fail;
-       error = add_deltas(old->roas, new->roas, deltas, FLAG_WITHDRAWAL);
-       if (error)
-               goto fail;
-
-       *result = deltas;
-       return 0;
-
-fail:
-       deltas_refput(deltas);
-       return error;
-}
diff --git a/src/rtr/db/roa_table.h b/src/rtr/db/roa_table.h
deleted file mode 100644 (file)
index f977639..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-#ifndef SRC_ROA_TABLE_H_
-#define SRC_ROA_TABLE_H_
-
-#include "rtr/db/delta.h"
-#include "rtr/db/vrp.h"
-
-struct roa_table;
-
-struct roa_table *roa_table_create(void);
-void roa_table_destroy(struct roa_table *);
-
-int roa_table_merge(struct roa_table *, struct roa_table *);
-int roa_table_clone(struct roa_table **, struct roa_table *);
-
-int roa_table_foreach_roa(struct roa_table *, vrp_foreach_cb, void *);
-void roa_table_remove_roa(struct roa_table *, struct vrp const *);
-
-int rtrhandler_handle_roa_v4(struct roa_table *, uint32_t,
-    struct ipv4_prefix const *, uint8_t);
-int rtrhandler_handle_roa_v6(struct roa_table *, uint32_t,
-    struct ipv6_prefix const *, uint8_t);
-
-int compute_deltas(struct roa_table *, struct roa_table *, struct deltas **);
-
-#endif /* SRC_ROA_TABLE_H_ */
index f1ffb0c104d95ed868a0ef2250a9bfbb7f66f1f0..b8a03bd5512299df56e876543e3411f8fda993cf 100644 (file)
@@ -11,7 +11,7 @@
 #include "data_structure/array_list.h"
 #include "object/router_key.h"
 #include "object/tal.h"
-#include "rtr/db/roa_table.h"
+#include "rtr/db/db_table.h"
 #include "slurm/slurm_loader.h"
 
 /*
@@ -39,7 +39,7 @@ struct state {
         * (We use this to know we're supposed to generate a @deltas entry
         * during the current iteration.)
         */
-       struct roa_table *base;
+       struct db_table *base;
        /** ROA changes to @base over time. */
        struct deltas_db deltas;
 
@@ -94,7 +94,7 @@ void
 vrps_destroy(void)
 {
        if (state.base != NULL)
-               roa_table_destroy(state.base);
+               db_table_destroy(state.base);
        deltas_db_cleanup(&state.deltas, deltagroup_cleanup);
        pthread_rwlock_destroy(&lock); /* Nothing to do with error code */
 }
@@ -114,39 +114,35 @@ __handle_roa_v6(uint32_t as, struct ipv6_prefix const * prefix,
 }
 
 int
-__handle_bgpsec(struct router_key const *router_key, void *arg)
+__handle_bgpsec(unsigned char const *ski, uint32_t as, unsigned char const *spk,
+    size_t spk_len, void *arg)
 {
-       pr_debug("Handling BGPsec for ASN %u", router_key->asn);
-       /*
-        * FIXME Add RTR handler
-        * return rtrhandler_handle_router_key(arg, as, prefix, max_length);
-        */
-       return 0;
+       return rtrhandler_handle_router_key(arg, ski, as, spk, spk_len);
 }
 
 static int
-__perform_standalone_validation(struct roa_table **result)
+__perform_standalone_validation(struct db_table **result)
 {
-       struct roa_table *roas;
+       struct db_table *db;
        struct validation_handler validation_handler;
        int error;
 
-       roas = roa_table_create();
-       if (roas == NULL)
+       db = db_table_create();
+       if (db == NULL)
                return pr_enomem();
 
        validation_handler.handle_roa_v4 = __handle_roa_v4;
        validation_handler.handle_roa_v6 = __handle_roa_v6;
        validation_handler.handle_bgpsec = __handle_bgpsec;
-       validation_handler.arg = roas;
+       validation_handler.arg = db;
 
        error = perform_standalone_validation(&validation_handler);
        if (error) {
-               roa_table_destroy(roas);
+               db_table_destroy(db);
                return error;
        }
 
-       *result = roas;
+       *result = db;
        return 0;
 }
 
@@ -233,8 +229,8 @@ vrps_purge(struct deltas **deltas)
 int
 vrps_update(bool *changed)
 {
-       struct roa_table *old_base;
-       struct roa_table *new_base;
+       struct db_table *old_base;
+       struct db_table *new_base;
        struct deltas *deltas; /* Deltas in raw form */
        struct delta_group deltas_node; /* Deltas in database node form */
        serial_t min_serial;
@@ -311,10 +307,10 @@ vrps_update(bool *changed)
        rwlock_unlock(&lock);
 
        if (old_base != NULL)
-               roa_table_destroy(old_base);
+               db_table_destroy(old_base);
 
        /* Print after validation to avoid duplicated info */
-       output_print_roas(new_base);
+       output_print_data(new_base);
 
        return 0;
 
@@ -322,8 +318,8 @@ revert_deltas:
        deltas_refput(deltas);
 revert_base:
        /* Print info that was already validated */
-       output_print_roas(new_base);
-       roa_table_destroy(new_base);
+       output_print_data(new_base);
+       db_table_destroy(new_base);
        return error;
 }
 
@@ -343,7 +339,7 @@ vrps_foreach_base_roa(vrp_foreach_cb cb, void *arg)
                return error;
 
        if (state.base != NULL)
-               error = roa_table_foreach_roa(state.base, cb, arg);
+               error = db_table_foreach_roa(state.base, cb, arg);
        else
                error = -EAGAIN;
 
@@ -402,7 +398,7 @@ vrps_foreach_filtered_delta(struct deltas_db *deltas, delta_vrp_foreach_cb cb,
         */
        SLIST_INIT(&filtered_vrps);
        ARRAYLIST_FOREACH(deltas, group, i) {
-               /* FIXME Add function for router keys */
+               /* FIXME Add cb function for router keys */
                error = deltas_foreach(group->serial, group->deltas,
                    vrp_ovrd_remove, NULL, &filtered_vrps);
                if (error)
index bd7cb00e63938bb888dbf766d57456fad391cc15..547ef260bf348ccc78954fb7a2c91c59b699a08c 100644 (file)
@@ -170,28 +170,36 @@ send_router_key_pdu(int fd, struct router_key const *router_key, uint8_t flags)
        reserved += (flags << 8);
        set_header_values(&pdu.header, PDU_TYPE_ROUTER_KEY, reserved);
 
-       pdu.ski = router_key->ski;
-       pdu.ski_len = router_key->ski_len;
-       pdu.asn = router_key->asn;
-       pdu.spki = router_key->spk;
-       pdu.spki_len = router_key->spk_len;
+       pdu.ski = sk_info_get_ski(router_key->sk);
+       pdu.ski_len = RK_SKI_LEN;
+       pdu.asn = router_key->as;
+       pdu.spki = sk_info_get_spk(router_key->sk);
+       pdu.spki_len = sk_info_get_spk_len(router_key->sk);
        pdu.header.length = RTRPDU_HDR_LEN
-           + router_key->ski_len
-           + sizeof(router_key->asn)
-           + router_key->spk_len;
+           + RK_SKI_LEN
+           + sizeof(router_key->as)
+           + pdu.spki_len;
+       sk_info_refget(router_key->sk);
 
        data = malloc(pdu.header.length);
-       if (data == NULL)
-               return pr_enomem();
+       if (data == NULL) {
+               error = pr_enomem();
+               goto release_sk;
+       }
 
        len = serialize_router_key_pdu(&pdu, data);
-       if (len != pdu.header.length)
+       if (len != pdu.header.length) {
+               sk_info_refput(router_key->sk);
+               free(data);
                pr_crit("Serialized Router Key PDU is %zu bytes, not the expected %u.",
                    len, pdu.header.length);
+       }
 
        error = send_response(fd, data, len);
-
        free(data);
+
+release_sk:
+       sk_info_refput(router_key->sk);
        return error;
 }
 
index 413061d8ca6332bda0bdf3e7b3d887f53254acda..58b179cf3aef5e9d59ba98113fb419bd7597ca18 100644 (file)
@@ -2,6 +2,7 @@
 #define SRC_RTR_PDU_SENDER_H_
 
 #include "pdu.h"
+#include "object/router_key.h"
 #include "rtr/db/vrps.h"
 
 void init_sender_common(int, int, uint8_t);
index 8b089b4e2afdf1becf2a7acba5bb77c3964e3e9b..482097a1557c9c9bd85783986356ae37c3ba8658 100644 (file)
@@ -39,10 +39,10 @@ slurm_cleanup(void)
 static int
 slurm_pfx_filters_apply(struct vrp const *vrp, void *arg)
 {
-       struct roa_table *table = arg;
+       struct db_table *table = arg;
 
        if (slurm_db_vrp_is_filtered(vrp))
-               roa_table_remove_roa(table, vrp);
+               db_table_remove_roa(table, vrp);
 
        return 0;
 }
@@ -50,7 +50,7 @@ slurm_pfx_filters_apply(struct vrp const *vrp, void *arg)
 static int
 slurm_pfx_assertions_add(struct slurm_prefix *prefix, void *arg)
 {
-       struct roa_table *table = arg;
+       struct db_table *table = arg;
        struct ipv4_prefix prefix4;
        struct ipv6_prefix prefix6;
        struct vrp vrp;
@@ -76,7 +76,7 @@ slurm_pfx_assertions_add(struct slurm_prefix *prefix, void *arg)
 }
 
 static int
-slurm_pfx_assertions_apply(struct roa_table *base)
+slurm_pfx_assertions_apply(struct db_table *base)
 {
        return slurm_db_foreach_assertion_prefix(slurm_pfx_assertions_add,
            base);
@@ -88,9 +88,9 @@ slurm_pfx_assertions_apply(struct roa_table *base)
  * On any error the SLURM won't be applied to @base.
  */
 int
-slurm_apply(struct roa_table **base)
+slurm_apply(struct db_table **base)
 {
-       struct roa_table *new_base;
+       struct db_table *new_base;
        bool loaded;
        int error;
 
@@ -103,25 +103,25 @@ slurm_apply(struct roa_table **base)
                return 0;
 
        /* Deep copy of the base so that updates can be reverted */
-       error = roa_table_clone(&new_base, *base);
+       error = db_table_clone(&new_base, *base);
        if (error)
                goto cleanup;
 
-       error = roa_table_foreach_roa(new_base, slurm_pfx_filters_apply,
+       error = db_table_foreach_roa(new_base, slurm_pfx_filters_apply,
            new_base);
        if (error)
                goto release_new;
 
        error = slurm_pfx_assertions_apply(new_base);
        if (!error) {
-               roa_table_destroy(*base);
+               db_table_destroy(*base);
                *base = new_base;
                goto cleanup;
        }
 
        /** TODO (next iteration) Apply BGPsec filters and assertions */
 release_new:
-       roa_table_destroy(new_base);
+       db_table_destroy(new_base);
 cleanup:
        slurm_cleanup();
        return error;
index 55093ccd226554ac12d738d78b440d146e169915..c9801cc03359805bc4cf6130289af05e3acedfed 100644 (file)
@@ -1,8 +1,8 @@
 #ifndef SRC_SLURM_SLURM_LOADER_H_
 #define SRC_SLURM_SLURM_LOADER_H_
 
-#include "rtr/db/roa_table.h"
+#include "rtr/db/db_table.h"
 
-int slurm_apply(struct roa_table **);
+int slurm_apply(struct db_table **);
 
 #endif /* SRC_SLURM_SLURM_LOADER_H_ */
index ec17b12779ef9c372b878bd1efd0644904883b7c..c9cc3bf61d0bbe7adbb636771cd06b9c71a86287 100644 (file)
@@ -54,7 +54,8 @@ vhandler_handle_roa_v6(uint32_t as, struct ipv6_prefix const *prefix,
 }
 
 int
-vhandler_handle_bgpsec(struct router_key const *router_key)
+vhandler_handle_bgpsec(unsigned char const *ski, uint32_t as,
+    unsigned char const *spk, size_t spk_len)
 {
        struct validation_handler const *handler;
        int error;
@@ -64,6 +65,6 @@ vhandler_handle_bgpsec(struct router_key const *router_key)
                return error;
 
        return (handler->handle_bgpsec != NULL)
-           ? handler->handle_bgpsec(router_key, handler->arg)
+           ? handler->handle_bgpsec(ski, as, spk, spk_len, handler->arg)
            : 0;
 }
index 85cebf0d7396fa8f716bbe30aaf7daf0d1561b3d..9165122034a4946bcb4a312b929f0cd353b8cecd 100644 (file)
@@ -29,14 +29,16 @@ struct validation_handler {
        /** Called every time Fort has successfully validated an IPv6 ROA. */
        int (*handle_roa_v6)(uint32_t, struct ipv6_prefix const *, uint8_t,
            void *);
-       /** Called every time Fort has successfully a BGPsec certificate */
-       int (*handle_bgpsec)(struct router_key const *, void *);
+       /** Called every time Fort has successfully validated a BGPsec cert */
+       int (*handle_bgpsec)(unsigned char const *, uint32_t,
+           unsigned char const *, size_t, void *);
        /** Generic user-defined argument for the functions above. */
        void *arg;
 };
 
 int vhandler_handle_roa_v4(uint32_t, struct ipv4_prefix const *, uint8_t);
 int vhandler_handle_roa_v6(uint32_t, struct ipv6_prefix const *, uint8_t);
-int vhandler_handle_bgpsec(struct router_key const *);
+int vhandler_handle_bgpsec(unsigned char const *, uint32_t,
+    unsigned char const *, size_t);
 
 #endif /* SRC_VALIDATION_HANDLER_H_ */
index d86011c0967ce9134b9db105e9c117420addae48..549709b24833095966d3f25643049b3b5982fa04 100644 (file)
@@ -21,10 +21,10 @@ MY_LDADD = ${CHECK_LIBS}
 
 check_PROGRAMS  = address.test
 check_PROGRAMS += clients.test
+check_PROGRAMS += db_table.test
 check_PROGRAMS += line_file.test
 check_PROGRAMS += pdu_handler.test
 check_PROGRAMS += rsync.test
-check_PROGRAMS += roa_table.test
 check_PROGRAMS += tal.test
 check_PROGRAMS += vcard.test
 check_PROGRAMS += vrps.test
@@ -38,15 +38,15 @@ address_test_LDADD = ${MY_LDADD}
 clients_test_SOURCES = client_test.c
 clients_test_LDADD = ${MY_LDADD}
 
+db_table_test_SOURCES = rtr/db/db_table_test.c
+db_table_test_LDADD = ${MY_LDADD}
+
 line_file_test_SOURCES = line_file_test.c
 line_file_test_LDADD = ${MY_LDADD}
 
 pdu_handler_test_SOURCES = rtr/pdu_handler_test.c
 pdu_handler_test_LDADD = ${MY_LDADD} ${JANSSON_LIBS}
 
-roa_table_test_SOURCES = rtr/db/roa_table_test.c
-roa_table_test_LDADD = ${MY_LDADD}
-
 rsync_test_SOURCES = rsync_test.c
 rsync_test_LDADD = ${MY_LDADD}
 
index d4175e3acae5c25cdeeb849381a2d1da0780ed87..16a9140d10b6e61f5fae5510ab7aaa25b914bcde 100644 (file)
@@ -107,6 +107,12 @@ config_get_output_roa(void)
        return NULL;
 }
 
+char const *
+config_get_output_bgpsec(void)
+{
+       return NULL;
+}
+
 enum incidence_action
 incidence_get_action(enum incidence_id id)
 {
similarity index 92%
rename from test/rtr/db/roa_table_test.c
rename to test/rtr/db/db_table_test.c
index f3d4dc9b657d4bc1d9a44baa0507e783891e94c0..f83c5e15c78c7af030aba9a4be0edda86259bd7c 100644 (file)
@@ -4,8 +4,9 @@
 #include "address.c"
 #include "log.c"
 #include "impersonator.c"
+#include "object/router_key.c"
 #include "rtr/db/delta.c"
-#include "rtr/db/roa_table.c"
+#include "rtr/db/db_table.c"
 
 #define ADDR1 htonl(0xC0000201) /* 192.0.2.1 */
 #define ADDR2 htonl(0xC0000202) /* 192.0.2.2 */
@@ -94,10 +95,10 @@ START_TEST(test_basic)
 {
        struct ipv4_prefix prefix4;
        struct ipv6_prefix prefix6;
-       struct roa_table *table;
+       struct db_table *table;
        array_index i;
 
-       table = roa_table_create();
+       table = db_table_create();
        ck_assert_ptr_ne(NULL, table);
 
        prefix4.addr.s_addr = ADDR1;
@@ -152,12 +153,12 @@ START_TEST(test_basic)
        /* Check table contents */
        memset(roas_found, 0, sizeof(roas_found));
        total_found = 0;
-       ck_assert_int_eq(0, roa_table_foreach_roa(table, foreach_cb, NULL));
+       ck_assert_int_eq(0, db_table_foreach_roa(table, foreach_cb, NULL));
        ck_assert_int_eq(TOTAL_ROAS, total_found);
        for (i = 0; i < TOTAL_ROAS; i++)
                ck_assert_int_eq(true, roas_found[i]);
 
-       roa_table_destroy(table);
+       db_table_destroy(table);
 }
 END_TEST
 
@@ -165,15 +166,15 @@ START_TEST(test_merge)
 {
        struct ipv4_prefix prefix4;
        struct ipv6_prefix prefix6;
-       struct roa_table *left, *right, *merged;
+       struct db_table *left, *right, *merged;
        array_index i;
        int left_count, right_count, total_merged;
 
-       left = roa_table_create();
+       left = db_table_create();
        ck_assert_ptr_ne(NULL, left);
-       right = roa_table_create();
+       right = db_table_create();
        ck_assert_ptr_ne(NULL, right);
-       merged = roa_table_create();
+       merged = db_table_create();
        ck_assert_ptr_ne(NULL, merged);
 
        prefix4.addr.s_addr = ADDR1;
@@ -229,8 +230,8 @@ START_TEST(test_merge)
        right_count++;
 
        /** Do the merge */
-       ck_assert_int_eq(0, roa_table_merge(merged, left));
-       ck_assert_int_eq(0, roa_table_merge(merged, right));
+       ck_assert_int_eq(0, db_table_merge(merged, left));
+       ck_assert_int_eq(0, db_table_merge(merged, right));
 
        /**
         * Must have:
@@ -240,17 +241,17 @@ START_TEST(test_merge)
        ck_assert_int_eq(total_merged, TOTAL_ROAS);
 
        /* Check table contents and that merged table has new memory refs */
-       roa_table_destroy(left);
-       roa_table_destroy(right);
+       db_table_destroy(left);
+       db_table_destroy(right);
 
        memset(roas_found, 0, sizeof(roas_found));
        total_found = 0;
-       ck_assert_int_eq(0, roa_table_foreach_roa(merged, foreach_cb, NULL));
+       ck_assert_int_eq(0, db_table_foreach_roa(merged, foreach_cb, NULL));
        ck_assert_int_eq(TOTAL_ROAS, total_found);
        for (i = 0; i < TOTAL_ROAS; i++)
                ck_assert_int_eq(true, roas_found[i]);
 
-       roa_table_destroy(merged);
+       db_table_destroy(merged);
 }
 END_TEST
 
@@ -265,7 +266,7 @@ Suite *pdu_suite(void)
        merge = tcase_create("Merge");
        tcase_add_test(core, test_merge);
 
-       suite = suite_create("ROA Table");
+       suite = suite_create("DB Table");
        suite_add_tcase(suite, core);
        suite_add_tcase(suite, merge);
        return suite;
index c61988e1172055e3fd13144b5e27732e308ad8b0..8935cbb0c9804df8d9bdec0f4a46f5de4549cb34 100644 (file)
@@ -9,8 +9,9 @@
 #include "json_parser.c"
 #include "log.c"
 #include "output_printer.c"
+#include "object/router_key.c"
 #include "rtr/db/delta.c"
-#include "rtr/db/roa_table.c"
+#include "rtr/db/db_table.c"
 #include "rtr/db/rtr_db_impersonator.c"
 #include "rtr/db/vrps.c"
 #include "slurm/slurm_db.c"
@@ -126,7 +127,7 @@ get_vrp_index(struct vrp const *vrp)
 }
 
 static array_index
-get_delta_index(struct delta const *delta)
+get_delta_index(struct delta_vrp const *delta)
 {
        array_index result;
 
@@ -150,7 +151,7 @@ vrp_check(struct vrp const *vrp, void *arg)
 }
 
 static int
-delta_check(struct delta const *delta, void *arg)
+delta_check(struct delta_vrp const *delta, void *arg)
 {
        bool *array = arg;
        array_index index;
@@ -186,7 +187,7 @@ check_base(serial_t expected_serial, bool const *expected_base)
 }
 
 static int
-vrp_add(struct delta const *delta, void *arg)
+vrp_add(struct delta_vrp const *delta, void *arg)
 {
        struct deltas *deltas = arg;
        struct vrp const *vrp;
@@ -250,9 +251,10 @@ check_deltas(serial_t from, serial_t to, bool const *expected_deltas,
                filter_deltas(&deltas);
 
        memset(actual_deltas, 0, sizeof(actual_deltas));
+       /* FIXME Add cb function for router keys */
        ARRAYLIST_FOREACH(&deltas, group, i)
                ck_assert_int_eq(0, deltas_foreach(group->serial, group->deltas,
-                   delta_check, actual_deltas));
+                   delta_check, NULL, actual_deltas));
        for (i = 0; i < ARRAY_LEN(actual_deltas); i++)
                ck_assert_uint_eq(expected_deltas[i], actual_deltas[i]);
 }
index 1b77f00fc5db20007085882e570018071fe03666..64adca777a7eb5190d0da2634c366416f920f9d5 100644 (file)
@@ -10,6 +10,7 @@
 #include "log.c"
 #include "output_printer.c"
 #include "crypto/base64.c"
+#include "object/router_key.c"
 #include "rtr/pdu.c"
 #include "rtr/pdu_handler.c"
 #include "rtr/primitive_reader.c"
@@ -17,7 +18,7 @@
 #include "rtr/err_pdu.c"
 #include "rtr/stream.c"
 #include "rtr/db/delta.c"
-#include "rtr/db/roa_table.c"
+#include "rtr/db/db_table.c"
 #include "rtr/db/rtr_db_impersonator.c"
 #include "rtr/db/vrps.c"
 #include "slurm/slurm_db.c"
@@ -145,7 +146,7 @@ send_prefix_pdu(int fd, struct vrp const *vrp, uint8_t flags)
 }
 
 static int
-handle_delta(struct delta const *delta, void *arg)
+handle_delta(struct delta_vrp const *delta, void *arg)
 {
        int *fd = arg;
        ck_assert_int_eq(0, send_prefix_pdu(*fd, &delta->vrp, delta->flags));
@@ -158,9 +159,10 @@ send_delta_pdus(int fd, struct deltas_db *deltas)
        struct delta_group *group;
        array_index i;
 
+       /* FIXME Add cb function for router keys */
        ARRAYLIST_FOREACH(deltas, group, i)
                ck_assert_int_eq(0, deltas_foreach(group->serial, group->deltas,
-                   handle_delta, &fd));
+                   handle_delta, NULL, &fd));
 
        return 0;
 }