Index: trunk/kernel/kern/thread.c
===================================================================
--- trunk/kernel/kern/thread.c	(revision 581)
+++ trunk/kernel/kern/thread.c	(revision 583)
@@ -224,5 +224,5 @@
 
 	// update DQDT 
-    dqdt_update_threads( 1 );
+    dqdt_increment_threads();
 
 #if DEBUG_THREAD_INIT
@@ -768,4 +768,6 @@
     hal_cpu_context_init( thread );
 
+    // set THREAD_BLOCKED_IDLE for DEV threads
+    if( type == THREAD_DEV ) thread->blocked |= THREAD_BLOCKED_IDLE;
 
 #if DEBUG_THREAD_KERNEL_CREATE
@@ -815,10 +817,9 @@
 ///////////////////////////////////////////////////////////////////////////////////////
 // TODO: check that all memory dynamically allocated during thread execution
-// has been released, using a cache of mmap requests. [AG]
+// has been released => check vmm destroy for MMAP vsegs  [AG]
 ///////////////////////////////////////////////////////////////////////////////////////
-bool_t thread_destroy( thread_t * thread )
+void thread_destroy( thread_t * thread )
 {
     reg_t        save_sr;
-    bool_t       last_thread;
 
     process_t  * process    = thread->process;
@@ -826,13 +827,13 @@
 
 #if DEBUG_THREAD_DESTROY
-uint32_t cycle = (uint32_t)hal_get_cycles();
+uint32_t   cycle = (uint32_t)hal_get_cycles();
+thread_t * this  = CURRENT_THREAD;
 if( DEBUG_THREAD_DESTROY < cycle )
-printk("\n[DBG] %s : thread %x enter to destroy thread %x in process %x / cycle %d\n",
-__FUNCTION__, CURRENT_THREAD, thread->trdid, process->pid, cycle );
-#endif
-
-// check busylocks counter
-assert( (thread->busylocks == 0) ,
-"busylock not released for thread %x in process %x", thread->trdid, process->pid );
+printk("\n[DBG] %s : thread[%x,%x] enter to destroy thread[%x,%x] / cycle %d\n",
+__FUNCTION__, this->process->pid, this->trdid, process->pid, thread->trdid, cycle );
+#endif
+
+    // check busylocks counter
+    thread_assert_can_yield( thread , __FUNCTION__ );
 
     // update intrumentation values
@@ -852,10 +853,4 @@
 	hal_restore_irq( save_sr );
 
-    // remove thread from process th_tbl[]
-    last_thread = process_remove_thread( thread );
-	
-    // update DQDT
-    dqdt_update_threads( -1 );
-
     // invalidate thread descriptor
 	thread->signature = 0;
@@ -867,9 +862,7 @@
 cycle = (uint32_t)hal_get_cycles();
 if( DEBUG_THREAD_DESTROY < cycle )
-printk("\n[DBG] %s : thread %x exit / destroyed thread %x in process %x / last %d / cycle %d\n",
-__FUNCTION__, CURRENT_THREAD, thread->trdid, process->pid, last_thread / cycle );
-#endif
-
-    return last_thread;
+printk("\n[DBG] %s : thread[%x,%x] exit / destroyed thread[%x,%x] / cycle %d\n",
+__FUNCTION__, this->process->pid, this->trdid, process->pid, thread->trdid, cycle );
+#endif
 
 }   // end thread_destroy()
@@ -1023,11 +1016,8 @@
 uint32_t cycle  = (uint32_t)hal_get_cycles();
 if( DEBUG_THREAD_DELETE < cycle )
-printk("\n[DBG] %s : thread %x in process %x enters / target thread %x / cycle %d\n",
-__FUNCTION__, killer_ptr->trdid, killer_ptr->process->pid, target_ptr->trdid, cycle );
-#endif
-
-// check killer thread can yield 
-assert( (killer_ptr->busylocks == 0), 
-"cannot yield : busylocks = %d\n", killer_ptr->busylocks );
+printk("\n[DBG] %s : killer[%x,%x] enters / target[%x,%x] / cycle %d\n",
+__FUNCTION__, killer_ptr->process->pid, killer_ptr->trdid,  
+target_ptr->process->pid, target_ptr->trdid, cycle );
+#endif
 
 // check target thread is not the main thread, because the main thread
@@ -1036,16 +1026,12 @@
 "tharget thread cannot be the main thread\n" );
 
-    // block the target thread 
-    thread_block( target_xp , THREAD_BLOCKED_GLOBAL );
-
-    // synchronize with the joining thread if attached
-    if( target_attached && (is_forced == false) ) 
-    {
-
-#if (DEBUG_THREAD_DELETE & 1)
-if( DEBUG_THREAD_DELETE < cycle )
-printk("\n[DBG] %s : thread %x in process %x / target thread is attached\n",
-__FUNCTION__, killer_ptr->trdid, killer_ptr->process->pid );
-#endif
+    // check killer thread can yield 
+    thread_assert_can_yield( killer_ptr , __FUNCTION__ ); 
+
+    // if the target thread is attached, we must synchonize with the joining thread
+    // before blocking and marking the target thead for delete.
+
+    if( target_attached && (is_forced == false) ) // synchronize with joining thread 
+    {
         // build extended pointers on target thread join fields
         target_join_lock_xp  = XPTR( target_cxy , &target_ptr->join_lock );
@@ -1061,12 +1047,6 @@
         target_join_done = ((hal_remote_l32( target_flags_xp ) & THREAD_FLAG_JOIN_DONE) != 0);
     
-        if( target_join_done )  // joining thread arrived first => unblock the joining thread
+        if( target_join_done )                     // joining thread arrived first
         {
-
-#if (DEBUG_THREAD_DELETE & 1)
-if( DEBUG_THREAD_DELETE < cycle )
-printk("\n[DBG] %s : thread %x in process %x / joining thread arrived first\n",
-__FUNCTION__, killer_ptr->trdid, killer_ptr->process->pid );
-#endif
             // get extended pointer on joining thread
             joining_xp  = (xptr_t)hal_remote_l64( target_join_xp_xp );
@@ -1083,62 +1063,82 @@
             remote_busylock_release( target_join_lock_xp );
 
+            // block the target thread 
+            thread_block( target_xp , THREAD_BLOCKED_GLOBAL );
+
             // set the REQ_DELETE flag in target thread descriptor
             hal_remote_atomic_or( target_flags_xp , THREAD_FLAG_REQ_DELETE );
 
-            // restore IRQs
+            // exit critical section
             hal_restore_irq( save_sr );
-        }
-        else                // killer thread arrived first => register flags and deschedule
-        {
-
-#if (DEBUG_THREAD_DELETE & 1)
-if( DEBUG_THREAD_DELETE < cycle )
-printk("\n[DBG] %s : thread %x in process %x / killer thread arrived first\n",
-__FUNCTION__, killer_ptr->trdid, killer_ptr->process->pid );
-#endif
-            // set the kill_done flag in target thread
-            hal_remote_atomic_or( target_flags_xp , THREAD_FLAG_KILL_DONE );
-
-            // block this thread on BLOCKED_JOIN
-            thread_block( killer_xp , THREAD_BLOCKED_JOIN );
-
-            // set extended pointer on killer thread in target thread
-            hal_remote_s64( target_join_xp_xp , killer_xp );
-
-            // release the join_lock in target thread descriptor
-            remote_busylock_release( target_join_lock_xp );
-
-#if (DEBUG_THREAD_DELETE & 1)
-if( DEBUG_THREAD_DELETE < cycle )
-printk("\n[DBG] %s : thread %x in process %x / killer thread deschedule\n",
-__FUNCTION__, killer_ptr->trdid, killer_ptr->process->pid );
-#endif
-            // deschedule
-            sched_yield( "killer thread wait joining thread" );
-
-#if (DEBUG_THREAD_DELETE & 1)
-if( DEBUG_THREAD_DELETE < cycle )
-printk("\n[DBG] %s : thread %x in process %x / killer thread resume\n",
-__FUNCTION__, killer_ptr->trdid, killer_ptr->process->pid );
-#endif
-            // set the REQ_DELETE flag in target thread descriptor
-            hal_remote_atomic_or( target_flags_xp , THREAD_FLAG_REQ_DELETE );
-
-            // restore IRQs
-            hal_restore_irq( save_sr );
-        }
-    }
-    else                                                   // target thread not attached
-    {
-        // set the REQ_DELETE flag in target thread descriptor
-        hal_remote_atomic_or( target_flags_xp , THREAD_FLAG_REQ_DELETE );
-    }
 
 #if DEBUG_THREAD_DELETE
 cycle  = (uint32_t)hal_get_cycles;
 if( DEBUG_THREAD_DELETE < cycle )
-printk("\n[DBG] %s : thread %x in process %x exit / target thread %x / cycle %d\n",
-__FUNCTION__, killer_ptr->trdid, killer_ptr->process->pid, target_ptr->trdid, cycle );
-#endif
+printk("\n[DBG] %s : killer[%x,%x] exit / target[%x,%x] marked after join / cycle %d\n",
+__FUNCTION__, killer_ptr->process->pid, killer_ptr->trdid,
+target_ptr->process->pid, target_ptr->trdid, cycle );
+#endif
+
+        }
+        else                                      // killer thread arrived first
+        {
+            // set the kill_done flag in target thread
+            hal_remote_atomic_or( target_flags_xp , THREAD_FLAG_KILL_DONE );
+
+            // block this thread on BLOCKED_JOIN
+            thread_block( killer_xp , THREAD_BLOCKED_JOIN );
+
+            // set extended pointer on killer thread in target thread
+            hal_remote_s64( target_join_xp_xp , killer_xp );
+
+            // release the join_lock in target thread descriptor
+            remote_busylock_release( target_join_lock_xp );
+
+#if DEBUG_THREAD_DELETE
+cycle  = (uint32_t)hal_get_cycles;
+if( DEBUG_THREAD_DELETE < cycle )
+printk("\n[DBG] %s : killer[%x,%x] deschedules / target[%x,%x] not completed / cycle %d\n",
+__FUNCTION__, killer_ptr->process->pid, killer_ptr->trdid,
+target_ptr->process->pid, target_ptr->trdid, cycle );
+#endif
+            // deschedule
+            sched_yield( "killer thread wait joining thread" );
+
+            // block the target thread 
+            thread_block( target_xp , THREAD_BLOCKED_GLOBAL );
+
+            // set the REQ_DELETE flag in target thread descriptor
+            hal_remote_atomic_or( target_flags_xp , THREAD_FLAG_REQ_DELETE );
+
+            // exit critical section
+            hal_restore_irq( save_sr );
+
+#if DEBUG_THREAD_DELETE
+cycle  = (uint32_t)hal_get_cycles;
+if( DEBUG_THREAD_DELETE < cycle )
+printk("\n[DBG] %s : killer[%x,%x] exit / target[%x,%x] marked after join / cycle %d\n",
+__FUNCTION__, killer_ptr->process->pid, killer_ptr->trdid,
+target_ptr->process->pid, target_ptr->trdid, cycle );
+#endif
+
+        }
+    }
+    else                     // no synchronization with joining thread required
+    {
+        // block the target thread 
+        thread_block( target_xp , THREAD_BLOCKED_GLOBAL );
+
+        // set the REQ_DELETE flag in target thread descriptor
+        hal_remote_atomic_or( target_flags_xp , THREAD_FLAG_REQ_DELETE );
+
+#if DEBUG_THREAD_DELETE
+cycle  = (uint32_t)hal_get_cycles;
+if( DEBUG_THREAD_DELETE < cycle )
+printk("\n[DBG] %s : killer[%x,%x] exit / target [%x,%x] marked / no join / cycle %d\n",
+__FUNCTION__, killer_ptr->process->pid, killer_ptr->trdid,
+target_ptr->process->pid, target_ptr->trdid, cycle );
+#endif
+
+    }
 
 }  // end thread_delete()
@@ -1155,5 +1155,5 @@
 
         // force core to low-power mode (optional)
-        if( CONFIG_THREAD_IDLE_MODE_SLEEP ) 
+        if( CONFIG_SCHED_IDLE_MODE_SLEEP ) 
         {
 
@@ -1354,9 +1354,7 @@
 #if DEBUG_BUSYLOCK
 
-// get root of list of taken busylocks
+// scan list of busylocks
+xptr_t    iter_xp;
 xptr_t    root_xp  = XPTR( local_cxy , &thread->busylocks_root );
-xptr_t    iter_xp;
-
-// scan list of busylocks
 XLIST_FOREACH( root_xp , iter_xp )
 {
