Module: xenomai-forge
Branch: master
Commit: ab57b318966052b7997543a1c0cd71ea9e755ec2
URL:    
http://git.xenomai.org/?p=xenomai-forge.git;a=commit;h=ab57b318966052b7997543a1c0cd71ea9e755ec2

Author: Philippe Gerum <r...@xenomai.org>
Date:   Tue Nov 29 13:08:50 2011 +0100

psos/task: fix cancel state in ev_receive/send()

Nesting the task and sync object locks in these routines is a bad idea
because:

- it is useless, since holding the sync object prevents from async
  cancellation.

- calling threadobj_unlock() while syncobj_lock() is in effect wrecks
  the cancellation state for the current task (i.e. restoring the
  wrong one).

---

 lib/psos/task.c |   22 +++++++++-------------
 1 files changed, 9 insertions(+), 13 deletions(-)

diff --git a/lib/psos/task.c b/lib/psos/task.c
index 2c54faa..b91f618 100644
--- a/lib/psos/task.c
+++ b/lib/psos/task.c
@@ -586,21 +586,18 @@ u_long ev_receive(u_long events, u_long flags,
        struct service svc;
        int ret;
 
-       current = get_psos_task_or_self(0, &ret);
+       current = find_psos_task_or_self(0, &ret);
        if (current == NULL)
                return ret;
 
-       ret = syncobj_lock(&current->sobj, &syns);
-       /*
-        * We can't be cancelled asynchronously while we hold a
-        * syncobj lock, so we may safely drop our thread lock now.
-        */
-       put_psos_task(current);
-       if (ret)
-               return ERR_OBJDEL;
-
        COPPERPLATE_PROTECT(svc);
 
+       ret = syncobj_lock(&current->sobj, &syns);
+       if (ret) {
+               ret = ERR_OBJDEL;
+               goto out;
+       }
+
        if (events == 0) {
                *events_r = current->events; /* Only polling events. */
                goto done;
@@ -631,7 +628,7 @@ u_long ev_receive(u_long events, u_long flags,
        }
 done:
        syncobj_unlock(&current->sobj, &syns);
-
+out:
        COPPERPLATE_UNPROTECT(svc);
 
        return ret;
@@ -644,14 +641,13 @@ u_long ev_send(u_long tid, u_long events)
        struct service svc;
        int ret = SUCCESS;
 
-       task = get_psos_task(tid, &ret);
+       task = find_psos_task(tid, &ret);
        if (task == NULL)
                return ret;
 
        COPPERPLATE_PROTECT(svc);
 
        ret = syncobj_lock(&task->sobj, &syns);
-       put_psos_task(task);
        if (ret) {
                ret = ERR_OBJDEL;
                goto out;


_______________________________________________
Xenomai-git mailing list
Xenomai-git@gna.org
https://mail.gna.org/listinfo/xenomai-git

Reply via email to