diff options
author | Gleb Balykov <g.balykov@samsung.com> | 2020-07-02 17:01:13 +0300 |
---|---|---|
committer | Alexander Soldatov/AI Compiler Lab /SRR/Staff Engineer/Samsung Electronics <soldatov.a@samsung.com> | 2020-07-13 18:08:49 +0300 |
commit | 270f0d63034b0c7ab923766112b6593899a89f62 (patch) | |
tree | 4aa00d13f2d83a72ef5e7f7a20a0ead63e93f6ca /src/jit | |
parent | f1f94f32d098babc4fe9ed877334f402ab57be3a (diff) | |
download | coreclr-270f0d63034b0c7ab923766112b6593899a89f62.tar.gz coreclr-270f0d63034b0c7ab923766112b6593899a89f62.tar.bz2 coreclr-270f0d63034b0c7ab923766112b6593899a89f62.zip |
[Tizen] Support relative indirection for 1st and 2nd levels of vtable on arm64
Diffstat (limited to 'src/jit')
-rw-r--r-- | src/jit/codegencommon.cpp | 21 |
1 files changed, 20 insertions, 1 deletions
diff --git a/src/jit/codegencommon.cpp b/src/jit/codegencommon.cpp index 8725619ceb..3c0d0b600b 100644 --- a/src/jit/codegencommon.cpp +++ b/src/jit/codegencommon.cpp @@ -8479,6 +8479,7 @@ void CodeGen::genFnEpilog(BasicBlock* block) // ... // bx r12 + assert(REG_R12 == REG_INDIRECT_CALL_TARGET_REG); regNumber indCallReg = REG_R12; regNumber vptrReg1 = REG_LR; @@ -8510,6 +8511,24 @@ void CodeGen::genFnEpilog(BasicBlock* block) compiler->unwindBegEpilog(); genPopCalleeSavedRegistersAndFreeLclFrame(jmpEpilog); + + if (jmpEpilog && lastNode->gtOper == GT_JMP && addrInfo.accessType == IAT_RELPVALUE) + { + // TODO-ARM64-CQ: update this! + // IAT_RELPVALUE jump at the end is done using relative indirection, so, + // additional helper register is required. + // REG_IP1 (x17) is always reserved on arm64 (see Compiler::compRsvdRegCheck) + // and is used as a temporary register. Use it as temp register here too. + + assert(REG_IP0 == REG_INDIRECT_CALL_TARGET_REG); + regNumber indCallReg = REG_IP0; + regNumber vptrReg1 = REG_IP1; + + instGen_Set_Reg_To_Imm(EA_HANDLE_CNS_RELOC, indCallReg, (ssize_t)addrInfo.addr); + getEmitter()->emitIns_R_R(INS_mov, EA_PTRSIZE, vptrReg1, indCallReg); + getEmitter()->emitIns_R_R_I(INS_ldr, EA_PTRSIZE, indCallReg, indCallReg, 0); + getEmitter()->emitIns_R_R_R(INS_add, EA_PTRSIZE, indCallReg, indCallReg, vptrReg1); + } #endif // _TARGET_ARM64_ if (jmpEpilog) @@ -8583,7 +8602,7 @@ void CodeGen::genFnEpilog(BasicBlock* block) // LR is used as helper register right before it is restored from stack, thus, // all relative address calculations are performed before LR is restored. callType = emitter::EC_INDIR_R; - indCallReg = REG_R12; + indCallReg = REG_INDIRECT_CALL_TARGET_REG; addr = NULL; regSet.verifyRegUsed(indCallReg); |