Browse Source

fix(fs): make check on NOCOW

Yicheng Qin 11 years ago
parent
commit
375aeb57af
3 changed files with 24 additions and 13 deletions
  1. 1 1
      etcd/etcd.go
  2. 17 5
      pkg/fs/fs.go
  3. 6 7
      pkg/fs/fs_test.go

+ 1 - 1
etcd/etcd.go

@@ -105,7 +105,7 @@ func (e *Etcd) Run() {
 
 
 	// Set NOCOW for data directory in btrfs
 	// Set NOCOW for data directory in btrfs
 	if fs.IsBtrfs(e.Config.DataDir) {
 	if fs.IsBtrfs(e.Config.DataDir) {
-		fs.SetNOCOW(e.Config.DataDir)
+		fs.SetNOCOWDir(e.Config.DataDir)
 	}
 	}
 
 
 	var mbName string
 	var mbName string

+ 17 - 5
pkg/fs/fs.go

@@ -39,23 +39,35 @@ func IsBtrfs(path string) bool {
 	return true
 	return true
 }
 }
 
 
-// SetNOCOW sets NOCOW flag for the file
-func SetNOCOW(path string) {
+// SetNOCOWDir sets NOCOW flag for the directory
+func SetNOCOWDir(path string) error {
 	file, err := os.Open(path)
 	file, err := os.Open(path)
 	if err != nil {
 	if err != nil {
 		log.Warnf("Failed to open %v: %v", path, err)
 		log.Warnf("Failed to open %v: %v", path, err)
-		return
+		return err
 	}
 	}
 	defer file.Close()
 	defer file.Close()
+
+	fileinfo, err := file.Stat()
+	if err != nil {
+		log.Warnf("Failed to stat %v: %v", path, err)
+		return err
+	}
+	if !fileinfo.IsDir() {
+		log.Infof("Skip NOCOW setting for non directory")
+		return nil
+	}
+
 	var attr int
 	var attr int
 	if _, _, errno := syscall.Syscall(syscall.SYS_IOCTL, file.Fd(), FS_IOC_GETFLAGS, uintptr(unsafe.Pointer(&attr))); errno != 0 {
 	if _, _, errno := syscall.Syscall(syscall.SYS_IOCTL, file.Fd(), FS_IOC_GETFLAGS, uintptr(unsafe.Pointer(&attr))); errno != 0 {
 		log.Warnf("Failed to get file flags: %v", errno.Error())
 		log.Warnf("Failed to get file flags: %v", errno.Error())
-		return
+		return errno
 	}
 	}
 	attr |= FS_NOCOW_FL
 	attr |= FS_NOCOW_FL
 	if _, _, errno := syscall.Syscall(syscall.SYS_IOCTL, file.Fd(), FS_IOC_SETFLAGS, uintptr(unsafe.Pointer(&attr))); errno != 0 {
 	if _, _, errno := syscall.Syscall(syscall.SYS_IOCTL, file.Fd(), FS_IOC_SETFLAGS, uintptr(unsafe.Pointer(&attr))); errno != 0 {
 		log.Warnf("Failed to set file flags: %v", errno.Error())
 		log.Warnf("Failed to set file flags: %v", errno.Error())
-		return
+		return errno
 	}
 	}
 	log.Infof("Set NOCOW to path %v succeeded", path)
 	log.Infof("Set NOCOW to path %v succeeded", path)
+	return nil
 }
 }

+ 6 - 7
pkg/fs/fs_test.go

@@ -9,16 +9,15 @@ import (
 )
 )
 
 
 func TestSetNOCOW(t *testing.T) {
 func TestSetNOCOW(t *testing.T) {
-	f, err := ioutil.TempFile(".", "etcdtest")
+	name, err := ioutil.TempDir(".", "etcdtest")
 	if err != nil {
 	if err != nil {
-		t.Fatal("Failed creating temp file")
+		t.Fatal("Failed creating temp dir")
 	}
 	}
-	f.Close()
-	defer os.Remove(f.Name())
+	defer os.Remove(name)
 
 
-	if IsBtrfs(f.Name()) {
-		SetNOCOW(f.Name())
-		cmd := exec.Command("lsattr", f.Name())
+	if IsBtrfs(name) {
+		SetNOCOWDir(name)
+		cmd := exec.Command("lsattr", name)
 		out, err := cmd.Output()
 		out, err := cmd.Output()
 		if err != nil {
 		if err != nil {
 			t.Fatal("Failed executing lsattr")
 			t.Fatal("Failed executing lsattr")