+1998-06-29 12:27 Ulrich Drepper <drepper@cygnus.com>
+
+ * argp/argp.h: Use __PMT instead of __P for function pointer.
+ * iconv/gconv.h: Likewise.
+ * io/fts.h: Likewise.
+ * io/ftw.h: Likewise.
+ * libio/libio.h: Likewise.
+ * malloc/mcheck.h: Likewise.
+ * misc/search.h: Likewise.
+ * posix/glob.h: Likewise.
+ * resolv/resolv.h: Likewise.
+ * signal/signal.h: Likewise.
+ * stdlib/stdlib.h: Likewise.
+ * sysdeps/unix/sysv/linux/bits/sigaction.h: Likewise.
+ * sysdeps/unix/sysv/linux/bits/siginfo.h: Likewise.
+
+1998-06-26 Andreas Schwab <schwab@issan.informatik.uni-dortmund.de>
+
+ * Makeconfig (CPPFLAGS): Use $($(subdir)-CPPFLAGS) only once.
+
+1998-06-27 Andreas Schwab <schwab@issan.informatik.uni-dortmund.de>
+
+ * posix/wordexp.c (parse_param): Fix memory leak.
+
+1998-06-27 Andreas Schwab <schwab@issan.informatik.uni-dortmund.de>
+
+ * libc.map: Export _IO_ftrylockfile.
+
+1998-06-27 Andreas Schwab <schwab@issan.informatik.uni-dortmund.de>
+
+ * sysdeps/unix/sysv/linux/aio_sigqueue.c: Use get[pu]id instead of
+ __get[pu]id.
+
+1998-06-28 Andreas Schwab <schwab@issan.informatik.uni-dortmund.de>
+
+ * elf/dl-misc.c (_dl_debug_message): Don't cache the pid.
+
+ * elf/dl-runtime.c (_dl_object_relocation_scope): Avoid adding the
+ same search list twice.
+
+1998-06-29 Andreas Jaeger <aj@arthur.rhein-neckar.de>
+
+ * login/programs/utmpd.c (handle_requests): Set and use maximal fd
+ used to optimize loop/select.
+
+1998-06-24 Andreas Schwab <schwab@issan.informatik.uni-dortmund.de>
+
+ * sysdeps/generic/init-first.c: Don't define __libc_pid.
+ * sysdeps/unix/sysv/linux/init-first.c: Likewise.
+ * sysdeps/mach/hurd/i386/init-first.c: Likewise.
+ * sysdeps/mach/hurd/mips/init-first.c: Likewise.
+ * sysdeps/arm/init-first.c: Likewise.
+ * posix/getopt_init.c: Don't use __libc_pid.
+ * sysdeps/unix/sysv/linux/aio_sigqueue.c: Likewise.
+ * sysdeps/unix/sysv/linux/sigqueue.c: Likewise.
+ * libc.map: Remove __libc_uid and __libc_pid.
+
1998-06-28 Andreas Jaeger <aj@arthur.rhein-neckar.de>
* sunrpc/rtime.c (rtime): Use poll instead of select.
bug reports to the maintainers.
The GNU C library is very complex. The installation process has not been
-completely automated; there are too many variables. You can do substantial
+completely automated; there are too many variables. You can do substantial
damage to your system by installing the library incorrectly. Make sure you
understand what you are undertaking before you begin.
2.20. What do I need for C++ development?
2.21. Even statically linked programs need some shared libraries
which is not acceptable for me. What can I do?
+2.22. I just upgraded my Linux system to glibc and now I get
+ errors whenever I try to link any program.
3. Source and binary incompatibilities, and what to do about them
4.3. When I set the timezone by setting the TZ environment variable
to EST5EDT things go wrong since glibc computes the wrong time
from this information.
+4.4. What other sources of documentation about glibc are available?
\f
~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~
1.14. What's the problem with configure --enable-omitfp?
{AJ} When --enable-omitfp is set the libraries are built without frame
-pointers. Some compilers produce buggy code for this model and therefore we
+pointers. Some compilers produce buggy code for this model and therefore we
don't advise using it at the moment.
-If you use --enable-omitfp, you're on your own. If you encounter problems
+If you use --enable-omitfp, you're on your own. If you encounter problems
with a library that was build this way, we advise you to rebuild the library
without --enable-omitfp. If the problem vanishes consider tracking the
problem down and report it as compiler failure.
*highly* recommended *not* to use --enable-static-nss since this makes
the behaviour of the programs on the system inconsistent.
+
+2.22. I just upgraded my Linux system to glibc and now I get
+ errors whenever I try to link any program.
+
+{ZW} This happens when you have installed glibc as the primary C library but
+have stray symbolic links pointing at your old C library. If the first
+`libc.so' the linker finds is libc 5, it will use that. Your program
+expects to be linked with glibc, so the link fails.
+
+The most common case is that glibc put its `libc.so' in /usr/lib, but there
+was a `libc.so' from libc 5 in /lib, which gets searched first. To fix the
+problem, just delete /lib/libc.so. You may also need to delete other
+symbolic links in /lib, such as /lib/libm.so if it points to libm.so.5.
+
+{AJ} The perl script test-installation.pl which is run as last step during
+an installation of glibc that is configured with --prefix=/usr should help
+detect these situations. If the script reports problems, something is
+really screwed up.
+
\f
. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
functions. Why?
{AJ} glibc 2.1 has special string functions that are faster than the normal
-library functions. Some of the functions are additionally implemented as
+library functions. Some of the functions are additionally implemented as
inline functions and others as macros.
The optimized string functions are only used when compiling with
-optimizations (-O1 or higher). The behavior can be changed with two feature
+optimizations (-O1 or higher). The behavior can be changed with two feature
macros:
* __NO_STRING_INLINES: Don't do any string optimizations.
Since some of these string functions are now additionally defined as macros,
code like "char *strncpy();" doesn't work anymore (and is unnecessary, since
-<string.h> has the necessary declarations). Either change your code or
+<string.h> has the necessary declarations). Either change your code or
define __NO_STRING_INLINES.
{UD} Another problem in this area is that gcc still has problems on machines
{RM,AJ} Constructs like:
static FILE *InPtr = stdin;
-lead to this message. This is correct behaviour with glibc since stdin is
-not a constant expression. Please note that a strict reading of ISO C does
+lead to this message. This is correct behaviour with glibc since stdin is
+not a constant expression. Please note that a strict reading of ISO C does
not allow above constructs.
One of the advantages of this is that you can assign to stdin, stdout, and
stderr just like any other global variable (e.g. `stdout = my_stream;'),
which can be very useful with custom streams that you can write with libio
-(but beware this is not necessarily portable). The reason to implement it
+(but beware this is not necessarily portable). The reason to implement it
this way were versioning problems with the size of the FILE structure.
+To fix those programs you've got to initialize the variable at run time.
+This can be done, e.g. in main, like:
+
+static FILE *InPtr;
+int main(void)
+{
+ InPtr = stdin;
+}
+
+or by constructors (beware this is gcc specific):
+
+static FILE *InPtr;
+static void inPtr_construct (void) __attribute__((constructor));
+static void inPtr_construct (void) { InPtr = stdin; }
+
3.10. I can't compile with gcc -traditional (or
-traditional-cpp). Why?
{AJ} glibc2 does break -traditional and -traditonal-cpp - and will continue
-to do so. For example constructs of the form:
+to do so. For example constructs of the form:
enum {foo
#define foo foo
{AJ} The GNU C library is compatible with the ANSI/ISO C standard. If
you're using `gcc -ansi', the glibc includes which are specified in the
-standard follow the standard. The ANSI/ISO C standard defines what has to be
+standard follow the standard. The ANSI/ISO C standard defines what has to be
in the include files - and also states that nothing else should be in the
include files (btw. you can still enable additional standards with feature
flags).
the POSIX method and you have not verified something is really broken by
reading the POSIX standards.
+
+4.4. What other sources of documentation about glibc are available?
+
+{AJ} The FSF has a page about the GNU C library at
+<http://www.gnu.org/software/libc/>. The problem data base of open and
+solved bugs in GNU libc is available at
+<http://www-gnats.gnu.org:8080/cgi-bin/wwwgnats.pl>. Eric Green has written
+a HowTo for converting from Linux libc5 to glibc2. The HowTo is accessable
+via the FSF page and at <http://www.imaxx.net/~thrytis/glibc>. Frodo
+Looijaard describes a different way installing glibc2 as secondary libc at
+<http://huizen.dds.nl/~frodol/glibc>.
+
+Please note that this is not a complete list.
+
\f
~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~
bug reports to the maintainers.
The GNU C library is very complex. The installation process has not been
-completely automated; there are too many variables. You can do substantial
+completely automated; there are too many variables. You can do substantial
damage to your system by installing the library incorrectly. Make sure you
understand what you are undertaking before you begin.
?? What's the problem with configure --enable-omitfp?
{AJ} When --enable-omitfp is set the libraries are built without frame
-pointers. Some compilers produce buggy code for this model and therefore we
+pointers. Some compilers produce buggy code for this model and therefore we
don't advise using it at the moment.
-If you use --enable-omitfp, you're on your own. If you encounter problems
+If you use --enable-omitfp, you're on your own. If you encounter problems
with a library that was build this way, we advise you to rebuild the library
without --enable-omitfp. If the problem vanishes consider tracking the
problem down and report it as compiler failure.
functions. Why?
{AJ} glibc 2.1 has special string functions that are faster than the normal
-library functions. Some of the functions are additionally implemented as
+library functions. Some of the functions are additionally implemented as
inline functions and others as macros.
The optimized string functions are only used when compiling with
-optimizations (-O1 or higher). The behavior can be changed with two feature
+optimizations (-O1 or higher). The behavior can be changed with two feature
macros:
* __NO_STRING_INLINES: Don't do any string optimizations.
Since some of these string functions are now additionally defined as macros,
code like "char *strncpy();" doesn't work anymore (and is unnecessary, since
-<string.h> has the necessary declarations). Either change your code or
+<string.h> has the necessary declarations). Either change your code or
define __NO_STRING_INLINES.
{UD} Another problem in this area is that gcc still has problems on machines
{RM,AJ} Constructs like:
static FILE *InPtr = stdin;
-lead to this message. This is correct behaviour with glibc since stdin is
-not a constant expression. Please note that a strict reading of ISO C does
+lead to this message. This is correct behaviour with glibc since stdin is
+not a constant expression. Please note that a strict reading of ISO C does
not allow above constructs.
One of the advantages of this is that you can assign to stdin, stdout, and
stderr just like any other global variable (e.g. `stdout = my_stream;'),
which can be very useful with custom streams that you can write with libio
-(but beware this is not necessarily portable). The reason to implement it
+(but beware this is not necessarily portable). The reason to implement it
this way were versioning problems with the size of the FILE structure.
+To fix those programs you've got to initialize the variable at run time.
+This can be done, e.g. in main, like:
+
+static FILE *InPtr;
+int main(void)
+{
+ InPtr = stdin;
+}
+
+or by constructors (beware this is gcc specific):
+
+static FILE *InPtr;
+static void inPtr_construct (void) __attribute__((constructor));
+static void inPtr_construct (void) { InPtr = stdin; }
+
?? I can't compile with gcc -traditional (or
-traditional-cpp). Why?
{AJ} glibc2 does break -traditional and -traditonal-cpp - and will continue
-to do so. For example constructs of the form:
+to do so. For example constructs of the form:
enum {foo
#define foo foo
{AJ} The GNU C library is compatible with the ANSI/ISO C standard. If
you're using `gcc -ansi', the glibc includes which are specified in the
-standard follow the standard. The ANSI/ISO C standard defines what has to be
+standard follow the standard. The ANSI/ISO C standard defines what has to be
in the include files - and also states that nothing else should be in the
include files (btw. you can still enable additional standards with feature
flags).
the POSIX method and you have not verified something is really broken by
reading the POSIX standards.
+?? What other sources of documentation about glibc are available?
+
+{AJ} The FSF has a page about the GNU C library at
+<http://www.gnu.org/software/libc/>. The problem data base of open and
+solved bugs in GNU libc is available at
+<http://www-gnats.gnu.org:8080/cgi-bin/wwwgnats.pl>. Eric Green has written
+a HowTo for converting from Linux libc5 to glibc2. The HowTo is accessable
+via the FSF page and at <http://www.imaxx.net/~thrytis/glibc>. Frodo
+Looijaard describes a different way installing glibc2 as secondary libc at
+<http://huizen.dds.nl/~frodol/glibc>.
+
+Please note that this is not a complete list.
+
\f
Answers were given by:
{UD} Ulrich Drepper, <drepper@cygnus.com>
# These are the variables that the implicit compilation rules use.
CPPFLAGS = $($(subdir)-CPPFLAGS) $(+includes) $(defines) \
-include $(..)include/libc-symbols.h $(sysdep-CPPFLAGS) \
- $($(subdir)-CPPFLAGS) $(CPPFLAGS-$(suffix $@)) $(CPPFLAGS-$(<F)) \
- $(CPPFLAGS-$(@F))
+ $(CPPFLAGS-$(suffix $@)) $(CPPFLAGS-$(<F)) $(CPPFLAGS-$(@F))
override CFLAGS = $(filter-out %frame-pointer,$(+cflags)) $(sysdep-CFLAGS) \
$(CFLAGS-$(suffix $@)) $(CFLAGS-$(<F)) $(CFLAGS-$(@F))
#ifndef __P
# if (defined __STDC__ && __STDC__) || defined __cplusplus
-# define __P(args) args
+# if defined __GNUC__ && defined __cplusplus && __GNUC_MINOR__ >= 8
+# define __P(args) args throw ()
+# else
+# define __P(args) args
+# endif
+# define __PMT(args) args
# else
# define __P(args) ()
+# define __PMT(args) ()
# endif
#endif
\f
struct argp_child; /* " */
/* The type of a pointer to an argp parsing function. */
-typedef error_t (*argp_parser_t)(int key, char *arg, struct argp_state *state);
+typedef error_t (*argp_parser_t) __PMT ((int key, char *arg,
+ struct argp_state *state));
/* What to return for unrecognized keys. For special ARGP_KEY_ keys, such
returns will simply be ignored. For user keys, this error will be turned
has been done, so if any of the replacement text also needs translation,
that should be done by the filter function. INPUT is either the input
supplied to argp_parse, or NULL, if argp_help was called directly. */
- char *(*help_filter)(int __key, __const char *__text, void *__input);
+ char *(*help_filter) __PMT ((int __key, __const char *__text,
+ void *__input));
/* If non-zero the strings used in the argp library are translated using
the domain described by this string. Otherwise the currently installed
calls this function with a stream to print the version to and a pointer to
the current parsing state, and then exits (unless the ARGP_NO_EXIT flag is
used). This variable takes precedent over ARGP_PROGRAM_VERSION. */
-extern void (*argp_program_version_hook) __P ((FILE *__stream,
- struct argp_state *__state));
+extern void (*argp_program_version_hook) __PMT ((FILE *__stream,
+ struct argp_state *__state));
/* If defined or set by the user program, it should point to string that is
the bug-reporting address for the program. It will be printed by
{
/* We print the strings we get passed one after the other but start all
lines using the current PID. */
- static int pid;
+ int pid = 0;
va_list ap;
- if (pid == 0)
- pid = __getpid ();
-
va_start (ap, msg);
do
if (msg[0] == '\0')
{
char buf[7];
char *p;
+ if (pid == 0)
+ pid = __getpid ();
assert (pid >= 0 && pid < 100000);
p = _itoa_word (pid, &buf[5], 10, 0);
while (p > buf)
dependency tree that first caused this object to be loaded. */
while (l->l_loader)
l = l->l_loader;
- *_dl_global_scope_end = l;
+ /* There is no point in searching the same list twice. This isn't
+ guaranteed to always find all duplicates if new objects are added
+ to the global scope, but is good enough most of the time. */
+ if (_dl_global_scope[2] != l)
+ *_dl_global_scope_end = l;
return &_dl_global_scope[2];
}
}
/* Type of a conversion function. */
-typedef int (*gconv_fct) __P ((struct gconv_step *,
- struct gconv_step_data *, __const char **,
- __const char *, size_t *, int));
+typedef int (*gconv_fct) __PMT ((struct gconv_step *,
+ struct gconv_step_data *, __const char **,
+ __const char *, size_t *, int));
/* Constructor and destructor for local data for conversion step. */
-typedef int (*gconv_init_fct) __P ((struct gconv_step *));
-typedef void (*gconv_end_fct) __P ((struct gconv_step *));
+typedef int (*gconv_init_fct) __PMT ((struct gconv_step *));
+typedef void (*gconv_end_fct) __PMT ((struct gconv_step *));
/* Description of a conversion step. */
int fts_rfd; /* fd for root */
int fts_pathlen; /* sizeof(path) */
int fts_nitems; /* elements in the sort array */
- int (*fts_compar) __P((const void *, const void *)); /* compare fn */
+ int (*fts_compar) __PMT((const void *, const void *)); /* compare fn */
#define FTS_COMFOLLOW 0x0001 /* follow command line symlinks */
#define FTS_LOGICAL 0x0002 /* logical walk */
/* Convenient types for callback functions. */
-typedef int (*__ftw_func_t) __P ((__const char *__filename,
- __const struct stat *__status, int __flag));
-#ifdef __USE_LARGEFILE64
-typedef int (*__ftw64_func_t) __P ((__const char *__filename,
- __const struct stat64 *__status,
+typedef int (*__ftw_func_t) __PMT ((__const char *__filename,
+ __const struct stat *__status,
int __flag));
+#ifdef __USE_LARGEFILE64
+typedef int (*__ftw64_func_t) __PMT ((__const char *__filename,
+ __const struct stat64 *__status,
+ int __flag));
#endif
#ifdef __USE_XOPEN_EXTENDED
-typedef int (*__nftw_func_t) __P ((__const char *__filename,
- __const struct stat *__status, int __flag,
- struct FTW *__info));
+typedef int (*__nftw_func_t) __PMT ((__const char *__filename,
+ __const struct stat *__status, int __flag,
+ struct FTW *__info));
# ifdef __USE_LARGEFILE64
-typedef int (*__nftw64_func_t) __P ((__const char *__filename,
- __const struct stat64 *__status,
- int __flag, struct FTW *__info));
+typedef int (*__nftw64_func_t) __PMT ((__const char *__filename,
+ __const struct stat64 *__status,
+ int __flag, struct FTW *__info));
# endif
#endif
_IO_list_all; _IO_stderr_; _IO_stdin_; _IO_stdout_;
- __libc_pid;
-
# This is for sparc only.
.div; .mul; .rem; .udiv; .umul; .urem;
_IO_file_write; _IO_file_xsputn; _IO_fileno; _IO_flockfile;
_IO_flush_all; _IO_flush_all_linebuffered; _IO_fopen; _IO_fprintf;
_IO_fputs; _IO_fread; _IO_free_backup_area; _IO_freopen;
- _IO_fscanf; _IO_fseek; _IO_fsetpos; _IO_ftell; _IO_funlockfile;
- _IO_fwrite; _IO_getc; _IO_getline; _IO_gets;
+ _IO_fscanf; _IO_fseek; _IO_fsetpos; _IO_ftell; _IO_ftrylockfile;
+ _IO_funlockfile; _IO_fwrite; _IO_getc; _IO_getline; _IO_gets;
_IO_init; _IO_init_marker; _IO_link_in; _IO_marker_delta;
_IO_marker_difference; _IO_padn; _IO_pclose; _IO_peekc_locked;
_IO_perror; _IO_popen; _IO_printf; _IO_proc_close; _IO_proc_open;
-/* Copyright (C) 1991, 92, 93, 94, 95, 97 Free Software Foundation, Inc.
+/* Copyright (C) 1991, 92, 93, 94, 95, 97, 98 Free Software Foundation, Inc.
This file is part of the GNU IO Library.
Written by Per Bothner <bothner@cygnus.com>.
# else
# ifdef __STDC__
# define __P(p) p
+# define __PMT(p) p
# else
# define __P(p) ()
+# define __PMT(p) ()
# endif
# endif
#endif /*!__P*/
/* Define the user-visible type, with user-friendly member names. */
typedef struct
{
- _IO_ssize_t (*read) __P ((struct _IO_FILE *, void *, _IO_ssize_t));
- _IO_ssize_t (*write) __P ((struct _IO_FILE *, const void *, _IO_ssize_t));
- _IO_fpos_t (*seek) __P ((struct _IO_FILE *, _IO_off_t, int));
- int (*close) __P ((struct _IO_FILE *));
+ _IO_ssize_t (*read) __PMT ((struct _IO_FILE *, void *, _IO_ssize_t));
+ _IO_ssize_t (*write) __PMT ((struct _IO_FILE *, const void *, _IO_ssize_t));
+ _IO_fpos_t (*seek) __PMT ((struct _IO_FILE *, _IO_off_t, int));
+ int (*close) __PMT ((struct _IO_FILE *));
} _IO_cookie_io_functions_t;
/* Special file type for fopencookie function. */
+1998-06-29 12:34 Ulrich Drepper <drepper@cygnus.com>
+
+ * sysdeps/pthread/pthread.h: Use __PMT not __P for function pointers.
+
+ * sysdeps/pthread/pthread.h: Define various PTHREAD_* symbols also
+ as macros as demanded in POSIX.1, Annex C.
+
+1998-06-29 12:29 Ulrich Drepper <drepper@cygnus.com>
+
+ * internals.h (struct pthread_request): For free use pthread_t
+ instead of pthread_descr.
+ * join.c (pthread_join): Pass thread_id, not th to manager.
+ (pthread_detach): Likewise.
+ * manager.c (__pthread_manager): Except thread ID in FREE_REQ case.
+ (pthread_exited): Remove detached queue code.
+ (pthread_handle_free): Expect thread ID parameter and use it to
+ validate the thread decsriptor. Don't use detached queue.
+ Patches by Xavier Leroy.
+
+1998-06-27 Andreas Schwab <schwab@issan.informatik.uni-dortmund.de>
+
+ * libpthread.map: Export accept, longjmp, sigaction, siglongjmp,
+ _IO_flockfile, _IO_ftrylockfile, _IO_funlockfile,
+ __pthread_atfork, __pthread_key_create, __pthread_once.
+ * internals.h: Doc fix.
+ * pthread.c (__pthread_initialize): Define again.
+
1998-06-26 Ulrich Drepper <drepper@cygnus.com>
* manager.c (pthread_exited): If thread is not detached put it on
struct pthread_start_args p_start_args; /* arguments for thread creation */
void ** p_specific[PTHREAD_KEY_1STLEVEL_SIZE]; /* thread-specific data */
void * p_libc_specific[_LIBC_TSD_KEY_N]; /* thread-specific data for libc */
- int p_userstack; /* nonzero if the user provided the thread */
+ int p_userstack; /* nonzero if the user provided the stack */
void *p_guardaddr; /* address of guard area or NULL */
size_t p_guardsize; /* size of guard area */
};
sigset_t mask; /* signal mask */
} create;
struct { /* For REQ_FREE: */
- pthread_descr thread; /* descriptor of thread to free */
+ pthread_t thread_id; /* identifier of thread to free */
} free;
struct { /* For REQ_PROCESS_EXIT: */
int code; /* exit status */
extern int __pthread_nonstandard_stacks;
/* File descriptor for sending requests to the thread manager.
- Initially -1, meaning that pthread_initialize must be called. */
+ Initially -1, meaning that __pthread_initialize_manager must be called. */
extern int __pthread_manager_request;
if (__pthread_manager_request >= 0) {
request.req_thread = self;
request.req_kind = REQ_FREE;
- request.req_args.free.thread = th;
+ request.req_args.free.thread_id = thread_id;
__libc_write(__pthread_manager_request,
(char *) &request, sizeof(request));
}
if (terminated && __pthread_manager_request >= 0) {
request.req_thread = thread_self();
request.req_kind = REQ_FREE;
- request.req_args.free.thread = th;
+ request.req_args.free.thread_id = thread_id;
__libc_write(__pthread_manager_request,
(char *) &request, sizeof(request));
}
__libc_internal_tsd_get; __libc_internal_tsd_set;
# Overwritten libc functions.
- close; connect; fcntl; fork; fsync; lseek; msync; nanosleep; open;
- pause; raise; read; recv; recvfrom; recvmsg; send; sendmsg; sendto;
- system; tcdrain; wait; waitpid; write;
+ accept; close; connect; fcntl; fork; fsync; longjmp; lseek; msync;
+ nanosleep; open; pause; raise; read; recv; recvfrom; recvmsg; send;
+ sendmsg; sendto; sigaction; siglongjmp; system; tcdrain; wait;
+ waitpid; write;
__close; __connect; __fcntl; __lseek; __open; __read; __send; __wait;
__write;
+ _IO_flockfile; _IO_ftrylockfile; _IO_funlockfile;
# POSIX.1c extensions to libc.
flockfile; funlockfile; ftrylockfile;
sigwait;
# Protected names for functions used in other shared objects.
- __pthread_getspecific; __pthread_initialize; __pthread_mutex_destroy;
- __pthread_mutex_init; __pthread_mutex_lock; __pthread_mutex_trylock;
- __pthread_mutex_unlock; __pthread_mutexattr_destroy;
- __pthread_mutexattr_init; __pthread_mutexattr_setkind_np;
- __pthread_setspecific;
+ __pthread_atfork; __pthread_initialize; __pthread_getspecific;
+ __pthread_key_create; __pthread_mutex_destroy; __pthread_mutex_init;
+ __pthread_mutex_lock; __pthread_mutex_trylock; __pthread_mutex_unlock;
+ __pthread_mutexattr_destroy; __pthread_mutexattr_init;
+ __pthread_mutexattr_setkind_np; __pthread_once; __pthread_setspecific;
# The error functions.
__errno_location; __h_errno_location;
struct pthread_handle_struct __pthread_handles[PTHREAD_THREADS_MAX] =
{ { LOCK_INITIALIZER, &__pthread_initial_thread, 0}, /* All NULLs */ };
-/* This is a list of terminated, but not detached threads. This can happen
- when pthread_join() is called and the pthread_reap_children() function
- removes the thread from the live list before processing the FREE_REQ
- request. */
-static pthread_descr non_detached;
-
/* Indicate whether at least one thread has a user-defined stack (if 1),
or if all threads have stacks supplied by LinuxThreads (if 0). */
int __pthread_nonstandard_stacks = 0;
static int pthread_handle_create(pthread_t *thread, const pthread_attr_t *attr,
void * (*start_routine)(void *), void *arg,
sigset_t *mask, int father_pid);
-static void pthread_handle_free(pthread_descr th);
+static void pthread_handle_free(pthread_t th_id);
static void pthread_handle_exit(pthread_descr issuing_thread, int exitcode);
static void pthread_reap_children(void);
static void pthread_kill_all_threads(int sig, int main_thread_also);
restart(request.req_thread);
break;
case REQ_FREE:
- pthread_handle_free(request.req_args.free.thread);
+ pthread_handle_free(request.req_args.free.thread_id);
break;
case REQ_PROCESS_EXIT:
pthread_handle_exit(request.req_thread,
__pthread_unlock(th->p_lock);
if (detached)
pthread_free(th);
- else {
- /* Enqueue in the detached list. */
- th->p_nextlive = non_detached;
- if (non_detached != NULL)
- non_detached->p_prevlive = th;
- th->p_prevlive = NULL;
- non_detached = th;
- }
break;
}
}
/* Try to free the resources of a thread when requested by pthread_join
or pthread_detach on a terminated thread. */
-static void pthread_handle_free(pthread_descr th)
+static void pthread_handle_free(pthread_t th_id)
{
- pthread_descr t;
- /* Check that the thread th is still there -- pthread_reap_children
- might have deallocated it already */
- t = __pthread_main_thread;
- do {
- if (t == th) break;
- t = t->p_nextlive;
- } while (t != __pthread_main_thread);
- if (t != th) {
- /* Hum, it might be that the thread already was dequeued but
- wasn't detached. In the case the thread is already detached
- and we cannot find it this is a user bug but we must be
- gracious. */
- t = non_detached;
- while (t != NULL) {
- if (t == th) break;
- t = t->p_nextlive;
- }
- if (t == th) {
- if (th->p_prevlive == NULL)
- non_detached = th->p_nextlive;
- else
- th->p_prevlive->p_nextlive = th->p_nextlive;
- if (th->p_nextlive != NULL)
- th->p_nextlive->p_prevlive = th->p_prevlive;
+ pthread_handle handle = thread_handle(th_id);
+ pthread_descr th;
- /* Finally free it. */
- pthread_free (th);
- }
+ __pthread_lock(&handle->h_lock);
+ if (invalid_handle(handle, th_id)) {
+ /* pthread_reap_children has deallocated the thread already,
+ nothing needs to be done */
+ __pthread_unlock(&handle->h_lock);
return;
}
- __pthread_lock(th->p_lock);
+ th = handle->h_descr;
if (th->p_exited) {
- __pthread_unlock(th->p_lock);
+ __pthread_unlock(&handle->h_lock);
pthread_free(th);
} else {
/* The Unix process of the thread is still running.
Mark the thread as detached so that the thread manager will
deallocate its resources when the Unix process exits. */
th->p_detached = 1;
- __pthread_unlock(th->p_lock);
+ __pthread_unlock(&handle->h_lock);
}
}
__on_exit(pthread_exit_process, NULL);
}
+void __pthread_initialize(void)
+{
+ pthread_initialize();
+}
+
int __pthread_initialize_manager(void)
{
int manager_pipe[2];
enum
{
PTHREAD_CREATE_JOINABLE,
+#define PTHREAD_CREATE_JOINABLE PTHREAD_CREATE_JOINABLE
PTHREAD_CREATE_DETACHED
+#define PTHREAD_CREATE_DETACHED PTHREAD_CREATE_DETACHED
};
enum
{
PTHREAD_INHERIT_SCHED,
+#define PTHREAD_INHERIT_SCHED PTHREAD_INHERIT_SCHED
PTHREAD_EXPLICIT_SCHED
+#define PTHREAD_EXPLICIT_SCHED PTHREAD_EXPLICIT_SCHED
};
enum
{
PTHREAD_SCOPE_SYSTEM,
+#define PTHREAD_SCOPE_SYSTEM PTHREAD_SCOPE_SYSTEM
PTHREAD_SCOPE_PROCESS
+#define PTHREAD_SCOPE_PROCESS PTHREAD_SCOPE_PROCESS
};
typedef struct
enum
{
PTHREAD_PROCESS_PRIVATE,
+# define PTHREAD_PROCESS_PRIVATE PTHREAD_PROCESS_PRIVATE
PTHREAD_PROCESS_SHARED
+# define PTHREAD_PROCESS_SHARED PTHREAD_PROCESS_SHARED
};
enum
struct _pthread_cleanup_buffer
{
- void (*routine) __P ((void *)); /* Function to call. */
+ void (*routine) __PMT ((void *)); /* Function to call. */
void *arg; /* Its argument. */
int canceltype; /* Saved cancellation type. */
struct _pthread_cleanup_buffer *prev; /* Chaining of cleanup functions. */
/* Cancellation */
-enum { PTHREAD_CANCEL_ENABLE, PTHREAD_CANCEL_DISABLE };
-enum { PTHREAD_CANCEL_DEFERRED, PTHREAD_CANCEL_ASYNCHRONOUS };
+enum
+{
+ PTHREAD_CANCEL_ENABLE,
+#define PTHREAD_CANCEL_ENABLE PTHREAD_CANCEL_ENABLE
+ PTHREAD_CANCEL_DISABLE
+#define PTHREAD_CANCEL_DISABLE PTHREAD_CANCEL_DISABLE
+};
+enum
+{
+ PTHREAD_CANCEL_DEFERRED,
+#define PTHREAD_CANCEL_DEFERRED PTHREAD_CANCEL_DEFERRED
+ PTHREAD_CANCEL_ASYNCHRONOUS
+#define PTHREAD_CANCEL_ASYNCHRONOUS PTHREAD_CANCEL_ASYNCHRONOUS
+};
#define PTHREAD_CANCELED ((void *) -1)
-/* Copyright (C) 1997 Free Software Foundation, Inc.
+/* Copyright (C) 1997, 1998 Free Software Foundation, Inc.
This file is part of the GNU C Library.
Contributed by Mark Kettenis <kettenis@phys.uva.nl>, 1997.
#include <stdlib.h>
#include <signal.h>
#include <string.h>
+#include <sys/param.h>
#include <sys/select.h>
#include <sys/socket.h>
#include <sys/stat.h>
fd_set read_fd_set;
fd_set write_fd_set;
int fd;
+ int maxfd; /* Highest used fd to optimize select/loop. */
/* Initialize the set of active sockets. */
FD_ZERO (&active_read_fd_set);
FD_SET (rw_sock, &active_read_fd_set);
FD_SET (ro_sock, &active_read_fd_set);
+ maxfd = MAX (rw_sock, ro_sock);
+
while (1)
{
/* Block until input arrives on one or more active sockets. */
read_fd_set = active_read_fd_set;
write_fd_set = active_write_fd_set;
- if (select (FD_SETSIZE, &read_fd_set, &write_fd_set, NULL, NULL) < 0)
+ if (select (maxfd + 1, &read_fd_set, &write_fd_set, NULL, NULL) < 0)
error (EXIT_FAILURE, errno, _("cannot get input on sockets"));
/* Service all the sockets with input pending. */
- for (fd = 0; fd < FD_SETSIZE; fd++)
+ for (fd = 0; fd <= maxfd; ++fd)
{
if (FD_ISSET (fd, &read_fd_set))
{
error (0, errno, _("cannot accept connection"));
FD_SET (connection->sock, &active_read_fd_set);
+ maxfd = MAX (maxfd, connection->sock);
}
else
{
FD_CLR (fd, &active_write_fd_set);
}
}
+
+ /* Check if maxfd can be lowered. */
+ for (; maxfd >= 0; --maxfd)
+ {
+ if (FD_ISSET (maxfd, &active_read_fd_set)
+ || FD_ISSET (maxfd, &active_write_fd_set))
+ break;
+ }
}
}
-/* Copyright (C) 1996, 1997 Free Software Foundation, Inc.
+/* Copyright (C) 1996, 1997, 1998 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
before `malloc' is ever called. ABORTFUNC is called with an error code
(see enum above) when an inconsistency is detected. If ABORTFUNC is
null, the standard function prints on stderr and then calls `abort'. */
-extern int mcheck __P ((void (*__abortfunc) __P ((enum mcheck_status))));
+extern int mcheck __P ((void (*__abortfunc) (enum mcheck_status)));
/* Check for aberrations in a particular malloc'd block. You must have
called `mcheck' already. These are the same checks that `mcheck' does
/* For use with hsearch(3). */
#ifndef __COMPAR_FN_T
# define __COMPAR_FN_T
-typedef int (*__compar_fn_t) __P ((__const __ptr_t, __const __ptr_t));
+typedef int (*__compar_fn_t) __PMT ((__const __ptr_t, __const __ptr_t));
# ifdef __USE_GNU
typedef __compar_fn_t comparison_fn_t;
#ifndef __ACTION_FN_T
# define __ACTION_FN_T
-typedef void (*__action_fn_t) __P ((__const void *__nodep,
- VISIT __value,
- int __level));
+typedef void (*__action_fn_t) __PMT ((__const void *__nodep,
+ VISIT __value,
+ int __level));
#endif
/* Walk through the whole tree and call the ACTION callback for every node
/* Variable to synchronize work. */
char *__getopt_nonoption_flags;
-extern pid_t __libc_pid;
-
/* Remove the environment variable "_<PID>_GNU_nonoption_argv_flags_" if
it is still available. If the getopt functions are also used in the
char *cp, **ep;
size_t len;
- /* Generate name of the environment variable. We must know the PID
- and we must not use `sprintf'. */
- if (__libc_pid == 0xf00baa)
- __libc_pid = __getpid ();
-
- /* Construct "_<PID>_GNU_nonoption_argv_flags_=" string. */
+ /* Construct the "_<PID>_GNU_nonoption_argv_flags_=" string. We must
+ not use `sprintf'. */
cp = memcpy (&var[sizeof (var) - sizeof (envvar_tail)], envvar_tail,
sizeof (envvar_tail));
- cp = _itoa_word (__libc_pid, cp, 10, 0);
+ cp = _itoa_word (__getpid (), cp, 10, 0);
*--cp = '_';
len = (var + sizeof (var) - 1) - cp;
#if defined __cplusplus || (defined __STDC__ && __STDC__) || defined WINDOWS32
# undef __P
# define __P(protos) protos
+# define __PMT(protos) protos
# define __ptr_t void *
# if !defined __GNUC__ || __GNUC__ < 2
# undef __const
#else /* Not C++ or ANSI C. */
# undef __P
# define __P(protos) ()
+# define __PMT(protos) ()
# undef __const
# define __const
# define __ptr_t char *
/* If the GLOB_ALTDIRFUNC flag is set, the following functions
are used instead of the normal file access functions. */
- void (*gl_closedir) __P ((void *));
- struct dirent *(*gl_readdir) __P ((void *));
- __ptr_t (*gl_opendir) __P ((__const char *));
- int (*gl_lstat) __P ((__const char *, struct stat *));
- int (*gl_stat) __P ((__const char *, struct stat *));
+ void (*gl_closedir) __PMT ((void *));
+ struct dirent *(*gl_readdir) __PMT ((void *));
+ __ptr_t (*gl_opendir) __PMT ((__const char *));
+ int (*gl_lstat) __PMT ((__const char *, struct stat *));
+ int (*gl_stat) __PMT ((__const char *, struct stat *));
} glob_t;
/* Do glob searching for PATTERN, placing results in PGLOB.
/* Start a new word with the last parameter. */
*word = w_newword (word_length, max_length);
- value = __strdup (__libc_argv[p]);
+ value = __libc_argv[p];
}
else
{
typedef enum { res_goahead, res_nextns, res_modified, res_done, res_error }
res_sendhookact;
-typedef res_sendhookact (*res_send_qhook)__P((struct sockaddr_in * const *ns,
- const u_char **query,
- int *querylen,
- u_char *ans,
- int anssiz,
- int *resplen));
+typedef res_sendhookact (*res_send_qhook)__PMT((struct sockaddr_in * const *ns,
+ const u_char **query,
+ int *querylen,
+ u_char *ans,
+ int anssiz,
+ int *resplen));
-typedef res_sendhookact (*res_send_rhook)__P((const struct sockaddr_in *ns,
- const u_char *query,
- int querylen,
- u_char *ans,
- int anssiz,
- int *resplen));
+typedef res_sendhookact (*res_send_rhook)__PMT((const struct sockaddr_in *ns,
+ const u_char *query,
+ int querylen,
+ u_char *ans,
+ int anssiz,
+ int *resplen));
struct res_sym {
int number; /* Identifying number, like T_MX */
#include <bits/signum.h>
/* Type of a signal handler. */
-typedef void (*__sighandler_t) __P ((int));
+typedef void (*__sighandler_t) __PMT ((int));
/* The X/Open definition of `signal' specifies the SVID semantic. Use
the additional function `sysv_signal' when X/Open compatibility is
/* Shorthand for type of comparison functions. */
#ifndef __COMPAR_FN_T
# define __COMPAR_FN_T
-typedef int (*__compar_fn_t) __P ((__const __ptr_t, __const __ptr_t));
+typedef int (*__compar_fn_t) __PMT ((__const __ptr_t, __const __ptr_t));
# ifdef __USE_GNU
typedef __compar_fn_t comparison_fn_t;
int __libc_multiple_libcs = 1;
-pid_t __libc_pid;
-
static void
init (int *data)
{
/* Initialization code run first thing by the ELF startup code. Stub version.
- Copyright (C) 1995, 1997 Free Software Foundation, Inc.
+ Copyright (C) 1995, 1997, 1998 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
extern void __libc_init (int, char **, char **);
extern void __getopt_clean_environment (char **);
-pid_t __libc_pid;
-
#ifdef PIC
void
__libc_init_first (void)
extern int __libc_argc;
extern char **__libc_argv;
-/* We often need the PID. Cache this value. */
-pid_t __libc_pid = 0xf00baa;
-
void *(*_cthread_init_routine) (void); /* Returns new SP to use. */
void (*_cthread_exit_routine) (int status) __attribute__ ((__noreturn__));
/* Initialization code run first thing by the ELF startup code. For Mips/Hurd.
- Copyright (C) 1996, 1997 Free Software Foundation, Inc.
+ Copyright (C) 1996, 1997, 1998 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
int __libc_argc;
char **__libc_argv;
-/* We often need the PID. Cache this value. */
-pid_t __libc_pid;
-
void *(*_cthread_init_routine) (void); /* Returns new SP to use. */
void (*_cthread_exit_routine) (int status) __attribute__ ((__noreturn__));
info.si_errno = 0;
info.si_code = SI_ASYNCIO;
- if (__libc_pid ==0xf00baa)
- __libc_pid = __getpid ();
- info.si_pid = __libc_pid;
-
+ info.si_pid = getpid ();
info.si_uid = getuid ();
info.si_value = val;
- return __syscall_rt_sigqueueinfo (__libc_pid, sig, &info);
+ return __syscall_rt_sigqueueinfo (info.si_pid, sig, &info);
}
/* The proper definitions for Linux's sigaction.
- Copyright (C) 1993, 1994, 1995, 1996, 1997 Free Software Foundation, Inc.
+ Copyright (C) 1993, 94, 95, 96, 97, 98 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
/* Used if SA_SIGINFO is not set. */
__sighandler_t sa_handler;
/* Used if SA_SIGINFO is set. */
- void (*sa_sigaction) __P ((int, siginfo_t *, void *));
+ void (*sa_sigaction) __PMT ((int, siginfo_t *, void *));
}
__sigaction_handler;
#define sa_handler __sigaction_handler.sa_handler
int sa_flags;
/* Restore handler. */
- void (*sa_restorer) __P ((void));
+ void (*sa_restorer) __PMT ((void));
};
/* Bits in `sa_flags'. */
/* siginfo_t, sigevent and constants. Linux version.
- Copyright (C) 1997 Free Software Foundation, Inc.
+ Copyright (C) 1997, 1998 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
struct
{
- void (*_function) __P ((sigval_t)); /* Function to start. */
- void *_attribute; /* Really pthread_attr_t. */
+ void (*_function) __PMT ((sigval_t)); /* Function to start. */
+ void *_attribute; /* Really pthread_attr_t. */
} _sigev_thread;
} _sigev_un;
} sigevent_t;
int __libc_argc;
char **__libc_argv;
-/* We often need the UID and PID. Cache these values. */
-pid_t __libc_pid = 0xf00baa;
-
static void
init (int argc, char **argv, char **envp)
extern int __syscall_rt_sigqueueinfo (int, int, siginfo_t *);
-/* These variables are used quite often in the libc code. */
-extern pid_t __libc_pid;
-
/* Return any pending signal or wait for one for the given time. */
int
info.si_signo = sig;
info.si_errno = 0;
info.si_code = SI_QUEUE;
-
- if (__libc_pid == 0xf00baa)
- __libc_pid = __getpid ();
- info.si_pid = __libc_pid;
-
+ info.si_pid = __getpid ();
info.si_uid = __getuid ();
info.si_value = val;