WIP moving to nsini

Docker-DCO-1.1-Signed-off-by: Michael Crosby <michael@crosbymichael.com> (github: crosbymichael)
This commit is contained in:
Michael Crosby 2014-02-18 18:15:41 -08:00
parent c98df9e60a
commit d2612d7018
3 changed files with 52 additions and 52 deletions

View File

@ -6,6 +6,7 @@ import (
"fmt" "fmt"
"github.com/dotcloud/docker/pkg/libcontainer" "github.com/dotcloud/docker/pkg/libcontainer"
"github.com/dotcloud/docker/pkg/libcontainer/namespaces" "github.com/dotcloud/docker/pkg/libcontainer/namespaces"
"github.com/dotcloud/docker/pkg/libcontainer/namespaces/nsinit"
"github.com/dotcloud/docker/pkg/libcontainer/network" "github.com/dotcloud/docker/pkg/libcontainer/network"
"github.com/dotcloud/docker/pkg/libcontainer/utils" "github.com/dotcloud/docker/pkg/libcontainer/utils"
"os" "os"
@ -15,15 +16,26 @@ var (
displayPid bool displayPid bool
newCommand string newCommand string
usrNet bool usrNet bool
masterFd int
console string
) )
func init() { func init() {
flag.BoolVar(&displayPid, "pid", false, "display the pid before waiting") flag.BoolVar(&displayPid, "pid", false, "display the pid before waiting")
flag.StringVar(&newCommand, "cmd", "/bin/bash", "command to run in the existing namespace") flag.StringVar(&newCommand, "cmd", "/bin/bash", "command to run in the existing namespace")
flag.BoolVar(&usrNet, "net", false, "user a net namespace") flag.BoolVar(&usrNet, "net", false, "user a net namespace")
flag.IntVar(&masterFd, "master", 0, "master fd")
flag.StringVar(&console, "console", "", "console path")
flag.Parse() flag.Parse()
} }
func nsinitFunc(container *libcontainer.Container) error {
container.Master = uintptr(masterFd)
container.Console = console
return nsinit.InitNamespace(container)
}
func exec(container *libcontainer.Container) error { func exec(container *libcontainer.Container) error {
var ( var (
netFile *os.File netFile *os.File
@ -39,7 +51,7 @@ func exec(container *libcontainer.Container) error {
container.NetNsFd = netFile.Fd() container.NetNsFd = netFile.Fd()
} }
pid, err := namespaces.Exec(container) pid, err := namespaces.ExecContainer(container)
if err != nil { if err != nil {
return fmt.Errorf("error exec container %s", err) return fmt.Errorf("error exec container %s", err)
} }
@ -87,39 +99,39 @@ func execIn(container *libcontainer.Container) error {
} }
func createNet(config *libcontainer.Network) error { func createNet(config *libcontainer.Network) error {
root := "/root/nsroot"
if err := network.SetupNamespaceMountDir(root); err != nil {
return err
}
nspath := root + "/test"
if err := network.CreateNetworkNamespace(nspath); err != nil {
return nil
}
if err := network.CreateVethPair("veth0", config.TempVethName); err != nil {
return err
}
if err := network.SetInterfaceMaster("veth0", config.Bridge); err != nil {
return err
}
if err := network.InterfaceUp("veth0"); err != nil {
return err
}
f, err := os.Open(nspath)
if err != nil {
return err
}
defer f.Close()
if err := network.SetInterfaceInNamespaceFd("veth1", int(f.Fd())); err != nil {
return err
}
/* /*
if err := network.SetupVethInsideNamespace(f.Fd(), config); err != nil { root := "/root/nsroot"
if err := network.SetupNamespaceMountDir(root); err != nil {
return err return err
} }
nspath := root + "/test"
if err := network.CreateNetworkNamespace(nspath); err != nil {
return nil
}
if err := network.CreateVethPair("veth0", config.TempVethName); err != nil {
return err
}
if err := network.SetInterfaceMaster("veth0", config.Bridge); err != nil {
return err
}
if err := network.InterfaceUp("veth0"); err != nil {
return err
}
f, err := os.Open(nspath)
if err != nil {
return err
}
defer f.Close()
if err := network.SetInterfaceInNamespaceFd("veth1", int(f.Fd())); err != nil {
return err
}
if err := network.SetupVethInsideNamespace(f.Fd(), config); err != nil {
return err
}
*/ */
return nil return nil
} }
@ -133,7 +145,7 @@ func main() {
var ( var (
err error err error
cliCmd = flag.Arg(0) cliCmd = flag.Arg(0)
config = flag.Arg(1) config = "/root/development/gocode/src/github.com/dotcloud/docker/pkg/libcontainer/container.json" //flag.Arg(1)
) )
f, err := os.Open(config) f, err := os.Open(config)
if err != nil { if err != nil {
@ -149,6 +161,8 @@ func main() {
f.Close() f.Close()
switch cliCmd { switch cliCmd {
case "init":
err = nsinitFunc(container)
case "exec": case "exec":
err = exec(container) err = exec(container)
case "execin": case "execin":

View File

@ -12,6 +12,8 @@ import (
"log" "log"
"os" "os"
"os/exec" "os/exec"
"path/filepath"
"strconv"
"syscall" "syscall"
) )
@ -37,16 +39,15 @@ func ExecContainer(container *libcontainer.Container) (pid int, err error) {
if err != nil { if err != nil {
return -1, err return -1, err
} }
container.Console = console nsinit := filepath.Join(container.RootFs, ".nsinit")
container.Master = master.Fd()
// we need CLONE_VFORK so we can wait on the child // we need CLONE_VFORK so we can wait on the child
flag := uintptr(getNamespaceFlags(container.Namespaces) | CLONE_VFORK) flag := uintptr(getNamespaceFlags(container.Namespaces) | CLONE_VFORK)
command := exec.Command("/.nsinit") command := exec.Command(nsinit, "init", "-master", strconv.Itoa(int(master.Fd())), "-console", console)
command.SysProcAttr = &syscall.SysProcAttr{} command.SysProcAttr = &syscall.SysProcAttr{}
command.SysProcAttr.Cloneflags = flag command.SysProcAttr.Cloneflags = flag
command.SysProcAttr.Setctty = true // command.SysProcAttr.Setctty = true
if err := command.Start(); err != nil { if err := command.Start(); err != nil {
return -1, err return -1, err
@ -63,6 +64,7 @@ func ExecContainer(container *libcontainer.Container) (pid int, err error) {
log.Println(err) log.Println(err)
} }
}() }()
command.Wait()
return pid, nil return pid, nil
} }

View File

@ -3,7 +3,6 @@ package network
import ( import (
"fmt" "fmt"
"github.com/dotcloud/docker/pkg/libcontainer" "github.com/dotcloud/docker/pkg/libcontainer"
"github.com/dotcloud/docker/pkg/libcontainer/namespaces"
"os" "os"
"syscall" "syscall"
) )
@ -59,21 +58,6 @@ func SetupNamespaceMountDir(root string) error {
return nil return nil
} }
// CreateNetworkNamespace creates a new network namespace and binds it's fd
// at the binding path
func CreateNetworkNamespace(bindingPath string) error {
f, err := os.OpenFile(bindingPath, os.O_RDONLY|os.O_CREATE|os.O_EXCL, 0)
if err != nil {
return err
}
f.Close()
if err := namespaces.CreateNewNamespace(libcontainer.CLONE_NEWNET, bindingPath); err != nil {
return err
}
return nil
}
// DeleteNetworkNamespace unmounts the binding path and removes the // DeleteNetworkNamespace unmounts the binding path and removes the
// file so that no references to the fd are present and the network // file so that no references to the fd are present and the network
// namespace is automatically cleaned up // namespace is automatically cleaned up