parent *dir // mu protects the fields below. mu sync.Mutex name string blob *blobs.Blob dirty dirtiness handles uint32 // when was this entry last changed // TODO: written time.Time } var _ = node(&file{}) var _ = fs.Node(&file{}) var _ = fs.NodeForgetter(&file{}) var _ = fs.NodeOpener(&file{}) var _ = fs.NodeSetattrer(&file{}) var _ = fs.NodeFsyncer(&file{}) var _ = fs.HandleFlusher(&file{}) var _ = fs.HandleReader(&file{}) var _ = fs.HandleWriter(&file{}) var _ = fs.HandleReleaser(&file{}) func (f *file) setName(name string) { f.mu.Lock() defer f.mu.Unlock() f.name = name }
"bazil.org/bazil/cas/chunks" "bazil.org/bazil/fs/snap" wiresnap "bazil.org/bazil/fs/snap/wire" "bazil.org/bazil/fs/wire" "bazil.org/bazil/tokens" "bazil.org/bazil/util/env" "bazil.org/fuse" "bazil.org/fuse/fs" ) type listSnaps struct { fs *Volume rootDir *dir } var _ = fs.Node(&listSnaps{}) var _ = fs.NodeMkdirer(&listSnaps{}) var _ = fs.NodeStringLookuper(&listSnaps{}) var _ = fs.Handle(&listSnaps{}) var _ = fs.HandleReadDirer(&listSnaps{}) func (d *listSnaps) Attr() fuse.Attr { return fuse.Attr{ Inode: tokens.InodeSnap, Mode: os.ModeDir | 0755, Nlink: 1, Uid: env.MyUID, Gid: env.MyGID, } }
"io" "syscall" "bazil.org/bazil/fs/snap/wire" "bazil.org/bazil/util/env" "bazil.org/fuse" fusefs "bazil.org/fuse/fs" "golang.org/x/net/context" ) type fuseFile struct { de *wire.Dirent rat io.ReaderAt } var _ = fusefs.Node(fuseFile{}) var _ = fusefs.NodeOpener(fuseFile{}) var _ = fusefs.Handle(fuseFile{}) var _ = fusefs.HandleReader(fuseFile{}) func (e fuseFile) Attr(ctx context.Context, a *fuse.Attr) error { a.Mode = 0444 a.Uid = env.MyUID a.Gid = env.MyGID a.Size = e.de.File.Manifest.Size // a.Mtime = e.Meta.Written.UTC() // a.Ctime = e.Meta.Written.UTC() // a.Crtime = e.Meta.Written.UTC() a.Blocks = statBlocks(e.de.File.Manifest.Size) // TODO .Space? return nil }
a.Mode = 0666 return nil } // Dir can be embedded in a struct to make it look like a directory. type Dir struct{} func (f Dir) Attr(ctx context.Context, a *fuse.Attr) error { a.Mode = os.ModeDir | 0777 return nil } // ChildMap is a directory with child nodes looked up from a map. type ChildMap map[string]fs.Node var _ = fs.Node(ChildMap{}) var _ = fs.NodeStringLookuper(ChildMap{}) func (f ChildMap) Attr(ctx context.Context, a *fuse.Attr) error { a.Mode = os.ModeDir | 0777 return nil } func (f ChildMap) Lookup(ctx context.Context, name string) (fs.Node, error) { child, ok := f[name] if !ok { return nil, fuse.ENOENT } return child, nil }
func NewFilesystem(localdb *alpm.DB, syncdbs *[]*alpm.DB) *FS { wrapper := &DBWrapper{local: localdb, sync: syncdbs} return &FS{wrapper} } func (filesys FS) Root() (fs.Node, error) { root := &RootDir{filesys.dbs} return root, nil } type RootDir struct { *DBWrapper } var _ = fs.Node(RootDir{}) func (RootDir) Attr(ctx context.Context, attr *fuse.Attr) error { return GenericDirAttr(ctx, attr) } func (RootDir) ReadDirAll(ctx context.Context) ([]fuse.Dirent, error) { return []fuse.Dirent{ {Name: "installed", Type: fuse.DT_Dir}, {Name: "index", Type: fuse.DT_Dir}, {Name: "sync", Type: fuse.DT_File}, {Name: "upgrade", Type: fuse.DT_File}, }, nil }
import ( "../alpm" "log" "bazil.org/fuse" "bazil.org/fuse/fs" "golang.org/x/net/context" ) type DepsDir struct { pkg *alpm.Pkg dbs *[]*alpm.DB } var _ = fs.Node(DepsDir{}) func (dir DepsDir) Attr(ctx context.Context, attr *fuse.Attr) error { return GenericDirAttr(ctx, attr) } func (dir DepsDir) ReadDirAll(ctx context.Context) ([]fuse.Dirent, error) { log.Println("DepsDir ReadDirAll") dirs := []fuse.Dirent{} for _, dep := range dir.pkg.GetDeps() { entry := fuse.Dirent{ Name: dep.Name, Type: fuse.DT_Dir, }
chunkStore: chunkStore, reader: r, } return child, nil default: return nil, fmt.Errorf("unknown entry in tree, %v", de) } } type fuseDir struct { chunkStore chunks.Store reader *Reader } var _ = fusefs.Node(fuseDir{}) var _ = fusefs.NodeStringLookuper(fuseDir{}) var _ = fusefs.NodeCreater(fuseDir{}) var _ = fusefs.Handle(fuseDir{}) var _ = fusefs.HandleReadDirAller(fuseDir{}) func (d fuseDir) Attr(ctx context.Context, a *fuse.Attr) error { a.Mode = os.ModeDir | 0555 a.Uid = env.MyUID a.Gid = env.MyGID return nil } const _MAX_INT64 = 9223372036854775807 func (d fuseDir) Lookup(ctx context.Context, name string) (fusefs.Node, error) {
func (benchFS) Init(req *fuse.InitRequest, resp *fuse.InitResponse, intr fs.Intr) fuse.Error { resp.MaxReadahead = 64 * 1024 * 1024 resp.Flags |= fuse.InitAsyncRead return nil } func (f benchFS) Root() (fs.Node, fuse.Error) { return benchDir{conf: f.conf}, nil } type benchDir struct { conf *benchConfig } var _ = fs.Node(benchDir{}) var _ = fs.NodeStringLookuper(benchDir{}) var _ = fs.Handle(benchDir{}) var _ = fs.HandleReadDirer(benchDir{}) func (benchDir) Attr() fuse.Attr { return fuse.Attr{Inode: 1, Mode: os.ModeDir | 0555} } func (d benchDir) Lookup(name string, intr fs.Intr) (fs.Node, fuse.Error) { if name == "bench" { return benchFile{conf: d.conf}, nil } return nil, fuse.ENOENT }
import ( "bazil.org/fuse" "bazil.org/fuse/fs" "errors" log "github.com/Sirupsen/logrus" "golang.org/x/net/context" "os" ) type Dir struct { fs *FS // path from root to this dir; empty for root dir path []string } var _ = fs.Node(&Dir{}) func (d *Dir) Attr(c context.Context, a *fuse.Attr) error { defer log.Debugln("dir_attr:", d.path, a) return d.fs.backend.View(c, func(ctx Context) error { b, err := ctx.Dir(d.path) if err != nil { return err } meta, err := b.DirMeta() if err != nil { return err } a.Uid = meta.Uid a.Gid = meta.Gid a.Mode = os.ModeDir | meta.Perm
// mu protects the fields below. mu sync.Mutex name string // each in-memory child, so we can return the same node on // multiple Lookups and know what to do on .save() // // each child also stores its own name; if the value in the child, // looked up in this map, does not equal the child, that means the // child has been unlinked active map[string]node } var _ = node(&dir{}) var _ = fs.Node(&dir{}) var _ = fs.NodeCreater(&dir{}) var _ = fs.NodeForgetter(&dir{}) var _ = fs.NodeMkdirer(&dir{}) var _ = fs.NodeRemover(&dir{}) var _ = fs.NodeRenamer(&dir{}) var _ = fs.NodeStringLookuper(&dir{}) var _ = fs.HandleReadDirer(&dir{}) func (d *dir) setName(name string) { d.mu.Lock() defer d.mu.Unlock() d.name = name } func (d *dir) Attr() fuse.Attr {
executable, err := filepath.Abs(os.Args[0]) if err != nil { return nil, err } testName = regexp.QuoteMeta(testName) cmd := exec.Command(executable, "-test.run=^"+testName+"$", "-fuse.internal.childmode") cmd.Stdout = os.Stdout cmd.Stderr = os.Stderr return cmd, nil } // childMapFS is an FS with one fixed child named "child". type childMapFS map[string]fs.Node var _ = fs.FS(childMapFS{}) var _ = fs.Node(childMapFS{}) var _ = fs.NodeStringLookuper(childMapFS{}) func (f childMapFS) Attr() fuse.Attr { return fuse.Attr{Inode: 1, Mode: os.ModeDir | 0777} } func (f childMapFS) Root() (fs.Node, fuse.Error) { return f, nil } func (f childMapFS) Lookup(name string, intr fs.Intr) (fs.Node, fuse.Error) { child, ok := f[name] if !ok { return nil, fuse.ENOENT }
type File struct { dir *Dir name string mu sync.Mutex // number of write-capable handles currently open writers uint // only valid if writers > 0 data []byte link bool target string links uint32 } var _ = fs.Node(&File{}) var _ = fs.Handle(&File{}) func (f *File) same_path(o *File) bool { p1 := strings.Join(append(f.dir.path, f.name), "/") p2 := strings.Join(append(o.dir.path, o.name), "/") return p1 == p2 } // load calls fn inside a View with the contents of the file. Caller // must make a copy of the data if needed. func (f *File) load(c context.Context, fn func([]byte)) error { defer log.Debugln("load:", f.dir.path, f.name) err := f.dir.fs.backend.View(c, func(ctx Context) error { b, err := ctx.Dir(f.dir.path) if err != nil {
"fmt" "log" "strconv" "bazil.org/fuse" "bazil.org/fuse/fs" "golang.org/x/net/context" ) type IndexDir struct { // We have to use a slice pointer since slices aren't hashable, and bazil //hashes nodes. To go around that, we need to use a slice pointer. F**k me. dbs *[]*alpm.DB } var _ = fs.Node(IndexDir{}) func (IndexDir) Attr(ctx context.Context, attr *fuse.Attr) error { return GenericDirAttr(ctx, attr) } func (dir IndexDir) ReadDirAll(ctx context.Context) ([]fuse.Dirent, error) { log.Println("InstallDir ReadDirAll") dirs := []fuse.Dirent{} for _, db := range *dir.dbs { for _, pkg := range db.GetPkgcache() { entry := fuse.Dirent{ Name: pkg.Name, Type: fuse.DT_Dir,
return fuse.EIO } newPath := path.Join(newParent.path, req.NewName) if err := e.fsys.Store.Move(e.path, newPath, true); err != nil { log.Warningf("fuse: entry: mv: %v", err) return err } return nil } // // Compile time checks to see which interfaces we implement: // Please update this list when modifying code here. var _ = fs.Node(&Entry{}) var _ = fs.NodeFsyncer(&Entry{}) var _ = fs.NodeGetxattrer(&Entry{}) var _ = fs.NodeListxattrer(&Entry{}) var _ = fs.NodeOpener(&Entry{}) var _ = fs.NodeSetattrer(&Entry{}) // var _ = fs.NodeRenamer(&Entry{}) //var _ = fs.NodeReadlinker(&Entry{}) //var _ = fs.NodeRemover(&Entry{}) //var _ = fs.NodeRemovexattrer(&Entry{}) // var _ = fs.NodeRequestLookuper(&Entry{}) // var _ = fs.NodeAccesser(&Entry{}) // var _ = fs.NodeForgetter(&Entry{})
"../alpm" "fmt" "log" "strconv" "bazil.org/fuse" "bazil.org/fuse/fs" "golang.org/x/net/context" ) type InstalledDir struct { db *alpm.DB } var _ = fs.Node(InstalledDir{}) func (InstalledDir) Attr(ctx context.Context, attr *fuse.Attr) error { log.Println("InstalledDir Attr") return GenericDirAttr(ctx, attr) } func (dir InstalledDir) ReadDirAll(ctx context.Context) ([]fuse.Dirent, error) { log.Println("InstallDir ReadDirAll") dirs := []fuse.Dirent{} for _, pkg := range dir.db.GetPkgcache() { entry := fuse.Dirent{ Name: pkg.Name, Type: fuse.DT_Dir,
"bazil.org/fuse" "bazil.org/fuse/fs" "golang.org/x/net/context" ) type StupidDir struct { // I hate this, but I can't figure out a better alternative. // I wanted to only have one map, Children, which themselves either have a //Children property signifying a StupidDir, or a Content property //signifying a StupidFile. Files *map[string]fs.Node Dirs *map[string]*StupidDir } var _ = fs.Node(&StupidDir{}) var _ = fs.HandleReadDirAller(&StupidDir{}) func NewStupidDir() *StupidDir { files := make(map[string]fs.Node) dirs := make(map[string]*StupidDir) return &StupidDir{ Files: &files, Dirs: &dirs, } } func filesToStupidDir(files []*alpm.File) *StupidDir { // We need to parse this slice of path strings: /*