diff options
Diffstat (limited to 'vendor/golang.org/x/tools/go/buildutil/fakecontext.go')
-rw-r--r-- | vendor/golang.org/x/tools/go/buildutil/fakecontext.go | 109 |
1 files changed, 109 insertions, 0 deletions
diff --git a/vendor/golang.org/x/tools/go/buildutil/fakecontext.go b/vendor/golang.org/x/tools/go/buildutil/fakecontext.go new file mode 100644 index 0000000..8b7f066 --- /dev/null +++ b/vendor/golang.org/x/tools/go/buildutil/fakecontext.go | |||
@@ -0,0 +1,109 @@ | |||
1 | package buildutil | ||
2 | |||
3 | import ( | ||
4 | "fmt" | ||
5 | "go/build" | ||
6 | "io" | ||
7 | "io/ioutil" | ||
8 | "os" | ||
9 | "path" | ||
10 | "path/filepath" | ||
11 | "sort" | ||
12 | "strings" | ||
13 | "time" | ||
14 | ) | ||
15 | |||
16 | // FakeContext returns a build.Context for the fake file tree specified | ||
17 | // by pkgs, which maps package import paths to a mapping from file base | ||
18 | // names to contents. | ||
19 | // | ||
20 | // The fake Context has a GOROOT of "/go" and no GOPATH, and overrides | ||
21 | // the necessary file access methods to read from memory instead of the | ||
22 | // real file system. | ||
23 | // | ||
24 | // Unlike a real file tree, the fake one has only two levels---packages | ||
25 | // and files---so ReadDir("/go/src/") returns all packages under | ||
26 | // /go/src/ including, for instance, "math" and "math/big". | ||
27 | // ReadDir("/go/src/math/big") would return all the files in the | ||
28 | // "math/big" package. | ||
29 | // | ||
30 | func FakeContext(pkgs map[string]map[string]string) *build.Context { | ||
31 | clean := func(filename string) string { | ||
32 | f := path.Clean(filepath.ToSlash(filename)) | ||
33 | // Removing "/go/src" while respecting segment | ||
34 | // boundaries has this unfortunate corner case: | ||
35 | if f == "/go/src" { | ||
36 | return "" | ||
37 | } | ||
38 | return strings.TrimPrefix(f, "/go/src/") | ||
39 | } | ||
40 | |||
41 | ctxt := build.Default // copy | ||
42 | ctxt.GOROOT = "/go" | ||
43 | ctxt.GOPATH = "" | ||
44 | ctxt.Compiler = "gc" | ||
45 | ctxt.IsDir = func(dir string) bool { | ||
46 | dir = clean(dir) | ||
47 | if dir == "" { | ||
48 | return true // needed by (*build.Context).SrcDirs | ||
49 | } | ||
50 | return pkgs[dir] != nil | ||
51 | } | ||
52 | ctxt.ReadDir = func(dir string) ([]os.FileInfo, error) { | ||
53 | dir = clean(dir) | ||
54 | var fis []os.FileInfo | ||
55 | if dir == "" { | ||
56 | // enumerate packages | ||
57 | for importPath := range pkgs { | ||
58 | fis = append(fis, fakeDirInfo(importPath)) | ||
59 | } | ||
60 | } else { | ||
61 | // enumerate files of package | ||
62 | for basename := range pkgs[dir] { | ||
63 | fis = append(fis, fakeFileInfo(basename)) | ||
64 | } | ||
65 | } | ||
66 | sort.Sort(byName(fis)) | ||
67 | return fis, nil | ||
68 | } | ||
69 | ctxt.OpenFile = func(filename string) (io.ReadCloser, error) { | ||
70 | filename = clean(filename) | ||
71 | dir, base := path.Split(filename) | ||
72 | content, ok := pkgs[path.Clean(dir)][base] | ||
73 | if !ok { | ||
74 | return nil, fmt.Errorf("file not found: %s", filename) | ||
75 | } | ||
76 | return ioutil.NopCloser(strings.NewReader(content)), nil | ||
77 | } | ||
78 | ctxt.IsAbsPath = func(path string) bool { | ||
79 | path = filepath.ToSlash(path) | ||
80 | // Don't rely on the default (filepath.Path) since on | ||
81 | // Windows, it reports virtual paths as non-absolute. | ||
82 | return strings.HasPrefix(path, "/") | ||
83 | } | ||
84 | return &ctxt | ||
85 | } | ||
86 | |||
87 | type byName []os.FileInfo | ||
88 | |||
89 | func (s byName) Len() int { return len(s) } | ||
90 | func (s byName) Swap(i, j int) { s[i], s[j] = s[j], s[i] } | ||
91 | func (s byName) Less(i, j int) bool { return s[i].Name() < s[j].Name() } | ||
92 | |||
93 | type fakeFileInfo string | ||
94 | |||
95 | func (fi fakeFileInfo) Name() string { return string(fi) } | ||
96 | func (fakeFileInfo) Sys() interface{} { return nil } | ||
97 | func (fakeFileInfo) ModTime() time.Time { return time.Time{} } | ||
98 | func (fakeFileInfo) IsDir() bool { return false } | ||
99 | func (fakeFileInfo) Size() int64 { return 0 } | ||
100 | func (fakeFileInfo) Mode() os.FileMode { return 0644 } | ||
101 | |||
102 | type fakeDirInfo string | ||
103 | |||
104 | func (fd fakeDirInfo) Name() string { return string(fd) } | ||
105 | func (fakeDirInfo) Sys() interface{} { return nil } | ||
106 | func (fakeDirInfo) ModTime() time.Time { return time.Time{} } | ||
107 | func (fakeDirInfo) IsDir() bool { return true } | ||
108 | func (fakeDirInfo) Size() int64 { return 0 } | ||
109 | func (fakeDirInfo) Mode() os.FileMode { return 0755 } | ||