diff options
-rw-r--r-- | libpod/runtime.go | 2 | ||||
-rw-r--r-- | pkg/api/handlers/compat/networks.go | 5 | ||||
-rw-r--r-- | pkg/api/handlers/libpod/networks.go | 2 | ||||
-rw-r--r-- | pkg/domain/entities/engine_container.go | 2 | ||||
-rw-r--r-- | pkg/domain/infra/abi/network.go | 7 | ||||
-rw-r--r-- | pkg/domain/infra/abi/system.go | 44 | ||||
-rw-r--r-- | pkg/domain/infra/tunnel/network.go | 4 | ||||
-rw-r--r-- | test/e2e/network_create_test.go | 9 | ||||
-rw-r--r-- | utils/utils.go | 42 |
9 files changed, 67 insertions, 50 deletions
diff --git a/libpod/runtime.go b/libpod/runtime.go index d2b3d36da..a2279e56d 100644 --- a/libpod/runtime.go +++ b/libpod/runtime.go @@ -35,6 +35,7 @@ import ( "github.com/containers/podman/v3/pkg/rootless" "github.com/containers/podman/v3/pkg/systemd" "github.com/containers/podman/v3/pkg/util" + "github.com/containers/podman/v3/utils" "github.com/containers/storage" "github.com/containers/storage/pkg/unshare" "github.com/docker/docker/pkg/namesgenerator" @@ -543,6 +544,7 @@ func makeRuntime(ctx context.Context, runtime *Runtime) (retErr error) { return err } if became { + utils.MovePauseProcessToScope(pausePid) os.Exit(ret) } } diff --git a/pkg/api/handlers/compat/networks.go b/pkg/api/handlers/compat/networks.go index 28727a22b..b1456ed9e 100644 --- a/pkg/api/handlers/compat/networks.go +++ b/pkg/api/handlers/compat/networks.go @@ -224,7 +224,8 @@ func CreateNetwork(w http.ResponseWriter, r *http.Request) { // FIXME can we use the IPAM driver and options? } - network, err := runtime.Network().NetworkCreate(network) + ic := abi.ContainerEngine{Libpod: runtime} + newNetwork, err := ic.NetworkCreate(r.Context(), network) if err != nil { utils.InternalServerError(w, err) return @@ -234,7 +235,7 @@ func CreateNetwork(w http.ResponseWriter, r *http.Request) { ID string `json:"Id"` Warning []string }{ - ID: network.ID, + ID: newNetwork.ID, } utils.WriteResponse(w, http.StatusCreated, body) } diff --git a/pkg/api/handlers/libpod/networks.go b/pkg/api/handlers/libpod/networks.go index fcd8e0231..1f7f2e26c 100644 --- a/pkg/api/handlers/libpod/networks.go +++ b/pkg/api/handlers/libpod/networks.go @@ -25,7 +25,7 @@ func CreateNetwork(w http.ResponseWriter, r *http.Request) { } ic := abi.ContainerEngine{Libpod: runtime} - report, err := ic.Libpod.Network().NetworkCreate(network) + report, err := ic.NetworkCreate(r.Context(), network) if err != nil { utils.InternalServerError(w, err) return diff --git a/pkg/domain/entities/engine_container.go b/pkg/domain/entities/engine_container.go index b916d6fc6..383e42098 100644 --- a/pkg/domain/entities/engine_container.go +++ b/pkg/domain/entities/engine_container.go @@ -59,7 +59,7 @@ type ContainerEngine interface { HealthCheckRun(ctx context.Context, nameOrID string, options HealthCheckOptions) (*define.HealthCheckResults, error) Info(ctx context.Context) (*define.Info, error) NetworkConnect(ctx context.Context, networkname string, options NetworkConnectOptions) error - NetworkCreate(ctx context.Context, network types.Network) (*NetworkCreateReport, error) + NetworkCreate(ctx context.Context, network types.Network) (*types.Network, error) NetworkDisconnect(ctx context.Context, networkname string, options NetworkDisconnectOptions) error NetworkExists(ctx context.Context, networkname string) (*BoolReport, error) NetworkInspect(ctx context.Context, namesOrIds []string, options InspectOptions) ([]types.Network, []error, error) diff --git a/pkg/domain/infra/abi/network.go b/pkg/domain/infra/abi/network.go index 45d2c6925..d792226a8 100644 --- a/pkg/domain/infra/abi/network.go +++ b/pkg/domain/infra/abi/network.go @@ -107,12 +107,15 @@ func (ic *ContainerEngine) NetworkRm(ctx context.Context, namesOrIds []string, o return reports, nil } -func (ic *ContainerEngine) NetworkCreate(ctx context.Context, network types.Network) (*entities.NetworkCreateReport, error) { +func (ic *ContainerEngine) NetworkCreate(ctx context.Context, network types.Network) (*types.Network, error) { + if util.StringInSlice(network.Name, []string{"none", "host", "bridge", "private", "slirp4netns", "container", "ns"}) { + return nil, errors.Errorf("cannot create network with name %q because it conflicts with a valid network mode", network.Name) + } network, err := ic.Libpod.Network().NetworkCreate(network) if err != nil { return nil, err } - return &entities.NetworkCreateReport{Name: network.Name}, nil + return &network, nil } // NetworkDisconnect removes a container from a given network diff --git a/pkg/domain/infra/abi/system.go b/pkg/domain/infra/abi/system.go index bc98edd06..e326f26a8 100644 --- a/pkg/domain/infra/abi/system.go +++ b/pkg/domain/infra/abi/system.go @@ -3,16 +3,12 @@ package abi import ( "context" "fmt" - "io/ioutil" "net/url" "os" "os/exec" "path/filepath" - "strconv" - "strings" "github.com/containers/common/pkg/config" - "github.com/containers/podman/v3/libpod" "github.com/containers/podman/v3/libpod/define" "github.com/containers/podman/v3/pkg/cgroups" "github.com/containers/podman/v3/pkg/domain/entities" @@ -72,11 +68,7 @@ func (ic *ContainerEngine) SetupRootless(_ context.Context, noMoveProcess bool) if err != nil { return err } - - initCommand, err := ioutil.ReadFile("/proc/1/comm") - // On errors, default to systemd - runsUnderSystemd := err != nil || strings.TrimRight(string(initCommand), "\n") == "systemd" - + runsUnderSystemd := utils.RunsOnSystemd() unitName := fmt.Sprintf("podman-%d.scope", os.Getpid()) if runsUnderSystemd || conf.Engine.CgroupManager == config.SystemdCgroupsManager { if err := utils.RunUnderSystemdScope(os.Getpid(), "user.slice", unitName); err != nil { @@ -120,18 +112,7 @@ func (ic *ContainerEngine) SetupRootless(_ context.Context, noMoveProcess bool) } became, ret, err = rootless.TryJoinFromFilePaths(pausePidPath, true, paths) - - if err := movePauseProcessToScope(ic.Libpod); err != nil { - conf, err2 := ic.Config(context.Background()) - if err2 != nil { - return err - } - if conf.Engine.CgroupManager == config.SystemdCgroupsManager { - logrus.Warnf("Failed to add pause process to systemd sandbox cgroup: %v", err) - } else { - logrus.Debugf("Failed to add pause process to systemd sandbox cgroup: %v", err) - } - } + utils.MovePauseProcessToScope(pausePidPath) if err != nil { logrus.Error(errors.Wrapf(err, "invalid internal status, try resetting the pause process with %q", os.Args[0]+" system migrate")) os.Exit(1) @@ -142,27 +123,6 @@ func (ic *ContainerEngine) SetupRootless(_ context.Context, noMoveProcess bool) return nil } -func movePauseProcessToScope(r *libpod.Runtime) error { - tmpDir, err := r.TmpDir() - if err != nil { - return err - } - pausePidPath, err := util.GetRootlessPauseProcessPidPathGivenDir(tmpDir) - if err != nil { - return errors.Wrapf(err, "could not get pause process pid file path") - } - data, err := ioutil.ReadFile(pausePidPath) - if err != nil { - return errors.Wrapf(err, "cannot read pause pid file") - } - pid, err := strconv.ParseUint(string(data), 10, 0) - if err != nil { - return errors.Wrapf(err, "cannot parse pid file %s", pausePidPath) - } - - return utils.RunUnderSystemdScope(int(pid), "user.slice", "podman-pause.scope") -} - // SystemPrune removes unused data from the system. Pruning pods, containers, volumes and images. func (ic *ContainerEngine) SystemPrune(ctx context.Context, options entities.SystemPruneOptions) (*entities.SystemPruneReport, error) { var systemPruneReport = new(entities.SystemPruneReport) diff --git a/pkg/domain/infra/tunnel/network.go b/pkg/domain/infra/tunnel/network.go index 711c2e00c..6f227f565 100644 --- a/pkg/domain/infra/tunnel/network.go +++ b/pkg/domain/infra/tunnel/network.go @@ -62,12 +62,12 @@ func (ic *ContainerEngine) NetworkRm(ctx context.Context, namesOrIds []string, o return reports, nil } -func (ic *ContainerEngine) NetworkCreate(ctx context.Context, net types.Network) (*entities.NetworkCreateReport, error) { +func (ic *ContainerEngine) NetworkCreate(ctx context.Context, net types.Network) (*types.Network, error) { net, err := network.Create(ic.ClientCtx, &net) if err != nil { return nil, err } - return &entities.NetworkCreateReport{Name: net.Name}, nil + return &net, nil } // NetworkDisconnect removes a container from a given network diff --git a/test/e2e/network_create_test.go b/test/e2e/network_create_test.go index d419a701d..ae9f112b5 100644 --- a/test/e2e/network_create_test.go +++ b/test/e2e/network_create_test.go @@ -343,4 +343,13 @@ var _ = Describe("Podman network create", func() { Expect(nc.OutputToString()).ToNot(ContainSubstring("dnsname")) }) + It("podman network create with invalid name", func() { + for _, name := range []string{"none", "host", "bridge", "private", "slirp4netns", "container", "ns"} { + nc := podmanTest.Podman([]string{"network", "create", name}) + nc.WaitWithDefaultTimeout() + Expect(nc).To(Exit(125)) + Expect(nc.ErrorToString()).To(ContainSubstring("cannot create network with name %q because it conflicts with a valid network mode", name)) + } + }) + }) diff --git a/utils/utils.go b/utils/utils.go index 2e415130e..185ac4865 100644 --- a/utils/utils.go +++ b/utils/utils.go @@ -4,10 +4,12 @@ import ( "bytes" "fmt" "io" + "io/ioutil" "os" "os/exec" "strconv" "strings" + "sync" "github.com/containers/podman/v3/libpod/define" "github.com/containers/storage/pkg/archive" @@ -155,3 +157,43 @@ func RemoveScientificNotationFromFloat(x float64) (float64, error) { } return result, nil } + +var ( + runsOnSystemdOnce sync.Once + runsOnSystemd bool +) + +// RunsOnSystemd returns whether the system is using systemd +func RunsOnSystemd() bool { + runsOnSystemdOnce.Do(func() { + initCommand, err := ioutil.ReadFile("/proc/1/comm") + // On errors, default to systemd + runsOnSystemd = err != nil || strings.TrimRight(string(initCommand), "\n") == "systemd" + }) + return runsOnSystemd +} + +func moveProcessToScope(pidPath, slice, scope string) error { + data, err := ioutil.ReadFile(pidPath) + if err != nil { + return errors.Wrapf(err, "cannot read pid file %s", pidPath) + } + pid, err := strconv.ParseUint(string(data), 10, 0) + if err != nil { + return errors.Wrapf(err, "cannot parse pid file %s", pidPath) + } + return RunUnderSystemdScope(int(pid), slice, scope) +} + +// MovePauseProcessToScope moves the pause process used for rootless mode to keep the namespaces alive to +// a separate scope. +func MovePauseProcessToScope(pausePidPath string) { + err := moveProcessToScope(pausePidPath, "user.slice", "podman-pause.scope") + if err != nil { + if RunsOnSystemd() { + logrus.Warnf("Failed to add pause process to systemd sandbox cgroup: %v", err) + } else { + logrus.Debugf("Failed to add pause process to systemd sandbox cgroup: %v", err) + } + } +} |