Debug multiple binaries - Unix

This is a discussion on Debug multiple binaries - Unix ; Hi, I've a C++ program that has been compiled with "gcc -g". This program uses "syscall" to invoke another binary also compiled with "gcc -g". What I now want is to debug the invoked binary. I'm using gdb to debug ...

+ Reply to Thread
Results 1 to 8 of 8

Thread: Debug multiple binaries

  1. Debug multiple binaries

    Hi,

    I've a C++ program that has been compiled with "gcc -g". This
    program uses "syscall" to invoke another binary also compiled
    with "gcc -g". What I now want is to debug the invoked binary.

    I'm using gdb to debug the first program but didn't find any
    possibility to continue debugging of the second binary after
    its syscall invocation. So what I need is to make both
    binaries visible to gdb then set a breakpoint in the
    second program, run the first program and thus jump to the
    breakpoint after the second program has been invoked. Any ideas
    how to do that?

    Regards,
    Tim

  2. Re: Debug multiple binaries

    Tim Frink writes:

    > I've a C++ program that has been compiled with "gcc -g". This
    > program uses "syscall" to invoke another binary also compiled
    > with "gcc -g".


    Which 'syscall'? SYS_fork, SYS_execve, some other one?
    Or do you mean 'system(3)' call (which is entirely different thing) ?

    > What I now want is to debug the invoked binary.


    How you do that depends on how exactly the other process was invoked.
    One technique that works with any debugger, is to pass to the second
    process a command-line parameter, e.g. --hang, which would cause that
    process to wait forever. For example:

    int main(int argc, char *argv[])
    {
    bool hang = check_for_hang_param(argc, argv);
    while (hang) {
    sleep(1);
    }
    // rest of main
    }

    Then you can attach debugger to the second process (blocked in
    sleep()), set variable 'hang' to false, and proceed with your
    further debugging. [Unfortunately, sometimes that's too late,
    e.g. when you must debug early constructors and/or library
    initializers.]

    > I'm using gdb to debug the first program but didn't find any
    > possibility to continue debugging of the second binary after
    > its syscall invocation.


    If you mean 'system(3)' call, then newer versions of gdb have a
    'set follow-fork child', which might (on some platforms) allow you
    to attach to the child. However, you would not be able to set any
    breakpoints in your code yet, because the child is the shell. You'll
    have to wait until shell exec()s your process, and then you should
    be able to debug it. Generally, gdb in the past got easily confused
    when crossing exec(), and it is unlikely you'll have a "smooth"
    debugging session.

    > So what I need is to make both binaries visible to gdb


    I don't believe gdb is prepared to deal with multiple processes.
    If you really want to debug both processes at once, and having two
    separate gdb instances doesn't work for you, then maybe TotalView
    is the answer.

    Cheers,
    --
    In order to understand recursion you must first understand recursion.
    Remove /-nsp/ for email.

  3. Re: Debug multiple binaries

    On Wed, 17 Oct 2007 20:31:25 -0700, Paul Pluzhnikov wrote:

    > Which 'syscall'? SYS_fork, SYS_execve, some other one?
    > Or do you mean 'system(3)' call (which is entirely different thing) ?


    Sorry, I meant "system".

    > How you do that depends on how exactly the other process was invoked.
    > One technique that works with any debugger, is to pass to the second
    > process a command-line parameter, e.g. --hang, which would cause that
    > process to wait forever. For example:
    >
    > int main(int argc, char *argv[])
    > {
    > bool hang = check_for_hang_param(argc, argv);
    > while (hang) {
    > sleep(1);
    > }
    > // rest of main
    > }


    That's a possible solution. Thank you.


    > If you mean 'system(3)' call, then newer versions of gdb have a
    > 'set follow-fork child', which might (on some platforms) allow you
    > to attach to the child. However, you would not be able to set any
    > breakpoints in your code yet, because the child is the shell. You'll
    > have to wait until shell exec()s your process, and then you should
    > be able to debug it. Generally, gdb in the past got easily confused
    > when crossing exec(), and it is unlikely you'll have a "smooth"
    > debugging session.


    Unfortunately, "set follow-fork child"

    BTW, I have problem with breakpoints in constructors. When I
    set a breakpoint there in gdb, the constructor will be executed
    (I've inserted some printf) but the program execution does not
    break at that point. Any ideas why?

    Regards,
    Tim

  4. Re: Debug multiple binaries

    Tim Frink wrote:

    > BTW, I have problem with breakpoints in constructors. When I
    > set a breakpoint there in gdb, the constructor will be executed
    > (I've inserted some printf) but the program execution does not
    > break at that point. Any ideas why?


    g++ outputs two versions of a constructor.
    Perhaps gdb is setting the breakpoint in the wrong one?
    Do you have recent versions of g++ and gdb?

  5. Re: Debug multiple binaries

    Spoon writes:

    > Tim Frink wrote:
    >
    >> BTW, I have problem with breakpoints in constructors.


    > g++ outputs two versions of a constructor.


    If the constructor is inline, gcc outputs many more than 2 versions --
    it emits 2 versions into every compilation unit that #includes
    the definition of that constructor.

    On some, but not all, platforms, these duplicate instances are
    merged into one by the linker.

    > Perhaps gdb is setting the breakpoint in the wrong one?


    Likely. A "trick" that often works is to do 'rbreak SomeClass'
    to set a breakpoint on every instance of every method of SomeClass.
    Then run the exe, and delete all the breakpoints that aren't
    interesting, as you hit them.

    Cheers,
    --
    In order to understand recursion you must first understand recursion.
    Remove /-nsp/ for email.

  6. Re: Debug multiple binaries

    On Thu, 18 Oct 2007 15:53:37 +0200, Spoon wrote:

    > Do you have recent versions of g++ and gdb?


    I'm using gcc 3.4.6. Unfortunately, I can't switch to
    newer versions since some of the code is not compatible.

  7. Re: Debug multiple binaries

    On Thu, 18 Oct 2007 21:41:55 -0700, Paul Pluzhnikov wrote:

    > If the constructor is inline, gcc outputs many more than 2 versions --
    > it emits 2 versions into every compilation unit that #includes
    > the definition of that constructor.


    How does gcc decide if the constructor will be inlined?
    And why does it insert 2 versions for each #include?g one?
    >
    > Likely. A "trick" that often works is to do 'rbreak SomeClass'
    > to set a breakpoint on every instance of every method of SomeClass.
    > Then run the exe, and delete all the breakpoints that aren't
    > interesting, as you hit them.


    I'm solved this by adding a new function that is called in the
    constructor. Each time this function with a breakpoint is entered
    I do an "up" and get the calling constructor.

  8. Re: Debug multiple binaries

    Tim Frink writes:

    > On Thu, 18 Oct 2007 21:41:55 -0700, Paul Pluzhnikov wrote:
    >
    >> If the constructor is inline, gcc outputs many more than 2 versions --
    >> it emits 2 versions into every compilation unit that #includes
    >> the definition of that constructor.

    >
    > How does gcc decide if the constructor will be inlined?


    I didn't say anything about 'gcc inlining'.
    I said: if *you* declared the constructor inline, i.e. like this:

    struct A { A() { /* body of ctor */ } ... };

    When you do that, gcc has no option but to emit a copy of the "body"
    into every compilation unit.

    > And why does it insert 2 versions for each #include?g one?


    There sometimes are 'in-charge' and 'not-in-charge' versions:
    http://www.sourceware.org/ml/gdb/2003-10/msg00015.html

    Cheers,
    --
    In order to understand recursion you must first understand recursion.
    Remove /-nsp/ for email.

+ Reply to Thread