diff options
Diffstat (limited to 'src/pkg/syscall/exec_windows.go')
-rw-r--r-- | src/pkg/syscall/exec_windows.go | 46 |
1 files changed, 21 insertions, 25 deletions
diff --git a/src/pkg/syscall/exec_windows.go b/src/pkg/syscall/exec_windows.go index c3ed3ba98..7256c3ae3 100644 --- a/src/pkg/syscall/exec_windows.go +++ b/src/pkg/syscall/exec_windows.go @@ -107,7 +107,7 @@ func escapeAddQuotes(s string) string { func CloseOnExec(fd int) { - return + SetHandleInformation(int32(fd), HANDLE_FLAG_INHERIT, 0) } func SetNonblock(fd int, nonblocking bool) (errno int) { @@ -117,13 +117,9 @@ func SetNonblock(fd int, nonblocking bool) (errno int) { // TODO(kardia): Add trace //The command and arguments are passed via the Command line parameter. -func forkExec(argv0 string, argv []string, envv []string, traceme bool, dir string, fd []int) (pid int, err int) { - if traceme == true { - return 0, EWINDOWS - } - +func StartProcess(argv0 string, argv []string, envv []string, dir string, fd []int) (pid, handle int, err int) { if len(fd) > 3 { - return 0, EWINDOWS + return 0, 0, EWINDOWS } //CreateProcess will throw an error if the dir is not set to a valid dir @@ -144,22 +140,31 @@ func forkExec(argv0 string, argv []string, envv []string, traceme bool, dir stri startupInfo.StdOutput = 0 startupInfo.StdErr = 0 + // Acquire the fork lock so that no other threads + // create new fds that are not yet close-on-exec + // before we fork. + ForkLock.Lock() + defer ForkLock.Unlock() + var currentProc, _ = GetCurrentProcess() if len(fd) > 0 && fd[0] > 0 { - if ok, err := DuplicateHandle(currentProc, int32(fd[0]), currentProc, &startupInfo.StdInput, 0, true, DUPLICATE_SAME_ACCESS); !ok { - return 0, err + err := DuplicateHandle(currentProc, int32(fd[0]), currentProc, &startupInfo.StdInput, 0, true, DUPLICATE_SAME_ACCESS) + if err != 0 { + return 0, 0, err } defer CloseHandle(int32(startupInfo.StdInput)) } if len(fd) > 1 && fd[1] > 0 { - if ok, err := DuplicateHandle(currentProc, int32(fd[1]), currentProc, &startupInfo.StdOutput, 0, true, DUPLICATE_SAME_ACCESS); !ok { - return 0, err + err := DuplicateHandle(currentProc, int32(fd[1]), currentProc, &startupInfo.StdOutput, 0, true, DUPLICATE_SAME_ACCESS) + if err != 0 { + return 0, 0, err } defer CloseHandle(int32(startupInfo.StdOutput)) } if len(fd) > 2 && fd[2] > 0 { - if ok, err := DuplicateHandle(currentProc, int32(fd[2]), currentProc, &startupInfo.StdErr, 0, true, DUPLICATE_SAME_ACCESS); !ok { - return 0, err + err := DuplicateHandle(currentProc, int32(fd[2]), currentProc, &startupInfo.StdErr, 0, true, DUPLICATE_SAME_ACCESS) + if err != 0 { + return 0, 0, err } defer CloseHandle(int32(startupInfo.StdErr)) } @@ -168,7 +173,7 @@ func forkExec(argv0 string, argv []string, envv []string, traceme bool, dir stri } // argv0 must not be longer then 256 chars // but the entire cmd line can have up to 32k chars (msdn) - ok, err := CreateProcess( + err = CreateProcess( nil, StringToUTF16Ptr(escapeAddQuotes(argv0)+" "+stringJoin(argv[1:], " ", escapeAddQuotes)), nil, //ptr to struct lpProcessAttributes @@ -180,23 +185,14 @@ func forkExec(argv0 string, argv []string, envv []string, traceme bool, dir stri startupInfo, processInfo) - if ok { + if err != 0 { pid = int(processInfo.ProcessId) - CloseHandle(processInfo.Process) + handle = int(processInfo.Process) CloseHandle(processInfo.Thread) } return } -func ForkExec(argv0 string, argv []string, envv []string, dir string, fd []int) (pid int, err int) { - return forkExec(argv0, argv, envv, false, dir, fd) -} - -// PtraceForkExec is like ForkExec, but starts the child in a traced state. -func PtraceForkExec(argv0 string, argv []string, envv []string, dir string, fd []int) (pid int, err int) { - return forkExec(argv0, argv, envv, true, dir, fd) -} - // Ordinary exec. func Exec(argv0 string, argv []string, envv []string) (err int) { return EWINDOWS |