-
Не подскажите альтернативу фунции IsProcessInJob в Windows 2000, мне нужно только определить "under job" процесс или нет?
-
QueryInformationJobObject с JobObjectBasicProcessIdList ?
И та и та функция требует HANDLE от Job
-
> Игорь Шевченко © (15.05.09 15:52) [1]
Спасибо
Не подскажите как определить, использует ли процесс NET Framework, является ли он сервисным, короче как это делает Process Explorer, в какую сторону копать?
-
> Не подскажите как определить, использует ли процесс NET > Framework
Я анализом EXE-файла определял - довольно просто, кстати.
> является ли он сервисным
По Parent-процессу. Есть функция RegisterServicesProcess (уже не помню, в какой DLL, но функция пользовательская) - как-то с ее помощью можно попытаться найти истинный Services.exe, хотя, если все внутри одного сеанса - то без особой разницы, можно и по имени.
Ну и я не уверен, что эта механика будет работать под Vista и Windows 7
-
> Я анализом EXE-файла определял - довольно просто, кстати.
Просто это как?
-
with NtHeaders.OptionalHeader.DataDirectory[ IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR] do if (VirtualAddress <> 0) and (Size <> 0) then isDotNet := true
как в статье из RSDN про исследование внутренностей исполняемого файла .Net
-
Соотвественно, NtHeaders проще всего взять функцией RtlImageNtHeaders из Ntdll
-
Разобрался по поводу > Не подскажите альтернативу фунции IsProcessInJob в Windows > 2000, мне нужно только определить "under job" процесс или > нет?
Спасибо > Игорь Шевченко © (15.05.09 15:52) [1]
Если кому интересно type
TJobObjectInfoClass = Cardinal;
type
TNtQuerySystemInformation = function(SystemInformationClass : LongInt;
SystemInformation : Pointer;
SystemInformationLength : ULONG;
ReturnLength : PDWORD) : Integer; stdcall;
TQueryInformationJobObject = function(hJob : THandle;
JobObjectInformationClass : TJobObjectInfoClass;
lpJobObjectInformation : Pointer;
cbJobObjectInformationLength : DWORD;
lpReturnLength : PDWORD) : BOOL; stdcall;
var
_NtQuerySystemInformation: TNtQuerySystemInformation;
_QueryInformationJobObject: TQueryInformationJobObject;
type
SYSTEM_HANDLE_INFORMATION = packed record
ProcessId: DWORD;
ObjectTypeNumber: Byte;
Flags: Byte;
Handle: Word;
pObject: Pointer;
GrantedAccess: DWORD;
end;
TSYSTEM_HANDLE_INFORMATION = ^SYSTEM_HANDLE_INFORMATION;
PSYSTEM_HANDLE_INFORMATION = ^TSYSTEM_HANDLE_INFORMATION;
SYSTEM_HANDLE_INFORMATION_EX = packed record
NumberOfHandles: DWORD;
Information: Array [0..0] of SYSTEM_HANDLE_INFORMATION;
end;
PSYSTEM_HANDLE_INFORMATION_EX = ^SYSTEM_HANDLE_INFORMATION_EX;
PJOBOBJECT_BASIC_PROCESS_ID_LIST = ^JOBOBJECT_BASIC_PROCESS_ID_LIST;
JOBOBJECT_BASIC_PROCESS_ID_LIST = Record
NumberOfAssignedProcesses : DWORD;
NumberOfProcessIdsInList : DWORD;
ProcessIdList : Array[0..0] of ULONG;
end;
type
NTSTATUS = Integer;
const
STATUS_SUCCESS = NTSTATUS($00000000);
STATUS_INFO_LENGTH_MISMATCH = NTSTATUS($C0000004);
SystemHandleInformation = 16;
JobObjectBasicProcessIdList = 3;
function _QuerySystemInformation(SystemInformationClass: Integer; var ReturnStatus: NTSTATUS): Pointer;
var
SystemInformationLength: Integer;
ReturnLength: DWORD;
begin
SystemInformationLength:= $400;
GetMem(Result, SystemInformationLength);
ReturnStatus:= _NtQuerySystemInformation(SystemInformationClass, Result, SystemInformationLength, @ReturnLength);
while (ReturnStatus = STATUS_INFO_LENGTH_MISMATCH) do
begin
FreeMem(Result);
SystemInformationLength:= SystemInformationLength * 2;
GetMem(Result, SystemInformationLength);
ReturnStatus:= _NtQuerySystemInformation(SystemInformationClass, Result, SystemInformationLength, @ReturnLength);
end;
if (ReturnStatus <> STATUS_SUCCESS) then
begin
FreeMem(Result);
Result:= nil;
end;
end;
function _IsProcessInJob(PID: DWORD): Boolean;
var
PSHI: PSYSTEM_HANDLE_INFORMATION_EX;
ReturnStatus: NTSTATUS;
hProcess, hTargetProcess: Cardinal;
i, l: Cardinal;
Info: PJOBOBJECT_BASIC_PROCESS_ID_LIST;
Size: DWORD;
begin
Result:= False;
PSHI := _QuerySystemInformation(SystemHandleInformation, ReturnStatus);
if (ReturnStatus = STATUS_SUCCESS) then
begin
for i := 0 to PSHI^.NumberOfHandles - 1 do
begin
begin
if PSHI^.Information[i].ObjectTypeNumber = 07 then
begin
hProcess:= OpenProcess(MAXIMUM_ALLOWED, False, PSHI^.Information[i].ProcessId);
if hProcess <> 0 then
try
if DuplicateHandle(hProcess, PSHI^.Information[i].Handle, INVALID_HANDLE_VALUE, @hTargetProcess, 0, False, DUPLICATE_SAME_ACCESS) then
begin
try
Size:= SizeOf(JOBOBJECT_BASIC_PROCESS_ID_LIST) + 4 * 1000;
GetMem(Info, Size);
try
if _QueryInformationJobObject(hTargetProcess, JobObjectBasicProcessIdList, Info, Size, nil) then
begin
if Info^.NumberOfProcessIdsInList > 0 then
for l:= 0 to Info^.NumberOfProcessIdsInList - 1 do
if PID = Info^.ProcessIdList[l] then
begin
Result:= True;
Break;
end;
end;
finally
FreeMem(Info);
end;
finally
CloseHandle(hTargetProcess);
end;
end;
finally
CloseHandle(hProcess);
end;
end;
end;
end;
FreeMem(PSHI);
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
if _IsProcessInJob(2836) then
Caption:= 'ProcessInJob'
else
Caption:= '';
end;
procedure TForm1.FormCreate(Sender: TObject);
begin
@_NtQuerySystemInformation:= GetProcAddress(LoadLibrary('ntdll.dll'), 'NtQuerySystemInformation');
@_QueryInformationJobObject:= GetProcAddress(LoadLibrary('kernel32.dll'), 'QueryInformationJobObject');
end;
|