1 //===-- BreakpointResolverAddress.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/Breakpoint/BreakpointResolverAddress.h" 11 12 // C Includes 13 // C++ Includes 14 // Other libraries and framework includes 15 // Project includes 16 17 #include "lldb/Breakpoint/BreakpointLocation.h" 18 #include "lldb/Core/Log.h" 19 #include "lldb/Core/Module.h" 20 #include "lldb/Core/StreamString.h" 21 #include "lldb/Target/Process.h" 22 #include "lldb/Target/Target.h" 23 24 using namespace lldb; 25 using namespace lldb_private; 26 27 //---------------------------------------------------------------------- 28 // BreakpointResolverAddress: 29 //---------------------------------------------------------------------- 30 BreakpointResolverAddress::BreakpointResolverAddress( 31 Breakpoint *bkpt, const Address &addr, const FileSpec &module_spec) 32 : BreakpointResolver(bkpt, BreakpointResolver::AddressResolver), 33 m_addr(addr), m_resolved_addr(LLDB_INVALID_ADDRESS), 34 m_module_filespec(module_spec) {} 35 36 BreakpointResolverAddress::BreakpointResolverAddress(Breakpoint *bkpt, 37 const Address &addr) 38 : BreakpointResolver(bkpt, BreakpointResolver::AddressResolver), 39 m_addr(addr), m_resolved_addr(LLDB_INVALID_ADDRESS), m_module_filespec() { 40 } 41 42 BreakpointResolverAddress::~BreakpointResolverAddress() {} 43 44 void BreakpointResolverAddress::ResolveBreakpoint(SearchFilter &filter) { 45 // If the address is not section relative, then we should not try to 46 // re-resolve it, it is just some 47 // random address and we wouldn't know what to do on reload. But if it is 48 // section relative, we need to 49 // re-resolve it since the section it's in may have shifted on re-run. 50 bool re_resolve = false; 51 if (m_addr.GetSection() || m_module_filespec) 52 re_resolve = true; 53 else if (m_breakpoint->GetNumLocations() == 0) 54 re_resolve = true; 55 56 if (re_resolve) 57 BreakpointResolver::ResolveBreakpoint(filter); 58 } 59 60 void BreakpointResolverAddress::ResolveBreakpointInModules( 61 SearchFilter &filter, ModuleList &modules) { 62 // See comment in ResolveBreakpoint. 63 bool re_resolve = false; 64 if (m_addr.GetSection()) 65 re_resolve = true; 66 else if (m_breakpoint->GetNumLocations() == 0) 67 re_resolve = true; 68 69 if (re_resolve) 70 BreakpointResolver::ResolveBreakpointInModules(filter, modules); 71 } 72 73 Searcher::CallbackReturn 74 BreakpointResolverAddress::SearchCallback(SearchFilter &filter, 75 SymbolContext &context, Address *addr, 76 bool containing) { 77 assert(m_breakpoint != NULL); 78 79 if (filter.AddressPasses(m_addr)) { 80 if (m_breakpoint->GetNumLocations() == 0) { 81 // If the address is just an offset, and we're given a module, see if we 82 // can find the appropriate module 83 // loaded in the binary, and fix up m_addr to use that. 84 if (!m_addr.IsSectionOffset() && m_module_filespec) { 85 Target &target = m_breakpoint->GetTarget(); 86 ModuleSpec module_spec(m_module_filespec); 87 ModuleSP module_sp = target.GetImages().FindFirstModule(module_spec); 88 if (module_sp) { 89 Address tmp_address; 90 if (module_sp->ResolveFileAddress(m_addr.GetOffset(), tmp_address)) 91 m_addr = tmp_address; 92 } 93 } 94 95 m_resolved_addr = m_addr.GetLoadAddress(&m_breakpoint->GetTarget()); 96 BreakpointLocationSP bp_loc_sp(AddLocation(m_addr)); 97 if (bp_loc_sp && !m_breakpoint->IsInternal()) { 98 StreamString s; 99 bp_loc_sp->GetDescription(&s, lldb::eDescriptionLevelVerbose); 100 Log *log( 101 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_BREAKPOINTS)); 102 if (log) 103 log->Printf("Added location: %s\n", s.GetData()); 104 } 105 } else { 106 BreakpointLocationSP loc_sp = m_breakpoint->GetLocationAtIndex(0); 107 lldb::addr_t cur_load_location = 108 m_addr.GetLoadAddress(&m_breakpoint->GetTarget()); 109 if (cur_load_location != m_resolved_addr) { 110 m_resolved_addr = cur_load_location; 111 loc_sp->ClearBreakpointSite(); 112 loc_sp->ResolveBreakpointSite(); 113 } 114 } 115 } 116 return Searcher::eCallbackReturnStop; 117 } 118 119 Searcher::Depth BreakpointResolverAddress::GetDepth() { 120 return Searcher::eDepthTarget; 121 } 122 123 void BreakpointResolverAddress::GetDescription(Stream *s) { 124 s->PutCString("address = "); 125 m_addr.Dump(s, m_breakpoint->GetTarget().GetProcessSP().get(), 126 Address::DumpStyleModuleWithFileAddress, 127 Address::DumpStyleLoadAddress); 128 } 129 130 void BreakpointResolverAddress::Dump(Stream *s) const {} 131 132 lldb::BreakpointResolverSP 133 BreakpointResolverAddress::CopyForBreakpoint(Breakpoint &breakpoint) { 134 lldb::BreakpointResolverSP ret_sp( 135 new BreakpointResolverAddress(&breakpoint, m_addr)); 136 return ret_sp; 137 } 138