OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-dev/] [or1k-gcc/] [libgo/] [go/] [exp/] [gotype/] [gotype.go] - Blame information for rev 747

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 747 jeremybenn
// Copyright 2011 The Go Authors. All rights reserved.
2
// Use of this source code is governed by a BSD-style
3
// license that can be found in the LICENSE file.
4
 
5
package main
6
 
7
import (
8
        "errors"
9
        "exp/types"
10
        "flag"
11
        "fmt"
12
        "go/ast"
13
        "go/parser"
14
        "go/scanner"
15
        "go/token"
16
        "io/ioutil"
17
        "os"
18
        "path/filepath"
19
        "strings"
20
)
21
 
22
var (
23
        // main operation modes
24
        pkgName   = flag.String("p", "", "process only those files in package pkgName")
25
        recursive = flag.Bool("r", false, "recursively process subdirectories")
26
        verbose   = flag.Bool("v", false, "verbose mode")
27
        allErrors = flag.Bool("e", false, "print all (including spurious) errors")
28
 
29
        // debugging support
30
        printTrace = flag.Bool("trace", false, "print parse trace")
31
        printAST   = flag.Bool("ast", false, "print AST")
32
)
33
 
34
var exitCode = 0
35
 
36
func usage() {
37
        fmt.Fprintf(os.Stderr, "usage: gotype [flags] [path ...]\n")
38
        flag.PrintDefaults()
39
        os.Exit(2)
40
}
41
 
42
func report(err error) {
43
        scanner.PrintError(os.Stderr, err)
44
        exitCode = 2
45
}
46
 
47
// parse returns the AST for the Go source src.
48
// The filename is for error reporting only.
49
// The result is nil if there were errors or if
50
// the file does not belong to the -p package.
51
func parse(fset *token.FileSet, filename string, src []byte) *ast.File {
52
        if *verbose {
53
                fmt.Println(filename)
54
        }
55
 
56
        // ignore files with different package name
57
        if *pkgName != "" {
58
                file, err := parser.ParseFile(fset, filename, src, parser.PackageClauseOnly)
59
                if err != nil {
60
                        report(err)
61
                        return nil
62
                }
63
                if file.Name.Name != *pkgName {
64
                        if *verbose {
65
                                fmt.Printf("\tignored (package %s)\n", file.Name.Name)
66
                        }
67
                        return nil
68
                }
69
        }
70
 
71
        // parse entire file
72
        mode := parser.DeclarationErrors
73
        if *allErrors {
74
                mode |= parser.SpuriousErrors
75
        }
76
        if *printTrace {
77
                mode |= parser.Trace
78
        }
79
        file, err := parser.ParseFile(fset, filename, src, mode)
80
        if err != nil {
81
                report(err)
82
                return nil
83
        }
84
        if *printAST {
85
                ast.Print(fset, file)
86
        }
87
 
88
        return file
89
}
90
 
91
func parseStdin(fset *token.FileSet) (files map[string]*ast.File) {
92
        files = make(map[string]*ast.File)
93
        src, err := ioutil.ReadAll(os.Stdin)
94
        if err != nil {
95
                report(err)
96
                return
97
        }
98
        const filename = ""
99
        if file := parse(fset, filename, src); file != nil {
100
                files[filename] = file
101
        }
102
        return
103
}
104
 
105
func parseFiles(fset *token.FileSet, filenames []string) (files map[string]*ast.File) {
106
        files = make(map[string]*ast.File)
107
        for _, filename := range filenames {
108
                src, err := ioutil.ReadFile(filename)
109
                if err != nil {
110
                        report(err)
111
                        continue
112
                }
113
                if file := parse(fset, filename, src); file != nil {
114
                        if files[filename] != nil {
115
                                report(errors.New(fmt.Sprintf("%q: duplicate file", filename)))
116
                                continue
117
                        }
118
                        files[filename] = file
119
                }
120
        }
121
        return
122
}
123
 
124
func isGoFilename(filename string) bool {
125
        // ignore non-Go files
126
        return !strings.HasPrefix(filename, ".") && strings.HasSuffix(filename, ".go")
127
}
128
 
129
func processDirectory(dirname string) {
130
        f, err := os.Open(dirname)
131
        if err != nil {
132
                report(err)
133
                return
134
        }
135
        filenames, err := f.Readdirnames(-1)
136
        f.Close()
137
        if err != nil {
138
                report(err)
139
                // continue since filenames may not be empty
140
        }
141
        for i, filename := range filenames {
142
                filenames[i] = filepath.Join(dirname, filename)
143
        }
144
        processFiles(filenames, false)
145
}
146
 
147
func processFiles(filenames []string, allFiles bool) {
148
        i := 0
149
        for _, filename := range filenames {
150
                switch info, err := os.Stat(filename); {
151
                case err != nil:
152
                        report(err)
153
                case info.IsDir():
154
                        if allFiles || *recursive {
155
                                processDirectory(filename)
156
                        }
157
                default:
158
                        if allFiles || isGoFilename(info.Name()) {
159
                                filenames[i] = filename
160
                                i++
161
                        }
162
                }
163
        }
164
        fset := token.NewFileSet()
165
        processPackage(fset, parseFiles(fset, filenames[0:i]))
166
}
167
 
168
func processPackage(fset *token.FileSet, files map[string]*ast.File) {
169
        // make a package (resolve all identifiers)
170
        pkg, err := ast.NewPackage(fset, files, types.GcImporter, types.Universe)
171
        if err != nil {
172
                report(err)
173
                return
174
        }
175
        _, err = types.Check(fset, pkg)
176
        if err != nil {
177
                report(err)
178
        }
179
}
180
 
181
func main() {
182
        flag.Usage = usage
183
        flag.Parse()
184
 
185
        if flag.NArg() == 0 {
186
                fset := token.NewFileSet()
187
                processPackage(fset, parseStdin(fset))
188
        } else {
189
                processFiles(flag.Args(), true)
190
        }
191
 
192
        os.Exit(exitCode)
193
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.