diff options
| author | Sam Anthony <sam@samanthony.xyz> | 2026-03-14 20:01:34 -0400 |
|---|---|---|
| committer | Sam Anthony <sam@samanthony.xyz> | 2026-03-14 20:01:34 -0400 |
| commit | 3f16c6b240108bca18be0d1941f6dda1f1fc2d51 (patch) | |
| tree | e74054e695e2b411343eb1d36f717a8edba82b47 /back/cmd/authfs/rootdir.go | |
| parent | cab80e76783c416960b06d98058eeba8d4c254fb (diff) | |
| download | buth-mockup.zip | |
authfs.RootDir: implement Dir interfacemockup
Diffstat (limited to 'back/cmd/authfs/rootdir.go')
| -rw-r--r-- | back/cmd/authfs/rootdir.go | 112 |
1 files changed, 112 insertions, 0 deletions
diff --git a/back/cmd/authfs/rootdir.go b/back/cmd/authfs/rootdir.go new file mode 100644 index 0000000..870a5a8 --- /dev/null +++ b/back/cmd/authfs/rootdir.go @@ -0,0 +1,112 @@ +package main + +import ( + "bytes" + + p9 "github.com/Harvey-OS/ninep/protocol" + + "git.samanthony.xyz/buth/back/qver" +) + +type RootDir struct { + *qver.Version + *UsersDir + *SessionsDir +} + +func NewRootDir(path string) (*RootDir, error) { + ver := qver.New() + users, err := NewUsersDir(path, ver) + if err != nil { + ver.Close() + return nil, err + } + sessions := NewSessionsDir(ver) + return &RootDir{ver, users, sessions}, nil +} + +func (r *RootDir) Close() { + r.Version.Close() + r.UsersDir.Close() + r.SessionsDir.Close() +} + +func (r *RootDir) Qid() (p9.QID, error) { + ver, err := r.Version.Get() + if err != nil { + return p9.QID{}, err + } + return p9.QID{ + Type: p9.QTDIR, + Version: ver, + Path: rootQidPath, + }, nil +} + +func (r *RootDir) Stat() (p9.Dir, error) { + qid, err := r.Qid() + if err != nil { + return p9.Dir{}, err + } + return p9.Dir{ + QID: qid, + Mode: p9.DMDIR | p9.DMREAD, + // TODO: atime, mtime + Name: "/", + }, nil +} + +func (r *RootDir) Remove() error { return ErrPerm } + +func (r *RootDir) Open(mode p9.Mode) error { + if mode != p9.OREAD { + return ErrPerm + } + return nil +} + +func (r *RootDir) Read(off p9.Offset, n p9.Count) ([]byte, error) { + userInfo, err := r.UsersDir.Stat() + if err != nil { + return nil, err + } + sessInfo, err := r.SessionsDir.Stat() + if err != nil { + return nil, err + } + + buf := new(bytes.Buffer) + p9.Marshaldir(buf, userInfo) + p9.Marshaldir(buf, sessInfo) + + b := buf.Bytes() + lenb := uint64(len(b)) + lo := clamp(uint64(off), 0, lenb) + hi := clamp(lo+uint64(n), 0, lenb) + return b[lo:hi], nil +} + +func (r *RootDir) Write(off p9.Offset, b []byte) (p9.Count, error) { return 0, ErrPerm } + +func (r *RootDir) Create(name string, perm p9.Perm, mode p9.Mode) (File, error) { return nil, ErrPerm } + +func (r *RootDir) Walk(name string) (File, error) { + switch name { + case "users": + return r.UsersDir, nil + case "sessions": + return r.SessionsDir, nil + default: + return nil, ErrFileNotExist + } +} + +func clamp(x, min, max uint64) uint64 { + if x < min { + x = min + } + if x > max { + x = max + } + return x +} |