<html>
    <head>
      <base href="https://bugs.llvm.org/">
    </head>
    <body><table border="1" cellspacing="0" cellpadding="8">
        <tr>
          <th>Bug ID</th>
          <td><a class="bz_bug_link 
          bz_status_NEW "
   title="NEW - x86-64 COFF driver doesn't relocate ADDR32 relocations correctly"
   href="https://bugs.llvm.org/show_bug.cgi?id=49068">49068</a>
          </td>
        </tr>

        <tr>
          <th>Summary</th>
          <td>x86-64 COFF driver doesn't relocate ADDR32 relocations correctly
          </td>
        </tr>

        <tr>
          <th>Product</th>
          <td>lld
          </td>
        </tr>

        <tr>
          <th>Version</th>
          <td>unspecified
          </td>
        </tr>

        <tr>
          <th>Hardware</th>
          <td>PC
          </td>
        </tr>

        <tr>
          <th>OS</th>
          <td>Windows NT
          </td>
        </tr>

        <tr>
          <th>Status</th>
          <td>NEW
          </td>
        </tr>

        <tr>
          <th>Severity</th>
          <td>normal
          </td>
        </tr>

        <tr>
          <th>Priority</th>
          <td>P
          </td>
        </tr>

        <tr>
          <th>Component</th>
          <td>COFF
          </td>
        </tr>

        <tr>
          <th>Assignee</th>
          <td>unassignedbugs@nondot.org
          </td>
        </tr>

        <tr>
          <th>Reporter</th>
          <td>axel.y.rivera@intel.com
          </td>
        </tr>

        <tr>
          <th>CC</th>
          <td>llvm-bugs@lists.llvm.org
          </td>
        </tr></table>
      <p>
        <div>
        <pre>Created <span class=""><a href="attachment.cgi?id=24489" name="attach_24489" title="Simple test case">attachment 24489</a> <a href="attachment.cgi?id=24489&action=edit" title="Simple test case">[details]</a></span>
Simple test case

Hi,

I attached a simple example that contains inline assembly code (__asm). It
compiles and links, but produces a segmentation fault during execution.

bash-3.2$ clang-cl -c -Od -Zi simple.c
bash-3.2$ clang-cl -fuse-ld=lld -o simple.exe -Od -Zi simple.obj /link
/LARGEADDRESSAWARE:NO
clang-cl: warning: argument unused during compilation: '-Od'
[-Wunused-command-line-argument]
bash-3.2$ ./simple.exe
Segmentation fault

The test case pass if it is linked with MS-LINK:

bash-3.2$ clang-cl -o simple.exe -Od -Zi simple.obj /link /LARGEADDRESSAWARE:NO
clang-cl: warning: argument unused during compilation: '-Od'
[-Wunused-command-line-argument]
bash-3.2$ ./simple.exe
RESULT: 7

The generated object by clang-cl (simple.obj) contains an ADDR32 relocation:

RELOCATIONS #1
                                                Symbol    Symbol
 Offset    Type              Applied To         Index     Name
 --------  ----------------  -----------------  --------  ------
 00000007  REL32                      00000000        4D  __security_cookie
 0000001D  REL32                      00000014        50  arr
 00000033  ADDR32                     00000000        50  arr
 00000042  REL32                      00000000        35 
??_C@_0M@HGMGLEGP@RESULT?3?5?$CFd?6?$AA@ (`string')
 00000047  REL32                      00000000        1E  printf
 0000005A  REL32                      00000000        4E 
__security_check_cookie


And the executable generated by MS-LINK contains the relocation section:

BASE RELOCATIONS #8
    6000 RVA,        C SizeOfBlock
     EC3  HIGHLOW            00483070  arr
       0  ABS

But the executable generated by lld-link doesn't contain the relocatable
section, which produce a seg-fault when accessing arr inside the inline asm
code.

I noticed that the collection for the relocation base type
(lld/COFF/Chunks.cpp, getBaserelType) only checks for ADDR64 when the machine
is 64bits:

static uint8_t getBaserelType(const coff_relocation &rel) {
  switch (config->machine) {
  case AMD64:
    if (rel.Type == IMAGE_REL_AMD64_ADDR64)
      return IMAGE_REL_BASED_DIR64;
    return IMAGE_REL_BASED_ABSOLUTE;

It is ignoring the image when the relocation type is IMAGE_REL_AMD64_ADDR32 and
returns IMAGE_REL_BASED_ABSOLUTE, when the relocation needs the high and low
address information. This is producing that the relocation data is not being
inserted into the executable. I made this patch the returns the HIGHLOW image
base when the relocation type is AMD64_ADDR32:

diff --git a/lld/COFF/Chunks.cpp b/lld/COFF/Chunks.cpp
index 9d60bc746c96..c11f15e401d8 100644
--- a/lld/COFF/Chunks.cpp
+++ b/lld/COFF/Chunks.cpp
@@ -424,6 +424,8 @@ static uint8_t getBaserelType(const coff_relocation &rel) {
   case AMD64:
     if (rel.Type == IMAGE_REL_AMD64_ADDR64)
       return IMAGE_REL_BASED_DIR64;
+    if (rel.Type == IMAGE_REL_AMD64_ADDR32)
+      return IMAGE_REL_BASED_HIGHLOW;
     return IMAGE_REL_BASED_ABSOLUTE;
   case I386:
     if (rel.Type == IMAGE_REL_I386_DIR32)


bash-3.2$ clang-cl -fuse-ld=lld -Zi -o simple.exe -Od simple.obj /link
/LARGEADDRESSAWARE:NO
clang-cl: warning: argument unused during compilation: '-Od'
[-Wunused-command-line-argument]
bash-3.2$ ./simple.exe
RESULT: 7

The relocation section is now inserted into the executable generated by
lld-link:

BASE RELOCATIONS #8
    1000 RVA,        C SizeOfBlock
      33  HIGHLOW            4005FBC0
       0  ABS

It seems that the HIGHLOW address information needs to be inserted in the
relocation section when ADDR32 is found.</pre>
        </div>
      </p>


      <hr>
      <span>You are receiving this mail because:</span>

      <ul>
          <li>You are on the CC list for the bug.</li>
      </ul>
    </body>
</html>