我正在通过内联学习 Go 内存优化。以下代码是我的测试代码
我用
go build -gcflags=-m=2 main.go
得到所有的结果。我按照 Dave Cheney 的帖子 来做这个。
我的问题是:'gcflags' 的值是多少?文档在哪里,我谷歌找不到文档?
func fn1() int {
s := 1+2
return s
}
func fn2() string {
a := "h"
a += "e"
a += "l"
a += "l"
a += "o"
b := " "
c := "w"
c += "o"
c += "r"
c += "l"
c += "d"
d := "d"
d += "e"
d += "e"
d += "e"
d += "e"
d += "e"
d += "e"
d += "e"
d += "e"
d += "e"
s := a + b + c
return s
}
func fn3() {
p := fn1()
s := fn2()
println("p = " + string(p))
println("s = " + s)
}
输出:
go build -gcflags='-m=2' main.go
# command-line-arguments
./main.go:3:6: can inline fn1 as: func() int { s := 1 + 2; return s }
./main.go:16:6: cannot inline fn2: function too complex: cost 81 exceeds budget 80
./main.go:47:6: cannot inline fn3: function too complex: cost 85 exceeds budget 80
我也试过
-gcflags=-m=3, -gcflags=-m=4, -gcflags=-m=5
,结果如下,很难理解。也许有人可以帮我指出一个方向。
go build -gcflags=-m=3 main.go
# command-line-arguments
./main.go:3:6: can inline fn1 as: func() int { s := 1 + 2; return s }
./main.go:8:6: cannot inline fn2: recursive
./main.go:16:6: can inline fn3 as: func() { p := fn1(); p = fn2(p); println("p = " + string(p)) }
./main.go:17:10: inlining call to fn1 func() int { s := 1 + 2; return s }
./main.go:17:10: Before inlining:
. CALLFUNC l(17) tc(1) int
. . NAME-inlining.fn1 l(3) x(0) class(PFUNC) tc(1) used FUNC-@0
substituting name
. NAME-inlining.s g(2) l(4) x(0) class(PAUTO) tc(1) used int ->
. NAME-inlining.s l(4) x(0) class(PAUTO) tc(1) used int
substituting name
. NAME-inlining.s g(2) l(4) x(0) class(PAUTO) tc(1) used int ->
. NAME-inlining.s l(4) x(0) class(PAUTO) tc(1) used int
substituting name
. NAME-inlining.s g(2) l(4) x(0) class(PAUTO) tc(1) used int ->
. NAME-inlining.s l(4) x(0) class(PAUTO) tc(1) used int
./main.go:17:10: After inlining
. INLCALL-init
. . DCL l(17)
. . . NAME-inlining.~r0 l(3) x(0) class(PAUTO) tc(1) assigned used int
. . AS l(17) tc(1)
. . . NAME-inlining.~r0 l(3) x(0) class(PAUTO) tc(1) assigned used int
. . INLMARK l(+17) x(0)
. INLCALL l(17) tc(1) int
. INLCALL-rlist
. . NAME-inlining.~r0 l(3) x(0) class(PAUTO) tc(1) assigned used int
..... // too much
-gcflags
标志接受标志列表,在调用时应传递给go tool compile
。所以你可以在its documentation或运行命令中看到所有可能的选项:
go tool compile -help
更新: cd 到你有“.go”文件的文件夹(使用模块的项目)
然后运行:
go build -gcflags -help
示例:
$ go version
go version go1.20.2
$ ls -la
total 2
-rw-r--r-- 1 User 197121 199 Mar 20 09:04 hello.go
-rw-r--r-- 1 User 197121 198 Mar 20 09:04 hello_test.go
$ go build -gcflags -help
# gitlab.bla.com/bla_go/modules/hello
usage: compile [options] file.go...
-% debug non-static initializers
-+ compiling runtime
-B disable bounds checking
-C disable printing of columns in error messages
-D path
set relative path for local imports
-E debug symbol export
-I directory
add directory to import search path
-K debug missing line numbers
-L also show actual source file names in error messages for positions affected by //line directives
-N disable optimizations
-S print assembly listing
-V print version and exit
-W debug parse tree after type checking
-asan
build code compatible with C/C++ address sanitizer
-asmhdr file
write assembly header to file
-bench file
append benchmark times to file
-blockprofile file
write block profile to file
-buildid id
record id as the build id in the export metadata
-c int
concurrency during compilation (1 means no concurrency) (default 12)
-clobberdead
clobber dead stack slots (for debugging)
-clobberdeadreg
clobber dead registers (for debugging)
-complete
compiling complete package (no C or assembly)
-coveragecfg file
read coverage configuration from file
-cpuprofile file
write cpu profile to file
-d value
enable debugging settings; try -d help
-dwarf
generate DWARF symbols (default true)
-dwarfbasentries
use base address selection entries in DWARF (default true)
-dwarflocationlists
add location lists to DWARF in optimized mode (default true)
-dynlink
support references to Go symbols defined in other shared libraries
-e no limit on number of errors reported
-embedcfg file
read go:embed configuration from file
-gendwarfinl int
generate DWARF inline info records (default 2)
-goversion string
required version of the runtime
-h halt on error
-importcfg file
read import configuration from file
-installsuffix suffix
set pkg directory suffix
-j debug runtime-initialized variables
-json string
version,file for JSON compiler/optimizer detail output
-l disable inlining
-lang string
Go language version source code expects
-linkobj file
write linker-specific object to file
-linkshared
generate code that will be linked against Go shared libraries
-live
debug liveness analysis
-m print optimization decisions
-memprofile file
write memory profile to file
-memprofilerate rate
set runtime.MemProfileRate to rate
-msan
build code compatible with C/C++ memory sanitizer
-mutexprofile file
write mutex profile to file
-nolocalimports
reject local (relative) imports
-o file
write output to file
-oldcomparable
enable old comparable semantics
-p path
set expected package import path
-pack
write to file.a instead of file.o
-pgoprofile file
read profile from file
-r debug generated wrappers
-race
enable race detector
-shared
generate code that can be linked into a shared library
-smallframes
reduce the size limit for stack allocated objects
-spectre list
enable spectre mitigations in list (all, index, ret)
-std
compiling standard library
-symabis file
read symbol ABIs from file
-t enable tracing for debugging the compiler
-traceprofile file
write an execution trace to file
-trimpath prefix
remove prefix from recorded source file paths
-v increase debug verbosity
-w debug type checking
-wb
enable write barrier (default true)