コード例 #1
1
ファイル: main.go プロジェクト: wxdublin/Dominator
func unshareAndBind(workingRootDir string) bool {
	if *unshare {
		// Re-exec myself using the unshare syscall while on a locked thread.
		// This hack is required because syscall.Unshare() operates on only one
		// thread in the process, and Go switches execution between threads
		// randomly. Thus, the namespace can be suddenly switched for running
		// code. This is an aspect of Go that was not well thought out.
		runtime.LockOSThread()
		err := syscall.Unshare(syscall.CLONE_NEWNS)
		if err != nil {
			fmt.Printf("Unable to unshare mount namesace\t%s\n", err)
			return false
		}
		args := append(os.Args, "-unshare=false")
		err = syscall.Exec(args[0], args, os.Environ())
		if err != nil {
			fmt.Printf("Unable to Exec:%s\t%s\n", args[0], err)
			return false
		}
	}
	err := syscall.Mount("none", "/", "", syscall.MS_REC|syscall.MS_PRIVATE, "")
	if err != nil {
		fmt.Printf("Unable to set mount sharing to private\t%s\n", err)
		return false
	}
	syscall.Unmount(workingRootDir, 0)
	err = syscall.Mount(*rootDir, workingRootDir, "", syscall.MS_BIND, "")
	if err != nil {
		fmt.Printf("Unable to bind mount %s to %s\t%s\n",
			*rootDir, workingRootDir, err)
		return false
	}
	return true
}
コード例 #2
0
ファイル: root.go プロジェクト: coderjoe/os
func switchRoot(rootfs, subdir string, rmUsr bool) error {
	if err := syscall.Unmount(config.OEM, 0); err != nil {
		log.Debugf("Not umounting OEM: %v", err)
	}

	if subdir != "" {
		fullRootfs := path.Join(rootfs, subdir)
		if _, err := os.Stat(fullRootfs); os.IsNotExist(err) {
			if err := os.MkdirAll(fullRootfs, 0755); err != nil {
				log.Errorf("Failed to create directory %s: %v", fullRootfs, err)
				return err
			}
		}

		log.Debugf("Bind mounting mount %s to %s", fullRootfs, rootfs)
		if err := syscall.Mount(fullRootfs, rootfs, "", syscall.MS_BIND, ""); err != nil {
			log.Errorf("Failed to bind mount subdir for %s: %v", fullRootfs, err)
			return err
		}
	}

	for _, i := range []string{"/dev", "/sys", "/proc", "/run"} {
		log.Debugf("Moving mount %s to %s", i, path.Join(rootfs, i))
		if err := os.MkdirAll(path.Join(rootfs, i), 0755); err != nil {
			return err
		}
		if err := syscall.Mount(i, path.Join(rootfs, i), "", syscall.MS_MOVE, ""); err != nil {
			return err
		}
	}

	if err := copyMoveRoot(rootfs, rmUsr); err != nil {
		return err
	}

	log.Debugf("chdir %s", rootfs)
	if err := syscall.Chdir(rootfs); err != nil {
		return err
	}

	log.Debugf("mount MS_MOVE %s", rootfs)
	if err := syscall.Mount(rootfs, "/", "", syscall.MS_MOVE, ""); err != nil {
		return err
	}

	log.Debug("chroot .")
	if err := syscall.Chroot("."); err != nil {
		return err
	}

	log.Debug("chdir /")
	if err := syscall.Chdir("/"); err != nil {
		return err
	}

	log.Debugf("Successfully moved to new root at %s", path.Join(rootfs, subdir))
	os.Unsetenv("DOCKER_RAMDISK")

	return nil
}
コード例 #3
0
ファイル: devices.go プロジェクト: jsavikko/lxd
func deviceMountDisk(srcPath string, dstPath string, readonly bool, recursive bool) error {
	var err error

	// Prepare the mount flags
	flags := 0
	if readonly {
		flags |= syscall.MS_RDONLY
	}

	// Detect the filesystem
	fstype := "none"
	if deviceIsBlockdev(srcPath) {
		fstype, err = shared.BlockFsDetect(srcPath)
		if err != nil {
			return err
		}
	} else {
		flags |= syscall.MS_BIND
		if recursive {
			flags |= syscall.MS_REC
		}
	}

	// Mount the filesystem
	if err = syscall.Mount(srcPath, dstPath, fstype, uintptr(flags), ""); err != nil {
		return fmt.Errorf("Unable to mount %s at %s: %s", srcPath, dstPath, err)
	}

	flags = syscall.MS_REC | syscall.MS_SLAVE
	if err = syscall.Mount("", dstPath, "", uintptr(flags), ""); err != nil {
		return fmt.Errorf("unable to make mount %s private: %s", dstPath, err)
	}

	return nil
}
コード例 #4
0
ファイル: daemon.go プロジェクト: mickydelfavero/lxd
func setupSharedMounts() error {
	path := shared.VarPath("shmounts")

	isShared, err := shared.IsOnSharedMount(path)
	if err != nil {
		return err
	}

	if isShared {
		// / may already be ms-shared, or shmounts may have
		// been mounted by a previous lxd run
		return nil
	}

	if err := syscall.Mount(path, path, "none", syscall.MS_BIND, ""); err != nil {
		return err
	}

	var flags uintptr = syscall.MS_SHARED | syscall.MS_REC
	if err := syscall.Mount(path, path, "none", flags, ""); err != nil {
		return err
	}

	return nil
}
コード例 #5
0
ファイル: exec_linux.go プロジェクト: kangkot/nomad
// ConfigureTaskDir creates the necessary directory structure for a proper
// chroot. cleanTaskDir should be called after.
func (e *LinuxExecutor) ConfigureTaskDir(taskName string, alloc *allocdir.AllocDir) error {
	e.taskName = taskName
	e.allocDir = alloc.AllocDir

	taskDir, ok := alloc.TaskDirs[taskName]
	if !ok {
		fmt.Errorf("Couldn't find task directory for task %v", taskName)
	}
	e.taskDir = taskDir

	if err := alloc.MountSharedDir(taskName); err != nil {
		return err
	}

	// Embed ourselves if this is a test. This needs to be done so the test
	// binary is inside the chroot.
	if isTest(&e.cmd) {
		bin := e.cmd.Args[0]
		alloc.Embed(taskName, map[string]string{bin: bin})
	}

	if err := alloc.Embed(taskName, chrootEnv); err != nil {
		return err
	}

	// Mount dev
	dev := filepath.Join(taskDir, "dev")
	if !e.pathExists(dev) {
		if err := os.Mkdir(dev, 0777); err != nil {
			return fmt.Errorf("Mkdir(%v) failed: %v", dev, err)
		}

		if err := syscall.Mount("", dev, "devtmpfs", syscall.MS_RDONLY, ""); err != nil {
			return fmt.Errorf("Couldn't mount /dev to %v: %v", dev, err)
		}
	}

	// Mount proc
	proc := filepath.Join(taskDir, "proc")
	if !e.pathExists(proc) {
		if err := os.Mkdir(proc, 0777); err != nil {
			return fmt.Errorf("Mkdir(%v) failed: %v", proc, err)
		}

		if err := syscall.Mount("", proc, "proc", syscall.MS_RDONLY, ""); err != nil {
			return fmt.Errorf("Couldn't mount /proc to %v: %v", proc, err)
		}
	}

	// Set the tasks AllocDir environment variable.
	env, err := environment.ParseFromList(e.cmd.Env)
	if err != nil {
		return err
	}
	env.SetAllocDir(filepath.Join("/", allocdir.SharedAllocName))
	env.SetTaskLocalDir(filepath.Join("/", allocdir.TaskLocal))
	e.cmd.Env = env.List()

	return nil
}
コード例 #6
0
ファイル: container_unix.go プロジェクト: ai-traders/docker
func (container *Container) setupIpcDirs() error {
	shmPath, err := container.shmPath()
	if err != nil {
		return err
	}

	if err := os.MkdirAll(shmPath, 0700); err != nil {
		return err
	}

	if err := syscall.Mount("shm", shmPath, "tmpfs", uintptr(syscall.MS_NOEXEC|syscall.MS_NOSUID|syscall.MS_NODEV), label.FormatMountLabel("mode=1777,size=65536k", container.getMountLabel())); err != nil {
		return fmt.Errorf("mounting shm tmpfs: %s", err)
	}

	mqueuePath, err := container.mqueuePath()
	if err != nil {
		return err
	}

	if err := os.MkdirAll(mqueuePath, 0700); err != nil {
		return err
	}

	if err := syscall.Mount("mqueue", mqueuePath, "mqueue", uintptr(syscall.MS_NOEXEC|syscall.MS_NOSUID|syscall.MS_NODEV), ""); err != nil {
		return fmt.Errorf("mounting mqueue mqueue : %s", err)
	}

	return nil
}
コード例 #7
0
ファイル: init.go プロジェクト: beginnor/docker
// InitializeMountNamespace sets up the devices, mount points, and filesystems for use inside a
// new mount namespace.
func InitializeMountNamespace(rootfs, console string, sysReadonly bool, mountConfig *MountConfig) error {
	var (
		err  error
		flag = syscall.MS_PRIVATE
	)
	if mountConfig.NoPivotRoot {
		flag = syscall.MS_SLAVE
	}
	if err := syscall.Mount("", "/", "", uintptr(flag|syscall.MS_REC), ""); err != nil {
		return fmt.Errorf("mounting / with flags %X %s", (flag | syscall.MS_REC), err)
	}
	if err := syscall.Mount(rootfs, rootfs, "bind", syscall.MS_BIND|syscall.MS_REC, ""); err != nil {
		return fmt.Errorf("mouting %s as bind %s", rootfs, err)
	}
	if err := mountSystem(rootfs, sysReadonly, mountConfig); err != nil {
		return fmt.Errorf("mount system %s", err)
	}
	if err := setupBindmounts(rootfs, mountConfig); err != nil {
		return fmt.Errorf("bind mounts %s", err)
	}
	if err := nodes.CreateDeviceNodes(rootfs, mountConfig.DeviceNodes); err != nil {
		return fmt.Errorf("create device nodes %s", err)
	}
	if err := SetupPtmx(rootfs, console, mountConfig.MountLabel); err != nil {
		return err
	}

	// stdin, stdout and stderr could be pointing to /dev/null from parent namespace.
	// Re-open them inside this namespace.
	if err := reOpenDevNull(rootfs); err != nil {
		return fmt.Errorf("Failed to reopen /dev/null %s", err)
	}

	if err := setupDevSymlinks(rootfs); err != nil {
		return fmt.Errorf("dev symlinks %s", err)
	}

	if err := syscall.Chdir(rootfs); err != nil {
		return fmt.Errorf("chdir into %s %s", rootfs, err)
	}

	if mountConfig.NoPivotRoot {
		err = MsMoveRoot(rootfs)
	} else {
		err = PivotRoot(rootfs)
	}
	if err != nil {
		return err
	}

	if mountConfig.ReadonlyFs {
		if err := SetReadonly(); err != nil {
			return fmt.Errorf("set readonly %s", err)
		}
	}

	syscall.Umask(0022)

	return nil
}
コード例 #8
0
ファイル: rootfs_linux.go プロジェクト: jfrazelle/runc
// Do the mount operation followed by additional mounts required to take care
// of propagation flags.
func mountPropagate(m *configs.Mount, rootfs string, mountLabel string) error {
	var (
		dest  = m.Destination
		data  = label.FormatMountLabel(m.Data, mountLabel)
		flags = m.Flags
	)
	if libcontainerUtils.CleanPath(dest) == "/dev" {
		flags &= ^syscall.MS_RDONLY
	}

	copyUp := m.Extensions&configs.EXT_COPYUP == configs.EXT_COPYUP
	if !(copyUp || strings.HasPrefix(dest, rootfs)) {
		dest = filepath.Join(rootfs, dest)
	}

	if err := syscall.Mount(m.Source, dest, m.Device, uintptr(flags), data); err != nil {
		return err
	}

	for _, pflag := range m.PropagationFlags {
		if err := syscall.Mount("", dest, "", uintptr(pflag), ""); err != nil {
			return err
		}
	}
	return nil
}
コード例 #9
0
ファイル: container.go プロジェクト: seedubb/minimega
func containerSetupRoot(fsPath string) error {
	err := syscall.Mount("", "/", "", syscall.MS_SLAVE|syscall.MS_REC, "")
	if err != nil {
		return err
	}
	return syscall.Mount(fsPath, fsPath, "bind", syscall.MS_BIND|syscall.MS_REC, "")
}
コード例 #10
0
ファイル: playground.go プロジェクト: rhenium/poe
func PlaygroundCreate(systemdir, envdir string) (string, error) {
	basedir := POE_TEMPORARY_BASE + "/" + strconv.Itoa(os.Getpid())
	if _, err := os.Stat(POE_TEMPORARY_BASE); err == nil {
		if err := os.RemoveAll(basedir); err != nil {
			return "", err
		}
	}
	if err := os.MkdirAll(basedir, 0755); err != nil {
		return "", err
	}

	if err := syscall.Mount("none", basedir, "tmpfs", syscall.MS_NOSUID, "size=32m"); err != nil {
		return "", err
	}
	workdir := basedir + "/work"
	if err := os.Mkdir(workdir, 0755); err != nil {
		return "", err
	}
	upperdir := basedir + "/upper"
	if err := os.Mkdir(upperdir, 0755); err != nil {
		return "", err
	}
	mergeddir := basedir + "/merged"
	if err := os.Mkdir(mergeddir, 0755); err != nil {
		return "", err
	}

	opts := fmt.Sprintf("lowerdir=%s:%s,upperdir=%s,workdir=%s", envdir, systemdir, upperdir, workdir)
	if err := syscall.Mount("none", mergeddir, "overlay", syscall.MS_NOSUID, opts); err != nil {
		return "", err
	}

	return mergeddir, nil
}
コード例 #11
0
ファイル: alloc_dir_linux.go プロジェクト: achanda/nomad
// MountSpecialDirs mounts the dev and proc file system from the host to the
// chroot
func (d *AllocDir) MountSpecialDirs(taskDir string) error {
	// Mount dev
	dev := filepath.Join(taskDir, "dev")
	if !d.pathExists(dev) {
		if err := os.MkdirAll(dev, 0777); err != nil {
			return fmt.Errorf("Mkdir(%v) failed: %v", dev, err)
		}

		if err := syscall.Mount("none", dev, "devtmpfs", syscall.MS_RDONLY, ""); err != nil {
			return fmt.Errorf("Couldn't mount /dev to %v: %v", dev, err)
		}
	}

	// Mount proc
	proc := filepath.Join(taskDir, "proc")
	if !d.pathExists(proc) {
		if err := os.MkdirAll(proc, 0777); err != nil {
			return fmt.Errorf("Mkdir(%v) failed: %v", proc, err)
		}

		if err := syscall.Mount("none", proc, "proc", syscall.MS_RDONLY, ""); err != nil {
			return fmt.Errorf("Couldn't mount /proc to %v: %v", proc, err)
		}
	}

	return nil
}
コード例 #12
0
ファイル: rootfs.go プロジェクト: drptbl/oz
func setupRootfs(fsys *fs.Filesystem) error {
	if err := os.MkdirAll(fsys.Root(), 0755); err != nil {
		return fmt.Errorf("could not create rootfs path '%s': %v", fsys.Root(), err)
	}

	if err := syscall.Mount("", "/", "", syscall.MS_PRIVATE|syscall.MS_REC, ""); err != nil {
		return fmt.Errorf("failed to set MS_PRIVATE on '%s': %v", "/", err)
	}

	flags := uintptr(syscall.MS_NOSUID | syscall.MS_NOEXEC | syscall.MS_NODEV)
	if err := syscall.Mount("", fsys.Root(), "tmpfs", flags, "mode=755,gid=0"); err != nil {
		return fmt.Errorf("failed to mount tmpfs on '%s': %v", fsys.Root(), err)
	}

	if err := syscall.Mount("", fsys.Root(), "", syscall.MS_PRIVATE, ""); err != nil {
		return fmt.Errorf("failed to set MS_PRIVATE on '%s': %v", fsys.Root(), err)
	}

	for _, p := range basicBindDirs {
		if err := fsys.BindPath(p, fs.BindReadOnly, nil); err != nil {
			return fmt.Errorf("failed to bind directory '%s': %v", p, err)
		}
	}

	for _, p := range basicEmptyDirs {
		if err := fsys.CreateEmptyDir(p); err != nil {
			return fmt.Errorf("failed to create empty directory '%s': %v", p, err)
		}
	}

	dp := path.Join(fsys.Root(), "dev")
	if err := syscall.Mount("", dp, "tmpfs", syscall.MS_NOSUID|syscall.MS_NOEXEC, "mode=755"); err != nil {
		return err

	}
	for _, d := range basicDevices {
		if err := fsys.CreateDevice(d.path, d.dev, d.mode); err != nil {
			return err
		}
	}

	for _, sl := range append(basicSymlinks, deviceSymlinks...) {
		if err := fsys.CreateSymlink(sl[0], sl[1]); err != nil {
			return err
		}
	}

	if err := fsys.CreateBlacklistPaths(); err != nil {
		return err
	}

	for _, bl := range basicBlacklist {
		if err := fsys.BlacklistPath(bl, nil); err != nil {
			return err
		}
	}
	return nil
}
コード例 #13
0
ファイル: rootfs_linux.go プロジェクト: jfrazelle/runc
// maskPath masks the top of the specified path inside a container to avoid
// security issues from processes reading information from non-namespace aware
// mounts ( proc/kcore ).
// For files, maskPath bind mounts /dev/null over the top of the specified path.
// For directories, maskPath mounts read-only tmpfs over the top of the specified path.
func maskPath(path string) error {
	if err := syscall.Mount("/dev/null", path, "", syscall.MS_BIND, ""); err != nil && !os.IsNotExist(err) {
		if err == syscall.ENOTDIR {
			return syscall.Mount("tmpfs", path, "tmpfs", syscall.MS_RDONLY, "")
		}
		return err
	}
	return nil
}
コード例 #14
0
ファイル: kvm.go プロジェクト: coderhaoxin/rkt
func doBindMount(source, destination string, readOnly bool) error {
	if err := syscall.Mount(source, destination, "bind", syscall.MS_BIND, ""); err != nil {
		return err
	}
	if readOnly {
		return syscall.Mount(source, destination, "bind", syscall.MS_REMOUNT|syscall.MS_RDONLY|syscall.MS_BIND, "")
	}
	return nil
}
コード例 #15
0
ファイル: aufs.go プロジェクト: sulochan/hyper
func aufsMount(ro []string, rw, target, mountLabel string) (err error) {
	defer func() {
		if err != nil {
			aufsUnmount(target)
		}
	}()

	// Mount options are clipped to page size(4096 bytes). If there are more
	// layers then these are remounted individually using append.

	offset := 54
	if useDirperm() {
		offset += len("dirperm1")
	}
	b := make([]byte, syscall.Getpagesize()-len(mountLabel)-offset) // room for xino & mountLabel
	bp := copy(b, fmt.Sprintf("br:%s=rw", rw))

	firstMount := true
	i := 0

	for {
		for ; i < len(ro); i++ {
			layer := fmt.Sprintf(":%s=ro+wh", ro[i])

			if firstMount {
				if bp+len(layer) > len(b) {
					break
				}
				bp += copy(b[bp:], layer)
			} else {
				data := utils.FormatMountLabel(fmt.Sprintf("append%s", layer), mountLabel)
				if err = syscall.Mount("none", target, "aufs", MsRemount, data); err != nil {
					return
				}
			}
		}

		if firstMount {
			opts := "dio,xino=/dev/shm/aufs.xino"
			if useDirperm() {
				opts += ",dirperm1"
			}
			data := utils.FormatMountLabel(fmt.Sprintf("%s,%s", string(b[:bp]), opts), mountLabel)
			if err = syscall.Mount("none", target, "aufs", 0, data); err != nil {
				return
			}
			firstMount = false
		}

		if i == len(ro) {
			break
		}
	}

	return
}
コード例 #16
0
ファイル: rootfs_linux.go プロジェクト: wking/runc
func prepareRoot(config *configs.Config) error {
	flag := syscall.MS_SLAVE | syscall.MS_REC
	if config.Privatefs {
		flag = syscall.MS_PRIVATE | syscall.MS_REC
	}
	if err := syscall.Mount("", "/", "", uintptr(flag), ""); err != nil {
		return err
	}
	return syscall.Mount(config.Rootfs, config.Rootfs, "bind", syscall.MS_BIND|syscall.MS_REC, "")
}
コード例 #17
0
ファイル: container.go プロジェクト: seedubb/minimega
func containerMountDefaults(fsPath string) error {
	log.Debug("mountDefaults: %v", fsPath)

	var err error

	err = syscall.Mount("proc", filepath.Join(fsPath, "proc"), "proc", syscall.MS_NOEXEC|syscall.MS_NOSUID|syscall.MS_NODEV, "")
	if err != nil {
		log.Errorln(err)
		return err
	}

	err = syscall.Mount("tmpfs", filepath.Join(fsPath, "dev"), "tmpfs", syscall.MS_NOEXEC|syscall.MS_STRICTATIME, "mode=755")
	if err != nil {
		log.Errorln(err)
		return err
	}

	err = os.MkdirAll(filepath.Join(fsPath, "dev", "shm"), 0755)
	if err != nil {
		log.Errorln(err)
		return err
	}

	err = os.MkdirAll(filepath.Join(fsPath, "dev", "mqueue"), 0755)
	if err != nil {
		log.Errorln(err)
		return err
	}

	err = os.MkdirAll(filepath.Join(fsPath, "dev", "pts"), 0755)
	if err != nil {
		log.Errorln(err)
		return err
	}

	err = syscall.Mount("tmpfs", filepath.Join(fsPath, "dev", "shm"), "tmpfs", syscall.MS_NOEXEC|syscall.MS_NOSUID|syscall.MS_NODEV, "mode=1777,size=65536k")
	if err != nil {
		log.Errorln(err)
		return err
	}

	err = syscall.Mount("pts", filepath.Join(fsPath, "dev", "pts"), "devpts", syscall.MS_NOEXEC|syscall.MS_NOSUID, "newinstance,ptmxmode=666,gid=5,mode=620")
	if err != nil {
		log.Errorln(err)
		return err
	}

	err = syscall.Mount("sysfs", filepath.Join(fsPath, "sys"), "sysfs", syscall.MS_NOEXEC|syscall.MS_NOSUID|syscall.MS_NODEV|syscall.MS_RDONLY, "")
	if err != nil {
		log.Errorln(err)
		return err
	}

	return nil
}
コード例 #18
0
ファイル: deviceset.go プロジェクト: Crispy1975/deis
func (devices *DeviceSet) MountDevice(hash, path, mountLabel string) error {
	info, err := devices.lookupDevice(hash)
	if err != nil {
		return err
	}

	info.lock.Lock()
	defer info.lock.Unlock()

	devices.Lock()
	defer devices.Unlock()

	if info.mountCount > 0 {
		if path != info.mountPath {
			return fmt.Errorf("Trying to mount devmapper device in multple places (%s, %s)", info.mountPath, path)
		}

		info.mountCount++
		return nil
	}

	if err := devices.activateDeviceIfNeeded(info); err != nil {
		return fmt.Errorf("Error activating devmapper device for '%s': %s", hash, err)
	}

	var flags uintptr = syscall.MS_MGC_VAL

	fstype, err := ProbeFsType(info.DevName())
	if err != nil {
		return err
	}

	options := ""

	if fstype == "xfs" {
		// XFS needs nouuid or it can't mount filesystems with the same fs
		options = joinMountOptions(options, "nouuid")
	}

	options = joinMountOptions(options, devices.mountOptions)
	options = joinMountOptions(options, label.FormatMountLabel("", mountLabel))

	err = syscall.Mount(info.DevName(), path, fstype, flags, joinMountOptions("discard", options))
	if err != nil && err == syscall.EINVAL {
		err = syscall.Mount(info.DevName(), path, fstype, flags, options)
	}
	if err != nil {
		return fmt.Errorf("Error mounting '%s' on '%s': %s", info.DevName(), path, err)
	}

	info.mountCount = 1
	info.mountPath = path

	return nil
}
コード例 #19
0
ファイル: dm_test.go プロジェクト: m1911/hyper
func TestAttachFiles(t *testing.T) {
	Cleanup()
	if err := Init(); err != nil {
		t.Fatalf(err.Error())
	}
	if err := CreateNewDevice(containerId, devPrefix, dmRootDir); err != nil {
		t.Fatalf(err.Error())
	}
	parms := fmt.Sprintf("mkfs.ext4 \"/dev/mapper/%s-%s\"", devPrefix, containerId)
	if err := exec.Command("/bin/sh", "-c", parms).Run(); err != nil {
		t.Fatalf(err.Error())
	}

	var (
		flags       uintptr = syscall.MS_MGC_VAL
		idMountPath         = path.Join(dmRootDir, "mnt", containerId)
		rootFs              = path.Join(idMountPath, "rootfs")
		toDir               = "/"
		targetDir           = path.Join(rootFs, toDir)
		devFullName         = "/dev/mapper/" + devPrefix + "-" + containerId
	)
	if err := AttachFiles(containerId, devPrefix, "/etc/os-release", toDir, dmRootDir, "0755", "0", "0"); err != nil {
		t.Fatalf(err.Error())
	}

	fstype, err := ProbeFsType("/dev/mapper/dm-1:1-1234567-123")
	if err != nil {
		t.Fatalf(err.Error())
	}
	options := ""
	if fstype == "xfs" {
		// XFS needs nouuid or it can't mount filesystems with the same fs
		options = joinMountOptions(options, "nouuid")
	}

	err = syscall.Mount(devFullName, idMountPath, fstype, flags, joinMountOptions("discard", options))
	if err != nil && err == syscall.EINVAL {
		err = syscall.Mount(devFullName, idMountPath, fstype, flags, options)
	}
	if err != nil {
		t.Fatalf("Error mounting '%s' on '%s': %s", devFullName, idMountPath, err)
	}
	targetFile := targetDir + "/os-release"
	if _, err := os.Stat(targetFile); err != nil {
		t.Log(targetFile)
		t.Fatalf(err.Error())
	}
	syscall.Unmount(idMountPath, syscall.MNT_DETACH)
	defer func() {
		if err := Cleanup(); err != nil {
			t.Fatalf(err.Error())
		}
	}()
}
コード例 #20
0
ファイル: mounter_linux.go プロジェクト: 40a/bootkube
func mount(device, target, mType string, flag uintptr, data string) error {
	if err := syscall.Mount(device, target, mType, flag, data); err != nil {
		return err
	}

	// If we have a bind mount or remount, remount...
	if flag&syscall.MS_BIND == syscall.MS_BIND && flag&syscall.MS_RDONLY == syscall.MS_RDONLY {
		return syscall.Mount(device, target, mType, flag|syscall.MS_REMOUNT, data)
	}
	return nil
}
コード例 #21
0
ファイル: mount_linux.go プロジェクト: juito/hyper
func Mount(src, dst string, readOnly bool) error {
	if _, err := os.Stat(dst); os.IsNotExist(err) {
		os.MkdirAll(dst, 0755)
	}

	err := syscall.Mount(src, dst, "", syscall.MS_BIND|syscall.MS_REC, "")
	if err == nil && readOnly {
		err = syscall.Mount(src, dst, "", syscall.MS_BIND|syscall.MS_RDONLY|syscall.MS_REMOUNT|syscall.MS_REC, "")
	}
	return err
}
コード例 #22
0
ファイル: mount.go プロジェクト: NERSC/docker
func (m *Mount) bindMount(rootfs, mountLabel string) error {
	var (
		flags = syscall.MS_BIND | syscall.MS_REC
		dest  = filepath.Join(rootfs, m.Destination)
	)

	if !m.Writable {
		flags = flags | syscall.MS_RDONLY
	}

	if m.Slave {
		flags = flags | syscall.MS_SLAVE
	}

	stat, err := os.Stat(m.Source)
	if err != nil {
		return err
	}

	// FIXME: (crosbymichael) This does not belong here and should be done a layer above
	dest, err = symlink.FollowSymlinkInScope(dest, rootfs)
	if err != nil {
		return err
	}

	if err := createIfNotExists(dest, stat.IsDir()); err != nil {
		return fmt.Errorf("creating new bind mount target %s", err)
	}

	if err := syscall.Mount(m.Source, dest, "bind", uintptr(flags), ""); err != nil {
		return fmt.Errorf("mounting %s into %s %s", m.Source, dest, err)
	}

	if !m.Writable {
		if err := syscall.Mount(m.Source, dest, "bind", uintptr(flags|syscall.MS_REMOUNT), ""); err != nil {
			return fmt.Errorf("remounting %s into %s %s", m.Source, dest, err)
		}
	}

	if m.Relabel != "" {
		if err := label.Relabel(m.Source, mountLabel, m.Relabel); err != nil {
			return fmt.Errorf("relabeling %s to %s %s", m.Source, mountLabel, err)
		}
	}

	if m.Private {
		if err := syscall.Mount("", dest, "none", uintptr(syscall.MS_PRIVATE), ""); err != nil {
			return fmt.Errorf("mounting %s private %s", dest, err)
		}
	}

	return nil
}
コード例 #23
0
ファイル: rbd.go プロジェクト: Jimmy-Xu/learn-go
func (devices *RbdSet) MountDevice(hash, mountPoint, mountLabel string) error {
	info, err := devices.lookupDevice(hash)
	if err != nil {
		return err
	}

	info.lock.Lock()
	defer info.lock.Unlock()

	if info.mountCount > 0 {
		if mountPoint != info.mountPath {
			return fmt.Errorf("Trying to mount rbd device in multple places (%s, %s)", info.mountPath, info.Device)
		}

		info.mountCount++
		return nil
	}

	log.Debugf("[rbdset] Mount image %s with device %s to %s", info.Hash, info.Device, info.mountPath)
	if err := devices.mapImageToRbdDevice(info); err != nil {
		return err
	}

	var flags uintptr = syscall.MS_MGC_VAL

	fstype, err := ProbeFsType(info.Device)
	if err != nil {
		return err
	}

	options := ""

	if fstype == "xfs" {
		// XFS needs nouuid or it can't mount filesystems with the same fs
		options = joinMountOptions(options, "nouuid")
	}

	options = joinMountOptions(options, devices.mountOptions)
	options = joinMountOptions(options, label.FormatMountLabel("", mountLabel))

	err = syscall.Mount(info.Device, mountPoint, fstype, flags, joinMountOptions("discard", options))
	if err != nil && err == syscall.EINVAL {
		err = syscall.Mount(info.Device, mountPoint, fstype, flags, options)
	}
	if err != nil {
		return fmt.Errorf("Error mounting '%s' on '%s': %s", info.Device, mountPoint, err)
	}

	info.mountCount = 1
	info.mountPath = mountPoint

	return nil
}
コード例 #24
0
ファイル: veth.go プロジェクト: pombredanne/geard
// SetupNamespaceMountDir prepares a new root for use as a mount
// source for bind mounting namespace fd to an outside path
func SetupNamespaceMountDir(root string) error {
	if err := os.MkdirAll(root, 0666); err != nil {
		return err
	}
	// make sure mounts are not unmounted by other mnt namespaces
	if err := syscall.Mount("", root, "none", syscall.MS_SHARED|syscall.MS_REC, ""); err != nil && err != syscall.EINVAL {
		return err
	}
	if err := syscall.Mount(root, root, "none", syscall.MS_BIND, ""); err != nil {
		return err
	}
	return nil
}
コード例 #25
0
ファイル: exec_linux.go プロジェクト: riddopic/nomad
func (e *LinuxExecutor) ConfigureTaskDir(taskName string, alloc *allocdir.AllocDir) error {
	e.taskName = taskName
	taskDir, ok := alloc.TaskDirs[taskName]
	if !ok {
		fmt.Errorf("Couldn't find task directory for task %v", taskName)
	}
	e.taskDir = taskDir

	if err := alloc.MountSharedDir(taskName); err != nil {
		return err
	}

	if err := alloc.Embed(taskName, chrootEnv); err != nil {
		return err
	}

	// Mount dev
	dev := filepath.Join(taskDir, "dev")
	if err := os.Mkdir(dev, 0777); err != nil {
		return fmt.Errorf("Mkdir(%v) failed: %v", dev, err)
	}

	if err := syscall.Mount("", dev, "devtmpfs", syscall.MS_RDONLY, ""); err != nil {
		return fmt.Errorf("Couldn't mount /dev to %v: %v", dev, err)
	}

	// Mount proc
	proc := filepath.Join(taskDir, "proc")
	if err := os.Mkdir(proc, 0777); err != nil {
		return fmt.Errorf("Mkdir(%v) failed: %v", proc, err)
	}

	if err := syscall.Mount("", proc, "proc", syscall.MS_RDONLY, ""); err != nil {
		return fmt.Errorf("Couldn't mount /proc to %v: %v", proc, err)
	}

	// Set the tasks AllocDir environment variable.
	env, err := environment.ParseFromList(e.Cmd.Env)
	if err != nil {
		return err
	}
	env.SetAllocDir(filepath.Join("/", allocdir.SharedAllocName))
	env.SetTaskLocalDir(filepath.Join("/", allocdir.TaskLocal))
	e.Cmd.Env = env.List()

	e.alloc = alloc
	e.mounts = true
	return nil
}
コード例 #26
0
ファイル: rootfs_linux.go プロジェクト: pirater/os
func prepareRoot(config *configs.Config) error {
	flag := syscall.MS_SLAVE | syscall.MS_REC
	if config.RootPropagation != 0 {
		flag = config.RootPropagation
	}
	if err := syscall.Mount("", "/", "", uintptr(flag), ""); err != nil {
		return err
	}

	if err := rootfsParentMountPrivate(config); err != nil {
		return err
	}

	return syscall.Mount(config.Rootfs, config.Rootfs, "bind", syscall.MS_BIND|syscall.MS_REC, "")
}
コード例 #27
0
ファイル: dm.go プロジェクト: ZJU-SEL/hyper
func InjectFile(src io.Reader, containerId, devPrefix, target, rootPath string, perm, uid, gid int) error {
	if containerId == "" {
		return fmt.Errorf("Please make sure the arguments are not NULL!\n")
	}
	permDir := perm | 0111
	// Define the basic directory, need to get them via the 'info' command
	var (
		mntPath = fmt.Sprintf("%s/mnt/", rootPath)
		devName = fmt.Sprintf("%s-%s", devPrefix, containerId)
	)

	// Get the mount point for the container ID
	idMountPath := path.Join(mntPath, containerId)
	rootFs := path.Join(idMountPath, "rootfs")
	targetFile := path.Join(rootFs, target)

	// Whether we have the mounter directory
	if _, err := os.Stat(idMountPath); err != nil && os.IsNotExist(err) {
		if err := os.MkdirAll(idMountPath, os.FileMode(permDir)); err != nil {
			return err
		}
	}

	// Mount the block device to that mount point
	var flags uintptr = syscall.MS_MGC_VAL
	devFullName := fmt.Sprintf("/dev/mapper/%s", devName)
	fstype, err := ProbeFsType(devFullName)
	if err != nil {
		return err
	}
	glog.V(3).Infof("The filesytem type is %s", fstype)
	options := ""
	if fstype == "xfs" {
		// XFS needs nouuid or it can't mount filesystems with the same fs
		options = joinMountOptions(options, "nouuid")
	}

	err = syscall.Mount(devFullName, idMountPath, fstype, flags, joinMountOptions("discard", options))
	if err != nil && err == syscall.EINVAL {
		err = syscall.Mount(devFullName, idMountPath, fstype, flags, options)
	}
	if err != nil {
		return fmt.Errorf("Error mounting '%s' on '%s': %s", devFullName, idMountPath, err)
	}
	defer syscall.Unmount(idMountPath, syscall.MNT_DETACH)

	return storage.WriteFile(src, targetFile, perm, uid, gid)
}
コード例 #28
0
ファイル: run.go プロジェクト: krieg/rkt
// overlayRender renders the image that corresponds to the given hash using the
// overlay filesystem.
// It writes the manifest in the specified directory and mounts an overlay
// filesystem from the cached tree of the image as rootfs.
func overlayRender(cfg RunConfig, img types.Hash, cdir string, dest string) error {
	if err := writeManifest(cfg.CommonConfig, img, dest); err != nil {
		return err
	}

	destRootfs := path.Join(dest, "rootfs")
	if err := os.MkdirAll(destRootfs, 0755); err != nil {
		return err
	}

	cachedTreePath := cfg.Store.GetTreeStoreRootFS(img.String())

	overlayDir := path.Join(cdir, "overlay", img.String())
	if err := os.MkdirAll(overlayDir, 0755); err != nil {
		return err
	}

	upperDir := path.Join(overlayDir, "upper")
	if err := os.MkdirAll(upperDir, 0755); err != nil {
		return err
	}
	workDir := path.Join(overlayDir, "work")
	if err := os.MkdirAll(workDir, 0755); err != nil {
		return err
	}

	opts := fmt.Sprintf("lowerdir=%s,upperdir=%s,workdir=%s", cachedTreePath, upperDir, workDir)
	opts = label.FormatMountLabel(opts, cfg.MountLabel)
	if err := syscall.Mount("overlay", destRootfs, "overlay", 0, opts); err != nil {
		return fmt.Errorf("error mounting: %v", err)
	}

	return nil
}
コード例 #29
0
ファイル: rootfs_linux.go プロジェクト: pirater/os
// Make parent mount private if it was shared
func rootfsParentMountPrivate(config *configs.Config) error {
	sharedMount := false

	parentMount, optionalOpts, err := getParentMount(config.Rootfs)
	if err != nil {
		return err
	}

	optsSplit := strings.Split(optionalOpts, " ")
	for _, opt := range optsSplit {
		if strings.HasPrefix(opt, "shared:") {
			sharedMount = true
			break
		}
	}

	// Make parent mount PRIVATE if it was shared. It is needed for two
	// reasons. First of all pivot_root() will fail if parent mount is
	// shared. Secondly when we bind mount rootfs it will propagate to
	// parent namespace and we don't want that to happen.
	if sharedMount {
		return syscall.Mount("", parentMount, "", syscall.MS_PRIVATE, "")
	}

	return nil
}
コード例 #30
0
ファイル: rootfs_linux.go プロジェクト: pirater/os
func pivotRoot(rootfs, pivotBaseDir string) error {
	if pivotBaseDir == "" {
		pivotBaseDir = "/"
	}
	tmpDir := filepath.Join(rootfs, pivotBaseDir)
	if err := os.MkdirAll(tmpDir, 0755); err != nil {
		return fmt.Errorf("can't create tmp dir %s, error %v", tmpDir, err)
	}
	pivotDir, err := ioutil.TempDir(tmpDir, ".pivot_root")
	if err != nil {
		return fmt.Errorf("can't create pivot_root dir %s, error %v", pivotDir, err)
	}
	if err := syscall.PivotRoot(rootfs, pivotDir); err != nil {
		return fmt.Errorf("pivot_root %s", err)
	}
	if err := syscall.Chdir("/"); err != nil {
		return fmt.Errorf("chdir / %s", err)
	}
	// path to pivot dir now changed, update
	pivotDir = filepath.Join(pivotBaseDir, filepath.Base(pivotDir))

	// Make pivotDir rprivate to make sure any of the unmounts don't
	// propagate to parent.
	if err := syscall.Mount("", pivotDir, "", syscall.MS_PRIVATE|syscall.MS_REC, ""); err != nil {
		return err
	}

	if err := syscall.Unmount(pivotDir, syscall.MNT_DETACH); err != nil {
		return fmt.Errorf("unmount pivot_root dir %s", err)
	}
	return os.Remove(pivotDir)
}