[llvm] f4e418a - [RuntimeDyldChecker] Support offset in decode_operand expr

via llvm-commits llvm-commits at lists.llvm.org
Mon Aug 2 20:30:15 PDT 2021


Author: luxufan
Date: 2021-08-03T11:25:51+08:00
New Revision: f4e418ac1e02c516abb8cc5125e38073b159e56f

URL: https://github.com/llvm/llvm-project/commit/f4e418ac1e02c516abb8cc5125e38073b159e56f
DIFF: https://github.com/llvm/llvm-project/commit/f4e418ac1e02c516abb8cc5125e38073b159e56f.diff

LOG: [RuntimeDyldChecker] Support offset in decode_operand expr

In RISCV's relocations, some relocations are comprised of two relocation types. For example, R_RISCV_PCREL_HI20 and R_RISCV_PCREL_LO12_I compose a PC relative relocation. In general the compiler will set a label in the position of R_RISCV_PCREL_HI20. So, to test the R_RISCV_PCREL_LO12_I relocation, we need decode instruction at position of the label points to R_RISCV_PCREL_HI20 plus 4 (the size of a riscv non-compress instruction).

Reviewed By: lhames

Differential Revision: https://reviews.llvm.org/D105528

Added: 
    

Modified: 
    llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldChecker.cpp
    llvm/test/ExecutionEngine/JITLink/RISCV/ELF_pc_indirect.s

Removed: 
    


################################################################################
diff  --git a/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldChecker.cpp b/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldChecker.cpp
index a3005f786cf90..3af57cb6da812 100644
--- a/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldChecker.cpp
+++ b/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldChecker.cpp
@@ -232,6 +232,26 @@ class RuntimeDyldCheckerExprEval {
           EvalResult(("Cannot decode unknown symbol '" + Symbol + "'").str()),
           "");
 
+    // if there is an offset number expr
+    int64_t Offset = 0;
+    BinOpToken BinOp;
+    std::tie(BinOp, RemainingExpr) = parseBinOpToken(RemainingExpr);
+    switch (BinOp) {
+    case BinOpToken::Add: {
+      EvalResult Number;
+      std::tie(Number, RemainingExpr) = evalNumberExpr(RemainingExpr);
+      Offset = Number.getValue();
+      break;
+    }
+    case BinOpToken::Invalid:
+      break;
+    default:
+      return std::make_pair(
+          unexpectedToken(RemainingExpr, RemainingExpr,
+                          "expected '+' for offset or ',' if no offset"),
+          "");
+    }
+
     if (!RemainingExpr.startswith(","))
       return std::make_pair(
           unexpectedToken(RemainingExpr, RemainingExpr, "expected ','"), "");
@@ -249,7 +269,7 @@ class RuntimeDyldCheckerExprEval {
 
     MCInst Inst;
     uint64_t Size;
-    if (!decodeInst(Symbol, Inst, Size))
+    if (!decodeInst(Symbol, Inst, Size, Offset))
       return std::make_pair(
           EvalResult(("Couldn't decode instruction at '" + Symbol + "'").str()),
           "");
@@ -307,7 +327,7 @@ class RuntimeDyldCheckerExprEval {
 
     MCInst Inst;
     uint64_t InstSize;
-    if (!decodeInst(Symbol, Inst, InstSize))
+    if (!decodeInst(Symbol, Inst, InstSize, 0))
       return std::make_pair(
           EvalResult(("Couldn't decode instruction at '" + Symbol + "'").str()),
           "");
@@ -664,10 +684,14 @@ class RuntimeDyldCheckerExprEval {
     return evalComplexExpr(std::make_pair(ThisResult, RemainingExpr), PCtx);
   }
 
-  bool decodeInst(StringRef Symbol, MCInst &Inst, uint64_t &Size) const {
+  bool decodeInst(StringRef Symbol, MCInst &Inst, uint64_t &Size,
+                  int64_t Offset) const {
     MCDisassembler *Dis = Checker.Disassembler;
     StringRef SymbolMem = Checker.getSymbolContent(Symbol);
-    ArrayRef<uint8_t> SymbolBytes(SymbolMem.bytes_begin(), SymbolMem.size());
+    if (SymbolMem.size() <= Offset)
+      return false;
+    ArrayRef<uint8_t> SymbolBytes(SymbolMem.bytes_begin() + Offset,
+                                  SymbolMem.size() - Offset);
 
     MCDisassembler::DecodeStatus S =
         Dis->getInstruction(Inst, Size, SymbolBytes, 0, nulls());
@@ -675,7 +699,7 @@ class RuntimeDyldCheckerExprEval {
     return (S == MCDisassembler::Success);
   }
 };
-}
+} // namespace llvm
 
 RuntimeDyldCheckerImpl::RuntimeDyldCheckerImpl(
     IsSymbolValidFunction IsSymbolValid, GetSymbolInfoFunction GetSymbolInfo,

diff  --git a/llvm/test/ExecutionEngine/JITLink/RISCV/ELF_pc_indirect.s b/llvm/test/ExecutionEngine/JITLink/RISCV/ELF_pc_indirect.s
index 875c8c87613a4..02afc9f6ae33d 100644
--- a/llvm/test/ExecutionEngine/JITLink/RISCV/ELF_pc_indirect.s
+++ b/llvm/test/ExecutionEngine/JITLink/RISCV/ELF_pc_indirect.s
@@ -21,7 +21,8 @@ main:
         .size   main, .-main
 
 # Test R_RISCV_PCREL_HI20 and R_RISCV_PCREL_LO
-# jitlink-check: decode_operand(test_pcrel32, 1) = ((named_data - test_pcrel32) + 0x800)[31:12] 
+# jitlink-check: decode_operand(test_pcrel32, 1) = ((named_data - test_pcrel32) + 0x800)[31:12]
+# jitlink-check: decode_operand(test_pcrel32+4, 2)[11:0] = (named_data - test_pcrel32)[11:0]
         .globl  test_pcrel32
         .p2align  1
         .type   test_pcrel32, at function


        


More information about the llvm-commits mailing list