]> Cypherpunks repositories - gostls13.git/commitdiff
internal/syscall/unix: fix PosixFallocate error check on freebsd
authorTobias Klauser <tklauser@distanz.ch>
Wed, 5 Apr 2023 11:16:58 +0000 (13:16 +0200)
committerTobias Klauser <tobias.klauser@gmail.com>
Wed, 5 Apr 2023 14:17:36 +0000 (14:17 +0000)
The posix_fallocate syscall returns the result in r1 rather than in
errno:

> If successful, posix_fallocate() returns zero. It returns an error on failure, without
> setting errno.

Source: https://man.freebsd.org/cgi/man.cgi?query=posix_fallocate&sektion=2&n=1

Adjust the PosixFallocate wrappers on freebsd to account for that.

Also, CL 479715 used the same syscall wrapper for 386 and arm. However,
on arm the syscall argument order is different. The wrapper was
generated using mksyscall.go from the golang.org/x/sys/unix package,
adjusting the r1 check correspondingly.

Fixes #59352

Change-Id: I9a4e8e4546237010bc5e730c4988a2a476264cf4
Reviewed-on: https://go-review.googlesource.com/c/go/+/481621
Reviewed-by: Cherry Mui <cherryyz@google.com>
Run-TryBot: Tobias Klauser <tobias.klauser@gmail.com>
Reviewed-by: Yuval Pavel Zholkover <paulzhol@gmail.com>
Reviewed-by: Bryan Mills <bcmills@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>

src/cmd/link/internal/ld/fallocate_test.go
src/cmd/link/internal/ld/outbuf_freebsd.go
src/internal/syscall/unix/at_sysnum_freebsd.go
src/internal/syscall/unix/fallocate_freebsd_32bit.go [deleted file]
src/internal/syscall/unix/fallocate_freebsd_386.go [new file with mode: 0644]
src/internal/syscall/unix/fallocate_freebsd_64bit.go
src/internal/syscall/unix/fallocate_freebsd_arm.go [new file with mode: 0644]

index ad77be536fc834322c2812ed339458cba02a93c7..d95fec788a616bf18d6ff700f622883e34717afc 100644 (file)
@@ -7,6 +7,7 @@
 package ld
 
 import (
+       "errors"
        "os"
        "path/filepath"
        "syscall"
@@ -26,7 +27,7 @@ func TestFallocate(t *testing.T) {
        // Try fallocate first.
        for {
                err = out.fallocate(1 << 10)
-               if err == syscall.EOPNOTSUPP { // The underlying file system may not support fallocate
+               if errors.Is(err, errors.ErrUnsupported) || err == errNoFallocate { // The underlying file system may not support fallocate
                        t.Skip("fallocate is not supported")
                }
                if err == syscall.EINTR {
index 5ff17300c19686fffdccc2f25fed0dad17515148..7e718c1408e7304965af5e8836a7179a032e63e1 100644 (file)
@@ -6,8 +6,16 @@
 
 package ld
 
-import "internal/syscall/unix"
+import (
+       "internal/syscall/unix"
+       "syscall"
+)
 
 func (out *OutBuf) fallocate(size uint64) error {
-       return unix.PosixFallocate(int(out.f.Fd()), 0, int64(size))
+       err := unix.PosixFallocate(int(out.f.Fd()), 0, int64(size))
+       // ZFS on FreeBSD does not support posix_fallocate and returns EINVAL in that case.
+       if err == syscall.EINVAL {
+               return errNoFallocate
+       }
+       return err
 }
index adfbbcb92b4b9962afa22d8e59a70aaf483ac50b..530f5c2a2b8fe08f9693c2eed6e04bf883bc0f4d 100644 (file)
@@ -10,6 +10,7 @@ const (
        AT_REMOVEDIR        = 0x800
        AT_SYMLINK_NOFOLLOW = 0x200
 
-       unlinkatTrap uintptr = syscall.SYS_UNLINKAT
-       openatTrap   uintptr = syscall.SYS_OPENAT
+       unlinkatTrap       uintptr = syscall.SYS_UNLINKAT
+       openatTrap         uintptr = syscall.SYS_OPENAT
+       posixFallocateTrap uintptr = syscall.SYS_POSIX_FALLOCATE
 )
diff --git a/src/internal/syscall/unix/fallocate_freebsd_32bit.go b/src/internal/syscall/unix/fallocate_freebsd_32bit.go
deleted file mode 100644 (file)
index d821eea..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-// Copyright 2023 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.
-
-//go:build freebsd && (386 || arm)
-
-package unix
-
-import "syscall"
-
-// FreeBSD posix_fallocate system call number.
-const posixFallocateTrap uintptr = 530
-
-func PosixFallocate(fd int, off int64, size int64) error {
-       _, _, errno := syscall.Syscall6(posixFallocateTrap, uintptr(fd), uintptr(off), uintptr(off>>32), uintptr(size), uintptr(size>>32), 0)
-       if errno != 0 {
-               return errno
-       }
-       return nil
-}
diff --git a/src/internal/syscall/unix/fallocate_freebsd_386.go b/src/internal/syscall/unix/fallocate_freebsd_386.go
new file mode 100644 (file)
index 0000000..535b23d
--- /dev/null
@@ -0,0 +1,17 @@
+// Copyright 2023 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 unix
+
+import "syscall"
+
+func PosixFallocate(fd int, off int64, size int64) error {
+       // If successful, posix_fallocate() returns zero. It returns an error on failure, without
+       // setting errno. See https://man.freebsd.org/cgi/man.cgi?query=posix_fallocate&sektion=2&n=1
+       r1, _, _ := syscall.Syscall6(posixFallocateTrap, uintptr(fd), uintptr(off), uintptr(off>>32), uintptr(size), uintptr(size>>32), 0)
+       if r1 != 0 {
+               return syscall.Errno(r1)
+       }
+       return nil
+}
index f1ef6e347ca4763879cc011163915f203dfd5819..a9d52283f06a9b20af28dcf08bf8d0bc48d096ae 100644 (file)
@@ -8,13 +8,12 @@ package unix
 
 import "syscall"
 
-// FreeBSD posix_fallocate system call number.
-const posixFallocateTrap uintptr = 530
-
 func PosixFallocate(fd int, off int64, size int64) error {
-       _, _, errno := syscall.Syscall(posixFallocateTrap, uintptr(fd), uintptr(off), uintptr(size))
-       if errno != 0 {
-               return errno
+       // If successful, posix_fallocate() returns zero. It returns an error on failure, without
+       // setting errno. See https://man.freebsd.org/cgi/man.cgi?query=posix_fallocate&sektion=2&n=1
+       r1, _, _ := syscall.Syscall(posixFallocateTrap, uintptr(fd), uintptr(off), uintptr(size))
+       if r1 != 0 {
+               return syscall.Errno(r1)
        }
        return nil
 }
diff --git a/src/internal/syscall/unix/fallocate_freebsd_arm.go b/src/internal/syscall/unix/fallocate_freebsd_arm.go
new file mode 100644 (file)
index 0000000..1ded50f
--- /dev/null
@@ -0,0 +1,22 @@
+// Copyright 2023 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 unix
+
+import "syscall"
+
+func PosixFallocate(fd int, off int64, size int64) error {
+       // If successful, posix_fallocate() returns zero. It returns an error on failure, without
+       // setting errno. See https://man.freebsd.org/cgi/man.cgi?query=posix_fallocate&sektion=2&n=1
+       //
+       // The padding 0 argument is needed because the ARM calling convention requires that if an
+       // argument (off in this case) needs double-word alignment (8-byte), the NCRN (next core
+       // register number) is rounded up to the next even register number.
+       // See https://github.com/ARM-software/abi-aa/blob/2bcab1e3b22d55170c563c3c7940134089176746/aapcs32/aapcs32.rst#parameter-passing
+       r1, _, _ := syscall.Syscall6(posixFallocateTrap, uintptr(fd), 0, uintptr(off), uintptr(off>>32), uintptr(size), uintptr(size>>32))
+       if r1 != 0 {
+               return syscall.Errno(r1)
+       }
+       return nil
+}