Follow @Openwall on Twitter for new release announcements and other news
[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Date: Wed, 27 Aug 2014 17:32:12 +0400 (MSK)
From: Alexander Monakov <amonakov@...ras.ru>
To: musl@...ts.openwall.com
Subject: Re: sem_getvalue conformance considerations

On Wed, 27 Aug 2014, Alexander Monakov wrote:

> Why wouldn't the following design work?
> 
> val[0] is sem value if >= 0, negated waiters count otherwise
> val[1] is wakeup count, incremented before futex wake, tested and decremented
> by waiters returning from futex wait

Unless I'm missing something, the above can simplify sem ops
(sorry, eliding some details in the following pseudocode)

trywait:

  val = sem->val[0]
  while (val > 0) {
    oldval = val;
    if ((val = a_cas(sem->val, val, val-1)) == oldval)
      return 0;
  }
  errno = EAGAIN;
  return -1;


wait:

  if (atomic_fetch_and_decrement(sem->val) > 0)
    return 0;
  while (!(futex_wait(sem->val+1, 0) && errno == EINTR)) {
    wakecnt = sem->val[1];
    while (wakecnt > 0) {
      oldwcnt = wakecnt;
      if ((wakecnt = a_cas(sem->val+1, wakecnt, wakecnt-1)) == oldwcnt)
	return 0;
    }
  }
  return -1;

post:

  val = sem->val[0];
  do {
    if (val == SEM_VALUE_MAX) {
      errno = EOVERFLOW;
      return -1;
    }
    oldval = val;
  } while ((val = a_cas(sem->val, val, val+1)) != oldval);
  if (val < 0) {
    a_inc(sem->val+1);
    futex_wake(sem->val+1, 1);
  }
  return 0;

Alexander

Powered by blists - more mailing lists

Confused about mailing lists and their use? Read about mailing lists on Wikipedia and check out these guidelines on proper formatting of your messages.