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

proposal: cmd/go: allow setting runtime godebugs in go.mod / go:debug directives #71283

Open
hajimehoshi opened this issue Jan 15, 2025 · 8 comments
Labels
Proposal ToolProposal Issues describing a requested change to a Go tool or command-line program.
Milestone

Comments

@hajimehoshi
Copy link
Member

Proposal Details

Now asyncpreemptoff=1 cannot be specified by //go:debug:

examples\test\main.go:1:1: invalid //go:debug: unknown //go:debug setting "asyncpreemptoff"

However, there are many situations where disabling async preemption is required as a workaround to make applications work correctly:

I propose to enable to specify asyncpreemptoff=1 as //go:debug and godebug section in go.mod.

Note that it is still possible to specify it by -ldflags="-X=runtime.godebugDefault=asyncpreemptoff=1", but this is pretty hacky.

@gopherbot gopherbot added this to the Proposal milestone Jan 15, 2025
@seankhliao seankhliao changed the title proposal: cmd/go: enable to specify asyncpreemptoff=1 by //go:debug and godebug section in go.mod proposal: cmd/go: allow setting runtime godebugs in go.mod / go:debug directives Jan 15, 2025
@hajimehoshi
Copy link
Member Author

@seankhliao I don't intend to enable to specify other runtime godebugs than asyncpreemptoff.

@seankhliao
Copy link
Member

Rather than start with adding special cases, I think the entire class of godebugs should be considered together first, and only scoped down if it's not appropriate.

@hajimehoshi
Copy link
Member Author

Rather than start with adding special cases, I think the entire class of godebugs should be considered together first, and only scoped down if it's not appropriate.

I agree, though I don't have evidences to show how the other options are useful.

@thepudds
Copy link
Contributor

thepudds commented Jan 15, 2025

This proposal would have helped #69590 (I think?), where a user was not able to set GODEBUG=profstackdepth=32 in the application to work around a problem. (They could only set it in the environment, which was a problem for them).

#71187 was filed as a follow-up, which would be one solution for that particular issue, but this proposal here would be a more general solution, probably.

@ianlancetaylor ianlancetaylor moved this to Incoming in Proposals Jan 15, 2025
@seankhliao
Copy link
Member

there's also a runtime/debug package for a possible more code based api

@hajimehoshi
Copy link
Member Author

hajimehoshi commented Jan 15, 2025

there's also a runtime/debug package for a possible more code based api

Interesting. However, I guess that setting asyncpreemptoff=1 at code could be too late in some situations since this affects the scheduling. Even if this was set at an init function, other init functions in dependencies could do any odd things causing troubles.

@thepudds
Copy link
Contributor

thepudds commented Jan 15, 2025

A different direction would be to just promote asyncpreemptoff to an official GODEBUG setting, which would be more like what #71187 suggests for profstackdepth.

I don't know what would be better.

I do wonder though if there should be more of a formal split between:

  • official GODEBUG settings (which are documented at https://go.dev/doc/godebug, settable via go.mod, and so on), vs.
  • a runtime debug environment variable that is really for debugging.

Compared to the runtime, it seems the cmd/compile folks are more likely to add a debug flag to the compiler that helps them do their day-to-day work (and which can then later help triage reported issues, or help other gophers in the community when they are investigating something, etc.), and I wonder if it makes sense to make it easier to add a setting to the runtime for debugging while clearly communicating that it should not be relied upon (whether that's via GODEBUG, GOREALLYDEBUG, GODEBUG=experimental=foo=1, or something).

(I'm pretty sure this type of thing was discussed during the forward/backwards compatibility discussions, but at some point might be worth revisiting given there is now more experience with those changes).

(edit: sorry, my typing while distracted was not very successful ;-)

@mknyszek
Copy link
Contributor

mknyszek commented Jan 15, 2025

Historically, the runtime GODEBUGs have had a mix of purposes. Broadly, I see two categories: runtime debugging, and compatibility/workarounds. I feel like everything falling into the latter category should be visible to //go:debug.

I went down the list, and here's what I think falls into the compatibility/workarounds category:

  • cpu.* (Controls which CPU extensions can be used.)
  • disablethp (Controls THP, compatibility with Go 1.20 and earlier.)
  • madvdontneed (Controls the syscall used to return memory to the OS. Compatibility with Go 1.15 and earlier.)
  • memprofilerate (Same as runtime.MemProfileRate.)
  • profstackdepth (Controls stack depth for profiles. Compatibility with Go 1.22 and earlier.)
  • panicnil (This one was well-known and may already be available. TODO: which version this applied to.)
  • tracefpunwindoff (Controls whether to use frame pointer unwinding in execution traces. Not really that useful anymore as we squashed many of the bugs.)
  • asyncpreemptoff (Controls whether async preemption is done. Compatibility with Go 1.13 and earlier.
  • adaptivestackstart (Controls whether the initial goroutine stack size can change TODO: which version this applied to.)
  • asynctimerchan (This one was well-known and may already be available. TODO: which version this applied to.)

@gabyhelp gabyhelp added the ToolProposal Issues describing a requested change to a Go tool or command-line program. label Jan 15, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Proposal ToolProposal Issues describing a requested change to a Go tool or command-line program.
Projects
Status: Incoming
Development

No branches or pull requests

6 participants