Compare commits

...

70 Commits

Author SHA1 Message Date
Gopher Robot
34c8b14ca9 [release-branch.go1.24] go1.24.3
Change-Id: I83acf5f2bda35ee81abbbb2fc6143fa6c8e342aa
Reviewed-on: https://go-review.googlesource.com/c/go/+/670456
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Gopher Robot <gobot@golang.org>
Reviewed-by: Cherry Mui <cherryyz@google.com>
Reviewed-by: Carlos Amedee <carlos@golang.org>
2025-05-06 11:13:03 -07:00
Damien Neil
8947f3395e [release-branch.go1.24] os: avoid escape from Root via paths ending in ../
The doInRoot function operates on a path split into components.
The final path component retained any trailing path separator
characters, to permit operations in a Root to retain the
trailing-separator behavior of non-Root operations. However,
doInRoot failed to take trailing separators into account
when checking for .. path components.

This could permit opening the parent directory of the Root
with a path ending in "../".

Change the split path to never include path separators in
components, and handle trailing separators independently
of the split path.

Thanks to Dan Sebastian Thrane of SDU eScience Center for
reporting this issue.

Fixes #73556
Updates #73555
Fixes CVE-2025-22873

Change-Id: I9a33a145c22f5eb1dd4e4cafae5fcc61a8d4f0d4
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/2160
Reviewed-by: Neal Patel <nealpatel@google.com>
Reviewed-by: Roland Shoemaker <bracewell@google.com>
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/2180
Commit-Queue: Damien Neil <dneil@google.com>
Reviewed-by: Damien Neil <dneil@google.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/670357
Reviewed-by: Carlos Amedee <carlos@golang.org>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
2025-05-06 10:29:09 -07:00
David Chase
06fd2f115b [release-branch.go1.24] cmd/compile: remove no-longer-necessary recursive inlining checks
this does result in a little bit more inlining,
cmd/compile text is 0.5% larger,
bent-benchmark text geomeans grow by only 0.02%.
some of our tests make assumptions about inlining.

Fixes: #73440.

Change-Id: I999d1798aca5dc64a1928bd434258a61e702951a
Reviewed-on: https://go-review.googlesource.com/c/go/+/655157
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Keith Randall <khr@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/666555
Reviewed-by: Keith Randall <khr@golang.org>
Reviewed-by: Carlos Amedee <carlos@golang.org>
2025-04-29 10:12:17 -07:00
Zxilly
f66ab6521c [release-branch.go1.24] cmd/internal/obj/wasm: use i64 for large return addr
Use i64 to avoid overflow when getting PC_F from the return addr.

For #73246.
Fixes #73281.

Change-Id: I5683dccf7eada4b8536edf53e2e83116a2f6d943
GitHub-Last-Rev: 267d9a1a03
GitHub-Pull-Request: golang/go#73277
Reviewed-on: https://go-review.googlesource.com/c/go/+/663995
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
(cherry picked from commit d60a684c87)
Reviewed-on: https://go-review.googlesource.com/c/go/+/668615
Reviewed-by: Carlos Amedee <carlos@golang.org>
2025-04-29 10:11:30 -07:00
Dimitri John Ledkov
c1f9c2c7b0 [release-branch.go1.24] cmd/go/internal/load: join incompatible and dirty build specifiers with .
Change "+incompatible+dirty" version to be "+incompatible.dirty" such
that it is SemVer spec compatible.

Fixes #73500

Change-Id: I714ffb3f1ad88c793656c3652367db34739a2144
Reviewed-on: https://go-review.googlesource.com/c/go/+/652955
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Sam Thanawalla <samthanawalla@google.com>
Reviewed-by: Sean Liao <sean@liao.dev>
Auto-Submit: Sean Liao <sean@liao.dev>
Reviewed-by: Michael Matloob <matloob@golang.org>
(cherry picked from commit a6e7445457)
Reviewed-on: https://go-review.googlesource.com/c/go/+/668135
2025-04-28 13:41:55 -07:00
Michael Pratt
0ab64e2caa [release-branch.go1.24] runtime: cleanup M vgetrandom state before dropping P
When an M is destroyed, we put its vgetrandom state back on the shared
list for another M to reuse. This list is simply a slice, so appending
to the slice may allocate. Currently this operation is performed in
mdestroy, after the P is released, meaning allocation is not allowed.

More the cleanup earlier in mdestroy when allocation is still OK.

Also add //go:nowritebarrierrec to mdestroy since it runs without a P,
which would have caught this bug.

Fixes #73144.
For #73141.

Change-Id: I6a6a636c3fbf5c6eec09d07a260e39dbb4d2db12
Reviewed-on: https://go-review.googlesource.com/c/go/+/662455
Reviewed-by: Jason Donenfeld <Jason@zx2c4.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Keith Randall <khr@golang.org>
Reviewed-by: Keith Randall <khr@google.com>
(cherry picked from commit 0b31e6d4cc)
Reviewed-on: https://go-review.googlesource.com/c/go/+/662496
2025-04-28 10:33:46 -07:00
Mateusz Poliwczak
56eb99859d [release-branch.go1.24] internal/runtime/maps: pass proper func PC to race.WritePC/race.ReadPC
Fixes #73192
For #73191

Change-Id: I0f8a5a19faa745943a98476c7caf4c97ccdce184
Reviewed-on: https://go-review.googlesource.com/c/go/+/663175
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
Auto-Submit: Michael Pratt <mpratt@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
(cherry picked from commit 14b15a2bea)
Reviewed-on: https://go-review.googlesource.com/c/go/+/663777
Reviewed-by: Carlos Amedee <carlos@golang.org>
Auto-Submit: Junyang Shao <shaojunyang@google.com>
Reviewed-by: Junyang Shao <shaojunyang@google.com>
2025-04-28 10:31:34 -07:00
Keith Randall
43130aff52 [release-branch.go1.24] runtime: fix 9-arg syscall on darwin/amd64
The last 3 arguments need to be passed on the stack, not registers.

Fixes #73379

Change-Id: Ib1155ad1a805957fad3d9594c93981a558755591
Reviewed-on: https://go-review.googlesource.com/c/go/+/665435
Reviewed-by: Michael Pratt <mpratt@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Keith Randall <khr@google.com>
(cherry picked from commit 9d7de04838)
Reviewed-on: https://go-review.googlesource.com/c/go/+/665995
2025-04-28 10:28:37 -07:00
古大羊
b2c005e7b2 [release-branch.go1.24] crypto/tls: fix ECH compatibility
Previously, the code only checked supportedVersions[0] for TLS 1.3
However, Chromium-based
browsers may list TLS 1.3 at different positions, causing ECH failures.
This fix:
    Iterates through supportedVersions to accept connections as long as TLS 1.3 is present.
    Improves ECH compatibility, ensuring Chrome, Edge, and other browsers work properly.

Fixes #73118

Change-Id: I32f4219fb6654d5cc22c7f33497c6142c0acb4f2
Reviewed-on: https://go-review.googlesource.com/c/go/+/648015
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Roland Shoemaker <roland@golang.org>
Reviewed-by: David Chase <drchase@google.com>
Reviewed-by: Daniel McCarney <daniel@binaryparadox.net>
(cherry picked from commit cd2f347c61)
Reviewed-on: https://go-review.googlesource.com/c/go/+/661936
Reviewed-by: Carlos Amedee <carlos@golang.org>
Reviewed-by: 古大羊 <lj1788@gmail.com>
2025-04-28 10:22:47 -07:00
Cherry Mui
a9d9b55709 [release-branch.go1.24] cmd/link: choose one with larger size for duplicated BSS symbols
When two packages declare a variable with the same name (with
linkname at least on one side), the linker will choose one as the
actual definition of the symbol if one has content (i.e. a DATA
symbol) and the other does not (i.e. a BSS symbol). When both have
content, it is redefinition error. When neither has content,
currently the choice is sort of arbitrary (depending on symbol
loading order, etc. which are subject to change).

One use case for that is that one wants to reference a symbol
defined in another package, and the reference side just wants to
see some of the fields, so it may be declared with a smaller type.
In this case, we want to choose the one with the larger size as
the true definition. Otherwise the code accessing the larger
sized one may read/write out of bounds, corrupting the next
variable. This CL makes the linker do so.

Also include the followup fix CL 661915.

Fixes #73092.
Updates #72032.

Change-Id: I160aa9e0234702066cb8f141c186eaa89d0fcfed
Reviewed-on: https://go-review.googlesource.com/c/go/+/660696
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: David Chase <drchase@google.com>
Reviewed-by: Than McIntosh <thanm@golang.org>
(cherry picked from commit 8f6c083d7b)
Reviewed-on: https://go-review.googlesource.com/c/go/+/662335
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
2025-04-10 08:34:54 -07:00
Damien Neil
fa7217f74d [release-branch.go1.24] os: avoid panic in Root when symlink references the root
We would panic when opening a symlink ending in ..,
where the symlink references the root itself.

For #73081
Fixes #73082

Change-Id: I7dc3f041ca79df7942feec58c197fde6881ecae5
Reviewed-on: https://go-review.googlesource.com/c/go/+/661416
Reviewed-by: Alan Donovan <adonovan@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
(cherry picked from commit cfc784a152)
Reviewed-on: https://go-review.googlesource.com/c/go/+/662315
2025-04-03 11:49:16 -07:00
Gopher Robot
49860cf92a [release-branch.go1.24] go1.24.2
Change-Id: I8e6c68d7fff0519e2bdbc48f6dbf153bc40c02cb
Reviewed-on: https://go-review.googlesource.com/c/go/+/661916
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Auto-Submit: Gopher Robot <gobot@golang.org>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Carlos Amedee <carlos@golang.org>
2025-04-01 09:11:46 -07:00
Austin Clements
f3a302358f [release-branch.go1.24] testing: detect a stopped timer in B.Loop
Currently, if the user stops the timer in a B.Loop benchmark loop, the
benchmark will run until it hits the timeout and fails.

Fix this by detecting that the timer is stopped and failing the
benchmark right away. We avoid making the fast path more expensive for
this check by "poisoning" the B.Loop iteration counter when the timer
is stopped so that it falls back to the slow path, which can check the
timer.

This causes b to escape from B.Loop, which is totally harmless because
it was already definitely heap-allocated. But it causes the
test/inline_testingbloop.go errorcheck test to fail. I don't think the
escape messages actually mattered to that test, they just had to be
matched. To fix this, we drop the debug level to -m=1, since -m=2
prints a lot of extra information for escaping parameters that we
don't want to deal with, and change one error check to allow b to
escape.

Fixes #72974.

Change-Id: I7d4abbb1ec1e096685514536f91ba0d581cca6b7
Reviewed-on: https://go-review.googlesource.com/c/go/+/659657
Auto-Submit: Austin Clements <austin@google.com>
Reviewed-by: Junyang Shao <shaojunyang@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/660558
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
2025-03-26 09:44:03 -07:00
Austin Clements
1d755aa488 [release-branch.go1.24] testing: detect early return from B.Loop
Currently, if a benchmark function returns prior to B.Loop() returning
false, we'll report a bogus result. While there was no way to detect
this with b.N-style benchmarks, one way b.Loop()-style benchmarks are
more robust is that we *can* detect it.

This CL adds a flag to B that tracks if B.Loop() has finished and
checks it after the benchmark completes. If there was an early exit
(not caused by another error), it reports a B.Error.

For #72974.

Change-Id: I731c1350e6df938c0ffa08fcedc11dc147e78854
Reviewed-on: https://go-review.googlesource.com/c/go/+/659656
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Austin Clements <austin@google.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
Reviewed-by: Junyang Shao <shaojunyang@google.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/660557
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
2025-03-26 09:41:07 -07:00
Austin Clements
9204aca6c2 [release-branch.go1.24] testing: separate b.Loop counter from b.N
Currently, b.Loop uses b.N as the iteration count target. However,
since it updates the target as it goes, the behavior is quite
different from a b.N-style benchmark. To avoid user confusion, this CL
gives b.Loop a separate, unexported iteration count target. It ensures
b.N is 0 within the b.Loop loop to help catch misuses, and commits the
final iteration count to b.N only once the loop is done (as the
documentation states "After Loop returns false, b.N contains the total
number of iterations that ran, so the benchmark may use b.N to compute
other average metrics.")

Since there are now two variables used by b.Loop, we put them in an
unnamed struct. Also, we rename b.loopN to b.loop.i because this
variable tracks the current iteration index (conventionally "i"), not
the target (conventionally "n").

Unfortunately, a simple renaming causes B.Loop to be too large for the
inliner. Thus, we make one simplification to B.Loop to keep it under
the threshold. We're about to lean into that simplification anyway in
a follow-up CL, so this is just temporary.

For #72974.

Change-Id: Ide1c4f1b9ca37f300f3beb0e60ba6202331b183e
Reviewed-on: https://go-review.googlesource.com/c/go/+/659655
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Junyang Shao <shaojunyang@google.com>
Auto-Submit: Austin Clements <austin@google.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/660556
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
2025-03-26 09:41:02 -07:00
Andy Pan
0ae3ca0a20 [release-branch.go1.24] runtime: explicitly disable async preempt for internal/runtime
Fixes #72115
For #71591
Relevant CL 560155

Change-Id: Iebc497d56b36d50c13a6dd88e7bca4578a03cf63
Reviewed-on: https://go-review.googlesource.com/c/go/+/654916
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
Auto-Submit: Michael Pratt <mpratt@google.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
(cherry picked from commit 92a63bdfee)
Reviewed-on: https://go-review.googlesource.com/c/go/+/660857
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
2025-03-26 09:38:08 -07:00
Michael Pratt
dae59b594c [release-branch.go1.24] runtime: skip TestCgoCallbackPprof on platforms with broken profiling
CL 658035 added TestCgoCallbackPprof, which is consistently failing on
solaris. runtime/pprof maintains a list of platforms where CPU profiling
does not work properly. Since this test requires CPU profiling, skip the
this test on those platforms.

For #72870.
For #72876.
For #72872.

Change-Id: I6a6a636cbf6b16abcbba8771178fe1d001be9d9b
Reviewed-on: https://go-review.googlesource.com/c/go/+/658415
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Michael Pratt <mpratt@google.com>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/658416
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
2025-03-25 11:51:27 -07:00
Michael Pratt
b7fd97ae3e [release-branch.go1.24] runtime: only set isExtraInC if there are no Go frames left
mp.isExtraInC is intended to indicate that this M has no Go frames at
all; it is entirely executing in C.

If there was a cgocallback to Go and then a cgocall to C, such that the
leaf frames are C, that is fine. e.g., traceback can handle this fine
with SetCgoTraceback (or by simply skipping the C frames).

However, we currently mismanage isExtraInC, unconditionally setting it
on return from cgocallback. This means that if there are two levels of
cgocallback, we end up running Go code with isExtraInC set.

1. C-created thread calls into Go function 1 (via cgocallback).
2. Go function 1 calls into C function 1 (via cgocall).
3. C function 1 calls into Go function 2 (via cgocallback).
4. Go function 2 returns back to C function 1 (returning via the remainder of cgocallback).
5. C function 1 returns back to Go function 1 (returning via the remainder of cgocall).
6. Go function 1 is now running with mp.isExtraInC == true.

The fix is simple; only set isExtraInC on return from cgocallback if
there are no more Go frames. There can't be more Go frames unless there
is an active cgocall out of the Go frames.

For #72870.
Fixes #72872.

Cq-Include-Trybots: luci.golang.try:go1.24-linux-amd64-longtest
Change-Id: I6a6a636c4e7ba75a29639d7036c5af3738033467
Reviewed-on: https://go-review.googlesource.com/c/go/+/658035
Reviewed-by: Cherry Mui <cherryyz@google.com>
Commit-Queue: Michael Pratt <mpratt@google.com>
Auto-Submit: Michael Pratt <mpratt@google.com>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
(cherry picked from commit 577bb3d0ce)
Reviewed-on: https://go-review.googlesource.com/c/go/+/658056
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
2025-03-25 11:51:24 -07:00
Rob Findley
311096a6a2 [release-branch.go1.24] go/types,types2: allocate the used* maps in initFiles
As described in the associated comment, we need to reallocate usedVars
and usedPkgNames in initFiles, as they are nilled out at the end of
Checker.Files, which may be called multiple times.

For #72122
For #72826

Change-Id: I9f6eb86e072d9d43a8720f6a5e86d827de6006a9
Reviewed-on: https://go-review.googlesource.com/c/go/+/655437
Auto-Submit: Robert Findley <rfindley@google.com>
Reviewed-by: Robert Griesemer <gri@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Alan Donovan <adonovan@google.com>
(cherry picked from commit fe9b292b11)
Reviewed-on: https://go-review.googlesource.com/c/go/+/657695
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
TryBot-Bypass: Dmitri Shuralyov <dmitshur@google.com>
2025-03-25 09:47:46 -07:00
Rob Findley
e9162e7e22 [release-branch.go1.24] go/types,types2: externalize used objects
The 'used' field on Var and PkgName is fundamentally an aspect of the
type checking pass: it records when objects are used, for the purposes
of reporting errors for unused variables or package names. While
expedient and performant, recording this information in the types.Object
instances themselves increases the memory footprint of type-checked
packages, and (as we saw in golang/go#71817) can lead to data races when
Objects are reused in follow-up type checking, such as is done with the
CheckExpr and Eval APIs.

Fix this by externalizing the 'used' information into two maps (one for
variables and one for packages) on the types.Checker, so that they are
garbage-collected after type checking, and cannot be a source of data
races.

Benchmarks showed essentially no change in performance.

For #72826

Change-Id: I40daeabe4ecaca3bcb494e2f1c62a04232098e49
Reviewed-on: https://go-review.googlesource.com/c/go/+/650796
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Robert Findley <rfindley@google.com>
Reviewed-by: Robert Griesemer <gri@google.com>
(cherry picked from commit 9189921e47)
Reviewed-on: https://go-review.googlesource.com/c/go/+/657675
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
2025-03-25 09:45:16 -07:00
Junyang Shao
d107ee90df [release-branch.go1.24] testing: allow manual timer control in testing.B.Loop
Fixes #72934

Change-Id: I56610d2d11d151a8f95b6434bbedbfcd5c11c317
Reviewed-on: https://go-review.googlesource.com/c/go/+/658975
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Commit-Queue: Junyang Shao <shaojunyang@google.com>
Reviewed-by: Austin Clements <austin@google.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/660555
Reviewed-by: Junyang Shao <shaojunyang@google.com>
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
2025-03-25 08:50:14 -07:00
Jordan Liggitt
213f1566ee [release-branch.go1.24] internal/godebugs: fix changed version for winsymlink and winreadlinkvolume to 1.23
https://go.dev/doc/godebug#go-123 documents changes to winsymlink and
winreadlinkvolume in Go 1.23.

This fixes the registered "changed" minor version to Go 1.23,
so that defaults when building a Go 1.22 module are correct.

Fixes #72938

Change-Id: I5d5bf31ca04f9e95208fb0fdaad2232f9db653ff
Reviewed-on: https://go-review.googlesource.com/c/go/+/659035
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>
(cherry picked from commit 2e749a645a)
Reviewed-on: https://go-review.googlesource.com/c/go/+/659036
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@golang.org>
2025-03-24 15:37:49 -07:00
Damien Neil
ac1f5aa3d6 [release-branch.go1.24] net/http: reject newlines in chunk-size lines
Unlike request headers, where we are allowed to leniently accept
a bare LF in place of a CRLF, chunked bodies must always use CRLF
line terminators. We were already enforcing this for chunk-data lines;
do so for chunk-size lines as well. Also reject bare CRs anywhere
other than as part of the CRLF terminator.

Fixes CVE-2025-22871
Fixes #72011
For #71988

Change-Id: Ib0e21af5a8ba28c2a1ca52b72af8e2265ec79e4a
Reviewed-on: https://go-review.googlesource.com/c/go/+/652998
Reviewed-by: Jonathan Amsterdam <jba@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
(cherry picked from commit d31c805535)
Reviewed-on: https://go-review.googlesource.com/c/go/+/657056
2025-03-18 12:40:27 -07:00
Damien Neil
fd29397dca [release-branch.go1.24] net/http: don't modify caller's tls.Config.NextProtos
Clone the input slice before adjusting NextProtos
to add or remove "http/1.1" and "h2" entries,
so as not to modify a slice that the caller might be using.
(We clone the tls.Config that contains the slice, but
that's a shallow clone.)

For #72100
Fixes #72103

Change-Id: I9f228b8fb6f6f2ca5023179ec114929c002dbda9
Reviewed-on: https://go-review.googlesource.com/c/go/+/654875
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Auto-Submit: Damien Neil <dneil@google.com>
Reviewed-by: Jonathan Amsterdam <jba@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/657215
2025-03-17 14:37:18 -07:00
Alexandr Primak
4524009ba6 [release-branch.go1.24] runtime: Added usage example for the runtime.AddCleanup() function.
The existing description of the function lacks usage examples, which makes it difficult to understand, so I added one.

There is no open issue about this, since the implementation seems trivial.

For #72795
Fixes #72796

Change-Id: I96b29f0b21d1c7fda04128239633c8a2fc36fef2
Reviewed-on: https://go-review.googlesource.com/c/go/+/649995
Reviewed-by: Carlos Amedee <carlos@golang.org>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
Auto-Submit: Carlos Amedee <carlos@golang.org>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
(cherry picked from commit 4c75671871)
Reviewed-on: https://go-review.googlesource.com/c/go/+/656815
Reviewed-by: Cherry Mui <cherryyz@google.com>
2025-03-17 14:36:28 -07:00
Filippo Valsorda
bd1bc8a6e7 [release-branch.go1.24] crypto/tls: allow P-521 in FIPS 140-3 mode and Go+BoringCrypto
Partially reverts CL 587296, restoring the Go+BoringCrypto 1.23 behavior
in terms of supported curves.

Updates #71757
Fixes #72823

Change-Id: I6a6a465651a8407056fd0fae091d10a945b37997
Reviewed-on: https://go-review.googlesource.com/c/go/+/657135
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Roland Shoemaker <roland@golang.org>
Reviewed-by: Daniel McCarney <daniel@binaryparadox.net>
Reviewed-by: David Chase <drchase@google.com>
2025-03-17 14:33:52 -07:00
David Chase
c2a34bedee [release-branch.go1.24] cmd/compile: use inline-Pos-based recursion test
Look at the inlining stack of positions for a call site,
if the line/col/file of the call site appears in that
stack, do not inline.  This subsumes all the other
recently-added recursive inlining checks, but they are
left in to make this easier+safer to backport.

Fixes #72822

Change-Id: I0f487bb0d4c514015907c649312672b7be464abd
Reviewed-on: https://go-review.googlesource.com/c/go/+/655155
Reviewed-by: Keith Randall <khr@golang.org>
Reviewed-by: Keith Randall <khr@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
(cherry picked from commit cad4dca518)
Reviewed-on: https://go-review.googlesource.com/c/go/+/657075
2025-03-12 13:50:58 -07:00
Cuong Manh Le
0ace2d8aca [release-branch.go1.24] cmd/compile: fix out of memory when inlining closure
CL 629195 strongly favor closure inlining, allowing closures to be
inlined more aggressively.

However, if the closure body contains a call to a function, which itself
is one of the call arguments, it causes the infinite inlining.

Fixing this by prevent this kind of functions from being inlinable.

Fixes #72067

Change-Id: I5fb5723a819b1e2c5aadb57c1023ec84ca9fa53c
Reviewed-on: https://go-review.googlesource.com/c/go/+/654195
Reviewed-by: David Chase <drchase@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/654517
Commit-Queue: Junyang Shao <shaojunyang@google.com>
Auto-Submit: Junyang Shao <shaojunyang@google.com>
Reviewed-by: Junyang Shao <shaojunyang@google.com>
Reviewed-by: Jorropo <jorropo.pgm@gmail.com>
2025-03-05 13:27:11 -08:00
Junyang Shao
e4119e9b74 [release-branch.go1.24] all: updates vendored x/net
This is to update module version to the fixed x/net.

For #71984

Change-Id: I7d50e302e8ba7d3ee28df2669fc16f19c12cf088
Reviewed-on: https://go-review.googlesource.com/c/go/+/654795
Reviewed-by: Michael Pratt <mpratt@google.com>
Auto-Submit: Junyang Shao <shaojunyang@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Junyang Shao <shaojunyang@google.com>
2025-03-04 12:31:16 -08:00
Gopher Robot
339c903a75 [release-branch.go1.24] go1.24.1
Change-Id: I774fcee39151f830ad58fd1677239bc0207c6679
Reviewed-on: https://go-review.googlesource.com/c/go/+/654319
Auto-Submit: Gopher Robot <gobot@golang.org>
Auto-Submit: Junyang Shao <shaojunyang@google.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
Reviewed-by: Junyang Shao <shaojunyang@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
2025-03-04 11:27:08 -08:00
Damien Neil
334de7982f [release-branch.go1.24] all: updated vendored x/net with security fix
6ed00d0 [internal-branch.go1.24-vendor] proxy, http/httpproxy: do not mismatch IPv6 zone ids against hosts

Fixes CVE-2025-22870
For #71986

Change-Id: I7bda0825f1a9470b0708714d9cc32b5eae212f8b
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/2121
Reviewed-by: Neal Patel <nealpatel@google.com>
Reviewed-by: Roland Shoemaker <bracewell@google.com>
Commit-Queue: Roland Shoemaker <bracewell@google.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/654715
Reviewed-by: Michael Pratt <mpratt@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Junyang Shao <shaojunyang@google.com>
Reviewed-by: Damien Neil <dneil@google.com>
2025-03-04 10:41:47 -08:00
Ian Lance Taylor
5d6920842b [release-branch.go1.24] runtime/cgo: avoid errors from -Wdeclaration-after-statement
CL 652181 accidentally missed this iPhone only code.

For #71961
For #71963

Change-Id: I567f8bb38958907442e69494da330d5199d11f54
Reviewed-on: https://go-review.googlesource.com/c/go/+/653137
Commit-Queue: Ian Lance Taylor <iant@google.com>
Reviewed-by: Ian Lance Taylor <iant@google.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
Auto-Submit: Ian Lance Taylor <iant@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
2025-02-26 14:41:34 -08:00
Keith Randall
949eae84df [release-branch.go1.24] cmd/compile: don't pull constant offsets out of pointer arithmetic
This could lead to manufacturing a pointer that points outside
its original allocation.

Bug was introduced in CL 629858.

Fixes #71938

Change-Id: Ia86ab0b65ce5f80a8e0f4f4c81babd07c5904f8d
Reviewed-on: https://go-review.googlesource.com/c/go/+/652078
Reviewed-by: Keith Randall <khr@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
(cherry picked from commit 8b8bff7bb2)
Reviewed-on: https://go-review.googlesource.com/c/go/+/652855
2025-02-26 12:15:08 -08:00
Michael Anthony Knyszek
0bfde51e0d [release-branch.go1.24] runtime: document that cleanups can run concurrently with each other
For #71825.
Fixes #71955.

Change-Id: I25af19eb72d75f13cf661fc47ee5717782785326
Reviewed-on: https://go-review.googlesource.com/c/go/+/652637
Reviewed-by: Keith Randall <khr@golang.org>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Michael Knyszek <mknyszek@google.com>
Reviewed-by: Keith Randall <khr@google.com>
2025-02-26 12:04:21 -08:00
Ian Lance Taylor
45a52718e3 [release-branch.go1.24] runtime/cgo: avoid errors from -Wdeclaration-after-statement
It's used by the SWIG CI build, at least, and it's an easy fix.

Fixes #71963
For #71961

Change-Id: Id21071a5aef216b35ecf0e9cd3e05d08972d92fe
Reviewed-on: https://go-review.googlesource.com/c/go/+/652181
Reviewed-by: Cherry Mui <cherryyz@google.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Michael Pratt <mpratt@google.com>
(cherry picked from commit 76c7028253)
Reviewed-on: https://go-review.googlesource.com/c/go/+/652936
Reviewed-by: Michael Knyszek <mknyszek@google.com>
2025-02-26 11:46:33 -08:00
qiulaidongfeng
7f375e2c22 [release-branch.go1.24] reflect: let Value.Seq return the iteration value correct type
Fixes #71916
For #71905

Change-Id: I50a418f8552e071c6e5011af5b9accc7d41548d0
Reviewed-on: https://go-review.googlesource.com/c/go/+/651855
Reviewed-by: Ian Lance Taylor <iant@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Ian Lance Taylor <iant@google.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
(cherry picked from commit 194696f1d1)
Reviewed-on: https://go-review.googlesource.com/c/go/+/652895
Reviewed-by: Michael Knyszek <mknyszek@google.com>
Auto-Submit: Michael Pratt <mpratt@google.com>
2025-02-26 11:11:37 -08:00
Zxilly
4070531920 [release-branch.go1.24] syscall: disable O_DIRECTORY on Windows for js/wasm
O_DIRECTORY is not available on all platforms, as described at

https://nodejs.org/docs/latest/api/fs.html#file-open-constants .

On Windows, only O_APPEND, O_CREAT, O_EXCL, O_RDONLY, O_RDWR,
O_TRUNC, O_WRONLY, and UV_FS_O_FILEMAP are available.

For #71758.
Fixes #71977.

Change-Id: Iacc890ba9a30dcd75eb746ec324fa0c3e368048e
GitHub-Last-Rev: a0160e8fc8
GitHub-Pull-Request: golang/go#71770
Reviewed-on: https://go-review.googlesource.com/c/go/+/650015
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@golang.org>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
Auto-Submit: Dmitri Shuralyov <dmitshur@golang.org>
TryBot-Bypass: Dmitri Shuralyov <dmitshur@golang.org>
(cherry picked from commit ad8b33002b)
Reviewed-on: https://go-review.googlesource.com/c/go/+/652835
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
2025-02-26 10:08:02 -08:00
Michael Anthony Knyszek
5ffdb9c88b [release-branch.go1.24] reflect: correctly handle method values in Seq
Currently method values aren't correctly handled in Seq because we call
canRangeFunc on the reciever type, not the method value type, when we're
handling a method value. reflect.Value.Type has the logic to obtain the
method value type from the Value.

This change slightly refactors reflect.Value.Type into a separate
function so we can obtain the correct type as an abi.Type and pass it
off to canRangeFunc (and canRangeFunc2).

For #71874.
Fixes #71876.

Change-Id: Ie62dfca2a84b8f2f816bb87ff1ed1a58a7bb8122
Reviewed-on: https://go-review.googlesource.com/c/go/+/651416
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
Auto-Submit: Michael Knyszek <mknyszek@google.com>
(cherry picked from commit d93f6df0cc)
Reviewed-on: https://go-review.googlesource.com/c/go/+/651515
2025-02-26 09:53:54 -08:00
Michael Pratt
becc17ebcd [release-branch.go1.24] runtime: use WCLONE when waiting on pidfd test child
As of CL 650835, the pidfd test child no longer sends SIGCHLD on exit.
Per clone(2), "If [the child termination] signal is specified as
anything other than SIGCHLD, then the parent process must specify the
__WALL or __WCLONE options when waiting for the child with wait(2)."

Align with this requirement.

For #71849.
For #71828.

Change-Id: I6a6a636c739e4a59abe1533fe429a433e8588939
Reviewed-on: https://go-review.googlesource.com/c/go/+/651415
Reviewed-by: Ian Lance Taylor <iant@golang.org>
Auto-Submit: Michael Pratt <mpratt@google.com>
Reviewed-by: Ian Lance Taylor <iant@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
(cherry picked from commit e1e65ae3ee)
Reviewed-on: https://go-review.googlesource.com/c/go/+/651476
2025-02-26 09:45:51 -08:00
Ian Lance Taylor
d418e224ae [release-branch.go1.24] syscall: don't send child signal when testing pidfd
Avoid a spurious SIGCHLD the first time we start a process.

For #71828
Fixes #71849

Change-Id: I744100d21bf6aaaaafc99bc5eec9f9f807a50682
Reviewed-on: https://go-review.googlesource.com/c/go/+/651035
Reviewed-by: Michael Knyszek <mknyszek@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
2025-02-26 09:45:47 -08:00
Jorropo
456eaf5c29 [release-branch.go1.24] cmd/compile: don't report newLimit discovered when unsat happens multiple times
Fixes #71855

Change-Id: I696fcb8fc8c0c2e5e5ae6ab50596f6bdb9b7d498
Reviewed-on: https://go-review.googlesource.com/c/go/+/650975
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Keith Randall <khr@google.com>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
Reviewed-by: Keith Randall <khr@golang.org>
(cherry picked from commit 00635de759)
Reviewed-on: https://go-review.googlesource.com/c/go/+/652179
Reviewed-by: Jorropo <jorropo.pgm@gmail.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
2025-02-26 09:44:53 -08:00
Michael Pratt
e4ef83383e [release-branch.go1.24] debug/buildinfo: base64-encode test binaries
Overzealous security scanners don't like the Go 1.17 binary because they
think it has every 1.17 security vulnerability. base64-encode the binary
to hide from them.

I've also extended the instructions to make the binary easier to
reproduce.

Since we do the Go binary, we might as well do the C binary too, as it
apparently makes some virus scanners unhappy.

Fixes #71858.
For #71753.
For #71734.
For #71821.

Change-Id: I6a6a636cccbf5312522f52f27f74eded64048fb7
Reviewed-on: https://go-review.googlesource.com/c/go/+/651175
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Michael Pratt <mpratt@google.com>
Reviewed-by: Ian Lance Taylor <iant@google.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
(cherry picked from commit af00524a6c)
Reviewed-on: https://go-review.googlesource.com/c/go/+/651235
2025-02-26 09:44:08 -08:00
khr@golang.org
4e6d3468cc [release-branch.go1.24] cmd/compile: ensure we don't reuse temporary register
Before this CL, we could use the same register for both a temporary
register and for moving a value in the output register out of the way.

Fixes #71904

Change-Id: Iefbfd9d4139136174570d8aadf8a0fb391791ea9
Reviewed-on: https://go-review.googlesource.com/c/go/+/651221
Reviewed-by: David Chase <drchase@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Keith Randall <khr@google.com>
(cherry picked from commit cc16fb52e6)
Reviewed-on: https://go-review.googlesource.com/c/go/+/652178
2025-02-26 09:43:51 -08:00
Ian Lance Taylor
f5c388313f [release-branch.go1.24] internal/godebugs: add fips140 as an opaque godebug setting
This permits using "godebug fips140=on" in go.mod and
using "//go:debug fips140=on" in the main package.

Change code references to the godebug setting to remove the #
which is no longer required.

For #71666
Fixes #71745

Change-Id: I3a60ecc55b03848dadd6d431eb43137b6df6568b
Reviewed-on: https://go-review.googlesource.com/c/go/+/649495
Reviewed-by: Ian Lance Taylor <iant@google.com>
Auto-Submit: Ian Lance Taylor <iant@google.com>
Reviewed-by: Roland Shoemaker <roland@golang.org>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Filippo Valsorda <filippo@golang.org>
(cherry picked from commit 2b43ce0a9d5825d66aa42a6fa9076f2fb9c181ea)
Reviewed-on: https://go-review.googlesource.com/c/go/+/650675
Commit-Queue: Ian Lance Taylor <iant@google.com>
2025-02-25 21:52:03 -08:00
David Chase
af236716b2 [release-branch.go1.24] cmd/compile, runtime: use deferreturn as target PC for recover from deferrangefunc
The existing code for recover from deferrangefunc was broken in
several ways.

1. the code following a deferrangefunc call did not check the return
value for an out-of-band value indicating "return now" (i.e., recover
was called)

2. the returned value was delivered using a bespoke ABI that happened
to match on register-ABI platforms, but not on older stack-based
ABI.

3. the returned value was the wrong width (1 word versus 2) and
type/value(integer 1, not a pointer to anything) for deferrangefunc's
any-typed return value (in practice, the OOB value check could catch
this, but still, it's sketchy).

This -- using the deferreturn lookup method already in place for
open-coded defers -- turned out to be a much-less-ugly way of
obtaining the desired transfer of control for recover().

TODO: we also could do this for regular defer, and delete some code.

Fixes #71840

Change-Id: If7d7ea789ad4320821aab3b443759a7d71647ff0
Reviewed-on: https://go-review.googlesource.com/c/go/+/650476
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/651497
2025-02-21 18:58:02 -08:00
Ian Lance Taylor
0f7b7600fb [release-branch.go1.24] doc/godebug: mention GODEBUG=fips140
For #71666
For #71745

Change-Id: Ice816cf2943c5b6660f05934b4c7ca38545714b0
Reviewed-on: https://go-review.googlesource.com/c/go/+/648520
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Roland Shoemaker <roland@golang.org>
Reviewed-by: Filippo Valsorda <filippo@golang.org>
Commit-Queue: Ian Lance Taylor <iant@google.com>
Auto-Submit: Ian Lance Taylor <iant@google.com>
Reviewed-by: Ian Lance Taylor <iant@google.com>
(cherry picked from commit 5f65e5cb56)
Reviewed-on: https://go-review.googlesource.com/c/go/+/650596
Reviewed-by: Michael Knyszek <mknyszek@google.com>
2025-02-19 13:59:08 -08:00
Cuong Manh Le
eb58df7dbf [release-branch.go1.24] cmd/compile: avoid infinite recursion when inlining closures
CL 630696 changes budget for once-called closures, making them more
inlinable. However, when recursive inlining involve both the closure and
its parent, the inliner goes into an infinite loop:

	parent (a closure)  -> closure -> parent -> ...

The problem here dues to the closure name mangling, causing the inlined
checking condition failed, since the closure name affects how the
linker symbol generated.

To fix this, just prevent the closure from inlining its parent into
itself, avoid the infinite inlining loop.

Fixes #71829

Change-Id: Ib27626d70f95e5f1c24a3eb1c8e6c3443b7d90c8
Reviewed-on: https://go-review.googlesource.com/c/go/+/649656
Reviewed-by: David Chase <drchase@google.com>
Auto-Submit: Cuong Manh Le <cuong.manhle.vn@gmail.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/650555
2025-02-19 13:49:27 -08:00
qmuntal
30f4d9e117 [release-branch.go1.24] syscall: don't truncate newly created files on Windows
There is no need for syscall.OpenFile to truncate newly created files.
Some special Windows files, like the NUL device, can't be
truncated, so we should avoid truncating unless it is really necessary.

For #71752
Fixes #71836

Change-Id: I8238048594f706f6a5281053d55cfe3dc898828d
Reviewed-on: https://go-review.googlesource.com/c/go/+/650276
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Damien Neil <dneil@google.com>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
(cherry picked from commit 4267fd389e)
Reviewed-on: https://go-review.googlesource.com/c/go/+/650597
Reviewed-by: Ian Lance Taylor <iant@google.com>
Auto-Submit: Ian Lance Taylor <iant@google.com>
Commit-Queue: Ian Lance Taylor <iant@google.com>
Reviewed-by: Quim Muntal <quimmuntal@gmail.com>
2025-02-19 10:46:24 -08:00
Paul Murphy
bb0e5c2045 [release-branch.go1.24] runtime: fix usleep on s390x/linux
The timespec argument takes the remainder in nanoseconds, not
microseconds. Convert the remaining time to nsec.

Fixes #71728

Change-Id: I36cbbe3a088830c5e3afcc9516ef42e96ee21268
Reviewed-on: https://go-review.googlesource.com/c/go/+/648915
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Mauri de Souza Meneguzzo <mauri870@gmail.com>
Reviewed-by: Axel Busch <axel.busch@ibm.com>
Run-TryBot: Paul Murphy <murp@ibm.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
Reviewed-by: Ian Lance Taylor <iant@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Vishwanatha HD <vishwanatha.hd@ibm.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/649375
Auto-Submit: Ian Lance Taylor <iant@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
2025-02-19 09:14:47 -08:00
段仪
cd0e528d3d [release-branch.go1.24] runtime: add some linknames back for github.com/bytedance/sonic
Add some linknames back, therefore sonic (github.com/bytedance/sonic) can work correctly.

For #71672
Fixes #71705

Change-Id: Iae86c837d8a714855106a26766aa08b128e17e58
GitHub-Last-Rev: 4de0a48717
GitHub-Pull-Request: golang/go#71673
Reviewed-on: https://go-review.googlesource.com/c/go/+/650375
Auto-Submit: Ian Lance Taylor <iant@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
2025-02-19 09:12:30 -08:00
Quan Tong
80e2e474b8 [release-branch.go1.24] cmd/go: initialize req.Header when loading git credential
Fixes #71687

Change-Id: I3d733a50b4451dfb571aba91a28387ba9e0614dc
Reviewed-on: https://go-review.googlesource.com/c/go/+/647615
Reviewed-by: Michael Matloob <matloob@golang.org>
Reviewed-by: Sam Thanawalla <samthanawalla@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
(cherry picked from commit 58834c3ee0)
Reviewed-on: https://go-review.googlesource.com/c/go/+/648936
Reviewed-by: Dmitri Shuralyov <dmitshur@golang.org>
TryBot-Bypass: Dmitri Shuralyov <dmitshur@golang.org>
Auto-Submit: Dmitri Shuralyov <dmitshur@google.com>
2025-02-12 11:16:33 -08:00
Gopher Robot
3901409b5d [release-branch.go1.24] go1.24.0
Change-Id: I98457f219e75fb99233804d15c8b9577ee3d4a24
Reviewed-on: https://go-review.googlesource.com/c/go/+/648555
Reviewed-by: Cherry Mui <cherryyz@google.com>
TryBot-Bypass: Dmitri Shuralyov <dmitshur@golang.org>
Auto-Submit: Gopher Robot <gobot@golang.org>
Reviewed-by: Dmitri Shuralyov <dmitshur@golang.org>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
2025-02-11 09:55:39 -08:00
Cherry Mui
35c0ea22a9 [release-branch.go1.24] bytes: use "subslice" instead of "substring" in doc comments
The bytes package iterators return subslices, not substrings.

Updates #61901.

Change-Id: Ida91d3e33a0f178edfe9a267861adf4f13f9a965
Reviewed-on: https://go-review.googlesource.com/c/go/+/647875
Reviewed-by: Ian Lance Taylor <iant@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
(cherry picked from commit ff27d270c9)
Reviewed-on: https://go-review.googlesource.com/c/go/+/648095
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@golang.org>
TryBot-Bypass: Cherry Mui <cherryyz@google.com>
2025-02-10 11:50:28 -08:00
Michael Anthony Knyszek
6d399e9da6 [release-branch.go1.24] os: hide SetFinalizer from users of Root
Currently Root embeds a root and calls SetFinalizer on &r.root. This
sets the finalizer on the outer root, which is visible to users of
os.Root, and thus they can mutate the finalizer attached to it.

This change modifies Root to not embed its inner root, but rather to
refer to it by pointer. This allows us to set the finalizer on this
independent inner object, preventing users of os.Root from changing the
finalizer. This follows the same pattern as os.File's finalizer.

Fixes #71617.

Change-Id: Ibd199bab1b3c877d5e12ef380fd4647b4e10221f
Reviewed-on: https://go-review.googlesource.com/c/go/+/647876
Auto-Submit: Michael Knyszek <mknyszek@google.com>
Reviewed-by: Damien Neil <dneil@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
(cherry picked from commit a704d39b29)
Reviewed-on: https://go-review.googlesource.com/c/go/+/648135
TryBot-Bypass: Michael Knyszek <mknyszek@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@golang.org>
2025-02-10 10:48:31 -08:00
thepudds
b7b4c60585 [release-branch.go1.24] weak: prevent unsafe conversions using weak pointers
Prevent conversions between Pointer types,
like we do for sync/atomic.Pointer.

Fixes #71583

Change-Id: I20e83106d8a27996f221e6cd9d52637b0442cea4
Reviewed-on: https://go-review.googlesource.com/c/go/+/647195
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Michael Knyszek <mknyszek@google.com>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
(cherry picked from commit 8163ea1458)
Reviewed-on: https://go-review.googlesource.com/c/go/+/647435
Reviewed-by: Carlos Amedee <carlos@golang.org>
TryBot-Bypass: Cherry Mui <cherryyz@google.com>
2025-02-06 13:53:01 -08:00
Gopher Robot
18068cb96a [release-branch.go1.24] go1.24rc3
Change-Id: Ib3e93a2ea07a0ef1ce0989143d03c765ede8cc99
Reviewed-on: https://go-review.googlesource.com/c/go/+/646936
Reviewed-by: Carlos Amedee <carlos@golang.org>
Reviewed-by: Cherry Mui <cherryyz@google.com>
TryBot-Bypass: Cherry Mui <cherryyz@google.com>
Auto-Submit: Gopher Robot <gobot@golang.org>
2025-02-05 12:35:01 -08:00
Roland Shoemaker
c43ac38b3b [release-branch.go1.24] Revert "cmd/go/internal/work: allow @ character in some -Wl, linker flags on darwin"
This reverts commit e3cd55e9d2.

This change introduced a security issue as @ flags are first resolved as
files by the darwin linker, before their meaning as flags, allowing the
flag filtering logic to be entirely bypassed.

Thanks to Juho Forsén for reporting this issue.

Fixes #71476
Fixes CVE-2025-22867

Change-Id: I3a4b4a6fc534de105d930b8ed5b9900bc94b0c4e
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/1900
Reviewed-by: Russ Cox <rsc@google.com>
Reviewed-by: Damien Neil <dneil@google.com>
(cherry picked from commit cc0d725a4168f234ef38859b2d951a50a8fd94b5)
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/1940
Reviewed-by: Neal Patel <nealpatel@google.com>
Commit-Queue: Roland Shoemaker <bracewell@google.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/646995
Reviewed-by: Carlos Amedee <carlos@golang.org>
TryBot-Bypass: Cherry Mui <cherryyz@google.com>
2025-02-05 11:57:13 -08:00
Carlos Amedee
4241f582fc [release-branch.go1.24] all: merge master (37f27fb) into release-branch.go1.24
Conflicts:

- src/cmd/go/testdata/script/goauth_netrc.txt

Merge List:

+ 2025-01-31 37f27fbecd cmd/go: enable fips test and fix caching bug
+ 2025-01-31 77d20838e9 cmd: update golang.org/x/tools to CL 645697, and revendor
+ 2025-01-30 ce7ea0a6a5 cmd/go: refine GOAUTH user parsing to be more strict
+ 2025-01-29 e81f715515 lib/fips140: freeze v1.0.0 FIPS 140 module zip file
+ 2025-01-29 4f48ad5c6b cmd/link/internal/loader: fix linknames from FIPS 140 frozen tree
+ 2025-01-29 1f58ad5d6d Revert "os: employ sendfile(2) for file-to-file copying on Linux when needed"
+ 2025-01-28 90ec9996cb crypto/pbkdf2: add keyLength limit
+ 2025-01-28 62cd7cb6cd crypto/hkdf: check error in TestFIPSServiceIndicator
+ 2025-01-28 7764c502e2 crypto/internal/sysrand: skip TestNoGetrandom without cgo
+ 2025-01-28 50455385b0 internal/coverage: fix bug in text-format coverage output with multiple packages
+ 2025-01-28 28d389ef30 internal/godebug: check error from os.ReadFile in test
+ 2025-01-28 8071f2a169 runtime: mapiter linkname compatibility layer
+ 2025-01-28 78e6f2a1c8 runtime: rename mapiterinit and mapiternext
+ 2025-01-28 4ebd5bf855 internal/goexperiment: update location of baseline experiment in comment
+ 2025-01-27 f8937cb625 archive/zip, archive/tar: writer appends slash to directory names
+ 2025-01-27 11e08d9d96 strconv: adjust comment so that gofmt doesn't mung it
+ 2025-01-27 b9872221cd crypto/internal/fips140/rsa: avoid CAST unsetting the service indicator
+ 2025-01-27 3f791c8dfb crypto/internal/fips140/aes: set FIPS 140 service indicator for CTR and CBC
+ 2025-01-27 e0aeee82f3 crypto/ecdsa: avoid needless ScalarBaseMult in s390x
+ 2025-01-27 f70aa3824b cmd/go: do not call base.fatal for an unset HOME for GOAUTH=netrc
+ 2025-01-27 475e08349d Revert "runtime: Check LSE support on ARM64 at runtime init"
+ 2025-01-27 e2e700f8b1 crypto/internal/boring: keep ECDH public key alive during cgo calls
+ 2025-01-22 608acff847 go/types: avoid importer.Default
+ 2025-01-22 9d21ef3bd4 runtime: fix the equality check in AddCleanup
+ 2025-01-22 5a46b17b5f os: force a goroutine to be scheduled on WASM
+ 2025-01-22 6fc23a3cff crypto/internal/fips140/nistec: make p256NegCond constant time on ppc64le
+ 2025-01-22 70b603f4d2 go/importer: document limitations of this API
+ 2025-01-21 f6d17c5400 net/http: update bundled golang.org/x/net/http2 [generated]
+ 2025-01-21 3aa7c5ef01 testing: fix reference to B.N in docstring
+ 2025-01-20 3f4164f508 runtime: delete out of date comment
+ 2025-01-17 40b3c0e58a internal/coverage: refactor EmitTextual in preparation for bugfix
+ 2025-01-17 87023bb27f go/types, types2: ensure deterministic output when reporting an init cycle
+ 2025-01-17 80bf7d83ed go/types, types2: remove superfluous assertion (fix build)
+ 2025-01-16 1a93e4a2cf lib/time: update to 2025a/2025a
+ 2025-01-16 0b632d26b9 cmd/internal/obj/wasm, runtime: detect wasmexport call before runtime initialization
+ 2025-01-16 6a4effa08b crypto/x509: avoid panic when parsing partial PKCS#1 private keys
+ 2025-01-16 139d6eedae cmd/go: restore netrc preferences for GOAUTH and fix domain lookup
+ 2025-01-16 2b2314e9f6 crypto/x509: properly check for IPv6 hosts in URIs
+ 2025-01-16 6783377295 net/http: persist header stripping across repeated redirects
+ 2025-01-14 368a9ec998 encoding/json: cleanup tests
+ 2025-01-14 bd80d8956f cmd/go/internal/modfetch: do not trust server to send all tags in shallow fetch
+ 2025-01-14 4fa61d6f9c cmd/api: report error in test instead of crashing
+ 2025-01-14 c5e205e928 internal/runtime/maps: re-enable some tests
+ 2025-01-14 befc43655b testing/fstest: fix function name and comment
+ 2025-01-14 c83f2ca4b3 cmd/dist: ignore packages with no Go files in BenchmarkAll
+ 2025-01-13 6da16013ba cmd/go: check go version when parsing go.mod fails
+ 2025-01-13 de9fdc7b71 syscall/js: adjust comments to that gofmt does not change them
+ 2025-01-13 17ed215958 go/types, types2: don't panic when instantiating generic alias with wrong number of type arguments
+ 2025-01-13 c53307c3fd spec: fix grammar issue
+ 2025-01-13 47a56b2b6d encoding/json: add cases to TestUnmarshal for fatal syntactic errors
+ 2025-01-13 7bb192a1c5 encoding/json: always check resulting Go value for unmarshaling
+ 2025-01-12 44a6f817ea cmd/compile: fix write barrier coalescing
+ 2025-01-10 19e923182e crypto/internal/fips140test: add hmac DRBG ACVP tests
+ 2025-01-10 7255b94920 crypto/internal/fips140test: add ML-KEM ACVP tests
+ 2025-01-09 932ec2be8d crypto/rsa: fix GenerateKey flakes for toy-sized keys
+ 2025-01-09 d0c9142ce3 runtime/pprof: hide map runtime frames from heap profiles
+ 2025-01-09 c7c4420ae4 cmd/go: clarify GODEBUG in go help environment
+ 2025-01-09 c6ab13fc43 cmd/go/internal/mmap: reslice to file size on Windows
+ 2025-01-09 f5a89dff67 crypto: fix fips140=only detection of SHA-3
+ 2025-01-08 4225c6cb37 encoding/json: improve fidelity of TestUnmarshal for Numbers
+ 2025-01-08 c87a6f932e crypto/mlkem: merge mlkem768.go and mlkem1024.go to improve godoc
+ 2025-01-08 f57a3a7c04 crypto/mlkem: add example and improve docs
+ 2025-01-08 c9afcbade7 go/types, types2: require iterator yield to return bool (work-around)
+ 2025-01-08 54693a81fd crypto/md5,crypto/sha1: apply fips140=only to Write and Sum, not New
+ 2025-01-08 0cdf8c7a8c crypto/ecdsa: apply fips140=only to deterministic ECDSA hash
+ 2025-01-08 4640e92af7 crypto/rsa: apply fips140=only to opts.Hash in SignPSS

Change-Id: I443d8d9433e7f504905b60652d3fcd975e5f674b
2025-01-31 12:45:08 -05:00
Gopher Robot
8a4c24f9bb [release-branch.go1.24] go1.24rc2
Change-Id: I37362fe37c47078c17f3f6f610d8ca7664985bd0
Reviewed-on: https://go-review.googlesource.com/c/go/+/643157
Auto-Submit: Gopher Robot <gobot@golang.org>
Reviewed-by: Michael Pratt <mpratt@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
2025-01-16 12:13:48 -08:00
Filippo Valsorda
3de5aca7d0 [release-branch.go1.24] crypto/x509: avoid panic when parsing partial PKCS#1 private keys
These keys are off-spec, but have historically been accepted by
ParsePKCS1PrivateKey.

Thanks to Philippe Antoine (Catena cyber) for reporting this issue.

Fixes #71216
Fixes CVE-2025-22865

Change-Id: I6a6a46564156fa32e29e8d6acbec3fbac47c7352
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/1820
Reviewed-by: Tatiana Bradley <tatianabradley@google.com>
Reviewed-by: Damien Neil <dneil@google.com>
Commit-Queue: Roland Shoemaker <bracewell@google.com>
(cherry picked from commit 36c6c8b6957e155770461fd710aea9477ef3bc88)
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/1841
Reviewed-on: https://go-review.googlesource.com/c/go/+/643102
Auto-Submit: Michael Knyszek <mknyszek@google.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
2025-01-16 11:36:09 -08:00
Sam Thanawalla
8336dfde70 [release-branch.go1.24] cmd/go: restore netrc preferences for GOAUTH and fix domain lookup
Store netrc lines into the credential map backward so that earlier lines
take priority over later lines. This matches Go 1.23 netrc lookup which
stopped at the first match it found.
Additionally, this fixes a security issue related to domain parsing
which could have allowed servers to read credentials belonging to other
servers. The fix was to switch from using path.Dir(currentPrefix) to
strings.Cut(currentPrefix, "/")

Thanks to Juho Forsén of Mattermost for reporting this issue.

Fixes #71249
Fixes CVE-2024-45340

Change-Id: I175a00d6d7f4d31c9e4d79b7cf1c2a0ad35b2781
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/1781
Reviewed-by: Tatiana Bradley <tatianabradley@google.com>
Commit-Queue: Roland Shoemaker <bracewell@google.com>
Reviewed-by: Roland Shoemaker <bracewell@google.com>
Reviewed-by: Damien Neil <dneil@google.com>
(cherry picked from commit 76833d221aa3ccc978b6f41bd24e26babf771375)
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/1840
Reviewed-on: https://go-review.googlesource.com/c/go/+/643101
Reviewed-by: Michael Pratt <mpratt@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Michael Knyszek <mknyszek@google.com>
2025-01-16 11:36:07 -08:00
Damien Neil
6b60550504 [release-branch.go1.24] net/http: persist header stripping across repeated redirects
When an HTTP redirect changes the host of a request, we drop
sensitive headers such as Authorization from the redirected request.
Fix a bug where a chain of redirects could result in sensitive
headers being sent to the wrong host:

  1. request to a.tld with Authorization header
  2. a.tld redirects to b.tld
  3. request to b.tld with no Authorization header
  4. b.tld redirects to b.tld
  3. request to b.tld with Authorization header restored

Thanks to Kyle Seely for reporting this issue.

For #70530
Fixes #71212
Fixes CVE-2024-45336

Change-Id: Ia58a2e10d33d6b0cc7220935e771450e5c34de72
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/1641
Reviewed-by: Roland Shoemaker <bracewell@google.com>
Reviewed-by: Tatiana Bradley <tatianabradley@google.com>
Commit-Queue: Roland Shoemaker <bracewell@google.com>
(cherry picked from commit 2889169b87a61f1218a02994feb80fd3d8bfa87c)
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/1766
Reviewed-on: https://go-review.googlesource.com/c/go/+/643100
Auto-Submit: Michael Knyszek <mknyszek@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
2025-01-16 11:36:03 -08:00
Roland Shoemaker
468fad45a2 [release-branch.go1.24] crypto/x509: properly check for IPv6 hosts in URIs
When checking URI constraints, use netip.ParseAddr, which understands
zones, unlike net.ParseIP which chokes on them. This prevents zone IDs
from mistakenly satisfying URI constraints.

Thanks to Juho Forsén of Mattermost for reporting this issue.

For #71156
Fixes #71209
Fixes CVE-2024-45341

Change-Id: Iecac2529f3605382d257996e0fb6d6983547e400
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/1700
Reviewed-by: Tatiana Bradley <tatianabradley@google.com>
Reviewed-by: Damien Neil <dneil@google.com>
(cherry picked from commit 22ca55d396ba801e6ae9b2bd67a059fcb30562fd)
Reviewed-on: https://go-internal-review.googlesource.com/c/go/+/1800
Commit-Queue: Roland Shoemaker <bracewell@google.com>
Reviewed-by: Roland Shoemaker <bracewell@google.com>
Reviewed-on: https://go-review.googlesource.com/c/go/+/643099
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Michael Knyszek <mknyszek@google.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
2025-01-16 11:08:59 -08:00
Michael Pratt
e06b6fc58d [release-branch.go1.24] all: merge master (e966a27) into release-branch.go1.24
Merge List:

+ 2025-01-08 e966a2773c crypto/internal/fips140/drbg: avoid global lock on rand state

Change-Id: I1ca8f6bf2ba14ff3d5c4183a26cbd51ac20dad0a
2025-01-08 14:01:58 -05:00
Michael Pratt
b3799ba634 [release-branch.go1.24] all: merge master (9a44df6) into release-branch.go1.24
Merge List:

+ 2025-01-08 9a44df6675 cmd/go/testdata/script: fix TestScript/env_gocacheprog on Windows
+ 2025-01-08 f025d19e7b runtime: hold traceAcquire across casgstatus in injectglist
+ 2025-01-08 1e9835f5b1 internal/sync: fix typo of panic message
+ 2025-01-07 39f2032c17 testing/synctest: add some examples
+ 2025-01-07 b50ccef67a cmd/go/internal/modindex: don't write index entry if file open
+ 2025-01-07 b2aa18b96c cmd/internal/hash: stop using md5, sha1
+ 2025-01-07 d93b549f05 cmd/go/internal/cache: handle cacheprog not responding to close
+ 2025-01-07 d62154db83 weak: don't panic when calling Value on a zero Pointer
+ 2025-01-07 9d0772b23e cmd/compile/internal/syntax: add test case for invalid label use
+ 2025-01-07 1d20bce981 go/types, types2: expand documentation for Info.Types map
+ 2025-01-07 a9bd6239a4 cmd/go/internal/env: add GOCACHEPROG to go env output
+ 2025-01-07 850b276a67 crypto/tls: send illegal_parameter on invalid ECHClientHello.type
+ 2025-01-06 27c5164374 crypto/internal/fips140: zeroise integrity test temporary values
+ 2025-01-06 d8ad4af78b cmd/internal/disasm: correct instruction length handling for riscv64
+ 2025-01-06 a76cc5a4ec crypto/rsa: use λ(N) instead of φ(N)
+ 2025-01-06 3f002abb60 internal/sync: add test from issue 70970
+ 2025-01-06 7a2e88e911 net/http: update NewRequestWithContext wrong link to NewRequest
+ 2025-01-06 c112c0af13 Revert "internal/sync: optimize CompareAndSwap and Swap"
+ 2025-01-03 705b5a569a crypto/ecdsa: drop SEC 1 reference from package doc
+ 2025-01-03 f966695cce context: use "canceled" in docs to refer to timed-out contexts
+ 2025-01-03 5da026354c cmd/go/internal/vcweb: close the .access file
+ 2025-01-03 31cabcf084 crypto/internal/fips140: mark OpenBSD unsupported
+ 2025-01-03 eb0c2b2f96 crypto/internal/fips140: add Supported
+ 2025-01-03 f0a9b6df45 internal/fuzz: remove the exp2 method
+ 2025-01-03 5d626c49ec spec: fix a dead link
+ 2025-01-03 81566aff3a internal/exportdata: add missing return
+ 2025-01-03 e7a8bd5d8b crypto/internal/fips140/check: remove Enabled
+ 2025-01-02 4b652e9f5f cmd/go: fix two typos in helpdoc.go
+ 2025-01-02 0afd7e85e5 cmd/go: document GOCACHEPROG in go help environment
+ 2025-01-02 3c8e5b13df cmd/go/internal/cacheprog: drop redundant Prog prefixes
+ 2025-01-02 20da34c6d2 cmd/go: move GOCACHEPROG protocol types to their own package
+ 2025-01-02 858a0e9dfd crypto/tls: properly return ECH retry configs
+ 2025-01-02 a63aee4955 cmd/go: improve GOCACHEPROG types documentation
+ 2025-01-02 847c357bbb cmd/go: remove references to gopath-get
+ 2025-01-01 d1d9312950 crypto/tls: fix Config.Time in tests using expired certificates
+ 2024-12-31 94f15810e6 cmd/go: document default GOARM value
+ 2024-12-30 856a7bc8e9 builtin: use list instead of indentation for comments in cap, len, and make
+ 2024-12-30 5efb4239c6 spec: document that string conversions don't guarantee result slice capacity
+ 2024-12-30 0d8aa8cce6 spec: describe representation of values
+ 2024-12-30 8857a5a33f crypto/tls: fix misspelling in comment
+ 2024-12-30 3c4102bfd4 encoding/binary: add documentation for endian methods
+ 2024-12-30 b702a26cf8 os: mention fsys modifications during CopyFS
+ 2024-12-30 15f232456a encoding/json: remove suggestion on Unmarshaler with JSON null
+ 2024-12-30 ba1deb1cee cmd/link: document that -s implies -w
+ 2024-12-30 fd5e0d26d9 go/doc: resolve imports before predeclared identifiers in examples
+ 2024-12-30 a785d11ac4 unique: fix typo
+ 2024-12-27 2b794ed86c encoding/json: expand and modernize TestInterfaceSet
+ 2024-12-27 e3cd55e9d2 cmd/go/internal/work: allow @ character in some -Wl, linker flags on darwin
+ 2024-12-27 39794819aa doc/initial: remove fixed-width spacing notice
+ 2024-12-27 7c03fe70b8 cmd/compile: improve compiler directive docs
+ 2024-12-27 d7c3e93c16 iter: improve documentation with iterator example
+ 2024-12-26 cce75da30b crypto/mlkem: swap order of return values of Encapsulate
+ 2024-12-23 772f024c61 weak: fix typo in warning about tiny allocator optimization
+ 2024-12-23 b9955f0ad9 cmd/link, runtime: apply a delta to RODATA->DATA relocations
+ 2024-12-23 eef35e3bd9 internal/goexperiment: run go generate for synctest
+ 2024-12-23 9f6c80a76a cmd/go/internal/work: allow single character values in -Wl, linker flags
+ 2024-12-22 05d8984781 net: document LookupTXT behavior with multiple strings per record
+ 2024-12-21 500675a7c8 cmd/compile: load map length with the right type
+ 2024-12-21 06b191e11f internal/syscall/unix: apply fstatat fix to linux/mips64le
+ 2024-12-21 110ab1aaf4 slices: document two oddities
+ 2024-12-19 669d87a935 runtime/pprof: continued attempt to deflake the VMInfo test.
+ 2024-12-19 45f49139f5 runtime: test trap panic parsing in TestTracebackSystem
+ 2024-12-19 e63eb98e98 net/http: fix nil panic in test
+ 2024-12-19 7b6c94dd03 cmd/go: drop fips140 build ID hacks
+ 2024-12-19 cb72406c36 cmd/go: fix two-step toolchain upgrade through go install, GOTOOLCHAIN
+ 2024-12-18 4f0561f9d3 cmd/dist: skip fips140test in exe mode on Android
+ 2024-12-18 87dbfb9fa7 weak: improve grammar in doc comments
+ 2024-12-18 f4e3ec3dbe crypto/ecdsa: fix condition for fips140=only check
+ 2024-12-18 6aa46eb750 crypto/tls: normalize spelling of "ClientHello" in comments
+ 2024-12-18 10ca5ba4ff crypto/pbkdf2: update RFC reference in package doc
+ 2024-12-18 8ff4cee564 cmd/go,crypto: reject using Go+BoringCrypto and fips140 together
+ 2024-12-18 971448ddf8 testing: support B.Context and F.Context
+ 2024-12-17 95b433eed4 debug/elf: adjust version API per issue discussion
+ 2024-12-17 b2c0168893 crypto/internal/fips140/aes/gcm: use aes.EncryptBlockInternal on ppc64x and s390x
+ 2024-12-17 b9e2ffdcd2 crypto/internal/fips140: add Name and Version
+ 2024-12-17 8790372a8d cmd, go: fix some typos
+ 2024-12-17 b057b8872d bytes, strings: add cross-references in docstrings
+ 2024-12-17 e977b83b32 cmd/go/internal/help: use secure link to swig.org
+ 2024-12-17 4ac8f552e9 syscall, internal/syscall/unix: fix fstatat on linux/mips64
+ 2024-12-17 236a0b4ffb spec: explain function invocation and passing of parameters more precisely
+ 2024-12-17 9f806bb76c go/build: streamline the crypto package graph in TestDependencies
+ 2024-12-17 0cd833d198 go/build: remove nonexistent package from TestDependencies
+ 2024-12-17 31e50af5f3 crypto/rsa: revert minimum GenerateKey size to 32 bits
+ 2024-12-17 b47ce8b0e9 crypto/cipher: block non-AES CTR and CBC in fips140=only mode
+ 2024-12-17 dd7a7ba38f crypto/internal/fips140/aes: mark AES-ECB as not approved
+ 2024-12-17 427a2401af cmd/go/testdata/script: update test_flags for new test output
+ 2024-12-17 75736cc169 fmt, strconv: document that exponent is always two digits
+ 2024-12-16 1218566fe5 cmd/link: update runtime dependency list
+ 2024-12-16 d92c34a387 cmd/go: don't create test actions for incomplete packages
+ 2024-12-16 3bd08b9792 runtime: usleep in TestWeakToStrongMarkTermination
+ 2024-12-15 18b5435fc8 testing: don't measure cleanup time after B.Loop
+ 2024-12-15 c1f2542c8b testing: improve B.Loop test
+ 2024-12-15 6bd56fcaeb testing: improve b.Loop example
+ 2024-12-15 090748d6c7 testing: improve B.Loop docs, use B.Loop in examples
+ 2024-12-13 e39e965e0e cmd/go: drop FailedBuild field if gotestjsonbuildtext=1
+ 2024-12-13 08770a5b94 cmd/link: make dwarf name slice index self-describing
+ 2024-12-13 c4f356dd86 crypto/ecdsa: fix s390x assembly with P-521
+ 2024-12-13 08725f9de2 crypto/internal/cryptotest: skip TestAllocations on s390x
+ 2024-12-13 1cbfe8c482 fmt: add more function and allocation tests
+ 2024-12-13 8391579ece runtime: migrate missing map linkname allowlists
+ 2024-12-12 80a2982a80 spec: align EBNF rules consistently (cosmetic change)
+ 2024-12-12 38e9a671d7 syscall: on freebsd-386 only update written for certain errors
+ 2024-12-12 6f7a4540b1 net: fix example function name for IP.To4
+ 2024-12-12 14e5093ee5 cmd/internal/obj: disallow linknamed access to builtin symbols
+ 2024-12-12 fb764cdad0 cmd/link: block new standard library linknames

Change-Id: Ie423f050db80034c3af6c12bd6007db273c5d281
2025-01-08 13:21:10 -05:00
Gopher Robot
16afa6a740 [release-branch.go1.24] go1.24rc1
Change-Id: Ia3b0a8ec25312b73879d2561a2b4d1cfc648c295
Reviewed-on: https://go-review.googlesource.com/c/go/+/636036
Reviewed-by: Carlos Amedee <carlos@golang.org>
Auto-Submit: Gopher Robot <gobot@golang.org>
TryBot-Bypass: Carlos Amedee <carlos@golang.org>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
2024-12-13 08:52:10 -08:00
Carlos Amedee
817d7bdc0a [release-branch.go1.24] all: merge master (9118060) into release-branch.go1.24
Merge List:

+ 2024-12-12 9118060040 builtin: document clear is a no-op if its argument's value is nil
+ 2024-12-11 077d51909d internal/poll: in SendFile treat ENOTSUP like EOPNOTSUPP
+ 2024-12-11 fafd4477f3 cmd/cgo: use full prototype for main in C code

Change-Id: I4c4941eff4a1e842920eb9be47d28351af0e4c36
2024-12-12 12:06:37 -05:00
Carlos Amedee
14bb1e11b9 [release-branch.go1.24] all: merge master (0ca521f) into release-branch.go1.24
Merge List:

+ 2024-12-11 0ca521f9c1 debug/elf: adjust version API per issue discussion

Change-Id: Ibd6f628528dd366837ad0bbacad624474eee0088
2024-12-11 18:55:28 -05:00
Carlos Amedee
2297c34cdf [release-branch.go1.24] all: merge master (c93477b) into release-branch.go1.24
Merge List:

+ 2024-12-11 c93477b5e5 crypto: use provided random Reader in FIPS mode
+ 2024-12-11 3104b6adbb log/slog: make DiscardHandler example package-level
+ 2024-12-11 5424f2e200 cmd/go: add more tests for GOAUTH's user provided authenticator
+ 2024-12-11 d5c1333eb4 net/http: document zero value of Protocols
+ 2024-12-11 a7c4cadce0 cmd/compile: update broken link
+ 2024-12-11 979c1cfbe8 net: avoid unnecessary interface lookup fetching all interface addresses
+ 2024-12-11 e424d78c3d internal/goos: fix bug in gengoos.go
+ 2024-12-11 6c25cf1c5f cmd/internal/objfile: break out dissassemblers to another package
+ 2024-12-11 e0c76d95ab syscall: remove a wrong comment in Clearenv
+ 2024-12-11 a9922d096f reflect: consistently document when value must be settable
+ 2024-12-10 4ce116a884 runtime: avoid panic in expired synctest timer chan read
+ 2024-12-10 e6de1b2deb html/template: escape script tags in JS errors case insensitively
+ 2024-12-10 fce17b0c77 crypto/internal/fips140/ecdsa: fix reseed_counter check for HMAC_DRBG_Generate_algorithm
+ 2024-12-09 d87878c62b runtime: make special offset a uintptr
+ 2024-12-09 6705ac6885 runtime: remove datadog-agent from prof labels hall of shame
+ 2024-12-09 07398d2e57 weak: align weak.Pointer documentation with runtime.AddCleanup
+ 2024-12-09 e3e1d73528 bufio: make the description of Peek's behavior better
+ 2024-12-09 e79b2e1e3a cmd/go: document the build cache as safe for concurrent use
+ 2024-12-08 c8fb6ae617 lib/wasm: provide fs.constants.O_DIRECTORY definition
+ 2024-12-07 8c3e391573 runtime: improve AddCleanup documentation
+ 2024-12-07 04cdaa9984 cmd/go: document c-shared buildmode for building WASI library/reactor
+ 2024-12-06 312f7c1bd3 runtime: add note that Callers never returns an entry PC

Change-Id: I52e035228121de3d8219ab13f195d4293daaaa34
2024-12-11 17:45:39 -05:00
Michael Anthony Knyszek
26682773ca [release-branch.go1.24] update codereview.cfg for release-branch.go1.24
Change-Id: I63ffca43a935bc5ff060f19c01152a20182cba03
Reviewed-on: https://go-review.googlesource.com/c/go/+/634317
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@golang.org>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Auto-Submit: Michael Knyszek <mknyszek@google.com>
2024-12-06 21:58:36 +00:00
137 changed files with 22578 additions and 449 deletions

2
VERSION Normal file
View File

@@ -0,0 +1,2 @@
go1.24.3
time 2025-04-30T18:13:34Z

View File

@@ -1 +1,2 @@
branch: master
branch: release-branch.go1.24
parent-branch: master

View File

@@ -153,6 +153,17 @@ and the [go command documentation](/cmd/go#hdr-Build_and_test_caching).
### Go 1.24
Go 1.24 added a new `fips140` setting that controls whether the Go
Cryptographic Module operates in FIPS 140-3 mode.
The possible values are:
- "off": no special support for FIPS 140-3 mode. This is the default.
- "on": the Go Cryptographic Module operates in FIPS 140-3 mode.
- "only": like "on", but cryptographic algorithms not approved by
FIPS 140-3 return an error or panic.
For more information, see [FIPS 140-3 Compliance](/doc/security/fips140).
This setting is fixed at program startup time, and can't be modified
by changing the `GODEBUG` environment variable after the program starts.
Go 1.24 changed the global [`math/rand.Seed`](/pkg/math/rand/#Seed) to be a
no-op. This behavior is controlled by the `randseednop` setting.
For Go 1.24 it defaults to `randseednop=1`.

View File

@@ -67,26 +67,26 @@ func splitSeq(s, sep []byte, sepSave int) iter.Seq[[]byte] {
}
}
// SplitSeq returns an iterator over all substrings of s separated by sep.
// The iterator yields the same strings that would be returned by [Split](s, sep),
// but without constructing the slice.
// SplitSeq returns an iterator over all subslices of s separated by sep.
// The iterator yields the same subslices that would be returned by [Split](s, sep),
// but without constructing a new slice containing the subslices.
// It returns a single-use iterator.
func SplitSeq(s, sep []byte) iter.Seq[[]byte] {
return splitSeq(s, sep, 0)
}
// SplitAfterSeq returns an iterator over substrings of s split after each instance of sep.
// The iterator yields the same strings that would be returned by [SplitAfter](s, sep),
// but without constructing the slice.
// SplitAfterSeq returns an iterator over subslices of s split after each instance of sep.
// The iterator yields the same subslices that would be returned by [SplitAfter](s, sep),
// but without constructing a new slice containing the subslices.
// It returns a single-use iterator.
func SplitAfterSeq(s, sep []byte) iter.Seq[[]byte] {
return splitSeq(s, sep, len(sep))
}
// FieldsSeq returns an iterator over substrings of s split around runs of
// FieldsSeq returns an iterator over subslices of s split around runs of
// whitespace characters, as defined by [unicode.IsSpace].
// The iterator yields the same strings that would be returned by [Fields](s),
// but without constructing the slice.
// The iterator yields the same subslices that would be returned by [Fields](s),
// but without constructing a new slice containing the subslices.
func FieldsSeq(s []byte) iter.Seq[[]byte] {
return func(yield func([]byte) bool) {
start := -1
@@ -116,10 +116,10 @@ func FieldsSeq(s []byte) iter.Seq[[]byte] {
}
}
// FieldsFuncSeq returns an iterator over substrings of s split around runs of
// FieldsFuncSeq returns an iterator over subslices of s split around runs of
// Unicode code points satisfying f(c).
// The iterator yields the same strings that would be returned by [FieldsFunc](s),
// but without constructing the slice.
// The iterator yields the same subslices that would be returned by [FieldsFunc](s),
// but without constructing a new slice containing the subslices.
func FieldsFuncSeq(s []byte, f func(rune) bool) iter.Seq[[]byte] {
return func(yield func([]byte) bool) {
start := -1

View File

@@ -27,6 +27,7 @@ func test42018(t *testing.T) {
recurseHWND(400, hwnd, uintptr(unsafe.Pointer(&i)))
}
//go:noinline
func recurseHANDLE(n int, p C.HANDLE, v uintptr) {
if n > 0 {
recurseHANDLE(n-1, p, v)
@@ -36,6 +37,7 @@ func recurseHANDLE(n int, p C.HANDLE, v uintptr) {
}
}
//go:noinline
func recurseHWND(n int, p C.HWND, v uintptr) {
if n > 0 {
recurseHWND(n-1, p, v)

View File

@@ -42,6 +42,7 @@ import (
"cmd/compile/internal/types"
"cmd/internal/obj"
"cmd/internal/pgo"
"cmd/internal/src"
)
// Inlining budget parameters, gathered in one place
@@ -169,19 +170,8 @@ func CanInlineFuncs(funcs []*ir.Func, profile *pgoir.Profile) {
}
ir.VisitFuncsBottomUp(funcs, func(funcs []*ir.Func, recursive bool) {
numfns := numNonClosures(funcs)
for _, fn := range funcs {
if !recursive || numfns > 1 {
// We allow inlining if there is no
// recursion, or the recursion cycle is
// across more than one function.
CanInline(fn, profile)
} else {
if base.Flag.LowerM > 1 && fn.OClosure == nil {
fmt.Printf("%v: cannot inline %v: recursive\n", ir.Line(fn), fn.Nname)
}
}
CanInline(fn, profile)
if inlheur.Enabled() {
analyzeFuncProps(fn, profile)
}
@@ -974,6 +964,16 @@ func inlineCostOK(n *ir.CallExpr, caller, callee *ir.Func, bigCaller, closureCal
return true, 0, metric, hot
}
// parsePos returns all the inlining positions and the innermost position.
func parsePos(pos src.XPos, posTmp []src.Pos) ([]src.Pos, src.Pos) {
ctxt := base.Ctxt
ctxt.AllPos(pos, func(p src.Pos) {
posTmp = append(posTmp, p)
})
l := len(posTmp) - 1
return posTmp[:l], posTmp[l]
}
// canInlineCallExpr returns true if the call n from caller to callee
// can be inlined, plus the score computed for the call expr in question,
// and whether the callee is hot according to PGO.
@@ -1001,12 +1001,15 @@ func canInlineCallExpr(callerfn *ir.Func, n *ir.CallExpr, callee *ir.Func, bigCa
return false, 0, false
}
if callee == callerfn {
// Can't recursively inline a function into itself.
if log && logopt.Enabled() {
logopt.LogOpt(n.Pos(), "cannotInlineCall", "inline", fmt.Sprintf("recursive call to %s", ir.FuncName(callerfn)))
callees, calleeInner := parsePos(n.Pos(), make([]src.Pos, 0, 10))
for _, p := range callees {
if p.Line() == calleeInner.Line() && p.Col() == calleeInner.Col() && p.AbsFilename() == calleeInner.AbsFilename() {
if log && logopt.Enabled() {
logopt.LogOpt(n.Pos(), "cannotInlineCall", "inline", fmt.Sprintf("recursive call to %s", ir.FuncName(callerfn)))
}
return false, 0, false
}
return false, 0, false
}
if base.Flag.Cfg.Instrumenting && types.IsNoInstrumentPkg(callee.Sym().Pkg) {

View File

@@ -253,7 +253,7 @@ func (s *inlClosureState) mark(n ir.Node) ir.Node {
if isTestingBLoop(n) {
// No inlining nor devirtualization performed on b.Loop body
if base.Flag.LowerM > 1 {
if base.Flag.LowerM > 0 {
fmt.Printf("%v: skip inlining within testing.B.loop for %v\n", ir.Line(n), n)
}
// We still want to explore inlining opportunities in other parts of ForStmt.

View File

@@ -1148,10 +1148,12 @@
(SUB a l:(MNEGW x y)) && v.Type.Size() <= 4 && l.Uses==1 && clobber(l) => (MADDW a x y)
// madd/msub can't take constant arguments, so do a bit of reordering if a non-constant is available.
(ADD a p:(ADDconst [c] m:((MUL|MULW|MNEG|MNEGW) _ _))) && p.Uses==1 && m.Uses==1 => (ADDconst [c] (ADD <v.Type> a m))
(ADD a p:(SUBconst [c] m:((MUL|MULW|MNEG|MNEGW) _ _))) && p.Uses==1 && m.Uses==1 => (SUBconst [c] (ADD <v.Type> a m))
(SUB a p:(ADDconst [c] m:((MUL|MULW|MNEG|MNEGW) _ _))) && p.Uses==1 && m.Uses==1 => (SUBconst [c] (SUB <v.Type> a m))
(SUB a p:(SUBconst [c] m:((MUL|MULW|MNEG|MNEGW) _ _))) && p.Uses==1 && m.Uses==1 => (ADDconst [c] (SUB <v.Type> a m))
// Note: don't reorder arithmetic concerning pointers, as we must ensure that
// no intermediate computations are invalid pointers.
(ADD <t> a p:(ADDconst [c] m:((MUL|MULW|MNEG|MNEGW) _ _))) && p.Uses==1 && m.Uses==1 && !t.IsPtrShaped() => (ADDconst [c] (ADD <v.Type> a m))
(ADD <t> a p:(SUBconst [c] m:((MUL|MULW|MNEG|MNEGW) _ _))) && p.Uses==1 && m.Uses==1 && !t.IsPtrShaped() => (SUBconst [c] (ADD <v.Type> a m))
(SUB <t> a p:(ADDconst [c] m:((MUL|MULW|MNEG|MNEGW) _ _))) && p.Uses==1 && m.Uses==1 && !t.IsPtrShaped() => (SUBconst [c] (SUB <v.Type> a m))
(SUB <t> a p:(SUBconst [c] m:((MUL|MULW|MNEG|MNEGW) _ _))) && p.Uses==1 && m.Uses==1 && !t.IsPtrShaped() => (ADDconst [c] (SUB <v.Type> a m))
// optimize ADCSflags, SBCSflags and friends
(ADCSflags x y (Select1 <types.TypeFlags> (ADDSconstflags [-1] (ADCzerocarry <typ.UInt64> c)))) => (ADCSflags x y c)

View File

@@ -41,11 +41,12 @@ type Func struct {
ABISelf *abi.ABIConfig // ABI for function being compiled
ABIDefault *abi.ABIConfig // ABI for rtcall and other no-parsed-signature/pragma functions.
scheduled bool // Values in Blocks are in final order
laidout bool // Blocks are ordered
NoSplit bool // true if function is marked as nosplit. Used by schedule check pass.
dumpFileSeq uint8 // the sequence numbers of dump file. (%s_%02d__%s.dump", funcname, dumpFileSeq, phaseName)
IsPgoHot bool
scheduled bool // Values in Blocks are in final order
laidout bool // Blocks are ordered
NoSplit bool // true if function is marked as nosplit. Used by schedule check pass.
dumpFileSeq uint8 // the sequence numbers of dump file. (%s_%02d__%s.dump", funcname, dumpFileSeq, phaseName)
IsPgoHot bool
HasDeferRangeFunc bool // if true, needs a deferreturn so deferrangefunc can use it for recover() return PC
// when register allocation is done, maps value ids to locations
RegAlloc []Location

View File

@@ -552,8 +552,9 @@ func (ft *factsTable) newLimit(v *Value, newLim limit) bool {
}
if lim.unsat() {
r := !ft.unsat
ft.unsat = true
return true
return r
}
// Check for recursion. This normally happens because in unsatisfiable

View File

@@ -1670,6 +1670,7 @@ func (s *regAllocState) regalloc(f *Func) {
}
tmpReg = s.allocReg(m, &tmpVal)
s.nospill |= regMask(1) << tmpReg
s.tmpused |= regMask(1) << tmpReg
}
// Now that all args are in regs, we're ready to issue the value itself.

View File

@@ -1331,10 +1331,11 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
break
}
// match: (ADD a p:(ADDconst [c] m:(MUL _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (ADD <t> a p:(ADDconst [c] m:(MUL _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (ADDconst [c] (ADD <v.Type> a m))
for {
t := v.Type
for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 {
a := v_0
p := v_1
@@ -1343,7 +1344,7 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MUL || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MUL || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
continue
}
v.reset(OpARM64ADDconst)
@@ -1355,10 +1356,11 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
break
}
// match: (ADD a p:(ADDconst [c] m:(MULW _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (ADD <t> a p:(ADDconst [c] m:(MULW _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (ADDconst [c] (ADD <v.Type> a m))
for {
t := v.Type
for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 {
a := v_0
p := v_1
@@ -1367,7 +1369,7 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MULW || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MULW || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
continue
}
v.reset(OpARM64ADDconst)
@@ -1379,10 +1381,11 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
break
}
// match: (ADD a p:(ADDconst [c] m:(MNEG _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (ADD <t> a p:(ADDconst [c] m:(MNEG _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (ADDconst [c] (ADD <v.Type> a m))
for {
t := v.Type
for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 {
a := v_0
p := v_1
@@ -1391,7 +1394,7 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MNEG || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MNEG || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
continue
}
v.reset(OpARM64ADDconst)
@@ -1403,10 +1406,11 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
break
}
// match: (ADD a p:(ADDconst [c] m:(MNEGW _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (ADD <t> a p:(ADDconst [c] m:(MNEGW _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (ADDconst [c] (ADD <v.Type> a m))
for {
t := v.Type
for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 {
a := v_0
p := v_1
@@ -1415,7 +1419,7 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MNEGW || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MNEGW || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
continue
}
v.reset(OpARM64ADDconst)
@@ -1427,10 +1431,11 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
break
}
// match: (ADD a p:(SUBconst [c] m:(MUL _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (ADD <t> a p:(SUBconst [c] m:(MUL _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (SUBconst [c] (ADD <v.Type> a m))
for {
t := v.Type
for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 {
a := v_0
p := v_1
@@ -1439,7 +1444,7 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MUL || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MUL || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
continue
}
v.reset(OpARM64SUBconst)
@@ -1451,10 +1456,11 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
break
}
// match: (ADD a p:(SUBconst [c] m:(MULW _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (ADD <t> a p:(SUBconst [c] m:(MULW _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (SUBconst [c] (ADD <v.Type> a m))
for {
t := v.Type
for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 {
a := v_0
p := v_1
@@ -1463,7 +1469,7 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MULW || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MULW || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
continue
}
v.reset(OpARM64SUBconst)
@@ -1475,10 +1481,11 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
break
}
// match: (ADD a p:(SUBconst [c] m:(MNEG _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (ADD <t> a p:(SUBconst [c] m:(MNEG _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (SUBconst [c] (ADD <v.Type> a m))
for {
t := v.Type
for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 {
a := v_0
p := v_1
@@ -1487,7 +1494,7 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MNEG || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MNEG || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
continue
}
v.reset(OpARM64SUBconst)
@@ -1499,10 +1506,11 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
break
}
// match: (ADD a p:(SUBconst [c] m:(MNEGW _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (ADD <t> a p:(SUBconst [c] m:(MNEGW _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (SUBconst [c] (ADD <v.Type> a m))
for {
t := v.Type
for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 {
a := v_0
p := v_1
@@ -1511,7 +1519,7 @@ func rewriteValueARM64_OpARM64ADD(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MNEGW || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MNEGW || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
continue
}
v.reset(OpARM64SUBconst)
@@ -16604,10 +16612,11 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
v.AddArg3(a, x, y)
return true
}
// match: (SUB a p:(ADDconst [c] m:(MUL _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (SUB <t> a p:(ADDconst [c] m:(MUL _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (SUBconst [c] (SUB <v.Type> a m))
for {
t := v.Type
a := v_0
p := v_1
if p.Op != OpARM64ADDconst {
@@ -16615,7 +16624,7 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MUL || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MUL || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
break
}
v.reset(OpARM64SUBconst)
@@ -16625,10 +16634,11 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
v.AddArg(v0)
return true
}
// match: (SUB a p:(ADDconst [c] m:(MULW _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (SUB <t> a p:(ADDconst [c] m:(MULW _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (SUBconst [c] (SUB <v.Type> a m))
for {
t := v.Type
a := v_0
p := v_1
if p.Op != OpARM64ADDconst {
@@ -16636,7 +16646,7 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MULW || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MULW || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
break
}
v.reset(OpARM64SUBconst)
@@ -16646,10 +16656,11 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
v.AddArg(v0)
return true
}
// match: (SUB a p:(ADDconst [c] m:(MNEG _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (SUB <t> a p:(ADDconst [c] m:(MNEG _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (SUBconst [c] (SUB <v.Type> a m))
for {
t := v.Type
a := v_0
p := v_1
if p.Op != OpARM64ADDconst {
@@ -16657,7 +16668,7 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MNEG || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MNEG || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
break
}
v.reset(OpARM64SUBconst)
@@ -16667,10 +16678,11 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
v.AddArg(v0)
return true
}
// match: (SUB a p:(ADDconst [c] m:(MNEGW _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (SUB <t> a p:(ADDconst [c] m:(MNEGW _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (SUBconst [c] (SUB <v.Type> a m))
for {
t := v.Type
a := v_0
p := v_1
if p.Op != OpARM64ADDconst {
@@ -16678,7 +16690,7 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MNEGW || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MNEGW || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
break
}
v.reset(OpARM64SUBconst)
@@ -16688,10 +16700,11 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
v.AddArg(v0)
return true
}
// match: (SUB a p:(SUBconst [c] m:(MUL _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (SUB <t> a p:(SUBconst [c] m:(MUL _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (ADDconst [c] (SUB <v.Type> a m))
for {
t := v.Type
a := v_0
p := v_1
if p.Op != OpARM64SUBconst {
@@ -16699,7 +16712,7 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MUL || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MUL || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
break
}
v.reset(OpARM64ADDconst)
@@ -16709,10 +16722,11 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
v.AddArg(v0)
return true
}
// match: (SUB a p:(SUBconst [c] m:(MULW _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (SUB <t> a p:(SUBconst [c] m:(MULW _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (ADDconst [c] (SUB <v.Type> a m))
for {
t := v.Type
a := v_0
p := v_1
if p.Op != OpARM64SUBconst {
@@ -16720,7 +16734,7 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MULW || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MULW || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
break
}
v.reset(OpARM64ADDconst)
@@ -16730,10 +16744,11 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
v.AddArg(v0)
return true
}
// match: (SUB a p:(SUBconst [c] m:(MNEG _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (SUB <t> a p:(SUBconst [c] m:(MNEG _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (ADDconst [c] (SUB <v.Type> a m))
for {
t := v.Type
a := v_0
p := v_1
if p.Op != OpARM64SUBconst {
@@ -16741,7 +16756,7 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MNEG || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MNEG || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
break
}
v.reset(OpARM64ADDconst)
@@ -16751,10 +16766,11 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
v.AddArg(v0)
return true
}
// match: (SUB a p:(SUBconst [c] m:(MNEGW _ _)))
// cond: p.Uses==1 && m.Uses==1
// match: (SUB <t> a p:(SUBconst [c] m:(MNEGW _ _)))
// cond: p.Uses==1 && m.Uses==1 && !t.IsPtrShaped()
// result: (ADDconst [c] (SUB <v.Type> a m))
for {
t := v.Type
a := v_0
p := v_1
if p.Op != OpARM64SUBconst {
@@ -16762,7 +16778,7 @@ func rewriteValueARM64_OpARM64SUB(v *Value) bool {
}
c := auxIntToInt64(p.AuxInt)
m := p.Args[0]
if m.Op != OpARM64MNEGW || !(p.Uses == 1 && m.Uses == 1) {
if m.Op != OpARM64MNEGW || !(p.Uses == 1 && m.Uses == 1 && !t.IsPtrShaped()) {
break
}
v.reset(OpARM64ADDconst)

View File

@@ -4433,6 +4433,9 @@ func (s *state) call(n *ir.CallExpr, k callKind, returnResultAddr bool, deferExt
callABI = s.f.ABI1
}
}
if fn := n.Fun.Sym().Name; n.Fun.Sym().Pkg == ir.Pkgs.Runtime && fn == "deferrangefunc" {
s.f.HasDeferRangeFunc = true
}
break
}
closure = s.expr(fn)
@@ -6566,10 +6569,13 @@ func genssa(f *ssa.Func, pp *objw.Progs) {
// nop (which will never execute) after the call.
Arch.Ginsnop(s.pp)
}
if openDeferInfo != nil {
if openDeferInfo != nil || f.HasDeferRangeFunc {
// When doing open-coded defers, generate a disconnected call to
// deferreturn and a return. This will be used to during panic
// recovery to unwind the stack and return back to the runtime.
//
// deferrangefunc needs to be sure that at least one of these exists;
// if all returns are dead-code eliminated, there might not be.
s.pp.NextLive = s.livenessMap.DeferReturn
p := s.pp.Prog(obj.ACALL)
p.To.Type = obj.TYPE_MEM

View File

@@ -230,6 +230,9 @@ func TestIntendedInlining(t *testing.T) {
"(*Pointer[go.shape.int]).Store",
"(*Pointer[go.shape.int]).Swap",
},
"testing": {
"(*B).Loop",
},
}
if !goexperiment.SwissMap {

View File

@@ -204,7 +204,7 @@ func (check *Checker) lhsVar(lhs syntax.Expr) Type {
// dot-imported variables.
if w, _ := obj.(*Var); w != nil && w.pkg == check.pkg {
v = w
v_used = v.used
v_used = check.usedVars[v]
}
}
}
@@ -213,7 +213,7 @@ func (check *Checker) lhsVar(lhs syntax.Expr) Type {
check.expr(nil, &x, lhs)
if v != nil {
v.used = v_used // restore v.used
check.usedVars[v] = v_used // restore v.used
}
if x.mode == invalid || !isValid(x.typ) {

View File

@@ -687,7 +687,7 @@ func (check *Checker) selector(x *operand, e *syntax.SelectorExpr, def *TypeName
if pname, _ := obj.(*PkgName); pname != nil {
assert(pname.pkg == check.pkg)
check.recordUse(ident, pname)
pname.used = true
check.usedPkgNames[pname] = true
pkg := pname.imported
var exp Object
@@ -972,13 +972,13 @@ func (check *Checker) use1(e syntax.Expr, lhs bool) bool {
// dot-imported variables.
if w, _ := obj.(*Var); w != nil && w.pkg == check.pkg {
v = w
v_used = v.used
v_used = check.usedVars[v]
}
}
}
check.exprOrType(&x, n, true)
if v != nil {
v.used = v_used // restore v.used
check.usedVars[v] = v_used // restore v.used
}
case *syntax.ListExpr:
return check.useN(n.ElemList, lhs)

View File

@@ -162,6 +162,8 @@ type Checker struct {
dotImportMap map[dotImportKey]*PkgName // maps dot-imported objects to the package they were dot-imported through
brokenAliases map[*TypeName]bool // set of aliases with broken (not yet determined) types
unionTypeSets map[*Union]*_TypeSet // computed type sets for union types
usedVars map[*Var]bool // set of used variables
usedPkgNames map[*PkgName]bool // set of used package names
mono monoGraph // graph for detecting non-monomorphizable instantiation loops
firstErr error // first error encountered
@@ -285,12 +287,14 @@ func NewChecker(conf *Config, pkg *Package, info *Info) *Checker {
// (previously, pkg.goVersion was mutated here: go.dev/issue/61212)
return &Checker{
conf: conf,
ctxt: conf.Context,
pkg: pkg,
Info: info,
objMap: make(map[Object]*declInfo),
impMap: make(map[importKey]*Package),
conf: conf,
ctxt: conf.Context,
pkg: pkg,
Info: info,
objMap: make(map[Object]*declInfo),
impMap: make(map[importKey]*Package),
usedVars: make(map[*Var]bool),
usedPkgNames: make(map[*PkgName]bool),
}
}
@@ -298,6 +302,8 @@ func NewChecker(conf *Config, pkg *Package, info *Info) *Checker {
// The provided files must all belong to the same package.
func (check *Checker) initFiles(files []*syntax.File) {
// start with a clean slate (check.Files may be called multiple times)
// TODO(gri): what determines which fields are zeroed out here, vs at the end
// of checkFiles?
check.files = nil
check.imports = nil
check.dotImportMap = nil
@@ -309,6 +315,13 @@ func (check *Checker) initFiles(files []*syntax.File) {
check.objPath = nil
check.cleaners = nil
// We must initialize usedVars and usedPkgNames both here and in NewChecker,
// because initFiles is not called in the CheckExpr or Eval codepaths, yet we
// want to free this memory at the end of Files ('used' predicates are
// only needed in the context of a given file).
check.usedVars = make(map[*Var]bool)
check.usedPkgNames = make(map[*PkgName]bool)
// determine package name and collect valid files
pkg := check.pkg
for _, file := range files {
@@ -482,8 +495,11 @@ func (check *Checker) checkFiles(files []*syntax.File) {
check.seenPkgMap = nil
check.brokenAliases = nil
check.unionTypeSets = nil
check.usedVars = nil
check.usedPkgNames = nil
check.ctxt = nil
// TODO(gri): shouldn't the cleanup above occur after the bailout?
// TODO(gri) There's more memory we should release at this point.
}

View File

@@ -242,13 +242,12 @@ func (a *object) cmp(b *object) int {
type PkgName struct {
object
imported *Package
used bool // set if the package was used
}
// NewPkgName returns a new PkgName object representing an imported package.
// The remaining arguments set the attributes found with all Objects.
func NewPkgName(pos syntax.Pos, pkg *Package, name string, imported *Package) *PkgName {
return &PkgName{object{nil, pos, pkg, name, Typ[Invalid], 0, black, nopos}, imported, false}
return &PkgName{object{nil, pos, pkg, name, Typ[Invalid], 0, black, nopos}, imported}
}
// Imported returns the package that was imported.
@@ -331,10 +330,10 @@ func (obj *TypeName) IsAlias() bool {
// A Variable represents a declared variable (including function parameters and results, and struct fields).
type Var struct {
object
origin *Var // if non-nil, the Var from which this one was instantiated
embedded bool // if set, the variable is an embedded struct field, and name is the type name
isField bool // var is struct field
used bool // set if the variable was used
origin *Var // if non-nil, the Var from which this one was instantiated
isParam bool // var is a param, for backport of 'used' check to go1.24 (go.dev/issue/72826)
}
// NewVar returns a new variable.
@@ -345,7 +344,7 @@ func NewVar(pos syntax.Pos, pkg *Package, name string, typ Type) *Var {
// NewParam returns a new variable representing a function parameter.
func NewParam(pos syntax.Pos, pkg *Package, name string, typ Type) *Var {
return &Var{object: object{nil, pos, pkg, name, typ, 0, colorFor(typ), nopos}, used: true} // parameters are always 'used'
return &Var{object: object{nil, pos, pkg, name, typ, 0, colorFor(typ), nopos}, isParam: true}
}
// NewField returns a new variable representing a struct field.

View File

@@ -295,7 +295,7 @@ func (check *Checker) collectObjects() {
if imp.fake {
// match 1.17 cmd/compile (not prescribed by spec)
pkgName.used = true
check.usedPkgNames[pkgName] = true
}
// add import to file scope
@@ -715,7 +715,7 @@ func (check *Checker) unusedImports() {
// (initialization), use the blank identifier as explicit package name."
for _, obj := range check.imports {
if !obj.used && obj.name != "_" {
if obj.name != "_" && !check.usedPkgNames[obj] {
check.errorUnusedPkg(obj)
}
}

View File

@@ -36,7 +36,7 @@ func TestSizeof(t *testing.T) {
{term{}, 12, 24},
// Objects
{PkgName{}, 64, 104},
{PkgName{}, 60, 96},
{Const{}, 64, 104},
{TypeName{}, 56, 88},
{Var{}, 64, 104},

View File

@@ -58,7 +58,7 @@ func (check *Checker) usage(scope *Scope) {
var unused []*Var
for name, elem := range scope.elems {
elem = resolve(name, elem)
if v, _ := elem.(*Var); v != nil && !v.used {
if v, _ := elem.(*Var); v != nil && !v.isParam && !check.usedVars[v] {
unused = append(unused, v)
}
}
@@ -824,10 +824,10 @@ func (check *Checker) typeSwitchStmt(inner stmtContext, s *syntax.SwitchStmt, gu
if lhs != nil {
var used bool
for _, v := range lhsVars {
if v.used {
if check.usedVars[v] {
used = true
}
v.used = true // avoid usage error when checking entire function
check.usedVars[v] = true // avoid usage error when checking entire function
}
if !used {
check.softErrorf(lhs, UnusedVar, "%s declared and not used", lhs.Value)
@@ -934,7 +934,7 @@ func (check *Checker) rangeStmt(inner stmtContext, s *syntax.ForStmt, rclause *s
if typ == nil || typ == Typ[Invalid] {
// typ == Typ[Invalid] can happen if allowVersion fails.
obj.typ = Typ[Invalid]
obj.used = true // don't complain about unused variable
check.usedVars[obj] = true // don't complain about unused variable
continue
}

View File

@@ -55,7 +55,7 @@ func (check *Checker) ident(x *operand, e *syntax.Name, def *TypeName, wantType
// avoid "declared but not used" errors
// (don't use Checker.use - we don't want to evaluate too much)
if v, _ := obj.(*Var); v != nil && v.pkg == check.pkg /* see Checker.use1 */ {
v.used = true
check.usedVars[v] = true
}
return
}
@@ -83,7 +83,7 @@ func (check *Checker) ident(x *operand, e *syntax.Name, def *TypeName, wantType
// (This code is only needed for dot-imports. Without them,
// we only have to mark variables, see *Var case below).
if pkgName := check.dotImportMap[dotImportKey{scope, obj.Name()}]; pkgName != nil {
pkgName.used = true
check.usedPkgNames[pkgName] = true
}
switch obj := obj.(type) {
@@ -120,7 +120,7 @@ func (check *Checker) ident(x *operand, e *syntax.Name, def *TypeName, wantType
// from other packages to avoid potential race conditions with
// dot-imported variables.
if obj.pkg == check.pkg {
obj.used = true
check.usedVars[obj] = true
}
check.addDeclDep(obj)
if !isValid(typ) {

View File

@@ -128,7 +128,8 @@ func runGoAuth(client *http.Client, res *http.Response, url string) {
// If no GOAUTH command provided a credential for the given url
// and an error occurred, log the error.
if cfg.BuildX && url != "" {
if ok := loadCredential(&http.Request{}, url); !ok && len(cmdErrs) > 0 {
req := &http.Request{Header: make(http.Header)}
if ok := loadCredential(req, url); !ok && len(cmdErrs) > 0 {
log.Printf("GOAUTH encountered errors for %s:", url)
for _, err := range cmdErrs {
log.Printf(" %v", err)

View File

@@ -2571,7 +2571,12 @@ func (p *Package) setBuildInfo(ctx context.Context, autoVCS bool) {
vers := revInfo.Version
if vers != "" {
if st.Uncommitted {
vers += "+dirty"
// SemVer build metadata is dot-separated https://semver.org/#spec-item-10
if strings.HasSuffix(vers, "+incompatible") {
vers += ".dirty"
} else {
vers += "+dirty"
}
}
info.Main.Version = vers
}

View File

@@ -227,21 +227,6 @@ var validLinkerFlags = []*lazyregexp.Regexp{
re(`\./.*\.(a|o|obj|dll|dylib|so|tbd)`),
}
var validLinkerFlagsOnDarwin = []*lazyregexp.Regexp{
// The GNU linker interprets `@file` as "read command-line options from
// file". Thus, we forbid values starting with `@` on linker flags.
// However, this causes a problem when targeting Darwin.
// `@executable_path`, `@loader_path`, and `@rpath` are special values
// used in Mach-O to change the library search path and can be used in
// conjunction with the `-install_name` and `-rpath` linker flags.
// Since the GNU linker does not support Mach-O, targeting Darwin
// implies not using the GNU linker. Therefore, we allow @ in the linker
// flags if and only if cfg.Goos == "darwin" || cfg.Goos == "ios".
re(`-Wl,-dylib_install_name,@rpath(/[^,]*)?`),
re(`-Wl,-install_name,@rpath(/[^,]*)?`),
re(`-Wl,-rpath,@(executable_path|loader_path)(/[^,]*)?`),
}
var validLinkerFlagsWithNextArg = []string{
"-arch",
"-F",
@@ -264,13 +249,8 @@ func checkCompilerFlags(name, source string, list []string) error {
}
func checkLinkerFlags(name, source string, list []string) error {
validLinkerFlagsForPlatform := validLinkerFlags
if cfg.Goos == "darwin" || cfg.Goos == "ios" {
validLinkerFlagsForPlatform = append(validLinkerFlags, validLinkerFlagsOnDarwin...)
}
checkOverrides := true
return checkFlags(name, source, list, invalidLinkerFlags, validLinkerFlagsForPlatform, validLinkerFlagsWithNextArg, checkOverrides)
return checkFlags(name, source, list, invalidLinkerFlags, validLinkerFlags, validLinkerFlagsWithNextArg, checkOverrides)
}
// checkCompilerFlagsForInternalLink returns an error if 'list'

View File

@@ -8,8 +8,6 @@ import (
"os"
"strings"
"testing"
"cmd/go/internal/cfg"
)
var goodCompilerFlags = [][]string{
@@ -247,8 +245,6 @@ var badLinkerFlags = [][]string{
{"-Wl,--hash-style=foo"},
{"-x", "--c"},
{"-x", "@obj"},
{"-Wl,-dylib_install_name,@foo"},
{"-Wl,-install_name,@foo"},
{"-Wl,-rpath,@foo"},
{"-Wl,-R,foo,bar"},
{"-Wl,-R,@foo"},
@@ -265,21 +261,6 @@ var badLinkerFlags = [][]string{
{"./-Wl,--push-state,-R.c"},
}
var goodLinkerFlagsOnDarwin = [][]string{
{"-Wl,-dylib_install_name,@rpath"},
{"-Wl,-dylib_install_name,@rpath/"},
{"-Wl,-dylib_install_name,@rpath/foo"},
{"-Wl,-install_name,@rpath"},
{"-Wl,-install_name,@rpath/"},
{"-Wl,-install_name,@rpath/foo"},
{"-Wl,-rpath,@executable_path"},
{"-Wl,-rpath,@executable_path/"},
{"-Wl,-rpath,@executable_path/foo"},
{"-Wl,-rpath,@loader_path"},
{"-Wl,-rpath,@loader_path/"},
{"-Wl,-rpath,@loader_path/foo"},
}
func TestCheckLinkerFlags(t *testing.T) {
for _, f := range goodLinkerFlags {
if err := checkLinkerFlags("test", "test", f); err != nil {
@@ -291,31 +272,6 @@ func TestCheckLinkerFlags(t *testing.T) {
t.Errorf("missing error for %q", f)
}
}
goos := cfg.Goos
cfg.Goos = "darwin"
for _, f := range goodLinkerFlagsOnDarwin {
if err := checkLinkerFlags("test", "test", f); err != nil {
t.Errorf("unexpected error for %q: %v", f, err)
}
}
cfg.Goos = "ios"
for _, f := range goodLinkerFlagsOnDarwin {
if err := checkLinkerFlags("test", "test", f); err != nil {
t.Errorf("unexpected error for %q: %v", f, err)
}
}
cfg.Goos = "linux"
for _, f := range goodLinkerFlagsOnDarwin {
if err := checkLinkerFlags("test", "test", f); err == nil {
t.Errorf("missing error for %q", f)
}
}
cfg.Goos = goos
}
func TestCheckFlagAllowDisallow(t *testing.T) {

View File

@@ -108,6 +108,19 @@ go version -m example$GOEXE
stdout '\s+mod\s+example\s+v1.0.3-0.20220719150703-2e239bf29c13\s+'
rm example$GOEXE
# Create +incompatible module
exec git checkout v1.0.4
exec git rm go.mod
exec git commit -m 'commit 6'
exec git tag v2.0.0
exec git checkout HEAD^ go.mod
# And make the tree +dirty
mv README4 README5
go build
go version -m example$GOEXE
stdout '\s+mod\s+example\s+v2.0.0\+incompatible.dirty\s+'
rm example$GOEXE
-- $WORK/repo/go.mod --
module example

View File

@@ -49,6 +49,8 @@ go get vcs-test.golang.org/auth/or401
go mod tidy
go list all
stdout vcs-test.golang.org/auth/or404
# With cached credentials, re-downloading in debug mode should succeed.
go get -x vcs-test.golang.org/auth/or401
# Clearing GOAUTH credentials should result in failures.
env GOAUTH='off'

View File

@@ -1006,9 +1006,10 @@ func genWasmExportWrapper(s *obj.LSym, appendp func(p *obj.Prog, as obj.As, args
// In the unwinding case, we call wasm_pc_f_loop_export to handle stack switch and rewinding,
// until a normal return (non-unwinding) back to this function.
p = appendp(p, AIf)
p = appendp(p, AI32Const, retAddr)
p = appendp(p, AI32Const, constAddr(16))
p = appendp(p, AI32ShrU)
p = appendp(p, AI64Const, retAddr)
p = appendp(p, AI64Const, constAddr(16))
p = appendp(p, AI64ShrU)
p = appendp(p, AI32WrapI64)
p = appendp(p, ACall, obj.Addr{Type: obj.TYPE_MEM, Name: obj.NAME_EXTERN, Sym: wasm_pc_f_loop_export})
p = appendp(p, AEnd)

View File

@@ -43,6 +43,9 @@ type PkgSpecial struct {
}
var runtimePkgs = []string{
// TODO(panjf2000): consider syncing the list inside the
// isAsyncSafePoint in preempt.go based on this list?
"runtime",
"internal/runtime/atomic",

View File

@@ -432,16 +432,16 @@ func (st *loadState) addSym(name string, ver int, r *oReader, li uint32, kind in
return i
}
// symbol already exists
// Fix for issue #47185 -- given two dupok or BSS symbols with
// different sizes, favor symbol with larger size. See also
// issue #46653 and #72032.
oldsz := l.SymSize(oldi)
sz := int64(r.Sym(li).Siz())
if osym.Dupok() {
if l.flags&FlagStrictDups != 0 {
l.checkdup(name, r, li, oldi)
}
// Fix for issue #47185 -- given two dupok symbols with
// different sizes, favor symbol with larger size. See
// also issue #46653.
szdup := l.SymSize(oldi)
sz := int64(r.Sym(li).Siz())
if szdup < sz {
if oldsz < sz {
// new symbol overwrites old symbol.
l.objSyms[oldi] = objSym{r.objidx, li}
}
@@ -452,11 +452,24 @@ func (st *loadState) addSym(name string, ver int, r *oReader, li uint32, kind in
if oldsym.Dupok() {
return oldi
}
overwrite := r.DataSize(li) != 0
// If one is a DATA symbol (i.e. has content, DataSize != 0)
// and the other is BSS, the one with content wins.
// If both are BSS, the one with larger size wins.
// Specifically, the "overwrite" variable and the final result are
//
// new sym old sym overwrite
// ---------------------------------------------
// DATA DATA true => ERROR
// DATA lg/eq BSS sm/eq true => new wins
// DATA small BSS large true => ERROR
// BSS large DATA small true => ERROR
// BSS large BSS small true => new wins
// BSS sm/eq D/B lg/eq false => old wins
overwrite := r.DataSize(li) != 0 || oldsz < sz
if overwrite {
// new symbol overwrites old symbol.
oldtyp := sym.AbiSymKindToSymKind[objabi.SymKind(oldsym.Type())]
if !(oldtyp.IsData() && oldr.DataSize(oldli) == 0) {
if !(oldtyp.IsData() && oldr.DataSize(oldli) == 0) || oldsz > sz {
log.Fatalf("duplicated definition of symbol %s, from %s and %s", name, r.unit.Lib.Pkg, oldr.unit.Lib.Pkg)
}
l.objSyms[oldi] = objSym{r.objidx, li}

View File

@@ -20,6 +20,7 @@ import (
"testing"
imacho "cmd/internal/macho"
"cmd/internal/objfile"
"cmd/internal/sys"
)
@@ -1541,3 +1542,53 @@ func TestCheckLinkname(t *testing.T) {
})
}
}
func TestLinknameBSS(t *testing.T) {
// Test that the linker chooses the right one as the definition
// for linknamed variables. See issue #72032.
testenv.MustHaveGoBuild(t)
t.Parallel()
tmpdir := t.TempDir()
src := filepath.Join("testdata", "linkname", "sched.go")
exe := filepath.Join(tmpdir, "sched.exe")
cmd := testenv.Command(t, testenv.GoToolPath(t), "build", "-o", exe, src)
out, err := cmd.CombinedOutput()
if err != nil {
t.Fatalf("build failed unexpectedly: %v:\n%s", err, out)
}
// Check the symbol size.
f, err := objfile.Open(exe)
if err != nil {
t.Fatalf("fail to open executable: %v", err)
}
defer f.Close()
syms, err := f.Symbols()
if err != nil {
t.Fatalf("fail to get symbols: %v", err)
}
found := false
for _, s := range syms {
if s.Name == "runtime.sched" || s.Name == "_runtime.sched" {
found = true
if s.Size < 100 {
// As of Go 1.25 (Mar 2025), runtime.sched has 6848 bytes on
// darwin/arm64. It should always be larger than 100 bytes on
// all platforms.
t.Errorf("runtime.sched symbol size too small: want > 100, got %d", s.Size)
}
}
}
if !found {
t.Errorf("runtime.sched symbol not found")
}
// Executable should run.
cmd = testenv.Command(t, exe)
out, err = cmd.CombinedOutput()
if err != nil {
t.Errorf("executable failed to run: %v\n%s", err, out)
}
}

19
src/cmd/link/testdata/linkname/sched.go vendored Normal file
View File

@@ -0,0 +1,19 @@
// Copyright 2025 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package main
import _ "unsafe"
type schedt struct{}
//go:linkname sched runtime.sched
var sched schedt
func main() {
select {
default:
println("hello")
}
}

View File

@@ -10,7 +10,7 @@ import (
"internal/godebug"
)
var fips140GODEBUG = godebug.New("#fips140")
var fips140GODEBUG = godebug.New("fips140")
// Enabled reports whether the cryptography libraries are operating in FIPS
// 140-3 mode.

View File

@@ -100,7 +100,7 @@ func init() {
clear(nbuf[:])
h.Reset()
if godebug.Value("#fips140") == "debug" {
if godebug.Value("fips140") == "debug" {
println("fips140: verified code+data")
}

View File

@@ -16,7 +16,7 @@ import (
// Enabled reports whether FIPS 140-only mode is enabled, in which non-approved
// cryptography returns an error or panics.
var Enabled = godebug.New("#fips140").Value() == "only"
var Enabled = godebug.New("fips140").Value() == "only"
func ApprovedHash(h hash.Hash) bool {
switch h.(type) {

View File

@@ -26,7 +26,7 @@ func TestFIPSCheckVerify(t *testing.T) {
return
}
if godebug.New("#fips140").Value() == "on" {
if godebug.New("fips140").Value() == "on" {
t.Fatalf("GODEBUG=fips140=on but verification did not run")
}

View File

@@ -92,7 +92,8 @@ var defaultCipherSuitesTLS13NoAES = []uint16{
}
// The FIPS-only policies below match BoringSSL's
// ssl_compliance_policy_fips_202205, which is based on NIST SP 800-52r2.
// ssl_compliance_policy_fips_202205, which is based on NIST SP 800-52r2, with
// minor changes per https://go.dev/issue/71757.
// https://cs.opensource.google/boringssl/boringssl/+/master:ssl/ssl_lib.cc;l=3289;drc=ea7a88fa
var defaultSupportedVersionsFIPS = []uint16{
@@ -102,7 +103,7 @@ var defaultSupportedVersionsFIPS = []uint16{
// defaultCurvePreferencesFIPS are the FIPS-allowed curves,
// in preference order (most preferable first).
var defaultCurvePreferencesFIPS = []CurveID{CurveP256, CurveP384}
var defaultCurvePreferencesFIPS = []CurveID{CurveP256, CurveP384, CurveP521}
// defaultSupportedSignatureAlgorithmsFIPS currently are a subset of
// defaultSupportedSignatureAlgorithms without Ed25519 and SHA-1.
@@ -115,6 +116,7 @@ var defaultSupportedSignatureAlgorithmsFIPS = []SignatureScheme{
PKCS1WithSHA384,
ECDSAWithP384AndSHA384,
PKCS1WithSHA512,
ECDSAWithP521AndSHA512,
}
// defaultCipherSuitesFIPS are the FIPS-allowed cipher suites.

View File

@@ -381,8 +381,28 @@ func decodeInnerClientHello(outer *clientHelloMsg, encoded []byte) (*clientHello
return nil, errInvalidECHExt
}
if len(inner.supportedVersions) != 1 || (len(inner.supportedVersions) >= 1 && inner.supportedVersions[0] != VersionTLS13) {
return nil, errors.New("tls: client sent encrypted_client_hello extension and offered incompatible versions")
hasTLS13 := false
for _, v := range inner.supportedVersions {
// Skip GREASE values (values of the form 0x?A0A).
// GREASE (Generate Random Extensions And Sustain Extensibility) is a mechanism used by
// browsers like Chrome to ensure TLS implementations correctly ignore unknown values.
// GREASE values follow a specific pattern: 0x?A0A, where ? can be any hex digit.
// These values should be ignored when processing supported TLS versions.
if v&0x0F0F == 0x0A0A && v&0xff == v>>8 {
continue
}
// Ensure at least TLS 1.3 is offered.
if v == VersionTLS13 {
hasTLS13 = true
} else if v < VersionTLS13 {
// Reject if any non-GREASE value is below TLS 1.3, as ECH requires TLS 1.3+.
return nil, errors.New("tls: client sent encrypted_client_hello extension with unsupported versions")
}
}
if !hasTLS13 {
return nil, errors.New("tls: client sent encrypted_client_hello extension but did not offer TLS 1.3")
}
return inner, nil

View File

@@ -106,7 +106,7 @@ func isFIPSCipherSuite(id uint16) bool {
func isFIPSCurve(id CurveID) bool {
switch id {
case CurveP256, CurveP384:
case CurveP256, CurveP384, CurveP521:
return true
}
return false
@@ -130,6 +130,7 @@ func isFIPSSignatureScheme(alg SignatureScheme) bool {
PKCS1WithSHA384,
ECDSAWithP384AndSHA384,
PKCS1WithSHA512,
ECDSAWithP521AndSHA512,
PSSWithSHA256,
PSSWithSHA384,
PSSWithSHA512:

View File

@@ -11,6 +11,7 @@ import (
"encoding/binary"
"flag"
"fmt"
"internal/obscuretestdata"
"internal/testenv"
"os"
"os/exec"
@@ -275,24 +276,16 @@ func TestReadFile(t *testing.T) {
// Test117 verifies that parsing of the old, pre-1.18 format works.
func Test117(t *testing.T) {
// go117 was generated for linux-amd64 with:
//
// main.go:
//
// package main
// func main() {}
//
// GOTOOLCHAIN=go1.17 go mod init example.com/go117
// GOTOOLCHAIN=go1.17 go build
//
// TODO(prattmic): Ideally this would be built on the fly to better
// cover all executable formats, but then we need a network connection
// to download an old Go toolchain.
info, err := buildinfo.ReadFile("testdata/go117")
b, err := obscuretestdata.ReadFile("testdata/go117/go117.base64")
if err != nil {
t.Fatalf("ReadFile got err %v, want nil", err)
}
info, err := buildinfo.Read(bytes.NewReader(b))
if err != nil {
t.Fatalf("Read got err %v, want nil", err)
}
if info.GoVersion != "go1.17" {
t.Errorf("GoVersion got %s want go1.17", info.GoVersion)
}
@@ -306,20 +299,14 @@ func Test117(t *testing.T) {
// TestNotGo verifies that parsing of a non-Go binary returns the proper error.
func TestNotGo(t *testing.T) {
// notgo was generated for linux-amd64 with:
//
// main.c:
//
// int main(void) { return 0; }
//
// cc -o notgo main.c
//
// TODO(prattmic): Ideally this would be built on the fly to better
// cover all executable formats, but then we need to encode the
// intricacies of calling each platform's C compiler.
_, err := buildinfo.ReadFile("testdata/notgo")
b, err := obscuretestdata.ReadFile("testdata/notgo/notgo.base64")
if err != nil {
t.Fatalf("ReadFile got err %v, want nil", err)
}
_, err = buildinfo.Read(bytes.NewReader(b))
if err == nil {
t.Fatalf("ReadFile got nil err, want non-nil")
t.Fatalf("Read got nil err, want non-nil")
}
// The precise error text here isn't critical, but we want something
@@ -410,13 +397,13 @@ func TestIssue54968(t *testing.T) {
}
func FuzzRead(f *testing.F) {
go117, err := os.ReadFile("testdata/go117")
go117, err := obscuretestdata.ReadFile("testdata/go117/go117.base64")
if err != nil {
f.Errorf("Error reading go117: %v", err)
}
f.Add(go117)
notgo, err := os.ReadFile("testdata/notgo")
notgo, err := obscuretestdata.ReadFile("testdata/notgo/notgo.base64")
if err != nil {
f.Errorf("Error reading notgo: %v", err)
}

Binary file not shown.

View File

@@ -0,0 +1,15 @@
go117.base64 is a base64-encoded Go 1.17 hello world binary used to test
debug/buildinfo of pre-1.18 buildinfo encoding.
The binary is base64 encoded to hide it from security scanners that believe a
Go 1.17 is inherently insecure.
Generate go117.base64 with:
$ GOTOOLCHAIN=go1.17 GOOS=linux GOARCH=amd64 go build -trimpath
$ base64 go117 > go117.base64
$ rm go117
TODO(prattmic): Ideally this would be built on the fly to better cover all
executable formats, but then we need a network connection to download an old Go
toolchain.

View File

@@ -0,0 +1,3 @@
module example.com/go117
go 1.17

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,7 @@
// Copyright 2025 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package main
func main() {}

Binary file not shown.

View File

@@ -0,0 +1,17 @@
notgo.base64 is a base64-encoded C hello world binary used to test
debug/buildinfo errors on non-Go binaries.
The binary is base64 encoded to hide it from security scanners that might not
like it.
Generate notgo.base64 on linux-amd64 with:
$ cc -o notgo main.c
$ base64 notgo > notgo.base64
$ rm notgo
The current binary was built with "gcc version 14.2.0 (Debian 14.2.0-3+build4)".
TODO(prattmic): Ideally this would be built on the fly to better cover all
executable formats, but then we need to encode the intricacies of calling each
platform's C compiler.

View File

@@ -0,0 +1,7 @@
// Copyright 2025 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
int main(void) {
return 0;
}

View File

@@ -0,0 +1,278 @@
f0VMRgIBAQAAAAAAAAAAAAMAPgABAAAAQBAAAAAAAABAAAAAAAAAAGA2AAAAAAAAAAAAAEAAOAAN
AEAAHgAdAAYAAAAEAAAAQAAAAAAAAABAAAAAAAAAAEAAAAAAAAAA2AIAAAAAAADYAgAAAAAAAAgA
AAAAAAAAAwAAAAQAAAAYAwAAAAAAABgDAAAAAAAAGAMAAAAAAAAcAAAAAAAAABwAAAAAAAAAAQAA
AAAAAAABAAAABAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAOAFAAAAAAAA4AUAAAAAAAAAEAAA
AAAAAAEAAAAFAAAAABAAAAAAAAAAEAAAAAAAAAAQAAAAAAAAPQEAAAAAAAA9AQAAAAAAAAAQAAAA
AAAAAQAAAAQAAAAAIAAAAAAAAAAgAAAAAAAAACAAAAAAAADcAAAAAAAAANwAAAAAAAAAABAAAAAA
AAABAAAABgAAAAAuAAAAAAAAAD4AAAAAAAAAPgAAAAAAABACAAAAAAAAGAIAAAAAAAAAEAAAAAAA
AAIAAAAGAAAAEC4AAAAAAAAQPgAAAAAAABA+AAAAAAAAsAEAAAAAAACwAQAAAAAAAAgAAAAAAAAA
BAAAAAQAAAA4AwAAAAAAADgDAAAAAAAAOAMAAAAAAAAgAAAAAAAAACAAAAAAAAAACAAAAAAAAAAE
AAAABAAAAFgDAAAAAAAAWAMAAAAAAABYAwAAAAAAAEQAAAAAAAAARAAAAAAAAAAEAAAAAAAAAFPl
dGQEAAAAOAMAAAAAAAA4AwAAAAAAADgDAAAAAAAAIAAAAAAAAAAgAAAAAAAAAAgAAAAAAAAAUOV0
ZAQAAAAEIAAAAAAAAAQgAAAAAAAABCAAAAAAAAAsAAAAAAAAACwAAAAAAAAABAAAAAAAAABR5XRk
BgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQAAAAAAAAAFLldGQE
AAAAAC4AAAAAAAAAPgAAAAAAAAA+AAAAAAAAAAIAAAAAAAAAAgAAAAAAAAEAAAAAAAAAL2xpYjY0
L2xkLWxpbnV4LXg4Ni02NC5zby4yAAAAAAAEAAAAEAAAAAUAAABHTlUAAoAAwAQAAAABAAAAAAAA
AAQAAAAUAAAAAwAAAEdOVQB5fSf98eWTEBscIbS6nrsfguPLDgQAAAAQAAAAAQAAAEdOVQAAAAAA
AwAAAAIAAAAAAAAAAAAAAAIAAAAFAAAAAQAAAAYAAAAAAIEAAAAAAAUAAAAAAAAA0WXObQAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAAAAEgAAAAAAAAAAAAAAAAAAAAAAAABDAAAAIAAAAAAA
AAAAAAAAAAAAAAAAAABfAAAAIAAAAAAAAAAAAAAAAAAAAAAAAABuAAAAIAAAAAAAAAAAAAAAAAAA
AAAAAAATAAAAIgAAAAAAAAAAAAAAAAAAAAAAAAAAX19saWJjX3N0YXJ0X21haW4AX19jeGFfZmlu
YWxpemUAbGliYy5zby42AEdMSUJDXzIuMi41AEdMSUJDXzIuMzQAX0lUTV9kZXJlZ2lzdGVyVE1D
bG9uZVRhYmxlAF9fZ21vbl9zdGFydF9fAF9JVE1fcmVnaXN0ZXJUTUNsb25lVGFibGUAAAACAAEA
AQABAAMAAAAAAAEAAgAiAAAAEAAAAAAAAAB1GmkJAAADACwAAAAQAAAAtJGWBgAAAgA4AAAAAAAA
AAA+AAAAAAAACAAAAAAAAAAgEQAAAAAAAAg+AAAAAAAACAAAAAAAAADgEAAAAAAAAAhAAAAAAAAA
CAAAAAAAAAAIQAAAAAAAAMA/AAAAAAAABgAAAAEAAAAAAAAAAAAAAMg/AAAAAAAABgAAAAIAAAAA
AAAAAAAAANA/AAAAAAAABgAAAAMAAAAAAAAAAAAAANg/AAAAAAAABgAAAAQAAAAAAAAAAAAAAOA/
AAAAAAAABgAAAAUAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEiD7AhIiwXF
LwAASIXAdAL/0EiDxAjDAAAAAAAAAAAA/zXKLwAA/yXMLwAADx9AAP8lqi8AAGaQAAAAAAAAAAAx
7UmJ0V5IieJIg+TwUFRFMcAxyUiNPc4AAAD/FV8vAAD0Zi4PH4QAAAAAAA8fQABIjT2ZLwAASI0F
ki8AAEg5+HQVSIsFPi8AAEiFwHQJ/+APH4AAAAAAww8fgAAAAABIjT1pLwAASI01Yi8AAEgp/kiJ
8EjB7j9IwfgDSAHGSNH+dBRIiwUNLwAASIXAdAj/4GYPH0QAAMMPH4AAAAAA8w8e+oA9JS8AAAB1
K1VIgz3qLgAAAEiJ5XQMSIs9Bi8AAOgp////6GT////GBf0uAAABXcMPHwDDDx+AAAAAAPMPHvrp
d////1VIieW4AAAAAF3DSIPsCEiDxAjDAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAAIAARsDOygAAAAEAAAA
HPD//3QAAAAs8P//nAAAADzw//9EAAAAJfH//7QAAAAUAAAAAAAAAAF6UgABeBABGwwHCJABBxAU
AAAAHAAAAPDv//8iAAAAAAAAAAAAAAAUAAAAAAAAAAF6UgABeBABGwwHCJABAAAkAAAAHAAAAKDv
//8QAAAAAA4QRg4YSg8LdwiAAD8aOyozJCIAAAAAFAAAAEQAAACI7///CAAAAAAAAAAAAAAAHAAA
AFwAAABp8P//CwAAAABBDhCGAkMNBkYMBwgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACARAAAAAAAA4BAAAAAAAAABAAAAAAAA
ACIAAAAAAAAADAAAAAAAAAAAEAAAAAAAAA0AAAAAAAAANBEAAAAAAAAZAAAAAAAAAAA+AAAAAAAA
GwAAAAAAAAAIAAAAAAAAABoAAAAAAAAACD4AAAAAAAAcAAAAAAAAAAgAAAAAAAAA9f7/bwAAAACg
AwAAAAAAAAUAAAAAAAAAWAQAAAAAAAAGAAAAAAAAAMgDAAAAAAAACgAAAAAAAACIAAAAAAAAAAsA
AAAAAAAAGAAAAAAAAAAVAAAAAAAAAAAAAAAAAAAAAwAAAAAAAADoPwAAAAAAAAcAAAAAAAAAIAUA
AAAAAAAIAAAAAAAAAMAAAAAAAAAACQAAAAAAAAAYAAAAAAAAAPv//28AAAAAAAAACAAAAAD+//9v
AAAAAPAEAAAAAAAA////bwAAAAABAAAAAAAAAPD//28AAAAA4AQAAAAAAAD5//9vAAAAAAMAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAED4AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAIQAAAAAAAAEdDQzogKERl
YmlhbiAxNC4yLjAtMytidWlsZDQpIDE0LjIuMAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAB
AAAABADx/wAAAAAAAAAAAAAAAAAAAAAJAAAAAQAEAHwDAAAAAAAAIAAAAAAAAAATAAAABADx/wAA
AAAAAAAAAAAAAAAAAAAeAAAAAgAOAHAQAAAAAAAAAAAAAAAAAAAgAAAAAgAOAKAQAAAAAAAAAAAA
AAAAAAAzAAAAAgAOAOAQAAAAAAAAAAAAAAAAAABJAAAAAQAZABBAAAAAAAAAAQAAAAAAAABVAAAA
AQAUAAg+AAAAAAAAAAAAAAAAAAB8AAAAAgAOACARAAAAAAAAAAAAAAAAAACIAAAAAQATAAA+AAAA
AAAAAAAAAAAAAACnAAAABADx/wAAAAAAAAAAAAAAAAAAAAATAAAABADx/wAAAAAAAAAAAAAAAAAA
AACuAAAAAQASANggAAAAAAAAAAAAAAAAAAAAAAAABADx/wAAAAAAAAAAAAAAAAAAAAC8AAAAAQAV
ABA+AAAAAAAAAAAAAAAAAADFAAAAAAARAAQgAAAAAAAAAAAAAAAAAADYAAAAAQAXAOg/AAAAAAAA
AAAAAAAAAADuAAAAEgAAAAAAAAAAAAAAAAAAAAAAAAALAQAAIAAAAAAAAAAAAAAAAAAAAAAAAAA2
AQAAIAAYAABAAAAAAAAAAAAAAAAAAAAnAQAAEAAYABBAAAAAAAAAAAAAAAAAAAAuAQAAEgIPADQR
AAAAAAAAAAAAAAAAAAA0AQAAEAAYAABAAAAAAAAAAAAAAAAAAABBAQAAIAAAAAAAAAAAAAAAAAAA
AAAAAABQAQAAEQIYAAhAAAAAAAAAAAAAAAAAAABdAQAAEQAQAAAgAAAAAAAABAAAAAAAAABsAQAA
EAAZABhAAAAAAAAAAAAAAAAAAAA6AQAAEgAOAEAQAAAAAAAAIgAAAAAAAABxAQAAEAAZABBAAAAA
AAAAAAAAAAAAAAB9AQAAEgAOACkRAAAAAAAACwAAAAAAAACCAQAAEQIYABBAAAAAAAAAAAAAAAAA
AACOAQAAIAAAAAAAAAAAAAAAAAAAAAAAAACoAQAAIgAAAAAAAAAAAAAAAAAAAAAAAADDAQAAEgIL
AAAQAAAAAAAAAAAAAAAAAAAAU2NydDEubwBfX2FiaV90YWcAY3J0c3R1ZmYuYwBkZXJlZ2lzdGVy
X3RtX2Nsb25lcwBfX2RvX2dsb2JhbF9kdG9yc19hdXgAY29tcGxldGVkLjAAX19kb19nbG9iYWxf
ZHRvcnNfYXV4X2ZpbmlfYXJyYXlfZW50cnkAZnJhbWVfZHVtbXkAX19mcmFtZV9kdW1teV9pbml0
X2FycmF5X2VudHJ5AG1haW4uYwBfX0ZSQU1FX0VORF9fAF9EWU5BTUlDAF9fR05VX0VIX0ZSQU1F
X0hEUgBfR0xPQkFMX09GRlNFVF9UQUJMRV8AX19saWJjX3N0YXJ0X21haW5AR0xJQkNfMi4zNABf
SVRNX2RlcmVnaXN0ZXJUTUNsb25lVGFibGUAX2VkYXRhAF9maW5pAF9fZGF0YV9zdGFydABfX2dt
b25fc3RhcnRfXwBfX2Rzb19oYW5kbGUAX0lPX3N0ZGluX3VzZWQAX2VuZABfX2Jzc19zdGFydABt
YWluAF9fVE1DX0VORF9fAF9JVE1fcmVnaXN0ZXJUTUNsb25lVGFibGUAX19jeGFfZmluYWxpemVA
R0xJQkNfMi4yLjUAX2luaXQAAC5zeW10YWIALnN0cnRhYgAuc2hzdHJ0YWIALmludGVycAAubm90
ZS5nbnUucHJvcGVydHkALm5vdGUuZ251LmJ1aWxkLWlkAC5ub3RlLkFCSS10YWcALmdudS5oYXNo
AC5keW5zeW0ALmR5bnN0cgAuZ251LnZlcnNpb24ALmdudS52ZXJzaW9uX3IALnJlbGEuZHluAC5p
bml0AC5wbHQuZ290AC50ZXh0AC5maW5pAC5yb2RhdGEALmVoX2ZyYW1lX2hkcgAuZWhfZnJhbWUA
LmluaXRfYXJyYXkALmZpbmlfYXJyYXkALmR5bmFtaWMALmdvdC5wbHQALmRhdGEALmJzcwAuY29t
bWVudAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAABsAAAABAAAAAgAAAAAAAAAYAwAAAAAAABgDAAAAAAAAHAAAAAAA
AAAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAAAjAAAABwAAAAIAAAAAAAAAOAMAAAAAAAA4AwAAAAAA
ACAAAAAAAAAAAAAAAAAAAAAIAAAAAAAAAAAAAAAAAAAANgAAAAcAAAACAAAAAAAAAFgDAAAAAAAA
WAMAAAAAAAAkAAAAAAAAAAAAAAAAAAAABAAAAAAAAAAAAAAAAAAAAEkAAAAHAAAAAgAAAAAAAAB8
AwAAAAAAAHwDAAAAAAAAIAAAAAAAAAAAAAAAAAAAAAQAAAAAAAAAAAAAAAAAAABXAAAA9v//bwIA
AAAAAAAAoAMAAAAAAACgAwAAAAAAACQAAAAAAAAABgAAAAAAAAAIAAAAAAAAAAAAAAAAAAAAYQAA
AAsAAAACAAAAAAAAAMgDAAAAAAAAyAMAAAAAAACQAAAAAAAAAAcAAAABAAAACAAAAAAAAAAYAAAA
AAAAAGkAAAADAAAAAgAAAAAAAABYBAAAAAAAAFgEAAAAAAAAiAAAAAAAAAAAAAAAAAAAAAEAAAAA
AAAAAAAAAAAAAABxAAAA////bwIAAAAAAAAA4AQAAAAAAADgBAAAAAAAAAwAAAAAAAAABgAAAAAA
AAACAAAAAAAAAAIAAAAAAAAAfgAAAP7//28CAAAAAAAAAPAEAAAAAAAA8AQAAAAAAAAwAAAAAAAA
AAcAAAABAAAACAAAAAAAAAAAAAAAAAAAAI0AAAAEAAAAAgAAAAAAAAAgBQAAAAAAACAFAAAAAAAA
wAAAAAAAAAAGAAAAAAAAAAgAAAAAAAAAGAAAAAAAAACXAAAAAQAAAAYAAAAAAAAAABAAAAAAAAAA
EAAAAAAAABcAAAAAAAAAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAAA9wAAAAEAAAAGAAAAAAAAACAQ
AAAAAAAAIBAAAAAAAAAQAAAAAAAAAAAAAAAAAAAAEAAAAAAAAAAQAAAAAAAAAJ0AAAABAAAABgAA
AAAAAAAwEAAAAAAAADAQAAAAAAAACAAAAAAAAAAAAAAAAAAAAAgAAAAAAAAACAAAAAAAAACmAAAA
AQAAAAYAAAAAAAAAQBAAAAAAAABAEAAAAAAAAPQAAAAAAAAAAAAAAAAAAAAQAAAAAAAAAAAAAAAA
AAAArAAAAAEAAAAGAAAAAAAAADQRAAAAAAAANBEAAAAAAAAJAAAAAAAAAAAAAAAAAAAABAAAAAAA
AAAAAAAAAAAAALIAAAABAAAAEgAAAAAAAAAAIAAAAAAAAAAgAAAAAAAABAAAAAAAAAAAAAAAAAAA
AAQAAAAAAAAABAAAAAAAAAC6AAAAAQAAAAIAAAAAAAAABCAAAAAAAAAEIAAAAAAAACwAAAAAAAAA
AAAAAAAAAAAEAAAAAAAAAAAAAAAAAAAAyAAAAAEAAAACAAAAAAAAADAgAAAAAAAAMCAAAAAAAACs
AAAAAAAAAAAAAAAAAAAACAAAAAAAAAAAAAAAAAAAANIAAAAOAAAAAwAAAAAAAAAAPgAAAAAAAAAu
AAAAAAAACAAAAAAAAAAAAAAAAAAAAAgAAAAAAAAACAAAAAAAAADeAAAADwAAAAMAAAAAAAAACD4A
AAAAAAAILgAAAAAAAAgAAAAAAAAAAAAAAAAAAAAIAAAAAAAAAAgAAAAAAAAA6gAAAAYAAAADAAAA
AAAAABA+AAAAAAAAEC4AAAAAAACwAQAAAAAAAAcAAAAAAAAACAAAAAAAAAAQAAAAAAAAAKEAAAAB
AAAAAwAAAAAAAADAPwAAAAAAAMAvAAAAAAAAKAAAAAAAAAAAAAAAAAAAAAgAAAAAAAAACAAAAAAA
AADzAAAAAQAAAAMAAAAAAAAA6D8AAAAAAADoLwAAAAAAABgAAAAAAAAAAAAAAAAAAAAIAAAAAAAA
AAgAAAAAAAAA/AAAAAEAAAADAAAAAAAAAABAAAAAAAAAADAAAAAAAAAQAAAAAAAAAAAAAAAAAAAA
CAAAAAAAAAAAAAAAAAAAAAIBAAAIAAAAAwAAAAAAAAAQQAAAAAAAABAwAAAAAAAACAAAAAAAAAAA
AAAAAAAAAAEAAAAAAAAAAAAAAAAAAAAHAQAAAQAAADAAAAAAAAAAAAAAAAAAAAAQMAAAAAAAACUA
AAAAAAAAAAAAAAAAAAABAAAAAAAAAAEAAAAAAAAAAQAAAAIAAAAAAAAAAAAAAAAAAAAAAAAAODAA
AAAAAABIAwAAAAAAABwAAAASAAAACAAAAAAAAAAYAAAAAAAAAAkAAAADAAAAAAAAAAAAAAAAAAAA
AAAAAIAzAAAAAAAAyQEAAAAAAAAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAAARAAAAAwAAAAAAAAAA
AAAAAAAAAAAAAABJNQAAAAAAABABAAAAAAAAAAAAAAAAAAABAAAAAAAAAAAAAAAAAAAA

View File

@@ -4,7 +4,7 @@ go 1.24
require (
golang.org/x/crypto v0.30.0
golang.org/x/net v0.32.1-0.20250121202134-9a960c88dd98
golang.org/x/net v0.32.1-0.20250304185419-76f9bf3279ef
)
require (

View File

@@ -1,7 +1,7 @@
golang.org/x/crypto v0.30.0 h1:RwoQn3GkWiMkzlX562cLB7OxWvjH1L8xutO2WoJcRoY=
golang.org/x/crypto v0.30.0/go.mod h1:kDsLvtWBEx7MV9tJOj9bnXsPbxwJQ6csT/x4KIN4Ssk=
golang.org/x/net v0.32.1-0.20250121202134-9a960c88dd98 h1:36bTiCRO7f/J3t+LumnLTJDXqxsp1x6Q7754SsRD9u4=
golang.org/x/net v0.32.1-0.20250121202134-9a960c88dd98/go.mod h1:CwU0IoeOlnQQWJ6ioyFrfRuomB8GKF6KbYXZVyeXNfs=
golang.org/x/net v0.32.1-0.20250304185419-76f9bf3279ef h1:oQtTn7aH5kyi7dPmG2Eot3aG1XBwnkrX+zIq+lNeZeM=
golang.org/x/net v0.32.1-0.20250304185419-76f9bf3279ef/go.mod h1:CwU0IoeOlnQQWJ6ioyFrfRuomB8GKF6KbYXZVyeXNfs=
golang.org/x/sys v0.28.0 h1:Fksou7UEQUWlKvIdsqzJmUmCX3cZuD2+P3XyyzwMhlA=
golang.org/x/sys v0.28.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
golang.org/x/text v0.21.0 h1:zyQAAkrwaneQ066sspRyJaG9VNi/YJ1NfzcGB3hZ/qo=

View File

@@ -207,7 +207,7 @@ func (check *Checker) lhsVar(lhs ast.Expr) Type {
// dot-imported variables.
if w, _ := obj.(*Var); w != nil && w.pkg == check.pkg {
v = w
v_used = v.used
v_used = check.usedVars[v]
}
}
}
@@ -216,7 +216,7 @@ func (check *Checker) lhsVar(lhs ast.Expr) Type {
check.expr(nil, &x, lhs)
if v != nil {
v.used = v_used // restore v.used
check.usedVars[v] = v_used // restore v.used
}
if x.mode == invalid || !isValid(x.typ) {

View File

@@ -689,7 +689,7 @@ func (check *Checker) selector(x *operand, e *ast.SelectorExpr, def *TypeName, w
if pname, _ := obj.(*PkgName); pname != nil {
assert(pname.pkg == check.pkg)
check.recordUse(ident, pname)
pname.used = true
check.usedPkgNames[pname] = true
pkg := pname.imported
var exp Object
@@ -1020,13 +1020,13 @@ func (check *Checker) use1(e ast.Expr, lhs bool) bool {
// dot-imported variables.
if w, _ := obj.(*Var); w != nil && w.pkg == check.pkg {
v = w
v_used = v.used
v_used = check.usedVars[v]
}
}
}
check.exprOrType(&x, n, true)
if v != nil {
v.used = v_used // restore v.used
check.usedVars[v] = v_used // restore v.used
}
default:
check.rawExpr(nil, &x, e, nil, true)

View File

@@ -182,6 +182,8 @@ type Checker struct {
dotImportMap map[dotImportKey]*PkgName // maps dot-imported objects to the package they were dot-imported through
brokenAliases map[*TypeName]bool // set of aliases with broken (not yet determined) types
unionTypeSets map[*Union]*_TypeSet // computed type sets for union types
usedVars map[*Var]bool // set of used variables
usedPkgNames map[*PkgName]bool // set of used package names
mono monoGraph // graph for detecting non-monomorphizable instantiation loops
firstErr error // first error encountered
@@ -308,13 +310,15 @@ func NewChecker(conf *Config, fset *token.FileSet, pkg *Package, info *Info) *Ch
conf._EnableAlias = gotypesalias.Value() != "0"
return &Checker{
conf: conf,
ctxt: conf.Context,
fset: fset,
pkg: pkg,
Info: info,
objMap: make(map[Object]*declInfo),
impMap: make(map[importKey]*Package),
conf: conf,
ctxt: conf.Context,
fset: fset,
pkg: pkg,
Info: info,
objMap: make(map[Object]*declInfo),
impMap: make(map[importKey]*Package),
usedVars: make(map[*Var]bool),
usedPkgNames: make(map[*PkgName]bool),
}
}
@@ -322,6 +326,8 @@ func NewChecker(conf *Config, fset *token.FileSet, pkg *Package, info *Info) *Ch
// The provided files must all belong to the same package.
func (check *Checker) initFiles(files []*ast.File) {
// start with a clean slate (check.Files may be called multiple times)
// TODO(gri): what determines which fields are zeroed out here, vs at the end
// of checkFiles?
check.files = nil
check.imports = nil
check.dotImportMap = nil
@@ -333,6 +339,13 @@ func (check *Checker) initFiles(files []*ast.File) {
check.objPath = nil
check.cleaners = nil
// We must initialize usedVars and usedPkgNames both here and in NewChecker,
// because initFiles is not called in the CheckExpr or Eval codepaths, yet we
// want to free this memory at the end of Files ('used' predicates are
// only needed in the context of a given file).
check.usedVars = make(map[*Var]bool)
check.usedPkgNames = make(map[*PkgName]bool)
// determine package name and collect valid files
pkg := check.pkg
for _, file := range files {
@@ -507,9 +520,12 @@ func (check *Checker) checkFiles(files []*ast.File) {
check.seenPkgMap = nil
check.brokenAliases = nil
check.unionTypeSets = nil
check.usedVars = nil
check.usedPkgNames = nil
check.ctxt = nil
// TODO(rFindley) There's more memory we should release at this point.
// TODO(gri): shouldn't the cleanup above occur after the bailout?
// TODO(gri) There's more memory we should release at this point.
}
// processDelayed processes all delayed actions pushed after top.

View File

@@ -245,13 +245,12 @@ func (a *object) cmp(b *object) int {
type PkgName struct {
object
imported *Package
used bool // set if the package was used
}
// NewPkgName returns a new PkgName object representing an imported package.
// The remaining arguments set the attributes found with all Objects.
func NewPkgName(pos token.Pos, pkg *Package, name string, imported *Package) *PkgName {
return &PkgName{object{nil, pos, pkg, name, Typ[Invalid], 0, black, nopos}, imported, false}
return &PkgName{object{nil, pos, pkg, name, Typ[Invalid], 0, black, nopos}, imported}
}
// Imported returns the package that was imported.
@@ -334,10 +333,10 @@ func (obj *TypeName) IsAlias() bool {
// A Variable represents a declared variable (including function parameters and results, and struct fields).
type Var struct {
object
origin *Var // if non-nil, the Var from which this one was instantiated
embedded bool // if set, the variable is an embedded struct field, and name is the type name
isField bool // var is struct field
used bool // set if the variable was used
origin *Var // if non-nil, the Var from which this one was instantiated
isParam bool // var is a param, for backport of 'used' check to go1.24 (go.dev/issue/72826)
}
// NewVar returns a new variable.
@@ -348,7 +347,7 @@ func NewVar(pos token.Pos, pkg *Package, name string, typ Type) *Var {
// NewParam returns a new variable representing a function parameter.
func NewParam(pos token.Pos, pkg *Package, name string, typ Type) *Var {
return &Var{object: object{nil, pos, pkg, name, typ, 0, colorFor(typ), nopos}, used: true} // parameters are always 'used'
return &Var{object: object{nil, pos, pkg, name, typ, 0, colorFor(typ), nopos}, isParam: true}
}
// NewField returns a new variable representing a struct field.

View File

@@ -310,7 +310,7 @@ func (check *Checker) collectObjects() {
if imp.fake {
// match 1.17 cmd/compile (not prescribed by spec)
pkgName.used = true
check.usedPkgNames[pkgName] = true
}
// add import to file scope
@@ -710,7 +710,7 @@ func (check *Checker) unusedImports() {
// (initialization), use the blank identifier as explicit package name."
for _, obj := range check.imports {
if !obj.used && obj.name != "_" {
if obj.name != "_" && !check.usedPkgNames[obj] {
check.errorUnusedPkg(obj)
}
}

View File

@@ -35,7 +35,7 @@ func TestSizeof(t *testing.T) {
{term{}, 12, 24},
// Objects
{PkgName{}, 48, 88},
{PkgName{}, 44, 80},
{Const{}, 48, 88},
{TypeName{}, 40, 72},
{Var{}, 48, 88},

View File

@@ -59,7 +59,7 @@ func (check *Checker) usage(scope *Scope) {
var unused []*Var
for name, elem := range scope.elems {
elem = resolve(name, elem)
if v, _ := elem.(*Var); v != nil && !v.used {
if v, _ := elem.(*Var); v != nil && !v.isParam && !check.usedVars[v] {
unused = append(unused, v)
}
}
@@ -777,13 +777,16 @@ func (check *Checker) stmt(ctxt stmtContext, s ast.Stmt) {
}
// If lhs exists, we must have at least one lhs variable that was used.
// (We can't use check.usage because that only looks at one scope; and
// we don't want to use the same variable for all scopes and change the
// variable type underfoot.)
if lhs != nil {
var used bool
for _, v := range lhsVars {
if v.used {
if check.usedVars[v] {
used = true
}
v.used = true // avoid usage error when checking entire function
check.usedVars[v] = true // avoid usage error when checking entire function
}
if !used {
check.softErrorf(lhs, UnusedVar, "%s declared and not used", lhs.Name)
@@ -952,7 +955,7 @@ func (check *Checker) rangeStmt(inner stmtContext, s *ast.RangeStmt) {
if typ == nil || typ == Typ[Invalid] {
// typ == Typ[Invalid] can happen if allowVersion fails.
obj.typ = Typ[Invalid]
obj.used = true // don't complain about unused variable
check.usedVars[obj] = true // don't complain about unused variable
continue
}

View File

@@ -54,7 +54,7 @@ func (check *Checker) ident(x *operand, e *ast.Ident, def *TypeName, wantType bo
// avoid "declared but not used" errors
// (don't use Checker.use - we don't want to evaluate too much)
if v, _ := obj.(*Var); v != nil && v.pkg == check.pkg /* see Checker.use1 */ {
v.used = true
check.usedVars[v] = true
}
return
}
@@ -82,7 +82,7 @@ func (check *Checker) ident(x *operand, e *ast.Ident, def *TypeName, wantType bo
// (This code is only needed for dot-imports. Without them,
// we only have to mark variables, see *Var case below).
if pkgName := check.dotImportMap[dotImportKey{scope, obj.Name()}]; pkgName != nil {
pkgName.used = true
check.usedPkgNames[pkgName] = true
}
switch obj := obj.(type) {
@@ -119,7 +119,7 @@ func (check *Checker) ident(x *operand, e *ast.Ident, def *TypeName, wantType bo
// from other packages to avoid potential race conditions with
// dot-imported variables.
if obj.pkg == check.pkg {
obj.used = true
check.usedVars[obj] = true
}
check.addDeclDep(obj)
if !isValid(typ) {

View File

@@ -28,6 +28,7 @@ var All = []Info{
{Name: "asynctimerchan", Package: "time", Changed: 23, Old: "1"},
{Name: "dataindependenttiming", Package: "crypto/subtle", Opaque: true},
{Name: "execerrdot", Package: "os/exec"},
{Name: "fips140", Package: "crypto/fips140", Opaque: true},
{Name: "gocachehash", Package: "cmd/go"},
{Name: "gocachetest", Package: "cmd/go"},
{Name: "gocacheverify", Package: "cmd/go"},
@@ -58,8 +59,8 @@ var All = []Info{
{Name: "tlsmlkem", Package: "crypto/tls", Changed: 24, Old: "0", Opaque: true},
{Name: "tlsrsakex", Package: "crypto/tls", Changed: 22, Old: "1"},
{Name: "tlsunsafeekm", Package: "crypto/tls", Changed: 22, Old: "1"},
{Name: "winreadlinkvolume", Package: "os", Changed: 22, Old: "0"},
{Name: "winsymlink", Package: "os", Changed: 22, Old: "0"},
{Name: "winreadlinkvolume", Package: "os", Changed: 23, Old: "0"},
{Name: "winsymlink", Package: "os", Changed: 23, Old: "0"},
{Name: "x509keypairleaf", Package: "crypto/tls", Changed: 23, Old: "0"},
{Name: "x509negativeserial", Package: "crypto/x509", Changed: 23, Old: "1"},
{Name: "x509rsacrt", Package: "crypto/x509", Changed: 24, Old: "0"},

View File

@@ -17,7 +17,7 @@ import (
func runtime_mapaccess1_fast32(typ *abi.SwissMapType, m *Map, key uint32) unsafe.Pointer {
if race.Enabled && m != nil {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapaccess1)
pc := abi.FuncPCABIInternal(runtime_mapaccess1_fast32)
race.ReadPC(unsafe.Pointer(m), callerpc, pc)
}
@@ -86,7 +86,7 @@ func runtime_mapaccess1_fast32(typ *abi.SwissMapType, m *Map, key uint32) unsafe
func runtime_mapaccess2_fast32(typ *abi.SwissMapType, m *Map, key uint32) (unsafe.Pointer, bool) {
if race.Enabled && m != nil {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapaccess1)
pc := abi.FuncPCABIInternal(runtime_mapaccess2_fast32)
race.ReadPC(unsafe.Pointer(m), callerpc, pc)
}
@@ -198,7 +198,7 @@ func runtime_mapassign_fast32(typ *abi.SwissMapType, m *Map, key uint32) unsafe.
}
if race.Enabled {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapassign)
pc := abi.FuncPCABIInternal(runtime_mapassign_fast32)
race.WritePC(unsafe.Pointer(m), callerpc, pc)
}
if m.writing != 0 {
@@ -332,7 +332,7 @@ func runtime_mapassign_fast32ptr(typ *abi.SwissMapType, m *Map, key unsafe.Point
}
if race.Enabled {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapassign)
pc := abi.FuncPCABIInternal(runtime_mapassign_fast32ptr)
race.WritePC(unsafe.Pointer(m), callerpc, pc)
}
if m.writing != 0 {
@@ -458,7 +458,7 @@ outer:
func runtime_mapdelete_fast32(typ *abi.SwissMapType, m *Map, key uint32) {
if race.Enabled {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapassign)
pc := abi.FuncPCABIInternal(runtime_mapdelete_fast32)
race.WritePC(unsafe.Pointer(m), callerpc, pc)
}

View File

@@ -17,7 +17,7 @@ import (
func runtime_mapaccess1_fast64(typ *abi.SwissMapType, m *Map, key uint64) unsafe.Pointer {
if race.Enabled && m != nil {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapaccess1)
pc := abi.FuncPCABIInternal(runtime_mapaccess1_fast64)
race.ReadPC(unsafe.Pointer(m), callerpc, pc)
}
@@ -86,7 +86,7 @@ func runtime_mapaccess1_fast64(typ *abi.SwissMapType, m *Map, key uint64) unsafe
func runtime_mapaccess2_fast64(typ *abi.SwissMapType, m *Map, key uint64) (unsafe.Pointer, bool) {
if race.Enabled && m != nil {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapaccess1)
pc := abi.FuncPCABIInternal(runtime_mapaccess2_fast64)
race.ReadPC(unsafe.Pointer(m), callerpc, pc)
}
@@ -198,7 +198,7 @@ func runtime_mapassign_fast64(typ *abi.SwissMapType, m *Map, key uint64) unsafe.
}
if race.Enabled {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapassign)
pc := abi.FuncPCABIInternal(runtime_mapassign_fast64)
race.WritePC(unsafe.Pointer(m), callerpc, pc)
}
if m.writing != 0 {
@@ -370,7 +370,7 @@ func runtime_mapassign_fast64ptr(typ *abi.SwissMapType, m *Map, key unsafe.Point
}
if race.Enabled {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapassign)
pc := abi.FuncPCABIInternal(runtime_mapassign_fast64ptr)
race.WritePC(unsafe.Pointer(m), callerpc, pc)
}
if m.writing != 0 {
@@ -497,7 +497,7 @@ outer:
func runtime_mapdelete_fast64(typ *abi.SwissMapType, m *Map, key uint64) {
if race.Enabled {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapassign)
pc := abi.FuncPCABIInternal(runtime_mapdelete_fast64)
race.WritePC(unsafe.Pointer(m), callerpc, pc)
}

View File

@@ -103,7 +103,7 @@ func stringPtr(s string) unsafe.Pointer {
func runtime_mapaccess1_faststr(typ *abi.SwissMapType, m *Map, key string) unsafe.Pointer {
if race.Enabled && m != nil {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapaccess1)
pc := abi.FuncPCABIInternal(runtime_mapaccess1_faststr)
race.ReadPC(unsafe.Pointer(m), callerpc, pc)
}
@@ -162,7 +162,7 @@ func runtime_mapaccess1_faststr(typ *abi.SwissMapType, m *Map, key string) unsaf
func runtime_mapaccess2_faststr(typ *abi.SwissMapType, m *Map, key string) (unsafe.Pointer, bool) {
if race.Enabled && m != nil {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapaccess1)
pc := abi.FuncPCABIInternal(runtime_mapaccess2_faststr)
race.ReadPC(unsafe.Pointer(m), callerpc, pc)
}
@@ -266,7 +266,7 @@ func runtime_mapassign_faststr(typ *abi.SwissMapType, m *Map, key string) unsafe
}
if race.Enabled {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapassign)
pc := abi.FuncPCABIInternal(runtime_mapassign_faststr)
race.WritePC(unsafe.Pointer(m), callerpc, pc)
}
if m.writing != 0 {
@@ -396,7 +396,7 @@ outer:
func runtime_mapdelete_faststr(typ *abi.SwissMapType, m *Map, key string) {
if race.Enabled {
callerpc := sys.GetCallerPC()
pc := abi.FuncPCABIInternal(runtime_mapassign)
pc := abi.FuncPCABIInternal(runtime_mapdelete_faststr)
race.WritePC(unsafe.Pointer(m), callerpc, pc)
}

View File

@@ -504,3 +504,26 @@ func ParallelOn64Bit(t *testing.T) {
}
t.Parallel()
}
// CPUProfilingBroken returns true if CPU profiling has known issues on this
// platform.
func CPUProfilingBroken() bool {
switch runtime.GOOS {
case "plan9":
// Profiling unimplemented.
return true
case "aix":
// See https://golang.org/issue/45170.
return true
case "ios", "dragonfly", "netbsd", "illumos", "solaris":
// See https://golang.org/issue/13841.
return true
case "openbsd":
if runtime.GOARCH == "arm" || runtime.GOARCH == "arm64" {
// See https://golang.org/issue/13841.
return true
}
}
return false
}

View File

@@ -164,6 +164,19 @@ func readChunkLine(b *bufio.Reader) ([]byte, error) {
}
return nil, err
}
// RFC 9112 permits parsers to accept a bare \n as a line ending in headers,
// but not in chunked encoding lines. See https://www.rfc-editor.org/errata/eid7633,
// which explicitly rejects a clarification permitting \n as a chunk terminator.
//
// Verify that the line ends in a CRLF, and that no CRs appear before the end.
if idx := bytes.IndexByte(p, '\r'); idx == -1 {
return nil, errors.New("chunked line ends with bare LF")
} else if idx != len(p)-2 {
return nil, errors.New("invalid CR in chunked line")
}
p = p[:len(p)-2] // trim CRLF
if len(p) >= maxLineLength {
return nil, ErrLineTooLong
}
@@ -171,14 +184,14 @@ func readChunkLine(b *bufio.Reader) ([]byte, error) {
}
func trimTrailingWhitespace(b []byte) []byte {
for len(b) > 0 && isASCIISpace(b[len(b)-1]) {
for len(b) > 0 && isOWS(b[len(b)-1]) {
b = b[:len(b)-1]
}
return b
}
func isASCIISpace(b byte) bool {
return b == ' ' || b == '\t' || b == '\n' || b == '\r'
func isOWS(b byte) bool {
return b == ' ' || b == '\t'
}
var semi = []byte(";")

View File

@@ -280,6 +280,33 @@ func TestChunkReaderByteAtATime(t *testing.T) {
}
}
func TestChunkInvalidInputs(t *testing.T) {
for _, test := range []struct {
name string
b string
}{{
name: "bare LF in chunk size",
b: "1\na\r\n0\r\n",
}, {
name: "extra LF in chunk size",
b: "1\r\r\na\r\n0\r\n",
}, {
name: "bare LF in chunk data",
b: "1\r\na\n0\r\n",
}, {
name: "bare LF in chunk extension",
b: "1;\na\r\n0\r\n",
}} {
t.Run(test.name, func(t *testing.T) {
r := NewChunkedReader(strings.NewReader(test.b))
got, err := io.ReadAll(r)
if err == nil {
t.Fatalf("unexpectedly parsed invalid chunked data:\n%q", got)
}
})
}
}
type funcReader struct {
f func(iteration int) ([]byte, error)
i int

View File

@@ -13,6 +13,7 @@ import (
"compress/zlib"
"context"
"crypto/tls"
"crypto/x509"
"encoding/json"
"errors"
"fmt"
@@ -7303,3 +7304,120 @@ func testServerReadAfterHandlerAbort100Continue(t *testing.T, mode testMode) {
readyc <- struct{}{} // server starts reading from the request body
readyc <- struct{}{} // server finishes reading from the request body
}
// Issue #72100: Verify that we don't modify the caller's TLS.Config.NextProtos slice.
func TestServerTLSNextProtos(t *testing.T) {
run(t, testServerTLSNextProtos, []testMode{https1Mode, http2Mode})
}
func testServerTLSNextProtos(t *testing.T, mode testMode) {
CondSkipHTTP2(t)
cert, err := tls.X509KeyPair(testcert.LocalhostCert, testcert.LocalhostKey)
if err != nil {
t.Fatal(err)
}
leafCert, err := x509.ParseCertificate(cert.Certificate[0])
if err != nil {
t.Fatal(err)
}
certpool := x509.NewCertPool()
certpool.AddCert(leafCert)
protos := new(Protocols)
switch mode {
case https1Mode:
protos.SetHTTP1(true)
case http2Mode:
protos.SetHTTP2(true)
}
wantNextProtos := []string{"http/1.1", "h2", "other"}
nextProtos := slices.Clone(wantNextProtos)
// We don't use httptest here because it overrides the tls.Config.
srv := &Server{
TLSConfig: &tls.Config{
Certificates: []tls.Certificate{cert},
NextProtos: nextProtos,
},
Handler: HandlerFunc(func(w ResponseWriter, req *Request) {}),
Protocols: protos,
}
tr := &Transport{
TLSClientConfig: &tls.Config{
RootCAs: certpool,
NextProtos: nextProtos,
},
Protocols: protos,
}
listener := newLocalListener(t)
srvc := make(chan error, 1)
go func() {
srvc <- srv.ServeTLS(listener, "", "")
}()
t.Cleanup(func() {
srv.Close()
<-srvc
})
client := &Client{Transport: tr}
resp, err := client.Get("https://" + listener.Addr().String())
if err != nil {
t.Fatal(err)
}
resp.Body.Close()
if !slices.Equal(nextProtos, wantNextProtos) {
t.Fatalf("after running test: original NextProtos slice = %v, want %v", nextProtos, wantNextProtos)
}
}
func TestInvalidChunkedBodies(t *testing.T) {
for _, test := range []struct {
name string
b string
}{{
name: "bare LF in chunk size",
b: "1\na\r\n0\r\n\r\n",
}, {
name: "bare LF at body end",
b: "1\r\na\r\n0\r\n\n",
}} {
t.Run(test.name, func(t *testing.T) {
reqc := make(chan error)
ts := newClientServerTest(t, http1Mode, HandlerFunc(func(w ResponseWriter, r *Request) {
got, err := io.ReadAll(r.Body)
if err == nil {
t.Logf("read body: %q", got)
}
reqc <- err
})).ts
serverURL, err := url.Parse(ts.URL)
if err != nil {
t.Fatal(err)
}
conn, err := net.Dial("tcp", serverURL.Host)
if err != nil {
t.Fatal(err)
}
if _, err := conn.Write([]byte(
"POST / HTTP/1.1\r\n" +
"Host: localhost\r\n" +
"Transfer-Encoding: chunked\r\n" +
"Connection: close\r\n" +
"\r\n" +
test.b)); err != nil {
t.Fatal(err)
}
conn.(*net.TCPConn).CloseWrite()
if err := <-reqc; err == nil {
t.Errorf("server handler: io.ReadAll(r.Body) succeeded, want error")
}
})
}
}

View File

@@ -3521,6 +3521,12 @@ func (s *Server) protocols() Protocols {
// adjustNextProtos adds or removes "http/1.1" and "h2" entries from
// a tls.Config.NextProtos list, according to the set of protocols in protos.
func adjustNextProtos(nextProtos []string, protos Protocols) []string {
// Make a copy of NextProtos since it might be shared with some other tls.Config.
// (tls.Config.Clone doesn't do a deep copy.)
//
// We could avoid an allocation in the common case by checking to see if the slice
// is already in order, but this is just one small allocation per connection.
nextProtos = slices.Clone(nextProtos)
var have Protocols
nextProtos = slices.DeleteFunc(nextProtos, func(s string) bool {
switch s {

View File

@@ -11,12 +11,15 @@ import (
"internal/testenv"
"io"
"os"
"os/exec"
"os/signal"
"os/user"
"path/filepath"
"runtime"
"slices"
"strconv"
"strings"
"sync"
"syscall"
"testing"
"time"
@@ -24,6 +27,7 @@ import (
func init() {
registerHelperCommand("pwd", cmdPwd)
registerHelperCommand("signaltest", cmdSignalTest)
}
func cmdPwd(...string) {
@@ -274,3 +278,55 @@ func TestExplicitPWD(t *testing.T) {
})
}
}
// Issue 71828.
func TestSIGCHLD(t *testing.T) {
cmd := helperCommand(t, "signaltest")
out, err := cmd.CombinedOutput()
t.Logf("%s", out)
if err != nil {
t.Error(err)
}
}
// cmdSignaltest is for TestSIGCHLD.
// This runs in a separate process because the bug only happened
// the first time that a child process was started.
func cmdSignalTest(...string) {
chSig := make(chan os.Signal, 1)
signal.Notify(chSig, syscall.SIGCHLD)
var wg sync.WaitGroup
wg.Add(1)
go func() {
defer wg.Done()
c := 0
for range chSig {
c++
fmt.Printf("SIGCHLD %d\n", c)
if c > 1 {
fmt.Println("too many SIGCHLD signals")
os.Exit(1)
}
}
}()
defer func() {
signal.Reset(syscall.SIGCHLD)
close(chSig)
wg.Wait()
}()
exe, err := os.Executable()
if err != nil {
fmt.Printf("os.Executable failed: %v\n", err)
os.Exit(1)
}
cmd := exec.Command(exe, "hang", "200ms")
cmd.Stdout = os.Stdout
cmd.Stderr = os.Stderr
if err := cmd.Run(); err != nil {
fmt.Printf("failed to run child process: %v\n", err)
os.Exit(1)
}
}

View File

@@ -3848,3 +3848,14 @@ func TestRemoveReadOnlyFile(t *testing.T) {
}
})
}
func TestOpenFileDevNull(t *testing.T) {
// See https://go.dev/issue/71752.
t.Parallel()
f, err := OpenFile(DevNull, O_WRONLY|O_CREATE|O_TRUNC, 0o644)
if err != nil {
t.Fatalf("OpenFile(DevNull): %v", err)
}
f.Close()
}

View File

@@ -60,7 +60,7 @@ func OpenInRoot(dir, name string) (*File, error) {
// - When GOOS=plan9 or GOOS=js, Root does not track directories across renames.
// On these platforms, a Root references a directory name, not a file descriptor.
type Root struct {
root root
root *root
}
const (
@@ -186,20 +186,20 @@ func (r *Root) logStat(name string) {
//
// "." components are removed, except in the last component.
//
// Path separators following the last component are preserved.
func splitPathInRoot(s string, prefix, suffix []string) (_ []string, err error) {
// Path separators following the last component are returned in suffixSep.
func splitPathInRoot(s string, prefix, suffix []string) (_ []string, suffixSep string, err error) {
if len(s) == 0 {
return nil, errors.New("empty path")
return nil, "", errors.New("empty path")
}
if IsPathSeparator(s[0]) {
return nil, errPathEscapes
return nil, "", errPathEscapes
}
if runtime.GOOS == "windows" {
// Windows cleans paths before opening them.
s, err = rootCleanPath(s, prefix, suffix)
if err != nil {
return nil, err
return nil, "", err
}
prefix = nil
suffix = nil
@@ -215,13 +215,14 @@ func splitPathInRoot(s string, prefix, suffix []string) (_ []string, err error)
}
parts = append(parts, s[i:j])
// Advance to the next component, or end of the path.
partEnd := j
for j < len(s) && IsPathSeparator(s[j]) {
j++
}
if j == len(s) {
// If this is the last path component,
// preserve any trailing path separators.
parts[len(parts)-1] = s[i:]
suffixSep = s[partEnd:]
break
}
if parts[len(parts)-1] == "." {
@@ -235,7 +236,7 @@ func splitPathInRoot(s string, prefix, suffix []string) (_ []string, err error)
parts = parts[:len(parts)-1]
}
parts = append(parts, suffix...)
return parts, nil
return parts, suffixSep, nil
}
// FS returns a file system (an fs.FS) for the tree of files in the root.

View File

@@ -33,7 +33,7 @@ func checkPathEscapesInternal(r *Root, name string, lstat bool) error {
if r.root.closed.Load() {
return ErrClosed
}
parts, err := splitPathInRoot(name, nil, nil)
parts, suffixSep, err := splitPathInRoot(name, nil, nil)
if err != nil {
return err
}
@@ -61,11 +61,15 @@ func checkPathEscapesInternal(r *Root, name string, lstat bool) error {
continue
}
if lstat && i == len(parts)-1 {
break
part := parts[i]
if i == len(parts)-1 {
if lstat {
break
}
part += suffixSep
}
next := joinPath(base, parts[i])
next := joinPath(base, part)
fi, err := Lstat(next)
if err != nil {
if IsNotExist(err) {
@@ -82,10 +86,19 @@ func checkPathEscapesInternal(r *Root, name string, lstat bool) error {
if symlinks > rootMaxSymlinks {
return errors.New("too many symlinks")
}
newparts, err := splitPathInRoot(link, parts[:i], parts[i+1:])
newparts, newSuffixSep, err := splitPathInRoot(link, parts[:i], parts[i+1:])
if err != nil {
return err
}
if i == len(parts) {
// suffixSep contains any trailing path separator characters
// in the link target.
// If we are replacing the remainder of the path, retain these.
// If we're replacing some intermediate component of the path,
// ignore them, since intermediate components must always be
// directories.
suffixSep = newSuffixSep
}
parts = newparts
continue
}

View File

@@ -49,7 +49,7 @@ func newRoot(name string) (*Root, error) {
if !fi.IsDir() {
return nil, errors.New("not a directory")
}
return &Root{root{name: name}}, nil
return &Root{&root{name: name}}, nil
}
func (r *root) Close() error {

View File

@@ -98,7 +98,7 @@ func doInRoot[T any](r *Root, name string, f func(parent sysfdType, name string)
}
defer r.root.decref()
parts, err := splitPathInRoot(name, nil, nil)
parts, suffixSep, err := splitPathInRoot(name, nil, nil)
if err != nil {
return ret, err
}
@@ -146,6 +146,9 @@ func doInRoot[T any](r *Root, name string, f func(parent sysfdType, name string)
return ret, errPathEscapes
}
parts = slices.Delete(parts, i-count, end)
if len(parts) == 0 {
parts = []string{"."}
}
i = 0
if dirfd != rootfd {
syscall.Close(dirfd)
@@ -159,7 +162,9 @@ func doInRoot[T any](r *Root, name string, f func(parent sysfdType, name string)
// Call f to decide what to do with it.
// If f returns errSymlink, this element is a symlink
// which should be followed.
ret, err = f(dirfd, parts[i])
// suffixSep contains any trailing separator characters
// which we rejoin to the final part at this time.
ret, err = f(dirfd, parts[i]+suffixSep)
if _, ok := err.(errSymlink); !ok {
return ret, err
}
@@ -181,10 +186,19 @@ func doInRoot[T any](r *Root, name string, f func(parent sysfdType, name string)
if symlinks > rootMaxSymlinks {
return ret, syscall.ELOOP
}
newparts, err := splitPathInRoot(string(e), parts[:i], parts[i+1:])
newparts, newSuffixSep, err := splitPathInRoot(string(e), parts[:i], parts[i+1:])
if err != nil {
return ret, err
}
if i == len(parts)-1 {
// suffixSep contains any trailing path separator characters
// in the link target.
// If we are replacing the remainder of the path, retain these.
// If we're replacing some intermediate component of the path,
// ignore them, since intermediate components must always be
// directories.
suffixSep = newSuffixSep
}
if len(newparts) < i || !slices.Equal(parts[:i], newparts[:i]) {
// Some component in the path which we have already traversed
// has changed. We need to restart parsing from the root.

View File

@@ -186,6 +186,30 @@ var rootTestCases = []rootTest{{
open: "link",
target: "target",
ltarget: "link",
}, {
name: "symlink dotdot slash",
fs: []string{
"link => ../",
},
open: "link",
ltarget: "link",
wantError: true,
}, {
name: "symlink ending in slash",
fs: []string{
"dir/",
"link => dir/",
},
open: "link/target",
target: "dir/target",
}, {
name: "symlink dotdot dotdot slash",
fs: []string{
"dir/link => ../../",
},
open: "dir/link",
ltarget: "dir/link",
wantError: true,
}, {
name: "symlink chain",
fs: []string{
@@ -213,6 +237,16 @@ var rootTestCases = []rootTest{{
},
open: "a/../a/b/../../a/b/../b/target",
target: "a/b/target",
}, {
name: "path with dotdot slash",
fs: []string{},
open: "../",
wantError: true,
}, {
name: "path with dotdot dotdot slash",
fs: []string{},
open: "a/../../",
wantError: true,
}, {
name: "dotdot no symlink",
fs: []string{
@@ -1176,6 +1210,33 @@ func TestRootRaceRenameDir(t *testing.T) {
}
}
func TestRootSymlinkToRoot(t *testing.T) {
dir := makefs(t, []string{
"d/d => ..",
})
root, err := os.OpenRoot(dir)
if err != nil {
t.Fatal(err)
}
defer root.Close()
if err := root.Mkdir("d/d/new", 0777); err != nil {
t.Fatal(err)
}
f, err := root.Open("d/d")
if err != nil {
t.Fatal(err)
}
defer f.Close()
names, err := f.Readdirnames(-1)
if err != nil {
t.Fatal(err)
}
slices.Sort(names)
if got, want := names, []string{"d", "new"}; !slices.Equal(got, want) {
t.Errorf("root contains: %q, want %q", got, want)
}
}
func TestOpenInRoot(t *testing.T) {
dir := makefs(t, []string{
"file",

View File

@@ -48,11 +48,11 @@ func newRoot(fd int, name string) (*Root, error) {
syscall.CloseOnExec(fd)
}
r := &Root{root{
r := &Root{&root{
fd: fd,
name: name,
}}
runtime.SetFinalizer(&r.root, (*root).Close)
runtime.SetFinalizer(r.root, (*root).Close)
return r, nil
}

View File

@@ -105,11 +105,11 @@ func newRoot(fd syscall.Handle, name string) (*Root, error) {
return nil, &PathError{Op: "open", Path: name, Err: errors.New("not a directory")}
}
r := &Root{root{
r := &Root{&root{
fd: fd,
name: name,
}}
runtime.SetFinalizer(&r.root, (*root).Close)
runtime.SetFinalizer(r.root, (*root).Close)
return r, nil
}

View File

@@ -4,15 +4,24 @@
package reflect
import "iter"
import (
"iter"
)
func rangeNum[T int8 | int16 | int32 | int64 | int |
uint8 | uint16 | uint32 | uint64 | uint |
uintptr, N int64 | uint64](v N) iter.Seq[Value] {
uintptr, N int64 | uint64](num N, t Type) iter.Seq[Value] {
return func(yield func(v Value) bool) {
convert := t.PkgPath() != ""
// cannot use range T(v) because no core type.
for i := T(0); i < T(v); i++ {
if !yield(ValueOf(i)) {
for i := T(0); i < T(num); i++ {
tmp := ValueOf(i)
// if the iteration value type is define by
// type T built-in type.
if convert {
tmp = tmp.Convert(t)
}
if !yield(tmp) {
return
}
}
@@ -27,7 +36,7 @@ func rangeNum[T int8 | int16 | int32 | int64 | int |
// Uint, Uint8, Uint16, Uint32, Uint64, Uintptr,
// Array, Chan, Map, Slice, or String.
func (v Value) Seq() iter.Seq[Value] {
if canRangeFunc(v.typ()) {
if canRangeFunc(v.abiType()) {
return func(yield func(Value) bool) {
rf := MakeFunc(v.Type().In(0), func(in []Value) []Value {
return []Value{ValueOf(yield(in[0]))}
@@ -35,29 +44,29 @@ func (v Value) Seq() iter.Seq[Value] {
v.Call([]Value{rf})
}
}
switch v.Kind() {
switch v.kind() {
case Int:
return rangeNum[int](v.Int())
return rangeNum[int](v.Int(), v.Type())
case Int8:
return rangeNum[int8](v.Int())
return rangeNum[int8](v.Int(), v.Type())
case Int16:
return rangeNum[int16](v.Int())
return rangeNum[int16](v.Int(), v.Type())
case Int32:
return rangeNum[int32](v.Int())
return rangeNum[int32](v.Int(), v.Type())
case Int64:
return rangeNum[int64](v.Int())
return rangeNum[int64](v.Int(), v.Type())
case Uint:
return rangeNum[uint](v.Uint())
return rangeNum[uint](v.Uint(), v.Type())
case Uint8:
return rangeNum[uint8](v.Uint())
return rangeNum[uint8](v.Uint(), v.Type())
case Uint16:
return rangeNum[uint16](v.Uint())
return rangeNum[uint16](v.Uint(), v.Type())
case Uint32:
return rangeNum[uint32](v.Uint())
return rangeNum[uint32](v.Uint(), v.Type())
case Uint64:
return rangeNum[uint64](v.Uint())
return rangeNum[uint64](v.Uint(), v.Type())
case Uintptr:
return rangeNum[uintptr](v.Uint())
return rangeNum[uintptr](v.Uint(), v.Type())
case Pointer:
if v.Elem().kind() != Array {
break
@@ -113,7 +122,7 @@ func (v Value) Seq() iter.Seq[Value] {
// If v's kind is Pointer, the pointer element type must have kind Array.
// Otherwise v's kind must be Array, Map, Slice, or String.
func (v Value) Seq2() iter.Seq2[Value, Value] {
if canRangeFunc2(v.typ()) {
if canRangeFunc2(v.abiType()) {
return func(yield func(Value, Value) bool) {
rf := MakeFunc(v.Type().In(0), func(in []Value) []Value {
return []Value{ValueOf(yield(in[0], in[1]))}

View File

@@ -7,10 +7,13 @@ package reflect_test
import (
"iter"
"maps"
"reflect"
. "reflect"
"testing"
)
type N int8
func TestValueSeq(t *testing.T) {
m := map[string]int{
"1": 1,
@@ -173,6 +176,33 @@ func TestValueSeq(t *testing.T) {
t.Fatalf("should loop four times")
}
}},
{"method", ValueOf(methodIter{}).Method(0), func(t *testing.T, s iter.Seq[Value]) {
i := int64(0)
for v := range s {
if v.Int() != i {
t.Fatalf("got %d, want %d", v.Int(), i)
}
i++
}
if i != 4 {
t.Fatalf("should loop four times")
}
}},
{"type N int8", ValueOf(N(4)), func(t *testing.T, s iter.Seq[Value]) {
i := N(0)
for v := range s {
if v.Int() != int64(i) {
t.Fatalf("got %d, want %d", v.Int(), i)
}
i++
if v.Type() != reflect.TypeOf(i) {
t.Fatalf("got %s, want %s", v.Type(), reflect.TypeOf(i))
}
}
if i != 4 {
t.Fatalf("should loop four times")
}
}},
}
for _, tc := range tests {
seq := tc.val.Seq()
@@ -293,9 +323,84 @@ func TestValueSeq2(t *testing.T) {
t.Fatalf("should loop four times")
}
}},
{"method", ValueOf(methodIter2{}).Method(0), func(t *testing.T, s iter.Seq2[Value, Value]) {
i := int64(0)
for v1, v2 := range s {
if v1.Int() != i {
t.Fatalf("got %d, want %d", v1.Int(), i)
}
i++
if v2.Int() != i {
t.Fatalf("got %d, want %d", v2.Int(), i)
}
}
if i != 4 {
t.Fatalf("should loop four times")
}
}},
{"[4]N", ValueOf([4]N{0, 1, 2, 3}), func(t *testing.T, s iter.Seq2[Value, Value]) {
i := N(0)
for v1, v2 := range s {
if v1.Int() != int64(i) {
t.Fatalf("got %d, want %d", v1.Int(), i)
}
if v2.Int() != int64(i) {
t.Fatalf("got %d, want %d", v2.Int(), i)
}
i++
if v2.Type() != reflect.TypeOf(i) {
t.Fatalf("got %s, want %s", v2.Type(), reflect.TypeOf(i))
}
}
if i != 4 {
t.Fatalf("should loop four times")
}
}},
{"[]N", ValueOf([]N{1, 2, 3, 4}), func(t *testing.T, s iter.Seq2[Value, Value]) {
i := N(0)
for v1, v2 := range s {
if v1.Int() != int64(i) {
t.Fatalf("got %d, want %d", v1.Int(), i)
}
i++
if v2.Int() != int64(i) {
t.Fatalf("got %d, want %d", v2.Int(), i)
}
if v2.Type() != reflect.TypeOf(i) {
t.Fatalf("got %s, want %s", v2.Type(), reflect.TypeOf(i))
}
}
if i != 4 {
t.Fatalf("should loop four times")
}
}},
}
for _, tc := range tests {
seq := tc.val.Seq2()
tc.check(t, seq)
}
}
// methodIter is a type from which we can derive a method
// value that is an iter.Seq.
type methodIter struct{}
func (methodIter) Seq(yield func(int) bool) {
for i := range 4 {
if !yield(i) {
return
}
}
}
// methodIter2 is a type from which we can derive a method
// value that is an iter.Seq2.
type methodIter2 struct{}
func (methodIter2) Seq2(yield func(int, int) bool) {
for i := range 4 {
if !yield(i, i+1) {
return
}
}
}

View File

@@ -93,6 +93,9 @@ func (f flag) ro() flag {
return 0
}
// typ returns the *abi.Type stored in the Value. This method is fast,
// but it doesn't always return the correct type for the Value.
// See abiType and Type, which do return the correct type.
func (v Value) typ() *abi.Type {
// Types are either static (for compiler-created types) or
// heap-allocated but always reachable (for reflection-created
@@ -2380,14 +2383,26 @@ func (v Value) Type() Type {
return v.typeSlow()
}
//go:noinline
func (v Value) typeSlow() Type {
return toRType(v.abiTypeSlow())
}
func (v Value) abiType() *abi.Type {
if v.flag != 0 && v.flag&flagMethod == 0 {
return v.typ()
}
return v.abiTypeSlow()
}
func (v Value) abiTypeSlow() *abi.Type {
if v.flag == 0 {
panic(&ValueError{"reflect.Value.Type", Invalid})
}
typ := v.typ()
if v.flag&flagMethod == 0 {
return toRType(v.typ())
return v.typ()
}
// Method value.
@@ -2400,7 +2415,7 @@ func (v Value) typeSlow() Type {
panic("reflect: internal error: invalid method index")
}
m := &tt.Methods[i]
return toRType(typeOffFor(typ, m.Typ))
return typeOffFor(typ, m.Typ)
}
// Method on concrete type.
ms := typ.ExportedMethods()
@@ -2408,7 +2423,7 @@ func (v Value) typeSlow() Type {
panic("reflect: internal error: invalid method index")
}
m := ms[i]
return toRType(typeOffFor(typ, m.Mtyp))
return typeOffFor(typ, m.Mtyp)
}
// CanUint reports whether [Value.Uint] can be used without panicking.

View File

@@ -25,7 +25,8 @@ package cgo
// Use -fno-stack-protector to avoid problems locating the
// proper support functions. See issues #52919, #54313, #58385.
#cgo CFLAGS: -Wall -Werror -fno-stack-protector
// Use -Wdeclaration-after-statement because some CI builds use it.
#cgo CFLAGS: -Wall -Werror -fno-stack-protector -Wdeclaration-after-statement
#cgo solaris CPPFLAGS: -D_POSIX_PTHREAD_SEMANTICS

View File

@@ -76,19 +76,27 @@ threadentry(void *v)
static void
init_working_dir()
{
CFBundleRef bundle = CFBundleGetMainBundle();
CFBundleRef bundle;
CFURLRef url_ref;
CFStringRef url_str_ref;
char buf[MAXPATHLEN];
Boolean res;
int url_len;
char *dir;
CFStringRef wd_ref;
bundle = CFBundleGetMainBundle();
if (bundle == NULL) {
fprintf(stderr, "runtime/cgo: no main bundle\n");
return;
}
CFURLRef url_ref = CFBundleCopyResourceURL(bundle, CFSTR("Info"), CFSTR("plist"), NULL);
url_ref = CFBundleCopyResourceURL(bundle, CFSTR("Info"), CFSTR("plist"), NULL);
if (url_ref == NULL) {
// No Info.plist found. It can happen on Corellium virtual devices.
return;
}
CFStringRef url_str_ref = CFURLGetString(url_ref);
char buf[MAXPATHLEN];
Boolean res = CFStringGetCString(url_str_ref, buf, sizeof(buf), kCFStringEncodingUTF8);
url_str_ref = CFURLGetString(url_ref);
res = CFStringGetCString(url_str_ref, buf, sizeof(buf), kCFStringEncodingUTF8);
CFRelease(url_ref);
if (!res) {
fprintf(stderr, "runtime/cgo: cannot get URL string\n");
@@ -97,13 +105,13 @@ init_working_dir()
// url is of the form "file:///path/to/Info.plist".
// strip it down to the working directory "/path/to".
int url_len = strlen(buf);
url_len = strlen(buf);
if (url_len < sizeof("file://")+sizeof("/Info.plist")) {
fprintf(stderr, "runtime/cgo: bad URL: %s\n", buf);
return;
}
buf[url_len-sizeof("/Info.plist")+1] = 0;
char *dir = &buf[0] + sizeof("file://")-1;
dir = &buf[0] + sizeof("file://")-1;
if (chdir(dir) != 0) {
fprintf(stderr, "runtime/cgo: chdir(%s) failed\n", dir);
@@ -111,7 +119,7 @@ init_working_dir()
// The test harness in go_ios_exec passes the relative working directory
// in the GoExecWrapperWorkingDirectory property of the app bundle.
CFStringRef wd_ref = CFBundleGetValueForInfoDictionaryKey(bundle, CFSTR("GoExecWrapperWorkingDirectory"));
wd_ref = CFBundleGetValueForInfoDictionaryKey(bundle, CFSTR("GoExecWrapperWorkingDirectory"));
if (wd_ref != NULL) {
if (!CFStringGetCString(wd_ref, buf, sizeof(buf), kCFStringEncodingUTF8)) {
fprintf(stderr, "runtime/cgo: cannot get GoExecWrapperWorkingDirectory string\n");

View File

@@ -39,10 +39,11 @@ void
x_cgo_sys_thread_create(void* (*func)(void*), void* arg) {
pthread_attr_t attr;
pthread_t p;
int err;
pthread_attr_init(&attr);
pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
int err = _cgo_try_pthread_create(&p, &attr, func, arg);
err = _cgo_try_pthread_create(&p, &attr, func, arg);
if (err != 0) {
fprintf(stderr, "pthread_create failed: %s", strerror(err));
abort();
@@ -52,9 +53,11 @@ x_cgo_sys_thread_create(void* (*func)(void*), void* arg) {
uintptr_t
_cgo_wait_runtime_init_done(void) {
void (*pfn)(struct context_arg*);
int done;
pfn = __atomic_load_n(&cgo_context_function, __ATOMIC_CONSUME);
int done = 2;
done = 2;
if (__atomic_load_n(&runtime_init_done, __ATOMIC_CONSUME) != done) {
pthread_mutex_lock(&runtime_init_mu);
while (__atomic_load_n(&runtime_init_done, __ATOMIC_CONSUME) == 0) {

View File

@@ -75,8 +75,10 @@ x_cgo_sys_thread_create(void (*func)(void*), void* arg) {
int
_cgo_is_runtime_initialized() {
int status;
EnterCriticalSection(&runtime_init_cs);
int status = runtime_init_done;
status = runtime_init_done;
LeaveCriticalSection(&runtime_init_cs);
return status;
}

View File

@@ -355,7 +355,9 @@ func cgocallbackg(fn, frame unsafe.Pointer, ctxt uintptr) {
gp.m.incgo = true
unlockOSThread()
if gp.m.isextra {
if gp.m.isextra && gp.m.ncgo == 0 {
// There are no active cgocalls above this frame (ncgo == 0),
// thus there can't be more Go frames above this frame.
gp.m.isExtraInC = true
}

View File

@@ -72,6 +72,22 @@ func TestCgoCallbackGC(t *testing.T) {
}
}
func TestCgoCallbackPprof(t *testing.T) {
t.Parallel()
switch runtime.GOOS {
case "plan9", "windows":
t.Skipf("no pthreads on %s", runtime.GOOS)
}
if testenv.CPUProfilingBroken() {
t.Skip("skipping on platform with broken profiling")
}
got := runTestProg(t, "testprogcgo", "CgoCallbackPprof")
if want := "OK\n"; got != want {
t.Fatalf("expected %q, but got:\n%s", want, got)
}
}
func TestCgoExternalThreadPanic(t *testing.T) {
t.Parallel()
if runtime.GOOS == "plan9" {

View File

@@ -6,6 +6,7 @@ package runtime_test
import (
"fmt"
"os"
"runtime"
"strings"
)
@@ -59,3 +60,36 @@ func ExampleFrames() {
// - more:true | runtime_test.ExampleFrames.func3
// - more:true | runtime_test.ExampleFrames
}
func ExampleAddCleanup() {
tempFile, err := os.CreateTemp(os.TempDir(), "file.*")
if err != nil {
fmt.Println("failed to create temp file:", err)
return
}
ch := make(chan struct{})
// Attach a cleanup function to the file object.
runtime.AddCleanup(&tempFile, func(fileName string) {
if err := os.Remove(fileName); err == nil {
fmt.Println("temp file has been removed")
}
ch <- struct{}{}
}, tempFile.Name())
if err := tempFile.Close(); err != nil {
fmt.Println("failed to close temp file:", err)
return
}
// Run the garbage collector to reclaim unreachable objects
// and enqueue their cleanup functions.
runtime.GC()
// Wait until cleanup function is done.
<-ch
// Output:
// temp file has been removed
}

View File

@@ -30,8 +30,10 @@ import (
// unreachable at the same time, their cleanups all become eligible to run
// and can run in any order. This is true even if the objects form a cycle.
//
// A single goroutine runs all cleanup calls for a program, sequentially. If a
// cleanup function must run for a long time, it should create a new goroutine.
// Cleanups run concurrently with any user-created goroutines.
// Cleanups may also run concurrently with one another (unlike finalizers).
// If a cleanup function must run for a long time, it should create a new goroutine
// to avoid blocking the execution of other cleanups.
//
// If ptr has both a cleanup and a finalizer, the cleanup will only run once
// it has been finalized and becomes unreachable without an associated finalizer.

View File

@@ -234,8 +234,11 @@ func unminit() {
getg().m.procid = 0
}
// Called from exitm, but not from drop, to undo the effect of thread-owned
// Called from mexit, but not from dropm, to undo the effect of thread-owned
// resources in minit, semacreate, or elsewhere. Do not take locks after calling this.
//
// This always runs without a P, so //go:nowritebarrierrec is required.
//go:nowritebarrierrec
func mdestroy(mp *m) {
}

View File

@@ -186,8 +186,11 @@ func unminit() {
getg().m.procid = 0
}
// Called from exitm, but not from drop, to undo the effect of thread-owned
// Called from mexit, but not from dropm, to undo the effect of thread-owned
// resources in minit, semacreate, or elsewhere. Do not take locks after calling this.
//
// This always runs without a P, so //go:nowritebarrierrec is required.
//go:nowritebarrierrec
func mdestroy(mp *m) {
}

View File

@@ -344,8 +344,11 @@ func unminit() {
getg().m.procid = 0
}
// Called from exitm, but not from drop, to undo the effect of thread-owned
// Called from mexit, but not from dropm, to undo the effect of thread-owned
// resources in minit, semacreate, or elsewhere. Do not take locks after calling this.
//
// This always runs without a P, so //go:nowritebarrierrec is required.
//go:nowritebarrierrec
func mdestroy(mp *m) {
}

View File

@@ -216,8 +216,11 @@ func unminit() {
getg().m.procid = 0
}
// Called from exitm, but not from drop, to undo the effect of thread-owned
// Called from mexit, but not from dropm, to undo the effect of thread-owned
// resources in minit, semacreate, or elsewhere. Do not take locks after calling this.
//
// This always runs without a P, so //go:nowritebarrierrec is required.
//go:nowritebarrierrec
func mdestroy(mp *m) {
}

View File

@@ -412,13 +412,12 @@ func unminit() {
getg().m.procid = 0
}
// Called from exitm, but not from drop, to undo the effect of thread-owned
// Called from mexit, but not from dropm, to undo the effect of thread-owned
// resources in minit, semacreate, or elsewhere. Do not take locks after calling this.
//
// This always runs without a P, so //go:nowritebarrierrec is required.
//go:nowritebarrierrec
func mdestroy(mp *m) {
if mp.vgetrandomState != 0 {
vgetrandomPutState(mp.vgetrandomState)
mp.vgetrandomState = 0
}
}
// #ifdef GOARCH_386

View File

@@ -320,8 +320,11 @@ func unminit() {
// must continue working after unminit.
}
// Called from exitm, but not from drop, to undo the effect of thread-owned
// Called from mexit, but not from dropm, to undo the effect of thread-owned
// resources in minit, semacreate, or elsewhere. Do not take locks after calling this.
//
// This always runs without a P, so //go:nowritebarrierrec is required.
//go:nowritebarrierrec
func mdestroy(mp *m) {
}

View File

@@ -182,8 +182,11 @@ func unminit() {
getg().m.procid = 0
}
// Called from exitm, but not from drop, to undo the effect of thread-owned
// Called from mexit, but not from dropm, to undo the effect of thread-owned
// resources in minit, semacreate, or elsewhere. Do not take locks after calling this.
//
// This always runs without a P, so //go:nowritebarrierrec is required.
//go:nowritebarrierrec
func mdestroy(mp *m) {
}

View File

@@ -217,8 +217,11 @@ func minit() {
func unminit() {
}
// Called from exitm, but not from drop, to undo the effect of thread-owned
// Called from mexit, but not from dropm, to undo the effect of thread-owned
// resources in minit, semacreate, or elsewhere. Do not take locks after calling this.
//
// This always runs without a P, so //go:nowritebarrierrec is required.
//go:nowritebarrierrec
func mdestroy(mp *m) {
}

View File

@@ -906,9 +906,11 @@ func unminit() {
mp.procid = 0
}
// Called from exitm, but not from drop, to undo the effect of thread-owned
// Called from mexit, but not from dropm, to undo the effect of thread-owned
// resources in minit, semacreate, or elsewhere. Do not take locks after calling this.
//
// This always runs without a P, so //go:nowritebarrierrec is required.
//go:nowritebarrierrec
//go:nosplit
func mdestroy(mp *m) {
if mp.highResTimer != 0 {

View File

@@ -391,10 +391,15 @@ func deferrangefunc() any {
throw("defer on system stack")
}
fn := findfunc(sys.GetCallerPC())
if fn.deferreturn == 0 {
throw("no deferreturn")
}
d := newdefer()
d.link = gp._defer
gp._defer = d
d.pc = sys.GetCallerPC()
d.pc = fn.entry() + uintptr(fn.deferreturn)
// We must not be preempted between calling GetCallerSP and
// storing it to d.sp because GetCallerSP's result is a
// uintptr stack pointer.
@@ -1246,6 +1251,8 @@ func recovery(gp *g) {
// only gets us to the caller's fp.
gp.sched.bp = sp - goarch.PtrSize
}
// The value in ret is delivered IN A REGISTER, even if there is a
// stack ABI.
gp.sched.ret = 1
gogo(&gp.sched)
}

View File

@@ -416,27 +416,6 @@ func parseProfile(t *testing.T, valBytes []byte, f func(uintptr, []*profile.Loca
return p
}
func cpuProfilingBroken() bool {
switch runtime.GOOS {
case "plan9":
// Profiling unimplemented.
return true
case "aix":
// See https://golang.org/issue/45170.
return true
case "ios", "dragonfly", "netbsd", "illumos", "solaris":
// See https://golang.org/issue/13841.
return true
case "openbsd":
if runtime.GOARCH == "arm" || runtime.GOARCH == "arm64" {
// See https://golang.org/issue/13841.
return true
}
}
return false
}
// testCPUProfile runs f under the CPU profiler, checking for some conditions specified by need,
// as interpreted by matches, and returns the parsed profile.
func testCPUProfile(t *testing.T, matches profileMatchFunc, f func(dur time.Duration)) *profile.Profile {
@@ -454,7 +433,7 @@ func testCPUProfile(t *testing.T, matches profileMatchFunc, f func(dur time.Dura
t.Skip("skipping on wasip1")
}
broken := cpuProfilingBroken()
broken := testenv.CPUProfilingBroken()
deadline, ok := t.Deadline()
if broken || !ok {

Some files were not shown because too many files have changed in this diff Show More