// Re-exec this image without dropping the listener passed to this function. func restart(listener net.Listener, errLogger *common.ErrorLogger) error { argv0, err := exec.LookPath(os.Args[0]) if nil != err { return err } wd, err := os.Getwd() if nil != err { return err } v := reflect.ValueOf(listener).Elem().FieldByName("fd").Elem() fd := uintptr(v.FieldByName("sysfd").Int()) allFiles := append([]*os.File{os.Stdin, os.Stdout, os.Stderr}, os.NewFile(fd, string(v.FieldByName("sysfile").String()))) p, err := os.StartProcess(argv0, os.Args, &os.ProcAttr{ Dir: wd, Env: append(os.Environ(), fmt.Sprintf("%s=%d", FDKey, fd)), Files: allFiles, }) if nil != err { return err } errLogger.Printf("spawned child %d\n", p.Pid) return nil }