summaryrefslogtreecommitdiff
path: root/src/cmd/cgo/util.go
diff options
context:
space:
mode:
Diffstat (limited to 'src/cmd/cgo/util.go')
-rw-r--r--src/cmd/cgo/util.go110
1 files changed, 110 insertions, 0 deletions
diff --git a/src/cmd/cgo/util.go b/src/cmd/cgo/util.go
new file mode 100644
index 000000000..e79b0e1bf
--- /dev/null
+++ b/src/cmd/cgo/util.go
@@ -0,0 +1,110 @@
+// Copyright 2009 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+package main
+
+import (
+ "exec"
+ "fmt"
+ "go/token"
+ "io/ioutil"
+ "os"
+)
+
+// run runs the command argv, feeding in stdin on standard input.
+// It returns the output to standard output and standard error.
+// ok indicates whether the command exited successfully.
+func run(stdin []byte, argv []string) (stdout, stderr []byte, ok bool) {
+ cmd, err := exec.LookPath(argv[0])
+ if err != nil {
+ fatalf("exec %s: %s", argv[0], err)
+ }
+ r0, w0, err := os.Pipe()
+ if err != nil {
+ fatalf("%s", err)
+ }
+ r1, w1, err := os.Pipe()
+ if err != nil {
+ fatalf("%s", err)
+ }
+ r2, w2, err := os.Pipe()
+ if err != nil {
+ fatalf("%s", err)
+ }
+ p, err := os.StartProcess(cmd, argv, &os.ProcAttr{Files: []*os.File{r0, w1, w2}})
+ if err != nil {
+ fatalf("%s", err)
+ }
+ defer p.Release()
+ r0.Close()
+ w1.Close()
+ w2.Close()
+ c := make(chan bool)
+ go func() {
+ w0.Write(stdin)
+ w0.Close()
+ c <- true
+ }()
+ go func() {
+ stdout, _ = ioutil.ReadAll(r1)
+ r1.Close()
+ c <- true
+ }()
+ stderr, _ = ioutil.ReadAll(r2)
+ r2.Close()
+ <-c
+ <-c
+
+ w, err := p.Wait(0)
+ if err != nil {
+ fatalf("%s", err)
+ }
+ ok = w.Exited() && w.ExitStatus() == 0
+ return
+}
+
+// Die with an error message.
+func fatalf(msg string, args ...interface{}) {
+ fmt.Fprintf(os.Stderr, msg+"\n", args...)
+ os.Exit(2)
+}
+
+var nerrors int
+
+func error(pos token.Pos, msg string, args ...interface{}) {
+ nerrors++
+ if pos.IsValid() {
+ fmt.Fprintf(os.Stderr, "%s: ", fset.Position(pos).String())
+ }
+ fmt.Fprintf(os.Stderr, msg, args...)
+ fmt.Fprintf(os.Stderr, "\n")
+}
+
+// isName returns true if s is a valid C identifier
+func isName(s string) bool {
+ for i, v := range s {
+ if v != '_' && (v < 'A' || v > 'Z') && (v < 'a' || v > 'z') && (v < '0' || v > '9') {
+ return false
+ }
+ if i == 0 && '0' <= v && v <= '9' {
+ return false
+ }
+ }
+ return s != ""
+}
+
+func creat(name string) *os.File {
+ f, err := os.Create(name)
+ if err != nil {
+ fatalf("%s", err)
+ }
+ return f
+}
+
+func slashToUnderscore(c int) int {
+ if c == '/' || c == '\\' || c == ':' {
+ c = '_'
+ }
+ return c
+}