From 1e433915ce684049a6a44fd506f691f448b56c76 Mon Sep 17 00:00:00 2001 From: Joel Sing Date: Wed, 21 Feb 2024 23:29:12 +1100 Subject: [PATCH] cmd/link,debug/elf: mark Go binaries with no branch target CFI on openbsd OpenBSD enables Indirect Branch Tracking (IBT) on amd64 and Branch Target Identification (BTI) on arm64, where hardware permits. Since Go generated binaries do not currently support IBT or BTI, temporarily mark them with PT_OPENBSD_NOBTCFI which prevents branch target CFI from being enforced on execution. This should be removed as soon asn IBT and BTI support are available. Fixes #66040 Updates #66054 Change-Id: I91ac05736e6942c54502bef4b8815eb8740d2d5e Reviewed-on: https://go-review.googlesource.com/c/go/+/568435 LUCI-TryBot-Result: Go LUCI TryBot-Result: Gopher Robot Reviewed-by: Josh Rickmar Reviewed-by: Keith Randall Run-TryBot: Joel Sing Reviewed-by: Keith Randall Reviewed-by: Than McIntosh --- api/next/66054.txt | 2 ++ doc/next/6-stdlib/99-minor/debug/elf/66054.md | 3 +++ src/cmd/link/internal/ld/elf.go | 4 ++++ src/cmd/link/internal/ld/lib.go | 5 +++++ src/debug/elf/elf.go | 1 + 5 files changed, 15 insertions(+) create mode 100644 api/next/66054.txt create mode 100644 doc/next/6-stdlib/99-minor/debug/elf/66054.md diff --git a/api/next/66054.txt b/api/next/66054.txt new file mode 100644 index 0000000000..bef794c7cf --- /dev/null +++ b/api/next/66054.txt @@ -0,0 +1,2 @@ +pkg debug/elf, const PT_OPENBSD_NOBTCFI = 1705237480 #66054 +pkg debug/elf, const PT_OPENBSD_NOBTCFI ProgType #66054 diff --git a/doc/next/6-stdlib/99-minor/debug/elf/66054.md b/doc/next/6-stdlib/99-minor/debug/elf/66054.md new file mode 100644 index 0000000000..9cf1fa7ad1 --- /dev/null +++ b/doc/next/6-stdlib/99-minor/debug/elf/66054.md @@ -0,0 +1,3 @@ +The debug/elf package now defines PT_OPENBSD_NOBTCFI. This elf.ProgType is +used to disable Branch Tracking Control Flow Integrity (BTCFI) enforcement +on OpenBSD binaries. diff --git a/src/cmd/link/internal/ld/elf.go b/src/cmd/link/internal/ld/elf.go index 7c035df97e..746f359b68 100644 --- a/src/cmd/link/internal/ld/elf.go +++ b/src/cmd/link/internal/ld/elf.go @@ -2185,6 +2185,10 @@ func asmbElf(ctxt *Link) { ph.Type = elf.PT_GNU_STACK ph.Flags = elf.PF_W + elf.PF_R ph.Align = uint64(ctxt.Arch.RegSize) + } else if ctxt.HeadType == objabi.Hopenbsd { + ph := newElfPhdr() + ph.Type = elf.PT_OPENBSD_NOBTCFI + ph.Flags = elf.PF_X } else if ctxt.HeadType == objabi.Hsolaris { ph := newElfPhdr() ph.Type = elf.PT_SUNWSTACK diff --git a/src/cmd/link/internal/ld/lib.go b/src/cmd/link/internal/ld/lib.go index 97f3ed37e3..c68da4070b 100644 --- a/src/cmd/link/internal/ld/lib.go +++ b/src/cmd/link/internal/ld/lib.go @@ -1437,6 +1437,11 @@ func (ctxt *Link) hostlink() { } case objabi.Hopenbsd: argv = append(argv, "-Wl,-nopie") + if linkerFlagSupported(ctxt.Arch, argv[0], "", "-Wl,-z,nobtcfi") { + // -Wl,-z,nobtcfi is only supported on OpenBSD 7.4+, remove guard + // when OpenBSD 7.5 is released and 7.3 is no longer supported. + argv = append(argv, "-Wl,-z,nobtcfi") + } argv = append(argv, "-pthread") if ctxt.Arch.InFamily(sys.ARM64) { // Disable execute-only on openbsd/arm64 - the Go arm64 assembler diff --git a/src/debug/elf/elf.go b/src/debug/elf/elf.go index e78367750f..b97ddbf7cf 100644 --- a/src/debug/elf/elf.go +++ b/src/debug/elf/elf.go @@ -773,6 +773,7 @@ const ( PT_OPENBSD_RANDOMIZE ProgType = 0x65a3dbe6 /* Random data */ PT_OPENBSD_WXNEEDED ProgType = 0x65a3dbe7 /* W^X violations */ + PT_OPENBSD_NOBTCFI ProgType = 0x65a3dbe8 /* No branch target CFI */ PT_OPENBSD_BOOTDATA ProgType = 0x65a41be6 /* Boot arguments */ PT_SUNW_EH_FRAME ProgType = 0x6474e550 /* Frame unwind information */ -- 2.48.1