Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

runtime: fatal error stack traces are swallowed for binaries with elevated privileges #68103

Open
ronanj opened this issue Jun 21, 2024 · 3 comments
Labels
compiler/runtime Issues related to the Go compiler and/or runtime. NeedsInvestigation Someone must examine and confirm this is a valid issue and not a duplicate of an existing one.
Milestone

Comments

@ronanj
Copy link

ronanj commented Jun 21, 2024

Go version

go version go1.22.4 linux/amd64

Output of go env in your module/workspace:

GO111MODULE=''
GOARCH='amd64'
GOBIN=''
GOCACHE='/home/ronanj/.cache/go-build'
GOENV='/home/ronanj/.config/go/env'
GOEXE=''
GOEXPERIMENT=''
GOFLAGS=''
GOHOSTARCH='amd64'
GOHOSTOS='linux'
GOINSECURE=''
GOMODCACHE='/home/ronanj/go/pkg/mod'
GONOPROXY=''
GONOSUMDB=''
GOOS='linux'
GOPATH='/home/ronanj/go'
GOPRIVATE=''
GOPROXY='https://proxy.golang.org,direct'
GOROOT='/usr/local/go'
GOSUMDB='sum.golang.org'
GOTMPDIR=''
GOTOOLCHAIN='auto'
GOTOOLDIR='/usr/local/go/pkg/tool/linux_amd64'
GOVCS=''
GOVERSION='go1.22.4'
GCCGO='gccgo'
GOAMD64='v1'
AR='ar'
CC='gcc'
CXX='g++'
CGO_ENABLED='1'
GOMOD='/dev/null'
GOWORK=''
CGO_CFLAGS='-O2 -g'
CGO_CPPFLAGS=''
CGO_CXXFLAGS='-O2 -g'
CGO_FFLAGS='-O2 -g'
CGO_LDFLAGS='-O2 -g'
PKG_CONFIG='pkg-config'
GOGCCFLAGS='-fPIC -m64 -pthread -Wl,--no-gc-sections -fmessage-length=0 -fdebug-prefix-map=/tmp/go-build4169732472=/tmp/go-build -gno-record-gcc-switches'

What did you do?

The following program will generate a fatal error: concurrent map writes

package main

import (
	"runtime/debug"
	"time"
)

var l = map[nt]int{}

func worker() {
	for {
		l[1] = 0
	}
}

func main() {
	debug.SetTraceback("all")
	go worker()
	go worker()
	for {
		time.Sleep(time.Second)
	}
}

Run it with go run

$go build -o test test.go
$./test
fatal error: concurrent map writes

goroutine 6 gp=0xc000007500 m=2 mp=0xc000048808 [running]:
runtime.fatal({0x47c06b?, 0x0?})
	/usr/local/go/src/runtime/panic.go:1042 +0x5c fp=0xc000044f78 sp=0xc000044f48 pc=0x430fdc
runtime.mapassign_fast64(0x46e140, 0xc000072090, 0x1)
	/usr/local/go/src/runtime/map_fast64.go:102 +0x4d fp=0xc000044fb8 sp=0xc000044f78 pc=0x40ed2d
main.worker()
	/tmp/test.go:12 +0x26 fp=0xc000044fe0 sp=0xc000044fb8 pc=0x4654e6
runtime.goexit({})
	/usr/local/go/src/runtime/asm_amd64.s:1695 +0x1 fp=0xc000044fe8 sp=0xc000044fe0 pc=0x45f101
created by main.main in goroutine 1
	/tmp/test.go:18 +0x2b

goroutine 1 gp=0xc0000061c0 m=nil [sleep]:
runtime.gopark(0x1bdc37393cd958?, 0xc000042700?, 0x40?, 0xd4?, 0x480f28?)
	/usr/local/go/src/runtime/proc.go:402 +0xce fp=0xc0000426f0 sp=0xc0000426d0 pc=0x433dee
time.Sleep(0x3b9aca00)
	/usr/local/go/src/runtime/time.go:195 +0x115 fp=0xc000042730 sp=0xc0000426f0 pc=0x45c395
main.main()
	/tmp/test.go:21 +0x45 fp=0xc000042750 sp=0xc000042730 pc=0x465545
runtime.main()
	/usr/local/go/src/runtime/proc.go:271 +0x29d fp=0xc0000427e0 sp=0xc000042750 pc=0x4339bd
runtime.goexit({})
	/usr/local/go/src/runtime/asm_amd64.s:1695 +0x1 fp=0xc0000427e8 sp=0xc0000427e0 pc=0x45f101```

...

Now run it with elevated privileges

$ go build -o test test.go
$ sudo setcap CAP_NET_BIND_SERVICE+eip ./test
$ ./test
fatal error: concurrent map writes

Stack traces are gone.

What did you see happen?

A stack trace

What did you expect to see?

Referring to #60272, I expected the traces to be shown when using debug.SetTraceback("all"). But this solution only works for panic errors, and does not for fatal errors thrown internally from the go runtime (especially the map implementation).

Referring to the internal go runtime panic.go, it is mentioned that fatal does not include runtime frames, system goroutines, or frame metadata (fp, sp, pc) in the stack trace unless GOTRACEBACK=system or higher. Setting SetTraceback to system does not work either, as traces are also swallowed.

This issue, related to the change #60272 , is because the fatal function only checks for isSecureMode, while the panic function checks the gotraceback value before dumping the stack trace.

@gopherbot gopherbot added the compiler/runtime Issues related to the Go compiler and/or runtime. label Jun 21, 2024
@dr2chase
Copy link
Contributor

@golang/runtime

@dr2chase dr2chase added the NeedsInvestigation Someone must examine and confirm this is a valid issue and not a duplicate of an existing one. label Jun 21, 2024
@shuxiao9058
Copy link

The same issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
compiler/runtime Issues related to the Go compiler and/or runtime. NeedsInvestigation Someone must examine and confirm this is a valid issue and not a duplicate of an existing one.
Projects
Development

No branches or pull requests

6 participants