Сейчас на форуме: hgdagon, asfa (+4 невидимых)

 eXeL@B —› Программирование —› Пишу переходник процедуры hasp, входе процедуру всё умирает...
Посл.ответ Сообщение


Ранг: 450.3 (мудрец), 13thx
Активность: 0.20
Статус: Участник

Создано: 23 февраля 2007 12:41
· Личное сообщение · #1

Пытаюсь написать переходник процедуры hasp и вставить его в исследуемую прогу. Получается какой то косяк и на входе процедуру всё умирает… Делаю согласно этой доки:

С процедурой hasp() используются следующие девять параметров:
hasp (Service, SeedCode, PortNum, Password1, Password2, Par1, Par2, Par3, Par4)

делаю так:

library hsp;

uses Winprocs;

procedure Hasp(a1,a2,a3,a4,a5,a6,a7,a8,a9:longint); external 'Haspbc32.dll' name 'hasp';

procedure _msg(a1,a2,a3,a4,a5,a6,a7,a8,a9:longint); stdcall;
begin
hasp(a1,a2,a3,a4,a5,a6,a7,a8,a9);
end;

exports _msg;

begin
end.



Отлаживаю идой:

Было (без вызова моей процедуры):

CODE:004AEBF2 push offset unk_4CEA1C
CODE:004AEBF7 push ebx
CODE:004AEBF8 push offset dword_4CEA14
CODE:004AEBFD push offset dword_4CEA10
CODE:004AEC02 mov eax, ds:dword_4CEA0C
CODE:004AEC07 push eax
CODE:004AEC08 mov eax, ds:dword_4CEA08
CODE:004AEC0D push eax
CODE:004AEC0E mov eax, ds:dword_4CEA00
CODE:004AEC13 push eax
CODE:004AEC14 mov eax, ds:dword_4CEA04
CODE:004AEC19 push eax
CODE:004AEC1A push 3 ; передаётся 3
CODE:004AEC1C call hasp


Захожу в hasp

CODE:004AE3E4 hasp proc near ; CODE XREF: sub_4AEB90+42 p
CODE:004AE3E4 ; sub_4AEBE4+38 p ...
CODE:004AE3E4 jmp ds:__imp_hasp
CODE:004AE3E4 hasp endp


прыгаю:

Haspbc32.dll:0033413E haspbc32_hasp:
Haspbc32.dll:0033413E push ebp
Haspbc32.dll:0033413F mov ebp, esp
Haspbc32.dll:00334141 push dword ptr [ebp+28h]
Haspbc32.dll:00334144 push dword ptr [ebp+24h]
Haspbc32.dll:00334147 push dword ptr [ebp+20h]
Haspbc32.dll:0033414A push dword ptr [ebp+1Ch]
Haspbc32.dll:0033414D push dword ptr [ebp+18h]
Haspbc32.dll:00334150 push dword ptr [ebp+14h]
Haspbc32.dll:00334153 push dword ptr [ebp+10h]
Haspbc32.dll:00334156 push dword ptr [ebp+0Ch]
Haspbc32.dll:00334159 push dword ptr [ebp+8] ; передалась 3
Haspbc32.dll:0033415C call near ptr unk_331120
Haspbc32.dll:00334161 add esp, 24h
Haspbc32.dll:00334164 pop ebp
Haspbc32.dll:00334165 retn 24h


После ret-а успешно возвращаемся.


Внедряю свою длл, в отлаживаемой программе заменяю вызов hasp на вызов _msg.

Стало:

CODE:004AEBF2 push offset unk_4CEA1C
CODE:004AEBF7 push ebx
CODE:004AEBF8 push offset dword_4CEA14
CODE:004AEBFD push offset dword_4CEA10
CODE:004AEC02 mov eax, ds:dword_4CEA0C
CODE:004AEC07 push eax
CODE:004AEC08 mov eax, ds:dword_4CEA08
CODE:004AEC0D push eax
CODE:004AEC0E mov eax, ds:dword_4CEA00
CODE:004AEC13 push eax
CODE:004AEC14 mov eax, ds:dword_4CEA04
CODE:004AEC19 push eax
CODE:004AEC1A push 3 ; передаётся 3
CODE:004AEC1C call dword ptr ds:_msg


Захожу в _msg

hsp.dll:003DC624 hsp__msg:
hsp.dll:003DC624 push ebp
hsp.dll:003DC625 mov ebp, esp
hsp.dll:003DC627 mov eax, [ebp+14h]
hsp.dll:003DC62A push eax
hsp.dll:003DC62B mov eax, [ebp+18h]
hsp.dll:003DC62E push eax
hsp.dll:003DC62F mov eax, [ebp+1Ch]
hsp.dll:003DC632 push eax
hsp.dll:003DC633 mov eax, [ebp+20h]
hsp.dll:003DC636 push eax
hsp.dll:003DC637 mov eax, [ebp+24h]
hsp.dll:003DC63A push eax
hsp.dll:003DC63B mov eax, [ebp+28h]
hsp.dll:003DC63E push eax
hsp.dll:003DC63F mov ecx, [ebp+10h]
hsp.dll:003DC642 mov edx, [ebp+0Ch]
hsp.dll:003DC645 mov eax, [ebp+8] ; тут оказывается передаваемая 3
hsp.dll:003DC648 call near ptr unk_3DC61C ; идём в оригинальный hasp
hsp.dll:003DC64D pop ebp
hsp.dll:003DC64E retn 24h


переход

hsp.dll:003DC61C loc_3DC61C: ; CODE XREF: hsp.dll:003DC648 p
hsp.dll:003DC61C jmp ds:off_3E06F4


оказались тут:

Haspbc32.dll:0033413E haspbc32_hasp: ; DATA XREF: hsp.dll:off_3E06F4 o
Haspbc32.dll:0033413E push ebp
Haspbc32.dll:0033413F mov ebp, esp
Haspbc32.dll:00334141 push dword ptr [ebp+28h]
Haspbc32.dll:00334144 push dword ptr [ebp+24h]
Haspbc32.dll:00334147 push dword ptr [ebp+20h]
Haspbc32.dll:0033414A push dword ptr [ebp+1Ch]
Haspbc32.dll:0033414D push dword ptr [ebp+18h]
Haspbc32.dll:00334150 push dword ptr [ebp+14h]
Haspbc32.dll:00334153 push dword ptr [ebp+10h]
Haspbc32.dll:00334156 push dword ptr [ebp+0Ch]
Haspbc32.dll:00334159 push dword ptr [ebp+8] ; тут уже не передаётся цифра 3
Haspbc32.dll:0033415C call near ptr unk_331120 ; а тут всё умирает……
Haspbc32.dll:00334161 add esp, 24h
Haspbc32.dll:00334164 pop ebp
Haspbc32.dll:00334165 retn 24h





Ранг: 113.0 (ветеран)
Активность: 0.050
Статус: Участник

Создано: 23 февраля 2007 13:26
· Личное сообщение · #2

hsp.dll:003DC63F mov ecx, [ebp+10h]
hsp.dll:003DC642 mov edx, [ebp+0Ch]
hsp.dll:003DC645 mov eax, [ebp+8] ; тут оказывается передаваемая 3
hsp.dll:003DC648 call near ptr unk_3DC61C ; идём в оригинальный hasp

Не очень понял - первые параметры переданы через регистры? Без перехвата вроде все в стеке - ?

-----
The one derivative you manage is the one I abhore (c) Slipknot





Ранг: 450.3 (мудрец), 13thx
Активность: 0.20
Статус: Участник

Создано: 23 февраля 2007 14:35
· Личное сообщение · #3

Chingachguk пишет:
Не очень понял - первые параметры переданы через регистры?


Да, сам не понимаю почему так происходит... Скорее всего проблема закралась именно дельфевском куске. Может нужно как то по-другому объявлять процедуру или не использовать stdcall, а может быть стек корректировать ...



Ранг: 352.4 (мудрец), 4thx
Активность: 0.150
Статус: Участник
retired

Создано: 23 февраля 2007 14:52
· Личное сообщение · #4

Chingachguk пишет:
первые параметры переданы через регистры

fastcall ?




Ранг: 113.0 (ветеран)
Активность: 0.050
Статус: Участник

Создано: 23 февраля 2007 17:12
· Личное сообщение · #5

Да, надо что-то уточнить чтобы паскаль не считал hasp "своей" и не выделывался... не совсем понятно почему ты вообще в модуле msg об'являешь прототип hasp - ведь разве недостаточно объявить ~"uses hsp" (или как ты написал - "library hsp") - в самой либе разве нету аналога *.h?

-----
The one derivative you manage is the one I abhore (c) Slipknot





Ранг: 450.3 (мудрец), 13thx
Активность: 0.20
Статус: Участник

Создано: 23 февраля 2007 23:45
· Личное сообщение · #6

Chingachguk пишет:
не совсем понятно почему ты вообще в модуле msg об'являешь прототип hasp


Я хочу что бы в программе функция hasp не вызывалась. Вместо неё будет вызываться _msg, в которой я реализую всё, что планирую, а далее вызову оригинальную hasp, что бы программа работала. Естественно, что по мере реализации эмулирующих функций буду избавлятся от вызова оригинальной hasp, но это всё только в перспективе.

ssx пишет:
fastcall ?


хз. Пробывал по-разному, и safecall делал и без указания вообще...




Ранг: 450.3 (мудрец), 13thx
Активность: 0.20
Статус: Участник

Создано: 24 февраля 2007 00:06 · Поправил: ToBad
· Личное сообщение · #7

В общем у меня получилось… Если кому то интересно, то приведу полный вид того, как это сейчас выглядит.

Этот участок до внедрения и после остаётся без изменений.

CODE:004AEC19 push eax
CODE:004AEC1A push 3
CODE:004AEC1C call hasp
CODE:004AEC21 cmp dword ptr [ebx], 0


Вызов приводит нас в:

CODE:004AE3E4 hasp proc near ; CODE XREF: sub_4AEB90+42 p
CODE:004AE3E4 ; sub_4AEBE4+38 p ...
CODE:004AE3E4 jmp ds:__imp_hasp
CODE:004AE3E4 hasp endp


Тут мы меняем jmp на свой который указывает на _msg. Это позволит не патчить все вызовы hasp. Теперь это так:

CODE:004AE3E4 hasp proc near ; CODE XREF: sub_4AEB90+42 p
CODE:004AE3E4 ; sub_4AEBE4+38 p ...
CODE:004AE3E4 jmp dword ptr ds:_msg
CODE:004AE3E4 hasp endp


Теперь вид переходника…

library hsp;

uses Winprocs;

procedure Hasp(a1,a2,a3,a4,a5,a6,a7,a8,a9:dword); external 'Haspbc32.dll' name 'hasp';

procedure _msg(a1,a2,a3,a4,a5,a6,a7,a8,a9:dword); stdcall;
var p:pointer;
begin
p:=@hasp;
asm
push a9
push a8
push a7
push a6
push a5
push a4
push a3
push a2
push a1
call p
end;
end;

exports _msg;

begin
end.


При отладке всё выглядит так:

CODE:004AEC19 push eax
CODE:004AEC1A push 3 ; наша тройка
CODE:004AEC1C call hasp
CODE:004AEC21 cmp dword ptr [ebx], 0


По call попадаем сюда:

CODE:004AE3E4 hasp proc near ; CODE XREF: sub_4AEB90+42 p
CODE:004AE3E4 jmp dword ptr ds:_msg
CODE:004AE3E4 hasp endp


Потом по jmp сюда:

hsp.dll:003934D0 hsp__msg:
hsp.dll:003934D0 push ebp
hsp.dll:003934D1 mov ebp, esp
hsp.dll:003934D3 push ecx
hsp.dll:003934D4 mov dword ptr [ebp-4], offset unk_3934C8
hsp.dll:003934DB push dword ptr [ebp+28h]
hsp.dll:003934DE push dword ptr [ebp+24h]
hsp.dll:003934E1 push dword ptr [ebp+20h]
hsp.dll:003934E4 push dword ptr [ebp+1Ch]
hsp.dll:003934E7 push dword ptr [ebp+18h]
hsp.dll:003934EA push dword ptr [ebp+14h]
hsp.dll:003934ED push dword ptr [ebp+10h]
hsp.dll:003934F0 push dword ptr [ebp+0Ch]
hsp.dll:003934F3 push dword ptr [ebp+8] ; тройка тут
hsp.dll:003934F6 call dword ptr [ebp-4]
hsp.dll:003934F9 pop ecx
hsp.dll:003934FA pop ebp
hsp.dll:003934FB retn 24h


Call сюда:

hsp.dll:003934C8 loc_3934C8: ; DATA XREF: hsp.dll:003934D4 o
hsp.dll:003934C8 jmp ds:off_396108


И после jmp мы в оригинальной Hasp.

Haspbc32.dll:0033413E haspbc32_hasp: ; DATA XREF: hsp.dll:off_396108 o
Haspbc32.dll:0033413E push ebp
Haspbc32.dll:0033413F mov ebp, esp
Haspbc32.dll:00334141 push dword ptr [ebp+28h]
Haspbc32.dll:00334144 push dword ptr [ebp+24h]
Haspbc32.dll:00334147 push dword ptr [ebp+20h]
Haspbc32.dll:0033414A push dword ptr [ebp+1Ch]
Haspbc32.dll:0033414D push dword ptr [ebp+18h]
Haspbc32.dll:00334150 push dword ptr [ebp+14h]
Haspbc32.dll:00334153 push dword ptr [ebp+10h]
Haspbc32.dll:00334156 push dword ptr [ebp+0Ch]
Haspbc32.dll:00334159 push dword ptr [ebp+8] ; тройка опять тут…
Haspbc32.dll:0033415C call near ptr unk_331120
Haspbc32.dll:00334161 add esp, 24h
Haspbc32.dll:00334164 pop ebp
Haspbc32.dll:00334165 retn 24h


Всё работает…

Конечно для меня так и осталось загадкой почему не сработал изначальный вариант, ведь вроде не было грубых ошибок ?

procedure _msg(a1,a2,a3,a4,a5,a6,a7,a8,a9:longint); stdcall;
begin
hasp(a1,a2,a3,a4,a5,a6,a7,a8,a9);
end;


Я предполагал, что такая конструкция сама собой предполагает корректную передачу параметров, но выходит, ошибался…

Спасибо всем, кто пытался помочь ! Тему не закрываю, дабы дать возможность высказаться тем, кто знает в чём была ошибка…

p.s. Если модераторов не затруднит, прошу подредактировать название топика и добавить пропущенное. Предполагалось так: Пишу переходник процедуры hasp, при входе в процедуру всё умирает...



Ранг: 24.9 (новичок)
Активность: 0.010
Статус: Участник

Создано: 24 февраля 2007 00:31
· Личное сообщение · #8

ToBad пишет:
procedure Hasp(a1,a2,a3,a4,a5,a6,a7,a8,a9:dword); external 'Haspbc32.dll' name 'hasp';
procedure _msg(a1,a2,a3,a4,a5,a6,a7,a8,a9:dword); stdcall;


Правильно будет:
procedure Hasp(a1,a2,a3,a4,a5,a6,a7,a8,a9:dword); ); stdcall; external 'Haspbc32.dll' name 'hasp';
procedure _msg(a1,a2,a3,a4,a5,a6,a7,a8,a9:dword); stdcall;
или
procedure Hasp(a1,a2,a3,a4,a5,a6,a7,a8,a9:dword); ); external 'Haspbc32.dll' name 'hasp';
procedure _msg(a1,a2,a3,a4,a5,a6,a7,a8,a9:dword);

stdcall – это в какой последовательности запихивать a1…a9 в стек




Ранг: 450.3 (мудрец), 13thx
Активность: 0.20
Статус: Участник

Создано: 24 февраля 2007 00:50 · Поправил: ToBad
· Личное сообщение · #9

Xserg - не много не понял, чем мой вариант в твоём посте отличается от твоего второго. За исключением лишних скобок ? Эта конструкция:

procedure Hasp(a1,a2,a3,a4,a5,a6,a7,a8,a9:dword); ); stdcall; external 'Haspbc32.dll' name 'hasp';

Работает как нужно ! Теперь можно писать:

procedure _msg(a1,a2,a3,a4,a5,a6,a7,a8,a9:dword); stdcall;
begin
hasp(a1,a2,a3,a4,a5,a6,a7,a8,a9);
end;


И в отладчике будет это:

hsp.dll:003934D0 hsp__msg:
hsp.dll:003934D0 push ebp
hsp.dll:003934D1 mov ebp, esp
hsp.dll:003934D3 mov eax, [ebp+28h]
hsp.dll:003934D6 push eax
hsp.dll:003934D7 mov eax, [ebp+24h]
hsp.dll:003934DA push eax
hsp.dll:003934DB mov eax, [ebp+20h]
hsp.dll:003934DE push eax
hsp.dll:003934DF mov eax, [ebp+1Ch]
hsp.dll:003934E2 push eax
hsp.dll:003934E3 mov eax, [ebp+18h]
hsp.dll:003934E6 push eax
hsp.dll:003934E7 mov eax, [ebp+14h]
hsp.dll:003934EA push eax
hsp.dll:003934EB mov eax, [ebp+10h]
hsp.dll:003934EE push eax
hsp.dll:003934EF mov eax, [ebp+0Ch]
hsp.dll:003934F2 push eax
hsp.dll:003934F3 mov eax, [ebp+8]
hsp.dll:003934F6 push eax
hsp.dll:003934F7 call near ptr unk_3934C8
hsp.dll:003934FC pop ebp
hsp.dll:003934FD retn 24h


Параметры передаются правильно и в полном объёме, а не через регистры как у меня в первом посте...
Xserg - Спасибо !



Ранг: 38.9 (посетитель)
Активность: 0.010
Статус: Участник

Создано: 24 февраля 2007 01:53
· Личное сообщение · #10

Для передачи параметров черес стек в дельфях используй:
Напимер
function _SLM_CreateManager(arg1, arg2, arg3, arg4, arg5: DWORD):DWORD; cdecl; external '_sanctuarylib.dll' name 'SLM_CreateManager';


cdtcl




Ранг: 450.3 (мудрец), 13thx
Активность: 0.20
Статус: Участник

Создано: 25 февраля 2007 07:16
· Личное сообщение · #11

TretS пишет:
Для передачи параметров через стек в дельфях используй: cdtcl


Спасибо !

Во всём разобрался, тему закрываю, всем ещё раз огромное спасибо за помощь !


 eXeL@B —› Программирование —› Пишу переходник процедуры hasp, входе процедуру всё умирает...
Эта тема закрыта. Ответы больше не принимаются.
   Для печати Для печати