Skip to content

Commit 3a58877

Browse files
Bryan C. Millscagedmantis
Bryan C. Mills
authored andcommitted
[release-branch.go1.21] internal/syscall/windows: fix the signature of SetFileInformationByHandle
Also fix its call site in internal/poll to pass the length of the actual buffer instead of an unrelated variable, and update the definition of FILE_BASIC_INFO to match the documented field types and add padding that is empirically needed on the 386 architecture. Passing a pointer to a Go-allocated buffer as type uintptr violates the unsafe.Pointer conversion rules, which allow such a conversion only in the call expression itself for a call to syscall.Syscall or equivalent. That can allow the buffer to be corrupted arbitrarily if the Go runtime happens to garbage-collect it while the call to SetFileInformationByHandle is in progress. The Microsoft documentation for SetFileInformationByHandle specifies its third argument type as LPVOID, which corresponds to Go's unsafe.Pointer, not uintptr. Fixes #65882. Updates #58933. Change-Id: If577b57adea9922f5fcca55e46030c703d8f035c Cq-Include-Trybots: luci.golang.try:go1.21-windows-amd64-longtest Reviewed-on: https://go-review.googlesource.com/c/go/+/549256 LUCI-TryBot-Result: Go LUCI <[email protected]> Reviewed-by: Than McIntosh <[email protected]> Auto-Submit: Bryan Mills <[email protected]> Reviewed-by: Quim Muntal <[email protected]> Reviewed-by: Alex Brainman <[email protected]> (cherry picked from commit a709724) Reviewed-on: https://go-review.googlesource.com/c/go/+/566155 Reviewed-by: Bryan Mills <[email protected]>
1 parent 263c059 commit 3a58877

File tree

3 files changed

+18
-8
lines changed

3 files changed

+18
-8
lines changed

src/internal/poll/fd_windows.go

+1-2
Original file line numberDiff line numberDiff line change
@@ -1037,8 +1037,7 @@ func (fd *FD) Fchmod(mode uint32) error {
10371037

10381038
var du windows.FILE_BASIC_INFO
10391039
du.FileAttributes = attrs
1040-
l := uint32(unsafe.Sizeof(d))
1041-
return windows.SetFileInformationByHandle(fd.Sysfd, windows.FileBasicInfo, uintptr(unsafe.Pointer(&du)), l)
1040+
return windows.SetFileInformationByHandle(fd.Sysfd, windows.FileBasicInfo, unsafe.Pointer(&du), uint32(unsafe.Sizeof(du)))
10421041
}
10431042

10441043
// Fchdir wraps syscall.Fchdir.

src/internal/syscall/windows/syscall_windows.go

+16-5
Original file line numberDiff line numberDiff line change
@@ -129,11 +129,22 @@ type SecurityAttributes struct {
129129
}
130130

131131
type FILE_BASIC_INFO struct {
132-
CreationTime syscall.Filetime
133-
LastAccessTime syscall.Filetime
134-
LastWriteTime syscall.Filetime
135-
ChangedTime syscall.Filetime
132+
CreationTime int64
133+
LastAccessTime int64
134+
LastWriteTime int64
135+
ChangedTime int64
136136
FileAttributes uint32
137+
138+
// Pad out to 8-byte alignment.
139+
//
140+
// Without this padding, TestChmod fails due to an argument validation error
141+
// in SetFileInformationByHandle on windows/386.
142+
//
143+
// https://learn.microsoft.com/en-us/cpp/build/reference/zp-struct-member-alignment?view=msvc-170
144+
// says that “The C/C++ headers in the Windows SDK assume the platform's
145+
// default alignment is used.” What we see here is padding rather than
146+
// alignment, but maybe it is related.
147+
_ uint32
137148
}
138149

139150
const (
@@ -150,7 +161,7 @@ const (
150161
//sys GetComputerNameEx(nameformat uint32, buf *uint16, n *uint32) (err error) = GetComputerNameExW
151162
//sys MoveFileEx(from *uint16, to *uint16, flags uint32) (err error) = MoveFileExW
152163
//sys GetModuleFileName(module syscall.Handle, fn *uint16, len uint32) (n uint32, err error) = kernel32.GetModuleFileNameW
153-
//sys SetFileInformationByHandle(handle syscall.Handle, fileInformationClass uint32, buf uintptr, bufsize uint32) (err error) = kernel32.SetFileInformationByHandle
164+
//sys SetFileInformationByHandle(handle syscall.Handle, fileInformationClass uint32, buf unsafe.Pointer, bufsize uint32) (err error) = kernel32.SetFileInformationByHandle
154165
//sys VirtualQuery(address uintptr, buffer *MemoryBasicInformation, length uintptr) (err error) = kernel32.VirtualQuery
155166
//sys GetTempPath2(buflen uint32, buf *uint16) (n uint32, err error) = GetTempPath2W
156167

src/internal/syscall/windows/zsyscall_windows.go

+1-1
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)