blob: 87bc0b9a67f70fa6923bb5ff511c05512c5f97bc [file] [log] [blame]
Chris Lattner24943d22010-06-08 16:52:24 +00001//===-- ProcessGDBRemote.cpp ------------------------------------*- C++ -*-===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
10// C Includes
11#include <errno.h>
Chris Lattner24943d22010-06-08 16:52:24 +000012#include <spawn.h>
Chris Lattner24943d22010-06-08 16:52:24 +000013#include <sys/types.h>
Chris Lattner24943d22010-06-08 16:52:24 +000014#include <sys/stat.h>
Chris Lattner24943d22010-06-08 16:52:24 +000015
16// C++ Includes
17#include <algorithm>
18#include <map>
19
20// Other libraries and framework includes
21
22#include "lldb/Breakpoint/WatchpointLocation.h"
Jim Ingham84cdc152010-06-15 19:49:27 +000023#include "lldb/Interpreter/Args.h"
Chris Lattner24943d22010-06-08 16:52:24 +000024#include "lldb/Core/ArchSpec.h"
25#include "lldb/Core/Debugger.h"
26#include "lldb/Core/ConnectionFileDescriptor.h"
Greg Clayton5f54ac32011-02-08 05:05:52 +000027#include "lldb/Host/FileSpec.h"
Chris Lattner24943d22010-06-08 16:52:24 +000028#include "lldb/Core/InputReader.h"
29#include "lldb/Core/Module.h"
30#include "lldb/Core/PluginManager.h"
31#include "lldb/Core/State.h"
32#include "lldb/Core/StreamString.h"
33#include "lldb/Core/Timer.h"
34#include "lldb/Host/TimeValue.h"
35#include "lldb/Symbol/ObjectFile.h"
36#include "lldb/Target/DynamicLoader.h"
37#include "lldb/Target/Target.h"
38#include "lldb/Target/TargetList.h"
Jason Molendadea5ea72010-06-09 21:28:42 +000039#include "lldb/Utility/PseudoTerminal.h"
Chris Lattner24943d22010-06-08 16:52:24 +000040
41// Project includes
42#include "lldb/Host/Host.h"
Greg Clayton54e7afa2010-07-09 20:39:50 +000043#include "Utility/StringExtractorGDBRemote.h"
Chris Lattner24943d22010-06-08 16:52:24 +000044#include "GDBRemoteRegisterContext.h"
45#include "ProcessGDBRemote.h"
46#include "ProcessGDBRemoteLog.h"
47#include "ThreadGDBRemote.h"
Greg Clayton643ee732010-08-04 01:40:35 +000048#include "StopInfoMachException.h"
49
Chris Lattner24943d22010-06-08 16:52:24 +000050
Chris Lattner24943d22010-06-08 16:52:24 +000051
52#define DEBUGSERVER_BASENAME "debugserver"
53using namespace lldb;
54using namespace lldb_private;
55
56static inline uint16_t
57get_random_port ()
58{
59 return (arc4random() % (UINT16_MAX - 1000u)) + 1000u;
60}
61
62
63const char *
64ProcessGDBRemote::GetPluginNameStatic()
65{
66 return "process.gdb-remote";
67}
68
69const char *
70ProcessGDBRemote::GetPluginDescriptionStatic()
71{
72 return "GDB Remote protocol based debugging plug-in.";
73}
74
75void
76ProcessGDBRemote::Terminate()
77{
78 PluginManager::UnregisterPlugin (ProcessGDBRemote::CreateInstance);
79}
80
81
82Process*
83ProcessGDBRemote::CreateInstance (Target &target, Listener &listener)
84{
85 return new ProcessGDBRemote (target, listener);
86}
87
88bool
89ProcessGDBRemote::CanDebug(Target &target)
90{
91 // For now we are just making sure the file exists for a given module
92 ModuleSP exe_module_sp(target.GetExecutableModule());
93 if (exe_module_sp.get())
94 return exe_module_sp->GetFileSpec().Exists();
Jim Ingham7508e732010-08-09 23:31:02 +000095 // However, if there is no executable module, we return true since we might be preparing to attach.
96 return true;
Chris Lattner24943d22010-06-08 16:52:24 +000097}
98
99//----------------------------------------------------------------------
100// ProcessGDBRemote constructor
101//----------------------------------------------------------------------
102ProcessGDBRemote::ProcessGDBRemote(Target& target, Listener &listener) :
103 Process (target, listener),
104 m_dynamic_loader_ap (),
Chris Lattner24943d22010-06-08 16:52:24 +0000105 m_flags (0),
Chris Lattner24943d22010-06-08 16:52:24 +0000106 m_stdio_mutex (Mutex::eMutexTypeRecursive),
Chris Lattner24943d22010-06-08 16:52:24 +0000107 m_gdb_comm(),
108 m_debugserver_pid (LLDB_INVALID_PROCESS_ID),
Greg Clayton75ccf502010-08-21 02:22:51 +0000109 m_debugserver_thread (LLDB_INVALID_HOST_THREAD),
Greg Clayton54e7afa2010-07-09 20:39:50 +0000110 m_last_stop_packet (),
Chris Lattner24943d22010-06-08 16:52:24 +0000111 m_register_info (),
Chris Lattner24943d22010-06-08 16:52:24 +0000112 m_async_broadcaster ("lldb.process.gdb-remote.async-broadcaster"),
113 m_async_thread (LLDB_INVALID_HOST_THREAD),
Greg Clayton54e7afa2010-07-09 20:39:50 +0000114 m_curr_tid (LLDB_INVALID_THREAD_ID),
115 m_curr_tid_run (LLDB_INVALID_THREAD_ID),
Chris Lattner24943d22010-06-08 16:52:24 +0000116 m_z0_supported (1),
Greg Claytonc1f45872011-02-12 06:28:37 +0000117 m_continue_c_tids (),
118 m_continue_C_tids (),
119 m_continue_s_tids (),
120 m_continue_S_tids (),
Chris Lattner24943d22010-06-08 16:52:24 +0000121 m_dispatch_queue_offsets_addr (LLDB_INVALID_ADDRESS),
Greg Clayton54e7afa2010-07-09 20:39:50 +0000122 m_packet_timeout (1),
123 m_max_memory_size (512),
Jim Ingham7508e732010-08-09 23:31:02 +0000124 m_waiting_for_attach (false),
Jim Ingham55e01d82011-01-22 01:33:44 +0000125 m_local_debugserver (true),
126 m_thread_observation_bps()
Chris Lattner24943d22010-06-08 16:52:24 +0000127{
128}
129
130//----------------------------------------------------------------------
131// Destructor
132//----------------------------------------------------------------------
133ProcessGDBRemote::~ProcessGDBRemote()
134{
Greg Claytonff5cac22010-12-13 18:11:18 +0000135 m_dynamic_loader_ap.reset();
136
Greg Clayton09c81ef2011-02-08 01:34:25 +0000137 if (IS_VALID_LLDB_HOST_THREAD(m_debugserver_thread))
Greg Clayton75ccf502010-08-21 02:22:51 +0000138 {
139 Host::ThreadCancel (m_debugserver_thread, NULL);
140 thread_result_t thread_result;
141 Host::ThreadJoin (m_debugserver_thread, &thread_result, NULL);
142 m_debugserver_thread = LLDB_INVALID_HOST_THREAD;
143 }
Chris Lattner24943d22010-06-08 16:52:24 +0000144 // m_mach_process.UnregisterNotificationCallbacks (this);
145 Clear();
146}
147
148//----------------------------------------------------------------------
149// PluginInterface
150//----------------------------------------------------------------------
151const char *
152ProcessGDBRemote::GetPluginName()
153{
154 return "Process debugging plug-in that uses the GDB remote protocol";
155}
156
157const char *
158ProcessGDBRemote::GetShortPluginName()
159{
160 return GetPluginNameStatic();
161}
162
163uint32_t
164ProcessGDBRemote::GetPluginVersion()
165{
166 return 1;
167}
168
169void
170ProcessGDBRemote::GetPluginCommandHelp (const char *command, Stream *strm)
171{
172 strm->Printf("TODO: fill this in\n");
173}
174
175Error
176ProcessGDBRemote::ExecutePluginCommand (Args &command, Stream *strm)
177{
178 Error error;
179 error.SetErrorString("No plug-in commands are currently supported.");
180 return error;
181}
182
183Log *
184ProcessGDBRemote::EnablePluginLogging (Stream *strm, Args &command)
185{
186 return NULL;
187}
188
189void
Greg Clayton7e2f91c2011-01-29 07:10:55 +0000190ProcessGDBRemote::BuildDynamicRegisterInfo (bool force)
Chris Lattner24943d22010-06-08 16:52:24 +0000191{
Greg Clayton7e2f91c2011-01-29 07:10:55 +0000192 if (!force && m_register_info.GetNumRegisters() > 0)
193 return;
194
195 char packet[128];
Chris Lattner24943d22010-06-08 16:52:24 +0000196 m_register_info.Clear();
197 StringExtractorGDBRemote::Type packet_type = StringExtractorGDBRemote::eResponse;
198 uint32_t reg_offset = 0;
199 uint32_t reg_num = 0;
200 for (; packet_type == StringExtractorGDBRemote::eResponse; ++reg_num)
201 {
Greg Clayton7e2f91c2011-01-29 07:10:55 +0000202 const int packet_len = ::snprintf (packet, sizeof(packet), "qRegisterInfo%x", reg_num);
203 assert (packet_len < sizeof(packet));
Chris Lattner24943d22010-06-08 16:52:24 +0000204 StringExtractorGDBRemote response;
Greg Clayton7e2f91c2011-01-29 07:10:55 +0000205 if (m_gdb_comm.SendPacketAndWaitForResponse(packet, packet_len, response, 2, false))
Chris Lattner24943d22010-06-08 16:52:24 +0000206 {
207 packet_type = response.GetType();
208 if (packet_type == StringExtractorGDBRemote::eResponse)
209 {
210 std::string name;
211 std::string value;
212 ConstString reg_name;
213 ConstString alt_name;
214 ConstString set_name;
215 RegisterInfo reg_info = { NULL, // Name
216 NULL, // Alt name
217 0, // byte size
218 reg_offset, // offset
219 eEncodingUint, // encoding
220 eFormatHex, // formate
Chris Lattner24943d22010-06-08 16:52:24 +0000221 {
222 LLDB_INVALID_REGNUM, // GCC reg num
223 LLDB_INVALID_REGNUM, // DWARF reg num
224 LLDB_INVALID_REGNUM, // generic reg num
Jason Molenda3a4ea242010-09-10 07:49:16 +0000225 reg_num, // GDB reg num
226 reg_num // native register number
Chris Lattner24943d22010-06-08 16:52:24 +0000227 }
228 };
229
230 while (response.GetNameColonValue(name, value))
231 {
232 if (name.compare("name") == 0)
233 {
234 reg_name.SetCString(value.c_str());
235 }
236 else if (name.compare("alt-name") == 0)
237 {
238 alt_name.SetCString(value.c_str());
239 }
240 else if (name.compare("bitsize") == 0)
241 {
242 reg_info.byte_size = Args::StringToUInt32(value.c_str(), 0, 0) / CHAR_BIT;
243 }
244 else if (name.compare("offset") == 0)
245 {
246 uint32_t offset = Args::StringToUInt32(value.c_str(), UINT32_MAX, 0);
Jason Molenda53d96862010-06-11 23:44:18 +0000247 if (reg_offset != offset)
Chris Lattner24943d22010-06-08 16:52:24 +0000248 {
249 reg_offset = offset;
Chris Lattner24943d22010-06-08 16:52:24 +0000250 }
251 }
252 else if (name.compare("encoding") == 0)
253 {
254 if (value.compare("uint") == 0)
255 reg_info.encoding = eEncodingUint;
256 else if (value.compare("sint") == 0)
257 reg_info.encoding = eEncodingSint;
258 else if (value.compare("ieee754") == 0)
259 reg_info.encoding = eEncodingIEEE754;
260 else if (value.compare("vector") == 0)
261 reg_info.encoding = eEncodingVector;
262 }
263 else if (name.compare("format") == 0)
264 {
265 if (value.compare("binary") == 0)
266 reg_info.format = eFormatBinary;
267 else if (value.compare("decimal") == 0)
268 reg_info.format = eFormatDecimal;
269 else if (value.compare("hex") == 0)
270 reg_info.format = eFormatHex;
271 else if (value.compare("float") == 0)
272 reg_info.format = eFormatFloat;
273 else if (value.compare("vector-sint8") == 0)
274 reg_info.format = eFormatVectorOfSInt8;
275 else if (value.compare("vector-uint8") == 0)
276 reg_info.format = eFormatVectorOfUInt8;
277 else if (value.compare("vector-sint16") == 0)
278 reg_info.format = eFormatVectorOfSInt16;
279 else if (value.compare("vector-uint16") == 0)
280 reg_info.format = eFormatVectorOfUInt16;
281 else if (value.compare("vector-sint32") == 0)
282 reg_info.format = eFormatVectorOfSInt32;
283 else if (value.compare("vector-uint32") == 0)
284 reg_info.format = eFormatVectorOfUInt32;
285 else if (value.compare("vector-float32") == 0)
286 reg_info.format = eFormatVectorOfFloat32;
287 else if (value.compare("vector-uint128") == 0)
288 reg_info.format = eFormatVectorOfUInt128;
289 }
290 else if (name.compare("set") == 0)
291 {
292 set_name.SetCString(value.c_str());
293 }
294 else if (name.compare("gcc") == 0)
295 {
296 reg_info.kinds[eRegisterKindGCC] = Args::StringToUInt32(value.c_str(), LLDB_INVALID_REGNUM, 0);
297 }
298 else if (name.compare("dwarf") == 0)
299 {
300 reg_info.kinds[eRegisterKindDWARF] = Args::StringToUInt32(value.c_str(), LLDB_INVALID_REGNUM, 0);
301 }
302 else if (name.compare("generic") == 0)
303 {
304 if (value.compare("pc") == 0)
305 reg_info.kinds[eRegisterKindGeneric] = LLDB_REGNUM_GENERIC_PC;
306 else if (value.compare("sp") == 0)
307 reg_info.kinds[eRegisterKindGeneric] = LLDB_REGNUM_GENERIC_SP;
308 else if (value.compare("fp") == 0)
309 reg_info.kinds[eRegisterKindGeneric] = LLDB_REGNUM_GENERIC_FP;
310 else if (value.compare("ra") == 0)
311 reg_info.kinds[eRegisterKindGeneric] = LLDB_REGNUM_GENERIC_RA;
312 else if (value.compare("flags") == 0)
313 reg_info.kinds[eRegisterKindGeneric] = LLDB_REGNUM_GENERIC_FLAGS;
314 }
315 }
316
Jason Molenda53d96862010-06-11 23:44:18 +0000317 reg_info.byte_offset = reg_offset;
Chris Lattner24943d22010-06-08 16:52:24 +0000318 assert (reg_info.byte_size != 0);
319 reg_offset += reg_info.byte_size;
320 m_register_info.AddRegister(reg_info, reg_name, alt_name, set_name);
321 }
322 }
323 else
324 {
325 packet_type = StringExtractorGDBRemote::eError;
326 }
327 }
328
329 if (reg_num == 0)
330 {
331 // We didn't get anything. See if we are debugging ARM and fill with
332 // a hard coded register set until we can get an updated debugserver
333 // down on the devices.
334 ArchSpec arm_arch ("arm");
335 if (GetTarget().GetArchitecture() == arm_arch)
336 m_register_info.HardcodeARMRegisters();
337 }
338 m_register_info.Finalize ();
339}
340
341Error
342ProcessGDBRemote::WillLaunch (Module* module)
343{
344 return WillLaunchOrAttach ();
345}
346
347Error
Greg Clayton20d338f2010-11-18 05:57:03 +0000348ProcessGDBRemote::WillAttachToProcessWithID (lldb::pid_t pid)
Chris Lattner24943d22010-06-08 16:52:24 +0000349{
350 return WillLaunchOrAttach ();
351}
352
353Error
Greg Clayton20d338f2010-11-18 05:57:03 +0000354ProcessGDBRemote::WillAttachToProcessWithName (const char *process_name, bool wait_for_launch)
Chris Lattner24943d22010-06-08 16:52:24 +0000355{
356 return WillLaunchOrAttach ();
357}
358
359Error
Greg Claytone71e2582011-02-04 01:58:07 +0000360ProcessGDBRemote::DoConnectRemote (const char *remote_url)
361{
362 Error error (WillLaunchOrAttach ());
363
364 if (error.Fail())
365 return error;
366
367 if (strncmp (remote_url, "connect://", strlen ("connect://")) == 0)
368 {
369 error = ConnectToDebugserver (remote_url);
370 }
371 else
372 {
373 error.SetErrorStringWithFormat ("unsupported remote url: %s", remote_url);
374 }
375
376 if (error.Fail())
377 return error;
378 StartAsyncThread ();
379
380 lldb::pid_t pid = m_gdb_comm.GetCurrentProcessID (m_packet_timeout);
381 if (pid == LLDB_INVALID_PROCESS_ID)
382 {
383 // We don't have a valid process ID, so note that we are connected
384 // and could now request to launch or attach, or get remote process
385 // listings...
386 SetPrivateState (eStateConnected);
387 }
388 else
389 {
390 // We have a valid process
391 SetID (pid);
392 StringExtractorGDBRemote response;
393 if (m_gdb_comm.SendPacketAndWaitForResponse("?", 1, response, m_packet_timeout, false))
394 {
395 const StateType state = SetThreadStopInfo (response);
396 if (state == eStateStopped)
397 {
398 SetPrivateState (state);
399 }
400 else
401 error.SetErrorStringWithFormat ("Process %i was reported after connecting to '%s', but state was not stopped: %s", pid, remote_url, StateAsCString (state));
402 }
403 else
404 error.SetErrorStringWithFormat ("Process %i was reported after connecting to '%s', but no stop reply packet was received", pid, remote_url);
405 }
406 return error;
407}
408
409Error
Chris Lattner24943d22010-06-08 16:52:24 +0000410ProcessGDBRemote::WillLaunchOrAttach ()
411{
412 Error error;
413 // TODO: this is hardcoded for macosx right now. We need this to be more dynamic
414 m_dynamic_loader_ap.reset(DynamicLoader::FindPlugin(this, "dynamic-loader.macosx-dyld"));
415
416 if (m_dynamic_loader_ap.get() == NULL)
417 error.SetErrorString("unable to find the dynamic loader named 'dynamic-loader.macosx-dyld'");
418 m_stdio_communication.Clear ();
419
420 return error;
421}
422
423//----------------------------------------------------------------------
424// Process Control
425//----------------------------------------------------------------------
426Error
427ProcessGDBRemote::DoLaunch
428(
429 Module* module,
430 char const *argv[],
431 char const *envp[],
Greg Clayton452bf612010-08-31 18:35:14 +0000432 uint32_t launch_flags,
Chris Lattner24943d22010-06-08 16:52:24 +0000433 const char *stdin_path,
434 const char *stdout_path,
Greg Claytonde915be2011-01-23 05:56:20 +0000435 const char *stderr_path,
436 const char *working_dir
Chris Lattner24943d22010-06-08 16:52:24 +0000437)
438{
Greg Clayton4b407112010-09-30 21:49:03 +0000439 Error error;
Chris Lattner24943d22010-06-08 16:52:24 +0000440 // ::LogSetBitMask (GDBR_LOG_DEFAULT);
441 // ::LogSetOptions (LLDB_LOG_OPTION_THREADSAFE | LLDB_LOG_OPTION_PREPEND_TIMESTAMP | LLDB_LOG_OPTION_PREPEND_PROC_AND_THREAD);
442 // ::LogSetLogFile ("/dev/stdout");
Chris Lattner24943d22010-06-08 16:52:24 +0000443
444 ObjectFile * object_file = module->GetObjectFile();
445 if (object_file)
446 {
447 ArchSpec inferior_arch(module->GetArchitecture());
448 char host_port[128];
449 snprintf (host_port, sizeof(host_port), "localhost:%u", get_random_port ());
Greg Claytone71e2582011-02-04 01:58:07 +0000450 char connect_url[128];
451 snprintf (connect_url, sizeof(connect_url), "connect://%s", host_port);
Chris Lattner24943d22010-06-08 16:52:24 +0000452
Greg Clayton23cf0c72010-11-08 04:29:11 +0000453 const bool launch_process = true;
Chris Lattner24943d22010-06-08 16:52:24 +0000454 bool start_debugserver_with_inferior_args = false;
455 if (start_debugserver_with_inferior_args)
456 {
457 // We want to launch debugserver with the inferior program and its
458 // arguments on the command line. We should only do this if we
459 // the GDB server we are talking to doesn't support the 'A' packet.
460 error = StartDebugserverProcess (host_port,
461 argv,
462 envp,
Greg Claytonde915be2011-01-23 05:56:20 +0000463 stdin_path,
464 stdout_path,
465 stderr_path,
466 working_dir,
Greg Clayton23cf0c72010-11-08 04:29:11 +0000467 launch_process,
Chris Lattner24943d22010-06-08 16:52:24 +0000468 LLDB_INVALID_PROCESS_ID,
469 NULL, false,
Caroline Ticebd666012010-12-03 18:46:09 +0000470 launch_flags,
Chris Lattner24943d22010-06-08 16:52:24 +0000471 inferior_arch);
472 if (error.Fail())
473 return error;
474
Greg Claytone71e2582011-02-04 01:58:07 +0000475 error = ConnectToDebugserver (connect_url);
Chris Lattner24943d22010-06-08 16:52:24 +0000476 if (error.Success())
477 {
478 SetID (m_gdb_comm.GetCurrentProcessID (m_packet_timeout));
479 }
480 }
481 else
482 {
483 error = StartDebugserverProcess (host_port,
484 NULL,
485 NULL,
Greg Claytonde915be2011-01-23 05:56:20 +0000486 stdin_path,
487 stdout_path,
488 stderr_path,
489 working_dir,
Greg Clayton23cf0c72010-11-08 04:29:11 +0000490 launch_process,
Chris Lattner24943d22010-06-08 16:52:24 +0000491 LLDB_INVALID_PROCESS_ID,
Greg Claytonde915be2011-01-23 05:56:20 +0000492 NULL,
493 false,
Caroline Ticebd666012010-12-03 18:46:09 +0000494 launch_flags,
Chris Lattner24943d22010-06-08 16:52:24 +0000495 inferior_arch);
496 if (error.Fail())
497 return error;
498
Greg Claytone71e2582011-02-04 01:58:07 +0000499 error = ConnectToDebugserver (connect_url);
Chris Lattner24943d22010-06-08 16:52:24 +0000500 if (error.Success())
501 {
502 // Send the environment and the program + arguments after we connect
503 if (envp)
504 {
505 const char *env_entry;
506 for (int i=0; (env_entry = envp[i]); ++i)
507 {
508 if (m_gdb_comm.SendEnvironmentPacket(env_entry, m_packet_timeout) != 0)
509 break;
510 }
511 }
512
Greg Clayton960d6a42010-08-03 00:35:52 +0000513 // FIXME: convert this to use the new set/show variables when they are available
514#if 0
515 if (::getenv ("LLDB_DEBUG_DEBUGSERVER"))
516 {
517 const uint32_t attach_debugserver_secs = 10;
518 ::printf ("attach to debugserver (pid = %i)\n", m_debugserver_pid);
519 for (uint32_t i=0; i<attach_debugserver_secs; ++i)
520 {
521 printf ("%i\n", attach_debugserver_secs - i);
522 sleep (1);
523 }
524 }
525#endif
526
Chris Lattner24943d22010-06-08 16:52:24 +0000527 const uint32_t arg_timeout_seconds = 10;
528 int arg_packet_err = m_gdb_comm.SendArgumentsPacket (argv, arg_timeout_seconds);
529 if (arg_packet_err == 0)
530 {
531 std::string error_str;
532 if (m_gdb_comm.GetLaunchSuccess (m_packet_timeout, error_str))
533 {
534 SetID (m_gdb_comm.GetCurrentProcessID (m_packet_timeout));
535 }
536 else
537 {
538 error.SetErrorString (error_str.c_str());
539 }
540 }
541 else
542 {
543 error.SetErrorStringWithFormat("'A' packet returned an error: %i.\n", arg_packet_err);
544 }
545
546 SetID (m_gdb_comm.GetCurrentProcessID (m_packet_timeout));
547 }
548 }
549
550 if (GetID() == LLDB_INVALID_PROCESS_ID)
551 {
552 KillDebugserverProcess ();
553 return error;
554 }
555
556 StringExtractorGDBRemote response;
557 if (m_gdb_comm.SendPacketAndWaitForResponse("?", 1, response, m_packet_timeout, false))
558 SetPrivateState (SetThreadStopInfo (response));
559
560 }
561 else
562 {
563 // Set our user ID to an invalid process ID.
564 SetID(LLDB_INVALID_PROCESS_ID);
565 error.SetErrorStringWithFormat("Failed to get object file from '%s' for arch %s.\n", module->GetFileSpec().GetFilename().AsCString(), module->GetArchitecture().AsCString());
566 }
Chris Lattner24943d22010-06-08 16:52:24 +0000567 return error;
Greg Clayton4b407112010-09-30 21:49:03 +0000568
Chris Lattner24943d22010-06-08 16:52:24 +0000569}
570
571
572Error
Greg Claytone71e2582011-02-04 01:58:07 +0000573ProcessGDBRemote::ConnectToDebugserver (const char *connect_url)
Chris Lattner24943d22010-06-08 16:52:24 +0000574{
575 Error error;
576 // Sleep and wait a bit for debugserver to start to listen...
577 std::auto_ptr<ConnectionFileDescriptor> conn_ap(new ConnectionFileDescriptor());
578 if (conn_ap.get())
579 {
Chris Lattner24943d22010-06-08 16:52:24 +0000580 const uint32_t max_retry_count = 50;
581 uint32_t retry_count = 0;
582 while (!m_gdb_comm.IsConnected())
583 {
Greg Claytone71e2582011-02-04 01:58:07 +0000584 if (conn_ap->Connect(connect_url, &error) == eConnectionStatusSuccess)
Chris Lattner24943d22010-06-08 16:52:24 +0000585 {
586 m_gdb_comm.SetConnection (conn_ap.release());
587 break;
588 }
589 retry_count++;
590
591 if (retry_count >= max_retry_count)
592 break;
593
594 usleep (100000);
595 }
596 }
597
598 if (!m_gdb_comm.IsConnected())
599 {
600 if (error.Success())
601 error.SetErrorString("not connected to remote gdb server");
602 return error;
603 }
604
Chris Lattner24943d22010-06-08 16:52:24 +0000605 if (m_gdb_comm.StartReadThread(&error))
606 {
607 // Send an initial ack
Greg Claytona4881d02011-01-22 07:12:45 +0000608 m_gdb_comm.SendAck();
Chris Lattner24943d22010-06-08 16:52:24 +0000609
610 if (m_debugserver_pid != LLDB_INVALID_PROCESS_ID)
Greg Clayton75ccf502010-08-21 02:22:51 +0000611 m_debugserver_thread = Host::StartMonitoringChildProcess (MonitorDebugserverProcess,
612 this,
613 m_debugserver_pid,
614 false);
615
Greg Claytonc1f45872011-02-12 06:28:37 +0000616 m_gdb_comm.ResetDiscoverableSettings();
617 m_gdb_comm.GetSendAcks ();
618 m_gdb_comm.GetThreadSuffixSupported ();
619 m_gdb_comm.GetHostInfo ();
620 m_gdb_comm.GetVContSupported ('c');
Chris Lattner24943d22010-06-08 16:52:24 +0000621 }
622 return error;
623}
624
625void
626ProcessGDBRemote::DidLaunchOrAttach ()
627{
Greg Clayton0bfda0b2011-02-05 02:25:06 +0000628 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS));
629 if (log)
630 log->Printf ("ProcessGDBRemote::DidLaunch()");
Chris Lattner24943d22010-06-08 16:52:24 +0000631 if (GetID() == LLDB_INVALID_PROCESS_ID)
632 {
633 m_dynamic_loader_ap.reset();
634 }
635 else
636 {
637 m_dispatch_queue_offsets_addr = LLDB_INVALID_ADDRESS;
638
Greg Clayton7e2f91c2011-01-29 07:10:55 +0000639 BuildDynamicRegisterInfo (false);
Greg Clayton20d338f2010-11-18 05:57:03 +0000640
641 m_byte_order = m_gdb_comm.GetByteOrder();
642
Chris Lattner24943d22010-06-08 16:52:24 +0000643 StreamString strm;
644
Greg Claytonfc7920f2011-02-09 03:09:55 +0000645 ;
Chris Lattner24943d22010-06-08 16:52:24 +0000646 // See if the GDB server supports the qHostInfo information
647 const char *vendor = m_gdb_comm.GetVendorString().AsCString();
648 const char *os_type = m_gdb_comm.GetOSString().AsCString();
Greg Claytonfc7920f2011-02-09 03:09:55 +0000649 ArchSpec target_arch (GetTarget().GetArchitecture());
650 ArchSpec gdb_remote_arch (m_gdb_comm.GetHostArchitecture());
651
Greg Claytonc62176d2011-02-09 03:12:09 +0000652 // If the remote host is ARM and we have apple as the vendor, then
Greg Claytonfc7920f2011-02-09 03:09:55 +0000653 // ARM executables and shared libraries can have mixed ARM architectures.
654 // You can have an armv6 executable, and if the host is armv7, then the
655 // system will load the best possible architecture for all shared libraries
656 // it has, so we really need to take the remote host architecture as our
657 // defacto architecture in this case.
658
659 if (gdb_remote_arch == ArchSpec ("arm") &&
660 vendor != NULL &&
661 strcmp(vendor, "apple") == 0)
662 {
663 GetTarget().SetArchitecture (gdb_remote_arch);
664 target_arch = gdb_remote_arch;
665 }
666
667 if (!target_arch.IsValid())
668 target_arch = gdb_remote_arch;
669
Greg Claytone71e2582011-02-04 01:58:07 +0000670 if (target_arch.IsValid())
Chris Lattner24943d22010-06-08 16:52:24 +0000671 {
Greg Claytonfc7920f2011-02-09 03:09:55 +0000672 if (vendor == NULL)
673 vendor = Host::GetVendorString().AsCString("apple");
674
675 if (os_type == NULL)
676 os_type = Host::GetOSString().AsCString("darwin");
677
678 strm.Printf ("%s-%s-%s", target_arch.AsCString(), vendor, os_type);
679
680 std::transform (strm.GetString().begin(),
681 strm.GetString().end(),
682 strm.GetString().begin(),
683 ::tolower);
684
685 m_target_triple.SetCString(strm.GetString().c_str());
Chris Lattner24943d22010-06-08 16:52:24 +0000686 }
Chris Lattner24943d22010-06-08 16:52:24 +0000687 }
688}
689
690void
691ProcessGDBRemote::DidLaunch ()
692{
693 DidLaunchOrAttach ();
694 if (m_dynamic_loader_ap.get())
695 m_dynamic_loader_ap->DidLaunch();
696}
697
698Error
Greg Clayton54e7afa2010-07-09 20:39:50 +0000699ProcessGDBRemote::DoAttachToProcessWithID (lldb::pid_t attach_pid)
Chris Lattner24943d22010-06-08 16:52:24 +0000700{
701 Error error;
702 // Clear out and clean up from any current state
703 Clear();
Jim Ingham7508e732010-08-09 23:31:02 +0000704 ArchSpec arch_spec = GetTarget().GetArchitecture();
Greg Clayton0bfda0b2011-02-05 02:25:06 +0000705
Chris Lattner24943d22010-06-08 16:52:24 +0000706 if (attach_pid != LLDB_INVALID_PROCESS_ID)
707 {
Chris Lattner24943d22010-06-08 16:52:24 +0000708 char host_port[128];
709 snprintf (host_port, sizeof(host_port), "localhost:%u", get_random_port ());
Greg Claytone71e2582011-02-04 01:58:07 +0000710 char connect_url[128];
711 snprintf (connect_url, sizeof(connect_url), "connect://%s", host_port);
712
Greg Clayton452bf612010-08-31 18:35:14 +0000713 error = StartDebugserverProcess (host_port, // debugserver_url
714 NULL, // inferior_argv
715 NULL, // inferior_envp
716 NULL, // stdin_path
Greg Claytonde915be2011-01-23 05:56:20 +0000717 NULL, // stdout_path
718 NULL, // stderr_path
719 NULL, // working_dir
Greg Clayton23cf0c72010-11-08 04:29:11 +0000720 false, // launch_process == false (we are attaching)
721 LLDB_INVALID_PROCESS_ID, // Don't send any attach to pid options to debugserver
722 NULL, // Don't send any attach by process name option to debugserver
723 false, // Don't send any attach wait_for_launch flag as an option to debugserver
Caroline Ticebd666012010-12-03 18:46:09 +0000724 0, // launch_flags
Jim Ingham7508e732010-08-09 23:31:02 +0000725 arch_spec);
Chris Lattner24943d22010-06-08 16:52:24 +0000726
727 if (error.Fail())
728 {
729 const char *error_string = error.AsCString();
730 if (error_string == NULL)
731 error_string = "unable to launch " DEBUGSERVER_BASENAME;
732
733 SetExitStatus (-1, error_string);
734 }
735 else
736 {
Greg Claytone71e2582011-02-04 01:58:07 +0000737 error = ConnectToDebugserver (connect_url);
Chris Lattner24943d22010-06-08 16:52:24 +0000738 if (error.Success())
739 {
740 char packet[64];
741 const int packet_len = ::snprintf (packet, sizeof(packet), "vAttach;%x", attach_pid);
Greg Clayton7e2f91c2011-01-29 07:10:55 +0000742
743 m_async_broadcaster.BroadcastEvent (eBroadcastBitAsyncContinue, new EventDataBytes (packet, packet_len));
Chris Lattner24943d22010-06-08 16:52:24 +0000744 }
745 }
746 }
Chris Lattner24943d22010-06-08 16:52:24 +0000747 return error;
748}
749
750size_t
751ProcessGDBRemote::AttachInputReaderCallback
752(
753 void *baton,
754 InputReader *reader,
755 lldb::InputReaderAction notification,
756 const char *bytes,
757 size_t bytes_len
758)
759{
760 if (notification == eInputReaderGotToken)
761 {
762 ProcessGDBRemote *gdb_process = (ProcessGDBRemote *)baton;
763 if (gdb_process->m_waiting_for_attach)
764 gdb_process->m_waiting_for_attach = false;
765 reader->SetIsDone(true);
766 return 1;
767 }
768 return 0;
769}
770
771Error
Greg Clayton54e7afa2010-07-09 20:39:50 +0000772ProcessGDBRemote::DoAttachToProcessWithName (const char *process_name, bool wait_for_launch)
Chris Lattner24943d22010-06-08 16:52:24 +0000773{
774 Error error;
775 // Clear out and clean up from any current state
776 Clear();
777 // HACK: require arch be set correctly at the target level until we can
778 // figure out a good way to determine the arch of what we are attaching to
Chris Lattner24943d22010-06-08 16:52:24 +0000779
Chris Lattner24943d22010-06-08 16:52:24 +0000780 if (process_name && process_name[0])
781 {
Jim Ingham7508e732010-08-09 23:31:02 +0000782 ArchSpec arch_spec = GetTarget().GetArchitecture();
Greg Claytone71e2582011-02-04 01:58:07 +0000783
784 char host_port[128];
Chris Lattner24943d22010-06-08 16:52:24 +0000785 snprintf (host_port, sizeof(host_port), "localhost:%u", get_random_port ());
Greg Claytone71e2582011-02-04 01:58:07 +0000786 char connect_url[128];
787 snprintf (connect_url, sizeof(connect_url), "connect://%s", host_port);
788
Greg Clayton452bf612010-08-31 18:35:14 +0000789 error = StartDebugserverProcess (host_port, // debugserver_url
790 NULL, // inferior_argv
791 NULL, // inferior_envp
792 NULL, // stdin_path
Greg Claytonde915be2011-01-23 05:56:20 +0000793 NULL, // stdout_path
794 NULL, // stderr_path
795 NULL, // working_dir
Greg Clayton23cf0c72010-11-08 04:29:11 +0000796 false, // launch_process == false (we are attaching)
797 LLDB_INVALID_PROCESS_ID, // Don't send any attach to pid options to debugserver
798 NULL, // Don't send any attach by process name option to debugserver
799 false, // Don't send any attach wait_for_launch flag as an option to debugserver
Caroline Ticebd666012010-12-03 18:46:09 +0000800 0, // launch_flags
Jim Ingham7508e732010-08-09 23:31:02 +0000801 arch_spec);
Chris Lattner24943d22010-06-08 16:52:24 +0000802 if (error.Fail())
803 {
804 const char *error_string = error.AsCString();
805 if (error_string == NULL)
806 error_string = "unable to launch " DEBUGSERVER_BASENAME;
807
808 SetExitStatus (-1, error_string);
809 }
810 else
811 {
Greg Claytone71e2582011-02-04 01:58:07 +0000812 error = ConnectToDebugserver (connect_url);
Chris Lattner24943d22010-06-08 16:52:24 +0000813 if (error.Success())
814 {
815 StreamString packet;
816
Chris Lattner24943d22010-06-08 16:52:24 +0000817 if (wait_for_launch)
Greg Claytonc1d37752010-10-18 01:45:30 +0000818 packet.PutCString("vAttachWait");
819 else
820 packet.PutCString("vAttachName");
Chris Lattner24943d22010-06-08 16:52:24 +0000821 packet.PutChar(';');
Greg Claytoncd548032011-02-01 01:31:41 +0000822 packet.PutBytesAsRawHex8(process_name, strlen(process_name), lldb::endian::InlHostByteOrder(), lldb::endian::InlHostByteOrder());
Greg Clayton7e2f91c2011-01-29 07:10:55 +0000823
824 m_async_broadcaster.BroadcastEvent (eBroadcastBitAsyncContinue, new EventDataBytes (packet.GetData(), packet.GetSize()));
Chris Lattner24943d22010-06-08 16:52:24 +0000825
Chris Lattner24943d22010-06-08 16:52:24 +0000826 }
827 }
828 }
Chris Lattner24943d22010-06-08 16:52:24 +0000829 return error;
830}
831
Chris Lattner24943d22010-06-08 16:52:24 +0000832
833void
834ProcessGDBRemote::DidAttach ()
835{
Greg Claytone71e2582011-02-04 01:58:07 +0000836 DidLaunchOrAttach ();
Chris Lattner24943d22010-06-08 16:52:24 +0000837 if (m_dynamic_loader_ap.get())
838 m_dynamic_loader_ap->DidAttach();
839}
840
841Error
842ProcessGDBRemote::WillResume ()
843{
Greg Claytonc1f45872011-02-12 06:28:37 +0000844 m_continue_c_tids.clear();
845 m_continue_C_tids.clear();
846 m_continue_s_tids.clear();
847 m_continue_S_tids.clear();
Chris Lattner24943d22010-06-08 16:52:24 +0000848 return Error();
849}
850
851Error
852ProcessGDBRemote::DoResume ()
853{
Jim Ingham3ae449a2010-11-17 02:32:00 +0000854 Error error;
Greg Clayton0bfda0b2011-02-05 02:25:06 +0000855 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS));
856 if (log)
857 log->Printf ("ProcessGDBRemote::Resume()");
Greg Claytonb749a262010-12-03 06:02:24 +0000858
859 Listener listener ("gdb-remote.resume-packet-sent");
860 if (listener.StartListeningForEvents (&m_gdb_comm, GDBRemoteCommunication::eBroadcastBitRunPacketSent))
861 {
Greg Claytonc1f45872011-02-12 06:28:37 +0000862 StreamString continue_packet;
863 bool continue_packet_error = false;
864 if (m_gdb_comm.HasAnyVContSupport ())
865 {
866 continue_packet.PutCString ("vCont");
867
868 if (!m_continue_c_tids.empty())
869 {
870 if (m_gdb_comm.GetVContSupported ('c'))
871 {
872 for (tid_collection::const_iterator t_pos = m_continue_c_tids.begin(), t_end = m_continue_c_tids.end(); t_pos != t_end; ++t_pos)
873 continue_packet.Printf(";c:%4.4x", *t_pos);
874 }
875 else
876 continue_packet_error = true;
877 }
878
879 if (!continue_packet_error && !m_continue_C_tids.empty())
880 {
881 if (m_gdb_comm.GetVContSupported ('C'))
882 {
883 for (tid_sig_collection::const_iterator s_pos = m_continue_C_tids.begin(), s_end = m_continue_C_tids.end(); s_pos != s_end; ++s_pos)
884 continue_packet.Printf(";C%2.2x:%4.4x", s_pos->second, s_pos->first);
885 }
886 else
887 continue_packet_error = true;
888 }
Greg Claytonb749a262010-12-03 06:02:24 +0000889
Greg Claytonc1f45872011-02-12 06:28:37 +0000890 if (!continue_packet_error && !m_continue_s_tids.empty())
891 {
892 if (m_gdb_comm.GetVContSupported ('s'))
893 {
894 for (tid_collection::const_iterator t_pos = m_continue_s_tids.begin(), t_end = m_continue_s_tids.end(); t_pos != t_end; ++t_pos)
895 continue_packet.Printf(";s:%4.4x", *t_pos);
896 }
897 else
898 continue_packet_error = true;
899 }
900
901 if (!continue_packet_error && !m_continue_S_tids.empty())
902 {
903 if (m_gdb_comm.GetVContSupported ('S'))
904 {
905 for (tid_sig_collection::const_iterator s_pos = m_continue_S_tids.begin(), s_end = m_continue_S_tids.end(); s_pos != s_end; ++s_pos)
906 continue_packet.Printf(";S%2.2x:%4.4x", s_pos->second, s_pos->first);
907 }
908 else
909 continue_packet_error = true;
910 }
911
912 if (continue_packet_error)
913 continue_packet.GetString().clear();
914 }
915 else
916 continue_packet_error = true;
917
918 if (continue_packet_error)
919 {
920 continue_packet_error = false;
921 // Either no vCont support, or we tried to use part of the vCont
922 // packet that wasn't supported by the remote GDB server.
923 // We need to try and make a simple packet that can do our continue
924 const size_t num_threads = GetThreadList().GetSize();
925 const size_t num_continue_c_tids = m_continue_c_tids.size();
926 const size_t num_continue_C_tids = m_continue_C_tids.size();
927 const size_t num_continue_s_tids = m_continue_s_tids.size();
928 const size_t num_continue_S_tids = m_continue_S_tids.size();
929 if (num_continue_c_tids > 0)
930 {
931 if (num_continue_c_tids == num_threads)
932 {
933 // All threads are resuming...
934 SetCurrentGDBRemoteThreadForRun (-1);
935 continue_packet.PutChar ('c');
936 }
937 else if (num_continue_c_tids == 1 &&
938 num_continue_C_tids == 0 &&
939 num_continue_s_tids == 0 &&
940 num_continue_S_tids == 0 )
941 {
942 // Only one thread is continuing
943 SetCurrentGDBRemoteThreadForRun (m_continue_c_tids.front());
944 continue_packet.PutChar ('c');
945 }
946 else
947 {
948 // We can't represent this continue packet....
949 continue_packet_error = true;
950 }
951 }
952
953 if (!continue_packet_error && num_continue_C_tids > 0)
954 {
955 if (num_continue_C_tids == num_threads)
956 {
957 const int continue_signo = m_continue_C_tids.front().second;
958 if (num_continue_C_tids > 1)
959 {
960 for (size_t i=1; i<num_threads; ++i)
961 {
962 if (m_continue_C_tids[i].second != continue_signo)
963 continue_packet_error = true;
964 }
965 }
966 if (!continue_packet_error)
967 {
968 // Add threads continuing with the same signo...
969 SetCurrentGDBRemoteThreadForRun (-1);
970 continue_packet.Printf("C%2.2x", continue_signo);
971 }
972 }
973 else if (num_continue_c_tids == 0 &&
974 num_continue_C_tids == 1 &&
975 num_continue_s_tids == 0 &&
976 num_continue_S_tids == 0 )
977 {
978 // Only one thread is continuing with signal
979 SetCurrentGDBRemoteThreadForRun (m_continue_C_tids.front().first);
980 continue_packet.Printf("C%2.2x", m_continue_C_tids.front().second);
981 }
982 else
983 {
984 // We can't represent this continue packet....
985 continue_packet_error = true;
986 }
987 }
988
989 if (!continue_packet_error && num_continue_s_tids > 0)
990 {
991 if (num_continue_s_tids == num_threads)
992 {
993 // All threads are resuming...
994 SetCurrentGDBRemoteThreadForRun (-1);
995 continue_packet.PutChar ('s');
996 }
997 else if (num_continue_c_tids == 0 &&
998 num_continue_C_tids == 0 &&
999 num_continue_s_tids == 1 &&
1000 num_continue_S_tids == 0 )
1001 {
1002 // Only one thread is stepping
1003 SetCurrentGDBRemoteThreadForRun (m_continue_s_tids.front());
1004 continue_packet.PutChar ('s');
1005 }
1006 else
1007 {
1008 // We can't represent this continue packet....
1009 continue_packet_error = true;
1010 }
1011 }
1012
1013 if (!continue_packet_error && num_continue_S_tids > 0)
1014 {
1015 if (num_continue_S_tids == num_threads)
1016 {
1017 const int step_signo = m_continue_S_tids.front().second;
1018 // Are all threads trying to step with the same signal?
1019 if (num_continue_S_tids > 1)
1020 {
1021 for (size_t i=1; i<num_threads; ++i)
1022 {
1023 if (m_continue_S_tids[i].second != step_signo)
1024 continue_packet_error = true;
1025 }
1026 }
1027 if (!continue_packet_error)
1028 {
1029 // Add threads stepping with the same signo...
1030 SetCurrentGDBRemoteThreadForRun (-1);
1031 continue_packet.Printf("S%2.2x", step_signo);
1032 }
1033 }
1034 else if (num_continue_c_tids == 0 &&
1035 num_continue_C_tids == 0 &&
1036 num_continue_s_tids == 0 &&
1037 num_continue_S_tids == 1 )
1038 {
1039 // Only one thread is stepping with signal
1040 SetCurrentGDBRemoteThreadForRun (m_continue_S_tids.front().first);
1041 continue_packet.Printf("S%2.2x", m_continue_S_tids.front().second);
1042 }
1043 else
1044 {
1045 // We can't represent this continue packet....
1046 continue_packet_error = true;
1047 }
1048 }
1049 }
1050
1051 if (continue_packet_error)
1052 {
1053 error.SetErrorString ("can't make continue packet for this resume");
1054 }
1055 else
1056 {
1057 EventSP event_sp;
1058 TimeValue timeout;
1059 timeout = TimeValue::Now();
1060 timeout.OffsetWithSeconds (5);
1061 m_async_broadcaster.BroadcastEvent (eBroadcastBitAsyncContinue, new EventDataBytes (continue_packet.GetData(), continue_packet.GetSize()));
1062
1063 if (listener.WaitForEvent (&timeout, event_sp) == false)
1064 error.SetErrorString("Resume timed out.");
1065 }
Greg Claytonb749a262010-12-03 06:02:24 +00001066 }
1067
Jim Ingham3ae449a2010-11-17 02:32:00 +00001068 return error;
Chris Lattner24943d22010-06-08 16:52:24 +00001069}
1070
1071size_t
1072ProcessGDBRemote::GetSoftwareBreakpointTrapOpcode (BreakpointSite* bp_site)
1073{
1074 const uint8_t *trap_opcode = NULL;
1075 uint32_t trap_opcode_size = 0;
1076
1077 static const uint8_t g_arm_breakpoint_opcode[] = { 0xFE, 0xDE, 0xFF, 0xE7 };
1078 //static const uint8_t g_thumb_breakpooint_opcode[] = { 0xFE, 0xDE };
1079 static const uint8_t g_ppc_breakpoint_opcode[] = { 0x7F, 0xC0, 0x00, 0x08 };
1080 static const uint8_t g_i386_breakpoint_opcode[] = { 0xCC };
1081
Jim Ingham7508e732010-08-09 23:31:02 +00001082 ArchSpec::CPU arch_cpu = GetTarget().GetArchitecture().GetGenericCPUType();
Greg Claytoncf015052010-06-11 03:25:34 +00001083 switch (arch_cpu)
Chris Lattner24943d22010-06-08 16:52:24 +00001084 {
Greg Claytoncf015052010-06-11 03:25:34 +00001085 case ArchSpec::eCPU_i386:
1086 case ArchSpec::eCPU_x86_64:
1087 trap_opcode = g_i386_breakpoint_opcode;
1088 trap_opcode_size = sizeof(g_i386_breakpoint_opcode);
1089 break;
1090
1091 case ArchSpec::eCPU_arm:
1092 // TODO: fill this in for ARM. We need to dig up the symbol for
1093 // the address in the breakpoint locaiton and figure out if it is
1094 // an ARM or Thumb breakpoint.
1095 trap_opcode = g_arm_breakpoint_opcode;
1096 trap_opcode_size = sizeof(g_arm_breakpoint_opcode);
1097 break;
1098
1099 case ArchSpec::eCPU_ppc:
1100 case ArchSpec::eCPU_ppc64:
1101 trap_opcode = g_ppc_breakpoint_opcode;
1102 trap_opcode_size = sizeof(g_ppc_breakpoint_opcode);
1103 break;
Chris Lattner24943d22010-06-08 16:52:24 +00001104
Greg Claytoncf015052010-06-11 03:25:34 +00001105 default:
1106 assert(!"Unhandled architecture in ProcessMacOSX::GetSoftwareBreakpointTrapOpcode()");
1107 break;
Chris Lattner24943d22010-06-08 16:52:24 +00001108 }
1109
1110 if (trap_opcode && trap_opcode_size)
1111 {
1112 if (bp_site->SetTrapOpcode(trap_opcode, trap_opcode_size))
1113 return trap_opcode_size;
1114 }
1115 return 0;
1116}
1117
1118uint32_t
1119ProcessGDBRemote::UpdateThreadListIfNeeded ()
1120{
1121 // locker will keep a mutex locked until it goes out of scope
Greg Claytone005f2c2010-11-06 01:53:30 +00001122 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_THREAD));
Greg Claytonf3d0b0c2010-10-27 03:32:59 +00001123 if (log && log->GetMask().Test(GDBR_LOG_VERBOSE))
Chris Lattner24943d22010-06-08 16:52:24 +00001124 log->Printf ("ProcessGDBRemote::%s (pid = %i)", __FUNCTION__, GetID());
1125
Greg Clayton5205f0b2010-09-03 17:10:42 +00001126 Mutex::Locker locker (m_thread_list.GetMutex ());
Chris Lattner24943d22010-06-08 16:52:24 +00001127 const uint32_t stop_id = GetStopID();
1128 if (m_thread_list.GetSize(false) == 0 || stop_id != m_thread_list.GetStopID())
1129 {
1130 // Update the thread list's stop id immediately so we don't recurse into this function.
1131 ThreadList curr_thread_list (this);
1132 curr_thread_list.SetStopID(stop_id);
1133
1134 Error err;
1135 StringExtractorGDBRemote response;
1136 for (m_gdb_comm.SendPacketAndWaitForResponse("qfThreadInfo", response, 1, false);
1137 response.IsNormalPacket();
1138 m_gdb_comm.SendPacketAndWaitForResponse("qsThreadInfo", response, 1, false))
1139 {
1140 char ch = response.GetChar();
1141 if (ch == 'l')
1142 break;
1143 if (ch == 'm')
1144 {
1145 do
1146 {
1147 tid_t tid = response.GetHexMaxU32(false, LLDB_INVALID_THREAD_ID);
1148
1149 if (tid != LLDB_INVALID_THREAD_ID)
1150 {
1151 ThreadSP thread_sp (GetThreadList().FindThreadByID (tid, false));
Greg Claytona875b642011-01-09 21:07:35 +00001152 if (!thread_sp)
Chris Lattner24943d22010-06-08 16:52:24 +00001153 thread_sp.reset (new ThreadGDBRemote (*this, tid));
1154 curr_thread_list.AddThread(thread_sp);
1155 }
1156
1157 ch = response.GetChar();
1158 } while (ch == ',');
1159 }
1160 }
1161
1162 m_thread_list = curr_thread_list;
1163
1164 SetThreadStopInfo (m_last_stop_packet);
1165 }
1166 return GetThreadList().GetSize(false);
1167}
1168
1169
1170StateType
1171ProcessGDBRemote::SetThreadStopInfo (StringExtractor& stop_packet)
1172{
1173 const char stop_type = stop_packet.GetChar();
1174 switch (stop_type)
1175 {
1176 case 'T':
1177 case 'S':
1178 {
1179 // Stop with signal and thread info
1180 const uint8_t signo = stop_packet.GetHexU8();
1181 std::string name;
1182 std::string value;
1183 std::string thread_name;
1184 uint32_t exc_type = 0;
Greg Clayton7661a982010-07-23 16:45:51 +00001185 std::vector<addr_t> exc_data;
Chris Lattner24943d22010-06-08 16:52:24 +00001186 uint32_t tid = LLDB_INVALID_THREAD_ID;
1187 addr_t thread_dispatch_qaddr = LLDB_INVALID_ADDRESS;
1188 uint32_t exc_data_count = 0;
Greg Claytona875b642011-01-09 21:07:35 +00001189 ThreadSP thread_sp;
1190
Chris Lattner24943d22010-06-08 16:52:24 +00001191 while (stop_packet.GetNameColonValue(name, value))
1192 {
1193 if (name.compare("metype") == 0)
1194 {
1195 // exception type in big endian hex
1196 exc_type = Args::StringToUInt32 (value.c_str(), 0, 16);
1197 }
1198 else if (name.compare("mecount") == 0)
1199 {
1200 // exception count in big endian hex
1201 exc_data_count = Args::StringToUInt32 (value.c_str(), 0, 16);
1202 }
1203 else if (name.compare("medata") == 0)
1204 {
1205 // exception data in big endian hex
1206 exc_data.push_back(Args::StringToUInt64 (value.c_str(), 0, 16));
1207 }
1208 else if (name.compare("thread") == 0)
1209 {
1210 // thread in big endian hex
1211 tid = Args::StringToUInt32 (value.c_str(), 0, 16);
Greg Claytona875b642011-01-09 21:07:35 +00001212 thread_sp = m_thread_list.FindThreadByID(tid, false);
Chris Lattner24943d22010-06-08 16:52:24 +00001213 }
Greg Clayton4862fa22011-01-08 03:17:57 +00001214 else if (name.compare("hexname") == 0)
1215 {
1216 StringExtractor name_extractor;
1217 // Swap "value" over into "name_extractor"
1218 name_extractor.GetStringRef().swap(value);
1219 // Now convert the HEX bytes into a string value
1220 name_extractor.GetHexByteString (value);
1221 thread_name.swap (value);
1222 }
Chris Lattner24943d22010-06-08 16:52:24 +00001223 else if (name.compare("name") == 0)
1224 {
1225 thread_name.swap (value);
1226 }
Greg Clayton0a7f75f2010-09-09 06:32:46 +00001227 else if (name.compare("qaddr") == 0)
Chris Lattner24943d22010-06-08 16:52:24 +00001228 {
1229 thread_dispatch_qaddr = Args::StringToUInt64 (value.c_str(), 0, 16);
1230 }
Greg Claytona875b642011-01-09 21:07:35 +00001231 else if (name.size() == 2 && ::isxdigit(name[0]) && ::isxdigit(name[1]))
1232 {
1233 // We have a register number that contains an expedited
1234 // register value. Lets supply this register to our thread
1235 // so it won't have to go and read it.
1236 if (thread_sp)
1237 {
1238 uint32_t reg = Args::StringToUInt32 (name.c_str(), UINT32_MAX, 16);
1239
1240 if (reg != UINT32_MAX)
1241 {
1242 StringExtractor reg_value_extractor;
1243 // Swap "value" over into "reg_value_extractor"
1244 reg_value_extractor.GetStringRef().swap(value);
1245 static_cast<ThreadGDBRemote *> (thread_sp.get())->PrivateSetRegisterValue (reg, reg_value_extractor);
1246 }
1247 }
1248 }
Chris Lattner24943d22010-06-08 16:52:24 +00001249 }
Chris Lattner24943d22010-06-08 16:52:24 +00001250
1251 if (thread_sp)
1252 {
1253 ThreadGDBRemote *gdb_thread = static_cast<ThreadGDBRemote *> (thread_sp.get());
1254
1255 gdb_thread->SetThreadDispatchQAddr (thread_dispatch_qaddr);
Jim Ingham9082c8a2011-01-28 02:23:12 +00001256 gdb_thread->SetName (thread_name.empty() ? NULL : thread_name.c_str());
Chris Lattner24943d22010-06-08 16:52:24 +00001257 if (exc_type != 0)
1258 {
Greg Claytonbdcb6ab2011-01-25 23:55:37 +00001259 const size_t exc_data_size = exc_data.size();
Greg Clayton643ee732010-08-04 01:40:35 +00001260
1261 gdb_thread->SetStopInfo (StopInfoMachException::CreateStopReasonWithMachException (*thread_sp,
1262 exc_type,
Greg Claytonbdcb6ab2011-01-25 23:55:37 +00001263 exc_data_size,
1264 exc_data_size >= 1 ? exc_data[0] : 0,
1265 exc_data_size >= 2 ? exc_data[1] : 0));
Chris Lattner24943d22010-06-08 16:52:24 +00001266 }
1267 else if (signo)
1268 {
Greg Clayton643ee732010-08-04 01:40:35 +00001269 gdb_thread->SetStopInfo (StopInfo::CreateStopReasonWithSignal (*thread_sp, signo));
Chris Lattner24943d22010-06-08 16:52:24 +00001270 }
1271 else
1272 {
Greg Clayton643ee732010-08-04 01:40:35 +00001273 StopInfoSP invalid_stop_info_sp;
1274 gdb_thread->SetStopInfo (invalid_stop_info_sp);
Chris Lattner24943d22010-06-08 16:52:24 +00001275 }
1276 }
1277 return eStateStopped;
1278 }
1279 break;
1280
1281 case 'W':
1282 // process exited
1283 return eStateExited;
1284
1285 default:
1286 break;
1287 }
1288 return eStateInvalid;
1289}
1290
1291void
1292ProcessGDBRemote::RefreshStateAfterStop ()
1293{
Jim Ingham7508e732010-08-09 23:31:02 +00001294 // FIXME - add a variable to tell that we're in the middle of attaching if we
1295 // need to know that.
Chris Lattner24943d22010-06-08 16:52:24 +00001296 // We must be attaching if we don't already have a valid architecture
Jim Ingham7508e732010-08-09 23:31:02 +00001297// if (!GetTarget().GetArchitecture().IsValid())
1298// {
1299// Module *exe_module = GetTarget().GetExecutableModule().get();
1300// if (exe_module)
1301// m_arch_spec = exe_module->GetArchitecture();
1302// }
1303
Chris Lattner24943d22010-06-08 16:52:24 +00001304 // Let all threads recover from stopping and do any clean up based
1305 // on the previous thread state (if any).
1306 m_thread_list.RefreshStateAfterStop();
1307
1308 // Discover new threads:
1309 UpdateThreadListIfNeeded ();
1310}
1311
1312Error
Jim Ingham3ae449a2010-11-17 02:32:00 +00001313ProcessGDBRemote::DoHalt (bool &caused_stop)
Chris Lattner24943d22010-06-08 16:52:24 +00001314{
1315 Error error;
Jim Ingham3ae449a2010-11-17 02:32:00 +00001316
Greg Claytona4881d02011-01-22 07:12:45 +00001317 bool timed_out = false;
1318 Mutex::Locker locker;
Greg Clayton7e2f91c2011-01-29 07:10:55 +00001319
1320 if (m_public_state.GetValue() == eStateAttaching)
Greg Clayton20d338f2010-11-18 05:57:03 +00001321 {
Greg Clayton7e2f91c2011-01-29 07:10:55 +00001322 // We are being asked to halt during an attach. We need to just close
1323 // our file handle and debugserver will go away, and we can be done...
1324 m_gdb_comm.Disconnect();
Greg Clayton20d338f2010-11-18 05:57:03 +00001325 }
Greg Clayton7e2f91c2011-01-29 07:10:55 +00001326 else
1327 {
1328 if (!m_gdb_comm.SendInterrupt (locker, 2, caused_stop, timed_out))
1329 {
1330 if (timed_out)
1331 error.SetErrorString("timed out sending interrupt packet");
1332 else
1333 error.SetErrorString("unknown error sending interrupt packet");
1334 }
1335 }
Chris Lattner24943d22010-06-08 16:52:24 +00001336 return error;
1337}
1338
1339Error
Greg Clayton72e1c782011-01-22 23:43:18 +00001340ProcessGDBRemote::InterruptIfRunning
1341(
1342 bool discard_thread_plans,
1343 bool catch_stop_event,
Greg Clayton72e1c782011-01-22 23:43:18 +00001344 EventSP &stop_event_sp
1345)
Chris Lattner24943d22010-06-08 16:52:24 +00001346{
1347 Error error;
Chris Lattner24943d22010-06-08 16:52:24 +00001348
Greg Clayton2860ba92011-01-23 19:58:49 +00001349 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_PROCESS));
1350
Greg Clayton68ca8232011-01-25 02:58:48 +00001351 bool paused_private_state_thread = false;
Greg Clayton2860ba92011-01-23 19:58:49 +00001352 const bool is_running = m_gdb_comm.IsRunning();
1353 if (log)
Greg Clayton68ca8232011-01-25 02:58:48 +00001354 log->Printf ("ProcessGDBRemote::InterruptIfRunning(discard_thread_plans=%i, catch_stop_event=%i) is_running=%i",
Greg Clayton2860ba92011-01-23 19:58:49 +00001355 discard_thread_plans,
Greg Clayton68ca8232011-01-25 02:58:48 +00001356 catch_stop_event,
Greg Clayton2860ba92011-01-23 19:58:49 +00001357 is_running);
1358
Greg Clayton2860ba92011-01-23 19:58:49 +00001359 if (discard_thread_plans)
1360 {
1361 if (log)
1362 log->Printf ("ProcessGDBRemote::InterruptIfRunning() discarding all thread plans");
1363 m_thread_list.DiscardThreadPlans();
1364 }
1365 if (is_running)
Greg Clayton4fb400f2010-09-27 21:07:38 +00001366 {
Greg Clayton68ca8232011-01-25 02:58:48 +00001367 if (catch_stop_event)
1368 {
1369 if (log)
1370 log->Printf ("ProcessGDBRemote::InterruptIfRunning() pausing private state thread");
1371 PausePrivateStateThread();
1372 paused_private_state_thread = true;
1373 }
1374
Greg Clayton4fb400f2010-09-27 21:07:38 +00001375 bool timed_out = false;
Greg Claytona4881d02011-01-22 07:12:45 +00001376 bool sent_interrupt = false;
Greg Clayton4fb400f2010-09-27 21:07:38 +00001377 Mutex::Locker locker;
Greg Clayton72e1c782011-01-22 23:43:18 +00001378
Greg Clayton72e1c782011-01-22 23:43:18 +00001379 //m_debugserver_pid = LLDB_INVALID_PROCESS_ID;
1380 if (!m_gdb_comm.SendInterrupt (locker, 1, sent_interrupt, timed_out))
Greg Clayton4fb400f2010-09-27 21:07:38 +00001381 {
1382 if (timed_out)
1383 error.SetErrorString("timed out sending interrupt packet");
1384 else
1385 error.SetErrorString("unknown error sending interrupt packet");
Greg Clayton68ca8232011-01-25 02:58:48 +00001386 if (paused_private_state_thread)
Greg Clayton72e1c782011-01-22 23:43:18 +00001387 ResumePrivateStateThread();
1388 return error;
Greg Clayton4fb400f2010-09-27 21:07:38 +00001389 }
Greg Clayton72e1c782011-01-22 23:43:18 +00001390
Greg Clayton72e1c782011-01-22 23:43:18 +00001391 if (catch_stop_event)
1392 {
Greg Clayton68ca8232011-01-25 02:58:48 +00001393 // LISTEN HERE
Greg Clayton72e1c782011-01-22 23:43:18 +00001394 TimeValue timeout_time;
1395 timeout_time = TimeValue::Now();
Greg Clayton68ca8232011-01-25 02:58:48 +00001396 timeout_time.OffsetWithSeconds(5);
1397 StateType state = WaitForStateChangedEventsPrivate (&timeout_time, stop_event_sp);
Greg Clayton2860ba92011-01-23 19:58:49 +00001398
Greg Claytonbdcb6ab2011-01-25 23:55:37 +00001399 timed_out = state == eStateInvalid;
Greg Clayton2860ba92011-01-23 19:58:49 +00001400 if (log)
1401 log->Printf ("ProcessGDBRemote::InterruptIfRunning() catch stop event: state = %s, timed-out=%i", StateAsCString(state), timed_out);
Greg Clayton3b2c41c2010-10-18 04:14:23 +00001402
Greg Clayton2860ba92011-01-23 19:58:49 +00001403 if (timed_out)
Greg Clayton72e1c782011-01-22 23:43:18 +00001404 error.SetErrorString("unable to verify target stopped");
1405 }
1406
Greg Clayton68ca8232011-01-25 02:58:48 +00001407 if (paused_private_state_thread)
Greg Clayton2860ba92011-01-23 19:58:49 +00001408 {
1409 if (log)
1410 log->Printf ("ProcessGDBRemote::InterruptIfRunning() resuming private state thread");
Greg Clayton72e1c782011-01-22 23:43:18 +00001411 ResumePrivateStateThread();
Greg Clayton2860ba92011-01-23 19:58:49 +00001412 }
Greg Clayton4fb400f2010-09-27 21:07:38 +00001413 }
Chris Lattner24943d22010-06-08 16:52:24 +00001414 return error;
1415}
1416
Greg Clayton4fb400f2010-09-27 21:07:38 +00001417Error
Greg Clayton72e1c782011-01-22 23:43:18 +00001418ProcessGDBRemote::WillDetach ()
1419{
Greg Clayton2860ba92011-01-23 19:58:49 +00001420 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_PROCESS));
1421 if (log)
1422 log->Printf ("ProcessGDBRemote::WillDetach()");
1423
Greg Clayton72e1c782011-01-22 23:43:18 +00001424 bool discard_thread_plans = true;
1425 bool catch_stop_event = true;
Greg Clayton72e1c782011-01-22 23:43:18 +00001426 EventSP event_sp;
Greg Clayton68ca8232011-01-25 02:58:48 +00001427 return InterruptIfRunning (discard_thread_plans, catch_stop_event, event_sp);
Greg Clayton72e1c782011-01-22 23:43:18 +00001428}
1429
1430Error
Greg Clayton4fb400f2010-09-27 21:07:38 +00001431ProcessGDBRemote::DoDetach()
1432{
1433 Error error;
Greg Claytone005f2c2010-11-06 01:53:30 +00001434 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_PROCESS));
Greg Clayton4fb400f2010-09-27 21:07:38 +00001435 if (log)
1436 log->Printf ("ProcessGDBRemote::DoDetach()");
1437
1438 DisableAllBreakpointSites ();
1439
Greg Clayton3b2c41c2010-10-18 04:14:23 +00001440 m_thread_list.DiscardThreadPlans();
Greg Clayton4fb400f2010-09-27 21:07:38 +00001441
Greg Clayton3b2c41c2010-10-18 04:14:23 +00001442 size_t response_size = m_gdb_comm.SendPacket ("D", 1);
1443 if (log)
Greg Clayton4fb400f2010-09-27 21:07:38 +00001444 {
Greg Clayton3b2c41c2010-10-18 04:14:23 +00001445 if (response_size)
1446 log->PutCString ("ProcessGDBRemote::DoDetach() detach packet sent successfully");
1447 else
1448 log->PutCString ("ProcessGDBRemote::DoDetach() detach packet send failed");
Greg Clayton4fb400f2010-09-27 21:07:38 +00001449 }
Greg Clayton3b2c41c2010-10-18 04:14:23 +00001450 // Sleep for one second to let the process get all detached...
Greg Clayton4fb400f2010-09-27 21:07:38 +00001451 StopAsyncThread ();
Greg Clayton3b2c41c2010-10-18 04:14:23 +00001452
Greg Clayton4fb400f2010-09-27 21:07:38 +00001453 m_gdb_comm.StopReadThread();
Greg Clayton4fb400f2010-09-27 21:07:38 +00001454 m_gdb_comm.Disconnect(); // Disconnect from the debug server.
Greg Clayton3b2c41c2010-10-18 04:14:23 +00001455
1456 SetPrivateState (eStateDetached);
1457 ResumePrivateStateThread();
1458
1459 //KillDebugserverProcess ();
Greg Clayton4fb400f2010-09-27 21:07:38 +00001460 return error;
1461}
Chris Lattner24943d22010-06-08 16:52:24 +00001462
1463Error
1464ProcessGDBRemote::DoDestroy ()
1465{
1466 Error error;
Greg Claytone005f2c2010-11-06 01:53:30 +00001467 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_PROCESS));
Chris Lattner24943d22010-06-08 16:52:24 +00001468 if (log)
1469 log->Printf ("ProcessGDBRemote::DoDestroy()");
1470
1471 // Interrupt if our inferior is running...
Greg Claytona4881d02011-01-22 07:12:45 +00001472 if (m_gdb_comm.IsConnected())
Chris Lattner24943d22010-06-08 16:52:24 +00001473 {
Greg Clayton7e2f91c2011-01-29 07:10:55 +00001474 if (m_public_state.GetValue() == eStateAttaching)
Greg Clayton27a8dd72011-01-25 04:57:42 +00001475 {
Greg Clayton7e2f91c2011-01-29 07:10:55 +00001476 // We are being asked to halt during an attach. We need to just close
1477 // our file handle and debugserver will go away, and we can be done...
1478 m_gdb_comm.Disconnect();
Greg Clayton27a8dd72011-01-25 04:57:42 +00001479 }
1480 else
Greg Clayton72e1c782011-01-22 23:43:18 +00001481 {
Greg Clayton7e2f91c2011-01-29 07:10:55 +00001482
1483 StringExtractorGDBRemote response;
1484 bool send_async = true;
1485 if (m_gdb_comm.SendPacketAndWaitForResponse("k", 1, response, 2, send_async))
1486 {
1487 char packet_cmd = response.GetChar(0);
1488
1489 if (packet_cmd == 'W' || packet_cmd == 'X')
1490 {
1491 m_last_stop_packet = response;
1492 SetExitStatus(response.GetHexU8(), NULL);
1493 }
1494 }
1495 else
1496 {
1497 SetExitStatus(SIGABRT, NULL);
1498 //error.SetErrorString("kill packet failed");
1499 }
Greg Clayton72e1c782011-01-22 23:43:18 +00001500 }
1501 }
Chris Lattner24943d22010-06-08 16:52:24 +00001502 StopAsyncThread ();
1503 m_gdb_comm.StopReadThread();
1504 KillDebugserverProcess ();
Johnny Chenc5b15db2010-09-03 22:35:47 +00001505 m_gdb_comm.Disconnect(); // Disconnect from the debug server.
Chris Lattner24943d22010-06-08 16:52:24 +00001506 return error;
1507}
1508
Chris Lattner24943d22010-06-08 16:52:24 +00001509//------------------------------------------------------------------
1510// Process Queries
1511//------------------------------------------------------------------
1512
1513bool
1514ProcessGDBRemote::IsAlive ()
1515{
Greg Clayton58e844b2010-12-08 05:08:21 +00001516 return m_gdb_comm.IsConnected() && m_private_state.GetValue() != eStateExited;
Chris Lattner24943d22010-06-08 16:52:24 +00001517}
1518
1519addr_t
1520ProcessGDBRemote::GetImageInfoAddress()
1521{
1522 if (!m_gdb_comm.IsRunning())
1523 {
1524 StringExtractorGDBRemote response;
1525 if (m_gdb_comm.SendPacketAndWaitForResponse("qShlibInfoAddr", ::strlen ("qShlibInfoAddr"), response, 2, false))
1526 {
1527 if (response.IsNormalPacket())
1528 return response.GetHexMaxU64(false, LLDB_INVALID_ADDRESS);
1529 }
1530 }
1531 return LLDB_INVALID_ADDRESS;
1532}
1533
1534DynamicLoader *
1535ProcessGDBRemote::GetDynamicLoader()
1536{
1537 return m_dynamic_loader_ap.get();
1538}
1539
1540//------------------------------------------------------------------
1541// Process Memory
1542//------------------------------------------------------------------
1543size_t
1544ProcessGDBRemote::DoReadMemory (addr_t addr, void *buf, size_t size, Error &error)
1545{
1546 if (size > m_max_memory_size)
1547 {
1548 // Keep memory read sizes down to a sane limit. This function will be
1549 // called multiple times in order to complete the task by
1550 // lldb_private::Process so it is ok to do this.
1551 size = m_max_memory_size;
1552 }
1553
1554 char packet[64];
1555 const int packet_len = ::snprintf (packet, sizeof(packet), "m%llx,%zx", (uint64_t)addr, size);
1556 assert (packet_len + 1 < sizeof(packet));
1557 StringExtractorGDBRemote response;
1558 if (m_gdb_comm.SendPacketAndWaitForResponse(packet, packet_len, response, 2, true))
1559 {
1560 if (response.IsNormalPacket())
1561 {
1562 error.Clear();
1563 return response.GetHexBytes(buf, size, '\xdd');
1564 }
1565 else if (response.IsErrorPacket())
1566 error.SetErrorStringWithFormat("gdb remote returned an error: %s", response.GetStringRef().c_str());
1567 else if (response.IsUnsupportedPacket())
1568 error.SetErrorStringWithFormat("'%s' packet unsupported", packet);
1569 else
1570 error.SetErrorStringWithFormat("unexpected response to '%s': '%s'", packet, response.GetStringRef().c_str());
1571 }
1572 else
1573 {
1574 error.SetErrorStringWithFormat("failed to sent packet: '%s'", packet);
1575 }
1576 return 0;
1577}
1578
1579size_t
1580ProcessGDBRemote::DoWriteMemory (addr_t addr, const void *buf, size_t size, Error &error)
1581{
1582 StreamString packet;
1583 packet.Printf("M%llx,%zx:", addr, size);
Greg Claytoncd548032011-02-01 01:31:41 +00001584 packet.PutBytesAsRawHex8(buf, size, lldb::endian::InlHostByteOrder(), lldb::endian::InlHostByteOrder());
Chris Lattner24943d22010-06-08 16:52:24 +00001585 StringExtractorGDBRemote response;
1586 if (m_gdb_comm.SendPacketAndWaitForResponse(packet.GetData(), packet.GetSize(), response, 2, true))
1587 {
1588 if (response.IsOKPacket())
1589 {
1590 error.Clear();
1591 return size;
1592 }
1593 else if (response.IsErrorPacket())
1594 error.SetErrorStringWithFormat("gdb remote returned an error: %s", response.GetStringRef().c_str());
1595 else if (response.IsUnsupportedPacket())
1596 error.SetErrorStringWithFormat("'%s' packet unsupported", packet.GetString().c_str());
1597 else
1598 error.SetErrorStringWithFormat("unexpected response to '%s': '%s'", packet.GetString().c_str(), response.GetStringRef().c_str());
1599 }
1600 else
1601 {
1602 error.SetErrorStringWithFormat("failed to sent packet: '%s'", packet.GetString().c_str());
1603 }
1604 return 0;
1605}
1606
1607lldb::addr_t
1608ProcessGDBRemote::DoAllocateMemory (size_t size, uint32_t permissions, Error &error)
1609{
1610 addr_t allocated_addr = m_gdb_comm.AllocateMemory (size, permissions, m_packet_timeout);
1611 if (allocated_addr == LLDB_INVALID_ADDRESS)
1612 error.SetErrorStringWithFormat("unable to allocate %zu bytes of memory with permissions %u", size, permissions);
1613 else
1614 error.Clear();
1615 return allocated_addr;
1616}
1617
1618Error
1619ProcessGDBRemote::DoDeallocateMemory (lldb::addr_t addr)
1620{
1621 Error error;
1622 if (!m_gdb_comm.DeallocateMemory (addr, m_packet_timeout))
1623 error.SetErrorStringWithFormat("unable to deallocate memory at 0x%llx", addr);
1624 return error;
1625}
1626
1627
1628//------------------------------------------------------------------
1629// Process STDIO
1630//------------------------------------------------------------------
1631
1632size_t
1633ProcessGDBRemote::GetSTDOUT (char *buf, size_t buf_size, Error &error)
1634{
1635 Mutex::Locker locker(m_stdio_mutex);
1636 size_t bytes_available = m_stdout_data.size();
1637 if (bytes_available > 0)
1638 {
Greg Clayton0bfda0b2011-02-05 02:25:06 +00001639 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS));
1640 if (log)
1641 log->Printf ("ProcessGDBRemote::%s (&%p[%u]) ...", __FUNCTION__, buf, buf_size);
Chris Lattner24943d22010-06-08 16:52:24 +00001642 if (bytes_available > buf_size)
1643 {
Greg Clayton53d68e72010-07-20 22:52:08 +00001644 memcpy(buf, m_stdout_data.c_str(), buf_size);
Chris Lattner24943d22010-06-08 16:52:24 +00001645 m_stdout_data.erase(0, buf_size);
1646 bytes_available = buf_size;
1647 }
1648 else
1649 {
Greg Clayton53d68e72010-07-20 22:52:08 +00001650 memcpy(buf, m_stdout_data.c_str(), bytes_available);
Chris Lattner24943d22010-06-08 16:52:24 +00001651 m_stdout_data.clear();
1652
1653 //ResetEventBits(eBroadcastBitSTDOUT);
1654 }
1655 }
1656 return bytes_available;
1657}
1658
1659size_t
1660ProcessGDBRemote::GetSTDERR (char *buf, size_t buf_size, Error &error)
1661{
1662 // Can we get STDERR through the remote protocol?
1663 return 0;
1664}
1665
1666size_t
1667ProcessGDBRemote::PutSTDIN (const char *src, size_t src_len, Error &error)
1668{
1669 if (m_stdio_communication.IsConnected())
1670 {
1671 ConnectionStatus status;
1672 m_stdio_communication.Write(src, src_len, status, NULL);
1673 }
1674 return 0;
1675}
1676
1677Error
1678ProcessGDBRemote::EnableBreakpoint (BreakpointSite *bp_site)
1679{
1680 Error error;
1681 assert (bp_site != NULL);
1682
Greg Claytone005f2c2010-11-06 01:53:30 +00001683 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_BREAKPOINTS));
Chris Lattner24943d22010-06-08 16:52:24 +00001684 user_id_t site_id = bp_site->GetID();
1685 const addr_t addr = bp_site->GetLoadAddress();
1686 if (log)
1687 log->Printf ("ProcessGDBRemote::EnableBreakpoint (size_id = %d) address = 0x%llx", site_id, (uint64_t)addr);
1688
1689 if (bp_site->IsEnabled())
1690 {
1691 if (log)
1692 log->Printf ("ProcessGDBRemote::EnableBreakpoint (size_id = %d) address = 0x%llx -- SUCCESS (already enabled)", site_id, (uint64_t)addr);
1693 return error;
1694 }
1695 else
1696 {
1697 const size_t bp_op_size = GetSoftwareBreakpointTrapOpcode (bp_site);
1698
1699 if (bp_site->HardwarePreferred())
1700 {
1701 // Try and set hardware breakpoint, and if that fails, fall through
1702 // and set a software breakpoint?
1703 }
1704
1705 if (m_z0_supported)
1706 {
1707 char packet[64];
1708 const int packet_len = ::snprintf (packet, sizeof(packet), "Z0,%llx,%zx", addr, bp_op_size);
1709 assert (packet_len + 1 < sizeof(packet));
1710 StringExtractorGDBRemote response;
1711 if (m_gdb_comm.SendPacketAndWaitForResponse(packet, packet_len, response, 2, true))
1712 {
1713 if (response.IsUnsupportedPacket())
1714 {
1715 // Disable z packet support and try again
1716 m_z0_supported = 0;
1717 return EnableBreakpoint (bp_site);
1718 }
1719 else if (response.IsOKPacket())
1720 {
1721 bp_site->SetEnabled(true);
1722 bp_site->SetType (BreakpointSite::eExternal);
1723 return error;
1724 }
1725 else
1726 {
1727 uint8_t error_byte = response.GetError();
1728 if (error_byte)
1729 error.SetErrorStringWithFormat("%x packet failed with error: %i (0x%2.2x).\n", packet, error_byte, error_byte);
1730 }
1731 }
1732 }
1733 else
1734 {
1735 return EnableSoftwareBreakpoint (bp_site);
1736 }
1737 }
1738
1739 if (log)
1740 {
1741 const char *err_string = error.AsCString();
1742 log->Printf ("ProcessGDBRemote::EnableBreakpoint() error for breakpoint at 0x%8.8llx: %s",
1743 bp_site->GetLoadAddress(),
1744 err_string ? err_string : "NULL");
1745 }
1746 // We shouldn't reach here on a successful breakpoint enable...
1747 if (error.Success())
1748 error.SetErrorToGenericError();
1749 return error;
1750}
1751
1752Error
1753ProcessGDBRemote::DisableBreakpoint (BreakpointSite *bp_site)
1754{
1755 Error error;
1756 assert (bp_site != NULL);
1757 addr_t addr = bp_site->GetLoadAddress();
1758 user_id_t site_id = bp_site->GetID();
Greg Claytone005f2c2010-11-06 01:53:30 +00001759 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_BREAKPOINTS));
Chris Lattner24943d22010-06-08 16:52:24 +00001760 if (log)
1761 log->Printf ("ProcessGDBRemote::DisableBreakpoint (site_id = %d) addr = 0x%8.8llx", site_id, (uint64_t)addr);
1762
1763 if (bp_site->IsEnabled())
1764 {
1765 const size_t bp_op_size = GetSoftwareBreakpointTrapOpcode (bp_site);
1766
1767 if (bp_site->IsHardware())
1768 {
1769 // TODO: disable hardware breakpoint...
1770 }
1771 else
1772 {
1773 if (m_z0_supported)
1774 {
1775 char packet[64];
1776 const int packet_len = ::snprintf (packet, sizeof(packet), "z0,%llx,%zx", addr, bp_op_size);
1777 assert (packet_len + 1 < sizeof(packet));
1778 StringExtractorGDBRemote response;
1779 if (m_gdb_comm.SendPacketAndWaitForResponse(packet, packet_len, response, 2, true))
1780 {
1781 if (response.IsUnsupportedPacket())
1782 {
1783 error.SetErrorString("Breakpoint site was set with Z packet, yet remote debugserver states z packets are not supported.");
1784 }
1785 else if (response.IsOKPacket())
1786 {
1787 if (log)
1788 log->Printf ("ProcessGDBRemote::DisableBreakpoint (site_id = %d) addr = 0x%8.8llx -- SUCCESS", site_id, (uint64_t)addr);
1789 bp_site->SetEnabled(false);
1790 return error;
1791 }
1792 else
1793 {
1794 uint8_t error_byte = response.GetError();
1795 if (error_byte)
1796 error.SetErrorStringWithFormat("%x packet failed with error: %i (0x%2.2x).\n", packet, error_byte, error_byte);
1797 }
1798 }
1799 }
1800 else
1801 {
1802 return DisableSoftwareBreakpoint (bp_site);
1803 }
1804 }
1805 }
1806 else
1807 {
1808 if (log)
1809 log->Printf ("ProcessGDBRemote::DisableBreakpoint (site_id = %d) addr = 0x%8.8llx -- SUCCESS (already disabled)", site_id, (uint64_t)addr);
1810 return error;
1811 }
1812
1813 if (error.Success())
1814 error.SetErrorToGenericError();
1815 return error;
1816}
1817
1818Error
1819ProcessGDBRemote::EnableWatchpoint (WatchpointLocation *wp)
1820{
1821 Error error;
1822 if (wp)
1823 {
1824 user_id_t watchID = wp->GetID();
1825 addr_t addr = wp->GetLoadAddress();
Greg Claytone005f2c2010-11-06 01:53:30 +00001826 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_WATCHPOINTS));
Chris Lattner24943d22010-06-08 16:52:24 +00001827 if (log)
1828 log->Printf ("ProcessGDBRemote::EnableWatchpoint(watchID = %d)", watchID);
1829 if (wp->IsEnabled())
1830 {
1831 if (log)
1832 log->Printf("ProcessGDBRemote::EnableWatchpoint(watchID = %d) addr = 0x%8.8llx: watchpoint already enabled.", watchID, (uint64_t)addr);
1833 return error;
1834 }
1835 else
1836 {
1837 // Pass down an appropriate z/Z packet...
1838 error.SetErrorString("watchpoints not supported");
1839 }
1840 }
1841 else
1842 {
1843 error.SetErrorString("Watchpoint location argument was NULL.");
1844 }
1845 if (error.Success())
1846 error.SetErrorToGenericError();
1847 return error;
1848}
1849
1850Error
1851ProcessGDBRemote::DisableWatchpoint (WatchpointLocation *wp)
1852{
1853 Error error;
1854 if (wp)
1855 {
1856 user_id_t watchID = wp->GetID();
1857
Greg Claytone005f2c2010-11-06 01:53:30 +00001858 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_WATCHPOINTS));
Chris Lattner24943d22010-06-08 16:52:24 +00001859
1860 addr_t addr = wp->GetLoadAddress();
1861 if (log)
1862 log->Printf ("ProcessGDBRemote::DisableWatchpoint (watchID = %d) addr = 0x%8.8llx", watchID, (uint64_t)addr);
1863
1864 if (wp->IsHardware())
1865 {
1866 // Pass down an appropriate z/Z packet...
1867 error.SetErrorString("watchpoints not supported");
1868 }
1869 // TODO: clear software watchpoints if we implement them
1870 }
1871 else
1872 {
1873 error.SetErrorString("Watchpoint location argument was NULL.");
1874 }
1875 if (error.Success())
1876 error.SetErrorToGenericError();
1877 return error;
1878}
1879
1880void
1881ProcessGDBRemote::Clear()
1882{
1883 m_flags = 0;
1884 m_thread_list.Clear();
1885 {
1886 Mutex::Locker locker(m_stdio_mutex);
1887 m_stdout_data.clear();
1888 }
Chris Lattner24943d22010-06-08 16:52:24 +00001889}
1890
1891Error
1892ProcessGDBRemote::DoSignal (int signo)
1893{
1894 Error error;
Greg Claytone005f2c2010-11-06 01:53:30 +00001895 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_PROCESS));
Chris Lattner24943d22010-06-08 16:52:24 +00001896 if (log)
1897 log->Printf ("ProcessGDBRemote::DoSignal (signal = %d)", signo);
1898
1899 if (!m_gdb_comm.SendAsyncSignal (signo))
1900 error.SetErrorStringWithFormat("failed to send signal %i", signo);
1901 return error;
1902}
1903
Chris Lattner24943d22010-06-08 16:52:24 +00001904Error
1905ProcessGDBRemote::StartDebugserverProcess
1906(
1907 const char *debugserver_url, // The connection string to use in the spawned debugserver ("localhost:1234" or "/dev/tty...")
1908 char const *inferior_argv[], // Arguments for the inferior program including the path to the inferior itself as the first argument
1909 char const *inferior_envp[], // Environment to pass along to the inferior program
Greg Claytonde915be2011-01-23 05:56:20 +00001910 const char *stdin_path,
1911 const char *stdout_path,
1912 const char *stderr_path,
1913 const char *working_dir,
Greg Clayton23cf0c72010-11-08 04:29:11 +00001914 bool launch_process, // Set to true if we are going to be launching a the process
1915 lldb::pid_t attach_pid, // If inferior inferior_argv == NULL, and attach_pid != LLDB_INVALID_PROCESS_ID send this pid as an argument to debugserver
Chris Lattner24943d22010-06-08 16:52:24 +00001916 const char *attach_name, // Wait for the next process to launch whose basename matches "attach_name"
1917 bool wait_for_launch, // Wait for the process named "attach_name" to launch
Caroline Ticebd666012010-12-03 18:46:09 +00001918 uint32_t launch_flags, // Launch flags
Chris Lattner24943d22010-06-08 16:52:24 +00001919 ArchSpec& inferior_arch // The arch of the inferior that we will launch
1920)
1921{
1922 Error error;
Caroline Ticebd666012010-12-03 18:46:09 +00001923 bool disable_aslr = (launch_flags & eLaunchFlagDisableASLR) != 0;
1924 bool no_stdio = (launch_flags & eLaunchFlagDisableSTDIO) != 0;
Chris Lattner24943d22010-06-08 16:52:24 +00001925 if (m_debugserver_pid == LLDB_INVALID_PROCESS_ID)
1926 {
1927 // If we locate debugserver, keep that located version around
1928 static FileSpec g_debugserver_file_spec;
1929
1930 FileSpec debugserver_file_spec;
1931 char debugserver_path[PATH_MAX];
1932
1933 // Always check to see if we have an environment override for the path
1934 // to the debugserver to use and use it if we do.
1935 const char *env_debugserver_path = getenv("LLDB_DEBUGSERVER_PATH");
1936 if (env_debugserver_path)
Greg Clayton537a7a82010-10-20 20:54:39 +00001937 debugserver_file_spec.SetFile (env_debugserver_path, false);
Chris Lattner24943d22010-06-08 16:52:24 +00001938 else
1939 debugserver_file_spec = g_debugserver_file_spec;
1940 bool debugserver_exists = debugserver_file_spec.Exists();
1941 if (!debugserver_exists)
1942 {
1943 // The debugserver binary is in the LLDB.framework/Resources
1944 // directory.
Greg Clayton24b48ff2010-10-17 22:03:32 +00001945 if (Host::GetLLDBPath (ePathTypeSupportExecutableDir, debugserver_file_spec))
Chris Lattner24943d22010-06-08 16:52:24 +00001946 {
Greg Clayton24b48ff2010-10-17 22:03:32 +00001947 debugserver_file_spec.GetFilename().SetCString(DEBUGSERVER_BASENAME);
Chris Lattner24943d22010-06-08 16:52:24 +00001948 debugserver_exists = debugserver_file_spec.Exists();
Greg Clayton24b48ff2010-10-17 22:03:32 +00001949 if (debugserver_exists)
1950 {
1951 g_debugserver_file_spec = debugserver_file_spec;
1952 }
1953 else
1954 {
1955 g_debugserver_file_spec.Clear();
1956 debugserver_file_spec.Clear();
1957 }
Chris Lattner24943d22010-06-08 16:52:24 +00001958 }
1959 }
1960
1961 if (debugserver_exists)
1962 {
1963 debugserver_file_spec.GetPath (debugserver_path, sizeof(debugserver_path));
1964
1965 m_stdio_communication.Clear();
1966 posix_spawnattr_t attr;
1967
Greg Claytone005f2c2010-11-06 01:53:30 +00001968 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS));
Chris Lattner24943d22010-06-08 16:52:24 +00001969
1970 Error local_err; // Errors that don't affect the spawning.
1971 if (log)
1972 log->Printf ("%s ( path='%s', argv=%p, envp=%p, arch=%s )", __FUNCTION__, debugserver_path, inferior_argv, inferior_envp, inferior_arch.AsCString());
1973 error.SetError( ::posix_spawnattr_init (&attr), eErrorTypePOSIX);
1974 if (error.Fail() || log)
Greg Claytone005f2c2010-11-06 01:53:30 +00001975 error.PutToLog(log.get(), "::posix_spawnattr_init ( &attr )");
Chris Lattner24943d22010-06-08 16:52:24 +00001976 if (error.Fail())
1977 return error;;
1978
1979#if !defined (__arm__)
1980
Greg Clayton24b48ff2010-10-17 22:03:32 +00001981 // We don't need to do this for ARM, and we really shouldn't now
1982 // that we have multiple CPU subtypes and no posix_spawnattr call
1983 // that allows us to set which CPU subtype to launch...
Greg Claytoncf015052010-06-11 03:25:34 +00001984 if (inferior_arch.GetType() == eArchTypeMachO)
Chris Lattner24943d22010-06-08 16:52:24 +00001985 {
Greg Claytoncf015052010-06-11 03:25:34 +00001986 cpu_type_t cpu = inferior_arch.GetCPUType();
1987 if (cpu != 0 && cpu != UINT32_MAX && cpu != LLDB_INVALID_CPUTYPE)
1988 {
1989 size_t ocount = 0;
1990 error.SetError( ::posix_spawnattr_setbinpref_np (&attr, 1, &cpu, &ocount), eErrorTypePOSIX);
1991 if (error.Fail() || log)
Greg Claytone005f2c2010-11-06 01:53:30 +00001992 error.PutToLog(log.get(), "::posix_spawnattr_setbinpref_np ( &attr, 1, cpu_type = 0x%8.8x, count => %zu )", cpu, ocount);
Chris Lattner24943d22010-06-08 16:52:24 +00001993
Greg Claytoncf015052010-06-11 03:25:34 +00001994 if (error.Fail() != 0 || ocount != 1)
1995 return error;
1996 }
Chris Lattner24943d22010-06-08 16:52:24 +00001997 }
1998
1999#endif
2000
2001 Args debugserver_args;
2002 char arg_cstr[PATH_MAX];
Chris Lattner24943d22010-06-08 16:52:24 +00002003
Chris Lattner24943d22010-06-08 16:52:24 +00002004 lldb_utility::PseudoTerminal pty;
Greg Claytonde915be2011-01-23 05:56:20 +00002005 const char *stdio_path = NULL;
2006 if (launch_process &&
Caroline Ticee4450f02011-01-28 00:19:58 +00002007 (stdin_path == NULL || stdout_path == NULL || stderr_path == NULL) &&
Greg Claytonde915be2011-01-23 05:56:20 +00002008 m_local_debugserver &&
2009 no_stdio == false)
Chris Lattner24943d22010-06-08 16:52:24 +00002010 {
Chris Lattner24943d22010-06-08 16:52:24 +00002011 if (pty.OpenFirstAvailableMaster(O_RDWR|O_NOCTTY, NULL, 0))
Caroline Ticee4450f02011-01-28 00:19:58 +00002012 {
2013 const char *slave_name = pty.GetSlaveName (NULL, 0);
2014 if (stdin_path == NULL
2015 && stdout_path == NULL
2016 && stderr_path == NULL)
2017 stdio_path = slave_name;
2018 else
2019 {
2020 if (stdin_path == NULL)
2021 stdin_path = slave_name;
2022 if (stdout_path == NULL)
2023 stdout_path = slave_name;
2024 if (stderr_path == NULL)
2025 stderr_path = slave_name;
2026 }
2027 }
Chris Lattner24943d22010-06-08 16:52:24 +00002028 }
2029
2030 // Start args with "debugserver /file/path -r --"
2031 debugserver_args.AppendArgument(debugserver_path);
2032 debugserver_args.AppendArgument(debugserver_url);
Greg Clayton24b48ff2010-10-17 22:03:32 +00002033 // use native registers, not the GDB registers
2034 debugserver_args.AppendArgument("--native-regs");
2035 // make debugserver run in its own session so signals generated by
2036 // special terminal key sequences (^C) don't affect debugserver
2037 debugserver_args.AppendArgument("--setsid");
Chris Lattner24943d22010-06-08 16:52:24 +00002038
Greg Clayton452bf612010-08-31 18:35:14 +00002039 if (disable_aslr)
2040 debugserver_args.AppendArguments("--disable-aslr");
2041
Chris Lattner24943d22010-06-08 16:52:24 +00002042 // Only set the inferior
Greg Claytonde915be2011-01-23 05:56:20 +00002043 if (launch_process)
Chris Lattner24943d22010-06-08 16:52:24 +00002044 {
Greg Claytonde915be2011-01-23 05:56:20 +00002045 if (no_stdio)
2046 debugserver_args.AppendArgument("--no-stdio");
2047 else
2048 {
2049 if (stdin_path && stdout_path && stderr_path &&
2050 strcmp(stdin_path, stdout_path) == 0 &&
2051 strcmp(stdin_path, stderr_path) == 0)
2052 {
2053 stdio_path = stdin_path;
2054 stdin_path = stdout_path = stderr_path = NULL;
2055 }
2056
2057 if (stdio_path)
2058 {
2059 // All file handles to stdin, stdout, stderr are the same...
2060 debugserver_args.AppendArgument("--stdio-path");
2061 debugserver_args.AppendArgument(stdio_path);
2062 }
2063 else
2064 {
2065 if (stdin_path == NULL && (stdout_path || stderr_path))
2066 stdin_path = "/dev/null";
2067
2068 if (stdout_path == NULL && (stdin_path || stderr_path))
2069 stdout_path = "/dev/null";
2070
2071 if (stderr_path == NULL && (stdin_path || stdout_path))
2072 stderr_path = "/dev/null";
2073
2074 if (stdin_path)
2075 {
2076 debugserver_args.AppendArgument("--stdin-path");
2077 debugserver_args.AppendArgument(stdin_path);
2078 }
2079 if (stdout_path)
2080 {
2081 debugserver_args.AppendArgument("--stdout-path");
2082 debugserver_args.AppendArgument(stdout_path);
2083 }
2084 if (stderr_path)
2085 {
2086 debugserver_args.AppendArgument("--stderr-path");
2087 debugserver_args.AppendArgument(stderr_path);
2088 }
2089 }
2090 }
Chris Lattner24943d22010-06-08 16:52:24 +00002091 }
Greg Claytonde915be2011-01-23 05:56:20 +00002092
2093 if (working_dir)
Caroline Ticebd666012010-12-03 18:46:09 +00002094 {
Greg Claytonde915be2011-01-23 05:56:20 +00002095 debugserver_args.AppendArgument("--working-dir");
2096 debugserver_args.AppendArgument(working_dir);
Caroline Ticebd666012010-12-03 18:46:09 +00002097 }
Chris Lattner24943d22010-06-08 16:52:24 +00002098
2099 const char *env_debugserver_log_file = getenv("LLDB_DEBUGSERVER_LOG_FILE");
2100 if (env_debugserver_log_file)
2101 {
2102 ::snprintf (arg_cstr, sizeof(arg_cstr), "--log-file=%s", env_debugserver_log_file);
2103 debugserver_args.AppendArgument(arg_cstr);
2104 }
2105
2106 const char *env_debugserver_log_flags = getenv("LLDB_DEBUGSERVER_LOG_FLAGS");
2107 if (env_debugserver_log_flags)
2108 {
2109 ::snprintf (arg_cstr, sizeof(arg_cstr), "--log-flags=%s", env_debugserver_log_flags);
2110 debugserver_args.AppendArgument(arg_cstr);
2111 }
Greg Claytoncc3e6402011-01-25 06:55:13 +00002112// debugserver_args.AppendArgument("--log-file=/tmp/debugserver.txt");
Greg Clayton7e2f91c2011-01-29 07:10:55 +00002113// debugserver_args.AppendArgument("--log-flags=0x802e0e");
Chris Lattner24943d22010-06-08 16:52:24 +00002114
2115 // Now append the program arguments
2116 if (launch_process)
2117 {
2118 if (inferior_argv)
2119 {
2120 // Terminate the debugserver args so we can now append the inferior args
2121 debugserver_args.AppendArgument("--");
2122
2123 for (int i = 0; inferior_argv[i] != NULL; ++i)
2124 debugserver_args.AppendArgument (inferior_argv[i]);
2125 }
2126 else
2127 {
2128 // Will send environment entries with the 'QEnvironment:' packet
2129 // Will send arguments with the 'A' packet
2130 }
2131 }
2132 else if (attach_pid != LLDB_INVALID_PROCESS_ID)
2133 {
2134 ::snprintf (arg_cstr, sizeof(arg_cstr), "--attach=%u", attach_pid);
2135 debugserver_args.AppendArgument (arg_cstr);
2136 }
2137 else if (attach_name && attach_name[0])
2138 {
2139 if (wait_for_launch)
2140 debugserver_args.AppendArgument ("--waitfor");
2141 else
2142 debugserver_args.AppendArgument ("--attach");
2143 debugserver_args.AppendArgument (attach_name);
2144 }
2145
2146 Error file_actions_err;
2147 posix_spawn_file_actions_t file_actions;
2148#if DONT_CLOSE_DEBUGSERVER_STDIO
2149 file_actions_err.SetErrorString ("Remove this after uncommenting the code block below.");
2150#else
2151 file_actions_err.SetError( ::posix_spawn_file_actions_init (&file_actions), eErrorTypePOSIX);
2152 if (file_actions_err.Success())
2153 {
2154 ::posix_spawn_file_actions_addclose (&file_actions, STDIN_FILENO);
2155 ::posix_spawn_file_actions_addclose (&file_actions, STDOUT_FILENO);
2156 ::posix_spawn_file_actions_addclose (&file_actions, STDERR_FILENO);
2157 }
2158#endif
2159
2160 if (log)
2161 {
2162 StreamString strm;
2163 debugserver_args.Dump (&strm);
2164 log->Printf("%s arguments:\n%s", debugserver_args.GetArgumentAtIndex(0), strm.GetData());
2165 }
2166
Greg Clayton72e1c782011-01-22 23:43:18 +00002167 error.SetError (::posix_spawnp (&m_debugserver_pid,
2168 debugserver_path,
2169 file_actions_err.Success() ? &file_actions : NULL,
2170 &attr,
2171 debugserver_args.GetArgumentVector(),
2172 (char * const*)inferior_envp),
2173 eErrorTypePOSIX);
2174
Greg Claytone9d0df42010-07-02 01:29:13 +00002175
2176 ::posix_spawnattr_destroy (&attr);
2177
Chris Lattner24943d22010-06-08 16:52:24 +00002178 if (file_actions_err.Success())
2179 ::posix_spawn_file_actions_destroy (&file_actions);
2180
2181 // We have seen some cases where posix_spawnp was returning a valid
2182 // looking pid even when an error was returned, so clear it out
2183 if (error.Fail())
2184 m_debugserver_pid = LLDB_INVALID_PROCESS_ID;
2185
2186 if (error.Fail() || log)
Greg Claytone005f2c2010-11-06 01:53:30 +00002187 error.PutToLog(log.get(), "::posix_spawnp ( pid => %i, path = '%s', file_actions = %p, attr = %p, argv = %p, envp = %p )", m_debugserver_pid, debugserver_path, NULL, &attr, inferior_argv, inferior_envp);
Chris Lattner24943d22010-06-08 16:52:24 +00002188
Caroline Ticebd666012010-12-03 18:46:09 +00002189 if (m_debugserver_pid != LLDB_INVALID_PROCESS_ID && !no_stdio)
Caroline Tice91a1dab2010-11-05 22:37:44 +00002190 {
Greg Clayton23cf0c72010-11-08 04:29:11 +00002191 if (pty.GetMasterFileDescriptor() != lldb_utility::PseudoTerminal::invalid_fd)
Caroline Tice861efb32010-11-16 05:07:41 +00002192 SetUpProcessInputReader (pty.ReleaseMasterFileDescriptor());
Caroline Tice91a1dab2010-11-05 22:37:44 +00002193 }
Chris Lattner24943d22010-06-08 16:52:24 +00002194 }
2195 else
2196 {
2197 error.SetErrorStringWithFormat ("Unable to locate " DEBUGSERVER_BASENAME ".\n");
2198 }
2199
2200 if (m_debugserver_pid != LLDB_INVALID_PROCESS_ID)
2201 StartAsyncThread ();
2202 }
2203 return error;
2204}
2205
2206bool
2207ProcessGDBRemote::MonitorDebugserverProcess
2208(
2209 void *callback_baton,
2210 lldb::pid_t debugserver_pid,
2211 int signo, // Zero for no signal
2212 int exit_status // Exit value of process if signal is zero
2213)
2214{
2215 // We pass in the ProcessGDBRemote inferior process it and name it
2216 // "gdb_remote_pid". The process ID is passed in the "callback_baton"
2217 // pointer value itself, thus we need the double cast...
2218
2219 // "debugserver_pid" argument passed in is the process ID for
2220 // debugserver that we are tracking...
2221
Greg Clayton75ccf502010-08-21 02:22:51 +00002222 ProcessGDBRemote *process = (ProcessGDBRemote *)callback_baton;
Greg Clayton72e1c782011-01-22 23:43:18 +00002223
2224 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_PROCESS));
2225 if (log)
2226 log->Printf ("ProcessGDBRemote::MonitorDebugserverProcess (baton=%p, pid=%i, signo=%i (0x%x), exit_status=%i)", callback_baton, debugserver_pid, signo, signo, exit_status);
2227
Greg Clayton75ccf502010-08-21 02:22:51 +00002228 if (process)
Chris Lattner24943d22010-06-08 16:52:24 +00002229 {
Greg Clayton75ccf502010-08-21 02:22:51 +00002230 // Sleep for a half a second to make sure our inferior process has
2231 // time to set its exit status before we set it incorrectly when
2232 // both the debugserver and the inferior process shut down.
2233 usleep (500000);
2234 // If our process hasn't yet exited, debugserver might have died.
2235 // If the process did exit, the we are reaping it.
Greg Clayton3b2c41c2010-10-18 04:14:23 +00002236 const StateType state = process->GetState();
2237
2238 if (process->m_debugserver_pid != LLDB_INVALID_PROCESS_ID &&
2239 state != eStateInvalid &&
2240 state != eStateUnloaded &&
2241 state != eStateExited &&
2242 state != eStateDetached)
Chris Lattner24943d22010-06-08 16:52:24 +00002243 {
Greg Clayton75ccf502010-08-21 02:22:51 +00002244 char error_str[1024];
2245 if (signo)
Chris Lattner24943d22010-06-08 16:52:24 +00002246 {
Greg Clayton75ccf502010-08-21 02:22:51 +00002247 const char *signal_cstr = process->GetUnixSignals().GetSignalAsCString (signo);
2248 if (signal_cstr)
2249 ::snprintf (error_str, sizeof (error_str), DEBUGSERVER_BASENAME " died with signal %s", signal_cstr);
Chris Lattner24943d22010-06-08 16:52:24 +00002250 else
Greg Clayton75ccf502010-08-21 02:22:51 +00002251 ::snprintf (error_str, sizeof (error_str), DEBUGSERVER_BASENAME " died with signal %i", signo);
Chris Lattner24943d22010-06-08 16:52:24 +00002252 }
2253 else
2254 {
Greg Clayton75ccf502010-08-21 02:22:51 +00002255 ::snprintf (error_str, sizeof (error_str), DEBUGSERVER_BASENAME " died with an exit status of 0x%8.8x", exit_status);
Chris Lattner24943d22010-06-08 16:52:24 +00002256 }
Greg Clayton75ccf502010-08-21 02:22:51 +00002257
2258 process->SetExitStatus (-1, error_str);
2259 }
Greg Clayton3b2c41c2010-10-18 04:14:23 +00002260 // Debugserver has exited we need to let our ProcessGDBRemote
2261 // know that it no longer has a debugserver instance
2262 process->m_debugserver_pid = LLDB_INVALID_PROCESS_ID;
2263 // We are returning true to this function below, so we can
2264 // forget about the monitor handle.
2265 process->m_debugserver_thread = LLDB_INVALID_HOST_THREAD;
Chris Lattner24943d22010-06-08 16:52:24 +00002266 }
2267 return true;
2268}
2269
2270void
2271ProcessGDBRemote::KillDebugserverProcess ()
2272{
2273 if (m_debugserver_pid != LLDB_INVALID_PROCESS_ID)
2274 {
2275 ::kill (m_debugserver_pid, SIGINT);
2276 m_debugserver_pid = LLDB_INVALID_PROCESS_ID;
2277 }
2278}
2279
2280void
2281ProcessGDBRemote::Initialize()
2282{
2283 static bool g_initialized = false;
2284
2285 if (g_initialized == false)
2286 {
2287 g_initialized = true;
2288 PluginManager::RegisterPlugin (GetPluginNameStatic(),
2289 GetPluginDescriptionStatic(),
2290 CreateInstance);
2291
2292 Log::Callbacks log_callbacks = {
2293 ProcessGDBRemoteLog::DisableLog,
2294 ProcessGDBRemoteLog::EnableLog,
2295 ProcessGDBRemoteLog::ListLogCategories
2296 };
2297
2298 Log::RegisterLogChannel (ProcessGDBRemote::GetPluginNameStatic(), log_callbacks);
2299 }
2300}
2301
2302bool
2303ProcessGDBRemote::SetCurrentGDBRemoteThread (int tid)
2304{
2305 if (m_curr_tid == tid)
2306 return true;
2307
2308 char packet[32];
Greg Claytonc1f45872011-02-12 06:28:37 +00002309 int packet_len;
2310 if (tid <= 0)
2311 packet_len = ::snprintf (packet, sizeof(packet), "Hg%i", tid);
2312 else
2313 packet_len = ::snprintf (packet, sizeof(packet), "Hg%x", tid);
Chris Lattner24943d22010-06-08 16:52:24 +00002314 assert (packet_len + 1 < sizeof(packet));
2315 StringExtractorGDBRemote response;
2316 if (m_gdb_comm.SendPacketAndWaitForResponse(packet, packet_len, response, 2, false))
2317 {
2318 if (response.IsOKPacket())
2319 {
2320 m_curr_tid = tid;
2321 return true;
2322 }
2323 }
2324 return false;
2325}
2326
2327bool
2328ProcessGDBRemote::SetCurrentGDBRemoteThreadForRun (int tid)
2329{
2330 if (m_curr_tid_run == tid)
2331 return true;
2332
2333 char packet[32];
Greg Claytonc1f45872011-02-12 06:28:37 +00002334 int packet_len;
2335 if (tid <= 0)
2336 packet_len = ::snprintf (packet, sizeof(packet), "Hc%i", tid);
2337 else
2338 packet_len = ::snprintf (packet, sizeof(packet), "Hc%x", tid);
2339
Chris Lattner24943d22010-06-08 16:52:24 +00002340 assert (packet_len + 1 < sizeof(packet));
2341 StringExtractorGDBRemote response;
2342 if (m_gdb_comm.SendPacketAndWaitForResponse(packet, packet_len, response, 2, false))
2343 {
2344 if (response.IsOKPacket())
2345 {
2346 m_curr_tid_run = tid;
2347 return true;
2348 }
2349 }
2350 return false;
2351}
2352
2353void
2354ProcessGDBRemote::ResetGDBRemoteState ()
2355{
2356 // Reset and GDB remote state
2357 m_curr_tid = LLDB_INVALID_THREAD_ID;
2358 m_curr_tid_run = LLDB_INVALID_THREAD_ID;
2359 m_z0_supported = 1;
2360}
2361
2362
2363bool
2364ProcessGDBRemote::StartAsyncThread ()
2365{
2366 ResetGDBRemoteState ();
2367
Greg Claytone005f2c2010-11-06 01:53:30 +00002368 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_PROCESS));
Chris Lattner24943d22010-06-08 16:52:24 +00002369
2370 if (log)
2371 log->Printf ("ProcessGDBRemote::%s ()", __FUNCTION__);
2372
2373 // Create a thread that watches our internal state and controls which
2374 // events make it to clients (into the DCProcess event queue).
2375 m_async_thread = Host::ThreadCreate ("<lldb.process.gdb-remote.async>", ProcessGDBRemote::AsyncThread, this, NULL);
Greg Clayton09c81ef2011-02-08 01:34:25 +00002376 return IS_VALID_LLDB_HOST_THREAD(m_async_thread);
Chris Lattner24943d22010-06-08 16:52:24 +00002377}
2378
2379void
2380ProcessGDBRemote::StopAsyncThread ()
2381{
Greg Claytone005f2c2010-11-06 01:53:30 +00002382 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet(GDBR_LOG_PROCESS));
Chris Lattner24943d22010-06-08 16:52:24 +00002383
2384 if (log)
2385 log->Printf ("ProcessGDBRemote::%s ()", __FUNCTION__);
2386
2387 m_async_broadcaster.BroadcastEvent (eBroadcastBitAsyncThreadShouldExit);
2388
2389 // Stop the stdio thread
Greg Clayton09c81ef2011-02-08 01:34:25 +00002390 if (IS_VALID_LLDB_HOST_THREAD(m_async_thread))
Chris Lattner24943d22010-06-08 16:52:24 +00002391 {
2392 Host::ThreadJoin (m_async_thread, NULL, NULL);
2393 }
2394}
2395
2396
2397void *
2398ProcessGDBRemote::AsyncThread (void *arg)
2399{
2400 ProcessGDBRemote *process = (ProcessGDBRemote*) arg;
2401
Greg Claytone005f2c2010-11-06 01:53:30 +00002402 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS));
Chris Lattner24943d22010-06-08 16:52:24 +00002403 if (log)
2404 log->Printf ("ProcessGDBRemote::%s (arg = %p, pid = %i) thread starting...", __FUNCTION__, arg, process->GetID());
2405
2406 Listener listener ("ProcessGDBRemote::AsyncThread");
2407 EventSP event_sp;
2408 const uint32_t desired_event_mask = eBroadcastBitAsyncContinue |
2409 eBroadcastBitAsyncThreadShouldExit;
2410
2411 if (listener.StartListeningForEvents (&process->m_async_broadcaster, desired_event_mask) == desired_event_mask)
2412 {
2413 bool done = false;
2414 while (!done)
2415 {
2416 if (log)
2417 log->Printf ("ProcessGDBRemote::%s (arg = %p, pid = %i) listener.WaitForEvent (NULL, event_sp)...", __FUNCTION__, arg, process->GetID());
2418 if (listener.WaitForEvent (NULL, event_sp))
2419 {
2420 const uint32_t event_type = event_sp->GetType();
Jim Ingham3ae449a2010-11-17 02:32:00 +00002421 if (log)
2422 log->Printf ("ProcessGDBRemote::%s (arg = %p, pid = %i) Got an event of type: %d...", __FUNCTION__, arg, process->GetID(), event_type);
2423
Chris Lattner24943d22010-06-08 16:52:24 +00002424 switch (event_type)
2425 {
2426 case eBroadcastBitAsyncContinue:
2427 {
2428 const EventDataBytes *continue_packet = EventDataBytes::GetEventDataFromEvent(event_sp.get());
2429
2430 if (continue_packet)
2431 {
2432 const char *continue_cstr = (const char *)continue_packet->GetBytes ();
2433 const size_t continue_cstr_len = continue_packet->GetByteSize ();
2434 if (log)
2435 log->Printf ("ProcessGDBRemote::%s (arg = %p, pid = %i) got eBroadcastBitAsyncContinue: %s", __FUNCTION__, arg, process->GetID(), continue_cstr);
2436
Greg Clayton7e2f91c2011-01-29 07:10:55 +00002437 if (::strstr (continue_cstr, "vAttach") == NULL)
2438 process->SetPrivateState(eStateRunning);
Chris Lattner24943d22010-06-08 16:52:24 +00002439 StringExtractorGDBRemote response;
2440 StateType stop_state = process->GetGDBRemote().SendContinuePacketAndWaitForResponse (process, continue_cstr, continue_cstr_len, response);
2441
2442 switch (stop_state)
2443 {
2444 case eStateStopped:
2445 case eStateCrashed:
2446 case eStateSuspended:
2447 process->m_last_stop_packet = response;
2448 process->m_last_stop_packet.SetFilePos (0);
2449 process->SetPrivateState (stop_state);
2450 break;
2451
2452 case eStateExited:
2453 process->m_last_stop_packet = response;
2454 process->m_last_stop_packet.SetFilePos (0);
2455 response.SetFilePos(1);
2456 process->SetExitStatus(response.GetHexU8(), NULL);
2457 done = true;
2458 break;
2459
2460 case eStateInvalid:
2461 break;
2462
2463 default:
2464 process->SetPrivateState (stop_state);
2465 break;
2466 }
2467 }
2468 }
2469 break;
2470
2471 case eBroadcastBitAsyncThreadShouldExit:
2472 if (log)
2473 log->Printf ("ProcessGDBRemote::%s (arg = %p, pid = %i) got eBroadcastBitAsyncThreadShouldExit...", __FUNCTION__, arg, process->GetID());
2474 done = true;
2475 break;
2476
2477 default:
2478 if (log)
2479 log->Printf ("ProcessGDBRemote::%s (arg = %p, pid = %i) got unknown event 0x%8.8x", __FUNCTION__, arg, process->GetID(), event_type);
2480 done = true;
2481 break;
2482 }
2483 }
2484 else
2485 {
2486 if (log)
2487 log->Printf ("ProcessGDBRemote::%s (arg = %p, pid = %i) listener.WaitForEvent (NULL, event_sp) => false", __FUNCTION__, arg, process->GetID());
2488 done = true;
2489 }
2490 }
2491 }
2492
2493 if (log)
2494 log->Printf ("ProcessGDBRemote::%s (arg = %p, pid = %i) thread exiting...", __FUNCTION__, arg, process->GetID());
2495
2496 process->m_async_thread = LLDB_INVALID_HOST_THREAD;
2497 return NULL;
2498}
2499
Chris Lattner24943d22010-06-08 16:52:24 +00002500const char *
2501ProcessGDBRemote::GetDispatchQueueNameForThread
2502(
2503 addr_t thread_dispatch_qaddr,
2504 std::string &dispatch_queue_name
2505)
2506{
2507 dispatch_queue_name.clear();
2508 if (thread_dispatch_qaddr != 0 && thread_dispatch_qaddr != LLDB_INVALID_ADDRESS)
2509 {
2510 // Cache the dispatch_queue_offsets_addr value so we don't always have
2511 // to look it up
2512 if (m_dispatch_queue_offsets_addr == LLDB_INVALID_ADDRESS)
2513 {
Greg Claytonaf6e9e42010-10-12 17:33:06 +00002514 static ConstString g_dispatch_queue_offsets_symbol_name ("dispatch_queue_offsets");
2515 const Symbol *dispatch_queue_offsets_symbol = NULL;
Greg Clayton537a7a82010-10-20 20:54:39 +00002516 ModuleSP module_sp(GetTarget().GetImages().FindFirstModuleForFileSpec (FileSpec("libSystem.B.dylib", false)));
Greg Claytonaf6e9e42010-10-12 17:33:06 +00002517 if (module_sp)
2518 dispatch_queue_offsets_symbol = module_sp->FindFirstSymbolWithNameAndType (g_dispatch_queue_offsets_symbol_name, eSymbolTypeData);
2519
2520 if (dispatch_queue_offsets_symbol == NULL)
2521 {
Greg Clayton537a7a82010-10-20 20:54:39 +00002522 module_sp = GetTarget().GetImages().FindFirstModuleForFileSpec (FileSpec("libdispatch.dylib", false));
Greg Claytonaf6e9e42010-10-12 17:33:06 +00002523 if (module_sp)
2524 dispatch_queue_offsets_symbol = module_sp->FindFirstSymbolWithNameAndType (g_dispatch_queue_offsets_symbol_name, eSymbolTypeData);
2525 }
Chris Lattner24943d22010-06-08 16:52:24 +00002526 if (dispatch_queue_offsets_symbol)
Greg Claytoneea26402010-09-14 23:36:40 +00002527 m_dispatch_queue_offsets_addr = dispatch_queue_offsets_symbol->GetValue().GetLoadAddress(&m_target);
Chris Lattner24943d22010-06-08 16:52:24 +00002528
2529 if (m_dispatch_queue_offsets_addr == LLDB_INVALID_ADDRESS)
2530 return NULL;
2531 }
2532
2533 uint8_t memory_buffer[8];
2534 DataExtractor data(memory_buffer, sizeof(memory_buffer), GetByteOrder(), GetAddressByteSize());
2535
2536 // Excerpt from src/queue_private.h
2537 struct dispatch_queue_offsets_s
2538 {
2539 uint16_t dqo_version;
2540 uint16_t dqo_label;
2541 uint16_t dqo_label_size;
2542 } dispatch_queue_offsets;
2543
2544
2545 Error error;
2546 if (ReadMemory (m_dispatch_queue_offsets_addr, memory_buffer, sizeof(dispatch_queue_offsets), error) == sizeof(dispatch_queue_offsets))
2547 {
2548 uint32_t data_offset = 0;
2549 if (data.GetU16(&data_offset, &dispatch_queue_offsets.dqo_version, sizeof(dispatch_queue_offsets)/sizeof(uint16_t)))
2550 {
2551 if (ReadMemory (thread_dispatch_qaddr, &memory_buffer, data.GetAddressByteSize(), error) == data.GetAddressByteSize())
2552 {
2553 data_offset = 0;
2554 lldb::addr_t queue_addr = data.GetAddress(&data_offset);
2555 lldb::addr_t label_addr = queue_addr + dispatch_queue_offsets.dqo_label;
2556 dispatch_queue_name.resize(dispatch_queue_offsets.dqo_label_size, '\0');
2557 size_t bytes_read = ReadMemory (label_addr, &dispatch_queue_name[0], dispatch_queue_offsets.dqo_label_size, error);
2558 if (bytes_read < dispatch_queue_offsets.dqo_label_size)
2559 dispatch_queue_name.erase (bytes_read);
2560 }
2561 }
2562 }
2563 }
2564 if (dispatch_queue_name.empty())
2565 return NULL;
2566 return dispatch_queue_name.c_str();
2567}
2568
Jim Ingham7508e732010-08-09 23:31:02 +00002569uint32_t
2570ProcessGDBRemote::ListProcessesMatchingName (const char *name, StringList &matches, std::vector<lldb::pid_t> &pids)
2571{
2572 // If we are planning to launch the debugserver remotely, then we need to fire up a debugserver
2573 // process and ask it for the list of processes. But if we are local, we can let the Host do it.
2574 if (m_local_debugserver)
2575 {
2576 return Host::ListProcessesMatchingName (name, matches, pids);
2577 }
2578 else
2579 {
2580 // FIXME: Implement talking to the remote debugserver.
2581 return 0;
2582 }
2583
2584}
Jim Ingham55e01d82011-01-22 01:33:44 +00002585
2586bool
2587ProcessGDBRemote::NewThreadNotifyBreakpointHit (void *baton,
2588 lldb_private::StoppointCallbackContext *context,
2589 lldb::user_id_t break_id,
2590 lldb::user_id_t break_loc_id)
2591{
2592 // I don't think I have to do anything here, just make sure I notice the new thread when it starts to
2593 // run so I can stop it if that's what I want to do.
2594 LogSP log (lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_STEP));
2595 if (log)
2596 log->Printf("Hit New Thread Notification breakpoint.");
2597 return false;
2598}
2599
2600
2601bool
2602ProcessGDBRemote::StartNoticingNewThreads()
2603{
2604 static const char *bp_names[] =
2605 {
2606 "start_wqthread",
Jim Inghamff276fe2011-02-08 05:19:01 +00002607 "_pthread_wqthread",
Jim Ingham55e01d82011-01-22 01:33:44 +00002608 "_pthread_start",
2609 NULL
2610 };
2611
2612 LogSP log (lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_STEP));
2613 size_t num_bps = m_thread_observation_bps.size();
2614 if (num_bps != 0)
2615 {
2616 for (int i = 0; i < num_bps; i++)
2617 {
2618 lldb::BreakpointSP break_sp = m_target.GetBreakpointByID(m_thread_observation_bps[i]);
2619 if (break_sp)
2620 {
2621 if (log)
2622 log->Printf("Enabled noticing new thread breakpoint.");
2623 break_sp->SetEnabled(true);
2624 }
2625 }
2626 }
2627 else
2628 {
2629 for (int i = 0; bp_names[i] != NULL; i++)
2630 {
2631 Breakpoint *breakpoint = m_target.CreateBreakpoint (NULL, bp_names[i], eFunctionNameTypeFull, true).get();
2632 if (breakpoint)
2633 {
2634 if (log)
2635 log->Printf("Successfully created new thread notification breakpoint at \"%s\".", bp_names[i]);
2636 m_thread_observation_bps.push_back(breakpoint->GetID());
2637 breakpoint->SetCallback (ProcessGDBRemote::NewThreadNotifyBreakpointHit, this, true);
2638 }
2639 else
2640 {
2641 if (log)
2642 log->Printf("Failed to create new thread notification breakpoint.");
2643 return false;
2644 }
2645 }
2646 }
2647
2648 return true;
2649}
2650
2651bool
2652ProcessGDBRemote::StopNoticingNewThreads()
2653{
Jim Inghamff276fe2011-02-08 05:19:01 +00002654 LogSP log (lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_STEP));
2655 if (log)
2656 log->Printf ("Disabling new thread notification breakpoint.");
Jim Ingham55e01d82011-01-22 01:33:44 +00002657 size_t num_bps = m_thread_observation_bps.size();
2658 if (num_bps != 0)
2659 {
2660 for (int i = 0; i < num_bps; i++)
2661 {
Jim Ingham55e01d82011-01-22 01:33:44 +00002662
2663 lldb::BreakpointSP break_sp = m_target.GetBreakpointByID(m_thread_observation_bps[i]);
2664 if (break_sp)
2665 {
Jim Ingham55e01d82011-01-22 01:33:44 +00002666 break_sp->SetEnabled(false);
2667 }
2668 }
2669 }
2670 return true;
2671}
2672
2673