Summary: | ld.bfd error on releng/11.4 confuses many autoconf scripts | ||
---|---|---|---|
Product: | Base System | Reporter: | Jan Beich <jbeich> |
Component: | bin | Assignee: | freebsd-toolchain (Nobody) <toolchain> |
Status: | Closed FIXED | ||
Severity: | Affects Only Me | CC: | cem, dim, emaste, kib, zeising |
Priority: | --- | Keywords: | regression |
Version: | 11.4-RELEASE | ||
Hardware: | i386 | ||
OS: | Any | ||
URL: | https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=246537 | ||
Bug Depends on: | |||
Bug Blocks: | 240629 |
Description
Jan Beich
2020-05-09 07:19:53 UTC
Clang 9 from 11.4-BETA1 is also affected but Clang 8 from 11.4-PRERELEASE (2020-04-30) is not. Hmm, I can't reproduce on amd64. As emaste noted, it looks exactly like this very old DragonFly issue: https://bugs.dragonflybsd.org/issues/2511. The workaround they used eventually was to compile the crt objects with -fno-asynchronous-unwind-tables. But this is very likely a ld.bfd bug, as there seems to be nothing wrong with the .eh_frame section in crt1.o. Dwarfdump gives me: .eh_frame fde: < 0><0x00000020:0x00000039><_fini><cie offset 0x0000001c::cie index 0><fde offset 0x00000018 length: 0x00000018> <eh aug data len 0x0> 0x00000020: <off cfa=04(r4) > <off r8=-4(cfa) > 0x00000023: <off cfa=04(r4) > <off r8=-4(cfa) > 0x00000025: <off cfa=04(r5) > <off r5=-8(cfa) > <off r8=-4(cfa) > < 1><0x00000074:0x000001a3><><cie offset 0x0000001c::cie index 1><fde offset 0x0000004c length: 0x0000001c> <eh aug data len 0x0> 0x00000074: <off cfa=04(r4) > <off r8=-4(cfa) > 0x00000075: <off cfa=08(r4) > <off r5=-8(cfa) > <off r8=-4(cfa) > 0x00000077: <off cfa=08(r5) > <off r5=-8(cfa) > <off r8=-4(cfa) > 0x0000007d: <off cfa=08(r5) > <off r3=-12(cfa) > <off r5=-8(cfa) > <off r6=-20(cfa) > <off r7=-16(cfa) > <off r8=-4(cfa) > < 2><0x000001c4:0x00000297><><cie offset 0x0000003c::cie index 1><fde offset 0x0000006c length: 0x00000024> <eh aug data len 0x0> 0x000001c4: <off cfa=04(r4) > <off r8=-4(cfa) > 0x000001c5: <off cfa=08(r4) > <off r5=-8(cfa) > <off r8=-4(cfa) > 0x000001c7: <off cfa=08(r5) > <off r5=-8(cfa) > <off r8=-4(cfa) > 0x000001cd: <off cfa=08(r5) > <off r3=-12(cfa) > <off r5=-8(cfa) > <off r6=-20(cfa) > <off r7=-16(cfa) > <off r8=-4(cfa) > 0x00000296: <off cfa=04(r4) > <off r3=-12(cfa) > <off r5=-8(cfa) > <off r6=-20(cfa) > <off r7=-16(cfa) > <off r8=-4(cfa) > < 3><0x000002cc:0x00000311><><cie offset 0x00000064::cie index 1><fde offset 0x00000094 length: 0x00000020> <eh aug data len 0x0> 0x000002cc: <off cfa=04(r4) > <off r8=-4(cfa) > 0x000002cd: <off cfa=08(r4) > <off r5=-8(cfa) > <off r8=-4(cfa) > 0x000002cf: <off cfa=08(r5) > <off r5=-8(cfa) > <off r8=-4(cfa) > 0x000002d0: <off cfa=08(r5) > <off r5=-8(cfa) > <off r6=-12(cfa) > <off r8=-4(cfa) > 0x000002ed: <off cfa=04(r4) > <off r5=-8(cfa) > <off r6=-12(cfa) > <off r8=-4(cfa) > 0x000002f2: <off cfa=08(r5) > <off r5=-8(cfa) > <off r6=-12(cfa) > <off r8=-4(cfa) > cie: < 0> version 1 cie section offset 0 0x00000000 augmentation zR code_alignment_factor 1 data_alignment_factor -4 return_address_register 8 eh aug data len 0x1 bytes 0x1b bytes of initial instructions 7 cie length 20 initial instructions 0 DW_CFA_def_cfa r4 4 3 DW_CFA_offset r8 -4 5 DW_CFA_nop 6 DW_CFA_nop < 1> version 1 cie section offset 52 0x00000034 augmentation zR code_alignment_factor 1 data_alignment_factor -4 return_address_register 8 eh aug data len 0x1 bytes 0x1b bytes of initial instructions 7 cie length 20 initial instructions 0 DW_CFA_def_cfa r4 4 3 DW_CFA_offset r8 -4 5 DW_CFA_nop 6 DW_CFA_nop In any case clang 8 does not produce any .cfi directives in crt*.o, while clang 9 and 10 do. For instance /usr/obj/usr/src/lib/csu/i386/crt1_c.s with clang becomes: .text .file "crt1_c.c" # Start of file scope inline assembly .ident "$FreeBSD: stable/11/lib/csu/i386/crt1_c.c 292000 2015-12-08 19:32:58Z emaste $" .ident "$FreeBSD: stable/11/lib/csu/common/crtbrand.c 339300 2018-10-11 00:26:15Z emaste $" .ident "$FreeBSD: stable/11/lib/csu/common/ignore_init.c 339300 2018-10-11 00:26:15Z emaste $" .hidden _start1 # End of file scope inline assembly .globl _start1 # -- Begin function _start1 .p2align 4, 0x90 .type _start1,@function _start1: # @_start1 # %bb.0: ... With clang 10 this becomes: .text .file "crt1_c.c" # Start of file scope inline assembly .ident "$FreeBSD: stable/11/lib/csu/i386/crt1_c.c 292000 2015-12-08 19:32:58Z emaste $" .ident "$FreeBSD: stable/11/lib/csu/common/crtbrand.c 339300 2018-10-11 00:26:15Z emaste $" .ident "$FreeBSD: stable/11/lib/csu/common/ignore_init.c 339300 2018-10-11 00:26:15Z emaste $" .hidden _start1 # End of file scope inline assembly .globl _start1 # -- Begin function _start1 .p2align 4, 0x90 .type _start1,@function _start1: # @_start1 .cfi_startproc # %bb.0: ... The directives got turned on by emaste in https://github.com/llvm/llvm-project/commit/cb1761465a0d, referring in his commit message to bug 241562 ("failing test case: lib.libexecinfo.backtrace_test.backtrace_fmt_basic"). (In reply to Dimitry Andric from comment #4) So what shall we do here? I've gone a little bit into the rabbit hole that is BFD ld, but the bug does not "jump out" at me. So fixing it is likely not trivial. We could: 1) Patch out the error message in BFD ld (possibly only on stable/11) 2) Spend time to figure why BFD ld is choking on this .eh_frame section, get a fix, submit it upstream, merge it downstream, etc 3) Add -fno-asynchronous-unwind-tables to lib/csu in general 4) Add -fno-asynchronous-unwind-tables to lib/csu/i386 only 5) Add -fno-asynchronous-unwind-tables to lib/csu/i386 only, and only on stable/11 My preference would be for 5). Note that we'd need to MFS any fix to releng/11.4 too. (In reply to Dimitry Andric from comment #5) Look at r209294. I think 3 is best. A commit references this bug: Author: dim Date: Mon May 11 19:36:39 UTC 2020 New revision: 360915 URL: https://svnweb.freebsd.org/changeset/base/360915 Log: Use -fno-asynchronous-unwind-tables to compile lib/csu Summary: In r209294 kib added -fno-asynchronous-unwind-tables to the compile flags for the GNU C startup components. This was done to work around a BFD ld assertion, "no .eh_frame_hdr table will be created", which is produced because of the layout of the startup objects. Add the same flag to lib/csu too, for the same reason. And similarly to r209294, also add -fno-omit-frame-pointer. This is primarily meant to quickly MFC to stable/11, so it can end up in the 11.4 release, as a fix for https://bugs.freebsd.org/246322. PR: 246322 MFC after: 3 days Differential Revision: https://reviews.freebsd.org/D24797 Changes: head/lib/csu/Makefile.inc A commit references this bug: Author: dim Date: Thu May 14 19:09:14 UTC 2020 New revision: 361046 URL: https://svnweb.freebsd.org/changeset/base/361046 Log: MFC r360915: Use -fno-asynchronous-unwind-tables to compile lib/csu Summary: In r209294 kib added -fno-asynchronous-unwind-tables to the compile flags for the GNU C startup components. This was done to work around a BFD ld assertion, "no .eh_frame_hdr table will be created", which is produced because of the layout of the startup objects. Add the same flag to lib/csu too, for the same reason. And similarly to r209294, also add -fno-omit-frame-pointer. This is primarily meant to quickly MFC to stable/11, so it can end up in the 11.4 release, as a fix for https://bugs.freebsd.org/246322. PR: 246322 Differential Revision: https://reviews.freebsd.org/D24797 Changes: _U stable/12/ stable/12/lib/csu/Makefile.inc A commit references this bug: Author: dim Date: Thu May 14 19:09:26 UTC 2020 New revision: 361047 URL: https://svnweb.freebsd.org/changeset/base/361047 Log: MFC r360915: Use -fno-asynchronous-unwind-tables to compile lib/csu Summary: In r209294 kib added -fno-asynchronous-unwind-tables to the compile flags for the GNU C startup components. This was done to work around a BFD ld assertion, "no .eh_frame_hdr table will be created", which is produced because of the layout of the startup objects. Add the same flag to lib/csu too, for the same reason. And similarly to r209294, also add -fno-omit-frame-pointer. This is primarily meant to quickly MFC to stable/11, so it can end up in the 11.4 release, as a fix for https://bugs.freebsd.org/246322. PR: 246322 Differential Revision: https://reviews.freebsd.org/D24797 Changes: _U stable/11/ stable/11/lib/csu/Makefile.inc A commit references this bug: Author: dim Date: Thu May 14 19:32:42 UTC 2020 New revision: 361050 URL: https://svnweb.freebsd.org/changeset/base/361050 Log: MF11 r361047: MFC r360915: Use -fno-asynchronous-unwind-tables to compile lib/csu Summary: In r209294 kib added -fno-asynchronous-unwind-tables to the compile flags for the GNU C startup components. This was done to work around a BFD ld assertion, "no .eh_frame_hdr table will be created", which is produced because of the layout of the startup objects. Add the same flag to lib/csu too, for the same reason. And similarly to r209294, also add -fno-omit-frame-pointer. This is primarily meant to quickly MFC to stable/11, so it can end up in the 11.4 release, as a fix for https://bugs.freebsd.org/246322. Approved by: re (gjb) PR: 246322 Differential Revision: https://reviews.freebsd.org/D24797 Changes: _U releng/11.4/ releng/11.4/lib/csu/Makefile.inc Fixed after base r361050, which should end up soon in 11.4-BETA2. (In reply to Dimitry Andric from comment #4) > The directives got turned on by emaste in https://github.com/llvm/llvm- > project/commit/cb1761465a0d, referring in his commit message to bug 241562 > ("failing test case: lib.libexecinfo.backtrace_test.backtrace_fmt_basic"). Sort of; they were on before that, but only for amd64. That change just unified the behavior for all arch. (Link to regression introduced by this change: https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=246537 ) Could the cflags be more constrained to the specific problematic CUs? For gcc crt (probably dead now?), the exclusion should only be needed for crtend.o/So. That could either be a Makefile change, or we could #if 0 these lines from crtstuff.c? https://svnweb.freebsd.org/base/head/contrib/gcc/crtstuff.c?revision=169690&view=markup&pathrev=209294#l483 (inside a defined(CRT_END) section starting at line 446). For llvm csu, the issue reported was specific to i386 crt1.o; globally disabling unwind seems heavy-handed. Ideally we get a _start frame on i386, but as a first step we should undisable these frames on !i386. I don't see any obvious reason llvm csu would actually emit any special last-CIE eh_frame value for i386; unlike the GNU one above, there isn't any eh_frame section symbol with magic zero value in any of the lib/csu code. The weirdest thing about i386 crt1.o is that it has two DW_TAG_compile_units and also two CIEs. Supposing that is ld.bfd's problem, could crt1 be a .a? Alternatively, we could disable the unwind directives in crt1_s.S, keeping unwind directives for the rest of crt1.o (_start1, etc). We'd lose _start, but still have a _start1 frame below main. (There is a special __EH_FRAME_LIST_END__ in contrib/llvm-project/compiler-rt/lib/crt/crtend.c, but as far as I can tell we don't build that file into userspace anywhere and it wouldn't be impacted by lib/csu/Makefile.inc CFLAGS. We use the one in lib/csu/common/crtend.c.) Also, this doesn't seem to reproduce with modern (ports) binutils? $ llvm-readelf10 --sections /obj/usr/home/conrad/src/freebsd/i386.i386/lib/csu/i386/crt1.o ... [ 4] .eh_frame PROGBITS 00000000 0003fc 0000b8 00 A 0 0 4 $ cat main.c int main(int argc, char **argv) { return 1; } $ cc -Wall -Wextra -O2 -g -m32 -c main.c $ ld.bfd -melf_i386_fbsd /obj/usr/home/conrad/src/freebsd/i386.i386/lib/csu/i386/crt{1,i,n}.o main.o /obj/usr/home/conrad/src/freebsd/i386.i386/tmp/usr/lib/libc.a -o main.test (no error) $ ld.bfd --version GNU ld (GNU Binutils) 2.33.1 If this issue is specific to ancient base ld.bfd on 11 (and maybe 12?), I think we should just revert this in CURRENT. It's strange, but whatever I do I cannot reproduce the original issue on 11.4 anymore, even if I comment out the -fno-asynchronous-unwind-tables line from lib/csu/Makefile.inc and rebuild it. jbeich@ are you able to still reproduce this? A commit in branch main references this bug: URL: https://cgit.FreeBSD.org/src/commit/?id=c969310c992a12459ed4025c1cd8b22f29c763b5 commit c969310c992a12459ed4025c1cd8b22f29c763b5 Author: Dmitry Chagin <dchagin@FreeBSD.org> AuthorDate: 2023-06-29 16:34:39 +0000 Commit: Dmitry Chagin <dchagin@FreeBSD.org> CommitDate: 2023-06-29 16:34:39 +0000 csu: Implement _start using as to satisfy unwinders on x86_64 The right unwinding stop indicator should be CFI-undefined PC. https://dwarfstd.org/doc/Dwarf3.pdf - page 118: If a Return Address register is defined in the virtual unwind table, and its rule is undefined (for example, by DW_CFA_undefined), then there is no return address and no call address, and the virtual unwind of stack activations is complete. This requires the crt code be built with unwind tables, for that remove -fno-asynchronous-unwind-tables to enable unwind tables generation. PR: 241562, 246322, 246537 Reviewed by: kib Differential Revision: https://reviews.freebsd.org/D40780 lib/csu/Makefile.inc | 20 +++++----- lib/csu/amd64/Makefile | 3 ++ lib/csu/amd64/crt1_c.c | 22 ----------- lib/csu/amd64/crt1_s.S (new) | 88 ++++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 102 insertions(+), 31 deletions(-) A commit in branch main references this bug: URL: https://cgit.FreeBSD.org/src/commit/?id=a18b956b73cee784e5c422d20fd0e4dabebd7eee commit a18b956b73cee784e5c422d20fd0e4dabebd7eee Author: Dmitry Chagin <dchagin@FreeBSD.org> AuthorDate: 2023-06-29 16:53:07 +0000 Commit: Dmitry Chagin <dchagin@FreeBSD.org> CommitDate: 2023-06-29 16:53:07 +0000 libexecinfo: Enable backtrace_test.backtrace_fmt_basic on amd64 again Due to unwind tables generation enabled after c969310c for csu. PR: 241562, 246322, 246537 Reviewed by: kib, ngie Differential Revision: https://reviews.freebsd.org/D40758 contrib/netbsd-tests/lib/libexecinfo/t_backtrace.c | 5 ----- 1 file changed, 5 deletions(-) |