Don*_*dro 5 c++ winapi intel-pin
我制作了一个 pin 工具来转储 CreatFile win32 调用(在我的例子中为 CreateFileW)及其返回值。它看起来像这样:
/* ... */
VOID Image(IMG img, VOID *v)
{
RTN cfwRtn = RTN_FindByName(img, "CreateFileW");
if (RTN_Valid(cfwRtn))
{
RTN_Open(cfwRtn);
RTN_InsertCall(cfwRtn, IPOINT_BEFORE, (AFUNPTR)CreateFileWArg,
IARG_ADDRINT, "CreateFileW",
IARG_FUNCARG_ENTRYPOINT_VALUE, 0,
IARG_END);
RTN_InsertCall(cfwRtn, IPOINT_AFTER, (AFUNPTR)CreateFileWafter,
IARG_FUNCRET_EXITPOINT_VALUE, IARG_END);
RTN_Close(cfwRtn);
}
}
/* ... */
VOID CreateFileWArg(CHAR * name, wchar_t * filename)
{
TraceFile << name << "(" << filename << ")" << endl;
}
VOID CreateFileWafter(ADDRINT ret)
{
TraceFile << "\tReturned handle: " << ret << endl;
}
Run Code Online (Sandbox Code Playgroud)
它给出了有趣的结果。例如,在一个只打开现有文件而不执行其他操作的小程序上,它给出:
CreateFileW(file.txt)
Returned handle: 0
CreateFileW(file.txt)
Returned handle: 0x74
Returned handle: 0x74
Run Code Online (Sandbox Code Playgroud)
很多异常现象。
我还尝试测试一个简单的c++程序,直接调用CreateFileW一次,结果:
CreateFileW(file.txt)
Returned handle: 0
CreateFileW(file.txt)
Returned handle: 0xffffffff
Returned handle: 0xffffffff
Run Code Online (Sandbox Code Playgroud)
我尝试打开的文件不存在,因此返回值(-1 == INVALID_HANDLE_VALUE)至少是正确的。
有任何想法吗?提前致谢!
好吧,经过一段时间我终于弄清楚了这些问题的原因。
嗯,PIN 文档说:
注意:IPOINT_AFTER 是通过检测例程中的每个返回指令来实现的。Pin 尝试查找所有返回指令,但不能保证成功
如果在返回处转储函数的地址,则会发现CreateFileW不会返回 0。它是从 CreateFileW 调用的另一个函数返回的。PIN 的这种错误行为可以通过将 CreateFileW 方法包装在您自己的版本中来修复(转储参数、调用原始函数、转储返回值)。
事实证明,在我的系统上,CreateFileW 调用 Kernelbase.dll 的函数,该函数具有完全相同的名称。由于我按照例程的名称来检测例程,因此这是正确的行为。根据 kernel32.dll 检查映像名称解决了这个问题。