Skip to content

Commit c1a18c3

Browse files
Fallback scenario for mount_setattr
Based on kernel version, but it possible to implement it on checking syscall existence. Signed-off-by: Alexey Perevalov <[email protected]>
1 parent 25ec10e commit c1a18c3

File tree

1 file changed

+62
-10
lines changed

1 file changed

+62
-10
lines changed

libcontainer/rootfs_linux.go

Lines changed: 62 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -378,6 +378,52 @@ func doTmpfsCopyUp(m *configs.Mount, rootfs, mountLabel string) (Err error) {
378378
})
379379
}
380380

381+
// TODO move it to appropriate place
382+
func getVersion(release [65]int8) (major int, middle int, err error) {
383+
buf := make([]byte, 0, len(release))
384+
385+
for _, v := range release {
386+
if v == 0x00 {
387+
break
388+
}
389+
390+
if major == 0 && v == '.' {
391+
major, err = strconv.Atoi(string(buf))
392+
if err != nil {
393+
return 0, 0, err
394+
}
395+
buf = make([]byte, 0, len(release))
396+
continue
397+
}
398+
if major != 0 && v == '.' {
399+
middle, err = strconv.Atoi(string(buf))
400+
if err != nil {
401+
return 0, 0, err
402+
}
403+
return major, middle, nil
404+
}
405+
buf = append(buf, byte(v))
406+
}
407+
return 0, 0, fmt.Errorf("Can't parse uname")
408+
}
409+
410+
func properVersionForIDMapMounts() bool {
411+
var uname syscall.Utsname
412+
if err := syscall.Uname(&uname); err != nil {
413+
logrus.Errorf("Uname failed: %d", err)
414+
return false
415+
}
416+
417+
major, middle, err := getVersion(uname.Release)
418+
419+
if err != nil {
420+
logrus.Errorf("getVersion failed: %d", err)
421+
return false
422+
}
423+
424+
return major >= 5 && middle >= 16
425+
}
426+
381427
func mountToRootfs(m *configs.Mount, c *mountConfig) error {
382428
rootfs := c.root
383429
mountLabel := c.label
@@ -446,18 +492,24 @@ func mountToRootfs(m *configs.Mount, c *mountConfig) error {
446492
return err
447493
}
448494

449-
treeFd, err := openTree(-int(unix.EBADF), m.Source, uint(OPEN_TREE_CLONE|OPEN_TREE_CLOEXEC|unix.AT_EMPTY_PATH|unix.AT_RECURSIVE))
450-
if err != nil || treeFd < 0 {
451-
return err
452-
}
495+
if properVersionForIDMapMounts() {
496+
treeFd, err := openTree(-int(unix.EBADF), m.Source, uint(OPEN_TREE_CLONE|OPEN_TREE_CLOEXEC|unix.AT_EMPTY_PATH|unix.AT_RECURSIVE))
497+
if err != nil || treeFd < 0 {
498+
return err
499+
}
453500

454-
err = moveMount(treeFd, "", AT_FDCWD, dest, MOVE_MOUNT_F_EMPTY_PATH)
455-
if err != nil {
456-
return err
457-
}
501+
err = moveMount(treeFd, "", AT_FDCWD, dest, MOVE_MOUNT_F_EMPTY_PATH)
502+
if err != nil {
503+
return err
504+
}
458505

459-
if err := mountIDMapMapped(m, treeFd); err != nil {
460-
return err
506+
if err := mountIDMapMapped(m, treeFd); err != nil {
507+
return err
508+
}
509+
} else {
510+
if err := mountPropagate(m, rootfs, mountLabel, mountFd); err != nil {
511+
return err
512+
}
461513
}
462514

463515
// bind mount won't change mount options, we need remount to make mount options effective.

0 commit comments

Comments
 (0)