void CmdInternalTesting::onClientImpl(DebuggerClient &client) { TRACE(2, "CmdInternalTesting::onClientImpl\n"); if (DebuggerCommand::displayedHelp(client)) return; if (client.argCount() == 0) { help(client); return; } client.info("Executing internal test..."); m_arg = client.argValue(1); if (client.arg(1, "badcmdtypesend")) { // Give the cmd a bad type and send it over. This should cause the proxy to // disconnect from us. m_type = KindOfInternalTestingBad; client.sendToServer(this); // Spin here and wait for the client to be marked as stopped // before going back to the event loop. This will give the local // proxy time to recgonize the bad cmd, terminate, and wait for // the client to stop. This will ensure that we always exit on the // same path on both proxy and client threads, and remove any // spurious output form ths test case. while (!client.internalTestingIsClientStopped()) { sleep(1); } throw DebuggerConsoleExitException(); // Expect no response } else if (client.arg(1, "badcmdtypereceive")) { client.xend<CmdInternalTesting>(this); return; } else if (client.arg(1, "shortcmdsend")) { m_arg = "shortcmd"; // Force send to drop a field. client.sendToServer(this); // See note above about this wait. while (!client.internalTestingIsClientStopped()) { sleep(1); } throw DebuggerConsoleExitException(); // Expect no response } else if (client.arg(1, "shortcmdreceive")) { client.xend<CmdInternalTesting>(this); return; } else if (client.arg(1, "segfaultClient")) { int *px = nullptr; *px = 42; } else if (client.arg(1, "segfaultServer")) { client.xend<CmdInternalTesting>(this); return; } help(client); }
void CmdFlowControl::onClient(DebuggerClient &client) { if (DebuggerCommand::displayedHelp(client)) return; client.setFrame(0); if (client.argCount() > 1) { help(client); return; } if (client.argCount() == 1) { std::string snum = client.argValue(1); if (!DebuggerClient::IsValidNumber(snum)) { client.error("Count needs to be a number."); return; } m_count = atoi(snum.c_str()); if (m_count < 1) { client.error("Count needs to be a positive number."); return; } } m_smallStep = client.getDebuggerClientSmallStep(); client.sendToServer(this); throw DebuggerConsoleExitException(); }
bool CmdFlowControl::onClient(DebuggerClient *client) { if (DebuggerCommand::onClient(client)) return true; client->setFrame(0); if (client->argCount() > 1) { return help(client); } if (client->argCount() == 1) { string snum = client->argValue(1); if (!DebuggerClient::IsValidNumber(snum)) { client->error("Count needs to be a number."); return true; } m_count = atoi(snum.c_str()); if (m_count < 1) { client->error("Count needs to be a positive number."); return true; } } client->send(this); throw DebuggerConsoleExitException(); }
bool CmdRun::onClient(DebuggerClient *client) { if (DebuggerCommand::onClient(client)) return true; m_args = StringVecPtr(client->args(), null_deleter()); client->send(this); throw DebuggerConsoleExitException(); }
void CmdRun::onClient(DebuggerClient &client) { TRACE(2, "CmdRun::onClient\n"); if (DebuggerCommand::displayedHelp(client)) return; m_args = StringVecPtr(client.args(), null_deleter()); client.sendToServer(this); client.clearCachedLocal(); client.setFrame(0); throw DebuggerConsoleExitException(); }
void CmdRun::onClientImpl(DebuggerClient &client) { if (DebuggerCommand::displayedHelp(client)) return; m_args = StringVecPtr(client.args(), null_deleter()); m_smallStep = client.getDebuggerSmallStep(); client.sendToServer(this); client.clearCachedLocal(); client.setFrame(0); throw DebuggerConsoleExitException(); }
void CmdRun::onClient(DebuggerClient &client) { TRACE(2, "CmdRun::onClient\n"); if (DebuggerCommand::displayedHelp(client)) return; m_args = std::shared_ptr<std::vector<std::string>>(client.args(), [] (const void*) {}); client.sendToServer(this); client.clearCachedLocal(); client.setFrame(0); throw DebuggerConsoleExitException(); }
bool CmdMachine::AttachSandbox(DebuggerClient *client, DSandboxInfoPtr sandbox) { if (client->isLocal()) { client->error("Local script doesn't have sandbox to attach to."); return true; } CmdMachine cmd; cmd.m_body = "attach"; cmd.m_sandboxes.push_back(sandbox); client->send(&cmd); client->info("Pre-loading %s, please wait...", sandbox->desc().c_str()); throw DebuggerConsoleExitException(); }
void CmdThread::onClient(DebuggerClient &client) { if (DebuggerCommand::displayedHelp(client)) return; if (client.argCount() > 1) { help(client); return; } if (client.argCount() == 0) { m_body = "info"; auto res = client.xend<CmdThread>(this); client.print(res->m_out); } else if (client.arg(1, "list")) { processList(client); } else if (client.arg(1, "normal")) { m_body = "normal"; client.sendToServer(this); client.info("Thread is running in normal mode now. Other threads will " "interleave when they hit breakpoints as well."); } else if (client.arg(1, "sticky")) { m_body = "sticky"; client.sendToServer(this); client.info("Thread is running in sticky mode now. All other threads " "will wait until this thread finishes, when they hit " "breakpoints."); } else if (client.arg(1, "exclusive")) { m_body = "exclusive"; client.sendToServer(this); client.info("Thread is running in exclusive mode now. All other threads " "will not break, even when they hit breakpoints."); } else { std::string snum = client.argValue(1); if (!DebuggerClient::IsValidNumber(snum)) { client.error("'[t]hread {index}' needs a numeric argument."); client.tutorial( "You will have to run '[t]hread [l]ist' first to see a list of valid " "numbers or indices to specify. Thread 1 is always your current " "thread. If that's the only thread on the list, you do not have " "another thread at break to switch to." ); return; } int num = atoi(snum.c_str()); DThreadInfoPtr thread = client.getThread(num); if (!thread) { processList(client, false); thread = client.getThread(num); if (!thread) { client.error("\"%s\" is not a valid thread index. Choose one from " "this list:", snum.c_str()); processList(client); return; } } if (thread->m_id == client.getCurrentThreadId()) { client.info("This is your current thread already."); return; } m_body = "switch"; m_threads.push_back(thread); client.sendToServer(this); throw DebuggerConsoleExitException(); } }
void CmdMachine::onClientImpl(DebuggerClient &client) { if (DebuggerCommand::displayedHelp(client)) return; if (client.argCount() == 0) { help(client); return; } bool rpc = client.arg(1, "rpc"); if (rpc || client.arg(1, "connect")) { if (client.argCount() != 2) { help(client); return; } string host = client.argValue(2); int port = 0; size_t pos = host.find(":"); if (pos != string::npos) { if (!DebuggerClient::IsValidNumber(host.substr(pos + 1))) { client.error("Port needs to be a number"); help(client); return; } port = atoi(host.substr(pos + 1).c_str()); host = host.substr(0, pos); } if (rpc) { if (client.connectRPC(host, port)) { throw DebuggerConsoleExitException(); } } else { if (client.connect(host, port)) { throw DebuggerConsoleExitException(); } } if (!client.initializeMachine()) { throw DebuggerConsoleExitException(); } return; } if (client.arg(1, "disconnect")) { if (client.disconnect()) { throw DebuggerConsoleExitException(); } if (!client.initializeMachine()) { throw DebuggerConsoleExitException(); } return; } if (client.arg(1, "list")) { processList(client); return; } if (client.arg(1, "attach")) { DSandboxInfoPtr sandbox; string snum = client.argValue(2); if (DebuggerClient::IsValidNumber(snum)) { int num = atoi(snum.c_str()); sandbox = client.getSandbox(num); if (!sandbox) { processList(client, false); sandbox = client.getSandbox(num); if (!sandbox) { client.error("\"%s\" is not a valid sandbox index. Choose one from " "this list:", snum.c_str()); processList(client); return; } } } else { int argBase = 2; if (client.argCount() >= 2 && client.arg(2, "force")) { m_force = true; argBase++; } sandbox = DSandboxInfoPtr(new DSandboxInfo()); if (client.argCount() < argBase) { sandbox->m_user = client.getCurrentUser(); sandbox->m_name = "default"; } else if (client.argCount() == argBase) { sandbox->m_user = client.getCurrentUser(); sandbox->m_name = client.argValue(argBase); } else if (client.argCount() == argBase + 1) { sandbox->m_user = client.argValue(argBase); sandbox->m_name = client.argValue(argBase + 1); } else { help(client); return; } } if (AttachSandbox(client, sandbox, m_force)) { // Attach succeed, wait for next interrupt throw DebuggerConsoleExitException(); } return; } help(client); }
bool CmdMachine::onClient(DebuggerClient *client) { if (DebuggerCommand::onClient(client)) return true; if (client->argCount() == 0) return help(client); bool rpc = client->arg(1, "rpc"); if (rpc || client->arg(1, "connect")) { if (client->argCount() != 2) { return help(client); } string host = client->argValue(2); int port = 0; size_t pos = host.find(":"); if (pos != string::npos) { if (!DebuggerClient::IsValidNumber(host.substr(pos + 1))) { client->error("Port needs to be a number"); return help(client); } port = atoi(host.substr(pos + 1).c_str()); host = host.substr(0, pos); } if (rpc) { if (client->connectRPC(host, port)) { throw DebuggerConsoleExitException(); } } else { if (client->connect(host, port)) { throw DebuggerConsoleExitException(); } } client->initializeMachine(); return true; } if (client->arg(1, "disconnect")) { if (client->disconnect()) { throw DebuggerConsoleExitException(); } client->initializeMachine(); return true; } if (client->arg(1, "list")) { processList(client); return true; } if (client->arg(1, "attach")) { DSandboxInfoPtr sandbox; string snum = client->argValue(2); if (DebuggerClient::IsValidNumber(snum)) { int num = atoi(snum.c_str()); sandbox = client->getSandbox(num); if (!sandbox) { processList(client, false); sandbox = client->getSandbox(num); if (!sandbox) { client->error("\"%s\" is not a valid sandbox index. Choose one from " "this list:", snum.c_str()); processList(client); return true; } } } else if (client->argCount() == 2) { sandbox = DSandboxInfoPtr(new DSandboxInfo()); sandbox->m_user = Process::GetCurrentUser(); sandbox->m_name = snum; } else if (client->argCount() == 3) { sandbox = DSandboxInfoPtr(new DSandboxInfo()); sandbox->m_user = snum; sandbox->m_name = client->argValue(3); } else { return help(client); } return AttachSandbox(client, sandbox); } return help(client); }