Delphi 获取进程路径及命令行参数, 但有的进程获取时会报错,不知为啥

type
PVOID64 = UINT64; _UNICODE_STRING = packed record
Length : USHORT;
MaximumLength : USHORT;
Buffer : PWideChar;
end;
UNICODE_STRING = _UNICODE_STRING;
PUNICODE_STRING =^_UNICODE_STRING; _UNICODE_STRING64 = packed record
Length : USHORT;
MaximumLength : USHORT;
Fill : DWORD;
Buffer : PVOID64;
end;
UNICODE_STRING64 = _UNICODE_STRING64;
PUNICODE_STRING64 =^_UNICODE_STRING64; __PEB = packed record
Filler : array [..] of DWORD;
ProcessParameters : DWORD;
end; __PEB64 = packed record
Filler : array [..] of PVOID64;
ProcessParameters : PVOID64;
end; _CURDIR = packed record
DosPath : UNICODE_STRING;
Handle : THANDLE;
end; _CURDIR64 = packed record
DosPath : UNICODE_STRING64;
Handle : PVOID64;
end; _RTL_USER_PROCESS_PARAMETERS = packed record
MaximumLength :DWORD;
Length :DWORD;
Flags :DWORD;
DebugFlags :DWORD;
ConsoleHandle :THandle;
ConsoleFlags :DWORD;
StandardInput :THandle;
StandardOutput :THandle;
StandardError :THandle;
//////////////////////////
DosPath :UNICODE_STRING; //CurrentDirectory
Handle :THANDLE;
//////////////////////////
DllPath :UNICODE_STRING;
ImagePathName :UNICODE_STRING;
CmdLine :UNICODE_STRING;
end; _RTL_USER_PROCESS_PARAMETERS64 = record
MaximumLength :DWORD;
Length :DWORD;
Flags :DWORD;
DebugFlags :DWORD;
ConsoleHandle :PVOID64;
ConsoleFlags :DWORD;
StandardInput :PVOID64;
StandardOutput :PVOID64;
StandardError :PVOID64;
//////////////////////////
CurrentDirectory:_CURDIR64;
//////////////////////////
DllPath :UNICODE_STRING64;
ImagePathName :UNICODE_STRING64;
CmdLine :UNICODE_STRING64;
end; _PROCESS_BASIC_INFORMATION = packed record
Reserved1 :PVOID;
PebBaseAddress :PVOID;
Reserved2 :Array [..] of PVOID;
UniqueProcessId :PVOID;
Reserved3 :PVOID;
end;
PROCESS_BASIC_INFORMATION =_PROCESS_BASIC_INFORMATION;
PPROCESS_BASIC_INFORMATION =^_PROCESS_BASIC_INFORMATION; _PROCESS_BASIC_INFORMATION64 = packed record
Reserved1 :PVOID64;
PebBaseAddress :PVOID64;
Reserved2 :Array [..] of PVOID64;
UniqueProcessId :PVOID64;
Reserved3 :PVOID64;
end;
PROCESS_BASIC_INFORMATION64 =_PROCESS_BASIC_INFORMATION64;
PPROCESS_BASIC_INFORMATION64 =^_PROCESS_BASIC_INFORMATION64; TNtQueryInformationProcess = function(a:THANDLE;b:UINT;c:PVOID;d:ULONG;e:PULONG):LONG; stdcall;
TNtReadVirtualMemory = function(ProcessHandle:THANDLE; BaseAddress:PVOID; Buffer:PVOID; NumberOfBytesToRead:ULONG; NumberOfBytesReaded:PULONG):LONG; stdcall;
TNtReadVirtualMemory64 = function(ProcessHandle:THANDLE; BaseAddress:PVOID64; Buffer:PVOID; NumberOfBytesToRead:UINT64; NumberOfBytesReaded:PUINT64):LONG; stdcall;
TISWOW64PROCESS = function(hProcess:THANDLE; var Wow64Process:BOOL):BOOL; stdcall; function GetProcessImagePathAndCmdLine(hProcess:THandle; var ImagePath:string; var CmdLine:string):Boolean; implementation function GetProcessImagePathAndCmdLine32(hProcess:THandle; var ImagePath:string; var CmdLine:string):Boolean;
var
pbi : PROCESS_BASIC_INFORMATION;
pfnNtQueryInformationProcess : TNtQueryInformationProcess;
pfnNtReadVirtualMemory : TNtReadVirtualMemory;
dwSize:DWORD;
size:SIZE_T;
iReturn:Integer;
pAddrPEB:PVOID;
PEB:__PEB;
stBlock:_RTL_USER_PROCESS_PARAMETERS;
PathBuffer : PByte;
begin
Result := False;
@pfnNtQueryInformationProcess := GetProcAddress(GetModuleHandle('ntdll.dll'),'NtQueryInformationProcess');
@pfnNtReadVirtualMemory := GetProcAddress(GetModuleHandle('ntdll.dll'),'NtReadVirtualMemory'); if ( Assigned(pfnNtQueryInformationProcess) ) then
begin
pAddrPEB := nil;
iReturn := pfnNtQueryInformationProcess(hProcess,,@pbi,sizeof(pbi),@dwSize);
pAddrPEB := pbi.PebBaseAddress;
// NtQueryInformationProcess returns a negative value if it fails
if (iReturn >= ) then
begin
// . Find the Process Environment Block
size := dwSize;
if ( ERROR_SUCCESS <> pfnNtReadVirtualMemory(hProcess, pAddrPEB, @PEB, sizeof(PEB), PULONG(@size)) ) then
begin
// Call GetLastError() if you need to know why
Exit;
end;
// . From this PEB, get the address of the block containing
// a pointer to the CmdLine
if ( ERROR_SUCCESS <> pfnNtReadVirtualMemory(hProcess, PVOID(PEB.ProcessParameters), @stBlock, sizeof(stBlock), PULONG(@size))) then
begin
// Call GetLastError() if you need to know why
Exit;
end;
// . Get the ImagePathName
if (stBlock.ImagePathName.MaximumLength <= ) then
begin
PathBuffer := GetMemory(stBlock.ImagePathName.MaximumLength);
FillChar(PathBuffer^,stBlock.ImagePathName.MaximumLength,);
if (stBlock.ImagePathName.MaximumLength <= ) and ( ERROR_SUCCESS = pfnNtReadVirtualMemory(hProcess, PVOID(stBlock.ImagePathName.Buffer), PVOID(PathBuffer), stBlock.ImagePathName.Length*sizeof(Char), PULONG(@size))) then
begin // Call GetLastError() if you need to know why
SetString(ImagePath,PChar(PathBuffer),stBlock.ImagePathName.Length div );
Result := True;
end;
FreeMemory(PathBuffer);
end;
// . Get the CmdLine
if (stBlock.CmdLine.MaximumLength <= ) then
begin
PathBuffer := GetMemory(stBlock.CmdLine.MaximumLength);
FillChar(PathBuffer^,stBlock.CmdLine.MaximumLength,);
if ( ERROR_SUCCESS = pfnNtReadVirtualMemory(hProcess, PVOID(stBlock.CmdLine.Buffer), PVOID(PathBuffer), stBlock.CmdLine.Length*sizeof(Char), PULONG(@size))) then
begin // Call GetLastError() if you need to know why
SetString(CmdLine,PChar(PathBuffer),stBlock.CmdLine.Length div );
Result := True;
end;
FreeMemory(PathBuffer);
end;
end;
end;
end; function GetProcessImagePathAndCmdLine64(hProcess:THandle; var ImagePath:string; var CmdLine:string):Boolean;
var
pbi : PROCESS_BASIC_INFORMATION64;
pfnNtQueryInformationProcess : TNtQueryInformationProcess;
pfnNtReadVirtualMemory : TNtReadVirtualMemory64;
dwSize:DWORD;
size:UINT64;
iReturn:Integer;
pAddrPEB:PVOID64;
PEB:__PEB64;
stBlock:_RTL_USER_PROCESS_PARAMETERS64;
PathBuffer : PByte;
begin
Result := False;
@pfnNtQueryInformationProcess := GetProcAddress(GetModuleHandle('ntdll.dll'),'NtWow64QueryInformationProcess64');
@pfnNtReadVirtualMemory := GetProcAddress(GetModuleHandle('ntdll.dll'),'NtWow64ReadVirtualMemory64'); if ( Assigned(pfnNtQueryInformationProcess) ) then
begin
pAddrPEB := ;
iReturn := pfnNtQueryInformationProcess(hProcess,,@pbi,sizeof(pbi),PULONG(@dwSize));
pAddrPEB := pbi.PebBaseAddress;
// NtQueryInformationProcess returns a negative value if it fails
if (iReturn >= ) then
begin
// . Find the Process Environment Block
size := dwSize;
if ( ERROR_SUCCESS <> pfnNtReadVirtualMemory(hProcess, pAddrPEB, @PEB, sizeof(PEB), PUINT64(@size)) ) then
begin
// Call GetLastError() if you need to know why
Exit;
end;
// . From this PEB, get the address of the block containing
// a pointer to the CmdLine
if ( ERROR_SUCCESS <> pfnNtReadVirtualMemory(hProcess, PEB.ProcessParameters, @stBlock, sizeof(stBlock), PUINT64(@size))) then
begin
// Call GetLastError() if you need to know why
Exit;
end;
// . Get the ImagePathName
PathBuffer := GetMemory(stBlock.ImagePathName.MaximumLength);
FillChar(PathBuffer^,stBlock.ImagePathName.MaximumLength,);
if ( ERROR_SUCCESS = pfnNtReadVirtualMemory(hProcess, stBlock.ImagePathName.Buffer, PVOID(PathBuffer), stBlock.ImagePathName.Length*sizeof(Char), PUINT64(@size))) then
begin // Call GetLastError() if you need to know why
SetString(ImagePath,PChar(PathBuffer),stBlock.ImagePathName.Length div );
Result := True;
end;
// . Get the CmdLine
FreeMemory(PathBuffer);
PathBuffer := GetMemory(stBlock.CmdLine.MaximumLength);
FillChar(PathBuffer^,stBlock.CmdLine.MaximumLength,);
if ( ERROR_SUCCESS = pfnNtReadVirtualMemory(hProcess, stBlock.CmdLine.Buffer, PVOID(PathBuffer), stBlock.CmdLine.Length*sizeof(Char), PUINT64(@size))) then
begin // Call GetLastError() if you need to know why
SetString(CmdLine,PChar(PathBuffer),stBlock.CmdLine.Length div );
Result := True;
end;
FreeMemory(PathBuffer);
end;
end;
end; function GetProcessImagePathAndCmdLine(hProcess:THandle; var ImagePath:string; var CmdLine:string):Boolean;
var
fn:TISWOW64PROCESS;
begin
Result := False;
try
fn := GetProcAddress(GetModuleHandle('kernel32'),'IsWow64Process');
if Assigned(fn) then
begin
Result := GetProcessImagePathAndCmdLine64(hProcess,ImagePath,CmdLine);
end else
begin
Result := GetProcessImagePathAndCmdLine32(hProcess,ImagePath,CmdLine);
end;
Except
end;
end;

Delphi 获取进程路径及命令行参数的更多相关文章

  1. PED结构获取进程路径和命令行地址

    1.FS寄存器 2.进入FS寄存器地址,7FFDD000 3.偏移30为PED结构 4.偏移地址10 3C,44偏移:路径地址,命令行地址 // 通过PEB结构去查找所有进程模块 void *PEB ...

  2. Shell特殊变量:Shell $0, $#, $*, $@, $?, $$和命令行参数

    特殊变量列表 变量 含义 $0 当前脚本的文件名 $n 传递给脚本或函数的参数.n 是一个数字,表示第几个参数.例如,第一个参数是$1,第二个参数是$2. $# 传递给脚本或函数的参数个数. $* 传 ...

  3. 【Shell脚本学习8】Shell特殊变量:Shell $0, $#, $*, $@, $?, $$和命令行参数

    前面已经讲到,变量名只能包含数字.字母和下划线,因为某些包含其他字符的变量有特殊含义,这样的变量被称为特殊变量. 例如,$ 表示当前Shell进程的ID,即pid,看下面的代码: $echo $$ 运 ...

  4. 【转】shell 教程——07 Shell特殊变量:Shell $0, $#, $*, $@, $?, $$和命令行参数

    前面已经讲到,变量名只能包含数字.字母和下划线,因为某些包含其他字符的变量有特殊含义,这样的变量被称为特殊变量. 例如,$ 表示当前Shell进程的ID,即pid,看下面的代码: $echo $$ 运 ...

  5. linux bash Shell特殊变量:Shell $0, $#, $*, $@, $?, $$和命令行参数

    在linux下配置shell参数说明 前面已经讲到,变量名只能包含数字.字母和下划线,因为某些包含其他字符的变量有特殊含义,这样的变量被称为特殊变量. 例如,$ 表示当前Shell进程的ID,即pid ...

  6. UE4命令行参数解析

    转自:https://blog.csdn.net/u012999985/article/details/53544389 一 .命令行参数简述命令行参数是一连串的关键字字符串,当运行可执行文件时可以通 ...

  7. C#中如何获取其他进程的命令行参数 ( How to get other processes's command line argument )

    Subject: C#中如何获取其他进程的命令行参数 ( How to get other processes&apos;s command line argument )From: jian ...

  8. Linux进程-命令行参数和环境列表

    命令行参数 在C中,main函数有很多的变种,比如 main(), int main(), int main(int argc, char *argv[]), int main(int argc, c ...

  9. .NET 命令行参数包含应用程序路径吗?

    如果你关注过命令行参数,也许发现有时你会在命令行参数的第一个参数中中看到应用程序的路径,有时又不会.那么什么情况下有路径呢? 其实是否有路径只是取决于获取命令行参数的时候用的是什么方法.而这是 Win ...

随机推荐

  1. HDU 4432 Sum of divisors (水题,进制转换)

    题意:给定 n,m,把 n 的所有因数转 m 进制,再把各都平方,求和. 析:按它的要求做就好,注意的是,是因数,不可能有重复的...比如4的因数只有一个2,还有就是输出10进制以上的,要用AB.. ...

  2. ASMB的BUG(ORA-04030 kfmditer)导致数据库宕机

    ASMB的BUG(ORA-04030 kfmditer)导致数据库宕机 现象: 客户的一个重要生产系统RAC的一个实例宕机,查看alert日志: Fri Jun 21 17:05:52 2013 Er ...

  3. 如何在Visual Studio中选择C++和C#的编译器版本

    博客搬到了fresky.github.io - Dawei XU,请各位看官挪步.最新的一篇是:如何在Visual Studio中选择C++和C#的编译器版本.

  4. VMware Workstation 11.0 官方中文版最强虚拟机软件(附下载地址)

    VMware Workstation 11.0 新版本功能一览: 支持 Windows 8.1 Update.Windows Server 2012 R2.Ubuntu 14.10.RHEL 7.Ce ...

  5. PowerShell管理IIS(新建站点、应用程序池、应用程序、虚拟目录等)

    #导入IIS管理模块 Import-Module WebAdministration #新建应用程序池 api.dd.com New-Item iis:\AppPools\api.dd.com Set ...

  6. jsp页面用el表达式获取枚举的code

    jsp页面用el表达式获取枚举的code <c:set var="D_BUSINESS" value="<%=DeptEnum.D_BUSINESS%> ...

  7. 权限检查联系人ProfileProvider

    每日一贴,今天的内容关键字为权限检查 ProfileProvider继承自AbstractContyactsProvider. 源代码请自行下载     每日一道理 书籍好比一架梯子,它能引领人们登上 ...

  8. Codeforces Round #331 (Div. 2)C. Wilbur and Points 贪心

    C. Wilbur and Points Time Limit: 20 Sec Memory Limit: 256 MB 题目连接 http://codeforces.com/contest/596/ ...

  9. C语言默认參数值的实现

    from http://blog.csdn.net/pipisorry/article/details/25437893 C语言中没有參数默认值的概念,能够利用宏来模拟參数默认值: (对于有多个參数的 ...

  10. C++_直接插入排序(纯C版)

    //用于比较大小 int compared(const void *key1,const void *key2) { cout<<"enter compare"< ...