2
2
3
3
package abi
4
4
5
- import "github.com/containers/podman/v5/libpod/define"
5
+ import (
6
+ "fmt"
7
+ "os"
8
+ "strings"
9
+
10
+ "github.com/containers/podman/v5/libpod/define"
11
+ "golang.org/x/sys/unix"
12
+ )
6
13
7
14
// getSdNotifyMode returns the `sdNotifyAnnotation/$name` for the specified
8
15
// name. If name is empty, it'll only look for `sdNotifyAnnotation`.
@@ -16,3 +23,33 @@ func getSdNotifyMode(annotations map[string]string, name string) (string, error)
16
23
}
17
24
return mode , define .ValidateSdNotifyMode (mode )
18
25
}
26
+
27
+ // openPathSafely opens the given name under the trusted root path, the unsafeName
28
+ // must be a single path component and not contain "/".
29
+ // The resulting path will be opened or created if it does not exists.
30
+ // Following of symlink is done within staying under root, escapes outsides
31
+ // of root are not allowed and prevent.
32
+ //
33
+ // This custom function is needed because securejoin.SecureJoin() is not race safe
34
+ // and the volume might be mounted in another container that could swap in a symlink
35
+ // after the function ahs run. securejoin.OpenInRoot() doesn't work either because
36
+ // it cannot create files and doesn't work on freebsd.
37
+ func openPathSafely (root , unsafeName string ) (* os.File , error ) {
38
+ if strings .Contains (unsafeName , "/" ) {
39
+ return nil , fmt .Errorf ("name %q must not contain path separator" , unsafeName )
40
+ }
41
+ fdDir , err := os .OpenFile (root , unix .O_RDONLY , 0 )
42
+ if err != nil {
43
+ return nil , err
44
+ }
45
+ defer fdDir .Close ()
46
+ flags := unix .O_CREAT | unix .O_WRONLY | unix .O_TRUNC | unix .O_CLOEXEC
47
+ fd , err := unix .Openat (int (fdDir .Fd ()), unsafeName , flags | unix .O_NOFOLLOW , 0o644 )
48
+ if err == nil {
49
+ return os .NewFile (uintptr (fd ), unsafeName ), nil
50
+ }
51
+ if err == unix .ELOOP {
52
+ return openSymlinkPath (fdDir , unsafeName , flags )
53
+ }
54
+ return nil , & os.PathError {Op : "openat" , Path : unsafeName , Err : err }
55
+ }
0 commit comments