carlos / platform Public

Clone
git clone https://amadan.net/carlos/platform

Plain git — no account needed to clone.

Download

Download this file

1//go:build linux
2
3package instanceexec
4
5import (
6 "errors"
7 "net"
8 "syscall"
9 "time"
10
11 "golang.org/x/sys/unix"
12)
13
14// accessWritable asks the kernel whether path could be opened for writing
15// without opening it: on a read-only mount access(2) answers EROFS, which
16// is exactly the property ProtectControlGroups= must give a tenant.
17func accessWritable(path string) error {
18 return unix.Access(path, unix.W_OK)
19}
20
21// sendOneDatagram sends one empty UDP datagram. With a cgroup BPF egress
22// filter (IPAddressDeny=) the filter's verdict is sendmsg's return value,
23// EPERM; with no route it is ENETUNREACH; on a live path it is nil.
24func sendOneDatagram(network, addr string) error {
25 c, err := net.Dial(network, addr)
26 if err != nil {
27 return unwrapErrno(err)
28 }
29 defer c.Close()
30 _, err = c.Write([]byte{})
31 return unwrapErrno(err)
32}
33
34func connectWithTimeout(addr string, timeout time.Duration) error {
35 c, err := net.DialTimeout("tcp", addr, timeout)
36 if err != nil {
37 return unwrapErrno(err)
38 }
39 c.Close()
40 return nil
41}
42
43// unwrapErrno returns the syscall.Errno inside err so callers can
44// errors.Is against EPERM and ENETUNREACH; net.OpError and os.SyscallError
45// both unwrap to the Errno, so errors.As finds it. Anything else is
46// returned as is. (unix.Errno is an alias of syscall.Errno.)
47func unwrapErrno(err error) error {
48 var errno syscall.Errno
49 if errors.As(err, &errno) {
50 return errno
51 }
52 return err
53}
54