[Issue 18748] New: bt instruction with immediate offset uses 64-bit variant for 32-bit data

d-bugmail at puremagic.com d-bugmail at puremagic.com
Mon Apr 9 22:41:06 UTC 2018


https://issues.dlang.org/show_bug.cgi?id=18748

          Issue ID: 18748
           Summary: bt instruction with immediate offset uses 64-bit
                    variant for 32-bit data
           Product: D
           Version: D2
          Hardware: x86_64
                OS: Linux
            Status: NEW
          Keywords: wrong-code
          Severity: normal
          Priority: P1
         Component: dmd
          Assignee: nobody at puremagic.com
          Reporter: ag0aep6g at gmail.com

----
int bt_32_imm(in uint* p)
{
    enum bitnum = 1;
    return ((p[bitnum >> 5] & (1 << (bitnum & 31)))) != 0;
}
void main()
{
    import core.sys.posix.sys.mman;
    import core.sys.posix.unistd;
    // Allocate two pages.
    immutable sz = 2 * sysconf(_SC_PAGESIZE);
    auto m = mmap(null, sz, PROT_READ, MAP_PRIVATE | MAP_ANON, -1, 0);
    // Discard the higher page. It becomes unreadable.
    munmap(m + sz / 2, sz / 2);
    // Try looking at the last 4 bytes of the readable page.
    uint* p = cast(uint*) (m + sz / 2 - uint.sizeof);
    bt_32_imm(p);
    munmap(m, sz / 2); // Free the readable page.
}
----

Compile with `-O`. Resulting program segfaults.

Generated code for bt_32_imm:

----
   0:   55                      push   rbp
   1:   48 8b ec                mov    rbp,rsp
   4:   48 0f ba 27 01          bt     QWORD PTR [rdi],0x1
   9:   19 c0                   sbb    eax,eax
   b:   f7 d8                   neg    eax
   d:   5d                      pop    rbp
   e:   c3                      ret
----

The bt instruction should be the 32-bit variant (DWORD instead of QWORD). The
64-bit variant tries to load 8 bytes, but only 4 are accessible.

--


More information about the Digitalmars-d-bugs mailing list