[comp.lang.c++] two bugs in cfront 1.2.1

mikpe@lillefix.ida.liu.se (Mikael Pettersson) (10/30/89)

We're still using cfront 1.2.1. An upgrade to 2.0 doesn't seem to be
imminent :-( so spare me the "fixed in 2.0" comments.

Anyway, I've come across two bugs and I'm kind of hoping for someone
who knows their way around the source better than I do to give me some
hints on how to fix them.

1) Reference members in a struct must be initialized by a constructor,
but cfront dies with a SIGSEGV when compiling the initialization code.
E.g:
	struct foo {
		int& bar;
		foo(int& fie) : bar(fie) {}	// this line causes a SIGSEGV
	};

I tracked this one down to a NULL ptr dereference in expr::print() (print.c)
where ASSIGN falls through to the usual case for binary operators and has just
printed the left operand and the operator:
  
		if (e1->tp!=e2->tp && e2->base!=ZERO) {
			// cast, but beware of int!=long etc.
			Ptype t1 = e1->tp;
		cmp:
			switch (t1->base) {

When initializing reference members, e1->tp is 0, causing a trap in the
switch() head. My fix was to redo the test as:
  
		if (e1->tp && e1->tp!=e2->tp && e2->base!=ZERO) {
			// etc.

Not a pretty patch, especially since I don't fully understand the _cause_
of the bug.

2) Under certain circumstances, the initialization of temporary values is
done incorrectly:

	struct Cont {
		virtual int operator()();
	};
	struct Y : Cont {
		Y();
		int operator()();
	};
	int P_While() {
		return Y()();	// apparently too complex
	}

The code generated for that last function is (edited for readability):

	/* <<cfront 1.2.1 2/16/87>> */
	// stuff deleted
	int P_While (){ 
	struct Y _au0__K2 ;	// BUG
	{ 
	struct Y _au0__V1 ;
	return ( (_au0__K2 = ( _Y__ctor ( & _au0__V1 ) , (& _au0__V1 )) ),
		 (*(((int (*)())(*_au0__K2 -> _Cont__vptr ))))(_au0__K2 )  ) ;
	}
	}

Since, somehow, cfront "forgot" to turn _au0__K2 into a struct Y*, there are
two errors in the return statement: first, the initialization tries to assign
a struct Y* to a struct Y, and second: the argument to the virtual function
(to become "this") should be a struct Y*, not a struct Y.

If one simplifies the function to:

	int P_While() {
		Y teta;
		return teta();
	}

then everything works out as it should.

Any ideas? I haven't got a clue on where to start looking..

/Mike
-- 
Mikael Pettersson, Dept of Comp & Info Sci, University of Linkoping, Sweden
email: mpe@ida.liu.se or ...!{mcsun,munnari,uunet,unido,...}!sunic!liuida!mpe