Module: xenomai-forge Branch: master Commit: d4db547e281e3d1efba32311ad3d5efd8d4dc16e URL: http://git.xenomai.org/?p=xenomai-forge.git;a=commit;h=d4db547e281e3d1efba32311ad3d5efd8d4dc16e
Author: Philippe Gerum <r...@xenomai.org> Date: Tue Jan 28 10:12:42 2014 +0100 copperplate/threadobj: dismantle the TCB gradually on failure We may have to drop the TCB resources for threads which failed to start internally. To this end, we need to split the uninit/cleanup handlers, the same way we have the converse init/setup handlers. At this chance, threadobj_destroy() is renamed threadobj_uninit(), in order to match the common naming scheme (e.g. syncobj_destroy() vs synchobj_uninit()). This fixes issue: http://www.xenomai.org/pipermail/xenomai/2014-January/029966.html --- include/copperplate/threadobj.h | 2 +- lib/alchemy/task.c | 2 +- lib/copperplate/threadobj.c | 24 +++++++++++++++++++----- lib/psos/task.c | 6 ++---- lib/vxworks/taskLib.c | 5 ++--- 5 files changed, 25 insertions(+), 14 deletions(-) diff --git a/include/copperplate/threadobj.h b/include/copperplate/threadobj.h index 218c274..3529ca1 100644 --- a/include/copperplate/threadobj.h +++ b/include/copperplate/threadobj.h @@ -295,7 +295,7 @@ void threadobj_notify_entry(void); int threadobj_cancel(struct threadobj *thobj); -void threadobj_destroy(struct threadobj *thobj); +void threadobj_uninit(struct threadobj *thobj); int threadobj_suspend(struct threadobj *thobj); diff --git a/lib/alchemy/task.c b/lib/alchemy/task.c index f3a40b3..fbb8cb7 100644 --- a/lib/alchemy/task.c +++ b/lib/alchemy/task.c @@ -189,7 +189,7 @@ out: static void delete_tcb(struct alchemy_task *tcb) { syncobj_uninit(&tcb->sobj_msg); - threadobj_destroy(&tcb->thobj); + threadobj_uninit(&tcb->thobj); threadobj_free(&tcb->thobj); } diff --git a/lib/copperplate/threadobj.c b/lib/copperplate/threadobj.c index c54cdf8..e6e599e 100644 --- a/lib/copperplate/threadobj.c +++ b/lib/copperplate/threadobj.c @@ -95,6 +95,10 @@ static inline void threadobj_init_corespec(struct threadobj *thobj) { } +static inline void threadobj_uninit_corespec(struct threadobj *thobj) +{ +} + static inline int threadobj_setup_corespec(struct threadobj *thobj) { pthread_set_name_np(pthread_self(), thobj->name); @@ -445,6 +449,11 @@ static inline void threadobj_init_corespec(struct threadobj *thobj) thobj->core.rr_timer = NULL; } +static inline void threadobj_uninit_corespec(struct threadobj *thobj) +{ + pthread_cond_destroy(&thobj->core.grant_sync); +} + static inline int threadobj_setup_corespec(struct threadobj *thobj) { struct sigevent sev; @@ -481,7 +490,6 @@ static inline int threadobj_setup_corespec(struct threadobj *thobj) static inline void threadobj_cleanup_corespec(struct threadobj *thobj) { notifier_destroy(&thobj->core.notifier); - pthread_cond_destroy(&thobj->core.grant_sync); if (thobj->core.rr_timer) timer_delete(thobj->core.rr_timer); } @@ -872,17 +880,23 @@ void threadobj_init(struct threadobj *thobj, threadobj_init_corespec(thobj); } -static void destroy_thread(struct threadobj *thobj) +static void uninit_thread(struct threadobj *thobj) { - threadobj_cleanup_corespec(thobj); + threadobj_uninit_corespec(thobj); __RT(pthread_cond_destroy(&thobj->barrier)); __RT(pthread_mutex_destroy(&thobj->lock)); } -void threadobj_destroy(struct threadobj *thobj) /* thobj->lock free */ +static void destroy_thread(struct threadobj *thobj) +{ + threadobj_cleanup_corespec(thobj); + uninit_thread(thobj); +} + +void threadobj_uninit(struct threadobj *thobj) /* thobj->lock free */ { assert((thobj->status & (__THREAD_S_STARTED|__THREAD_S_ACTIVE)) == 0); - destroy_thread(thobj); + uninit_thread(thobj); } /* diff --git a/lib/psos/task.c b/lib/psos/task.c index 9112517..393dfaf 100644 --- a/lib/psos/task.c +++ b/lib/psos/task.c @@ -271,7 +271,6 @@ u_long t_create(const char *name, u_long prio, struct corethread_attributes cta; struct threadobj_init_data idata; struct psos_task *task; - struct syncstate syns; struct service svc; int ret, cprio = 1; char short_name[5]; @@ -339,11 +338,10 @@ u_long t_create(const char *name, u_long prio, ret = __bt(copperplate_create_thread(&cta, &task->thobj.tid)); if (ret) { cluster_delobj(&psos_task_table, &task->cobj); - threadobj_destroy(&task->thobj); + threadobj_uninit(&task->thobj); ret = ERR_NOTCB; fail: - syncobj_lock(&task->sobj, &syns); - syncobj_destroy(&task->sobj, &syns); + syncobj_uninit(&task->sobj); threadobj_free(&task->thobj); } out: diff --git a/lib/vxworks/taskLib.c b/lib/vxworks/taskLib.c index f590fd4..1ef52a5 100644 --- a/lib/vxworks/taskLib.c +++ b/lib/vxworks/taskLib.c @@ -360,7 +360,7 @@ static STATUS __taskInit(struct wind_task *task, ret = __bt(cluster_addobj(&wind_task_table, task->name, &task->cobj)); if (ret) { warning("duplicate task name: %s", task->name); - threadobj_destroy(&task->thobj); + threadobj_uninit(&task->thobj); __RT(pthread_mutex_destroy(&task->safelock)); errno = S_objLib_OBJ_ID_ERROR; return ERROR; @@ -374,11 +374,10 @@ static STATUS __taskInit(struct wind_task *task, cta.stacksize = stacksize; cta.detachstate = PTHREAD_CREATE_DETACHED; ret = __bt(copperplate_create_thread(&cta, &task->thobj.tid)); - if (ret) { registry_destroy_file(&task->fsobj); cluster_delobj(&wind_task_table, &task->cobj); - threadobj_destroy(&task->thobj); + threadobj_uninit(&task->thobj); __RT(pthread_mutex_destroy(&task->safelock)); errno = ret == -EAGAIN ? S_memLib_NOT_ENOUGH_MEMORY : -ret; return ERROR; _______________________________________________ Xenomai-git mailing list Xenomai-git@xenomai.org http://www.xenomai.org/mailman/listinfo/xenomai-git