Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 8 additions & 1 deletion src/coreclr/jit/emitarm.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5334,7 +5334,14 @@ BYTE* emitter::emitOutputLJ(insGroup* ig, BYTE* dst, instrDesc* i)
else
{
assert(ins == INS_movw || ins == INS_movt);
distVal = (ssize_t)emitOffsetToPtr(dstOffs) + 1; // Or in thumb bit
distVal = (ssize_t)emitOffsetToPtr(dstOffs);

// ILC defines method symbols with the thumb bit already set, so don't add it here.
// For ReadyToRun and non-relocatable code (runtime JIT), we set it ourselves.
if (!m_compiler->IsNativeAot())
{
distVal += 1;
}
}

if (dstOffs <= srcOffs)
Expand Down
24 changes: 8 additions & 16 deletions src/coreclr/tools/Common/Compiler/ObjectWriter/ObjectWriter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -189,20 +189,13 @@ or IMAGE_REL_BASED_THUMB_BRANCH24 or IMAGE_REL_BASED_THUMB_MOV32_PCREL &&
// Resolve the relocation to already defined symbol and write it into data
fixed (byte* pData = data)
{
// RyuJIT generates the Thumb bit in the addend and we also get it from
// the symbol value. The AAELF ABI specification defines the R_ARM_THM_JUMP24
// and R_ARM_THM_MOVW_PREL_NC relocations using the formula ((S + A) | T) – P.
// The thumb bit is thus supposed to be only added once.
// For R_ARM_THM_JUMP24 the thumb bit cannot be encoded, so mask it out.
//
// R2R doesn't use add the thumb bit to the symbol value, so we don't need to do this here.
#if !READYTORUN
long maskThumbBitOut = relocType is IMAGE_REL_BASED_THUMB_BRANCH24 or IMAGE_REL_BASED_THUMB_MOV32_PCREL ? 1 : 0;
long maskThumbBitIn = relocType is IMAGE_REL_BASED_THUMB_MOV32_PCREL ? 1 : 0;
#else
long maskThumbBitOut = 0;
long maskThumbBitIn = 0;
#endif
// Method symbols should be defined with the thumb bit (+1) set per the AAELF ABI
// convention. For BRANCH24, the encoding cannot represent the thumb bit
// (per AAELF formula ((S + A) | T) – P), so strip it from the symbol value.
// NOTE: R2R doesn't currently add the thumb bit to the symbol value, so this is a NOP.
long symbolValue = relocType is IMAGE_REL_BASED_THUMB_BRANCH24
? definedSymbol.Value & ~1L
: definedSymbol.Value;
long adjustedAddend = addend;

adjustedAddend -= relocType switch
Expand All @@ -213,9 +206,8 @@ or IMAGE_REL_BASED_THUMB_BRANCH24 or IMAGE_REL_BASED_THUMB_MOV32_PCREL &&
_ => 0
};

adjustedAddend += definedSymbol.Value & ~maskThumbBitOut;
adjustedAddend += symbolValue;
adjustedAddend += Relocation.ReadValue(relocType, (void*)pData);
adjustedAddend |= definedSymbol.Value & maskThumbBitIn;
adjustedAddend -= offset;

if (relocType is IMAGE_REL_BASED_THUMB_BRANCH24 && !Relocation.FitsInThumb2BlRel24((int)adjustedAddend))
Expand Down
Loading