...
1
2
3
4
5
6
7 package gatefs
8
9 import (
10 "fmt"
11 "os"
12
13 "golang.org/x/tools/godoc/vfs"
14 )
15
16
17
18
19 func New(fs vfs.FileSystem, gateCh chan bool) vfs.FileSystem {
20 if cap(gateCh) == 0 {
21 return fs
22 }
23 return gatefs{fs, gate(gateCh)}
24 }
25
26 type gate chan bool
27
28 func (g gate) enter() { g <- true }
29 func (g gate) leave() { <-g }
30
31 type gatefs struct {
32 fs vfs.FileSystem
33 gate
34 }
35
36 func (fs gatefs) String() string {
37 return fmt.Sprintf("gated(%s, %d)", fs.fs.String(), cap(fs.gate))
38 }
39
40 func (fs gatefs) RootType(path string) vfs.RootType {
41 return fs.fs.RootType(path)
42 }
43
44 func (fs gatefs) Open(p string) (vfs.ReadSeekCloser, error) {
45 fs.enter()
46 defer fs.leave()
47 rsc, err := fs.fs.Open(p)
48 if err != nil {
49 return nil, err
50 }
51 return gatef{rsc, fs.gate}, nil
52 }
53
54 func (fs gatefs) Lstat(p string) (os.FileInfo, error) {
55 fs.enter()
56 defer fs.leave()
57 return fs.fs.Lstat(p)
58 }
59
60 func (fs gatefs) Stat(p string) (os.FileInfo, error) {
61 fs.enter()
62 defer fs.leave()
63 return fs.fs.Stat(p)
64 }
65
66 func (fs gatefs) ReadDir(p string) ([]os.FileInfo, error) {
67 fs.enter()
68 defer fs.leave()
69 return fs.fs.ReadDir(p)
70 }
71
72 type gatef struct {
73 rsc vfs.ReadSeekCloser
74 gate
75 }
76
77 func (f gatef) Read(p []byte) (n int, err error) {
78 f.enter()
79 defer f.leave()
80 return f.rsc.Read(p)
81 }
82
83 func (f gatef) Seek(offset int64, whence int) (ret int64, err error) {
84 f.enter()
85 defer f.leave()
86 return f.rsc.Seek(offset, whence)
87 }
88
89 func (f gatef) Close() error {
90 f.enter()
91 defer f.leave()
92 return f.rsc.Close()
93 }
94
View as plain text