Golang二进制文件能否使用strip命令
Golang二进制文件能否使用strip命令
如果我对用于生产环境的Go二进制文件执行strip操作,会发生什么?
如果我使用 -ldflags="-s -w" 参数,是否可以使用 objcopy --keep-only-debug 来保留调试信息?
我应该怎么做?
4 回复
剥离二进制文件似乎能带来超过25%的空间缩减,但有一个名为“UPX”的项目可以将Go二进制文件压缩并减小到其原始大小的约15%:https://upx.github.io/
现在我发现你的另一篇帖子,你说你不想使用UPX。那样的话,你可以通过剥离二进制文件来节省大约25%的空间。
对于Go二进制文件执行strip操作,确实会移除调试信息,但需要注意Go的二进制结构特点。
strip对Go二进制文件的影响
执行strip命令会移除DWARF调试信息,但不会影响Go特有的运行时信息(如类型信息、栈映射等)。生产环境使用strip可以减少二进制大小,但会失去调试能力。
示例:
# 原始编译
go build -o app main.go
# 执行strip
strip app
# 检查文件大小变化
ls -lh app
使用-ldflags="-s -w"与objcopy的组合
-ldflags="-s -w"会移除调试信息,但通过objcopy可以更精细地控制:
# 编译时保留调试信息
go build -o app_with_debug main.go
# 提取调试信息到单独文件
objcopy --only-keep-debug app_with_debug app.debug
# 从原文件移除调试信息
objcopy --strip-debug app_with_debug app_stripped
# 或者使用strip命令
strip -g app_with_debug -o app_stripped
推荐的完整流程
# 1. 编译带完整调试信息的二进制
go build -o app_prod main.go
# 2. 提取调试信息到单独文件
objcopy --only-keep-debug app_prod app_prod.debug
# 3. 移除二进制中的调试信息(两种方式任选)
# 方式一:使用strip
strip --strip-debug app_prod -o app_prod_stripped
# 方式二:使用objcopy
objcopy --strip-debug app_prod app_prod_stripped
# 4. 验证调试信息已分离
file app_prod_stripped
readelf -S app_prod_stripped | grep debug
调试分离后的二进制
# 使用gdb调试时加载分离的调试信息
gdb -e app_prod_stripped -s app_prod.debug
# 或者在gdb中手动加载
(gdb) exec-file app_prod_stripped
(gdb) symbol-file app_prod.debug
这样既减少了生产环境二进制的大小,又保留了调试能力。

