Перехватил NtOpenProcess. Теперь необходимо получить полный путь процесса, который NtOpenProcess вызывает, и полный путь процесса, по отношению к которому эта функция вызывается. Делаю через PsLookupByProcessId и ObOpenObjectByPointer, а потом вызываю ZwQueryInformationProcess с параметром imagePath. Все работает, но возникает проблема: открытые хендлы функцией ObOpenObjectByPointer съедают память, а если применять к хендлам ZwClose(), то наблюдается интересная ситуация. Если закрываем хендлы, которые получили от ClientId, переданные NtOpenProcess все ок, а если закрывать хендлы которые получили, создав собственный ClientId с параметром UniqueProcess=(HANDLE) PsGetCurrentProcessI и UniqueThread=NULL, то все тоже работает. Но после запуска и завершения taskmanar`а система виснет как убитая. Помогите, что делать, чтобы этого не случалось?
NtOpenProcess процесс который вызывает эту функцию это (HANDLE)-1 процесс который хочет открыть получаем из ClientId->UniqueProcess (PID) для него нужно получить HANDLE схематично так: PsLookupProcessByProcessId -> ObOpenObjectByPointer -> ObfDereferenceObject -> ZwQueryInformationProcess -> ZwClose
Я так тоже делал. Но проблема в том, что драйвер все-равно при работе с taskmgr.exe вылетает в синьку с ошибкой 0x50 (PAGE_FAULT_IN_NONPAGED_AREA), а если оба хендла получать одинаковов через ObOpenObjectByPointer и не закрывать, то все работает без сбоев
Какой AccessMode (KernelMode или UserMode) был передан в функцию ObOpenObjectByPointer()? Должен быть KernelMode, если используются Zw-функции. Желательно вообще показать свой код реализации получения-закрытия описателя процесса. Еще нужен анализ bugcheck'а PAGE_FAULT_IN_NONPAGED_AREA: выхлоп !analyze -v. Телепатическими способностями тут мало кто обладает
0x6b65 Какраз наоборот. Сервисы - это пользовательский функционал, при ошибках в ядре ось закончит свою работу, фолты в ядре не допустимы.
Clerk Zw-функции это вызов Nt-сервисов через wrap'ер, который выставляет значение PreviousMode у текущей нити в KernelMode. Буферы, передаваемые в ZwQueryInformationProcess(), как я понимаю, используются выделенные в пуле или на стеке, т.е. Probe-функции на них вызвать не нужно (PreviousMode==KernelMode это гарантирует). Или я не понял твою фразу? И еще: если у описателя есть маска: Код (Text): #define KERNEL_HANDLE_MASK ((ULONG_PTR)((LONG)0x80000000)) То будет использована системная таблица описателей, иначе - текущего процесса. Эта маска будет в описателе, созданном с PreviousMode == KernelMode. Для Zw-функций все описатели должны иметь эту маску. Что бы создать такой описатель в данном случае, нужно указывать в ObOpenObjectByPointer(AccessMode == KernelMode)
Выдранно из вполне работающей проактивки, и даже по некоторым тестам являющейся лидером Код (Text): BOOLEAN GetProcessNameEx(HANDLE ProcessId, PWCHAR ProcessPath, ULONG ProcessPathLength) { /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/ BOOLEAN Status; HANDLE ProcessHandle; PEPROCESS Process; /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/ Process = NULL; ProcessHandle = NULL; if ( NT_SUCCESS(PsLookupProcessByProcessId(ProcessId, &Process)) ) { if ( NT_SUCCESS(ObOpenObjectByPointer(Process, OBJ_KERNEL_HANDLE, 0, 0x1F0FFF, 0, 0, &ProcessHandle)) || NT_SUCCESS(ObOpenObjectByPointer(Process, OBJ_KERNEL_HANDLE, 0, 0, 0, 0, &ProcessHandle)) ) { ObfDereferenceObject(Process); Status = GetProcessName(ProcessHandle, ProcessPath, ProcessPathLength); ZwClose(ProcessHandle); } else { ObfDereferenceObject(Process); Status = FALSE; } } else { Status = FALSE; } return (Status); } сверьтесь, код лично юзал, работает отлчино. если же вас все еще бсодит, смею предположить что проблема не в нем