1254721Semaste//===-- Block.cpp -----------------------------------------------*- C++ -*-===// 2254721Semaste// 3254721Semaste// The LLVM Compiler Infrastructure 4254721Semaste// 5254721Semaste// This file is distributed under the University of Illinois Open Source 6254721Semaste// License. See LICENSE.TXT for details. 7254721Semaste// 8254721Semaste//===----------------------------------------------------------------------===// 9254721Semaste 10254721Semaste#include "lldb/Symbol/Block.h" 11254721Semaste 12254721Semaste#include "lldb/lldb-private-log.h" 13254721Semaste 14254721Semaste#include "lldb/Core/Log.h" 15254721Semaste#include "lldb/Core/Module.h" 16254721Semaste#include "lldb/Core/Section.h" 17254721Semaste#include "lldb/Symbol/Function.h" 18254721Semaste#include "lldb/Symbol/SymbolFile.h" 19254721Semaste#include "lldb/Symbol/SymbolVendor.h" 20254721Semaste#include "lldb/Symbol/VariableList.h" 21254721Semaste 22254721Semasteusing namespace lldb; 23254721Semasteusing namespace lldb_private; 24254721Semaste 25254721SemasteBlock::Block(lldb::user_id_t uid) : 26254721Semaste UserID(uid), 27254721Semaste m_parent_scope (NULL), 28254721Semaste m_children (), 29254721Semaste m_ranges (), 30254721Semaste m_inlineInfoSP (), 31254721Semaste m_variable_list_sp (), 32254721Semaste m_parsed_block_info (false), 33254721Semaste m_parsed_block_variables (false), 34254721Semaste m_parsed_child_blocks (false) 35254721Semaste{ 36254721Semaste} 37254721Semaste 38254721SemasteBlock::~Block () 39254721Semaste{ 40254721Semaste} 41254721Semaste 42254721Semastevoid 43254721SemasteBlock::GetDescription(Stream *s, Function *function, lldb::DescriptionLevel level, Target *target) const 44254721Semaste{ 45254721Semaste *s << "id = " << ((const UserID&)*this); 46254721Semaste 47254721Semaste size_t num_ranges = m_ranges.GetSize(); 48254721Semaste if (num_ranges > 0) 49254721Semaste { 50254721Semaste 51254721Semaste addr_t base_addr = LLDB_INVALID_ADDRESS; 52254721Semaste if (target) 53254721Semaste base_addr = function->GetAddressRange().GetBaseAddress().GetLoadAddress(target); 54254721Semaste if (base_addr == LLDB_INVALID_ADDRESS) 55254721Semaste base_addr = function->GetAddressRange().GetBaseAddress().GetFileAddress(); 56254721Semaste 57254721Semaste s->Printf(", range%s = ", num_ranges > 1 ? "s" : ""); 58254721Semaste for (size_t i=0; i<num_ranges; ++i) 59254721Semaste { 60254721Semaste const Range &range = m_ranges.GetEntryRef(i); 61254721Semaste s->AddressRange(base_addr + range.GetRangeBase(), base_addr + range.GetRangeEnd(), 4); 62254721Semaste } 63254721Semaste } 64254721Semaste 65254721Semaste if (m_inlineInfoSP.get() != NULL) 66254721Semaste { 67254721Semaste bool show_fullpaths = (level == eDescriptionLevelVerbose); 68254721Semaste m_inlineInfoSP->Dump(s, show_fullpaths); 69254721Semaste } 70254721Semaste} 71254721Semaste 72254721Semastevoid 73254721SemasteBlock::Dump(Stream *s, addr_t base_addr, int32_t depth, bool show_context) const 74254721Semaste{ 75254721Semaste if (depth < 0) 76254721Semaste { 77254721Semaste Block *parent = GetParent(); 78254721Semaste if (parent) 79254721Semaste { 80254721Semaste // We have a depth that is less than zero, print our parent blocks 81254721Semaste // first 82254721Semaste parent->Dump(s, base_addr, depth + 1, show_context); 83254721Semaste } 84254721Semaste } 85254721Semaste 86254721Semaste s->Printf("%p: ", this); 87254721Semaste s->Indent(); 88254721Semaste *s << "Block" << ((const UserID&)*this); 89254721Semaste const Block* parent_block = GetParent(); 90254721Semaste if (parent_block) 91254721Semaste { 92254721Semaste s->Printf(", parent = {0x%8.8" PRIx64 "}", parent_block->GetID()); 93254721Semaste } 94254721Semaste if (m_inlineInfoSP.get() != NULL) 95254721Semaste { 96254721Semaste bool show_fullpaths = false; 97254721Semaste m_inlineInfoSP->Dump(s, show_fullpaths); 98254721Semaste } 99254721Semaste 100254721Semaste if (!m_ranges.IsEmpty()) 101254721Semaste { 102254721Semaste *s << ", ranges ="; 103254721Semaste 104254721Semaste size_t num_ranges = m_ranges.GetSize(); 105254721Semaste for (size_t i=0; i<num_ranges; ++i) 106254721Semaste { 107254721Semaste const Range &range = m_ranges.GetEntryRef(i); 108254721Semaste if (parent_block != NULL && parent_block->Contains(range) == false) 109254721Semaste *s << '!'; 110254721Semaste else 111254721Semaste *s << ' '; 112254721Semaste s->AddressRange(base_addr + range.GetRangeBase(), base_addr + range.GetRangeEnd(), 4); 113254721Semaste } 114254721Semaste } 115254721Semaste s->EOL(); 116254721Semaste 117254721Semaste if (depth > 0) 118254721Semaste { 119254721Semaste s->IndentMore(); 120254721Semaste 121254721Semaste if (m_variable_list_sp.get()) 122254721Semaste { 123254721Semaste m_variable_list_sp->Dump(s, show_context); 124254721Semaste } 125254721Semaste 126254721Semaste collection::const_iterator pos, end = m_children.end(); 127254721Semaste for (pos = m_children.begin(); pos != end; ++pos) 128254721Semaste (*pos)->Dump(s, base_addr, depth - 1, show_context); 129254721Semaste 130254721Semaste s->IndentLess(); 131254721Semaste } 132254721Semaste 133254721Semaste} 134254721Semaste 135254721Semaste 136254721SemasteBlock * 137254721SemasteBlock::FindBlockByID (user_id_t block_id) 138254721Semaste{ 139254721Semaste if (block_id == GetID()) 140254721Semaste return this; 141254721Semaste 142254721Semaste Block *matching_block = NULL; 143254721Semaste collection::const_iterator pos, end = m_children.end(); 144254721Semaste for (pos = m_children.begin(); pos != end; ++pos) 145254721Semaste { 146254721Semaste matching_block = (*pos)->FindBlockByID (block_id); 147254721Semaste if (matching_block) 148254721Semaste break; 149254721Semaste } 150254721Semaste return matching_block; 151254721Semaste} 152254721Semaste 153254721Semastevoid 154254721SemasteBlock::CalculateSymbolContext (SymbolContext* sc) 155254721Semaste{ 156254721Semaste if (m_parent_scope) 157254721Semaste m_parent_scope->CalculateSymbolContext(sc); 158254721Semaste sc->block = this; 159254721Semaste} 160254721Semaste 161254721Semastelldb::ModuleSP 162254721SemasteBlock::CalculateSymbolContextModule () 163254721Semaste{ 164254721Semaste if (m_parent_scope) 165254721Semaste return m_parent_scope->CalculateSymbolContextModule (); 166254721Semaste return lldb::ModuleSP(); 167254721Semaste} 168254721Semaste 169254721SemasteCompileUnit * 170254721SemasteBlock::CalculateSymbolContextCompileUnit () 171254721Semaste{ 172254721Semaste if (m_parent_scope) 173254721Semaste return m_parent_scope->CalculateSymbolContextCompileUnit (); 174254721Semaste return NULL; 175254721Semaste} 176254721Semaste 177254721SemasteFunction * 178254721SemasteBlock::CalculateSymbolContextFunction () 179254721Semaste{ 180254721Semaste if (m_parent_scope) 181254721Semaste return m_parent_scope->CalculateSymbolContextFunction (); 182254721Semaste return NULL; 183254721Semaste} 184254721Semaste 185254721SemasteBlock * 186254721SemasteBlock::CalculateSymbolContextBlock () 187254721Semaste{ 188254721Semaste return this; 189254721Semaste} 190254721Semaste 191254721Semastevoid 192254721SemasteBlock::DumpSymbolContext(Stream *s) 193254721Semaste{ 194254721Semaste Function *function = CalculateSymbolContextFunction(); 195254721Semaste if (function) 196254721Semaste function->DumpSymbolContext(s); 197254721Semaste s->Printf(", Block{0x%8.8" PRIx64 "}", GetID()); 198254721Semaste} 199254721Semaste 200254721Semastevoid 201254721SemasteBlock::DumpAddressRanges (Stream *s, lldb::addr_t base_addr) 202254721Semaste{ 203254721Semaste if (!m_ranges.IsEmpty()) 204254721Semaste { 205254721Semaste size_t num_ranges = m_ranges.GetSize(); 206254721Semaste for (size_t i=0; i<num_ranges; ++i) 207254721Semaste { 208254721Semaste const Range &range = m_ranges.GetEntryRef(i); 209254721Semaste s->AddressRange(base_addr + range.GetRangeBase(), base_addr + range.GetRangeEnd(), 4); 210254721Semaste } 211254721Semaste } 212254721Semaste} 213254721Semaste 214254721Semastebool 215254721SemasteBlock::Contains (addr_t range_offset) const 216254721Semaste{ 217254721Semaste return m_ranges.FindEntryThatContains(range_offset) != NULL; 218254721Semaste} 219254721Semaste 220254721Semastebool 221254721SemasteBlock::Contains (const Block *block) const 222254721Semaste{ 223254721Semaste if (this == block) 224254721Semaste return false; // This block doesn't contain itself... 225254721Semaste 226254721Semaste // Walk the parent chain for "block" and see if any if them match this block 227254721Semaste const Block *block_parent; 228254721Semaste for (block_parent = block->GetParent(); 229254721Semaste block_parent != NULL; 230254721Semaste block_parent = block_parent->GetParent()) 231254721Semaste { 232254721Semaste if (this == block_parent) 233254721Semaste return true; // One of the parents of "block" is this object! 234254721Semaste } 235254721Semaste return false; 236254721Semaste} 237254721Semaste 238254721Semastebool 239254721SemasteBlock::Contains (const Range& range) const 240254721Semaste{ 241254721Semaste return m_ranges.FindEntryThatContains (range) != NULL; 242254721Semaste} 243254721Semaste 244254721SemasteBlock * 245254721SemasteBlock::GetParent () const 246254721Semaste{ 247254721Semaste if (m_parent_scope) 248254721Semaste return m_parent_scope->CalculateSymbolContextBlock(); 249254721Semaste return NULL; 250254721Semaste} 251254721Semaste 252254721SemasteBlock * 253254721SemasteBlock::GetContainingInlinedBlock () 254254721Semaste{ 255254721Semaste if (GetInlinedFunctionInfo()) 256254721Semaste return this; 257254721Semaste return GetInlinedParent (); 258254721Semaste} 259254721Semaste 260254721SemasteBlock * 261254721SemasteBlock::GetInlinedParent () 262254721Semaste{ 263254721Semaste Block *parent_block = GetParent (); 264254721Semaste if (parent_block) 265254721Semaste { 266254721Semaste if (parent_block->GetInlinedFunctionInfo()) 267254721Semaste return parent_block; 268254721Semaste else 269254721Semaste return parent_block->GetInlinedParent(); 270254721Semaste } 271254721Semaste return NULL; 272254721Semaste} 273254721Semaste 274254721Semaste 275254721Semastebool 276254721SemasteBlock::GetRangeContainingOffset (const addr_t offset, Range &range) 277254721Semaste{ 278254721Semaste const Range *range_ptr = m_ranges.FindEntryThatContains (offset); 279254721Semaste if (range_ptr) 280254721Semaste { 281254721Semaste range = *range_ptr; 282254721Semaste return true; 283254721Semaste } 284254721Semaste range.Clear(); 285254721Semaste return false; 286254721Semaste} 287254721Semaste 288254721Semaste 289254721Semastebool 290254721SemasteBlock::GetRangeContainingAddress (const Address& addr, AddressRange &range) 291254721Semaste{ 292254721Semaste Function *function = CalculateSymbolContextFunction(); 293254721Semaste if (function) 294254721Semaste { 295254721Semaste const AddressRange &func_range = function->GetAddressRange(); 296254721Semaste if (addr.GetSection() == func_range.GetBaseAddress().GetSection()) 297254721Semaste { 298254721Semaste const addr_t addr_offset = addr.GetOffset(); 299254721Semaste const addr_t func_offset = func_range.GetBaseAddress().GetOffset(); 300254721Semaste if (addr_offset >= func_offset && addr_offset < func_offset + func_range.GetByteSize()) 301254721Semaste { 302254721Semaste addr_t offset = addr_offset - func_offset; 303254721Semaste 304254721Semaste const Range *range_ptr = m_ranges.FindEntryThatContains (offset); 305254721Semaste 306254721Semaste if (range_ptr) 307254721Semaste { 308254721Semaste range.GetBaseAddress() = func_range.GetBaseAddress(); 309254721Semaste range.GetBaseAddress().SetOffset(func_offset + range_ptr->GetRangeBase()); 310254721Semaste range.SetByteSize(range_ptr->GetByteSize()); 311254721Semaste return true; 312254721Semaste } 313254721Semaste } 314254721Semaste } 315254721Semaste } 316254721Semaste range.Clear(); 317254721Semaste return false; 318254721Semaste} 319254721Semaste 320254721Semastebool 321254721SemasteBlock::GetRangeContainingLoadAddress (lldb::addr_t load_addr, Target &target, AddressRange &range) 322254721Semaste{ 323254721Semaste Address load_address; 324254721Semaste load_address.SetLoadAddress(load_addr, &target); 325254721Semaste AddressRange containing_range; 326254721Semaste return GetRangeContainingAddress(load_address, containing_range); 327254721Semaste} 328254721Semaste 329254721Semaste 330254721Semasteuint32_t 331254721SemasteBlock::GetRangeIndexContainingAddress (const Address& addr) 332254721Semaste{ 333254721Semaste Function *function = CalculateSymbolContextFunction(); 334254721Semaste if (function) 335254721Semaste { 336254721Semaste const AddressRange &func_range = function->GetAddressRange(); 337254721Semaste if (addr.GetSection() == func_range.GetBaseAddress().GetSection()) 338254721Semaste { 339254721Semaste const addr_t addr_offset = addr.GetOffset(); 340254721Semaste const addr_t func_offset = func_range.GetBaseAddress().GetOffset(); 341254721Semaste if (addr_offset >= func_offset && addr_offset < func_offset + func_range.GetByteSize()) 342254721Semaste { 343254721Semaste addr_t offset = addr_offset - func_offset; 344254721Semaste return m_ranges.FindEntryIndexThatContains (offset); 345254721Semaste } 346254721Semaste } 347254721Semaste } 348254721Semaste return UINT32_MAX; 349254721Semaste} 350254721Semaste 351254721Semastebool 352254721SemasteBlock::GetRangeAtIndex (uint32_t range_idx, AddressRange &range) 353254721Semaste{ 354254721Semaste if (range_idx < m_ranges.GetSize()) 355254721Semaste { 356254721Semaste Function *function = CalculateSymbolContextFunction(); 357254721Semaste if (function) 358254721Semaste { 359254721Semaste const Range &vm_range = m_ranges.GetEntryRef(range_idx); 360254721Semaste range.GetBaseAddress() = function->GetAddressRange().GetBaseAddress(); 361254721Semaste range.GetBaseAddress().Slide(vm_range.GetRangeBase ()); 362254721Semaste range.SetByteSize (vm_range.GetByteSize()); 363254721Semaste return true; 364254721Semaste } 365254721Semaste } 366254721Semaste return false; 367254721Semaste} 368254721Semaste 369254721Semastebool 370254721SemasteBlock::GetStartAddress (Address &addr) 371254721Semaste{ 372254721Semaste if (m_ranges.IsEmpty()) 373254721Semaste return false; 374254721Semaste 375254721Semaste Function *function = CalculateSymbolContextFunction(); 376254721Semaste if (function) 377254721Semaste { 378254721Semaste addr = function->GetAddressRange().GetBaseAddress(); 379254721Semaste addr.Slide(m_ranges.GetEntryRef(0).GetRangeBase ()); 380254721Semaste return true; 381254721Semaste } 382254721Semaste return false; 383254721Semaste} 384254721Semaste 385254721Semastevoid 386254721SemasteBlock::FinalizeRanges () 387254721Semaste{ 388254721Semaste m_ranges.Sort(); 389254721Semaste m_ranges.CombineConsecutiveRanges (); 390254721Semaste} 391254721Semaste 392254721Semastevoid 393254721SemasteBlock::AddRange (const Range& range) 394254721Semaste{ 395254721Semaste Block *parent_block = GetParent (); 396254721Semaste if (parent_block && !parent_block->Contains(range)) 397254721Semaste { 398254721Semaste Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_SYMBOLS)); 399254721Semaste if (log) 400254721Semaste { 401254721Semaste ModuleSP module_sp (m_parent_scope->CalculateSymbolContextModule()); 402254721Semaste Function *function = m_parent_scope->CalculateSymbolContextFunction(); 403254721Semaste const addr_t function_file_addr = function->GetAddressRange().GetBaseAddress().GetFileAddress(); 404254721Semaste const addr_t block_start_addr = function_file_addr + range.GetRangeBase (); 405254721Semaste const addr_t block_end_addr = function_file_addr + range.GetRangeEnd (); 406254721Semaste Type *func_type = function->GetType(); 407254721Semaste 408254721Semaste const Declaration &func_decl = func_type->GetDeclaration(); 409254721Semaste if (func_decl.GetLine()) 410254721Semaste { 411254721Semaste log->Printf ("warning: %s:%u block {0x%8.8" PRIx64 "} has range[%u] [0x%" PRIx64 " - 0x%" PRIx64 ") which is not contained in parent block {0x%8.8" PRIx64 "} in function {0x%8.8" PRIx64 "} from %s", 412254721Semaste func_decl.GetFile().GetPath().c_str(), 413254721Semaste func_decl.GetLine(), 414254721Semaste GetID(), 415254721Semaste (uint32_t)m_ranges.GetSize(), 416254721Semaste block_start_addr, 417254721Semaste block_end_addr, 418254721Semaste parent_block->GetID(), 419254721Semaste function->GetID(), 420254721Semaste module_sp->GetFileSpec().GetPath().c_str()); 421254721Semaste } 422254721Semaste else 423254721Semaste { 424254721Semaste log->Printf ("warning: block {0x%8.8" PRIx64 "} has range[%u] [0x%" PRIx64 " - 0x%" PRIx64 ") which is not contained in parent block {0x%8.8" PRIx64 "} in function {0x%8.8" PRIx64 "} from %s", 425254721Semaste GetID(), 426254721Semaste (uint32_t)m_ranges.GetSize(), 427254721Semaste block_start_addr, 428254721Semaste block_end_addr, 429254721Semaste parent_block->GetID(), 430254721Semaste function->GetID(), 431254721Semaste module_sp->GetFileSpec().GetPath().c_str()); 432254721Semaste } 433254721Semaste } 434254721Semaste parent_block->AddRange (range); 435254721Semaste } 436254721Semaste m_ranges.Append(range); 437254721Semaste} 438254721Semaste 439254721Semaste// Return the current number of bytes that this object occupies in memory 440254721Semastesize_t 441254721SemasteBlock::MemorySize() const 442254721Semaste{ 443254721Semaste size_t mem_size = sizeof(Block) + m_ranges.GetSize() * sizeof(Range); 444254721Semaste if (m_inlineInfoSP.get()) 445254721Semaste mem_size += m_inlineInfoSP->MemorySize(); 446254721Semaste if (m_variable_list_sp.get()) 447254721Semaste mem_size += m_variable_list_sp->MemorySize(); 448254721Semaste return mem_size; 449254721Semaste 450254721Semaste} 451254721Semaste 452254721Semastevoid 453254721SemasteBlock::AddChild(const BlockSP &child_block_sp) 454254721Semaste{ 455254721Semaste if (child_block_sp) 456254721Semaste { 457254721Semaste child_block_sp->SetParentScope (this); 458254721Semaste m_children.push_back (child_block_sp); 459254721Semaste } 460254721Semaste} 461254721Semaste 462254721Semastevoid 463254721SemasteBlock::SetInlinedFunctionInfo(const char *name, const char *mangled, const Declaration *decl_ptr, const Declaration *call_decl_ptr) 464254721Semaste{ 465254721Semaste m_inlineInfoSP.reset(new InlineFunctionInfo(name, mangled, decl_ptr, call_decl_ptr)); 466254721Semaste} 467254721Semaste 468254721Semaste 469254721Semaste 470254721SemasteVariableListSP 471254721SemasteBlock::GetBlockVariableList (bool can_create) 472254721Semaste{ 473254721Semaste if (m_parsed_block_variables == false) 474254721Semaste { 475254721Semaste if (m_variable_list_sp.get() == NULL && can_create) 476254721Semaste { 477254721Semaste m_parsed_block_variables = true; 478254721Semaste SymbolContext sc; 479254721Semaste CalculateSymbolContext(&sc); 480254721Semaste assert(sc.module_sp); 481254721Semaste sc.module_sp->GetSymbolVendor()->ParseVariablesForContext(sc); 482254721Semaste } 483254721Semaste } 484254721Semaste return m_variable_list_sp; 485254721Semaste} 486254721Semaste 487254721Semasteuint32_t 488254721SemasteBlock::AppendBlockVariables (bool can_create, 489254721Semaste bool get_child_block_variables, 490254721Semaste bool stop_if_child_block_is_inlined_function, 491254721Semaste VariableList *variable_list) 492254721Semaste{ 493254721Semaste uint32_t num_variables_added = 0; 494254721Semaste VariableList *block_var_list = GetBlockVariableList (can_create).get(); 495254721Semaste if (block_var_list) 496254721Semaste { 497254721Semaste num_variables_added += block_var_list->GetSize(); 498254721Semaste variable_list->AddVariables (block_var_list); 499254721Semaste } 500254721Semaste 501254721Semaste if (get_child_block_variables) 502254721Semaste { 503254721Semaste collection::const_iterator pos, end = m_children.end(); 504254721Semaste for (pos = m_children.begin(); pos != end; ++pos) 505254721Semaste { 506254721Semaste Block *child_block = pos->get(); 507254721Semaste if (stop_if_child_block_is_inlined_function == false || 508254721Semaste child_block->GetInlinedFunctionInfo() == NULL) 509254721Semaste { 510254721Semaste num_variables_added += child_block->AppendBlockVariables (can_create, 511254721Semaste get_child_block_variables, 512254721Semaste stop_if_child_block_is_inlined_function, 513254721Semaste variable_list); 514254721Semaste } 515254721Semaste } 516254721Semaste } 517254721Semaste return num_variables_added; 518254721Semaste} 519254721Semaste 520254721Semasteuint32_t 521254721SemasteBlock::AppendVariables 522254721Semaste( 523254721Semaste bool can_create, 524254721Semaste bool get_parent_variables, 525254721Semaste bool stop_if_block_is_inlined_function, 526254721Semaste VariableList *variable_list 527254721Semaste) 528254721Semaste{ 529254721Semaste uint32_t num_variables_added = 0; 530254721Semaste VariableListSP variable_list_sp(GetBlockVariableList(can_create)); 531254721Semaste 532254721Semaste bool is_inlined_function = GetInlinedFunctionInfo() != NULL; 533254721Semaste if (variable_list_sp.get()) 534254721Semaste { 535254721Semaste num_variables_added = variable_list_sp->GetSize(); 536254721Semaste variable_list->AddVariables(variable_list_sp.get()); 537254721Semaste } 538254721Semaste 539254721Semaste if (get_parent_variables) 540254721Semaste { 541254721Semaste if (stop_if_block_is_inlined_function && is_inlined_function) 542254721Semaste return num_variables_added; 543254721Semaste 544254721Semaste Block* parent_block = GetParent(); 545254721Semaste if (parent_block) 546254721Semaste num_variables_added += parent_block->AppendVariables (can_create, get_parent_variables, stop_if_block_is_inlined_function, variable_list); 547254721Semaste } 548254721Semaste return num_variables_added; 549254721Semaste} 550254721Semaste 551254721Semasteclang::DeclContext * 552254721SemasteBlock::GetClangDeclContext() 553254721Semaste{ 554254721Semaste SymbolContext sc; 555254721Semaste 556254721Semaste CalculateSymbolContext (&sc); 557254721Semaste 558254721Semaste if (!sc.module_sp) 559254721Semaste return NULL; 560254721Semaste 561254721Semaste SymbolVendor *sym_vendor = sc.module_sp->GetSymbolVendor(); 562254721Semaste 563254721Semaste if (!sym_vendor) 564254721Semaste return NULL; 565254721Semaste 566254721Semaste SymbolFile *sym_file = sym_vendor->GetSymbolFile(); 567254721Semaste 568254721Semaste if (!sym_file) 569254721Semaste return NULL; 570254721Semaste 571254721Semaste return sym_file->GetClangDeclContextForTypeUID (sc, m_uid); 572254721Semaste} 573254721Semaste 574254721Semastevoid 575254721SemasteBlock::SetBlockInfoHasBeenParsed (bool b, bool set_children) 576254721Semaste{ 577254721Semaste m_parsed_block_info = b; 578254721Semaste if (set_children) 579254721Semaste { 580254721Semaste m_parsed_child_blocks = true; 581254721Semaste collection::const_iterator pos, end = m_children.end(); 582254721Semaste for (pos = m_children.begin(); pos != end; ++pos) 583254721Semaste (*pos)->SetBlockInfoHasBeenParsed (b, true); 584254721Semaste } 585254721Semaste} 586254721Semaste 587254721Semastevoid 588254721SemasteBlock::SetDidParseVariables (bool b, bool set_children) 589254721Semaste{ 590254721Semaste m_parsed_block_variables = b; 591254721Semaste if (set_children) 592254721Semaste { 593254721Semaste collection::const_iterator pos, end = m_children.end(); 594254721Semaste for (pos = m_children.begin(); pos != end; ++pos) 595254721Semaste (*pos)->SetDidParseVariables (b, true); 596254721Semaste } 597254721Semaste} 598254721Semaste 599254721Semaste 600254721SemasteBlock * 601254721SemasteBlock::GetSibling() const 602254721Semaste{ 603254721Semaste if (m_parent_scope) 604254721Semaste { 605254721Semaste Block *parent_block = GetParent(); 606254721Semaste if (parent_block) 607254721Semaste return parent_block->GetSiblingForChild (this); 608254721Semaste } 609254721Semaste return NULL; 610254721Semaste} 611254721Semaste// A parent of child blocks can be asked to find a sibling block given 612254721Semaste// one of its child blocks 613254721SemasteBlock * 614254721SemasteBlock::GetSiblingForChild (const Block *child_block) const 615254721Semaste{ 616254721Semaste if (!m_children.empty()) 617254721Semaste { 618254721Semaste collection::const_iterator pos, end = m_children.end(); 619254721Semaste for (pos = m_children.begin(); pos != end; ++pos) 620254721Semaste { 621254721Semaste if (pos->get() == child_block) 622254721Semaste { 623254721Semaste if (++pos != end) 624254721Semaste return pos->get(); 625254721Semaste break; 626254721Semaste } 627254721Semaste } 628254721Semaste } 629254721Semaste return NULL; 630254721Semaste} 631254721Semaste 632