From: Russ Cox Date: Sat, 14 Jan 2023 20:12:11 +0000 (-0500) Subject: doc: add godebug.md, documenting GODEBUG X-Git-Tag: go1.21rc1~1080 X-Git-Url: http://www.git.cypherpunks.su/?a=commitdiff_plain;h=a7fd2fab0e865f7fcedd3b437f1fa6e958bacc61;p=gostls13.git doc: add godebug.md, documenting GODEBUG Document the changes to GODEBUG implemented as part of proposal #56986. Fixes #56986. Change-Id: I23153a123e23820c5b22db4767620e037bbdd083 Reviewed-on: https://go-review.googlesource.com/c/go/+/462202 Reviewed-by: Damien Neil Run-TryBot: Russ Cox Reviewed-by: Ian Lance Taylor TryBot-Result: Gopher Robot Auto-Submit: Russ Cox --- diff --git a/doc/godebug.md b/doc/godebug.md new file mode 100644 index 0000000000..44e5a6e5b4 --- /dev/null +++ b/doc/godebug.md @@ -0,0 +1,181 @@ +--- +title: "Go, Backwards Compatibility, and GODEBUG" +layout: article +--- + + + +## Introduction {#intro} + +Go's emphasis on backwards compatibility is one of its key strengths. +There are, however, times when we cannot maintain complete compatibility. +If code depends on buggy (including insecure) behavior, +then fixing the bug will break that code. +New features can also have similar impacts: +enabling the HTTP/2 use by the HTTP client broke programs +connecting to servers with buggy HTTP/2 implementations. +These kinds of changes are unavoidable and +[permitted by the Go 1 compatibility rules](/doc/go1compat). +Even so, Go provides a mechanism called GODEBUG to +reduce the impact such changes have on Go developers +using newer toolchains to compile old code. + +A GODEBUG setting is a `key=value` pair +that controls the execution of certain parts of a Go program. +The environment variable `GODEBUG` +can hold a comma-separated list of these settings. +For example, if a Go program is running in an environment that contains + + GODEBUG=http2client=0,http2server=0 + +then that Go program will disable the use of HTTP/2 by default in both +the HTTP client and the HTTP server. +It is also possible to set the default `GODEBUG` for a given program +(discussed below). + +When preparing any change that is permitted by Go 1 compatibility +but may nonetheless break some existing programs, +we first engineer the change to keep as many existing programs working as possible. +For the remaining programs, +we define a new GODEBUG setting that +allows individual programs to opt back in to the old behavior. +A GODEBUG setting may not be added if doing so is infeasible, +but that should be extremely rare. + +GODEBUG settings added for compatibility will be maintained +for a minimum of two years (four Go releases). +Some, such as `http2client` and `http2server`, +will be maintained much longer, even indefinitely. + +When possible, each GODEBUG setting has an associated +[runtime/metrics](/pkg/runtime/metrics/) counter +named `/godebug/non-default-behavior/:events` +that counts the number of times a particular program's +behavior has changed based on a non-default value +for that setting. +For example, when `GODEBUG=http2client=0` is set, +`/godebug/non-default-behavior/http2client:events` +counts the number of HTTP transports that the program +has configured without HTTP/2 support. + +## Default GODEBUG Values {#default} + +When a GODEBUG setting is not listed in the environment variable, +its value is derived from three sources: +the defaults for the Go toolchain used to build the program, +amended to match the Go version listed in `go.mod`, +and then overridden by explicit `//go:debug` lines in the program. + +The [GODEBUG History](#history) gives the exact defaults for each Go toolchain version. +For example, Go 1.21 introduces the `panicnil` setting, +controlling whether `panic(nil)` is allowed; +it defaults to `panicnil=0`, making `panic(nil)` a run-time error. +Using `panicnil=1` restores the behavior of Go 1.20 and earlier. + +When compiling a work module or workspace that declares +an older Go version, the Go toolchain amends its defaults +to match that older Go version as closely as possible. +For example, when a Go 1.21 toolchain compiles a program, +if the work module's `go.mod` or the workspace's `go.work` +says `go` `1.20`, then the program defaults to `panicnil=1`, +matching Go 1.20 instead of Go 1.21. + +Because this method of setting GODEBUG defaults was introduced only in Go 1.21, +programs listing versions of Go earlier than Go 1.20 are configured to match Go 1.20, +not the older version. + +To override these defaults, a main package's source files +can include one or more `//go:debug` directives at the top of the file +(preceding the `package` statement). +Continuing the `panicnil` example, if the module or workspace is updated +to say `go` `1.21`, the program can opt back into the old `panic(nil)` +behavior by including this directive: + + //go:debug panicnil=1 + +Starting in Go 1.21, the Go toolchain treats a `//go:debug` directive +with an unrecognized GODEBUG setting as an invalid program. +Programs with more than one `//go:debug` line for a given setting +are also treated as invalid. +(Older toolchains ignore `//go:debug` directives entirely.) + +The defaults that will be compiled into a main package +are reported by the command: + + go list -f '{{.DefaultGODEBUG}}' my/main/package + +Only differences from the base Go toolchain defaults are reported. + +When testing a package, `//go:debug` lines in the `*_test.go` +files are treated as directives for the test's main package. +In any other context, `//go:debug` lines are ignored by the toolchain; +`go` `vet` reports such lines as misplaced. + +## GODEBUG History {#history} + +This section documents the GODEBUG settings introduced and removed in each major Go release +for compatibility reasons. +Packages or programs may define additional settings for internal debugging purposes; +for example, +see the [runtime documentation](/pkg/runtime#hdr-Environment_Variables) +and the [go command documentation](/cmd/go#hdr-Build_and_test_caching). + +### Go 1.21 + +Go 1.21 made it a run-time error to call `panic` with a nil interface value, +controlled by the [`panicnil` setting](/pkg/builtin/#panic). +There is no plan to remove this setting. + +### Go 1.20 + +Go 1.20 introduced support for rejecting insecure paths in tar and zip archives, +controlled by the [`tarinsecurepath` setting](/pkg/archive/tar/#Reader.Next) +and the [`zipinsecurepath` setting](/pkg/archive/zip/#NewReader). +These default to `tarinsecurepath=1` and `zipinsecurepath=1`, +preserving the behavior of earlier versions of Go. +A future version of Go may change the defaults to +`tarinsecurepath=0` and `zipinsecurepath=0`. + +Go 1.20 introduced automatic seeding of the +[`math/rand`](/pkg/math/rand) global random number generator, +controlled by the [`randautoseed` setting](/pkg/math/rand/#Seed). + +Go 1.20 introduced the concept of fallback roots for use during certificate verification, +controlled by the [`x509usefallbackroots` setting](/pkg/crypto/x509/#SetFallbackRoots). + +Go 1.20 removed the preinstalled `.a` files for the standard library +from the Go distribution. +Installations now build and cache the standard library like +packages in other modules. +The [`installgoroot` setting](/cmd/go#hdr-Compile_and_install_packages_and_dependencies) +restores the installation and use of preinstalled `.a` files. + +There is no plan to remove any of these settings. + +### Go 1.19 + +Go 1.19 made it an error for path lookups to resolve to binaries in the current directory, +controlled by the [`execerrdot` setting](/pkg/os/exec#hdr-Executables_in_the_current_directory). +There is no plan to remove this setting. + +### Go 1.18 + +Go 1.18 removed support for SHA1 in most X.509 certificates, +controlled by the [`x509sha1` setting](/crypto/x509#InsecureAlgorithmError). +This setting will be removed in a future release, Go 1.22 at the earliest. + +### Go 1.6 + +Go 1.6 introduced transparent support for HTTP/2, +controlled by the [`http2client`, `http2server`, and `http2debug` settings](/pkg/net/http/#hdr-HTTP_2). +There is no plan to remove these settings. + +### Go 1.5 + +Go 1.5 introduced a pure Go DNS resolver, +controlled by the [`netdns` setting](/pkg/net/#hdr-Name_Resolution). +There is no plan to remove this setting. diff --git a/src/cmd/go/alldocs.go b/src/cmd/go/alldocs.go index 99a4f75ab5..7ce8a071ad 100644 --- a/src/cmd/go/alldocs.go +++ b/src/cmd/go/alldocs.go @@ -2119,7 +2119,7 @@ // GOMODCACHE // The directory where the go command will store downloaded modules. // GODEBUG -// Enable various debugging facilities. See 'go doc runtime' +// Enable various debugging facilities. See https://go.dev/doc/godebug // for details. // GOENV // The location of the Go environment configuration file. diff --git a/src/cmd/go/internal/help/helpdoc.go b/src/cmd/go/internal/help/helpdoc.go index dddb785c0d..199d8af1b4 100644 --- a/src/cmd/go/internal/help/helpdoc.go +++ b/src/cmd/go/internal/help/helpdoc.go @@ -501,7 +501,7 @@ General-purpose environment variables: GOMODCACHE The directory where the go command will store downloaded modules. GODEBUG - Enable various debugging facilities. See 'go doc runtime' + Enable various debugging facilities. See https://go.dev/doc/godebug for details. GOENV The location of the Go environment configuration file.