From d947aad0aede71936c592d65afcaedcaec0f0beb Mon Sep 17 00:00:00 2001 From: dimitri staessens Date: Sat, 29 Apr 2017 12:10:25 +0200 Subject: ipcpd: Fix sending fa dealloc message The frct instance was previously destroyed before sending the message, resulting in the destination address being 0 and the message getting dropped. Some fixes in the normal for deallocation, but will require further revision once all data transfer protocols are in place. --- src/ipcpd/normal/dt.c | 2 +- src/ipcpd/normal/fa.c | 47 ++++++++++++++++++++++++++++++----------------- 2 files changed, 31 insertions(+), 18 deletions(-) diff --git a/src/ipcpd/normal/dt.c b/src/ipcpd/normal/dt.c index 0816ec10..4e0ba51d 100644 --- a/src/ipcpd/normal/dt.c +++ b/src/ipcpd/normal/dt.c @@ -275,7 +275,7 @@ int dt_write_sdu(uint64_t dst_addr, fd = pff_nhop(dt.pff[qc], dst_addr); if (fd < 0) { - log_err("Could not get nhop for address %" PRIu64, dst_addr); + log_err("Could not get nhop for addr %" PRIu64 ".", dst_addr); return -1; } diff --git a/src/ipcpd/normal/fa.c b/src/ipcpd/normal/fa.c index b116c842..6ea5b711 100644 --- a/src/ipcpd/normal/fa.c +++ b/src/ipcpd/normal/fa.c @@ -128,6 +128,7 @@ static struct shm_du_buff * create_fa_sdb(flow_alloc_msg_t * msg) return sdb; } +/* FIXME: Revise when Delta-t is fully implemented */ static void destroy_conn(int fd, cep_id_t cep_id) { @@ -181,7 +182,7 @@ int fa_alloc(int fd, free(dst_ipcp); - if (rib_read(path, &addr, sizeof(addr)) < 0) + if (rib_read(path, &addr, sizeof(addr)) != sizeof(addr)) return -1; cep_id = frct_i_create(addr, qc); @@ -280,6 +281,7 @@ int fa_alloc_resp(int fd, PDU_TYPE_FA, sdb)) { destroy_conn(fd, fa.fd_to_cep_id[fd]); + pthread_rwlock_unlock(&fa.flows_lock); ipcp_sdb_release(sdb); return -1; } @@ -294,37 +296,44 @@ int fa_dealloc(int fd) flow_alloc_msg_t msg = FLOW_ALLOC_MSG__INIT; struct shm_du_buff * sdb; qoscube_t qc; - - pthread_rwlock_wrlock(&fa.flows_lock); - - sdu_sched_del(fa.sdu_sched, fd); - - destroy_conn(fd, fa.fd_to_cep_id[fd]); + uint64_t addr; msg.code = FLOW_ALLOC_CODE__FLOW_DEALLOC; msg.has_cep_id = true; + + pthread_rwlock_rdlock(&fa.flows_lock); + msg.cep_id = frct_i_get_id(fa.fd_to_cep_id[fd]); - sdb = create_fa_sdb(&msg); - if (sdb == NULL) { - pthread_rwlock_unlock(&fa.flows_lock); - return -1; - } + addr = frct_i_get_addr(fa.fd_to_cep_id[fd]); pthread_rwlock_unlock(&fa.flows_lock); + sdb = create_fa_sdb(&msg); + if (sdb == NULL) + return -1; + ipcp_flow_get_qoscube(fd, &qc); assert(qc >= 0 && qc < QOS_CUBE_MAX); - if (dt_write_sdu(frct_i_get_addr(fa.fd_to_cep_id[fd]), - qc, - PDU_TYPE_FA, - sdb)) { + if (dt_write_sdu(addr, qc, PDU_TYPE_FA, sdb)) { ipcp_sdb_release(sdb); - return -1; + log_warn("Failed to send dealloc message."); } + ipcp_flow_fini(fd); + + pthread_rwlock_wrlock(&fa.flows_lock); + + sdu_sched_del(fa.sdu_sched, fd); + + destroy_conn(fd, fa.fd_to_cep_id[fd]); + + pthread_rwlock_unlock(&fa.flows_lock); + + flow_dealloc(fd); + return 0; } @@ -430,7 +439,11 @@ int fa_post_sdu(struct shm_du_buff * sdb) break; case FLOW_ALLOC_CODE__FLOW_DEALLOC: + /* FIXME: mark flow and wait for frct_i to time out */ + pthread_rwlock_rdlock(&fa.flows_lock); fd = fa.cep_id_to_fd[msg->cep_id]; + pthread_rwlock_unlock(&fa.flows_lock); + ipcp_flow_fini(fd); sdu_sched_del(fa.sdu_sched, fd); flow_dealloc(fd); break; -- cgit v1.2.3