Welcome to mirror list, hosted at ThFree Co, Russian Federation.

cygwin.com/git/newlib-cygwin.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/winsup
diff options
context:
space:
mode:
authorChristopher Faylor <me@cgf.cx>2000-10-17 03:55:58 +0400
committerChristopher Faylor <me@cgf.cx>2000-10-17 03:55:58 +0400
commit166b2571ce446b4085d4c2067b0d0d36c608f131 (patch)
tree097f18452160a8058924634fa52d5e454e8dfe9e /winsup
parentd9d9b707185277db9c0be4eaa2ee5dba9df71fd7 (diff)
* Makefile.in: Remove some obsolete stuff.
* dcrt0.cc (dll_crt0_1): Call signal_fixup_after_exec where appropriate. Set myself->uid from parent version. Just use ThreadItem Init method. Close or store hexec_proc as appropriate. (_dll_crt0): Store user_data->forkee here so that proper tests can be made subsequently. (do_exit): Remove hExeced stuff. * environ.cc (environ_init): Accept environ count as well as environ pointer. * environ.h: Reflect above change. * pinfo.cc (pinfo_init): Ditto. Accept environ count. (fixup_in_spawned_child): Remove. * spawn.cc (spawn_guts): Move signal code to dll_crt0_1. Don't suspend execing process since it is no longer necessary. Store envc. * exceptions.cc (signal_fixup_after_exec): New function. (call_handler): Remove hExeced test. * child_info.h (cygheap_exec_info): Store envc as well as envp. (child_info_spawn): Store hexec_proc so that it can be closed in child. * path.cc (normalize_posix_path): Avoid intermediate use of temporary cwd buf. (normalize_win32_path): Ditto. (cwdstuff::get_initial): Always set lock. * sigproc.h: Remove hExeced. * strace.cc (strace::vsprntf): Modify to accomodate for lack of hExeced. * thread.cc (MTinterface::Init): Merge Init1 and ClearReent into this method. (MTinterface::Init1): Eliminate. (MTinterface::ClearReent): Eliminate. * thread.h: Reflect above changes. * include/sys/strace.h (strace): Make microseconds() public. Make various functions 'regparm', throughout. * pinfo.h (_pinfo): Inline simple signal manipulation functions. Requires inclusion of thread.h which was removed from .cc files, where appropriate. throughout. * pinfo.cc: Eliminate signal manipulation functions. (_pinfo::exit): Calculate total rusage for exiting process here. * cygheap.cc (size2bucket): Eliminate. (init_buckets): Ditto. (_cmalloc): Calculate size and bits in a loop rather than going through a function call. (_crealloc): Use stored array index to calculate allocated size. * spawn.cc (spawn_guts): Use _pinfo exit method to exit, calculating cpu usage.
Diffstat (limited to 'winsup')
-rw-r--r--winsup/cygwin/ChangeLog46
-rw-r--r--winsup/cygwin/Makefile.in26
-rw-r--r--winsup/cygwin/child_info.h11
-rw-r--r--winsup/cygwin/cygerrno.h6
-rw-r--r--winsup/cygwin/cygheap.cc46
-rw-r--r--winsup/cygwin/cygheap.h12
-rw-r--r--winsup/cygwin/dcrt0.cc74
-rw-r--r--winsup/cygwin/debug.h16
-rw-r--r--winsup/cygwin/dtable.cc3
-rw-r--r--winsup/cygwin/dtable.h4
-rw-r--r--winsup/cygwin/environ.cc16
-rw-r--r--winsup/cygwin/environ.h2
-rw-r--r--winsup/cygwin/exceptions.cc17
-rw-r--r--winsup/cygwin/fhandler.cc4
-rw-r--r--winsup/cygwin/fork.cc1
-rw-r--r--winsup/cygwin/grp.cc1
-rw-r--r--winsup/cygwin/include/sys/strace.h2
-rw-r--r--winsup/cygwin/mmap.cc1
-rw-r--r--winsup/cygwin/net.cc1
-rw-r--r--winsup/cygwin/passwd.cc1
-rw-r--r--winsup/cygwin/path.cc25
-rw-r--r--winsup/cygwin/pinfo.cc112
-rw-r--r--winsup/cygwin/pinfo.h45
-rw-r--r--winsup/cygwin/sigproc.cc13
-rw-r--r--winsup/cygwin/sigproc.h3
-rw-r--r--winsup/cygwin/spawn.cc101
-rw-r--r--winsup/cygwin/strace.cc4
-rw-r--r--winsup/cygwin/syscalls.cc1
-rw-r--r--winsup/cygwin/thread.cc135
-rw-r--r--winsup/cygwin/thread.h8
-rw-r--r--winsup/cygwin/times.cc1
-rw-r--r--winsup/cygwin/uinfo.cc1
-rw-r--r--winsup/cygwin/winsup.h14
33 files changed, 322 insertions, 431 deletions
diff --git a/winsup/cygwin/ChangeLog b/winsup/cygwin/ChangeLog
index bdc040099..695ada4a9 100644
--- a/winsup/cygwin/ChangeLog
+++ b/winsup/cygwin/ChangeLog
@@ -1,3 +1,49 @@
+Mon Oct 16 18:37:22 2000 Christopher Faylor <cgf@cygnus.com>
+
+ * Makefile.in: Remove some obsolete stuff.
+ * dcrt0.cc (dll_crt0_1): Call signal_fixup_after_exec where appropriate.
+ Set myself->uid from parent version.
+ Just use ThreadItem Init method. Close or store hexec_proc as appropriate.
+ (_dll_crt0): Store user_data->forkee here so that proper tests can be made
+ subsequently.
+ (do_exit): Remove hExeced stuff.
+ * environ.cc (environ_init): Accept environ count as well as environ pointer.
+ * environ.h: Reflect above change.
+ * pinfo.cc (pinfo_init): Ditto. Accept environ count.
+ (fixup_in_spawned_child): Remove.
+ * spawn.cc (spawn_guts): Move signal code to dll_crt0_1. Don't suspend
+ execing process since it is no longer necessary. Store envc.
+ * exceptions.cc (signal_fixup_after_exec): New function.
+ (call_handler): Remove hExeced test.
+ * child_info.h (cygheap_exec_info): Store envc as well as envp.
+ (child_info_spawn): Store hexec_proc so that it can be closed in child.
+ * path.cc (normalize_posix_path): Avoid intermediate use of temporary cwd buf.
+ (normalize_win32_path): Ditto.
+ (cwdstuff::get_initial): Always set lock.
+ * sigproc.h: Remove hExeced.
+ * strace.cc (strace::vsprntf): Modify to accomodate for lack of hExeced.
+ * thread.cc (MTinterface::Init): Merge Init1 and ClearReent into this method.
+ (MTinterface::Init1): Eliminate.
+ (MTinterface::ClearReent): Eliminate.
+ * thread.h: Reflect above changes.
+ * include/sys/strace.h (strace): Make microseconds() public.
+
+Sun Oct 15 21:54:52 2000 Christopher Faylor <cgf@cygnus.com>
+
+ Make various functions 'regparm', throughout.
+ * pinfo.h (_pinfo): Inline simple signal manipulation functions.
+ Requires inclusion of thread.h which was removed from .cc files, where
+ appropriate. throughout.
+ * pinfo.cc: Eliminate signal manipulation functions.
+ (_pinfo::exit): Calculate total rusage for exiting process here.
+ * cygheap.cc (size2bucket): Eliminate.
+ (init_buckets): Ditto.
+ (_cmalloc): Calculate size and bits in a loop rather than going through
+ a function call.
+ (_crealloc): Use stored array index to calculate allocated size.
+ * spawn.cc (spawn_guts): Use _pinfo exit method to exit, calculating
+ cpu usage.
+
Sat Oct 14 21:24:16 2000 Christopher Faylor <cgf@cygnus.com>
* exceptions.cc (set_console_handler): Don't allocate
diff --git a/winsup/cygwin/Makefile.in b/winsup/cygwin/Makefile.in
index a5a780e24..2d2f4083c 100644
--- a/winsup/cygwin/Makefile.in
+++ b/winsup/cygwin/Makefile.in
@@ -51,7 +51,7 @@ CC:=@CC@
# FIXME: Which is it, CC or CC_FOR_TARGET?
CC_FOR_TARGET:=$(CC)
CFLAGS:=@CFLAGS@
-CFLAGS+=-MD
+CFLAGS+=-MD -fbuiltin
CXXFLAGS:=@CXXFLAGS@
# For linking mount, etc. crt0.o isn't accessable in a fresh build.
@@ -84,11 +84,6 @@ RUNTEST = `if [ -f $${srcdir}/../dejagnu/runtest ] ; then \
else echo runtest; fi`
RUNTESTFLAGS =
-ifdef MT_SAFE
-MT_SAFE_HEADERS:=thread.h
-MT_SAFE_OBJECTS:=pthread.o thread.o
-endif
-
# Parameters used in building the cygwin.dll.
# We build as new-cygwin.dll and rename at install time to overcome
# native rebuilding issues (we don't want the build tools to see a partially
@@ -123,11 +118,11 @@ DLL_OFILES:=assert.o cygheap.o dcrt0.o debug.o delqueue.o dir.o dlfcn.o \
fhandler_random.o fhandler_raw.o fhandler_serial.o fhandler_tape.o \
fhandler_termios.o fhandler_tty.o fhandler_windows.o fhandler_zero.o \
fork.o glob.o grp.o heap.o init.o ioctl.o localtime.o malloc.o mmap.o \
- net.o ntea.o passwd.o path.o pinfo.o pipe.o poll.o regexp.o regerror.o \
- regsub.o registry.o resource.o scandir.o security.o select.o shared.o \
- signal.o sigproc.o smallprint.o spawn.o strace.o strsep.o sync.o \
- syscalls.o sysconf.o syslog.o termios.o times.o tty.o uinfo.o uname.o \
- wait.o window.o \
+ net.o ntea.o passwd.o path.o pinfo.o pipe.o poll.o pthread.o regexp.o \
+ regerror.o regsub.o registry.o resource.o scandir.o security.o select.o \
+ shared.o signal.o sigproc.o smallprint.o spawn.o strace.o strsep.o \
+ sync.o syscalls.o sysconf.o syslog.o termios.o thread.o times.o tty.o \
+ uinfo.o uname.o wait.o window.o \
$(EXTRA_DLL_OFILES) $(EXTRA_OFILES) $(MT_SAFE_OBJECTS)
GMON_OFILES:= gmon.o mcount.o profil.o
@@ -219,15 +214,6 @@ Makefile: cygwin.din
$(DEF_FILE): cygwin.din config.status
$(SHELL) config.status
-# .h file dependencies
-# This may be overkill, but it's better than the previous situation.
-# As files/dependencies are added and removed from Cygwin, please keep
-# this list up to date.
-
-WINSUP_H:=winsup.h fhandler.h path.h shared.h \
- sigproc.h include/cygwin/version.h \
- $(MT_SAFE_HEADERS)
-
winsup.h: config.h
ifneq (,${wildcard *.d})
diff --git a/winsup/cygwin/child_info.h b/winsup/cygwin/child_info.h
index b3018c67b..725833050 100644
--- a/winsup/cygwin/child_info.h
+++ b/winsup/cygwin/child_info.h
@@ -60,12 +60,14 @@ class fhandler_base;
class cygheap_exec_info
{
public:
+ uid_t uid;
char *old_title;
fhandler_base **fds;
size_t nfds;
int argc;
char **argv;
- char **environ;
+ int envc;
+ char **envp;
HANDLE myself_pinfo;
char *cwd_posix;
char *cwd_win32;
@@ -76,6 +78,7 @@ class child_info_spawn: public child_info
{
public:
cygheap_exec_info *moreinfo;
+ HANDLE hexec_proc;
child_info_spawn (): moreinfo (NULL) {}
~child_info_spawn ()
@@ -90,11 +93,11 @@ public:
cfree (moreinfo->cwd_posix);
if (moreinfo->cwd_win32)
cfree (moreinfo->cwd_win32);
- if (moreinfo->environ)
+ if (moreinfo->envp)
{
- for (char **e = moreinfo->environ; *e; e++)
+ for (char **e = moreinfo->envp; *e; e++)
cfree (*e);
- cfree (moreinfo->environ);
+ cfree (moreinfo->envp);
}
CloseHandle (moreinfo->myself_pinfo);
cfree (moreinfo);
diff --git a/winsup/cygwin/cygerrno.h b/winsup/cygwin/cygerrno.h
index c83120095..dd40819b9 100644
--- a/winsup/cygwin/cygerrno.h
+++ b/winsup/cygwin/cygerrno.h
@@ -8,9 +8,9 @@ This software is a copyrighted work licensed under the terms of the
Cygwin license. Please consult the file "CYGWIN_LICENSE" for
details. */
-void __stdcall seterrno_from_win_error (const char *file, int line, DWORD code);
-void __stdcall seterrno (const char *, int line);
-int __stdcall geterrno_from_win_error (DWORD code, int deferrno);
+void __stdcall seterrno_from_win_error (const char *file, int line, DWORD code) __attribute__ ((regparm(3)));
+void __stdcall seterrno (const char *, int line) __attribute__ ((regparm(2)));
+int __stdcall geterrno_from_win_error (DWORD code, int deferrno) __attribute__ ((regparm(2)));
#define __seterrno() seterrno (__FILE__, __LINE__)
#define __seterrno_from_win_error(val) seterrno_from_win_error (__FILE__, __LINE__, val)
diff --git a/winsup/cygwin/cygheap.cc b/winsup/cygwin/cygheap.cc
index 21bde12e1..e583c1efc 100644
--- a/winsup/cygwin/cygheap.cc
+++ b/winsup/cygwin/cygheap.cc
@@ -70,35 +70,6 @@ _csbrk (int sbs)
#define NBUCKETS 32
char *buckets[NBUCKETS] = {0};
-int bucket2size[NBUCKETS] = {0};
-
-static inline int
-size2bucket (int size)
-{
- int rv = 0x1f;
- int bit = ~0x10;
- int i;
-
- if (size < 4)
- size = 4;
- size = (size + 3) & ~3;
-
- for (i = 0; i < 5; i++)
- {
- if (bucket2size[rv & bit] >= size)
- rv &= bit;
- bit >>= 1;
- }
- return rv;
-}
-
-static inline void
-init_buckets ()
-{
- unsigned b;
- for (b = 0; b < NBUCKETS; b++)
- bucket2size[b] = (1 << b);
-}
struct _cmalloc_entry
{
@@ -116,16 +87,19 @@ struct _cmalloc_entry
#define to_cmalloc(s) ((_cmalloc_entry *) (((char *) (s)) - (int) (N0->data)))
#define cygheap_chain ((_cmalloc_entry **)cygheap)
+static void *_cmalloc (int size) __attribute ((regparm(1)));
+static void *__stdcall _crealloc (void *ptr, int size) __attribute ((regparm(2)));
+
static void *__stdcall
_cmalloc (int size)
{
_cmalloc_entry *rvc;
- int b;
+ int b, sz;
- if (bucket2size[0] == 0)
- init_buckets ();
+ /* Calculate "bit bucket" and size as a power of two. */
+ for (b = 3, sz = 8; sz && sz < (size + 4); b++, sz <<= 1)
+ continue;
- b = size2bucket (size);
cygheap_protect->acquire ();
if (buckets[b])
{
@@ -135,7 +109,7 @@ _cmalloc (int size)
}
else
{
- size = bucket2size[b] + sizeof (_cmalloc_entry);
+ size = sz + sizeof (_cmalloc_entry);
rvc = (_cmalloc_entry *) _csbrk (size);
rvc->b = b;
@@ -165,7 +139,7 @@ _crealloc (void *ptr, int size)
newptr = _cmalloc (size);
else
{
- int oldsize = bucket2size[to_cmalloc (ptr)->b];
+ int oldsize = 1 << to_cmalloc (ptr)->b;
if (size <= oldsize)
return ptr;
newptr = _cmalloc (size);
@@ -228,7 +202,7 @@ cygheap_fixup_in_child (HANDLE parent, bool execed)
}
}
-static void *__stdcall
+inline static void *
creturn (cygheap_types x, cygheap_entry * c, int len)
{
if (!c)
diff --git a/winsup/cygwin/cygheap.h b/winsup/cygwin/cygheap.h
index fc335c231..425185c6a 100644
--- a/winsup/cygwin/cygheap.h
+++ b/winsup/cygwin/cygheap.h
@@ -32,12 +32,12 @@ extern HANDLE cygheap_max;
#define incygheap(s) (cygheap && ((char *) (s) >= (char *) cygheap) && ((char *) (s) <= ((char *) cygheap_max)))
extern "C" {
-void __stdcall cfree (void *);
+void __stdcall cfree (void *) __attribute__ ((regparm(1)));
void __stdcall cygheap_fixup_in_child (HANDLE, bool);
-void *__stdcall cmalloc (cygheap_types, DWORD);
-void *__stdcall crealloc (void *, DWORD);
-void *__stdcall ccalloc (cygheap_types, DWORD, DWORD);
-char *__stdcall cstrdup (const char *);
-char *__stdcall cstrdup1 (const char *);
+void *__stdcall cmalloc (cygheap_types, DWORD) __attribute__ ((regparm(2)));
+void *__stdcall crealloc (void *, DWORD) __attribute__ ((regparm(2)));
+void *__stdcall ccalloc (cygheap_types, DWORD, DWORD) __attribute__ ((regparm(3)));
+char *__stdcall cstrdup (const char *) __attribute__ ((regparm(1)));
+char *__stdcall cstrdup1 (const char *) __attribute__ ((regparm(1)));
void __stdcall cygheap_init ();
}
diff --git a/winsup/cygwin/dcrt0.cc b/winsup/cygwin/dcrt0.cc
index 5adf59478..117cb75c6 100644
--- a/winsup/cygwin/dcrt0.cc
+++ b/winsup/cygwin/dcrt0.cc
@@ -15,6 +15,7 @@ details. */
#include "exceptions.h"
#include "autoload.h"
#include <ctype.h>
+#include <limits.h>
#include "sync.h"
#include "sigproc.h"
#include "pinfo.h"
@@ -27,7 +28,6 @@ details. */
#include "perthread.h"
#include "path.h"
#include "dtable.h"
-#include "thread.h"
#include "shared_info.h"
#include "cygwin_version.h"
#include "perprocess.h"
@@ -650,7 +650,7 @@ dll_crt0_1 ()
_impure_ptr = &reent_data;
user_data->resourcelocks->Init ();
- user_data->threadinterface->Init0 ();
+ user_data->threadinterface->Init (user_data->forkee);
threadname_init ();
debug_init ();
@@ -658,6 +658,7 @@ dll_crt0_1 ()
regthread ("main", GetCurrentThreadId ());
+ int envc = 0;
char **envp = NULL;
if (child_proc_info)
@@ -671,14 +672,17 @@ dll_crt0_1 ()
cygheap_fixup_in_child (child_proc_info->parent, 0);
alloc_stack (fork_info);
set_myself (mypid);
- user_data->forkee = child_proc_info->cygpid;
user_data->heaptop = child_proc_info->heaptop;
user_data->heapbase = child_proc_info->heapbase;
user_data->heapptr = child_proc_info->heapptr;
ProtectHandle (child_proc_info->forker_finished);
break;
- case PROC_EXEC:
case PROC_SPAWN:
+ CloseHandle (spawn_info->hexec_proc);
+ goto around;
+ case PROC_EXEC:
+ hexec_proc = spawn_info->hexec_proc;
+ around:
HANDLE h;
cygheap_fixup_in_child (spawn_info->parent, 1);
if (!spawn_info->moreinfo->myself_pinfo ||
@@ -689,12 +693,14 @@ dll_crt0_1 ()
set_myself (mypid, h);
__argc = spawn_info->moreinfo->argc;
__argv = spawn_info->moreinfo->argv;
- envp = spawn_info->moreinfo->environ;
+ envp = spawn_info->moreinfo->envp;
+ envc = spawn_info->moreinfo->envc;
cygcwd.fixup_after_exec (spawn_info->moreinfo->cwd_win32,
spawn_info->moreinfo->cwd_posix,
spawn_info->moreinfo->cwd_hash);
fdtab.fixup_after_exec (spawn_info->parent, spawn_info->moreinfo->nfds,
spawn_info->moreinfo->fds);
+ signal_fixup_after_exec (child_proc_info->type == PROC_SPAWN);
CloseHandle (spawn_info->parent);
if (spawn_info->moreinfo->old_title)
{
@@ -702,6 +708,9 @@ dll_crt0_1 ()
cfree (spawn_info->moreinfo->old_title);
}
ProtectHandle (child_proc_info->subproc_ready);
+ myself->uid = spawn_info->moreinfo->uid;
+ if (myself->uid == USHRT_MAX)
+ myself->use_psid = 0;
break;
}
}
@@ -730,6 +739,8 @@ dll_crt0_1 ()
instead of each time a file is opened. */
set_process_privileges ();
+ cygbench ("pre-forkee");
+
if (user_data->forkee)
{
/* If we've played with the stack, stacksize != 0. That means that
@@ -751,24 +762,11 @@ dll_crt0_1 ()
cygcwd.init ();
/* Initialize our process table entry. */
- pinfo_init (envp);
+ pinfo_init (envp, envc);
if (!old_title && GetConsoleTitle (title_buf, TITLESIZE))
old_title = title_buf;
- /* Nasty static stuff needed by newlib - initialize it.
- Note that impure_ptr has already been set up to point to this above
- NB. This *MUST* be done here, just after the forkee code as some
- of the calls below (eg. uinfo_init) do stdio calls - this area must
- be set to zero before then. */
-
- user_data->threadinterface->ClearReent();
- user_data->threadinterface->Init1();
-
- char *line = GetCommandLineA ();
-
- line = strcpy ((char *) alloca (strlen (line) + 1), line);
-
/* Allocate fdtab */
dtable_init ();
@@ -786,6 +784,9 @@ dll_crt0_1 ()
if (!__argc)
{
+ char *line = GetCommandLineA ();
+ line = strcpy ((char *) alloca (strlen (line) + 1), line);
+
/* Scan the command line and build argv. Expand wildcards if not
called from another cygwin process. */
build_argv (line, __argv, __argc,
@@ -848,6 +849,7 @@ dll_crt0_1 ()
set_errno (0);
MALLOC_CHECK;
+ cygbench (__progname);
if (user_data->main)
exit (user_data->main (__argc, __argv, *user_data->envptr));
}
@@ -862,6 +864,9 @@ extern "C" void __stdcall
_dll_crt0 ()
{
char zeros[sizeof (fork_info->zero)] = {0};
+#ifdef DEBUGGING
+ strace.microseconds ();
+#endif
/* Set the os_being_run global. */
set_os_type ();
@@ -893,10 +898,11 @@ _dll_crt0 ()
{
switch (fork_info->type)
{
- case PROC_EXEC:
- case PROC_SPAWN:
case PROC_FORK:
case PROC_FORK1:
+ user_data->forkee = fork_info->cygpid;
+ case PROC_EXEC:
+ case PROC_SPAWN:
{
child_proc_info = fork_info;
mypid = child_proc_info->cygpid;
@@ -997,9 +1003,7 @@ do_exit (int status)
}
}
- if ((hExeced && hExeced != INVALID_HANDLE_VALUE) || (n & EXIT_NOCLOSEALL))
- n &= ~EXIT_NOCLOSEALL;
- else if (exit_state < ES_CLOSEALL)
+ if (exit_state < ES_CLOSEALL)
{
exit_state = ES_CLOSEALL;
close_all_files ();
@@ -1024,6 +1028,8 @@ do_exit (int status)
/* Kill orphaned children on group leader exit */
if (myself->pid == myself->pgid)
{
+ system_printf ("%d == pgrp %d, send SIG{HUP,CONT} to stopped children",
+ myself->pid, myself->pgid);
sigproc_printf ("%d == pgrp %d, send SIG{HUP,CONT} to stopped children",
myself->pid, myself->pgid);
kill_pgrp (myself->pgid, -SIGHUP);
@@ -1044,17 +1050,7 @@ do_exit (int status)
}
window_terminate ();
- fill_rusage (&myself->rusage_self, hMainProc);
-
events_terminate ();
-
- if (hExeced && hExeced != INVALID_HANDLE_VALUE)
- {
- debug_printf ("Killing(%d) non-cygwin process, handle %p", n, hExeced);
- TerminateProcess (hExeced, n);
- ForceCloseHandle1 (hExeced, childhProc);
- }
-
shared_terminate ();
minimal_printf ("winpid %d, exit %d", GetCurrentProcessId (), n);
@@ -1101,6 +1097,16 @@ __api_fatal (const char *fmt, ...)
myself->exit (1);
}
+#ifdef DEBUGGING
+void __stdcall
+cygbench (const char *s)
+{
+ char buf[1024];
+ if (GetEnvironmentVariable ("CYGWIN_BENCH", buf, sizeof (buf)))
+ small_printf ("%05d ***** %s : %10d\n", GetCurrentProcessId (), s, strace.microseconds ());
+}
+#endif
+
extern "C" {
/* This struct is unused, but it illustrates the layout of a DLL
diff --git a/winsup/cygwin/debug.h b/winsup/cygwin/debug.h
index 419cbab1b..ff4313f77 100644
--- a/winsup/cygwin/debug.h
+++ b/winsup/cygwin/debug.h
@@ -16,22 +16,12 @@ details. */
#endif
extern "C" {
-#ifndef DEBUGGING0
-DWORD __stdcall WFSO (HANDLE, DWORD);
-DWORD __stdcall WFMO (DWORD, CONST HANDLE *, BOOL, DWORD);
-#else
-DWORD __stdcall WFSO (const char *fn, int ln, HANDLE, DWORD);
-DWORD __stdcall WFMO (const char *fn, int ln, DWORD, CONST HANDLE *, BOOL, DWORD);
-#endif
+DWORD __stdcall WFSO (HANDLE, DWORD) __attribute__ ((regparm(2)));
+DWORD __stdcall WFMO (DWORD, CONST HANDLE *, BOOL, DWORD) __attribute__ ((regparm(3)));
}
-#ifndef DEBUGGING0
#define WaitForSingleObject WFSO
#define WaitForMultipleObject WFMO
-#else
-#define WaitForSingleObject(a, b) WFSO (__FUNCTION__, __LINE__, a, b)
-#define WaitForMultipleObject(a, b, c, d) WFMO (__FUNCTION__, __LINE__, a, b, c, d)
-#endif
#if !defined(_DEBUG_H_)
#define _DEBUG_H_
@@ -43,6 +33,7 @@ void __stdcall regthread (const char *, DWORD);
int __stdcall iscygthread ();
#ifndef DEBUGGING
+# define cygbench(s)
# define ForceCloseHandle CloseHandle
# define ForceCloseHandle1(h, n) CloseHandle (h)
# define ForceCloseHandle2(h, n) CloseHandle (h)
@@ -75,6 +66,7 @@ void debug_init ();
void __stdcall add_handle (const char *, int, HANDLE, const char *);
BOOL __stdcall close_handle (const char *, int, HANDLE, const char *, BOOL);
int __stdcall lpfu (const char *, int, DWORD timeout);
+void __stdcall cygbench (const char *s);
#endif /*DEBUGGING*/
#endif /*_DEBUG_H_*/
diff --git a/winsup/cygwin/dtable.cc b/winsup/cygwin/dtable.cc
index 7d520b6da..be92bfce4 100644
--- a/winsup/cygwin/dtable.cc
+++ b/winsup/cygwin/dtable.cc
@@ -29,7 +29,6 @@ details. */
#include "fhandler.h"
#include "path.h"
#include "dtable.h"
-#include "thread.h"
dtable fdtab;
@@ -154,7 +153,7 @@ dtable::release (int fd)
{
if (!not_open (fd))
{
- delete fds[fd]; /* CGF FIXME */
+ delete fds[fd];
fds[fd] = NULL;
}
}
diff --git a/winsup/cygwin/dtable.h b/winsup/cygwin/dtable.h
index 85963fc2d..1952e944b 100644
--- a/winsup/cygwin/dtable.h
+++ b/winsup/cygwin/dtable.h
@@ -27,14 +27,14 @@ public:
fhandler_base *build_fhandler (int fd, DWORD dev, const char *name,
int unit = -1);
fhandler_base *build_fhandler (int fd, const char *name, HANDLE h);
- int not_open (int n);
+ int not_open (int n) __attribute__ ((regparm(1)));
int find_unused_handle (int start);
int find_unused_handle () { return find_unused_handle (first_fd_for_open);}
void release (int fd);
void init_std_file_from_handle (int fd, HANDLE handle, DWORD access, const char *name);
int dup2 (int oldfd, int newfd);
void fixup_after_exec (HANDLE, size_t, fhandler_base **);
- fhandler_base *operator [](int fd) { return fds[fd]; }
+ inline fhandler_base *operator [](int fd) { return fds[fd]; }
select_record *select_read (int fd, select_record *s);
select_record *select_write (int fd, select_record *s);
select_record *select_except (int fd, select_record *s);
diff --git a/winsup/cygwin/environ.cc b/winsup/cygwin/environ.cc
index f0a3fc7d7..612e7e13e 100644
--- a/winsup/cygwin/environ.cc
+++ b/winsup/cygwin/environ.cc
@@ -517,10 +517,10 @@ regopt (const char *name)
* environment variable and set appropriate options from it.
*/
void
-environ_init (char **envp)
+environ_init (char **envp, int envc)
{
char *rawenv;
- int sz, i;
+ int i;
char *p;
char *newp;
int sawTERM = 0;
@@ -541,9 +541,8 @@ environ_init (char **envp)
envp_passed_in = 0;
else
{
- sz = envsize (envp, 1);
- char **newenv = (char **) malloc (sz);
- memcpy (newenv, envp, sz);
+ char **newenv = (char **) malloc (envc);
+ memcpy (newenv, envp, envc);
cfree (envp);
envp = newenv;
envp_passed_in = 1;
@@ -551,7 +550,7 @@ environ_init (char **envp)
}
/* Allocate space for environment + trailing NULL + CYGWIN env. */
- lastenviron = envp = (char **) malloc ((4 + (sz = 100)) * sizeof (char *));
+ lastenviron = envp = (char **) malloc ((4 + (envc = 100)) * sizeof (char *));
rawenv = GetEnvironmentStrings ();
/* Current directory information is recorded as variables of the
@@ -561,9 +560,8 @@ environ_init (char **envp)
for (i = 0, p = rawenv; *p != '\0'; p = strchr (p, '\0') + 1, i++)
{
newp = strdup (p);
- if (i >= sz)
- envp = (char **) realloc (envp, (4 + (sz += 100)) *
- sizeof (char *));
+ if (i >= envc)
+ envp = (char **) realloc (envp, (4 + (envc += 100)) * sizeof (char *));
envp[i] = newp;
if (*newp == '=')
*newp = '!';
diff --git a/winsup/cygwin/environ.h b/winsup/cygwin/environ.h
index e5967eb20..888b473dd 100644
--- a/winsup/cygwin/environ.h
+++ b/winsup/cygwin/environ.h
@@ -9,7 +9,7 @@ Cygwin license. Please consult the file "CYGWIN_LICENSE" for
details. */
/* Initialize the environment */
-void environ_init (char **);
+void environ_init (char **, int);
/* The structure below is used to control conversion to/from posix-style
* file specs. Currently, only PATH and HOME are converted, but PATH
diff --git a/winsup/cygwin/exceptions.cc b/winsup/cygwin/exceptions.cc
index 8a65f355b..75ad01c67 100644
--- a/winsup/cygwin/exceptions.cc
+++ b/winsup/cygwin/exceptions.cc
@@ -18,7 +18,6 @@ details. */
#include "sigproc.h"
#include "pinfo.h"
#include "cygerrno.h"
-#include "thread.h"
#include "perthread.h"
#include "shared_info.h"
#include "perprocess.h"
@@ -639,7 +638,7 @@ interrupt_now (CONTEXT *ctx, int sig, struct sigaction& siga, void *handler)
SetThreadContext (myself->getthread2signal (), ctx); /* Restart the thread */
}
-void __cdecl
+void __stdcall
signal_fixup_after_fork ()
{
if (!sigsave.sig)
@@ -653,6 +652,18 @@ signal_fixup_after_fork ()
}
}
+void __stdcall
+signal_fixup_after_exec (bool isspawn)
+{
+ /* Set up child's signal handlers */
+ for (int i = 0; i < NSIG; i++)
+ {
+ myself->getsig(i).sa_mask = 0;
+ if (myself->getsig(i).sa_handler != SIG_IGN || isspawn)
+ myself->getsig(i).sa_handler = SIG_DFL;
+ }
+}
+
static int
interrupt_on_return (DWORD ebp, int sig, struct sigaction& siga, void *handler)
{
@@ -775,7 +786,7 @@ call_handler (int sig, struct sigaction& siga, void *handler)
}
next:
- if (hExeced != NULL || (!using_mainthread_frame && interruptible (cx.Eip)))
+ if (!using_mainthread_frame && interruptible (cx.Eip))
interrupt_now (&cx, sig, siga, handler);
else if (!interrupt_on_return (ebp, sig, siga, handler))
{
diff --git a/winsup/cygwin/fhandler.cc b/winsup/cygwin/fhandler.cc
index 7c1299bf8..f6ce3adf9 100644
--- a/winsup/cygwin/fhandler.cc
+++ b/winsup/cygwin/fhandler.cc
@@ -463,7 +463,7 @@ fhandler_base::read (void *in_ptr, size_t in_len)
}
/* Scan buffer and turn \r\n into \n */
- register char *src= (char *) ptr;
+ register char *src = (char *) ptr;
register char *dst = (char *) ptr;
register char *end = src + copied_chars - 1;
@@ -772,7 +772,7 @@ rootdir(char *full_path)
* \\server\share... -> \\server\share\
* else current drive.
*/
- char *root=full_path;
+ char *root = full_path;
if (full_path[1] == ':')
strcpy (full_path + 2, "\\");
diff --git a/winsup/cygwin/fork.cc b/winsup/cygwin/fork.cc
index c51fe23a3..a883ed553 100644
--- a/winsup/cygwin/fork.cc
+++ b/winsup/cygwin/fork.cc
@@ -301,6 +301,7 @@ fork_child (HANDLE& hParent, dll *&first_dll, bool& load_dlls)
/* Initialize signal/process handling */
sigproc_init ();
+ cygbench ("fork-child");
return 0;
}
diff --git a/winsup/cygwin/grp.cc b/winsup/cygwin/grp.cc
index 9c4f3794a..0469c0217 100644
--- a/winsup/cygwin/grp.cc
+++ b/winsup/cygwin/grp.cc
@@ -16,7 +16,6 @@ details. */
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
-#include "thread.h"
#include "sync.h"
#include "sigproc.h"
#include "pinfo.h"
diff --git a/winsup/cygwin/include/sys/strace.h b/winsup/cygwin/include/sys/strace.h
index 82cc75d5c..d40e3ad7d 100644
--- a/winsup/cygwin/include/sys/strace.h
+++ b/winsup/cygwin/include/sys/strace.h
@@ -23,10 +23,10 @@
class strace
{
- int microseconds ();
int vsprntf (char *buf, const char *func, const char *infmt, va_list ap);
void write (unsigned category, const char *buf, int count);
public:
+ int microseconds ();
int version;
int active;
int lmicrosec;
diff --git a/winsup/cygwin/mmap.cc b/winsup/cygwin/mmap.cc
index 6beb45a2e..6d00a53f1 100644
--- a/winsup/cygwin/mmap.cc
+++ b/winsup/cygwin/mmap.cc
@@ -16,7 +16,6 @@ details. */
#include "fhandler.h"
#include "dtable.h"
#include "cygerrno.h"
-#include "thread.h"
#include "sync.h"
#include "sigproc.h"
#include "pinfo.h"
diff --git a/winsup/cygwin/net.cc b/winsup/cygwin/net.cc
index c6d88f613..bb33bca57 100644
--- a/winsup/cygwin/net.cc
+++ b/winsup/cygwin/net.cc
@@ -27,7 +27,6 @@ details. */
#include "fhandler.h"
#include "path.h"
#include "dtable.h"
-#include "thread.h"
#include "sync.h"
#include "sigproc.h"
#include "pinfo.h"
diff --git a/winsup/cygwin/passwd.cc b/winsup/cygwin/passwd.cc
index 29e912699..62b2955a0 100644
--- a/winsup/cygwin/passwd.cc
+++ b/winsup/cygwin/passwd.cc
@@ -16,7 +16,6 @@ details. */
#include "cygerrno.h"
#include "fhandler.h"
#include "dtable.h"
-#include "thread.h"
#include "sync.h"
#include "sigproc.h"
#include "pinfo.h"
diff --git a/winsup/cygwin/path.cc b/winsup/cygwin/path.cc
index cfc81263a..cbd6e5493 100644
--- a/winsup/cygwin/path.cc
+++ b/winsup/cygwin/path.cc
@@ -62,7 +62,6 @@ details. */
#include "cygerrno.h"
#include "fhandler.h"
#include "path.h"
-#include "thread.h"
#include "sync.h"
#include "sigproc.h"
#include "pinfo.h"
@@ -574,15 +573,13 @@ normalize_posix_path (const char *src, char *dst)
}
if (!isslash (src[0]))
{
- char cwd[MAX_PATH];
- if (!cygcwd.get (cwd))
+ if (!cygcwd.get (dst))
return get_errno ();
- if (strlen (cwd) + 1 + strlen (src) >= MAX_PATH)
+ if (strlen (dst) + 1 + strlen (src) >= MAX_PATH)
{
debug_printf ("ENAMETOOLONG = normalize_posix_path (%s)", src);
return ENAMETOOLONG;
}
- strcpy (dst, cwd);
dst = strchr (dst, '\0');
if (*src == '.')
goto sawdot;
@@ -681,17 +678,15 @@ normalize_win32_path (const char *src, char *dst)
if (!SLASH_P (src[0]) && strchr (src, ':') == NULL)
{
- char cwd[MAX_PATH];
- if (!cygcwd.get (cwd, 0))
+ if (!cygcwd.get (dst, 0))
return get_errno ();
- if (strlen (cwd) + 1 + strlen (src) >= MAX_PATH)
+ if (strlen (dst) + 1 + strlen (src) >= MAX_PATH)
{
debug_printf ("ENAMETOOLONG = normalize_win32_path (%s)", src);
return ENAMETOOLONG;
}
- strcpy (dst, cwd);
dst += strlen (dst);
- if (!*cwd || !SLASH_P (dst[-1]))
+ if (!SLASH_P (dst[-1]))
*dst++ = '\\';
}
/* Two leading \'s? If so, preserve them. */
@@ -2775,7 +2770,7 @@ cygwin_split_path (const char *path, char *dir, char *file)
})
/* Return TRUE if two strings match up to length n */
-int __stdcall
+extern "C" int __stdcall
strncasematch (const char *s1, const char *s2, size_t n)
{
if (s1 == s2)
@@ -2792,7 +2787,7 @@ strncasematch (const char *s1, const char *s2, size_t n)
}
/* Return TRUE if two strings match */
-int __stdcall
+extern "C" int __stdcall
strcasematch (const char *s1, const char *s2)
{
if (s1 == s2)
@@ -2807,7 +2802,7 @@ strcasematch (const char *s1, const char *s2)
return *s2 == '\0';
}
-char * __stdcall
+extern "C" char * __stdcall
strcasestr (const char *searchee, const char *lookfor)
{
if (*searchee == 0)
@@ -2881,10 +2876,11 @@ cwdstuff::fixup_after_exec (char *win32_cwd, char *posix_cwd, DWORD hash_cwd)
bool
cwdstuff::get_initial ()
{
+ lock->acquire ();
+
if (win32)
return 1;
- lock->acquire ();
int i;
DWORD len, dlen;
for (i = 0, dlen = MAX_PATH, len = 0; i < 3; dlen *= 2, i++)
@@ -2899,6 +2895,7 @@ cwdstuff::get_initial ()
__seterrno ();
lock->release ();
debug_printf ("get_initial_cwd failed, %E");
+ lock->release ();
return 0;
}
set (NULL);
diff --git a/winsup/cygwin/pinfo.cc b/winsup/cygwin/pinfo.cc
index 8d037e3af..21aa0fb8d 100644
--- a/winsup/cygwin/pinfo.cc
+++ b/winsup/cygwin/pinfo.cc
@@ -16,7 +16,6 @@ details. */
#include "fhandler.h"
#include "dtable.h"
#include "cygerrno.h"
-#include "thread.h"
#include "sync.h"
#include "sigproc.h"
#include "pinfo.h"
@@ -30,7 +29,7 @@ static char NO_COPY pinfo_dummy[sizeof(pinfo)] = {0};
pinfo NO_COPY myself ((_pinfo *)&pinfo_dummy); // Avoid myself != NULL checks
-static HANDLE hexec_proc = NULL;
+HANDLE hexec_proc = NULL;
void __stdcall
pinfo_fixup_after_fork ()
@@ -46,19 +45,6 @@ pinfo_fixup_after_fork ()
}
}
-void __stdcall
-pinfo_fixup_in_spawned_child (HANDLE hchild)
-{
- HANDLE h;
- if (!hexec_proc)
- return;
- if (!DuplicateHandle (hchild, hexec_proc, hMainProc, &h, 0, TRUE,
- DUPLICATE_CLOSE_SOURCE))
- system_printf ("couldn't close handle %p in child, %E", hexec_proc);
- else
- CloseHandle (h);
-}
-
/* Initialize the process table.
This is done once when the dll is first loaded. */
@@ -102,11 +88,11 @@ set_myself (pid_t pid, HANDLE h)
/* Initialize the process table entry for the current task.
This is not called for fork'd tasks, only exec'd ones. */
void __stdcall
-pinfo_init (char **envp)
+pinfo_init (char **envp, int envc)
{
if (envp)
{
- environ_init (envp);
+ environ_init (envp, envc);
/* spawn has already set up a pid structure for us so we'll use that */
myself->process_state |= PID_CYGPARENT;
}
@@ -120,96 +106,26 @@ pinfo_init (char **envp)
myself->ctty = -1;
myself->uid = USHRT_MAX;
- environ_init (NULL); /* call after myself has been set up */
+ environ_init (NULL, 0); /* call after myself has been set up */
}
debug_printf ("pid %d, pgid %d", myself->pid, myself->pgid);
}
void
-_pinfo::exit (UINT n)
+_pinfo::exit (UINT n, bool norecord)
{
- process_state = PID_EXITED;
- sigproc_printf ("Calling ExitProcess %d", n);
- ExitProcess (n);
-}
+ if (!norecord)
+ process_state = PID_EXITED;
-struct sigaction&
-_pinfo::getsig(int sig)
-{
-#ifdef _MT_SAFE
- if (thread2signal)
- return thread2signal->sigs[sig];
- return sigs[sig];
-#else
- return sigs[sig];
-#endif
-};
-
-sigset_t&
-_pinfo::getsigmask ()
-{
-#ifdef _MT_SAFE
- if (thread2signal)
- return *thread2signal->sigmask;
- return sig_mask;
-#else
- return sig_mask;
-#endif
-};
-
-void
-_pinfo::setsigmask (sigset_t _mask)
-{
-#ifdef _MT_SAFE
- if (thread2signal)
- *(thread2signal->sigmask) = _mask;
- sig_mask=_mask;
-#else
- sig_mask=_mask;
-#endif
-}
+ /* FIXME: There is a potential race between an execed process and its
+ parent here. I hated to add a mutex just for this, though. */
+ struct rusage r;
+ fill_rusage (&r, hMainProc);
+ add_rusage (&rusage_self, &r);
-LONG *
-_pinfo::getsigtodo(int sig)
-{
-#ifdef _MT_SAFE
- if (thread2signal)
- return thread2signal->sigtodo + __SIGOFFSET + sig;
- return _sigtodo + __SIGOFFSET + sig;
-#else
- return _sigtodo + __SIGOFFSET + sig;
-#endif
-}
-
-extern HANDLE hMainThread;
-
-HANDLE
-_pinfo::getthread2signal()
-{
-#ifdef _MT_SAFE
- if (thread2signal)
- return thread2signal->win32_obj_id;
- return hMainThread;
-#else
- return hMainThread;
-#endif
-}
-
-void
-_pinfo::setthread2signal(void *_thr)
-{
-#ifdef _MT_SAFE
- // assert has myself lock
- thread2signal=(ThreadItem*)_thr;
-#else
-#endif
-}
-
-void
-_pinfo::copysigs(_pinfo *_other)
-{
- sigs = _other->sigs;
+ sigproc_printf ("Calling ExitProcess %d", n);
+ ExitProcess (n);
}
void
diff --git a/winsup/cygwin/pinfo.h b/winsup/cygwin/pinfo.h
index 2c57d83c8..067ef6104 100644
--- a/winsup/cygwin/pinfo.h
+++ b/winsup/cygwin/pinfo.h
@@ -20,8 +20,8 @@ enum
#define PSIZE 1024
-class ThreadItem;
#include <sys/resource.h>
+#include "thread.h"
class _pinfo
{
@@ -104,20 +104,41 @@ public:
/* Non-zero if process was stopped by a signal. */
char stopsig;
- struct sigaction& getsig (int);
- void copysigs (_pinfo* );
- sigset_t& getsigmask ();
- void setsigmask (sigset_t);
- LONG* getsigtodo (int);
- HANDLE getthread2signal ();
- void setthread2signal (void *);
- void exit (UINT n) __attribute__ ((noreturn));
+ void exit (UINT n, bool norecord = 0) __attribute__ ((noreturn, regparm(2)));
+
+ inline struct sigaction& getsig (int sig)
+ {
+ return thread2signal ? thread2signal->sigs[sig] : sigs[sig];
+ }
+
+ inline void copysigs (_pinfo *p) {sigs = p->sigs;}
+
+ inline sigset_t& getsigmask ()
+ {
+ return thread2signal ? *thread2signal->sigmask : sig_mask;
+ }
+
+ inline void setsigmask (sigset_t mask)
+ {
+ if (thread2signal)
+ *(thread2signal->sigmask) = mask;
+ sig_mask = mask;
+ }
+
+ inline LONG* getsigtodo (int sig) {return _sigtodo + __SIGOFFSET + sig;}
+
+ inline HANDLE getthread2signal ()
+ {
+ return thread2signal ? thread2signal->win32_obj_id : hMainThread;
+ }
+
+ inline void setthread2signal (void *thr) {thread2signal = (ThreadItem *) thr;}
private:
struct sigaction sigs[NSIG];
sigset_t sig_mask; /* one set for everything to ignore. */
LONG _sigtodo[NSIG + __SIGOFFSET];
- ThreadItem* thread2signal; // NULL means means thread any other means a pthread
+ ThreadItem *thread2signal; // NULL means means thread any other means a pthread
};
class pinfo
@@ -172,7 +193,7 @@ cygwin_pid (pid_t pid)
return (pid_t) (os_being_run == winNT) ? pid : -(int) pid;
}
-void __stdcall pinfo_init (char **);
+void __stdcall pinfo_init (char **, int);
void __stdcall set_myself (pid_t pid, HANDLE h = NULL);
extern pinfo myself;
@@ -181,7 +202,7 @@ extern "C" int _spawnve (HANDLE hToken, int mode, const char *path,
const char *const *argv, const char *const *envp);
extern void __stdcall pinfo_fixup_after_fork ();
-extern void __stdcall pinfo_fixup_in_spawned_child (HANDLE hchild);
+extern HANDLE hexec_proc;
/* For mmaps across fork(). */
int __stdcall recreate_mmaps_after_fork (void *);
diff --git a/winsup/cygwin/sigproc.cc b/winsup/cygwin/sigproc.cc
index 1253b23eb..1d381d8bb 100644
--- a/winsup/cygwin/sigproc.cc
+++ b/winsup/cygwin/sigproc.cc
@@ -456,22 +456,9 @@ proc_terminate (void)
pchildren[i].release ();
}
nchildren = nzombies = 0;
-
/* Just zero sync_proc_subproc as the delete below seems to cause
problems for older gccs. */
- #if 1
sync_proc_subproc = NULL;
- #else
- /* Attempt to close and release sync_proc_subproc in a
- * non-raceable manner.
- */
- muto *m = sync_proc_subproc;
- if (m)
- {
- sync_proc_subproc = NULL;
- // delete m;
- }
- #endif
}
sigproc_printf ("leaving");
}
diff --git a/winsup/cygwin/sigproc.h b/winsup/cygwin/sigproc.h
index ee2e6a6cd..1a79cffc5 100644
--- a/winsup/cygwin/sigproc.h
+++ b/winsup/cygwin/sigproc.h
@@ -101,11 +101,10 @@ BOOL __stdcall proc_exists (_pinfo *);
BOOL __stdcall pid_exists (pid_t);
int __stdcall sig_send (_pinfo *, int, DWORD ebp = (DWORD) __builtin_frame_address (0));
void __stdcall signal_fixup_after_fork ();
+void __stdcall signal_fixup_after_exec (bool);
extern char myself_nowait_dummy[];
extern char myself_nowait_nonmain_dummy[];
-extern HANDLE hExeced; // Process handle of new window
- // process created by spawn_guts()
#define WAIT_SIG_EXITING (WAIT_OBJECT_0 + 1)
diff --git a/winsup/cygwin/spawn.cc b/winsup/cygwin/spawn.cc
index 6939ad578..74f01fcd4 100644
--- a/winsup/cygwin/spawn.cc
+++ b/winsup/cygwin/spawn.cc
@@ -158,8 +158,6 @@ handle (int n, int direction)
return fh->get_output_handle ();
}
-HANDLE NO_COPY hExeced = NULL;
-
int
iscmd (const char *argv0, const char *what)
{
@@ -289,12 +287,9 @@ static int __stdcall
spawn_guts (HANDLE hToken, const char * prog_arg, const char *const *argv,
const char *const envp[], int mode)
{
- int i;
BOOL rc;
pid_t cygpid;
- hExeced = NULL;
-
MALLOC_CHECK;
if (prog_arg == NULL)
@@ -507,10 +502,12 @@ spawn_guts (HANDLE hToken, const char * prog_arg, const char *const *argv,
cygcwd.copy (ciresrv.moreinfo->cwd_posix, ciresrv.moreinfo->cwd_win32,
ciresrv.moreinfo->cwd_hash);
- ciresrv.moreinfo->environ = (char **) cmalloc (HEAP_1_ARGV, envsize (envp, 1));
+ ciresrv.moreinfo->envc = envsize (envp, 0);
+ ciresrv.moreinfo->envp = (char **) cmalloc (HEAP_1_ARGV, ciresrv.moreinfo->envc);
+ ciresrv.hexec_proc = hexec_proc;
char **c;
const char * const *e;
- for (c = ciresrv.moreinfo->environ, e = envp; *e;)
+ for (c = ciresrv.moreinfo->envp, e = envp; *e;)
*c++ = cstrdup1 (*e++);
*c = NULL;
if (mode != _P_OVERLAY ||
@@ -530,11 +527,12 @@ skip_arg_parsing:
syscall_printf ("spawn_guts (%s, %.132s)", (char *) real_path, one_line.buf);
- int flags = CREATE_DEFAULT_ERROR_MODE | CREATE_SUSPENDED |
- GetPriorityClass (hMainProc);
+ int flags = CREATE_DEFAULT_ERROR_MODE | GetPriorityClass (hMainProc);
if (mode == _P_DETACH || !set_console_state_for_spawn ())
flags |= DETACHED_PROCESS;
+ if (mode != _P_OVERLAY)
+ flags |= CREATE_SUSPENDED;
/* Build windows style environment list */
char *envblock;
@@ -552,7 +550,24 @@ skip_arg_parsing:
if (!hToken && myself->token != INVALID_HANDLE_VALUE)
hToken = myself->token;
- if (hToken)
+cygbench ("spawn-guts");
+ if (!hToken)
+ {
+ ciresrv.moreinfo->uid = getuid ();
+ rc = CreateProcess (real_path, /* image name - with full path */
+ one_line.buf, /* what was passed to exec */
+ /* process security attrs */
+ allow_ntsec ? sec_user (sa_buf) : &sec_all_nih,
+ /* thread security attrs */
+ allow_ntsec ? sec_user (sa_buf) : &sec_all_nih,
+ TRUE, /* inherit handles from parent */
+ flags,
+ envblock,/* environment */
+ 0, /* use current drive/directory */
+ &si,
+ &pi);
+ }
+ else
{
/* allow the child to interact with our window station/desktop */
HANDLE hwst, hdsk;
@@ -561,6 +576,7 @@ skip_arg_parsing:
char wstname[1024];
char dskname[1024];
+ ciresrv.moreinfo->uid = USHRT_MAX;
hwst = GetProcessWindowStation();
SetUserObjectSecurity(hwst, &dsi, get_null_sd ());
GetUserObjectInformation(hwst, UOI_NAME, wstname, 1024, &n);
@@ -612,19 +628,6 @@ skip_arg_parsing:
&& myself->impersonated && myself->token != INVALID_HANDLE_VALUE)
seteuid (uid);
}
- else
- rc = CreateProcess (real_path, /* image name - with full path */
- one_line.buf, /* what was passed to exec */
- /* process security attrs */
- allow_ntsec ? sec_user (sa_buf) : &sec_all_nih,
- /* thread security attrs */
- allow_ntsec ? sec_user (sa_buf) : &sec_all_nih,
- TRUE, /* inherit handles from parent */
- flags,
- envblock,/* environment */
- 0, /* use current drive/directory */
- &si,
- &pi);
MALLOC_CHECK;
if (envblock)
@@ -654,26 +657,17 @@ skip_arg_parsing:
/* Name the handle similarly to proc_subproc. */
ProtectHandle1 (pi.hProcess, childhProc);
- ProtectHandle (pi.hThread);
if (mode == _P_OVERLAY)
{
+ /* These are both duplicated in the child code. We do this here,
+ primarily for strace. */
strcpy (myself->progname, real_path);
- hExeced = pi.hProcess;
myself->dwProcessId = pi.dwProcessId;
-
- /* Set up child's signal handlers */
- /* CGF FIXME - consolidate with signal stuff below */
- for (i = 0; i < NSIG; i++)
- {
- myself->getsig(i).sa_mask = 0;
- if (myself->getsig(i).sa_handler != SIG_IGN || (mode != _P_OVERLAY))
- myself->getsig(i).sa_handler = SIG_DFL;
- }
}
else
{
- pinfo_fixup_in_spawned_child (pi.hProcess);
+ ProtectHandle (pi.hThread);
pinfo child (cygpid, 1);
if (!child)
{
@@ -684,7 +678,6 @@ skip_arg_parsing:
child->username[0] = '\0';
child->progname[0] = '\0';
child->ppid = myself->pid;
- child->uid = myself->uid;
child->gid = myself->gid;
child->pgid = myself->pgid;
child->sid = myself->sid;
@@ -702,27 +695,15 @@ skip_arg_parsing:
child->rootlen = myself->rootlen;
child->dwProcessId = pi.dwProcessId;
child->hProcess = pi.hProcess;
- for (i = 0; i < NSIG; i++)
- {
- child->getsig(i).sa_mask = 0;
- if (child->getsig(i).sa_handler != SIG_IGN || (mode != _P_OVERLAY))
- child->getsig(i).sa_handler = SIG_DFL;
- }
- if (hToken)
- {
- /* Set child->uid to USHRT_MAX to force calling internal_getlogin()
- from child process. Clear username and psid to play it safe. */
- child->uid = USHRT_MAX;
- child->use_psid = 0;
- }
child.remember ();
+ /* Start the child running */
+ ResumeThread (pi.hThread);
}
- sigproc_printf ("spawned windows pid %d", pi.dwProcessId);
- /* Start the child running */
- ResumeThread (pi.hThread);
ForceCloseHandle (pi.hThread);
+ sigproc_printf ("spawned windows pid %d", pi.dwProcessId);
+
if (hToken && hToken != myself->token)
CloseHandle (hToken);
@@ -824,16 +805,6 @@ skip_arg_parsing:
system_printf ("old hProcess %p, hProcess %p", oldh, myself->hProcess);
}
}
- if (hExeced)
- {
- ForceCloseHandle1 (hExeced, childhProc);
- hExeced = INVALID_HANDLE_VALUE;
- }
- }
- else if (exited)
- {
- ForceCloseHandle1 (hExeced, childhProc);
- hExeced = INVALID_HANDLE_VALUE; // stop do_exit from attempting to terminate child
}
MALLOC_CHECK;
@@ -841,11 +812,9 @@ skip_arg_parsing:
switch (mode)
{
case _P_OVERLAY:
+ ForceCloseHandle1 (pi.hProcess, childhProc);
proc_terminate ();
- struct rusage r;
- fill_rusage (&r, hMainProc);
- add_rusage (&myself->rusage_self, &r);
- ExitProcess (0);
+ myself->exit (0, 1);
break;
case _P_WAIT:
waitpid (cygpid, (int *) &res, 0);
diff --git a/winsup/cygwin/strace.cc b/winsup/cygwin/strace.cc
index badf0001a..74f77e1ad 100644
--- a/winsup/cygwin/strace.cc
+++ b/winsup/cygwin/strace.cc
@@ -134,7 +134,9 @@ strace::vsprntf (char *buf, const char *func, const char *infmt, va_list ap)
*p = '\000';
p = progname;
count = __small_sprintf (buf, fmt, p && *p ? p : "?",
- myself->pid, hExeced ? "!" : "");
+ myself->pid,
+ myself->dwProcessId != GetCurrentProcessId ()
+ ? "!" : "");
if (func)
count += getfunc (buf + count, func);
}
diff --git a/winsup/cygwin/syscalls.cc b/winsup/cygwin/syscalls.cc
index f54cc1ccf..f4a13b0a7 100644
--- a/winsup/cygwin/syscalls.cc
+++ b/winsup/cygwin/syscalls.cc
@@ -29,7 +29,6 @@ details. */
#include "fhandler.h"
#include "path.h"
#include "dtable.h"
-#include "thread.h"
#include "sync.h"
#include "sigproc.h"
#include "pinfo.h"
diff --git a/winsup/cygwin/thread.cc b/winsup/cygwin/thread.cc
index fb1a3d67c..cb2a98efe 100644
--- a/winsup/cygwin/thread.cc
+++ b/winsup/cygwin/thread.cc
@@ -20,7 +20,6 @@ details. */
#include <assert.h>
#include <stdlib.h>
#include <syslog.h>
-#include "thread.h"
#include "sync.h"
#include "sigproc.h"
#include "pinfo.h"
@@ -81,7 +80,7 @@ _reent_clib ()
SetLastError (tmp);
return _r->_clib;
-};
+}
struct _winsup_t *
_reent_winsup ()
@@ -95,7 +94,7 @@ _reent_winsup ()
#endif
SetLastError (tmp);
return _r->_winsup;
-};
+}
inline LPCRITICAL_SECTION
ResourceLocks::Lock (int _resid)
@@ -108,7 +107,7 @@ ResourceLocks::Lock (int _resid)
_resid, &lock, user_data, myself->pid, GetCurrentThreadId ());
#endif
return &lock;
-};
+}
void
SetResourceLock (int _res_id, int _mode, const char *_function)
@@ -138,7 +137,7 @@ ReleaseResourceLock (int _res_id, int _mode, const char *_function)
#endif
LeaveCriticalSection (user_data->resourcelocks->Lock (_res_id));
-};
+}
#ifdef _CYG_THREAD_FAILSAFE
void
@@ -157,8 +156,6 @@ AssertResourceOwner (int _res_id, int _mode)
void
ResourceLocks::Init ()
{
- thread_printf ("Init resource lock %p -> %p", this, &lock);
-
InitializeCriticalSection (&lock);
inited = true;
@@ -167,8 +164,8 @@ ResourceLocks::Init ()
count = 0;
#endif
- thread_printf ("Resource lock %p inited by %p , %d", &lock, user_data, myself->pid);
-};
+ thread_printf ("lock %p inited by %p , %d", &lock, user_data, myself->pid);
+}
void
ResourceLocks::Delete ()
@@ -179,7 +176,7 @@ ResourceLocks::Delete ()
DeleteCriticalSection (&lock);
inited = false;
}
-};
+}
// Thread interface
@@ -188,7 +185,7 @@ void
MTinterface::ReleaseItem (MTitem * _item)
{
_item->used = false;
-};
+}
MTitem *
MTinterface::Find (void *_value, int (*comp) (void *, void *), register int &_index, MTList * _list)
@@ -202,7 +199,7 @@ MTinterface::Find (void *_value, int (*comp) (void *, void *), register int &_in
current = NULL;
}
return current;
-};
+}
int
MTinterface::Find (MTitem & _item, MTList * _list)
@@ -216,21 +213,22 @@ MTinterface::Find (MTitem & _item, MTList * _list)
break;
}
return (_index == _list->index ? -1 : _index);
-};
+}
int
MTinterface::FindNextUnused (MTList * _list)
{
register int i = 0;
- for (; i < _list->index && _list->items[i] != NULL && _list->items[i]->used && _list->items[i]->joinable != 'Y'; i++);
+ for (; i < _list->index && _list->items[i] != NULL && _list->items[i]->used && _list->items[i]->joinable != 'Y'; i++)
+ continue;
return i;
-};
+}
MTitem *
MTinterface::GetItem (int _index, MTList * _list)
{
return (_index < _list->index ? _list->items[_index] : NULL);
-};
+}
MTitem *
MTinterface::SetItem (int _index, MTitem * _item, MTList * _list)
@@ -238,23 +236,24 @@ MTinterface::SetItem (int _index, MTitem * _item, MTList * _list)
if (_index == _list->index && _list->index < MT_MAX_ITEMS)
_list->index++;
return (_index < _list->index ? _list->items[_index] = _item : NULL);
-};
+}
int
CmpPthreadObj (void *_i, void *_value)
{
return ((MTitem *) _i)->Id () == *(int *) _value;
-};
+}
int
CmpThreadId (void *_i, void *_id)
{
return ((ThreadItem *) _i)->thread_id == * (DWORD *) _id;
-};
+}
void
-MTinterface::Init0 ()
+MTinterface::Init (int forked)
{
+#if 0
for (int i = 0; i < MT_MAX_ITEMS; i++)
{
threadlist.items[i] = NULL;
@@ -265,6 +264,7 @@ MTinterface::Init0 ()
threadlist.index = 0;
mutexlist.index = 0;
semalist.index = 0;
+#endif
reent_index = TlsAlloc ();
@@ -272,39 +272,35 @@ MTinterface::Init0 ()
reents._winsup = &winsup_reent;
winsup_reent._process_logmask = LOG_UPTO (LOG_DEBUG);
+#if 0
winsup_reent._grp_pos = 0;
winsup_reent._process_ident = 0;
winsup_reent._process_logopt = 0;
winsup_reent._process_facility = 0;
+#endif
TlsSetValue (reent_index, &reents);
// the static reent_data will be used in the main thread
-};
+ if (forked)
+ return;
-void
-MTinterface::Init1 ()
-{
// create entry for main thread
- int i = FindNextUnused (&threadlist);
- assert (i == 0);
- ThreadItem *item = (ThreadItem *) GetItem (i, &threadlist);
+ ThreadItem *item = (ThreadItem *) GetItem (0, &threadlist);
- item = (ThreadItem *) SetItem (i, &mainthread, &threadlist);
+ item = (ThreadItem *) SetItem (0, &mainthread, &threadlist);
item->used = true;
item->win32_obj_id = myself->hProcess;
item->thread_id = GetCurrentThreadId ();
+#if 0
item->function = NULL;
item->sigs = NULL;
item->sigmask = NULL;
item->sigtodo = NULL;
-};
+#endif
-void
-MTinterface::ClearReent ()
-{
struct _reent *r = _REENT;
memset (r, 0, sizeof (struct _reent));
@@ -312,9 +308,7 @@ MTinterface::ClearReent ()
r->_stdin = &r->__sf[0];
r->_stdout = &r->__sf[1];
r->_stderr = &r->__sf[2];
-
-};
-
+}
ThreadItem *
MTinterface::CreateThread (pthread_t * t, TFD (func), void *arg, pthread_attr_t a)
@@ -342,8 +336,7 @@ MTinterface::CreateThread (pthread_t * t, TFD (func), void *arg, pthread_attr_t
*t = (pthread_t) item->win32_obj_id;
return item;
-};
-
+}
MutexItem *
MTinterface::CreateMutex (pthread_mutex_t * mutex)
@@ -375,7 +368,7 @@ MTinterface::GetCallingThread ()
DWORD id = GetCurrentThreadId ();
int index = 0;
return (ThreadItem *) Find (&id, &CmpThreadId, index, &threadlist);
-};
+}
ThreadItem *
MTinterface::GetThread (pthread_t * _t)
@@ -383,7 +376,7 @@ MTinterface::GetThread (pthread_t * _t)
AssertResourceOwner (LOCK_THREAD_LIST, READ_LOCK);
int index = 0;
return (ThreadItem *) Find (_t, &CmpPthreadObj, index, &threadlist);
-};
+}
MutexItem *
MTinterface::GetMutex (pthread_mutex_t * mp)
@@ -406,19 +399,19 @@ void
MTitem::Destroy ()
{
CloseHandle (win32_obj_id);
-};
+}
int
MutexItem::Lock ()
{
return WaitForSingleObject (win32_obj_id, INFINITE);
-};
+}
int
MutexItem::TryLock ()
{
return WaitForSingleObject (win32_obj_id, 0);
-};
+}
int
MutexItem::UnLock ()
@@ -448,26 +441,26 @@ MTinterface::CreateSemaphore (sem_t * _s, int pshared, int _v)
*_s = (sem_t) item->win32_obj_id;
return item;
-};
+}
int
SemaphoreItem::Wait ()
{
return WaitForSingleObject (win32_obj_id, INFINITE);
-};
+}
int
SemaphoreItem::Post ()
{
long pc;
return ReleaseSemaphore (win32_obj_id, 1, &pc);
-};
+}
int
SemaphoreItem::TryWait ()
{
return WaitForSingleObject (win32_obj_id, 0);
-};
+}
////////////////////////// Pthreads
@@ -547,34 +540,34 @@ __pthread_create (pthread_t * thread, const pthread_attr_t * attr, TFD (start_ro
ReleaseResourceLock (LOCK_THREAD_LIST, WRITE_LOCK | READ_LOCK, "__pthread_create");
return 0;
-};
+}
int
__pthread_attr_init (pthread_attr_t * attr)
{
attr->stacksize = 0;
return 0;
-};
+}
int
__pthread_attr_setstacksize (pthread_attr_t * attr, size_t size)
{
attr->stacksize = size;
return 0;
-};
+}
int
__pthread_attr_getstacksize (pthread_attr_t * attr, size_t * size)
{
*size = attr->stacksize;
return 0;
-};
+}
int
__pthread_attr_destroy (pthread_attr_t * /*attr*/)
{
return 0;
-};
+}
int
__pthread_exit (void *value_ptr)
@@ -609,7 +602,7 @@ __pthread_join (pthread_t * thread, void **return_val)
}/* End if*/
return 0;
-};
+}
int
__pthread_detach (pthread_t * thread)
@@ -667,30 +660,30 @@ __pthread_getsequence_np (pthread_t * thread)
{
GETTHREAD ("__pthread_getsequence_np");
return item->GetThreadId ();
-};
+}
/* Thread SpecificData */
int
__pthread_key_create (pthread_key_t */*key*/)
{
NOT_IMP ("_p_key_create\n");
-};
+}
int
__pthread_key_delete (pthread_key_t */*key*/)
{
NOT_IMP ("_p_key_delete\n");
-};
+}
int
__pthread_setspecific (pthread_key_t */*key*/, const void */*value*/)
{
NOT_IMP ("_p_key_setsp\n");
-};
+}
void *
__pthread_getspecific (pthread_key_t */*key*/)
{
NOT_IMP ("_p_key_getsp\n");
-};
+}
/* Thread signal */
int
@@ -708,7 +701,7 @@ __pthread_kill (pthread_t * thread, int sig)
// unlock myself
return rval;
-};
+}
int
__pthread_sigmask (int operation, const sigset_t * set, sigset_t * old_set)
@@ -728,7 +721,7 @@ __pthread_sigmask (int operation, const sigset_t * set, sigset_t * old_set)
// unlock this myself
return rval;
-};
+}
/* ID */
pthread_t
@@ -741,13 +734,13 @@ __pthread_self ()
ReleaseResourceLock (LOCK_THREAD_LIST, READ_LOCK, "__pthread_self");
return (pthread_t) item->Id ();
-};
+}
int
__pthread_equal (pthread_t * t1, pthread_t * t2)
{
return (*t1 - *t2);
-};
+}
/* Mutexes */
@@ -762,7 +755,7 @@ __pthread_mutex_init (pthread_mutex_t * mutex, const pthread_mutexattr_t */*_att
ReleaseResourceLock (LOCK_MUTEX_LIST, WRITE_LOCK | READ_LOCK, "__pthread_mutex_init");
return 0;
-};
+}
int
__pthread_mutex_lock (pthread_mutex_t * mutex)
@@ -772,7 +765,7 @@ __pthread_mutex_lock (pthread_mutex_t * mutex)
item->Lock ();
return 0;
-};
+}
int
__pthread_mutex_trylock (pthread_mutex_t * mutex)
@@ -783,7 +776,7 @@ __pthread_mutex_trylock (pthread_mutex_t * mutex)
return EBUSY;
return 0;
-};
+}
int
__pthread_mutex_unlock (pthread_mutex_t * mutex)
@@ -793,7 +786,7 @@ __pthread_mutex_unlock (pthread_mutex_t * mutex)
item->UnLock ();
return 0;
-};
+}
int
__pthread_mutex_destroy (pthread_mutex_t * mutex)
@@ -810,7 +803,7 @@ __pthread_mutex_destroy (pthread_mutex_t * mutex)
ReleaseResourceLock (LOCK_MUTEX_LIST, READ_LOCK | WRITE_LOCK, "__pthread_mutex_destroy");
return 0;
-};
+}
/* Semaphores */
int
@@ -824,7 +817,7 @@ __sem_init (sem_t * sem, int pshared, unsigned int value)
ReleaseResourceLock (LOCK_SEM_LIST, READ_LOCK | WRITE_LOCK, "__sem_init");
return 0;
-};
+}
int
__sem_destroy (sem_t * sem)
@@ -841,7 +834,7 @@ __sem_destroy (sem_t * sem)
ReleaseResourceLock (LOCK_SEM_LIST, READ_LOCK | WRITE_LOCK, "__sem_destroy");
return 0;
-};
+}
int
__sem_wait (sem_t * sem)
@@ -851,7 +844,7 @@ __sem_wait (sem_t * sem)
item->Wait ();
return 0;
-};
+}
int
__sem_trywait (sem_t * sem)
@@ -862,7 +855,7 @@ __sem_trywait (sem_t * sem)
return EAGAIN;
return 0;
-};
+}
int
__sem_post (sem_t * sem)
@@ -872,7 +865,7 @@ __sem_post (sem_t * sem)
item->Post ();
return 0;
-};
+}
#else
diff --git a/winsup/cygwin/thread.h b/winsup/cygwin/thread.h
index 0ef4725c5..999bd5ed8 100644
--- a/winsup/cygwin/thread.h
+++ b/winsup/cygwin/thread.h
@@ -110,8 +110,8 @@ struct __reent_t
_reent *_reent_clib ();
_winsup_t *_reent_winsup ();
-void SetResourceLock (int, int, const char *);
-void ReleaseResourceLock (int, int, const char *);
+void SetResourceLock (int, int, const char *) __attribute__ ((regparm(3)));
+void ReleaseResourceLock (int, int, const char *) __attribute__ ((regparm(3)));
#ifdef _CYG_THREAD_FAILSAFE
void AssertResourceOwner (int, int);
@@ -209,9 +209,7 @@ public:
struct _winsup_t winsup_reent;
ThreadItem mainthread;
- void Init0 ();
- void Init1 ();
- void ClearReent ();
+ void Init (int);
void ReleaseItem (MTitem *);
diff --git a/winsup/cygwin/times.cc b/winsup/cygwin/times.cc
index b8e715deb..bff40b612 100644
--- a/winsup/cygwin/times.cc
+++ b/winsup/cygwin/times.cc
@@ -19,7 +19,6 @@ details. */
#include "cygerrno.h"
#include "fhandler.h"
#include "path.h"
-#include "thread.h"
#include "sync.h"
#include "sigproc.h"
#include "pinfo.h"
diff --git a/winsup/cygwin/uinfo.cc b/winsup/cygwin/uinfo.cc
index 7057fd11e..e0c5d0726 100644
--- a/winsup/cygwin/uinfo.cc
+++ b/winsup/cygwin/uinfo.cc
@@ -18,7 +18,6 @@ details. */
#include <stdlib.h>
#include <wchar.h>
#include <lm.h>
-#include "thread.h"
#include "sync.h"
#include "sigproc.h"
#include "pinfo.h"
diff --git a/winsup/cygwin/winsup.h b/winsup/cygwin/winsup.h
index 2deee0e6a..bd1fd9b12 100644
--- a/winsup/cygwin/winsup.h
+++ b/winsup/cygwin/winsup.h
@@ -184,15 +184,15 @@ int __stdcall writable_directory (const char *file);
int __stdcall stat_dev (DWORD, int, unsigned long, struct stat *);
extern BOOL allow_ntsec;
-unsigned long __stdcall hash_path_name (unsigned long hash, const char *name);
-void __stdcall nofinalslash (const char *src, char *dst);
-extern "C" char *__stdcall rootdir (char *full_path);
+unsigned long __stdcall hash_path_name (unsigned long hash, const char *name) __attribute__ ((regparm(2)));
+void __stdcall nofinalslash (const char *src, char *dst) __attribute__ ((regparm(2)));
+extern "C" char *__stdcall rootdir (char *full_path) __attribute__ ((regparm(1)));
/* String manipulation */
-char *__stdcall strccpy (char *s1, const char **s2, char c);
-int __stdcall strcasematch (const char *s1, const char *s2);
-int __stdcall strncasematch (const char *s1, const char *s2, size_t n);
-char *__stdcall strcasestr (const char *searchee, const char *lookfor);
+extern "C" char *__stdcall strccpy (char *s1, const char **s2, char c);
+extern "C" int __stdcall strcasematch (const char *s1, const char *s2) __attribute__ ((regparm(2)));
+extern "C" int __stdcall strncasematch (const char *s1, const char *s2, size_t n) __attribute__ ((regparm(3)));
+extern "C" char *__stdcall strcasestr (const char *searchee, const char *lookfor) __attribute__ ((regparm(2)));
/* Time related */
void __stdcall totimeval (struct timeval *dst, FILETIME * src, int sub, int flag);