]> git.ipfire.org Git - thirdparty/glibc.git/commitdiff
* sysdeps/mach/hurd/bits/libc-lock.h: New file, initially copied from
authorRoland McGrath <roland@gnu.org>
Fri, 24 Aug 2001 03:21:51 +0000 (03:21 +0000)
committerRoland McGrath <roland@gnu.org>
Fri, 24 Aug 2001 03:21:51 +0000 (03:21 +0000)
sysdeps/mach version.  Implement counting ("recursive") mutexes
on top of cthreads mutexes.
* sysdeps/mach/hurd/bits/stdio-lock.h: File removed; generic now works.

* sysdeps/generic/bits/stdio-lock.h (_IO_lock_initializer): Define to
_LIBC_LOCK_RECURSIVE_INITIALIZER if defined, else do an #error.
(__libc_cleanup_region_start, __libc_cleanup_region_end,
__libc_clean_end): Define these to call the cleanup function after
normal exit when they're supposed to.

* sysdeps/mach/bits/libc-lock.h (__libc_cleanup_region_start):
Take new first arg DOIT, a boolean saying whether to really install
any cleanup handler.
(__libc_cleanup_region_end): Do nothing if start's DOIT arg was zero.
(__libc_cleanup_end): Likewise.
* stdio-common/vfscanf.c (LOCK_STREAM): Pass new arg.
* stdio-common/vfprintf.c (buffered_vfprintf, vfprintf): Likewise.
* sysdeps/mach/hurd/bits/stdio-lock.h (_IO_cleanup_region_start):
Likewise.
* misc/syslog.c (vsyslog, openlog, closelog): Likewise.
* sysdeps/generic/bits/stdio-lock.h
(_IO_cleanup_region_start, _IO_cleanup_region_start_noarg): Likewise.

ChangeLog
misc/syslog.c
stdio-common/vfprintf.c
stdio-common/vfscanf.c
sysdeps/mach/bits/libc-lock.h
sysdeps/mach/hurd/bits/libc-lock.h [new file with mode: 0644]
sysdeps/mach/hurd/bits/stdio-lock.h [deleted file]

index d6e9aeb69fc337fe12932ae7f3576f716ad24fb0..279224393fcfd37c09ac78e6ebb9a89c1f556a5e 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,29 @@
+2001-08-23  Roland McGrath  <roland@frob.com>
+
+       * sysdeps/mach/hurd/bits/libc-lock.h: New file, initially copied from
+       sysdeps/mach version.  Implement counting ("recursive") mutexes
+       on top of cthreads mutexes.
+       * sysdeps/mach/hurd/bits/stdio-lock.h: File removed; generic now works.
+
+       * sysdeps/generic/bits/stdio-lock.h (_IO_lock_initializer): Define to
+       _LIBC_LOCK_RECURSIVE_INITIALIZER if defined, else do an #error.
+       (__libc_cleanup_region_start, __libc_cleanup_region_end,
+       __libc_clean_end): Define these to call the cleanup function after
+       normal exit when they're supposed to.
+
+       * sysdeps/mach/bits/libc-lock.h (__libc_cleanup_region_start):
+       Take new first arg DOIT, a boolean saying whether to really install
+       any cleanup handler.
+       (__libc_cleanup_region_end): Do nothing if start's DOIT arg was zero.
+       (__libc_cleanup_end): Likewise.
+       * stdio-common/vfscanf.c (LOCK_STREAM): Pass new arg.
+       * stdio-common/vfprintf.c (buffered_vfprintf, vfprintf): Likewise.
+       * sysdeps/mach/hurd/bits/stdio-lock.h (_IO_cleanup_region_start):
+       Likewise.
+       * misc/syslog.c (vsyslog, openlog, closelog): Likewise.
+       * sysdeps/generic/bits/stdio-lock.h
+       (_IO_cleanup_region_start, _IO_cleanup_region_start_noarg): Likewise.
+
 2001-08-23  Jakub Jelinek  <jakub@redhat.com>
 
        * elf/ldconfig.c (search_dir): Remove stale symlinks.
index b89055b7b24358e419c58ab3e82344b8590cb12b..9553c296eaa1facde2150fe49caf9fbc45b73303 100644 (file)
@@ -216,7 +216,7 @@ vsyslog(pri, fmt, ap)
 
        /* Prepare for multiple users.  We have to take care: open and
           write are cancellation points.  */
-       __libc_cleanup_region_start ((void (*) (void *)) cancel_handler,
+       __libc_cleanup_region_start (1, (void (*) (void *)) cancel_handler,
                                     &oldaction_ptr);
        __libc_lock_lock (syslog_lock);
 
@@ -315,7 +315,8 @@ void
 openlog (const char *ident, int logstat, int logfac)
 {
   /* Protect against multiple users.  */
-  __libc_cleanup_region_start ((void (*) __P ((void *))) __libc_mutex_unlock,
+  __libc_cleanup_region_start (1,
+                              (void (*) __P ((void *))) __libc_mutex_unlock,
                               &syslog_lock);
   __libc_lock_lock (syslog_lock);
 
@@ -346,7 +347,8 @@ void
 closelog ()
 {
   /* Protect against multiple users.  */
-  __libc_cleanup_region_start ((void (*) __P ((void *))) __libc_mutex_unlock,
+  __libc_cleanup_region_start (1,
+                              (void (*) __P ((void *))) __libc_mutex_unlock,
                               &syslog_lock);
   __libc_lock_lock (syslog_lock);
 
index 68631fe9032ea9ca333d89b6169ddcd50e695538..c5e78c74999562cce94ede26aeabd25c17fd6c7d 100644 (file)
@@ -1296,10 +1296,10 @@ vfprintf (FILE *s, const CHAR_T *format, va_list ap)
 
   /* Lock stream.  */
 #ifdef USE_IN_LIBIO
-  __libc_cleanup_region_start ((void (*) (void *)) &_IO_funlockfile, s);
+  __libc_cleanup_region_start (1, (void (*) (void *)) &_IO_funlockfile, s);
   _IO_flockfile (s);
 #else
-  __libc_cleanup_region_start ((void (*) (void *)) &__funlockfile, s);
+  __libc_cleanup_region_start (1, (void (*) (void *)) &__funlockfile, s);
   __flockfile (s);
 #endif
 
@@ -2086,7 +2086,7 @@ buffered_vfprintf (register _IO_FILE *s, const CHAR_T *format,
   result = vfprintf (hp, format, args);
 
   /* Lock stream.  */
-  __libc_cleanup_region_start ((void (*) (void *)) &_IO_funlockfile, s);
+  __libc_cleanup_region_start (1, (void (*) (void *)) &_IO_funlockfile, s);
   _IO_flockfile (s);
 
   /* Now flush anything from the helper to the S. */
index 4dc9cfe3a21beace624969678eae51bc5983b47d..0b53d7e0b66831886dddea83154012c79fa7b3bf 100644 (file)
        }                                                                     \
     } while (0)
 # define LOCK_STREAM(S)                                                              \
-  __libc_cleanup_region_start ((void (*) (void *)) &_IO_funlockfile, (S));    \
+  __libc_cleanup_region_start (1, (void (*) (void *)) &_IO_funlockfile, (S)); \
   _IO_flockfile (S)
 # define UNLOCK_STREAM(S)                                                    \
   _IO_funlockfile (S);                                                       \
index 57c36cba0baa097e1734e5e2f514367f4252368f..2484297c8a0724390a1ca0aba57815f1e5fbdcd4 100644 (file)
@@ -76,21 +76,21 @@ typedef cthread_key_t __libc_key_t;
 
 
 /* Start a critical region with a cleanup function */
-#define __libc_cleanup_region_start(FCT, ARG)                              \
+#define __libc_cleanup_region_start(DOIT, FCT, ARG)                        \
 {                                                                          \
-  typeof (***(FCT)) *__save_FCT = FCT;                                     \
+  typeof (***(FCT)) *__save_FCT = (DOIT) ? (FCT) : 0;                      \
   typeof (ARG) __save_ARG = ARG;                                           \
   /* close brace is in __libc_cleanup_region_end below. */
 
 /* End a critical region started with __libc_cleanup_region_start. */
 #define __libc_cleanup_region_end(DOIT)                                            \
-  if (DOIT)                                                                \
+  if ((DOIT) && __save_FCT != 0)                                           \
     (*__save_FCT)(__save_ARG);                                             \
 }
 
 /* Sometimes we have to exit the block in the middle.  */
 #define __libc_cleanup_end(DOIT)                                           \
-  if (DOIT)                                                                \
+  if ((DOIT) && __save_FCT != 0)                                           \
     (*__save_FCT)(__save_ARG);                                             \
 
 
diff --git a/sysdeps/mach/hurd/bits/libc-lock.h b/sysdeps/mach/hurd/bits/libc-lock.h
new file mode 100644 (file)
index 0000000..6e38353
--- /dev/null
@@ -0,0 +1,183 @@
+/* libc-internal interface for mutex locks.  Hurd version using Mach cthreads.
+   Copyright (C) 1996,97,98,2000,01 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, write to the Free
+   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+   02111-1307 USA.  */
+
+#ifndef _BITS_LIBC_LOCK_H
+#define _BITS_LIBC_LOCK_H 1
+
+#if (_LIBC - 0) || (_CTHREADS_ - 0)
+#include <cthreads.h>
+#include <hurd/threadvar.h>
+
+typedef struct mutex __libc_lock_t;
+typedef struct
+{
+  struct mutex mutex;
+  void *owner;
+  int count;
+} __libc_lock_recursive_t;
+
+#define __libc_lock_owner_self() ((void *) __hurd_threadvar_location (0))
+
+#else
+typedef struct __libc_lock_opaque__ __libc_lock_t;
+typedef struct __libc_lock_recursive_opaque__ __libc_lock_recursive_t;
+#endif
+
+/* Define a lock variable NAME with storage class CLASS.  The lock must be
+   initialized with __libc_lock_init before it can be used (or define it
+   with __libc_lock_define_initialized, below).  Use `extern' for CLASS to
+   declare a lock defined in another module.  In public structure
+   definitions you must use a pointer to the lock structure (i.e., NAME
+   begins with a `*'), because its storage size will not be known outside
+   of libc.  */
+#define __libc_lock_define(CLASS,NAME) \
+  CLASS __libc_lock_t NAME;
+
+/* Define an initialized lock variable NAME with storage class CLASS.  */
+#define __libc_lock_define_initialized(CLASS,NAME) \
+  CLASS __libc_lock_t NAME = MUTEX_INITIALIZER;
+
+/* Initialize the named lock variable, leaving it in a consistent, unlocked
+   state.  */
+#define __libc_lock_init(NAME) __mutex_init (&(NAME))
+
+/* Finalize the named lock variable, which must be locked.  It cannot be
+   used again until __libc_lock_init is called again on it.  This must be
+   called on a lock variable before the containing storage is reused.  */
+#define __libc_lock_fini(NAME) __mutex_unlock (&(NAME))
+#define __libc_lock_fini_recursive(NAME) __mutex_unlock (&(NAME).mutex)
+
+
+/* Lock the named lock variable.  */
+#define __libc_lock_lock(NAME) __mutex_lock (&(NAME))
+
+/* Lock the named lock variable.  */
+#define __libc_lock_trylock(NAME) (!__mutex_trylock (&(NAME)))
+
+/* Unlock the named lock variable.  */
+#define __libc_lock_unlock(NAME) __mutex_unlock (&(NAME))
+
+
+#define __libc_lock_define_recursive(CLASS,NAME) \
+  CLASS __libc_lock_recursive_t NAME;
+#define _LIBC_LOCK_RECURSIVE_INITIALIZER { MUTEX_INITIALIZER, 0, 0 }
+#define __libc_lock_define_initialized_recursive(CLASS,NAME) \
+  CLASS __libc_lock_recursive_t NAME = _LIBC_LOCK_RECURSIVE_INITIALIZER;
+
+#define __libc_lock_init_recursive(NAME) \
+  ({ __libc_lock_recursive_t *const __lock = &(NAME); \
+     __lock->owner = 0; mutex_init (&__lock->mutex); })
+
+#define __libc_lock_trylock_recursive(NAME)                                  \
+  ({ __libc_lock_recursive_t *const __lock = &(NAME);                        \
+     void *__self = __libc_lock_owner_self ();                               \
+     __mutex_trylock (&__lock->mutex)                                        \
+     ? (__lock->owner = __self, __lock->count = 1, 0)                        \
+     : __lock->owner == __self ? (++__lock->count, 0) : 1; })
+
+#define __libc_lock_lock_recursive(NAME)                                     \
+  ({ __libc_lock_recursive_t *const __lock = &(NAME);                        \
+     void *__self = __libc_lock_owner_self ();                               \
+     if (__mutex_trylock (&__lock->mutex)                                    \
+        || (__lock->owner != __self                                          \
+            && (__mutex_lock (&__lock->mutex), 1)))                          \
+       __lock->owner = __self, __lock->count = 1;                            \
+     else                                                                    \
+       ++__lock->count;                                                              \
+  })
+#define __libc_lock_unlock_recursive(NAME)                                   \
+  ({ __libc_lock_recursive_t *const __lock = &(NAME);                        \
+     if (--__lock->count == 0)                                               \
+       {                                                                     \
+        __lock->owner = 0;                                                   \
+        __mutex_unlock (&__lock->mutex);                                     \
+       }                                                                     \
+  })
+
+
+/* XXX for now */
+#define __libc_rwlock_define           __libc_lock_define
+#define __libc_rwlock_define_initialized __libc_lock_define_initialized
+#define __libc_rwlock_init             __libc_lock_init
+#define __libc_rwlock_fini             __libc_lock_fini
+#define __libc_rwlock_rdlock           __libc_lock_lock
+#define __libc_rwlock_wrlock           __libc_lock_lock
+#define __libc_rwlock_tryrdlock                __libc_lock_trylock
+#define __libc_rwlock_trywrlock                __libc_lock_trylock
+#define __libc_rwlock_unlock           __libc_lock_unlock
+
+
+/* Start a critical region with a cleanup function */
+#define __libc_cleanup_region_start(DOIT, FCT, ARG)                        \
+{                                                                          \
+  typeof (***(FCT)) *__save_FCT = (DOIT) ? (FCT) : 0;                      \
+  typeof (ARG) __save_ARG = ARG;                                           \
+  /* close brace is in __libc_cleanup_region_end below. */
+
+/* End a critical region started with __libc_cleanup_region_start. */
+#define __libc_cleanup_region_end(DOIT)                                            \
+  if ((DOIT) && __save_FCT != 0)                                           \
+    (*__save_FCT)(__save_ARG);                                             \
+}
+
+/* Sometimes we have to exit the block in the middle.  */
+#define __libc_cleanup_end(DOIT)                                           \
+  if ((DOIT) && __save_FCT != 0)                                           \
+    (*__save_FCT)(__save_ARG);                                             \
+
+
+#if (_CTHREADS_ - 0)
+
+/* Use mutexes as once control variables. */
+
+struct __libc_once
+  {
+    __libc_lock_t lock;
+    int done;
+  };
+
+#define __libc_once_define(CLASS,NAME) \
+  CLASS struct __libc_once NAME = { MUTEX_INITIALIZER, 0 }
+
+/* Call handler iff the first call.  */
+#define __libc_once(ONCE_CONTROL, INIT_FUNCTION) \
+  do {                                                                       \
+    __libc_lock_lock (ONCE_CONTROL.lock);                                    \
+    if (!ONCE_CONTROL.done)                                                  \
+      (INIT_FUNCTION) ();                                                    \
+    ONCE_CONTROL.done = 1;                                                   \
+    __libc_lock_unlock (ONCE_CONTROL.lock);                                  \
+  } while (0)
+
+#ifdef _LIBC
+/* We need portable names for some functions.  E.g., when they are
+   used as argument to __libc_cleanup_region_start.  */
+#define __libc_mutex_unlock __mutex_unlock
+#endif
+
+/* Type for key of thread specific data.  */
+typedef cthread_key_t __libc_key_t;
+
+#define __libc_key_create(KEY,DEST) cthread_keycreate (KEY)
+#define __libc_setspecific(KEY,VAL) cthread_setspecific (KEY, VAL)
+void *__libc_getspecific (__libc_key_t key);
+
+#endif /* _CTHREADS_ */
+
+#endif /* bits/libc-lock.h */
diff --git a/sysdeps/mach/hurd/bits/stdio-lock.h b/sysdeps/mach/hurd/bits/stdio-lock.h
deleted file mode 100644 (file)
index e2b3957..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-/* Thread package specific definitions of stream lock type.  Hurd version.
-   Copyright (C) 2000, 2001 Free Software Foundation, Inc.
-   This file is part of the GNU C Library.
-
-   The GNU C Library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 2.1 of the License, or (at your option) any later version.
-
-   The GNU C Library is distributed in the hope that it will be useful,
-   but WITHOUT ANY WARRANTY; without even the implied warranty of
-   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with the GNU C Library; if not, write to the Free
-   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
-   02111-1307 USA.  */
-
-#ifndef _BITS_STDIO_LOCK_H
-#define _BITS_STDIO_LOCK_H 1
-
-/* We need recursive (counting) mutexes.  Since cthreads doesn't really
-   have them, we implement them just for libio.  The implementation is
-   partially here and partially in Hurd's version of cthreads (i.e. the
-   libthreads library, libthreads/lockfile.c).  */
-
-#if (_LIBC - 0) || (_CTHREADS_ - 0)
-#include <cthreads.h>
-
-struct _IO_cthreads_lock
-{
-  struct mutex mutex;
-  cthread_t owner;
-  unsigned int count;
-};
-#else
-struct _IO_cthreads_lock;
-#endif
-typedef struct _IO_cthreads_lock _IO_lock_t;
-
-#define _IO_lock_initializer   { MUTEX_INITIALIZER, 0, 0 }
-
-#define _IO_lock_init(_name) ({ (_name) = (_IO_lock_t) _IO_lock_initializer; })
-#define _IO_lock_fini(_name) ((void) 0)        /* nothing to do */
-
-/* These are in fact only used for `list_all_lock' (libio/genops.c),
-   which does not need a recursive lock.  The per-FILE locks are only
-   accessed through _IO_flockfile et al, which Hurd's libthreads overrides.  */
-#define _IO_lock_lock(_name) __libc_lock_lock ((_name).mutex)
-#define _IO_lock_unlock(_name) __libc_lock_unlock ((_name).mutex)
-
-#ifdef _LIBC
-#include <bits/libc-lock.h>
-
-#define _IO_cleanup_region_start(_fct, _fp) \
-     __libc_cleanup_region_start (_fct, _fp)
-#define _IO_cleanup_region_start_noarg(_fct) \
-     __libc_cleanup_region_start (_fct, NULL)
-#define _IO_cleanup_region_end(_doit) \
-     __libc_cleanup_region_end (_doit)
-#endif
-
-
-#endif /* bits/stdio-lock.h */