opal/fifo: if available use load-linked store-conditional
These instructions allow a more efficient implementation of the opal_fifo_pop_atomic function. Signed-off-by: Nathan Hjelm <hjelmn@lanl.gov>
Этот коммит содержится в:
родитель
6a19a10fbb
Коммит
2a7e191dd8
@ -216,6 +216,27 @@ static inline opal_list_item_t *opal_fifo_pop_atomic (opal_fifo_t *fifo)
|
|||||||
{
|
{
|
||||||
opal_list_item_t *item, *next;
|
opal_list_item_t *item, *next;
|
||||||
|
|
||||||
|
#if OPAL_HAVE_ATOMIC_LLSC_PTR
|
||||||
|
/* use load-linked store-conditional to avoid ABA issues */
|
||||||
|
do {
|
||||||
|
item = opal_atomic_ll_ptr (&fifo->opal_fifo_head.data.item);
|
||||||
|
if (&fifo->opal_fifo_ghost == item) {
|
||||||
|
if (&fifo->opal_fifo_ghost == fifo->opal_fifo_tail.data.item) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* fifo does not appear empty. wait for the fifo to be made
|
||||||
|
* consistent by conflicting thread. */
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
next = (opal_list_item_t *) item->opal_list_next;
|
||||||
|
if (opal_atomic_sc_ptr (&fifo->opal_fifo_head.data.item, next)) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} while (1);
|
||||||
|
#else
|
||||||
|
/* protect against ABA issues by "locking" the head */
|
||||||
do {
|
do {
|
||||||
if (opal_atomic_cmpset_32 ((int32_t *) &fifo->opal_fifo_head.data.counter, 0, 1)) {
|
if (opal_atomic_cmpset_32 ((int32_t *) &fifo->opal_fifo_head.data.counter, 0, 1)) {
|
||||||
break;
|
break;
|
||||||
@ -234,6 +255,7 @@ static inline opal_list_item_t *opal_fifo_pop_atomic (opal_fifo_t *fifo)
|
|||||||
|
|
||||||
next = (opal_list_item_t *) item->opal_list_next;
|
next = (opal_list_item_t *) item->opal_list_next;
|
||||||
fifo->opal_fifo_head.data.item = next;
|
fifo->opal_fifo_head.data.item = next;
|
||||||
|
#endif
|
||||||
|
|
||||||
if (&fifo->opal_fifo_ghost == next) {
|
if (&fifo->opal_fifo_ghost == next) {
|
||||||
if (!opal_atomic_cmpset_ptr (&fifo->opal_fifo_tail.data.item, item, &fifo->opal_fifo_ghost)) {
|
if (!opal_atomic_cmpset_ptr (&fifo->opal_fifo_tail.data.item, item, &fifo->opal_fifo_ghost)) {
|
||||||
|
Загрузка…
x
Ссылка в новой задаче
Block a user