问题
I'm trying to get a handle to a function within a .dll. I am creating a CreateToolHelp32Snapshot and then enumerating over the modules until I find the one I want, from that .dll I want to find a particular function. How do I call GetProcAddress() correctly so that I get the function within 'that' .dll rather than another instance that may be running?
The continuation from the above question would then be, ok so I have a handle to the function, how do I actually call it?
EDIT: As has already been pointed out. I am already in the 3rd party app address space. If getprocaddress will not work, how do I get the entry point for the function using readprocessmemory and necessary offset?
Thanks.
HANDLE h_th_32snap = CreateToolhelp32Snapshot(0x8u, pid);
if( h_th_32snap == INVALID_HANDLE_VALUE )
{
printError( TEXT("CreateToolhelp32Snapshot (of modules)") );
return( FALSE );
}
// Set the size of the structure before using it.
me32.dwSize = sizeof( MODULEENTRY32 );
// Retrieve information about the first module,
// and exit if unsuccessful
if( !Module32First( h_th_32snap, &me32 ) )
{
printError( TEXT("Module32First") ); // show cause of failure
CloseHandle( h_th_32snap ); // clean the snapshot object
return( FALSE );
}
// Now walk the module list of the process,
// and display information about each module
BYTE *d_pointer_qtgui4_dll = 0x0;
do
{
_tprintf( TEXT("\n\n MODULE NAME: %s"), me32.szModule );
_tprintf( TEXT("\n Executable = %s"), me32.szExePath );
_tprintf( TEXT("\n Process ID = 0x%08X"), me32.th32ProcessID );
_tprintf( TEXT("\n Ref count (g) = 0x%04X"), me32.GlblcntUsage );
_tprintf( TEXT("\n Ref count (p) = 0x%04X"), me32.ProccntUsage );
_tprintf( TEXT("\n Base address = 0x%08X"), (DWORD) me32.modBaseAddr );
_tprintf( TEXT("\n Base size = %d"), me32.modBaseSize );
if(!wcsncmp(me32.szModule, L"QtGui4.dll", 255))
{
FARPROC test = GetProcAddress(GetModuleHandle( L"QtGui4.dll"),"?rowsInserted@QListView@@MAEXABVQModelIndex@@HH@Z");
}
} while( Module32Next( h_th_32snap, &me32 ) );
CloseHandle( h_th_32snap );
Greg, I would be interested to know why this is wrong? It doesn't throw any errors but it doesn't work either!
function prototype:
QWidget * QWidget::find ( WId id ) [static];
My attempt to call it:
hDLL = GetModuleHandle( L"QtGui4.dll");
if (hDLL != NULL)
{
func pointer_find = (func)GetProcAddress(hDLL,"?find@QWidget@@SAPAV1@PAUHWND__@@@Z");
if (!pointer_find)
{
// handle the error
FreeLibrary(hDLL);
//return SOME_ERROR_CODE;
}
else
{
// call the function
widget = pointer_find(my_hwnd);
}
}
回答1:
Not possible, GetProcAddress() requires a module handle. A HMODULE is only valid inside the process in which it was obtained. You would have to do the same kind of thing that GetProcAddress() does, iterating the IAT to find the entrypoint. And apply the base address offset. This is beyond painful to do for another process since you cannot directly access the memory to read the IAT. ReadProcessMemory is required.
Injecting code in the target process is the only reasonable approach. Which is also required to do what I presume you'd want to do next, call the function. Code injection techniques are covered well at codeproject.com
回答2:
If you are in process you are almost there.
GetModuleHandle will get a currently loaded module handle, compared to LoadLibrary which will load a module (and increase the ref count). Just need the right prototype for the function.
typedef void __thiscall (QListView::*rowsInserted)(class QModelIndex const &,int,int);
rowsInserted test = (rowsInserted)GetProcAddress(GetModuleHandle( L"QtGui4.dll"),"?rowsInserted@QListView@@MAEXABVQModelIndex@@HH@Z");
//QListView *object
if( test && object )
(object.*test)(my_QModelIndex, int_x, int_y);
来源:https://stackoverflow.com/questions/4618906/finding-a-loaded-dll-using-a-createtoolhelp32snapshot-finding-a-function-within