[Issue 9331] incorrect "ulong.max" value

d-bugmail at puremagic.com d-bugmail at puremagic.com
Sat Feb 9 07:51:37 PST 2013


http://d.puremagic.com/issues/show_bug.cgi?id=9331



--- Comment #3 from hsteoh at quickfur.ath.cx 2013-02-09 07:51:35 PST ---
Seems that something is wrong with the codegen. To probe this problem, I made a
slight modification to the code:

-------------
import std.stdio;

void marker() {}

void main()
{
    ubyte u1 = cast(byte)-1;
    byte u2 = cast(short)-1;
    uint u3 = cast(int)-1;
    int u4 = cast(long)-1;
    writefln("%d", u1);
    writefln("%d", u2);
    writefln("%d", u3);
    version(WithBug) writefln("%d\n", u4);

    marker();

    writefln("long.sizeof: %d  ulong.max: %20d", ulong.sizeof, ulong.max);
    writefln("long.sizeof: %d   long max: %20d", long.sizeof, long.max);
}
--------------

When compiling with dmd -m64, here's the assembly:

0000000000424ce8 <_Dmain>:
  424ce8:    55                       push   %rbp
  424ce9:    48 8b ec                 mov    %rsp,%rbp
  424cec:    48 83 ec 10              sub    $0x10,%rsp
  424cf0:    b0 ff                    mov    $0xff,%al
  424cf2:    b1 ff                    mov    $0xff,%cl
  424cf4:    88 4d f8                 mov    %cl,-0x8(%rbp)
  424cf7:    ba ff ff ff ff           mov    $0xffffffff,%edx
  424cfc:    89 55 fc                 mov    %edx,-0x4(%rbp)
  424cff:    48 8b 15 e2 5f 02 00     mov    0x25fe2(%rip),%rdx        # 44ace8
<_TMP0+0x8>
  424d06:    48 8b 35 d3 5f 02 00     mov    0x25fd3(%rip),%rsi        # 44ace0
<_TMP0>
  424d0d:    48 89 c7                 mov    %rax,%rdi
  424d10:    e8 8b 00 00 00           callq  424da0 <void
std.stdio.writefln!(immutable(char)[], ubyte).writefln(immutable(char)[],
ubyte)>
  424d15:    48 8b 15 cc 5f 02 00     mov    0x25fcc(%rip),%rdx        # 44ace8
<_TMP0+0x8>
  424d1c:    48 8b 35 bd 5f 02 00     mov    0x25fbd(%rip),%rsi        # 44ace0
<_TMP0>
  424d23:    40 8a 7d f8              mov    -0x8(%rbp),%dil
  424d27:    e8 28 4f 00 00           callq  429c54 <void
std.stdio.writefln!(immutable(char)[], byte).writefln(immutable(char)[], byte)>
  424d2c:    48 8b 15 b5 5f 02 00     mov    0x25fb5(%rip),%rdx        # 44ace8
<_TMP0+0x8>
  424d33:    48 8b 35 a6 5f 02 00     mov    0x25fa6(%rip),%rsi        # 44ace0
<_TMP0>
  424d3a:    8b 7d fc                 mov    -0x4(%rbp),%edi
  424d3d:    e8 12 5a 00 00           callq  42a754 <void
std.stdio.writefln!(immutable(char)[], uint).writefln(immutable(char)[], uint)>
  424d42:    e8 99 ff ff ff           callq  424ce0 <void test.marker()>
  424d47:    48 8b 0d da 5f 02 00     mov    0x25fda(%rip),%rcx        # 44ad28
<_TMP1+0x8>
  424d4e:    48 8b 05 cb 5f 02 00     mov    0x25fcb(%rip),%rax        # 44ad20
<_TMP1>
  424d55:    48 89 c2                 mov    %rax,%rdx
  424d58:    48 be 08 00 00 00 00     movabs $0x8,%rsi
  424d5f:    00 00 00 
  424d62:    48 bf ff ff ff ff ff     movabs $0xffffffffffffffff,%rdi
  424d69:    ff ff ff 
  424d6c:    e8 53 64 00 00           callq  42b1c4 <void
std.stdio.writefln!(immutable(char)[], ulong,
ulong).writefln(immutable(char)[], ulong, ulong)>
  424d71:    48 8b 0d f0 5f 02 00     mov    0x25ff0(%rip),%rcx        # 44ad68
<_TMP2+0x8>
  424d78:    48 8b 05 e1 5f 02 00     mov    0x25fe1(%rip),%rax        # 44ad60
<_TMP2>
  424d7f:    48 89 c2                 mov    %rax,%rdx
  424d82:    48 be 08 00 00 00 00     movabs $0x8,%rsi
  424d89:    00 00 00 
  424d8c:    48 bf ff ff ff ff ff     movabs $0x7fffffffffffffff,%rdi
  424d93:    ff ff 7f 
  424d96:    e8 fd 6e 00 00           callq  42bc98 <void
std.stdio.writefln!(immutable(char)[], ulong, long).writefln(immutable(char)[],
ulong, long)>
  424d9b:    31 c0                    xor    %eax,%eax
  424d9d:    c9                       leaveq 
  424d9e:    c3                       retq   
  424d9f:    90                       nop

When compiling with dmd -m64 -version=WithBug, here's the assembly:

0000000000425698 <_Dmain>:
  425698:    55                       push   %rbp
  425699:    48 8b ec                 mov    %rsp,%rbp
  42569c:    48 83 ec 18              sub    $0x18,%rsp
  4256a0:    53                       push   %rbx
  4256a1:    b0 ff                    mov    $0xff,%al
  4256a3:    b1 ff                    mov    $0xff,%cl
  4256a5:    88 4d f8                 mov    %cl,-0x8(%rbp)
  4256a8:    ba ff ff ff ff           mov    $0xffffffff,%edx
  4256ad:    89 55 fc                 mov    %edx,-0x4(%rbp)
  4256b0:    48 89 d3                 mov    %rdx,%rbx
  4256b3:    48 8b 15 8e 69 02 00     mov    0x2698e(%rip),%rdx        # 44c048
<_TMP0+0x8>
  4256ba:    48 8b 35 7f 69 02 00     mov    0x2697f(%rip),%rsi        # 44c040
<_TMP0>
  4256c1:    48 89 c7                 mov    %rax,%rdi
  4256c4:    e8 9b 00 00 00           callq  425764 <void
std.stdio.writefln!(immutable(char)[], ubyte).writefln(immutable(char)[],
ubyte)>
  4256c9:    48 8b 15 78 69 02 00     mov    0x26978(%rip),%rdx        # 44c048
<_TMP0+0x8>
  4256d0:    48 8b 35 69 69 02 00     mov    0x26969(%rip),%rsi        # 44c040
<_TMP0>
  4256d7:    40 8a 7d f8              mov    -0x8(%rbp),%dil
  4256db:    e8 38 4f 00 00           callq  42a618 <void
std.stdio.writefln!(immutable(char)[], byte).writefln(immutable(char)[], byte)>
  4256e0:    48 8b 15 61 69 02 00     mov    0x26961(%rip),%rdx        # 44c048
<_TMP0+0x8>
  4256e7:    48 8b 35 52 69 02 00     mov    0x26952(%rip),%rsi        # 44c040
<_TMP0>
  4256ee:    8b 7d fc                 mov    -0x4(%rbp),%edi
  4256f1:    e8 22 5a 00 00           callq  42b118 <void
std.stdio.writefln!(immutable(char)[], uint).writefln(immutable(char)[], uint)>
  4256f6:    48 8b 15 6b 69 02 00     mov    0x2696b(%rip),%rdx        # 44c068
<_TMP1+0x8>
  4256fd:    48 8b 35 5c 69 02 00     mov    0x2695c(%rip),%rsi        # 44c060
<_TMP1>
  425704:    48 89 df                 mov    %rbx,%rdi
  425707:    e8 7c 64 00 00           callq  42bb88 <void
std.stdio.writefln!(immutable(char)[], int).writefln(immutable(char)[], int)>
  42570c:    e8 7f ff ff ff           callq  425690 <void test.marker()>
  425711:    48 8b 0d 90 69 02 00     mov    0x26990(%rip),%rcx        # 44c0a8
<_TMP2+0x8>
  425718:    48 8b 05 81 69 02 00     mov    0x26981(%rip),%rax        # 44c0a0
<_TMP2>
  42571f:    48 89 c2                 mov    %rax,%rdx
  425722:    48 be 08 00 00 00 00     movabs $0x8,%rsi
  425729:    00 00 00 
  42572c:    48 89 df                 mov    %rbx,%rdi
  42572f:    e8 ec 6d 00 00           callq  42c520 <void
std.stdio.writefln!(immutable(char)[], ulong,
ulong).writefln(immutable(char)[], ulong, ulong)>
  425734:    48 8b 0d ad 69 02 00     mov    0x269ad(%rip),%rcx        # 44c0e8
<_TMP3+0x8>
  42573b:    48 8b 05 9e 69 02 00     mov    0x2699e(%rip),%rax        # 44c0e0
<_TMP3>
  425742:    48 89 c2                 mov    %rax,%rdx
  425745:    48 be 08 00 00 00 00     movabs $0x8,%rsi
  42574c:    00 00 00 
  42574f:    48 bf ff ff ff ff ff     movabs $0x7fffffffffffffff,%rdi
  425756:    ff ff 7f 
  425759:    e8 96 78 00 00           callq  42cff4 <void
std.stdio.writefln!(immutable(char)[], ulong, long).writefln(immutable(char)[],
ulong, long)>
  42575e:    31 c0                    xor    %eax,%eax
  425760:    5b                       pop    %rbx
  425761:    c9                       leaveq 
  425762:    c3                       retq   
  425763:    90                       nop

I inserted the no-op marker() function so that the faulty code is easier to
locate in the disassembly (I also filtered it through ddemangle so that
identifiers are easier to read).

Worthy of note is that in the version=WithBug version, the movabs
$0xffffffffffffffff,%rdi instruction prior to calling <void
std.stdio.writefln!(immutable(char)[], ulong,
ulong).writefln(immutable(char)[], ulong, ulong)> is missing. Instead, it
copies the value from %rbx, but earlier, near the top of the function, %rbx got
its value from %rdx, but %rdx was never set in its entirety. Instead, we have:

  4256a8:       ba ff ff ff ff          mov    $0xffffffff,%edx
  4256ad:       89 55 fc                ... (irrelevant)
  4256b0:       48 89 d3                mov    %rdx,%rbx

Looks like the codegen is wrongly assuming that the first immediate value,
$0xffffffff, is 64-bit, whereas it's only 32-bit. So only the lower bits of
%rdx are set. Hence the truncated value of ulong.max later on, when this value
is passed to writefln.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------


More information about the Digitalmars-d-bugs mailing list