Пример #1
0
func compilePackage(compiler llgo.Compiler, fset *token.FileSet, files map[string]*ast.File, importpath string) (*llgo.Module, error) {
	// make a package (resolve all identifiers)
	pkg, err := ast.NewPackage(fset, files, types.GcImport, types.Universe)
	if err != nil {
		report(err)
		return nil, err
	}

	// an empty importpath means the same as the package name
	if importpath == "" {
		importpath = pkg.Name
	}

	exprTypes, err := types.Check(importpath, compiler, fset, pkg)
	if err != nil {
		report(err)
		return nil, err
	}

	if *dumpast {
		ast.Fprint(os.Stderr, fset, pkg, nil)
		os.Exit(0)
	}

	return compiler.Compile(fset, pkg, importpath, exprTypes)
}
Пример #2
0
func (f *file) debugRender(x interface{}) string {
	var buf bytes.Buffer
	if err := ast.Fprint(&buf, f.fset, x, nil); err != nil {
		panic(err)
	}
	return buf.String()
}
Пример #3
0
func compilePackage(fset *token.FileSet, files map[string]*ast.File) (*llgo.Module, error) {
	// make a package (resolve all identifiers)
	pkg, err := ast.NewPackage(fset, files, types.GcImport, types.Universe)
	if err != nil {
		report(err)
		return nil, err
	}

	exprTypes, err := types.Check(fset, pkg)
	if err != nil {
		report(err)
		return nil, err
	}

	if *dumpast {
		ast.Fprint(os.Stderr, fset, pkg, nil)
		os.Exit(0)
	}

	compiler := llgo.NewCompiler()
	compiler.SetTraceEnabled(*trace)
	compiler.SetTargetArch(*arch)
	compiler.SetTargetOs(*os_)
	return compiler.Compile(fset, pkg, exprTypes)
}
Пример #4
0
func main() {
	var filename string
	var src io.Reader
	var err error
	var astfile *ast.File

	fargs := flag.Args()
	if len(fargs) == 0 {
		filename = "-"
		src = os.Stdin
	} else if len(fargs) == 1 {
		filename = fargs[0]
		src, err = os.Open(filename)
		if err != nil {
			log.Fatal(err)
		}
	} else {
		fmt.Printf("usage: %s [-h] [options] [file]\n", path.Base(os.Args[0]))
		os.Exit(2)
	}

	fset := token.NewFileSet()
	astfile, err = parser.ParseFile(fset, filename, src, mode)
	if err != nil {
		log.Fatal(err)
	}

	if *astPrint {
		err = ast.Fprint(os.Stdout, fset, astfile, nil)
		if err != nil {
			log.Fatal(err)
		}
	}
}
Пример #5
0
func (w *Walker) nodeDebug(node interface{}) string {
	if node == nil {
		return ""
	}
	var b bytes.Buffer
	ast.Fprint(&b, w.fset, node, nil)
	return b.String()
}
Пример #6
0
func TestAddImport(t *testing.T) {
	for _, test := range addTests {
		file := parse(t, test.name, test.in)
		var before bytes.Buffer
		ast.Fprint(&before, fset, file, nil)
		AddNamedImport(fset, file, test.renamedPkg, test.pkg)
		if got := print(t, test.name, file); got != test.out {
			if test.broken {
				t.Logf("%s is known broken:\ngot: %s\nwant: %s", test.name, got, test.out)
			} else {
				t.Errorf("%s:\ngot: %s\nwant: %s", test.name, got, test.out)
			}
			var after bytes.Buffer
			ast.Fprint(&after, fset, file, nil)

			t.Logf("AST before:\n%s\nAST after:\n%s\n", before.String(), after.String())
		}
	}
}
Пример #7
0
func Parse(filename string, source string) (a *Ast, dump string, err error) {

	// Create the AST by parsing src.
	fset := token.NewFileSet() // positions are relative to fset
	f, err := parser.ParseFile(fset, filename, source, 0)

	// Print the AST.
	var bf bytes.Buffer
	ast.Fprint(&bf, fset, f, ast.NotNilFilter)

	a, err = BuildAst("", f)
	if err != nil {
		return nil, "", err
	}
	return a, string(bf.Bytes()), nil
}
Пример #8
0
func main() {
	var input io.Reader
	var err os.Error
	var filename string

	{
		temp := "a⍨c"
		fmt.Printf("Len: %v\n", len(temp))
		for i := 0; i < len(temp); i++ {
			fmt.Printf("%3d: %02x\n", i, temp[i])
		}
	}

	if flag.NArg() > 0 {
		filename = flag.Arg(0)
		if input, err = os.Open(flag.Arg(0)); err != nil {
			fmt.Print("Failed to open input: ", err)
			os.Exit(1)
		}
	} else {
		input = os.Stdin
		filename = "stdin"
	}

	var src_ast *ast.File
	fset := token.NewFileSet()
	src_ast, err = parser.ParseFile(fset, filename, input, parser.ParseComments) // | parser.Trace)
	if err != nil {
		panic(err)
	}

	Transform(src_ast)
	//dfa := CreateAutomata(source)

	outfile, err := os.Create(*output_file)
	if err != nil {
		fmt.Print("Failed to open output file: ", err)
		os.Exit(1)
	}
	//if  err := printer.Fprint(outfile, fset, src_ast); err != nil {
	//fmt.Printf("%#v\n", src_ast)
	if _, err := ast.Fprint(outfile, fset, src_ast, nil); err != nil {
		fmt.Print("Write failed: ", err)
		os.Exit(1)
	}
	outfile.Close()
}
Пример #9
0
func Example() {
	stmt, err := parserutil.ParseStmt("var x int")
	if err != nil {
		panic(err)
	}

	ast.Fprint(os.Stdout, nil, stmt, nil)

	// Output:
	//      0  *ast.DeclStmt {
	//      1  .  Decl: *ast.GenDecl {
	//      2  .  .  Doc: nil
	//      3  .  .  TokPos: 31
	//      4  .  .  Tok: var
	//      5  .  .  Lparen: 0
	//      6  .  .  Specs: []ast.Spec (len = 1) {
	//      7  .  .  .  0: *ast.ValueSpec {
	//      8  .  .  .  .  Doc: nil
	//      9  .  .  .  .  Names: []*ast.Ident (len = 1) {
	//     10  .  .  .  .  .  0: *ast.Ident {
	//     11  .  .  .  .  .  .  NamePos: 35
	//     12  .  .  .  .  .  .  Name: "x"
	//     13  .  .  .  .  .  .  Obj: *ast.Object {
	//     14  .  .  .  .  .  .  .  Kind: var
	//     15  .  .  .  .  .  .  .  Name: "x"
	//     16  .  .  .  .  .  .  .  Decl: *(obj @ 7)
	//     17  .  .  .  .  .  .  .  Data: 0
	//     18  .  .  .  .  .  .  .  Type: nil
	//     19  .  .  .  .  .  .  }
	//     20  .  .  .  .  .  }
	//     21  .  .  .  .  }
	//     22  .  .  .  .  Type: *ast.Ident {
	//     23  .  .  .  .  .  NamePos: 37
	//     24  .  .  .  .  .  Name: "int"
	//     25  .  .  .  .  .  Obj: nil
	//     26  .  .  .  .  }
	//     27  .  .  .  .  Values: nil
	//     28  .  .  .  .  Comment: nil
	//     29  .  .  .  }
	//     30  .  .  }
	//     31  .  .  Rparen: 0
	//     32  .  }
	//     33  }
}
Пример #10
0
func main() {
	if len(os.Args) != 2 {
		fmt.Printf("usage: astprint <filename.go>\n")
		return
	}

	// Создаём хранилище данных об исходных файлах
	fset := token.NewFileSet()

	// Вызываем парсер
	if file, err := parser.ParseFile(
		fset,                 // данные об исходниках
		os.Args[1],           // имя файла с исходником программы
		nil,                  // пусть парсер сам загрузит исходник
		parser.ParseComments, // приказываем сохранять комментарии
	); err == nil {
		// Если парсер отработал без ошибок, печатаем дерево
		ast.Fprint(os.Stdout, fset, file, nil)
	} else {
		// в противном случае, выводим сообщение об ошибке
		fmt.Printf("Error: %v", err)
	}
}
Пример #11
0
func Process(filename string) (pkg string, mocks []*Mock, err os.Error) {
	fset := token.NewFileSet()
	file, err := parser.ParseFile(fset, filename, nil, parser.ParseComments)
	if err != nil {
		return "", nil, err
	}

	var toString func(interface{}) string
	toString = func(x interface{}) (str string) {
		switch x := x.(type) {
		case *ast.BasicLit:
			return x.Value
		case *ast.Ident:
			return x.Name
		case *ast.ArrayType:
			return "[" + toString(x.Len) + "]" + toString(x.Elt)
		case *ast.MapType:
			return "map[" + toString(x.Key) + "]" + toString(x.Value)
		case *ast.SelectorExpr:
			return toString(x.X) + "." + toString(x.Sel)
		case nil:
			return ""
		default:
			// TODO(kevlar): Ellipsis (variadic functions)
			fmt.Fprintf(os.Stderr, "Unable to determine string for %T:\n", x)
			ast.Fprint(os.Stderr, fset, x, nil)
		}
		return "unknown"
	}

	pkg = toString(file.Name)

	for _, decl := range file.Decls {
		if gen, ok := decl.(*ast.GenDecl); ok && gen.Tok == token.TYPE {
			for _, spec := range gen.Specs {
				if tspec, ok := spec.(*ast.TypeSpec); ok {
					if iface, ok := tspec.Type.(*ast.InterfaceType); ok {
						mock := &Mock{
							Name: toString(tspec.Name),
						}
						mocks = append(mocks, mock)
						for _, method := range iface.Methods.List {
							meth := &Method{
								Name: toString(method.Names[0]),
							}
							mock.Methods = append(mock.Methods, meth)
							if f, ok := method.Type.(*ast.FuncType); ok {
								if f.Params != nil {
									for _, param := range f.Params.List {
										meth.Params = append(meth.Params, toString(param.Type))
									}
								}
								if f.Results != nil {
									for _, ret := range f.Results.List {
										meth.Returns = append(meth.Returns, toString(ret.Type))
									}
								}
							}
						}
					}
				}
			}
		}
	}

	return
}
Пример #12
0
func oneFile(dir, s string, fset *token.FileSet, f *ast.File) error {
	// Inspect the AST and change all instances of main()
	isMain := false
	ast.Inspect(f, func(n ast.Node) bool {
		switch x := n.(type) {
		case *ast.File:
			x.Name.Name = config.CmdName
		case *ast.FuncDecl:
			if x.Name.Name == "main" {
				x.Name.Name = fmt.Sprintf("Main")
				// Append a return.
				x.Body.List = append(x.Body.List, &ast.ReturnStmt{})
				isMain = true
			}

		case *ast.CallExpr:
			debug("%v %v\n", reflect.TypeOf(n), n)
			switch z := x.Fun.(type) {
			case *ast.SelectorExpr:
				// somebody tell me how to do this.
				sel := fmt.Sprintf("%v", z.X)
				// TODO: Need to have fixFlag and fixFlagVar
				// as the Var variation has name in the SECOND argument.
				if sel == "flag" {
					if ix, ok := fixFlag[z.Sel.Name]; ok {
						switch zz := x.Args[ix].(type) {
						case *ast.BasicLit:
							zz.Value = "\"" + config.CmdName + "." + zz.Value[1:]
						}
					}
				}
			}
		}
		return true
	})

	if *dumpAST {
		ast.Fprint(os.Stderr, fset, f, nil)
	}
	var buf bytes.Buffer
	if err := format.Node(&buf, fset, f); err != nil {
		panic(err)
	}
	debug("%s", buf.Bytes())
	out := string(buf.Bytes())

	// fix up any imports. We may have forced the issue
	// with os.Args
	opts := imports.Options{
		Fragment:  true,
		AllErrors: true,
		Comments:  true,
		TabIndent: true,
		TabWidth:  8,
	}
	fullCode, err := imports.Process("commandline", []byte(out), &opts)
	if err != nil {
		log.Fatalf("bad parse: '%v': %v", out, err)
	}

	of := path.Join(dir, path.Base(s))
	if err := ioutil.WriteFile(of, []byte(fullCode), 0666); err != nil {
		log.Fatalf("%v\n", err)
	}

	// fun: must write the file first so the import fixup works :-)
	if isMain {
		// Write the file to interface to the command package.
		t := template.Must(template.New("cmdFunc").Parse(cmdFunc))
		var b bytes.Buffer
		if err := t.Execute(&b, config); err != nil {
			log.Fatalf("spec %v: %v\n", cmdFunc, err)
		}
		fullCode, err := imports.Process("commandline", []byte(b.Bytes()), &opts)
		if err != nil {
			log.Fatalf("bad parse: '%v': %v", out, err)
		}
		if err := ioutil.WriteFile(path.Join(config.Bbsh, "cmd_"+config.CmdName+".go"), fullCode, 0444); err != nil {
			log.Fatalf("%v\n", err)
		}
	}

	return nil
}
Пример #13
0
func createAstFileDump(filename string, fileSet *token.FileSet, astFile *ast.File) {
	file, err := os.Create(filename)
	util.PanicOnError(err)
	defer file.Close()
	ast.Fprint(file, fileSet, astFile, ast.NotNilFilter)
}
Пример #14
0
func printNode(n ast.Node) {
	var w bytes.Buffer
	ast.Fprint(&w, nil, n, nil)
	fmt.Printf(w.String())
}