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

cmd/compile: encoded pkg path shown in stack trace #35558

Open
myitcv opened this issue Nov 13, 2019 · 7 comments
Milestone

Comments

@myitcv
Copy link
Member

@myitcv myitcv commented Nov 13, 2019

What version of Go are you using (go version)?

$ go version
go version devel +99957b6930 Tue Nov 12 05:35:33 2019 +0000 linux/amd64

Does this issue reproduce with the latest release?

Yes

What operating system and processor architecture are you using (go env)?

go env Output
$ go env
GO111MODULE=""
GOARCH="amd64"
GOBIN=""
GOCACHE="/home/myitcv/.cache/go-build"
GOENV="/home/myitcv/.config/go/env"
GOEXE=""
GOFLAGS=""
GOHOSTARCH="amd64"
GOHOSTOS="linux"
GOINSECURE=""
GONOPROXY=""
GONOSUMDB=""
GOOS="linux"
GOPATH="/home/myitcv/gostuff"
GOPRIVATE=""
GOPROXY="https://proxy.golang.org,direct"
GOROOT="/home/myitcv/gos"
GOSUMDB="sum.golang.org"
GOTMPDIR=""
GOTOOLDIR="/home/myitcv/gos/pkg/tool/linux_amd64"
GCCGO="gccgo"
AR="ar"
CC="gcc"
CXX="g++"
CGO_ENABLED="1"
GOMOD=""
CGO_CFLAGS="-g -O2"
CGO_CPPFLAGS=""
CGO_CXXFLAGS="-g -O2"
CGO_FFLAGS="-g -O2"
CGO_LDFLAGS="-g -O2"
PKG_CONFIG="pkg-config"
GOGCCFLAGS="-fPIC -m64 -pthread -fmessage-length=0 -fdebug-prefix-map=/tmp/go-build670035236=/tmp/go-build -gno-record-gcc-switches"

What did you do?

Run the following testscript repro:

go run main.go

-- go.mod --
module mod.com

go 1.14

require (
        golang.org/x/net v0.0.0-20190620200207-3b0461eec859 // indirect
        gopkg.in/tomb.v2 v2.0.0-20161208151619-d5d1b5820637
)
-- main.go --
package main

import "gopkg.in/tomb.v2"

func main() {
	done := make(chan struct{})
	var t tomb.Tomb
	t.Go(func() error {
		panic("here")
		close(done)
		return nil
	})
	<-done
}

What did you expect to see?

panic: here

goroutine 18 [running]:
main.main.func1(0x0, 0x0)
        /home/myitcv/gostuff/src/github.com/myitcv/playground/main.go:9 +0x39
gopkg.in/tomb.v2.(*Tomb).run(0xc00018e000, 0xc00018a060)
        /home/myitcv/gostuff/pkg/mod/gopkg.in/tomb.v2@v2.0.0-20161208151619-d5d1b5820637/tomb.go:163 +0x38
created by gopkg.in/tomb.v2.(*Tomb).Go
        /home/myitcv/gostuff/pkg/mod/gopkg.in/tomb.v2@v2.0.0-20161208151619-d5d1b5820637/tomb.go:159 +0xba
exit status 2

What did you see instead?

panic: here

goroutine 18 [running]:
main.main.func1(0x0, 0x0)
        /home/myitcv/gostuff/src/github.com/myitcv/playground/main.go:9 +0x39
gopkg.in/tomb%2ev2.(*Tomb).run(0xc00018e000, 0xc00018a060)
        /home/myitcv/gostuff/pkg/mod/gopkg.in/tomb.v2@v2.0.0-20161208151619-d5d1b5820637/tomb.go:163 +0x38
created by gopkg.in/tomb%2ev2.(*Tomb).Go
        /home/myitcv/gostuff/pkg/mod/gopkg.in/tomb.v2@v2.0.0-20161208151619-d5d1b5820637/tomb.go:159 +0xba
exit status 2

Note the %2e in the stack trace.

cc @bcmills @randall77 @jayconrod

@jayconrod jayconrod added this to the Go1.14 milestone Nov 13, 2019
@jayconrod jayconrod self-assigned this Nov 14, 2019
@jayconrod jayconrod changed the title cmd/go: encoded pkg path shown in stack trace cmd/compile: encoded pkg path shown in stack trace Nov 14, 2019
@jayconrod jayconrod modified the milestones: Go1.14, Backlog Nov 14, 2019
@jayconrod jayconrod removed their assignment Nov 14, 2019
@jayconrod

This comment has been minimized.

Copy link
Contributor

@jayconrod jayconrod commented Nov 14, 2019

It seems like the compiler is doing this. I was able to reproduce this back as far as 1.11.

Here's a simpler test case that shows %2e in the symbol table. Versions before 1.13 have %22%22 instead ("").

go tool compile -o foo.a -p example.com/foo.v2 foo.go
go tool nm foo.a
! stdout %2e

-- foo.go --
package main

func main() {}

@cherrymui @randall77 @aclements Is this a bug or intended behavior?

@cherrymui

This comment has been minimized.

Copy link
Contributor

@cherrymui cherrymui commented Nov 14, 2019

Yeah, this is just the symbol name in the binary. The symbol names are escaped to avoid collisions as well as other problems. We never document or guarantee how the symbol names are constructed, although we try to make it readable and close to the identifier in the source code. Gccgo constructs symbol names differently.

Is this a bug or intended behavior?

I would say this is an implementation detail that happens to be this way.

Versions before 1.13 have %22%22 instead ("").

Yeah. Before 1.13 the compiler writes "" and the linker expands to the same escaped name.

@jayconrod

This comment has been minimized.

Copy link
Contributor

@jayconrod jayconrod commented Nov 15, 2019

@cherrymui Escaping symbol names in compiled code makes sense to me, but can we unescape those names in stack traces?

@ianlancetaylor

This comment has been minimized.

Copy link
Contributor

@ianlancetaylor ianlancetaylor commented Nov 15, 2019

We could tweak the names in stack traces, but the question is: which choice is more confusing? For example, do people expect to be able to match the symbol names shown in stack traces to the symbol names reported by nm?

@aclements

This comment has been minimized.

Copy link
Member

@aclements aclements commented Nov 15, 2019

I suspect very few people are running nm, while a lot of people are looking at stack traces. OTOH, the sorts of things that cause escaping aren't very common. I'd lean toward showing un-escaped function names in the stack trace.

@ianlancetaylor

This comment has been minimized.

Copy link
Contributor

@ianlancetaylor ianlancetaylor commented Nov 15, 2019

It's exactly because few people run nm that I think this kind of thing can be problematic. Just as you're running into some problem that requires you to reach for the uncommon tool, you encounter the baffling fact that the symbol you see in the stack trace is not in the binary, at which point you face hours of debugging until you discover the truth. If you used nm all the time you would know about this problem.

@aclements

This comment has been minimized.

Copy link
Member

@aclements aclements commented Nov 15, 2019

Hmm. That assumes the user's mental model is that the stack trace contains binary symbols, as opposed to something at the level of language semantics like package paths and function/method names. This makes perfect sense to us as compiler authors, but I doubt many users think of it this way. Indeed, we go to some trouble to make the stack traces match language semantics rather than implementation details: eliding wrapper functions, rewriting names of some runtime functions, etc. All of our binary symbols on Darwin start with an underscore, but we don't print that in the stack trace. go doc gopkg.in/tomb.v2 works, but go doc gopkg.in/tomb%2ev2 doesn't. These are all operating at the language level.

That said, our symbols are so lightly escaped right now that we can just have our cake and eat it, too, and only occasionally find a bit of egg shell. We might as well err on the side of printing the symbol name since that will confuse basically no one (though it may surprise, as demonstrated by this bug report!) and will help the few people for whom it is better to have the raw symbol name.

I do wonder if generics will change this, if we use a stenciling implementation. If our symbols become significantly more mangled (say, like C++ symbols, though hopefully not that bad), I absolutely think it would be more meaningful to show something semantic in a stack trace over a mangled symbol name.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
5 participants
You can’t perform that action at this time.