когда-то писал программку, в которой надо было выполнить код, при завершении собственно этой программы. помогла кртшная функция _onexit(); она ставит функции на выполнение, при завершении процесса. http://msdn.microsoft.com/en-us/library/zk17ww08(VS.71).aspx
Вынужден тебя огорчить. 1) при перехвате ExitProcess считать потоки совершенно не обязательно 2) при перехвате ExitThread их считать тоже не обязательно. посмотри что делает система: Code: 7C80CCA9 > 6A 14 PUSH 14 7C80CCAB 68 10CD807C PUSH kernel32.7C80CD10 7C80CCB0 E8 1658FFFF CALL kernel32.7C8024CB 7C80CCB5 64:A1 18000000 MOV EAX,DWORD PTR FS:[18] 7C80CCBB 8BF0 MOV ESI,EAX 7C80CCBD 8975 E0 MOV DWORD PTR SS:[EBP-20],ESI 7C80CCC0 33FF XOR EDI,EDI 7C80CCC2 57 PUSH EDI 7C80CCC3 6A 04 PUSH 4 7C80CCC5 8D45 E4 LEA EAX,DWORD PTR SS:[EBP-1C] 7C80CCC8 50 PUSH EAX 7C80CCC9 6A 0C PUSH 0C 7C80CCCB 6A FE PUSH -2 7C80CCCD FF15 2811807C CALL DWORD PTR DS:[<&ntdll.NtQueryInform>; ntdll.ZwQueryInformationThread 7C80CCD3 3BC7 CMP EAX,EDI 7C80CCD5 75 05 JNZ SHORT kernel32.7C80CCDC 7C80CCD7 397D E4 CMP DWORD PTR SS:[EBP-1C],EDI 7C80CCDA 75 28 JNZ SHORT kernel32.7C80CD04 7C80CCDC FF15 F414807C CALL DWORD PTR DS:[<&ntdll.RtlFreeThread>; ntdll.RtlFreeThreadActivationContextStack 7C80CCE2 E8 3A000000 CALL <JMP.&ntdll.LdrShutdownThread> 7C80CCE7 39BE 940F0000 CMP DWORD PTR DS:[ESI+F94],EDI 7C80CCED 0F85 F6770300 JNZ kernel32.7C8444E9 7C80CCF3 C686 750F0000 01 MOV BYTE PTR DS:[ESI+F75],1 7C80CCFA FF75 08 PUSH DWORD PTR SS:[EBP+8] 7C80CCFD 57 PUSH EDI 7C80CCFE FF15 6C14807C CALL DWORD PTR DS:[<&ntdll.NtTerminateTh>; ntdll.ZwTerminateThread 7C80CD04 FF75 08 PUSH DWORD PTR SS:[EBP+8] 7C80CD07 E8 96FD0000 CALL kernel32.ExitProcess
Я совсем не огорчен, это были только мои предположения Выходит в перехвате ExitThread нет необходимости. Однако приложение может поубивать свои потоки функцией TerminateThread или завершиться с помощью TerminateProcess.