A float parameter of a stackless generator arrives as its bit pattern
function G(d: Double): Double; generator; stackless;
begin
WriteLn(d:0:2); // 4612811918334230528.00
yield d; // the loop variable got the bit pattern
end;
Mechanism
A generator instance slot is one Int64 word, written with
SlSet(g, off, v: Int64) and read with SlGet. A Double stored that way is
converted to an integer on the way in and back on the way out. The caller stored
arguments that way, the step saved and restored locals that way, and the yield
published the element that way.
Fix
In pasparser_stmt.inc, float slots are copied bitwise at their own width
(SLFloatSlotBytes: 4 for Single, 8 otherwise):
GenSeedArgseeds a float argument through a temp of the parameter's kind, thenSlBlob. The temp also converts an integer argument, as a plain call would.SLSaveLocalsandSLRestoreLocalsuseSlBlobandSlUnblob.SLLowerYieldblobs a float element into the CURRENT word, and theforconsumer unblobs it into a temp of the element kind, then assigns.- Nil Python's
PyBuildGeneratorValueseeds throughGenSeedArg.
Test
test/test_stackless_float_param_and_element.pas: a row in test-core and rows
in test-i386, test-aarch64 and test-arm32. riscv32 was also measured. Measured wrong with pin v446 (stable_linux_amd64/default/stable_pinned) on 2026-09-28.