x86_64: Fix long double to int cast
Some checks are pending
build and test / test-x86_64-linux (push) Waiting to run
build and test / test-x86_64-osx (push) Waiting to run
build and test / test-aarch64-osx (push) Waiting to run
build and test / test-x86_64-win32 (push) Waiting to run
build and test / test-i386-win32 (push) Waiting to run
build and test / test-arm64-win32 (push) Waiting to run
build and test / test-armv7-linux (push) Waiting to run
build and test / test-aarch64-linux (push) Waiting to run
build and test / test-riscv64-linux (push) Waiting to run
build and test / test-i386-linux (push) Waiting to run

x86_64-gen.c:
- gen_cvt_ftoi()
    Use TOK___fixxfdi for VT_LDOUBLE independently of the size of the
    target integer type, avoiding a wrong conversion to doube.

    This solves:

    int main(void) {
        long double x = 0.999999999999999999l;
        return (int)x;
    }

    Before for VT_INT a long double was first converted to double with
    rounding, possibly leading to a wrong result when truncating with
    cvttsd2si.
This commit is contained in:
Stefan 2026-11-04 13:25:31 +01:00
parent e23dabed15
commit 32d1c0a561

View File

@ -2121,17 +2121,14 @@ void gen_cvt_ftoi(int t)
ft = vtop->type.t;
bt = ft & VT_BTYPE;
if (bt == VT_LDOUBLE) {
if (t != VT_INT) {
vpush_helper_func(TOK___fixxfdi);
vswap();
gfunc_call(1);
vpushi(0);
vtop->r = REG_IRET;
vpush_helper_func(TOK___fixxfdi);
vswap();
gfunc_call(1);
vpushi(0);
vtop->r = REG_IRET;
if (t != VT_INT)
vtop->r2 = REG_IRE2;
return;
}
gen_cvt_ftof(VT_DOUBLE);
bt = VT_DOUBLE;
return;
}
gv(RC_FLOAT);