public inbox for gdb@sourceware.org
 help / color / mirror / Atom feed
From: Alexander Yermolovich <ayermolo@fb.com>
To: David Blaikie <dblaikie@gmail.com>
Cc: Jorge Gorbe Moya <jgorbe@google.com>,
	Sterling Augustine <saugustine@google.com>,
	"gdb@sourceware.org" <gdb@sourceware.org>
Subject: Re: GDB and debug fission
Date: Mon, 1 Feb 2021 20:07:52 +0000	[thread overview]
Message-ID: <BYAPR15MB247042506899838A30CEBBFFBFB69@BYAPR15MB2470.namprd15.prod.outlook.com> (raw)
In-Reply-To: <CAENS6Etv9hWsxComaOsqScEjjwQhJaPiFvQ3KrC7WpR9wsM9tw@mail.gmail.com>

I tried creating dwp, even without deleting dwo I see:
(gdb) ptype t1
No symbol "t1" in current context.
(gdb) start
Temporary breakpoint 1 at 0x4005ca: file main.cpp, line 3.
Starting program: /data/users/ayermolo/tasks/T81935790/main
warning: Loadable section ".note.gnu.property" outside of ELF segments
warning: Loadable section ".note.gnu.property" outside of ELF segments

Temporary breakpoint 1, main () at main.cpp:3
3 int main() { t1 v1; }
(gdb) ptype t1
No symbol "t1" in current context.

I guess it makes sense since I think gdb will just use dwp if it sees it in same directory.
With -Wl,--gdb-index I see same behavior as you. Everything gets resovled.

I see same behavior with TOT clang.

Alex
________________________________
From: David Blaikie <dblaikie@gmail.com>
Sent: Friday, January 29, 2021 5:06 PM
To: Alexander Yermolovich <ayermolo@fb.com>
Cc: Jorge Gorbe Moya <jgorbe@google.com>; Sterling Augustine <saugustine@google.com>; gdb@sourceware.org <gdb@sourceware.org>
Subject: Re: GDB and debug fission

Ah, you might need a dwp to reproduce this. Try building a dwp for the .dwo and deleting the dwo?



On Fri, Jan 29, 2021 at 4:42 PM Alexander Yermolovich <ayermolo@fb.com<mailto:ayermolo@fb.com>> wrote:
I tried it locally with:

struct t1 { int x; };

int main() { t1 v1; }
Using your commands, but with g++ (GCC) 8.4.1 20200928 (Red Hat 8.4.1-1)/gold and TOT clang++/lld.
GNU gdb (GDB) 9.1
For me it was able to resolve t1.
Some kind of regression with TOT gcc?

Alex
________________________________
From: David Blaikie <dblaikie@gmail.com<mailto:dblaikie@gmail.com>>
Sent: Friday, January 29, 2021 12:34 PM
To: Alexander Yermolovich <ayermolo@fb.com<mailto:ayermolo@fb.com>>; Jorge Gorbe Moya <jgorbe@google.com<mailto:jgorbe@google.com>>
Cc: Sterling Augustine <saugustine@google.com<mailto:saugustine@google.com>>; gdb@sourceware.org<mailto:gdb@sourceware.org> <gdb@sourceware.org<mailto:gdb@sourceware.org>>
Subject: Re: GDB and debug fission

Well, I found one place where the index seems necessary: Type units:

$ g++-tot a.cpp -fdebug-types-section -gdwarf-4 -gsplit-dwarf -c
$ g++-tot a.o -fuse-ld=gold
$ gdb ./a.out
...
(gdb) ptype t1
No symbol "t1" in current context.
(gdb) start
Temporary breakpoint 1 at 0x401106: file a.cpp, line 3.
Starting program: /usr/local/google/home/blaikie/dev/scratch/a.out

Temporary breakpoint 1, main () at a.cpp:3
3       int main() { t1 v1; }
(gdb) ptype t1
type = const float

But if you add -Wl,--gdb-index to the link command - it works correctly, with t1 being found and rendered.

On Thu, Jan 7, 2021 at 7:16 PM David Blaikie <dblaikie@gmail.com<mailto:dblaikie@gmail.com>> wrote:


On Thu, Jan 7, 2021 at 6:13 PM Alexander Yermolovich via Gdb <gdb@sourceware.org<mailto:gdb@sourceware.org>> wrote:
Thanks for clarification.
Yep I saw LLD builds gdb_index using gnu-pubnames. It just wasn't clear to me if gdb needs it with split-dwarf. I saw a comment on one of llvm reviews from couple years ago about it, but things might have changed since then. So thought I would ask. 🙂

Without gdb_index and gnu_pubnames what will be the behavior of gdb?
I tried a toy example locally with split-dwarf without gdb_index and pubnames and it seemed to work with binary compiled with -O2 and -g2.
By work I mean I was able to step through code and print same variables as when I compiled it with monolithic debug information.

Hmm - so far, I haven't been able to reproduce the failures I've seen in the past - it's possible I've made mistakes in the past and promoted the idea that gdb requires an index when using Split DWARF.

What /does/ seem to be the case is that if you do create a gdb-index, it must be comprehensive - you must have built all your objects (that have DWARF) with -ggnu-pubnames, because it looks like gdb is assuming the index is comprehensive.

Here's my example:

$ cat a.cpp

struct t1 { int x; };

void a() {

  t1 v1 = {3};

}

$ cat b.cpp

void a();

int main() {

  a();

}

$ clang++ a.cpp b.cpp -gsplit-dwarf -g -gno-pubnames

$ gdb --batch -ex "ptype t1" ./a.out

...

type = struct t1 {

    int x;

}

Aborted

$ clang++ a.cpp b.cpp -gsplit-dwarf -g -Wl,--gdb-index -fuse-ld=lld

$ gdb --batch -ex "ptype t1" ./a.out

...

type = struct t1 {

    int x;

}

Aborted

$ clang++ a.cpp b.cpp -gsplit-dwarf -g -gno-pubnames -Wl,--gdb-index -fuse-ld=lld

$ gdb --batch -ex "ptype t1" ./a.out

...

No symbol "t1" in current context.


And just for some added complexity... let's check if gdb can appropriately respect DW_AT_GNU_pubnames on CUs without an index.

Hmm, seems it doesn't (or, at least, it doesn't worry about DW_AT_GNU_pubnames, perhaps it relies on checking the contents of the debug_gnu_pubnames/pubtypes section to see which units are covered by names? Or it's ignoring the contents entirely... - would have to hand-craft a dodgy debug_gnu_pub* section to test whether it's using it at all)

(expanding/modifying the above example with 3 "external" files (so there's no risk gdb accidentally parsed them when parsing the main function, for instance) and 3 types)


$ clang++ -gsplit-dwarf -ggnu-pubnames -g b.cpp c.cpp -c
$ llvm-objcopy --remove-section=.debug_gnu_pubnames --remove-section=.debug_gnu_pubtypes c.o
$ clang++ -gsplit-dwarf -g -gno-pubnames d.cpp -c
$ clang++ a.cpp b.o c.o d.o -g

$ gdb --batch -ex "ptype at" -ex "ptype bt" -ex "ptype ct" ./a.out

...

type = struct at {

    int i;

}

type = struct bt {

    int i;

}

type = struct ct {

    int i;

}

Aborted

Let's try that hand-crafted/corrupt pubnames.

Hmm, looks like gdb didn't care about my pubnames?


$ llvm-dwarfdump-tot a.out -debug-gnu-pubtypes

a.out:  file format elf64-x86-64


.debug_gnu_pubtypes contents:

length = 0x00000017, format = DWARF32, version = 0x0002, unit_offset = 0x00000000, unit_size = 0x00000030

Offset     Linkage  Kind     Name

0x00000041 STATIC   TYPE     "int"

length = 0x0000001f, format = DWARF32, version = 0x0002, unit_offset = 0x00000030, unit_size = 0x00000030

Offset     Linkage  Kind     Name

0x00000031 EXTERNAL TYPE     "at"

0x00000041 STATIC   TYPE     "int"

length = 0x00000017, format = DWARF32, version = 0x0002, unit_offset = 0x00000060, unit_size = 0x00000030

Offset     Linkage  Kind     Name
<<<<<<<<<<<<<< hand modified to remove "bt" here >>>>>>>>>>

0x00000028 STATIC   TYPE     "int"

length = 0x0000001f, format = DWARF32, version = 0x0002, unit_offset = 0x00000090, unit_size = 0x00000030

Offset     Linkage  Kind     Name

0x00000031 EXTERNAL TYPE     "ct"

0x00000041 STATIC   TYPE     "int"

$ gdb --batch -ex "ptype at" -ex "ptype bt" -ex "ptype ct" ./a.out

Unable to determine compiler version.

Skipping loading of libstdc++ pretty-printers for now.

Loading libc++ pretty-printers.

Non-google3 binary detected.

type = struct at {

    int i;

}
<<<<<<<<<< gdb still manages to find bt >>>>>>>>>>>

type = struct bt {

    int i;

}

type = struct ct {

    int i;

}

Aborted

So based on all that, I /think/ the answer is:

If you are going to use a linker-generated gdb-index with Split DWARF, then you must have gnu-pubnames on every input file. (because it can't build indexes for CUs without pubnames because it doesn't have access to the unit contents (because they're split) - in non-split cases, 'gold' will build the index itself by parsing the DWARF, I don't think 'lld' can do that, so if you're using lld, this advice applies to non-split DWARF too (either index everything, or don't have an index))
But you'll have a really slow debugging experience if you don't do that - but, so far as I can tell, it looks like it'll be correct, just slow.

But I'm super not sure about all of this. The "gdb only handles Split DWARF with an index" may be rumor, rumor that I accidentally promoted as fact based on some misunderstandings/incomplete experiments. Or maybe there's some truth to it I don't know how to reproduce...

- Dave

Thank You
Alex

________________________________
From: Sterling Augustine <saugustine@google.com<mailto:saugustine@google.com>>
Sent: Thursday, January 7, 2021 5:48 PM
To: Alexander Yermolovich <ayermolo@fb.com<mailto:ayermolo@fb.com>>
Cc: gdb@sourceware.org<mailto:gdb@sourceware.org> <gdb@sourceware.org<mailto:gdb@sourceware.org>>
Subject: Re: GDB and debug fission

On Thu, Jan 7, 2021 at 5:25 PM Alexander Yermolovich via Gdb
<gdb@sourceware.org<mailto:gdb@sourceware.org>> wrote:
>
> Hello.
>
> For latest gdb to work with -gsplit-dwarf debug information generated by clang, either in split or single mode does it need gdb_index or pubnames?
> In normal case where debug information is part of executable gdb_index is nice to speed up startup time, and I think I read pubnames is not used, but with debug fission are either gdb_index or pubnames necessary?

For gdb to work with split-dwarf debug info, it needs a gdb_index.
That can be generated in several ways. Gdb can build one itself--there
is a script somewhere to add a gdb index.

But it is somewhat easier to have the linker you use generate
gdb_index for you (both gnu-ld and llvm's lld can do this). They do
this by reading the .gnu_pubnames section, so in some way, you need
both pubnames *and* an index.

So you would ordinarily use the following commands:

$(CC) $(normal_arguments) -ggnu-pubnames
$(LD)  $(normal_arguments) -Wl,--gdb-index

  reply	other threads:[~2021-02-01 20:07 UTC|newest]

Thread overview: 12+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-01-08  1:25 Alexander Yermolovich
2021-01-08  1:48 ` Sterling Augustine
2021-01-08  2:12   ` Alexander Yermolovich
2021-01-08  3:16     ` David Blaikie
2021-01-08 18:52       ` Alexander Yermolovich
2021-01-08 19:01         ` David Blaikie
2021-01-29 20:34       ` David Blaikie
2021-01-30  0:42         ` Alexander Yermolovich
2021-01-30  1:06           ` David Blaikie
2021-02-01 20:07             ` Alexander Yermolovich [this message]
2021-02-01 20:14               ` David Blaikie
2021-01-08  2:17   ` David Blaikie

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=BYAPR15MB247042506899838A30CEBBFFBFB69@BYAPR15MB2470.namprd15.prod.outlook.com \
    --to=ayermolo@fb.com \
    --cc=dblaikie@gmail.com \
    --cc=gdb@sourceware.org \
    --cc=jgorbe@google.com \
    --cc=saugustine@google.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).