1// Copyright 2013 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 5package gccgoimporter 6 7import ( 8 "bufio" 9 "go/types" 10 "os" 11 "os/exec" 12 "path/filepath" 13 "strings" 14) 15 16// Information about a specific installation of gccgo. 17type GccgoInstallation struct { 18 // Version of gcc (e.g. 4.8.0). 19 GccVersion string 20 21 // Target triple (e.g. x86_64-unknown-linux-gnu). 22 TargetTriple string 23 24 // Built-in library paths used by this installation. 25 LibPaths []string 26} 27 28// Ask the driver at the given path for information for this GccgoInstallation. 29func (inst *GccgoInstallation) InitFromDriver(gccgoPath string) (err error) { 30 cmd := exec.Command(gccgoPath, "-###", "-S", "-x", "go", "-") 31 stderr, err := cmd.StderrPipe() 32 if err != nil { 33 return 34 } 35 36 err = cmd.Start() 37 if err != nil { 38 return 39 } 40 41 scanner := bufio.NewScanner(stderr) 42 for scanner.Scan() { 43 line := scanner.Text() 44 switch { 45 case strings.HasPrefix(line, "Target: "): 46 inst.TargetTriple = line[8:] 47 48 case line[0] == ' ': 49 args := strings.Fields(line) 50 for _, arg := range args[1:] { 51 if strings.HasPrefix(arg, "-L") { 52 inst.LibPaths = append(inst.LibPaths, arg[2:]) 53 } 54 } 55 } 56 } 57 58 stdout, err := exec.Command(gccgoPath, "-dumpversion").Output() 59 if err != nil { 60 return 61 } 62 inst.GccVersion = strings.TrimSpace(string(stdout)) 63 64 return 65} 66 67// Return the list of export search paths for this GccgoInstallation. 68func (inst *GccgoInstallation) SearchPaths() (paths []string) { 69 for _, lpath := range inst.LibPaths { 70 spath := filepath.Join(lpath, "go", inst.GccVersion) 71 fi, err := os.Stat(spath) 72 if err != nil || !fi.IsDir() { 73 continue 74 } 75 paths = append(paths, spath) 76 77 spath = filepath.Join(spath, inst.TargetTriple) 78 fi, err = os.Stat(spath) 79 if err != nil || !fi.IsDir() { 80 continue 81 } 82 paths = append(paths, spath) 83 } 84 85 paths = append(paths, inst.LibPaths...) 86 87 return 88} 89 90// Return an importer that searches incpaths followed by the gcc installation's 91// built-in search paths and the current directory. 92func (inst *GccgoInstallation) GetImporter(incpaths []string, initmap map[*types.Package]InitData) Importer { 93 return GetImporter(append(append(incpaths, inst.SearchPaths()...), "."), initmap) 94} 95