ViewVC Help
View File | Revision Log | Show Annotations | Revision Graph | Root Listing
root/cebix/SheepShaver/src/Unix/Linux/sheepthreads.c
(Generate patch)

Comparing SheepShaver/src/Unix/Linux/sheepthreads.c (file contents):
Revision 1.3 by gbeauche, 2004-01-04T06:55:50Z vs.
Revision 1.6 by gbeauche, 2005-01-30T21:48:20Z

# Line 2 | Line 2
2   *  sheepthreads.c - Minimal pthreads implementation (libpthreads doesn't
3   *                   like nonstandard stacks)
4   *
5 < *  SheepShaver (C) 1997-2002 Christian Bauer and Marc Hellwig
5 > *  SheepShaver (C) 1997-2005 Christian Bauer and Marc Hellwig
6   *
7   *  This program is free software; you can redistribute it and/or modify
8   *  it under the terms of the GNU General Public License as published by
# Line 57 | Line 57 | extern int __clone(int (*fn)(void *), vo
57   #define sem_value __sem_value
58   #define sem_waiting __sem_waiting
59  
60 + /* Wait for "clone" children only (Linux 2.4+ specific) */
61 + #ifndef __WCLONE
62 + #define __WCLONE 0
63 + #endif
64 +
65  
66   /*
67   *  Return pthread ID of self
# Line 137 | Line 142 | int pthread_create(pthread_t *thread, co
142   int pthread_join(pthread_t thread, void **ret)
143   {
144          do {
145 <                if (waitpid(thread, NULL, 0) >= 0)
145 >                if (waitpid(thread, NULL, __WCLONE) >= 0);
146                          break;
147          } while (errno == EINTR);
148          if (ret)
# Line 325 | Line 330 | void null_handler(int sig)
330   int sem_wait(sem_t *sem)
331   {
332          acquire_spinlock(&sem->sem_lock.spinlock);
333 <        if (atomic_add((int *)&sem->sem_value, -1) >= 0) {
333 >        if (sem->sem_value > 0)
334 >                atomic_add((int *)&sem->sem_value, -1);
335 >        else {
336                  sigset_t mask;
337                  if (!sem->sem_lock.status) {
338                          struct sigaction sa;
# Line 352 | Line 359 | int sem_wait(sem_t *sem)
359   int sem_post(sem_t *sem)
360   {
361          acquire_spinlock(&sem->sem_lock.spinlock);
362 <        atomic_add((int *)&sem->sem_value, 1);
363 <        if (sem->sem_waiting)
362 >        if (sem->sem_waiting == NULL)
363 >                atomic_add((int *)&sem->sem_value, 1);
364 >        else
365                  kill((pid_t)sem->sem_waiting, sem->sem_lock.status);
366          release_spinlock(&sem->sem_lock.spinlock);
367          return 0;
368   }
369 +
370 +
371 + /*
372 + *  Simple producer/consumer test program
373 + */
374 +
375 + #ifdef TEST
376 + #include <stdio.h>
377 +
378 + static sem_t p_sem, c_sem;
379 + static int data = 0;
380 +
381 + static void *producer_func(void *arg)
382 + {
383 +        int i, n = (int)arg;
384 +        for (i = 0; i < n; i++) {
385 +                sem_wait(&p_sem);
386 +                data++;
387 +                sem_post(&c_sem);
388 +        }
389 +        return NULL;
390 + }
391 +
392 + static void *consumer_func(void *arg)
393 + {
394 +        int i, n = (int)arg;
395 +        for (i = 0; i < n; i++) {
396 +                sem_wait(&c_sem);
397 +                printf("data: %d\n", data);
398 +                sem_post(&p_sem);
399 +        }
400 +        sleep(1); // for testing pthread_join()
401 +        return NULL;
402 + }
403 +
404 + int main(void)
405 + {
406 +        pthread_t producer_thread, consumer_thread;
407 +        static const int N = 5;
408 +
409 +        if (sem_init(&c_sem, 0, 0) < 0)
410 +                return 1;
411 +        if (sem_init(&p_sem, 0, 1) < 0)
412 +                return 2;
413 +        if (pthread_create(&producer_thread, NULL, producer_func, (void *)N) != 0)
414 +                return 3;
415 +        if (pthread_create(&consumer_thread, NULL, consumer_func, (void *)N) != 0)
416 +                return 4;
417 +        pthread_join(producer_thread, NULL);
418 +        pthread_join(consumer_thread, NULL);
419 +        sem_destroy(&p_sem);
420 +        sem_destroy(&c_sem);
421 +        if (data != N)
422 +                return 5;
423 +        return 0;
424 + }
425 + #endif

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines