mirror of
https://gitlab.gnome.org/GNOME/glib.git
synced 2025-02-23 18:52:09 +01:00
Added new default thread implementation on top of the mozilla nspr
1998-12-11 Sebastian Wilhelmi <wilhelmi@ira.uka.de> * gthread/gthread-nspr.c, configure.in: Added new default thread implementation on top of the mozilla nspr library. * gmem.c, gmessaged.c, gthread/gthread.c, gthread/gthread-*.c: Changed GStaticMutex and GStaticPrivate in gmem.c and gmessages.c into GMutex and GPrivate resp. to make error reporting and use of gmem possible in most (not all, though) gthread functions. Also initialized the modules via new init functions. * configure.in: Fixed syntax bug in definition of type GStaticMutex. * gthread/testgthread.c: Updated to work with nspr, but see note there for remaining problems.
This commit is contained in:
parent
502084745c
commit
7589569f13
17
ChangeLog
17
ChangeLog
@ -1,3 +1,20 @@
|
||||
1998-12-11 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gthread/gthread-nspr.c, configure.in: Added new default thread
|
||||
implementation on top of the mozilla nspr library.
|
||||
|
||||
* gmem.c, gmessaged.c, gthread/gthread.c, gthread/gthread-*.c:
|
||||
Changed GStaticMutex and GStaticPrivate in gmem.c and gmessages.c
|
||||
into GMutex and GPrivate resp. to make error reporting and use of
|
||||
gmem possible in most (not all, though) gthread functions. Also
|
||||
initialized the modules via new init functions.
|
||||
|
||||
* configure.in: Fixed syntax bug in definition of type
|
||||
GStaticMutex.
|
||||
|
||||
* gthread/testgthread.c: Updated to work with nspr, but see note
|
||||
there for remaining problems.
|
||||
|
||||
1998-12-10 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gmutex.c, glib.h: Now abort, if a mutex/cond/private is
|
||||
|
@ -1,3 +1,20 @@
|
||||
1998-12-11 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gthread/gthread-nspr.c, configure.in: Added new default thread
|
||||
implementation on top of the mozilla nspr library.
|
||||
|
||||
* gmem.c, gmessaged.c, gthread/gthread.c, gthread/gthread-*.c:
|
||||
Changed GStaticMutex and GStaticPrivate in gmem.c and gmessages.c
|
||||
into GMutex and GPrivate resp. to make error reporting and use of
|
||||
gmem possible in most (not all, though) gthread functions. Also
|
||||
initialized the modules via new init functions.
|
||||
|
||||
* configure.in: Fixed syntax bug in definition of type
|
||||
GStaticMutex.
|
||||
|
||||
* gthread/testgthread.c: Updated to work with nspr, but see note
|
||||
there for remaining problems.
|
||||
|
||||
1998-12-10 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gmutex.c, glib.h: Now abort, if a mutex/cond/private is
|
||||
|
@ -1,3 +1,20 @@
|
||||
1998-12-11 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gthread/gthread-nspr.c, configure.in: Added new default thread
|
||||
implementation on top of the mozilla nspr library.
|
||||
|
||||
* gmem.c, gmessaged.c, gthread/gthread.c, gthread/gthread-*.c:
|
||||
Changed GStaticMutex and GStaticPrivate in gmem.c and gmessages.c
|
||||
into GMutex and GPrivate resp. to make error reporting and use of
|
||||
gmem possible in most (not all, though) gthread functions. Also
|
||||
initialized the modules via new init functions.
|
||||
|
||||
* configure.in: Fixed syntax bug in definition of type
|
||||
GStaticMutex.
|
||||
|
||||
* gthread/testgthread.c: Updated to work with nspr, but see note
|
||||
there for remaining problems.
|
||||
|
||||
1998-12-10 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gmutex.c, glib.h: Now abort, if a mutex/cond/private is
|
||||
|
@ -1,3 +1,20 @@
|
||||
1998-12-11 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gthread/gthread-nspr.c, configure.in: Added new default thread
|
||||
implementation on top of the mozilla nspr library.
|
||||
|
||||
* gmem.c, gmessaged.c, gthread/gthread.c, gthread/gthread-*.c:
|
||||
Changed GStaticMutex and GStaticPrivate in gmem.c and gmessages.c
|
||||
into GMutex and GPrivate resp. to make error reporting and use of
|
||||
gmem possible in most (not all, though) gthread functions. Also
|
||||
initialized the modules via new init functions.
|
||||
|
||||
* configure.in: Fixed syntax bug in definition of type
|
||||
GStaticMutex.
|
||||
|
||||
* gthread/testgthread.c: Updated to work with nspr, but see note
|
||||
there for remaining problems.
|
||||
|
||||
1998-12-10 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gmutex.c, glib.h: Now abort, if a mutex/cond/private is
|
||||
|
@ -1,3 +1,20 @@
|
||||
1998-12-11 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gthread/gthread-nspr.c, configure.in: Added new default thread
|
||||
implementation on top of the mozilla nspr library.
|
||||
|
||||
* gmem.c, gmessaged.c, gthread/gthread.c, gthread/gthread-*.c:
|
||||
Changed GStaticMutex and GStaticPrivate in gmem.c and gmessages.c
|
||||
into GMutex and GPrivate resp. to make error reporting and use of
|
||||
gmem possible in most (not all, though) gthread functions. Also
|
||||
initialized the modules via new init functions.
|
||||
|
||||
* configure.in: Fixed syntax bug in definition of type
|
||||
GStaticMutex.
|
||||
|
||||
* gthread/testgthread.c: Updated to work with nspr, but see note
|
||||
there for remaining problems.
|
||||
|
||||
1998-12-10 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gmutex.c, glib.h: Now abort, if a mutex/cond/private is
|
||||
|
@ -1,3 +1,20 @@
|
||||
1998-12-11 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gthread/gthread-nspr.c, configure.in: Added new default thread
|
||||
implementation on top of the mozilla nspr library.
|
||||
|
||||
* gmem.c, gmessaged.c, gthread/gthread.c, gthread/gthread-*.c:
|
||||
Changed GStaticMutex and GStaticPrivate in gmem.c and gmessages.c
|
||||
into GMutex and GPrivate resp. to make error reporting and use of
|
||||
gmem possible in most (not all, though) gthread functions. Also
|
||||
initialized the modules via new init functions.
|
||||
|
||||
* configure.in: Fixed syntax bug in definition of type
|
||||
GStaticMutex.
|
||||
|
||||
* gthread/testgthread.c: Updated to work with nspr, but see note
|
||||
there for remaining problems.
|
||||
|
||||
1998-12-10 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gmutex.c, glib.h: Now abort, if a mutex/cond/private is
|
||||
|
@ -1,3 +1,20 @@
|
||||
1998-12-11 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gthread/gthread-nspr.c, configure.in: Added new default thread
|
||||
implementation on top of the mozilla nspr library.
|
||||
|
||||
* gmem.c, gmessaged.c, gthread/gthread.c, gthread/gthread-*.c:
|
||||
Changed GStaticMutex and GStaticPrivate in gmem.c and gmessages.c
|
||||
into GMutex and GPrivate resp. to make error reporting and use of
|
||||
gmem possible in most (not all, though) gthread functions. Also
|
||||
initialized the modules via new init functions.
|
||||
|
||||
* configure.in: Fixed syntax bug in definition of type
|
||||
GStaticMutex.
|
||||
|
||||
* gthread/testgthread.c: Updated to work with nspr, but see note
|
||||
there for remaining problems.
|
||||
|
||||
1998-12-10 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gmutex.c, glib.h: Now abort, if a mutex/cond/private is
|
||||
|
@ -1,3 +1,20 @@
|
||||
1998-12-11 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gthread/gthread-nspr.c, configure.in: Added new default thread
|
||||
implementation on top of the mozilla nspr library.
|
||||
|
||||
* gmem.c, gmessaged.c, gthread/gthread.c, gthread/gthread-*.c:
|
||||
Changed GStaticMutex and GStaticPrivate in gmem.c and gmessages.c
|
||||
into GMutex and GPrivate resp. to make error reporting and use of
|
||||
gmem possible in most (not all, though) gthread functions. Also
|
||||
initialized the modules via new init functions.
|
||||
|
||||
* configure.in: Fixed syntax bug in definition of type
|
||||
GStaticMutex.
|
||||
|
||||
* gthread/testgthread.c: Updated to work with nspr, but see note
|
||||
there for remaining problems.
|
||||
|
||||
1998-12-10 Sebastian Wilhelmi <wilhelmi@ira.uka.de>
|
||||
|
||||
* gmutex.c, glib.h: Now abort, if a mutex/cond/private is
|
||||
|
12
configure.in
12
configure.in
@ -513,7 +513,7 @@ dnl ***********************
|
||||
dnl *** g_thread checks ***
|
||||
dnl ***********************
|
||||
|
||||
AC_ARG_WITH(threads, [ --with-threads=[none/posix/solaris] specify a thread implementation to use.],,)
|
||||
AC_ARG_WITH(threads, [ --with-threads=[none/posix/solaris/nspr] specify a thread implementation to use.],,)
|
||||
|
||||
dnl error and warning message
|
||||
dnl *************************
|
||||
@ -548,6 +548,7 @@ if test x"$with_threads" = x; then
|
||||
if test x"$with_threads" = x; then
|
||||
AC_CHECK_LIB(pthread,pthread_cond_init,with_threads=posix)
|
||||
AC_CHECK_LIB(pthreads,pthread_attr_init,with_threads=posix)
|
||||
AC_CHECK_LIB(nspr21,PRP_NewNakedCondVar,with_threads=nspr)
|
||||
fi
|
||||
fi
|
||||
|
||||
@ -586,6 +587,10 @@ case $with_threads in
|
||||
[solaris_mutex_init_broken=no])
|
||||
AC_MSG_RESULT($solaris_mutex_init_broken)
|
||||
;;
|
||||
nspr)
|
||||
AC_CHECK_LIB(nspr21,PRP_NewNakedCondVar,
|
||||
G_THREAD_LIBS="-lnspr21")
|
||||
;;
|
||||
none)
|
||||
;;
|
||||
*)
|
||||
@ -793,7 +798,7 @@ outfile_EOF
|
||||
else
|
||||
cat >>$outfile <<outfile_EOF
|
||||
|
||||
typedef GMutex* GStaticMutex;
|
||||
typedef struct _GMutex* GStaticMutex;
|
||||
#define G_STATIC_MUTEX_INIT NULL
|
||||
#define g_static_mutex_get_mutex(mutex) g_static_mutex_get_mutex_impl(&mutex)
|
||||
outfile_EOF
|
||||
@ -1031,6 +1036,9 @@ case $with_threads in
|
||||
fi
|
||||
g_mutex_header_file='thread.h'
|
||||
;;
|
||||
nspr)
|
||||
g_mutex_has_default=no
|
||||
;;
|
||||
*)
|
||||
g_mutex_has_default=no
|
||||
;;
|
||||
|
74
glib/gmem.c
74
glib/gmem.c
@ -53,13 +53,11 @@
|
||||
|
||||
#if defined(ENABLE_MEM_PROFILE) && defined(ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS)
|
||||
#define ENTER_MEM_CHUNK_ROUTINE() \
|
||||
g_static_private_set (allocating_for_mem_chunk, \
|
||||
g_static_private_get (allocating_for_mem_chunk) + 1, \
|
||||
NULL)
|
||||
g_static_set (allocating_for_mem_chunk, \
|
||||
g_static_get (allocating_for_mem_chunk) + 1)
|
||||
#define ENTER_MEM_CHUNK_ROUTINE() \
|
||||
g_static_private_set (allocating_for_mem_chunk, \
|
||||
g_static_private_get (allocating_for_mem_chunk) - 1, \
|
||||
NULL)
|
||||
g_static_set (allocating_for_mem_chunk, \
|
||||
g_static_get (allocating_for_mem_chunk) - 1)
|
||||
#else
|
||||
#define ENTER_MEM_CHUNK_ROUTINE()
|
||||
#define LEAVE_MEM_CHUNK_ROUTINE()
|
||||
@ -127,17 +125,19 @@ static gint g_mem_chunk_area_search (GMemArea *a,
|
||||
gchar *addr);
|
||||
|
||||
|
||||
static G_LOCK_DEFINE(mem_chunks);
|
||||
/* here we can't use StaticMutexes, as they depend upon a working
|
||||
* g_malloc, the same holds true for StaticPrivate */
|
||||
static GMutex* mem_chunks_lock = NULL;
|
||||
static GRealMemChunk *mem_chunks = NULL;
|
||||
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
static G_LOCK_DEFINE(mem_profile);
|
||||
static GMutex* mem_profile_lock;
|
||||
static gulong allocations[MEM_PROFILE_TABLE_SIZE] = { 0 };
|
||||
static gulong allocated_mem = 0;
|
||||
static gulong freed_mem = 0;
|
||||
static GStaticPrivate allocating_for_mem_chunk = G_STATIC_PRIVATE_INIT;
|
||||
static GPrivate* allocating_for_mem_chunk = NULL;
|
||||
#define IS_IN_MEM_CHUNK_ROUTINE() \
|
||||
GPOINTER_TO_UINT (g_static_private_get (allocating_for_mem_chunk))
|
||||
GPOINTER_TO_UINT (g_static_get (allocating_for_mem_chunk))
|
||||
#endif /* ENABLE_MEM_PROFILE */
|
||||
|
||||
|
||||
@ -188,7 +188,7 @@ g_malloc (gulong size)
|
||||
*t = size;
|
||||
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
g_lock(mem_profile);
|
||||
g_mutex_lock (mem_profile_lock);
|
||||
# ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
if(!IS_IN_MEM_CHUNK_ROUTINE()) {
|
||||
# endif
|
||||
@ -200,7 +200,7 @@ g_malloc (gulong size)
|
||||
# ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
}
|
||||
# endif
|
||||
g_unlock(mem_profile);
|
||||
g_mutex_unlock (mem_profile_lock);
|
||||
#endif /* ENABLE_MEM_PROFILE */
|
||||
#endif /* ENABLE_MEM_PROFILE || ENABLE_MEM_CHECK */
|
||||
|
||||
@ -253,7 +253,7 @@ g_malloc0 (gulong size)
|
||||
*t = size;
|
||||
|
||||
# ifdef ENABLE_MEM_PROFILE
|
||||
g_lock(mem_profile);
|
||||
g_mutex_lock (mem_profile_lock);
|
||||
# ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
if(!IS_IN_MEM_CHUNK_ROUTINE()) {
|
||||
# endif
|
||||
@ -265,7 +265,7 @@ g_malloc0 (gulong size)
|
||||
# ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
}
|
||||
# endif
|
||||
g_unlock(mem_profile);
|
||||
g_mutex_unlock (mem_profile_lock);
|
||||
# endif /* ENABLE_MEM_PROFILE */
|
||||
#endif /* ENABLE_MEM_PROFILE || ENABLE_MEM_CHECK */
|
||||
|
||||
@ -304,9 +304,9 @@ g_realloc (gpointer mem,
|
||||
#if defined(ENABLE_MEM_PROFILE) || defined(ENABLE_MEM_CHECK)
|
||||
t = (gulong*) ((guchar*) mem - SIZEOF_LONG);
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
g_lock (mem_profile);
|
||||
g_mutex_lock (mem_profile);
|
||||
freed_mem += *t;
|
||||
g_unlock (mem_profile);
|
||||
g_mutex_unlock (mem_profile);
|
||||
#endif /* ENABLE_MEM_PROFILE */
|
||||
mem = t;
|
||||
#endif /* ENABLE_MEM_PROFILE || ENABLE_MEM_CHECK */
|
||||
@ -341,7 +341,7 @@ g_realloc (gpointer mem,
|
||||
*t = size;
|
||||
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
g_lock(mem_profile);
|
||||
g_mutex_lock (mem_profile_lock);
|
||||
#ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
if(!IS_IN_MEM_CHUNK_ROUTINE()) {
|
||||
#endif
|
||||
@ -353,7 +353,7 @@ g_realloc (gpointer mem,
|
||||
#ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
}
|
||||
#endif
|
||||
g_unlock(mem_profile);
|
||||
g_mutex_unlock (mem_profile_lock);
|
||||
#endif /* ENABLE_MEM_PROFILE */
|
||||
#endif /* ENABLE_MEM_PROFILE || ENABLE_MEM_CHECK */
|
||||
|
||||
@ -375,9 +375,9 @@ g_free (gpointer mem)
|
||||
t = (gulong*) ((guchar*) mem - SIZEOF_LONG);
|
||||
size = *t;
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
g_lock (mem_profile);
|
||||
g_mutex_lock (mem_profile);
|
||||
freed_mem += size;
|
||||
g_unlock (mem_profile);
|
||||
g_mutex_unlock (mem_profile);
|
||||
#endif /* ENABLE_MEM_PROFILE */
|
||||
mem = t;
|
||||
#endif /* ENABLE_MEM_PROFILE || ENABLE_MEM_CHECK */
|
||||
@ -408,12 +408,12 @@ g_mem_profile (void)
|
||||
gulong local_allocated_mem;
|
||||
gulong local_freed_mem;
|
||||
|
||||
g_lock (mem_profile);
|
||||
g_mutex_lock (mem_profile);
|
||||
for (i = 0; i < (MEM_PROFILE_TABLE_SIZE - 1); i++)
|
||||
local_allocations[i] = allocations[i];
|
||||
local_allocated_mem = allocated_mem;
|
||||
local_freed_mem = freed_mem;
|
||||
g_unlock (mem_profile);
|
||||
g_mutex_unlock (mem_profile);
|
||||
|
||||
for (i = 0; i < (MEM_PROFILE_TABLE_SIZE - 1); i++)
|
||||
if (local_allocations[i] > 0)
|
||||
@ -494,13 +494,13 @@ g_mem_chunk_new (gchar *name,
|
||||
mem_chunk->area_size += mem_chunk->atom_size - (mem_chunk->area_size % mem_chunk->atom_size);
|
||||
*/
|
||||
|
||||
g_lock (mem_chunks);
|
||||
g_mutex_lock (mem_chunks_lock);
|
||||
mem_chunk->next = mem_chunks;
|
||||
mem_chunk->prev = NULL;
|
||||
if (mem_chunks)
|
||||
mem_chunks->prev = mem_chunk;
|
||||
mem_chunks = mem_chunk;
|
||||
g_unlock (mem_chunks);
|
||||
g_mutex_unlock (mem_chunks_lock);
|
||||
|
||||
LEAVE_MEM_CHUNK_ROUTINE();
|
||||
|
||||
@ -533,10 +533,10 @@ g_mem_chunk_destroy (GMemChunk *mem_chunk)
|
||||
if (rmem_chunk->prev)
|
||||
rmem_chunk->prev->next = rmem_chunk->next;
|
||||
|
||||
g_lock (mem_chunks);
|
||||
g_mutex_lock (mem_chunks_lock);
|
||||
if (rmem_chunk == mem_chunks)
|
||||
mem_chunks = mem_chunks->next;
|
||||
g_unlock (mem_chunks);
|
||||
g_mutex_unlock (mem_chunks_lock);
|
||||
|
||||
if (rmem_chunk->type == G_ALLOC_AND_FREE)
|
||||
g_tree_destroy (rmem_chunk->mem_tree);
|
||||
@ -864,20 +864,20 @@ g_mem_chunk_info (void)
|
||||
gint count;
|
||||
|
||||
count = 0;
|
||||
g_lock (mem_chunks);
|
||||
g_mutex_lock (mem_chunks_lock);
|
||||
mem_chunk = mem_chunks;
|
||||
while (mem_chunk)
|
||||
{
|
||||
count += 1;
|
||||
mem_chunk = mem_chunk->next;
|
||||
}
|
||||
g_unlock (mem_chunks);
|
||||
g_mutex_unlock (mem_chunks_lock);
|
||||
|
||||
g_log (g_log_domain_glib, G_LOG_LEVEL_INFO, "%d mem chunks\n", count);
|
||||
|
||||
g_lock (mem_chunks);
|
||||
g_mutex_lock (mem_chunks_lock);
|
||||
mem_chunk = mem_chunks;
|
||||
g_unlock (mem_chunks);
|
||||
g_mutex_unlock (mem_chunks_lock);
|
||||
|
||||
while (mem_chunk)
|
||||
{
|
||||
@ -891,9 +891,9 @@ g_blow_chunks (void)
|
||||
{
|
||||
GRealMemChunk *mem_chunk;
|
||||
|
||||
g_lock (mem_chunks);
|
||||
g_mutex_lock (mem_chunks_lock);
|
||||
mem_chunk = mem_chunks;
|
||||
g_unlock (mem_chunks);
|
||||
g_mutex_unlock (mem_chunks_lock);
|
||||
while (mem_chunk)
|
||||
{
|
||||
g_mem_chunk_clean ((GMemChunk*) mem_chunk);
|
||||
@ -985,3 +985,13 @@ g_allocator_free (GAllocator *allocator)
|
||||
|
||||
g_free (allocator);
|
||||
}
|
||||
|
||||
void
|
||||
g_mem_init (void)
|
||||
{
|
||||
mem_chunks_lock = g_mutex_new();
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
mem_profile_lock = g_mutex_new();
|
||||
allocating_for_mem_chunk = g_private_new(NULL);
|
||||
#endif
|
||||
}
|
||||
|
@ -72,7 +72,7 @@ struct _GLogHandler
|
||||
|
||||
/* --- variables --- */
|
||||
|
||||
static G_LOCK_DEFINE(g_messages_global);
|
||||
static GMutex* g_messages_lock = NULL;
|
||||
|
||||
const gchar *g_log_domain_glib = "GLib";
|
||||
static GLogDomain *g_log_domains = NULL;
|
||||
@ -83,7 +83,7 @@ static GErrorFunc glib_error_func = NULL;
|
||||
static GWarningFunc glib_warning_func = NULL;
|
||||
static GPrintFunc glib_message_func = NULL;
|
||||
|
||||
static GStaticPrivate g_log_depth = G_STATIC_PRIVATE_INIT;
|
||||
static GPrivate* g_log_depth = NULL;
|
||||
|
||||
|
||||
/* --- functions --- */
|
||||
@ -92,18 +92,18 @@ g_log_find_domain (const gchar *log_domain)
|
||||
{
|
||||
register GLogDomain *domain;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
domain = g_log_domains;
|
||||
while (domain)
|
||||
{
|
||||
if (strcmp (domain->log_domain, log_domain) == 0)
|
||||
{
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
return domain;
|
||||
}
|
||||
domain = domain->next;
|
||||
}
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@ -117,10 +117,10 @@ g_log_domain_new (const gchar *log_domain)
|
||||
domain->fatal_mask = G_LOG_FATAL_MASK;
|
||||
domain->handlers = NULL;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
domain->next = g_log_domains;
|
||||
g_log_domains = domain;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return domain;
|
||||
}
|
||||
@ -135,7 +135,7 @@ g_log_domain_check_free (GLogDomain *domain)
|
||||
|
||||
last = NULL;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
work = g_log_domains;
|
||||
while (work)
|
||||
{
|
||||
@ -151,7 +151,7 @@ g_log_domain_check_free (GLogDomain *domain)
|
||||
}
|
||||
work = work->next;
|
||||
}
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
}
|
||||
}
|
||||
|
||||
@ -190,10 +190,10 @@ g_log_set_always_fatal (GLogLevelFlags fatal_mask)
|
||||
/* remove bogus flag */
|
||||
fatal_mask &= ~G_LOG_FLAG_FATAL;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_mask = g_log_always_fatal;
|
||||
g_log_always_fatal = fatal_mask;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_mask;
|
||||
}
|
||||
@ -245,9 +245,9 @@ g_log_set_handler (const gchar *log_domain,
|
||||
domain = g_log_domain_new (log_domain);
|
||||
|
||||
handler = g_new (GLogHandler, 1);
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
handler->id = ++handler_id;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
handler->log_level = log_levels;
|
||||
handler->log_func = log_func;
|
||||
handler->data = user_data;
|
||||
@ -335,7 +335,7 @@ g_logv (const gchar *log_domain,
|
||||
test_level = 1 << i;
|
||||
if (log_level & test_level)
|
||||
{
|
||||
guint depth = GPOINTER_TO_UINT (g_static_private_get (&g_log_depth));
|
||||
guint depth = GPOINTER_TO_UINT (g_private_get (g_log_depth));
|
||||
GLogDomain *domain;
|
||||
GLogFunc log_func;
|
||||
gpointer data = NULL;
|
||||
@ -346,13 +346,13 @@ g_logv (const gchar *log_domain,
|
||||
test_level |= G_LOG_FLAG_RECURSION;
|
||||
|
||||
depth++;
|
||||
g_static_private_set (&g_log_depth, GUINT_TO_POINTER (depth), NULL);
|
||||
g_private_set (g_log_depth, GUINT_TO_POINTER (depth));
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
if ((((domain ? domain->fatal_mask : G_LOG_FATAL_MASK) |
|
||||
g_log_always_fatal) & test_level) != 0)
|
||||
test_level |= G_LOG_FLAG_FATAL;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
log_func = g_log_domain_get_handler (domain, test_level, &data);
|
||||
log_func (log_domain, test_level, buffer, data);
|
||||
@ -363,7 +363,7 @@ g_logv (const gchar *log_domain,
|
||||
abort ();
|
||||
|
||||
depth--;
|
||||
g_static_private_set (&g_log_depth, GUINT_TO_POINTER (depth), NULL);
|
||||
g_private_set (g_log_depth, GUINT_TO_POINTER (depth));
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -414,11 +414,11 @@ g_log_default_handler (const gchar *log_domain,
|
||||
fd = (log_level >= G_LOG_LEVEL_MESSAGE) ? 1 : 2;
|
||||
#endif
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
local_glib_error_func = glib_error_func;
|
||||
local_glib_warning_func = glib_warning_func;
|
||||
local_glib_message_func = glib_message_func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
switch (log_level)
|
||||
{
|
||||
@ -593,10 +593,10 @@ g_set_print_handler (GPrintFunc func)
|
||||
{
|
||||
GPrintFunc old_print_func;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_print_func = glib_print_func;
|
||||
glib_print_func = func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_print_func;
|
||||
}
|
||||
@ -615,9 +615,9 @@ g_print (const gchar *format,
|
||||
string = g_strdup_vprintf (format, args);
|
||||
va_end (args);
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
local_glib_print_func = glib_print_func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
if (local_glib_print_func)
|
||||
local_glib_print_func (string);
|
||||
@ -634,10 +634,10 @@ g_set_printerr_handler (GPrintFunc func)
|
||||
{
|
||||
GPrintFunc old_printerr_func;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_printerr_func = glib_printerr_func;
|
||||
glib_printerr_func = func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_printerr_func;
|
||||
}
|
||||
@ -656,9 +656,9 @@ g_printerr (const gchar *format,
|
||||
string = g_strdup_vprintf (format, args);
|
||||
va_end (args);
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
local_glib_printerr_func = glib_printerr_func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
if (local_glib_printerr_func)
|
||||
local_glib_printerr_func (string);
|
||||
@ -676,10 +676,10 @@ g_set_error_handler (GErrorFunc func)
|
||||
{
|
||||
GErrorFunc old_error_func;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_error_func = glib_error_func;
|
||||
glib_error_func = func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_error_func;
|
||||
}
|
||||
@ -690,10 +690,10 @@ g_set_warning_handler (GWarningFunc func)
|
||||
{
|
||||
GWarningFunc old_warning_func;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_warning_func = glib_warning_func;
|
||||
glib_warning_func = func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_warning_func;
|
||||
}
|
||||
@ -704,10 +704,17 @@ g_set_message_handler (GPrintFunc func)
|
||||
{
|
||||
GPrintFunc old_message_func;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_message_func = glib_message_func;
|
||||
glib_message_func = func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_message_func;
|
||||
}
|
||||
|
||||
void
|
||||
g_messages_init (void)
|
||||
{
|
||||
g_messages_lock = g_mutex_new();
|
||||
g_log_depth = g_private_new(NULL);
|
||||
}
|
||||
|
74
gmem.c
74
gmem.c
@ -53,13 +53,11 @@
|
||||
|
||||
#if defined(ENABLE_MEM_PROFILE) && defined(ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS)
|
||||
#define ENTER_MEM_CHUNK_ROUTINE() \
|
||||
g_static_private_set (allocating_for_mem_chunk, \
|
||||
g_static_private_get (allocating_for_mem_chunk) + 1, \
|
||||
NULL)
|
||||
g_static_set (allocating_for_mem_chunk, \
|
||||
g_static_get (allocating_for_mem_chunk) + 1)
|
||||
#define ENTER_MEM_CHUNK_ROUTINE() \
|
||||
g_static_private_set (allocating_for_mem_chunk, \
|
||||
g_static_private_get (allocating_for_mem_chunk) - 1, \
|
||||
NULL)
|
||||
g_static_set (allocating_for_mem_chunk, \
|
||||
g_static_get (allocating_for_mem_chunk) - 1)
|
||||
#else
|
||||
#define ENTER_MEM_CHUNK_ROUTINE()
|
||||
#define LEAVE_MEM_CHUNK_ROUTINE()
|
||||
@ -127,17 +125,19 @@ static gint g_mem_chunk_area_search (GMemArea *a,
|
||||
gchar *addr);
|
||||
|
||||
|
||||
static G_LOCK_DEFINE(mem_chunks);
|
||||
/* here we can't use StaticMutexes, as they depend upon a working
|
||||
* g_malloc, the same holds true for StaticPrivate */
|
||||
static GMutex* mem_chunks_lock = NULL;
|
||||
static GRealMemChunk *mem_chunks = NULL;
|
||||
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
static G_LOCK_DEFINE(mem_profile);
|
||||
static GMutex* mem_profile_lock;
|
||||
static gulong allocations[MEM_PROFILE_TABLE_SIZE] = { 0 };
|
||||
static gulong allocated_mem = 0;
|
||||
static gulong freed_mem = 0;
|
||||
static GStaticPrivate allocating_for_mem_chunk = G_STATIC_PRIVATE_INIT;
|
||||
static GPrivate* allocating_for_mem_chunk = NULL;
|
||||
#define IS_IN_MEM_CHUNK_ROUTINE() \
|
||||
GPOINTER_TO_UINT (g_static_private_get (allocating_for_mem_chunk))
|
||||
GPOINTER_TO_UINT (g_static_get (allocating_for_mem_chunk))
|
||||
#endif /* ENABLE_MEM_PROFILE */
|
||||
|
||||
|
||||
@ -188,7 +188,7 @@ g_malloc (gulong size)
|
||||
*t = size;
|
||||
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
g_lock(mem_profile);
|
||||
g_mutex_lock (mem_profile_lock);
|
||||
# ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
if(!IS_IN_MEM_CHUNK_ROUTINE()) {
|
||||
# endif
|
||||
@ -200,7 +200,7 @@ g_malloc (gulong size)
|
||||
# ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
}
|
||||
# endif
|
||||
g_unlock(mem_profile);
|
||||
g_mutex_unlock (mem_profile_lock);
|
||||
#endif /* ENABLE_MEM_PROFILE */
|
||||
#endif /* ENABLE_MEM_PROFILE || ENABLE_MEM_CHECK */
|
||||
|
||||
@ -253,7 +253,7 @@ g_malloc0 (gulong size)
|
||||
*t = size;
|
||||
|
||||
# ifdef ENABLE_MEM_PROFILE
|
||||
g_lock(mem_profile);
|
||||
g_mutex_lock (mem_profile_lock);
|
||||
# ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
if(!IS_IN_MEM_CHUNK_ROUTINE()) {
|
||||
# endif
|
||||
@ -265,7 +265,7 @@ g_malloc0 (gulong size)
|
||||
# ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
}
|
||||
# endif
|
||||
g_unlock(mem_profile);
|
||||
g_mutex_unlock (mem_profile_lock);
|
||||
# endif /* ENABLE_MEM_PROFILE */
|
||||
#endif /* ENABLE_MEM_PROFILE || ENABLE_MEM_CHECK */
|
||||
|
||||
@ -304,9 +304,9 @@ g_realloc (gpointer mem,
|
||||
#if defined(ENABLE_MEM_PROFILE) || defined(ENABLE_MEM_CHECK)
|
||||
t = (gulong*) ((guchar*) mem - SIZEOF_LONG);
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
g_lock (mem_profile);
|
||||
g_mutex_lock (mem_profile);
|
||||
freed_mem += *t;
|
||||
g_unlock (mem_profile);
|
||||
g_mutex_unlock (mem_profile);
|
||||
#endif /* ENABLE_MEM_PROFILE */
|
||||
mem = t;
|
||||
#endif /* ENABLE_MEM_PROFILE || ENABLE_MEM_CHECK */
|
||||
@ -341,7 +341,7 @@ g_realloc (gpointer mem,
|
||||
*t = size;
|
||||
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
g_lock(mem_profile);
|
||||
g_mutex_lock (mem_profile_lock);
|
||||
#ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
if(!IS_IN_MEM_CHUNK_ROUTINE()) {
|
||||
#endif
|
||||
@ -353,7 +353,7 @@ g_realloc (gpointer mem,
|
||||
#ifdef ENABLE_MEM_PROFILE_EXCLUDES_MEM_CHUNKS
|
||||
}
|
||||
#endif
|
||||
g_unlock(mem_profile);
|
||||
g_mutex_unlock (mem_profile_lock);
|
||||
#endif /* ENABLE_MEM_PROFILE */
|
||||
#endif /* ENABLE_MEM_PROFILE || ENABLE_MEM_CHECK */
|
||||
|
||||
@ -375,9 +375,9 @@ g_free (gpointer mem)
|
||||
t = (gulong*) ((guchar*) mem - SIZEOF_LONG);
|
||||
size = *t;
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
g_lock (mem_profile);
|
||||
g_mutex_lock (mem_profile);
|
||||
freed_mem += size;
|
||||
g_unlock (mem_profile);
|
||||
g_mutex_unlock (mem_profile);
|
||||
#endif /* ENABLE_MEM_PROFILE */
|
||||
mem = t;
|
||||
#endif /* ENABLE_MEM_PROFILE || ENABLE_MEM_CHECK */
|
||||
@ -408,12 +408,12 @@ g_mem_profile (void)
|
||||
gulong local_allocated_mem;
|
||||
gulong local_freed_mem;
|
||||
|
||||
g_lock (mem_profile);
|
||||
g_mutex_lock (mem_profile);
|
||||
for (i = 0; i < (MEM_PROFILE_TABLE_SIZE - 1); i++)
|
||||
local_allocations[i] = allocations[i];
|
||||
local_allocated_mem = allocated_mem;
|
||||
local_freed_mem = freed_mem;
|
||||
g_unlock (mem_profile);
|
||||
g_mutex_unlock (mem_profile);
|
||||
|
||||
for (i = 0; i < (MEM_PROFILE_TABLE_SIZE - 1); i++)
|
||||
if (local_allocations[i] > 0)
|
||||
@ -494,13 +494,13 @@ g_mem_chunk_new (gchar *name,
|
||||
mem_chunk->area_size += mem_chunk->atom_size - (mem_chunk->area_size % mem_chunk->atom_size);
|
||||
*/
|
||||
|
||||
g_lock (mem_chunks);
|
||||
g_mutex_lock (mem_chunks_lock);
|
||||
mem_chunk->next = mem_chunks;
|
||||
mem_chunk->prev = NULL;
|
||||
if (mem_chunks)
|
||||
mem_chunks->prev = mem_chunk;
|
||||
mem_chunks = mem_chunk;
|
||||
g_unlock (mem_chunks);
|
||||
g_mutex_unlock (mem_chunks_lock);
|
||||
|
||||
LEAVE_MEM_CHUNK_ROUTINE();
|
||||
|
||||
@ -533,10 +533,10 @@ g_mem_chunk_destroy (GMemChunk *mem_chunk)
|
||||
if (rmem_chunk->prev)
|
||||
rmem_chunk->prev->next = rmem_chunk->next;
|
||||
|
||||
g_lock (mem_chunks);
|
||||
g_mutex_lock (mem_chunks_lock);
|
||||
if (rmem_chunk == mem_chunks)
|
||||
mem_chunks = mem_chunks->next;
|
||||
g_unlock (mem_chunks);
|
||||
g_mutex_unlock (mem_chunks_lock);
|
||||
|
||||
if (rmem_chunk->type == G_ALLOC_AND_FREE)
|
||||
g_tree_destroy (rmem_chunk->mem_tree);
|
||||
@ -864,20 +864,20 @@ g_mem_chunk_info (void)
|
||||
gint count;
|
||||
|
||||
count = 0;
|
||||
g_lock (mem_chunks);
|
||||
g_mutex_lock (mem_chunks_lock);
|
||||
mem_chunk = mem_chunks;
|
||||
while (mem_chunk)
|
||||
{
|
||||
count += 1;
|
||||
mem_chunk = mem_chunk->next;
|
||||
}
|
||||
g_unlock (mem_chunks);
|
||||
g_mutex_unlock (mem_chunks_lock);
|
||||
|
||||
g_log (g_log_domain_glib, G_LOG_LEVEL_INFO, "%d mem chunks\n", count);
|
||||
|
||||
g_lock (mem_chunks);
|
||||
g_mutex_lock (mem_chunks_lock);
|
||||
mem_chunk = mem_chunks;
|
||||
g_unlock (mem_chunks);
|
||||
g_mutex_unlock (mem_chunks_lock);
|
||||
|
||||
while (mem_chunk)
|
||||
{
|
||||
@ -891,9 +891,9 @@ g_blow_chunks (void)
|
||||
{
|
||||
GRealMemChunk *mem_chunk;
|
||||
|
||||
g_lock (mem_chunks);
|
||||
g_mutex_lock (mem_chunks_lock);
|
||||
mem_chunk = mem_chunks;
|
||||
g_unlock (mem_chunks);
|
||||
g_mutex_unlock (mem_chunks_lock);
|
||||
while (mem_chunk)
|
||||
{
|
||||
g_mem_chunk_clean ((GMemChunk*) mem_chunk);
|
||||
@ -985,3 +985,13 @@ g_allocator_free (GAllocator *allocator)
|
||||
|
||||
g_free (allocator);
|
||||
}
|
||||
|
||||
void
|
||||
g_mem_init (void)
|
||||
{
|
||||
mem_chunks_lock = g_mutex_new();
|
||||
#ifdef ENABLE_MEM_PROFILE
|
||||
mem_profile_lock = g_mutex_new();
|
||||
allocating_for_mem_chunk = g_private_new(NULL);
|
||||
#endif
|
||||
}
|
||||
|
75
gmessages.c
75
gmessages.c
@ -72,7 +72,7 @@ struct _GLogHandler
|
||||
|
||||
/* --- variables --- */
|
||||
|
||||
static G_LOCK_DEFINE(g_messages_global);
|
||||
static GMutex* g_messages_lock = NULL;
|
||||
|
||||
const gchar *g_log_domain_glib = "GLib";
|
||||
static GLogDomain *g_log_domains = NULL;
|
||||
@ -83,7 +83,7 @@ static GErrorFunc glib_error_func = NULL;
|
||||
static GWarningFunc glib_warning_func = NULL;
|
||||
static GPrintFunc glib_message_func = NULL;
|
||||
|
||||
static GStaticPrivate g_log_depth = G_STATIC_PRIVATE_INIT;
|
||||
static GPrivate* g_log_depth = NULL;
|
||||
|
||||
|
||||
/* --- functions --- */
|
||||
@ -92,18 +92,18 @@ g_log_find_domain (const gchar *log_domain)
|
||||
{
|
||||
register GLogDomain *domain;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
domain = g_log_domains;
|
||||
while (domain)
|
||||
{
|
||||
if (strcmp (domain->log_domain, log_domain) == 0)
|
||||
{
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
return domain;
|
||||
}
|
||||
domain = domain->next;
|
||||
}
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@ -117,10 +117,10 @@ g_log_domain_new (const gchar *log_domain)
|
||||
domain->fatal_mask = G_LOG_FATAL_MASK;
|
||||
domain->handlers = NULL;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
domain->next = g_log_domains;
|
||||
g_log_domains = domain;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return domain;
|
||||
}
|
||||
@ -135,7 +135,7 @@ g_log_domain_check_free (GLogDomain *domain)
|
||||
|
||||
last = NULL;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
work = g_log_domains;
|
||||
while (work)
|
||||
{
|
||||
@ -151,7 +151,7 @@ g_log_domain_check_free (GLogDomain *domain)
|
||||
}
|
||||
work = work->next;
|
||||
}
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
}
|
||||
}
|
||||
|
||||
@ -190,10 +190,10 @@ g_log_set_always_fatal (GLogLevelFlags fatal_mask)
|
||||
/* remove bogus flag */
|
||||
fatal_mask &= ~G_LOG_FLAG_FATAL;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_mask = g_log_always_fatal;
|
||||
g_log_always_fatal = fatal_mask;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_mask;
|
||||
}
|
||||
@ -245,9 +245,9 @@ g_log_set_handler (const gchar *log_domain,
|
||||
domain = g_log_domain_new (log_domain);
|
||||
|
||||
handler = g_new (GLogHandler, 1);
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
handler->id = ++handler_id;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
handler->log_level = log_levels;
|
||||
handler->log_func = log_func;
|
||||
handler->data = user_data;
|
||||
@ -335,7 +335,7 @@ g_logv (const gchar *log_domain,
|
||||
test_level = 1 << i;
|
||||
if (log_level & test_level)
|
||||
{
|
||||
guint depth = GPOINTER_TO_UINT (g_static_private_get (&g_log_depth));
|
||||
guint depth = GPOINTER_TO_UINT (g_private_get (g_log_depth));
|
||||
GLogDomain *domain;
|
||||
GLogFunc log_func;
|
||||
gpointer data = NULL;
|
||||
@ -346,13 +346,13 @@ g_logv (const gchar *log_domain,
|
||||
test_level |= G_LOG_FLAG_RECURSION;
|
||||
|
||||
depth++;
|
||||
g_static_private_set (&g_log_depth, GUINT_TO_POINTER (depth), NULL);
|
||||
g_private_set (g_log_depth, GUINT_TO_POINTER (depth));
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
if ((((domain ? domain->fatal_mask : G_LOG_FATAL_MASK) |
|
||||
g_log_always_fatal) & test_level) != 0)
|
||||
test_level |= G_LOG_FLAG_FATAL;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
log_func = g_log_domain_get_handler (domain, test_level, &data);
|
||||
log_func (log_domain, test_level, buffer, data);
|
||||
@ -363,7 +363,7 @@ g_logv (const gchar *log_domain,
|
||||
abort ();
|
||||
|
||||
depth--;
|
||||
g_static_private_set (&g_log_depth, GUINT_TO_POINTER (depth), NULL);
|
||||
g_private_set (g_log_depth, GUINT_TO_POINTER (depth));
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -414,11 +414,11 @@ g_log_default_handler (const gchar *log_domain,
|
||||
fd = (log_level >= G_LOG_LEVEL_MESSAGE) ? 1 : 2;
|
||||
#endif
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
local_glib_error_func = glib_error_func;
|
||||
local_glib_warning_func = glib_warning_func;
|
||||
local_glib_message_func = glib_message_func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
switch (log_level)
|
||||
{
|
||||
@ -593,10 +593,10 @@ g_set_print_handler (GPrintFunc func)
|
||||
{
|
||||
GPrintFunc old_print_func;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_print_func = glib_print_func;
|
||||
glib_print_func = func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_print_func;
|
||||
}
|
||||
@ -615,9 +615,9 @@ g_print (const gchar *format,
|
||||
string = g_strdup_vprintf (format, args);
|
||||
va_end (args);
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
local_glib_print_func = glib_print_func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
if (local_glib_print_func)
|
||||
local_glib_print_func (string);
|
||||
@ -634,10 +634,10 @@ g_set_printerr_handler (GPrintFunc func)
|
||||
{
|
||||
GPrintFunc old_printerr_func;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_printerr_func = glib_printerr_func;
|
||||
glib_printerr_func = func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_printerr_func;
|
||||
}
|
||||
@ -656,9 +656,9 @@ g_printerr (const gchar *format,
|
||||
string = g_strdup_vprintf (format, args);
|
||||
va_end (args);
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
local_glib_printerr_func = glib_printerr_func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
if (local_glib_printerr_func)
|
||||
local_glib_printerr_func (string);
|
||||
@ -676,10 +676,10 @@ g_set_error_handler (GErrorFunc func)
|
||||
{
|
||||
GErrorFunc old_error_func;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_error_func = glib_error_func;
|
||||
glib_error_func = func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_error_func;
|
||||
}
|
||||
@ -690,10 +690,10 @@ g_set_warning_handler (GWarningFunc func)
|
||||
{
|
||||
GWarningFunc old_warning_func;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_warning_func = glib_warning_func;
|
||||
glib_warning_func = func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_warning_func;
|
||||
}
|
||||
@ -704,10 +704,17 @@ g_set_message_handler (GPrintFunc func)
|
||||
{
|
||||
GPrintFunc old_message_func;
|
||||
|
||||
g_lock (g_messages_global);
|
||||
g_mutex_lock (g_messages_lock);
|
||||
old_message_func = glib_message_func;
|
||||
glib_message_func = func;
|
||||
g_unlock (g_messages_global);
|
||||
g_mutex_unlock (g_messages_lock);
|
||||
|
||||
return old_message_func;
|
||||
}
|
||||
|
||||
void
|
||||
g_messages_init (void)
|
||||
{
|
||||
g_messages_lock = g_mutex_new();
|
||||
g_log_depth = g_private_new(NULL);
|
||||
}
|
||||
|
6
gmutex.c
6
gmutex.c
@ -75,7 +75,11 @@ g_mutex_init (void)
|
||||
the data, that it set before calling g_thread_init */
|
||||
gpointer private_old = g_thread_specific_private;
|
||||
g_thread_specific_private = g_private_new (g_static_private_free_data);
|
||||
g_private_set (g_thread_specific_private, private_old);
|
||||
|
||||
/* we can not use g_private_set here, as g_thread_supported is not
|
||||
yet set TRUE, whereas the private_set function is already set. */
|
||||
g_thread_functions_for_glib_use.private_set (g_thread_specific_private,
|
||||
private_old);
|
||||
|
||||
g_mutex_protect_static_mutex_allocation = g_mutex_new();
|
||||
g_thread_specific_mutex = g_mutex_new();
|
||||
|
@ -39,46 +39,46 @@
|
||||
if( error ) { posix_print_error( what, error ); } \
|
||||
}G_STMT_END
|
||||
|
||||
static GMutex*
|
||||
static GMutex *
|
||||
g_mutex_new_posix_impl (void)
|
||||
{
|
||||
/* we can not use g_new and friends, as they might use mutexes by
|
||||
themself */
|
||||
GMutex* result = malloc(sizeof(pthread_mutex_t));
|
||||
posix_check_for_error( pthread_mutex_init( (pthread_mutex_t*)result,
|
||||
NULL ) );
|
||||
GMutex *result = (GMutex *) g_new (pthread_mutex_t, 1);
|
||||
posix_check_for_error (pthread_mutex_init ((pthread_mutex_t *) result, NULL));
|
||||
return result;
|
||||
}
|
||||
|
||||
static void
|
||||
g_mutex_free_posix_impl (GMutex* mutex)
|
||||
g_mutex_free_posix_impl (GMutex * mutex)
|
||||
{
|
||||
posix_check_for_error( pthread_mutex_destroy((pthread_mutex_t*)mutex) );
|
||||
posix_check_for_error (pthread_mutex_destroy ((pthread_mutex_t *) mutex));
|
||||
free (mutex);
|
||||
}
|
||||
|
||||
/* NOTE: the functions g_mutex_lock and g_mutex_unlock may not use
|
||||
functions from gmem.c and gmessages.c; */
|
||||
|
||||
/* pthread_mutex_lock, pthread_mutex_unlock can be taken directly, as
|
||||
signature and semantic are right, but without error check then!!!!,
|
||||
we might want to change this therfore. */
|
||||
we might want to change this therefore. */
|
||||
|
||||
static gboolean
|
||||
g_mutex_trylock_posix_impl (GMutex* mutex)
|
||||
g_mutex_trylock_posix_impl (GMutex * mutex)
|
||||
{
|
||||
int result;
|
||||
result = pthread_mutex_trylock((pthread_mutex_t*)mutex);
|
||||
if( result == EBUSY )
|
||||
{
|
||||
|
||||
result = pthread_mutex_trylock ((pthread_mutex_t *) mutex);
|
||||
if (result != EBUSY)
|
||||
return FALSE;
|
||||
}
|
||||
posix_check_for_error( result );
|
||||
|
||||
posix_check_for_error (result);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static GCond*
|
||||
static GCond *
|
||||
g_cond_new_posix_impl (void)
|
||||
{
|
||||
GCond* result = (GCond*) g_new0 (pthread_cond_t, 1);
|
||||
posix_check_for_error( pthread_cond_init( (pthread_cond_t*)result, NULL ) );
|
||||
GCond *result = (GCond *) g_new (pthread_cond_t, 1);
|
||||
posix_check_for_error (pthread_cond_init ((pthread_cond_t *) result, NULL));
|
||||
return result;
|
||||
}
|
||||
|
||||
@ -91,9 +91,9 @@ g_cond_new_posix_impl (void)
|
||||
#define G_NANOSEC 1000000000
|
||||
|
||||
static gboolean
|
||||
g_cond_timed_wait_posix_impl (GCond* cond,
|
||||
GMutex* entered_mutex,
|
||||
GTimeVal* abs_time)
|
||||
g_cond_timed_wait_posix_impl (GCond * cond,
|
||||
GMutex * entered_mutex,
|
||||
GTimeVal * abs_time)
|
||||
{
|
||||
int result;
|
||||
struct timespec end_time;
|
||||
@ -104,75 +104,73 @@ g_cond_timed_wait_posix_impl (GCond* cond,
|
||||
|
||||
if (!abs_time)
|
||||
{
|
||||
g_cond_wait(cond, entered_mutex);
|
||||
g_cond_wait (cond, entered_mutex);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
end_time.tv_sec = abs_time->tv_sec;
|
||||
end_time.tv_nsec = abs_time->tv_usec * (G_NANOSEC / G_MICROSEC);
|
||||
g_assert (end_time.tv_nsec < G_NANOSEC);
|
||||
result = pthread_cond_timedwait ((pthread_cond_t*)cond,
|
||||
(pthread_mutex_t*)entered_mutex,
|
||||
result = pthread_cond_timedwait ((pthread_cond_t *) cond,
|
||||
(pthread_mutex_t *) entered_mutex,
|
||||
&end_time);
|
||||
timed_out = ( result == ETIMEDOUT );
|
||||
timed_out = (result == ETIMEDOUT);
|
||||
if (!timed_out)
|
||||
posix_check_for_error (result);
|
||||
return !timed_out;
|
||||
}
|
||||
|
||||
static void
|
||||
g_cond_free_posix_impl(GCond* cond)
|
||||
g_cond_free_posix_impl (GCond * cond)
|
||||
{
|
||||
posix_check_for_error (pthread_cond_destroy((pthread_cond_t*)cond));
|
||||
posix_check_for_error (pthread_cond_destroy ((pthread_cond_t *) cond));
|
||||
g_free (cond);
|
||||
}
|
||||
|
||||
static GPrivate*
|
||||
g_private_new_posix_impl(GDestroyNotify destructor)
|
||||
static GPrivate *
|
||||
g_private_new_posix_impl (GDestroyNotify destructor)
|
||||
{
|
||||
/* we can not use g_new and friends, as they might use mutexes by
|
||||
themself */
|
||||
GPrivate* result = malloc( sizeof(pthread_key_t) );
|
||||
/* FIXME: we shouldn't use g_log here actually */
|
||||
posix_check_for_error( pthread_key_create( (pthread_key_t*)result,
|
||||
destructor) );
|
||||
GPrivate *result = (GPrivate *) g_new (pthread_key_t, 1);
|
||||
posix_check_for_error (pthread_key_create ((pthread_key_t *) result,
|
||||
destructor));
|
||||
return result;
|
||||
}
|
||||
|
||||
void
|
||||
g_private_set_posix_impl(GPrivate* private, gpointer value)
|
||||
{
|
||||
g_return_if_fail (private != NULL);
|
||||
/* NOTE: the functions g_private_get and g_private_set may not use
|
||||
functions from gmem.c and gmessages.c */
|
||||
|
||||
/* FIXME: we shouldn't use g_log here actually */
|
||||
posix_check_for_error( pthread_setspecific(*(pthread_key_t*)private,
|
||||
value) );
|
||||
static void
|
||||
g_private_set_posix_impl (GPrivate * private, gpointer value)
|
||||
{
|
||||
if (!private)
|
||||
return;
|
||||
|
||||
pthread_setspecific (*(pthread_key_t *) private, value);
|
||||
}
|
||||
|
||||
gpointer
|
||||
g_private_get_posix_impl(GPrivate* private)
|
||||
static gpointer
|
||||
g_private_get_posix_impl (GPrivate * private)
|
||||
{
|
||||
g_return_val_if_fail (private != NULL, NULL);
|
||||
if (!private)
|
||||
return NULL;
|
||||
|
||||
/* FIXME: we shouldn't use g_log here actually */
|
||||
return pthread_getspecific(*(pthread_key_t*)private );
|
||||
return pthread_getspecific (*(pthread_key_t *) private);
|
||||
}
|
||||
|
||||
static GThreadFunctions
|
||||
g_thread_functions_for_glib_use_default = {
|
||||
static GThreadFunctions g_thread_functions_for_glib_use_default =
|
||||
{
|
||||
g_mutex_new_posix_impl,
|
||||
(void(*)(GMutex*))pthread_mutex_lock,
|
||||
(void (*)(GMutex *)) pthread_mutex_lock,
|
||||
g_mutex_trylock_posix_impl,
|
||||
(void(*)(GMutex*))pthread_mutex_unlock,
|
||||
(void (*)(GMutex *)) pthread_mutex_unlock,
|
||||
g_mutex_free_posix_impl,
|
||||
g_cond_new_posix_impl,
|
||||
(void(*)(GCond*))pthread_cond_signal,
|
||||
(void(*)(GCond*))pthread_cond_broadcast,
|
||||
(void(*)(GCond*,GMutex*))pthread_cond_wait,
|
||||
(void (*)(GCond *)) pthread_cond_signal,
|
||||
(void (*)(GCond *)) pthread_cond_broadcast,
|
||||
(void (*)(GCond *, GMutex *)) pthread_cond_wait,
|
||||
g_cond_timed_wait_posix_impl,
|
||||
g_cond_free_posix_impl,
|
||||
g_private_new_posix_impl,
|
||||
g_private_get_posix_impl,
|
||||
g_private_set_posix_impl
|
||||
};
|
||||
|
||||
|
@ -29,30 +29,20 @@
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
|
||||
/* we can't use g_log in the g_thread functions, because g_log depends
|
||||
on these functions to work properly, we even should not use
|
||||
g_strerror (might be a FIXME) */
|
||||
|
||||
#define solaris_error_args( name, num ) \
|
||||
"Gthread: Fatal error in file %s: line %d (%s): error %s during %s\n", \
|
||||
#define solaris_print_error( name, num ) \
|
||||
g_error( "file %s: line %d (%s): error %s during %s", \
|
||||
__FILE__, __LINE__, G_GNUC_PRETTY_FUNCTION, \
|
||||
g_strerror((num)), #name
|
||||
g_strerror((num)), #name )
|
||||
|
||||
#define solaris_check_for_error( what ) G_STMT_START{ \
|
||||
int error = (what); \
|
||||
if( error ) { \
|
||||
fprintf(stderr, solaris_error_args( what, error ) ); \
|
||||
exit(1); \
|
||||
} \
|
||||
if( error ) { solaris_print_error( what, error ); } \
|
||||
}G_STMT_END
|
||||
|
||||
static GMutex *
|
||||
g_mutex_new_solaris_impl (void)
|
||||
{
|
||||
/* we can not use g_new and friends, as they might use mutexes by
|
||||
themself */
|
||||
GMutex *result = malloc (sizeof (mutex_t));
|
||||
solaris_check_for_error (result?NULL:ENOMEM);
|
||||
GMutex *result = (GMutex *) g_new (mutex_t, 1);
|
||||
solaris_check_for_error (mutex_init ((mutex_t *) result, USYNC_PROCESS, 0));
|
||||
return result;
|
||||
}
|
||||
@ -64,6 +54,9 @@ g_mutex_free_solaris_impl (GMutex * mutex)
|
||||
free (mutex);
|
||||
}
|
||||
|
||||
/* NOTE: the functions g_mutex_lock and g_mutex_unlock may not use
|
||||
functions from gmem.c and gmessages.c; */
|
||||
|
||||
/* mutex_lock, mutex_unlock can be taken directly, as
|
||||
signature and semantic are right, but without error check then!!!!,
|
||||
we might want to change this therefore. */
|
||||
@ -82,7 +75,7 @@ g_mutex_trylock_solaris_impl (GMutex * mutex)
|
||||
static GCond *
|
||||
g_cond_new_solaris_impl ()
|
||||
{
|
||||
GCond *result = (GCond *) g_new0 (cond_t, 1);
|
||||
GCond *result = (GCond *) g_new (cond_t, 1);
|
||||
solaris_check_for_error (cond_init ((cond_t *) result, USYNC_THREAD, 0));
|
||||
return result;
|
||||
}
|
||||
@ -96,7 +89,8 @@ g_cond_new_solaris_impl ()
|
||||
#define G_NANOSEC 1000000000
|
||||
|
||||
static gboolean
|
||||
g_cond_timed_wait_solaris_impl (GCond * cond, GMutex * entered_mutex,
|
||||
g_cond_timed_wait_solaris_impl (GCond * cond,
|
||||
GMutex * entered_mutex,
|
||||
GTimeVal * abs_time)
|
||||
{
|
||||
int result;
|
||||
@ -133,39 +127,38 @@ g_cond_free_solaris_impl (GCond * cond)
|
||||
static GPrivate *
|
||||
g_private_new_solaris_impl (GDestroyNotify destructor)
|
||||
{
|
||||
/* we can not use g_new and friends, as they might use private data
|
||||
by themself */
|
||||
GPrivate *result = malloc (sizeof (thread_key_t));
|
||||
|
||||
solaris_check_for_error (malloc ? NULL : ENOMEM);
|
||||
|
||||
GPrivate *result = (GPrivate *) g_new (thread_key_t,1);
|
||||
solaris_check_for_error (thr_keycreate ((thread_key_t *) result,
|
||||
destructor));
|
||||
return result;
|
||||
}
|
||||
|
||||
void
|
||||
/* NOTE: the functions g_private_get and g_private_set may not use
|
||||
functions from gmem.c and gmessages.c */
|
||||
|
||||
static void
|
||||
g_private_set_solaris_impl (GPrivate * private, gpointer value)
|
||||
{
|
||||
solaris_check_for_error (private ? NULL : EINVAL);
|
||||
if (!private)
|
||||
return;
|
||||
|
||||
solaris_check_for_error (thr_setspecific (*(thread_key_t *) private, value));
|
||||
thr_setspecific (*(thread_key_t *) private, value);
|
||||
}
|
||||
|
||||
gpointer
|
||||
static gpointer
|
||||
g_private_get_solaris_impl (GPrivate * private)
|
||||
{
|
||||
gpointer result;
|
||||
|
||||
solaris_check_for_error (private ? NULL : EINVAL);
|
||||
if (!private)
|
||||
return NULL;
|
||||
|
||||
thr_getspecific (*(thread_key_t *) private, &result);
|
||||
|
||||
solaris_check_for_error (thr_getspecific (*(thread_key_t *) private,
|
||||
&result));
|
||||
return result;
|
||||
}
|
||||
|
||||
static GThreadFunctions
|
||||
g_thread_functions_for_glib_use_default =
|
||||
static GThreadFunctions g_thread_functions_for_glib_use_default =
|
||||
{
|
||||
g_mutex_new_solaris_impl,
|
||||
(void (*)(GMutex *)) mutex_lock,
|
||||
|
@ -36,10 +36,14 @@ static gboolean thread_system_already_initialized = FALSE;
|
||||
#include G_THREAD_SOURCE
|
||||
|
||||
void g_mutex_init (void);
|
||||
void g_mem_init (void);
|
||||
void g_messages_init (void);
|
||||
|
||||
void
|
||||
g_thread_init(GThreadFunctions* init)
|
||||
{
|
||||
gboolean supported;
|
||||
|
||||
if (thread_system_already_initialized)
|
||||
g_error ("the glib thread system may only be initialized once.");
|
||||
|
||||
@ -52,7 +56,11 @@ g_thread_init(GThreadFunctions* init)
|
||||
|
||||
g_thread_functions_for_glib_use = *init;
|
||||
|
||||
g_thread_supported =
|
||||
/* It is important, that g_thread_supported is not set before the
|
||||
thread initialization functions of the different modules are
|
||||
called */
|
||||
|
||||
supported =
|
||||
init->mutex_new &&
|
||||
init->mutex_lock &&
|
||||
init->mutex_trylock &&
|
||||
@ -71,7 +79,7 @@ g_thread_init(GThreadFunctions* init)
|
||||
/* if somebody is calling g_thread_init (), it means that he wants to
|
||||
have thread support, so check this */
|
||||
|
||||
if (!g_thread_supported)
|
||||
if (!supported)
|
||||
{
|
||||
if (g_thread_use_default_impl)
|
||||
g_error ("Threads are not supported on this platform.");
|
||||
@ -83,4 +91,11 @@ g_thread_init(GThreadFunctions* init)
|
||||
glib modules. BTW: order does matter, g_mutex_init MUST be first */
|
||||
|
||||
g_mutex_init ();
|
||||
g_mem_init ();
|
||||
g_messages_init ();
|
||||
|
||||
/* now we can set g_thread_supported and thus enable all the thread
|
||||
functions */
|
||||
|
||||
g_thread_supported = TRUE;
|
||||
}
|
||||
|
@ -8,166 +8,193 @@
|
||||
#define TEST_PRIVATE_ROUNDS 5
|
||||
|
||||
void
|
||||
test_mutexes()
|
||||
test_mutexes ()
|
||||
{
|
||||
GMutex* mutex;
|
||||
GCond* cond;
|
||||
GMutex *mutex = NULL;
|
||||
GCond *cond = NULL;
|
||||
GStaticMutex static_mutex = G_STATIC_MUTEX_INIT;
|
||||
G_LOCK_DEFINE(test_me);
|
||||
G_LOCK_DEFINE (test_me);
|
||||
|
||||
if( g_thread_supported )
|
||||
if (g_thread_supported)
|
||||
{
|
||||
mutex = g_mutex_new();
|
||||
cond = g_cond_new();
|
||||
mutex = g_mutex_new ();
|
||||
cond = g_cond_new ();
|
||||
}
|
||||
|
||||
g_mutex_lock(mutex);
|
||||
g_mutex_unlock(mutex);
|
||||
g_mutex_lock (mutex);
|
||||
g_mutex_unlock (mutex);
|
||||
|
||||
g_static_mutex_lock(static_mutex);
|
||||
g_static_mutex_unlock(static_mutex);
|
||||
g_static_mutex_lock (static_mutex);
|
||||
g_static_mutex_unlock (static_mutex);
|
||||
|
||||
g_cond_signal(cond);
|
||||
g_cond_broadcast(cond);
|
||||
g_cond_signal (cond);
|
||||
g_cond_broadcast (cond);
|
||||
|
||||
g_lock(test_me);
|
||||
g_unlock(test_me);
|
||||
g_lock (test_me);
|
||||
g_unlock (test_me);
|
||||
|
||||
if( g_thread_supported )
|
||||
if (g_thread_supported)
|
||||
{
|
||||
g_cond_free(cond);
|
||||
g_mutex_free(mutex);
|
||||
g_cond_free (cond);
|
||||
g_mutex_free (mutex);
|
||||
}
|
||||
}
|
||||
|
||||
#if defined(DEFAULTMUTEX) /* we are using solaris threads */
|
||||
gulong
|
||||
new_thread(GHookFunc func, gpointer data)
|
||||
#if defined(NSPR) /* we are using nspr threads */
|
||||
/* this option must be specified by hand during compile of
|
||||
testgthread. also note, that you have to link with whatever library
|
||||
nspr is building upon, it might otherwise (as on solaris) lead to
|
||||
run time failure, as the mutex functions are defined in libc, but
|
||||
as noops, that will make some nspr assertions fail. */
|
||||
#include <prthread.h>
|
||||
|
||||
gpointer
|
||||
new_thread (GHookFunc func, gpointer data)
|
||||
{
|
||||
thread_t thread;
|
||||
thr_create( NULL, 0, (void* (*)(void*))func, data, THR_BOUND, &thread);
|
||||
PRThread *thread = PR_CreateThread (PR_SYSTEM_THREAD, func, data,
|
||||
PR_PRIORITY_NORMAL, PR_LOCAL_THREAD,
|
||||
PR_JOINABLE_THREAD, 0);
|
||||
return thread;
|
||||
}
|
||||
#define join_thread(thread) thr_join( (thread_t)thread, NULL, NULL )
|
||||
#define self_thread() (gulong)thr_self()
|
||||
#define join_thread(thread) PR_JoinThread (thread)
|
||||
#define self_thread() PR_GetCurrentThread ()
|
||||
|
||||
#elif defined(DEFAULTMUTEX) /* we are using solaris threads */
|
||||
|
||||
gpointer
|
||||
new_thread (GHookFunc func, gpointer data)
|
||||
{
|
||||
thread_t thread;
|
||||
thr_create (NULL, 0, (void *(*)(void *)) func, data, THR_BOUND, &thread);
|
||||
return GUINT_TO_POINTER (thread);
|
||||
}
|
||||
#define join_thread(thread) \
|
||||
thr_join ((thread_t)GPOINTER_TO_UINT (thread), NULL, NULL)
|
||||
#define self_thread() GUINT_TO_POINTER (thr_self ())
|
||||
|
||||
#elif defined(PTHREAD_MUTEX_INITIALIZER) /* we are using posix threads */
|
||||
gulong
|
||||
gpointer
|
||||
new_thread(GHookFunc func, gpointer data)
|
||||
{
|
||||
pthread_t thread;
|
||||
pthread_attr_t pthread_attr;
|
||||
pthread_attr_init( &pthread_attr );
|
||||
pthread_attr_setdetachstate( &pthread_attr, PTHREAD_CREATE_JOINABLE );
|
||||
pthread_create( &thread, &pthread_attr, (void* (*)(void*))func, data );
|
||||
return thread;
|
||||
pthread_attr_init (&pthread_attr);
|
||||
pthread_attr_setdetachstate (&pthread_attr, PTHREAD_CREATE_JOINABLE);
|
||||
pthread_create (&thread, &pthread_attr, (void *(*)(void *)) func, data);
|
||||
return GUINT_TO_POINTER (thread);
|
||||
}
|
||||
#define join_thread(thread) pthread_join( (pthread_t)thread, NULL )
|
||||
#define self_thread() (gulong)pthread_self()
|
||||
#define join_thread(thread) \
|
||||
pthread_join ((pthread_t)GPOINTER_TO_UINT (thread), NULL)
|
||||
#define self_thread() GUINT_TO_POINTER (pthread_self ())
|
||||
|
||||
#else /* we are not having a thread implementation, do nothing */
|
||||
#define new_thread(func,data) (0)
|
||||
|
||||
#define new_thread(func,data) (NULL)
|
||||
#define join_thread(thread) ((void)0)
|
||||
#define self_thread() NULL
|
||||
|
||||
#endif
|
||||
|
||||
#define G_MICROSEC 1000000
|
||||
|
||||
void
|
||||
wait_thread(double seconds)
|
||||
wait_thread (double seconds)
|
||||
{
|
||||
GMutex* mutex;
|
||||
GCond* cond;
|
||||
GMutex *mutex;
|
||||
GCond *cond;
|
||||
GTimeVal current_time;
|
||||
|
||||
g_get_current_time (¤t_time);
|
||||
mutex = g_mutex_new();
|
||||
cond = g_cond_new();
|
||||
mutex = g_mutex_new ();
|
||||
cond = g_cond_new ();
|
||||
|
||||
current_time.tv_sec += (guint)seconds;
|
||||
seconds -= (guint)seconds;
|
||||
current_time.tv_usec += (guint)(seconds * G_MICROSEC);
|
||||
while( current_time.tv_usec >= G_MICROSEC )
|
||||
current_time.tv_sec += (guint) seconds;
|
||||
seconds -= (guint) seconds;
|
||||
current_time.tv_usec += (guint) (seconds * G_MICROSEC);
|
||||
while (current_time.tv_usec >= G_MICROSEC)
|
||||
{
|
||||
current_time.tv_usec -= G_MICROSEC;
|
||||
current_time.tv_sec++;
|
||||
}
|
||||
|
||||
g_mutex_lock( mutex );
|
||||
g_cond_timed_wait( cond, mutex, ¤t_time );
|
||||
g_mutex_unlock( mutex );
|
||||
g_mutex_lock (mutex);
|
||||
g_cond_timed_wait (cond, mutex, ¤t_time);
|
||||
g_mutex_unlock (mutex);
|
||||
|
||||
g_mutex_free( mutex );
|
||||
g_cond_free( cond );
|
||||
g_mutex_free (mutex);
|
||||
g_cond_free (cond);
|
||||
}
|
||||
|
||||
gpointer
|
||||
private_constructor()
|
||||
private_constructor ()
|
||||
{
|
||||
guint* result = g_new(guint,2);
|
||||
gpointer *result = g_new (gpointer, 2);
|
||||
result[0] = 0;
|
||||
result[1] = self_thread();
|
||||
g_print("allocating data for the thread %d.\n",result[1]);
|
||||
result[1] = self_thread ();
|
||||
g_print ("allocating data for the thread %p.\n", result[1]);
|
||||
return result;
|
||||
}
|
||||
|
||||
void
|
||||
private_destructor(gpointer data)
|
||||
private_destructor (gpointer data)
|
||||
{
|
||||
guint* real = data;
|
||||
g_print("freeing data for the thread %d.\n",real[1]);
|
||||
g_free( real );
|
||||
gpointer *real = data;
|
||||
g_print ("freeing data for the thread %p.\n", real[1]);
|
||||
g_free (real);
|
||||
}
|
||||
|
||||
GStaticPrivate private;
|
||||
|
||||
void
|
||||
test_private_func(void* data)
|
||||
test_private_func (void *data)
|
||||
{
|
||||
guint i = 0;
|
||||
wait_thread(1);
|
||||
while( i < TEST_PRIVATE_ROUNDS )
|
||||
wait_thread (1);
|
||||
while (i < TEST_PRIVATE_ROUNDS)
|
||||
{
|
||||
guint random_value = rand() % 10000;
|
||||
guint* data = g_static_private_get( &private );
|
||||
guint random_value = rand () % 10000;
|
||||
guint *data = g_static_private_get (&private);
|
||||
if (!data)
|
||||
{
|
||||
data = private_constructor();
|
||||
g_static_private_set( &private, data, private_destructor );
|
||||
data = private_constructor ();
|
||||
g_static_private_set (&private, data, private_destructor);
|
||||
}
|
||||
*data = random_value;
|
||||
wait_thread(.2);
|
||||
g_assert( *(guint*)g_static_private_get( &private ) == random_value );
|
||||
wait_thread (.2);
|
||||
g_assert (*(guint *) g_static_private_get (&private) == random_value);
|
||||
i++;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
test_private()
|
||||
test_private ()
|
||||
{
|
||||
int i;
|
||||
gulong threads[ TEST_PRIVATE_THREADS ];
|
||||
for( i = 0; i < TEST_PRIVATE_THREADS; i++ )
|
||||
gpointer threads[TEST_PRIVATE_THREADS];
|
||||
for (i = 0; i < TEST_PRIVATE_THREADS; i++)
|
||||
{
|
||||
threads[ i ] = new_thread( test_private_func, (gpointer)i );
|
||||
threads[i] = new_thread (test_private_func, (gpointer) i);
|
||||
}
|
||||
for( i = 0; i < TEST_PRIVATE_THREADS; i++ )
|
||||
for (i = 0; i < TEST_PRIVATE_THREADS; i++)
|
||||
{
|
||||
join_thread( threads[ i ] );
|
||||
join_thread (threads[i]);
|
||||
}
|
||||
g_print("\n");
|
||||
g_print ("\n");
|
||||
}
|
||||
|
||||
int
|
||||
main()
|
||||
main ()
|
||||
{
|
||||
test_mutexes();
|
||||
test_mutexes ();
|
||||
|
||||
g_thread_init( NULL );
|
||||
g_thread_init (NULL);
|
||||
|
||||
test_mutexes();
|
||||
test_mutexes ();
|
||||
|
||||
test_private();
|
||||
test_private ();
|
||||
|
||||
/* later we might want to start n copies of that */
|
||||
testglib_main(0,NULL);
|
||||
testglib_main (0, NULL);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user