|
|
Регистрация | << Правила форума >> | FAQ | Пользователи | Календарь | Поиск | Сообщения за сегодня | Все разделы прочитаны |
|
Опции темы | Поиск в этой теме | Опции просмотра |
#1
|
||||
|
||||
Передача параметров в DLL
Всем Здравствуйте! Есть такой вопрос. Есть моя длл-ка которая инжектируется в другой процесс. Так вот как мне передать параметры в процедуру (например reset(par1,par2:word), в длл-ке она есть), из своей программы?
|
#2
|
||||
|
||||
Как вариант - при инжекте зарезервировать до/после инжект-кода место под переменные, и писать туда. После чего выставить там же какой-нибудь флаг. Этот флаг проверять в цикле в ДЛЛ, и как только он выставился - сбросить и вызвать нужную функцию с нужными параметрами. Инжект-код может сказать ДЛЛ-ке свой адрес вызовом какой-нибудь специально для этого сделанной функции в самой DLL.
Только вот нескромный вопрос - ради чего такие сложности? jmp $ ; Happy End! The Cake Is A Lie. |
#3
|
||||
|
||||
А ещё наверное так можно, библиотека ведь загружена, в смысле её копия в памяти уже есть
сначало объявить Код:
... MyProc = procedure reset(par1, par2: word); stdcall; ... Код:
... var proc: MyProc; begin @proc := GetProcAddress(HandleDll{нужно подставить}, 'reset'); proc(par1, par2); ... end; Я не понял Вашего вопроса, но всё же Вам на него отвечу! |
#4
|
||||
|
||||
Цитата:
jmp $ ; Happy End! The Cake Is A Lie. |
#5
|
||||
|
||||
Bargest, а че я до длл-ки не могу добратся через CreateToolhelp32Snapshot? Alegun тут как-то мне не понятно
Цитата:
|
#6
|
||||
|
||||
Цитата:
Я не понял Вашего вопроса, но всё же Вам на него отвечу! |
#7
|
||||
|
||||
Цитата:
Код:
mov eax, param1 mov edx, param2 call reset Цитата:
Klyaksa, поясни, зачем тебе вообще это надо. Может есть решение проще. И код инжекта приведи. jmp $ ; Happy End! The Cake Is A Lie. Последний раз редактировалось Bargest, 06.04.2014 в 00:36. |
#8
|
||||
|
||||
Цитата:
Я не понял Вашего вопроса, но всё же Вам на него отвечу! |
#9
|
||||
|
||||
Цитата:
Цитата:
Цитата:
Код:
function InjectModule(ModulePath: PAnsiChar; ProcessID: DWORD): Boolean; type TNtCreateThreadEx = function( ThreadHandle: PHANDLE; DesiredAccess: ACCESS_MASK; ObjectAttributes: Pointer; ProcessHandle: THANDLE; lpStartAddress: Pointer; lpParameter: Pointer; CreateSuspended: BOOL; dwStackSize: DWORD; Unknown1: Pointer; Unknown2: Pointer; Unknown3: Pointer): HRESULT; stdcall; var lpStartAddress, lpParameter: Pointer; dwSize: Integer; hProcess, hThread, lpThreadId, lpExitCode, lpBytesWritten: Cardinal; NtCreateThreadEx: TNtCreateThreadEx; begin Result := False; if IsModuleLoaded(ModulePath, ProcessID) = True then Exit; hProcess := 0; hProcess := OpenProcess(MAXIMUM_ALLOWED, False, ProcessID); if hProcess = 0 then Exit; dwSize := StrLen(ModulePath) + 1; lpParameter := VirtualAllocEx(hProcess, nil, dwSize, MEM_COMMIT, PAGE_READWRITE); if (lpParameter = nil) then begin if hProcess <> 0 then CloseHandle(hProcess); Exit; end; if GetOSVersion >= 60 then NtCreateThreadEx := GetProcAddress(GetModuleHandleW('ntdll'), 'NtCreateThreadEx'); lpStartAddress := GetProcAddress(GetModuleHandleW('kernel32'), 'LoadLibraryA'); if (lpStartAddress = nil) then Exit; if GetOSVersion >= 60 then if (@NtCreateThreadEx = nil) then Exit; lpBytesWritten := 0; if (WriteProcessMemory(hProcess, lpParameter, ModulePath, dwSize, lpBytesWritten) = False) then begin VirtualFreeEx(hProcess, lpParameter, 0, MEM_RELEASE); if hProcess <> 0 then CloseHandle(hProcess); Exit; end; hThread := 0; lpThreadId := 0; if GetOSVersion >= 60 then NtCreateThreadEx(@hThread, MAXIMUM_ALLOWED, nil, hProcess, lpStartAddress, lpParameter, false, 0, 0, 0, 0) else hThread := CreateRemoteThread(hProcess, nil, 0, lpStartAddress, lpParameter, 0, lpThreadId); if (hThread = 0) then begin VirtualFreeEx(hProcess, lpParameter, 0, MEM_RELEASE); CloseHandle(hProcess); Exit; end; GetExitCodeThread(hThread, lpExitCode); if hProcess <> 0 then CloseHandle(hProcess); if hThread <> 0 then CloseHandle(hThread); Result := True; end; Последний раз редактировалось Klyaksa, 06.04.2014 в 00:48. |
#10
|
||||
|
||||
Цитата:
Я не понял Вашего вопроса, но всё же Вам на него отвечу! |
#11
|
||||
|
||||
Цитата:
1) Скомпилировал бы в DLL проект с формой для редактирования данных; 2) Сделал бы в этой DLL функцию, заменяющую QueryPerformanceCounter, берущую значение из введенных данных; 3) Сделал бы, чотбы DLL заменила в импорте QueryPerformanceCounter на адрес подменной функции; 4) Пропатчил бы точку входа игры, чтобы она загрузила DLL. Ну или на крайняк написал бы мелкий сторонний инжектор. Если же обязательно надо, чтобы программа ввода была отдельно - то проще всего, на мой взгляд, как я сказал в начале. Стандартная технология инжекта - VirtualAlloc в чужом процессе, создание там побайтово кода загрузки ДЛЛ и запуск этого кода через CreateRemoteThread. Можно запросто выделить побольше места и передать в ДЛЛ после загрузки через какой-нибудь самописный Initialize адрес. Затем брать параметры всегда по какому-то смещению от этого адреса. То есть инжектируемый код будет примерно таким (FASM-синтаксис! не пытайся это скомпилировать во встроенном асм в делфи): Код:
push libName call LoadLibrary push aStart push eax call GetProcAddress call $+5 ; push eip - текущий адрес call eax ; call Start; _stdcall функция с одним параметром; никогда не возвращается ret ; не обязательно, чисто ради приличия param1: .dw 0 param2: .dw 0 libName: .db 'HelloWorld.dll',0 aStart: .db 'Start',0 Остается только менять эти параметры через WriteProcessMemory - в сторонней проге адрес тоже известен, она ведь его и выделила через VirtualAlloc. ЗЫЖ разумеется, при таком подходе DllMain должен сразу завершиться, и вернуть не ноль. Иначе либа автоматом выгрузиться и будешь долго кусать локти и искать ошибку. [EDIT] Код, который ты привел, не очень хорош тем, что вся работа обязательно должна происходить в DLLMain, и никогда нельзя из него выходить. А в DllMain сторонние параметры передать трудновато. Цитата:
jmp $ ; Happy End! The Cake Is A Lie. Последний раз редактировалось Bargest, 06.04.2014 в 01:29. |
#12
|
||||
|
||||
Цитата:
Я не понял Вашего вопроса, но всё же Вам на него отвечу! |
#13
|
||||
|
||||
Цитата:
Также есть PostThreadMessage, хотя им я ни разу не пользовался. Но думаю, если есть - должен работать. Можно попробовать в дебаге инициировать запуск функции, вручную передав параметры и вручную же отловив выход. Но это все такие извраты, что лучше о них даже не думать. jmp $ ; Happy End! The Cake Is A Lie. |
#14
|
||||
|
||||
Пришлось делать по пункту
Цитата:
|