[Bug general/21203] New: Poor error handling for archives with non-ELF members
https://sourceware.org/bugzilla/show_bug.cgi?id=21203 Bug ID: 21203 Summary: Poor error handling for archives with non-ELF members Product: elfutils Version: unspecified Status: NEW Severity: normal Priority: P2 Component: general Assignee: unassigned at sourceware dot org Reporter: jistone at redhat dot com CC: elfutils-devel at sourceware dot org Target Milestone: --- Elfutils doesn't seem to behave well when it encounters non-ELF objects in an archive. As an easy example, a Rust *.rlib contains both ELF *.o and non-ELF metadata and bytecode. $ eu-readelf -h /usr/lib/rustlib/x86_64-unknown-linux-gnu/lib/libstd-*.rlib eu-readelf: cannot stat input file: Bad file descriptor For comparison, binutils prints errors about the unrecognized objects, but still provides useful output for the rest. $ readelf -h /usr/lib/rustlib/x86_64-unknown-linux-gnu/lib/libstd-*.rlib [...] File: /usr/lib/rustlib/x86_64-unknown-linux-gnu/lib/libstd-570da8f8.rlib(rust.metadata.bin) readelf: Error: Not an ELF file - it has the wrong magic bytes at the start File: /usr/lib/rustlib/x86_64-unknown-linux-gnu/lib/libstd-570da8f8.rlib(std-570da8f8.0.bytecode.deflate) readelf: Error: Not an ELF file - it has the wrong magic bytes at the start This particular archive has 13 ELF and those 2 non-ELF members. With strace, I can see 13 close(4) calls in a row, followed by the fstat(4,...) that leads to "cannot stat input file". Then there's yet another close(4)=EBADF, *after* that file descriptor was already momentarily re-used for locale purposes. open("/usr/lib/rustlib/x86_64-unknown-linux-gnu/lib/libstd-570da8f8.rlib", O_RDONLY) = 3 dup(3) = 4 fcntl(4, F_GETFL) = 0x8000 (flags O_RDONLY|O_LARGEFILE) fstat(4, {st_mode=S_IFREG|0644, st_size=12447250, ...}) = 0 mmap(NULL, 12447250, PROT_READ|PROT_WRITE, MAP_PRIVATE, 4, 0) = 0x7fc8577ba000 mmap(NULL, 692224, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7fc85fcae000 close(4)= 0 close(4)= -1 EBADF (Bad file descriptor) close(4)= -1 EBADF (Bad file descriptor) close(4)= -1 EBADF (Bad file descriptor) close(4)= -1 EBADF (Bad file descriptor) close(4)= -1 EBADF (Bad file descriptor) close(4)= -1 EBADF (Bad file descriptor) close(4)= -1 EBADF (Bad file descriptor) close(4)= -1 EBADF (Bad file descriptor) close(4)= -1 EBADF (Bad file descriptor) close(4)= -1 EBADF (Bad file descriptor) close(4)= -1 EBADF (Bad file descriptor) close(4)= -1 EBADF (Bad file descriptor) fstat(4, 0x7ffd45ce0630)= -1 EBADF (Bad file descriptor) open("/usr/share/locale/locale.alias", O_RDONLY|O_CLOEXEC) = 4 fstat(4, {st_mode=S_IFREG|0644, st_size=2502, ...}) = 0 mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7fc85fd6c000 read(4, "# Locale name alias data base.\n#"..., 4096) = 2502 read(4, "", 4096) = 0 close(4)= 0 munmap(0x7fc85fd6c000, 4096)= 0 open("/usr/share/locale/en_US.UTF-8/LC_MESSAGES/elfutils.mo", O_RDONLY) = -1 ENOENT (No such file or directory) open("/usr/share/locale/en_US.utf8/LC_MESSAGES/elfutils.mo", O_RDONLY) = -1 ENOENT (No such file or directory) open("/usr/share/locale/en_US/LC_MESSAGES/elfutils.mo", O_RDONLY) = -1 ENOENT (No such file or directory) open("/usr/share/locale/en.UTF-8/LC_MESSAGES/elfutils.mo", O_RDONLY) = -1 ENOENT (No such file or directory) open("/usr/share/locale/en.utf8/LC_MESSAGES/elfutils.mo", O_RDONLY) = -1 ENOENT (No such file or directory) open("/usr/share/locale/en/LC_MESSAGES/elfutils.mo", O_RDONLY) = -1 ENOENT (No such file or directory) write(2, "eu-readelf: ", 12eu-readelf: )= 12 write(2, "cannot stat input file", 22cannot stat input file) = 22 open("/usr/share/locale/en_US.UTF-8/LC_MESSAGES/libc.mo", O_RDONLY) = -1 ENOENT (No such file or directory) open("/usr/share/locale/en_US.utf8/LC_MESSAGES/libc.mo", O_RDONLY) = -1 ENOENT (No such file or directory) open("/usr/share/locale/en_US/LC_MESSAGES/libc.mo", O_RDONLY) = -1 ENOENT (No such file or directory) open("/usr/share/locale/en.UTF-8/LC_MESSAGES/libc.mo", O_RDONLY) = -1 ENOENT (No such file or directory) open("/usr/share/locale/en.utf8/LC_MESSAGES/libc.mo", O_RDONLY) = -1 ENOENT (No such file or di
[Bug general/21203] Poor error handling for archives with non-ELF members
https://sourceware.org/bugzilla/show_bug.cgi?id=21203 --- Comment #1 from Josh Stone --- Actually, the repeated close(4) seems to be a more general problem. I see this even for a more typical archive, like my libz.a with 15 objects sees 15 EBADF. -- You are receiving this mail because: You are on the CC list for the bug.
[Bug tools/22288] New: eu-addr2line doesn't find a rust file:line
https://sourceware.org/bugzilla/show_bug.cgi?id=22288 Bug ID: 22288 Summary: eu-addr2line doesn't find a rust file:line Product: elfutils Version: unspecified Status: NEW Severity: normal Priority: P2 Component: tools Assignee: unassigned at sourceware dot org Reporter: jistone at redhat dot com CC: elfutils-devel at sourceware dot org Target Milestone: --- Created attachment 10524 --> https://sourceware.org/bugzilla/attachment.cgi?id=10524&action=edit hello world binary With a simple hello world program in Rust, eu-addr2line can't locate the file:line of the main subprogram. The binary is attached, generated using: rust-1.20.0-2.fc26.x86_64 cargo-0.21.1-1.fc26.x86_64 $ cargo new --bin hello Created binary (application) `hello` project $ cd hello/ $ cargo run Compiling hello v0.1.0 (file:///tmp/hello) Finished dev [unoptimized + debuginfo] target(s) in 0.13 secs Running `target/debug/hello` Hello, world! Let's try to locate hello::main... $ nm target/debug/hello | grep main U __libc_start_main@@GLIBC_2.2.5 3750 T main 00227808 d _ZN5hello4main15__STATIC_FMTSTR17h02cd196921af1863E 3710 t _ZN5hello4main17ha1ca5e9e738df91eE $ eu-addr2line -e target/debug/hello -f 3710 _ZN5hello4main17ha1ca5e9e738df91eE ??:0 $ addr2line -e target/debug/hello -f 3710 _ZN5hello4mainE /tmp/hello/src/main.rs:1 So elfutils finds the raw symbol name, but not the file:line, whereas binutils finds the DIE's DW_AT_linkage_name and the correct file:line. (I don't know why the linkage name doesn't have the hashed part, but that's indeed what the DWARF says.) elfutils-0.169-1.fc26.x86_64 (and also master, commit 734118467b1a) binutils-2.27-24.fc26.x86_64 -- You are receiving this mail because: You are on the CC list for the bug.
[Bug tools/22288] eu-addr2line doesn't find a rust file:line
https://sourceware.org/bugzilla/show_bug.cgi?id=22288 --- Comment #2 from Josh Stone --- (In reply to Mark Wielaard from comment #1) > But if there are .debug_aranges then it seems bad to assume they > are wrong or incomplete. I think it's safe to trust that given aranges are valid, but not that they're complete. The binary may be composed of objects from multiple compilers, with different policies toward aranges, and the final user linking it all may not be able to control this. > Best would be to fix rustc to generate .debug_aranges. I found that Clang also doesn't emit .debug_aranges by default, but it has -gdwarf-aranges for that. This passes to LLVM -generate-arange-section, and in fact "rustc -Cllvm-args=-generate-arange-section" does work! I can talk to upstream about making that the default, but they may well take a similar stance as Clang, that it's redundant with other pc/range info. > Second best would be to have a mechanism to for scanning all CUs and > (re)create the same cache that dwarf_getaranges() would create from the > .debug_aranges section for the CU. One question is if this isn't the default > how it interacts with other users of the aranges cache like dwarf_addrdie, > dwfl_module_addrdie and dwfl_module_getsrc. The last one is what > eu-addr2line (and eu-stack) use. I think this mechanism is desirable even if rustc changes its default. Start with the aranges, and lazily augment it with a CU scan if that misses. But I don't doubt there are tricky corners to this. -- You are receiving this mail because: You are on the CC list for the bug.
[Bug tools/22288] eu-addr2line doesn't find a rust file:line
https://sourceware.org/bugzilla/show_bug.cgi?id=22288 --- Comment #3 from Josh Stone --- > I can talk to upstream about making that the default, https://github.com/rust-lang/rust/issues/45246 -- You are receiving this mail because: You are on the CC list for the bug.
[Bug libdw/25173] dwarf_getsrc_die fails for rust code
https://sourceware.org/bugzilla/show_bug.cgi?id=25173 Josh Stone changed: What|Removed |Added CC||jistone at redhat dot com --- Comment #3 from Josh Stone --- (In reply to Mark Wielaard from comment #1) > It might help if you could attach the binary. Locally (Fedora 31, rustc > 1.38.0) I cannot replicate. Neither binutils addr2line, not elfutils > eu-addr2line seem able to resolve addresses to source lines. Note that rpmbuild strips Rust's rlibs (static archives), so you won't have any debuginfo for pre-compiled code from the standard library. You should still be able to resolve the user's own code though, as well as generic std code that gets monomorphized in the user's compilation. $ bat main.rs ───┬── │ File: main.rs ───┼── 1 │ fn main() { 2 │ println!("Hello, world!"); 3 │ } ───┴── $ rustc -g main.rs $ nm main | grep main U __libc_start_main@@GLIBC_2.2.5 53d0 T main 5390 t _ZN4main4main17h6b07ac6c6f06cdd6E $ addr2line -e main 5390 /tmp/hello/src/main.rs:1 $ eu-addr2line -e main 5390 ??:0 -- You are receiving this mail because: You are on the CC list for the bug.
[Bug libdw/25173] dwarf_getsrc_die fails for rust code
https://sourceware.org/bugzilla/show_bug.cgi?id=25173 --- Comment #4 from Josh Stone --- I can also reproduce this with Clang (clang-9.0.0-1.fc31.x86_64), so it seems to be a more general problem with LLVM as the producer. $ bat main.c ───┬── │ File: main.c ───┼── 1 │ #include 2 │ int main() { 3 │ printf("Hello, world!\n"); 4 │ return 0; 5 │ } ───┴── $ clang -g main.c -o main $ nm main | grep main U __libc_start_main@@GLIBC_2.2.5 00401130 T main $ addr2line -e main 401130 /tmp/hello/src/main.c:2 $ eu-addr2line -e main 401130 ??:0 When compiled with GCC, eu-addr2line resolves it fine. -- You are receiving this mail because: You are on the CC list for the bug.
[Bug libdw/25173] dwarf_getsrc_die fails for rust code
https://sourceware.org/bugzilla/show_bug.cgi?id=25173 --- Comment #6 from Josh Stone --- Aha, I thought this was familiar. I guess I should try to implement that aranges change in rustc after all. However, I think elfutils should probably still try to deal without aranges, on par with binutils. -- You are receiving this mail because: You are on the CC list for the bug.
[Bug tools/22288] eu-addr2line doesn't find a rust file:line
https://sourceware.org/bugzilla/show_bug.cgi?id=22288 --- Comment #4 from Josh Stone --- Here's my rustc PR to enable aranges by default: https://github.com/rust-lang/rust/pull/66532 -- You are receiving this mail because: You are on the CC list for the bug.
[Bug libdw/26773] sleb128 values near INT64_MAX/MIN not correctly read
https://sourceware.org/bugzilla/show_bug.cgi?id=26773 Josh Stone changed: What|Removed |Added CC||jistone at redhat dot com --- Comment #2 from Josh Stone --- (In reply to Tom Tromey from comment #1) > This limits the number of bytes read-- but it seems like > it maybe ought to read until the first byte without the > high bit set. Beware, golang just dealt with a CVE for reading unlimited varints: https://github.com/golang/go/issues/40618 (But the context is different since that's used in stuff like protocol buffers that may be streamed.) -- You are receiving this mail because: You are on the CC list for the bug.