/************************************************************************** * SIGNAL.C * * Routines used to clean up on a forced KERNEL termination of a * TOOLHELP using app. * **************************************************************************/ #include #include "toolpriv.h" /* ----- Global variables ----- */ WORD wSignalInstalled; SIGNAL NEAR *npSignalHead; /* SignalRegister * Registers a default signal proc to a task. This signal proc is * called when the task is about to be terminated and is called before * the USER signal proc is called. The registered callback is * called HelperSignalProc() [HELPER.ASM] and chains to the USER signal * proc (if any) instead of returning. */ BOOL PASCAL SignalRegister( HANDLE hTask) { SIGNAL *pSig; SIGNAL *pTemp; /* NULL hTask means current task */ if (!hTask) hTask = GetCurrentTask(); /* Check to see if this task is already registered */ for (pSig = npSignalHead ; pSig ; pSig = pSig->pNext) if (pSig->hTask == hTask) return FALSE; /* Allocate a new SIGNAL structure */ pSig = (SIGNAL *)LocalAlloc(LMEM_FIXED, sizeof (SIGNAL)); if (!pSig) return FALSE; /* Fill in the useful fields */ pSig->hTask = hTask; pSig->lpfn = (LPFNCALLBACK)HelperSignalProc; pSig->lpfnOld = (LPFNCALLBACK) HelperSetSignalProc(hTask, (DWORD)HelperSignalProc); /* If this is the only handler, just insert it */ if (!npSignalHead) { pSig->pNext = npSignalHead; npSignalHead = pSig; } /* Otherwise, insert at the end of the list */ else { for (pTemp = npSignalHead ; pTemp->pNext ; pTemp = pTemp->pNext) ; pSig->pNext = pTemp->pNext; pTemp->pNext = pSig; } return TRUE; } /* SignalUnRegister * Called by an app whose callback is no longer to be used. * NULL hTask uses current task. */ BOOL PASCAL SignalUnRegister( HANDLE hTask) { SIGNAL *pSig; SIGNAL *pBefore; /* NULL hTask means current task */ if (!hTask) hTask = GetCurrentTask(); /* First try to find the task */ pBefore = NULL; for (pSig = npSignalHead ; pSig ; pSig = pSig->pNext) if (pSig->hTask == hTask) break; else pBefore = pSig; if (!pSig) return FALSE; /* Remove it from the list */ if (!pBefore) npSignalHead = pSig->pNext; else pBefore->pNext = pSig->pNext; /* Replace the old signal proc */ HelperSetSignalProc(hTask, (DWORD)pSig->lpfnOld); /* Free the structure */ LocalFree((HANDLE)pSig); return TRUE; }