Go保留符号表定位panic
去掉 -w -s 后,panic 堆栈信息会完整很多,跟踪起来更容易。
对比效果
带 -w -s(去掉符号表)的 panic
panic: runtime error: index out of range [5] with length 3
goroutine 1 [running]:
main.main.func1.2
<autogenerated>:1 +0x25
main.main.func1
<autogenerated>:1 +0x45
main.main
<autogenerated>:1 +0x85
去掉 -w -s(保留符号表)的 panic
panic: runtime error: index out of range [5] with length 3
goroutine 1 [running]:
github.com/leijmdas/godi.(*Container).resolveDependency(0xc0000a2000, {0x1234567, 0x89abcde})
/home/user/project/godi/container.go:142 +0x2a5
github.com/leijmdas/godi.(*Container).Inject(0xc0000a2000, {0x7654321, 0x1fedcba})
/home/user/project/godi/container.go:89 +0x145
main.main()
/home/user/project/cmd/server/main.go:34 +0x85
关键差异
信息 带 -w -s 去掉后
包路径 ❌ 缺失或 <autogenerated> ✅ github.com/leijmdas/godi
函数名 ❌ 可能被截断/混淆 ✅ (*Container).resolveDependency
文件名 ❌ 无或 <autogenerated> ✅ container.go
行号 ❌ 无 ✅ :142
可 pprof 分析 ❌ 否 ✅ 是
实际建议
# 开发/测试/预发环境:一定保留
go build -o myapp main.go
# 生产环境:推荐保留,除非体积是硬约束
go build -o myapp main.go
# 只有对体积极度敏感时,才去掉
go build -ldflags="-w -s" -o myapp main.go
补充:即使去掉 -w -s,也可用 objdump 救急
如果二进制已经去掉了符号表,但线上出了 panic,可以:
# 用相同源码重新编译一个带符号的版本
go build -gcflags="all=-N -l" -o myapp.debug main.go
# 用 addr2line 或 go 工具映射地址到源码
go tool addr2line myapp.debug < 0x2a5
结论:对于你的 Go 全家桶项目(godi、goconfig 等),建议生产环境也保留符号表,panic 排查效率高很多,现代服务器不差那几 MB。
