[Vm-dev] Re: x64 FFI plugin
Eliot Miranda
eliot.miranda at gmail.com
Wed Feb 17 03:41:10 UTC 2016
Hi ALl,
On Mon, Feb 15, 2016 at 8:26 PM, Eliot Miranda <eliot.miranda at gmail.com>
wrote:
> Hi Esteban, Hi All,
>
> I thought I'd help by doing the ThreadedFFIPlugin subclass for x64.
> turns out that the System V x86-64 ABI and the Win64 x86-64 ABI are
> sufficiently different that I'm splitting it across two classes. But in
> doing so I've had a moment of clarity (increasingly rare these days ;-) ).
>
> I've finally realised that Andreas put the type information in the right
> place, and that there is (I think) sufficient type information for structs
> to be parsed correctly.
>
> Andreas puts the type information in the first literal of the method
> containing the FFI call. (There is also an eval form where the function is
> passed in). The point here is that the type information is associated with
> the function, and hence with the function's signature. This is correct.
>
> In VisualWorks a big mistake was made by putting the type information in
> the actual parameter, so if one accidentally passes a parameter of the
> wrong type (types are only checked in debug mode) then it can be marshalled
> incorrectly.
>
> This difference is really important with the System V x86-64 AB, because
> the ABI uses register parameters, 6 integer register args and 8
> floating-point register args, and will pass fields of a struct in available
> registers of either type as available. So if one passes just the following
> structure:
>
> struct foo { long a; double b; long c; double d; long e; double f; long g;
> double h; long i; double j; long k; double l; long m; double n; long o;
> double p; long q; double r; long s; double t; }
>
> to a function declared as (long one, double two, struct foo), a,b,c,d & e
> get passed in integer registers (along with one), and b,d,f,h,j,l & n get
> passed in xmm registers (along with two), while g,i,k,m,n,o,p,q,r,s & t get
> passed on the stack (strange but true).
>
Well I'm horribly embarrassed. I didn't read the spec carefully enough.
It turns out that registers are only used for structs of size 4 eightbytes
(e,g. version 0.99.6, http://www.x86-64.org/documentation/abi.pdf) or 2
eightbytes (e.g. version 0.90, as used on Mac OS X x86_64,
http://people.freebsd.org/~obrien/amd64-elf-abi.pdf). But looking at linux
x86_64 code tehre is no register passing for structures at all. Forgive
the misinformation. And it looks like life is much easier. Nice to get
rid of this baggage.
I had thought that this implies we need to generate machine code specific
> to each signature to efficiently marshall calls. But because the type
> information is flat, easily parsed and specific to each function rather
> than (as in VW) to a particular set of actual parameters, the interpreted
> approach we're currently using should at least be correct. So any
> marshalling code generation can be left as an optimization exercise, rather
> than an explicit requirement to achieve correctness.
>
> I hope to have the ThreadedX64SysVFFIPlugin written and tested before the
> end of the month.
>
> _,,,^..^,,,_
> best, Eliot
>
_,,,^..^,,,_
best, Eliot
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.squeakfoundation.org/pipermail/vm-dev/attachments/20160216/8ea5c765/attachment.htm
More information about the Vm-dev
mailing list