Добрый день! Подскажите кто какие функции использует для вывода отладочных сообщений. Важное условие без привязки к CRT(нужно чтобы работало на абсолютно чистой ОС) и чтобы нормально выводила переменные указанные в качестве аргументов. Т.е. по сути чем можно заменить _vsnprintf в примере ниже: static VOID TRACE(const char *szFormat,...) { char szBuff[1024]; va_list arg; va_start(arg, szFormat); _vsnprintf(szBuff,sizeof(szBuff), szFormat, arg); va_end(arg); OutputDebugString(szBuff); } Спасибо
va_list, va_start и va_end определяется дефайнами... достаточно просто подключить хедер... _vsnprintf экспортируется из user32.dll (wvsprintfA), безопасность по длине буфера уже в CRT реализуется... OutputDebugString - экспортируется из kernel32.dll (OutputDebugStringA)...
Great Ну да, OutputDebugString сводится к RaiseException(DBG_PRINTEXCEPTION_C), а DbgPrintEx к int 2d. Собственно, всегда использую второе (xp-7) и проблем не было.
И да. я торможу насчет Peb (. На самом деле int 2D/RaiseException в DbgPrintEx определяется значением KUSER_SHARED_DATA.KdDebuggerEnabled. Сейчас посмотрено. Удалите №8 что ли. UPD: Проверяются 2 флага. Если BeingDebugged, то сразу на raiseexception. Если же BeingDebugged = 0, то проверяется KUSER-SHARED_DATA.KdDebuggerEnabled. Если оно равно 3, то int 2d. Дизасм листинги нельзя смотреть бегло лол.
ULONG (__cdecl *DbgPrint_)(LPCSTR, ...) = (ULONG (__cdecl*)(LPCSTR, ...)) GetProcAddress(GetModuleHandleW(L"ntdll.dll"),"DbgPrint"); int main() { DbgPrint_("fuck %s", "you"); }
Суровый код ппц: Этоже насколько тупым нужно быть чтоб такое вызывать. Накол. lhc645 Разница то в режиме. Для пользовательского отладчика генерится сепшен посредством NtRaiseException, для ядерного посредством Int 0x2D.
karabas_barabas #pragma comment (lib, "ntdll.lib") extern "C" VOID _cdecl DbgPrint (PCH, ...); ... DbgPrint ("lala");
ТС поставил конкретный вопрос - я ему дал корректный, работающий код... без лишних "вы*бонов",заморочек и т.д. GetProcAddress(GetModuleHandleW(L"ntdll.dll"),"DbgPrint") - выполняется только один раз при инициализации, а не каждый...дальше происходит обращение по указателю...
Clerk understand. Кстати может быть кто-то подскажет почему значение 3? listing x64 w7 Код (Text): .text:0000000078EED85D mov rax, gs:30h .text:0000000078EED866 mov rdx, [rax+60h] .text:0000000078EED86A cmp PEB.FastPebLock, 0 .text:0000000078EED86F jz int_2d_call .text:0000000078EED875 mov rax, gs:30h .text:0000000078EED87E mov rdx, [rax+60h] .text:0000000078EED882 cmp PEB.BeingDebugged, 0 .text:0000000078EED886 jnz short raise_expt .text:0000000078EED888 mov al, ds:7FFE02D4h ; KUSER_SHARED_DATA.KdDebuggerEnabled .text:0000000078EED88F and al, 3 .text:0000000078EED891 cmp al, 3 .text:0000000078EED893 jz short int_2d_call .text:0000000078EED895 .text:0000000078EED895 raise_expt: ; CODE XREF: vDbgPrintExWithPrefixInternal+535E6j .text:0000000078EED895 mov [rsp+338h+var_2E8], 40010006h Бегло были просмотрены сорцы w2k и из kdinit.c!KdInitSystem Код (Text): KdDebuggerEnabled = TRUE; SharedUserData->KdDebuggerEnabled = TRUE; Стало быть должно быть true/false. Почему тогда проверка на 3 в ntdll ?