Locking around osutil.Rename and some descriptive text

This commit is contained in:
Jakob Borg 2014-09-22 15:48:46 +02:00
parent 7fd2e4d2db
commit 4ddd87e773
2 changed files with 14 additions and 11 deletions

View File

@ -630,13 +630,6 @@ func (m *Model) SetIgnores(repo string, content []string) error {
fmt.Fprintln(writer, line)
}
err = writer.Flush()
if err != nil {
l.Warnln("Saving .stignore:", err)
fd.Close()
return err
}
err = fd.Close()
if err != nil {
l.Warnln("Saving .stignore:", err)
@ -644,10 +637,7 @@ func (m *Model) SetIgnores(repo string, content []string) error {
}
file := filepath.Join(cfg.Directory, ".stignore")
m.rmut.Lock()
os.Remove(file)
err = osutil.Rename(fd.Name(), file)
m.rmut.Unlock()
err = osutil.Rename(tmpFileName, file)
if err != nil {
l.Warnln("Saving .stignore:", err)
return err

View File

@ -9,9 +9,22 @@ import (
"os"
"path/filepath"
"runtime"
"sync"
)
// Try to keep this entire operation atomic-like. We shouldn't be doing this
// often enough that there is any contention on this lock.
var renameLock sync.Mutex
// Rename renames a file, while trying hard to succeed on various systems by
// temporarily tweaking directory permissions and removing the destination
// file when necessary. Will make sure to delete the from file if the
// operation fails, so use only for situations like committing a temp file to
// it's final location.
func Rename(from, to string) error {
renameLock.Lock()
defer renameLock.Unlock()
// Make sure the destination directory is writeable
toDir := filepath.Dir(to)
if info, err := os.Stat(toDir); err == nil {