1 //===-- StackFrame.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/lldb-python.h"
11 
12 #include "lldb/Target/StackFrame.h"
13 
14 // C Includes
15 // C++ Includes
16 // Other libraries and framework includes
17 // Project includes
18 #include "lldb/Core/Module.h"
19 #include "lldb/Core/Debugger.h"
20 #include "lldb/Core/Disassembler.h"
21 #include "lldb/Core/Value.h"
22 #include "lldb/Core/ValueObjectVariable.h"
23 #include "lldb/Core/ValueObjectConstResult.h"
24 #include "lldb/Symbol/CompileUnit.h"
25 #include "lldb/Symbol/Function.h"
26 #include "lldb/Symbol/Symbol.h"
27 #include "lldb/Symbol/SymbolContextScope.h"
28 #include "lldb/Symbol/VariableList.h"
29 #include "lldb/Target/ExecutionContext.h"
30 #include "lldb/Target/Process.h"
31 #include "lldb/Target/RegisterContext.h"
32 #include "lldb/Target/Target.h"
33 #include "lldb/Target/Thread.h"
34 
35 using namespace lldb;
36 using namespace lldb_private;
37 
38 // The first bits in the flags are reserved for the SymbolContext::Scope bits
39 // so we know if we have tried to look up information in our internal symbol
40 // context (m_sc) already.
41 #define RESOLVED_FRAME_CODE_ADDR        (uint32_t(eSymbolContextEverything + 1))
42 #define RESOLVED_FRAME_ID_SYMBOL_SCOPE  (RESOLVED_FRAME_CODE_ADDR << 1)
43 #define GOT_FRAME_BASE                  (RESOLVED_FRAME_ID_SYMBOL_SCOPE << 1)
44 #define RESOLVED_VARIABLES              (GOT_FRAME_BASE << 1)
45 #define RESOLVED_GLOBAL_VARIABLES       (RESOLVED_VARIABLES << 1)
46 
47 StackFrame::StackFrame (const ThreadSP &thread_sp,
48                         user_id_t frame_idx,
49                         user_id_t unwind_frame_index,
50                         addr_t cfa,
51                         bool cfa_is_valid,
52                         addr_t pc,
53                         uint32_t stop_id,
54                         bool stop_id_is_valid,
55                         bool is_history_frame,
56                         const SymbolContext *sc_ptr) :
57     m_thread_wp (thread_sp),
58     m_frame_index (frame_idx),
59     m_concrete_frame_index (unwind_frame_index),
60     m_reg_context_sp (),
61     m_id (pc, cfa, NULL),
62     m_frame_code_addr (pc),
63     m_sc (),
64     m_flags (),
65     m_frame_base (),
66     m_frame_base_error (),
67     m_cfa_is_valid (cfa_is_valid),
68     m_stop_id  (stop_id),
69     m_stop_id_is_valid (stop_id_is_valid),
70     m_is_history_frame (is_history_frame),
71     m_variable_list_sp (),
72     m_variable_list_value_objects (),
73     m_disassembly (),
74     m_mutex (Mutex::eMutexTypeRecursive)
75 {
76     // If we don't have a CFA value, use the frame index for our StackID so that recursive
77     // functions properly aren't confused with one another on a history stack.
78     if (m_is_history_frame && m_cfa_is_valid == false)
79     {
80         m_id.SetCFA (m_frame_index);
81     }
82 
83     if (sc_ptr != NULL)
84     {
85         m_sc = *sc_ptr;
86         m_flags.Set(m_sc.GetResolvedMask ());
87     }
88 }
89 
90 StackFrame::StackFrame (const ThreadSP &thread_sp,
91                         user_id_t frame_idx,
92                         user_id_t unwind_frame_index,
93                         const RegisterContextSP &reg_context_sp,
94                         addr_t cfa,
95                         addr_t pc,
96                         const SymbolContext *sc_ptr) :
97     m_thread_wp (thread_sp),
98     m_frame_index (frame_idx),
99     m_concrete_frame_index (unwind_frame_index),
100     m_reg_context_sp (reg_context_sp),
101     m_id (pc, cfa, NULL),
102     m_frame_code_addr (pc),
103     m_sc (),
104     m_flags (),
105     m_frame_base (),
106     m_frame_base_error (),
107     m_cfa_is_valid (true),
108     m_stop_id  (0),
109     m_stop_id_is_valid (false),
110     m_is_history_frame (false),
111     m_variable_list_sp (),
112     m_variable_list_value_objects (),
113     m_disassembly (),
114     m_mutex (Mutex::eMutexTypeRecursive)
115 {
116     if (sc_ptr != NULL)
117     {
118         m_sc = *sc_ptr;
119         m_flags.Set(m_sc.GetResolvedMask ());
120     }
121 
122     if (reg_context_sp && !m_sc.target_sp)
123     {
124         m_sc.target_sp = reg_context_sp->CalculateTarget();
125         if (m_sc.target_sp)
126             m_flags.Set (eSymbolContextTarget);
127     }
128 }
129 
130 StackFrame::StackFrame (const ThreadSP &thread_sp,
131                         user_id_t frame_idx,
132                         user_id_t unwind_frame_index,
133                         const RegisterContextSP &reg_context_sp,
134                         addr_t cfa,
135                         const Address& pc_addr,
136                         const SymbolContext *sc_ptr) :
137     m_thread_wp (thread_sp),
138     m_frame_index (frame_idx),
139     m_concrete_frame_index (unwind_frame_index),
140     m_reg_context_sp (reg_context_sp),
141     m_id (pc_addr.GetLoadAddress (thread_sp->CalculateTarget().get()), cfa, NULL),
142     m_frame_code_addr (pc_addr),
143     m_sc (),
144     m_flags (),
145     m_frame_base (),
146     m_frame_base_error (),
147     m_cfa_is_valid (true),
148     m_stop_id  (0),
149     m_stop_id_is_valid (false),
150     m_is_history_frame (false),
151     m_variable_list_sp (),
152     m_variable_list_value_objects (),
153     m_disassembly (),
154     m_mutex (Mutex::eMutexTypeRecursive)
155 {
156     if (sc_ptr != NULL)
157     {
158         m_sc = *sc_ptr;
159         m_flags.Set(m_sc.GetResolvedMask ());
160     }
161 
162     if (m_sc.target_sp.get() == NULL && reg_context_sp)
163     {
164         m_sc.target_sp = reg_context_sp->CalculateTarget();
165         if (m_sc.target_sp)
166             m_flags.Set (eSymbolContextTarget);
167     }
168 
169     ModuleSP pc_module_sp (pc_addr.GetModule());
170     if (!m_sc.module_sp || m_sc.module_sp != pc_module_sp)
171     {
172         if (pc_module_sp)
173         {
174             m_sc.module_sp = pc_module_sp;
175             m_flags.Set (eSymbolContextModule);
176         }
177         else
178         {
179             m_sc.module_sp.reset();
180         }
181     }
182 }
183 
184 
185 //----------------------------------------------------------------------
186 // Destructor
187 //----------------------------------------------------------------------
188 StackFrame::~StackFrame()
189 {
190 }
191 
192 StackID&
193 StackFrame::GetStackID()
194 {
195     Mutex::Locker locker(m_mutex);
196     // Make sure we have resolved the StackID object's symbol context scope if
197     // we already haven't looked it up.
198 
199     if (m_flags.IsClear (RESOLVED_FRAME_ID_SYMBOL_SCOPE))
200     {
201         if (m_id.GetSymbolContextScope ())
202         {
203             // We already have a symbol context scope, we just don't have our
204             // flag bit set.
205             m_flags.Set (RESOLVED_FRAME_ID_SYMBOL_SCOPE);
206         }
207         else
208         {
209             // Calculate the frame block and use this for the stack ID symbol
210             // context scope if we have one.
211             SymbolContextScope *scope = GetFrameBlock ();
212             if (scope == NULL)
213             {
214                 // We don't have a block, so use the symbol
215                 if (m_flags.IsClear (eSymbolContextSymbol))
216                     GetSymbolContext (eSymbolContextSymbol);
217 
218                 // It is ok if m_sc.symbol is NULL here
219                 scope = m_sc.symbol;
220             }
221             // Set the symbol context scope (the accessor will set the
222             // RESOLVED_FRAME_ID_SYMBOL_SCOPE bit in m_flags).
223             SetSymbolContextScope (scope);
224         }
225     }
226     return m_id;
227 }
228 
229 uint32_t
230 StackFrame::GetFrameIndex () const
231 {
232     ThreadSP thread_sp = GetThread();
233     if (thread_sp)
234         return thread_sp->GetStackFrameList()->GetVisibleStackFrameIndex(m_frame_index);
235     else
236         return m_frame_index;
237 }
238 
239 void
240 StackFrame::SetSymbolContextScope (SymbolContextScope *symbol_scope)
241 {
242     Mutex::Locker locker(m_mutex);
243     m_flags.Set (RESOLVED_FRAME_ID_SYMBOL_SCOPE);
244     m_id.SetSymbolContextScope (symbol_scope);
245 }
246 
247 const Address&
248 StackFrame::GetFrameCodeAddress()
249 {
250     Mutex::Locker locker(m_mutex);
251     if (m_flags.IsClear(RESOLVED_FRAME_CODE_ADDR) && !m_frame_code_addr.IsSectionOffset())
252     {
253         m_flags.Set (RESOLVED_FRAME_CODE_ADDR);
254 
255         // Resolve the PC into a temporary address because if ResolveLoadAddress
256         // fails to resolve the address, it will clear the address object...
257         ThreadSP thread_sp (GetThread());
258         if (thread_sp)
259         {
260             TargetSP target_sp (thread_sp->CalculateTarget());
261             if (target_sp)
262             {
263                 if (m_frame_code_addr.SetOpcodeLoadAddress (m_frame_code_addr.GetOffset(), target_sp.get()))
264                 {
265                     ModuleSP module_sp (m_frame_code_addr.GetModule());
266                     if (module_sp)
267                     {
268                         m_sc.module_sp = module_sp;
269                         m_flags.Set(eSymbolContextModule);
270                     }
271                 }
272             }
273         }
274     }
275     return m_frame_code_addr;
276 }
277 
278 bool
279 StackFrame::ChangePC (addr_t pc)
280 {
281     Mutex::Locker locker(m_mutex);
282     // We can't change the pc value of a history stack frame - it is immutable.
283     if (m_is_history_frame)
284         return false;
285     m_frame_code_addr.SetRawAddress(pc);
286     m_sc.Clear(false);
287     m_flags.Reset(0);
288     ThreadSP thread_sp (GetThread());
289     if (thread_sp)
290         thread_sp->ClearStackFrames ();
291     return true;
292 }
293 
294 const char *
295 StackFrame::Disassemble ()
296 {
297     Mutex::Locker locker(m_mutex);
298     if (m_disassembly.GetSize() == 0)
299     {
300         ExecutionContext exe_ctx (shared_from_this());
301         Target *target = exe_ctx.GetTargetPtr();
302         if (target)
303         {
304             const char *plugin_name = NULL;
305             const char *flavor = NULL;
306             Disassembler::Disassemble (target->GetDebugger(),
307                                        target->GetArchitecture(),
308                                        plugin_name,
309                                        flavor,
310                                        exe_ctx,
311                                        0,
312                                        0,
313                                        0,
314                                        m_disassembly);
315         }
316         if (m_disassembly.GetSize() == 0)
317             return NULL;
318     }
319     return m_disassembly.GetData();
320 }
321 
322 Block *
323 StackFrame::GetFrameBlock ()
324 {
325     if (m_sc.block == NULL && m_flags.IsClear (eSymbolContextBlock))
326         GetSymbolContext (eSymbolContextBlock);
327 
328     if (m_sc.block)
329     {
330         Block *inline_block = m_sc.block->GetContainingInlinedBlock();
331         if (inline_block)
332         {
333             // Use the block with the inlined function info
334             // as the frame block we want this frame to have only the variables
335             // for the inlined function and its non-inlined block child blocks.
336             return inline_block;
337         }
338         else
339         {
340             // This block is not contained withing any inlined function blocks
341             // with so we want to use the top most function block.
342             return &m_sc.function->GetBlock (false);
343         }
344     }
345     return NULL;
346 }
347 
348 //----------------------------------------------------------------------
349 // Get the symbol context if we already haven't done so by resolving the
350 // PC address as much as possible. This way when we pass around a
351 // StackFrame object, everyone will have as much information as
352 // possible and no one will ever have to look things up manually.
353 //----------------------------------------------------------------------
354 const SymbolContext&
355 StackFrame::GetSymbolContext (uint32_t resolve_scope)
356 {
357     Mutex::Locker locker(m_mutex);
358     // Copy our internal symbol context into "sc".
359     if ((m_flags.Get() & resolve_scope) != resolve_scope)
360     {
361         uint32_t resolved = 0;
362 
363         // If the target was requested add that:
364         if (!m_sc.target_sp)
365         {
366             m_sc.target_sp = CalculateTarget();
367             if (m_sc.target_sp)
368                 resolved |= eSymbolContextTarget;
369         }
370 
371 
372         // Resolve our PC to section offset if we haven't already done so
373         // and if we don't have a module. The resolved address section will
374         // contain the module to which it belongs
375         if (!m_sc.module_sp && m_flags.IsClear(RESOLVED_FRAME_CODE_ADDR))
376             GetFrameCodeAddress();
377 
378         // If this is not frame zero, then we need to subtract 1 from the PC
379         // value when doing address lookups since the PC will be on the
380         // instruction following the function call instruction...
381 
382         Address lookup_addr(GetFrameCodeAddress());
383         if (m_frame_index > 0 && lookup_addr.IsValid())
384         {
385             addr_t offset = lookup_addr.GetOffset();
386             if (offset > 0)
387                 lookup_addr.SetOffset(offset - 1);
388         }
389 
390 
391         if (m_sc.module_sp)
392         {
393             // We have something in our stack frame symbol context, lets check
394             // if we haven't already tried to lookup one of those things. If we
395             // haven't then we will do the query.
396 
397             uint32_t actual_resolve_scope = 0;
398 
399             if (resolve_scope & eSymbolContextCompUnit)
400             {
401                 if (m_flags.IsClear (eSymbolContextCompUnit))
402                 {
403                     if (m_sc.comp_unit)
404                         resolved |= eSymbolContextCompUnit;
405                     else
406                         actual_resolve_scope |= eSymbolContextCompUnit;
407                 }
408             }
409 
410             if (resolve_scope & eSymbolContextFunction)
411             {
412                 if (m_flags.IsClear (eSymbolContextFunction))
413                 {
414                     if (m_sc.function)
415                         resolved |= eSymbolContextFunction;
416                     else
417                         actual_resolve_scope |= eSymbolContextFunction;
418                 }
419             }
420 
421             if (resolve_scope & eSymbolContextBlock)
422             {
423                 if (m_flags.IsClear (eSymbolContextBlock))
424                 {
425                     if (m_sc.block)
426                         resolved |= eSymbolContextBlock;
427                     else
428                         actual_resolve_scope |= eSymbolContextBlock;
429                 }
430             }
431 
432             if (resolve_scope & eSymbolContextSymbol)
433             {
434                 if (m_flags.IsClear (eSymbolContextSymbol))
435                 {
436                     if (m_sc.symbol)
437                         resolved |= eSymbolContextSymbol;
438                     else
439                         actual_resolve_scope |= eSymbolContextSymbol;
440                 }
441             }
442 
443             if (resolve_scope & eSymbolContextLineEntry)
444             {
445                 if (m_flags.IsClear (eSymbolContextLineEntry))
446                 {
447                     if (m_sc.line_entry.IsValid())
448                         resolved |= eSymbolContextLineEntry;
449                     else
450                         actual_resolve_scope |= eSymbolContextLineEntry;
451                 }
452             }
453 
454             if (actual_resolve_scope)
455             {
456                 // We might be resolving less information than what is already
457                 // in our current symbol context so resolve into a temporary
458                 // symbol context "sc" so we don't clear out data we have
459                 // already found in "m_sc"
460                 SymbolContext sc;
461                 // Set flags that indicate what we have tried to resolve
462                 resolved |= m_sc.module_sp->ResolveSymbolContextForAddress (lookup_addr, actual_resolve_scope, sc);
463                 // Only replace what we didn't already have as we may have
464                 // information for an inlined function scope that won't match
465                 // what a standard lookup by address would match
466                 if ((resolved & eSymbolContextCompUnit)  && m_sc.comp_unit == NULL)
467                     m_sc.comp_unit = sc.comp_unit;
468                 if ((resolved & eSymbolContextFunction)  && m_sc.function == NULL)
469                     m_sc.function = sc.function;
470                 if ((resolved & eSymbolContextBlock)     && m_sc.block == NULL)
471                     m_sc.block = sc.block;
472                 if ((resolved & eSymbolContextSymbol)    && m_sc.symbol == NULL)
473                     m_sc.symbol = sc.symbol;
474                 if ((resolved & eSymbolContextLineEntry) && !m_sc.line_entry.IsValid())
475                 {
476                     m_sc.line_entry = sc.line_entry;
477                     if (m_sc.target_sp)
478                     {
479                         // Be sure to apply and file remappings to our file and line
480                         // entries when handing out a line entry
481                         FileSpec new_file_spec;
482                         if (m_sc.target_sp->GetSourcePathMap().FindFile (m_sc.line_entry.file, new_file_spec))
483                             m_sc.line_entry.file = new_file_spec;
484                     }
485                 }
486             }
487         }
488         else
489         {
490             // If we don't have a module, then we can't have the compile unit,
491             // function, block, line entry or symbol, so we can safely call
492             // ResolveSymbolContextForAddress with our symbol context member m_sc.
493             if (m_sc.target_sp)
494             {
495                 resolved |= m_sc.target_sp->GetImages().ResolveSymbolContextForAddress (lookup_addr, resolve_scope, m_sc);
496             }
497         }
498 
499         // Update our internal flags so we remember what we have tried to locate so
500         // we don't have to keep trying when more calls to this function are made.
501         // We might have dug up more information that was requested (for example
502         // if we were asked to only get the block, we will have gotten the
503         // compile unit, and function) so set any additional bits that we resolved
504         m_flags.Set (resolve_scope | resolved);
505     }
506 
507     // Return the symbol context with everything that was possible to resolve
508     // resolved.
509     return m_sc;
510 }
511 
512 
513 VariableList *
514 StackFrame::GetVariableList (bool get_file_globals)
515 {
516     Mutex::Locker locker(m_mutex);
517     if (m_flags.IsClear(RESOLVED_VARIABLES))
518     {
519         m_flags.Set(RESOLVED_VARIABLES);
520 
521         Block *frame_block = GetFrameBlock();
522 
523         if (frame_block)
524         {
525             const bool get_child_variables = true;
526             const bool can_create = true;
527             const bool stop_if_child_block_is_inlined_function = true;
528             m_variable_list_sp.reset(new VariableList());
529             frame_block->AppendBlockVariables(can_create, get_child_variables, stop_if_child_block_is_inlined_function, m_variable_list_sp.get());
530         }
531     }
532 
533     if (m_flags.IsClear(RESOLVED_GLOBAL_VARIABLES) &&
534         get_file_globals)
535     {
536         m_flags.Set(RESOLVED_GLOBAL_VARIABLES);
537 
538         if (m_flags.IsClear (eSymbolContextCompUnit))
539             GetSymbolContext (eSymbolContextCompUnit);
540 
541         if (m_sc.comp_unit)
542         {
543             VariableListSP global_variable_list_sp (m_sc.comp_unit->GetVariableList(true));
544             if (m_variable_list_sp)
545                 m_variable_list_sp->AddVariables (global_variable_list_sp.get());
546             else
547                 m_variable_list_sp = global_variable_list_sp;
548         }
549     }
550 
551     return m_variable_list_sp.get();
552 }
553 
554 VariableListSP
555 StackFrame::GetInScopeVariableList (bool get_file_globals)
556 {
557     Mutex::Locker locker(m_mutex);
558     // We can't fetch variable information for a history stack frame.
559     if (m_is_history_frame)
560         return VariableListSP();
561 
562     VariableListSP var_list_sp(new VariableList);
563     GetSymbolContext (eSymbolContextCompUnit | eSymbolContextBlock);
564 
565     if (m_sc.block)
566     {
567         const bool can_create = true;
568         const bool get_parent_variables = true;
569         const bool stop_if_block_is_inlined_function = true;
570         m_sc.block->AppendVariables (can_create,
571                                      get_parent_variables,
572                                      stop_if_block_is_inlined_function,
573                                      var_list_sp.get());
574     }
575 
576     if (m_sc.comp_unit)
577     {
578         VariableListSP global_variable_list_sp (m_sc.comp_unit->GetVariableList(true));
579         if (global_variable_list_sp)
580             var_list_sp->AddVariables (global_variable_list_sp.get());
581     }
582 
583     return var_list_sp;
584 }
585 
586 
587 ValueObjectSP
588 StackFrame::GetValueForVariableExpressionPath (const char *var_expr_cstr,
589                                                DynamicValueType use_dynamic,
590                                                uint32_t options,
591                                                VariableSP &var_sp,
592                                                Error &error)
593 {
594     // We can't fetch variable information for a history stack frame.
595     if (m_is_history_frame)
596         return ValueObjectSP();
597 
598     if (var_expr_cstr && var_expr_cstr[0])
599     {
600         const bool check_ptr_vs_member = (options & eExpressionPathOptionCheckPtrVsMember) != 0;
601         const bool no_fragile_ivar = (options & eExpressionPathOptionsNoFragileObjcIvar) != 0;
602         const bool no_synth_child = (options & eExpressionPathOptionsNoSyntheticChildren) != 0;
603         //const bool no_synth_array = (options & eExpressionPathOptionsNoSyntheticArrayRange) != 0;
604         error.Clear();
605         bool deref = false;
606         bool address_of = false;
607         ValueObjectSP valobj_sp;
608         const bool get_file_globals = true;
609         // When looking up a variable for an expression, we need only consider the
610         // variables that are in scope.
611         VariableListSP var_list_sp (GetInScopeVariableList (get_file_globals));
612         VariableList *variable_list = var_list_sp.get();
613 
614         if (variable_list)
615         {
616             // If first character is a '*', then show pointer contents
617             const char *var_expr = var_expr_cstr;
618             if (var_expr[0] == '*')
619             {
620                 deref = true;
621                 var_expr++; // Skip the '*'
622             }
623             else if (var_expr[0] == '&')
624             {
625                 address_of = true;
626                 var_expr++; // Skip the '&'
627             }
628 
629             std::string var_path (var_expr);
630             size_t separator_idx = var_path.find_first_of(".-[=+~|&^%#@!/?,<>{}");
631             StreamString var_expr_path_strm;
632 
633             ConstString name_const_string;
634             if (separator_idx == std::string::npos)
635                 name_const_string.SetCString (var_path.c_str());
636             else
637                 name_const_string.SetCStringWithLength (var_path.c_str(), separator_idx);
638 
639             var_sp = variable_list->FindVariable(name_const_string);
640 
641             bool synthetically_added_instance_object = false;
642 
643             if (var_sp)
644             {
645                 var_path.erase (0, name_const_string.GetLength ());
646             }
647             else if (options & eExpressionPathOptionsAllowDirectIVarAccess)
648             {
649                 // Check for direct ivars access which helps us with implicit
650                 // access to ivars with the "this->" or "self->"
651                 GetSymbolContext(eSymbolContextFunction|eSymbolContextBlock);
652                 lldb::LanguageType method_language = eLanguageTypeUnknown;
653                 bool is_instance_method = false;
654                 ConstString method_object_name;
655                 if (m_sc.GetFunctionMethodInfo (method_language, is_instance_method, method_object_name))
656                 {
657                     if (is_instance_method && method_object_name)
658                     {
659                         var_sp = variable_list->FindVariable(method_object_name);
660                         if (var_sp)
661                         {
662                             separator_idx = 0;
663                             var_path.insert(0, "->");
664                             synthetically_added_instance_object = true;
665                         }
666                     }
667                 }
668             }
669 
670             if (var_sp)
671             {
672                 valobj_sp = GetValueObjectForFrameVariable (var_sp, use_dynamic);
673                 if (!valobj_sp)
674                     return valobj_sp;
675 
676                 // We are dumping at least one child
677                 while (separator_idx != std::string::npos)
678                 {
679                     // Calculate the next separator index ahead of time
680                     ValueObjectSP child_valobj_sp;
681                     const char separator_type = var_path[0];
682                     switch (separator_type)
683                     {
684 
685                     case '-':
686                         if (var_path.size() >= 2 && var_path[1] != '>')
687                             return ValueObjectSP();
688 
689                         if (no_fragile_ivar)
690                         {
691                             // Make sure we aren't trying to deref an objective
692                             // C ivar if this is not allowed
693                             const uint32_t pointer_type_flags = valobj_sp->GetClangType().GetTypeInfo (NULL);
694                             if ((pointer_type_flags & ClangASTType::eTypeIsObjC) &&
695                                 (pointer_type_flags & ClangASTType::eTypeIsPointer))
696                             {
697                                 // This was an objective C object pointer and
698                                 // it was requested we skip any fragile ivars
699                                 // so return nothing here
700                                 return ValueObjectSP();
701                             }
702                         }
703                         var_path.erase (0, 1); // Remove the '-'
704                         // Fall through
705                     case '.':
706                         {
707                             const bool expr_is_ptr = var_path[0] == '>';
708 
709                             var_path.erase (0, 1); // Remove the '.' or '>'
710                             separator_idx = var_path.find_first_of(".-[");
711                             ConstString child_name;
712                             if (separator_idx == std::string::npos)
713                                 child_name.SetCString (var_path.c_str());
714                             else
715                                 child_name.SetCStringWithLength(var_path.c_str(), separator_idx);
716 
717                             if (check_ptr_vs_member)
718                             {
719                                 // We either have a pointer type and need to verify
720                                 // valobj_sp is a pointer, or we have a member of a
721                                 // class/union/struct being accessed with the . syntax
722                                 // and need to verify we don't have a pointer.
723                                 const bool actual_is_ptr = valobj_sp->IsPointerType ();
724 
725                                 if (actual_is_ptr != expr_is_ptr)
726                                 {
727                                     // Incorrect use of "." with a pointer, or "->" with
728                                     // a class/union/struct instance or reference.
729                                     valobj_sp->GetExpressionPath (var_expr_path_strm, false);
730                                     if (actual_is_ptr)
731                                         error.SetErrorStringWithFormat ("\"%s\" is a pointer and . was used to attempt to access \"%s\". Did you mean \"%s->%s\"?",
732                                                                         var_expr_path_strm.GetString().c_str(),
733                                                                         child_name.GetCString(),
734                                                                         var_expr_path_strm.GetString().c_str(),
735                                                                         var_path.c_str());
736                                     else
737                                         error.SetErrorStringWithFormat ("\"%s\" is not a pointer and -> was used to attempt to access \"%s\". Did you mean \"%s.%s\"?",
738                                                                         var_expr_path_strm.GetString().c_str(),
739                                                                         child_name.GetCString(),
740                                                                         var_expr_path_strm.GetString().c_str(),
741                                                                         var_path.c_str());
742                                     return ValueObjectSP();
743                                 }
744                             }
745                             child_valobj_sp = valobj_sp->GetChildMemberWithName (child_name, true);
746                             if (!child_valobj_sp)
747                             {
748                                 if (no_synth_child == false)
749                                 {
750                                     child_valobj_sp = valobj_sp->GetSyntheticValue();
751                                     if (child_valobj_sp)
752                                         child_valobj_sp = child_valobj_sp->GetChildMemberWithName (child_name, true);
753                                 }
754 
755                                 if (no_synth_child || !child_valobj_sp)
756                                 {
757                                     // No child member with name "child_name"
758                                     if (synthetically_added_instance_object)
759                                     {
760                                         // We added a "this->" or "self->" to the beginning of the expression
761                                         // and this is the first pointer ivar access, so just return the normal
762                                         // error
763                                         error.SetErrorStringWithFormat("no variable or instance variable named '%s' found in this frame",
764                                                                        name_const_string.GetCString());
765                                     }
766                                     else
767                                     {
768                                         valobj_sp->GetExpressionPath (var_expr_path_strm, false);
769                                         if (child_name)
770                                         {
771                                             error.SetErrorStringWithFormat ("\"%s\" is not a member of \"(%s) %s\"",
772                                                                             child_name.GetCString(),
773                                                                             valobj_sp->GetTypeName().AsCString("<invalid type>"),
774                                                                             var_expr_path_strm.GetString().c_str());
775                                         }
776                                         else
777                                         {
778                                             error.SetErrorStringWithFormat ("incomplete expression path after \"%s\" in \"%s\"",
779                                                                             var_expr_path_strm.GetString().c_str(),
780                                                                             var_expr_cstr);
781                                         }
782                                     }
783                                     return ValueObjectSP();
784                                 }
785                             }
786                             synthetically_added_instance_object = false;
787                             // Remove the child name from the path
788                             var_path.erase(0, child_name.GetLength());
789                             if (use_dynamic != eNoDynamicValues)
790                             {
791                                 ValueObjectSP dynamic_value_sp(child_valobj_sp->GetDynamicValue(use_dynamic));
792                                 if (dynamic_value_sp)
793                                     child_valobj_sp = dynamic_value_sp;
794                             }
795                         }
796                         break;
797 
798                     case '[':
799                         // Array member access, or treating pointer as an array
800                         if (var_path.size() > 2) // Need at least two brackets and a number
801                         {
802                             char *end = NULL;
803                             long child_index = ::strtol (&var_path[1], &end, 0);
804                             if (end && *end == ']'
805                                 && *(end-1) != '[') // this code forces an error in the case of arr[]. as bitfield[] is not a good syntax we're good to go
806                             {
807                                 if (valobj_sp->GetClangType().IsPointerToScalarType() && deref)
808                                 {
809                                     // what we have is *ptr[low]. the most similar C++ syntax is to deref ptr
810                                     // and extract bit low out of it. reading array item low
811                                     // would be done by saying ptr[low], without a deref * sign
812                                     Error error;
813                                     ValueObjectSP temp(valobj_sp->Dereference(error));
814                                     if (error.Fail())
815                                     {
816                                         valobj_sp->GetExpressionPath (var_expr_path_strm, false);
817                                         error.SetErrorStringWithFormat ("could not dereference \"(%s) %s\"",
818                                                                         valobj_sp->GetTypeName().AsCString("<invalid type>"),
819                                                                         var_expr_path_strm.GetString().c_str());
820                                         return ValueObjectSP();
821                                     }
822                                     valobj_sp = temp;
823                                     deref = false;
824                                 }
825                                 else if (valobj_sp->GetClangType().IsArrayOfScalarType() && deref)
826                                 {
827                                     // what we have is *arr[low]. the most similar C++ syntax is to get arr[0]
828                                     // (an operation that is equivalent to deref-ing arr)
829                                     // and extract bit low out of it. reading array item low
830                                     // would be done by saying arr[low], without a deref * sign
831                                     Error error;
832                                     ValueObjectSP temp(valobj_sp->GetChildAtIndex (0, true));
833                                     if (error.Fail())
834                                     {
835                                         valobj_sp->GetExpressionPath (var_expr_path_strm, false);
836                                         error.SetErrorStringWithFormat ("could not get item 0 for \"(%s) %s\"",
837                                                                         valobj_sp->GetTypeName().AsCString("<invalid type>"),
838                                                                         var_expr_path_strm.GetString().c_str());
839                                         return ValueObjectSP();
840                                     }
841                                     valobj_sp = temp;
842                                     deref = false;
843                                 }
844 
845                                 bool is_incomplete_array = false;
846                                 if (valobj_sp->IsPointerType ())
847                                 {
848                                     bool is_objc_pointer = true;
849 
850                                     if (valobj_sp->GetClangType().GetMinimumLanguage() != eLanguageTypeObjC)
851                                         is_objc_pointer = false;
852                                     else if (!valobj_sp->GetClangType().IsPointerType())
853                                         is_objc_pointer = false;
854 
855                                     if (no_synth_child && is_objc_pointer)
856                                     {
857                                         error.SetErrorStringWithFormat("\"(%s) %s\" is an Objective-C pointer, and cannot be subscripted",
858                                                                        valobj_sp->GetTypeName().AsCString("<invalid type>"),
859                                                                        var_expr_path_strm.GetString().c_str());
860 
861                                         return ValueObjectSP();
862                                     }
863                                     else if (is_objc_pointer)
864                                     {
865                                         // dereferencing ObjC variables is not valid.. so let's try and recur to synthetic children
866                                         ValueObjectSP synthetic = valobj_sp->GetSyntheticValue();
867                                         if (synthetic.get() == NULL /* no synthetic */
868                                             || synthetic == valobj_sp) /* synthetic is the same as the original object */
869                                         {
870                                             valobj_sp->GetExpressionPath (var_expr_path_strm, false);
871                                             error.SetErrorStringWithFormat ("\"(%s) %s\" is not an array type",
872                                                                             valobj_sp->GetTypeName().AsCString("<invalid type>"),
873                                                                             var_expr_path_strm.GetString().c_str());
874                                         }
875                                         else if (static_cast<uint32_t>(child_index) >= synthetic->GetNumChildren() /* synthetic does not have that many values */)
876                                         {
877                                             valobj_sp->GetExpressionPath (var_expr_path_strm, false);
878                                             error.SetErrorStringWithFormat ("array index %ld is not valid for \"(%s) %s\"",
879                                                                             child_index,
880                                                                             valobj_sp->GetTypeName().AsCString("<invalid type>"),
881                                                                             var_expr_path_strm.GetString().c_str());
882                                         }
883                                         else
884                                         {
885                                             child_valobj_sp = synthetic->GetChildAtIndex(child_index, true);
886                                             if (!child_valobj_sp)
887                                             {
888                                                 valobj_sp->GetExpressionPath (var_expr_path_strm, false);
889                                                 error.SetErrorStringWithFormat ("array index %ld is not valid for \"(%s) %s\"",
890                                                                                 child_index,
891                                                                                 valobj_sp->GetTypeName().AsCString("<invalid type>"),
892                                                                                 var_expr_path_strm.GetString().c_str());
893                                             }
894                                         }
895                                     }
896                                     else
897                                     {
898                                         child_valobj_sp = valobj_sp->GetSyntheticArrayMemberFromPointer (child_index, true);
899                                         if (!child_valobj_sp)
900                                         {
901                                             valobj_sp->GetExpressionPath (var_expr_path_strm, false);
902                                             error.SetErrorStringWithFormat ("failed to use pointer as array for index %ld for \"(%s) %s\"",
903                                                                             child_index,
904                                                                             valobj_sp->GetTypeName().AsCString("<invalid type>"),
905                                                                             var_expr_path_strm.GetString().c_str());
906                                         }
907                                     }
908                                 }
909                                 else if (valobj_sp->GetClangType().IsArrayType (NULL, NULL, &is_incomplete_array))
910                                 {
911                                     // Pass false to dynamic_value here so we can tell the difference between
912                                     // no dynamic value and no member of this type...
913                                     child_valobj_sp = valobj_sp->GetChildAtIndex (child_index, true);
914                                     if (!child_valobj_sp && (is_incomplete_array || no_synth_child == false))
915                                         child_valobj_sp = valobj_sp->GetSyntheticArrayMember (child_index, true);
916 
917                                     if (!child_valobj_sp)
918                                     {
919                                         valobj_sp->GetExpressionPath (var_expr_path_strm, false);
920                                         error.SetErrorStringWithFormat ("array index %ld is not valid for \"(%s) %s\"",
921                                                                         child_index,
922                                                                         valobj_sp->GetTypeName().AsCString("<invalid type>"),
923                                                                         var_expr_path_strm.GetString().c_str());
924                                     }
925                                 }
926                                 else if (valobj_sp->GetClangType().IsScalarType())
927                                 {
928                                     // this is a bitfield asking to display just one bit
929                                     child_valobj_sp = valobj_sp->GetSyntheticBitFieldChild(child_index, child_index, true);
930                                     if (!child_valobj_sp)
931                                     {
932                                         valobj_sp->GetExpressionPath (var_expr_path_strm, false);
933                                         error.SetErrorStringWithFormat ("bitfield range %ld-%ld is not valid for \"(%s) %s\"",
934                                                                         child_index, child_index,
935                                                                         valobj_sp->GetTypeName().AsCString("<invalid type>"),
936                                                                         var_expr_path_strm.GetString().c_str());
937                                     }
938                                 }
939                                 else
940                                 {
941                                     ValueObjectSP synthetic = valobj_sp->GetSyntheticValue();
942                                     if (no_synth_child /* synthetic is forbidden */ ||
943                                         synthetic.get() == NULL /* no synthetic */
944                                         || synthetic == valobj_sp) /* synthetic is the same as the original object */
945                                     {
946                                         valobj_sp->GetExpressionPath (var_expr_path_strm, false);
947                                         error.SetErrorStringWithFormat ("\"(%s) %s\" is not an array type",
948                                                                         valobj_sp->GetTypeName().AsCString("<invalid type>"),
949                                                                         var_expr_path_strm.GetString().c_str());
950                                     }
951                                     else if (static_cast<uint32_t>(child_index) >= synthetic->GetNumChildren() /* synthetic does not have that many values */)
952                                     {
953                                         valobj_sp->GetExpressionPath (var_expr_path_strm, false);
954                                         error.SetErrorStringWithFormat ("array index %ld is not valid for \"(%s) %s\"",
955                                                                         child_index,
956                                                                         valobj_sp->GetTypeName().AsCString("<invalid type>"),
957                                                                         var_expr_path_strm.GetString().c_str());
958                                     }
959                                     else
960                                     {
961                                         child_valobj_sp = synthetic->GetChildAtIndex(child_index, true);
962                                         if (!child_valobj_sp)
963                                         {
964                                             valobj_sp->GetExpressionPath (var_expr_path_strm, false);
965                                             error.SetErrorStringWithFormat ("array index %ld is not valid for \"(%s) %s\"",
966                                                                             child_index,
967                                                                             valobj_sp->GetTypeName().AsCString("<invalid type>"),
968                                                                             var_expr_path_strm.GetString().c_str());
969                                         }
970                                     }
971                                 }
972 
973                                 if (!child_valobj_sp)
974                                 {
975                                     // Invalid array index...
976                                     return ValueObjectSP();
977                                 }
978 
979                                 // Erase the array member specification '[%i]' where
980                                 // %i is the array index
981                                 var_path.erase(0, (end - var_path.c_str()) + 1);
982                                 separator_idx = var_path.find_first_of(".-[");
983                                 if (use_dynamic != eNoDynamicValues)
984                                 {
985                                     ValueObjectSP dynamic_value_sp(child_valobj_sp->GetDynamicValue(use_dynamic));
986                                     if (dynamic_value_sp)
987                                         child_valobj_sp = dynamic_value_sp;
988                                 }
989                                 // Break out early from the switch since we were
990                                 // able to find the child member
991                                 break;
992                             }
993                             else if (end && *end == '-')
994                             {
995                                 // this is most probably a BitField, let's take a look
996                                 char *real_end = NULL;
997                                 long final_index = ::strtol (end+1, &real_end, 0);
998                                 bool expand_bitfield = true;
999                                 if (real_end && *real_end == ']')
1000                                 {
1001                                     // if the format given is [high-low], swap range
1002                                     if (child_index > final_index)
1003                                     {
1004                                         long temp = child_index;
1005                                         child_index = final_index;
1006                                         final_index = temp;
1007                                     }
1008 
1009                                     if (valobj_sp->GetClangType().IsPointerToScalarType() && deref)
1010                                     {
1011                                         // what we have is *ptr[low-high]. the most similar C++ syntax is to deref ptr
1012                                         // and extract bits low thru high out of it. reading array items low thru high
1013                                         // would be done by saying ptr[low-high], without a deref * sign
1014                                         Error error;
1015                                         ValueObjectSP temp(valobj_sp->Dereference(error));
1016                                         if (error.Fail())
1017                                         {
1018                                             valobj_sp->GetExpressionPath (var_expr_path_strm, false);
1019                                             error.SetErrorStringWithFormat ("could not dereference \"(%s) %s\"",
1020                                                                             valobj_sp->GetTypeName().AsCString("<invalid type>"),
1021                                                                             var_expr_path_strm.GetString().c_str());
1022                                             return ValueObjectSP();
1023                                         }
1024                                         valobj_sp = temp;
1025                                         deref = false;
1026                                     }
1027                                     else if (valobj_sp->GetClangType().IsArrayOfScalarType() && deref)
1028                                     {
1029                                         // what we have is *arr[low-high]. the most similar C++ syntax is to get arr[0]
1030                                         // (an operation that is equivalent to deref-ing arr)
1031                                         // and extract bits low thru high out of it. reading array items low thru high
1032                                         // would be done by saying arr[low-high], without a deref * sign
1033                                         Error error;
1034                                         ValueObjectSP temp(valobj_sp->GetChildAtIndex (0, true));
1035                                         if (error.Fail())
1036                                         {
1037                                             valobj_sp->GetExpressionPath (var_expr_path_strm, false);
1038                                             error.SetErrorStringWithFormat ("could not get item 0 for \"(%s) %s\"",
1039                                                                             valobj_sp->GetTypeName().AsCString("<invalid type>"),
1040                                                                             var_expr_path_strm.GetString().c_str());
1041                                             return ValueObjectSP();
1042                                         }
1043                                         valobj_sp = temp;
1044                                         deref = false;
1045                                     }
1046                                     /*else if (valobj_sp->IsArrayType() || valobj_sp->IsPointerType())
1047                                     {
1048                                         child_valobj_sp = valobj_sp->GetSyntheticArrayRangeChild(child_index, final_index, true);
1049                                         expand_bitfield = false;
1050                                         if (!child_valobj_sp)
1051                                         {
1052                                             valobj_sp->GetExpressionPath (var_expr_path_strm, false);
1053                                             error.SetErrorStringWithFormat ("array range %i-%i is not valid for \"(%s) %s\"",
1054                                                                             child_index, final_index,
1055                                                                             valobj_sp->GetTypeName().AsCString("<invalid type>"),
1056                                                                             var_expr_path_strm.GetString().c_str());
1057                                         }
1058                                     }*/
1059 
1060                                     if (expand_bitfield)
1061                                     {
1062                                         child_valobj_sp = valobj_sp->GetSyntheticBitFieldChild(child_index, final_index, true);
1063                                         if (!child_valobj_sp)
1064                                         {
1065                                             valobj_sp->GetExpressionPath (var_expr_path_strm, false);
1066                                             error.SetErrorStringWithFormat ("bitfield range %ld-%ld is not valid for \"(%s) %s\"",
1067                                                                             child_index, final_index,
1068                                                                             valobj_sp->GetTypeName().AsCString("<invalid type>"),
1069                                                                             var_expr_path_strm.GetString().c_str());
1070                                         }
1071                                     }
1072                                 }
1073 
1074                                 if (!child_valobj_sp)
1075                                 {
1076                                     // Invalid bitfield range...
1077                                     return ValueObjectSP();
1078                                 }
1079 
1080                                 // Erase the bitfield member specification '[%i-%i]' where
1081                                 // %i is the index
1082                                 var_path.erase(0, (real_end - var_path.c_str()) + 1);
1083                                 separator_idx = var_path.find_first_of(".-[");
1084                                 if (use_dynamic != eNoDynamicValues)
1085                                 {
1086                                     ValueObjectSP dynamic_value_sp(child_valobj_sp->GetDynamicValue(use_dynamic));
1087                                     if (dynamic_value_sp)
1088                                         child_valobj_sp = dynamic_value_sp;
1089                                 }
1090                                 // Break out early from the switch since we were
1091                                 // able to find the child member
1092                                 break;
1093 
1094                             }
1095                         }
1096                         else
1097                         {
1098                             error.SetErrorStringWithFormat("invalid square bracket encountered after \"%s\" in \"%s\"",
1099                                                            var_expr_path_strm.GetString().c_str(),
1100                                                            var_path.c_str());
1101                         }
1102                         return ValueObjectSP();
1103 
1104                     default:
1105                         // Failure...
1106                         {
1107                             valobj_sp->GetExpressionPath (var_expr_path_strm, false);
1108                             error.SetErrorStringWithFormat ("unexpected char '%c' encountered after \"%s\" in \"%s\"",
1109                                                             separator_type,
1110                                                             var_expr_path_strm.GetString().c_str(),
1111                                                             var_path.c_str());
1112 
1113                             return ValueObjectSP();
1114                         }
1115                     }
1116 
1117                     if (child_valobj_sp)
1118                         valobj_sp = child_valobj_sp;
1119 
1120                     if (var_path.empty())
1121                         break;
1122 
1123                 }
1124                 if (valobj_sp)
1125                 {
1126                     if (deref)
1127                     {
1128                         ValueObjectSP deref_valobj_sp (valobj_sp->Dereference(error));
1129                         valobj_sp = deref_valobj_sp;
1130                     }
1131                     else if (address_of)
1132                     {
1133                         ValueObjectSP address_of_valobj_sp (valobj_sp->AddressOf(error));
1134                         valobj_sp = address_of_valobj_sp;
1135                     }
1136                 }
1137                 return valobj_sp;
1138             }
1139             else
1140             {
1141                 error.SetErrorStringWithFormat("no variable named '%s' found in this frame",
1142                                                name_const_string.GetCString());
1143             }
1144         }
1145     }
1146     else
1147     {
1148         error.SetErrorStringWithFormat("invalid variable path '%s'", var_expr_cstr);
1149     }
1150     return ValueObjectSP();
1151 }
1152 
1153 bool
1154 StackFrame::GetFrameBaseValue (Scalar &frame_base, Error *error_ptr)
1155 {
1156     Mutex::Locker locker(m_mutex);
1157     if (m_cfa_is_valid == false)
1158     {
1159         m_frame_base_error.SetErrorString("No frame base available for this historical stack frame.");
1160         return false;
1161     }
1162 
1163     if (m_flags.IsClear(GOT_FRAME_BASE))
1164     {
1165         if (m_sc.function)
1166         {
1167             m_frame_base.Clear();
1168             m_frame_base_error.Clear();
1169 
1170             m_flags.Set(GOT_FRAME_BASE);
1171             ExecutionContext exe_ctx (shared_from_this());
1172             Value expr_value;
1173             addr_t loclist_base_addr = LLDB_INVALID_ADDRESS;
1174             if (m_sc.function->GetFrameBaseExpression().IsLocationList())
1175                 loclist_base_addr = m_sc.function->GetAddressRange().GetBaseAddress().GetLoadAddress (exe_ctx.GetTargetPtr());
1176 
1177             if (m_sc.function->GetFrameBaseExpression().Evaluate(&exe_ctx, NULL, NULL, NULL, loclist_base_addr, NULL, expr_value, &m_frame_base_error) == false)
1178             {
1179                 // We should really have an error if evaluate returns, but in case
1180                 // we don't, lets set the error to something at least.
1181                 if (m_frame_base_error.Success())
1182                     m_frame_base_error.SetErrorString("Evaluation of the frame base expression failed.");
1183             }
1184             else
1185             {
1186                 m_frame_base = expr_value.ResolveValue(&exe_ctx);
1187             }
1188         }
1189         else
1190         {
1191             m_frame_base_error.SetErrorString ("No function in symbol context.");
1192         }
1193     }
1194 
1195     if (m_frame_base_error.Success())
1196         frame_base = m_frame_base;
1197 
1198     if (error_ptr)
1199         *error_ptr = m_frame_base_error;
1200     return m_frame_base_error.Success();
1201 }
1202 
1203 RegisterContextSP
1204 StackFrame::GetRegisterContext ()
1205 {
1206     Mutex::Locker locker(m_mutex);
1207     if (!m_reg_context_sp)
1208     {
1209         ThreadSP thread_sp (GetThread());
1210         if (thread_sp)
1211             m_reg_context_sp = thread_sp->CreateRegisterContextForFrame (this);
1212     }
1213     return m_reg_context_sp;
1214 }
1215 
1216 bool
1217 StackFrame::HasDebugInformation ()
1218 {
1219     GetSymbolContext (eSymbolContextLineEntry);
1220     return m_sc.line_entry.IsValid();
1221 }
1222 
1223 
1224 ValueObjectSP
1225 StackFrame::GetValueObjectForFrameVariable (const VariableSP &variable_sp, DynamicValueType use_dynamic)
1226 {
1227     Mutex::Locker locker(m_mutex);
1228     ValueObjectSP valobj_sp;
1229     if (m_is_history_frame)
1230     {
1231         return valobj_sp;
1232     }
1233     VariableList *var_list = GetVariableList (true);
1234     if (var_list)
1235     {
1236         // Make sure the variable is a frame variable
1237         const uint32_t var_idx = var_list->FindIndexForVariable (variable_sp.get());
1238         const uint32_t num_variables = var_list->GetSize();
1239         if (var_idx < num_variables)
1240         {
1241             valobj_sp = m_variable_list_value_objects.GetValueObjectAtIndex (var_idx);
1242             if (valobj_sp.get() == NULL)
1243             {
1244                 if (m_variable_list_value_objects.GetSize() < num_variables)
1245                     m_variable_list_value_objects.Resize(num_variables);
1246                 valobj_sp = ValueObjectVariable::Create (this, variable_sp);
1247                 m_variable_list_value_objects.SetValueObjectAtIndex (var_idx, valobj_sp);
1248             }
1249         }
1250     }
1251     if (use_dynamic != eNoDynamicValues && valobj_sp)
1252     {
1253         ValueObjectSP dynamic_sp = valobj_sp->GetDynamicValue (use_dynamic);
1254         if (dynamic_sp)
1255             return dynamic_sp;
1256     }
1257     return valobj_sp;
1258 }
1259 
1260 ValueObjectSP
1261 StackFrame::TrackGlobalVariable (const VariableSP &variable_sp, DynamicValueType use_dynamic)
1262 {
1263     Mutex::Locker locker(m_mutex);
1264     if (m_is_history_frame)
1265         return ValueObjectSP();
1266 
1267     // Check to make sure we aren't already tracking this variable?
1268     ValueObjectSP valobj_sp (GetValueObjectForFrameVariable (variable_sp, use_dynamic));
1269     if (!valobj_sp)
1270     {
1271         // We aren't already tracking this global
1272         VariableList *var_list = GetVariableList (true);
1273         // If this frame has no variables, create a new list
1274         if (var_list == NULL)
1275             m_variable_list_sp.reset (new VariableList());
1276 
1277         // Add the global/static variable to this frame
1278         m_variable_list_sp->AddVariable (variable_sp);
1279 
1280         // Now make a value object for it so we can track its changes
1281         valobj_sp = GetValueObjectForFrameVariable (variable_sp, use_dynamic);
1282     }
1283     return valobj_sp;
1284 }
1285 
1286 bool
1287 StackFrame::IsInlined ()
1288 {
1289     if (m_sc.block == NULL)
1290         GetSymbolContext (eSymbolContextBlock);
1291     if (m_sc.block)
1292         return m_sc.block->GetContainingInlinedBlock() != NULL;
1293     return false;
1294 }
1295 
1296 TargetSP
1297 StackFrame::CalculateTarget ()
1298 {
1299     TargetSP target_sp;
1300     ThreadSP thread_sp(GetThread());
1301     if (thread_sp)
1302     {
1303         ProcessSP process_sp (thread_sp->CalculateProcess());
1304         if (process_sp)
1305             target_sp = process_sp->CalculateTarget();
1306     }
1307     return target_sp;
1308 }
1309 
1310 ProcessSP
1311 StackFrame::CalculateProcess ()
1312 {
1313     ProcessSP process_sp;
1314     ThreadSP thread_sp(GetThread());
1315     if (thread_sp)
1316         process_sp = thread_sp->CalculateProcess();
1317     return process_sp;
1318 }
1319 
1320 ThreadSP
1321 StackFrame::CalculateThread ()
1322 {
1323     return GetThread();
1324 }
1325 
1326 StackFrameSP
1327 StackFrame::CalculateStackFrame ()
1328 {
1329     return shared_from_this();
1330 }
1331 
1332 
1333 void
1334 StackFrame::CalculateExecutionContext (ExecutionContext &exe_ctx)
1335 {
1336     exe_ctx.SetContext (shared_from_this());
1337 }
1338 
1339 void
1340 StackFrame::DumpUsingSettingsFormat (Stream *strm, const char *frame_marker)
1341 {
1342     if (strm == NULL)
1343         return;
1344 
1345     GetSymbolContext(eSymbolContextEverything);
1346     ExecutionContext exe_ctx (shared_from_this());
1347     StreamString s;
1348 
1349     if (frame_marker)
1350         s.PutCString(frame_marker);
1351 
1352     const char *frame_format = NULL;
1353     Target *target = exe_ctx.GetTargetPtr();
1354     if (target)
1355         frame_format = target->GetDebugger().GetFrameFormat();
1356     if (frame_format && Debugger::FormatPrompt (frame_format, &m_sc, &exe_ctx, NULL, s))
1357     {
1358         strm->Write(s.GetData(), s.GetSize());
1359     }
1360     else
1361     {
1362         Dump (strm, true, false);
1363         strm->EOL();
1364     }
1365 }
1366 
1367 void
1368 StackFrame::Dump (Stream *strm, bool show_frame_index, bool show_fullpaths)
1369 {
1370     if (strm == NULL)
1371         return;
1372 
1373     if (show_frame_index)
1374         strm->Printf("frame #%u: ", m_frame_index);
1375     ExecutionContext exe_ctx (shared_from_this());
1376     Target *target = exe_ctx.GetTargetPtr();
1377     strm->Printf("0x%0*" PRIx64 " ",
1378                  target ? (target->GetArchitecture().GetAddressByteSize() * 2) : 16,
1379                  GetFrameCodeAddress().GetLoadAddress(target));
1380     GetSymbolContext(eSymbolContextEverything);
1381     const bool show_module = true;
1382     const bool show_inline = true;
1383     const bool show_function_arguments = true;
1384     m_sc.DumpStopContext (strm,
1385                           exe_ctx.GetBestExecutionContextScope(),
1386                           GetFrameCodeAddress(),
1387                           show_fullpaths,
1388                           show_module,
1389                           show_inline,
1390                           show_function_arguments);
1391 }
1392 
1393 void
1394 StackFrame::UpdateCurrentFrameFromPreviousFrame (StackFrame &prev_frame)
1395 {
1396     Mutex::Locker locker(m_mutex);
1397     assert (GetStackID() == prev_frame.GetStackID());    // TODO: remove this after some testing
1398     m_variable_list_sp = prev_frame.m_variable_list_sp;
1399     m_variable_list_value_objects.Swap (prev_frame.m_variable_list_value_objects);
1400     if (!m_disassembly.GetString().empty())
1401         m_disassembly.GetString().swap (m_disassembly.GetString());
1402 }
1403 
1404 
1405 void
1406 StackFrame::UpdatePreviousFrameFromCurrentFrame (StackFrame &curr_frame)
1407 {
1408     Mutex::Locker locker(m_mutex);
1409     assert (GetStackID() == curr_frame.GetStackID());        // TODO: remove this after some testing
1410     m_id.SetPC (curr_frame.m_id.GetPC());       // Update the Stack ID PC value
1411     assert (GetThread() == curr_frame.GetThread());
1412     m_frame_index = curr_frame.m_frame_index;
1413     m_concrete_frame_index = curr_frame.m_concrete_frame_index;
1414     m_reg_context_sp = curr_frame.m_reg_context_sp;
1415     m_frame_code_addr = curr_frame.m_frame_code_addr;
1416     assert (m_sc.target_sp.get() == NULL || curr_frame.m_sc.target_sp.get() == NULL || m_sc.target_sp.get() == curr_frame.m_sc.target_sp.get());
1417     assert (m_sc.module_sp.get() == NULL || curr_frame.m_sc.module_sp.get() == NULL || m_sc.module_sp.get() == curr_frame.m_sc.module_sp.get());
1418     assert (m_sc.comp_unit == NULL || curr_frame.m_sc.comp_unit == NULL || m_sc.comp_unit == curr_frame.m_sc.comp_unit);
1419     assert (m_sc.function == NULL || curr_frame.m_sc.function == NULL || m_sc.function == curr_frame.m_sc.function);
1420     m_sc = curr_frame.m_sc;
1421     m_flags.Clear(GOT_FRAME_BASE | eSymbolContextEverything);
1422     m_flags.Set (m_sc.GetResolvedMask());
1423     m_frame_base.Clear();
1424     m_frame_base_error.Clear();
1425 }
1426 
1427 
1428 bool
1429 StackFrame::HasCachedData () const
1430 {
1431     if (m_variable_list_sp.get())
1432         return true;
1433     if (m_variable_list_value_objects.GetSize() > 0)
1434         return true;
1435     if (!m_disassembly.GetString().empty())
1436         return true;
1437     return false;
1438 }
1439 
1440 bool
1441 StackFrame::GetStatus (Stream& strm,
1442                        bool show_frame_info,
1443                        bool show_source,
1444                        const char *frame_marker)
1445 {
1446 
1447     if (show_frame_info)
1448     {
1449         strm.Indent();
1450         DumpUsingSettingsFormat (&strm, frame_marker);
1451     }
1452 
1453     if (show_source)
1454     {
1455         ExecutionContext exe_ctx (shared_from_this());
1456         bool have_source = false;
1457         Debugger::StopDisassemblyType disasm_display = Debugger::eStopDisassemblyTypeNever;
1458         Target *target = exe_ctx.GetTargetPtr();
1459         if (target)
1460         {
1461             Debugger &debugger = target->GetDebugger();
1462             const uint32_t source_lines_before = debugger.GetStopSourceLineCount(true);
1463             const uint32_t source_lines_after = debugger.GetStopSourceLineCount(false);
1464             disasm_display = debugger.GetStopDisassemblyDisplay ();
1465 
1466             GetSymbolContext(eSymbolContextCompUnit | eSymbolContextLineEntry);
1467             if (m_sc.comp_unit && m_sc.line_entry.IsValid())
1468             {
1469                 have_source = true;
1470                 if (source_lines_before > 0 || source_lines_after > 0)
1471                 {
1472                     target->GetSourceManager().DisplaySourceLinesWithLineNumbers (m_sc.line_entry.file,
1473                                                                                       m_sc.line_entry.line,
1474                                                                                       source_lines_before,
1475                                                                                       source_lines_after,
1476                                                                                       "->",
1477                                                                                       &strm);
1478                 }
1479             }
1480             switch (disasm_display)
1481             {
1482             case Debugger::eStopDisassemblyTypeNever:
1483                 break;
1484 
1485             case Debugger::eStopDisassemblyTypeNoSource:
1486                 if (have_source)
1487                     break;
1488                 // Fall through to next case
1489             case Debugger::eStopDisassemblyTypeAlways:
1490                 if (target)
1491                 {
1492                     const uint32_t disasm_lines = debugger.GetDisassemblyLineCount();
1493                     if (disasm_lines > 0)
1494                     {
1495                         const ArchSpec &target_arch = target->GetArchitecture();
1496                         AddressRange pc_range;
1497                         pc_range.GetBaseAddress() = GetFrameCodeAddress();
1498                         pc_range.SetByteSize(disasm_lines * target_arch.GetMaximumOpcodeByteSize());
1499                         const char *plugin_name = NULL;
1500                         const char *flavor = NULL;
1501                         Disassembler::Disassemble (target->GetDebugger(),
1502                                                    target_arch,
1503                                                    plugin_name,
1504                                                    flavor,
1505                                                    exe_ctx,
1506                                                    pc_range,
1507                                                    disasm_lines,
1508                                                    0,
1509                                                    Disassembler::eOptionMarkPCAddress,
1510                                                    strm);
1511                     }
1512                 }
1513                 break;
1514             }
1515         }
1516     }
1517     return true;
1518 }
1519 
1520