type
TCharRec = record
X, Y: Char;
end;
function MyHostFunc(const U, V: TCharRec): String; stdcall;
begin
result := U.X + V.Y;
end;
var
R: TCharRec;
S: String;
begin
R.X := 'a';
R.Y := 'b';
PaxInvoke1.Address := @ MyHostFunc;
PaxInvoke1.This := nil; // this is not a method
PaxInvoke1.ClearArguments;
PaxInvoke1.AddArgAsRecord(R, SizeOf(R));
PaxInvoke1.AddArgAsRecord(R, SizeOf(R));
PaxInvoke1.SetResultAsAnsiString;
PaxInvoke1.CallConv := _ccSTDCALL;
PaxInvoke1.CallHost; // call host-defined function
S := String(PaxInvoke1.GetResultPtr^);
ShowMessage(S);
PaxInvoke1.ClearResult;
function TForm1.MyHostMethod(const X, Y: ShortString; Z: Integer): String;
begin
result := X + Y + IntToStr(Z);
end;
procedure TForm1.Button3Click(Sender: TObject);
begin
PaxInvoke1.Address := @ TForm1.MyHostMethod;
PaxInvoke1.This := Self; // we call a method
PaxInvoke1.ClearArguments;
PaxInvoke1.AddArgAsShortString('xyz');
PaxInvoke1.AddArgAsShortString('uv');
PaxInvoke1.AddArgAsInteger(8);
PaxInvoke1.SetResultAsAnsiString;
PaxInvoke1.CallConv := _ccREGISTER;
PaxInvoke1.CallHost;
ShowMessage(String(PaxInvoke1.GetResultPtr^));
PaxInvoke1.ClearResult;
end;
// Point __msfastcall ret_struct(int x, int y, int z);
type
TMyPoint = record
x, y, z: Integer;
end;
var
r: TMyPoint;
begin
PaxInvoke1.This := nil; // this is not a method
PaxInvoke1.CallConv := _ccMSFASTCALL;
PaxInvoke1.LoadAddress('CppDll.dll', 'ret_struct');
PaxInvoke1.ClearArguments;
PaxInvoke1.AddArgAsInteger(2);
PaxInvoke1.AddArgAsInteger(3);
PaxInvoke1.AddArgAsInteger(5);
PaxInvoke1.SetResultAsRecord(SizeOf(TMyPoint));
PaxInvoke1.CallHost; // call dll-defined function
r := TMyPoint(PaxInvoke1.GetResultPtr^);
ShowMessage(IntToStr(r.x) + ' ' + IntToStr(r.y) + ' ' + IntToStr(r.z));
end;
uses
IMPORT_SysUtils;
procedure Print(const S: String);
begin
ShowMessage(S);
end;
var
H_MyFunc: Integer;
I: Integer;
P: Pointer;
begin
{$O-}
PaxCompiler1.Reset;
PaxCompiler1.RegisterLanguage(PaxPascalLanguage1);
PaxCompiler1.RegisterHeader(0, 'procedure Print(const S: String);', @Print);
PaxCompiler1.AddModule('1', PaxPascalLanguage1.LanguageName);
PaxCompiler1.AddCode('1', 'uses SysUtils;');
PaxCompiler1.AddCode('1', 'function MyFunc(U, V: Integer): Currency; cdecl;');
PaxCompiler1.AddCode('1', 'begin');
PaxCompiler1.AddCode('1', ' try');
PaxCompiler1.AddCode('1', ' result := U / V;');
PaxCompiler1.AddCode('1', ' except');
PaxCompiler1.AddCode('1', ' on E: Exception do');
PaxCompiler1.AddCode('1', ' begin');
PaxCompiler1.AddCode('1', ' print(E.Message);');
PaxCompiler1.AddCode('1', ' result := 7;');
PaxCompiler1.AddCode('1', ' end;');
PaxCompiler1.AddCode('1', ' end;');
PaxCompiler1.AddCode('1', 'end;');
PaxCompiler1.AddCode('1', 'begin');
PaxCompiler1.AddCode('1', 'end.');
if PaxCompiler1.Compile(PaxProgram1) then
begin
H_MyFunc := PaxCompiler1.GetHandle(0, 'MyFunc', true);
P := PaxProgram1.GetAddress(H_MyFunc); // get address of script-defined function
PaxInvoke1.Address := P;
PaxInvoke1.This := nil; // this is not a method, but global function.
PaxInvoke1.ClearArguments;
PaxInvoke1.AddArgAsInteger(8);
PaxInvoke1.AddArgAsInteger(2);
PaxInvoke1.SetResultAsCurrency;
PaxInvoke1.CallConv := _ccCDECL;
PaxProgram1.SetEntryPoint(PaxInvoke1);
PaxProgram1.Run;
ShowMessage(CurrToStr(Currency(PaxInvoke1.GetResultPtr^)));
end
else
for I:=0 to PaxCompiler1.ErrorCount do
ShowMessage(PaxCompiler1.ErrorMessage[I]);
end;