0

in mongodb, class cursor is defined as 'Cursor : boost::noncopyable', and then there are many class which are derived from it. I want to know for a given operation from client, which XXXCursor was used. so I want to set a breakpoint on Cursor::Cursor. but failed.

(gdb) b mongo::Cursor::Cursor
the class mongo::Cursor does not have any method named Cursor
Hint: try 'mongo::Cursor::Cursor<TAB> or 'mongo::Cursor::Cursor<ESC-?>
(Note leading single quote.)
Make breakpoint pending on future shared library load? (y or [n]) n

(gdb) ptype mongo::Cursor
type = class mongo::Cursor : private boost::noncopyable_::noncopyable {
  public:
    ~Cursor(int);
    virtual bool ok(void);
    bool eof(void);
    virtual mongo::Record * _current(void);
    virtual mongo::BSONObj current(void);
    virtual mongo::DiskLoc currLoc(void);
    virtual bool advance(void);
    virtual mongo::BSONObj currKey(void) const;
    ....
}
(gdb) list mongo::Cursor::Cursor
**the class mongo::Cursor does not have any method named Cursor
Hint: try 'mongo::Cursor::Cursor<TAB> or 'mongo::Cursor::Cursor<ESC-?>**
(Note leading single quote.)

But I wrote a similar program

#include <iostream>
#include <boost/utility.hpp>
class Base : boost::noncopyable {
public:
    void printx() {std::cout<< getx() <<"\n" ;}
    virtual int getx()=0;
};


class P : public Base {
public:
    int x;
    virtual int getx() { return x*3;}
    P(int c){ x= c;}
};

int main(){
    P p(2);
    p.printx();
    return 0;
}

I can set breakpoint on Base::Base sucessfully.

do you have any idea why I can't set breakpoint on mongo::Cursor::Cursor ?

mongo::Cursor was definied here: https://github.com/mongodb/mongo/blob/master/src/mongo/db/cursor.h

zhihuifan
  • 1,093
  • 2
  • 16
  • 30

1 Answers1

0

As for your example. If I compile it like this:

g++ -O0 -g -m64 -I ./boost_1_53_0 main.cpp

I can set a breakpoint on Base::Base and I see Base::Base as a symbol:

>nm -C a.out | grep Base::Base
0000000000400a4e W Base::Base()

If I compile compile it like this (with optimization level O2):

g++ -O2 -g -m64 -I ./boost_1_53_0 main.cpp

I don't see Base::Base as a symbol:

>nm -C a.out | grep Base::Base
>

And can't set a breakpoint:

(gdb) b Base::Base
the class Base does not have any method named Base
Hint: try 'Base::Base<TAB> or 'Base::Base<ESC-?>

So as a first step make sure that there is mongo::Cursor::Cursor as a symbol in your program or shared library. It can be optimized out.

  • FWIW - it isn't enough to look at "nm" output. gdb can also use debuginfo to set breakpoints on inlined functions. For that you have to dig through the "readelf -wi" output. Offhand I don't know the problem in this situation. There are many possible things - compiler bug, gdb bug, obscure intentional behavior, etc. – Tom Tromey Aug 13 '13 at 14:13
  • Tom, in this example Base::Base() is not defined by a user. My point is that Base::Base() is implicitly defined on the level O0 by a compiler and it is empty. On the level O2 the compiler get rid of it completely so it is not inlined. –  Aug 14 '13 at 06:45
  • Thanks both of you! I build the mongod with 'scons -Q --d all'. I do see the output contains -O0. like: g++ -o build/linux2/d/mongo/db/jsobj.o -c -Wnon-virtual-dtor -Woverloaded-virtual -fPIC -fno-strict-aliasing -ggdb -pthread -Wall -Wsign-compare -Wno-unknown-pragmas -Winvalid-pch -Werror -pipe -O0 -fstack-protector -Wno-unused-function -Wno-deprecated-declarations -fno-builtin-memcmp -DBOOST_ALL_NO_LIB -D_SCONS -DMONGO_EXPOSE_MACROS -DSUPPORT_UTF8 -D_FILE_OFFSET_BITS=64 -DMONGO_HAVE_HEADER_UNISTD_H -DMONGO_HAVE_EXECINFO_BACKTRACE ...src/mongo/db/jsobj.cpp so maybe have other reason. – zhihuifan Aug 15 '13 at 06:46