diff options
author | dimitri staessens <dimitri.staessens@ugent.be> | 2017-04-12 16:57:48 +0200 |
---|---|---|
committer | dimitri staessens <dimitri.staessens@ugent.be> | 2017-04-13 11:30:20 +0200 |
commit | fc10a7587b1a642748ae0fd69f08d92b4a902248 (patch) | |
tree | e0b570cf30753a564855242c94d242f597b5c499 /src/ipcpd | |
parent | a3d550ff972121641562d375f75bcf188fc7fe59 (diff) | |
download | ouroboros-fc10a7587b1a642748ae0fd69f08d92b4a902248.tar.gz ouroboros-fc10a7587b1a642748ae0fd69f08d92b4a902248.zip |
lib, ipcpd, irmd: Register hash instead of name
All information passed over the IRMd/IPCP boundary for using IPC
services (flow allocation, registration) is now hashed. This
effectively fixes the shared namespace between DIFs and the IRMDs.
This PR also fixes some API issues (adding const identifiers),
shuffles the include headers a bit and some small bugs.
Diffstat (limited to 'src/ipcpd')
26 files changed, 524 insertions, 738 deletions
diff --git a/src/ipcpd/ipcp.c b/src/ipcpd/ipcp.c index 587d70c5..795ce42c 100644 --- a/src/ipcpd/ipcp.c +++ b/src/ipcpd/ipcp.c @@ -38,6 +38,54 @@ #include <sys/socket.h> #include <stdlib.h> +void ipcp_sig_handler(int sig, + siginfo_t * info, + void * c) +{ + (void) c; + + switch(sig) { + case SIGINT: + case SIGTERM: + case SIGHUP: + case SIGQUIT: + if (info->si_pid == ipcpi.irmd_api) { + if (ipcp_get_state() == IPCP_INIT) + ipcp_set_state(IPCP_NULL); + + if (ipcp_get_state() == IPCP_OPERATIONAL) + ipcp_set_state(IPCP_SHUTDOWN); + } + default: + return; + } +} + +uint8_t * ipcp_hash_dup(const uint8_t * hash) +{ + uint8_t * dup = malloc(ipcpi.dir_hash_len); + if (dup == NULL) + return NULL; + + memcpy(dup, hash, ipcpi.dir_hash_len); + + return dup; +} + +void ipcp_hash_str(char buf[DIR_HASH_STRLEN + 1], + const uint8_t * hash) +{ + size_t i; + + char * HEX = "0123456789abcdef"; + + for (i = 0; i < ipcpi.dir_hash_len; ++i) { + buf[i * 2] = HEX[(hash[i] & 0xF0) >> 4]; + buf[i * 2 + 1] = HEX[hash[i] & 0x0F]; + } + + buf[2 * i] = '\0'; +} static void thread_inc(void) { @@ -93,8 +141,8 @@ static void * ipcp_main_loop(void * o) buffer_t buffer; ipcp_msg_t ret_msg = IPCP_MSG__INIT; - dif_config_msg_t * conf_msg; - struct dif_config conf; + ipcp_config_msg_t * conf_msg; + struct ipcp_config conf; struct timeval ltv = {(SOCKET_TIMEOUT / 1000), (SOCKET_TIMEOUT % 1000) * 1000}; @@ -109,18 +157,13 @@ static void * ipcp_main_loop(void * o) #endif int fd = -1; - pthread_rwlock_rdlock(&ipcpi.state_lock); - if (ipcp_get_state() == IPCP_SHUTDOWN || ipcp_get_state() == IPCP_NULL || thread_check()) { thread_exit(id); - pthread_rwlock_unlock(&ipcpi.state_lock); break; } - pthread_rwlock_unlock(&ipcpi.state_lock); - ret_msg.code = IPCP_MSG_CODE__IPCP_REPLY; #ifdef __FreeBSD__ FD_ZERO(&fds); @@ -153,12 +196,23 @@ static void * ipcp_main_loop(void * o) switch (msg->code) { case IPCP_MSG_CODE__IPCP_BOOTSTRAP: + ret_msg.has_result = true; + if (ipcpi.ops->ipcp_bootstrap == NULL) { log_err("Bootstrap unsupported."); + ret_msg.result = -ENOTSUP; break; } + + if (ipcp_get_state() != IPCP_INIT) { + log_err("IPCP in wrong state."); + ret_msg.result = -EIPCPSTATE; + break; + } + conf_msg = msg->conf; conf.type = conf_msg->ipcp_type; + conf.dir_hash_len = conf_msg->dir_hash_len; conf.dif_name = conf_msg->dif_name; if (conf.dif_name == NULL) { ret_msg.has_result = true; @@ -179,74 +233,123 @@ static void * ipcp_main_loop(void * o) conf.dt_gam_type = conf_msg->dt_gam_type; conf.rm_gam_type = conf_msg->rm_gam_type; } + if (conf_msg->ipcp_type == IPCP_SHIM_UDP) { conf.ip_addr = conf_msg->ip_addr; conf.dns_addr = conf_msg->dns_addr; } + if (conf_msg->ipcp_type == IPCP_SHIM_ETH_LLC) conf.if_name = conf_msg->if_name; - ret_msg.has_result = true; ret_msg.result = ipcpi.ops->ipcp_bootstrap(&conf); break; case IPCP_MSG_CODE__IPCP_ENROLL: + ret_msg.has_result = true; + if (ipcpi.ops->ipcp_enroll == NULL) { log_err("Enroll unsupported."); + ret_msg.result = -ENOTSUP; break; } - ret_msg.has_result = true; - ret_msg.result = ipcpi.ops->ipcp_enroll(msg->dif_name); - break; - case IPCP_MSG_CODE__IPCP_NAME_REG: - if (ipcpi.ops->ipcp_name_reg == NULL) { - log_err("Ap_reg unsupported."); + + if (ipcp_get_state() != IPCP_INIT) { + log_err("IPCP in wrong state."); + ret_msg.result = -EIPCPSTATE; break; } + + ret_msg.result = ipcpi.ops->ipcp_enroll(msg->dst_name); + break; + case IPCP_MSG_CODE__IPCP_REG: ret_msg.has_result = true; + + if (ipcpi.ops->ipcp_reg == NULL) { + log_err("Registration unsupported."); + ret_msg.result = -ENOTSUP; + break; + } + + assert(msg->hash.len == ipcpi.dir_hash_len); + ret_msg.result = - ipcpi.ops->ipcp_name_reg(msg->name); + ipcpi.ops->ipcp_reg(msg->hash.data); break; - case IPCP_MSG_CODE__IPCP_NAME_UNREG: - if (ipcpi.ops->ipcp_name_unreg == NULL) { - log_err("Ap_unreg unsupported."); + case IPCP_MSG_CODE__IPCP_UNREG: + ret_msg.has_result = true; + + if (ipcpi.ops->ipcp_unreg == NULL) { + log_err("Unregistration unsupported."); + ret_msg.result = -ENOTSUP; break; } - ret_msg.has_result = true; + + assert(msg->hash.len == ipcpi.dir_hash_len); + ret_msg.result = - ipcpi.ops->ipcp_name_unreg(msg->name); + ipcpi.ops->ipcp_unreg(msg->hash.data); break; - case IPCP_MSG_CODE__IPCP_NAME_QUERY: - if (ipcpi.ops->ipcp_name_query == NULL) { - log_err("Ap_query unsupported."); + case IPCP_MSG_CODE__IPCP_QUERY: + ret_msg.has_result = true; + + if (ipcpi.ops->ipcp_query == NULL) { + log_err("Directory query unsupported."); + ret_msg.result = -ENOTSUP; break; } - ret_msg.has_result = true; + + assert(msg->hash.len == ipcpi.dir_hash_len); + + if (ipcp_get_state() != IPCP_OPERATIONAL) { + log_err("IPCP in wrong state."); + ret_msg.result = -EIPCPSTATE; + break; + } + ret_msg.result = - ipcpi.ops->ipcp_name_query(msg->name); + ipcpi.ops->ipcp_query(msg->hash.data); break; case IPCP_MSG_CODE__IPCP_FLOW_ALLOC: + ret_msg.has_result = true; + if (ipcpi.ops->ipcp_flow_alloc == NULL) { - log_err("Flow_alloc unsupported."); + log_err("Flow allocation unsupported."); + ret_msg.result = -ENOTSUP; + break; + } + + assert(msg->hash.len == ipcpi.dir_hash_len); + + if (ipcp_get_state() != IPCP_OPERATIONAL) { + log_err("IPCP in wrong state."); + ret_msg.result = -EIPCPSTATE; break; } + fd = np1_flow_alloc(msg->api, msg->port_id); if (fd < 0) { log_err("Failed allocating fd on port_id %d.", msg->port_id); - ret_msg.has_result = true; ret_msg.result = -1; break; } - ret_msg.has_result = true; ret_msg.result = ipcpi.ops->ipcp_flow_alloc(fd, - msg->dst_name, + msg->hash.data, msg->qoscube); break; case IPCP_MSG_CODE__IPCP_FLOW_ALLOC_RESP: + ret_msg.has_result = true; if (ipcpi.ops->ipcp_flow_alloc_resp == NULL) { log_err("Flow_alloc_resp unsupported."); + ret_msg.result = -ENOTSUP; + break; + } + + if (ipcp_get_state() != IPCP_OPERATIONAL) { + log_err("IPCP in wrong state."); + ret_msg.result = -EIPCPSTATE; break; } @@ -255,20 +358,26 @@ static void * ipcp_main_loop(void * o) if (fd < 0) { log_warn("Port_id %d is not known.", msg->port_id); - ret_msg.has_result = true; ret_msg.result = -1; break; } } - ret_msg.has_result = true; ret_msg.result = ipcpi.ops->ipcp_flow_alloc_resp(fd, msg->response); break; case IPCP_MSG_CODE__IPCP_FLOW_DEALLOC: + ret_msg.has_result = true; if (ipcpi.ops->ipcp_flow_dealloc == NULL) { - log_err("Flow_dealloc unsupported."); + log_err("Flow deallocation unsupported."); + ret_msg.result = -ENOTSUP; + break; + } + + if (ipcp_get_state() != IPCP_OPERATIONAL) { + log_err("IPCP in wrong state."); + ret_msg.result = -EIPCPSTATE; break; } @@ -276,12 +385,10 @@ static void * ipcp_main_loop(void * o) if (fd < 0) { log_warn("Could not deallocate port_id %d.", msg->port_id); - ret_msg.has_result = true; ret_msg.result = -1; break; } - ret_msg.has_result = true; ret_msg.result = ipcpi.ops->ipcp_flow_dealloc(fd); break; @@ -409,11 +516,6 @@ int ipcp_init(int argc, ipcpi.ops = ops; - if (pthread_rwlock_init(&ipcpi.state_lock, NULL)) { - log_err("Could not create rwlock."); - goto fail_state_rwlock; - } - if (pthread_mutex_init(&ipcpi.state_mtx, NULL)) { log_err("Could not create mutex."); goto fail_state_mtx; @@ -492,8 +594,6 @@ int ipcp_init(int argc, fail_thread_lock: pthread_mutex_destroy(&ipcpi.state_mtx); fail_state_mtx: - pthread_rwlock_destroy(&ipcpi.state_lock); - fail_state_rwlock: close(ipcpi.sockfd); fail_serv_sock: free(ipcpi.sock_path); @@ -522,10 +622,8 @@ void * threadpoolmgr(void * o) clock_gettime(PTHREAD_COND_CLOCK, &dl); ts_add(&dl, &to, &dl); - pthread_rwlock_rdlock(&ipcpi.state_lock); if (ipcp_get_state() == IPCP_SHUTDOWN || ipcp_get_state() == IPCP_NULL) { - pthread_rwlock_unlock(&ipcpi.state_lock); pthread_attr_destroy(&pattr); log_dbg("Waiting for threads to exit."); pthread_mutex_lock(&ipcpi.threads_lock); @@ -538,8 +636,6 @@ void * threadpoolmgr(void * o) break; } - pthread_rwlock_unlock(&ipcpi.state_lock); - pthread_mutex_lock(&ipcpi.threads_lock); if (ipcpi.threads < IPCP_MIN_AV_THREADS) { @@ -576,10 +672,34 @@ void * threadpoolmgr(void * o) int ipcp_boot() { + struct sigaction sig_act; + sigset_t sigset; + sigemptyset(&sigset); + sigaddset(&sigset, SIGINT); + sigaddset(&sigset, SIGQUIT); + sigaddset(&sigset, SIGHUP); + sigaddset(&sigset, SIGPIPE); + + /* init sig_act */ + memset(&sig_act, 0, sizeof(sig_act)); + + /* install signal traps */ + sig_act.sa_sigaction = &ipcp_sig_handler; + sig_act.sa_flags = SA_SIGINFO; + + sigaction(SIGINT, &sig_act, NULL); + sigaction(SIGTERM, &sig_act, NULL); + sigaction(SIGHUP, &sig_act, NULL); + sigaction(SIGPIPE, &sig_act, NULL); + + pthread_sigmask(SIG_BLOCK, &sigset, NULL); + ipcp_set_state(IPCP_INIT); pthread_create(&ipcpi.tpm, NULL, threadpoolmgr, NULL); + pthread_sigmask(SIG_UNBLOCK, &sigset, NULL); + return 0; } @@ -607,7 +727,6 @@ void ipcp_fini() pthread_cond_destroy(&ipcpi.threads_cond); pthread_mutex_destroy(&ipcpi.threads_lock); pthread_mutex_destroy(&ipcpi.state_mtx); - pthread_rwlock_destroy(&ipcpi.state_lock); pthread_cond_destroy(&ipcpi.alloc_cond); pthread_mutex_destroy(&ipcpi.alloc_lock); diff --git a/src/ipcpd/ipcp.h b/src/ipcpd/ipcp.h index e5c4b9af..d6e2aa7c 100644 --- a/src/ipcpd/ipcp.h +++ b/src/ipcpd/ipcp.h @@ -24,12 +24,13 @@ #define IPCPD_IPCP_H #include <ouroboros/config.h> -#include <ouroboros/irm_config.h> +#include <ouroboros/ipcp.h> #include "shim-data.h" #include <pthread.h> #include <time.h> +#include <signal.h> enum ipcp_state { IPCP_NULL = 0, @@ -39,19 +40,19 @@ enum ipcp_state { }; struct ipcp_ops { - int (* ipcp_bootstrap)(struct dif_config * conf); + int (* ipcp_bootstrap)(const struct ipcp_config * conf); - int (* ipcp_enroll)(char * dif_name); + int (* ipcp_enroll)(const char * dst); - int (* ipcp_name_reg)(char * name); + int (* ipcp_reg)(const uint8_t * hash); - int (* ipcp_name_unreg)(char * name); + int (* ipcp_unreg)(const uint8_t * hash); - int (* ipcp_name_query)(char * name); + int (* ipcp_query)(const uint8_t * hash); - int (* ipcp_flow_alloc)(int fd, - char * dst_ap_name, - qoscube_t qos); + int (* ipcp_flow_alloc)(int fd, + const uint8_t * dst, + qoscube_t qos); int (* ipcp_flow_alloc_resp)(int fd, int response); @@ -59,6 +60,8 @@ struct ipcp_ops { int (* ipcp_flow_dealloc)(int fd); }; +#define DIR_HASH_STRLEN (ipcpi.dir_hash_len * 2) + struct ipcp { int irmd_api; char * name; @@ -67,6 +70,7 @@ struct ipcp { char * dif_name; uint64_t dt_addr; + uint16_t dir_hash_len; struct ipcp_ops * ops; int irmd_fd; @@ -117,4 +121,15 @@ int ipcp_wait_state(enum ipcp_state state, int ipcp_parse_arg(int argc, char * argv[]); +/* Handle shutdown of IPCP */ +void ipcp_sig_handler(int sig, + siginfo_t * info, + void * c); + +/* Helper functions for directory entries, could be moved */ +uint8_t * ipcp_hash_dup(const uint8_t * hash); + +void ipcp_hash_str(char buf[], + const uint8_t * hash); + #endif diff --git a/src/ipcpd/local/main.c b/src/ipcpd/local/main.c index 897ec3a0..21ca7400 100644 --- a/src/ipcpd/local/main.c +++ b/src/ipcpd/local/main.c @@ -27,13 +27,14 @@ #include <ouroboros/errno.h> #include <ouroboros/dev.h> #include <ouroboros/fqueue.h> +#include <ouroboros/ipcp.h> #include <ouroboros/ipcp-dev.h> #include <ouroboros/local-dev.h> +#include <ouroboros/hash.h> #include "ipcp.h" #include <string.h> -#include <signal.h> #include <stdlib.h> #include <pthread.h> #include <sys/wait.h> @@ -113,110 +114,74 @@ static void * ipcp_local_sdu_loop(void * o) return (void *) 0; } -void ipcp_sig_handler(int sig, - siginfo_t * info, - void * c) +static int ipcp_local_bootstrap(const struct ipcp_config * conf) { - (void) c; - - switch(sig) { - case SIGINT: - case SIGTERM: - case SIGHUP: - case SIGQUIT: - if (info->si_pid == ipcpi.irmd_api) { - if (ipcp_get_state() == IPCP_INIT) - ipcp_set_state(IPCP_NULL); - - if (ipcp_get_state() == IPCP_OPERATIONAL) - ipcp_set_state(IPCP_SHUTDOWN); - } - default: - return; - } -} - -static int ipcp_local_bootstrap(struct dif_config * conf) -{ - (void) conf; - assert(conf); assert(conf->type == THIS_TYPE); - if (ipcp_get_state() != IPCP_INIT) { - log_err("IPCP in wrong state."); - return -1; - } + ipcpi.dir_hash_len = conf->dir_hash_len; ipcp_set_state(IPCP_OPERATIONAL); - pthread_create(&local_data.sduloop, NULL, ipcp_local_sdu_loop, NULL); + if (pthread_create(&local_data.sduloop, NULL, + ipcp_local_sdu_loop, NULL)) { + ipcp_set_state(IPCP_INIT); + return -1; + } log_info("Bootstrapped local IPCP with api %d.", getpid()); return 0; } -static int ipcp_local_name_reg(char * name) +static int ipcp_local_reg(const uint8_t * hash) { - char * name_dup = strdup(name); - if (name_dup == NULL) { - log_err("Failed to duplicate name."); + uint8_t * hash_dup = ipcp_hash_dup(hash); + if (hash_dup == NULL) { + log_err("Failed to duplicate hash."); return -ENOMEM; } - pthread_rwlock_rdlock(&ipcpi.state_lock); - - if (shim_data_reg_add_entry(ipcpi.shim_data, name_dup)) { - pthread_rwlock_unlock(&ipcpi.state_lock); - log_dbg("Failed to add %s to local registry.", name); - free(name_dup); + if (shim_data_reg_add_entry(ipcpi.shim_data, hash_dup)) { + log_dbg("Failed to add " HASH_FMT " to local registry.", + HASH_VAL(hash)); + free(hash_dup); return -1; } - pthread_rwlock_unlock(&ipcpi.state_lock); - - log_info("Registered %s.", name); + log_info("Registered " HASH_FMT ".", HASH_VAL(hash)); return 0; } -static int ipcp_local_name_unreg(char * name) +static int ipcp_local_unreg(const uint8_t * hash) { - pthread_rwlock_rdlock(&ipcpi.state_lock); - - shim_data_reg_del_entry(ipcpi.shim_data, name); + shim_data_reg_del_entry(ipcpi.shim_data, hash); - pthread_rwlock_unlock(&ipcpi.state_lock); - - log_info("Unregistered %s.", name); + log_info("Unregistered " HASH_FMT ".", HASH_VAL(hash)); return 0; } -static int ipcp_local_name_query(char * name) +static int ipcp_local_query(const uint8_t * hash) { int ret; - pthread_rwlock_rdlock(&ipcpi.state_lock); - - ret = (shim_data_reg_has(ipcpi.shim_data, name) ? 0 : -1); - - pthread_rwlock_unlock(&ipcpi.state_lock); + ret = (shim_data_reg_has(ipcpi.shim_data, hash) ? 0 : -1); return ret; } -static int ipcp_local_flow_alloc(int fd, - char * dst_name, - qoscube_t cube) +static int ipcp_local_flow_alloc(int fd, + const uint8_t * dst, + qoscube_t cube) { struct timespec ts = {0, EVENT_WAIT_TIMEOUT * 1000}; int out_fd = -1; - log_dbg("Allocating flow to %s on fd %d.", dst_name, fd); + log_dbg("Allocating flow to " HASH_FMT " on fd %d.", HASH_VAL(dst), fd); - assert(dst_name); + assert(dst); pthread_mutex_lock(&ipcpi.alloc_lock); @@ -233,7 +198,7 @@ static int ipcp_local_flow_alloc(int fd, assert(ipcpi.alloc_id == -1); - out_fd = ipcp_flow_req_arr(getpid(), dst_name, cube); + out_fd = ipcp_flow_req_arr(getpid(), dst, ipcpi.dir_hash_len, cube); if (out_fd < 0) { pthread_mutex_unlock(&ipcpi.alloc_lock); log_dbg("Flow allocation failed: %d", out_fd); @@ -335,9 +300,9 @@ static int ipcp_local_flow_dealloc(int fd) static struct ipcp_ops local_ops = { .ipcp_bootstrap = ipcp_local_bootstrap, .ipcp_enroll = NULL, /* shim */ - .ipcp_name_reg = ipcp_local_name_reg, - .ipcp_name_unreg = ipcp_local_name_unreg, - .ipcp_name_query = ipcp_local_name_query, + .ipcp_reg = ipcp_local_reg, + .ipcp_unreg = ipcp_local_unreg, + .ipcp_query = ipcp_local_query, .ipcp_flow_alloc = ipcp_local_flow_alloc, .ipcp_flow_alloc_resp = ipcp_local_flow_alloc_resp, .ipcp_flow_dealloc = ipcp_local_flow_dealloc @@ -346,26 +311,6 @@ static struct ipcp_ops local_ops = { int main(int argc, char * argv[]) { - struct sigaction sig_act; - sigset_t sigset; - sigemptyset(&sigset); - sigaddset(&sigset, SIGINT); - sigaddset(&sigset, SIGQUIT); - sigaddset(&sigset, SIGHUP); - sigaddset(&sigset, SIGPIPE); - - /* init sig_act */ - memset(&sig_act, 0, sizeof(sig_act)); - - /* install signal traps */ - sig_act.sa_sigaction = &ipcp_sig_handler; - sig_act.sa_flags = SA_SIGINFO; - - sigaction(SIGINT, &sig_act, NULL); - sigaction(SIGTERM, &sig_act, NULL); - sigaction(SIGHUP, &sig_act, NULL); - sigaction(SIGPIPE, &sig_act, NULL); - if (ipcp_init(argc, argv, THIS_TYPE, &local_ops) < 0) { ipcp_create_r(getpid(), -1); exit(EXIT_FAILURE); @@ -378,8 +323,6 @@ int main(int argc, exit(EXIT_FAILURE); } - pthread_sigmask(SIG_BLOCK, &sigset, NULL); - if (ipcp_boot() < 0) { log_err("Failed to boot IPCP."); ipcp_create_r(getpid(), -1); @@ -388,8 +331,6 @@ int main(int argc, exit(EXIT_FAILURE); } - pthread_sigmask(SIG_UNBLOCK, &sigset, NULL); - if (ipcp_create_r(getpid(), 0)) { log_err("Failed to notify IRMd we are initialized."); ipcp_set_state(IPCP_NULL); diff --git a/src/ipcpd/normal/addr_auth.h b/src/ipcpd/normal/addr_auth.h index fbe7d790..6883b4b3 100644 --- a/src/ipcpd/normal/addr_auth.h +++ b/src/ipcpd/normal/addr_auth.h @@ -23,7 +23,7 @@ #ifndef OUROBOROS_IPCPD_NORMAL_ADDR_AUTH_H #define OUROBOROS_IPCPD_NORMAL_ADDR_AUTH_H -#include <ouroboros/irm_config.h> +#include <ouroboros/ipcp.h> #include <stdint.h> diff --git a/src/ipcpd/normal/connmgr.c b/src/ipcpd/normal/connmgr.c index 8068d173..421bc5b0 100644 --- a/src/ipcpd/normal/connmgr.c +++ b/src/ipcpd/normal/connmgr.c @@ -116,16 +116,11 @@ static void * flow_acceptor(void * o) memset(&fail_info, 0, sizeof(fail_info)); while (true) { - pthread_rwlock_rdlock(&ipcpi.state_lock); - if (ipcp_get_state() != IPCP_OPERATIONAL) { - pthread_rwlock_unlock(&ipcpi.state_lock); log_info("Shutting down flow acceptor."); return 0; } - pthread_rwlock_unlock(&ipcpi.state_lock); - fd = flow_accept(&qs, NULL); if (fd < 0) { if (fd != -EIRMD) @@ -271,7 +266,7 @@ void connmgr_ae_destroy(struct ae * ae) } int connmgr_alloc(struct ae * ae, - char * dst_name, + const char * dst_name, qosspec_t * qs, struct conn * conn) { diff --git a/src/ipcpd/normal/connmgr.h b/src/ipcpd/normal/connmgr.h index c0356f6d..12992ef6 100644 --- a/src/ipcpd/normal/connmgr.h +++ b/src/ipcpd/normal/connmgr.h @@ -47,7 +47,7 @@ struct ae * connmgr_ae_create(struct conn_info info); void connmgr_ae_destroy(struct ae * ae); int connmgr_alloc(struct ae * ae, - char * dst_name, + const char * dst, qosspec_t * qs, struct conn * conn); diff --git a/src/ipcpd/normal/dir.c b/src/ipcpd/normal/dir.c index ae9793c6..cbc50ba4 100644 --- a/src/ipcpd/normal/dir.c +++ b/src/ipcpd/normal/dir.c @@ -60,22 +60,23 @@ int dir_fini(void) return 0; } -int dir_name_reg(char * name) +int dir_reg(const uint8_t * hash) { + char hashstr[DIR_HASH_STRLEN + 1]; int ret; - assert(name); - - if (ipcp_get_state() != IPCP_OPERATIONAL) - return -EPERM; + assert(hash); dir_path_reset(); - ret = rib_add(dir_path, name); + ipcp_hash_str(hashstr, hash); + + ret = rib_add(dir_path, hashstr); if (ret == -ENOMEM) - return -ENOMEM; + return -ENOMEM; + + rib_path_append(dir_path, hashstr); - rib_path_append(dir_path, name); ret = rib_add(dir_path, ipcpi.name); if (ret == -EPERM) return -EPERM; @@ -88,18 +89,16 @@ int dir_name_reg(char * name) return 0; } -int dir_name_unreg(char * name) +int dir_unreg(const uint8_t * hash) { + char hashstr[DIR_HASH_STRLEN + 1]; size_t len; - assert(name); - - if (ipcp_get_state() != IPCP_OPERATIONAL) - return -EPERM; + assert(hash); dir_path_reset(); - rib_path_append(dir_path, name); + rib_path_append(dir_path, hashstr); if (!rib_has(dir_path)) return 0; @@ -118,16 +117,16 @@ int dir_name_unreg(char * name) return 0; } -int dir_name_query(char * name) +int dir_query(const uint8_t * hash) { + char hashstr[DIR_HASH_STRLEN + 1]; size_t len; - if (ipcp_get_state() != IPCP_OPERATIONAL) - return -EPERM; - dir_path_reset(); - rib_path_append(dir_path, name); + ipcp_hash_str(hashstr, hash); + + rib_path_append(dir_path, hashstr); if (!rib_has(dir_path)) return -1; diff --git a/src/ipcpd/normal/dir.h b/src/ipcpd/normal/dir.h index 04e722f3..1b28a5c0 100644 --- a/src/ipcpd/normal/dir.h +++ b/src/ipcpd/normal/dir.h @@ -27,10 +27,10 @@ int dir_init(void); int dir_fini(void); -int dir_name_reg(char * name); +int dir_reg(const uint8_t * hash); -int dir_name_unreg(char * name); +int dir_unreg(const uint8_t * hash); -int dir_name_query(char * name); +int dir_query(const uint8_t * hash); #endif /* OUROBOROS_IPCPD_NORMAL_DIR_H */ diff --git a/src/ipcpd/normal/enroll.c b/src/ipcpd/normal/enroll.c index 3e6a0197..f1f804c6 100644 --- a/src/ipcpd/normal/enroll.c +++ b/src/ipcpd/normal/enroll.c @@ -65,11 +65,9 @@ static void * enroll_handle(void * o) bool boot_r = false; bool members_r = false; - bool dif_name_r = false; char * boot_ro = BOOT_PATH; char * members_ro = MEMBERS_PATH; - char * dif_ro = DIF_PATH; cdap = (struct cdap *) o; @@ -87,7 +85,7 @@ static void * enroll_handle(void * o) continue; } - while (!(boot_r && members_r && dif_name_r)) { + while (!(boot_r && members_r)) { key = cdap_request_wait(cdap, &oc, &name, &data, (size_t *) &len , &flags); assert(key >= 0); @@ -109,8 +107,6 @@ static void * enroll_handle(void * o) boot_r = true; } else if (strcmp(name, members_ro) == 0) { members_r = true; - } else if (strcmp(name, dif_ro) == 0) { - dif_name_r = true; } else if (strcmp(name, TIME_PATH) == 0) { struct timespec t; uint64_t buf[2]; @@ -153,13 +149,13 @@ static void * enroll_handle(void * o) cdap_del_flow(cdap, conn.flow_info.fd); flow_dealloc(conn.flow_info.fd); - boot_r = members_r = dif_name_r = false; + boot_r = members_r = false; } return 0; } -int enroll_boot(char * dst_name) +int enroll_boot(const char * dst) { struct cdap * cdap; cdap_key_t * key; @@ -174,7 +170,6 @@ int enroll_boot(char * dst_name) char * boot_ro = BOOT_PATH; char * members_ro = MEMBERS_PATH; - char * dif_ro = DIF_PATH; cdap = cdap_create(); if (cdap == NULL) { @@ -182,7 +177,7 @@ int enroll_boot(char * dst_name) return -1; } - if (connmgr_alloc(enroll.ae, dst_name, NULL, &conn)) { + if (connmgr_alloc(enroll.ae, dst, NULL, &conn)) { log_err("Failed to get connection."); cdap_destroy(cdap); return -1; @@ -195,7 +190,7 @@ int enroll_boot(char * dst_name) return -1; } - log_dbg("Getting boot information from %s.", dst_name); + log_dbg("Getting boot information from %s.", dst); clock_gettime(CLOCK_REALTIME, &t0); @@ -293,37 +288,6 @@ int enroll_boot(char * dst_name) log_dbg("Packed information inserted into RIB."); - key = cdap_request_send(cdap, CDAP_READ, dif_ro, NULL, 0, 0); - if (key == NULL || key[0] == INVALID_CDAP_KEY) { - log_err("Failed to send CDAP request."); - cdap_destroy(cdap); - flow_dealloc(conn.flow_info.fd); - return -1; - } - - if (cdap_reply_wait(cdap, key[0], &data, &len)) { - log_err("Failed to get CDAP reply."); - free(key); - cdap_destroy(cdap); - flow_dealloc(conn.flow_info.fd); - return -1; - } - - free(key); - - log_dbg("Packed information received (%zu bytes).", len); - - if (rib_unpack(data, len, UNPACK_CREATE)) { - log_warn("Error unpacking RIB data."); - rib_del(boot_ro); - free(data); - cdap_destroy(cdap); - flow_dealloc(conn.flow_info.fd); - return -1; - } - - log_dbg("Packed information inserted into RIB."); - cdap_destroy(cdap); flow_dealloc(conn.flow_info.fd); diff --git a/src/ipcpd/normal/enroll.h b/src/ipcpd/normal/enroll.h index 05f950ba..bed4bf9f 100644 --- a/src/ipcpd/normal/enroll.h +++ b/src/ipcpd/normal/enroll.h @@ -31,6 +31,6 @@ int enroll_start(void); void enroll_stop(void); -int enroll_boot(char * dst_name); +int enroll_boot(const char * dst); #endif /* OUROBOROS_IPCPD_NORMAL_ENROLL_H */ diff --git a/src/ipcpd/normal/flow_alloc.proto b/src/ipcpd/normal/flow_alloc.proto index 3b08f047..35624799 100644 --- a/src/ipcpd/normal/flow_alloc.proto +++ b/src/ipcpd/normal/flow_alloc.proto @@ -30,7 +30,7 @@ enum flow_alloc_code { message flow_alloc_msg { required flow_alloc_code code = 1; - optional string dst_name = 2; + optional bytes hash = 2; optional uint32 qoscube = 3; optional sint32 response = 4; }; diff --git a/src/ipcpd/normal/fmgr.c b/src/ipcpd/normal/fmgr.c index 19c329af..5166cc5d 100644 --- a/src/ipcpd/normal/fmgr.c +++ b/src/ipcpd/normal/fmgr.c @@ -427,9 +427,9 @@ void fmgr_stop(void) gam_destroy(fmgr.gam); } -int fmgr_np1_alloc(int fd, - char * dst_ap_name, - qoscube_t cube) +int fmgr_np1_alloc(int fd, + const uint8_t * dst, + qoscube_t cube) { cep_id_t cep_id; buffer_t buf; @@ -439,14 +439,17 @@ int fmgr_np1_alloc(int fd, ssize_t ch; ssize_t i; char ** children; + char hashstr[DIR_HASH_STRLEN + 1]; char * dst_ipcp = NULL; - assert(strlen(dst_ap_name) + strlen("/" DIR_NAME) + 1 + ipcp_hash_str(hashstr, dst); + + assert(strlen(hashstr) + strlen(DIR_PATH) + 1 < RIB_MAX_PATH_LEN); strcpy(path, DIR_PATH); - rib_path_append(path, dst_ap_name); + rib_path_append(path, hashstr); ch = rib_children(path, &children); if (ch <= 0) @@ -463,7 +466,7 @@ int fmgr_np1_alloc(int fd, if (dst_ipcp == NULL) return -1; - strcpy(path, "/" MEMBERS_NAME); + strcpy(path, MEMBERS_PATH); rib_path_append(path, dst_ipcp); @@ -472,10 +475,12 @@ int fmgr_np1_alloc(int fd, if (rib_read(path, &addr, sizeof(addr)) < 0) return -1; - msg.code = FLOW_ALLOC_CODE__FLOW_REQ; - msg.dst_name = dst_ap_name; + msg.code = FLOW_ALLOC_CODE__FLOW_REQ; + msg.has_hash = true; + msg.hash.len = ipcpi.dir_hash_len; + msg.hash.data = (uint8_t *) dst; msg.has_qoscube = true; - msg.qoscube = cube; + msg.qoscube = cube; buf.len = flow_alloc_msg__get_packed_size(&msg); if (buf.len == 0) @@ -637,6 +642,11 @@ int fmgr_np1_post_buf(cep_id_t cep_id, case FLOW_ALLOC_CODE__FLOW_REQ: pthread_mutex_lock(&ipcpi.alloc_lock); + if (!msg->has_hash) { + log_err("Bad flow request."); + return -1; + } + while (ipcpi.alloc_id != -1 && ipcp_get_state() == IPCP_OPERATIONAL) pthread_cond_timedwait(&ipcpi.alloc_cond, @@ -652,7 +662,8 @@ int fmgr_np1_post_buf(cep_id_t cep_id, assert(ipcpi.alloc_id == -1); fd = ipcp_flow_req_arr(getpid(), - msg->dst_name, + msg->hash.data, + ipcpi.dir_hash_len, msg->qoscube); if (fd < 0) { pthread_mutex_unlock(&ipcpi.alloc_lock); diff --git a/src/ipcpd/normal/fmgr.h b/src/ipcpd/normal/fmgr.h index b4d0b65a..c59c0875 100644 --- a/src/ipcpd/normal/fmgr.h +++ b/src/ipcpd/normal/fmgr.h @@ -37,9 +37,9 @@ int fmgr_start(void); void fmgr_stop(void); -int fmgr_np1_alloc(int fd, - char * dst_ap_name, - qoscube_t qos); +int fmgr_np1_alloc(int fd, + const uint8_t * dst, + qoscube_t qos); int fmgr_np1_alloc_resp(int fd, int response); diff --git a/src/ipcpd/normal/gam.h b/src/ipcpd/normal/gam.h index 4ae0b1b3..752d8e37 100644 --- a/src/ipcpd/normal/gam.h +++ b/src/ipcpd/normal/gam.h @@ -23,8 +23,8 @@ #ifndef OUROBOROS_IPCPD_NORMAL_GAM_H #define OUROBOROS_IPCPD_NORMAL_GAM_H +#include <ouroboros/ipcp.h> #include <ouroboros/cacep.h> -#include <ouroboros/irm_config.h> #include "neighbors.h" diff --git a/src/ipcpd/normal/main.c b/src/ipcpd/normal/main.c index ef7f07cf..e37a0fbc 100644 --- a/src/ipcpd/normal/main.c +++ b/src/ipcpd/normal/main.c @@ -23,12 +23,13 @@ #define OUROBOROS_PREFIX "normal-ipcp" #include <ouroboros/config.h> +#include <ouroboros/endian.h> #include <ouroboros/logs.h> #include <ouroboros/ipcp-dev.h> #include <ouroboros/time_utils.h> #include <ouroboros/irm.h> #include <ouroboros/rib.h> -#include <ouroboros/irm_config.h> +#include <ouroboros/hash.h> #include <ouroboros/errno.h> #include "addr_auth.h" @@ -49,37 +50,6 @@ #define THIS_TYPE IPCP_NORMAL -void ipcp_sig_handler(int sig, - siginfo_t * info, - void * c) -{ - (void) c; - - switch(sig) { - case SIGINT: - case SIGTERM: - case SIGHUP: - if (info->si_pid == ipcpi.irmd_api) { - pthread_rwlock_wrlock(&ipcpi.state_lock); - - if (ipcp_get_state() == IPCP_INIT) - ipcp_set_state(IPCP_NULL); - - if (ipcp_get_state() == IPCP_OPERATIONAL) - ipcp_set_state(IPCP_SHUTDOWN); - - pthread_rwlock_unlock(&ipcpi.state_lock); - } - default: - return; - } -} - -/* - * Boots the IPCP off information in the rib. - * Common function after bootstrap or enroll. - * Call under ipcpi.state_lock - */ static int boot_components(void) { char buf[256]; @@ -87,7 +57,7 @@ static int boot_components(void) enum pol_addr_auth pa; char path[RIB_MAX_PATH_LEN + 1]; - len = rib_read(DIF_PATH, &buf, 256); + len = rib_read(BOOT_PATH "/general/dif_name", buf, 256); if (len < 0) { log_err("Failed to read DIF name: %zd.", len); return -1; @@ -99,6 +69,17 @@ static int boot_components(void) return -1; } + len = rib_read(BOOT_PATH "/general/dir_hash_len", + &ipcpi.dir_hash_len, sizeof(ipcpi.dir_hash_len)); + if (len < 0) { + log_err("Failed to read hash length: %zd.", len); + return -1; + } + + ipcpi.dir_hash_len = ntoh16(ipcpi.dir_hash_len); + + assert(ipcpi.dir_hash_len != 0); + if (rib_add(MEMBERS_PATH, ipcpi.name)) { log_err("Failed to add name to " MEMBERS_PATH); return -1; @@ -160,12 +141,11 @@ static int boot_components(void) } if (fmgr_init()) { - log_err("Failed to initialize flow manager component."); frct_fini(); dir_fini(); ribmgr_fini(); addr_auth_fini(); - log_err("Failed to start flow manager."); + log_err("Failed to initialize flow manager component."); return -1; } @@ -229,38 +209,25 @@ void shutdown_components(void) free(ipcpi.dif_name); } -static int normal_ipcp_enroll(char * dst_name) +static int normal_ipcp_enroll(const char * dst) { - pthread_rwlock_wrlock(&ipcpi.state_lock); - - if (ipcp_get_state() != IPCP_INIT) { - pthread_rwlock_unlock(&ipcpi.state_lock); - log_err("IPCP in wrong state."); - return -1; /* -ENOTINIT */ - } - if (rib_add(RIB_ROOT, MEMBERS_NAME)) { - pthread_rwlock_unlock(&ipcpi.state_lock); log_err("Failed to create members."); return -1; } /* Get boot state from peer */ - if (enroll_boot(dst_name)) { - pthread_rwlock_unlock(&ipcpi.state_lock); + if (enroll_boot(dst)) { log_err("Failed to boot IPCP components."); return -1; } if (boot_components()) { - pthread_rwlock_unlock(&ipcpi.state_lock); log_err("Failed to boot IPCP components."); return -1; } - pthread_rwlock_unlock(&ipcpi.state_lock); - - log_dbg("Enrolled with %s.", dst_name); + log_dbg("Enrolled with " HASH_FMT, HASH_VAL(dst)); return 0; } @@ -269,12 +236,17 @@ const struct ros { char * parent; char * child; } ros[] = { - /* GENERAL IPCP INFO */ - {RIB_ROOT, DIF_NAME}, /* BOOT INFO */ {RIB_ROOT, BOOT_NAME}, /* OTHER RIB STRUCTURES */ {RIB_ROOT, MEMBERS_NAME}, + + /* GENERAL IPCP INFO */ + {BOOT_PATH, "general"}, + + {BOOT_PATH "/general", "dif_name"}, + {BOOT_PATH "/general", "dir_hash_len"}, + /* DT COMPONENT */ {BOOT_PATH, "dt"}, @@ -319,28 +291,28 @@ int normal_rib_init(void) return 0; } -static int normal_ipcp_bootstrap(struct dif_config * conf) +static int normal_ipcp_bootstrap(const struct ipcp_config * conf) { + uint16_t hash_len; + assert(conf); assert(conf->type == THIS_TYPE); - pthread_rwlock_wrlock(&ipcpi.state_lock); + hash_len = hton16((uint16_t) conf->dir_hash_len); - if (ipcp_get_state() != IPCP_INIT) { - pthread_rwlock_unlock(&ipcpi.state_lock); - log_err("IPCP in wrong state."); - return -1; /* -ENOTINIT */ - } + assert(ntoh16(hash_len) != 0); if (normal_rib_init()) { - pthread_rwlock_unlock(&ipcpi.state_lock); log_err("Failed to write initial structure to the RIB."); return -1; } - if (rib_write(DIF_PATH, + if (rib_write(BOOT_PATH "/general/dif_name", conf->dif_name, strlen(conf->dif_name) + 1) || + rib_write(BOOT_PATH "/general/dir_hash_len", + &hash_len, + sizeof(hash_len)) || rib_write(BOOT_PATH "/dt/const/addr_size", &conf->addr_size, sizeof(conf->addr_size)) || @@ -375,18 +347,14 @@ static int normal_ipcp_bootstrap(struct dif_config * conf) &conf->addr_auth_type, sizeof(conf->addr_auth_type))) { log_err("Failed to write boot info to RIB."); - pthread_rwlock_unlock(&ipcpi.state_lock); return -1; } if (boot_components()) { log_err("Failed to boot IPCP components."); - pthread_rwlock_unlock(&ipcpi.state_lock); return -1; } - pthread_rwlock_unlock(&ipcpi.state_lock); - log_dbg("Bootstrapped in DIF %s.", conf->dif_name); return 0; @@ -395,9 +363,9 @@ static int normal_ipcp_bootstrap(struct dif_config * conf) static struct ipcp_ops normal_ops = { .ipcp_bootstrap = normal_ipcp_bootstrap, .ipcp_enroll = normal_ipcp_enroll, - .ipcp_name_reg = dir_name_reg, - .ipcp_name_unreg = dir_name_unreg, - .ipcp_name_query = dir_name_query, + .ipcp_reg = dir_reg, + .ipcp_unreg = dir_unreg, + .ipcp_query = dir_query, .ipcp_flow_alloc = fmgr_np1_alloc, .ipcp_flow_alloc_resp = fmgr_np1_alloc_resp, .ipcp_flow_dealloc = fmgr_np1_dealloc @@ -406,27 +374,6 @@ static struct ipcp_ops normal_ops = { int main(int argc, char * argv[]) { - struct sigaction sig_act; - sigset_t sigset; - - sigemptyset(&sigset); - sigaddset(&sigset, SIGINT); - sigaddset(&sigset, SIGQUIT); - sigaddset(&sigset, SIGHUP); - sigaddset(&sigset, SIGPIPE); - - /* init sig_act */ - memset(&sig_act, 0, sizeof(sig_act)); - - /* install signal traps */ - sig_act.sa_sigaction = &ipcp_sig_handler; - sig_act.sa_flags = SA_SIGINFO; - - sigaction(SIGINT, &sig_act, NULL); - sigaction(SIGTERM, &sig_act, NULL); - sigaction(SIGHUP, &sig_act, NULL); - sigaction(SIGPIPE, &sig_act, NULL); - if (ipcp_init(argc, argv, THIS_TYPE, &normal_ops) < 0) { ipcp_create_r(getpid(), -1); exit(EXIT_FAILURE); @@ -466,7 +413,6 @@ int main(int argc, exit(EXIT_FAILURE); } - pthread_sigmask(SIG_BLOCK, &sigset, NULL); if (ipcp_boot() < 0) { log_err("Failed to boot IPCP."); @@ -479,8 +425,6 @@ int main(int argc, exit(EXIT_FAILURE); } - pthread_sigmask(SIG_UNBLOCK, &sigset, NULL); - if (ipcp_create_r(getpid(), 0)) { log_err("Failed to notify IRMd we are initialized."); ipcp_set_state(IPCP_NULL); diff --git a/src/ipcpd/normal/neighbors.h b/src/ipcpd/normal/neighbors.h index 8714a9aa..c958affc 100644 --- a/src/ipcpd/normal/neighbors.h +++ b/src/ipcpd/normal/neighbors.h @@ -23,7 +23,7 @@ #ifndef OUROBOROS_IPCPD_NORMAL_NEIGHBORS_H #define OUROBOROS_IPCPD_NORMAL_NEIGHBORS_H -#include <ouroboros/irm_config.h> +#include <ouroboros/ipcp.h> #include <ouroboros/list.h> #include <ouroboros/qos.h> #include <ouroboros/fqueue.h> diff --git a/src/ipcpd/normal/pol/complete.h b/src/ipcpd/normal/pol/complete.h index 46a535c2..230fecb9 100644 --- a/src/ipcpd/normal/pol/complete.h +++ b/src/ipcpd/normal/pol/complete.h @@ -23,7 +23,7 @@ #ifndef OUROBOROS_IPCPD_NORMAL_POL_COMPLETE_H #define OUROBOROS_IPCPD_NORMAL_POL_COMPLETE_H -#include <ouroboros/irm_config.h> +#include <ouroboros/ipcp.h> #include <ouroboros/qos.h> #include "pol-gam-ops.h" diff --git a/src/ipcpd/normal/ribconfig.h b/src/ipcpd/normal/ribconfig.h index 5ecdaab3..2f5daf72 100644 --- a/src/ipcpd/normal/ribconfig.h +++ b/src/ipcpd/normal/ribconfig.h @@ -29,10 +29,8 @@ #define DLR "/" #define BOOT_NAME "boot" #define MEMBERS_NAME "members" -#define DIF_NAME "dif_name" #define DIR_NAME "directory" #define ROUTING_NAME "fsdb" -#define DIF_PATH DLR DIF_NAME #define DIR_PATH DLR DIR_NAME #define BOOT_PATH DLR BOOT_NAME #define MEMBERS_PATH DLR MEMBERS_NAME diff --git a/src/ipcpd/normal/ribmgr.h b/src/ipcpd/normal/ribmgr.h index 8922688a..83d5ec3a 100644 --- a/src/ipcpd/normal/ribmgr.h +++ b/src/ipcpd/normal/ribmgr.h @@ -23,7 +23,7 @@ #ifndef OUROBOROS_IPCPD_NORMAL_RIBMGR_H #define OUROBOROS_IPCPD_NORMAL_RIBMGR_H -#include <ouroboros/irm_config.h> +#include <ouroboros/ipcp.h> #include <ouroboros/utils.h> #include <ouroboros/qos.h> diff --git a/src/ipcpd/shim-data.c b/src/ipcpd/shim-data.c index eb4ec33f..4459837d 100644 --- a/src/ipcpd/shim-data.c +++ b/src/ipcpd/shim-data.c @@ -34,26 +34,24 @@ struct reg_entry { struct list_head list; - char * name; + uint8_t * hash; }; struct dir_entry { struct list_head list; - char * name; + uint8_t * hash; uint64_t addr; }; -static struct reg_entry * reg_entry_create(char * name) +static struct reg_entry * reg_entry_create(uint8_t * hash) { struct reg_entry * entry = malloc(sizeof(*entry)); if (entry == NULL) return NULL; - assert(name); + assert(hash); - entry->name = name; - if (entry->name == NULL) - return NULL; + entry->hash = hash; return entry; } @@ -62,25 +60,23 @@ static void reg_entry_destroy(struct reg_entry * entry) { assert(entry); - if (entry->name != NULL) - free(entry->name); + if (entry->hash != NULL) + free(entry->hash); free(entry); } -static struct dir_entry * dir_entry_create(char * name, - uint64_t addr) +static struct dir_entry * dir_entry_create(uint8_t * hash, + uint64_t addr) { struct dir_entry * entry = malloc(sizeof(*entry)); if (entry == NULL) return NULL; - assert(name); + assert(hash); - entry->addr = addr; - entry->name = name; - if (entry->name == NULL) - return NULL; + entry->addr = addr; + entry->hash = hash; return entry; } @@ -89,8 +85,8 @@ static void dir_entry_destroy(struct dir_entry * entry) { assert(entry); - if (entry->name != NULL) - free(entry->name); + if (entry->hash != NULL) + free(entry->hash); free(entry); } @@ -181,17 +177,17 @@ void shim_data_destroy(struct shim_data * data) free(data); } -static struct reg_entry * find_reg_entry_by_name(struct shim_data * data, - const char * name) +static struct reg_entry * find_reg_entry_by_hash(struct shim_data * data, + const uint8_t * hash) { struct list_head * h; assert(data); - assert(name); + assert(hash); list_for_each(h, &data->registry) { struct reg_entry * e = list_entry(h, struct reg_entry, list); - if (!strcmp(e->name, name)) + if (!memcmp(e->hash, hash, ipcpi.dir_hash_len)) return e; } @@ -199,13 +195,14 @@ static struct reg_entry * find_reg_entry_by_name(struct shim_data * data, } static struct dir_entry * find_dir_entry(struct shim_data * data, - const char * name, + const uint8_t * hash, uint64_t addr) { struct list_head * h; list_for_each(h, &data->directory) { struct dir_entry * e = list_entry(h, struct dir_entry, list); - if (e->addr == addr && !strcmp(e->name, name)) + if (e->addr == addr && + !memcmp(e->hash, hash, ipcpi.dir_hash_len)) return e; } @@ -213,12 +210,12 @@ static struct dir_entry * find_dir_entry(struct shim_data * data, } static struct dir_entry * find_dir_entry_any(struct shim_data * data, - const char * name) + const uint8_t * hash) { struct list_head * h; list_for_each(h, &data->directory) { struct dir_entry * e = list_entry(h, struct dir_entry, list); - if (!strcmp(e->name, name)) + if (!memcmp(e->hash, hash, ipcpi.dir_hash_len)) return e; } @@ -226,21 +223,21 @@ static struct dir_entry * find_dir_entry_any(struct shim_data * data, } int shim_data_reg_add_entry(struct shim_data * data, - char * name) + uint8_t * hash) { struct reg_entry * entry; - if (data == NULL || name == NULL) - return -1; + assert(data); + assert(hash); pthread_rwlock_wrlock(&data->reg_lock); - if (find_reg_entry_by_name(data, name)) { + if (find_reg_entry_by_hash(data, hash)) { pthread_rwlock_unlock(&data->reg_lock); return -1; } - entry = reg_entry_create(name); + entry = reg_entry_create(hash); if (entry == NULL) { pthread_rwlock_unlock(&data->reg_lock); return -1; @@ -254,7 +251,7 @@ int shim_data_reg_add_entry(struct shim_data * data, } int shim_data_reg_del_entry(struct shim_data * data, - const char * name) + const uint8_t * hash) { struct reg_entry * e; if (data == NULL) @@ -262,7 +259,7 @@ int shim_data_reg_del_entry(struct shim_data * data, pthread_rwlock_wrlock(&data->reg_lock); - e = find_reg_entry_by_name(data, name); + e = find_reg_entry_by_hash(data, hash); if (e == NULL) { pthread_rwlock_unlock(&data->reg_lock); return 0; /* nothing to do */ @@ -278,16 +275,16 @@ int shim_data_reg_del_entry(struct shim_data * data, } bool shim_data_reg_has(struct shim_data * data, - const char * name) + const uint8_t * hash) { bool ret = false; - if (data == NULL || name == NULL) - return false; + assert(data); + assert(hash); pthread_rwlock_rdlock(&data->reg_lock); - ret = (find_reg_entry_by_name(data, name) != NULL); + ret = (find_reg_entry_by_hash(data, hash) != NULL); pthread_rwlock_unlock(&data->reg_lock); @@ -295,29 +292,29 @@ bool shim_data_reg_has(struct shim_data * data, } int shim_data_dir_add_entry(struct shim_data * data, - char * name, + const uint8_t * hash, uint64_t addr) { struct dir_entry * entry; - char * entry_name; + uint8_t * entry_hash; - if (data == NULL || name == NULL) - return -1; + assert(data); + assert(hash); pthread_rwlock_wrlock(&data->dir_lock); - if (find_dir_entry(data, name, addr) != NULL) { + if (find_dir_entry(data, hash, addr) != NULL) { pthread_rwlock_unlock(&data->dir_lock); return -1; } - entry_name = strdup(name); - if (entry_name == NULL) { + entry_hash = ipcp_hash_dup(hash); + if (entry_hash == NULL) { pthread_rwlock_unlock(&data->dir_lock); return -1; } - entry = dir_entry_create(entry_name, addr); + entry = dir_entry_create(entry_hash, addr); if (entry == NULL) { pthread_rwlock_unlock(&data->dir_lock); return -1; @@ -331,7 +328,7 @@ int shim_data_dir_add_entry(struct shim_data * data, } int shim_data_dir_del_entry(struct shim_data * data, - const char * name, + const uint8_t * hash, uint64_t addr) { struct dir_entry * e; @@ -340,7 +337,7 @@ int shim_data_dir_del_entry(struct shim_data * data, pthread_rwlock_wrlock(&data->dir_lock); - e = find_dir_entry(data, name, addr); + e = find_dir_entry(data, hash, addr); if (e == NULL) { pthread_rwlock_unlock(&data->dir_lock); return 0; /* nothing to do */ @@ -356,13 +353,13 @@ int shim_data_dir_del_entry(struct shim_data * data, } bool shim_data_dir_has(struct shim_data * data, - const char * name) + const uint8_t * hash) { bool ret = false; pthread_rwlock_rdlock(&data->dir_lock); - ret = (find_dir_entry_any(data, name) != NULL); + ret = (find_dir_entry_any(data, hash) != NULL); pthread_rwlock_unlock(&data->dir_lock); @@ -370,14 +367,14 @@ bool shim_data_dir_has(struct shim_data * data, } uint64_t shim_data_dir_get_addr(struct shim_data * data, - const char * name) + const uint8_t * hash) { struct dir_entry * entry; uint64_t addr; pthread_rwlock_rdlock(&data->dir_lock); - entry = find_dir_entry_any(data, name); + entry = find_dir_entry_any(data, hash); if (entry == NULL) { pthread_rwlock_unlock(&data->dir_lock); @@ -391,7 +388,7 @@ uint64_t shim_data_dir_get_addr(struct shim_data * data, return addr; } -struct dir_query * shim_data_dir_query_create(char * name) +struct dir_query * shim_data_dir_query_create(const uint8_t * hash) { struct dir_query * query; pthread_condattr_t cattr; @@ -400,8 +397,8 @@ struct dir_query * shim_data_dir_query_create(char * name) if (query == NULL) return NULL; - query->name = strdup(name); - if (query->name == NULL) { + query->hash = ipcp_hash_dup(hash); + if (query->hash == NULL) { free(query); return NULL; } @@ -467,7 +464,7 @@ void shim_data_dir_query_destroy(struct dir_query * query) pthread_cond_destroy(&query->cond); pthread_mutex_destroy(&query->lock); - free(query->name); + free(query->hash); free(query); } diff --git a/src/ipcpd/shim-data.h b/src/ipcpd/shim-data.h index ac670b43..d53373df 100644 --- a/src/ipcpd/shim-data.h +++ b/src/ipcpd/shim-data.h @@ -30,7 +30,6 @@ #include <pthread.h> #include <stdint.h> - enum dir_query_state { QUERY_INIT = 0, QUERY_PENDING, @@ -41,7 +40,7 @@ enum dir_query_state { struct dir_query { struct list_head next; - char * name; + uint8_t * hash; enum dir_query_state state; pthread_mutex_t lock; @@ -49,14 +48,14 @@ struct dir_query { }; struct shim_data { - struct list_head registry; - pthread_rwlock_t reg_lock; + struct list_head registry; + pthread_rwlock_t reg_lock; - struct list_head directory; - pthread_rwlock_t dir_lock; + struct list_head directory; + pthread_rwlock_t dir_lock; - struct list_head dir_queries; - pthread_mutex_t dir_queries_lock; + struct list_head dir_queries; + pthread_mutex_t dir_queries_lock; }; struct shim_data * shim_data_create(void); @@ -64,29 +63,29 @@ struct shim_data * shim_data_create(void); void shim_data_destroy(struct shim_data * data); int shim_data_reg_add_entry(struct shim_data * data, - char * name); + uint8_t * hash); int shim_data_reg_del_entry(struct shim_data * data, - const char * name); + const uint8_t * hash); bool shim_data_reg_has(struct shim_data * data, - const char * name); + const uint8_t * hash); int shim_data_dir_add_entry(struct shim_data * data, - char * name, + const uint8_t * hash, uint64_t addr); int shim_data_dir_del_entry(struct shim_data * data, - const char * name, + const uint8_t * hash, uint64_t addr); bool shim_data_dir_has(struct shim_data * data, - const char * name); + const uint8_t * hash); uint64_t shim_data_dir_get_addr(struct shim_data * data, - const char * name); + const uint8_t * hash); -struct dir_query * shim_data_dir_query_create(char * name); +struct dir_query * shim_data_dir_query_create(const uint8_t * hash); void shim_data_dir_query_respond(struct dir_query * query); diff --git a/src/ipcpd/shim-eth-llc/main.c b/src/ipcpd/shim-eth-llc/main.c index 27456eb7..9a9e11b5 100644 --- a/src/ipcpd/shim-eth-llc/main.c +++ b/src/ipcpd/shim-eth-llc/main.c @@ -34,6 +34,7 @@ #include <ouroboros/fqueue.h> #include <ouroboros/logs.h> #include <ouroboros/time_utils.h> +#include <ouroboros/hash.h> #include "ipcp.h" #include "shim_eth_llc_messages.pb-c.h" @@ -248,11 +249,11 @@ static uint8_t reverse_bits(uint8_t b) return b; } -static int eth_llc_ipcp_send_frame(uint8_t * dst_addr, - uint8_t dsap, - uint8_t ssap, - uint8_t * payload, - size_t len) +static int eth_llc_ipcp_send_frame(const uint8_t * dst_addr, + uint8_t dsap, + uint8_t ssap, + const uint8_t * payload, + size_t len) { uint32_t frame_len = 0; uint8_t cf = 0x03; @@ -311,7 +312,7 @@ static int eth_llc_ipcp_send_frame(uint8_t * dst_addr, } static int eth_llc_ipcp_send_mgmt_frame(shim_eth_llc_msg_t * msg, - uint8_t * dst_addr) + const uint8_t * dst_addr) { size_t len; uint8_t * buf; @@ -338,17 +339,19 @@ static int eth_llc_ipcp_send_mgmt_frame(shim_eth_llc_msg_t * msg, return 0; } -static int eth_llc_ipcp_sap_alloc(uint8_t * dst_addr, - uint8_t ssap, - char * dst_name, - qoscube_t cube) +static int eth_llc_ipcp_sap_alloc(const uint8_t * dst_addr, + uint8_t ssap, + const uint8_t * hash, + qoscube_t cube) { shim_eth_llc_msg_t msg = SHIM_ETH_LLC_MSG__INIT; msg.code = SHIM_ETH_LLC_MSG_CODE__FLOW_REQ; msg.has_ssap = true; msg.ssap = ssap; - msg.dst_name = dst_name; + msg.has_hash = true; + msg.hash.len = ipcpi.dir_hash_len; + msg.hash.data = (uint8_t *) hash; msg.has_qoscube = true; msg.qoscube = cube; @@ -373,10 +376,10 @@ static int eth_llc_ipcp_sap_alloc_resp(uint8_t * dst_addr, return eth_llc_ipcp_send_mgmt_frame(&msg, dst_addr); } -static int eth_llc_ipcp_sap_req(uint8_t r_sap, - uint8_t * r_addr, - char * dst_name, - qoscube_t cube) +static int eth_llc_ipcp_sap_req(uint8_t r_sap, + uint8_t * r_addr, + const uint8_t * dst, + qoscube_t cube) { struct timespec ts = {0, EVENT_WAIT_TIMEOUT * 1000}; int fd; @@ -395,7 +398,7 @@ static int eth_llc_ipcp_sap_req(uint8_t r_sap, } /* reply to IRM, called under lock to prevent race */ - fd = ipcp_flow_req_arr(getpid(), dst_name, cube); + fd = ipcp_flow_req_arr(getpid(), dst, ipcpi.dir_hash_len, cube); if (fd < 0) { pthread_mutex_unlock(&ipcpi.alloc_lock); log_err("Could not get new flow from IRMd."); @@ -453,14 +456,16 @@ static int eth_llc_ipcp_sap_alloc_reply(uint8_t ssap, } -static int eth_llc_ipcp_name_query_req(char * name, - uint8_t * r_addr) +static int eth_llc_ipcp_name_query_req(const uint8_t * hash, + uint8_t * r_addr) { shim_eth_llc_msg_t msg = SHIM_ETH_LLC_MSG__INIT; - if (shim_data_reg_has(ipcpi.shim_data, name)) { - msg.code = SHIM_ETH_LLC_MSG_CODE__NAME_QUERY_REPLY; - msg.dst_name = name; + if (shim_data_reg_has(ipcpi.shim_data, hash)) { + msg.code = SHIM_ETH_LLC_MSG_CODE__NAME_QUERY_REPLY; + msg.has_hash = true; + msg.hash.len = ipcpi.dir_hash_len; + msg.hash.data = (uint8_t *) hash; eth_llc_ipcp_send_mgmt_frame(&msg, r_addr); } @@ -468,21 +473,21 @@ static int eth_llc_ipcp_name_query_req(char * name, return 0; } -static int eth_llc_ipcp_name_query_reply(char * name, - uint8_t * r_addr) +static int eth_llc_ipcp_name_query_reply(const uint8_t * hash, + uint8_t * r_addr) { uint64_t address = 0; struct list_head * pos; memcpy(&address, r_addr, MAC_SIZE); - shim_data_dir_add_entry(ipcpi.shim_data, name, address); + shim_data_dir_add_entry(ipcpi.shim_data, hash, address); pthread_mutex_lock(&ipcpi.shim_data->dir_queries_lock); list_for_each(pos, &ipcpi.shim_data->dir_queries) { struct dir_query * e = list_entry(pos, struct dir_query, next); - if (strcmp(e->name, name) == 0) { + if (memcmp(e->hash, hash, ipcpi.dir_hash_len) == 0) { shim_data_dir_query_respond(e); } } @@ -491,9 +496,9 @@ static int eth_llc_ipcp_name_query_reply(char * name, return 0; } -static int eth_llc_ipcp_mgmt_frame(uint8_t * buf, - size_t len, - uint8_t * r_addr) +static int eth_llc_ipcp_mgmt_frame(const uint8_t * buf, + size_t len, + uint8_t * r_addr) { shim_eth_llc_msg_t * msg; @@ -505,10 +510,10 @@ static int eth_llc_ipcp_mgmt_frame(uint8_t * buf, switch (msg->code) { case SHIM_ETH_LLC_MSG_CODE__FLOW_REQ: - if (shim_data_reg_has(ipcpi.shim_data, msg->dst_name)) { + if (shim_data_reg_has(ipcpi.shim_data, msg->hash.data)) { eth_llc_ipcp_sap_req(msg->ssap, r_addr, - msg->dst_name, + msg->hash.data, msg->qoscube); } break; @@ -519,10 +524,10 @@ static int eth_llc_ipcp_mgmt_frame(uint8_t * buf, msg->response); break; case SHIM_ETH_LLC_MSG_CODE__NAME_QUERY_REQ: - eth_llc_ipcp_name_query_req(msg->dst_name, r_addr); + eth_llc_ipcp_name_query_req(msg->hash.data, r_addr); break; case SHIM_ETH_LLC_MSG_CODE__NAME_QUERY_REPLY: - eth_llc_ipcp_name_query_reply(msg->dst_name, r_addr); + eth_llc_ipcp_name_query_reply(msg->hash.data, r_addr); break; default: log_err("Unknown message received %d.", msg->code); @@ -734,29 +739,7 @@ static void * eth_llc_ipcp_sdu_writer(void * o) return (void *) 1; } -void ipcp_sig_handler(int sig, - siginfo_t * info, - void * c) -{ - (void) c; - - switch(sig) { - case SIGINT: - case SIGTERM: - case SIGHUP: - if (info->si_pid == ipcpi.irmd_api) { - if (ipcp_get_state() == IPCP_INIT) - ipcp_set_state(IPCP_NULL); - - if (ipcp_get_state() == IPCP_OPERATIONAL) - ipcp_set_state(IPCP_SHUTDOWN); - } - default: - return; - } -} - -static int eth_llc_ipcp_bootstrap(struct dif_config * conf) +static int eth_llc_ipcp_bootstrap(const struct ipcp_config * conf) { int idx; struct ifreq ifr; @@ -777,10 +760,7 @@ static int eth_llc_ipcp_bootstrap(struct dif_config * conf) assert(conf); assert(conf->type == THIS_TYPE); - if (ipcp_get_state() != IPCP_INIT) { - log_err("IPCP in wrong state."); - return -1; - } + ipcpi.dir_hash_len = conf->dir_hash_len; if (conf->if_name == NULL) { log_err("Interface name is NULL."); @@ -921,35 +901,36 @@ static int eth_llc_ipcp_bootstrap(struct dif_config * conf) return 0; } -static int eth_llc_ipcp_name_reg(char * name) +static int eth_llc_ipcp_reg(const uint8_t * hash) { - char * name_dup; + uint8_t * hash_dup; - name_dup = strdup(name); - if (name_dup == NULL) { - log_err("Failed to duplicate name."); + hash_dup = ipcp_hash_dup(hash); + if (hash_dup == NULL) { + log_err("Failed to duplicate hash."); return -ENOMEM; } - if (shim_data_reg_add_entry(ipcpi.shim_data, name_dup)) { - log_err("Failed to add %s to local registry.", name); - free(name_dup); + if (shim_data_reg_add_entry(ipcpi.shim_data, hash_dup)) { + log_err("Failed to add " HASH_FMT " to local registry.", + HASH_VAL(hash)); + free(hash_dup); return -1; } - log_dbg("Registered %s.", name); + log_dbg("Registered " HASH_FMT ".", HASH_VAL(hash)); return 0; } -static int eth_llc_ipcp_name_unreg(char * name) +static int eth_llc_ipcp_unreg(const uint8_t * hash) { - shim_data_reg_del_entry(ipcpi.shim_data, name); + shim_data_reg_del_entry(ipcpi.shim_data, hash); return 0; } -static int eth_llc_ipcp_name_query(char * name) +static int eth_llc_ipcp_query(const uint8_t * hash) { uint8_t r_addr[MAC_SIZE]; struct timespec timeout = {(NAME_QUERY_TIMEOUT / 1000), @@ -958,15 +939,17 @@ static int eth_llc_ipcp_name_query(char * name) struct dir_query * query; int ret; - if (shim_data_dir_has(ipcpi.shim_data, name)) + if (shim_data_dir_has(ipcpi.shim_data, hash)) return 0; - msg.code = SHIM_ETH_LLC_MSG_CODE__NAME_QUERY_REQ; - msg.dst_name = name; + msg.code = SHIM_ETH_LLC_MSG_CODE__NAME_QUERY_REQ; + msg.has_hash = true; + msg.hash.len = ipcpi.dir_hash_len; + msg.hash.data = (uint8_t *) hash; memset(r_addr, 0xff, MAC_SIZE); - query = shim_data_dir_query_create(name); + query = shim_data_dir_query_create(hash); if (query == NULL) return -1; @@ -986,34 +969,28 @@ static int eth_llc_ipcp_name_query(char * name) return ret; } -static int eth_llc_ipcp_flow_alloc(int fd, - char * dst_name, - qoscube_t cube) +static int eth_llc_ipcp_flow_alloc(int fd, + const uint8_t * hash, + qoscube_t cube) { uint8_t ssap = 0; uint8_t r_addr[MAC_SIZE]; uint64_t addr = 0; - log_dbg("Allocating flow to %s.", dst_name); + log_dbg("Allocating flow to " HASH_FMT ".", HASH_VAL(hash)); - if (dst_name == NULL) - return -1; + assert(hash); if (cube != QOS_CUBE_BE && cube != QOS_CUBE_FRC) { log_dbg("Unsupported QoS requested."); return -1; } - if (ipcp_get_state() != IPCP_OPERATIONAL) { - log_dbg("Won't allocate flow with non-enrolled IPCP."); - return -1; /* -ENOTENROLLED */ - } - - if (!shim_data_dir_has(ipcpi.shim_data, dst_name)) { + if (!shim_data_dir_has(ipcpi.shim_data, hash)) { log_err("Destination unreachable."); return -1; } - addr = shim_data_dir_get_addr(ipcpi.shim_data, dst_name); + addr = shim_data_dir_get_addr(ipcpi.shim_data, hash); pthread_rwlock_wrlock(ð_llc_data.flows_lock); @@ -1030,7 +1007,7 @@ static int eth_llc_ipcp_flow_alloc(int fd, memcpy(r_addr, &addr, MAC_SIZE); - if (eth_llc_ipcp_sap_alloc(r_addr, ssap, dst_name, cube) < 0) { + if (eth_llc_ipcp_sap_alloc(r_addr, ssap, hash, cube) < 0) { pthread_rwlock_wrlock(ð_llc_data.flows_lock); bmp_release(eth_llc_data.saps, eth_llc_data.fd_to_ef[fd].sap); eth_llc_data.fd_to_ef[fd].sap = -1; @@ -1107,11 +1084,6 @@ static int eth_llc_ipcp_flow_dealloc(int fd) ipcp_flow_fini(fd); - if (ipcp_get_state() != IPCP_OPERATIONAL) { - log_dbg("Won't register with non-enrolled IPCP."); - return -1; /* -ENOTENROLLED */ - } - pthread_rwlock_wrlock(ð_llc_data.flows_lock); flow_set_del(eth_llc_data.np1_flows, fd); @@ -1137,9 +1109,9 @@ static int eth_llc_ipcp_flow_dealloc(int fd) static struct ipcp_ops eth_llc_ops = { .ipcp_bootstrap = eth_llc_ipcp_bootstrap, .ipcp_enroll = NULL, - .ipcp_name_reg = eth_llc_ipcp_name_reg, - .ipcp_name_unreg = eth_llc_ipcp_name_unreg, - .ipcp_name_query = eth_llc_ipcp_name_query, + .ipcp_reg = eth_llc_ipcp_reg, + .ipcp_unreg = eth_llc_ipcp_unreg, + .ipcp_query = eth_llc_ipcp_query, .ipcp_flow_alloc = eth_llc_ipcp_flow_alloc, .ipcp_flow_alloc_resp = eth_llc_ipcp_flow_alloc_resp, .ipcp_flow_dealloc = eth_llc_ipcp_flow_dealloc @@ -1148,27 +1120,6 @@ static struct ipcp_ops eth_llc_ops = { int main(int argc, char * argv[]) { - struct sigaction sig_act; - sigset_t sigset; - - sigemptyset(&sigset); - sigaddset(&sigset, SIGINT); - sigaddset(&sigset, SIGQUIT); - sigaddset(&sigset, SIGHUP); - sigaddset(&sigset, SIGPIPE); - - /* init sig_act */ - memset(&sig_act, 0, sizeof(sig_act)); - - /* install signal traps */ - sig_act.sa_sigaction = &ipcp_sig_handler; - sig_act.sa_flags = SA_SIGINFO; - - sigaction(SIGINT, &sig_act, NULL); - sigaction(SIGTERM, &sig_act, NULL); - sigaction(SIGHUP, &sig_act, NULL); - sigaction(SIGPIPE, &sig_act, NULL); - if (ipcp_init(argc, argv, THIS_TYPE, ð_llc_ops) < 0) { ipcp_create_r(getpid(), -1); exit(EXIT_FAILURE); @@ -1181,9 +1132,6 @@ int main(int argc, exit(EXIT_FAILURE); } - - pthread_sigmask(SIG_BLOCK, &sigset, NULL); - if (ipcp_boot() < 0) { log_err("Failed to boot IPCP."); ipcp_create_r(getpid(), -1); @@ -1192,8 +1140,6 @@ int main(int argc, exit(EXIT_FAILURE); } - pthread_sigmask(SIG_UNBLOCK, &sigset, NULL); - if (ipcp_create_r(getpid(), 0)) { log_err("Failed to notify IRMd we are initialized."); ipcp_set_state(IPCP_NULL); diff --git a/src/ipcpd/shim-eth-llc/shim_eth_llc_messages.proto b/src/ipcpd/shim-eth-llc/shim_eth_llc_messages.proto index 2d66428c..09281698 100644 --- a/src/ipcpd/shim-eth-llc/shim_eth_llc_messages.proto +++ b/src/ipcpd/shim-eth-llc/shim_eth_llc_messages.proto @@ -31,7 +31,7 @@ enum shim_eth_llc_msg_code { message shim_eth_llc_msg { required shim_eth_llc_msg_code code = 1; - optional string dst_name = 2; + optional bytes hash = 2; optional uint32 ssap = 3; optional uint32 dsap = 4; optional uint32 qoscube = 5; diff --git a/src/ipcpd/shim-udp/main.c b/src/ipcpd/shim-udp/main.c index b1a88fae..e1fe5c7c 100644 --- a/src/ipcpd/shim-udp/main.c +++ b/src/ipcpd/shim-udp/main.c @@ -30,6 +30,7 @@ #include <ouroboros/fqueue.h> #include <ouroboros/errno.h> #include <ouroboros/logs.h> +#include <ouroboros/hash.h> #include "shim_udp_messages.pb-c.h" #include "ipcp.h" @@ -197,14 +198,16 @@ static int send_shim_udp_msg(shim_udp_msg_t * msg, static int ipcp_udp_port_alloc(uint32_t dst_ip_addr, uint16_t src_udp_port, - char * dst_name, + const uint8_t * dst, qoscube_t cube) { shim_udp_msg_t msg = SHIM_UDP_MSG__INIT; msg.code = SHIM_UDP_MSG_CODE__FLOW_REQ; msg.src_udp_port = src_udp_port; - msg.dst_name = dst_name; + msg.has_hash = true; + msg.hash.len = ipcpi.dir_hash_len; + msg.hash.data = (uint8_t *) dst; msg.has_qoscube = true; msg.qoscube = cube; @@ -229,7 +232,7 @@ static int ipcp_udp_port_alloc_resp(uint32_t dst_ip_addr, } static int ipcp_udp_port_req(struct sockaddr_in * c_saddr, - char * dst_name, + const uint8_t * dst, qoscube_t cube) { struct timespec ts = {0, FD_UPDATE_TIMEOUT * 1000}; @@ -283,7 +286,7 @@ static int ipcp_udp_port_req(struct sockaddr_in * c_saddr, } /* reply to IRM */ - fd = ipcp_flow_req_arr(getpid(), dst_name, cube); + fd = ipcp_flow_req_arr(getpid(), dst, ipcpi.dir_hash_len, cube); if (fd < 0) { pthread_mutex_unlock(&ipcpi.alloc_lock); log_err("Could not get new flow from IRMd."); @@ -291,7 +294,6 @@ static int ipcp_udp_port_req(struct sockaddr_in * c_saddr, return -1; } - pthread_rwlock_rdlock(&ipcpi.state_lock); pthread_rwlock_wrlock(&udp_data.flows_lock); udp_data.uf_to_fd[skfd] = fd; @@ -299,7 +301,6 @@ static int ipcp_udp_port_req(struct sockaddr_in * c_saddr, udp_data.fd_to_uf[fd].udp = f_saddr.sin_port; pthread_rwlock_unlock(&udp_data.flows_lock); - pthread_rwlock_unlock(&ipcpi.state_lock); pthread_mutex_unlock(&ipcpi.alloc_lock); ipcpi.alloc_id = fd; @@ -337,14 +338,12 @@ static int ipcp_udp_port_alloc_reply(uint16_t src_udp_port, log_dbg("Received reply for flow on udp port %d.", ntohs(dst_udp_port)); - pthread_rwlock_rdlock(&ipcpi.state_lock); pthread_rwlock_rdlock(&udp_data.flows_lock); fd = udp_port_to_fd(dst_udp_port); skfd = udp_data.fd_to_uf[fd].skfd; pthread_rwlock_unlock(&udp_data.flows_lock); - pthread_rwlock_unlock(&ipcpi.state_lock); /* get the original address with the LISTEN PORT */ if (getpeername(skfd, (struct sockaddr *) &t_saddr, &t_saddr_len) < 0) { @@ -360,13 +359,11 @@ static int ipcp_udp_port_alloc_reply(uint16_t src_udp_port, return -1; } - pthread_rwlock_rdlock(&ipcpi.state_lock); pthread_rwlock_rdlock(&udp_data.flows_lock); set_fd(skfd); pthread_rwlock_unlock(&udp_data.flows_lock); - pthread_rwlock_unlock(&ipcpi.state_lock); if (ipcp_flow_alloc_reply(fd, response) < 0) return -1; @@ -410,7 +407,7 @@ static void * ipcp_udp_listener(void * o) case SHIM_UDP_MSG_CODE__FLOW_REQ: c_saddr.sin_port = msg->src_udp_port; ipcp_udp_port_req(&c_saddr, - msg->dst_name, + msg->hash.data, msg->qoscube); break; case SHIM_UDP_MSG_CODE__FLOW_REPLY: @@ -447,7 +444,6 @@ static void * ipcp_udp_sdu_reader(void * o) (void) o; while (true) { - pthread_rwlock_rdlock(&ipcpi.state_lock); pthread_rwlock_rdlock(&udp_data.flows_lock); pthread_mutex_lock(&udp_data.fd_set_lock); @@ -457,7 +453,6 @@ static void * ipcp_udp_sdu_reader(void * o) pthread_mutex_unlock(&udp_data.fd_set_lock); pthread_rwlock_unlock(&udp_data.flows_lock); - pthread_rwlock_unlock(&ipcpi.state_lock); if (select(FD_SETSIZE, &read_fds, NULL, NULL, &tv) <= 0) continue; @@ -476,13 +471,11 @@ static void * ipcp_udp_sdu_reader(void * o) (unsigned *) &n)) <= 0) continue; - pthread_rwlock_rdlock(&ipcpi.state_lock); pthread_rwlock_rdlock(&udp_data.flows_lock); fd = udp_data.uf_to_fd[skfd]; pthread_rwlock_unlock(&udp_data.flows_lock); - pthread_rwlock_unlock(&ipcpi.state_lock); flow_write(fd, buf, n); } @@ -506,12 +499,10 @@ static void * ipcp_udp_sdu_loop(void * o) continue; } - pthread_rwlock_rdlock(&ipcpi.state_lock); if (ipcp_get_state() != IPCP_OPERATIONAL) { - pthread_rwlock_unlock(&ipcpi.state_lock); ipcp_flow_del(sdb); - return (void *) -1; /* -ENOTENROLLED */ + return (void *) 0; /* -ENOTENROLLED */ } pthread_rwlock_rdlock(&udp_data.flows_lock); @@ -519,7 +510,6 @@ static void * ipcp_udp_sdu_loop(void * o) fd = udp_data.fd_to_uf[fd].skfd; pthread_rwlock_unlock(&udp_data.flows_lock); - pthread_rwlock_unlock(&ipcpi.state_lock); if (send(fd, shm_du_buff_head(sdb), shm_du_buff_tail(sdb) - shm_du_buff_head(sdb), @@ -533,33 +523,7 @@ static void * ipcp_udp_sdu_loop(void * o) return (void *) 1; } -void ipcp_sig_handler(int sig, - siginfo_t * info, - void * c) -{ - (void) c; - - switch(sig) { - case SIGINT: - case SIGTERM: - case SIGHUP: - if (info->si_pid == ipcpi.irmd_api) { - pthread_rwlock_wrlock(&ipcpi.state_lock); - - if (ipcp_get_state() == IPCP_INIT) - ipcp_set_state(IPCP_NULL); - - if (ipcp_get_state() == IPCP_OPERATIONAL) - ipcp_set_state(IPCP_SHUTDOWN); - - pthread_rwlock_unlock(&ipcpi.state_lock); - } - default: - return; - } -} - -static int ipcp_udp_bootstrap(struct dif_config * conf) +static int ipcp_udp_bootstrap(const struct ipcp_config * conf) { struct sockaddr_in s_saddr; char ipstr[INET_ADDRSTRLEN]; @@ -570,6 +534,8 @@ static int ipcp_udp_bootstrap(struct dif_config * conf) assert(conf); assert(conf->type == THIS_TYPE); + ipcpi.dir_hash_len = conf->dir_hash_len; + if (inet_ntop(AF_INET, &conf->ip_addr, ipstr, @@ -619,15 +585,6 @@ static int ipcp_udp_bootstrap(struct dif_config * conf) return -1; } - pthread_rwlock_wrlock(&ipcpi.state_lock); - - if (ipcp_get_state() != IPCP_INIT) { - pthread_rwlock_unlock(&ipcpi.state_lock); - log_err("IPCP in wrong state."); - close(fd); - return -1; - } - udp_data.s_fd = fd; udp_data.ip_addr = conf->ip_addr; udp_data.dns_addr = conf->dns_addr; @@ -650,8 +607,6 @@ static int ipcp_udp_bootstrap(struct dif_config * conf) ipcp_udp_sdu_loop, NULL); - pthread_rwlock_unlock(&ipcpi.state_lock); - log_dbg("Bootstrapped shim IPCP over UDP with api %d.", getpid()); log_dbg("Bound to IP address %s.", ipstr); log_dbg("DNS server address is %s.", dnsstr); @@ -784,7 +739,7 @@ static uint32_t ddns_resolve(char * name, } #endif -static int ipcp_udp_name_reg(char * name) +static int ipcp_udp_reg(const uint8_t * hash) { #ifdef CONFIG_OUROBOROS_ENABLE_DNS char ipstr[INET_ADDRSTRLEN]; @@ -794,25 +749,23 @@ static int ipcp_udp_name_reg(char * name) uint32_t dns_addr; uint32_t ip_addr; #endif - char * name_dup; + char hashstr[DIR_HASH_STRLEN + 1]; + uint8_t * hash_dup; - if (strlen(name) > 24) { - log_err("DNS names cannot be longer than 24 chars."); - return -1; - } + assert(hash); - name_dup = strdup(name); - if (name_dup == NULL) { - log_err("Failed to duplicate name."); + ipcp_hash_str(hashstr, hash); + + hash_dup = ipcp_hash_dup(hash); + if (hash_dup == NULL) { + log_err("Failed to duplicate hash."); return -ENOMEM; } - pthread_rwlock_rdlock(&ipcpi.state_lock); - - if (shim_data_reg_add_entry(ipcpi.shim_data, name_dup)) { - pthread_rwlock_unlock(&ipcpi.state_lock); - log_err("Failed to add %s to local registry.", name); - free(name_dup); + if (shim_data_reg_add_entry(ipcpi.shim_data, hash_dup)) { + log_err("Failed to add " HASH_FMT " to local registry.", + HASH_VAL(hash)); + free(hash_dup); return -1; } @@ -821,8 +774,6 @@ static int ipcp_udp_name_reg(char * name) dns_addr = udp_data.dns_addr; - pthread_rwlock_unlock(&ipcpi.state_lock); - if (dns_addr != 0) { ip_addr = udp_data.ip_addr; @@ -837,24 +788,20 @@ static int ipcp_udp_name_reg(char * name) } sprintf(cmd, "server %s\nupdate add %s %d A %s\nsend\nquit\n", - dnsstr, name, DNS_TTL, ipstr); + dnsstr, hashstr, DNS_TTL, ipstr); if (ddns_send(cmd)) { - pthread_rwlock_rdlock(&ipcpi.state_lock); - shim_data_reg_del_entry(ipcpi.shim_data, name); - pthread_rwlock_unlock(&ipcpi.state_lock); + shim_data_reg_del_entry(ipcpi.shim_data, hash_dup); return -1; } } -#else - pthread_rwlock_unlock(&ipcpi.state_lock); #endif - log_dbg("Registered %s.", name); + log_dbg("Registered " HASH_FMT ".", HASH_VAL(hash)); return 0; } -static int ipcp_udp_name_unreg(char * name) +static int ipcp_udp_unreg(const uint8_t * hash) { #ifdef CONFIG_OUROBOROS_ENABLE_DNS char dnsstr[INET_ADDRSTRLEN]; @@ -862,94 +809,66 @@ static int ipcp_udp_name_unreg(char * name) char cmd[100]; uint32_t dns_addr; #endif - if (strlen(name) > 24) { - log_err("DNS names cannot be longer than 24 chars."); - return -1; - } + char hashstr[DIR_HASH_STRLEN + 1]; + + assert(hash); + + ipcp_hash_str(hashstr, hash); #ifdef CONFIG_OUROBOROS_ENABLE_DNS /* unregister application with DNS server */ - pthread_rwlock_rdlock(&ipcpi.state_lock); - dns_addr = udp_data.dns_addr; - pthread_rwlock_unlock(&ipcpi.state_lock); - if (dns_addr != 0) { if (inet_ntop(AF_INET, &dns_addr, dnsstr, INET_ADDRSTRLEN) == NULL) { return -1; } sprintf(cmd, "server %s\nupdate delete %s A\nsend\nquit\n", - dnsstr, name); + dnsstr, hashstr); ddns_send(cmd); } #endif - pthread_rwlock_rdlock(&ipcpi.state_lock); - - shim_data_reg_del_entry(ipcpi.shim_data, name); + shim_data_reg_del_entry(ipcpi.shim_data, hash); - pthread_rwlock_unlock(&ipcpi.state_lock); + log_dbg("Unregistered " HASH_FMT ".", HASH_VAL(hash)); return 0; } -static int ipcp_udp_name_query(char * name) +static int ipcp_udp_query(const uint8_t * hash) { uint32_t ip_addr = 0; struct hostent * h; #ifdef CONFIG_OUROBOROS_ENABLE_DNS uint32_t dns_addr = 0; #endif + char hashstr[DIR_HASH_STRLEN + 1]; - assert(name); - - if (strlen(name) > 24) { - log_err("DNS names cannot be longer than 24 chars."); - return -1; - } - - pthread_rwlock_rdlock(&ipcpi.state_lock); + assert(hash); - if (ipcp_get_state() != IPCP_OPERATIONAL) { - pthread_rwlock_unlock(&ipcpi.state_lock); - log_dbg("Won't query a name on a non-enrolled IPCP."); - return -1; /* -ENOTENROLLED */ - } + ipcp_hash_str(hashstr, hash); - if (shim_data_dir_has(ipcpi.shim_data, name)) { - pthread_rwlock_unlock(&ipcpi.state_lock); + if (shim_data_dir_has(ipcpi.shim_data, hash)) return 0; - } #ifdef CONFIG_OUROBOROS_ENABLE_DNS dns_addr = udp_data.dns_addr; if (dns_addr != 0) { - pthread_rwlock_unlock(&ipcpi.state_lock); - - ip_addr = ddns_resolve(name, dns_addr); + ip_addr = ddns_resolve(hashstr, dns_addr); if (ip_addr == 0) { - log_dbg("Could not resolve %s.", name); + log_dbg("Could not resolve %s.", hashstr); return -1; } - - pthread_rwlock_rdlock(&ipcpi.state_lock); - - if (ipcp_get_state() != IPCP_OPERATIONAL) { - pthread_rwlock_unlock(&ipcpi.state_lock); - log_dbg("Won't add name to the directory."); - return -1; /* -ENOTENROLLED */ - } } else { #endif - h = gethostbyname(name); + h = gethostbyname(hashstr); if (h == NULL) { - pthread_rwlock_unlock(&ipcpi.state_lock); - log_dbg("Could not resolve %s.", name); + log_dbg("Could not resolve %s.", hashstr); return -1; } @@ -958,20 +877,17 @@ static int ipcp_udp_name_query(char * name) } #endif - if (shim_data_dir_add_entry(ipcpi.shim_data, name, ip_addr)) { - pthread_rwlock_unlock(&ipcpi.state_lock); + if (shim_data_dir_add_entry(ipcpi.shim_data, hash, ip_addr)) { log_err("Failed to add directory entry."); return -1; } - pthread_rwlock_unlock(&ipcpi.state_lock); - return 0; } -static int ipcp_udp_flow_alloc(int fd, - char * dst_name, - qoscube_t cube) +static int ipcp_udp_flow_alloc(int fd, + const uint8_t * dst, + qoscube_t cube) { struct sockaddr_in r_saddr; /* server address */ struct sockaddr_in f_saddr; /* flow */ @@ -979,14 +895,9 @@ static int ipcp_udp_flow_alloc(int fd, int skfd; uint32_t ip_addr = 0; - log_dbg("Allocating flow to %s.", dst_name); + log_dbg("Allocating flow to " HASH_FMT ".", HASH_VAL(dst)); - assert(dst_name); - - if (strlen(dst_name) > 255) { - log_err("Name too long for this shim."); - return -1; - } + assert(dst); if (cube != QOS_CUBE_BE && cube != QOS_CUBE_FRC) { log_dbg("Unsupported QoS requested."); @@ -1012,22 +923,13 @@ static int ipcp_udp_flow_alloc(int fd, return -1; } - pthread_rwlock_rdlock(&ipcpi.state_lock); - if (ipcp_get_state() != IPCP_OPERATIONAL) { - pthread_rwlock_unlock(&ipcpi.state_lock); - log_dbg("Won't allocate flow with non-enrolled IPCP."); - close(skfd); - return -1; /* -ENOTENROLLED */ - } - - if (!shim_data_dir_has(ipcpi.shim_data, dst_name)) { - pthread_rwlock_unlock(&ipcpi.state_lock); + if (!shim_data_dir_has(ipcpi.shim_data, dst)) { log_dbg("Could not resolve destination."); close(skfd); return -1; } - ip_addr = (uint32_t) shim_data_dir_get_addr(ipcpi.shim_data, dst_name); + ip_addr = (uint32_t) shim_data_dir_get_addr(ipcpi.shim_data, dst); /* connect to server (store the remote IP address in the fd) */ memset((char *) &r_saddr, 0, sizeof(r_saddr)); @@ -1049,13 +951,11 @@ static int ipcp_udp_flow_alloc(int fd, flow_set_add(udp_data.np1_flows, fd); pthread_rwlock_unlock(&udp_data.flows_lock); - pthread_rwlock_unlock(&ipcpi.state_lock); if (ipcp_udp_port_alloc(ip_addr, f_saddr.sin_port, - dst_name, + dst, cube) < 0) { - pthread_rwlock_rdlock(&ipcpi.state_lock); pthread_rwlock_wrlock(&udp_data.flows_lock); udp_data.fd_to_uf[fd].udp = -1; @@ -1063,7 +963,6 @@ static int ipcp_udp_flow_alloc(int fd, udp_data.uf_to_fd[skfd] = -1; pthread_rwlock_unlock(&udp_data.flows_lock); - pthread_rwlock_unlock(&ipcpi.state_lock); close(skfd); return -1; } @@ -1103,11 +1002,12 @@ static int ipcp_udp_flow_alloc_resp(int fd, pthread_mutex_unlock(&ipcpi.alloc_lock); - pthread_rwlock_rdlock(&ipcpi.state_lock); - pthread_rwlock_wrlock(&udp_data.flows_lock); + pthread_rwlock_rdlock(&udp_data.flows_lock); skfd = udp_data.fd_to_uf[fd].skfd; + pthread_rwlock_unlock(&udp_data.flows_lock); + if (getsockname(skfd, (struct sockaddr *) &f_saddr, &len) < 0) { log_dbg("Socket with fd %d has no address.", skfd); return -1; @@ -1118,7 +1018,6 @@ static int ipcp_udp_flow_alloc_resp(int fd, return -1; } - pthread_rwlock_unlock(&udp_data.flows_lock); pthread_rwlock_rdlock(&udp_data.flows_lock); set_fd(skfd); @@ -1126,18 +1025,12 @@ static int ipcp_udp_flow_alloc_resp(int fd, flow_set_add(udp_data.np1_flows, fd); pthread_rwlock_unlock(&udp_data.flows_lock); - pthread_rwlock_unlock(&ipcpi.state_lock); - if (ipcp_udp_port_alloc_resp(r_saddr.sin_addr.s_addr, - f_saddr.sin_port, - r_saddr.sin_port, - response) < 0) { - pthread_rwlock_rdlock(&ipcpi.state_lock); + if (ipcp_udp_port_alloc_resp(r_saddr.sin_addr.s_addr, f_saddr.sin_port, + r_saddr.sin_port, response) < 0) { pthread_rwlock_rdlock(&udp_data.flows_lock); clr_fd(skfd); pthread_rwlock_unlock(&udp_data.flows_lock); - pthread_rwlock_unlock(&ipcpi.state_lock); - return -1; } @@ -1153,14 +1046,6 @@ static int ipcp_udp_flow_dealloc(int fd) ipcp_flow_fini(fd); - pthread_rwlock_rdlock(&ipcpi.state_lock); - - if (ipcp_get_state() != IPCP_OPERATIONAL) { - pthread_rwlock_unlock(&ipcpi.state_lock); - log_dbg("Won't register with non-enrolled IPCP."); - return -1; /* -ENOTENROLLED */ - } - pthread_rwlock_wrlock(&udp_data.flows_lock); flow_set_del(udp_data.np1_flows, fd); @@ -1179,7 +1064,6 @@ static int ipcp_udp_flow_dealloc(int fd) clr_fd(skfd); pthread_rwlock_unlock(&udp_data.flows_lock); - pthread_rwlock_unlock(&ipcpi.state_lock); flow_dealloc(fd); @@ -1191,9 +1075,9 @@ static int ipcp_udp_flow_dealloc(int fd) static struct ipcp_ops udp_ops = { .ipcp_bootstrap = ipcp_udp_bootstrap, .ipcp_enroll = NULL, /* shim */ - .ipcp_name_reg = ipcp_udp_name_reg, - .ipcp_name_unreg = ipcp_udp_name_unreg, - .ipcp_name_query = ipcp_udp_name_query, + .ipcp_reg = ipcp_udp_reg, + .ipcp_unreg = ipcp_udp_unreg, + .ipcp_query = ipcp_udp_query, .ipcp_flow_alloc = ipcp_udp_flow_alloc, .ipcp_flow_alloc_resp = ipcp_udp_flow_alloc_resp, .ipcp_flow_dealloc = ipcp_udp_flow_dealloc @@ -1202,26 +1086,6 @@ static struct ipcp_ops udp_ops = { int main(int argc, char * argv[]) { - struct sigaction sig_act; - sigset_t sigset; - sigemptyset(&sigset); - sigaddset(&sigset, SIGINT); - sigaddset(&sigset, SIGQUIT); - sigaddset(&sigset, SIGHUP); - sigaddset(&sigset, SIGPIPE); - - /* init sig_act */ - memset(&sig_act, 0, sizeof(sig_act)); - - /* install signal traps */ - sig_act.sa_sigaction = &ipcp_sig_handler; - sig_act.sa_flags = SA_SIGINFO; - - sigaction(SIGINT, &sig_act, NULL); - sigaction(SIGTERM, &sig_act, NULL); - sigaction(SIGHUP, &sig_act, NULL); - sigaction(SIGPIPE, &sig_act, NULL); - if (ipcp_init(argc, argv, THIS_TYPE, &udp_ops) < 0) { ipcp_create_r(getpid(), -1); exit(EXIT_FAILURE); @@ -1234,9 +1098,6 @@ int main(int argc, exit(EXIT_FAILURE); } - - pthread_sigmask(SIG_BLOCK, &sigset, NULL); - if (ipcp_boot() < 0) { log_err("Failed to boot IPCP."); ipcp_create_r(getpid(), -1); @@ -1245,8 +1106,6 @@ int main(int argc, exit(EXIT_FAILURE); } - pthread_sigmask(SIG_UNBLOCK, &sigset, NULL); - if (ipcp_create_r(getpid(), 0)) { log_err("Failed to notify IRMd we are initialized."); ipcp_set_state(IPCP_NULL); diff --git a/src/ipcpd/shim-udp/shim_udp_messages.proto b/src/ipcpd/shim-udp/shim_udp_messages.proto index 75f0cb64..ae89a119 100644 --- a/src/ipcpd/shim-udp/shim_udp_messages.proto +++ b/src/ipcpd/shim-udp/shim_udp_messages.proto @@ -29,10 +29,9 @@ enum shim_udp_msg_code { message shim_udp_msg { required shim_udp_msg_code code = 1; - optional string dst_name = 2; - optional string src_ae_name = 4; - required uint32 src_udp_port = 5; - optional uint32 dst_udp_port = 6; - optional uint32 qoscube = 7; - optional sint32 response = 8; + optional bytes hash = 2; + required uint32 src_udp_port = 3; + optional uint32 dst_udp_port = 4; + optional uint32 qoscube = 5; + optional sint32 response = 6; }; diff --git a/src/ipcpd/shim-udp/tests/shim_udp_test.c b/src/ipcpd/shim-udp/tests/shim_udp_test.c index d7bd0bb7..015bb49f 100644 --- a/src/ipcpd/shim-udp/tests/shim_udp_test.c +++ b/src/ipcpd/shim-udp/tests/shim_udp_test.c @@ -21,7 +21,7 @@ */ #include <ouroboros/config.h> -#include <ouroboros/dif_config.h> +#include <ouroboros/ipcp.h> #include <ouroboros/utils.h> #include <ouroboros/shm_du_map.h> #include <sys/types.h> @@ -41,7 +41,7 @@ int shim_udp_test(int argc, char ** argv) char bogus[16]; memset(&bogus, 0, 16); - struct dif_config conf; + struct ipcp_config conf; memset(&conf, 0, sizeof conf); conf.dif_name = strdup("test-dif"); conf.type = IPCP_SHIM_UDP; |