Index: src/libcfa/concurrency/coroutine.c
===================================================================
--- src/libcfa/concurrency/coroutine.c	(revision b10affdcb702e2f50d20fa65715ce6473d2bebb4)
+++ src/libcfa/concurrency/coroutine.c	(revision 534d84ecf33237664da77b0cdc43872095a15533)
@@ -39,47 +39,32 @@
 //-----------------------------------------------------------------------------
 // Coroutine ctors and dtors
-void ?{}(coStack_t& this) with( this ) {
-	size		= 65000;	// size of stack
-	storage	= NULL;	// pointer to stack
-	limit		= NULL;	// stack grows towards stack limit
-	base		= NULL;	// base of stack
-	context	= NULL;	// address of cfa_context_t
-	top		= NULL;	// address of top of storage
-	userStack	= false;
-}
-
-void ?{}(coStack_t& this, size_t size) {
-	this{};
-	this.size = size;
-
-	create_stack(&this, this.size);
-}
-
-void ?{}(coroutine_desc& this) {
-	this{ "Anonymous Coroutine" };
-}
-
-void ?{}(coroutine_desc& this, const char * name) with( this ) {
-	this.name = name;
-	errno_ = 0;
-	state = Start;
-	starter = NULL;
-	last = NULL;
-}
-
-void ?{}(coroutine_desc& this, size_t size) {
-	this{};
-	(this.stack){size};
+void ?{}( coStack_t & this, void * storage, size_t storageSize ) with( this ) {
+      size		 = storageSize == 0 ? 65000 : storageSize; // size of stack
+      this.storage = storage;                                // pointer to stack
+      limit		 = NULL;                                   // stack grows towards stack limit
+      base		 = NULL;                                   // base of stack
+      context	 = NULL;                                   // address of cfa_context_t
+      top		 = NULL;                                   // address of top of storage
+      userStack	 = storage != NULL;
 }
 
 void ^?{}(coStack_t & this) {
-	if ( ! this.userStack && this.storage ) {
-		__cfaabi_dbg_debug_do(
-			if ( mprotect( this.storage, pageSize, PROT_READ | PROT_WRITE ) == -1 ) {
-				abort( "(coStack_t *)%p.^?{}() : internal error, mprotect failure, error(%d) %s.", &this, errno, strerror( errno ) );
-			}
-		);
-		free( this.storage );
-	}
+      if ( ! this.userStack && this.storage ) {
+            __cfaabi_dbg_debug_do(
+                  if ( mprotect( this.storage, pageSize, PROT_READ | PROT_WRITE ) == -1 ) {
+                        abort( "(coStack_t *)%p.^?{}() : internal error, mprotect failure, error(%d) %s.", &this, errno, strerror( errno ) );
+                  }
+            );
+            free( this.storage );
+      }
+}
+
+void ?{}( coroutine_desc & this, const char * name, void * storage, size_t storageSize ) with( this ) {
+      (this.stack){storage, storageSize};
+      this.name = name;
+      errno_ = 0;
+      state = Start;
+      starter = NULL;
+      last = NULL;
 }
 
@@ -90,76 +75,80 @@
 forall(dtype T | is_coroutine(T))
 void prime(T& cor) {
-	coroutine_desc* this = get_coroutine(cor);
-	assert(this->state == Start);
+      coroutine_desc* this = get_coroutine(cor);
+      assert(this->state == Start);
 
-	this->state = Primed;
-	resume(cor);
+      this->state = Primed;
+      resume(cor);
 }
 
 // Wrapper for co
 void CoroutineCtxSwitch(coroutine_desc* src, coroutine_desc* dst) {
-	verify( TL_GET( preemption_state ).enabled || TL_GET( this_processor )->do_terminate );
-	disable_interrupts();
+      verify( TL_GET( preemption_state ).enabled || TL_GET( this_processor )->do_terminate );
+      disable_interrupts();
 
-	// set state of current coroutine to inactive
-	src->state = src->state == Halted ? Halted : Inactive;
+      // set state of current coroutine to inactive
+      src->state = src->state == Halted ? Halted : Inactive;
 
-	// set new coroutine that task is executing
-	TL_SET( this_coroutine, dst );
+      // set new coroutine that task is executing
+      TL_SET( this_coroutine, dst );
 
-	// context switch to specified coroutine
-	assert( src->stack.context );
-	CtxSwitch( src->stack.context, dst->stack.context );
-	// when CtxSwitch returns we are back in the src coroutine
+      // context switch to specified coroutine
+      assert( src->stack.context );
+      CtxSwitch( src->stack.context, dst->stack.context );
+      // when CtxSwitch returns we are back in the src coroutine
 
-	// set state of new coroutine to active
-	src->state = Active;
+      // set state of new coroutine to active
+      src->state = Active;
 
-	enable_interrupts( __cfaabi_dbg_ctx );
-	verify( TL_GET( preemption_state ).enabled || TL_GET( this_processor )->do_terminate );
+      enable_interrupts( __cfaabi_dbg_ctx );
+      verify( TL_GET( preemption_state ).enabled || TL_GET( this_processor )->do_terminate );
 } //ctxSwitchDirect
 
 void create_stack( coStack_t* this, unsigned int storageSize ) with( *this ) {
-	//TEMP HACK do this on proper kernel startup
-	if(pageSize == 0ul) pageSize = sysconf( _SC_PAGESIZE );
+      //TEMP HACK do this on proper kernel startup
+      if(pageSize == 0ul) pageSize = sysconf( _SC_PAGESIZE );
 
-	size_t cxtSize = libCeiling( sizeof(machine_context_t), 8 ); // minimum alignment
+      size_t cxtSize = libCeiling( sizeof(machine_context_t), 8 ); // minimum alignment
 
-	if ( (intptr_t)storage == 0 ) {
-		userStack = false;
-		size = libCeiling( storageSize, 16 );
-		// use malloc/memalign because "new" raises an exception for out-of-memory
+      if ( !storage ) {
+            __cfaabi_dbg_print_safe("Kernel : Creating stack of size %zu for stack obj %p\n", cxtSize + size + 8, this);
 
-		// assume malloc has 8 byte alignment so add 8 to allow rounding up to 16 byte alignment
-		__cfaabi_dbg_debug_do( storage = memalign( pageSize, cxtSize + size + pageSize ) );
-		__cfaabi_dbg_no_debug_do( storage = malloc( cxtSize + size + 8 ) );
+            userStack = false;
+            size = libCeiling( storageSize, 16 );
+            // use malloc/memalign because "new" raises an exception for out-of-memory
 
-		__cfaabi_dbg_debug_do(
-			if ( mprotect( storage, pageSize, PROT_NONE ) == -1 ) {
-				abort( "(uMachContext &)%p.createContext() : internal error, mprotect failure, error(%d) %s.", this, (int)errno, strerror( (int)errno ) );
-			} // if
-		);
+            // assume malloc has 8 byte alignment so add 8 to allow rounding up to 16 byte alignment
+            __cfaabi_dbg_debug_do( storage = memalign( pageSize, cxtSize + size + pageSize ) );
+            __cfaabi_dbg_no_debug_do( storage = malloc( cxtSize + size + 8 ) );
 
-		if ( (intptr_t)storage == 0 ) {
-			abort( "Attempt to allocate %zd bytes of storage for coroutine or task execution-state but insufficient memory available.", size );
-		} // if
+            __cfaabi_dbg_debug_do(
+                  if ( mprotect( storage, pageSize, PROT_NONE ) == -1 ) {
+                        abort( "(uMachContext &)%p.createContext() : internal error, mprotect failure, error(%d) %s.", this, (int)errno, strerror( (int)errno ) );
+                  } // if
+            );
 
-		__cfaabi_dbg_debug_do( limit = (char *)storage + pageSize );
-		__cfaabi_dbg_no_debug_do( limit = (char *)libCeiling( (unsigned long)storage, 16 ) ); // minimum alignment
+            if ( (intptr_t)storage == 0 ) {
+                  abort( "Attempt to allocate %zd bytes of storage for coroutine or task execution-state but insufficient memory available.", size );
+            } // if
 
-	} else {
-		assertf( ((size_t)storage & (libAlign() - 1)) != 0ul, "Stack storage %p for task/coroutine must be aligned on %d byte boundary.", storage, (int)libAlign() );
-		userStack = true;
-		size = storageSize - cxtSize;
+            __cfaabi_dbg_debug_do( limit = (char *)storage + pageSize );
+            __cfaabi_dbg_no_debug_do( limit = (char *)libCeiling( (unsigned long)storage, 16 ) ); // minimum alignment
 
-		if ( size % 16 != 0u ) size -= 8;
+      } else {
+            __cfaabi_dbg_print_safe("Kernel : stack obj %p using user stack %p(%u bytes)\n", this, storage, storageSize);
 
-		limit = (char *)libCeiling( (unsigned long)storage, 16 ); // minimum alignment
-	} // if
-	assertf( size >= MinStackSize, "Stack size %zd provides less than minimum of %d bytes for a stack.", size, MinStackSize );
+            assertf( ((size_t)storage & (libAlign() - 1)) == 0ul, "Stack storage %p for task/coroutine must be aligned on %d byte boundary.", storage, (int)libAlign() );
+            userStack = true;
+            size = storageSize - cxtSize;
 
-	base = (char *)limit + size;
-	context = base;
-	top = (char *)context + cxtSize;
+            if ( size % 16 != 0u ) size -= 8;
+
+            limit = (char *)libCeiling( (unsigned long)storage, 16 ); // minimum alignment
+      } // if
+      assertf( size >= MinStackSize, "Stack size %zd provides less than minimum of %d bytes for a stack.", size, MinStackSize );
+
+      base = (char *)limit + size;
+      context = base;
+      top = (char *)context + cxtSize;
 }
 
@@ -167,22 +156,22 @@
 // is not inline (We can't inline Cforall in C)
 extern "C" {
-	void __suspend_internal(void) {
-		suspend();
-	}
+      void __suspend_internal(void) {
+            suspend();
+      }
 
-	void __leave_coroutine(void) {
-		coroutine_desc * src = TL_GET( this_coroutine ); // optimization
+      void __leave_coroutine(void) {
+            coroutine_desc * src = TL_GET( this_coroutine ); // optimization
 
-		assertf( src->starter != 0,
-			"Attempt to suspend/leave coroutine \"%.256s\" (%p) that has never been resumed.\n"
-			"Possible cause is a suspend executed in a member called by a coroutine user rather than by the coroutine main.",
-			src->name, src );
-		assertf( src->starter->state != Halted,
-			"Attempt by coroutine \"%.256s\" (%p) to suspend/leave back to terminated coroutine \"%.256s\" (%p).\n"
-			"Possible cause is terminated coroutine's main routine has already returned.",
-			src->name, src, src->starter->name, src->starter );
+            assertf( src->starter != 0,
+                  "Attempt to suspend/leave coroutine \"%.256s\" (%p) that has never been resumed.\n"
+                  "Possible cause is a suspend executed in a member called by a coroutine user rather than by the coroutine main.",
+                  src->name, src );
+            assertf( src->starter->state != Halted,
+                  "Attempt by coroutine \"%.256s\" (%p) to suspend/leave back to terminated coroutine \"%.256s\" (%p).\n"
+                  "Possible cause is terminated coroutine's main routine has already returned.",
+                  src->name, src, src->starter->name, src->starter );
 
-		CoroutineCtxSwitch( src, src->starter );
-	}
+            CoroutineCtxSwitch( src, src->starter );
+      }
 }
 
