-
Notifications
You must be signed in to change notification settings - Fork 17.9k
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
cmd/cgo: add -ldflags to augment CGO_LDFLAGS #66456
Comments
What is the specific change? Cgo already understands response files for command line arguments; the problem here is that the info is being passed to cgo in $CGO_LDFLAGS, and that's exacerbated by the go command and Bazel rules_go both not deduplicating the CGO_LDFLAGS info they gather from every cgo-using package in the build. (If 10 packages all say the same CGO_LDFLAGS, no need to say that part 10 times, just say it once.) Perhaps they should both deduplicate and then the length limit is not a problem anymore. We may need to deduplicate some linker arguments to appease the Mac linker anyway. |
Our I had tried de-duplication, but there were some ordering dependencies in the linker command. |
How did you use a response file at all? Response files are for command-line arguments, not environment variables. |
If we need to do something, we should add a -ldflags argument to the cgo command, and then that can be put in a response file. Interpreting @ signs in environment variables is a big scary door to open. |
The linked bazel-contrib/rules_go#2654 has an actual CGO_LDFLAGS line in the top comment. It is one line but it is very very long and GitHub has added a scroll bar, so you don't notice how long it is. That CGO_LDFLAGS has:
So deduplicating is not going to cut it. My suggestion is we add -ldflags to cgo, and then the go command and Bazel can use the support cgo already has for response files on its command line. |
In short, Support for this in
The fixed environment-variable length limit on Linux/Windows makes it currently impossible to compile larger projects. Thinking about whether |
It would help because cgo accepts response files on the command line already. |
Sorry for taking so long to understand - if adding |
This proposal has been added to the active column of the proposals project |
Thank you. |
Based on the discussion above, this proposal seems like a likely accept. The proposal is to add a -ldflags argument to cmd/cgo and then use that argument inside the go command. When the command line gets too long, the go command will automatically switch to response files, avoiding the possibility of $CGO_LDFLAGS getting too long. Bazel could then do the same (adopt -ldflags and use the existing response file functionality for command line arguments) to avoid the same problem. |
No change in consensus, so accepted. 🎉 The proposal is to add a -ldflags argument to cmd/cgo and then use that argument inside the go command. When the command line gets too long, the go command will automatically switch to response files, avoiding the possibility of $CGO_LDFLAGS getting too long. Bazel could then do the same (adopt -ldflags and use the existing response file functionality for command line arguments) to avoid the same problem. |
Change https://go.dev/cl/584655 mentions this issue: |
The PR that closed this issue ended up breaking rules_go (and other external users of Could this be fixed in a patch release? If that isn't possible, what would you recommend as a workaround? |
@fmeum - the problem is in
The "fix in the Go toolchain" was this proposal and the PR that folllowed. The next step is updating This should not be difficult to do, happy to collaborate. |
This part of the PR looks good to me, thanks! We can adopt it. The problem is that existing versions of rules_go no longer work with Go 1.23 due to |
I will send a patch to cgo to use both the We should presumably be able to remove that when we no longer need to support older versions of Bazel. |
Change https://go.dev/cl/596615 mentions this issue: |
For #66456 we changed from the CGO_LDFLAGS environment variable to the -ldflags option. This broke Bazel, which uses CGO_LDFLAGS. So restore reading CGO_LDFLAGS for now. For #66456 Change-Id: Iebdd8bde1c7c18da09c6370e284c7ac7fa08fc54 Reviewed-on: https://go-review.googlesource.com/c/go/+/596615 LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com> Reviewed-by: Ian Lance Taylor <iant@google.com> Auto-Submit: Ian Lance Taylor <iant@google.com> Commit-Queue: Ian Lance Taylor <iant@google.com> Auto-Submit: Ian Lance Taylor <iant@golang.org> Reviewed-by: Cherry Mui <cherryyz@google.com>
Thanks, this should be fixed in the next release candidate. If you are able to, please test Go repo HEAD. |
@ianlancetaylor Thanks for the quick fix! @grrtrr Happy to review a change to rules_go to make use of the new flag. |
For golang#66456 we changed from the CGO_LDFLAGS environment variable to the -ldflags option. This broke Bazel, which uses CGO_LDFLAGS. So restore reading CGO_LDFLAGS for now. For golang#66456 Change-Id: Iebdd8bde1c7c18da09c6370e284c7ac7fa08fc54 Reviewed-on: https://go-review.googlesource.com/c/go/+/596615 LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com> Reviewed-by: Ian Lance Taylor <iant@google.com> Auto-Submit: Ian Lance Taylor <iant@google.com> Commit-Queue: Ian Lance Taylor <iant@google.com> Auto-Submit: Ian Lance Taylor <iant@golang.org> Reviewed-by: Cherry Mui <cherryyz@google.com>
Proposal Details
cgo
proposal to avoid "argument list too long" (E2BIG
) issues whenCGO_LDFLAGS
outgrows system limits.Problem Description
The
cgo
command writes the contents of theCGO_LDFLAGS
environment variable into the archive.C/C++ linker flags and dependencies are passed via this environment variable.
When there is a large list of C/C++ dependencies, it is easy to hit the system size limits, causing compilation to fail with
cgo: argument list too long
.MAX_ARG_STRLEN
(128kiB).Related issues
Overly large lists dependencies can be written into a response file, using the
@file
syntax, passingCGO_LDFLAGS=@<path-to-file>
instead of failing the compilation.This is a convention supported by many compilers, such as
gcc
orclang
, and mirrors thepassLongArgsInResponseFiles
fix for long argument lists in #18468.Multiple
go
commands also support response file arguments viaobjabi.Flagparse
.Proposal: Since build systems such as
bazel
may execute compile and link stages in different locations,cmd/cgo
should@response_file
,expandArgs
function can be used to do this.The text was updated successfully, but these errors were encountered: