Méthode de l'objet d'appel à l'aide d'ASM
-
13-11-2019 - |
Question
Pour mieux expliquer ce que j'essaie d'accomplir, je vais commencer par quelque chose qui fonctionne.
Disons que nous avons une procédure qui peut appeler une autre procédure et lui passer un paramètre de chaîne:
procedure CallSaySomething(AProc: Pointer; const AValue: string);
var
LAddr: Integer;
begin
LAddr := Integer(PChar(AValue));
asm
MOV EAX, LAddr
CALL AProc;
end;
end;
C'est la procédure que nous appellerons:
procedure SaySomething(const AValue: string);
begin
ShowMessage( AValue );
end;
Maintenant je peux appeler Dis quelquechose Comme ainsi (testé et fonctionne (:):
CallSaySomething(@SaySomething, 'Morning people!');
Ma question est de savoir comment puis-je réaliser des fonctionnalités similaires, mais cette fois Dis quelquechose devrait être un méthode:
type
TMyObj = class
public
procedure SaySomething(const AValue: string); // calls show message by passing AValue
end;
Donc, si vous êtes toujours avec moi ..., mon objectif est d'atteindre une procédure similaire à:
procedure CallMyObj(AObjInstance, AObjMethod: Pointer; const AValue: string);
begin
asm
// here is where I need help...
end;
end;
Je lui ai donné pas mal de plans, mais mes connaissances de l'assemblage sont limitées.
La solution
Quelle est la raison d'utiliser ASM?
Lorsque vous appelez la méthode des objets, le pointeur d'instance doit être le premier paramètre de l'appel de la méthode
program Project1;
{$APPTYPE CONSOLE}
{$R *.res}
uses System.SysUtils;
type
TTest = class
procedure test(x : integer);
end;
procedure TTest.test(x: integer);
begin
writeln(x);
end;
procedure CallObjMethod(data, code : pointer; value : integer);
begin
asm
mov eax, data;
mov edx, value;
call code;
end;
end;
var t : TTest;
begin
t := TTest.Create();
try
CallObjMethod(t, @TTest.test, 2);
except
end;
readln;
end.