[Issue 2224] Bad codegen for array element assignment

d-bugmail at puremagic.com d-bugmail at puremagic.com
Fri Sep 11 00:24:25 PDT 2009


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


Don <clugdbug at yahoo.com.au> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |clugdbug at yahoo.com.au
            Version|2.012                       |1.020
            Summary|Temporary assignment        |Bad codegen for array
                   |circumvents bug             |element assignment
         OS/Version|Linux                       |All


--- Comment #2 from Don <clugdbug at yahoo.com.au> 2009-09-11 00:24:21 PDT ---
This is a TERRIBLE bug report! The test case is really complicated, and very
far from minimal. I've reduced it slightly so that it at least asserts when it
fails.
It also fails on D1, at least as far back as 1.020.

If you comment out the line marked 'FAILS' and replace it with the line marked
'WORKS' it will work correctly. I would appreciate if someone could cut this
test case down. I think it might be important. (OTOH it might just be luck that
it works at all, it might just be reading whatever's on the stack).

----
class Stack{
    private uint len;
    private uint[] dat;

    uint[] data() { return dat[0..len]; }

    int length() { return len; }

    void push(uint t) {
        if(dat.length<=len) dat.length=dat.length+32;
        dat[len]=t;
        len++;
    }
    void pushn(uint n) {
        len+=n;
        if(dat.length<len) dat.length=len+32;
    }
}

class termmem{
    Stack mem;
    this(){mem=new Stack;}

    uint cell(uint addr) { return mem.data[addr]; }
    uint head(uint addr) { return cell(deref(addr)); }

    uint deref(uint addr) {
        for(;;) {
            uint c=mem.data[addr];
            if(0!=(c & 0xf000_0000)) break;
            if(c==addr) break;
            addr=c;
        }
        return addr;
    }
    uint var() {
        uint d=mem.length;
        mem.push(d);
        return d;
    }
    uint f(uint fnId, uint[] arg...) { return f_(fnId,arg); }
    uint f_(uint fnId, uint[] arg) {
        uint a=fnId>>28;
        assert(a>0x8);
        a-=0x8;
        assert(a==arg.length);
        uint r=mem.length;
        mem.push(fnId);
        for(uint i=0; i<a; i++) {
            uint w=arg[i];
            uint t=w>>28;
            assert(0==t || 0x8==t);
            mem.push(w);
        }
        return r;
    }

    uint copyfskeleton(uint _addr)
    {
        uint r(uint a) {
            a=deref(a);
            uint c=head(a);
            uint t=c>>28;
            if(t==0 || t==0x8) return var();
            t=t&7;
            uint d=mem.length;
            mem.push(c);
            mem.pushn(t);
            for(int i=1; i<=t; i++) {
// FAILS:
      mem.data[d+i]=r(a+i);
// WORKS:
      //uint rr=r(a+i); mem.data[d+i]=rr;
            }
            return d;
        }
        return r(_addr);
    }
}

void main()
{
    termmem T=new termmem;
    uint S(uint x) { return T.f(0x9000_0000,x); }
    uint P(uint x, uint y) { return T.f(0xa000_0000,x,y); }
    uint x=T.var;
    uint y=T.var;
    uint t=S(P(S(S(x)),x));
    uint s=S(P(S(S(x)),S(x))); // if commented out, bad behaviour disappears
    uint u=T.copyfskeleton(t);
    assert(T.mem.data[0x17]==0x18);
}

-- 
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