augusto2112 created this revision.
augusto2112 added reviewers: labath, clayborg, jingham, aprantl.
augusto2112 requested review of this revision.
Herald added a project: LLDB.
Herald added a subscriber: lldb-commits.
Implements the required functions on gdb-remote so the '--include-existing'
flag of process attach works correctly on Linux.
Repository:
rG LLVM Github Monorepo
https://reviews.llvm.org/D94672
Files:
lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp
lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.h
Index: lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.h
===================================================================
--- lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.h
+++ lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.h
@@ -68,7 +68,7 @@
/// \return
/// An Status object indicating the success or failure of the
/// attach operation.
- Status AttachWaitProcess(llvm::StringRef process_name);
+ Status AttachWaitProcess(llvm::StringRef process_name, bool include_existing);
// NativeProcessProtocol::NativeDelegate overrides
void InitializeDelegate(NativeProcessProtocol *process) override;
@@ -183,6 +183,10 @@
PacketResult Handle_vAttachWait(StringExtractorGDBRemote &packet);
+ PacketResult Handle_qVAttachOrWaitSupported(StringExtractorGDBRemote &packet);
+
+ PacketResult Handle_vAttachOrWait(StringExtractorGDBRemote &packet);
+
PacketResult Handle_D(StringExtractorGDBRemote &packet);
PacketResult Handle_qThreadStopInfo(StringExtractorGDBRemote &packet);
Index: lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp
===================================================================
--- lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp
+++ lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp
@@ -162,6 +162,12 @@
RegisterMemberFunctionHandler(
StringExtractorGDBRemote::eServerPacketType_vAttachWait,
&GDBRemoteCommunicationServerLLGS::Handle_vAttachWait);
+ RegisterMemberFunctionHandler(
+ StringExtractorGDBRemote::eServerPacketType_qVAttachOrWaitSupported,
+ &GDBRemoteCommunicationServerLLGS::Handle_qVAttachOrWaitSupported);
+ RegisterMemberFunctionHandler(
+ StringExtractorGDBRemote::eServerPacketType_vAttachOrWait,
+ &GDBRemoteCommunicationServerLLGS::Handle_vAttachOrWait);
RegisterMemberFunctionHandler(
StringExtractorGDBRemote::eServerPacketType_vCont,
&GDBRemoteCommunicationServerLLGS::Handle_vCont);
@@ -338,7 +344,7 @@
}
Status GDBRemoteCommunicationServerLLGS::AttachWaitProcess(
- llvm::StringRef process_name) {
+ llvm::StringRef process_name, bool include_existing) {
Log *log(GetLogIfAnyCategoriesSet(LIBLLDB_LOG_PROCESS));
std::chrono::milliseconds polling_interval = std::chrono::milliseconds(1);
@@ -347,31 +353,43 @@
ProcessInstanceInfoList exclusion_list;
ProcessInstanceInfoMatch match_info;
match_info.GetProcessInfo().GetExecutableFile().SetFile(
- process_name, llvm::sys::path::Style::posix);
+ process_name, llvm::sys::path::Style::native);
match_info.SetNameMatchType(NameMatch::EndsWith);
- // Create the excluded process list before polling begins.
- Host::FindProcesses(match_info, exclusion_list);
- LLDB_LOG(log, "placed '{0}' processes in the exclusion list.",
- exclusion_list.size());
+ if (!include_existing) {
+ // Create the excluded process list before polling begins.
+ Host::FindProcesses(match_info, exclusion_list);
+ LLDB_LOG(log, "placed '{0}' processes in the exclusion list.",
+ exclusion_list.size());
+ } else {
+ LLDB_LOG(log, "including existing processes in search");
+ }
LLDB_LOG(log, "waiting for '{0}' to appear", process_name);
- auto is_in_exclusion_list =
- [&exclusion_list](const ProcessInstanceInfo &info) {
- for (auto &excluded : exclusion_list) {
- if (excluded.GetProcessID() == info.GetProcessID())
- return true;
- }
- return false;
- };
+ StreamString name_with_slash_stream;
+ name_with_slash_stream.Format("/{0}", process_name);
+ auto name_with_slash = name_with_slash_stream.GetString();
+
+ // Exclude a process if it's in the exclusion list, OR if the process info's
+ // name doesn't exactly match the desired name, nor ends with a slash followed
+ // by the desired name.
+ auto should_exclude_process = [&exclusion_list, &process_name,
+ &name_with_slash](
+ const ProcessInstanceInfo &info) {
+ for (auto &excluded : exclusion_list) {
+ if (excluded.GetProcessID() == info.GetProcessID())
+ return true;
+ }
+ auto info_name = info.GetNameAsStringRef();
+ return info_name != process_name && !info_name.endswith(name_with_slash);
+ };
ProcessInstanceInfoList loop_process_list;
while (true) {
loop_process_list.clear();
if (Host::FindProcesses(match_info, loop_process_list)) {
- // Remove all the elements that are in the exclusion list.
- llvm::erase_if(loop_process_list, is_in_exclusion_list);
+ llvm::erase_if(loop_process_list, should_exclude_process);
// One match! We found the desired process.
if (loop_process_list.size() == 1) {
@@ -3275,7 +3293,43 @@
LLDB_LOG(log, "attempting to attach to process named '{0}'", process_name);
- Status error = AttachWaitProcess(process_name);
+ Status error = AttachWaitProcess(process_name, false);
+ if (error.Fail()) {
+ LLDB_LOG(log, "failed to attach to process named '{0}': {1}", process_name,
+ error);
+ return SendErrorResponse(error);
+ }
+
+ // Notify we attached by sending a stop packet.
+ return SendStopReasonForState(m_debugged_process_up->GetState());
+}
+
+GDBRemoteCommunication::PacketResult
+GDBRemoteCommunicationServerLLGS::Handle_qVAttachOrWaitSupported(
+ StringExtractorGDBRemote &packet) {
+ return SendOKResponse();
+}
+
+GDBRemoteCommunication::PacketResult
+GDBRemoteCommunicationServerLLGS::Handle_vAttachOrWait(
+ StringExtractorGDBRemote &packet) {
+ Log *log(GetLogIfAnyCategoriesSet(LIBLLDB_LOG_PROCESS));
+
+ // Consume the ';' after the identifier.
+ packet.SetFilePos(strlen("vAttachOrWait"));
+
+ if (!packet.GetBytesLeft() || packet.GetChar() != ';')
+ return SendIllFormedResponse(packet, "vAttachOrWait missing expected ';'");
+
+ // Allocate the buffer for the process name from vAttachWait.
+ std::string process_name;
+ if (!packet.GetHexByteString(process_name))
+ return SendIllFormedResponse(packet,
+ "vAttachOrWait failed to parse process name");
+
+ LLDB_LOG(log, "attempting to attach to process named '{0}'", process_name);
+
+ Status error = AttachWaitProcess(process_name, true);
if (error.Fail()) {
LLDB_LOG(log, "failed to attach to process named '{0}': {1}", process_name,
error);
_______________________________________________
lldb-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits