This is the mail archive of the gcc-prs@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

c++/91: Re: implicit assignment operator and copy constructor



>Number:         91
>Category:       c++
>Synopsis:       implicit assignment operator and copy constructor
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    unassigned
>State:          open
>Class:          wrong-code
>Submitter-Id:   net
>Arrival-Date:   Thu Mar 09 01:56:01 PST 2000
>Closed-Date:
>Last-Modified:
>Originator:     Wolfgang Sepp <wolfgang.sepp@informatik.uni-ulm.de>
>Release:        2.95.2
>Organization:
Uni-Ulm
>Environment:
>Description:
 Original-Message-ID: <36C83408.6C1E7CCA@informatik.uni-ulm.de>
 Date: Mon, 15 Feb 1999 15:49:44 +0100
 
 Bug or stdc++ feature?

 1) Environment: 
    - Linux 2.0.32 i586 and also on SunOS 5.6 sun4u 
    - egcs-2.91.57 (1.1), egcs 1.0.2, g++ 2.7.2.1

 2) Short description: 
    The implicitly defined copy constructor and assignment operator do
 not
    distinguish between "const B&" and "B&" arguments. Both functions
 call the
    non-const version --that is "operator=(A&)" and "A(A&)"-- of the
    function defined in the superclasses.



 example code:
 ---------------------------------------------------------------------
 #include<iostream>

 class A
 {
 public:
   A() {}

   A(       A& arg) 
   { cout << "called    A(      A&)" << endl; }

   A( const A& arg)
   { cout << "called    A(const A&)" << endl; }

   A& operator=(       A& ) 
   { cout << "called A::=(      A&)" << endl; return *this; }

   A& operator=( const A& ) 
   { cout << "called A::=(const A&)" << endl; return *this; }
 };

 class B : public A
 {
 public:
   B() {}
 };

 void foo( A& )
 {
   cout << "called  foo(      A&)" << endl;
 }

 void foo( const A& )
 {
   cout << "called  foo(const A&)" << endl;
 }


 int main()
 {
   const A a0;
   cout << "A(cA)  : ";  A a1(a0);
   cout << "A(A )  : ";  A a2(a1);
   const B b0;
   cout << "B(cB)  : ";  B b1(b0);
   cout << "B(B )  : ";  B b2(b1);

   cout << "A= cA  : ";  a1= a0;
   cout << "A= A   : ";  a1= a2;
   cout << "B= cB  : ";  b1= b0;
   cout << "B= B   : ";  b1= b2;
   cout << "foo(cB): ";  foo(b0);
   cout << "foo(B ): ";  foo(b2);

   return 0;
 }
 ---------------------------------------------------------------------



 The program produces the output:
 ---------------------------------------------------------------------
 A(cA)  : called    A(const A&)
 A(A )  : called    A(      A&)
 B(cB)  : called    A(      A&)
 B(B )  : called    A(      A&)
 A= cA  : called A::=(const A&)
 A= A   : called A::=(      A&)
 B= cB  : called A::=(      A&)
 B= B   : called A::=(      A&)
 foo(cB): called  foo(const A&)
 foo(B ): called  foo(      A&)
 ---------------------------------------------------------------------


 description:

 line 3,7 of the output: 
   A call of the implicitly defined assignment operator and copy
   constructor is always mapped to the function defined in the
   superclass with non-const arguments. Thus it neglects non-const and
   const arguments.

 line 9,10 of the output: 
   When an explicitely defined function is called with a subclass of
   the argument then this call is correctly mapped to appropriate
   functions (with either const or non-const arguments).


 output of the compilation command
 /usr/local/bin/g++ -v -Wall -o bug bug.cc
 ---------------------------------------------------------------------
 /usr/local/bin/g++ -v -Wall -o bug bug.cc
 Reading specs from
 /usr/local/lib/gcc-lib/i586-pc-linux-gnulibc1/egcs-2.91.57/specs
 gcc version egcs-2.91.57 19980901 (egcs-1.1 release)
  /usr/local/lib/gcc-lib/i586-pc-linux-gnulibc1/egcs-2.91.57/cpp
 -lang-c++ -v -undef -D__GNUC__=2 -D__GNUG__=2 -D__cplusplus
 -D__GNUC_MINOR__=91 -D__ELF__ -Dunix -Dlinux -D__ELF__ -D__unix__
 -D__linux__ -D__unix -D__linux -Asystem(posix) -D__EXCEPTIONS -Wall
 -Asystem(unix) -Acpu(i386) -Amachine(i386) -Di386 -D__i386 -D__i386__
 -Di586 -Dpentium -D__i586 -D__i586__ -D__pentium -D__pentium__ bug.cc
 /tmp/cc2EMhj1.ii
 GNU CPP version egcs-2.91.57 19980901 (egcs-1.1 release) (i386
 Linux/ELF)
 #include "..." search starts here:
 #include <...> search starts here:
  /usr/local/include/g++
  /usr/local/include
  /usr/local/i586-pc-linux-gnulibc1/include
  /usr/local/lib/gcc-lib/i586-pc-linux-gnulibc1/egcs-2.91.57/include
  /usr/include
 End of search list.
  /usr/local/lib/gcc-lib/i586-pc-linux-gnulibc1/egcs-2.91.57/cc1plus
 /tmp/cc2EMhj1.ii -quiet -dumpbase bug.cc -Wall -version -o
 /tmp/ccSg10e2.s
 GNU C++ version egcs-2.91.57 19980901 (egcs-1.1 release)
 (i586-pc-linux-gnulibc1) compiled by GNU C version egcs-2.91.57 19980901
 (egcs-1.1 release).
  as -V -Qy -o /tmp/cc9ha41n.o /tmp/ccSg10e2.s
 GNU assembler version 2.9.1 (i586-linux), using BFD version 2.9.1.0.7
  /usr/local/lib/gcc-lib/i586-pc-linux-gnulibc1/egcs-2.91.57/collect2 -m
 elf_i386 -dynamic-linker /lib/ld-linux.so.1 -o bug /usr/lib/crt1.o
 /usr/lib/crti.o
 /usr/local/lib/gcc-lib/i586-pc-linux-gnulibc1/egcs-2.91.57/crtbegin.o
 -L/usr/local/lib/gcc-lib/i586-pc-linux-gnulibc1/egcs-2.91.57
 -L/usr/local/i586-pc-linux-gnulibc1/lib -L/usr/local/lib /tmp/cc9ha41n.o
 -lstdc++ -lm -lgcc -lc -lgcc
 /usr/local/lib/gcc-lib/i586-pc-linux-gnulibc1/egcs-2.91.57/crtend.o
 /usr/lib/crtn.o
 -----------------------------------------------------------------------------------


 any comments are welcome,

 wolfgang
 (wsepp@neuro.informatik.uni-ulm.de)

 [MvL 20000309: gcc now generates
 A(cA)  : called    A(const A&)
 A(A )  : called    A(      A&)
 B(cB)  : called    A(const A&)
 B(B )  : called    A(const A&)
 A= cA  : called A::=(const A&)
 A= A   : called A::=(      A&)
 B= cB  : called A::=(      A&)
 B= B   : called A::=(      A&)
 foo(cB): called  foo(const A&)
 foo(B ): called  foo(      A&)
 which is still incorrect for the assignment operator.
 }

>How-To-Repeat:
>Fix:
>Release-Note:
>Audit-Trail:
>Unformatted:

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]