OSDN Git Service

* cygtls.h (_threadinfo::call): Remove regparm declaration to work around
authorcgf <cgf>
Wed, 14 Jan 2004 15:45:35 +0000 (15:45 +0000)
committercgf <cgf>
Wed, 14 Jan 2004 15:45:35 +0000 (15:45 +0000)
compiler bug.
* autoload.cc (TryEnterCriticalSection): Remove.
* dcrt0.cc (dll_crt0_0): Delete inappropriate setting of _my_tls.stackptr to
NULL since it has really bad consequences.  Make 'si' an automatic variable.
* cygtls.cc (_threadinfo::init_thread): Correct thinko which caused thread list
to be allocated every time.
* cygtls.h (CYGTLS_PADSIZE): Define as const int.
* sync.h: Make multiple inclusion safe.
(muto::next): Eliminate.
(muto::exiting_thread): New variable.
(muto::set_exiting_thread): New function.
(new_muto): Change to use different section for mutos since c++ give
inexplicable warning in some cases otherwise.
(new_muto1): Ditto.
* dcrt0.cc (do_exit): Call muto::set_exiting_thread here.
* sync.cc (muto_start): Eliminate.
(muto::acquire): Always give exiting thread a lock.  Never give thread a lock
if exiting.
(muto::release): Ditto for releasing.
* dtable.cc (dtable::init_lock): Unline function and define here.
* dtable.h (lock_cs): Define as a muto since critical sections seem to work
oddly on Windows Me.
(lock): Accommodate switch to muto.
(unlock): Ditto.
* exceptions.cc (setup_handler): Don't worry about acquiring mutos since that
hasn't mattered for a long time.
(signal_exit): Ditto: muto stuff will be handled automatically on exit now.
* Makefile.in (DLL_IMPORTS): Link advapi32 to ensure proper DLL initialization.
* autoload.cc (RegCloseKey): Arbitrarily choose this function as a "seed" to
pull the advapi32 link library in.  So, comment out the autoloading.
* cygtls.cc (_threadinfo::init_thread): Just clear CYGTLS_PADSIZE.
(_threadinfo::remove): Add debugging.
(_threadinfo::find_tls): Ditto.
* cygtls.h (_threadinfo::padding): Make zero length (for now?).
* dcrt0.cc (dll_crt0_0): Move more initialization here from dll_crt0_1.
(dll_crt0_1): See above.
* dtable.h (dtable::lock): Remove commented out critical section locking.
* dtable.h (dtable::init_lock): Remove commented out critical section locking.
* dtable.h (dtable::unlock): Remove commented out critical section locking.
* exceptions.cc (interruptible): bool'ize.
* init.cc (threadfunc_fe): Revert to storing threadfunc at stack bottom.
(munge_threadfunc): Ditto.  Avoid adding overhead to calibration_thread.
(prime_threads): Don't initialize tls stuff.
(dll_entry): Make minor change to initialization order.
* tlsoffsets.h: Regenerate.
* sigproc.cc (wait_sig): Add sanity check for end of process thread exit.
* select.h: Make minor formatting change.
* Makefile.in: Add still more -fomit-frame-pointer functions.
* dtable.h (dtable::lock): New function.
(dtable::unlock): New function.
(dtable::init_lock): New function.
* cygheap.h (HEAP_TLS): Declare new enum value.
(init_cygheap::threadlist): Declare new array.
(init_cygheap::sthreads): Declare new variable.
(cygheap_fdmanip::~cygheap_fdmanip): Use new dtable lock/unlock functions.
(cygheap_fdnew::cygheap_fdnew): Ditto.
(cygheap_fdget::cygheap_fdget): Ditto.
* dtable.cc (dtable_init): Initialize fdtab critical section.
(dtable::fixup_after_fork): Ditto.
(dtable::fixup_after_exec): Ditto.
(dtable::dup2): Use lock/unlock calls to protect access to fdtab.
(dtable::find_fifo): Ditto.
(dtable::fixup_before_fork): Ditto.
(dtable::fixup_before_exec): Ditto.
(dtable::set_file_pointers_for_exec): Ditto.
(dtable::vfork_child_dup): Ditto.
(dtable::vfork_parent_restore): Ditto.
* syscalls.cc (close_all_files): Ditto.
* sync.h (muto::acquired): Declare new function.
(new_muto1): Declare new macro used to specify name of muto storage.
* sync.cc (muto::acquired): Define new function.
* cygthread.cc (cygthread::stub): Remove signal chain removal call since it is
handled during initialization now.
* cygthread.cc (cygthread::simplestub): Remove signal chain removal call since
it is handled during initialization now.
* cygtls.cc (sentry): New class used for locking.  Use throughout.
(_threadinfo::reset_exception): Don't pop stack.
(_threadinfo::find_tls): Move from exceptions.cc.
(_threadinfo::init_thread): Initialize array of threads rather than linked
list.  Take second argument indicating thread function for this thread.
(_threadinfo::remove): Search thread array rather than linked list.  Use sentry
to lock.  Only unlock if we got the lock.
(_threadinfo::find_tls): Ditto for first two.
(handle_threadlist_exception): Handle exceptions when manipulating the thread
list in case of premature thread termination.
(_threadinfo::init_threadlist_exceptions): Ditto.
* cygtls.h (TLS_STACK_SIZE): Decrease size.
(_threadinfo::padding): Add element to avoid overwriting lower part of stack.
(_threadinfo::remove): Add a "wait" argument to control how long we wait for a
lock before removing.
* exceptions.cc (init_exception_handler): Make global.  Take argument to
control exception handler being set.
(ctrl_c_handler): Wait forever when removing self from signal chain.
(_threadinfo::find_tls): Move to cygtls.cc.
(sig_handle): Reorganize detection for thread-specific signals.
* heap.cc (heap_init): Rework slightly.  Make fatal error more verbose.  Remove
malloc initialization since it can't happen during dll attach.
* init.cc (search_for): Move address to search for on stack here.
(threadfunc_ix): Ditto for stack offset.  Make shared so that stack walk
potentially only has to be done once when cygwin processes are running.
(threadfunc_fe): Use standard tls to store thread function (may change back
later).
(calibration_thread): New function.  Potentially called to find threadfunc_ix.
(munge_threadfunc): Search for "search_for" value on stack.  Output warning
when thread func not found on stack.  Use standard tls to store thread
function.
(prime_threads): New function.  Called to prime thread front end.
(dll_entry): Call dll_crt0_0 here when DLL_PROCESS_ATTACH.  Call prime_threads
here.  Try to remove thread from signal list here.
* sigproc.cc (wait_sig): Initialize threadlist exception stuff here.
* thread.cc (pthread::exit): Pass argument to signal list remove function.
* thread.h: Remove obsolete *ResourceLock defines.
* tlsoffsets.h: Regenerate.
* winsup.h (spf): Define temporary debug macro to be deleted later.
* dcrt0.cc (dll_crt0_0): New function, called during DLL initialization.
Mainly consists of code pulled from dll_crt0_1.
(dll_crt0_1): See above.
(_dll_crt0): Wait for initial calibration thread to complete, if appropriate.
Move some stuff to dll_crt0_0.
(initialize_main_tls): Accommodate argument change to
_thread_info::init_thread.
* fork.cc (fork_child): Ditto.
(sync_with_child): Fix debug message.
* external.cc (cygwin_internal): Remove special considerations for
uninitialized dll since initialization happens during dll attach now.
* dlfcn.cc (dlopen): Remove obsolete *ResourceLock calls.
(dlclose): Ditto.
* cygheap.h (init_cygheap::close_ctty): Declare new function.
* cygheap.cc (init_cygheap::close_ctty): Define new function.
* syscalls.cc (close_all_files): Use close_ctty.
(setsid): Ditto.
* cygthread.cc (cygthread::stub): Remove exception initialization.
* cygthread.cc (cygthread::stub): Remove exception initialization.
(cygthread::simplestub): Ditto.
* thread.cc (pthread::thread_init_wrapper): Ditto.
* cygtls.cc (_last_thread): Make static.
(_threadinfo::call2): Initialize exception handler here.
(_threadinfo::find_tls): Move here.
* exceptions.cc (_threadinfo::find_tls): Move.
* dcrt0.cc (__api_fatal): Add prefix info to message here rather than including
it in every call to function.
* winsup.h (api_fatal): Accommodate above change.
* debug.cc (add_handle): Don't do anything if cygheap not around.
(mark_closed): Ditto.
* dll_init.cc (dll_list::detach): Fix debug output.
* fork.cc (sync_with_child): Ditto.
(vfork): Improve debug output.
* heap.cc (heap_init): Ditto.
* exceptions.cc (try_to_debug): Clarify message when debugger attaches.

37 files changed:
winsup/cygwin/ChangeLog
winsup/cygwin/Makefile.in
winsup/cygwin/autoload.cc
winsup/cygwin/cygheap.cc
winsup/cygwin/cygheap.h
winsup/cygwin/cygthread.cc
winsup/cygwin/cygthread.h
winsup/cygwin/cygtls.cc
winsup/cygwin/cygtls.h
winsup/cygwin/dcrt0.cc
winsup/cygwin/debug.cc
winsup/cygwin/dlfcn.cc
winsup/cygwin/dll_init.cc
winsup/cygwin/dll_init.sgml
winsup/cygwin/dtable.cc
winsup/cygwin/dtable.h
winsup/cygwin/dtable.sgml
winsup/cygwin/exceptions.cc
winsup/cygwin/external.cc
winsup/cygwin/external.sgml
winsup/cygwin/fork.cc
winsup/cygwin/heap.cc
winsup/cygwin/init.cc
winsup/cygwin/malloc_wrapper.cc
winsup/cygwin/path.sgml
winsup/cygwin/pinfo.cc
winsup/cygwin/select.h
winsup/cygwin/shared.sgml
winsup/cygwin/sigproc.cc
winsup/cygwin/stackdump.sgml
winsup/cygwin/sync.cc
winsup/cygwin/sync.h
winsup/cygwin/syscalls.cc
winsup/cygwin/thread.cc
winsup/cygwin/thread.h
winsup/cygwin/tlsoffsets.h
winsup/cygwin/winsup.h

index e970723..b52a26b 100644 (file)
@@ -1,3 +1,198 @@
+2004-01-14  Christopher Faylor  <cgf@redhat.com>
+
+       * cygtls.h (_threadinfo::call): Remove regparm declaration to work
+       around compiler bug.
+
+2004-01-13  Christopher Faylor  <cgf@redhat.com>
+
+       * autoload.cc (TryEnterCriticalSection): Remove.
+       * dcrt0.cc (dll_crt0_0): Delete inappropriate setting of
+       _my_tls.stackptr to NULL since it has really bad consequences.  Make
+       'si' an automatic variable.
+
+2004-01-13  Christopher Faylor  <cgf@redhat.com>
+
+       * cygtls.cc (_threadinfo::init_thread): Correct thinko which caused
+       thread list to be allocated every time.
+       * cygtls.h (CYGTLS_PADSIZE): Define as const int.
+       * sync.h: Make multiple inclusion safe.
+       (muto::next): Eliminate.
+       (muto::exiting_thread): New variable.
+       (muto::set_exiting_thread): New function.
+       (new_muto): Change to use different section for mutos since c++ give
+       inexplicable warning in some cases otherwise.
+       (new_muto1): Ditto.
+       * dcrt0.cc (do_exit): Call muto::set_exiting_thread here.
+       * sync.cc (muto_start): Eliminate.
+       (muto::acquire): Always give exiting thread a lock.  Never give thread
+       a lock if exiting.
+       (muto::release): Ditto for releasing.
+       * dtable.cc (dtable::init_lock): Unline function and define here.
+       * dtable.h (lock_cs): Define as a muto since critical sections seem to
+       work oddly on Windows Me.
+       (lock): Accommodate switch to muto.
+       (unlock): Ditto.
+       * exceptions.cc (setup_handler): Don't worry about acquiring mutos
+       since that hasn't mattered for a long time.
+       (signal_exit): Ditto: muto stuff will be handled automatically on exit
+       now.
+
+2004-01-12  Christopher Faylor  <cgf@redhat.com>
+
+       * Makefile.in (DLL_IMPORTS): Link advapi32 to ensure proper DLL
+       initialization.
+       * autoload.cc (RegCloseKey): Arbitrarily choose this function as a
+       "seed" to pull the advapi32 link library in.  So, comment out the
+       autoloading.
+       * cygtls.cc (_threadinfo::init_thread): Just clear CYGTLS_PADSIZE.
+       (_threadinfo::remove): Add debugging.
+       (_threadinfo::find_tls): Ditto.
+       * cygtls.h (_threadinfo::padding): Make zero length (for now?).
+       * dcrt0.cc (dll_crt0_0): Move more initialization here from dll_crt0_1.
+       (dll_crt0_1): See above.
+       * dtable.h (dtable::lock): Remove commented out critical section
+       locking.
+       * dtable.h (dtable::init_lock): Remove commented out critical section
+       locking.
+       * dtable.h (dtable::unlock): Remove commented out critical section
+       locking.
+       * exceptions.cc (interruptible): bool'ize.
+       * init.cc (threadfunc_fe): Revert to storing threadfunc at stack
+       bottom.
+       (munge_threadfunc): Ditto.  Avoid adding overhead to
+       calibration_thread.
+       (prime_threads): Don't initialize tls stuff.
+       (dll_entry): Make minor change to initialization order.
+       * tlsoffsets.h: Regenerate.
+
+       * sigproc.cc (wait_sig): Add sanity check for end of process thread
+       exit.
+
+       * select.h: Make minor formatting change.
+
+2004-01-10  Christopher Faylor  <cgf@redhat.com>
+
+       * Makefile.in: Add still more -fomit-frame-pointer functions.
+       * dtable.h (dtable::lock): New function.
+       (dtable::unlock): New function.
+       (dtable::init_lock): New function.
+       * cygheap.h (HEAP_TLS): Declare new enum value.
+       (init_cygheap::threadlist): Declare new array.
+       (init_cygheap::sthreads): Declare new variable.
+       (cygheap_fdmanip::~cygheap_fdmanip): Use new dtable lock/unlock
+       functions.
+       (cygheap_fdnew::cygheap_fdnew): Ditto.
+       (cygheap_fdget::cygheap_fdget): Ditto.
+       * dtable.cc (dtable_init): Initialize fdtab critical section.
+       (dtable::fixup_after_fork): Ditto.
+       (dtable::fixup_after_exec): Ditto.
+       (dtable::dup2): Use lock/unlock calls to protect access to fdtab.
+       (dtable::find_fifo): Ditto.
+       (dtable::fixup_before_fork): Ditto.
+       (dtable::fixup_before_exec): Ditto.
+       (dtable::set_file_pointers_for_exec): Ditto.
+       (dtable::vfork_child_dup): Ditto.
+       (dtable::vfork_parent_restore): Ditto.
+       * syscalls.cc (close_all_files): Ditto.
+       * sync.h (muto::acquired): Declare new function.
+       (new_muto1): Declare new macro used to specify name of muto storage.
+       * sync.cc (muto::acquired): Define new function.
+
+       * cygthread.cc (cygthread::stub): Remove signal chain removal call
+       since it is handled during initialization now.
+       * cygthread.cc (cygthread::simplestub): Remove signal chain removal
+       call since it is handled during initialization now.
+       * cygtls.cc (sentry): New class used for locking.  Use throughout.
+       (_threadinfo::reset_exception): Don't pop stack.
+       (_threadinfo::find_tls): Move from exceptions.cc.
+       (_threadinfo::init_thread): Initialize array of threads rather than
+       linked list.  Take second argument indicating thread function for this
+       thread.
+       (_threadinfo::remove): Search thread array rather than linked list.
+       Use sentry to lock.  Only unlock if we got the lock.
+       (_threadinfo::find_tls): Ditto for first two.
+       (handle_threadlist_exception): Handle exceptions when manipulating the
+       thread list in case of premature thread termination.
+       (_threadinfo::init_threadlist_exceptions): Ditto.
+       * cygtls.h (TLS_STACK_SIZE): Decrease size.
+       (_threadinfo::padding): Add element to avoid overwriting lower part of
+       stack.
+       (_threadinfo::remove): Add a "wait" argument to control how long we
+       wait for a lock before removing.
+       * exceptions.cc (init_exception_handler): Make global.  Take argument
+       to control exception handler being set.
+       (ctrl_c_handler): Wait forever when removing self from signal chain.
+       (_threadinfo::find_tls): Move to cygtls.cc.
+       (sig_handle): Reorganize detection for thread-specific signals.
+       * heap.cc (heap_init): Rework slightly.  Make fatal error more verbose.
+       Remove malloc initialization since it can't happen during dll attach.
+       * init.cc (search_for): Move address to search for on stack here.
+       (threadfunc_ix): Ditto for stack offset.  Make shared so that stack
+       walk potentially only has to be done once when cygwin processes are
+       running.
+       (threadfunc_fe): Use standard tls to store thread function (may change
+       back later).
+       (calibration_thread): New function.  Potentially called to find
+       threadfunc_ix.
+       (munge_threadfunc): Search for "search_for" value on stack.  Output
+       warning when thread func not found on stack.  Use standard tls to store
+       thread function.
+       (prime_threads): New function.  Called to prime thread front end.
+       (dll_entry): Call dll_crt0_0 here when DLL_PROCESS_ATTACH.  Call
+       prime_threads here.  Try to remove thread from signal list here.
+       * sigproc.cc (wait_sig): Initialize threadlist exception stuff here.
+       * thread.cc (pthread::exit): Pass argument to signal list remove
+       function.
+       * thread.h: Remove obsolete *ResourceLock defines.
+
+       * tlsoffsets.h: Regenerate.
+
+       * winsup.h (spf): Define temporary debug macro to be deleted later.
+
+       * dcrt0.cc (dll_crt0_0): New function, called during DLL
+       initialization.  Mainly consists of code pulled from dll_crt0_1.
+       (dll_crt0_1): See above.
+       (_dll_crt0): Wait for initial calibration thread to complete, if
+       appropriate.  Move some stuff to dll_crt0_0.
+       (initialize_main_tls): Accommodate argument change to
+       _thread_info::init_thread.
+       * fork.cc (fork_child): Ditto.
+       (sync_with_child): Fix debug message.
+       * external.cc (cygwin_internal): Remove special considerations for
+       uninitialized dll since initialization happens during dll attach now.
+
+       * dlfcn.cc (dlopen): Remove obsolete *ResourceLock calls.
+       (dlclose): Ditto.
+
+2004-01-05  Christopher Faylor  <cgf@redhat.com>
+
+       * cygheap.h (init_cygheap::close_ctty): Declare new function.
+       * cygheap.cc (init_cygheap::close_ctty): Define new function.
+       * syscalls.cc (close_all_files): Use close_ctty.
+       (setsid): Ditto.
+
+       * cygthread.cc (cygthread::stub): Remove exception initialization.
+       * cygthread.cc (cygthread::stub): Remove exception initialization.
+       (cygthread::simplestub): Ditto.
+       * thread.cc (pthread::thread_init_wrapper): Ditto.
+       * cygtls.cc (_last_thread): Make static.
+       (_threadinfo::call2): Initialize exception handler here.
+       (_threadinfo::find_tls): Move here.
+       * exceptions.cc (_threadinfo::find_tls): Move.
+
+       * dcrt0.cc (__api_fatal): Add prefix info to message here rather than
+       including it in every call to function.
+       * winsup.h (api_fatal): Accommodate above change.
+       * debug.cc (add_handle): Don't do anything if cygheap not around.
+       (mark_closed): Ditto.
+
+       * dll_init.cc (dll_list::detach): Fix debug output.
+       * fork.cc (sync_with_child): Ditto.
+       (vfork): Improve debug output.
+       * heap.cc (heap_init): Ditto.
+
+       * exceptions.cc (try_to_debug): Clarify message when debugger attaches.
+
 2004-01-03  Christopher Faylor  <cgf@redhat.com>
 
        * exceptions.cc (_threadinfo::interrupt_now): Avoid double call to
index 742a2e2..cf15b32 100644 (file)
@@ -113,7 +113,7 @@ EXTRA_OFILES=$(bupdir1)/libiberty/random.o $(bupdir1)/libiberty/strsignal.o
 
 MALLOC_OFILES=@MALLOC_OFILES@
 
-DLL_IMPORTS:=$(w32api_lib)/libkernel32.a
+DLL_IMPORTS:=$(w32api_lib)/libkernel32.a $(w32api_lib)/libadvapi32.a
 
 MT_SAFE_OBJECTS:=
 # Please maintain this list in sorted order, with maximum files per 80 col line
@@ -254,6 +254,8 @@ regexec_CFLAGS=-fomit-frame-pointer
 regfree_CFLAGS=-fomit-frame-pointer
 shared_CFLAGS:=-fomit-frame-pointer
 smallprint_CFLAGS:=-fomit-frame-pointer
+sysconf_CFLAGS:=-fomit-frame-pointer
+uinfo_CFLAGS:=-fomit-frame-pointer
 endif
 
 .PHONY: all force dll_ofiles install all_target install_target all_host install_host \
index 1628480..9cd7f6a 100644 (file)
@@ -354,7 +354,7 @@ LoadDLLfunc (LsaQueryInformationPolicy, 12, advapi32)
 LoadDLLfunc (MakeSelfRelativeSD, 12, advapi32)
 LoadDLLfunc (OpenProcessToken, 12, advapi32)
 LoadDLLfunc (OpenThreadToken, 16, advapi32)
-LoadDLLfunc (RegCloseKey, 4, advapi32)
+// LoadDLLfunc (RegCloseKey, 4, advapi32)
 LoadDLLfunc (RegCreateKeyExA, 36, advapi32)
 LoadDLLfunc (RegDeleteKeyA, 8, advapi32)
 LoadDLLfunc (RegDeleteValueA, 8, advapi32)
@@ -515,7 +515,6 @@ LoadDLLfuncEx (Process32Next, 8, kernel32, 1)
 LoadDLLfuncEx (RegisterServiceProcess, 8, kernel32, 1)
 LoadDLLfuncEx (SignalObjectAndWait, 16, kernel32, 1)
 LoadDLLfuncEx (SwitchToThread, 0, kernel32, 1)
-LoadDLLfunc (TryEnterCriticalSection, 4, kernel32)
 
 LoadDLLfuncEx (waveOutGetNumDevs, 0, winmm, 1)
 LoadDLLfuncEx (waveOutOpen, 24, winmm, 1)
index 6859e43..0171f99 100644 (file)
@@ -172,6 +172,16 @@ cygheap_fixup_in_child (bool execed)
     }
 }
 
+void
+init_cygheap::close_ctty ()
+{
+  debug_printf ("closing cygheap->ctty %p", cygheap->ctty);
+  cygheap->ctty->close ();
+  if (cygheap->ctty_on_hold == cygheap->ctty)
+    cygheap->ctty_on_hold = NULL;
+  cygheap->ctty = NULL;
+}
+
 #define pagetrunc(x) ((void *) (((DWORD) (x)) & ~(4096 - 1)))
 
 static void *__stdcall
@@ -206,6 +216,7 @@ cygheap_init ()
     cygheap->fdtab.init ();
   if (!cygheap->sigs)
     sigalloc ();
+
   if (!cygheap->shared_prefix)
     cygheap->shared_prefix = cstrdup (
            wincap.has_terminal_services ()
index 4a56968..be51527 100644 (file)
@@ -19,6 +19,7 @@ enum cygheap_types
   HEAP_MOUNT,
   HEAP_SIGS,
   HEAP_ARCHETYPES,
+  HEAP_TLS,
   HEAP_1_START,
   HEAP_1_STR,
   HEAP_1_ARGV,
@@ -263,7 +264,10 @@ struct init_cygheap
 
   fhandler_tty_slave *ctty;    /* Current tty */
   fhandler_tty_slave *ctty_on_hold;
+  struct _threadinfo **threadlist;
+  size_t sthreads;
   int open_fhs;
+  void close_ctty ();
 };
 
 #define CYGHEAPSIZE (sizeof (init_cygheap) + (20000 * sizeof (fhandler_union)) + (5 * 65536))
@@ -282,7 +286,7 @@ class cygheap_fdmanip
   virtual ~cygheap_fdmanip ()
   {
     if (locked)
-      ReleaseResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "cygheap_fdmanip");
+      cygheap->fdtab.unlock ();
   }
   void release ()
   {
@@ -308,7 +312,7 @@ class cygheap_fdnew : public cygheap_fdmanip
   cygheap_fdnew (int seed_fd = -1, bool lockit = true)
   {
     if (lockit)
-      SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "cygheap_fdnew");
+      cygheap->fdtab.lock ();
     if (seed_fd < 0)
       fd = cygheap->fdtab.find_unused_handle ();
     else
@@ -322,7 +326,7 @@ class cygheap_fdnew : public cygheap_fdmanip
       {
        set_errno (EMFILE);
        if (lockit)
-         ReleaseResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "cygheap_fdnew");
+         cygheap->fdtab.unlock ();
        locked = false;
       }
   }
@@ -335,7 +339,7 @@ class cygheap_fdget : public cygheap_fdmanip
   cygheap_fdget (int fd, bool lockit = false, bool do_set_errno = true)
   {
     if (lockit)
-      SetResourceLock (LOCK_FD_LIST, READ_LOCK, "cygheap_fdget");
+      cygheap->fdtab.lock ();
     if (fd >= 0 && fd < (int) cygheap->fdtab.size
        && *(fh = cygheap->fdtab + fd) != NULL)
       {
@@ -348,7 +352,7 @@ class cygheap_fdget : public cygheap_fdmanip
        if (do_set_errno)
          set_errno (EBADF);
        if (lockit)
-         ReleaseResourceLock (LOCK_FD_LIST, READ_LOCK, "cygheap_fdget");
+         cygheap->fdtab.unlock ();
        locked = false;
       }
   }
index 16f6296..e830196 100644 (file)
@@ -32,12 +32,6 @@ bool NO_COPY cygthread::exiting;
 DWORD WINAPI
 cygthread::stub (VOID *arg)
 {
-  exception_list except_entry;
-  /* Initialize this thread's ability to respond to things like
-     SIGSEGV or SIGFPE. */
-  init_exceptions (&except_entry);
-  _my_tls.remove ();   // Remove me from signal chain -- not signalable.
-
   cygthread *info = (cygthread *) arg;
   if (info->arg == cygself)
     {
@@ -46,7 +40,7 @@ cygthread::stub (VOID *arg)
          CloseHandle (info->ev);
          CloseHandle (info->thread_sync);
        }
-    info->ev = info->thread_sync = info->stack_ptr = NULL;
+      info->ev = info->thread_sync = info->stack_ptr = NULL;
     }
   else
     {
@@ -57,6 +51,7 @@ cygthread::stub (VOID *arg)
          info->thread_sync = CreateEvent (&sec_none_nih, FALSE, FALSE, NULL);
        }
     }
+
   while (1)
     {
       if (!info->__name)
@@ -92,12 +87,6 @@ cygthread::stub (VOID *arg)
 DWORD WINAPI
 cygthread::simplestub (VOID *arg)
 {
-  exception_list except_entry;
-  /* Initialize this thread's ability to respond to things like
-     SIGSEGV or SIGFPE. */
-  init_exceptions (&except_entry);
-  _my_tls.remove ();   // Remove me from signal chain -- not signalable.
-
   cygthread *info = (cygthread *) arg;
   info->stack_ptr = &arg;
   info->ev = info->h;
index eb2eb9a..76604b4 100644 (file)
@@ -19,12 +19,10 @@ class cygthread
   VOID *arg;
   bool is_freerange;
   static bool exiting;
-  static void stub2 (void *, void *);
-  static DWORD WINAPI simplestub (VOID *);
-  static void simplestub2 (void *, void *);
   void terminate_thread ();
  public:
   static DWORD WINAPI stub (VOID *);
+  static DWORD WINAPI simplestub (VOID *);
   static DWORD main_thread_id;
   static const char * name (DWORD = 0);
   cygthread (LPTHREAD_START_ROUTINE, LPVOID, const char *);
@@ -43,7 +41,6 @@ class cygthread
     (void) CloseHandle (h);
     h = NULL;
   }
-
 };
 
 #define cygself NULL
index 2734cf5..5c9fa61 100644 (file)
@@ -1,6 +1,6 @@
-/* cygtls.h
+/* cygtls.cc
 
-   Copyright 2003 Red Hat, Inc.
+   Copyright 2003, 2004 Red Hat, Inc.
 
 This software is a copyrighted work licensed under the terms of the
 Cygwin license.  Please consult the file "CYGWIN_LICENSE" for
@@ -11,11 +11,48 @@ details. */
 #include "cygtls.h"
 #include "assert.h"
 #include <syslog.h>
+#include <signal.h>
+#include "exceptions.h"
+#include "sync.h"
+#include "cygerrno.h"
+#include "path.h"
+#include "fhandler.h"
+#include "dtable.h"
+#include "cygheap.h"
+#include "cygthread.h"
+
+class sentry
+{
+  static muto *lock;
+  int destroy;
+public:
+  void init ();
+  bool acquired () {return lock->acquired ();}
+  sentry () {destroy = 0;}
+  sentry (DWORD wait) {destroy = lock->acquire (wait);}
+  ~sentry () {if (destroy) lock->release ();}
+  friend void _threadinfo::init ();
+};
+
+muto NO_COPY *sentry::lock;
 
-static _threadinfo NO_COPY dummy_thread;
-_threadinfo NO_COPY *_last_thread = &dummy_thread;
+static size_t NO_COPY nthreads;
 
-CRITICAL_SECTION NO_COPY _threadinfo::protect_linked_list;
+#define THREADLIST_CHUNK 256
+
+void
+_threadinfo::init ()
+{
+  if (cygheap->threadlist)
+    memset (cygheap->threadlist, 0, cygheap->sthreads * sizeof (cygheap->threadlist[0]));
+  else
+    {
+      cygheap->sthreads = THREADLIST_CHUNK;
+      cygheap->threadlist = (_threadinfo **) ccalloc (HEAP_TLS, cygheap->sthreads,
+                                                    sizeof (cygheap->threadlist[0]));
+    }
+  new_muto1 (sentry::lock, sentry_lock);
+}
 
 void
 _threadinfo::set_state (bool is_exception)
@@ -32,7 +69,6 @@ _threadinfo::reset_exception ()
       debug_printf ("resetting stack after an exception stack %p, stackptr %p", stack, stackptr);
 #endif
       set_state (false);
-      stackptr--;
     }
 }
 
@@ -47,22 +83,22 @@ _threadinfo::call (DWORD (*func) (void *, void *), void *arg)
 void
 _threadinfo::call2 (DWORD (*func) (void *, void *), void *arg, void *buf)
 {
-  _my_tls.init_thread (buf);
-  ExitThread (func (arg, buf));
-}
-
-void
-_threadinfo::init ()
-{
-  InitializeCriticalSection (&protect_linked_list);
+  exception_list except_entry;
+  /* Initialize this thread's ability to respond to things like
+     SIGSEGV or SIGFPE. */
+  init_exceptions (&except_entry);
+  _my_tls.init_thread (buf, func);
+  DWORD res = func (arg, buf);
+  _my_tls.remove (INFINITE);
+  ExitThread (res);
 }
 
 void
-_threadinfo::init_thread (void *x)
+_threadinfo::init_thread (void *x, DWORD (*func) (void *, void *))
 {
   if (x)
     {
-      memset (this, 0, sizeof (*this));
+      memset (this, 0, CYGTLS_PADSIZE);
       stackptr = stack;
       if (_GLOBAL_REENT)
        {
@@ -76,30 +112,40 @@ _threadinfo::init_thread (void *x)
       locals.process_logmask = LOG_UPTO (LOG_DEBUG);
     }
 
-  EnterCriticalSection (&protect_linked_list);
-  prev = _last_thread;
-  _last_thread->next = this;
-  _last_thread = this;
-  LeaveCriticalSection (&protect_linked_list);
-
   set_state (false);
   errno_addr = &(local_clib._errno);
+
+  if ((void *) func == (void *) cygthread::stub
+      || (void *) func == (void *) cygthread::simplestub)
+    return;
+
+  sentry here (INFINITE);
+  if (nthreads >= cygheap->sthreads)
+    {
+      cygheap->threadlist = (_threadinfo **)
+       crealloc (cygheap->threadlist, (cygheap->sthreads += THREADLIST_CHUNK)
+                * sizeof (cygheap->threadlist[0]));
+      memset (cygheap->threadlist + nthreads, 0, THREADLIST_CHUNK * sizeof (cygheap->threadlist[0]));
+    }
+
+  cygheap->threadlist[nthreads++] = this;
 }
 
 void
-_threadinfo::remove ()
+_threadinfo::remove (DWORD wait)
 {
-  EnterCriticalSection (&protect_linked_list);
-  if (prev)
+  debug_printf ("wait %p\n", wait);
+  sentry here (wait);
+  if (here.acquired ())
     {
-      prev->next = next;
-      if (next)
-       next->prev = prev;
-      if (this == _last_thread)
-       _last_thread = prev;
-      prev = next = NULL;
+      for (size_t i = 0; i < nthreads; i++)
+       if (&_my_tls == cygheap->threadlist[i])
+         {
+           if (i < --nthreads)
+             cygheap->threadlist[i] = cygheap->threadlist[nthreads];
+           break;
+         }
     }
-  LeaveCriticalSection (&protect_linked_list);
 }
 
 void
@@ -123,3 +169,48 @@ _threadinfo::pop ()
   return res;
 }
 
+#define BAD_IX ((size_t) -1)
+static size_t NO_COPY threadlist_ix = BAD_IX;
+
+_threadinfo *
+_threadinfo::find_tls (int sig)
+{
+  debug_printf ("sig %d\n", sig);
+  sentry here (INFINITE);
+  __asm__ volatile (".equ _threadlist_exception_return,.");
+  _threadinfo *res = NULL;
+  for (threadlist_ix = 0; threadlist_ix < nthreads; threadlist_ix++)
+    if (sigismember (&(cygheap->threadlist[threadlist_ix]->sigwait_mask), sig))
+      {
+       res = cygheap->threadlist[threadlist_ix];
+       break;
+      }
+  threadlist_ix = BAD_IX;
+  return res;
+}
+
+extern "C" DWORD __stdcall RtlUnwind (void *, void *, void *, DWORD);
+static int
+handle_threadlist_exception (EXCEPTION_RECORD *e, void *frame, CONTEXT *, void *)
+{
+  small_printf ("in handle_threadlist_exception!\n");
+  if (e->ExceptionCode != STATUS_ACCESS_VIOLATION)
+    return 1;
+
+  sentry here;
+  if (threadlist_ix != BAD_IX || !here.acquired ())
+    return 1;
+
+  extern void *threadlist_exception_return;
+  cygheap->threadlist[threadlist_ix]->remove (INFINITE);
+  threadlist_ix = 0;
+  RtlUnwind (frame, threadlist_exception_return, e, 0);
+  return 0;
+}
+
+void
+_threadinfo::init_threadlist_exceptions (exception_list *el)
+{
+  extern void init_exception_handler (exception_list *, exception_handler *);
+  init_exception_handler (el, handle_threadlist_exception);
+}
index f11c65b..779e42b 100644 (file)
@@ -28,7 +28,7 @@ details. */
 # define UNLEN 256
 #endif
 
-#define TLS_STACK_SIZE 1024
+#define TLS_STACK_SIZE 256
 
 #pragma pack(push,4)
 struct _local_storage
@@ -110,15 +110,16 @@ struct _threadinfo
   __stack_t *stackptr;
   int sig;
   __stack_t stack[TLS_STACK_SIZE];
+  unsigned padding[0];
 
   /*gentls_offsets*/
   static CRITICAL_SECTION protect_linked_list;
   static void init ();
-  void init_thread (void *) __attribute__ ((regparm (2)));
-  static void call (DWORD (*) (void *, void *), void *) __attribute__ ((regparm (3)));
+  void init_thread (void *, DWORD (*) (void *, void *));
+  static void call (DWORD (*) (void *, void *), void *);
   static void call2 (DWORD (*) (void *, void *), void *, void *) __attribute__ ((regparm (3)));
   static struct _threadinfo *find_tls (int sig);
-  void remove ();
+  void remove (DWORD);
   void push (__stack_t, bool = false);
   __stack_t pop ();
   bool isinitialized () {return initialized == CYGTLS_INITIALIZED || initialized == CYGTLS_EXCEPTION;}
@@ -128,6 +129,7 @@ struct _threadinfo
     __attribute__((regparm(3)));
   void __stdcall interrupt_setup (int sig, void *handler, struct sigaction& siga, __stack_t retaddr)
     __attribute__((regparm(3)));
+  void init_threadlist_exceptions (struct _exception_list *);
   operator HANDLE () const {return tid->win32_obj_id;}
   /*gentls_offsets*/
 };
@@ -140,5 +142,5 @@ extern _threadinfo *_main_tls;
 
 #define __getreent() (&_my_tls.local_clib)
 
-#define CYGTLS_PADSIZE (sizeof (_threadinfo))
+const int CYGTLS_PADSIZE  = (((char *) _main_tls->padding) - ((char *) _main_tls));
 #endif /*_CYGTLS_H*/
index f97c0f9..3d6b7a8 100644 (file)
@@ -35,6 +35,7 @@ details. */
 #include "dll_init.h"
 #include "cygthread.h"
 #include "sync.h"
+#include "heap.h"
 
 #define MAX_AT_FILE_LEVEL 10
 
@@ -55,11 +56,13 @@ bool strip_title_path;
 bool allow_glob = true;
 codepage_type current_codepage = ansi_cp;
 
-static NO_COPY int mypid = 0;
 int __argc_safe;
 int _declspec(dllexport) __argc;
 char _declspec(dllexport) **__argv;
-vfork_save NO_COPY *main_vfork = NULL;
+vfork_save NO_COPY *main_vfork;
+
+static int NO_COPY envc;
+char NO_COPY **envp;
 
 extern "C" void __sinit (_reent *);
 
@@ -519,41 +522,127 @@ alloc_stack (child_info_fork *ci)
   return;
 }
 
-/* Take over from libc's crt0.o and start the application. Note the
-   various special cases when Cygwin DLL is being runtime loaded (as
-   opposed to being link-time loaded by Cygwin apps) from a non
-   cygwin app via LoadLibrary.  */
+#ifdef DEBUGGING
+void
+break_here ()
+{
+  debug_printf ("break here");
+}
+#endif
+
 static void
-dll_crt0_1 (char *)
+initial_env ()
 {
-  /* According to onno@stack.urc.tue.nl, the exception handler record must
-     be on the stack.  */
-  /* FIXME: Verify forked children get their exception handler set up ok. */
-  exception_list cygwin_except_entry;
+  char buf[CYG_MAX_PATH + 1];
+#ifdef DEBUGGING
+  DWORD len;
+  if (GetEnvironmentVariable ("CYGWIN_SLEEP", buf, sizeof (buf) - 1))
+    {
+      DWORD ms = atoi (buf);
+      buf[0] = '\0';
+      len = GetModuleFileName (NULL, buf, CYG_MAX_PATH);
+      console_printf ("Sleeping %d, pid %u %s\n", ms, GetCurrentProcessId (), buf);
+      while (ms--)
+       Sleep (1);
+    }
+  if (GetEnvironmentVariable ("CYGWIN_DEBUG", buf, sizeof (buf) - 1))
+    {
+      char buf1[CYG_MAX_PATH + 1];
+      len = GetModuleFileName (NULL, buf1, CYG_MAX_PATH);
+      strlwr (buf1);
+      strlwr (buf);
+      char *p = strchr (buf, ':');
+      if (!p)
+       p = (char *) "gdb.exe -nw";
+      else
+       *p++ = '\0';
+      if (strstr (buf1, buf))
+       {
+         error_start_init (p);
+         try_to_debug ();
+         break_here ();
+       }
+    }
+#endif
 
-  /* Initialize SIGSEGV handling, etc. */
-  init_exceptions (&cygwin_except_entry);
+  if (GetEnvironmentVariable ("CYGWIN_TESTING", buf, sizeof (buf) - 1))
+    _cygwin_testing = 1;
+}
 
-  /* Set the os_being_run global. */
+void __stdcall
+dll_crt0_0 ()
+{
   wincap.init ();
-  device::init ();
-  check_sanity_and_sync (user_data);
+  initial_env ();
 
-  do_global_ctors (&__CTOR_LIST__, 1);
+  char zeros[sizeof (child_proc_info->zero)] = {0};
 
-  /* Nasty static stuff needed by newlib -- point to a local copy of
-     the reent stuff.
-     Note: this MUST be done here (before the forkee code) as the
-     fork copy code doesn't copy the data in libccrt0.cc (that's why we
-     pass in the per_process struct into the .dll from libccrt0). */
+  init_console_handler ();
+  init_global_security ();
+  if (!DuplicateHandle (GetCurrentProcess (), GetCurrentProcess (),
+                      GetCurrentProcess (), &hMainProc, 0, FALSE,
+                       DUPLICATE_SAME_ACCESS))
+    hMainProc = GetCurrentProcess ();
 
-  user_data->resourcelocks->Init ();
-  user_data->threadinterface->Init ();
+  DuplicateHandle (hMainProc, GetCurrentThread (), hMainProc,
+                  &hMainThread, 0, false, DUPLICATE_SAME_ACCESS);
 
-  winpids::init ();
+  (void) SetErrorMode (SEM_FAILCRITICALERRORS);
 
-  int envc = 0;
-  char **envp = NULL;
+  STARTUPINFO si;
+  GetStartupInfo (&si);
+  child_proc_info = (child_info *) si.lpReserved2;
+
+  int mypid = 0;
+  if (si.cbReserved2 < EXEC_MAGIC_SIZE || !child_proc_info
+      || memcmp (child_proc_info->zero, zeros,
+                sizeof (child_proc_info->zero)) != 0)
+    child_proc_info = NULL;
+  else
+    {
+      if ((child_proc_info->intro & OPROC_MAGIC_MASK) == OPROC_MAGIC_GENERIC)
+       multiple_cygwin_problem ("proc", child_proc_info->intro, 0);
+      else if (child_proc_info->intro == PROC_MAGIC_GENERIC
+              && child_proc_info->magic != CHILD_INFO_MAGIC)
+       multiple_cygwin_problem ("proc", child_proc_info->magic,
+                                CHILD_INFO_MAGIC);
+      else if (child_proc_info->cygheap != (void *) &_cygheap_start)
+       multiple_cygwin_problem ("cygheap", (DWORD) child_proc_info->cygheap,
+                                (DWORD) &_cygheap_start);
+      unsigned should_be_cb = 0;
+      switch (child_proc_info->type)
+       {
+         case _PROC_FORK:
+           user_data->forkee = child_proc_info->cygpid;
+           should_be_cb = sizeof (child_info_fork);
+           /* fall through */;
+         case _PROC_SPAWN:
+         case _PROC_EXEC:
+           if (!should_be_cb)
+             should_be_cb = sizeof (child_info);
+           if (should_be_cb != child_proc_info->cb)
+             multiple_cygwin_problem ("proc size", child_proc_info->cb, should_be_cb);
+           else if (sizeof (fhandler_union) != child_proc_info->fhandler_union_cb)
+             multiple_cygwin_problem ("fhandler size", child_proc_info->fhandler_union_cb, sizeof (fhandler_union));
+           else
+             {
+               cygwin_user_h = child_proc_info->user_h;
+               mypid = child_proc_info->cygpid;
+               break;
+             }
+         default:
+           system_printf ("unknown exec type %d", child_proc_info->type);
+           /* intentionally fall through */
+         case _PROC_WHOOPS:
+           child_proc_info = NULL;
+           break;
+       }
+    }
+
+  device::init ();
+  winpids::init ();
+  do_global_ctors (&__CTOR_LIST__, 1);
+  cygthread::init ();
 
   if (!child_proc_info)
     memory_init ();
@@ -591,6 +680,7 @@ dll_crt0_1 (char *)
            __argv = spawn_info->moreinfo->argv;
            envp = spawn_info->moreinfo->envp;
            envc = spawn_info->moreinfo->envc;
+           envp = spawn_info->moreinfo->envp;
            cygheap->fdtab.fixup_after_exec (spawn_info->parent);
            signal_fixup_after_exec ();
            CloseHandle (spawn_info->parent);
@@ -607,9 +697,44 @@ dll_crt0_1 (char *)
        CloseHandle (child_proc_info->pppid_handle);
     }
 
+  _threadinfo::init ();
+
+  /* Initialize events */
+  events_init ();
+
+  /* Init global well known SID objects */
+  cygsid::init ();
+  cygheap->cwd.init ();
+}
+
+/* Take over from libc's crt0.o and start the application. Note the
+   various special cases when Cygwin DLL is being runtime loaded (as
+   opposed to being link-time loaded by Cygwin apps) from a non
+   cygwin app via LoadLibrary.  */
+static void
+dll_crt0_1 (char *)
+{
+  /* According to onno@stack.urc.tue.nl, the exception handler record must
+     be on the stack.  */
+  /* FIXME: Verify forked children get their exception handler set up ok. */
+  exception_list cygwin_except_entry;
+
+  check_sanity_and_sync (user_data);
+  malloc_init ();
+
+  /* Initialize SIGSEGV handling, etc. */
+  init_exceptions (&cygwin_except_entry);
+
+  /* Nasty static stuff needed by newlib -- point to a local copy of
+     the reent stuff.
+     Note: this MUST be done here (before the forkee code) as the
+     fork copy code doesn't copy the data in libccrt0.cc (that's why we
+     pass in the per_process struct into the .dll from libccrt0). */
+
+  user_data->resourcelocks->Init ();
+  user_data->threadinterface->Init ();
   ProtectHandle (hMainProc);
   ProtectHandle (hMainThread);
-  cygthread::init ();
 
   /* Initialize pthread mainthread when not forked and it is safe to call new,
      otherwise it is reinitalized in fixup_after_fork */
@@ -629,12 +754,6 @@ dll_crt0_1 (char *)
 
   cygheap->fdtab.vfork_child_fixup ();
 
-  (void) SetErrorMode (SEM_FAILCRITICALERRORS);
-
-  /* Initialize events. */
-  events_init ();
-
-  cygheap->cwd.init ();
   main_vfork = vfork_storage.create ();
 
   cygbench ("pre-forkee");
@@ -663,9 +782,6 @@ dll_crt0_1 (char *)
   }
 #endif
 
-  /* Init global well known SID objects */
-  cygsid::init ();
-
   /* Initialize our process table entry. */
   pinfo_init (envp, envc);
 
@@ -773,60 +889,13 @@ dll_crt0_1 (char *)
     exit (user_data->main (__argc, __argv, *user_data->envptr));
 }
 
-#ifdef DEBUGGING
-void
-break_here ()
-{
-  debug_printf ("break here");
-}
-#endif
-
-void
-initial_env ()
-{
-  char buf[CYG_MAX_PATH + 1];
-#ifdef DEBUGGING
-  DWORD len;
-  if (GetEnvironmentVariable ("CYGWIN_SLEEP", buf, sizeof (buf) - 1))
-    {
-      DWORD ms = atoi (buf);
-      buf[0] = '\0';
-      len = GetModuleFileName (NULL, buf, CYG_MAX_PATH);
-      console_printf ("Sleeping %d, pid %u %s\n", ms, GetCurrentProcessId (), buf);
-      Sleep (ms);
-    }
-  if (GetEnvironmentVariable ("CYGWIN_DEBUG", buf, sizeof (buf) - 1))
-    {
-      char buf1[CYG_MAX_PATH + 1];
-      len = GetModuleFileName (NULL, buf1, CYG_MAX_PATH);
-      strlwr (buf1);
-      strlwr (buf);
-      char *p = strchr (buf, ':');
-      if (!p)
-       p = (char *) "gdb.exe -nw";
-      else
-       *p++ = '\0';
-      if (strstr (buf1, buf))
-       {
-         error_start_init (p);
-         try_to_debug ();
-         break_here ();
-       }
-    }
-#endif
-
-  if (GetEnvironmentVariable ("CYGWIN_TESTING", buf, sizeof (buf) - 1))
-    _cygwin_testing = 1;
-}
-
 struct _reent *
 initialize_main_tls (char *padding)
 {
   if (!_main_tls)
     {
-      _threadinfo::init ();
       _main_tls = &_my_tls;
-      _main_tls->init_thread (padding);
+      _main_tls->init_thread (padding, NULL);
     }
   return &_main_tls->local_clib;
 }
@@ -836,81 +905,31 @@ initialize_main_tls (char *padding)
 
    UPTR is a pointer to global data that lives on the libc side of the
    line [if one distinguishes the application from the dll].  */
-
+  
 extern "C" void __stdcall
 _dll_crt0 ()
 {
-  initial_env ();
-  char zeros[max (CYGTLS_PADSIZE, sizeof (child_proc_info->zero))] = {0};
-  static NO_COPY STARTUPINFO si;
+  extern HANDLE sync_startup;
+  if (sync_startup)
+    {
+      (void) WaitForSingleObject (sync_startup, INFINITE);
+      CloseHandle (sync_startup);
+    }
 
   main_environ = user_data->envptr;
   *main_environ = NULL;
 
-  init_console_handler ();
-  init_global_security ();
-  if (!DuplicateHandle (GetCurrentProcess (), GetCurrentProcess (),
-                      GetCurrentProcess (), &hMainProc, 0, FALSE,
-                       DUPLICATE_SAME_ACCESS))
-    hMainProc = GetCurrentProcess ();
+  if (child_proc_info && child_proc_info->type == _PROC_FORK)
+    user_data->forkee = child_proc_info->cygpid;
 
-  DuplicateHandle (hMainProc, GetCurrentThread (), hMainProc,
-                  &hMainThread, 0, false, DUPLICATE_SAME_ACCESS);
-
-  GetStartupInfo (&si);
-  child_proc_info = (child_info *) si.lpReserved2;
-  if (si.cbReserved2 < EXEC_MAGIC_SIZE || !child_proc_info
-      || memcmp (child_proc_info->zero, zeros,
-                sizeof (child_proc_info->zero)) != 0)
-    child_proc_info = NULL;
-  else
-    {
-      if ((child_proc_info->intro & OPROC_MAGIC_MASK) == OPROC_MAGIC_GENERIC)
-       multiple_cygwin_problem ("proc", child_proc_info->intro, 0);
-      else if (child_proc_info->intro == PROC_MAGIC_GENERIC
-              && child_proc_info->magic != CHILD_INFO_MAGIC)
-       multiple_cygwin_problem ("proc", child_proc_info->magic,
-                                CHILD_INFO_MAGIC);
-      else if (child_proc_info->cygheap != (void *) &_cygheap_start)
-       multiple_cygwin_problem ("cygheap", (DWORD) child_proc_info->cygheap,
-                                (DWORD) &_cygheap_start);
-      unsigned should_be_cb = 0;
-      switch (child_proc_info->type)
-       {
-         case _PROC_FORK:
-           user_data->forkee = child_proc_info->cygpid;
-           should_be_cb = sizeof (child_info_fork);
-           /* fall through */;
-         case _PROC_SPAWN:
-         case _PROC_EXEC:
-           if (!should_be_cb)
-             should_be_cb = sizeof (child_info);
-           if (should_be_cb != child_proc_info->cb)
-             multiple_cygwin_problem ("proc size", child_proc_info->cb, should_be_cb);
-           else if (sizeof (fhandler_union) != child_proc_info->fhandler_union_cb)
-             multiple_cygwin_problem ("fhandler size", child_proc_info->fhandler_union_cb, sizeof (fhandler_union));
-           else
-             {
-               cygwin_user_h = child_proc_info->user_h;
-               mypid = child_proc_info->cygpid;
-               break;
-             }
-         default:
-           system_printf ("unknown exec type %d", child_proc_info->type);
-           /* intentionally fall through */
-         case _PROC_WHOOPS:
-           child_proc_info = NULL;
-           break;
-       }
-    }
-  
+  char padding[CYGTLS_PADSIZE];
   _impure_ptr = &reent_data;
   _impure_ptr->_stdin = &_impure_ptr->__sf[0];
   _impure_ptr->_stdout = &_impure_ptr->__sf[1];
   _impure_ptr->_stderr = &_impure_ptr->__sf[2];
   _impure_ptr->_current_locale = "C";
-  initialize_main_tls (zeros);
-  dll_crt0_1 (zeros);
+  initialize_main_tls (padding);
+  dll_crt0_1 (padding);
 }
 
 void
@@ -970,6 +989,7 @@ do_exit (int status)
     }
 
   EnterCriticalSection (&exit_lock);
+  muto::set_exiting_thread ();
   if (exit_state < ES_EVENTS_TERMINATE)
     {
       exit_state = ES_EVENTS_TERMINATE;
@@ -1090,7 +1110,8 @@ __api_fatal (const char *fmt, ...)
   va_list ap;
 
   va_start (ap, fmt);
-  __small_vsprintf (buf, fmt, ap);
+  int n = __small_sprintf (buf, "%P (%u): *** ", cygwin_pid (GetCurrentProcessId ()));
+  __small_vsprintf (buf + n, fmt, ap);
   va_end (ap);
   strcat (buf, "\n");
   int len = strlen (buf);
index 4f1d6df..05b53cf 100644 (file)
@@ -112,6 +112,9 @@ add_handle (const char *func, int ln, HANDLE h, const char *name, bool inh)
   handle_list *hl;
   lock_debug here;
 
+  if (!cygheap)
+    return;
+
   if ((hl = find_handle (h)))
     {
       hl = hl->next;
@@ -172,6 +175,9 @@ mark_closed (const char *func, int ln, HANDLE h, const char *name, bool force)
   handle_list *hl;
   lock_debug here;
 
+  if (!cygheap)
+    return true;
+
   if ((hl = find_handle (h)) && !force)
     {
       hl = hl->next;
index 2bc987f..8a25b7d 100644 (file)
@@ -83,8 +83,6 @@ get_full_path_of_dll (const char* str, char *name)
 void *
 dlopen (const char *name, int)
 {
-  SetResourceLock (LOCK_DLL_LIST, READ_LOCK | WRITE_LOCK, "dlopen");
-
   void *ret;
 
   if (name == NULL)
@@ -108,7 +106,6 @@ dlopen (const char *name, int)
     set_dl_error ("dlopen");
   debug_printf ("ret %p", ret);
 
-  ReleaseResourceLock (LOCK_DLL_LIST, READ_LOCK | WRITE_LOCK, "dlopen");
   return ret;
 }
 
@@ -125,8 +122,6 @@ dlsym (void *handle, const char *name)
 int
 dlclose (void *handle)
 {
-  SetResourceLock (LOCK_DLL_LIST, READ_LOCK | WRITE_LOCK, "dlclose");
-
   int ret = -1;
   void *temphandle = (void *) GetModuleHandle (NULL);
   if (temphandle == handle || FreeLibrary ((HMODULE) handle))
@@ -134,8 +129,6 @@ dlclose (void *handle)
   if (ret)
     set_dl_error ("dlclose");
   CloseHandle ((HMODULE) temphandle);
-
-  ReleaseResourceLock (LOCK_DLL_LIST, READ_LOCK | WRITE_LOCK, "dlclose");
   return ret;
 }
 
index 1bfd61c..14bfe93 100644 (file)
@@ -195,7 +195,7 @@ dll_list::detach (void *retaddr)
     if (d->handle != h)
       continue;
     else if (d->count <= 0)
-      system_printf ("WARNING: try to detach an already detached dll ...");
+      system_printf ("WARNING: trying to detach an already detached dll ...");
     else if (--d->count == 0)
       {
        d->p.run_dtors ();
index 2c37a22..3807039 100644 (file)
@@ -3,11 +3,9 @@
 <title>cygwin_detach_dll</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" void
 <function>cygwin_detach_dll</function></funcdef>
 <paramdef>int <parameter>dll_index</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 </sect1>
index 141e173..cd41cb9 100644 (file)
@@ -33,19 +33,21 @@ details. */
 #include "ntdll.h"
 #include "tty.h"
 
+static const char NO_COPY unknown_file[] = "some disk file";
+
 static const NO_COPY DWORD std_consts[] = {STD_INPUT_HANDLE, STD_OUTPUT_HANDLE,
                                           STD_ERROR_HANDLE};
 
 static const char *handle_to_fn (HANDLE, char *);
 
-static const char NO_COPY unknown_file[] = "some disk file";
-
 /* Set aside space for the table of fds */
 void
-dtable_init (void)
+dtable_init ()
 {
   if (!cygheap->fdtab.size)
     cygheap->fdtab.extend (NOFILE_INCR);
+  cygheap->fdtab.init_lock ();
+
 }
 
 void __stdcall
@@ -57,6 +59,12 @@ set_std_handle (int fd)
     SetStdHandle (std_consts[fd], cygheap->fdtab[fd]->get_output_handle ());
 }
 
+void
+dtable::init_lock ()
+{
+  new_muto (lock_cs);
+}
+
 int
 dtable::extend (int howmuch)
 {
@@ -490,7 +498,7 @@ dtable::dup2 (int oldfd, int newfd)
 
   MALLOC_CHECK;
   debug_printf ("dup2 (%d, %d)", oldfd, newfd);
-  SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "dup");
+  lock ();
 
   if (not_open (oldfd))
     {
@@ -539,7 +547,7 @@ dtable::dup2 (int oldfd, int newfd)
 
 done:
   MALLOC_CHECK;
-  ReleaseResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "dup");
+  unlock ();
   syscall_printf ("%d = dup2 (%d, %d)", res, oldfd, newfd);
 
   return res;
@@ -548,7 +556,7 @@ done:
 fhandler_fifo *
 dtable::find_fifo (ATOM hill)
 {
-  SetResourceLock (LOCK_FD_LIST, READ_LOCK, "dup");
+  lock ();
   for (unsigned i = 0; i < size; i++)
     {
       fhandler_base *fh = fds[i];
@@ -614,7 +622,7 @@ dtable::select_except (int fd, select_record *s)
 void
 dtable::fixup_before_fork (DWORD target_proc_id)
 {
-  SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "fixup_before_fork");
+  lock ();
   fhandler_base *fh;
   for (size_t i = 0; i < size; i++)
     if ((fh = fds[i]) != NULL)
@@ -622,13 +630,13 @@ dtable::fixup_before_fork (DWORD target_proc_id)
        debug_printf ("fd %d (%s)", i, fh->get_name ());
        fh->fixup_before_fork_exec (target_proc_id);
       }
-  ReleaseResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "fixup_before_fork");
+  unlock ();
 }
 
 void
 dtable::fixup_before_exec (DWORD target_proc_id)
 {
-  SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "fixup_before_exec");
+  lock ();
   fhandler_base *fh;
   for (size_t i = 0; i < size; i++)
     if ((fh = fds[i]) != NULL && !fh->get_close_on_exec ())
@@ -636,18 +644,18 @@ dtable::fixup_before_exec (DWORD target_proc_id)
        debug_printf ("fd %d (%s)", i, fh->get_name ());
        fh->fixup_before_fork_exec (target_proc_id);
       }
-  ReleaseResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "fixup_before_exec");
+  unlock ();
 }
 
 void
 dtable::set_file_pointers_for_exec ()
 {
-  SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "set_file_pointers_for_exec");
+  lock ();
   fhandler_base *fh;
   for (size_t i = 0; i < size; i++)
     if ((fh = fds[i]) != NULL && fh->get_flags () & O_APPEND)
       SetFilePointer (fh->get_handle (), 0, 0, FILE_END);
-  ReleaseResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "fixup_before_exec");
+  unlock ();
 }
 
 void
@@ -655,6 +663,7 @@ dtable::fixup_after_exec (HANDLE parent)
 {
   first_fd_for_open = 0;
   fhandler_base *fh;
+  cygheap->fdtab.init_lock ();
   for (size_t i = 0; i < size; i++)
     if ((fh = fds[i]) != NULL)
       {
@@ -680,6 +689,7 @@ void
 dtable::fixup_after_fork (HANDLE parent)
 {
   fhandler_base *fh;
+  cygheap->fdtab.init_lock ();
   for (size_t i = 0; i < size; i++)
     if ((fh = fds[i]) != NULL)
       {
@@ -699,7 +709,7 @@ int
 dtable::vfork_child_dup ()
 {
   fhandler_base **newtable;
-  SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "dup");
+  lock ();
   newtable = (fhandler_base **) ccalloc (HEAP_ARGV, size, sizeof (fds[0]));
   int res = 1;
 
@@ -731,21 +741,21 @@ out:
   /* Restore impersonation */
   cygheap->user.reimpersonate ();
 
-  ReleaseResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "dup");
+  unlock ();
   return 1;
 }
 
 void
 dtable::vfork_parent_restore ()
 {
-  SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "restore");
+  lock ();
 
   close_all_files ();
   fhandler_base **deleteme = fds;
   fds = fds_on_hold;
   fds_on_hold = NULL;
   cfree (deleteme);
-  ReleaseResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "restore");
+  unlock ();
 
   cygheap->ctty = cygheap->ctty_on_hold;       // revert
   if (cygheap->ctty)
index 0b2db91..573467d 100644 (file)
@@ -12,6 +12,7 @@ details. */
 #define NOFILE_INCR    32
 
 #include "thread.h"
+#include "sync.h"
 
 class suffix_info;
 class fhandler_fifo;
@@ -19,6 +20,7 @@ class fhandler_fifo;
 #define BFH_OPTS (PC_NULLEMPTY | PC_FULL | PC_POSIX)
 class dtable
 {
+  muto *lock_cs;
   fhandler_base **fds;
   fhandler_base **fds_on_hold;
   fhandler_base **archetypes;
@@ -27,6 +29,9 @@ class dtable
   static const int initial_archetype_size = 8;
   int first_fd_for_open;
   int cnt_need_fixup_before;
+  void lock () {lock_cs->acquire ();}
+  void unlock () {lock_cs->release ();}
+  void init_lock ();
 public:
   size_t size;
 
@@ -50,11 +55,9 @@ public:
   void fixup_after_fork (HANDLE);
   inline int not_open (int fd)
   {
-    SetResourceLock (LOCK_FD_LIST, READ_LOCK, "not_open");
-
+    lock ();
     int res = fd < 0 || fd >= (int) size || fds[fd] == NULL;
-
-    ReleaseResourceLock (LOCK_FD_LIST, READ_LOCK, "not open");
+    unlock ();
     return res;
   }
   int find_unused_handle (int start);
@@ -76,6 +79,11 @@ public:
   fhandler_base *find_archetype (device& dev);
   fhandler_base **add_archetype ();
   void delete_archetype (fhandler_base *);
+  friend void dtable_init ();
+  friend void __stdcall close_all_files ();
+  friend class cygheap_fdmanip;
+  friend class cygheap_fdget;
+  friend class cygheap_fdnew;
 };
 
 fhandler_base *build_fh_dev (const device&, const char * = NULL);
index 5e80788..9f292ee 100644 (file)
@@ -3,7 +3,6 @@
 <title>cygwin_attach_handle_to_fd</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" int
 <function>cygwin_attach_handle_to_fd</function></funcdef>
 <paramdef>char *<parameter>name</parameter></paramdef>
@@ -11,7 +10,6 @@
 <paramdef>HANDLE <parameter>handle</parameter></paramdef>
 <paramdef>int <parameter>bin</parameter></paramdef>
 <paramdef>int <parameter>access</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>This function can be used to turn a Win32 "handle" into a
index 669b516..597c58e 100644 (file)
@@ -98,18 +98,22 @@ NO_COPY static struct
 // of code that handles exceptions.  The x86 on the other hand uses segment
 // register fs, offset 0 to point to the current exception handler.
 
-asm (".equ __except_list,0");
+extern exception_list *_except_list asm ("%fs:0");
 
-extern exception_list *_except_list asm ("%fs:__except_list");
-
-static void
-init_exception_handler (exception_list *el)
+void
+init_exception_handler (exception_list *el, exception_handler *eh)
 {
-  el->handler = handle_exceptions;
+  el->handler = eh;
   el->prev = _except_list;
   _except_list = el;
 }
 
+extern "C" void
+init_exceptions (exception_list *el)
+{
+  init_exception_handler (el, handle_exceptions);
+}
+
 void
 init_console_handler ()
 {
@@ -119,12 +123,6 @@ init_console_handler ()
 }
 
 extern "C" void
-init_exceptions (exception_list *el)
-{
-  init_exception_handler (el);
-}
-
-extern "C" void
 error_start_init (const char *buf)
 {
   if (!buf || !*buf)
@@ -363,6 +361,8 @@ try_to_debug (bool waitloop)
        }
     }
 
+  small_printf ("*** starting debugger for pid %u\n",
+               cygwin_pid (GetCurrentProcessId ()));
   BOOL dbg;
   dbg = CreateProcess (NULL,
                       debugger_command,
@@ -383,9 +383,9 @@ try_to_debug (bool waitloop)
        return 1;
       SetThreadPriority (GetCurrentThread (), THREAD_PRIORITY_IDLE);
       while (!being_debugged ())
-       Sleep (0);
-      Sleep (2000);
-      small_printf ("*** continuing from debugger call\n");
+       low_priority_sleep (0);
+      small_printf ("*** continuing pid %u from debugger call\n",
+                   cygwin_pid (GetCurrentProcessId ()));
     }
 
   SetThreadPriority (GetCurrentThread (), prio);
@@ -615,7 +615,7 @@ sig_handle_tty_stop (int sig)
 }
 }
 
-int
+bool
 interruptible (DWORD pc)
 {
   int res;
@@ -633,11 +633,11 @@ interruptible (DWORD pc)
      GetThreadContext.  These resolve to a strange allocation base.
      These should *never* be treated as interruptible. */
   if (!h || m.State != MEM_COMMIT)
-    res = 0;
+    res = false;
   else if (h == user_data->hmodule)
-    res = 1;
+    res = true;
   else if (!GetModuleFileName (h, checkdir, windows_system_directory_length + 2))
-    res = 0;
+    res = false;
   else
     res = !strncasematch (windows_system_directory, checkdir,
                          windows_system_directory_length);
@@ -666,7 +666,8 @@ _threadinfo::interrupt_setup (int sig, void *handler,
   /* Clear any waiting threads prior to dispatching to handler function */
   int res = SetEvent (signal_arrived); // For an EINTR case
   proc_subproc (PROC_CLEARWAIT, 1);
-  sigproc_printf ("armed signal_arrived %p, res %d", signal_arrived, res);
+  sigproc_printf ("armed signal_arrived %p, sig %d, res %d", signal_arrived,
+                 sig, res);
 }
 
 bool
@@ -762,26 +763,16 @@ setup_handler (int sig, void *handler, struct sigaction& siga, _threadinfo *tls)
 
       // FIXME - add check for reentering of DLL here
 
-      muto *m;
-      /* FIXME: Make multi-thread aware */
-      for (m = muto_start.next;  m != NULL; m = m->next)
-       if (m->unstable () || m->owner () == cygthread::main_thread_id)
-         {
-           sigproc_printf ("suspended thread owns a muto (%s)", m->name);
-           goto resume_thread;
-         }
-
       cx.ContextFlags = CONTEXT_CONTROL | CONTEXT_INTEGER;
       if (!GetThreadContext (hth, &cx))
        system_printf ("couldn't get context of main thread, %E");
       else if (interruptible (cx.Eip))
        interrupted = tls->interrupt_now (&cx, sig, handler, siga);
 
-    resume_thread:
       res = ResumeThread (hth);
-
       if (interrupted)
        break;
+
       sigproc_printf ("couldn't interrupt.  trying again.");
       low_priority_sleep (0);
     }
@@ -801,7 +792,7 @@ static BOOL WINAPI
 ctrl_c_handler (DWORD type)
 {
   static bool saw_close;
-  _my_tls.remove ();
+  _my_tls.remove (INFINITE);
 
   /* Return FALSE to prevent an "End task" dialog box from appearing
      for each Cygwin process window that's open when the computer
@@ -892,19 +883,6 @@ set_signal_mask (sigset_t newmask, sigset_t oldmask)
   return;
 }
 
-extern _threadinfo *_last_thread;
-
-_threadinfo *
-_threadinfo::find_tls (int sig)
-{
-  EnterCriticalSection (&protect_linked_list);
-  for (_threadinfo *t = _last_thread; t ; t = t->prev)
-    if (sigismember (&t->sigwait_mask, sig))
-      return t;
-  LeaveCriticalSection (&protect_linked_list);
-  return NULL;
-}
-
 int __stdcall
 sig_handle (int sig, sigset_t mask, int pid, _threadinfo *tls)
 {
@@ -924,15 +902,15 @@ sig_handle (int sig, sigset_t mask, int pid, _threadinfo *tls)
 
   int rc = 1;
   bool insigwait_mask = tls ? sigismember (&tls->sigwait_mask, sig) : false;
+  bool special_case = ISSTATE (myself, PID_STOPPED) || main_vfork->pid;
+  bool masked = sigismember (&mask, sig);
   if (sig != SIGKILL && sig != SIGSTOP
-      && (sigismember (&mask, sig)
-         || (tls
-             && (insigwait_mask || sigismember (&tls->sigmask, sig)))
-         || main_vfork->pid
-         || ISSTATE (myself, PID_STOPPED)))
+      && (special_case || main_vfork->pid || masked || insigwait_mask
+         || (tls && sigismember (&tls->sigmask, sig))))
     {
       sigproc_printf ("signal %d blocked", sig);
-      if (insigwait_mask || (tls = _threadinfo::find_tls (sig)) != NULL)
+      if ((!special_case && !masked)
+         && (insigwait_mask || (tls = _threadinfo::find_tls (sig)) != NULL))
        goto thread_specific;
       rc = -1;
       goto done;
@@ -1045,12 +1023,6 @@ signal_exit (int rc)
   (void) SetThreadPriority (hMainThread, THREAD_PRIORITY_IDLE);
   (void) SetThreadPriority (GetCurrentThread (), THREAD_PRIORITY_TIME_CRITICAL);
 
-  /* Unlock any main thread mutos since we're executing with prejudice. */
-  muto *m;
-  for (m = muto_start.next;  m != NULL; m = m->next)
-    if (m->unstable () || m->owner () == cygthread::main_thread_id)
-      m->reset ();
-
   user_data->resourcelocks->Delete ();
   user_data->resourcelocks->Init ();
 
@@ -1114,6 +1086,7 @@ call_signal_handler_now ()
       sa_flags = _my_tls.sa_flags;
       int sig = _my_tls.sig;
       void (*sigfunc) (int) = _my_tls.func;
+
       (void) _my_tls.pop ();
 #ifdef DEBUGGING
       if (_my_tls.stackptr > (_my_tls.stack + 1))
index 07b58b2..b637d2f 100644 (file)
@@ -135,16 +135,6 @@ cygwin_internal (cygwin_getinfo_types t, ...)
 {
   va_list arg;
   va_start (arg, t);
-  if (t != CW_USER_DATA)
-    {
-      wincap.init ();
-      if (!myself)
-       {
-         memory_init ();
-         malloc_init ();
-         set_myself (1);
-       }
-    }
 
   switch (t)
     {
index 88d6725..270eede 100644 (file)
@@ -3,12 +3,10 @@
 <title>cygwin_internal</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" DWORD
 <function>cygwin_internal</function></funcdef>
 <paramdef>cygwin_getinfo_types <parameter>t</parameter></paramdef>
 <paramdef><parameter>...</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>This function gives you access to various internal data and functions.
index b4ff074..407a47d 100644 (file)
@@ -167,8 +167,8 @@ sync_with_child (PROCESS_INFORMATION &pi, HANDLE subproc_ready,
        */
       if (errcode != STATUS_CONTROL_C_EXIT)
        {
-           system_printf ("child %d(%p) died before initialization with status code %p",
-                         pi.dwProcessId, pi.hProcess, errcode);
+           system_printf ("child %u(%p) died before initialization with status code %p",
+                         cygwin_pid (pi.dwProcessId), pi.hProcess, errcode);
            system_printf ("*** child state %s", s);
 #ifdef DEBUGGING
            abort ();
@@ -263,7 +263,7 @@ fork_child (HANDLE& hParent, dll *&first_dll, bool& load_dlls)
   if (fork_info->stacksize)
     {
       _main_tls = &_my_tls;
-      _main_tls->init_thread (NULL);
+      _main_tls->init_thread (NULL, NULL);
       _main_tls->local_clib = *_impure_ptr;
       _impure_ptr = &_main_tls->local_clib;
     }
@@ -721,6 +721,7 @@ vfork ()
       vf->pgid = myself->pgid;
       cygheap->ctty_on_hold = cygheap->ctty;
       vf->open_fhs = cygheap->open_fhs;
+      debug_printf ("cygheap->ctty_on_hold %p, cygheap->open_fhs %d", cygheap->ctty_on_hold, cygheap->open_fhs);
       int res = cygheap->fdtab.vfork_child_dup () ? 0 : -1;
       debug_printf ("%d = vfork()", res);
       call_signal_handler_now ();      // FIXME: racy
index 95d9b17..af5ec2f 100644 (file)
@@ -31,7 +31,6 @@ extern "C" size_t getpagesize ();
 #define MINHEAP_SIZE (4 * 1024 * 1024)
 
 /* Initialize the heap at process start up.  */
-
 void
 heap_init ()
 {
@@ -64,12 +63,11 @@ heap_init ()
       /* total size commited in parent */
       DWORD allocsize = (char *) cygheap->user_heap.top -
                        (char *) cygheap->user_heap.base;
-      /* round up by chunk size */
-      DWORD reserve_size = chunk * ((allocsize + (chunk - 1)) / chunk);
 
       /* Loop until we've managed to reserve an adequate amount of memory. */
       char *p;
-      for (;;)
+      DWORD reserve_size = chunk * ((allocsize + (chunk - 1)) / chunk);
+      while (1)
        {
          p = (char *) VirtualAlloc (cygheap->user_heap.base, reserve_size,
                                     MEM_RESERVE, PAGE_READWRITE);
@@ -78,8 +76,13 @@ heap_init ()
          if ((reserve_size -= page_const) <= allocsize)
            break;
        }
+      if (!p)
+       api_fatal ("couldn't allocate cygwin heap, %E, base %p, top %p, "
+                  "reserve_size %d, allocsize %d, page_const %d",
+                  cygheap->user_heap.base, cygheap->user_heap.top,
+                  reserve_size, allocsize, page_const);
       if (p != cygheap->user_heap.base)
-       api_fatal ("heap allocated but not at %p", cygheap->user_heap.base);
+       api_fatal ("heap allocated at wrong address %p (mapped) != %p (expected)", p, cygheap->user_heap.base);
       if (!VirtualAlloc (cygheap->user_heap.base, allocsize, MEM_COMMIT, PAGE_READWRITE))
        api_fatal ("MEM_COMMIT failed, %E");
     }
@@ -87,7 +90,7 @@ heap_init ()
   debug_printf ("heap base %p, heap top %p", cygheap->user_heap.base,
                cygheap->user_heap.top);
   page_const--;
-  malloc_init ();
+  // malloc_init ();
 }
 
 #define pround(n) (((size_t)(n) + page_const) & ~page_const)
index f6a29f2..a85a8a2 100644 (file)
@@ -16,51 +16,95 @@ details. */
 #include "cygtls.h"
 
 int NO_COPY dynamically_loaded;
+static char *search_for = (char *) cygthread::stub;
+static unsigned threadfunc_ix __attribute__((section ("cygwin_dll_common"), shared)) = 0;
+DWORD tls_func;
+
+HANDLE sync_startup;
+
+#define OLDFUNC_OFFSET -1
 
 static void WINAPI
 threadfunc_fe (VOID *arg)
 {
-  _threadinfo::call ((DWORD (*)  (void *, void *)) (((char **) _tlsbase)[-1]), arg);
+  _threadinfo::call ((DWORD (*)  (void *, void *)) (((char **) _tlsbase)[OLDFUNC_OFFSET]), arg);
+  // void *threadfunc = (void *) TlsGetValue (tls_func);
+  // TlsFree (tls_func);
+  // _threadinfo::call ((DWORD (*)  (void *, void *)) (threadfunc), arg);
+}
+
+static DWORD WINAPI
+calibration_thread (VOID *arg)
+{
+  ExitThread (0);
 }
 
 static void
 munge_threadfunc (HANDLE cygwin_hmodule)
 {
-  char **ebp = (char **) __builtin_frame_address (0); 
-  static unsigned threadfunc_ix;
+  char **ebp = (char **) __builtin_frame_address (0);
   if (!threadfunc_ix)
     {
       for (char **peb = ebp; peb < (char **) _tlsbase; peb++)
-       if (*peb == (char *) cygthread::stub)
+       if (*peb == search_for)
          {
            threadfunc_ix = peb - ebp;
            goto foundit;
          }
+#ifdef DEBUGGING
+      system_printf ("non-fatal warning: unknown thread! search_for %p, cygthread::stub %p, calibration_thread %p, possible func offset %p",
+                    search_for, cygthread::stub, calibration_thread, ebp[137]);
+#endif
+      try_to_debug ();
       return;
     }
 
 foundit:
   char *threadfunc = ebp[threadfunc_ix];
-  ebp[threadfunc_ix] = (char *) threadfunc_fe;
-  ((char **) _tlsbase)[-1] = threadfunc;
+  if (threadfunc == (char *) calibration_thread)
+    /* no need for the overhead */;
+  else
+    {
+      ebp[threadfunc_ix] = (char *) threadfunc_fe;
+      ((char **) _tlsbase)[OLDFUNC_OFFSET] = threadfunc;
+      // TlsSetValue (tls_func, (void *) threadfunc);
+    }
 }
 
+void
+prime_threads ()
+{
+  // tls_func = TlsAlloc ();
+  if (!threadfunc_ix)
+    {
+      DWORD id;
+      search_for = (char *) calibration_thread;
+      sync_startup = CreateThread (NULL, 0, calibration_thread, 0, 0, &id);
+    }
+}
+
+extern void __stdcall dll_crt0_0 ();
+
 extern "C" int WINAPI
 dll_entry (HANDLE h, DWORD reason, void *static_load)
 {
   switch (reason)
     {
     case DLL_PROCESS_ATTACH:
+      prime_threads ();
       dynamically_loaded = (static_load == NULL);
       // __cygwin_user_data.impure_ptr = &_my_tls.local_clib;
-      _my_tls.stackptr = NULL;
+      dll_crt0_0 ();
+      // small_printf ("%u, %p, %p\n", cygwin_pid (GetCurrentProcessId ()), _tlstop, _tlsbase);
       break;
     case DLL_PROCESS_DETACH:
       break;
     case DLL_THREAD_ATTACH:
       munge_threadfunc (h);
+      // small_printf ("%u, %p, %p\n", cygwin_pid (GetCurrentProcessId ()), _tlstop, _tlsbase);
       break;
     case DLL_THREAD_DETACH:
+      _my_tls.remove (0);
       break;
     }
   return 1;
index 5798cf4..7bcd181 100644 (file)
@@ -316,6 +316,7 @@ void
 malloc_init ()
 {
   new_muto (mallock);
+
   /* Check if mallock is provided by application. If so, redirect all
      calls to malloc/free/realloc to application provided. This may
      happen if some other dll calls cygwin's malloc, but main code provides
index 6638e92..6030c8f 100644 (file)
@@ -2,12 +2,10 @@
 <title>cygwin_posix_to_win32_path_list</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" void
 <function>cygwin_posix_to_win32_path_list</function></funcdef>
 <paramdef>const char *<parameter>posix</parameter></paramdef>
 <paramdef>char *<parameter>win32</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>Given a POSIX path-style string (i.e. /foo:/bar) convert it to
@@ -41,12 +39,10 @@ cygwin_posix_to_win32_path_list_buf_size</link></para>
 <title>cygwin_win32_to_posix_path_list</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" void
 <function>cygwin_win32_to_posix_path_list</function></funcdef>
 <paramdef>const char *<parameter>win32</parameter></paramdef>
 <paramdef>char *<parameter>posix</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>Given a Win32 path-style string (i.e. d:\;e:\bar) convert it to
@@ -62,11 +58,9 @@ cygwin_win32_to_posix_path_list_buf_size</link></para>
 <title>cygwin_posix_to_win32_path_list_buf_size</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" int
 <function>cygwin_posix_to_win32_path_list_buf_size</function></funcdef>
 <paramdef>const char *<parameter>path_list</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>Returns the number of bytes needed to hold the result of calling
@@ -79,11 +73,9 @@ cygwin_posix_to_win32_path_list</link>.</para>
 <title>cygwin_win32_to_posix_path_list_buf_size</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" int
 <function>cygwin_win32_to_posix_path_list_buf_size</function></funcdef>
 <paramdef>const char *<parameter>path_list</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>Tells you how many bytes are needed for the results of <link
@@ -96,12 +88,10 @@ cygwin_win32_to_posix_path_list</link>.</para>
 <title>cygwin_conv_to_posix_path</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" void
 <function>cygwin_conv_to_posix_path</function></funcdef>
 <paramdef>const char *<parameter>path</parameter></paramdef>
 <paramdef>char *<parameter>posix_path</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>Converts a Win32 path to a POSIX path.  If
@@ -117,12 +107,10 @@ size; use MAX_PATH if needed.</para>
 <title>cygwin_conv_to_win32_path</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" void
 <function>cygwin_conv_to_win32_path</function></funcdef>
 <paramdef>const char *<parameter>path</parameter></paramdef>
 <paramdef>char *<parameter>win32_path</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>Converts a POSIX path to a Win32 path.  If
@@ -137,12 +125,10 @@ size; use MAX_PATH if needed.</para>
 <title>cygwin_conv_to_full_posix_path</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" void
 <function>cygwin_conv_to_full_posix_path</function></funcdef>
 <paramdef>const char *<parameter>path</parameter></paramdef>
 <paramdef>char *<parameter>posix_path</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>Converts a Win32 path to a POSIX path.  If
@@ -158,12 +144,10 @@ buffer of sufficient size; use MAX_PATH if needed.</para>
 <title>cygwin_conv_to_full_win32_path</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" void
 <function>cygwin_conv_to_full_win32_path</function></funcdef>
 <paramdef>const char *<parameter>path</parameter></paramdef>
 <paramdef>char *<parameter>win32_path</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>Converts a POSIX path to a Win32 path.  If
@@ -179,11 +163,9 @@ buffer of sufficient size; use MAX_PATH if needed.</para>
 <title>cygwin_posix_path_list_p</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" int
 <function>posix_path_list_p</function></funcdef>
 <paramdef>const char *<parameter>path</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>This function tells you if the supplied
@@ -200,14 +182,12 @@ parameter.</para>
 <title>cygwin_split_path</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" void
 <function>cygwin_split_path</function>
 </funcdef>
 <paramdef>const char * <parameter>path</parameter></paramdef>
 <paramdef>char * <parameter>dir</parameter></paramdef>
 <paramdef>char * <parameter>file</parameter></paramdef>
-</funcprototype>
 </funcsynopsis>
 
 <para>Split a path into the directory and the file portions.  Both
index 2eca86a..834fa85 100644 (file)
@@ -610,12 +610,10 @@ pinfo::release ()
   <title>cygwin_winpid_to_pid</title>
 
   <funcsynopsis>
-    <funcprototype>
     <funcdef>extern "C" pid_t
       <function>cygwin_winpid_to_pid</function>
       </funcdef>
       <paramdef>int <parameter>winpid</parameter></paramdef>
-    </funcprototype>
   </funcsynopsis>
 
   <para>Given a windows pid, converts to the corresponding Cygwin
index 30b5996..d38e19c 100644 (file)
@@ -1,6 +1,6 @@
 /* select.h
 
-   Copyright 1998, 1999, 2000, 2001 Red Hat, Inc.
+   Copyright 1998, 1999, 2000, 2001, 2004 Red Hat, Inc.
 
 This file is part of Cygwin.
 
@@ -52,5 +52,4 @@ extern "C" int PASCAL win32_select(int, fd_set*, fd_set*, fd_set*, const struct
  * type coercion need to appease confused prototypes
  */
 #define WINSOCK_SELECT(nfd, rd, wr, ex, timeo) \
-    win32_select (nfd, (fd_set *)rd, (fd_set *)wr, (fd_set *)ex, timeo)
-
+  win32_select (nfd, (fd_set *) rd, (fd_set *) wr, (fd_set *) ex, timeo)
index f06f065..f43d654 100644 (file)
@@ -3,11 +3,9 @@
 <title>cygwin_getshared</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>shared_info *
 <function>cygwin_getshared</function></funcdef>
 <void>
-</funcprototype>
 </funcsynopsis>
 
 <para>Returns a pointer to an internal Cygwin memory structure
index 25bce84..e143a82 100644 (file)
@@ -1,6 +1,6 @@
 /* sigproc.cc: inter/intra signal and sub process handler
 
-   Copyright 1997, 1998, 1999, 2000, 2001, 2002, 2003 Red Hat, Inc.
+   Copyright 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004 Red Hat, Inc.
 
    Written by Christopher Faylor
 
@@ -32,6 +32,7 @@ details. */
 #include "cygtls.h"
 #include "sigproc.h"
 #include "perthread.h"
+#include "exceptions.h"
 
 /*
  * Convenience defines
@@ -1105,12 +1106,17 @@ wait_sig (VOID *self)
   SetEvent (wait_sig_inited);
   sigtid = GetCurrentThreadId ();
 
+  exception_list el;
+  _my_tls.init_threadlist_exceptions (&el);
+
   for (;;)
     {
       DWORD nb;
       sigpacket pack;
       if (!ReadFile (readsig, &pack, sizeof (pack), &nb, NULL))
        break;
+      if (myself->sendsig == INVALID_HANDLE_VALUE)
+       break;
 
       if (nb != sizeof (pack))
        {
index 5c20954..bff76bf 100644 (file)
@@ -2,11 +2,9 @@
 <title>cygwin_stackdump</title>
 
 <funcsynopsis>
-<funcprototype>
 <funcdef>extern "C" void
 <function>cygwin_stackdump</function></funcdef>
 <void>
-</funcprototype>
 </funcsynopsis>
 
 <para> Outputs a stackdump to stderr from the called location.
index b6dec83..dbc2630 100644 (file)
@@ -23,10 +23,10 @@ details. */
 #include "sync.h"
 #include "security.h"
 
-muto NO_COPY muto_start;
-
 #undef WaitForSingleObject
 
+DWORD NO_COPY muto::exiting_thread;
+
 /* Constructor */
 muto *
 muto::init (const char *s)
@@ -40,8 +40,6 @@ muto::init (const char *s)
       return NULL;
     }
   name = s;
-  next = muto_start.next;
-  muto_start.next = this;
   return this;
 }
 
@@ -71,6 +69,8 @@ int
 muto::acquire (DWORD ms)
 {
   DWORD this_tid = GetCurrentThreadId ();
+  if (exiting_thread)
+    return this_tid == exiting_thread;
 
   if (tid != this_tid)
     {
@@ -113,6 +113,8 @@ int
 muto::release ()
 {
   DWORD this_tid = GetCurrentThreadId ();
+  if (exiting_thread)
+    return this_tid == exiting_thread;
 
   if (tid != this_tid || !visits)
     {
@@ -135,6 +137,12 @@ muto::release ()
   return 1;    /* success. */
 }
 
+bool
+muto::acquired ()
+{
+  return tid == GetCurrentThreadId ();
+}
+
 /* Call only when we're exiting.  This is not thread safe. */
 void
 muto::reset ()
index 9cd50c3..3ae0937 100644 (file)
@@ -10,17 +10,20 @@ This software is a copyrighted work licensed under the terms of the
 Cygwin license.  Please consult the file "CYGWIN_LICENSE" for
 details. */
 
+#ifndef _SYNC_H
+#define _SYNC_H
 /* FIXME: Note that currently this class cannot be allocated via `new' since
    there are issues with malloc and fork. */
 class muto
 {
+  static DWORD exiting_thread;
   LONG sync;   /* Used to serialize access to this class. */
   LONG visits; /* Count of number of times a thread has called acquire. */
   LONG waiters;        /* Number of threads waiting for lock. */
   HANDLE bruteforce; /* event handle used to control waiting for lock. */
   DWORD tid;   /* Thread Id of lock owner. */
 public:
-  class muto *next;
+  // class muto *next;
   const char *name;
 
   /* The real constructor. */
@@ -37,6 +40,8 @@ public:
   DWORD owner () {return tid;}
   int unstable () {return !tid && (sync || waiters >= 0);}
   void reset () __attribute__ ((regparm (1)));
+  bool acquired ();
+  static void set_exiting_thread () {exiting_thread = GetCurrentThreadId ();}
 };
 
 extern muto muto_start;
@@ -44,6 +49,14 @@ extern muto muto_start;
 /* Use a statically allocated buffer as the storage for a muto */
 #define new_muto(__name) \
 ({ \
-  static muto __name##_storage __attribute__((nocommon)) __attribute__((section(".data_cygwin_nocopy"))); \
+  static muto __name##_storage __attribute__((nocommon)) __attribute__((section(".data_cygwin_nocopy1"))); \
   __name = __name##_storage.init (#__name); \
 })
+
+/* Use a statically allocated buffer as the storage for a muto */
+#define new_muto1(__name, __storage) \
+({ \
+  static muto __storage __attribute__((nocommon)) __attribute__((section(".data_cygwin_nocopy1"))); \
+  __name = __storage.init (#__name); \
+})
+#endif /*_SYNC_H*/
index 47d6b10..5abe0ca 100644 (file)
@@ -87,7 +87,7 @@ static int __stdcall stat_worker (const char *name, struct __stat64 *buf,
 void __stdcall
 close_all_files (void)
 {
-  SetResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "close_all_files");
+  cygheap->fdtab.lock ();
 
   fhandler_base *fh;
   for (int i = 0; i < (int) cygheap->fdtab.size; i++)
@@ -101,13 +101,9 @@ close_all_files (void)
       }
 
   if (cygheap->ctty)
-    {
-      debug_printf ("closing ctty");
-      cygheap->ctty->close ();
-      cygheap->ctty = NULL;
-    }
+    cygheap->close_ctty ();
 
-  ReleaseResourceLock (LOCK_FD_LIST, WRITE_LOCK | READ_LOCK, "close_all_files");
+  cygheap->fdtab.unlock ();
   user_shared->delqueue.process_queue ();
 }
 
@@ -332,10 +328,7 @@ setsid (void)
       syscall_printf ("sid %d, pgid %d, ctty %d, open_fhs %d", myself->sid,
                      myself->pgid, myself->ctty, cygheap->open_fhs);
       if (cygheap->ctty)
-       {
-         cygheap->ctty->close ();
-         cygheap->ctty = NULL;
-       }
+       cygheap->close_ctty ();
       return myself->sid;
     }
 
index fe460a1..ae03dc6 100644 (file)
@@ -297,7 +297,7 @@ pthread::exit (void *value_ptr)
     ::exit (0);
   else
     {
-      _my_tls.remove ();
+      _my_tls.remove (INFINITE);
       ExitThread (0);
     }
 }
@@ -1783,9 +1783,6 @@ pthread::thread_init_wrapper (void *arg)
   pthread *thread = (pthread *) arg;
   _my_tls.tid = thread;
 
-  exception_list cygwin_except_entry;
-  init_exceptions (&cygwin_except_entry); /* Initialize SIGSEGV handling, etc. */
-
   thread->mutex.lock ();
 
   // if thread is detached force cleanup on exit
index ed79b8d..0e9779a 100644 (file)
@@ -14,10 +14,7 @@ details. */
 #ifndef _CYGNUS_THREADS_
 #define _CYGNUS_THREADS_
 
-#define LOCK_FD_LIST     1
-#define LOCK_MEMORY_LIST 2
-#define LOCK_MMAP_LIST   3
-#define LOCK_DLL_LIST    4
+#define LOCK_MMAP_LIST   1
 
 #define WRITE_LOCK 1
 #define READ_LOCK  2
index 191fe37..6aeea68 100644 (file)
@@ -1,44 +1,46 @@
 //;# autogenerated:  Do not edit.
 
-//; $tls::func = -7148;
-//; $tls::saved_errno = -7144;
-//; $tls::sa_flags = -7140;
-//; $tls::oldmask = -7136;
-//; $tls::newmask = -7132;
-//; $tls::event = -7128;
-//; $tls::errno_addr = -7124;
-//; $tls::initialized = -7120;
-//; $tls::sigmask = -7116;
-//; $tls::sigwait_mask = -7112;
-//; $tls::sigwait_info = -7108;
-//; $tls::infodata = -7104;
-//; $tls::tid = -6580;
-//; $tls::local_clib = -6576;
-//; $tls::locals = -5648;
-//; $tls::prev = -4112;
-//; $tls::next = -4108;
-//; $tls::stackptr = -4104;
-//; $tls::sig = -4100;
-//; $tls::stack = -4096;
+//; $tls::func = -4076;
+//; $tls::saved_errno = -4072;
+//; $tls::sa_flags = -4068;
+//; $tls::oldmask = -4064;
+//; $tls::newmask = -4060;
+//; $tls::event = -4056;
+//; $tls::errno_addr = -4052;
+//; $tls::initialized = -4048;
+//; $tls::sigmask = -4044;
+//; $tls::sigwait_mask = -4040;
+//; $tls::sigwait_info = -4036;
+//; $tls::infodata = -4032;
+//; $tls::tid = -3508;
+//; $tls::local_clib = -3504;
+//; $tls::locals = -2576;
+//; $tls::prev = -1040;
+//; $tls::next = -1036;
+//; $tls::stackptr = -1032;
+//; $tls::sig = -1028;
+//; $tls::stack = -1024;
+//; $tls::padding = 0;
 //; __DATA__
 
-#define tls_func (-7148)
-#define tls_saved_errno (-7144)
-#define tls_sa_flags (-7140)
-#define tls_oldmask (-7136)
-#define tls_newmask (-7132)
-#define tls_event (-7128)
-#define tls_errno_addr (-7124)
-#define tls_initialized (-7120)
-#define tls_sigmask (-7116)
-#define tls_sigwait_mask (-7112)
-#define tls_sigwait_info (-7108)
-#define tls_infodata (-7104)
-#define tls_tid (-6580)
-#define tls_local_clib (-6576)
-#define tls_locals (-5648)
-#define tls_prev (-4112)
-#define tls_next (-4108)
-#define tls_stackptr (-4104)
-#define tls_sig (-4100)
-#define tls_stack (-4096)
+#define tls_func (-4076)
+#define tls_saved_errno (-4072)
+#define tls_sa_flags (-4068)
+#define tls_oldmask (-4064)
+#define tls_newmask (-4060)
+#define tls_event (-4056)
+#define tls_errno_addr (-4052)
+#define tls_initialized (-4048)
+#define tls_sigmask (-4044)
+#define tls_sigwait_mask (-4040)
+#define tls_sigwait_info (-4036)
+#define tls_infodata (-4032)
+#define tls_tid (-3508)
+#define tls_local_clib (-3504)
+#define tls_locals (-2576)
+#define tls_prev (-1040)
+#define tls_next (-1036)
+#define tls_stackptr (-1032)
+#define tls_sig (-1028)
+#define tls_stack (-1024)
+#define tls_padding (0)
index 2d60fcd..6c2e58f 100644 (file)
@@ -8,6 +8,12 @@ This software is a copyrighted work licensed under the terms of the
 Cygwin license.  Please consult the file "CYGWIN_LICENSE" for
 details. */
 
+#ifdef DEBUGIT
+#define spf(a, b, c) small_printf (a, b, c)
+#else
+#define spf(a, b, c) do {} while (0)
+#endif
+
 #ifdef HAVE_CONFIG_H
 # include "config.h"
 #endif
@@ -150,11 +156,11 @@ extern HANDLE title_mutex;
     })
 
 /* Convert a signal to a signal mask */
-#define SIGTOMASK(sig) (1<<((sig) - signal_shift_subtract))
+#define SIGTOMASK(sig) (1 << ((sig) - signal_shift_subtract))
 extern unsigned int signal_shift_subtract;
 
 #ifdef NEW_MACRO_VARARGS
-# define api_fatal(...) __api_fatal ("%P: *** " __VA_ARGS__)
+# define api_fatal(...) __api_fatal (__VA_ARGS__)
 #else
 # define api_fatal(fmt, args...) __api_fatal ("%P: *** " fmt,## args)
 #endif