github.com/containerd/nerdctl@v1.7.7/pkg/bypass4netnsutil/bypass4netnsutil.go (about) 1 /* 2 Copyright The containerd Authors. 3 4 Licensed under the Apache License, Version 2.0 (the "License"); 5 you may not use this file except in compliance with the License. 6 You may obtain a copy of the License at 7 8 http://www.apache.org/licenses/LICENSE-2.0 9 10 Unless required by applicable law or agreed to in writing, software 11 distributed under the License is distributed on an "AS IS" BASIS, 12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 See the License for the specific language governing permissions and 14 limitations under the License. 15 */ 16 17 package bypass4netnsutil 18 19 import ( 20 "context" 21 "fmt" 22 "os" 23 "path/filepath" 24 "strconv" 25 26 "github.com/containerd/containerd/containers" 27 "github.com/containerd/containerd/oci" 28 "github.com/containerd/nerdctl/pkg/labels" 29 "github.com/opencontainers/runtime-spec/specs-go" 30 b4nnoci "github.com/rootless-containers/bypass4netns/pkg/oci" 31 ) 32 33 func generateSecurityOpt(listenerPath string) (oci.SpecOpts, error) { 34 opt := func(_ context.Context, _ oci.Client, _ *containers.Container, s *specs.Spec) error { 35 if s.Linux.Seccomp == nil { 36 s.Linux.Seccomp = b4nnoci.GetDefaultSeccompProfile(listenerPath) 37 } else { 38 sc, err := b4nnoci.TranslateSeccompProfile(*s.Linux.Seccomp, listenerPath) 39 if err != nil { 40 return err 41 } 42 s.Linux.Seccomp = sc 43 } 44 return nil 45 } 46 return opt, nil 47 } 48 49 func GenerateBypass4netnsOpts(securityOptsMaps map[string]string, labelMaps map[string]string, id string) ([]oci.SpecOpts, error) { 50 b4nn, ok := labelMaps[labels.Bypass4netns] 51 if !ok { 52 return nil, nil 53 } 54 55 b4nnEnable, err := strconv.ParseBool(b4nn) 56 if err != nil { 57 return nil, err 58 } 59 60 if !b4nnEnable { 61 return nil, nil 62 } 63 64 socketPath, err := GetSocketPathByID(id) 65 if err != nil { 66 return nil, err 67 } 68 69 err = CreateSocketDir() 70 if err != nil { 71 return nil, err 72 } 73 74 opts := []oci.SpecOpts{} 75 opt, err := generateSecurityOpt(socketPath) 76 if err != nil { 77 return nil, err 78 } 79 opts = append(opts, opt) 80 81 return opts, nil 82 } 83 84 func getXDGRuntimeDir() (string, error) { 85 if xrd := os.Getenv("XDG_RUNTIME_DIR"); xrd != "" { 86 return xrd, nil 87 } 88 return "", fmt.Errorf("environment variable XDG_RUNTIME_DIR is not set") 89 } 90 91 func CreateSocketDir() error { 92 xdgRuntimeDir, err := getXDGRuntimeDir() 93 if err != nil { 94 return err 95 } 96 dirPath := filepath.Join(xdgRuntimeDir, "bypass4netns") 97 if _, err := os.Stat(dirPath); os.IsNotExist(err) { 98 err = os.MkdirAll(dirPath, 0775) 99 if err != nil { 100 return err 101 } 102 } 103 104 return nil 105 } 106 107 func GetBypass4NetnsdDefaultSocketPath() (string, error) { 108 xdgRuntimeDir, err := getXDGRuntimeDir() 109 if err != nil { 110 return "", err 111 } 112 113 return filepath.Join(xdgRuntimeDir, "bypass4netnsd.sock"), nil 114 } 115 116 func GetSocketPathByID(id string) (string, error) { 117 xdgRuntimeDir, err := getXDGRuntimeDir() 118 if err != nil { 119 return "", err 120 } 121 122 socketPath := filepath.Join(xdgRuntimeDir, "bypass4netns", id[0:15]+".sock") 123 return socketPath, nil 124 } 125 126 func GetPidFilePathByID(id string) (string, error) { 127 xdgRuntimeDir, err := getXDGRuntimeDir() 128 if err != nil { 129 return "", err 130 } 131 132 socketPath := filepath.Join(xdgRuntimeDir, "bypass4netns", id[0:15]+".pid") 133 return socketPath, nil 134 } 135 136 func IsBypass4netnsEnabled(annotations map[string]string) (bool, error) { 137 if b4nn, ok := annotations[labels.Bypass4netns]; ok { 138 b4nnEnable, err := strconv.ParseBool(b4nn) 139 if err != nil { 140 return false, err 141 } 142 143 return b4nnEnable, nil 144 } 145 146 return false, nil 147 }