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 bool
512 SBDebugger::DeleteTarget (lldb::SBTarget &target)
513 {
514     bool result = false;
515     if (m_opaque_sp)
516     {
517         // No need to lock, the target list is thread safe
518         result = m_opaque_sp->GetTargetList().DeleteTarget (target.m_opaque_sp);
519     }
520 
521     LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
522     if (log)
523     {
524         log->Printf ("SBDebugger(%p)::DeleteTarget (SBTarget(%p)) => %i", m_opaque_sp.get(), target.m_opaque_sp.get(), result);
525     }
526 
527     return result;
528 }
529 SBTarget
530 SBDebugger::GetTargetAtIndex (uint32_t idx)
531 {
532     SBTarget sb_target;
533     if (m_opaque_sp)
534     {
535         // No need to lock, the target list is thread safe
536         sb_target.reset(m_opaque_sp->GetTargetList().GetTargetAtIndex (idx));
537     }
538     return sb_target;
539 }
540 
541 SBTarget
542 SBDebugger::FindTargetWithProcessID (pid_t pid)
543 {
544     SBTarget sb_target;
545     if (m_opaque_sp)
546     {
547         // No need to lock, the target list is thread safe
548         sb_target.reset(m_opaque_sp->GetTargetList().FindTargetWithProcessID (pid));
549     }
550     return sb_target;
551 }
552 
553 SBTarget
554 SBDebugger::FindTargetWithFileAndArch (const char *filename, const char *arch_name)
555 {
556     SBTarget sb_target;
557     if (m_opaque_sp && filename && filename[0])
558     {
559         // No need to lock, the target list is thread safe
560         ArchSpec arch (arch_name, m_opaque_sp->GetPlatformList().GetSelectedPlatform().get());
561         TargetSP target_sp (m_opaque_sp->GetTargetList().FindTargetWithExecutableAndArchitecture (FileSpec(filename, false), arch_name ? &arch : NULL));
562         sb_target.reset(target_sp);
563     }
564     return sb_target;
565 }
566 
567 SBTarget
568 SBDebugger::FindTargetWithLLDBProcess (const ProcessSP &process_sp)
569 {
570     SBTarget sb_target;
571     if (m_opaque_sp)
572     {
573         // No need to lock, the target list is thread safe
574         sb_target.reset(m_opaque_sp->GetTargetList().FindTargetWithProcess (process_sp.get()));
575     }
576     return sb_target;
577 }
578 
579 
580 uint32_t
581 SBDebugger::GetNumTargets ()
582 {
583     if (m_opaque_sp)
584     {
585         // No need to lock, the target list is thread safe
586         return m_opaque_sp->GetTargetList().GetNumTargets ();
587     }
588     return 0;
589 }
590 
591 SBTarget
592 SBDebugger::GetSelectedTarget ()
593 {
594     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
595 
596     SBTarget sb_target;
597     if (m_opaque_sp)
598     {
599         // No need to lock, the target list is thread safe
600         sb_target.reset(m_opaque_sp->GetTargetList().GetSelectedTarget ());
601     }
602 
603     if (log)
604     {
605         SBStream sstr;
606         sb_target.GetDescription (sstr, eDescriptionLevelBrief);
607         log->Printf ("SBDebugger(%p)::GetSelectedTarget () => SBTarget(%p): %s", m_opaque_sp.get(),
608                      sb_target.get(), sstr.GetData());
609     }
610 
611     return sb_target;
612 }
613 
614 void
615 SBDebugger::DispatchInput (void *baton, const void *data, size_t data_len)
616 {
617     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
618 
619     if (log)
620         log->Printf ("SBDebugger(%p)::DispatchInput (baton=%p, data=\"%.*s\", size_t=%zu)", m_opaque_sp.get(),
621                      baton, (int) data_len, (const char *) data, data_len);
622 
623     if (m_opaque_sp)
624         m_opaque_sp->DispatchInput ((const char *) data, data_len);
625 }
626 
627 void
628 SBDebugger::DispatchInputInterrupt ()
629 {
630     if (m_opaque_sp)
631         m_opaque_sp->DispatchInputInterrupt ();
632 }
633 
634 void
635 SBDebugger::DispatchInputEndOfFile ()
636 {
637     if (m_opaque_sp)
638         m_opaque_sp->DispatchInputEndOfFile ();
639 }
640 
641 bool
642 SBDebugger::InputReaderIsTopReader (const lldb::SBInputReader &reader)
643 {
644     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
645 
646     if (log)
647         log->Printf ("SBDebugger(%p)::InputReaderIsTopReader (SBInputReader(%p))", m_opaque_sp.get(), &reader);
648 
649     if (m_opaque_sp && reader.IsValid())
650     {
651         InputReaderSP reader_sp (*reader);
652         return m_opaque_sp->InputReaderIsTopReader (reader_sp);
653     }
654 
655     return false;
656 }
657 
658 
659 void
660 SBDebugger::PushInputReader (SBInputReader &reader)
661 {
662     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
663 
664     if (log)
665         log->Printf ("SBDebugger(%p)::PushInputReader (SBInputReader(%p))", m_opaque_sp.get(), &reader);
666 
667     if (m_opaque_sp && reader.IsValid())
668     {
669         TargetSP target_sp (m_opaque_sp->GetSelectedTarget());
670         Mutex::Locker api_locker;
671         if (target_sp)
672             api_locker.Reset(target_sp->GetAPIMutex().GetMutex());
673         InputReaderSP reader_sp(*reader);
674         m_opaque_sp->PushInputReader (reader_sp);
675     }
676 }
677 
678 void
679 SBDebugger::NotifyTopInputReader (InputReaderAction notification)
680 {
681     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
682 
683     if (log)
684         log->Printf ("SBDebugger(%p)::NotifyTopInputReader (%d)", m_opaque_sp.get(), notification);
685 
686     if (m_opaque_sp)
687         m_opaque_sp->NotifyTopInputReader (notification);
688 }
689 
690 void
691 SBDebugger::reset (const DebuggerSP &debugger_sp)
692 {
693     m_opaque_sp = debugger_sp;
694 }
695 
696 Debugger *
697 SBDebugger::get () const
698 {
699     return m_opaque_sp.get();
700 }
701 
702 Debugger &
703 SBDebugger::ref () const
704 {
705     assert (m_opaque_sp.get());
706     return *m_opaque_sp;
707 }
708 
709 
710 SBDebugger
711 SBDebugger::FindDebuggerWithID (int id)
712 {
713     // No need to lock, the debugger list is thread safe
714     SBDebugger sb_debugger;
715     DebuggerSP debugger_sp = Debugger::FindDebuggerWithID (id);
716     if (debugger_sp)
717         sb_debugger.reset (debugger_sp);
718     return sb_debugger;
719 }
720 
721 const char *
722 SBDebugger::GetInstanceName()
723 {
724     if (m_opaque_sp)
725         return m_opaque_sp->GetInstanceName().AsCString();
726     else
727         return NULL;
728 }
729 
730 SBError
731 SBDebugger::SetInternalVariable (const char *var_name, const char *value, const char *debugger_instance_name)
732 {
733     UserSettingsControllerSP root_settings_controller = Debugger::GetSettingsController();
734 
735     Error err = root_settings_controller->SetVariable (var_name,
736                                                        value,
737                                                        eVarSetOperationAssign,
738                                                        true,
739                                                        debugger_instance_name);
740     SBError sb_error;
741     sb_error.SetError (err);
742 
743     return sb_error;
744 }
745 
746 SBStringList
747 SBDebugger::GetInternalVariableValue (const char *var_name, const char *debugger_instance_name)
748 {
749     SBStringList ret_value;
750     SettableVariableType var_type;
751     Error err;
752 
753     UserSettingsControllerSP root_settings_controller = Debugger::GetSettingsController();
754 
755     StringList value = root_settings_controller->GetVariable (var_name, var_type, debugger_instance_name, err);
756 
757     if (err.Success())
758     {
759         for (unsigned i = 0; i != value.GetSize(); ++i)
760             ret_value.AppendString (value.GetStringAtIndex(i));
761     }
762     else
763     {
764         ret_value.AppendString (err.AsCString());
765     }
766 
767 
768     return ret_value;
769 }
770 
771 uint32_t
772 SBDebugger::GetTerminalWidth () const
773 {
774     if (m_opaque_sp)
775         return m_opaque_sp->GetTerminalWidth ();
776     return 0;
777 }
778 
779 void
780 SBDebugger::SetTerminalWidth (uint32_t term_width)
781 {
782     if (m_opaque_sp)
783         m_opaque_sp->SetTerminalWidth (term_width);
784 }
785 
786 const char *
787 SBDebugger::GetPrompt() const
788 {
789     LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
790 
791     if (log)
792         log->Printf ("SBDebugger(%p)::GetPrompt () => \"%s\"", m_opaque_sp.get(),
793                      (m_opaque_sp ? m_opaque_sp->GetPrompt() : ""));
794 
795     if (m_opaque_sp)
796         return m_opaque_sp->GetPrompt ();
797     return 0;
798 }
799 
800 void
801 SBDebugger::SetPrompt (const char *prompt)
802 {
803     if (m_opaque_sp)
804         m_opaque_sp->SetPrompt (prompt);
805 }
806 
807 
808 ScriptLanguage
809 SBDebugger::GetScriptLanguage() const
810 {
811     if (m_opaque_sp)
812         return m_opaque_sp->GetScriptLanguage ();
813     return eScriptLanguageNone;
814 }
815 
816 void
817 SBDebugger::SetScriptLanguage (ScriptLanguage script_lang)
818 {
819     if (m_opaque_sp)
820     {
821         m_opaque_sp->SetScriptLanguage (script_lang);
822     }
823 }
824 
825 bool
826 SBDebugger::SetUseExternalEditor (bool value)
827 {
828     if (m_opaque_sp)
829         return m_opaque_sp->SetUseExternalEditor (value);
830     return false;
831 }
832 
833 bool
834 SBDebugger::GetUseExternalEditor ()
835 {
836     if (m_opaque_sp)
837         return m_opaque_sp->GetUseExternalEditor ();
838     return false;
839 }
840 
841 bool
842 SBDebugger::GetDescription (SBStream &description)
843 {
844     if (m_opaque_sp)
845     {
846         const char *name = m_opaque_sp->GetInstanceName().AsCString();
847         user_id_t id = m_opaque_sp->GetID();
848         description.Printf ("Debugger (instance: \"%s\", id: %d)", name, id);
849     }
850     else
851         description.Printf ("No value");
852 
853     return true;
854 }
855 
856 user_id_t
857 SBDebugger::GetID()
858 {
859     if (m_opaque_sp)
860         return m_opaque_sp->GetID();
861     return LLDB_INVALID_UID;
862 }
863 
864 
865 SBError
866 SBDebugger::SetCurrentPlatform (const char *platform_name)
867 {
868     SBError sb_error;
869     if (m_opaque_sp)
870     {
871         PlatformSP platform_sp (Platform::Create (platform_name, sb_error.ref()));
872 
873         if (platform_sp)
874         {
875             bool make_selected = true;
876             m_opaque_sp->GetPlatformList().Append (platform_sp, make_selected);
877         }
878     }
879     return sb_error;
880 }
881 
882 bool
883 SBDebugger::SetCurrentPlatformSDKRoot (const char *sysroot)
884 {
885     if (m_opaque_sp)
886     {
887         PlatformSP platform_sp (m_opaque_sp->GetPlatformList().GetSelectedPlatform());
888 
889         if (platform_sp)
890         {
891             platform_sp->SetSDKRootDirectory (ConstString (sysroot));
892             return true;
893         }
894     }
895     return false;
896 }
897 
898 bool
899 SBDebugger::GetCloseInputOnEOF () const
900 {
901     if (m_opaque_sp)
902         return m_opaque_sp->GetCloseInputOnEOF ();
903     return false;
904 }
905 
906 void
907 SBDebugger::SetCloseInputOnEOF (bool b)
908 {
909     if (m_opaque_sp)
910         m_opaque_sp->SetCloseInputOnEOF (b);
911 }
912