diff --git a/winsup/cygwin/ChangeLog b/winsup/cygwin/ChangeLog
index d695f4b7b..66f84a415 100644
--- a/winsup/cygwin/ChangeLog
+++ b/winsup/cygwin/ChangeLog
@@ -1,3 +1,11 @@
+2010-03-28  Christopher Faylor  <me+cygwin@cgf.cx>
+
+	* globals.cc (exit_status): Add new ES_EXIT_STARTING enum.
+	* dcrt0.cc (cygwin_exit): Set exit_state to ES_EXIT_STARTING prior to
+	calling real exit.
+	* dll_init.cc (dll_list::detach): Remove dll from linked list and call
+	destructors even if exiting.  Don't call __cxa_finalize in exiting case.
+
 2010-03-27  Corinna Vinschen  <corinna@vinschen.de>
 
 	* nlsfuncs.cc (__set_charset_from_locale):  Set default charset for
diff --git a/winsup/cygwin/dcrt0.cc b/winsup/cygwin/dcrt0.cc
index 6a1a341aa..76b89517b 100644
--- a/winsup/cygwin/dcrt0.cc
+++ b/winsup/cygwin/dcrt0.cc
@@ -1127,6 +1127,7 @@ cygwin_atexit (void (*fn) (void))
 extern "C" void
 cygwin_exit (int n)
 {
+  exit_state = ES_EXIT_STARTING;
   exit (n);
 }
 
diff --git a/winsup/cygwin/dll_init.cc b/winsup/cygwin/dll_init.cc
index bd3d7d996..24d6d5c5f 100644
--- a/winsup/cygwin/dll_init.cc
+++ b/winsup/cygwin/dll_init.cc
@@ -164,7 +164,7 @@ void
 dll_list::detach (void *retaddr)
 {
   dll *d;
-  if (!myself || exit_state || !(d = find (retaddr)))
+  if (!myself || !(d = find (retaddr)))
     return;
   if (d->count <= 0)
     system_printf ("WARNING: trying to detach an already detached dll ...");
@@ -172,7 +172,9 @@ dll_list::detach (void *retaddr)
     {
       /* Ensure our exception handler is enabled for destructors */
       exception protect;
-      __cxa_finalize (d);
+      /* Call finalize function if we are not already exiting */
+      if (!exit_state)
+	__cxa_finalize (d);
       d->run_dtors ();
       d->prev->next = d->next;
       if (d->next)
diff --git a/winsup/cygwin/globals.cc b/winsup/cygwin/globals.cc
index 5934a72b7..0baa96e3a 100644
--- a/winsup/cygwin/globals.cc
+++ b/winsup/cygwin/globals.cc
@@ -30,6 +30,7 @@ int NO_COPY sigExeced;
 enum exit_states
   {
     ES_NOT_EXITING = 0,
+    ES_EXIT_STARTING,
     ES_PROCESS_LOCKED,
     ES_EVENTS_TERMINATE,
     ES_THREADTERM,