Commit 16dcef80 authored by David du Colombier's avatar David du Colombier

os: rename only works as part of the same directory on Plan 9

R=golang-dev, lucio.dere, rsc
CC=golang-dev
https://golang.org/cl/44080046
parent 6f6ff951
...@@ -6,6 +6,7 @@ package os ...@@ -6,6 +6,7 @@ package os
import ( import (
"runtime" "runtime"
"strings"
"syscall" "syscall"
"time" "time"
) )
...@@ -314,6 +315,15 @@ func Remove(name string) error { ...@@ -314,6 +315,15 @@ func Remove(name string) error {
} }
func rename(oldname, newname string) error { func rename(oldname, newname string) error {
dirname := oldname[:strings.LastIndex(oldname, "/")+1]
if strings.HasPrefix(newname, dirname) {
newname = newname[len(dirname):]
}
// If newname still contains slashes after removing the oldname
// prefix, the rename is cross-directory and must be rejected.
// This case is caught by d.Marshal below.
var d syscall.Dir var d syscall.Dir
d.Null() d.Null()
...@@ -322,10 +332,10 @@ func rename(oldname, newname string) error { ...@@ -322,10 +332,10 @@ func rename(oldname, newname string) error {
buf := make([]byte, syscall.STATFIXLEN+len(d.Name)) buf := make([]byte, syscall.STATFIXLEN+len(d.Name))
n, err := d.Marshal(buf[:]) n, err := d.Marshal(buf[:])
if err != nil { if err != nil {
return &PathError{"rename", oldname, err} return &LinkError{"rename", oldname, newname, err}
} }
if err = syscall.Wstat(oldname, buf[:n]); err != nil { if err = syscall.Wstat(oldname, buf[:n]); err != nil {
return &PathError{"rename", oldname, err} return &LinkError{"rename", oldname, newname, err}
} }
return nil return nil
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment