Commit 2c2a582a authored by Anthony Martin's avatar Anthony Martin Committed by Russ Cox

os: fix Plan 9 build for new FileInfo API

R=lucio.dere, rsc
CC=golang-dev
https://golang.org/cl/5440073
parent 1cb254a0
...@@ -64,9 +64,7 @@ func (file *File) Readdir(n int) (fi []FileInfo, err error) { ...@@ -64,9 +64,7 @@ func (file *File) Readdir(n int) (fi []FileInfo, err error) {
if e != nil { if e != nil {
return result, &PathError{"readdir", file.name, e} return result, &PathError{"readdir", file.name, e}
} }
var f FileInfo result = append(result, fileInfoFromStat(dir))
fileInfoFromStat(&f, dir)
result = append(result, f)
d.bufp += int(m) d.bufp += int(m)
n-- n--
...@@ -94,7 +92,7 @@ func (file *File) Readdirnames(n int) (names []string, err error) { ...@@ -94,7 +92,7 @@ func (file *File) Readdirnames(n int) (names []string, err error) {
fi, err := file.Readdir(n) fi, err := file.Readdir(n)
names = make([]string, len(fi)) names = make([]string, len(fi))
for i := range fi { for i := range fi {
names[i] = fi[i].Name names[i] = fi[i].Name()
} }
return return
} }
......
...@@ -18,7 +18,7 @@ func findExecutable(file string) error { ...@@ -18,7 +18,7 @@ func findExecutable(file string) error {
if err != nil { if err != nil {
return err return err
} }
if d.IsRegular() && d.Permission()&0111 != 0 { if m := d.Mode(); !m.IsDir() && m&0111 != 0 {
return nil return nil
} }
return os.EPERM return os.EPERM
......
...@@ -140,12 +140,12 @@ func (file *file) close() error { ...@@ -140,12 +140,12 @@ func (file *file) close() error {
// Stat returns the FileInfo structure describing file. // Stat returns the FileInfo structure describing file.
// It returns the FileInfo and an error, if any. // It returns the FileInfo and an error, if any.
func (f *File) Stat() (fi *FileInfo, err error) { func (f *File) Stat() (FileInfo, error) {
d, err := dirstat(f) d, err := dirstat(f)
if err != nil { if err != nil {
return nil, err return nil, err
} }
return fileInfoFromStat(new(FileInfo), d), err return fileInfoFromStat(d), nil
} }
// Truncate changes the size of the file. // Truncate changes the size of the file.
......
...@@ -4,87 +4,96 @@ ...@@ -4,87 +4,96 @@
package os package os
import "syscall" import (
"syscall"
func fileInfoFromStat(fi *FileInfo, d *Dir) *FileInfo { "time"
fi.Dev = uint64(d.Qid.Vers) | uint64(d.Qid.Type<<32) )
fi.Ino = d.Qid.Path
func sameFile(fs1, fs2 *FileStat) bool {
a := fs1.Sys.(*Dir)
b := fs2.Sys.(*Dir)
return a.Qid.Path == b.Qid.Path && a.Type == b.Type && a.Dev == b.Dev
}
fi.Mode = uint32(d.Mode) & 0777 func fileInfoFromStat(d *Dir) FileInfo {
if (d.Mode & syscall.DMDIR) == syscall.DMDIR { fs := &FileStat{
fi.Mode |= syscall.S_IFDIR name: d.Name,
} else { size: int64(d.Length),
fi.Mode |= syscall.S_IFREG modTime: time.Unix(int64(d.Mtime), 0),
Sys: d,
} }
fs.mode = FileMode(d.Mode & 0777)
fi.Size = int64(d.Length) if d.Mode&syscall.DMDIR != 0 {
fi.Atime_ns = 1e9 * int64(d.Atime) fs.mode |= ModeDir
fi.Mtime_ns = 1e9 * int64(d.Mtime) }
fi.Name = d.Name if d.Mode&syscall.DMAPPEND != 0 {
fi.FollowedSymlink = false fs.mode |= ModeAppend
return fi }
if d.Mode&syscall.DMEXCL != 0 {
fs.mode |= ModeExclusive
}
if d.Mode&syscall.DMTMP != 0 {
fs.mode |= ModeTemporary
}
return fs
} }
// arg is an open *File or a path string. // arg is an open *File or a path string.
func dirstat(arg interface{}) (d *Dir, err error) { func dirstat(arg interface{}) (d *Dir, err error) {
var name string var name string
nd := syscall.STATFIXLEN + 16*4
for i := 0; i < 2; i++ { /* should work by the second try */ // This is big enough for most stat messages
buf := make([]byte, nd) // and rounded to a multiple of 128 bytes.
size := (syscall.STATFIXLEN + 16*4 + 128) &^ 128
var n int for i := 0; i < 2; i++ {
var e error buf := make([]byte, size)
switch syscallArg := arg.(type) { var n int
switch a := arg.(type) {
case *File: case *File:
name = syscallArg.name name = a.name
n, e = syscall.Fstat(syscallArg.fd, buf) n, err = syscall.Fstat(a.fd, buf)
case string: case string:
name = syscallArg name = a
n, e = syscall.Stat(name, buf) n, err = syscall.Stat(name, buf)
} }
if err != nil {
if e != nil { return nil, &PathError{"stat", name, err}
return nil, &PathError{"stat", name, e}
} }
if n < syscall.STATFIXLEN { if n < syscall.STATFIXLEN {
return nil, &PathError{"stat", name, Eshortstat} return nil, &PathError{"stat", name, Eshortstat}
} }
ntmp, _ := gbit16(buf) // Pull the real size out of the stat message.
nd = int(ntmp) s, _ := gbit16(buf)
size = int(s)
if nd <= n {
d, e := UnmarshalDir(buf[:n])
if e != nil { // If the stat message is larger than our buffer we will
return nil, &PathError{"stat", name, e} // go around the loop and allocate one that is big enough.
if size <= n {
d, err = UnmarshalDir(buf[:n])
if err != nil {
return nil, &PathError{"stat", name, err}
} }
return d, e return
} }
} }
return nil, &PathError{"stat", name, Ebadstat} return nil, &PathError{"stat", name, Ebadstat}
} }
// Stat returns a FileInfo structure describing the named file and an error, if any. // Stat returns a FileInfo structure describing the named file and an error, if any.
func Stat(name string) (fi *FileInfo, err error) { func Stat(name string) (FileInfo, error) {
d, err := dirstat(name) d, err := dirstat(name)
if err != nil { if err != nil {
return nil, err return nil, err
} }
return fileInfoFromStat(new(FileInfo), d), err return fileInfoFromStat(d), nil
} }
// Lstat returns the FileInfo structure describing the named file and an // Lstat returns the FileInfo structure describing the named file and an
// error, if any. If the file is a symbolic link (though Plan 9 does not have symbolic links), // error, if any. If the file is a symbolic link (though Plan 9 does not have symbolic links),
// the returned FileInfo describes the symbolic link. Lstat makes no attempt to follow the link. // the returned FileInfo describes the symbolic link. Lstat makes no attempt to follow the link.
func Lstat(name string) (fi *FileInfo, err error) { func Lstat(name string) (FileInfo, error) {
d, err := dirstat(name) return Stat(name)
if err != nil {
return nil, err
}
return fileInfoFromStat(new(FileInfo), d), err
} }
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