+xbt_os_sem_t xbt_os_sem_init(unsigned int value)
+{
+ xbt_os_sem_t res = xbt_new(s_xbt_os_sem_t, 1);
+
+ /* On some systems (MAC OS X), only the stub of sem_init is to be found.
+ * Any attempt to use it leads to ENOSYS (function not implemented).
+ * If such a prehistoric system is detected, do the job with sem_open instead
+ */
+#ifdef HAVE_SEM_INIT
+ if (sem_init(&(res->s), 0, value) != 0)
+ THROW1(system_error, errno, "sem_init() failed: %s", strerror(errno));
+ res->ps = &(res->s);
+
+#else /* damn, no sem_init(). Reimplement it */
+
+ xbt_os_mutex_acquire(next_sem_ID_lock);
+ res->name = bprintf("/%d.%d", (*xbt_getpid) (), ++next_sem_ID);
+ xbt_os_mutex_release(next_sem_ID_lock);
+
+ res->ps = sem_open(res->name, O_CREAT, 0644, value);
+ if ((res->ps == (sem_t *) SEM_FAILED) && (errno == ENAMETOOLONG)) {
+ /* Old darwins only allow 13 chars. Did you create *that* amount of semaphores? */
+ res->name[13] = '\0';
+ res->ps = sem_open(res->name, O_CREAT, 0644, 1);
+ }
+ if ((res->ps == (sem_t *) SEM_FAILED))
+ THROW1(system_error, errno, "sem_open() failed: %s", strerror(errno));
+
+ /* Remove the name from the semaphore namespace: we never join on it */
+ if (sem_unlink(res->name) < 0)
+ THROW1(system_error, errno, "sem_unlink() failed: %s", strerror(errno));