OSDN Git Service

Fix calling make with slice whose element type is size zero.
[pf3gnuchains/gcc-fork.git] / libgo / runtime / go-note.c
1 /* go-note.c -- implement notesleep, notewakeup and noteclear.
2
3    Copyright 2009 The Go Authors. All rights reserved.
4    Use of this source code is governed by a BSD-style
5    license that can be found in the LICENSE file.  */
6
7 /* A note is a one-time notification.  noteclear clears the note.
8    notesleep waits for a call to notewakeup.  notewakeup wakes up
9    every thread waiting on the note.  */
10
11 #include "go-assert.h"
12 #include "runtime.h"
13
14 /* We use a single global lock and condition variable.  It would be
15    better to use a futex on Linux.  */
16
17 static pthread_mutex_t note_lock = PTHREAD_MUTEX_INITIALIZER;
18 static pthread_cond_t note_cond = PTHREAD_COND_INITIALIZER;
19
20 /* noteclear is called before any calls to notesleep or
21    notewakeup.  */
22
23 void
24 runtime_noteclear (Note* n)
25 {
26   int32 i;
27
28   i = pthread_mutex_lock (&note_lock);
29   __go_assert (i == 0);
30
31   n->woken = 0;
32
33   i = pthread_mutex_unlock (&note_lock);
34   __go_assert (i == 0);
35 }
36
37 /* Wait until notewakeup is called.  */
38
39 void
40 runtime_notesleep (Note* n)
41 {
42   int32 i;
43
44   i = pthread_mutex_lock (&note_lock);
45   __go_assert (i == 0);
46
47   while (!n->woken)
48     {
49       i = pthread_cond_wait (&note_cond, &note_lock);
50       __go_assert (i == 0);
51     }
52
53   i = pthread_mutex_unlock (&note_lock);
54   __go_assert (i == 0);
55 }
56
57 /* Wake up every thread sleeping on the note.  */
58
59 void
60 runtime_notewakeup (Note *n)
61 {
62   int32 i;
63
64   i = pthread_mutex_lock (&note_lock);
65   __go_assert (i == 0);
66
67   n->woken = 1;
68
69   i = pthread_cond_broadcast (&note_cond);
70   __go_assert (i == 0);
71
72   i = pthread_mutex_unlock (&note_lock);
73   __go_assert (i == 0);
74 }