1 //===-- SBDebugger.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 #include "lldb/API/SBDebugger.h"
11 
12 #include "lldb/lldb-private.h"
13 
14 #include "lldb/API/SBListener.h"
15 #include "lldb/API/SBBroadcaster.h"
16 #include "lldb/API/SBCommandInterpreter.h"
17 #include "lldb/API/SBCommandReturnObject.h"
18 #include "lldb/API/SBError.h"
19 #include "lldb/API/SBEvent.h"
20 #include "lldb/API/SBFrame.h"
21 #include "lldb/API/SBInputReader.h"
22 #include "lldb/API/SBProcess.h"
23 #include "lldb/API/SBSourceManager.h"
24 #include "lldb/API/SBStream.h"
25 #include "lldb/API/SBStringList.h"
26 #include "lldb/API/SBTarget.h"
27 #include "lldb/API/SBThread.h"
28 #include "lldb/Core/Debugger.h"
29 #include "lldb/Core/State.h"
30 #include "lldb/Interpreter/Args.h"
31 #include "lldb/Interpreter/CommandInterpreter.h"
32 #include "lldb/Target/Process.h"
33 #include "lldb/Target/TargetList.h"
34 
35 using namespace lldb;
36 using namespace lldb_private;
37 
38 void
39 SBDebugger::Initialize ()
40 {
41     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
42 
43     if (log)
44         log->Printf ("SBDebugger::Initialize ()");
45 
46     SBCommandInterpreter::InitializeSWIG ();
47 
48     Debugger::Initialize();
49 }
50 
51 void
52 SBDebugger::Terminate ()
53 {
54     Debugger::Terminate();
55 }
56 
57 void
58 SBDebugger::Clear ()
59 {
60     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
61 
62     if (log)
63         log->Printf ("SBDebugger(%p)::Clear ()", m_opaque_sp.get());
64 
65     if (m_opaque_sp)
66         m_opaque_sp->CleanUpInputReaders ();
67 
68     m_opaque_sp.reset();
69 }
70 
71 SBDebugger
72 SBDebugger::Create()
73 {
74     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
75 
76     SBDebugger debugger;
77     debugger.reset(Debugger::CreateInstance());
78 
79     if (log)
80     {
81         SBStream sstr;
82         debugger.GetDescription (sstr);
83         log->Printf ("SBDebugger::Create () => SBDebugger(%p): %s", debugger.m_opaque_sp.get(), sstr.GetData());
84     }
85 
86     return debugger;
87 }
88 
89 void
90 SBDebugger::Destroy (SBDebugger &debugger)
91 {
92     LogSP log (GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
93 
94     if (log)
95     {
96         SBStream sstr;
97         debugger.GetDescription (sstr);
98         log->Printf ("SBDebugger::Destroy () => SBDebugger(%p): %s", debugger.m_opaque_sp.get(), sstr.GetData());
99     }
100 
101     Debugger::Destroy (debugger.m_opaque_sp);
102 
103     if (debugger.m_opaque_sp.get() != NULL)
104         debugger.m_opaque_sp.reset();
105 }
106 
107 SBDebugger::SBDebugger () :
108     m_opaque_sp ()
109 {
110 }
111 
112 SBDebugger::SBDebugger(const SBDebugger &rhs) :
113     m_opaque_sp (rhs.m_opaque_sp)
114 {
115 }
116 
117 SBDebugger &
118 SBDebugger::operator = (const SBDebugger &rhs)
119 {
120     if (this != &rhs)
121     {
122         m_opaque_sp = rhs.m_opaque_sp;
123     }
124     return *this;
125 }
126 
127 SBDebugger::~SBDebugger ()
128 {
129 }
130 
131 bool
132 SBDebugger::IsValid() const
133 {
134     return m_opaque_sp.get() != NULL;
135 }
136 
137 
138 void
139 SBDebugger::SetAsync (bool b)
140 {
141     if (m_opaque_sp)
142         m_opaque_sp->SetAsyncExecution(b);
143 }
144 
145 void
146 SBDebugger::SkipLLDBInitFiles (bool b)
147 {
148     if (m_opaque_sp)
149         m_opaque_sp->GetCommandInterpreter().SkipLLDBInitFiles (b);
150 }
151 
152 // Shouldn't really be settable after initialization as this could cause lots of problems; don't want users
153 // trying to switch modes in the middle of a debugging session.
154 void
155 SBDebugger::SetInputFileHandle (FILE *fh, bool transfer_ownership)
156 {
157     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
158 
159     if (log)
160         log->Printf ("SBDebugger(%p)::SetInputFileHandle (fh=%p, transfer_ownership=%i)", m_opaque_sp.get(),
161                      fh, transfer_ownership);
162 
163     if (m_opaque_sp)
164         m_opaque_sp->SetInputFileHandle (fh, transfer_ownership);
165 }
166 
167 void
168 SBDebugger::SetOutputFileHandle (FILE *fh, bool transfer_ownership)
169 {
170     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
171 
172 
173     if (log)
174         log->Printf ("SBDebugger(%p)::SetOutputFileHandle (fh=%p, transfer_ownership=%i)", m_opaque_sp.get(),
175                      fh, transfer_ownership);
176 
177     if (m_opaque_sp)
178         m_opaque_sp->SetOutputFileHandle (fh, transfer_ownership);
179 }
180 
181 void
182 SBDebugger::SetErrorFileHandle (FILE *fh, bool transfer_ownership)
183 {
184     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
185 
186 
187     if (log)
188         log->Printf ("SBDebugger(%p)::SetErrorFileHandle (fh=%p, transfer_ownership=%i)", m_opaque_sp.get(),
189                      fh, transfer_ownership);
190 
191     if (m_opaque_sp)
192         m_opaque_sp->SetErrorFileHandle (fh, transfer_ownership);
193 }
194 
195 FILE *
196 SBDebugger::GetInputFileHandle ()
197 {
198     if (m_opaque_sp)
199         return m_opaque_sp->GetInputFile().GetStream();
200     return NULL;
201 }
202 
203 FILE *
204 SBDebugger::GetOutputFileHandle ()
205 {
206     if (m_opaque_sp)
207         return m_opaque_sp->GetOutputFile().GetStream();
208     return NULL;
209 }
210 
211 FILE *
212 SBDebugger::GetErrorFileHandle ()
213 {
214     if (m_opaque_sp)
215         return m_opaque_sp->GetErrorFile().GetStream();
216     return NULL;
217 }
218 
219 SBCommandInterpreter
220 SBDebugger::GetCommandInterpreter ()
221 {
222     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
223 
224     SBCommandInterpreter sb_interpreter;
225     if (m_opaque_sp)
226         sb_interpreter.reset (&m_opaque_sp->GetCommandInterpreter());
227 
228     if (log)
229         log->Printf ("SBDebugger(%p)::GetCommandInterpreter () => SBCommandInterpreter(%p)",
230                      m_opaque_sp.get(), sb_interpreter.get());
231 
232     return sb_interpreter;
233 }
234 
235 void
236 SBDebugger::HandleCommand (const char *command)
237 {
238     if (m_opaque_sp)
239     {
240         TargetSP target_sp (m_opaque_sp->GetSelectedTarget());
241         Mutex::Locker api_locker;
242         if (target_sp)
243             api_locker.Reset(target_sp->GetAPIMutex().GetMutex());
244 
245         SBCommandInterpreter sb_interpreter(GetCommandInterpreter ());
246         SBCommandReturnObject result;
247 
248         sb_interpreter.HandleCommand (command, result, false);
249 
250         if (GetErrorFileHandle() != NULL)
251             result.PutError (GetErrorFileHandle());
252         if (GetOutputFileHandle() != NULL)
253             result.PutOutput (GetOutputFileHandle());
254 
255         if (m_opaque_sp->GetAsyncExecution() == false)
256         {
257             SBProcess process(GetCommandInterpreter().GetProcess ());
258             if (process.IsValid())
259             {
260                 EventSP event_sp;
261                 Listener &lldb_listener = m_opaque_sp->GetListener();
262                 while (lldb_listener.GetNextEventForBroadcaster (process.get(), event_sp))
263                 {
264                     SBEvent event(event_sp);
265                     HandleProcessEvent (process, event, GetOutputFileHandle(), GetErrorFileHandle());
266                 }
267             }
268         }
269     }
270 }
271 
272 SBListener
273 SBDebugger::GetListener ()
274 {
275     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
276 
277     SBListener sb_listener;
278     if (m_opaque_sp)
279         sb_listener.reset(&m_opaque_sp->GetListener(), false);
280 
281     if (log)
282         log->Printf ("SBDebugger(%p)::GetListener () => SBListener(%p)", m_opaque_sp.get(),
283                      sb_listener.get());
284 
285     return sb_listener;
286 }
287 
288 void
289 SBDebugger::HandleProcessEvent (const SBProcess &process, const SBEvent &event, FILE *out, FILE *err)
290 {
291     if (!process.IsValid())
292         return;
293 
294     const uint32_t event_type = event.GetType();
295     char stdio_buffer[1024];
296     size_t len;
297 
298     Mutex::Locker api_locker (process.GetTarget()->GetAPIMutex());
299 
300     if (event_type & (Process::eBroadcastBitSTDOUT | Process::eBroadcastBitStateChanged))
301     {
302         // Drain stdout when we stop just in case we have any bytes
303         while ((len = process.GetSTDOUT (stdio_buffer, sizeof (stdio_buffer))) > 0)
304             if (out != NULL)
305                 ::fwrite (stdio_buffer, 1, len, out);
306     }
307 
308     if (event_type & (Process::eBroadcastBitSTDERR | Process::eBroadcastBitStateChanged))
309     {
310         // Drain stderr when we stop just in case we have any bytes
311         while ((len = process.GetSTDERR (stdio_buffer, sizeof (stdio_buffer))) > 0)
312             if (err != NULL)
313                 ::fwrite (stdio_buffer, 1, len, err);
314     }
315 
316     if (event_type & Process::eBroadcastBitStateChanged)
317     {
318         StateType event_state = SBProcess::GetStateFromEvent (event);
319 
320         if (event_state == eStateInvalid)
321             return;
322 
323         bool is_stopped = StateIsStoppedState (event_state);
324         if (!is_stopped)
325             process.ReportEventState (event, out);
326     }
327 }
328 
329 SBSourceManager &
330 SBDebugger::GetSourceManager ()
331 {
332     static SourceManager g_lldb_source_manager;
333     static SBSourceManager g_sb_source_manager (&g_lldb_source_manager);
334     return g_sb_source_manager;
335 }
336 
337 
338 bool
339 SBDebugger::GetDefaultArchitecture (char *arch_name, size_t arch_name_len)
340 {
341     if (arch_name && arch_name_len)
342     {
343         ArchSpec default_arch = Target::GetDefaultArchitecture ();
344 
345         if (default_arch.IsValid())
346         {
347             const std::string &triple_str = default_arch.GetTriple().str();
348             if (!triple_str.empty())
349                 ::snprintf (arch_name, arch_name_len, "%s", triple_str.c_str());
350             else
351                 ::snprintf (arch_name, arch_name_len, "%s", default_arch.GetArchitectureName());
352             return true;
353         }
354     }
355     if (arch_name && arch_name_len)
356         arch_name[0] = '\0';
357     return false;
358 }
359 
360 
361 bool
362 SBDebugger::SetDefaultArchitecture (const char *arch_name)
363 {
364     if (arch_name)
365     {
366         ArchSpec arch (arch_name, NULL);
367         if (arch.IsValid())
368         {
369             Target::SetDefaultArchitecture (arch);
370             return true;
371         }
372     }
373     return false;
374 }
375 
376 ScriptLanguage
377 SBDebugger::GetScriptingLanguage (const char *script_language_name)
378 {
379 
380     return Args::StringToScriptLanguage (script_language_name,
381                                          eScriptLanguageDefault,
382                                          NULL);
383 }
384 
385 const char *
386 SBDebugger::GetVersionString ()
387 {
388     return GetVersion();
389 }
390 
391 const char *
392 SBDebugger::StateAsCString (StateType state)
393 {
394     return lldb_private::StateAsCString (state);
395 }
396 
397 bool
398 SBDebugger::StateIsRunningState (StateType state)
399 {
400     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
401 
402     const bool result = lldb_private::StateIsRunningState (state);
403     if (log)
404         log->Printf ("SBDebugger::StateIsRunningState (state=%s) => %i",
405                      StateAsCString (state), result);
406 
407     return result;
408 }
409 
410 bool
411 SBDebugger::StateIsStoppedState (StateType state)
412 {
413     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
414 
415     const bool result = lldb_private::StateIsStoppedState (state);
416     if (log)
417         log->Printf ("SBDebugger::StateIsStoppedState (state=%s) => %i",
418                      StateAsCString (state), result);
419 
420     return result;
421 }
422 
423 
424 SBTarget
425 SBDebugger::CreateTargetWithFileAndTargetTriple (const char *filename,
426                                                  const char *target_triple)
427 {
428     SBTarget target;
429     if (m_opaque_sp)
430     {
431         ArchSpec arch;
432         FileSpec file_spec (filename, true);
433         arch.SetTriple (target_triple, m_opaque_sp->GetPlatformList().GetSelectedPlatform().get());
434         TargetSP target_sp;
435         Error error (m_opaque_sp->GetTargetList().CreateTarget (*m_opaque_sp, file_spec, arch, true, target_sp));
436         target.reset (target_sp);
437     }
438 
439     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
440     if (log)
441     {
442         log->Printf ("SBDebugger(%p)::CreateTargetWithFileAndTargetTriple (filename=\"%s\", triple=%s) => SBTarget(%p)",
443                      m_opaque_sp.get(), filename, target_triple, target.get());
444     }
445 
446     return target;
447 }
448 
449 SBTarget
450 SBDebugger::CreateTargetWithFileAndArch (const char *filename, const char *arch_cstr)
451 {
452     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
453 
454     SBTarget target;
455     if (m_opaque_sp)
456     {
457         FileSpec file (filename, true);
458         ArchSpec arch;
459         TargetSP target_sp;
460         Error error;
461 
462         if (arch_cstr)
463             arch.SetTriple (arch_cstr, m_opaque_sp->GetPlatformList().GetSelectedPlatform().get());
464 
465         error = m_opaque_sp->GetTargetList().CreateTarget (*m_opaque_sp, file, arch, true, target_sp);
466 
467         if (error.Success())
468         {
469             m_opaque_sp->GetTargetList().SetSelectedTarget (target_sp.get());
470             target.reset(target_sp);
471         }
472     }
473 
474     if (log)
475     {
476         log->Printf ("SBDebugger(%p)::CreateTargetWithFileAndArch (filename=\"%s\", arch=%s) => SBTarget(%p)",
477                      m_opaque_sp.get(), filename, arch_cstr, target.get());
478     }
479 
480     return target;
481 }
482 
483 SBTarget
484 SBDebugger::CreateTarget (const char *filename)
485 {
486     SBTarget target;
487     if (m_opaque_sp)
488     {
489         FileSpec file (filename, true);
490         ArchSpec arch = Target::GetDefaultArchitecture ();
491         TargetSP target_sp;
492         Error error;
493 
494         error = m_opaque_sp->GetTargetList().CreateTarget (*m_opaque_sp, file, arch, true, target_sp);
495 
496         if (error.Success())
497         {
498             m_opaque_sp->GetTargetList().SetSelectedTarget (target_sp.get());
499             target.reset (target_sp);
500         }
501     }
502     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
503     if (log)
504     {
505         log->Printf ("SBDebugger(%p)::CreateTarget (filename=\"%s\") => SBTarget(%p)",
506                      m_opaque_sp.get(), filename, target.get());
507     }
508     return target;
509 }
510 
511 SBTarget
512 SBDebugger::GetTargetAtIndex (uint32_t idx)
513 {
514     SBTarget sb_target;
515     if (m_opaque_sp)
516     {
517         // No need to lock, the target list is thread safe
518         sb_target.reset(m_opaque_sp->GetTargetList().GetTargetAtIndex (idx));
519     }
520     return sb_target;
521 }
522 
523 SBTarget
524 SBDebugger::FindTargetWithProcessID (pid_t pid)
525 {
526     SBTarget sb_target;
527     if (m_opaque_sp)
528     {
529         // No need to lock, the target list is thread safe
530         sb_target.reset(m_opaque_sp->GetTargetList().FindTargetWithProcessID (pid));
531     }
532     return sb_target;
533 }
534 
535 SBTarget
536 SBDebugger::FindTargetWithFileAndArch (const char *filename, const char *arch_name)
537 {
538     SBTarget sb_target;
539     if (m_opaque_sp && filename && filename[0])
540     {
541         // No need to lock, the target list is thread safe
542         ArchSpec arch (arch_name, m_opaque_sp->GetPlatformList().GetSelectedPlatform().get());
543         TargetSP target_sp (m_opaque_sp->GetTargetList().FindTargetWithExecutableAndArchitecture (FileSpec(filename, false), arch_name ? &arch : NULL));
544         sb_target.reset(target_sp);
545     }
546     return sb_target;
547 }
548 
549 SBTarget
550 SBDebugger::FindTargetWithLLDBProcess (const ProcessSP &process_sp)
551 {
552     SBTarget sb_target;
553     if (m_opaque_sp)
554     {
555         // No need to lock, the target list is thread safe
556         sb_target.reset(m_opaque_sp->GetTargetList().FindTargetWithProcess (process_sp.get()));
557     }
558     return sb_target;
559 }
560 
561 
562 uint32_t
563 SBDebugger::GetNumTargets ()
564 {
565     if (m_opaque_sp)
566     {
567         // No need to lock, the target list is thread safe
568         return m_opaque_sp->GetTargetList().GetNumTargets ();
569     }
570     return 0;
571 }
572 
573 SBTarget
574 SBDebugger::GetSelectedTarget ()
575 {
576     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
577 
578     SBTarget sb_target;
579     if (m_opaque_sp)
580     {
581         // No need to lock, the target list is thread safe
582         sb_target.reset(m_opaque_sp->GetTargetList().GetSelectedTarget ());
583     }
584 
585     if (log)
586     {
587         SBStream sstr;
588         sb_target.GetDescription (sstr, eDescriptionLevelBrief);
589         log->Printf ("SBDebugger(%p)::GetSelectedTarget () => SBTarget(%p): %s", m_opaque_sp.get(),
590                      sb_target.get(), sstr.GetData());
591     }
592 
593     return sb_target;
594 }
595 
596 void
597 SBDebugger::DispatchInput (void *baton, const void *data, size_t data_len)
598 {
599     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
600 
601     if (log)
602         log->Printf ("SBDebugger(%p)::DispatchInput (baton=%p, data=\"%.*s\", size_t=%zu)", m_opaque_sp.get(),
603                      baton, (int) data_len, (const char *) data, data_len);
604 
605     if (m_opaque_sp)
606         m_opaque_sp->DispatchInput ((const char *) data, data_len);
607 }
608 
609 void
610 SBDebugger::DispatchInputInterrupt ()
611 {
612     if (m_opaque_sp)
613         m_opaque_sp->DispatchInputInterrupt ();
614 }
615 
616 void
617 SBDebugger::DispatchInputEndOfFile ()
618 {
619     if (m_opaque_sp)
620         m_opaque_sp->DispatchInputEndOfFile ();
621 }
622 
623 void
624 SBDebugger::PushInputReader (SBInputReader &reader)
625 {
626     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
627 
628     if (log)
629         log->Printf ("SBDebugger(%p)::PushInputReader (SBInputReader(%p))", m_opaque_sp.get(), &reader);
630 
631     if (m_opaque_sp && reader.IsValid())
632     {
633         TargetSP target_sp (m_opaque_sp->GetSelectedTarget());
634         Mutex::Locker api_locker;
635         if (target_sp)
636             api_locker.Reset(target_sp->GetAPIMutex().GetMutex());
637         InputReaderSP reader_sp(*reader);
638         m_opaque_sp->PushInputReader (reader_sp);
639     }
640 }
641 
642 void
643 SBDebugger::NotifyTopInputReader (InputReaderAction notification)
644 {
645     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
646 
647     if (log)
648         log->Printf ("SBDebugger(%p)::NotifyTopInputReader (%d)", m_opaque_sp.get(), notification);
649 
650     if (m_opaque_sp)
651         m_opaque_sp->NotifyTopInputReader (notification);
652 }
653 
654 void
655 SBDebugger::reset (const DebuggerSP &debugger_sp)
656 {
657     m_opaque_sp = debugger_sp;
658 }
659 
660 Debugger *
661 SBDebugger::get () const
662 {
663     return m_opaque_sp.get();
664 }
665 
666 Debugger &
667 SBDebugger::ref () const
668 {
669     assert (m_opaque_sp.get());
670     return *m_opaque_sp;
671 }
672 
673 
674 SBDebugger
675 SBDebugger::FindDebuggerWithID (int id)
676 {
677     // No need to lock, the debugger list is thread safe
678     SBDebugger sb_debugger;
679     DebuggerSP debugger_sp = Debugger::FindDebuggerWithID (id);
680     if (debugger_sp)
681         sb_debugger.reset (debugger_sp);
682     return sb_debugger;
683 }
684 
685 const char *
686 SBDebugger::GetInstanceName()
687 {
688     if (m_opaque_sp)
689         return m_opaque_sp->GetInstanceName().AsCString();
690     else
691         return NULL;
692 }
693 
694 SBError
695 SBDebugger::SetInternalVariable (const char *var_name, const char *value, const char *debugger_instance_name)
696 {
697     UserSettingsControllerSP root_settings_controller = Debugger::GetSettingsController();
698 
699     Error err = root_settings_controller->SetVariable (var_name,
700                                                        value,
701                                                        eVarSetOperationAssign,
702                                                        true,
703                                                        debugger_instance_name);
704     SBError sb_error;
705     sb_error.SetError (err);
706 
707     return sb_error;
708 }
709 
710 SBStringList
711 SBDebugger::GetInternalVariableValue (const char *var_name, const char *debugger_instance_name)
712 {
713     SBStringList ret_value;
714     SettableVariableType var_type;
715     Error err;
716 
717     UserSettingsControllerSP root_settings_controller = Debugger::GetSettingsController();
718 
719     StringList value = root_settings_controller->GetVariable (var_name, var_type, debugger_instance_name, err);
720 
721     if (err.Success())
722     {
723         for (unsigned i = 0; i != value.GetSize(); ++i)
724             ret_value.AppendString (value.GetStringAtIndex(i));
725     }
726     else
727     {
728         ret_value.AppendString (err.AsCString());
729     }
730 
731 
732     return ret_value;
733 }
734 
735 uint32_t
736 SBDebugger::GetTerminalWidth () const
737 {
738     if (m_opaque_sp)
739         return m_opaque_sp->GetTerminalWidth ();
740     return 0;
741 }
742 
743 void
744 SBDebugger::SetTerminalWidth (uint32_t term_width)
745 {
746     if (m_opaque_sp)
747         m_opaque_sp->SetTerminalWidth (term_width);
748 }
749 
750 const char *
751 SBDebugger::GetPrompt() const
752 {
753     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
754 
755     if (log)
756         log->Printf ("SBDebugger(%p)::GetPrompt () => \"%s\"", m_opaque_sp.get(),
757                      (m_opaque_sp ? m_opaque_sp->GetPrompt() : ""));
758 
759     if (m_opaque_sp)
760         return m_opaque_sp->GetPrompt ();
761     return 0;
762 }
763 
764 void
765 SBDebugger::SetPrompt (const char *prompt)
766 {
767     if (m_opaque_sp)
768         m_opaque_sp->SetPrompt (prompt);
769 }
770 
771 
772 ScriptLanguage
773 SBDebugger::GetScriptLanguage() const
774 {
775     if (m_opaque_sp)
776         return m_opaque_sp->GetScriptLanguage ();
777     return eScriptLanguageNone;
778 }
779 
780 void
781 SBDebugger::SetScriptLanguage (ScriptLanguage script_lang)
782 {
783     if (m_opaque_sp)
784     {
785         m_opaque_sp->SetScriptLanguage (script_lang);
786     }
787 }
788 
789 bool
790 SBDebugger::SetUseExternalEditor (bool value)
791 {
792     if (m_opaque_sp)
793         return m_opaque_sp->SetUseExternalEditor (value);
794     return false;
795 }
796 
797 bool
798 SBDebugger::GetUseExternalEditor ()
799 {
800     if (m_opaque_sp)
801         return m_opaque_sp->GetUseExternalEditor ();
802     return false;
803 }
804 
805 bool
806 SBDebugger::GetDescription (SBStream &description)
807 {
808     if (m_opaque_sp)
809     {
810         const char *name = m_opaque_sp->GetInstanceName().AsCString();
811         user_id_t id = m_opaque_sp->GetID();
812         description.Printf ("Debugger (instance: \"%s\", id: %d)", name, id);
813     }
814     else
815         description.Printf ("No value");
816 
817     return true;
818 }
819 
820 user_id_t
821 SBDebugger::GetID()
822 {
823     if (m_opaque_sp)
824         return m_opaque_sp->GetID();
825     return LLDB_INVALID_UID;
826 }
827 
828 
829 SBError
830 SBDebugger::SetCurrentPlatform (const char *platform_name)
831 {
832     SBError sb_error;
833     if (m_opaque_sp)
834     {
835         PlatformSP platform_sp (Platform::Create (platform_name, sb_error.ref()));
836 
837         if (platform_sp)
838         {
839             bool make_selected = true;
840             m_opaque_sp->GetPlatformList().Append (platform_sp, make_selected);
841         }
842     }
843     return sb_error;
844 }
845 
846