From a7b199253f7a517fd62f36a5d632efee3bac737e Mon Sep 17 00:00:00 2001 From: Dmitry Vyukov Date: Mon, 3 Jul 2017 14:00:47 +0200 Subject: all: use consistent file permissions Currently we have unix permissions for new files/dirs hardcoded throughout the code base. Some places use 0644, some - 0640, some - 0600 and a variety of other constants. Introduce osutil.MkdirAll/WriteFile that use the default permissions and use them throughout the code base. This makes permissions consistent and also allows to easily change the permissions later if we change our minds. Also merge pkg/fileutil into pkg/osutil as they become dependent on each other. The line between them was poorly defined anyway as both operate on files. --- pkg/config/config.go | 4 +- pkg/csource/csource_test.go | 4 +- pkg/db/db.go | 5 +- pkg/fileutil/fileutil.go | 107 ----------------------------------------- pkg/fileutil/fileutil_linux.go | 24 --------- pkg/fileutil/fileutil_test.go | 65 ------------------------- pkg/git/git.go | 2 +- pkg/ipc/ipc.go | 10 ++-- pkg/ipc/ipc_test.go | 4 +- pkg/kernel/kernel.go | 11 ++--- pkg/osutil/fileutil.go | 107 +++++++++++++++++++++++++++++++++++++++++ pkg/osutil/fileutil_linux.go | 24 +++++++++ pkg/osutil/fileutil_test.go | 65 +++++++++++++++++++++++++ pkg/osutil/osutil.go | 26 +++++++--- pkg/repro/repro.go | 6 +-- sys/syz-extract/extract.go | 4 +- syz-ci/manager.go | 9 ++-- syz-ci/syzupdater.go | 9 ++-- syz-gce/syz-gce.go | 10 ++-- syz-hub/state/state.go | 9 ++-- syz-manager/manager.go | 29 ++++++----- tools/syz-db/syz-db.go | 5 +- tools/syz-execprog/execprog.go | 3 +- tools/syz-upgrade/upgrade.go | 3 +- vm/kvm/kvm.go | 8 ++- vm/qemu/qemu.go | 3 +- vm/vm.go | 4 +- 27 files changed, 286 insertions(+), 274 deletions(-) delete mode 100644 pkg/fileutil/fileutil.go delete mode 100644 pkg/fileutil/fileutil_linux.go delete mode 100644 pkg/fileutil/fileutil_test.go create mode 100644 pkg/osutil/fileutil.go create mode 100644 pkg/osutil/fileutil_linux.go create mode 100644 pkg/osutil/fileutil_test.go diff --git a/pkg/config/config.go b/pkg/config/config.go index 537b9f3d6..c1a761e18 100644 --- a/pkg/config/config.go +++ b/pkg/config/config.go @@ -9,6 +9,8 @@ import ( "io/ioutil" "reflect" "strings" + + "github.com/google/syzkaller/pkg/osutil" ) func LoadFile(filename string, cfg interface{}) error { @@ -37,7 +39,7 @@ func SaveFile(filename string, cfg interface{}) error { if err != nil { return err } - return ioutil.WriteFile(filename, data, 0600) + return osutil.WriteFile(filename, data) } func checkUnknownFields(data []byte, typ reflect.Type) error { diff --git a/pkg/csource/csource_test.go b/pkg/csource/csource_test.go index 9357dcf65..dc703d37d 100644 --- a/pkg/csource/csource_test.go +++ b/pkg/csource/csource_test.go @@ -11,7 +11,7 @@ import ( "testing" "time" - "github.com/google/syzkaller/pkg/fileutil" + "github.com/google/syzkaller/pkg/osutil" "github.com/google/syzkaller/prog" ) @@ -123,7 +123,7 @@ func testOne(t *testing.T, p *prog.Prog, opts Options) { t.Logf("program:\n%s\n", p.Serialize()) t.Fatalf("%v", err) } - srcf, err := fileutil.WriteTempFile(src) + srcf, err := osutil.WriteTempFile(src) if err != nil { t.Logf("program:\n%s\n", p.Serialize()) t.Fatalf("%v", err) diff --git a/pkg/db/db.go b/pkg/db/db.go index 0277cb3d1..1ab76a29d 100644 --- a/pkg/db/db.go +++ b/pkg/db/db.go @@ -19,6 +19,7 @@ import ( "os" . "github.com/google/syzkaller/pkg/log" + "github.com/google/syzkaller/pkg/osutil" ) type DB struct { @@ -38,7 +39,7 @@ func Open(filename string) (*DB, error) { db := &DB{ filename: filename, } - f, err := os.OpenFile(db.filename, os.O_RDONLY|os.O_CREATE, 0640) + f, err := os.OpenFile(db.filename, os.O_RDONLY|os.O_CREATE, osutil.DefaultFilePerm) if err != nil { return nil, err } @@ -79,7 +80,7 @@ func (db *DB) Flush() error { if db.pending == nil { return nil } - f, err := os.OpenFile(db.filename, os.O_WRONLY|os.O_APPEND|os.O_CREATE, 0640) + f, err := os.OpenFile(db.filename, os.O_WRONLY|os.O_APPEND|os.O_CREATE, osutil.DefaultFilePerm) if err != nil { return err } diff --git a/pkg/fileutil/fileutil.go b/pkg/fileutil/fileutil.go deleted file mode 100644 index 056eee50f..000000000 --- a/pkg/fileutil/fileutil.go +++ /dev/null @@ -1,107 +0,0 @@ -// Copyright 2015 syzkaller project authors. All rights reserved. -// Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file. - -package fileutil - -import ( - "fmt" - "io" - "io/ioutil" - "os" - "path/filepath" - "strconv" - "syscall" -) - -// CopyFile atomically copies oldFile to newFile preserving permissions and modification time. -func CopyFile(oldFile, newFile string) error { - oldf, err := os.Open(oldFile) - if err != nil { - return err - } - defer oldf.Close() - stat, err := oldf.Stat() - if err != nil { - return err - } - tmpFile := newFile + ".tmp" - newf, err := os.OpenFile(tmpFile, os.O_WRONLY|os.O_CREATE|os.O_TRUNC, stat.Mode()&os.ModePerm) - if err != nil { - return err - } - defer newf.Close() - _, err = io.Copy(newf, oldf) - if err != nil { - return err - } - if err := newf.Close(); err != nil { - return err - } - if err := os.Chtimes(tmpFile, stat.ModTime(), stat.ModTime()); err != nil { - return err - } - return os.Rename(tmpFile, newFile) -} - -// WriteTempFile writes data to a temp file and returns its name. -func WriteTempFile(data []byte) (string, error) { - f, err := ioutil.TempFile("", "syzkaller") - if err != nil { - return "", fmt.Errorf("failed to create a temp file: %v", err) - } - if _, err := f.Write(data); err != nil { - f.Close() - os.Remove(f.Name()) - return "", fmt.Errorf("failed to write a temp file: %v", err) - } - f.Close() - return f.Name(), nil -} - -// ProcessTempDir creates a new temp dir in where and returns its path and an unique index. -// It also cleans up old, unused temp dirs after dead processes. -func ProcessTempDir(where string) (string, error) { - lk := filepath.Join(where, "instance-lock") - lkf, err := syscall.Open(lk, syscall.O_RDWR|syscall.O_CREAT, 0600) - if err != nil { - return "", err - } - defer syscall.Close(lkf) - if err := syscall.Flock(lkf, syscall.LOCK_EX); err != nil { - return "", err - } - defer syscall.Flock(lkf, syscall.LOCK_UN) - - for i := 0; i < 1e3; i++ { - path := filepath.Join(where, fmt.Sprintf("instance-%v", i)) - pidfile := filepath.Join(path, ".pid") - err := os.Mkdir(path, 0700) - if os.IsExist(err) { - // Try to clean up. - data, err := ioutil.ReadFile(pidfile) - if err == nil && len(data) > 0 { - pid, err := strconv.Atoi(string(data)) - if err == nil && pid > 1 { - if err := syscall.Kill(pid, 0); err == syscall.ESRCH { - if os.Remove(pidfile) == nil { - if os.RemoveAll(path) == nil { - i-- - continue - } - } - } - } - } - // If err != nil, assume that the pid file is not created yet. - continue - } - if err != nil { - return "", err - } - if err := ioutil.WriteFile(pidfile, []byte(strconv.Itoa(syscall.Getpid())), 0600); err != nil { - return "", err - } - return path, nil - } - return "", fmt.Errorf("too many live instances") -} diff --git a/pkg/fileutil/fileutil_linux.go b/pkg/fileutil/fileutil_linux.go deleted file mode 100644 index 217036256..000000000 --- a/pkg/fileutil/fileutil_linux.go +++ /dev/null @@ -1,24 +0,0 @@ -// Copyright 2017 syzkaller project authors. All rights reserved. -// Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file. - -package fileutil - -import ( - "io/ioutil" - "path/filepath" - "syscall" - "unsafe" -) - -// UmountAll recurusively unmounts all mounts in dir. -func UmountAll(dir string) { - files, _ := ioutil.ReadDir(dir) - for _, f := range files { - name := filepath.Join(dir, f.Name()) - if f.IsDir() { - UmountAll(name) - } - fn := []byte(name + "\x00") - syscall.Syscall(syscall.SYS_UMOUNT2, uintptr(unsafe.Pointer(&fn[0])), syscall.MNT_FORCE, 0) - } -} diff --git a/pkg/fileutil/fileutil_test.go b/pkg/fileutil/fileutil_test.go deleted file mode 100644 index d432ef5e7..000000000 --- a/pkg/fileutil/fileutil_test.go +++ /dev/null @@ -1,65 +0,0 @@ -// Copyright 2015 syzkaller project authors. All rights reserved. -// Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file. - -package fileutil - -import ( - "io/ioutil" - "os" - "path/filepath" - "strconv" - "sync" - "testing" -) - -func TestProcessTempDir(t *testing.T) { - for try := 0; try < 10; try++ { - func() { - tmp, err := ioutil.TempDir("", "syz") - if err != nil { - t.Fatalf("failed to create a temp dir: %v", err) - } - defer os.RemoveAll(tmp) - const P = 16 - // Pre-create half of the instances with stale pid. - var dirs []string - for i := 0; i < P/2; i++ { - dir, err := ProcessTempDir(tmp) - if err != nil { - t.Fatalf("failed to create process temp dir") - } - dirs = append(dirs, dir) - } - for _, dir := range dirs { - if err := ioutil.WriteFile(filepath.Join(dir, ".pid"), []byte(strconv.Itoa(999999999)), 0600); err != nil { - t.Fatalf("failed to write pid file: %v", err) - } - } - // Now request a bunch of instances concurrently. - done := make(chan bool) - allDirs := make(map[string]bool) - var mu sync.Mutex - for p := 0; p < P; p++ { - go func() { - defer func() { - done <- true - }() - dir, err := ProcessTempDir(tmp) - if err != nil { - t.Fatalf("failed to create process temp dir") - } - mu.Lock() - present := allDirs[dir] - allDirs[dir] = true - mu.Unlock() - if present { - t.Fatalf("duplicate dir %v", dir) - } - }() - } - for p := 0; p < P; p++ { - <-done - } - }() - } -} diff --git a/pkg/git/git.go b/pkg/git/git.go index 29ebcbadc..a3bdcec00 100644 --- a/pkg/git/git.go +++ b/pkg/git/git.go @@ -52,7 +52,7 @@ func clone(dir, repo, branch string) error { if err := os.RemoveAll(dir); err != nil { return fmt.Errorf("failed to remove repo dir: %v", err) } - if err := os.MkdirAll(dir, 0700); err != nil { + if err := osutil.MkdirAll(dir); err != nil { return fmt.Errorf("failed to create repo dir: %v", err) } args := []string{ diff --git a/pkg/ipc/ipc.go b/pkg/ipc/ipc.go index 6c68433b6..61d48d802 100644 --- a/pkg/ipc/ipc.go +++ b/pkg/ipc/ipc.go @@ -18,7 +18,7 @@ import ( "time" "unsafe" - "github.com/google/syzkaller/pkg/fileutil" + "github.com/google/syzkaller/pkg/osutil" "github.com/google/syzkaller/prog" ) @@ -357,7 +357,7 @@ func createMapping(size int) (f *os.File, mem []byte, err error) { } f.Close() fname := f.Name() - f, err = os.OpenFile(f.Name(), os.O_RDWR, 0) + f, err = os.OpenFile(f.Name(), os.O_RDWR, osutil.DefaultFilePerm) if err != nil { err = fmt.Errorf("failed to open shm file: %v", err) os.Remove(fname) @@ -506,7 +506,7 @@ func (c *command) close() { c.abort() c.wait() } - fileutil.UmountAll(c.dir) + osutil.UmountAll(c.dir) os.RemoveAll(c.dir) if c.inrp != nil { c.inrp.Close() @@ -669,10 +669,10 @@ func serializeUint64(buf []byte, v uint64) { var enableFaultOnce sync.Once func enableFaultInjection() { - if err := ioutil.WriteFile("/sys/kernel/debug/failslab/ignore-gfp-wait", []byte("N"), 0600); err != nil { + if err := osutil.WriteFile("/sys/kernel/debug/failslab/ignore-gfp-wait", []byte("N")); err != nil { panic(fmt.Sprintf("failed to write /sys/kernel/debug/failslab/ignore-gfp-wait: %v", err)) } - if err := ioutil.WriteFile("/sys/kernel/debug/fail_futex/ignore-private", []byte("N"), 0600); err != nil { + if err := osutil.WriteFile("/sys/kernel/debug/fail_futex/ignore-private", []byte("N")); err != nil { panic(fmt.Sprintf("failed to write /sys/kernel/debug/fail_futex/ignore-private: %v", err)) } } diff --git a/pkg/ipc/ipc_test.go b/pkg/ipc/ipc_test.go index b7d591d5d..68fbb94cd 100644 --- a/pkg/ipc/ipc_test.go +++ b/pkg/ipc/ipc_test.go @@ -11,7 +11,7 @@ import ( "time" "github.com/google/syzkaller/pkg/csource" - "github.com/google/syzkaller/pkg/fileutil" + "github.com/google/syzkaller/pkg/osutil" "github.com/google/syzkaller/prog" ) @@ -22,7 +22,7 @@ func buildExecutor(t *testing.T) string { } func buildSource(t *testing.T, src []byte) string { - tmp, err := fileutil.WriteTempFile(src) + tmp, err := osutil.WriteTempFile(src) if err != nil { t.Fatalf("%v", err) } diff --git a/pkg/kernel/kernel.go b/pkg/kernel/kernel.go index c38020b59..208b61815 100644 --- a/pkg/kernel/kernel.go +++ b/pkg/kernel/kernel.go @@ -21,12 +21,11 @@ import ( "strings" "time" - "github.com/google/syzkaller/pkg/fileutil" "github.com/google/syzkaller/pkg/osutil" ) func Build(dir, compiler, config string) error { - if err := fileutil.CopyFile(config, filepath.Join(dir, ".config")); err != nil { + if err := osutil.CopyFile(config, filepath.Join(dir, ".config")); err != nil { return fmt.Errorf("failed to write config file: %v", err) } return build(dir, compiler) @@ -37,7 +36,7 @@ func BuildWithPartConfig(dir, compiler, config string) error { const timeout = 10 * time.Minute // default timeout for command invocations os.Remove(filepath.Join(dir, ".config")) configFile := filepath.Join(dir, "syz.config") - if err := ioutil.WriteFile(configFile, []byte(config), 0600); err != nil { + if err := osutil.WriteFile(configFile, []byte(config)); err != nil { return fmt.Errorf("failed to write config file: %v", err) } defer os.Remove(configFile) @@ -77,17 +76,17 @@ func CreateImage(kernelDir, userspaceDir, image, sshkey string) error { } defer os.RemoveAll(tempDir) scriptFile := filepath.Join(tempDir, "create.sh") - if err := ioutil.WriteFile(scriptFile, []byte(createImageScript), 0700); err != nil { + if err := osutil.WriteExecFile(scriptFile, []byte(createImageScript)); err != nil { return fmt.Errorf("failed to write script file: %v", err) } bzImage := filepath.Join(kernelDir, filepath.FromSlash("arch/x86/boot/bzImage")) if _, err := osutil.RunCmd(time.Hour, tempDir, scriptFile, userspaceDir, bzImage); err != nil { return fmt.Errorf("image build failed: %v", err) } - if err := fileutil.CopyFile(filepath.Join(tempDir, "disk.raw"), image); err != nil { + if err := osutil.CopyFile(filepath.Join(tempDir, "disk.raw"), image); err != nil { return err } - if err := fileutil.CopyFile(filepath.Join(tempDir, "key"), sshkey); err != nil { + if err := osutil.CopyFile(filepath.Join(tempDir, "key"), sshkey); err != nil { return err } if err := os.Chmod(sshkey, 0600); err != nil { diff --git a/pkg/osutil/fileutil.go b/pkg/osutil/fileutil.go new file mode 100644 index 000000000..801453326 --- /dev/null +++ b/pkg/osutil/fileutil.go @@ -0,0 +1,107 @@ +// Copyright 2015 syzkaller project authors. All rights reserved. +// Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file. + +package osutil + +import ( + "fmt" + "io" + "io/ioutil" + "os" + "path/filepath" + "strconv" + "syscall" +) + +// CopyFile atomically copies oldFile to newFile preserving permissions and modification time. +func CopyFile(oldFile, newFile string) error { + oldf, err := os.Open(oldFile) + if err != nil { + return err + } + defer oldf.Close() + stat, err := oldf.Stat() + if err != nil { + return err + } + tmpFile := newFile + ".tmp" + newf, err := os.OpenFile(tmpFile, os.O_WRONLY|os.O_CREATE|os.O_TRUNC, stat.Mode()&os.ModePerm) + if err != nil { + return err + } + defer newf.Close() + _, err = io.Copy(newf, oldf) + if err != nil { + return err + } + if err := newf.Close(); err != nil { + return err + } + if err := os.Chtimes(tmpFile, stat.ModTime(), stat.ModTime()); err != nil { + return err + } + return os.Rename(tmpFile, newFile) +} + +// WriteTempFile writes data to a temp file and returns its name. +func WriteTempFile(data []byte) (string, error) { + f, err := ioutil.TempFile("", "syzkaller") + if err != nil { + return "", fmt.Errorf("failed to create a temp file: %v", err) + } + if _, err := f.Write(data); err != nil { + f.Close() + os.Remove(f.Name()) + return "", fmt.Errorf("failed to write a temp file: %v", err) + } + f.Close() + return f.Name(), nil +} + +// ProcessTempDir creates a new temp dir in where and returns its path and an unique index. +// It also cleans up old, unused temp dirs after dead processes. +func ProcessTempDir(where string) (string, error) { + lk := filepath.Join(where, "instance-lock") + lkf, err := syscall.Open(lk, syscall.O_RDWR|syscall.O_CREAT, DefaultFilePerm) + if err != nil { + return "", err + } + defer syscall.Close(lkf) + if err := syscall.Flock(lkf, syscall.LOCK_EX); err != nil { + return "", err + } + defer syscall.Flock(lkf, syscall.LOCK_UN) + + for i := 0; i < 1e3; i++ { + path := filepath.Join(where, fmt.Sprintf("instance-%v", i)) + pidfile := filepath.Join(path, ".pid") + err := os.Mkdir(path, DefaultDirPerm) + if os.IsExist(err) { + // Try to clean up. + data, err := ioutil.ReadFile(pidfile) + if err == nil && len(data) > 0 { + pid, err := strconv.Atoi(string(data)) + if err == nil && pid > 1 { + if err := syscall.Kill(pid, 0); err == syscall.ESRCH { + if os.Remove(pidfile) == nil { + if os.RemoveAll(path) == nil { + i-- + continue + } + } + } + } + } + // If err != nil, assume that the pid file is not created yet. + continue + } + if err != nil { + return "", err + } + if err := WriteFile(pidfile, []byte(strconv.Itoa(syscall.Getpid()))); err != nil { + return "", err + } + return path, nil + } + return "", fmt.Errorf("too many live instances") +} diff --git a/pkg/osutil/fileutil_linux.go b/pkg/osutil/fileutil_linux.go new file mode 100644 index 000000000..415c00353 --- /dev/null +++ b/pkg/osutil/fileutil_linux.go @@ -0,0 +1,24 @@ +// Copyright 2017 syzkaller project authors. All rights reserved. +// Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file. + +package osutil + +import ( + "io/ioutil" + "path/filepath" + "syscall" + "unsafe" +) + +// UmountAll recurusively unmounts all mounts in dir. +func UmountAll(dir string) { + files, _ := ioutil.ReadDir(dir) + for _, f := range files { + name := filepath.Join(dir, f.Name()) + if f.IsDir() { + UmountAll(name) + } + fn := []byte(name + "\x00") + syscall.Syscall(syscall.SYS_UMOUNT2, uintptr(unsafe.Pointer(&fn[0])), syscall.MNT_FORCE, 0) + } +} diff --git a/pkg/osutil/fileutil_test.go b/pkg/osutil/fileutil_test.go new file mode 100644 index 000000000..4db5c0d83 --- /dev/null +++ b/pkg/osutil/fileutil_test.go @@ -0,0 +1,65 @@ +// Copyright 2015 syzkaller project authors. All rights reserved. +// Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file. + +package osutil + +import ( + "io/ioutil" + "os" + "path/filepath" + "strconv" + "sync" + "testing" +) + +func TestProcessTempDir(t *testing.T) { + for try := 0; try < 10; try++ { + func() { + tmp, err := ioutil.TempDir("", "syz") + if err != nil { + t.Fatalf("failed to create a temp dir: %v", err) + } + defer os.RemoveAll(tmp) + const P = 16 + // Pre-create half of the instances with stale pid. + var dirs []string + for i := 0; i < P/2; i++ { + dir, err := ProcessTempDir(tmp) + if err != nil { + t.Fatalf("failed to create process temp dir") + } + dirs = append(dirs, dir) + } + for _, dir := range dirs { + if err := WriteFile(filepath.Join(dir, ".pid"), []byte(strconv.Itoa(999999999))); err != nil { + t.Fatalf("failed to write pid file: %v", err) + } + } + // Now request a bunch of instances concurrently. + done := make(chan bool) + allDirs := make(map[string]bool) + var mu sync.Mutex + for p := 0; p < P; p++ { + go func() { + defer func() { + done <- true + }() + dir, err := ProcessTempDir(tmp) + if err != nil { + t.Fatalf("failed to create process temp dir") + } + mu.Lock() + present := allDirs[dir] + allDirs[dir] = true + mu.Unlock() + if present { + t.Fatalf("duplicate dir %v", dir) + } + }() + } + for p := 0; p < P; p++ { + <-done + } + }() + } +} diff --git a/pkg/osutil/osutil.go b/pkg/osutil/osutil.go index b63fffc1e..4a411c38e 100644 --- a/pkg/osutil/osutil.go +++ b/pkg/osutil/osutil.go @@ -7,19 +7,19 @@ import ( "bytes" "fmt" "io" + "io/ioutil" "os" "os/exec" "os/signal" "path/filepath" "syscall" "time" - - "github.com/google/syzkaller/pkg/fileutil" ) const ( DefaultDirPerm = 0755 DefaultFilePerm = 0644 + DefaultExecPerm = 0755 ) // RunCmd runs "bin args..." in dir with timeout and returns its output. @@ -121,16 +121,16 @@ func CopyFiles(srcDir, dstDir string, files []string) error { if err := os.RemoveAll(tmpDir); err != nil { return err } - if err := os.MkdirAll(tmpDir, DefaultDirPerm); err != nil { + if err := MkdirAll(tmpDir); err != nil { return err } for _, f := range files { src := filepath.Join(srcDir, filepath.FromSlash(f)) dst := filepath.Join(tmpDir, filepath.FromSlash(f)) - if err := os.MkdirAll(filepath.Dir(dst), DefaultDirPerm); err != nil { + if err := MkdirAll(filepath.Dir(dst)); err != nil { return err } - if err := fileutil.CopyFile(src, dst); err != nil { + if err := CopyFile(src, dst); err != nil { return err } } @@ -147,13 +147,13 @@ func LinkFiles(srcDir, dstDir string, files []string) error { if err := os.RemoveAll(dstDir); err != nil { return err } - if err := os.MkdirAll(dstDir, DefaultDirPerm); err != nil { + if err := MkdirAll(dstDir); err != nil { return err } for _, f := range files { src := filepath.Join(srcDir, filepath.FromSlash(f)) dst := filepath.Join(dstDir, filepath.FromSlash(f)) - if err := os.MkdirAll(filepath.Dir(dst), DefaultDirPerm); err != nil { + if err := MkdirAll(filepath.Dir(dst)); err != nil { return err } if err := os.Link(src, dst); err != nil { @@ -162,3 +162,15 @@ func LinkFiles(srcDir, dstDir string, files []string) error { } return nil } + +func MkdirAll(dir string) error { + return os.MkdirAll(dir, DefaultDirPerm) +} + +func WriteFile(filename string, data []byte) error { + return ioutil.WriteFile(filename, data, DefaultFilePerm) +} + +func WriteExecFile(filename string, data []byte) error { + return ioutil.WriteFile(filename, data, DefaultExecPerm) +} diff --git a/pkg/repro/repro.go b/pkg/repro/repro.go index d3f4bc6cb..eb7316982 100644 --- a/pkg/repro/repro.go +++ b/pkg/repro/repro.go @@ -13,8 +13,8 @@ import ( "time" "github.com/google/syzkaller/pkg/csource" - "github.com/google/syzkaller/pkg/fileutil" . "github.com/google/syzkaller/pkg/log" + "github.com/google/syzkaller/pkg/osutil" "github.com/google/syzkaller/pkg/report" "github.com/google/syzkaller/prog" "github.com/google/syzkaller/syz-manager/mgrconfig" @@ -581,7 +581,7 @@ func (ctx *context) testProgs(entries []*prog.LogEntry, duration time.Duration, } pstr := encodeEntries(entries) - progFile, err := fileutil.WriteTempFile(pstr) + progFile, err := osutil.WriteTempFile(pstr) if err != nil { return false, err } @@ -620,7 +620,7 @@ func (ctx *context) testCProg(p *prog.Prog, duration time.Duration, opts csource if err != nil { return false, err } - srcf, err := fileutil.WriteTempFile(src) + srcf, err := osutil.WriteTempFile(src) if err != nil { return false, err } diff --git a/sys/syz-extract/extract.go b/sys/syz-extract/extract.go index 4972b6bbc..ad0f1f4a6 100644 --- a/sys/syz-extract/extract.go +++ b/sys/syz-extract/extract.go @@ -8,11 +8,11 @@ import ( "flag" "fmt" "io" - "io/ioutil" "os" "sort" "strings" + "github.com/google/syzkaller/pkg/osutil" . "github.com/google/syzkaller/sys/sysparser" ) @@ -69,7 +69,7 @@ func main() { out := new(bytes.Buffer) generateConsts(*flagArch, consts, out) - if err := ioutil.WriteFile(outname, out.Bytes(), 0660); err != nil { + if err := osutil.WriteFile(outname, out.Bytes()); err != nil { failf("failed to write output file: %v", err) } } diff --git a/syz-ci/manager.go b/syz-ci/manager.go index 1b5c500df..d4cbf8353 100644 --- a/syz-ci/manager.go +++ b/syz-ci/manager.go @@ -12,7 +12,6 @@ import ( "github.com/google/syzkaller/dashboard/dashapi" "github.com/google/syzkaller/pkg/config" - "github.com/google/syzkaller/pkg/fileutil" "github.com/google/syzkaller/pkg/git" "github.com/google/syzkaller/pkg/hash" "github.com/google/syzkaller/pkg/kernel" @@ -59,7 +58,7 @@ type Manager struct { func createManager(dash *dashapi.Dashboard, cfg *Config, mgrcfg *ManagerConfig, stop chan struct{}) *Manager { dir := osutil.Abs(filepath.Join("managers", mgrcfg.Name)) - if err := os.MkdirAll(dir, osutil.DefaultDirPerm); err != nil { + if err := osutil.MkdirAll(dir); err != nil { Fatal(err) } @@ -219,7 +218,7 @@ func (mgr *Manager) build() error { if err := os.RemoveAll(tmpDir); err != nil { return fmt.Errorf("failed to remove tmp dir: %v", err) } - if err := os.MkdirAll(tmpDir, osutil.DefaultDirPerm); err != nil { + if err := osutil.MkdirAll(tmpDir); err != nil { return fmt.Errorf("failed to create tmp dir: %v", err) } @@ -232,12 +231,12 @@ func (mgr *Manager) build() error { vmlinux := filepath.Join(mgr.kernelDir, "vmlinux") objDir := filepath.Join(tmpDir, "obj") - os.MkdirAll(objDir, osutil.DefaultDirPerm) + osutil.MkdirAll(objDir) if err := os.Rename(vmlinux, filepath.Join(objDir, "vmlinux")); err != nil { return fmt.Errorf("failed to rename vmlinux file: %v", err) } kernelConfig := filepath.Join(tmpDir, "kernel.config") - if err := fileutil.CopyFile(mgr.mgrcfg.Kernel_Config, kernelConfig); err != nil { + if err := osutil.CopyFile(mgr.mgrcfg.Kernel_Config, kernelConfig); err != nil { return err } diff --git a/syz-ci/syzupdater.go b/syz-ci/syzupdater.go index 8d72052a7..16fc960e1 100644 --- a/syz-ci/syzupdater.go +++ b/syz-ci/syzupdater.go @@ -11,7 +11,6 @@ import ( "syscall" "time" - "github.com/google/syzkaller/pkg/fileutil" "github.com/google/syzkaller/pkg/git" . "github.com/google/syzkaller/pkg/log" "github.com/google/syzkaller/pkg/osutil" @@ -68,7 +67,7 @@ func NewSyzUpdater(cfg *Config) *SyzUpdater { os.Setenv("PATH", filepath.Join(cfg.Goroot, "bin")+ string(filepath.ListSeparator)+os.Getenv("PATH")) syzkallerDir := filepath.Join(gopath, "src", "github.com", "google", "syzkaller") - os.MkdirAll(syzkallerDir, osutil.DefaultDirPerm) + osutil.MkdirAll(syzkallerDir) return &SyzUpdater{ exe: exe, @@ -152,10 +151,10 @@ func (upd *SyzUpdater) UpdateAndRestart() { Logf(0, "restarting executable for update") latestBin := filepath.Join(upd.latestDir, "bin", upd.exe) latestTag := filepath.Join(upd.latestDir, "tag") - if err := fileutil.CopyFile(latestBin, upd.exe); err != nil { + if err := osutil.CopyFile(latestBin, upd.exe); err != nil { Fatal(err) } - if err := fileutil.CopyFile(latestTag, upd.exe+".tag"); err != nil { + if err := osutil.CopyFile(latestTag, upd.exe+".tag"); err != nil { Fatal(err) } if err := syscall.Exec(upd.exe, os.Args, os.Environ()); err != nil { @@ -193,7 +192,7 @@ func (upd *SyzUpdater) build() error { return fmt.Errorf("tests failed: %v", err) } tagFile := filepath.Join(upd.syzkallerDir, "tag") - if err := ioutil.WriteFile(tagFile, []byte(commit), osutil.DefaultFilePerm); err != nil { + if err := osutil.WriteFile(tagFile, []byte(commit)); err != nil { return fmt.Errorf("filed to write tag file: %v", err) } if err := osutil.CopyFiles(upd.syzkallerDir, upd.latestDir, syzFiles); err != nil { diff --git a/syz-gce/syz-gce.go b/syz-gce/syz-gce.go index 0f3ef7499..2a7511221 100644 --- a/syz-gce/syz-gce.go +++ b/syz-gce/syz-gce.go @@ -364,11 +364,11 @@ func (a *LocalBuildAction) Build() error { } } Logf(0, "building image...") - os.MkdirAll("image/obj", 0700) + osutil.MkdirAll("image/obj") if err := kernel.CreateImage(dir, a.UserspaceDir, "image/disk.raw", "image/key"); err != nil { return fmt.Errorf("image build failed: %v", err) } - if err := ioutil.WriteFile("image/tag", []byte(hash), 0600); err != nil { + if err := osutil.WriteFile("image/tag", []byte(hash)); err != nil { return fmt.Errorf("failed to write tag file: %v", err) } vmlinux := filepath.Join(dir, "vmlinux") @@ -477,7 +477,7 @@ func writeManagerConfig(cfg *Config, httpPort int, file string) error { if err != nil { return err } - if err := ioutil.WriteFile(file, data, 0600); err != nil { + if err := osutil.WriteFile(file, data); err != nil { return err } return nil @@ -519,10 +519,10 @@ func downloadAndExtract(f *gcs.File, dir string) error { } files[filepath.Clean(hdr.Name)] = true base, file := filepath.Split(hdr.Name) - if err := os.MkdirAll(filepath.Join(dir, base), 0700); err != nil { + if err := osutil.MkdirAll(filepath.Join(dir, base)); err != nil { return err } - dst, err := os.OpenFile(filepath.Join(dir, base, file), os.O_CREATE|os.O_TRUNC|os.O_WRONLY, 0600) + dst, err := os.OpenFile(filepath.Join(dir, base, file), os.O_CREATE|os.O_TRUNC|os.O_WRONLY, osutil.DefaultFilePerm) if err != nil { return err } diff --git a/syz-hub/state/state.go b/syz-hub/state/state.go index 2d77b2a1f..31ee6d2ea 100644 --- a/syz-hub/state/state.go +++ b/syz-hub/state/state.go @@ -15,6 +15,7 @@ import ( "github.com/google/syzkaller/pkg/db" "github.com/google/syzkaller/pkg/hash" . "github.com/google/syzkaller/pkg/log" + "github.com/google/syzkaller/pkg/osutil" "github.com/google/syzkaller/prog" ) @@ -47,7 +48,7 @@ func Make(dir string) (*State, error) { Managers: make(map[string]*Manager), } - os.MkdirAll(st.dir, 0750) + osutil.MkdirAll(st.dir) var err error Logf(0, "reading corpus...") st.Corpus, err = db.Open(filepath.Join(st.dir, "corpus.db")) @@ -75,7 +76,7 @@ func Make(dir string) (*State, error) { } managersDir := filepath.Join(st.dir, "manager") - os.MkdirAll(managersDir, 0700) + osutil.MkdirAll(managersDir) managers, err := ioutil.ReadDir(managersDir) if err != nil { return nil, fmt.Errorf("failed to read %v dir: %v", managersDir, err) @@ -111,7 +112,7 @@ func (st *State) Connect(name string, fresh bool, calls []string, corpus [][]byt mgr = new(Manager) st.Managers[name] = mgr mgr.dir = filepath.Join(st.dir, "manager", name) - os.MkdirAll(mgr.dir, 0700) + osutil.MkdirAll(mgr.dir) } mgr.Connected = time.Now() if fresh { @@ -233,7 +234,7 @@ func (st *State) addInput(mgr *Manager, input []byte) { } func writeFile(name string, data []byte) { - if err := ioutil.WriteFile(name, data, 0600); err != nil { + if err := osutil.WriteFile(name, data); err != nil { Logf(0, "failed to write file %v: %v", name, err) } } diff --git a/syz-manager/manager.go b/syz-manager/manager.go index e0ee2caa0..2eaa94778 100644 --- a/syz-manager/manager.go +++ b/syz-manager/manager.go @@ -8,7 +8,6 @@ import ( "encoding/json" "flag" "fmt" - "io/ioutil" "math/rand" "net" "os" @@ -122,7 +121,7 @@ func RunManager(cfg *mgrconfig.Config, syscalls map[int]bool) { } crashdir := filepath.Join(cfg.Workdir, "crashes") - os.MkdirAll(crashdir, 0700) + osutil.MkdirAll(crashdir) enabledSyscalls := "" if len(syscalls) != 0 { @@ -241,7 +240,7 @@ func RunManager(cfg *mgrconfig.Config, syscalls map[int]bool) { }() if *flagBench != "" { - f, err := os.OpenFile(*flagBench, os.O_WRONLY|os.O_CREATE|os.O_EXCL, 0640) + f, err := os.OpenFile(*flagBench, os.O_WRONLY|os.O_CREATE|os.O_EXCL, osutil.DefaultFilePerm) if err != nil { Fatalf("failed to open bench file: %v", err) } @@ -552,8 +551,8 @@ func (mgr *Manager) saveCrash(crash *Crash) { sig := hash.Hash([]byte(crash.desc)) id := sig.String() dir := filepath.Join(mgr.crashdir, id) - os.MkdirAll(dir, 0700) - if err := ioutil.WriteFile(filepath.Join(dir, "description"), []byte(crash.desc+"\n"), 0660); err != nil { + osutil.MkdirAll(dir) + if err := osutil.WriteFile(filepath.Join(dir, "description"), []byte(crash.desc+"\n")); err != nil { Logf(0, "failed to write crash: %v", err) } // Save up to 100 reports. If we already have 100, overwrite the oldest one. @@ -572,12 +571,12 @@ func (mgr *Manager) saveCrash(crash *Crash) { oldestTime = info.ModTime() } } - ioutil.WriteFile(filepath.Join(dir, fmt.Sprintf("log%v", oldestI)), crash.output, 0660) + osutil.WriteFile(filepath.Join(dir, fmt.Sprintf("log%v", oldestI)), crash.output) if len(mgr.cfg.Tag) > 0 { - ioutil.WriteFile(filepath.Join(dir, fmt.Sprintf("tag%v", oldestI)), []byte(mgr.cfg.Tag), 0660) + osutil.WriteFile(filepath.Join(dir, fmt.Sprintf("tag%v", oldestI)), []byte(mgr.cfg.Tag)) } if len(crash.text) > 0 { - ioutil.WriteFile(filepath.Join(dir, fmt.Sprintf("report%v", oldestI)), crash.text, 0660) + osutil.WriteFile(filepath.Join(dir, fmt.Sprintf("report%v", oldestI)), crash.text) } } @@ -617,7 +616,7 @@ func (mgr *Manager) saveRepro(crash *Crash, res *repro.Result) { for i := 0; i < maxReproAttempts; i++ { name := filepath.Join(dir, fmt.Sprintf("repro%v", i)) if !osutil.IsExist(name) { - ioutil.WriteFile(name, nil, 0660) + osutil.WriteFile(name, nil) break } } @@ -625,17 +624,17 @@ func (mgr *Manager) saveRepro(crash *Crash, res *repro.Result) { } opts := fmt.Sprintf("# %+v\n", res.Opts) prog := res.Prog.Serialize() - ioutil.WriteFile(filepath.Join(dir, "repro.prog"), append([]byte(opts), prog...), 0660) + osutil.WriteFile(filepath.Join(dir, "repro.prog"), append([]byte(opts), prog...)) if len(mgr.cfg.Tag) > 0 { - ioutil.WriteFile(filepath.Join(dir, "repro.tag"), []byte(mgr.cfg.Tag), 0660) + osutil.WriteFile(filepath.Join(dir, "repro.tag"), []byte(mgr.cfg.Tag)) } if len(crash.text) > 0 { - ioutil.WriteFile(filepath.Join(dir, "repro.report"), []byte(crash.text), 0660) + osutil.WriteFile(filepath.Join(dir, "repro.report"), []byte(crash.text)) } - ioutil.WriteFile(filepath.Join(dir, "repro.log"), res.Stats.Log, 0660) + osutil.WriteFile(filepath.Join(dir, "repro.log"), res.Stats.Log) stats := fmt.Sprintf("Extracting prog: %s\nMinimizing prog: %s\nSimplifying prog options: %s\nExtracting C: %s\nSimplifying C: %s\n", res.Stats.ExtractProgTime, res.Stats.MinimizeProgTime, res.Stats.SimplifyProgTime, res.Stats.ExtractCTime, res.Stats.SimplifyCTime) - ioutil.WriteFile(filepath.Join(dir, "repro.stats"), []byte(stats), 0660) + osutil.WriteFile(filepath.Join(dir, "repro.stats"), []byte(stats)) var cprogText []byte if res.CRepro { cprog, err := csource.Write(res.Prog, res.Opts) @@ -644,7 +643,7 @@ func (mgr *Manager) saveRepro(crash *Crash, res *repro.Result) { if err == nil { cprog = formatted } - ioutil.WriteFile(filepath.Join(dir, "repro.cprog"), cprog, 0660) + osutil.WriteFile(filepath.Join(dir, "repro.cprog"), cprog) cprogText = cprog } else { Logf(0, "failed to write C source: %v", err) diff --git a/tools/syz-db/syz-db.go b/tools/syz-db/syz-db.go index 2ebbc186d..0ea8a9c10 100644 --- a/tools/syz-db/syz-db.go +++ b/tools/syz-db/syz-db.go @@ -13,6 +13,7 @@ import ( "github.com/google/syzkaller/pkg/db" "github.com/google/syzkaller/pkg/hash" + "github.com/google/syzkaller/pkg/osutil" ) func main() { @@ -76,13 +77,13 @@ func unpack(file, dir string) { if err != nil { failf("failed to open database: %v", err) } - os.Mkdir(dir, 0750) + osutil.MkdirAll(dir) for key, rec := range db.Records { fname := filepath.Join(dir, key) if rec.Seq != 0 { fname += fmt.Sprintf("-%v", rec.Seq) } - if err := ioutil.WriteFile(fname, rec.Val, 0640); err != nil { + if err := osutil.WriteFile(fname, rec.Val); err != nil { failf("failed to output file: %v", err) } } diff --git a/tools/syz-execprog/execprog.go b/tools/syz-execprog/execprog.go index 825052ffc..a2e530fbf 100644 --- a/tools/syz-execprog/execprog.go +++ b/tools/syz-execprog/execprog.go @@ -21,6 +21,7 @@ import ( "github.com/google/syzkaller/pkg/cover" "github.com/google/syzkaller/pkg/ipc" . "github.com/google/syzkaller/pkg/log" + "github.com/google/syzkaller/pkg/osutil" "github.com/google/syzkaller/prog" ) @@ -155,7 +156,7 @@ func main() { for _, pc := range inf.Cover { binary.Write(buf, binary.LittleEndian, cover.RestorePC(pc, 0xffffffff)) } - err := ioutil.WriteFile(fmt.Sprintf("%v.%v", *flagCoverFile, i), buf.Bytes(), 0660) + err := osutil.WriteFile(fmt.Sprintf("%v.%v", *flagCoverFile, i), buf.Bytes()) if err != nil { Fatalf("failed to write coverage file: %v", err) } diff --git a/tools/syz-upgrade/upgrade.go b/tools/syz-upgrade/upgrade.go index ea2b3b6df..0d7c42112 100644 --- a/tools/syz-upgrade/upgrade.go +++ b/tools/syz-upgrade/upgrade.go @@ -16,6 +16,7 @@ import ( "os" "path/filepath" + "github.com/google/syzkaller/pkg/osutil" "github.com/google/syzkaller/prog" ) @@ -44,7 +45,7 @@ func main() { fmt.Printf("upgrading:\n%s\nto:\n%s\n\n", data, data1) hash := sha1.Sum(data1) fname1 := filepath.Join(os.Args[1], hex.EncodeToString(hash[:])) - if err := ioutil.WriteFile(fname1, data1, 0640); err != nil { + if err := osutil.WriteFile(fname1, data1); err != nil { fatalf("failed to write program: %v", err) } if err := os.Remove(fname); err != nil { diff --git a/vm/kvm/kvm.go b/vm/kvm/kvm.go index 8f17f260c..c404ba917 100644 --- a/vm/kvm/kvm.go +++ b/vm/kvm/kvm.go @@ -7,7 +7,6 @@ package kvm import ( "fmt" - "io/ioutil" "os" "os/exec" "path/filepath" @@ -17,7 +16,6 @@ import ( "time" "github.com/google/syzkaller/pkg/config" - "github.com/google/syzkaller/pkg/fileutil" "github.com/google/syzkaller/pkg/osutil" "github.com/google/syzkaller/vm/vmimpl" ) @@ -121,7 +119,7 @@ func (pool *Pool) Create(workdir string, index int) (vmimpl.Instance, error) { return nil, fmt.Errorf("failed to lkvm setup: %v\n%s", err, out) } scriptPath := filepath.Join(workdir, "script.sh") - if err := ioutil.WriteFile(scriptPath, []byte(script), 0700); err != nil { + if err := osutil.WriteExecFile(scriptPath, []byte(script)); err != nil { return nil, fmt.Errorf("failed to create temp file: %v", err) } @@ -218,7 +216,7 @@ func (inst *instance) Forward(port int) (string, error) { func (inst *instance) Copy(hostSrc string) (string, error) { vmDst := filepath.Join("/", filepath.Base(hostSrc)) dst := filepath.Join(inst.sandboxPath, vmDst) - if err := fileutil.CopyFile(hostSrc, dst); err != nil { + if err := osutil.CopyFile(hostSrc, dst); err != nil { return "", err } if err := os.Chmod(dst, 0777); err != nil { @@ -237,7 +235,7 @@ func (inst *instance) Run(timeout time.Duration, stop <-chan bool, command strin cmdFile := filepath.Join(inst.sandboxPath, "/syz-cmd") tmpFile := cmdFile + "-tmp" - if err := ioutil.WriteFile(tmpFile, []byte(command), 0700); err != nil { + if err := osutil.WriteExecFile(tmpFile, []byte(command)); err != nil { return nil, nil, err } if err := os.Rename(tmpFile, cmdFile); err != nil { diff --git a/vm/qemu/qemu.go b/vm/qemu/qemu.go index a264d00b1..dc6c0158e 100644 --- a/vm/qemu/qemu.go +++ b/vm/qemu/qemu.go @@ -6,7 +6,6 @@ package qemu import ( "fmt" "io" - "io/ioutil" "math/rand" "net" "os" @@ -117,7 +116,7 @@ func (pool *Pool) Create(workdir string, index int) (vmimpl.Instance, error) { return nil, fmt.Errorf("failed to execute ssh-keygen: %v\n%s", err, out) } initFile := filepath.Join(workdir, "init.sh") - if err := ioutil.WriteFile(initFile, []byte(strings.Replace(initScript, "{{KEY}}", sshkey, -1)), 0777); err != nil { + if err := osutil.WriteExecFile(initFile, []byte(strings.Replace(initScript, "{{KEY}}", sshkey, -1))); err != nil { return nil, fmt.Errorf("failed to create init file: %v", err) } } diff --git a/vm/vm.go b/vm/vm.go index 8e4aa47b9..74eca2199 100644 --- a/vm/vm.go +++ b/vm/vm.go @@ -15,7 +15,7 @@ import ( "regexp" "time" - "github.com/google/syzkaller/pkg/fileutil" + "github.com/google/syzkaller/pkg/osutil" "github.com/google/syzkaller/pkg/report" "github.com/google/syzkaller/vm/vmimpl" @@ -63,7 +63,7 @@ func (pool *Pool) Create(index int) (*Instance, error) { if index < 0 || index >= pool.Count() { return nil, fmt.Errorf("invalid VM index %v (count %v)", index, pool.Count()) } - workdir, err := fileutil.ProcessTempDir(pool.workdir) + workdir, err := osutil.ProcessTempDir(pool.workdir) if err != nil { return nil, fmt.Errorf("failed to create instance temp dir: %v", err) } -- cgit mrf-deployment