Skip to content

Commit bd364ce

Browse files
authored
Clean up JIT<->EE relocations (#121920)
Introduce a `CorInfoReloc` enum and use it exclusively to communicate relocation types between the EE and JIT. Translate it in crossgen2/ILC to the file-format relocation type when necessary. Fix #121878
1 parent 5eca9d9 commit bd364ce

35 files changed

Lines changed: 497 additions & 522 deletions

src/coreclr/inc/corinfo.h

Lines changed: 53 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -852,6 +852,59 @@ enum InfoAccessType
852852
IAT_RELPVALUE // The value needs to be accessed via a relative indirection
853853
};
854854

855+
enum class CorInfoReloc
856+
{
857+
NONE,
858+
859+
// General relocation types
860+
DIRECT, // Direct/absolute pointer sized address
861+
RELATIVE32, // 32-bit relative address from byte following reloc
862+
863+
// Arm64 relocs
864+
ARM64_BRANCH26, // Arm64: B, BL
865+
ARM64_PAGEBASE_REL21, // ADRP
866+
ARM64_PAGEOFFSET_12A, // ADD/ADDS (immediate) with zero shift, for page offset
867+
// Linux arm64
868+
ARM64_LIN_TLSDESC_ADR_PAGE21,
869+
ARM64_LIN_TLSDESC_LD64_LO12,
870+
ARM64_LIN_TLSDESC_ADD_LO12,
871+
ARM64_LIN_TLSDESC_CALL,
872+
// Windows arm64
873+
ARM64_WIN_TLS_SECREL_HIGH12A, // ADD high 12-bit offset for tls
874+
ARM64_WIN_TLS_SECREL_LOW12A, // ADD low 12-bit offset for tls
875+
876+
// Windows x64
877+
AMD64_WIN_SECREL,
878+
879+
// Linux x64
880+
// GD model
881+
AMD64_LIN_TLSGD,
882+
883+
// Arm32 relocs
884+
ARM32_THUMB_BRANCH24, // Thumb2: B, BL
885+
ARM32_THUMB_MOV32, // Thumb2: MOVW/MOVT
886+
// The identifier for ARM32-specific PC-relative address
887+
// computation corresponds to the following instruction
888+
// sequence:
889+
// l0: movw rX, #imm_lo // 4 byte
890+
// l4: movt rX, #imm_hi // 4 byte
891+
// l8: add rX, pc <- after this instruction rX = relocTarget
892+
//
893+
// Program counter at l8 is address of l8 + 4
894+
// Address of relocated movw/movt is l0
895+
// So, imm should be calculated as the following:
896+
// imm = relocTarget - (l8 + 4) = relocTarget - (l0 + 8 + 4) = relocTarget - (l_0 + 12)
897+
// So, the value of offset correction is 12
898+
ARM32_THUMB_MOV32_PCREL, // Thumb2: MOVW/MOVT
899+
900+
// LoongArch64 relocs
901+
LOONGARCH64_PC, // LoongArch64: pcalau12i+imm12
902+
LOONGARCH64_JIR, // LoongArch64: pcaddu18i+jirl
903+
904+
// RISCV64 relocs
905+
RISCV64_PC, // RiscV64: auipc
906+
};
907+
855908
enum CorInfoGCType
856909
{
857910
TYPE_GC_NONE, // no embedded objectrefs
@@ -3399,50 +3452,6 @@ class ICorDynamicInfo : public ICorStaticInfo
33993452
virtual CORINFO_METHOD_HANDLE getSpecialCopyHelper(CORINFO_CLASS_HANDLE type) = 0;
34003453
};
34013454

3402-
/**********************************************************************************/
3403-
3404-
// It would be nicer to use existing IMAGE_REL_XXX constants instead of defining our own here...
3405-
#define IMAGE_REL_BASED_REL32 0x10
3406-
#define IMAGE_REL_BASED_THUMB_BRANCH24 0x13
3407-
#define IMAGE_REL_SECREL 0x104
3408-
3409-
// Linux x64
3410-
// GD model
3411-
#define IMAGE_REL_TLSGD 0x105
3412-
3413-
// Linux arm64
3414-
// TLSDESC (dynamic)
3415-
#define IMAGE_REL_AARCH64_TLSDESC_ADR_PAGE21 0x107
3416-
#define IMAGE_REL_AARCH64_TLSDESC_LD64_LO12 0x108
3417-
#define IMAGE_REL_AARCH64_TLSDESC_ADD_LO12 0x109
3418-
#define IMAGE_REL_AARCH64_TLSDESC_CALL 0x10A
3419-
3420-
// The identifier for ARM32-specific PC-relative address
3421-
// computation corresponds to the following instruction
3422-
// sequence:
3423-
// l0: movw rX, #imm_lo // 4 byte
3424-
// l4: movt rX, #imm_hi // 4 byte
3425-
// l8: add rX, pc <- after this instruction rX = relocTarget
3426-
//
3427-
// Program counter at l8 is address of l8 + 4
3428-
// Address of relocated movw/movt is l0
3429-
// So, imm should be calculated as the following:
3430-
// imm = relocTarget - (l8 + 4) = relocTarget - (l0 + 8 + 4) = relocTarget - (l_0 + 12)
3431-
// So, the value of offset correction is 12
3432-
//
3433-
#define IMAGE_REL_BASED_REL_THUMB_MOV32_PCREL 0x14
3434-
3435-
//
3436-
// LOONGARCH64 relocation types
3437-
//
3438-
#define IMAGE_REL_LOONGARCH64_PC 0x0003
3439-
#define IMAGE_REL_LOONGARCH64_JIR 0x0004
3440-
3441-
//
3442-
// RISCV64 relocation types
3443-
//
3444-
#define IMAGE_REL_RISCV64_PC 0x0003
3445-
34463455
/**********************************************************************************/
34473456
#ifdef TARGET_64BIT
34483457
#define USE_PER_FRAME_PINVOKE_INIT

src/coreclr/inc/corjit.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -425,11 +425,11 @@ class ICorJitInfo : public ICorDynamicInfo
425425
void * location, /* IN */
426426
void * locationRW, /* IN */
427427
void * target, /* IN */
428-
uint16_t fRelocType, /* IN */
428+
CorInfoReloc fRelocType, /* IN */
429429
int32_t addlDelta = 0 /* IN */
430430
) = 0;
431431

432-
virtual uint16_t getRelocTypeHint(void * target) = 0;
432+
virtual CorInfoReloc getRelocTypeHint(void * target) = 0;
433433

434434
// For what machine does the VM expect the JIT to generate code? The VM
435435
// returns one of the CorInfoArch values. Note that if the VM is cross

src/coreclr/inc/icorjitinfoimpl_generated.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -743,10 +743,10 @@ void recordRelocation(
743743
void* location,
744744
void* locationRW,
745745
void* target,
746-
uint16_t fRelocType,
746+
CorInfoReloc fRelocType,
747747
int32_t addlDelta) override;
748748

749-
uint16_t getRelocTypeHint(
749+
CorInfoReloc getRelocTypeHint(
750750
void* target) override;
751751

752752
uint32_t getExpectedTargetArchitecture() override;

src/coreclr/inc/jiteeversionguid.h

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -37,11 +37,11 @@
3737

3838
#include <minipal/guid.h>
3939

40-
constexpr GUID JITEEVersionIdentifier = { /* c3e8a087-931a-4aa4-a311-13e6736e509a */
41-
0xc3e8a087,
42-
0x931a,
43-
0x4aa4,
44-
{0xa3, 0x11, 0x13, 0xe6, 0x73, 0x6e, 0x50, 0x9a}
40+
constexpr GUID JITEEVersionIdentifier = { /* 567f89f4-2ddb-4d80-9107-0ce8c30a18ff */
41+
0x567f89f4,
42+
0x2ddb,
43+
0x4d80,
44+
{0x91, 0x07, 0x0c, 0xe8, 0xc3, 0x0a, 0x18, 0xff}
4545
};
4646

4747
#endif // JIT_EE_VERSIONING_GUID_H

src/coreclr/jit/ICorJitInfo_wrapper_generated.hpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1723,19 +1723,19 @@ void WrapICorJitInfo::recordRelocation(
17231723
void* location,
17241724
void* locationRW,
17251725
void* target,
1726-
uint16_t fRelocType,
1726+
CorInfoReloc fRelocType,
17271727
int32_t addlDelta)
17281728
{
17291729
API_ENTER(recordRelocation);
17301730
wrapHnd->recordRelocation(location, locationRW, target, fRelocType, addlDelta);
17311731
API_LEAVE(recordRelocation);
17321732
}
17331733

1734-
uint16_t WrapICorJitInfo::getRelocTypeHint(
1734+
CorInfoReloc WrapICorJitInfo::getRelocTypeHint(
17351735
void* target)
17361736
{
17371737
API_ENTER(getRelocTypeHint);
1738-
uint16_t temp = wrapHnd->getRelocTypeHint(target);
1738+
CorInfoReloc temp = wrapHnd->getRelocTypeHint(target);
17391739
API_LEAVE(getRelocTypeHint);
17401740
return temp;
17411741
}

src/coreclr/jit/codegeninterface.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -270,7 +270,7 @@ class CodeGenInterface
270270
#ifdef TARGET_XARCH
271271
#ifdef TARGET_AMD64
272272
// There are no reloc hints on x86
273-
unsigned short genAddrRelocTypeHint(size_t addr);
273+
CorInfoReloc genAddrRelocTypeHint(size_t addr);
274274
#endif
275275
bool genDataIndirAddrCanBeEncodedAsPCRelOffset(size_t addr);
276276
bool genCodeIndirAddrCanBeEncodedAsPCRelOffset(size_t addr);

src/coreclr/jit/codegenxarch.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11722,7 +11722,7 @@ void CodeGen::instGen_MemoryBarrier(BarrierKind barrierKind)
1172211722
// Returns
1172311723
// relocation type hint
1172411724
//
11725-
unsigned short CodeGenInterface::genAddrRelocTypeHint(size_t addr)
11725+
CorInfoReloc CodeGenInterface::genAddrRelocTypeHint(size_t addr)
1172611726
{
1172711727
return compiler->eeGetRelocTypeHint((void*)addr);
1172811728
}
@@ -11742,7 +11742,7 @@ unsigned short CodeGenInterface::genAddrRelocTypeHint(size_t addr)
1174211742
bool CodeGenInterface::genDataIndirAddrCanBeEncodedAsPCRelOffset(size_t addr)
1174311743
{
1174411744
#ifdef TARGET_AMD64
11745-
return genAddrRelocTypeHint(addr) == IMAGE_REL_BASED_REL32;
11745+
return genAddrRelocTypeHint(addr) == CorInfoReloc::RELATIVE32;
1174611746
#else
1174711747
// x86: PC-relative addressing is available only for control flow instructions (jmp and call)
1174811748
return false;
@@ -11763,7 +11763,7 @@ bool CodeGenInterface::genDataIndirAddrCanBeEncodedAsPCRelOffset(size_t addr)
1176311763
bool CodeGenInterface::genCodeIndirAddrCanBeEncodedAsPCRelOffset(size_t addr)
1176411764
{
1176511765
#ifdef TARGET_AMD64
11766-
return genAddrRelocTypeHint(addr) == IMAGE_REL_BASED_REL32;
11766+
return genAddrRelocTypeHint(addr) == CorInfoReloc::RELATIVE32;
1176711767
#else
1176811768
// x86: PC-relative addressing is available only for control flow instructions (jmp and call)
1176911769
return true;

src/coreclr/jit/compiler.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8579,7 +8579,7 @@ class Compiler
85798579

85808580
void eeSetEHinfo(unsigned EHnumber, const CORINFO_EH_CLAUSE* clause);
85818581

8582-
WORD eeGetRelocTypeHint(void* target);
8582+
CorInfoReloc eeGetRelocTypeHint(void* target);
85838583

85848584
// ICorStaticInfo wrapper functions
85858585

src/coreclr/jit/ee_il_dll.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1276,7 +1276,7 @@ void Compiler::eeSetEHinfo(unsigned EHnumber, const CORINFO_EH_CLAUSE* clause)
12761276
}
12771277
}
12781278

1279-
WORD Compiler::eeGetRelocTypeHint(void* target)
1279+
CorInfoReloc Compiler::eeGetRelocTypeHint(void* target)
12801280
{
12811281
if (info.compMatchedVM)
12821282
{
@@ -1285,7 +1285,7 @@ WORD Compiler::eeGetRelocTypeHint(void* target)
12851285
else
12861286
{
12871287
// No hints
1288-
return (WORD)-1;
1288+
return CorInfoReloc::NONE;
12891289
}
12901290
}
12911291

src/coreclr/jit/emit.cpp

Lines changed: 15 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -8528,8 +8528,7 @@ void emitter::emitOutputDataSec(dataSecDsc* sec, BYTE* dst)
85288528
bDstRW[i] = (target_size_t)(size_t)target;
85298529
if (emitComp->opts.compReloc)
85308530
{
8531-
uint16_t relocType = TARGET_POINTER_SIZE == 8 ? IMAGE_REL_BASED_DIR64 : IMAGE_REL_BASED_HIGHLOW;
8532-
emitRecordRelocation(&(bDstRW[i]), target, relocType);
8531+
emitRecordRelocation(&(bDstRW[i]), target, CorInfoReloc::DIRECT);
85338532
}
85348533

85358534
JITDUMP(" " FMT_BB ": 0x%p\n", block->bbNum, bDstRW[i]);
@@ -8575,11 +8574,10 @@ void emitter::emitOutputDataSec(dataSecDsc* sec, BYTE* dst)
85758574
aDstRW[i].DiagnosticIP = (target_size_t)(uintptr_t)target;
85768575
if (emitComp->opts.compReloc)
85778576
{
8578-
uint16_t relocType = TARGET_POINTER_SIZE == 8 ? IMAGE_REL_BASED_DIR64 : IMAGE_REL_BASED_HIGHLOW;
8579-
emitRecordRelocation(&aDstRW[i].Resume, emitAsyncResumeStubEntryPoint, relocType);
8577+
emitRecordRelocation(&aDstRW[i].Resume, emitAsyncResumeStubEntryPoint, CorInfoReloc::DIRECT);
85808578
if (target != nullptr)
85818579
{
8582-
emitRecordRelocation(&aDstRW[i].DiagnosticIP, target, relocType);
8580+
emitRecordRelocation(&aDstRW[i].DiagnosticIP, target, CorInfoReloc::DIRECT);
85838581
}
85848582
}
85858583

@@ -10521,25 +10519,25 @@ void emitter::emitStackKillArgs(BYTE* addr, unsigned count, unsigned char callIn
1052110519

1052210520
#ifdef DEBUG
1052310521

10524-
void emitter::emitRecordRelocationHelp(void* location, /* IN */
10525-
void* target, /* IN */
10526-
uint16_t fRelocType, /* IN */
10527-
const char* relocTypeName, /* IN */
10528-
int32_t addlDelta /* = 0 */) /* IN */
10522+
void emitter::emitRecordRelocationHelp(void* location, /* IN */
10523+
void* target, /* IN */
10524+
CorInfoReloc fRelocType, /* IN */
10525+
const char* relocTypeName, /* IN */
10526+
int32_t addlDelta /* = 0 */) /* IN */
1052910527

1053010528
#else // !DEBUG
1053110529

10532-
void emitter::emitRecordRelocation(void* location, /* IN */
10533-
void* target, /* IN */
10534-
uint16_t fRelocType, /* IN */
10535-
int32_t addlDelta /* = 0 */) /* IN */
10530+
void emitter::emitRecordRelocation(void* location, /* IN */
10531+
void* target, /* IN */
10532+
CorInfoReloc fRelocType, /* IN */
10533+
int32_t addlDelta /* = 0 */) /* IN */
1053610534

1053710535
#endif // !DEBUG
1053810536
{
1053910537
void* locationRW = (BYTE*)location + writeableOffset;
1054010538

1054110539
JITDUMP("recordRelocation: %p (rw: %p) => %p, type %u (%s), delta %d\n", dspPtr(location), dspPtr(locationRW),
10542-
dspPtr(target), fRelocType, relocTypeName, addlDelta);
10540+
dspPtr(target), (unsigned)fRelocType, relocTypeName, addlDelta);
1054310541

1054410542
// If we're an unmatched altjit, don't tell the VM anything. We still record the relocation for
1054510543
// late disassembly; maybe we'll need it?
@@ -10566,11 +10564,11 @@ void emitter::emitHandlePCRelativeMov32(void* location, /* IN */
1056610564
{
1056710565
if (emitComp->opts.jitFlags->IsSet(JitFlags::JIT_FLAG_RELATIVE_CODE_RELOCS))
1056810566
{
10569-
emitRecordRelocation(location, target, IMAGE_REL_BASED_REL_THUMB_MOV32_PCREL);
10567+
emitRecordRelocation(location, target, CorInfoReloc::ARM32_THUMB_MOV32_PCREL);
1057010568
}
1057110569
else
1057210570
{
10573-
emitRecordRelocation(location, target, IMAGE_REL_BASED_THUMB_MOV32);
10571+
emitRecordRelocation(location, target, CorInfoReloc::ARM32_THUMB_MOV32);
1057410572
}
1057510573
}
1057610574
#endif // TARGET_ARM

0 commit comments

Comments
 (0)