summaryrefslogtreecommitdiff
path: root/src/irmd/main.c
diff options
context:
space:
mode:
authordimitri staessens <dimitri.staessens@intec.ugent.be>2016-08-04 15:25:42 +0200
committerdimitri staessens <dimitri.staessens@intec.ugent.be>2016-08-04 17:19:01 +0200
commit2567329483ab1fe5384782da50e06aa0bbdd3cfe (patch)
tree7dba3fd7e728642d2146b860a56a9fda4d9c2db2 /src/irmd/main.c
parent139001b60b32e756e947d6e3a55767be9063029d (diff)
downloadouroboros-2567329483ab1fe5384782da50e06aa0bbdd3cfe.tar.gz
ouroboros-2567329483ab1fe5384782da50e06aa0bbdd3cfe.zip
irmd: Fix destroying allocated flows
When a flow was in FLOW_ALLOCATED state, it would not change to NULL state and irm_flow_destroy would hang forever.
Diffstat (limited to 'src/irmd/main.c')
-rw-r--r--src/irmd/main.c23
1 files changed, 16 insertions, 7 deletions
diff --git a/src/irmd/main.c b/src/irmd/main.c
index b3228789..8c19990a 100644
--- a/src/irmd/main.c
+++ b/src/irmd/main.c
@@ -151,11 +151,13 @@ static void irm_flow_destroy(struct irm_flow * e)
if (e->state == FLOW_PENDING)
e->state = FLOW_DESTROY;
+ else
+ e->state = FLOW_NULL;
pthread_cond_signal(&e->state_cond);
pthread_mutex_unlock(&e->state_lock);
- pthread_cleanup_push((void(*)(void *)) pthread_mutex_unlock,
+ pthread_cleanup_push((void (*)(void *)) pthread_mutex_unlock,
(void *) &e->state_lock);
while (e->state != FLOW_NULL)
@@ -942,6 +944,14 @@ static struct irm_flow * flow_alloc(pid_t api,
return pme;
}
+static void cleanup_alloc_res(void * o)
+{
+ struct irm_flow * e = (struct irm_flow *) o;
+ if (e->state == FLOW_PENDING)
+ e->state = FLOW_NULL;
+ pthread_mutex_unlock(&e->state_lock);
+}
+
static int flow_alloc_res(int port_id)
{
struct irm_flow * e;
@@ -979,8 +989,7 @@ static int flow_alloc_res(int port_id)
pthread_rwlock_unlock(&irmd->state_lock);
pthread_mutex_lock(&e->state_lock);
- pthread_cleanup_push((void(*)(void *))pthread_mutex_unlock,
- (void*) &e->state_lock);
+ pthread_cleanup_push(cleanup_alloc_res, (void *) e);
while (e->state == FLOW_PENDING)
pthread_cond_wait(&e->state_cond, &e->state_lock);
@@ -1035,7 +1044,7 @@ static int flow_dealloc(int port_id)
pthread_rwlock_unlock(&irmd->state_lock);
- free(e);
+ irm_flow_destroy(e);
return ret;
}
@@ -1147,7 +1156,7 @@ static struct irm_flow * flow_req_arr(pid_t api,
pthread_rwlock_unlock(&irmd->reg_lock);
pthread_mutex_lock(&rne->state_lock);
- pthread_cleanup_push((void(*)(void *)) pthread_mutex_unlock,
+ pthread_cleanup_push((void (*)(void *)) pthread_mutex_unlock,
(void *) &rne->state_lock);
while (rne->state == REG_NAME_AUTO_EXEC)
@@ -1203,7 +1212,7 @@ static struct irm_flow * flow_req_arr(pid_t api,
pthread_rwlock_unlock(&irmd->state_lock);
- pthread_cleanup_push((void(*)(void *)) pthread_mutex_unlock,
+ pthread_cleanup_push((void (*)(void *)) pthread_mutex_unlock,
(void *) &rne->state_lock);
while (rne->state == REG_NAME_FLOW_ARRIVED &&
@@ -1268,7 +1277,7 @@ static int flow_dealloc_ipcp(int port_id)
pthread_rwlock_unlock(&irmd->flows_lock);
pthread_rwlock_unlock(&irmd->state_lock);
- free(e);
+ irm_flow_destroy(e);
return 0;
}