devicemapper: Probe what filesystem to use when mounting
Docker-DCO-1.1-Signed-off-by: Alexander Larsson <alexl@redhat.com> (github: alexlarsson)
This commit is contained in:
parent
7f5ba068f4
commit
10083f4140
2 changed files with 54 additions and 2 deletions
|
@ -921,11 +921,16 @@ func (devices *DeviceSet) MountDevice(hash, path, mountLabel string) error {
|
|||
|
||||
var flags uintptr = syscall.MS_MGC_VAL
|
||||
|
||||
fstype, err := ProbeFsType(info.DevName())
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
mountOptions := label.FormatMountLabel("discard", mountLabel)
|
||||
err = syscall.Mount(info.DevName(), path, "ext4", flags, mountOptions)
|
||||
err = syscall.Mount(info.DevName(), path, fstype, flags, mountOptions)
|
||||
if err != nil && err == syscall.EINVAL {
|
||||
mountOptions = label.FormatMountLabel("", mountLabel)
|
||||
err = syscall.Mount(info.DevName(), path, "ext4", flags, mountOptions)
|
||||
err = syscall.Mount(info.DevName(), path, fstype, flags, mountOptions)
|
||||
}
|
||||
if err != nil {
|
||||
return fmt.Errorf("Error mounting '%s' on '%s': %s", info.DevName(), path, err)
|
||||
|
|
|
@ -3,6 +3,8 @@
|
|||
package devmapper
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"syscall"
|
||||
|
@ -27,3 +29,48 @@ func Mounted(mountpoint string) (bool, error) {
|
|||
parentSt := parent.Sys().(*syscall.Stat_t)
|
||||
return mntpointSt.Dev != parentSt.Dev, nil
|
||||
}
|
||||
|
||||
type probeData struct {
|
||||
fsName string
|
||||
magic string
|
||||
offset uint64
|
||||
}
|
||||
|
||||
func ProbeFsType(device string) (string, error) {
|
||||
probes := []probeData{
|
||||
{"btrfs", "_BHRfS_M", 0x10040},
|
||||
{"ext4", "\123\357", 0x438},
|
||||
{"xfs", "XFSB", 0},
|
||||
}
|
||||
|
||||
maxLen := uint64(0)
|
||||
for _, p := range probes {
|
||||
l := p.offset + uint64(len(p.magic))
|
||||
if l > maxLen {
|
||||
maxLen = l
|
||||
}
|
||||
}
|
||||
|
||||
file, err := os.Open(device)
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
|
||||
buffer := make([]byte, maxLen)
|
||||
l, err := file.Read(buffer)
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
file.Close()
|
||||
if uint64(l) != maxLen {
|
||||
return "", fmt.Errorf("unable to detect filesystem type of %s, short read", device)
|
||||
}
|
||||
|
||||
for _, p := range probes {
|
||||
if bytes.Equal([]byte(p.magic), buffer[p.offset:p.offset+uint64(len(p.magic))]) {
|
||||
return p.fsName, nil
|
||||
}
|
||||
}
|
||||
|
||||
return "", fmt.Errorf("Unknown filesystem type on %s", device)
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue