2011-03-15 20:33:57 -06:00
|
|
|
// Copyright 2011 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 (
|
|
|
|
"go/ast"
|
|
|
|
"go/token"
|
|
|
|
)
|
|
|
|
|
|
|
|
var procattrFix = fix{
|
|
|
|
"procattr",
|
|
|
|
procattr,
|
2011-03-29 19:30:59 -06:00
|
|
|
`Adapt calls to os.StartProcess to use new ProcAttr type.
|
2011-03-15 20:33:57 -06:00
|
|
|
|
|
|
|
http://codereview.appspot.com/4253052
|
|
|
|
`,
|
|
|
|
}
|
|
|
|
|
|
|
|
func procattr(f *ast.File) bool {
|
|
|
|
if !imports(f, "os") && !imports(f, "syscall") {
|
|
|
|
return false
|
|
|
|
}
|
|
|
|
|
|
|
|
fixed := false
|
2011-04-08 10:27:08 -06:00
|
|
|
walk(f, func(n interface{}) {
|
2011-03-15 20:33:57 -06:00
|
|
|
call, ok := n.(*ast.CallExpr)
|
|
|
|
if !ok || len(call.Args) != 5 {
|
|
|
|
return
|
|
|
|
}
|
|
|
|
var pkg string
|
|
|
|
if isPkgDot(call.Fun, "os", "StartProcess") {
|
|
|
|
pkg = "os"
|
|
|
|
} else if isPkgDot(call.Fun, "syscall", "StartProcess") {
|
|
|
|
pkg = "syscall"
|
|
|
|
} else {
|
|
|
|
return
|
|
|
|
}
|
|
|
|
// os.StartProcess(a, b, c, d, e) -> os.StartProcess(a, b, &os.ProcAttr{Env: c, Dir: d, Files: e})
|
|
|
|
lit := &ast.CompositeLit{Type: ast.NewIdent(pkg + ".ProcAttr")}
|
|
|
|
env, dir, files := call.Args[2], call.Args[3], call.Args[4]
|
|
|
|
if !isName(env, "nil") && !isCall(env, "os", "Environ") {
|
|
|
|
lit.Elts = append(lit.Elts, &ast.KeyValueExpr{Key: ast.NewIdent("Env"), Value: env})
|
|
|
|
}
|
|
|
|
if !isEmptyString(dir) {
|
|
|
|
lit.Elts = append(lit.Elts, &ast.KeyValueExpr{Key: ast.NewIdent("Dir"), Value: dir})
|
|
|
|
}
|
|
|
|
if !isName(files, "nil") {
|
|
|
|
lit.Elts = append(lit.Elts, &ast.KeyValueExpr{Key: ast.NewIdent("Files"), Value: files})
|
|
|
|
}
|
|
|
|
call.Args[2] = &ast.UnaryExpr{Op: token.AND, X: lit}
|
|
|
|
call.Args = call.Args[:3]
|
|
|
|
fixed = true
|
|
|
|
})
|
|
|
|
return fixed
|
|
|
|
}
|