summaryrefslogtreecommitdiffstats
path: root/otherlibs/systhreads/posix.c
diff options
context:
space:
mode:
authorXavier Leroy <xavier.leroy@inria.fr>1998-08-08 18:42:22 +0000
committerXavier Leroy <xavier.leroy@inria.fr>1998-08-08 18:42:22 +0000
commit26be0e1ee24e62f94f2c91d995664467bcbca7ba (patch)
treefe484ba2f28aecb1b0a68a35d5e258d7b0f8fbe7 /otherlibs/systhreads/posix.c
parentd57065040cdbd794bbfba1ba68ec4cf21beb8005 (diff)
Suppression des semaphores (mauvaise idee!). Revu l'implementation de Thread.wait_signal dans systhreads
git-svn-id: http://caml.inria.fr/svn/ocaml/trunk@2043 f963ae5c-01c2-4b8c-9fe0-0dff7051ff02
Diffstat (limited to 'otherlibs/systhreads/posix.c')
-rw-r--r--otherlibs/systhreads/posix.c92
1 files changed, 45 insertions, 47 deletions
diff --git a/otherlibs/systhreads/posix.c b/otherlibs/systhreads/posix.c
index 6931d7500..17daf0985 100644
--- a/otherlibs/systhreads/posix.c
+++ b/otherlibs/systhreads/posix.c
@@ -561,62 +561,60 @@ value caml_condition_broadcast(value wrapper) /* ML */
return Val_unit;
}
-/* Semaphore operations. Currently not exported to the user,
- used only for implementing Thread.wait_signal */
+/* Synchronous signal wait */
-#define Semaphore_val(v) ((sem_t *) Field(v, 1))
-#define Max_semaphore_number 1000
+static sem_t * wait_signal_sem[NSIG];
+static int * wait_signal_received[NSIG];
-static void caml_semaphore_finalize(value wrapper)
+static void caml_wait_signal_handler(int signo)
{
- sem_t * sem = Semaphore_val(wrapper);
- sem_destroy(sem);
- stat_free(sem);
+ char buf[100];
+ sprintf(buf, "Got signal %d\n", signo);
+ write(2, buf, strlen(buf));
+ *(wait_signal_received[signo]) = signo;
+ sem_post(wait_signal_sem[signo]);
}
-value caml_semaphore_new(value vinit) /* ML */
-{
- sem_t * sem;
- value wrapper;
- sem = stat_alloc(sizeof(sem_t));
- if (sem_init(sem, 0, Int_val(vinit)) == -1)
- caml_pthread_check(errno, "Semaphore.create");
- wrapper = alloc_final(2, caml_semaphore_finalize, 1, Max_semaphore_number);
- Semaphore_val(wrapper) = sem;
- return wrapper;
-}
+extern int posix_signals[]; /* from byterun/sys.c */
-value caml_semaphore_wait(value wrapper) /* ML */
+value caml_wait_signal(value sigs)
{
- int retcode;
- sem_t * sem = Semaphore_val(wrapper);
- Begin_root(wrapper) /* prevent deallocation of semaphore */
- enter_blocking_section();
- retcode = 0;
- while (sem_wait(sem) == -1) {
- if (errno != EINTR) { retcode = errno; break; }
+ sem_t sem;
+ int res, s, retcode;
+ value l;
+ struct sigaction sa, oldsignals[NSIG];
+
+ Begin_root(sigs);
+ if (sem_init(&sem, 0, 0) == -1)
+ caml_pthread_check(errno, "Thread.wait_signal (sem_init)");
+ res = 0;
+ sa.sa_handler = caml_wait_signal_handler;
+ sigemptyset(&sa.sa_mask);
+ sa.sa_flags = 0;
+ for (l = sigs; l != Val_int(0); l = Field(l, 1)) {
+ s = Int_val(Field(l, 0));
+ if (s < 0) s = posix_signals[-s-1];
+ if (sigaction(s, &sa, &oldsignals[s]) == -1) {
+ sem_destroy(&sem);
+ caml_pthread_check(errno, "Thread.wait_signal (sigaction)");
}
- leave_blocking_section();
+ wait_signal_sem[s] = &sem;
+ wait_signal_received[s] = &res;
+ }
+ enter_blocking_section();
+ retcode = 0;
+ while (sem_wait(&sem) == -1) {
+ if (errno != EINTR) { retcode = errno; break; }
+ }
+ leave_blocking_section();
+ caml_pthread_check(retcode, "Thread.wait_signal (sem_wait)");
+ for (l = sigs; l != Val_int(0); l = Field(l, 1)) {
+ s = Int_val(Field(l, 0));
+ sigaction(s, &oldsignals[s], NULL);
+ }
+ sem_destroy(&sem);
End_roots();
- caml_pthread_check(retcode, "Semaphore.wait");
- return Val_unit;
-}
-
-value caml_semaphore_post(value wrapper) /* ML */
-{
- sem_t * sem = Semaphore_val(wrapper);
- if (sem_post(sem) == -1)
- caml_pthread_check(errno, "Semaphore.post");
- return Val_unit;
-}
-
-value caml_semaphore_getvalue(value wrapper) /* ML */
-{
- sem_t * sem = Semaphore_val(wrapper);
- int val;
- if (sem_getvalue(sem, &val) == -1)
- caml_pthread_check(errno, "Semaphore.getvalue");
- return Val_int(val);
+ return Val_int(res);
}
/* Error report */