On 2020-07-08, Ted Unangst wrote:
> I think this makes sem_init(pshared) work.

Whoops, need more context to include the header file changes.

Index: include/semaphore.h
===================================================================
RCS file: /home/cvs/src/include/semaphore.h,v
retrieving revision 1.1
diff -u -p -r1.1 semaphore.h
--- include/semaphore.h 15 Oct 2017 23:40:33 -0000      1.1
+++ include/semaphore.h 8 Jul 2020 08:47:06 -0000
@@ -38,10 +38,16 @@
 #define _SEMAPHORE_H_
 
 #include <sys/cdefs.h>
+#include <machine/spinlock.h>
 
 /* Opaque type definition. */
-struct __sem;
-typedef struct __sem *sem_t;
+struct __sem {
+       _atomic_lock_t lock;
+       volatile int waitcount;
+       volatile int value;
+       int shared;
+};
+typedef struct __sem sem_t;
 struct timespec;
 
 #define SEM_FAILED      ((sem_t *)0)
Index: lib/libc/include/thread_private.h
===================================================================
RCS file: /home/cvs/src/lib/libc/include/thread_private.h,v
retrieving revision 1.35
diff -u -p -r1.35 thread_private.h
--- lib/libc/include/thread_private.h   13 Feb 2019 13:22:14 -0000      1.35
+++ lib/libc/include/thread_private.h   8 Jul 2020 08:44:45 -0000
@@ -273,13 +273,6 @@ __END_HIDDEN_DECLS
 
 #define        _SPINLOCK_UNLOCKED _ATOMIC_LOCK_UNLOCKED
 
-struct __sem {
-       _atomic_lock_t lock;
-       volatile int waitcount;
-       volatile int value;
-       int shared;
-};
-
 TAILQ_HEAD(pthread_queue, pthread);
 
 #ifdef FUTEX
Index: lib/librthread/rthread.h
===================================================================
RCS file: /home/cvs/src/lib/librthread/rthread.h,v
retrieving revision 1.64
diff -u -p -r1.64 rthread.h
--- lib/librthread/rthread.h    13 Feb 2019 13:22:14 -0000      1.64
+++ lib/librthread/rthread.h    8 Jul 2020 09:18:34 -0000
@@ -79,8 +79,8 @@ struct pthread_spinlock {
        (((size) + (_thread_pagesize - 1)) & ~(_thread_pagesize - 1))
 
 __BEGIN_HIDDEN_DECLS
-int    _sem_wait(sem_t, int, const struct timespec *, int *);
-int    _sem_post(sem_t);
+int    _sem_wait(sem_t *, int, const struct timespec *, int *);
+int    _sem_post(sem_t *);
 
 void   _rthread_init(void);
 struct stack *_rthread_alloc_stack(pthread_t);
Index: lib/librthread/rthread_sem.c
===================================================================
RCS file: /home/cvs/src/lib/librthread/rthread_sem.c,v
retrieving revision 1.32
diff -u -p -r1.32 rthread_sem.c
--- lib/librthread/rthread_sem.c        6 Apr 2020 00:01:08 -0000       1.32
+++ lib/librthread/rthread_sem.c        8 Jul 2020 09:18:34 -0000
@@ -55,7 +55,7 @@
  * Internal implementation of semaphores
  */
 int
-_sem_wait(sem_t sem, int can_eintr, const struct timespec *abstime,
+_sem_wait(sem_t *sem, int can_eintr, const struct timespec *abstime,
     int *delayed_cancel)
 {
        unsigned int val;
@@ -86,7 +86,7 @@ _sem_wait(sem_t sem, int can_eintr, cons
 
 /* always increment count */
 int
-_sem_post(sem_t sem)
+_sem_post(sem_t *sem)
 {
        membar_exit_before_atomic();
        atomic_inc_int(&sem->value);
@@ -98,70 +98,29 @@ _sem_post(sem_t sem)
  * exported semaphores
  */
 int
-sem_init(sem_t *semp, int pshared, unsigned int value)
+sem_init(sem_t *sem, int pshared, unsigned int value)
 {
-       sem_t sem;
 
        if (value > SEM_VALUE_MAX) {
                errno = EINVAL;
                return (-1);
        }
 
-       if (pshared) {
-               errno = EPERM;
-               return (-1);
-#ifdef notyet
-               char name[SEM_RANDOM_NAME_LEN];
-               sem_t *sempshared;
-               int i;
-
-               for (;;) {
-                       for (i = 0; i < SEM_RANDOM_NAME_LEN - 1; i++)
-                               name[i] = arc4random_uniform(255) + 1;
-                       name[SEM_RANDOM_NAME_LEN - 1] = '\0';
-                       sempshared = sem_open(name, O_CREAT | O_EXCL, 0, value);
-                       if (sempshared != SEM_FAILED)
-                               break;
-                       if (errno == EEXIST)
-                               continue;
-                       if (errno != EPERM)
-                               errno = ENOSPC;
-                       return (-1);
-               }
-
-               /* unnamed semaphore should not be opened twice */
-               if (sem_unlink(name) == -1) {
-                       sem_close(sempshared);
-                       errno = ENOSPC;
-                       return (-1);
-               }
-
-               *semp = *sempshared;
-               free(sempshared);
-               return (0);
-#endif
-       }
-
-       sem = calloc(1, sizeof(*sem));
-       if (!sem) {
-               errno = ENOSPC;
-               return (-1);
-       }
+       memset(sem, 0, sizeof(*sem));
        sem->value = value;
-       *semp = sem;
+       sem->shared = pshared;
 
        return (0);
 }
 
 int
-sem_destroy(sem_t *semp)
+sem_destroy(sem_t *sem)
 {
-       sem_t sem;
 
        if (!_threads_ready)             /* for SEM_MMAP_SIZE */
                _rthread_init();
 
-       if (!semp || !(sem = *semp)) {
+       if (!sem) {
                errno = EINVAL;
                return (-1);
        }
@@ -174,21 +133,19 @@ sem_destroy(sem_t *semp)
                return (-1);
        }
 
-       *semp = NULL;
        if (sem->shared)
                munmap(sem, SEM_MMAP_SIZE);
        else
-               free(sem);
+               memset(sem, 0, sizeof(*sem));
 
        return (0);
 }
 
 int
-sem_getvalue(sem_t *semp, int *sval)
+sem_getvalue(sem_t *sem, int *sval)
 {
-       sem_t sem;
 
-       if (!semp || !(sem = *semp)) {
+       if (!sem) {
                errno = EINVAL;
                return (-1);
        }
@@ -199,11 +156,10 @@ sem_getvalue(sem_t *semp, int *sval)
 }
 
 int
-sem_post(sem_t *semp)
+sem_post(sem_t *sem)
 {
-       sem_t sem;
 
-       if (!semp || !(sem = *semp)) {
+       if (!sem) {
                errno = EINVAL;
                return (-1);
        }
@@ -214,11 +170,10 @@ sem_post(sem_t *semp)
 }
 
 int
-sem_wait(sem_t *semp)
+sem_wait(sem_t *sem)
 {
        struct tib *tib = TIB_GET();
        pthread_t self;
-       sem_t sem;
        int error;
        PREP_CANCEL_POINT(tib);
 
@@ -226,7 +181,7 @@ sem_wait(sem_t *semp)
                _rthread_init();
        self = tib->tib_thread;
 
-       if (!semp || !(sem = *semp)) {
+       if (!sem) {
                errno = EINVAL;
                return (-1);
        }
@@ -246,15 +201,14 @@ sem_wait(sem_t *semp)
 }
 
 int
-sem_timedwait(sem_t *semp, const struct timespec *abstime)
+sem_timedwait(sem_t *sem, const struct timespec *abstime)
 {
        struct tib *tib = TIB_GET();
        pthread_t self;
-       sem_t sem;
        int error;
        PREP_CANCEL_POINT(tib);
 
-       if (!semp || !(sem = *semp) || abstime == NULL ||
+       if (!sem || abstime == NULL ||
           abstime->tv_nsec < 0 || abstime->tv_nsec >= 1000000000) {
                errno = EINVAL;
                return (-1);
@@ -279,12 +233,11 @@ sem_timedwait(sem_t *semp, const struct 
 }
 
 int
-sem_trywait(sem_t *semp)
+sem_trywait(sem_t *sem)
 {
-       sem_t sem;
        unsigned int val;
 
-       if (!semp || !(sem = *semp)) {
+       if (!sem) {
                errno = EINVAL;
                return (-1);
        }
@@ -316,7 +269,7 @@ sem_open(const char *name, int oflag, ..
 {
        char sempath[SEM_PATH_SIZE];
        struct stat sb;
-       sem_t sem, *semp;
+       sem_t *sem;
        unsigned int value = 0;
        int created = 0, fd;
 
@@ -382,34 +335,24 @@ sem_open(const char *name, int oflag, ..
                errno = EINVAL;
                return (SEM_FAILED);
        }
-       semp = malloc(sizeof(*semp));
-       if (!semp) {
-               munmap(sem, SEM_MMAP_SIZE);
-               errno = ENOSPC;
-               return (SEM_FAILED);
-       }
        if (created) {
                sem->value = value;
                sem->shared = 1;
        }
-       *semp = sem;
 
-       return (semp);
+       return (sem);
 }
 
 int
-sem_close(sem_t *semp)
+sem_close(sem_t *sem)
 {
-       sem_t sem;
 
-       if (!semp || !(sem = *semp) || !sem->shared) {
+       if (!sem) {
                errno = EINVAL;
                return (-1);
        }
 
-       *semp = NULL;
        munmap(sem, SEM_MMAP_SIZE);
-       free(semp);
 
        return (0);
 }
Index: lib/librthread/rthread_sem_compat.c
===================================================================
RCS file: /home/cvs/src/lib/librthread/rthread_sem_compat.c,v
retrieving revision 1.1
diff -u -p -r1.1 rthread_sem_compat.c
--- lib/librthread/rthread_sem_compat.c 8 Jun 2018 13:53:01 -0000       1.1
+++ lib/librthread/rthread_sem_compat.c 8 Jul 2020 09:18:35 -0000
@@ -53,7 +53,7 @@
  * Internal implementation of semaphores
  */
 int
-_sem_wait(sem_t sem, int can_eintr, const struct timespec *abstime,
+_sem_wait(sem_t *sem, int can_eintr, const struct timespec *abstime,
     int *delayed_cancel)
 {
        void *ident = (void *)&sem->waitcount;
@@ -87,7 +87,7 @@ _sem_wait(sem_t sem, int can_eintr, cons
 
 /* always increment count */
 int
-_sem_post(sem_t sem)
+_sem_post(sem_t *sem)
 {
        void *ident = (void *)&sem->waitcount;
        int rv = 0;
@@ -109,71 +109,31 @@ _sem_post(sem_t sem)
  * exported semaphores
  */
 int
-sem_init(sem_t *semp, int pshared, unsigned int value)
+sem_init(sem_t *sem, int pshared, unsigned int value)
 {
-       sem_t sem;
 
        if (value > SEM_VALUE_MAX) {
                errno = EINVAL;
                return (-1);
        }
 
-       if (pshared) {
-               errno = EPERM;
-               return (-1);
-#ifdef notyet
-               char name[SEM_RANDOM_NAME_LEN];
-               sem_t *sempshared;
-               int i;
-
-               for (;;) {
-                       for (i = 0; i < SEM_RANDOM_NAME_LEN - 1; i++)
-                               name[i] = arc4random_uniform(255) + 1;
-                       name[SEM_RANDOM_NAME_LEN - 1] = '\0';
-                       sempshared = sem_open(name, O_CREAT | O_EXCL, 0, value);
-                       if (sempshared != SEM_FAILED)
-                               break;
-                       if (errno == EEXIST)
-                               continue;
-                       if (errno != EPERM)
-                               errno = ENOSPC;
-                       return (-1);
-               }
-
-               /* unnamed semaphore should not be opened twice */
-               if (sem_unlink(name) == -1) {
-                       sem_close(sempshared);
-                       errno = ENOSPC;
-                       return (-1);
-               }
 
-               *semp = *sempshared;
-               free(sempshared);
-               return (0);
-#endif
-       }
-
-       sem = calloc(1, sizeof(*sem));
-       if (!sem) {
-               errno = ENOSPC;
-               return (-1);
-       }
+       memset(sem, 0, sizeof(*sem));
        sem->lock = _SPINLOCK_UNLOCKED;
        sem->value = value;
-       *semp = sem;
+       sem->shared = pshared;
 
        return (0);
 }
 
 int
-sem_destroy(sem_t *semp)
+sem_destroy(sem_t *sem)
 {
-       sem_t sem;
 
        if (!_threads_ready)             /* for SEM_MMAP_SIZE */
                _rthread_init();
 
-       if (!semp || !(sem = *semp)) {
+       if (!sem) {
                errno = EINVAL;
                return (-1);
        }
@@ -186,21 +146,17 @@ sem_destroy(sem_t *semp)
                return (-1);
        }
 
-       *semp = NULL;
        if (sem->shared)
                munmap(sem, SEM_MMAP_SIZE);
-       else
-               free(sem);
 
        return (0);
 }
 
 int
-sem_getvalue(sem_t *semp, int *sval)
+sem_getvalue(sem_t *sem, int *sval)
 {
-       sem_t sem;
 
-       if (!semp || !(sem = *semp)) {
+       if (!sem) {
                errno = EINVAL;
                return (-1);
        }
@@ -213,11 +169,10 @@ sem_getvalue(sem_t *semp, int *sval)
 }
 
 int
-sem_post(sem_t *semp)
+sem_post(sem_t *sem)
 {
-       sem_t sem;
 
-       if (!semp || !(sem = *semp)) {
+       if (!sem) {
                errno = EINVAL;
                return (-1);
        }
@@ -228,11 +183,10 @@ sem_post(sem_t *semp)
 }
 
 int
-sem_wait(sem_t *semp)
+sem_wait(sem_t *sem)
 {
        struct tib *tib = TIB_GET();
        pthread_t self;
-       sem_t sem;
        int r;
        PREP_CANCEL_POINT(tib);
 
@@ -240,7 +194,7 @@ sem_wait(sem_t *semp)
                _rthread_init();
        self = tib->tib_thread;
 
-       if (!semp || !(sem = *semp)) {
+       if (!sem) {
                errno = EINVAL;
                return (-1);
        }
@@ -258,15 +212,14 @@ sem_wait(sem_t *semp)
 }
 
 int
-sem_timedwait(sem_t *semp, const struct timespec *abstime)
+sem_timedwait(sem_t *sem, const struct timespec *abstime)
 {
        struct tib *tib = TIB_GET();
        pthread_t self;
-       sem_t sem;
        int r;
        PREP_CANCEL_POINT(tib);
 
-       if (!semp || !(sem = *semp) || abstime == NULL ||
+       if (!sem || abstime == NULL ||
            abstime->tv_nsec < 0 || abstime->tv_nsec >= 1000000000) {
                errno = EINVAL;
                return (-1);
@@ -289,12 +242,11 @@ sem_timedwait(sem_t *semp, const struct 
 }
 
 int
-sem_trywait(sem_t *semp)
+sem_trywait(sem_t *sem)
 {
-       sem_t sem;
        int r;
 
-       if (!semp || !(sem = *semp)) {
+       if (!sem) {
                errno = EINVAL;
                return (-1);
        }
@@ -330,7 +282,7 @@ sem_open(const char *name, int oflag, ..
 {
        char sempath[SEM_PATH_SIZE];
        struct stat sb;
-       sem_t sem, *semp;
+       sem_t *sem;
        unsigned int value = 0;
        int created = 0, fd;
 
@@ -396,35 +348,25 @@ sem_open(const char *name, int oflag, ..
                errno = EINVAL;
                return (SEM_FAILED);
        }
-       semp = malloc(sizeof(*semp));
-       if (!semp) {
-               munmap(sem, SEM_MMAP_SIZE);
-               errno = ENOSPC;
-               return (SEM_FAILED);
-       }
        if (created) {
                sem->lock = _SPINLOCK_UNLOCKED;
                sem->value = value;
                sem->shared = 1;
        }
-       *semp = sem;
 
-       return (semp);
+       return (sem);
 }
 
 int
-sem_close(sem_t *semp)
+sem_close(sem_t *sem)
 {
-       sem_t sem;
 
-       if (!semp || !(sem = *semp) || !sem->shared) {
+       if (!sem || !sem->shared) {
                errno = EINVAL;
                return (-1);
        }
 
-       *semp = NULL;
        munmap(sem, SEM_MMAP_SIZE);
-       free(semp);
 
        return (0);
 }

Reply via email to