[llvm] r179240 - MC: Support COFF image-relative MCSymbolRefs

Nico Rieck nico.rieck at gmail.com
Wed Apr 10 16:28:18 PDT 2013


Author: nrieck
Date: Wed Apr 10 18:28:17 2013
New Revision: 179240

URL: http://llvm.org/viewvc/llvm-project?rev=179240&view=rev
Log:
MC: Support COFF image-relative MCSymbolRefs

Add support for the COFF relocation types IMAGE_REL_I386_DIR32NB and
IMAGE_REL_AMD64_ADDR32NB for 32- and 64-bit respectively. These are
similar to normal 4-byte relocations except that they do not include
the base address of the image.

Image-relative relocations are used for debug information (32-bit) and
SEH unwind tables (64-bit).

A new MCSymbolRef variant called 'VK_COFF_IMGREL32' is introduced to
specify such relocations. For AT&T assembly, this variant can be accessed
using the symbol suffix '@imgrel'.

Added:
    llvm/trunk/docs/Extensions.rst
    llvm/trunk/test/MC/COFF/relocation-imgrel.s
Modified:
    llvm/trunk/docs/index.rst
    llvm/trunk/include/llvm/MC/MCExpr.h
    llvm/trunk/include/llvm/MC/MCWinCOFFObjectWriter.h
    llvm/trunk/lib/MC/MCExpr.cpp
    llvm/trunk/lib/MC/WinCOFFObjectWriter.cpp
    llvm/trunk/lib/Target/X86/MCTargetDesc/X86WinCOFFObjectWriter.cpp

Added: llvm/trunk/docs/Extensions.rst
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/Extensions.rst?rev=179240&view=auto
==============================================================================
--- llvm/trunk/docs/Extensions.rst (added)
+++ llvm/trunk/docs/Extensions.rst Wed Apr 10 18:28:17 2013
@@ -0,0 +1,39 @@
+===============
+LLVM Extensions
+===============
+
+.. contents::
+   :local:
+   :depth: 1
+
+.. toctree::
+   :hidden:
+
+Introduction
+============
+
+This document describes extensions to tools and formats LLVM seeks compatibility
+with.
+
+Machine-specific Assembly Syntax
+================================
+
+X86/COFF-Dependent
+------------------
+
+The following additional relocation type is supported:
+
+**@IMGREL** (AT&T syntax only) generates an image-relative relocation that
+corresponds to the COFF relocation types ``IMAGE_REL_I386_DIR32NB`` (32-bit) or
+``IMAGE_REL_AMD64_ADDR32NB`` (64-bit).
+
+.. code-block:: gas
+
+  .text
+  fun:
+    mov foo at IMGREL(%ebx, %ecx, 4), %eax
+
+  .section .pdata
+    .long fun at IMGREL
+    .long (fun at imgrel + 0x3F)
+    .long $unwind$fun at imgrel

Modified: llvm/trunk/docs/index.rst
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/index.rst?rev=179240&r1=179239&r2=179240&view=diff
==============================================================================
--- llvm/trunk/docs/index.rst (original)
+++ llvm/trunk/docs/index.rst Wed Apr 10 18:28:17 2013
@@ -160,6 +160,7 @@ For developers of applications which use
    ExtendingLLVM
    HowToSetUpLLVMStyleRTTI
    ProgrammersManual
+   Extensions
 
 :doc:`LLVM Language Reference Manual <LangRef>`
   Defines the LLVM intermediate representation and the assembly form of the
@@ -172,6 +173,9 @@ For developers of applications which use
   Introduction to the general layout of the LLVM sourcebase, important classes
   and APIs, and some tips & tricks.
 
+:doc:`Extensions`
+  LLVM-specific extensions to tools and formats LLVM seeks compatibility with.
+
 :doc:`CommandLine`
   Provides information on using the command line parsing library.
 

Modified: llvm/trunk/include/llvm/MC/MCExpr.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCExpr.h?rev=179240&r1=179239&r2=179240&view=diff
==============================================================================
--- llvm/trunk/include/llvm/MC/MCExpr.h (original)
+++ llvm/trunk/include/llvm/MC/MCExpr.h Wed Apr 10 18:28:17 2013
@@ -216,7 +216,9 @@ public:
     VK_Mips_GOT_HI16,
     VK_Mips_GOT_LO16,
     VK_Mips_CALL_HI16,
-    VK_Mips_CALL_LO16
+    VK_Mips_CALL_LO16,
+
+    VK_COFF_IMGREL32 // symbol at imgrel (image-relative)
   };
 
 private:

Modified: llvm/trunk/include/llvm/MC/MCWinCOFFObjectWriter.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCWinCOFFObjectWriter.h?rev=179240&r1=179239&r2=179240&view=diff
==============================================================================
--- llvm/trunk/include/llvm/MC/MCWinCOFFObjectWriter.h (original)
+++ llvm/trunk/include/llvm/MC/MCWinCOFFObjectWriter.h Wed Apr 10 18:28:17 2013
@@ -11,7 +11,9 @@
 #define LLVM_MC_MCWINCOFFOBJECTWRITER_H
 
 namespace llvm {
+  class MCFixup;
   class MCObjectWriter;
+  class MCValue;
   class raw_ostream;
 
   class MCWinCOFFObjectTargetWriter {
@@ -24,7 +26,9 @@ namespace llvm {
     virtual ~MCWinCOFFObjectTargetWriter() {}
 
     unsigned getMachine() const { return Machine; }
-    virtual unsigned getRelocType(unsigned FixupKind) const = 0;
+    virtual unsigned getRelocType(const MCValue &Target,
+                                  const MCFixup &Fixup,
+                                  bool IsCrossSection) const = 0;
   };
 
   /// \brief Construct a new Win COFF writer instance.

Modified: llvm/trunk/lib/MC/MCExpr.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCExpr.cpp?rev=179240&r1=179239&r2=179240&view=diff
==============================================================================
--- llvm/trunk/lib/MC/MCExpr.cpp (original)
+++ llvm/trunk/lib/MC/MCExpr.cpp Wed Apr 10 18:28:17 2013
@@ -250,6 +250,7 @@ StringRef MCSymbolRefExpr::getVariantKin
   case VK_Mips_GOT_LO16: return "GOT_LO16";
   case VK_Mips_CALL_HI16: return "CALL_HI16";
   case VK_Mips_CALL_LO16: return "CALL_LO16";
+  case VK_COFF_IMGREL32: return "IMGREL32";
   }
   llvm_unreachable("Invalid variant kind");
 }
@@ -285,6 +286,8 @@ MCSymbolRefExpr::getVariantKindForName(S
     .Case("dtpoff", VK_DTPOFF)
     .Case("TLVP", VK_TLVP)
     .Case("tlvp", VK_TLVP)
+    .Case("IMGREL", VK_COFF_IMGREL32)
+    .Case("imgrel", VK_COFF_IMGREL32)
     .Default(VK_Invalid);
 }
 

Modified: llvm/trunk/lib/MC/WinCOFFObjectWriter.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/WinCOFFObjectWriter.cpp?rev=179240&r1=179239&r2=179240&view=diff
==============================================================================
--- llvm/trunk/lib/MC/WinCOFFObjectWriter.cpp (original)
+++ llvm/trunk/lib/MC/WinCOFFObjectWriter.cpp Wed Apr 10 18:28:17 2013
@@ -689,13 +689,8 @@ void WinCOFFObjectWriter::RecordRelocati
   ++Reloc.Symb->Relocations;
 
   Reloc.Data.VirtualAddress += Fixup.getOffset();
-
-  unsigned FixupKind = Fixup.getKind();
-
-  if (CrossSection)
-    FixupKind = FK_PCRel_4;
-
-  Reloc.Data.Type = TargetObjectWriter->getRelocType(FixupKind);
+  Reloc.Data.Type = TargetObjectWriter->getRelocType(Target, Fixup,
+                                                     CrossSection);
 
   // FIXME: Can anyone explain what this does other than adjust for the size
   // of the offset?

Modified: llvm/trunk/lib/Target/X86/MCTargetDesc/X86WinCOFFObjectWriter.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/X86/MCTargetDesc/X86WinCOFFObjectWriter.cpp?rev=179240&r1=179239&r2=179240&view=diff
==============================================================================
--- llvm/trunk/lib/Target/X86/MCTargetDesc/X86WinCOFFObjectWriter.cpp (original)
+++ llvm/trunk/lib/Target/X86/MCTargetDesc/X86WinCOFFObjectWriter.cpp Wed Apr 10 18:28:17 2013
@@ -9,6 +9,8 @@
 
 #include "MCTargetDesc/X86FixupKinds.h"
 #include "MCTargetDesc/X86MCTargetDesc.h"
+#include "llvm/MC/MCExpr.h"
+#include "llvm/MC/MCValue.h"
 #include "llvm/MC/MCWinCOFFObjectWriter.h"
 #include "llvm/Support/COFF.h"
 #include "llvm/Support/ErrorHandling.h"
@@ -27,7 +29,9 @@ namespace {
     X86WinCOFFObjectWriter(bool Is64Bit_);
     ~X86WinCOFFObjectWriter();
 
-    virtual unsigned getRelocType(unsigned FixupKind) const;
+    virtual unsigned getRelocType(const MCValue &Target,
+                                  const MCFixup &Fixup,
+                                  bool IsCrossSection) const LLVM_OVERRIDE;
   };
 }
 
@@ -38,7 +42,14 @@ X86WinCOFFObjectWriter::X86WinCOFFObject
 
 X86WinCOFFObjectWriter::~X86WinCOFFObjectWriter() {}
 
-unsigned X86WinCOFFObjectWriter::getRelocType(unsigned FixupKind) const {
+unsigned X86WinCOFFObjectWriter::getRelocType(const MCValue &Target,
+                                              const MCFixup &Fixup,
+                                              bool IsCrossSection) const {
+  unsigned FixupKind = IsCrossSection ? FK_PCRel_4 : Fixup.getKind();
+
+  MCSymbolRefExpr::VariantKind Modifier = Target.isAbsolute() ?
+    MCSymbolRefExpr::VK_None : Target.getSymA()->getKind();
+
   switch (FixupKind) {
   case FK_PCRel_4:
   case X86::reloc_riprel_4byte:
@@ -46,6 +57,9 @@ unsigned X86WinCOFFObjectWriter::getRelo
     return Is64Bit ? COFF::IMAGE_REL_AMD64_REL32 : COFF::IMAGE_REL_I386_REL32;
   case FK_Data_4:
   case X86::reloc_signed_4byte:
+    if (Modifier == MCSymbolRefExpr::VK_COFF_IMGREL32)
+      return Is64Bit ? COFF::IMAGE_REL_AMD64_ADDR32NB :
+                       COFF::IMAGE_REL_I386_DIR32NB;
     return Is64Bit ? COFF::IMAGE_REL_AMD64_ADDR32 : COFF::IMAGE_REL_I386_DIR32;
   case FK_Data_8:
     if (Is64Bit)

Added: llvm/trunk/test/MC/COFF/relocation-imgrel.s
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/COFF/relocation-imgrel.s?rev=179240&view=auto
==============================================================================
--- llvm/trunk/test/MC/COFF/relocation-imgrel.s (added)
+++ llvm/trunk/test/MC/COFF/relocation-imgrel.s Wed Apr 10 18:28:17 2013
@@ -0,0 +1,29 @@
+// COFF Image-relative relocations
+//
+// Test that we produce image-relative relocations (IMAGE_REL_I386_DIR32NB
+// and IMAGE_REL_AMD64_ADDR32NB) when accessing foo at imgrel.
+
+// RUN: llvm-mc -filetype=obj -triple i686-pc-win32 %s | llvm-readobj -r | FileCheck --check-prefix=W32 %s
+// RUN: llvm-mc -filetype=obj -triple x86_64-pc-win32 %s | llvm-readobj -r | FileCheck --check-prefix=W64 %s
+
+.data
+foo:
+    .long 1
+
+.text
+    mov foo at IMGREL(%ebx, %ecx, 4), %eax
+    mov foo at imgrel(%ebx, %ecx, 4), %eax
+
+// W32:      Relocations [
+// W32-NEXT:   Section (1) .text {
+// W32-NEXT:     0x3 IMAGE_REL_I386_DIR32NB foo
+// W32-NEXT:     0xA IMAGE_REL_I386_DIR32NB foo
+// W32-NEXT:   }
+// W32-NEXT: ]
+
+// W64:      Relocations [
+// W64-NEXT:   Section (1) .text {
+// W64-NEXT:     0x4 IMAGE_REL_AMD64_ADDR32NB foo
+// W64-NEXT:     0xC IMAGE_REL_AMD64_ADDR32NB foo
+// W64-NEXT:   }
+// W64-NEXT: ]





More information about the llvm-commits mailing list