in src/agent/Agent.cc [351:421]
void Agent::handleStartProcessPacket(ReadBuffer &packet)
{
ASSERT(m_childProcess == nullptr);
ASSERT(!m_closingOutputPipes);
const uint64_t spawnFlags = packet.getInt64();
const bool wantProcessHandle = packet.getInt32() != 0;
const bool wantThreadHandle = packet.getInt32() != 0;
const auto program = packet.getWString();
const auto cmdline = packet.getWString();
const auto cwd = packet.getWString();
const auto env = packet.getWString();
const auto desktop = packet.getWString();
packet.assertEof();
auto cmdlineV = vectorWithNulFromString(cmdline);
auto desktopV = vectorWithNulFromString(desktop);
auto envV = vectorFromString(env);
LPCWSTR programArg = program.empty() ? nullptr : program.c_str();
LPWSTR cmdlineArg = cmdline.empty() ? nullptr : cmdlineV.data();
LPCWSTR cwdArg = cwd.empty() ? nullptr : cwd.c_str();
LPWSTR envArg = env.empty() ? nullptr : envV.data();
STARTUPINFOW sui = {};
PROCESS_INFORMATION pi = {};
sui.cb = sizeof(sui);
sui.lpDesktop = desktop.empty() ? nullptr : desktopV.data();
BOOL inheritHandles = FALSE;
if (m_useConerr) {
inheritHandles = TRUE;
sui.dwFlags |= STARTF_USESTDHANDLES;
sui.hStdInput = GetStdHandle(STD_INPUT_HANDLE);
sui.hStdOutput = GetStdHandle(STD_OUTPUT_HANDLE);
sui.hStdError = m_errorBuffer->conout();
}
const BOOL success =
CreateProcessW(programArg, cmdlineArg, nullptr, nullptr,
/*bInheritHandles=*/inheritHandles,
/*dwCreationFlags=*/CREATE_UNICODE_ENVIRONMENT,
envArg, cwdArg, &sui, &pi);
const int lastError = success ? 0 : GetLastError();
trace("CreateProcess: %s %u",
(success ? "success" : "fail"),
static_cast<unsigned int>(pi.dwProcessId));
auto reply = newPacket();
if (success) {
int64_t replyProcess = 0;
int64_t replyThread = 0;
if (wantProcessHandle) {
replyProcess = int64FromHandle(duplicateHandle(pi.hProcess));
}
if (wantThreadHandle) {
replyThread = int64FromHandle(duplicateHandle(pi.hThread));
}
CloseHandle(pi.hThread);
m_childProcess = pi.hProcess;
m_autoShutdown = (spawnFlags & WINPTY_SPAWN_FLAG_AUTO_SHUTDOWN) != 0;
m_exitAfterShutdown = (spawnFlags & WINPTY_SPAWN_FLAG_EXIT_AFTER_SHUTDOWN) != 0;
reply.putInt32(static_cast<int32_t>(StartProcessResult::ProcessCreated));
reply.putInt64(replyProcess);
reply.putInt64(replyThread);
} else {
reply.putInt32(static_cast<int32_t>(StartProcessResult::CreateProcessFailed));
reply.putInt32(lastError);
}
writePacket(reply);
}