func TestDirJoin(t *testing.T) { if runtime.GOOS == "windows" { t.Skip("skipping test on windows") } wfi, err := os.Stat("/etc/hosts") if err != nil { t.Skip("skipping test; no /etc/hosts file") } test := func(d http.Dir, name string) { f, err := d.Open(name) if err != nil { t.Fatalf("open of %s: %v", name, err) } defer f.Close() gfi, err := f.Stat() if err != nil { t.Fatalf("stat of %s: %v", name, err) } if !os.SameFile(gfi, wfi) { t.Errorf("%s got different file", name) } } test(http.Dir("/etc/"), "/hosts") test(http.Dir("/etc/"), "hosts") test(http.Dir("/etc/"), "../../../../hosts") test(http.Dir("/etc"), "/hosts") test(http.Dir("/etc"), "hosts") test(http.Dir("/etc"), "../../../../hosts") // Not really directories, but since we use this trick in // ServeFile, test it: test(http.Dir("/etc/hosts"), "") test(http.Dir("/etc/hosts"), "/") test(http.Dir("/etc/hosts"), "../") }
func TestSameWindowsFile(t *testing.T) { temp, err := ioutil.TempDir("", "TestSameWindowsFile") if err != nil { t.Fatal(err) } defer os.RemoveAll(temp) wd, err := os.Getwd() if err != nil { t.Fatal(err) } err = os.Chdir(temp) if err != nil { t.Fatal(err) } defer os.Chdir(wd) f, err := os.Create("a") if err != nil { t.Fatal(err) } f.Close() ia1, err := os.Stat("a") if err != nil { t.Fatal(err) } path, err := filepath.Abs("a") if err != nil { t.Fatal(err) } ia2, err := os.Stat(path) if err != nil { t.Fatal(err) } if !os.SameFile(ia1, ia2) { t.Errorf("files should be same") } p := filepath.VolumeName(path) + filepath.Base(path) if err != nil { t.Fatal(err) } ia3, err := os.Stat(p) if err != nil { t.Fatal(err) } if !os.SameFile(ia1, ia3) { t.Errorf("files should be same") } }
func main() { fi1, err := os.Stat("Hello.go") if err != nil { fmt.Printf("Error: %v\n", err) return } fi2, err := os.Stat("World.go") if err != nil { fmt.Printf("Error: %v\n", err) return } fmt.Printf("%t\n", os.SameFile(fi1, fi2)) fmt.Printf("%t\n", os.SameFile(fi1, fi1)) }
func (w *outWrapper) monitorFile(i int) { for { time.Sleep(time.Second * time.Duration(i)) fs, err := os.Stat(w.p) if err != nil && os.IsNotExist(err) { if os.IsNotExist(err) { fmt.Fprintln(os.Stderr, "looks like output was deleted") w.reopen() } else { fmt.Fprintln(os.Stderr, "error doing stat on open file:", w.p) } continue } cs, err := w.f.Stat() if err != nil { fmt.Fprintln(os.Stderr, "error doing stat on open file:", w.p) continue } if !os.SameFile(fs, cs) { fmt.Fprintln(os.Stderr, "looks like output was rotated") w.reopen() } } }
func TestGitAndRootDirs(t *testing.T) { repo := test.NewRepo(t) repo.Pushd() defer func() { repo.Popd() repo.Cleanup() }() git, root, err := GitAndRootDirs() if err != nil { t.Fatal(err) } expected, err := os.Stat(git) if err != nil { t.Fatal(err) } actual, err := os.Stat(filepath.Join(root, ".git")) if err != nil { t.Fatal(err) } assert.True(t, os.SameFile(expected, actual)) }
func shouldReopen(file *os.File, path string) bool { // Compare the current open file against the path to see // if there's been any file rotation or truncation. filestat, err := file.Stat() if err != nil { // Error in fstat? Odd fmt.Printf("error fstat'ing already open file '%s': %s\n", path, err) return false } pathstat, err := os.Stat(path) if err != nil { // Stat on the 'path' failed, keep the current file open fmt.Printf("error stat on path '%s': %s\n", path, err) return false } /* TODO(sissel): Check if path is a symlink and if it has changed */ if os.SameFile(filestat, pathstat) { /* Same file, check for truncation */ pos, _ := file.Seek(0, os.SEEK_CUR) if pos > filestat.Size() { // Current read position exceeds file length. File was truncated. fmt.Printf("File '%s' truncated.\n", path) return true } } else { // Not the same file; open the path again. fmt.Printf("Reopening '%s' (new inode/device)\n", path) return true } return false } /* checkForRotation */
func (group *TailGroup) activate(match string) { tail, ok := group.Tails[match] if !ok { fi, _ := os.Stat(match) for _, tail = range group.Tails { tfi, _ := tail.Stat() if os.SameFile(fi, tfi) { tail.Close() delete(group.Tails, tail.Path) off := tail.Offset() tail.SetOffset(0) tail.WriteOffset() base := path.Base(match) offset := path.Join(group.OffsetDir, base+".ptr") tail = NewTail(group.NewParser(base), group.maxBackfill, match, offset, off) group.Tails[match] = tail return } } base := path.Base(match) offset := path.Join(group.OffsetDir, base+".ptr") tail = NewTail(group.NewParser(base), group.maxBackfill, match, offset, 0) group.Tails[match] = tail } }
func (n *navigation) refreshParent() { wd, err := os.Getwd() if err != nil { n.parent = newErrNavColumn(err) return } if wd == "/" { n.parent = newNavColumn(nil, nil) } else { all, err := n.loaddir("..") if err != nil { n.parent = newErrNavColumn(err) return } cwd, err := os.Stat(".") if err != nil { n.parent = newErrNavColumn(err) return } n.parent = newNavColumn(all, func(i int) bool { d, _ := os.Lstat("../" + all[i].text) return os.SameFile(d, cwd) }) } }
// CopyFile copies a file from src to dst. If src and dst files exist, and are // the same, then return success. Otherise, attempt to create a hard link // between the two files. If that fail, copy the file contents from src to dst. func CopyFile(src, dst string) (err error) { sfi, err := os.Stat(src) if err != nil { return } if !sfi.Mode().IsRegular() { // cannot copy non-regular files (e.g., directories, // symlinks, devices, etc.) return fmt.Errorf("CopyFile: non-regular source file %s (%q)", sfi.Name(), sfi.Mode().String()) } dfi, err := os.Stat(dst) if err != nil { if !os.IsNotExist(err) { return } } else { if !(dfi.Mode().IsRegular()) { return fmt.Errorf("CopyFile: non-regular destination file %s (%q)", dfi.Name(), dfi.Mode().String()) } if os.SameFile(sfi, dfi) { return } } if err = os.Link(src, dst); err == nil { return } err = copyFileContents(src, dst) return }
// GetAllCurrentFiles scans the download directory and parses the files inside // for possible future linking, if a duplicate is found. func GetAllCurrentFiles() { os.MkdirAll(cfg.DownloadDirectory, 0755) dirs, err := ioutil.ReadDir(cfg.DownloadDirectory) if err != nil { panic(err) } // TODO: Make GetAllCurrentFiles a LOT more stable. A lot could go wrong, but meh. for _, d := range dirs { if !d.IsDir() { continue } dir, err := os.Open(cfg.DownloadDirectory + string(os.PathSeparator) + d.Name()) if err != nil { log.Fatal(err) } // fmt.Println(dir.Name()) files, err := dir.Readdirnames(0) if err != nil { log.Fatal(err) } for _, f := range files { if info, ok := FileTracker.m[f]; ok { // File exists. p := dir.Name() + string(os.PathSeparator) + f checkFile, err := os.Stat(p) if err != nil { log.Fatal(err) } if !os.SameFile(info.FileInfo(), checkFile) { os.Remove(p) err := os.Link(info.Path, p) if err != nil { log.Fatal(err) } } } else { // New file. closedChannel := make(chan struct{}) close(closedChannel) FileTracker.m[f] = FileStatus{ Name: f, Path: dir.Name() + string(os.PathSeparator) + f, Priority: 0, // TODO(Liru): Add priority to file list when it is implemented Exists: closedChannel, } } } } }
// DirectoryScanner implements filepath.WalkFunc, necessary to walk and // register each file in the download directory before beginning the // download. This lets us know which files are already downloaded, and // which ones can be hardlinked. // // Deprecated; replaced by GetAllCurrentFiles(). func DirectoryScanner(path string, f os.FileInfo, err error) error { if f == nil { // Only exists if the directory doesn't exist beforehand. return err } if f.IsDir() { return err } if info, ok := FileTracker.m[f.Name()]; ok { // File exists. if !os.SameFile(info.FileInfo(), f) { os.Remove(path) err := os.Link(info.Path, path) if err != nil { log.Fatal(err) } } } else { // New file. closedChannel := make(chan struct{}) close(closedChannel) FileTracker.m[f.Name()] = FileStatus{ Name: f.Name(), Path: path, Priority: 0, // TODO(Liru): Add priority to file list when it is implemented Exists: closedChannel, } } return err }
func CopyFile(srcPath string, destPath string) error { srcFile, err := os.Stat(srcPath) if err != nil { return err } if !srcFile.Mode().IsRegular() { return fmt.Errorf("Unregular source file: %s (%s)", srcFile.Name(), srcFile.Mode().String()) } destFile, err := os.Stat(destPath) if err != nil { if !os.IsNotExist(err) { return err } } else { if !(destFile.Mode().IsRegular()) { return fmt.Errorf("Unregular source file: %s (%s)", srcFile.Name(), srcFile.Mode().String()) } if os.SameFile(srcFile, destFile) { return nil } } if err := os.Link(srcPath, destPath); err == nil { return err } return copyFileContents(srcPath, destPath) }
// pollForRotations hits the filesystem every interval looking to see if the file at `filename` path is different from what it was previously func (t *File) pollForRotations(d time.Duration) { previousFile, err := t.file.Stat() if err != nil { t.errc <- err } for !t.closed { currentFile, err := os.Stat(t.filename) switch err { case nil: switch os.SameFile(currentFile, previousFile) { case true: if t.checkForTruncate() { if err := t.reopenFile(); err != nil { t.errc <- err } } case false: previousFile = currentFile if err := t.reopenFile(); err != nil { t.errc <- err } } default: // Filename doens't seem to be there (or something else weird), wait for it to re-appear } time.Sleep(d) } }
// 重命名 func testRename() { fp1 := "config/config.txt" fp2 := "config/config1.txt" fp3 := "config/temp.txt" err := os.Rename(fp1, fp2) if err != nil { if os.IsExist(err) { fmt.Println("fp2 is exist", err) } } os.Rename(fp1, fp3) fmt.Println("Rename Ok!!") os.Rename(fp3, fp1) var fi1 os.FileInfo var fi2 os.FileInfo fi1, err = os.Stat(fp1) if err != nil { fmt.Println("Error : ", err) return } fi2, err = os.Stat(fp2) if err != nil { fmt.Println("Error : ", err) return } fmt.Println("os.SameFile : ", os.SameFile(fi1, fi2)) fmt.Println("fi1 : ", fi1) fmt.Println("fi2 : ", fi2) }
// Copy file (hard link) func Copy(oldname, newname string) (err error) { oldfile, err := os.Stat(oldname) checkError(err) if !oldfile.Mode().IsRegular() { return fmt.Errorf("Copy: non-regular old file %s (%q)", oldfile.Name(), oldfile.Mode().String()) } newfile, err := os.Stat(newname) if err != nil { if !os.IsNotExist(err) { return } } else { if !(newfile.Mode().IsRegular()) { return fmt.Errorf("Copy: non-regular new file %s (%q)", oldfile.Name(), oldfile.Mode().String()) } if os.SameFile(oldfile, newfile) { return } } if err = os.Link(oldname, newname); err != nil { return } err = copyFileContents(oldname, newname) return }
func TestImageLocExtractDate(t *testing.T) { type testRes struct { path string date ImageDate } tests := []testRes{ {"testdata/tmp.jpg", ImageDate{2012, 12, 10}}, {"testdata/img2016_02_17.jpg", ImageDate{2016, 02, 17}}, {"testdata/1455684141000.jpg", ImageDate{2016, 02, 17}}, } for _, tr := range tests { osinfo, err := os.Stat(tr.path) if err != nil { t.Errorf("image is not found %s\n", tr.path) continue } loc := &ImageLoc{tr.path, osinfo, GetImageKind(tr.path)} info, err := loc.ExtractDate() if err != nil { t.Errorf("could not get the date for %s: %s\n", tr.path, err.Error()) continue } if !os.SameFile(loc.info, info.info) { t.Errorf("different info for %s\n", tr.path) continue } if info.date != tr.date { t.Errorf("wrong date found for %s: %v != %v\n", tr.path, info.date, tr.date) continue } } }
func (me *fileScannerImpl) onFileFound(newFile *FileAttr) { // Update map[SHA256]... if list, ok := me.scannedFiles[newFile.SHA256]; ok { for _, existing := range list { // 1. Check file size here to avoid hash collision. // 2. If the two paths are the same, then skip. // 3. If the two paths point to the same file, then skip. if existing.Size != newFile.Size || SamePath(existing.Path, newFile.Path) || os.SameFile(existing.Details, newFile.Details) { return } } me.scannedFiles[newFile.SHA256] = append(list, newFile) } else { me.scannedFiles[newFile.SHA256] = []*FileAttr{newFile} } me.updater.Log(LOG_TRACE, "%v (%v)", newFile.Path, &newFile.SHA256) // Update total count. me.totalFiles++ me.totalBytes += newFile.Size }
func (n *navigation) refreshParent() { wd, err := os.Getwd() if err != nil { n.parent = newErrNavColumn(err) return } if wd == "/" { n.parent = newNavColumn(nil, nil) } else { names, styles, err := readdirnames("..") if err != nil { n.parent = newErrNavColumn(err) return } n.parent = newNavColumn(names, styles) cwd, err := os.Stat(".") if err != nil { n.parent = newErrNavColumn(err) return } n.parent.selected = -1 for i, name := range n.parent.names { d, _ := os.Lstat("../" + name) if os.SameFile(d, cwd) { n.parent.selected = i break } } } }
func copyFile(src, dst string) (err error) { sfi, err := os.Stat(src) if err != nil { return err } if !sfi.Mode().IsRegular() { return fmt.Errorf("non-regular source file %s (%q)", sfi.Name(), sfi.Mode().String()) } dfi, err := os.Stat(dst) if err != nil { if !os.IsNotExist(err) { return nil } } else { if !(dfi.Mode().IsRegular()) { return fmt.Errorf("non-regular destination file %s (%q)", dfi.Name(), dfi.Mode().String()) } if os.SameFile(sfi, dfi) { return nil } } if err = os.Link(src, dst); err == nil { return err } return copyFileContents(src, dst) }
// Leaf is a descendent of root. func pruneEmptyDirs(root string, leaf string) (err error) { rootInfo, err := os.Stat(root) if err != nil { return } for { var leafInfo os.FileInfo leafInfo, err = os.Stat(leaf) if os.IsNotExist(err) { goto parent } if err != nil { return } if !leafInfo.IsDir() { return } if os.SameFile(rootInfo, leafInfo) { return } if os.Remove(leaf) != nil { return } parent: leaf = filepath.Dir(leaf) } }
func (fm *FileMonitor) ReadLines(fileName string) { fd, _ := fm.fds[fileName] // Determine if we're farther into the file than possible (truncate) finfo, err := fd.Stat() if err == nil { if finfo.Size() < fm.seek[fileName] { fd.Seek(0, 0) fm.seek[fileName] = 0 } } // Attempt to read lines from where we are reader := bufio.NewReader(fd) readLine, err := reader.ReadString('\n') for err == nil { line := Logline{Path: fileName, Line: readLine} fm.seek[fileName] += int64(len(readLine)) fm.NewLines <- line readLine, err = reader.ReadString('\n') } fm.seek[fileName] += int64(len(readLine)) // Check that we haven't been rotated, if we have, put this back on // discover pinfo, err := os.Stat(fileName) if err != nil || !os.SameFile(pinfo, finfo) { fd.Close() delete(fm.fds, fileName) delete(fm.seek, fileName) fm.discover[fileName] = true } return }
// Try to get Lockfile lock. Returns nil, if successful and and error describing the reason, it didn't work out. // Please note, that existing lockfiles containing pids of dead processes and lockfiles containing no pid at all // are deleted. func (l Lockfile) TryLock() error { name := string(l) // This has been checked by New already. If we trigger here, // the caller didn't use New and re-implemented it's functionality badly. // So panic, that he might find this easily during testing. if !filepath.IsAbs(string(name)) { panic(ErrNeedAbsPath) } tmplock, err := ioutil.TempFile(filepath.Dir(name), "") if err != nil { return err } else { defer tmplock.Close() defer os.Remove(tmplock.Name()) } _, err = tmplock.WriteString(fmt.Sprintf("%d\n", os.Getpid())) if err != nil { return err } // return value intentionally ignored, as ignoring it is part of the algorithm _ = os.Link(tmplock.Name(), name) fiTmp, err := os.Lstat(tmplock.Name()) if err != nil { return err } fiLock, err := os.Lstat(name) if err != nil { return err } // Success if os.SameFile(fiTmp, fiLock) { return nil } _, err = l.GetOwner() switch err { default: // Other errors -> defensively fail and let caller handle this return err case nil: return ErrBusy case ErrDeadOwner, ErrInvalidPid: // cases we can fix below } // clean stale/invalid lockfile err = os.Remove(name) if err != nil { return err } // now that we cleaned up the stale lockfile, let's recurse return l.TryLock() }
func (h *Harvester) prepareHarvester() error { // Special handling that "-" means to read from standard input if h.path == "-" { h.file = os.Stdin return nil } var err error h.file, err = h.openFile(h.path) if err != nil { log.Error("Failed opening %s: %s", h.path, err) return err } // Check we opened the right file info, err := h.file.Stat() if err != nil { h.file.Close() return err } if !os.SameFile(info, h.fileinfo) { h.file.Close() return fmt.Errorf("Not the same file") } // Store latest stat() h.fileinfo = info // TODO: Check error? h.file.Seek(h.offset, os.SEEK_SET) return nil }
func TestAbs(t *testing.T) { oldwd, err := os.Getwd() if err != nil { t.Fatal("Getwd failed: ", err) } defer os.Chdir(oldwd) root, err := ioutil.TempDir("", "TestAbs") if err != nil { t.Fatal("TempDir failed: ", err) } defer os.RemoveAll(root) wd, err := os.Getwd() if err != nil { t.Fatal("getwd failed: ", err) } err = os.Chdir(root) if err != nil { t.Fatal("chdir failed: ", err) } defer os.Chdir(wd) for _, dir := range absTestDirs { err = os.Mkdir(dir, 0777) if err != nil { t.Fatal("Mkdir failed: ", err) } } err = os.Chdir(absTestDirs[0]) if err != nil { t.Fatal("chdir failed: ", err) } for _, path := range absTests { path = strings.Replace(path, "$", root, -1) info, err := os.Stat(path) if err != nil { t.Errorf("%s: %s", path, err) continue } abspath, err := filepath.Abs(path) if err != nil { t.Errorf("Abs(%q) error: %v", path, err) continue } absinfo, err := os.Stat(abspath) if err != nil || !os.SameFile(absinfo, info) { t.Errorf("Abs(%q)=%q, not the same file", path, abspath) } if !filepath.IsAbs(abspath) { t.Errorf("Abs(%q)=%q, not an absolute path", path, abspath) } if filepath.IsAbs(path) && abspath != filepath.Clean(path) { t.Errorf("Abs(%q)=%q, isn't clean", path, abspath) } } }
func TestStatDir(t *testing.T) { defer chtmpdir(t)() f, err := os.Open(".") if err != nil { t.Fatal(err) } defer f.Close() fi, err := f.Stat() if err != nil { t.Fatal(err) } err = os.Chdir("..") if err != nil { t.Fatal(err) } fi2, err := f.Stat() if err != nil { t.Fatal(err) } if !os.SameFile(fi, fi2) { t.Fatal("race condition occurred") } }
// copyFile copies a file from src to dst. If src and dst files exist, and are // the same, then return success. Otherwise copy the file contents from src to dst. func (fbm *fileBaseManager) copyFile(src, dst string) error { sfi, err := os.Stat(src) if err != nil { return err } if !sfi.Mode().IsRegular() { // cannot copy non-regular files (e.g., directories, // symlinks, devices, etc.) // FIXME return fmt.Errorf("CopyFile: non-regular source file %s (%q)", sfi.Name(), sfi.Mode().String()) } dfi, err := os.Stat(dst) if err != nil { if !os.IsNotExist(err) { return err } } else { if !(dfi.Mode().IsRegular()) { return fmt.Errorf("CopyFile: non-regular destination file %s (%q)", dfi.Name(), dfi.Mode().String()) } if os.SameFile(sfi, dfi) { return err } } if err := fbm.copyFileContents(src, dst); err != nil { return err } return nil }
func sameFile(path1, path2 string) bool { fi1, err := os.Stat(path1) Expect(err).NotTo(HaveOccurred()) fi2, err := os.Stat(path2) Expect(err).NotTo(HaveOccurred()) return os.SameFile(fi1, fi2) }
// xsamefile reports whether f1 and f2 are the same file (or dir) func xsamefile(f1, f2 string) bool { fi1, err1 := os.Stat(f1) fi2, err2 := os.Stat(f2) if err1 != nil || err2 != nil { return f1 == f2 } return os.SameFile(fi1, fi2) }
func (me *File) checkGone() { if me.gone { return } ffi, _ := me.Stat() fsfi, _ := os.Stat(me.c.realpath(me.path)) me.gone = !os.SameFile(ffi, fsfi) }
func skipDir(fi os.FileInfo) bool { for _, ignoredDir := range ignoredDirs { if os.SameFile(fi, ignoredDir) { return true } } return false }