This is the mail archive of the gcc-bugs@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]

Re: Instantiation of pure virtual class


Roger Leblanc wrote:

> Hi,
>
> I think I found a bug in g++ version 2.95.2 running on a Intel Linux box
> (Red Hat 6.1).
> Consider the following code:
>
> #include <iostream>
> #include <list>
> #include <algo.h>
> #include <assert.h>
>
> // Pure virtual class
> struct  BasePredicate
> {
>     virtual bool operator ()(int a) = 0;
> };
>
> struct DerivedPredicate : public BasePredicate
> {
>     bool operator ()(int a)
>     {
>         return a == 2;
>     }
> };
>
> int Find2(list<int> a_list, BasePredicate &p)
> {
>     list<int>::iterator iter = find_if(a_list.begin(), a_list.end(), p);
>
>     return (*iter);
> }
>
> int main (int argc, char *argv[])
> {
>     // Example taken from
> http://mrcadm1/silicongraphic/stl_doc/List.html
>     list<int> L;
>     L.push_back(0);
>     L.push_front(1);
>     L.insert(++L.begin(), 2);
>
>     DerivedPredicate my_predicate;
>     assert ( Find2( L, my_predicate ) == 2);
> }
>
> At first sight, it looks OK but the third parameter of the the STL
> function find_if is passed by copy and the parameter being declared in
> the header of Find2() is a pure virtual class. Therefore, the g++
> compiler should report an error saying that an abstract class cannot be
> instantiated. It doesn't. Instead, it compiles and links but crashes on
> run time caused by a pure virtual function call.

A simpler example that demonstrates the problem:

class C {
public:
    virtual void v () = 0;
};

class D : public C {
public:
    void v () {}
};

#ifdef TEMPLATE
template <typename E> void f (E);
#else
void f (C);
#endif

void
g (C& c) {
    f (c);
}

With -DTEMPLATE, 2.95.2 compiles it without even a warning.

> Moreover, if the base class in the example above was not pure virtual,
> the operator in the the derived class would never be called because the
> predicate in STL find_if() is passed by copy and since it is
> templatized, it creates THAT type of object, not the derived one. I
> don't know if it's a bug in STL or if it's part of the standard but it's
> a little ugly.

It's a part of the Standard (25.1.2).

> Roger Leblanc  Software Developer

Dima


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