[BPF] Disable relocation for .BTF.ext section

Build llvm with assertion on, and then build bcc against this llvm.
Run any bcc tool with debug=8 (turning on -g for clang compilation),
you will get the following assertion errors,
  /home/yhs/work/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp:888:
  void llvm::RuntimeDyldELF::resolveBPFRelocation(const llvm::SectionEntry&, uint64_t,
    uint64_t, uint32_t, int64_t): Assertion `Value <= (4294967295U)' failed.

The .BTF.ext ELF section uses Fixup's to get the instruction
offsets. The data width of the Fixup is 4 bytes since we only need
the insn offset within the section.

This caused the above error though since R_BPF_64_32 expects
4-byte value and the Runtime Dyld tried to resolve the actual
insn address which is 8 bytes.

Actually the offset within the section is all what we need.
Therefore, there is no need to perform any kind of relocation
for .BTF.ext section and such relocation will actually cause
incorrect result.

This patch changed BPFELFObjectWriter::getRelocType() such that
for Fixup Kind FK_Data_4, if the relocation Target is a temporary
symbol, let us skip the relocation (ELF::R_BPF_NONE).

Acked-by: Alexei Starovoitov <ast@kernel.org>
Signed-off-by: Yonghong Song <yhs@fb.com>
llvm-svn: 349778
This commit is contained in:
Yonghong Song 2018-12-20 17:40:23 +00:00
parent b17464e4e8
commit 821c93d556
1 changed files with 10 additions and 0 deletions

View File

@ -12,6 +12,7 @@
#include "llvm/MC/MCELFObjectWriter.h"
#include "llvm/MC/MCFixup.h"
#include "llvm/MC/MCObjectWriter.h"
#include "llvm/MC/MCValue.h"
#include "llvm/Support/ErrorHandling.h"
#include <cstdint>
@ -50,6 +51,15 @@ unsigned BPFELFObjectWriter::getRelocType(MCContext &Ctx, const MCValue &Target,
case FK_Data_8:
return ELF::R_BPF_64_64;
case FK_Data_4:
// .BTF.ext generates FK_Data_4 relocations for
// insn offset by creating temporary labels.
// The insn offset is within the code section and
// already been fulfilled by applyFixup(). No
// further relocation is needed.
if (const MCSymbolRefExpr *A = Target.getSymA()) {
if (A->getSymbol().isTemporary())
return ELF::R_BPF_NONE;
}
return ELF::R_BPF_64_32;
}
}