From: anders@elvin.UUCP (Anders Franzen)
Subject: g++ 2.1 global object instance initialization problem
Organization: GNUs Not Usenet
Distribution: gnu
Date: Mon, 6 Apr 1992 23:15:01 GMT

BUG REPORT
--------------
FROM:
--
Anders Franzen                  | TEL: +1 904/422-3574  | 
Software Engineer               | FAX: +1 904/386-2562  |
TechnoTeacher, Inc.             |                       |
1810 High Road                  | <anders@cmr.fsu.edu>  |
Tallahassee, FL 32303           |                       |


PROGRAM: g++  SUBPROGRAM: cc1plus
VERSION: 2.1
 SYSTEM: Sun 4/40 (IPC)
     OS: SunOS 4.1.1 Rev B.

LOCAL INSTALLATION:
gcc 2.1 was installed by patching the 2.0 distribution
with the gcc.diff-2.0-2.1 file. The following commands were then
issued to build and install the new release:

  configure sun4
  make LANGUAGES=c
  make stage1
  make CC=stage1/gcc CFLAGS="-g -O -Bstage1/"
  make stage2
  make CC=stage2/gcc CFLAGS="-g -O -Bstage2/"

  for file in *.o; do
  cmp $file stage2/$file
  done

  make CC=stage2/gcc install
  make install-fixincludes

All of the above commands were successful.

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

BUG DESCRIPTION:

The problem occurs when I try to use global instances of C++ objects
with constructors as initializers.

Here's an example of a global object array initialization. The
following C++ code example (which I condensed from a much larger source)
causes a signal 11, Segmentation fault, when compiled with g++ 2.1 on
my system.

-- Begin itest.cc

class X {
    int i1;
    int i2;
  public:
    X(
      int ii1,
      char ii2
      )
      {
	  i1 = ii1;
	  i2 = ii2;
      }
};

X x[] = { X(1, 2) };

-- End itest.cc

Here is an example g++ compilation of the above example:

  anders@scofield 3% g++ -v -c itest.cc
  Reading specs from /usr/local/lib/gcc-lib/sun4/2.1/specs
  gcc version 2.1
   /usr/local/lib/gcc-lib/sun4/2.1/cpp -lang-c++ -v -undef -D__GNUC__=2 -D__GNUG__=2 -D__cplusplus -Dsparc -Dsun -Dunix -D__sparc__ -D__sun__ -D__unix__ -D__sparc -D__sun -D__unix itest.cc /usr/tmp/cca06032.i
  GNU CPP version 2.1 (sparc)
   /usr/local/lib/gcc-lib/sun4/2.1/cc1plus /usr/tmp/cca06032.i -quiet -dumpbase itest.cc -version -o /usr/tmp/cca06032.s
  GNU C++ version 2.1 (sparc) compiled by GNU C version 2.1.
  /usr/local/bin/gcc: Internal compiler error: program cc1plus got fatal signal 11

I also ran gdb (V4.4) directly on cc1plus (using the options dictaded
by the -v output above), which gave me the following information:

Exception place as reported by gdb:
  #0  0xa162c in expand_call (exp=0x183060, ignore=0, modifier=EXPAND_SUM, target=0x0) at calls.c:759

Source code context in expand_call() (file calls.c) where it broke (=>
in the margin shows where the segmentation fault took place):

    /* In this loop, we consider args in the order they are written.
       We fill up ARGS from the front of from the back if necessary
       so that in any case the first arg to be pushed ends up at the front.  */

  #ifdef PUSH_ARGS_REVERSED
    i = num_actuals - 1, inc = -1;
    /* In this case, must reverse order of args
       so that we compute and push the last arg first.  */
  #else
    i = 0, inc = 1;
  #endif

    /* I counts args in order (to be) pushed; ARGPOS counts in order written.  */
    for (p = actparms, argpos = 0; p; p = TREE_CHAIN (p), i += inc, argpos++)
      {
  =>    tree type = TREE_TYPE (TREE_VALUE (p));

	args[i].tree_value = TREE_VALUE (p);

	/* Replace erroneous argument with constant zero.  */
	if (type == error_mark_node || TYPE_SIZE (type) == 0)
	  args[i].tree_value = integer_zero_node, type = integer_type_node;


gdb p command of various members of pointer "p":

(gdb) p p->common
$20 = {chain = 0x182fb0, type = 0x0, code = TREE_LIST, side_effects_flag = 0, constant_flag = 0, permanent_flag = 1, 
  addressable_flag = 0, volatile_flag = 0, readonly_flag = 0, unsigned_flag = 0, asm_written_flag = 0, used_flag = 0, 
  raises_flag = 0, static_flag = 0, public_flag = 0, private_flag = 0, protected_flag = 0, lang_flag_0 = 0, lang_flag_1 = 0, 
  lang_flag_2 = 0, lang_flag_3 = 0, lang_flag_4 = 0, lang_flag_5 = 0, lang_flag_6 = 0}

(gdb) p p->list
$21 = {common = {"\000\030/0\000\000\000\000\003 \000\000"}, purpose = 0x0, value = 0x0}

gdb p command of global variable "lineno", which yields the value 12.
This is where the global array is defined in the itest.cc source file.

(gdb) p lineno
$22 = 12

I would give more info from the debugger, but because of my lack of
exposure to the gcc internal code (basically about a day now) I think
I would probably be more obfuscatory than helpful.  I hope this is
somewhat useful, at least.

Thank you,

--Anders

Newsgroups: gnu.gcc.bug