Fix failure handling for thread creation
authorDavid Bartley <dtbartle@maltodextrin.csclub.uwaterloo.ca>
Wed, 21 Jan 2009 08:54:14 +0000 (08:54 +0000)
committerDavid Bartley <dtbartle@maltodextrin.csclub.uwaterloo.ca>
Wed, 21 Jan 2009 08:54:14 +0000 (08:54 +0000)
nptl/pthread_create.c
nptl/sysdeps/unix/sysv/solaris2/kopensolaris-gnu/createthread.c
nptl/sysdeps/unix/sysv/solaris2/kopensolaris-gnu/internaltypes.h

index 7368df8..9844624 100644 (file)
@@ -245,6 +245,14 @@ start_thread (void *arg)
 {
   struct pthread *pd = (struct pthread *) arg;
 
+#ifdef ATTR_FLAG_CREATE_FAILED
+  if ((pd->flags & ATTR_FLAG_CREATE_FAILED) && IS_DETACHED (pd))
+    {
+      __free_tcb (pd);
+      __exit_thread_inline (0);
+    }
+#endif
+
 #if HP_TIMING_AVAIL
   /* Remember the time when the thread was started.  */
   hp_timing_t now;
index 1f28c6e..1917152 100644 (file)
@@ -98,16 +98,24 @@ create_thread (struct pthread *pd, const struct pthread_attr *attr,
             errval = EPERM;
         }
 
-      /* Resume thread if requested.  */
-      if (errval == 0)
+      if (errval == 0 && !(attr->flags & ATTR_FLAG_SUSPENDED))
         {
-          if (!(attr->flags & ATTR_FLAG_SUSPENDED))
-            errval = INLINE_SYSCALL (lwp_continue, 1, pd->tid);
+          errval = INLINE_SYSCALL (lwp_continue, 1, pd->tid);
         }
+      else if (errval != 0)
+        {
+          pd->flags |= ATTR_FLAG_CREATE_FAILED;
+          INLINE_SYSCALL (lwp_continue, 1, pd->tid);
+
+          if (!IS_DETACHED (pd))
+            {
+              int result;
+              lll_wait_tid (pd->tid);
+            }
 
-      /* Kill the thread if we didn't succeed above.  */
-      if (errval != 0)
-        INLINE_SYSCALL (lwp_kill, 2, pd->tid, SIGKILL);
+          /* Note: if the thread is detached, start_thread will free pd;
+             otherwise the caller of create_thread will free pd.  */
+        }
     }
 
   if (errval == 0)
@@ -120,13 +128,6 @@ create_thread (struct pthread *pd, const struct pthread_attr *attr,
   else
     {
       atomic_decrement (&__nptl_nthreads); /* Oops, we lied for a second.  */
-
-      /* Failed.  If the thread is detached, remove the TCB here since
-         the caller cannot do this.  The caller remembered the thread
-         as detached and cannot reverify that it is not since it must
-         not access the thread descriptor again.  */
-      if (IS_DETACHED (pd))
-        __deallocate_stack (pd);
     }
 
   return errval;
index 8c291d9..c6ab6ec 100644 (file)
@@ -54,6 +54,7 @@ struct pthread_attr
 #define ATTR_FLAG_DAEMON               0x0080
 #define ATTR_FLAG_SUSPENDED            0x0100
 #define ATTR_FLAG_THR_CREATE   0x0200
+#define ATTR_FLAG_CREATE_FAILED                0x0400
 
 
 /* Mutex attribute data structure.  */