[fpc-pascal] Question on Calling Conventions (for: PascalScript on Win x64)

Florian Klämpfl florian at freepascal.org
Wed Sep 5 20:18:58 CEST 2012

Am 05.09.2012 18:27, schrieb Alexander Hofmann:
> Hi there.
> This is a cross-post (cross-mail ?) to
> http://www.lazarus.freepascal.org/index.php/topic,17978.0.html as I got
> the hint there that it might be better to ask on the list instead of in
> the forum, at least concerning the calling conventions - but I'll ask
> the whole lot, anyway; I hope that's ok (and, yes, I made the mistake to
> ask on the Lazarus list before, so I sincerely hope I won't bother the
> wrong people again, sorry)
> Question:
> Is there any difference in the calling convention on x64-Systems between
> Delphi and Lazarus? I could only find the "standard" information on
> Windows x64 calling conventions, without special care of constructors,
> if there is any.

Constructors are not part of the Win x64 ABI so any compiler is free to
pass the hidden parameters needed by a constructor.

> The reason why I'm asking is the following:
> I'm trying to get PascalScript running (completely, it does up to some
> extend) on Win x64. I had to do some changes in x64.inc, see below - but
> as far as I know, that should work - and it does, for all kinds of
> calls, except calling constructors on Components.
> Scripts like the following will crash the Program with a SIGSEGV.
> |program Script;
> var
>   f:TForm;
>   b:TButton;
> begin
>   f:=TForm.CreateNew(nil); //<- Works
>   b:=TButton.Create(f); //<- crash
>   b.Parent:=f;
>   f.Show;
> end.|
> Crash in the Program is here:
> 000000000044F900 4883ec38                 sub    $0x38,%rsp
> 000000000044F904 48895c2420               mov    %rbx,0x20(%rsp)
> 000000000044F909 4889742428               mov    %rsi,0x28(%rsp)
> 000000000044F90E 4889cb                   mov    %rcx,%rbx
> 000000000044F911 4889d6                   mov    %rdx,%rsi
> 000000000044F914 4889da                   mov    %rbx,%rdx
> 000000000044F917 4889f1                   mov    %rsi,%rcx
> 000000000044F91A 4889f0                   mov    %rsi,%rax
> 000000000044F91D 488b00                   mov    (%rax),%rax
> 000000000044F920 ff9068010000             callq  *0x168(%rax)  <-- crash| 
> The same Script runs fine when the Application was compiled with x86
> Lazarus 1.0. By the way: creating a TObject with e.g. o:=TObject.Create
> doesn't break at al.
> Interestingly (and that is how I came to ask about the calling
> conventions), when I start debugging
> <SomeClass>.Create(aOwner:TComponent)-Type of Constructors, there is
> some difference in the Register values, depending on whether the
> Constructor was called from "pure" FPC-Code or the Script (at least so
> it seems):
> o Called from FPC: rcx: 0 (nil), rdx: Class Reference, r8: Value of aOwner
> o Called from Script: rcx: Class Reference, rdx: 1 (!?), r8: Value of
> aOwner (at least so it seems)

You need to adapt PascalScript appropriately then: probably similiar
code to x86.inc:534+ needs to be added to x64.inc around 582.

More information about the fpc-pascal mailing list