diff options
author | Gregory Nutt <gnutt@nuttx.org> | 2015-02-25 07:45:04 -0600 |
---|---|---|
committer | Gregory Nutt <gnutt@nuttx.org> | 2015-02-25 07:45:04 -0600 |
commit | f9aaaea355c5686a6e627b886b7a56c4fa31ce1d (patch) | |
tree | 9e36cdeec8de7ac44f67190c62fc5f8d3a8a1845 | |
parent | d007ca9840471211479065f4b265f604ee5f6238 (diff) | |
download | px4-nuttx-f9aaaea355c5686a6e627b886b7a56c4fa31ce1d.tar.gz px4-nuttx-f9aaaea355c5686a6e627b886b7a56c4fa31ce1d.tar.bz2 px4-nuttx-f9aaaea355c5686a6e627b886b7a56c4fa31ce1d.zip |
Fix places where the errno value was being overwritten by subsequent actions so that the returned errno value was incorrect. From Max Neklyudov.
-rw-r--r-- | nuttx/fs/vfs/fs_select.c | 17 | ||||
-rw-r--r-- | nuttx/sched/semaphore/sem_timedwait.c | 33 |
2 files changed, 40 insertions, 10 deletions
diff --git a/nuttx/fs/vfs/fs_select.c b/nuttx/fs/vfs/fs_select.c index 6edf2b7c3..47fa65004 100644 --- a/nuttx/fs/vfs/fs_select.c +++ b/nuttx/fs/vfs/fs_select.c @@ -103,6 +103,7 @@ int select(int nfds, FAR fd_set *readfds, FAR fd_set *writefds, FAR fd_set *exceptfds, FAR struct timeval *timeout) { struct pollfd *pollset; + int errcode; int fd; int npfds; int msec; @@ -198,6 +199,12 @@ int select(int nfds, FAR fd_set *readfds, FAR fd_set *writefds, /* Then let poll do all of the real work. */ ret = poll(pollset, npfds, msec); + if (ret < 0) + { + /* poll() failed! Save the errno value */ + + errcode = get_errno(); + } /* Now set up the return values */ @@ -263,6 +270,16 @@ int select(int nfds, FAR fd_set *readfds, FAR fd_set *writefds, } kmm_free(pollset); + + /* Did poll() fail above? */ + + if (ret < 0) + { + /* Yes.. restore the errno value */ + + set_errno(errcode); + } + return ret; } diff --git a/nuttx/sched/semaphore/sem_timedwait.c b/nuttx/sched/semaphore/sem_timedwait.c index b7d850728..4d5e58342 100644 --- a/nuttx/sched/semaphore/sem_timedwait.c +++ b/nuttx/sched/semaphore/sem_timedwait.c @@ -167,7 +167,7 @@ int sem_timedwait(FAR sem_t *sem, FAR const struct timespec *abstime) FAR struct tcb_s *rtcb = (FAR struct tcb_s *)g_readytorun.head; irqstate_t flags; int ticks; - int err; + int errcode; int ret = ERROR; DEBUGASSERT(up_interrupt_context() == false && rtcb->waitdog == NULL); @@ -179,7 +179,7 @@ int sem_timedwait(FAR sem_t *sem, FAR const struct timespec *abstime) #ifdef CONFIG_DEBUG if (!abstime || !sem) { - err = EINVAL; + errcode = EINVAL; goto errout; } #endif @@ -192,7 +192,7 @@ int sem_timedwait(FAR sem_t *sem, FAR const struct timespec *abstime) rtcb->waitdog = wd_create(); if (!rtcb->waitdog) { - err = ENOMEM; + errcode = ENOMEM; goto errout; } @@ -225,7 +225,7 @@ int sem_timedwait(FAR sem_t *sem, FAR const struct timespec *abstime) if (abstime->tv_nsec < 0 || abstime->tv_nsec >= 1000000000) { - err = EINVAL; + errcode = EINVAL; goto errout_disabled; } @@ -233,31 +233,37 @@ int sem_timedwait(FAR sem_t *sem, FAR const struct timespec *abstime) * disabled here so that this time stays valid until the wait begins. */ - err = clock_abstime2ticks(CLOCK_REALTIME, abstime, &ticks); + errcode = clock_abstime2ticks(CLOCK_REALTIME, abstime, &ticks); /* If the time has already expired return immediately. */ - if (err == OK && ticks <= 0) + if (errcode == OK && ticks <= 0) { - err = ETIMEDOUT; + errcode = ETIMEDOUT; goto errout_disabled; } /* Handle any time-related errors */ - if (err != OK) + if (errcode != OK) { goto errout_disabled; } /* Start the watchdog */ - err = OK; + errcode = OK; wd_start(rtcb->waitdog, ticks, (wdentry_t)sem_timeout, 1, getpid()); /* Now perform the blocking wait */ ret = sem_wait(sem); + if (ret < 0) + { + /* sem_wait() failed. Save the errno value */ + + errcode = get_errno(); + } /* Stop the watchdog timer */ @@ -275,6 +281,13 @@ int sem_timedwait(FAR sem_t *sem, FAR const struct timespec *abstime) * cases. */ + if (ret < 0) + { + /* On failure, restore the errno value returned by sem_wait */ + + set_errno(errcode); + } + return ret; /* Error exits */ @@ -285,6 +298,6 @@ errout_disabled: rtcb->waitdog = NULL; errout: - set_errno(err); + set_errno(errcode); return ERROR; } |