1
/* GLIB - Library of useful routines for C programming
2
* Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
4
* gthread.c: nspr thread system implementation
5
* Copyright 1998 Sebastian Wilhelmi; University of Karlsruhe
7
* This library is free software; you can redistribute it and/or
8
* modify it under the terms of the GNU Library General Public
9
* License as published by the Free Software Foundation; either
10
* version 2 of the License, or (at your option) any later version.
12
* This library is distributed in the hope that it will be useful,
13
* but WITHOUT ANY WARRANTY; without even the implied warranty of
14
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15
* Library General Public License for more details.
17
* You should have received a copy of the GNU Library General Public
18
* License along with this library; if not, write to the
19
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
20
* Boston, MA 02111-1307, USA.
31
#ifdef G_DISABLE_ASSERT
33
#define STDERR_ASSERT(expr)
35
#else /* G_DISABLE_ASSERT */
37
#define STDERR_ASSERT(expr) G_STMT_START{ \
39
g_log (G_LOG_DOMAIN, \
41
"file %s: line %d: assertion failed: (%s)", \
46
#endif /* G_DISABLE_ASSERT */
48
/* NOTE: the functions g_mutex_lock and g_mutex_unlock may not use
49
functions from gmem.c and gmessages.c; */
52
g_mutex_trylock_nspr_impl (GMutex * mutex)
54
PRStatus status = PRP_TryLock ((PRLock *) mutex);
55
if (status == PR_SUCCESS)
63
g_cond_wait_nspr_impl (GCond * cond,
64
GMutex * entered_mutex)
66
PRStatus status = PRP_NakedWait ((PRCondVar *) cond,
67
(PRLock *) entered_mutex,
68
PR_INTERVAL_NO_TIMEOUT);
69
g_assert (status == PR_SUCCESS);
72
#define G_MICROSEC 1000000
75
g_cond_timed_wait_nspr_impl (GCond * cond,
76
GMutex * entered_mutex,
80
PRIntervalTime interval;
81
GTimeVal current_time;
84
g_return_val_if_fail (cond != NULL, FALSE);
85
g_return_val_if_fail (entered_mutex != NULL, FALSE);
87
g_get_current_time (¤t_time);
89
if (abs_time->tv_sec < current_time.tv_sec ||
90
(abs_time->tv_sec == current_time.tv_sec &&
91
abs_time->tv_usec < current_time.tv_usec))
94
interval = PR_SecondsToInterval (abs_time->tv_sec - current_time.tv_sec);
95
microsecs = abs_time->tv_usec - current_time.tv_usec;
97
interval -= PR_MicrosecondsToInterval (-microsecs);
99
interval += PR_MicrosecondsToInterval (microsecs);
101
status = PRP_NakedWait ((PRCondVar *) cond, (PRLock *) entered_mutex,
104
g_assert (status == PR_SUCCESS);
106
g_get_current_time (¤t_time);
108
if (abs_time->tv_sec < current_time.tv_sec ||
109
(abs_time->tv_sec == current_time.tv_sec &&
110
abs_time->tv_usec < current_time.tv_usec))
115
typedef struct _GPrivateNSPRData GPrivateNSPRData;
116
struct _GPrivateNSPRData
119
GDestroyNotify destructor;
122
typedef struct _GPrivateNSPR GPrivateNSPR;
126
GDestroyNotify destructor;
129
static GPrivateNSPRData *
130
g_private_nspr_data_constructor (GDestroyNotify destructor, gpointer data)
132
/* we can not use g_new and friends, as they might use private data by
134
GPrivateNSPRData *private = malloc (sizeof (GPrivateNSPRData));
136
private->data = data;
137
private->destructor = destructor;
143
g_private_nspr_data_destructor (gpointer data)
145
GPrivateNSPRData *private = data;
146
if (private->destructor && private->data)
147
(*private->destructor) (private->data);
152
g_private_new_nspr_impl (GDestroyNotify destructor)
154
GPrivateNSPR *result = g_new (GPrivateNSPR, 1);
155
PRStatus status = PR_NewThreadPrivateIndex (&result->private,
156
g_private_nspr_data_destructor);
157
g_assert (status == PR_SUCCESS);
159
result->destructor = destructor;
160
return (GPrivate *) result;
163
/* NOTE: the functions g_private_get and g_private_set may not use
164
functions from gmem.c and gmessages.c */
166
static GPrivateNSPRData *
167
g_private_nspr_data_get (GPrivateNSPR * private)
169
GPrivateNSPRData *data;
171
STDERR_ASSERT (private);
173
data = PR_GetThreadPrivate (private->private);
176
data = g_private_nspr_data_constructor (private->destructor, NULL);
177
STDERR_ASSERT (PR_SetThreadPrivate (private->private, data)
185
g_private_set_nspr_impl (GPrivate * private, gpointer value)
190
g_private_nspr_data_get ((GPrivateNSPR *) private)->data = value;
194
g_private_get_nspr_impl (GPrivate * private)
199
return g_private_nspr_data_get ((GPrivateNSPR *) private)->data;
202
static GThreadFunctions g_thread_functions_for_glib_use_default =
204
(GMutex * (*)())PR_NewLock,
205
(void (*)(GMutex *)) PR_Lock,
206
g_mutex_trylock_nspr_impl,
207
(void (*)(GMutex *)) PR_Unlock,
208
(void (*)(GMutex *)) PR_DestroyLock,
209
(GCond * (*)())PRP_NewNakedCondVar,
210
(void (*)(GCond *)) PRP_NakedNotify,
211
(void (*)(GCond *)) PRP_NakedBroadcast,
212
g_cond_wait_nspr_impl,
213
g_cond_timed_wait_nspr_impl,
214
(void (*)(GCond *)) PRP_DestroyNakedCondVar,
215
g_private_new_nspr_impl,
216
g_private_get_nspr_impl,
217
g_private_set_nspr_impl