130fdc8d8SChris Lattner //===-- BreakpointResolverFileLine.cpp --------------------------*- C++ -*-===//
230fdc8d8SChris Lattner //
330fdc8d8SChris Lattner //                     The LLVM Compiler Infrastructure
430fdc8d8SChris Lattner //
530fdc8d8SChris Lattner // This file is distributed under the University of Illinois Open Source
630fdc8d8SChris Lattner // License. See LICENSE.TXT for details.
730fdc8d8SChris Lattner //
830fdc8d8SChris Lattner //===----------------------------------------------------------------------===//
930fdc8d8SChris Lattner 
1030fdc8d8SChris Lattner #include "lldb/Breakpoint/BreakpointResolverFileLine.h"
1130fdc8d8SChris Lattner 
1230fdc8d8SChris Lattner // C Includes
1330fdc8d8SChris Lattner // C++ Includes
1430fdc8d8SChris Lattner // Other libraries and framework includes
1530fdc8d8SChris Lattner // Project includes
1630fdc8d8SChris Lattner #include "lldb/Breakpoint/BreakpointLocation.h"
1730fdc8d8SChris Lattner #include "lldb/Core/Log.h"
181f746071SGreg Clayton #include "lldb/Core/Module.h"
1930fdc8d8SChris Lattner #include "lldb/Core/StreamString.h"
201f746071SGreg Clayton #include "lldb/Symbol/CompileUnit.h"
211f746071SGreg Clayton #include "lldb/Symbol/Function.h"
2230fdc8d8SChris Lattner #include "lldb/lldb-private-log.h"
2330fdc8d8SChris Lattner 
2430fdc8d8SChris Lattner using namespace lldb;
2530fdc8d8SChris Lattner using namespace lldb_private;
2630fdc8d8SChris Lattner 
2730fdc8d8SChris Lattner //----------------------------------------------------------------------
2830fdc8d8SChris Lattner // BreakpointResolverFileLine:
2930fdc8d8SChris Lattner //----------------------------------------------------------------------
3030fdc8d8SChris Lattner BreakpointResolverFileLine::BreakpointResolverFileLine
3130fdc8d8SChris Lattner (
3230fdc8d8SChris Lattner     Breakpoint *bkpt,
3330fdc8d8SChris Lattner     const FileSpec &file_spec,
3430fdc8d8SChris Lattner     uint32_t line_no,
35a8558b62SJim Ingham     bool check_inlines,
36a8558b62SJim Ingham     bool skip_prologue
3730fdc8d8SChris Lattner ) :
38b7234e40SJohnny Chen     BreakpointResolver (bkpt, BreakpointResolver::FileLineResolver),
3930fdc8d8SChris Lattner     m_file_spec (file_spec),
4030fdc8d8SChris Lattner     m_line_number (line_no),
41a8558b62SJim Ingham     m_inlines (check_inlines),
42a8558b62SJim Ingham     m_skip_prologue(skip_prologue)
4330fdc8d8SChris Lattner {
4430fdc8d8SChris Lattner }
4530fdc8d8SChris Lattner 
4630fdc8d8SChris Lattner BreakpointResolverFileLine::~BreakpointResolverFileLine ()
4730fdc8d8SChris Lattner {
4830fdc8d8SChris Lattner }
4930fdc8d8SChris Lattner 
5030fdc8d8SChris Lattner Searcher::CallbackReturn
5130fdc8d8SChris Lattner BreakpointResolverFileLine::SearchCallback
5230fdc8d8SChris Lattner (
5330fdc8d8SChris Lattner     SearchFilter &filter,
5430fdc8d8SChris Lattner     SymbolContext &context,
5530fdc8d8SChris Lattner     Address *addr,
5630fdc8d8SChris Lattner     bool containing
5730fdc8d8SChris Lattner )
5830fdc8d8SChris Lattner {
5930fdc8d8SChris Lattner     SymbolContextList sc_list;
6030fdc8d8SChris Lattner 
6130fdc8d8SChris Lattner     assert (m_breakpoint != NULL);
6230fdc8d8SChris Lattner 
63bc2f9182SJim Ingham     // There is a tricky bit here.  You can have two compilation units that #include the same file, and
64bc2f9182SJim Ingham     // in one of them the function at m_line_number is used (and so code and a line entry for it is generated) but in the
65bc2f9182SJim Ingham     // other it isn't.  If we considered the CU's independently, then in the second inclusion, we'd move the breakpoint
66bc2f9182SJim Ingham     // to the next function that actually generated code in the header file.  That would end up being confusing.
67bc2f9182SJim Ingham     // So instead, we do the CU iterations by hand here, then scan through the complete list of matches, and figure out
68bc2f9182SJim Ingham     // the closest line number match, and only set breakpoints on that match.
69bc2f9182SJim Ingham 
70bc2f9182SJim Ingham     // Note also that if file_spec only had a file name and not a directory, there may be many different file spec's in
71bc2f9182SJim Ingham     // the resultant list.  The closest line match for one will not be right for some totally different file.
72bc2f9182SJim Ingham     // So we go through the match list and pull out the sets that have the same file spec in their line_entry
73bc2f9182SJim Ingham     // and treat each set separately.
74bc2f9182SJim Ingham 
75c7bece56SGreg Clayton     const size_t num_comp_units = context.module_sp->GetNumCompileUnits();
76c7bece56SGreg Clayton     for (size_t i = 0; i < num_comp_units; i++)
77bc2f9182SJim Ingham     {
78bc2f9182SJim Ingham         CompUnitSP cu_sp (context.module_sp->GetCompileUnitAtIndex (i));
792dafd8edSGreg Clayton         if (cu_sp)
802dafd8edSGreg Clayton         {
812dafd8edSGreg Clayton             if (filter.CompUnitPasses(*cu_sp))
82bc2f9182SJim Ingham                 cu_sp->ResolveSymbolContext (m_file_spec, m_line_number, m_inlines, false, eSymbolContextEverything, sc_list);
83bc2f9182SJim Ingham         }
842dafd8edSGreg Clayton     }
8530fdc8d8SChris Lattner     StreamString s;
86f642373cSJim Ingham     s.Printf ("for %s:%d ",
87969795f1SJim Ingham                         m_file_spec.GetFilename().AsCString("<Unknown>"),
88969795f1SJim Ingham                         m_line_number);
89f642373cSJim Ingham 
90f642373cSJim Ingham     SetSCMatchesByLine (filter, sc_list, m_skip_prologue, s.GetData());
91bc2f9182SJim Ingham 
9230fdc8d8SChris Lattner     return Searcher::eCallbackReturnContinue;
9330fdc8d8SChris Lattner }
9430fdc8d8SChris Lattner 
9530fdc8d8SChris Lattner Searcher::Depth
9630fdc8d8SChris Lattner BreakpointResolverFileLine::GetDepth()
9730fdc8d8SChris Lattner {
98bc2f9182SJim Ingham     return Searcher::eDepthModule;
9930fdc8d8SChris Lattner }
10030fdc8d8SChris Lattner 
10130fdc8d8SChris Lattner void
10230fdc8d8SChris Lattner BreakpointResolverFileLine::GetDescription (Stream *s)
10330fdc8d8SChris Lattner {
104405fab90SGreg Clayton     s->Printf ("file = '%s', line = %u", m_file_spec.GetPath().c_str(), m_line_number);
10530fdc8d8SChris Lattner }
10630fdc8d8SChris Lattner 
10730fdc8d8SChris Lattner void
10830fdc8d8SChris Lattner BreakpointResolverFileLine::Dump (Stream *s) const
10930fdc8d8SChris Lattner {
11030fdc8d8SChris Lattner 
11130fdc8d8SChris Lattner }
11230fdc8d8SChris Lattner 
113*33df7cd3SJim Ingham lldb::BreakpointResolverSP
114*33df7cd3SJim Ingham BreakpointResolverFileLine::CopyForBreakpoint (Breakpoint &breakpoint)
115*33df7cd3SJim Ingham {
116*33df7cd3SJim Ingham     lldb::BreakpointResolverSP ret_sp(new BreakpointResolverFileLine(&breakpoint,
117*33df7cd3SJim Ingham                                                                      m_file_spec,
118*33df7cd3SJim Ingham                                                                      m_line_number,
119*33df7cd3SJim Ingham                                                                      m_inlines,
120*33df7cd3SJim Ingham                                                                      m_skip_prologue));
121*33df7cd3SJim Ingham 
122*33df7cd3SJim Ingham     return ret_sp;
123*33df7cd3SJim Ingham }
124