Flasher Нельзя это делоть, можно только суспендить, иначе инхронизация может быть нарушена. KeSqueer Отправь мне на мэйл, я с форума аттачи не могу скачивать.
Clerk 1) У всех потоков в процессе переписываем in-thread-seh-обработчик. Для этого делаем инжект (GetThreadContext/SetThreadContext). В инжекте делаем MOV FS:[0], <адрес_структуры_EXCEPTION_REGISTRATION> и переход на старый EIP. Значение <адрес_структуры_EXCEPTION_REGISTRATION> у всех потоков будет разное и обязательно должно находится внутри стека потока, тут надо будет найти дно стека из _NT_TIB.StackBase и записать туда EXCEPTION_REGISTRATION специфичную для этого потока. EXCEPTION_REGISTRATION будет указывать на наш псевдо-глобальный обработчик. Также как-то сохраняем старый обработчик до перезаписи. 2) Ставим TF 3) Псевдо-глобальный обработчик будет обрабатывать TF (проверка на PUSH ESP(-1)) и после передавать управление на реальный обработчик.
Osen При чём тут контекст не понятно.. Я уже скозал(пост #16), что ядро процесс прибьёт, как в кернелмоде отследить я знаю, с этим проблем нет.
Clerk в форумском мыле нельзя файл прикрепить, поэтому исходник прилагается, или e-mail в личку нужен Код (Text): #include <windows.h> #include <stdio.h> #include <tchar.h> TCHAR szSubKey[] = _T("SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\AeDebug"); void Error(TCHAR *szFuncName, DWORD dwErr) { _tprintf(_T("Function %s failed. Error code: 0x%08lx\n"), szFuncName, dwErr); } BOOL SetModuleAsDebugger(void) { TCHAR szModuleFileName[0x200] = {0}; TCHAR szKeyValue[0x200] = {0}; HKEY hKey; LSTATUS status; status = RegOpenKeyEx(HKEY_LOCAL_MACHINE, szSubKey, 0, KEY_SET_VALUE, &hKey); if (status != ERROR_SUCCESS) { Error(_T("RegOpenKeyEx()"), status); return FALSE; } GetModuleFileName(NULL, szModuleFileName, sizeof(szModuleFileName)/sizeof(szModuleFileName[0])-1); _stprintf_s(szKeyValue, sizeof(szKeyValue)/sizeof(szKeyValue[0]), _T("%s -p %%ld -e %%ld"), szModuleFileName); status = RegSetValueEx(hKey, _T("Debugger"), 0, REG_SZ, (LPBYTE)szKeyValue, (lstrlen(szKeyValue)+1)*sizeof(szKeyValue[0])); if (status != ERROR_SUCCESS) { Error(_T("RegSetValueEx()"), status); return FALSE; } status = RegSetValueEx(hKey, _T("Auto"), 0, REG_SZ, (LPBYTE)"1", 2*sizeof(TCHAR)); if (status != ERROR_SUCCESS) Error(_T("RegSetValueEx()"), status); status = RegCloseKey(hKey); if (status != ERROR_SUCCESS) Error(_T("RegCloseKey()"), status); return TRUE; } int _tmain(int argc, _TCHAR* argv[]) { if (argc > 1) { TCHAR buf[0x200] = {0}; int i; _tprintf(_T("Debugger \"%s\" called with following arguments:\n"), argv[0]); for (i = 1; i < argc; ++i) { _tcscat_s(buf, sizeof(buf)/sizeof(buf[0]), argv[i]); _tcscat_s(buf, sizeof(buf)/sizeof(buf[0]), _T(" ")); } _tprintf(buf); getc(stdin); return 0; } else { if (SetModuleAsDebugger()) { __asm xor esp, esp; __asm dec esp; __asm push esp; } else { _tprintf(_T("Can't set module as a debugger.\n")); getc(stdin); return 1; } } return 0; }
KeSqueer Да ладно, параметры в реестре я никогда писать не буду, для подключения отладчика достаточно сервисов. Всем спасибо, тема закрыта.
Clerk Я предлагаю не доводить до этого исключения, а трейсить, в обработчике трейсера проверять на PUSH ESP (-1).