From 896aa2b266284155999ff0c03583c4440de97510 Mon Sep 17 00:00:00 2001 From: Qiao Pengcheng Date: Sun, 28 Apr 2024 11:45:49 +0800 Subject: [PATCH 1/4] fixed the split error for LoongArch64. --- src/coreclr/jit/codegencommon.cpp | 20 ++++++++++++++------ 1 file changed, 14 insertions(+), 6 deletions(-) diff --git a/src/coreclr/jit/codegencommon.cpp b/src/coreclr/jit/codegencommon.cpp index c3608402d27ec..b914f0c93bfd7 100644 --- a/src/coreclr/jit/codegencommon.cpp +++ b/src/coreclr/jit/codegencommon.cpp @@ -4119,7 +4119,7 @@ void CodeGen::genEnregisterOSRArgsAndLocals() } } -#if defined(SWIFT_SUPPORT) || defined(TARGET_RISCV64) +#if defined(SWIFT_SUPPORT) || defined(TARGET_RISCV64) || defined(TARGET_LOONGARCH64) //----------------------------------------------------------------------------- // genHomeSwiftStructParameters: Move the incoming segment to the local stack frame. // @@ -4159,8 +4159,16 @@ void CodeGen::genHomeStackSegment(unsigned lclNum, } emitAttr size = emitTypeSize(loadType); - int loadOffset = - -(isFramePointerUsed() ? genCallerSPtoFPdelta() : genCallerSPtoInitialSPdelta()) + (int)seg.GetStackOffset(); + int loadOffset; + if (isFramePointerUsed()) + { + loadOffset = -genCallerSPtoFPdelta(); + } + else + { + loadOffset = -(int)seg.GetStackOffset() - genCallerSPtoInitialSPdelta(); + } + #ifdef TARGET_XARCH GetEmitter()->emitIns_R_AR(ins_Load(loadType), size, initReg, genFramePointerReg(), loadOffset); #else @@ -4171,7 +4179,7 @@ void CodeGen::genHomeStackSegment(unsigned lclNum, if (initRegStillZeroed) *initRegStillZeroed = false; } -#endif // defined(SWIFT_SUPPORT) || defined(TARGET_RISCV64) +#endif // defined(SWIFT_SUPPORT) || defined(TARGET_RISCV64) || defined(TARGET_LOONGARCH64) #ifdef SWIFT_SUPPORT @@ -4248,7 +4256,7 @@ void CodeGen::genHomeSwiftStructParameters(bool handleStack) // void CodeGen::genHomeStackPartOfSplitParameter(regNumber initReg, bool* initRegStillZeroed) { -#ifdef TARGET_RISCV64 +#if defined(TARGET_RISCV64) || defined(TARGET_LOONGARCH64) unsigned lclNum = 0; for (; lclNum < compiler->info.compArgsCount; lclNum++) { @@ -4273,7 +4281,7 @@ void CodeGen::genHomeStackPartOfSplitParameter(regNumber initReg, bool* initRegS } break; } -#endif +#endif // TARGET_RISCV64 || TARGET_LOONGARCH64 } /*----------------------------------------------------------------------------- From 3bf26c94ce475f397624e7c9f22eb9458e5073a2 Mon Sep 17 00:00:00 2001 From: Qiao Pengcheng Date: Sun, 28 Apr 2024 16:02:21 +0800 Subject: [PATCH 2/4] amend code for CRs. --- src/coreclr/jit/codegencommon.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/coreclr/jit/codegencommon.cpp b/src/coreclr/jit/codegencommon.cpp index b914f0c93bfd7..a1f7f5e8a8be1 100644 --- a/src/coreclr/jit/codegencommon.cpp +++ b/src/coreclr/jit/codegencommon.cpp @@ -4159,14 +4159,14 @@ void CodeGen::genHomeStackSegment(unsigned lclNum, } emitAttr size = emitTypeSize(loadType); - int loadOffset; + int loadOffset = (int)seg.GetStackOffset(); if (isFramePointerUsed()) { - loadOffset = -genCallerSPtoFPdelta(); + loadOffset -= genCallerSPtoFPdelta(); } else { - loadOffset = -(int)seg.GetStackOffset() - genCallerSPtoInitialSPdelta(); + loadOffset -= genCallerSPtoInitialSPdelta(); } #ifdef TARGET_XARCH From 6bf9d1776431b0bdb9d07262ab9bb4f258ba1895 Mon Sep 17 00:00:00 2001 From: Qiao Pengcheng Date: Sun, 28 Apr 2024 18:01:29 +0800 Subject: [PATCH 3/4] amend the splitting's judge independent of the `var->lvIsSplit` which will be delete in future. --- src/coreclr/jit/abi.cpp | 12 ++++------- src/coreclr/jit/codegencommon.cpp | 35 +++++++++++++++++++------------ 2 files changed, 26 insertions(+), 21 deletions(-) diff --git a/src/coreclr/jit/abi.cpp b/src/coreclr/jit/abi.cpp index 7a594f77f3912..7b62dfb0b12a2 100644 --- a/src/coreclr/jit/abi.cpp +++ b/src/coreclr/jit/abi.cpp @@ -258,16 +258,12 @@ bool ABIPassingInformation::HasExactlyOneStackSegment() const // bool ABIPassingInformation::IsSplitAcrossRegistersAndStack() const { - if (NumSegments < 2) - return false; - - bool isFirstInReg = Segments[0].IsPassedInRegister(); - for (unsigned i = 1; i < NumSegments; i++) + if (NumSegments != 2) { - if (isFirstInReg != Segments[i].IsPassedInRegister()) - return true; + return false; } - return false; + + return Segments[0].IsPassedInRegister() && Segments[1].IsPassedOnStack(); } //----------------------------------------------------------------------------- diff --git a/src/coreclr/jit/codegencommon.cpp b/src/coreclr/jit/codegencommon.cpp index a1f7f5e8a8be1..6bde561049ee9 100644 --- a/src/coreclr/jit/codegencommon.cpp +++ b/src/coreclr/jit/codegencommon.cpp @@ -4261,25 +4261,34 @@ void CodeGen::genHomeStackPartOfSplitParameter(regNumber initReg, bool* initRegS for (; lclNum < compiler->info.compArgsCount; lclNum++) { LclVarDsc* var = compiler->lvaGetDesc(lclNum); - if (!var->lvIsSplit || !var->lvOnFrame) + if (!var->lvOnFrame || !varTypeIsStruct(var)) + { continue; + } - JITDUMP("Homing stack part of split parameter V%02u\n", lclNum); - - assert(varTypeIsStruct(var)); - assert(!compiler->lvaIsImplicitByRefLocal(lclNum)); const ABIPassingInformation& abiInfo = compiler->lvaGetParameterABIInfo(lclNum); - assert(abiInfo.NumSegments == 2); - assert(abiInfo.Segments[0].GetRegister() == REG_ARG_LAST); - const ABIPassingSegment& seg = abiInfo.Segments[1]; + if (abiInfo.IsSplitAcrossRegistersAndStack()) + { + assert(var->lvIsSplit); + JITDUMP("Homing stack part of split parameter V%02u\n", lclNum); - genHomeStackSegment(lclNum, seg, initReg, initRegStillZeroed); + assert(abiInfo.NumSegments == 2); + assert(abiInfo.Segments[0].GetRegister() == REG_ARG_LAST); + assert(abiInfo.Segments[1].GetStackOffset() == 0); + const ABIPassingSegment& seg = abiInfo.Segments[1]; - for (lclNum += 1; lclNum < compiler->info.compArgsCount; lclNum++) - { - assert(!compiler->lvaGetDesc(lclNum)->lvIsSplit); // There should be only one split parameter + genHomeStackSegment(lclNum, seg, initReg, initRegStillZeroed); + +#ifdef DEBUG + for (lclNum += 1; lclNum < compiler->info.compArgsCount; lclNum++) + { + abiInfo = compiler->lvaGetParameterABIInfo(lclNum); + // There should be only one split parameter + assert(!abiInfo.IsSplitAcrossRegistersAndStack()); + } +#endif + break; } - break; } #endif // TARGET_RISCV64 || TARGET_LOONGARCH64 } From 6b223d32685cb64e18d572b08d8ca17546dfff45 Mon Sep 17 00:00:00 2001 From: Qiao Pengcheng Date: Mon, 29 Apr 2024 09:20:16 +0800 Subject: [PATCH 4/4] revert `IsSplitAcrossRegistersAndStack()`. --- src/coreclr/jit/abi.cpp | 12 ++++++++++-- src/coreclr/jit/codegencommon.cpp | 4 ++-- 2 files changed, 12 insertions(+), 4 deletions(-) diff --git a/src/coreclr/jit/abi.cpp b/src/coreclr/jit/abi.cpp index 7b62dfb0b12a2..7fa39d0464434 100644 --- a/src/coreclr/jit/abi.cpp +++ b/src/coreclr/jit/abi.cpp @@ -258,12 +258,20 @@ bool ABIPassingInformation::HasExactlyOneStackSegment() const // bool ABIPassingInformation::IsSplitAcrossRegistersAndStack() const { - if (NumSegments != 2) + if (NumSegments < 2) { return false; } - return Segments[0].IsPassedInRegister() && Segments[1].IsPassedOnStack(); + bool isFirstInReg = Segments[0].IsPassedInRegister(); + for (unsigned i = 1; i < NumSegments; i++) + { + if (isFirstInReg != Segments[i].IsPassedInRegister()) + { + return true; + } + } + return false; } //----------------------------------------------------------------------------- diff --git a/src/coreclr/jit/codegencommon.cpp b/src/coreclr/jit/codegencommon.cpp index 6bde561049ee9..301b10b1de071 100644 --- a/src/coreclr/jit/codegencommon.cpp +++ b/src/coreclr/jit/codegencommon.cpp @@ -4282,9 +4282,9 @@ void CodeGen::genHomeStackPartOfSplitParameter(regNumber initReg, bool* initRegS #ifdef DEBUG for (lclNum += 1; lclNum < compiler->info.compArgsCount; lclNum++) { - abiInfo = compiler->lvaGetParameterABIInfo(lclNum); + const ABIPassingInformation& abiInfo2 = compiler->lvaGetParameterABIInfo(lclNum); // There should be only one split parameter - assert(!abiInfo.IsSplitAcrossRegistersAndStack()); + assert(!abiInfo2.IsSplitAcrossRegistersAndStack()); } #endif break;