From aeb08cb2cd05d6c4c969f3c83c088e45812b432a Mon Sep 17 00:00:00 2001 From: 0-v-0 Date: Fri, 12 Jul 2024 17:25:15 +0800 Subject: [PATCH] refactor longdouble.d (#16680) * refactor longdouble.d * reduce duplicative code * fix error --- compiler/src/dmd/root/longdouble.d | 144 +++++++++++++---------------- 1 file changed, 62 insertions(+), 82 deletions(-) diff --git a/compiler/src/dmd/root/longdouble.d b/compiler/src/dmd/root/longdouble.d index bf203bbcacf0..64ea0460e9bb 100644 --- a/compiler/src/dmd/root/longdouble.d +++ b/compiler/src/dmd/root/longdouble.d @@ -170,25 +170,23 @@ nothrow @nogc pure: T opCast(T)() const @trusted { static if (is(T == bool)) return mantissa != 0 || (exp_sign & 0x7fff) != 0; - else static if (is(T == byte)) return cast(T)ld_read(&this); - else static if (is(T == ubyte)) return cast(T)ld_read(&this); - else static if (is(T == short)) return cast(T)ld_read(&this); - else static if (is(T == ushort)) return cast(T)ld_read(&this); - else static if (is(T == int)) return cast(T)ld_read(&this); - else static if (is(T == uint)) return cast(T)ld_read(&this); - else static if (is(T == float)) return cast(T)ld_read(&this); - else static if (is(T == double)) return cast(T)ld_read(&this); + else static if (is(T == byte) || is(T == ubyte) || + is(T == short) || is(T == ushort) || + is(T == int) || is(T == uint)) + return cast(T)ld_read(&this); + else static if (is(T == float) || is(T == double)) + return cast(T)ld_read(&this); else static if (is(T == long)) return ld_readll(&this); else static if (is(T == ulong)) return ld_readull(&this); else static if (is(T == real)) { // convert to front end real if built with dmd - if (real.sizeof > 8) + static if (real.sizeof > 8) return *cast(real*)&this; else return ld_read(&this); } - else static assert(false, "usupported type"); + else static assert(false, "unsupported type"); } } @@ -217,24 +215,18 @@ version(LDC) extern(D): private: - string fld_arg (string arg)() { return `__asm("fldt $0", "*m,~{st}", &` ~ arg ~ `);`; } - string fstp_arg (string arg)() { return `__asm("fstpt $0", "=*m,~{st}", &` ~ arg ~ `);`; } - string fld_parg (string arg)() { return `__asm("fldt $0", "*m,~{st}", ` ~ arg ~ `);`; } - string fstp_parg(string arg)() { return `__asm("fstpt $0", "=*m,~{st}", ` ~ arg ~ `);`; } + enum fld_arg(string arg) = `__asm("fldt $0", "*m,~{st}", &` ~ arg ~ `);`; + enum fstp_arg(string arg) = `__asm("fstpt $0", "=*m,~{st}", &` ~ arg ~ `);`; + enum fld_parg(string arg) = `__asm("fldt $0", "*m,~{st}", ` ~ arg ~ `);`; + enum fstp_parg(string arg) = `__asm("fstpt $0", "=*m,~{st}", ` ~ arg ~ `);`; } else version(D_InlineAsm_X86_64) { // longdouble_soft passed by reference extern(D): private: - string fld_arg(string arg)() - { - return "asm nothrow @nogc pure @trusted { mov RAX, " ~ arg ~ "; fld real ptr [RAX]; }"; - } - string fstp_arg(string arg)() - { - return "asm nothrow @nogc pure @trusted { mov RAX, " ~ arg ~ "; fstp real ptr [RAX]; }"; - } + enum fld_arg(string arg) = "asm nothrow @nogc pure @trusted { mov RAX, " ~ arg ~ "; fld real ptr [RAX]; }"; + enum fstp_arg(string arg) = "asm nothrow @nogc pure @trusted { mov RAX, " ~ arg ~ "; fstp real ptr [RAX]; }"; alias fld_parg = fld_arg; alias fstp_parg = fstp_arg; } @@ -243,22 +235,10 @@ else version(D_InlineAsm_X86) // longdouble_soft passed by value extern(D): private: - string fld_arg(string arg)() - { - return "asm nothrow @nogc pure @trusted { lea EAX, " ~ arg ~ "; fld real ptr [EAX]; }"; - } - string fstp_arg(string arg)() - { - return "asm nothrow @nogc pure @trusted { lea EAX, " ~ arg ~ "; fstp real ptr [EAX]; }"; - } - string fld_parg(string arg)() - { - return "asm nothrow @nogc pure @trusted { mov EAX, " ~ arg ~ "; fld real ptr [EAX]; }"; - } - string fstp_parg(string arg)() - { - return "asm nothrow @nogc pure @trusted { mov EAX, " ~ arg ~ "; fstp real ptr [EAX]; }"; - } + enum fld_arg(string arg) = "asm nothrow @nogc pure @trusted { lea EAX, " ~ arg ~ "; fld real ptr [EAX]; }"; + enum fstp_arg(string arg) = "asm nothrow @nogc pure @trusted { lea EAX, " ~ arg ~ "; fstp real ptr [EAX]; }"; + enum fld_parg(string arg) = "asm nothrow @nogc pure @trusted { mov EAX, " ~ arg ~ "; fld real ptr [EAX]; }"; + enum fstp_parg(string arg) = "asm nothrow @nogc pure @trusted { mov EAX, " ~ arg ~ "; fstp real ptr [EAX]; }"; } double ld_read(const longdouble_soft* pthis) @@ -266,7 +246,7 @@ double ld_read(const longdouble_soft* pthis) double res; version(AsmX86) { - mixin(fld_parg!("pthis")); + mixin(fld_parg!"pthis"); asm nothrow @nogc pure @trusted { fstp res; @@ -320,7 +300,7 @@ void ld_set(longdouble_soft* pthis, double d) { fld d; } - mixin(fstp_parg!("pthis")); + mixin(fstp_parg!"pthis"); } } @@ -332,7 +312,7 @@ void ld_setll(longdouble_soft* pthis, long d) { fild qword ptr d; } - mixin(fstp_parg!("pthis")); + mixin(fstp_parg!"pthis"); } } @@ -342,13 +322,13 @@ void ld_setull(longdouble_soft* pthis, ulong d) version(AsmX86) { auto pTwoPow63 = &twoPow63; - mixin(fld_parg!("pTwoPow63")); + mixin(fld_parg!"pTwoPow63"); asm nothrow @nogc pure @trusted { fild qword ptr d; faddp; } - mixin(fstp_parg!("pthis")); + mixin(fstp_parg!"pthis"); } } @@ -361,13 +341,13 @@ longdouble_soft ldexpl(longdouble_soft ld, int exp) { fild dword ptr exp; } - mixin(fld_arg!("ld")); + mixin(fld_arg!"ld"); asm nothrow @nogc pure @trusted { fscale; // ST(0) = ST(0) * (2**ST(1)) fstp ST(1); } - mixin(fstp_arg!("ld")); + mixin(fstp_arg!"ld"); } return ld; } @@ -377,13 +357,13 @@ longdouble_soft ld_add(longdouble_soft ld1, longdouble_soft ld2) { version(AsmX86) { - mixin(fld_arg!("ld1")); - mixin(fld_arg!("ld2")); + mixin(fld_arg!"ld1"); + mixin(fld_arg!"ld2"); asm nothrow @nogc pure @trusted { fadd; } - mixin(fstp_arg!("ld1")); + mixin(fstp_arg!"ld1"); } return ld1; } @@ -392,13 +372,13 @@ longdouble_soft ld_sub(longdouble_soft ld1, longdouble_soft ld2) { version(AsmX86) { - mixin(fld_arg!("ld1")); - mixin(fld_arg!("ld2")); + mixin(fld_arg!"ld1"); + mixin(fld_arg!"ld2"); asm nothrow @nogc pure @trusted { fsub; } - mixin(fstp_arg!("ld1")); + mixin(fstp_arg!"ld1"); } return ld1; } @@ -407,13 +387,13 @@ longdouble_soft ld_mul(longdouble_soft ld1, longdouble_soft ld2) { version(AsmX86) { - mixin(fld_arg!("ld1")); - mixin(fld_arg!("ld2")); + mixin(fld_arg!"ld1"); + mixin(fld_arg!"ld2"); asm nothrow @nogc pure @trusted { fmul; } - mixin(fstp_arg!("ld1")); + mixin(fstp_arg!"ld1"); } return ld1; } @@ -422,13 +402,13 @@ longdouble_soft ld_div(longdouble_soft ld1, longdouble_soft ld2) { version(AsmX86) { - mixin(fld_arg!("ld1")); - mixin(fld_arg!("ld2")); + mixin(fld_arg!"ld1"); + mixin(fld_arg!"ld2"); asm nothrow @nogc pure @trusted { fdiv; } - mixin(fstp_arg!("ld1")); + mixin(fstp_arg!"ld1"); } return ld1; } @@ -439,8 +419,8 @@ bool ld_cmpb(longdouble_soft x, longdouble_soft y) bool res; version(AsmX86) { - mixin(fld_arg!("y")); - mixin(fld_arg!("x")); + mixin(fld_arg!"y"); + mixin(fld_arg!"x"); asm nothrow @nogc pure @trusted { fucomip ST(1); @@ -460,8 +440,8 @@ bool ld_cmpbe(longdouble_soft x, longdouble_soft y) bool res; version(AsmX86) { - mixin(fld_arg!("y")); - mixin(fld_arg!("x")); + mixin(fld_arg!"y"); + mixin(fld_arg!"x"); asm nothrow @nogc pure @trusted { fucomip ST(1); @@ -481,8 +461,8 @@ bool ld_cmpa(longdouble_soft x, longdouble_soft y) bool res; version(AsmX86) { - mixin(fld_arg!("y")); - mixin(fld_arg!("x")); + mixin(fld_arg!"y"); + mixin(fld_arg!"x"); asm nothrow @nogc pure @trusted { fucomip ST(1); @@ -502,8 +482,8 @@ bool ld_cmpae(longdouble_soft x, longdouble_soft y) bool res; version(AsmX86) { - mixin(fld_arg!("y")); - mixin(fld_arg!("x")); + mixin(fld_arg!"y"); + mixin(fld_arg!"x"); asm nothrow @nogc pure @trusted { fucomip ST(1); @@ -523,8 +503,8 @@ bool ld_cmpe(longdouble_soft x, longdouble_soft y) bool res; version(AsmX86) { - mixin(fld_arg!("y")); - mixin(fld_arg!("x")); + mixin(fld_arg!"y"); + mixin(fld_arg!"x"); asm nothrow @nogc pure @trusted { fucomip ST(1); @@ -544,8 +524,8 @@ bool ld_cmpne(longdouble_soft x, longdouble_soft y) bool res; version(AsmX86) { - mixin(fld_arg!("y")); - mixin(fld_arg!("x")); + mixin(fld_arg!"y"); + mixin(fld_arg!"x"); asm nothrow @nogc pure @trusted { fucomip ST(1); @@ -566,8 +546,8 @@ int ld_cmp(longdouble_soft x, longdouble_soft y) int res; version(AsmX86) { - mixin(fld_arg!("y")); - mixin(fld_arg!("x")); + mixin(fld_arg!"y"); + mixin(fld_arg!"x"); asm nothrow @nogc pure @trusted { fucomip ST(1); @@ -600,12 +580,12 @@ longdouble_soft sqrtl(longdouble_soft ld) { version(AsmX86) { - mixin(fld_arg!("ld")); + mixin(fld_arg!"ld"); asm nothrow @nogc pure @trusted { fsqrt; } - mixin(fstp_arg!("ld")); + mixin(fstp_arg!"ld"); } return ld; } @@ -616,12 +596,12 @@ longdouble_soft sinl (longdouble_soft ld) { version(AsmX86) { - mixin(fld_arg!("ld")); + mixin(fld_arg!"ld"); asm nothrow @nogc pure @trusted { fsin; // exact for |x|<=PI/4 } - mixin(fstp_arg!("ld")); + mixin(fstp_arg!"ld"); } return ld; } @@ -629,12 +609,12 @@ longdouble_soft cosl (longdouble_soft ld) { version(AsmX86) { - mixin(fld_arg!("ld")); + mixin(fld_arg!"ld"); asm nothrow @nogc pure @trusted { fcos; // exact for |x|<=PI/4 } - mixin(fstp_arg!("ld")); + mixin(fstp_arg!"ld"); } return ld; } @@ -642,13 +622,13 @@ longdouble_soft tanl (longdouble_soft ld) { version(AsmX86) { - mixin(fld_arg!("ld")); + mixin(fld_arg!"ld"); asm nothrow @nogc pure @trusted { fptan; fstp ST(0); // always 1 } - mixin(fstp_arg!("ld")); + mixin(fstp_arg!"ld"); } return ld; } @@ -663,8 +643,8 @@ longdouble_soft ld_mod(longdouble_soft x, longdouble_soft y) short sw; version(AsmX86) { - mixin(fld_arg!("y")); - mixin(fld_arg!("x")); + mixin(fld_arg!"y"); + mixin(fld_arg!"x"); asm nothrow @nogc pure @trusted { FM1: // We don't use fprem1 because for some inexplicable @@ -677,7 +657,7 @@ longdouble_soft ld_mod(longdouble_soft x, longdouble_soft y) jp FM1; // continue till ST < ST1 fstp ST(1); // leave remainder on stack } - mixin(fstp_arg!("x")); + mixin(fstp_arg!"x"); } return x; }