diff options
Diffstat (limited to 'pkg')
-rw-r--r-- | pkg/adapter/containers.go | 36 | ||||
-rw-r--r-- | pkg/adapter/pods.go | 8 | ||||
-rw-r--r-- | pkg/adapter/sigproxy_linux.go | 4 | ||||
-rw-r--r-- | pkg/adapter/terminal.go | 6 | ||||
-rw-r--r-- | pkg/api/handlers/containers_create.go | 2 | ||||
-rw-r--r-- | pkg/api/handlers/utils/images.go | 9 | ||||
-rw-r--r-- | pkg/bindings/test/common_test.go | 76 | ||||
-rw-r--r-- | pkg/bindings/test/images_test.go | 65 | ||||
-rw-r--r-- | pkg/capabilities/capabilities.go | 129 | ||||
-rw-r--r-- | pkg/signal/signal_linux.go | 127 | ||||
-rw-r--r-- | pkg/signal/signal_unsupported.go | 28 | ||||
-rw-r--r-- | pkg/spec/security.go | 6 | ||||
-rw-r--r-- | pkg/util/utils.go | 2 |
13 files changed, 439 insertions, 59 deletions
diff --git a/pkg/adapter/containers.go b/pkg/adapter/containers.go index f66999ffa..cada93829 100644 --- a/pkg/adapter/containers.go +++ b/pkg/adapter/containers.go @@ -444,9 +444,12 @@ func (r *LocalRuntime) Run(ctx context.Context, c *cliconfig.RunValues, exitCode } } - keys, err := r.selectDetachKeys(c.String("detach-keys")) - if err != nil { - return exitCode, err + keys := c.String("detach-keys") + if !c.IsSet("detach-keys") { + keys, err = r.selectDetachKeys(keys) + if err != nil { + return exitCode, err + } } // if the container was created as part of a pod, also start its dependencies, if any. @@ -534,9 +537,12 @@ func (r *LocalRuntime) Attach(ctx context.Context, c *cliconfig.AttachValues) er inputStream = nil } - keys, err := r.selectDetachKeys(c.DetachKeys) - if err != nil { - return err + keys := c.DetachKeys + if !c.IsSet("detach-keys") { + keys, err = r.selectDetachKeys(keys) + if err != nil { + return err + } } // If the container is in a pod, also set to recursively start dependencies @@ -674,9 +680,12 @@ func (r *LocalRuntime) Start(ctx context.Context, c *cliconfig.StartValues, sigP } } - keys, err := r.selectDetachKeys(c.DetachKeys) - if err != nil { - return exitCode, err + keys := c.DetachKeys + if !c.IsSet("detach-keys") { + keys, err = r.selectDetachKeys(keys) + if err != nil { + return exitCode, err + } } // attach to the container and also start it not already running @@ -975,9 +984,12 @@ func (r *LocalRuntime) ExecContainer(ctx context.Context, cli *cliconfig.ExecVal streams.AttachOutput = true streams.AttachError = true - keys, err := r.selectDetachKeys(cli.DetachKeys) - if err != nil { - return ec, err + keys := cli.DetachKeys + if !cli.IsSet("detach-keys") { + keys, err = r.selectDetachKeys(keys) + if err != nil { + return ec, err + } } ec, err = ExecAttachCtr(ctx, ctr.Container, cli.Tty, cli.Privileged, env, cmd, cli.User, cli.Workdir, streams, uint(cli.PreserveFDs), keys) diff --git a/pkg/adapter/pods.go b/pkg/adapter/pods.go index a30ec6649..49f086ef3 100644 --- a/pkg/adapter/pods.go +++ b/pkg/adapter/pods.go @@ -565,8 +565,8 @@ func (r *LocalRuntime) PlayKubeYAML(ctx context.Context, c *cliconfig.KubePlayVa return nil, errors.Errorf("Error creating HostPath %s at %s", volume.Name, hostPath.Path) } } - // unconditionally label a newly created volume as private - if err := libpod.LabelVolumePath(hostPath.Path, false); err != nil { + // Label a newly created volume + if err := libpod.LabelVolumePath(hostPath.Path); err != nil { return nil, errors.Wrapf(err, "Error giving %s a label", hostPath.Path) } case v1.HostPathFileOrCreate: @@ -579,8 +579,8 @@ func (r *LocalRuntime) PlayKubeYAML(ctx context.Context, c *cliconfig.KubePlayVa logrus.Warnf("Error in closing newly created HostPath file: %v", err) } } - // unconditionally label a newly created volume as private - if err := libpod.LabelVolumePath(hostPath.Path, false); err != nil { + // unconditionally label a newly created volume + if err := libpod.LabelVolumePath(hostPath.Path); err != nil { return nil, errors.Wrapf(err, "Error giving %s a label", hostPath.Path) } case v1.HostPathDirectory: diff --git a/pkg/adapter/sigproxy_linux.go b/pkg/adapter/sigproxy_linux.go index 35745a6aa..8295e4250 100644 --- a/pkg/adapter/sigproxy_linux.go +++ b/pkg/adapter/sigproxy_linux.go @@ -5,7 +5,7 @@ import ( "syscall" "github.com/containers/libpod/libpod" - "github.com/docker/docker/pkg/signal" + "github.com/containers/libpod/pkg/signal" "github.com/sirupsen/logrus" ) @@ -20,7 +20,7 @@ func ProxySignals(ctr *libpod.Container) { for s := range sigBuffer { // Ignore SIGCHLD and SIGPIPE - these are mostly likely // intended for the podman command itself. - if s == signal.SIGCHLD || s == signal.SIGPIPE { + if s == syscall.SIGCHLD || s == syscall.SIGPIPE { continue } diff --git a/pkg/adapter/terminal.go b/pkg/adapter/terminal.go index 51b747d23..499e77def 100644 --- a/pkg/adapter/terminal.go +++ b/pkg/adapter/terminal.go @@ -3,9 +3,9 @@ package adapter import ( "context" "os" - gosignal "os/signal" + "os/signal" - "github.com/docker/docker/pkg/signal" + lsignal "github.com/containers/libpod/pkg/signal" "github.com/docker/docker/pkg/term" "github.com/pkg/errors" "github.com/sirupsen/logrus" @@ -33,7 +33,7 @@ func getResize() *remotecommand.TerminalSize { // Helper for prepareAttach - set up a goroutine to generate terminal resize events func resizeTty(ctx context.Context, resize chan remotecommand.TerminalSize) { sigchan := make(chan os.Signal, 1) - gosignal.Notify(sigchan, signal.SIGWINCH) + signal.Notify(sigchan, lsignal.SIGWINCH) go func() { defer close(resize) // Update the terminal size immediately without waiting diff --git a/pkg/api/handlers/containers_create.go b/pkg/api/handlers/containers_create.go index 4781b23bc..48f0de94d 100644 --- a/pkg/api/handlers/containers_create.go +++ b/pkg/api/handlers/containers_create.go @@ -12,9 +12,9 @@ import ( image2 "github.com/containers/libpod/libpod/image" "github.com/containers/libpod/pkg/api/handlers/utils" "github.com/containers/libpod/pkg/namespaces" + "github.com/containers/libpod/pkg/signal" createconfig "github.com/containers/libpod/pkg/spec" "github.com/containers/storage" - "github.com/docker/docker/pkg/signal" "github.com/gorilla/schema" "github.com/pkg/errors" log "github.com/sirupsen/logrus" diff --git a/pkg/api/handlers/utils/images.go b/pkg/api/handlers/utils/images.go index 2b651584a..d0dfbf3ab 100644 --- a/pkg/api/handlers/utils/images.go +++ b/pkg/api/handlers/utils/images.go @@ -31,9 +31,12 @@ func GetImages(w http.ResponseWriter, r *http.Request) ([]*image.Image, error) { if _, found := mux.Vars(r)["digests"]; found && query.Digests { UnSupportedParameter("digests") } - - if _, found := r.URL.Query()["filters"]; found { - filters = append(filters, fmt.Sprintf("reference=%s", "")) + if len(query.Filters) > 0 { + for k, v := range query.Filters { + for _, val := range v { + filters = append(filters, fmt.Sprintf("%s=%s", k, val)) + } + } } return runtime.ImageRuntime().GetImagesWithFilters(filters) } diff --git a/pkg/bindings/test/common_test.go b/pkg/bindings/test/common_test.go index 22cd0b7e0..dba94cb35 100644 --- a/pkg/bindings/test/common_test.go +++ b/pkg/bindings/test/common_test.go @@ -13,10 +13,30 @@ import ( "github.com/pkg/errors" ) +type testImage struct { + name string + shortName string + tarballName string +} + const ( defaultPodmanBinaryLocation string = "/usr/bin/podman" - alpine string = "docker.io/library/alpine:latest" - busybox string = "docker.io/library/busybox:latest" +) + +var ( + ImageCacheDir = "/tmp/podman/imagecachedir" + LockTmpDir string + alpine = testImage{ + name: "docker.io/library/alpine:latest", + shortName: "alpine", + tarballName: "alpine.tar", + } + busybox = testImage{ + name: "docker.io/library/busybox:latest", + shortName: "busybox", + tarballName: "busybox.tar", + } + CACHE_IMAGES = []testImage{alpine, busybox} ) type bindingTest struct { @@ -109,7 +129,7 @@ func (b *bindingTest) startAPIService() *gexec.Session { var ( cmd []string ) - cmd = append(cmd, "--log-level=debug", "service", "--timeout=999999", b.sock) + cmd = append(cmd, "--log-level=debug", "system", "service", "--timeout=999999", b.sock) return b.runPodman(cmd) } @@ -127,6 +147,21 @@ func (b *bindingTest) Pull(name string) { p.Wait(45) } +func (b *bindingTest) Save(i testImage) { + p := b.runPodman([]string{"save", "-o", filepath.Join(ImageCacheDir, i.tarballName), i.name}) + p.Wait(45) +} + +func (b *bindingTest) RestoreImagesFromCache() { + for _, i := range CACHE_IMAGES { + b.restoreImageFromCache(i) + } +} +func (b *bindingTest) restoreImageFromCache(i testImage) { + p := b.runPodman([]string{"load", "-i", filepath.Join(ImageCacheDir, i.tarballName), i.name}) + p.Wait(45) +} + // Run a container and add append the alpine image to it func (b *bindingTest) RunTopContainer(name *string) { cmd := []string{"run", "-dt"} @@ -134,7 +169,7 @@ func (b *bindingTest) RunTopContainer(name *string) { containerName := *name cmd = append(cmd, "--name", containerName) } - cmd = append(cmd, alpine, "top") + cmd = append(cmd, alpine.name, "top") p := b.runPodman(cmd) p.Wait(45) } @@ -149,3 +184,36 @@ func StringInSlice(s string, sl []string) bool { } return false } + +var _ = ginkgo.SynchronizedBeforeSuite(func() []byte { + // make cache dir + if err := os.MkdirAll(ImageCacheDir, 0777); err != nil { + fmt.Printf("%q\n", err) + os.Exit(1) + } + + // If running localized tests, the cache dir is created and populated. if the + // tests are remote, this is a no-op + createCache() + path, err := ioutil.TempDir("", "libpodlock") + if err != nil { + fmt.Println(err) + os.Exit(1) + } + return []byte(path) +}, func(data []byte) { + LockTmpDir = string(data) +}) + +func createCache() { + b := newBindingTest() + for _, i := range CACHE_IMAGES { + _, err := os.Stat(filepath.Join(ImageCacheDir, i.tarballName)) + if os.IsNotExist(err) { + // pull the image + b.Pull(i.name) + b.Save(i) + } + } + b.cleanup() +} diff --git a/pkg/bindings/test/images_test.go b/pkg/bindings/test/images_test.go index fea611601..74e0cc67a 100644 --- a/pkg/bindings/test/images_test.go +++ b/pkg/bindings/test/images_test.go @@ -2,6 +2,7 @@ package test_bindings import ( "context" + "net/http" "time" "github.com/containers/libpod/pkg/bindings" @@ -34,8 +35,7 @@ var _ = Describe("Podman images", func() { //podmanTest.Setup() //podmanTest.SeedImages() bt = newBindingTest() - bt.Pull(alpine) - bt.Pull(busybox) + bt.RestoreImagesFromCache() s = bt.startAPIService() time.Sleep(1 * time.Second) connText, err = bindings.NewConnection(bt.sock) @@ -54,10 +54,10 @@ var _ = Describe("Podman images", func() { _, err = images.GetImage(connText, "foobar5000", nil) Expect(err).ToNot(BeNil()) code, _ := bindings.CheckResponseCode(err) - Expect(code).To(BeNumerically("==", 404)) + Expect(code).To(BeNumerically("==", http.StatusNotFound)) // Inspect by short name - data, err := images.GetImage(connText, "alpine", nil) + data, err := images.GetImage(connText, alpine.shortName, nil) Expect(err).To(BeNil()) // Inspect with full ID @@ -68,10 +68,9 @@ var _ = Describe("Podman images", func() { _, err = images.GetImage(connText, data.ID[0:12], nil) Expect(err).To(BeNil()) - // The test to inspect by long name needs to fixed. - // Inspect by long name should work, it doesnt (yet) i think it needs to be html escaped - // _, err = images.GetImage(connText, alpine, nil) - // Expect(err).To(BeNil()) + // Inspect by long name + _, err = images.GetImage(connText, alpine.name, nil) + Expect(err).To(BeNil()) }) // Test to validate the remove image api @@ -80,17 +79,17 @@ var _ = Describe("Podman images", func() { _, err = images.Remove(connText, "foobar5000", &falseFlag) Expect(err).ToNot(BeNil()) code, _ := bindings.CheckResponseCode(err) - Expect(code).To(BeNumerically("==", 404)) + Expect(code).To(BeNumerically("==", http.StatusNotFound)) // Remove an image by name, validate image is removed and error is nil - inspectData, err := images.GetImage(connText, "busybox", nil) + inspectData, err := images.GetImage(connText, busybox.shortName, nil) Expect(err).To(BeNil()) - response, err := images.Remove(connText, "busybox", nil) + response, err := images.Remove(connText, busybox.shortName, nil) Expect(err).To(BeNil()) Expect(inspectData.ID).To(Equal(response[0]["Deleted"])) - inspectData, err = images.GetImage(connText, "busybox", nil) + inspectData, err = images.GetImage(connText, busybox.shortName, nil) code, _ = bindings.CheckResponseCode(err) - Expect(code).To(BeNumerically("==", 404)) + Expect(code).To(BeNumerically("==", http.StatusNotFound)) // Start a container with alpine image var top string = "top" @@ -102,38 +101,38 @@ var _ = Describe("Podman images", func() { // try to remove the image "alpine". This should fail since we are not force // deleting hence image cannot be deleted until the container is deleted. - response, err = images.Remove(connText, "alpine", &falseFlag) + response, err = images.Remove(connText, alpine.shortName, &falseFlag) code, _ = bindings.CheckResponseCode(err) - Expect(code).To(BeNumerically("==", 500)) + Expect(code).To(BeNumerically("==", http.StatusInternalServerError)) // Removing the image "alpine" where force = true - response, err = images.Remove(connText, "alpine", &trueFlag) + response, err = images.Remove(connText, alpine.shortName, &trueFlag) Expect(err).To(BeNil()) // Checking if both the images are gone as well as the container is deleted - inspectData, err = images.GetImage(connText, "busybox", nil) + inspectData, err = images.GetImage(connText, busybox.shortName, nil) code, _ = bindings.CheckResponseCode(err) - Expect(code).To(BeNumerically("==", 404)) + Expect(code).To(BeNumerically("==", http.StatusNotFound)) - inspectData, err = images.GetImage(connText, "alpine", nil) + inspectData, err = images.GetImage(connText, alpine.shortName, nil) code, _ = bindings.CheckResponseCode(err) - Expect(code).To(BeNumerically("==", 404)) + Expect(code).To(BeNumerically("==", http.StatusNotFound)) _, err = containers.Inspect(connText, "top", &falseFlag) code, _ = bindings.CheckResponseCode(err) - Expect(code).To(BeNumerically("==", 404)) + Expect(code).To(BeNumerically("==", http.StatusNotFound)) }) // Tests to validate the image tag command. It("tag image", func() { // Validates if invalid image name is given a bad response is encountered. - err = images.Tag(connText, "dummy", "demo", "alpine") + err = images.Tag(connText, "dummy", "demo", alpine.shortName) Expect(err).ToNot(BeNil()) code, _ := bindings.CheckResponseCode(err) - Expect(code).To(BeNumerically("==", 404)) + Expect(code).To(BeNumerically("==", http.StatusNotFound)) // Validates if the image is tagged sucessfully. - err = images.Tag(connText, "alpine", "demo", "alpine") + err = images.Tag(connText, alpine.shortName, "demo", alpine.shortName) Expect(err).To(BeNil()) //Validates if name updates when the image is retagged. @@ -164,8 +163,22 @@ var _ = Describe("Podman images", func() { for _, i := range imageSummary { names = append(names, i.RepoTags...) } - Expect(StringInSlice(alpine, names)).To(BeTrue()) - Expect(StringInSlice(busybox, names)).To(BeTrue()) + Expect(StringInSlice(alpine.name, names)).To(BeTrue()) + Expect(StringInSlice(busybox.name, names)).To(BeTrue()) + + // List images with a filter + filters := make(map[string][]string) + filters["reference"] = []string{alpine.name} + filteredImages, err := images.List(connText, &falseFlag, filters) + Expect(err).To(BeNil()) + Expect(len(filteredImages)).To(BeNumerically("==", 1)) + + // List images with a bad filter + filters["name"] = []string{alpine.name} + _, err = images.List(connText, &falseFlag, filters) + Expect(err).ToNot(BeNil()) + code, _ := bindings.CheckResponseCode(err) + Expect(code).To(BeNumerically("==", http.StatusInternalServerError)) }) }) diff --git a/pkg/capabilities/capabilities.go b/pkg/capabilities/capabilities.go new file mode 100644 index 000000000..ea22498b8 --- /dev/null +++ b/pkg/capabilities/capabilities.go @@ -0,0 +1,129 @@ +package capabilities + +// Copyright 2013-2018 Docker, Inc. + +// NOTE: this package has been copied from github.com/docker/docker but been +// changed significantly to fit the needs of libpod. + +import ( + "strings" + + "github.com/containers/libpod/pkg/util" + "github.com/pkg/errors" + "github.com/syndtr/gocapability/capability" +) + +var ( + // Used internally and populated during init(). + capabilityList []string + + // ErrUnknownCapability is thrown when an unknown capability is processed. + ErrUnknownCapability = errors.New("unknown capability") +) + +// All is a special value used to add/drop all known capababilities. +// Useful on the CLI for `--cap-add=all` etc. +const All = "ALL" + +func init() { + last := capability.CAP_LAST_CAP + // hack for RHEL6 which has no /proc/sys/kernel/cap_last_cap + if last == capability.Cap(63) { + last = capability.CAP_BLOCK_SUSPEND + } + for _, cap := range capability.List() { + if cap > last { + continue + } + capabilityList = append(capabilityList, "CAP_"+strings.ToUpper(cap.String())) + } +} + +// AllCapabilities returns all known capabilities. +func AllCapabilities() []string { + return capabilityList +} + +// normalizeCapabilities normalizes caps by adding a "CAP_" prefix (if not yet +// present). +func normalizeCapabilities(caps []string) ([]string, error) { + normalized := make([]string, len(caps)) + for i, c := range caps { + c = strings.ToUpper(c) + if c == All { + normalized = append(normalized, c) + continue + } + if !strings.HasPrefix(c, "CAP_") { + c = "CAP_" + c + } + if !util.StringInSlice(c, capabilityList) { + return nil, errors.Wrapf(ErrUnknownCapability, "%q", c) + } + normalized[i] = c + } + return normalized, nil +} + +// ValidateCapabilities validates if caps only contains valid capabilities. +func ValidateCapabilities(caps []string) error { + for _, c := range caps { + if !util.StringInSlice(c, capabilityList) { + return errors.Wrapf(ErrUnknownCapability, "%q", c) + } + } + return nil +} + +// MergeCapabilities computes a set of capabilities by adding capapbitilities +// to or dropping them from base. +// +// Note that "ALL" will cause all known capabilities to be added/dropped but +// the ones specified to be dropped/added. +func MergeCapabilities(base, adds, drops []string) ([]string, error) { + if len(adds) == 0 && len(drops) == 0 { + // Nothing to tweak; we're done + return base, nil + } + + capDrop, err := normalizeCapabilities(drops) + if err != nil { + return nil, err + } + capAdd, err := normalizeCapabilities(adds) + if err != nil { + return nil, err + } + + // Make sure that capDrop and capAdd are distinct sets. + for _, drop := range capDrop { + if util.StringInSlice(drop, capAdd) { + return nil, errors.Errorf("capability %q cannot be dropped and added", drop) + } + } + + var caps []string + + switch { + case util.StringInSlice(All, capAdd): + // Add all capabilities except ones on capDrop + for _, c := range capabilityList { + if !util.StringInSlice(c, capDrop) { + caps = append(caps, c) + } + } + case util.StringInSlice(All, capDrop): + // "Drop" all capabilities; use what's in capAdd instead + caps = capAdd + default: + // First drop some capabilities + for _, c := range base { + if !util.StringInSlice(c, capDrop) { + caps = append(caps, c) + } + } + // Then add the list of capabilities from capAdd + caps = append(caps, capAdd...) + } + return caps, nil +} diff --git a/pkg/signal/signal_linux.go b/pkg/signal/signal_linux.go new file mode 100644 index 000000000..3d549898f --- /dev/null +++ b/pkg/signal/signal_linux.go @@ -0,0 +1,127 @@ +// +build linux + +// Signal handling for Linux only. +package signal + +// Copyright 2013-2018 Docker, Inc. + +// NOTE: this package has originally been copied from github.com/docker/docker. + +import ( + "fmt" + "os" + "os/signal" + "strconv" + "strings" + "syscall" + + "golang.org/x/sys/unix" +) + +const ( + sigrtmin = 34 + sigrtmax = 64 + + SIGWINCH = syscall.SIGWINCH // For cross-compilation with Windows +) + +// signalMap is a map of Linux signals. +var signalMap = map[string]syscall.Signal{ + "ABRT": unix.SIGABRT, + "ALRM": unix.SIGALRM, + "BUS": unix.SIGBUS, + "CHLD": unix.SIGCHLD, + "CLD": unix.SIGCLD, + "CONT": unix.SIGCONT, + "FPE": unix.SIGFPE, + "HUP": unix.SIGHUP, + "ILL": unix.SIGILL, + "INT": unix.SIGINT, + "IO": unix.SIGIO, + "IOT": unix.SIGIOT, + "KILL": unix.SIGKILL, + "PIPE": unix.SIGPIPE, + "POLL": unix.SIGPOLL, + "PROF": unix.SIGPROF, + "PWR": unix.SIGPWR, + "QUIT": unix.SIGQUIT, + "SEGV": unix.SIGSEGV, + "STKFLT": unix.SIGSTKFLT, + "STOP": unix.SIGSTOP, + "SYS": unix.SIGSYS, + "TERM": unix.SIGTERM, + "TRAP": unix.SIGTRAP, + "TSTP": unix.SIGTSTP, + "TTIN": unix.SIGTTIN, + "TTOU": unix.SIGTTOU, + "URG": unix.SIGURG, + "USR1": unix.SIGUSR1, + "USR2": unix.SIGUSR2, + "VTALRM": unix.SIGVTALRM, + "WINCH": unix.SIGWINCH, + "XCPU": unix.SIGXCPU, + "XFSZ": unix.SIGXFSZ, + "RTMIN": sigrtmin, + "RTMIN+1": sigrtmin + 1, + "RTMIN+2": sigrtmin + 2, + "RTMIN+3": sigrtmin + 3, + "RTMIN+4": sigrtmin + 4, + "RTMIN+5": sigrtmin + 5, + "RTMIN+6": sigrtmin + 6, + "RTMIN+7": sigrtmin + 7, + "RTMIN+8": sigrtmin + 8, + "RTMIN+9": sigrtmin + 9, + "RTMIN+10": sigrtmin + 10, + "RTMIN+11": sigrtmin + 11, + "RTMIN+12": sigrtmin + 12, + "RTMIN+13": sigrtmin + 13, + "RTMIN+14": sigrtmin + 14, + "RTMIN+15": sigrtmin + 15, + "RTMAX-14": sigrtmax - 14, + "RTMAX-13": sigrtmax - 13, + "RTMAX-12": sigrtmax - 12, + "RTMAX-11": sigrtmax - 11, + "RTMAX-10": sigrtmax - 10, + "RTMAX-9": sigrtmax - 9, + "RTMAX-8": sigrtmax - 8, + "RTMAX-7": sigrtmax - 7, + "RTMAX-6": sigrtmax - 6, + "RTMAX-5": sigrtmax - 5, + "RTMAX-4": sigrtmax - 4, + "RTMAX-3": sigrtmax - 3, + "RTMAX-2": sigrtmax - 2, + "RTMAX-1": sigrtmax - 1, + "RTMAX": sigrtmax, +} + +// ParseSignal translates a string to a valid syscall signal. +// It returns an error if the signal map doesn't include the given signal. +func ParseSignal(rawSignal string) (syscall.Signal, error) { + s, err := strconv.Atoi(rawSignal) + if err == nil { + if s == 0 { + return -1, fmt.Errorf("invalid signal: %s", rawSignal) + } + return syscall.Signal(s), nil + } + signal, ok := signalMap[strings.TrimPrefix(strings.ToUpper(rawSignal), "SIG")] + if !ok { + return -1, fmt.Errorf("invalid signal: %s", rawSignal) + } + return signal, nil +} + +// CatchAll catches all signals and relays them to the specified channel. +func CatchAll(sigc chan os.Signal) { + var handledSigs []os.Signal + for _, s := range signalMap { + handledSigs = append(handledSigs, s) + } + signal.Notify(sigc, handledSigs...) +} + +// StopCatch stops catching the signals and closes the specified channel. +func StopCatch(sigc chan os.Signal) { + signal.Stop(sigc) + close(sigc) +} diff --git a/pkg/signal/signal_unsupported.go b/pkg/signal/signal_unsupported.go new file mode 100644 index 000000000..0a92a5b3a --- /dev/null +++ b/pkg/signal/signal_unsupported.go @@ -0,0 +1,28 @@ +// +build !linux + +// Signal handling for Linux only. +package signal + +import ( + "fmt" + "os" + "syscall" +) + +const SIGWINCH = syscall.Signal(0xff) + +// ParseSignal translates a string to a valid syscall signal. +// It returns an error if the signal map doesn't include the given signal. +func ParseSignal(rawSignal string) (syscall.Signal, error) { + return 0, fmt.Errorf("unsupported on non-linux platforms") +} + +// CatchAll catches all signals and relays them to the specified channel. +func CatchAll(sigc chan os.Signal) { + panic("Unsupported on non-linux platforms") +} + +// StopCatch stops catching the signals and closes the specified channel. +func StopCatch(sigc chan os.Signal) { + panic("Unsupported on non-linux platforms") +} diff --git a/pkg/spec/security.go b/pkg/spec/security.go index 372fe87c6..3bad9f97a 100644 --- a/pkg/spec/security.go +++ b/pkg/spec/security.go @@ -5,7 +5,7 @@ import ( "strings" "github.com/containers/libpod/libpod" - "github.com/docker/docker/oci/caps" + "github.com/containers/libpod/pkg/capabilities" "github.com/opencontainers/runtime-tools/generate" "github.com/opencontainers/selinux/go-selinux/label" "github.com/pkg/errors" @@ -118,7 +118,7 @@ func (c *SecurityConfig) ConfigureGenerator(g *generate.Generator, user *UserCon if useNotRoot(user.User) { configSpec.Process.Capabilities.Bounding = caplist } - caplist, err = caps.TweakCapabilities(configSpec.Process.Capabilities.Bounding, c.CapAdd, c.CapDrop, nil, false) + caplist, err = capabilities.MergeCapabilities(configSpec.Process.Capabilities.Bounding, c.CapAdd, c.CapDrop) if err != nil { return err } @@ -129,7 +129,7 @@ func (c *SecurityConfig) ConfigureGenerator(g *generate.Generator, user *UserCon configSpec.Process.Capabilities.Effective = caplist configSpec.Process.Capabilities.Ambient = caplist if useNotRoot(user.User) { - caplist, err = caps.TweakCapabilities(bounding, c.CapAdd, c.CapDrop, nil, false) + caplist, err = capabilities.MergeCapabilities(bounding, c.CapAdd, c.CapDrop) if err != nil { return err } diff --git a/pkg/util/utils.go b/pkg/util/utils.go index 6aa3c221e..4a52ea68d 100644 --- a/pkg/util/utils.go +++ b/pkg/util/utils.go @@ -18,9 +18,9 @@ import ( "github.com/containers/libpod/pkg/errorhandling" "github.com/containers/libpod/pkg/namespaces" "github.com/containers/libpod/pkg/rootless" + "github.com/containers/libpod/pkg/signal" "github.com/containers/storage" "github.com/containers/storage/pkg/idtools" - "github.com/docker/docker/pkg/signal" v1 "github.com/opencontainers/image-spec/specs-go/v1" "github.com/pkg/errors" "github.com/sirupsen/logrus" |