posix/pthreads: fix pthread_barrier_wait() behavior to match Posix
Exactly one caller of pthread_barrier_wait() should receive a return value of PTHREAD_BARRIER_SERIAL_WAIT; all others should receive zero (or an error code). Added a test to match. Fixes: #9953 Signed-off-by: Charles E. Youse <charles.youse@intel.com>
This commit is contained in:
parent
6c8825fc96
commit
3522e05f76
3 changed files with 20 additions and 7 deletions
|
@ -334,6 +334,8 @@ static inline int pthread_mutexattr_destroy(pthread_mutexattr_t *m)
|
|||
.max = count, \
|
||||
}
|
||||
|
||||
#define PTHREAD_BARRIER_SERIAL_THREAD 1
|
||||
|
||||
/**
|
||||
* @brief POSIX threading compatibility API
|
||||
*
|
||||
|
|
|
@ -11,10 +11,8 @@
|
|||
|
||||
int pthread_barrier_wait(pthread_barrier_t *b)
|
||||
{
|
||||
/* FIXME: This function should return PTHREAD_BARRIER_SERIAL_THREAD
|
||||
* for an arbitrary thread and 0 for the others.
|
||||
*/
|
||||
int key = irq_lock();
|
||||
unsigned int key = irq_lock();
|
||||
int ret = 0;
|
||||
|
||||
b->count++;
|
||||
|
||||
|
@ -25,8 +23,10 @@ int pthread_barrier_wait(pthread_barrier_t *b)
|
|||
_ready_one_thread(&b->wait_q);
|
||||
}
|
||||
_reschedule_irqlock(key);
|
||||
return 0;
|
||||
ret = PTHREAD_BARRIER_SERIAL_THREAD;
|
||||
} else {
|
||||
return _pend_curr_irqlock(key, &b->wait_q, K_FOREVER);
|
||||
(void) _pend_curr_irqlock(key, &b->wait_q, K_FOREVER);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
|
|
@ -44,6 +44,7 @@ static int curr_bounce_thread;
|
|||
|
||||
static int barrier_failed;
|
||||
static int barrier_done[N_THR_E];
|
||||
static int barrier_return[N_THR_E];
|
||||
|
||||
/* First phase bounces execution between two threads using a condition
|
||||
* variable, continuously testing that no other thread is mucking with
|
||||
|
@ -138,7 +139,7 @@ void *thread_top_exec(void *p1)
|
|||
sem_post(&main_sem);
|
||||
}
|
||||
}
|
||||
pthread_barrier_wait(&barrier);
|
||||
barrier_return[id] = pthread_barrier_wait(&barrier);
|
||||
barrier_done[id] = 1;
|
||||
sem_post(&main_sem);
|
||||
pthread_exit(p1);
|
||||
|
@ -231,6 +232,7 @@ void test_posix_pthread_execution(void)
|
|||
int schedpolicy = SCHED_FIFO;
|
||||
void *retval, *stackaddr;
|
||||
size_t stacksize;
|
||||
int serial_threads = 0;
|
||||
|
||||
sem_init(&main_sem, 0, 1);
|
||||
schedparam.sched_priority = CONFIG_NUM_COOP_PRIORITIES - 1;
|
||||
|
@ -346,6 +348,15 @@ void test_posix_pthread_execution(void)
|
|||
pthread_join(newthread[i], &retval);
|
||||
}
|
||||
|
||||
for (i = 0; i < N_THR_E; i++) {
|
||||
if (barrier_return[i] == PTHREAD_BARRIER_SERIAL_THREAD) {
|
||||
++serial_threads;
|
||||
}
|
||||
}
|
||||
|
||||
/* TESTPOINT: Check only one PTHREAD_BARRIER_SERIAL_THREAD returned. */
|
||||
zassert_true(serial_threads == 1, "Bungled barrier return value(s)");
|
||||
|
||||
printk("Barrier test OK\n");
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue