[Vm-dev] Help: Float returns on RISCV
ken.dickey at whidbey.com
ken.dickey at whidbey.com
Wed Jun 29 14:32:12 UTC 2022
Greetings,
I could use some help in how register values are passed in the FFI.
The basic situation is that on RISC-V, simple float/double values are
returned in FA0 (float reg), not A0 (integer reg).
E.g. for unit test:
=======================================
testConstructedDoubleCall
"Test using generic FFI spec"
| result meth |
meth := ExternalLibraryFunction
name:'ffiTestDoubles' module: FFITestLibrary moduleName
callType: 0 returnType: ExternalType double
argumentTypes: ((1 to: 2) collect:[:i| ExternalType double]).
result := meth invokeWithArguments: (Array with: 41 with: true).
self assert: result = 42.0
=======================================
EXPORT(double) ffiTestDoubles(double d1, double d2)
{
printf("The two floats are %f and %f\n", (float)d1, (float)d2);
return d1+d2;
}
Looking at:
ThreadedARM64FFIPlugin>>ffiCalloutTo:SpecOnStack:in:
=======================================
Stepping in GDB
--> ffiCallArgArrayOrNilNumArgs()
..
(floatRet.d =
dispatchFunctionPointerwithwithwithwithwithwithwithwith(...)
At this point, I can single step to ffiTestDoubles(),
the proper values are printed (41,1),
42 is placed in register FA0
But the first value in float.d is _1_ (value presumably from A0).
So I need to set GDB into asm mode and crawl through the C assign to
floatRet.d,
but some theory of operations could help me out here.
Different setup passed to #setReturnRegister:andCall:withArgsArray: ??
Thanks much for help,
-KenD
More information about the Vm-dev
mailing list