[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Dangling pointers in cancelsigintrs()



Hello Howard, you wrote:

/*
 * cancelsigintrs: remove any interrupts requested by this process, called
 * at process termination.
 */
void ARGS_ON_STACK
cancelsigintrs()
{
	usig *ptr, *old;
	short s = spl7();

	for (old=NULL, ptr=usiglst; ptr; old=ptr, ptr=ptr->next)
		if (ptr->proc == curproc) {
			setexc(ptr->vec, ptr->oldv);
			if (old)
				old->next = ptr->next;
			else
				usiglst = ptr->next;
			kfree(ptr);
		}
	spl(s);
}


It seems that there is a potential problem with this routine: once you
have freed `ptr', the `ptr->next' information is no longer available (it
lies in de-allocated memory). It also seems that the routine won't work
if it must unlink consecutive usig's (because `old' will point to the
previous usig, which has just been deallocated). Here is a (hopefully)
safe variant of the same routine:


/*
 * cancelsigintrs: remove any interrupts requested by this process, called
 * at process termination.
 */
void ARGS_ON_STACK
cancelsigintrs()
{
	usig *ptr, **old, *nxt;
	short s = spl7();

	for (old=&usiglst, ptr=usiglst; ptr; ) {
		nxt = ptr->next;
		if (ptr->proc == curproc) {
			setexc(ptr->vec, ptr->oldv);
			*old = nxt;
			kfree(ptr);
			/* note that `old' does not move! */
		} else {
			old = &(ptr->next);
		}
		ptr = nxt;
	}
	spl(s);
}


Thierry.