[gnu.g++.bug] incorrect code generated by g++ 1.32

scott@CS.ROCHESTER.EDU (01/23/89)

BUG REPORT

tm.h = tm-sun3.h
md = m68k.md
aux-output.c = output-m68k.c

sun 3-50, Sun Unix 3.4

summary:
    when using __user_new, and passing it a struct parameter that has a
    constructor, consecutive calls to 'new' result in INCORRECT CODE

g++ version 1.32

---------------------------

cedar> cat unew.cc
struct user_new_arg {
    unsigned long contents;
    inline user_new_arg(int i) { contents = i; }
}; 
void* __user_new (int size, int x,  user_new_arg y)
    // this routine is for use with g++'s special operator new support
{
    printf ("user_new args: size %d, %d %d\n", size, x, y);
    return (void*) malloc (size);
}

struct simple_channel {
    int x[4];
public:
    simple_channel (int a, int b, int c);
};

simple_channel::simple_channel (int a, int b, int c)
{
    printf ("constructor args: %d %d %d\n", a, b, c);
}

main ()
{
    user_new_arg foo (234);
    simple_channel* chan1 = new {123, foo} simple_channel (1, 2, 3);
    foo.contents = 567;
    simple_channel* chan2 = new {456, foo} simple_channel (4, 5, 6);
}
cedar> g++ -v -g -W unew.cc
g++ version 1.32.0
 /usr/su/lib/gcc-cpp+ -+ -v -undef -D__GNU__ -D__GNUG__ -Dmc68000 -Dsun -Dunix
unew.cc /tmp/cca19060.cpp
GNU CPP version 1.32.0
 /usr/su/lib/gcc-c++ /tmp/cca19060.cpp -quiet -dumpbase unew.cc -W -noreg
-version -G -o /tmp/cca19060.s
GNU C++ version 1.32.0 (68k, MIT syntax) compiled by CC.
 as -mc68020 /tmp/cca19060.s -o unew.o
 /usr/su/lib/gcc-ld++ -C /usr/su/lib/crt0+.o /lib/Mcrt1.o unew.o -lg++
/usr/su/lib/gcc-gnulib+ -lg -lc
cedar> a.out
user_new args: size 16, 123 234
constructor args: 1 2 3
user_new args: size 16, 456 567
constructor args: 144044 1 2
cedar>

----------------------------

This program compiles correctly with v. 1.25.1:

maple> g++ -v -g -W unew.cc
g++ version 1.25.1
 /usr/su/lib/cpp+ -v -undef -D__GNU__ -D__GNUG__ -Dmc68000 -Dsun -Dunix unew.cc
/tmp/cca00273.cpp
GNU CPP version 1.25.1
 /usr/su/lib/c++ /tmp/cca00273.cpp -quiet -dumpbase unew.cc -W -noreg -version
-G -o /tmp/cca00273.s
GNU C++ version 1.25.1 (68k, MIT syntax) compiled by CC.
In function void *__user_new (int, int, struct user_new_arg):
unew.cc:8: warning: implicit declaration of function `printf'
unew.cc:9: warning: implicit declaration of function `malloc'
 as -mc68020 /tmp/cca00273.s -o unew.o
 /usr/su/lib/ld++ -C /usr/su/lib/crt0+.o unew.o -lg++ /usr/su/lib/gnulib+ -lg
-lc
maple> a.out
user_new args: size 16, 123 234
constructor args: 1 2 3
user_new args: size 16, 456 567
constructor args: 4 5 6
maple>

-------------------------------

Eliminating the constructor for struct user_new_arg also does the trick:

cedar> diff unew.cc good2.cc
3d2
<   inline user_new_arg(int i) { contents = i; }
25c24,25
<   user_new_arg foo (234);
---
>   user_new_arg foo;
>   foo.contents = 234;
cedar> g++ -v -g -W good2.cc
g++ version 1.32.0
 /usr/su/lib/gcc-cpp+ -+ -v -undef -D__GNU__ -D__GNUG__ -Dmc68000 -Dsun -Dunix
good2.cc /tmp/cca19109.cpp
GNU CPP version 1.32.0
 /usr/su/lib/gcc-c++ /tmp/cca19109.cpp -quiet -dumpbase good2.cc -W -noreg
-version -G -o /tmp/cca19109.s
GNU C++ version 1.32.0 (68k, MIT syntax) compiled by CC.
 as -mc68020 /tmp/cca19109.s -o good2.o
 /usr/su/lib/gcc-ld++ -C /usr/su/lib/crt0+.o /lib/Mcrt1.o good2.o -lg++
/usr/su/lib/gcc-gnulib+ -lg -lc
cedar> a.out
user_new args: size 16, 123 234
constructor args: 1 2 3
user_new args: size 16, 456 567
constructor args: 4 5 6
cedar>