🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Article View: gnu.g++.bug
Article #1767

G++ 1.34.1 named return values (and related 1.34.1 problems)

#1767
From: Doug Lea
Date: Sat, 18 Mar 1989 13:39
96 lines
3193 bytes
I think Michael's documentation was wrong (or at least misleading). If
you have a named return value, you should *only* return via `return'
or by falling-off-the-edge. (Otherwise, in your example, it says to
make tmp out of itself using A(A&), which is not very sensible.)  See
below. [Anyone wanting further rationale for this construct should see
my recent comp.lang.c++ postings.]

A few other notes about my experience with 1.34.1+ (1.34.1 plus Michael's
2 posted patches) on a vax750, 4.3BSD:

The -felide-constructors switch seems buggy.  All libg++ problems I've
been able to diagnose when testing this switch appear due to the kind
of local-variable-trashing behavior shown below.  Note, however, that
constructs both of the form `var a = fun()' and `var a(fun())' now, in
1.34.1, produce the same results (no temps!) with or without this switch.

Using the -fsave-memoized switch also seems buggy. Several libg++
tests (test5, intList.cc) fail to compile with this switch.

By the way, in the example, if you #include <stream.h>, you ought to
use `cout.form(...)' (or `cout << form(...)') instead of `printf' to
ensure proper flushing of output on program termination (on most
machines, this apparently only matters if you are redirecting output).


-Doug

------ file A.cc (a revision of rjc's example)

#include <stream.h>

struct A {
	int i;
	A(int x) { cout.form("A(%d)\n", x); i = x; };
	A(A& x) { cout.form("A(A& x), x.i == %d\n", x.i); i = x.i; };
	~A(void) { cout.form("~A(%d)\n", i); };
	void operator += (A& x) { cout.form("+=(%d, %d)\n", i, x.i); i += x.i; };
};

A foo () return tmp(4); // essentially equivalent to `tmp=4', 
                        // but explicitly use a constr. for clarity!
{
	cout.form("foo(void), tmp.i == %d\n", tmp.i);
	return;             // *not* `return tmp'
}

main()
{
	A bar = 5;
	bar += foo();
	cout.form("main(), bar.i == %d\n", bar.i);
    A baz = foo();
	cout.form("main(), baz.i == %d\n", baz.i);
    A baz_con(foo());
	cout.form("main(), baz_con.i == %d\n", baz_con.i);
}

-------- A correct compile/run without -felide-constructors

R>g++ -g -O -finline-functions A.cc
R>a.out
A(5)
A(4)
foo(void), tmp.i == 4
+=(5, 4)
~A(4)
main(), bar.i == 9
A(4)
foo(void), tmp.i == 4
main(), baz.i == 4
A(4)
foo(void), tmp.i == 4
main(), baz_con.i == 4
~A(4)
~A(4)
~A(9)

----------- with -felide-constructors

R>g++ -g -O -finline-functions -felide-constructors A.cc
R>a.out
A(5)
A(4)
foo(void), tmp.i == 4
+=(4, 4)                  # `bar' is trashed!
main(), bar.i == 8
A(4)
foo(void), tmp.i == 4
main(), baz.i == 4
A(4)
foo(void), tmp.i == 4
main(), baz_con.i == 4
~A(4)
~A(4)
~A(8)
Technical Details
Message-ID: <8903181339.AA27932@rocky>
Path: arc1-ca.pugleaf.net!utzoo!telly!lethe!dptcdc!attcan!uunet!tut.cis.ohio-state.edu!ROCKY.OSWEGO.EDU!dl
References: <21944@shemp.CS.UCLA.EDU>

Show Full Headers
Complete Article Headers
Path: arc1-ca.pugleaf.net!utzoo!telly!lethe!dptcdc!attcan!uunet!tut.cis.ohio-state.edu!ROCKY.OSWEGO.EDU!dl
From: dl@ROCKY.OSWEGO.EDU (Doug Lea)
Newsgroups: gnu.g++.bug
Subject: G++ 1.34.1 named return values (and related 1.34.1 problems)
Message-ID: <8903181339.AA27932@rocky>
Date: 18 Mar 89 13:39:42 GMT
References: <21944@shemp.CS.UCLA.EDU>
Sender: daemon@tut.cis.ohio-state.edu
Reply-To: dl@rocky.oswego.edu
Distribution: gnu
Organization: GNUs Not Usenet
Lines: 96