🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

2 total messages Started by Fergus Henderson Fri, 03 Nov 1995 04:04
Re: auto_ptr<T> as function return type
#2404
Author: Fergus Henderson
Date: Fri, 03 Nov 1995 04:04
97 lines
3484 bytes
"ian (i.) willmott" <willmott@bnr.ca> writes:

>matt@cyclops5.berkeley.edu (Matt Austern) wrote:
>>If a function returns an auto_ptr as an rvalue, it can't be used as
>>the argument to a function that expects a non-const reference.  There
>>are ways to get around this, but they're all a bit clumsy.
>
>So the problem is that rvalues cannot be passed as non-const reference
>parameters?

That's right.

>Can you call a non-const member function on an object rvalue?

Yes.

>If so, isn't that an inconsistency, since member functions are passed an
>implicit reference to the object they are called for?

You got it ;-)

>What part, if any, of the following code is legal under the draft standard?
>
>class X {
>    int i;
>public:
>    X(int);
>    X(X &);
>    int get(void);
>    void set(int);
>};
>
>X f(void);
>void g1(X &);
>void g2(const X &);
>
>void h(int i)
>{
>    X x(f());     // 1 - illegal?
>
>    f().set(i);   // 2 - legal?
>    g1(f());      // 3 - illegal?
>    g2(f());      // 4 - legal?
>}

Yes, 1 and 3 are ill-formed ("illegal"), while 2 and 4 are fine.

>I couldn't tell from sections [basic.lval] and [dcl.init.ref]
>of the April draft (maybe this has changed in the September version)
>exactly what the rule is

Here's what the April draft says.

|   5.2.2  Function call                                       [expr.call]
| 
| 3 When a function is called, each parameter (_dcl.fct_)  shall  be  ini-
|   tialized  (_dcl.init.ref_, _class.copy_, _class.ctor_) with its corre-
|   sponding argument.

As far as I can tell, this rule applies to copy constructors, which are
after all a special type of member function.  Since the argument
of a copy constructor is a reference, we next consult [dcl.init.ref]:

|   8.5.3  References                                       [dcl.init.ref]
| 
| 5 A reference to type "cv1 T1" is initialized by an expression  of  type
|   "cv2 T2" as follows:
| 
|   --If  the initializer expression is an lvalue ...
...
| 8
|   --Otherwise,  the  reference  shall  be  to  a non-volatile const type
|     (i.e., cv1 shall be const).

This seems pretty clear to me - for a non-const reference, the
initializer must be an lvalue.  (If there was any doubt as to whether
this rule is intended to apply to copy constructors, it should be
dispelled by footnote 10 in this section.)

>My Cfront v3.03 compiler (HP) calls line 3 an anachronism, but doesn't mind
>the others.

Yes, there are quite a few compilers that detect the error in line 3
but fail to detect the error in line 1.  But I think these compilers
are just buggy; I think the draft standard definitely makes line 1
ill-formed.

--
Fergus Henderson             	WWW: http://www.cs.mu.oz.au/~fjh
fjh@cs.mu.oz.au              	PGP: finger fjh@128.250.37.3


---
[ comp.std.c++ is moderated.  Submission address: std-c++@ncar.ucar.edu.
  Contact address: std-c++-request@ncar.ucar.edu.  The moderation policy
  is summarized in http://dogbert.lbl.gov/~matt/std-c++/policy.html. ]
Re: auto_ptr<T> as function return type
#2414
Author: James Kanze US/ESC 60/3/141 #407...
Date: Fri, 03 Nov 1995 19:23
79 lines
3644 bytes
In article <9530713.8851@mulga.cs.mu.OZ.AU> fjh@munta.cs.mu.OZ.AU
(Fergus Henderson) writes:

|> "ian (i.) willmott" <willmott@bnr.ca> writes:

|> >What part, if any, of the following code is legal under the draft standard?

|> >
|> >class X {
|> >    int i;
|> >public:
|> >    X(int);
|> >    X(X &);
|> >    int get(void);
|> >    void set(int);
|> >};
|> >
|> >X f(void);
|> >void g1(X &);
|> >void g2(const X &);
|> >
|> >void h(int i)
|> >{
|> >    X x(f());     // 1 - illegal?
|> >
|> >    f().set(i);   // 2 - legal?
|> >    g1(f());      // 3 - illegal?
|> >    g2(f());      // 4 - legal?
|> >}

|> Yes, 1 and 3 are ill-formed ("illegal"), while 2 and 4 are fine.

|> >I couldn't tell from sections [basic.lval] and [dcl.init.ref]
|> >of the April draft (maybe this has changed in the September version)
|> >exactly what the rule is

    [...]
|> This seems pretty clear to me - for a non-const reference, the
|> initializer must be an lvalue.  (If there was any doubt as to whether
|> this rule is intended to apply to copy constructors, it should be
|> dispelled by footnote 10 in this section.)

|> >My Cfront v3.03 compiler (HP) calls line 3 an anachronism, but doesn't mind

|> >the others.

|> Yes, there are quite a few compilers that detect the error in line 3
|> but fail to detect the error in line 1.  But I think these compilers
|> are just buggy; I think the draft standard definitely makes line 1
|> ill-formed.

One question: in the compilers which do detect the error in line 3,
but not in line 1, what is the actual code generated.  I suspect it is
not so much a case of the compiler binding a temporary to a non-const
reference, but one of the compiler not accepting
auto_ptr<T>::auto_ptr( auto_ptr<T>& ) as a copy constructor (since it
cannot be called), and *generating* its own copy constructor (with a
const parameter).

If this is the case, not only do you not get an error in the case of
line 1, you also get wrong code; both the temporary and the declared
variable think that they own the object pointed to.  When the
temporary is destructed (at the end of the statement), it will delete
the object, but the declared variable will continue to point to it.

I don't believe that the ARM was completely clear on this point; such
compilers may simply be implementing their interpretation of the ARM.
I would suggest, however, that given the above senario, the
implementors put this update at the highest priority.
--

James Kanze         Tel.: (+33) 88 14 49 00        email: kanze@gabi-soft.fr
GABI Software, Sarl., 8 rue des Francs-Bourgeois, F-67000 Strasbourg, France
Conseils en informatique industrielle --
                              -- Beratung in industrieller Datenverarbeitung
---
[ comp.std.c++ is moderated.  Submission address: std-c++@ncar.ucar.edu.
  Contact address: std-c++-request@ncar.ucar.edu.  The moderation policy
  is summarized in http://dogbert.lbl.gov/~matt/std-c++/policy.html. ]
Thread Navigation

This is a paginated view of messages in the thread with full content displayed inline.

Messages are displayed in chronological order, with the original post highlighted in green.

Use pagination controls to navigate through all messages in large threads.

Back to All Threads