diff options
| author | Rich Felker <dalias@aerifal.cx> | 2011-04-17 17:06:05 -0400 | 
|---|---|---|
| committer | Rich Felker <dalias@aerifal.cx> | 2011-04-17 17:06:05 -0400 | 
| commit | 1ebde9c3a228e8daa4bdba98046556b4b6829f5e (patch) | |
| tree | 61ed4895a116fae89024e73079618a904fb05958 | |
| parent | 9080cc153cc2b09881c3245becbd68534db18d7c (diff) | |
| download | musl-1ebde9c3a228e8daa4bdba98046556b4b6829f5e.tar.gz | |
fix pthread_exit from cancellation handler
cancellation frames were not correctly popped, so this usage would not
only loop, but also reuse discarded and invalid parts of the stack.
| -rw-r--r-- | src/thread/pthread_create.c | 10 | 
1 files changed, 5 insertions, 5 deletions
diff --git a/src/thread/pthread_create.c b/src/thread/pthread_create.c index 8e3a4a26..c6a23955 100644 --- a/src/thread/pthread_create.c +++ b/src/thread/pthread_create.c @@ -18,12 +18,13 @@ weak_alias(dummy_1, __pthread_tsd_run_dtors);  void __pthread_unwind_next(struct __ptcb *cb)  { -	pthread_t self; +	pthread_t self = pthread_self();  	int n; -	if (cb->__next) longjmp((void *)cb->__next->__jb, 1); - -	self = pthread_self(); +	if (cb->__next) { +		self->cancelbuf = cb->__next->__next; +		longjmp((void *)cb->__next->__jb, 1); +	}  	LOCK(&self->exitlock); @@ -104,7 +105,6 @@ int pthread_create(pthread_t *res, const pthread_attr_t *attr, void *(*entry)(vo  	new->detached = attr->_a_detach;  	new->attr = *attr;  	new->unblock_cancel = self->cancel; -	new->result = PTHREAD_CANCELED;  	memcpy(new->tlsdesc, self->tlsdesc, sizeof new->tlsdesc);  	new->tlsdesc[1] = (uintptr_t)new;  	stack = (void *)((uintptr_t)new-1 & ~(uintptr_t)15);  | 
