1 //===-- SearchFilter.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 // C Includes
11 // C++ Includes
12 // Other libraries and framework includes
13 // Project includes
14
15 #include "lldb/lldb-private.h"
16 #include "lldb/Core/SearchFilter.h"
17 #include "lldb/Core/Module.h"
18 #include "lldb/Symbol/CompileUnit.h"
19 #include "lldb/Target/Target.h"
20
21 using namespace lldb;
22 using namespace lldb_private;
23
24 //----------------------------------------------------------------------
25 // SearchFilter constructor
26 //----------------------------------------------------------------------
Searcher()27 Searcher::Searcher ()
28 {
29
30 }
31
~Searcher()32 Searcher::~Searcher ()
33 {
34
35 }
36
37 void
GetDescription(Stream * s)38 Searcher::GetDescription (Stream *s)
39 {
40 }
41
42 //----------------------------------------------------------------------
43 // SearchFilter constructor
44 //----------------------------------------------------------------------
SearchFilter(const TargetSP & target_sp)45 SearchFilter::SearchFilter(const TargetSP &target_sp) :
46 m_target_sp (target_sp)
47 {
48 }
49
50 //----------------------------------------------------------------------
51 // SearchFilter copy constructor
52 //----------------------------------------------------------------------
SearchFilter(const SearchFilter & rhs)53 SearchFilter::SearchFilter(const SearchFilter& rhs) :
54 m_target_sp (rhs.m_target_sp)
55 {
56 }
57
58 //----------------------------------------------------------------------
59 // SearchFilter assignment operator
60 //----------------------------------------------------------------------
61 const SearchFilter&
operator =(const SearchFilter & rhs)62 SearchFilter::operator=(const SearchFilter& rhs)
63 {
64 m_target_sp = rhs.m_target_sp;
65 return *this;
66 }
67
68 //----------------------------------------------------------------------
69 // Destructor
70 //----------------------------------------------------------------------
~SearchFilter()71 SearchFilter::~SearchFilter()
72 {
73 }
74
75 bool
ModulePasses(const FileSpec & spec)76 SearchFilter::ModulePasses (const FileSpec &spec)
77 {
78 return true;
79 }
80
81 bool
ModulePasses(const ModuleSP & module_sp)82 SearchFilter::ModulePasses (const ModuleSP &module_sp)
83 {
84 return true;
85 }
86
87 bool
AddressPasses(Address & address)88 SearchFilter::AddressPasses (Address &address)
89 {
90 return true;
91 }
92
93 bool
CompUnitPasses(FileSpec & fileSpec)94 SearchFilter::CompUnitPasses (FileSpec &fileSpec)
95 {
96 return true;
97 }
98
99 bool
CompUnitPasses(CompileUnit & compUnit)100 SearchFilter::CompUnitPasses (CompileUnit &compUnit)
101 {
102 return true;
103 }
104
105 uint32_t
GetFilterRequiredItems()106 SearchFilter::GetFilterRequiredItems()
107 {
108 return (lldb::SymbolContextItem) 0;
109 }
110
111 void
GetDescription(Stream * s)112 SearchFilter::GetDescription (Stream *s)
113 {
114 }
115
116 void
Dump(Stream * s) const117 SearchFilter::Dump (Stream *s) const
118 {
119
120 }
121
122 lldb::SearchFilterSP
CopyForBreakpoint(Breakpoint & breakpoint)123 SearchFilter::CopyForBreakpoint (Breakpoint &breakpoint)
124 {
125 SearchFilterSP ret_sp = DoCopyForBreakpoint (breakpoint);
126 TargetSP target_sp = breakpoint.GetTargetSP();
127 ret_sp->SetTarget(target_sp);
128 return ret_sp;
129 }
130
131 //----------------------------------------------------------------------
132 // UTILITY Functions to help iterate down through the elements of the
133 // SymbolContext.
134 //----------------------------------------------------------------------
135
136 void
Search(Searcher & searcher)137 SearchFilter::Search (Searcher &searcher)
138 {
139 SymbolContext empty_sc;
140
141 if (!m_target_sp)
142 return;
143 empty_sc.target_sp = m_target_sp;
144
145 if (searcher.GetDepth() == Searcher::eDepthTarget)
146 searcher.SearchCallback (*this, empty_sc, NULL, false);
147 else
148 DoModuleIteration(empty_sc, searcher);
149 }
150
151 void
SearchInModuleList(Searcher & searcher,ModuleList & modules)152 SearchFilter::SearchInModuleList (Searcher &searcher, ModuleList &modules)
153 {
154 SymbolContext empty_sc;
155
156 if (!m_target_sp)
157 return;
158 empty_sc.target_sp = m_target_sp;
159
160 if (searcher.GetDepth() == Searcher::eDepthTarget)
161 searcher.SearchCallback (*this, empty_sc, NULL, false);
162 else
163 {
164 Mutex::Locker modules_locker(modules.GetMutex());
165 const size_t numModules = modules.GetSize();
166
167 for (size_t i = 0; i < numModules; i++)
168 {
169 ModuleSP module_sp(modules.GetModuleAtIndexUnlocked(i));
170 if (ModulePasses(module_sp))
171 {
172 if (DoModuleIteration(module_sp, searcher) == Searcher::eCallbackReturnStop)
173 return;
174 }
175 }
176 }
177 }
178
179
180 Searcher::CallbackReturn
DoModuleIteration(const lldb::ModuleSP & module_sp,Searcher & searcher)181 SearchFilter::DoModuleIteration (const lldb::ModuleSP& module_sp, Searcher &searcher)
182 {
183 SymbolContext matchingContext (m_target_sp, module_sp);
184 return DoModuleIteration(matchingContext, searcher);
185 }
186
187 Searcher::CallbackReturn
DoModuleIteration(const SymbolContext & context,Searcher & searcher)188 SearchFilter::DoModuleIteration (const SymbolContext &context, Searcher &searcher)
189 {
190 if (searcher.GetDepth () >= Searcher::eDepthModule)
191 {
192 if (context.module_sp)
193 {
194 if (searcher.GetDepth () == Searcher::eDepthModule)
195 {
196 SymbolContext matchingContext(context.module_sp.get());
197 searcher.SearchCallback (*this, matchingContext, NULL, false);
198 }
199 else
200 {
201 return DoCUIteration(context.module_sp, context, searcher);
202 }
203 }
204 else
205 {
206 const ModuleList &target_images = m_target_sp->GetImages();
207 Mutex::Locker modules_locker(target_images.GetMutex());
208
209 size_t n_modules = target_images.GetSize();
210 for (size_t i = 0; i < n_modules; i++)
211 {
212 // If this is the last level supplied, then call the callback directly,
213 // otherwise descend.
214 ModuleSP module_sp(target_images.GetModuleAtIndexUnlocked (i));
215 if (!ModulePasses (module_sp))
216 continue;
217
218 if (searcher.GetDepth () == Searcher::eDepthModule)
219 {
220 SymbolContext matchingContext(m_target_sp, module_sp);
221
222 Searcher::CallbackReturn shouldContinue = searcher.SearchCallback (*this, matchingContext, NULL, false);
223 if (shouldContinue == Searcher::eCallbackReturnStop
224 || shouldContinue == Searcher::eCallbackReturnPop)
225 return shouldContinue;
226 }
227 else
228 {
229 Searcher::CallbackReturn shouldContinue = DoCUIteration(module_sp, context, searcher);
230 if (shouldContinue == Searcher::eCallbackReturnStop)
231 return shouldContinue;
232 else if (shouldContinue == Searcher::eCallbackReturnPop)
233 continue;
234 }
235 }
236 }
237 }
238 return Searcher::eCallbackReturnContinue;
239 }
240
241 Searcher::CallbackReturn
DoCUIteration(const ModuleSP & module_sp,const SymbolContext & context,Searcher & searcher)242 SearchFilter::DoCUIteration (const ModuleSP &module_sp, const SymbolContext &context, Searcher &searcher)
243 {
244 Searcher::CallbackReturn shouldContinue;
245 if (context.comp_unit == NULL)
246 {
247 const size_t num_comp_units = module_sp->GetNumCompileUnits();
248 for (size_t i = 0; i < num_comp_units; i++)
249 {
250 CompUnitSP cu_sp (module_sp->GetCompileUnitAtIndex (i));
251 if (cu_sp)
252 {
253 if (!CompUnitPasses (*(cu_sp.get())))
254 continue;
255
256 if (searcher.GetDepth () == Searcher::eDepthCompUnit)
257 {
258 SymbolContext matchingContext(m_target_sp, module_sp, cu_sp.get());
259
260 shouldContinue = searcher.SearchCallback (*this, matchingContext, NULL, false);
261
262 if (shouldContinue == Searcher::eCallbackReturnPop)
263 return Searcher::eCallbackReturnContinue;
264 else if (shouldContinue == Searcher::eCallbackReturnStop)
265 return shouldContinue;
266 }
267 else
268 {
269 // FIXME Descend to block.
270 }
271 }
272 }
273 }
274 else
275 {
276 if (CompUnitPasses(*context.comp_unit))
277 {
278 SymbolContext matchingContext (m_target_sp, module_sp, context.comp_unit);
279 return searcher.SearchCallback (*this, matchingContext, NULL, false);
280 }
281 }
282 return Searcher::eCallbackReturnContinue;
283 }
284
285 Searcher::CallbackReturn
DoFunctionIteration(Function * function,const SymbolContext & context,Searcher & searcher)286 SearchFilter::DoFunctionIteration (Function *function, const SymbolContext &context, Searcher &searcher)
287 {
288 // FIXME: Implement...
289 return Searcher::eCallbackReturnContinue;
290 }
291
292 //----------------------------------------------------------------------
293 // SearchFilterForUnconstrainedSearches:
294 // Selects a shared library matching a given file spec, consulting the targets "black list".
295 //----------------------------------------------------------------------
296
297 bool
ModulePasses(const FileSpec & module_spec)298 SearchFilterForUnconstrainedSearches::ModulePasses (const FileSpec &module_spec)
299 {
300 if (m_target_sp->ModuleIsExcludedForUnconstrainedSearches (module_spec))
301 return false;
302 else
303 return true;
304 }
305
306 bool
ModulePasses(const lldb::ModuleSP & module_sp)307 SearchFilterForUnconstrainedSearches::ModulePasses (const lldb::ModuleSP &module_sp)
308 {
309 if (!module_sp)
310 return true;
311 else if (m_target_sp->ModuleIsExcludedForUnconstrainedSearches (module_sp))
312 return false;
313 else
314 return true;
315 }
316
317 lldb::SearchFilterSP
DoCopyForBreakpoint(Breakpoint & breakpoint)318 SearchFilterForUnconstrainedSearches::DoCopyForBreakpoint (Breakpoint &breakpoint)
319 {
320 SearchFilterSP ret_sp(new SearchFilterForUnconstrainedSearches(*this));
321 return ret_sp;
322 }
323
324 //----------------------------------------------------------------------
325 // SearchFilterByModule:
326 // Selects a shared library matching a given file spec
327 //----------------------------------------------------------------------
328
329 //----------------------------------------------------------------------
330 // SearchFilterByModule constructors
331 //----------------------------------------------------------------------
332
SearchFilterByModule(const lldb::TargetSP & target_sp,const FileSpec & module)333 SearchFilterByModule::SearchFilterByModule (const lldb::TargetSP &target_sp, const FileSpec &module) :
334 SearchFilter (target_sp),
335 m_module_spec (module)
336 {
337 }
338
339
340 //----------------------------------------------------------------------
341 // SearchFilterByModule copy constructor
342 //----------------------------------------------------------------------
SearchFilterByModule(const SearchFilterByModule & rhs)343 SearchFilterByModule::SearchFilterByModule(const SearchFilterByModule& rhs) :
344 SearchFilter (rhs),
345 m_module_spec (rhs.m_module_spec)
346 {
347 }
348
349 //----------------------------------------------------------------------
350 // SearchFilterByModule assignment operator
351 //----------------------------------------------------------------------
352 const SearchFilterByModule&
operator =(const SearchFilterByModule & rhs)353 SearchFilterByModule::operator=(const SearchFilterByModule& rhs)
354 {
355 m_target_sp = rhs.m_target_sp;
356 m_module_spec = rhs.m_module_spec;
357 return *this;
358 }
359
360 //----------------------------------------------------------------------
361 // Destructor
362 //----------------------------------------------------------------------
~SearchFilterByModule()363 SearchFilterByModule::~SearchFilterByModule()
364 {
365 }
366
367 bool
ModulePasses(const ModuleSP & module_sp)368 SearchFilterByModule::ModulePasses (const ModuleSP &module_sp)
369 {
370 if (module_sp && FileSpec::Equal(module_sp->GetFileSpec(), m_module_spec, false))
371 return true;
372 else
373 return false;
374 }
375
376 bool
ModulePasses(const FileSpec & spec)377 SearchFilterByModule::ModulePasses (const FileSpec &spec)
378 {
379 // Do a full match only if "spec" has a directory
380 const bool full_match = (bool)spec.GetDirectory();
381 return FileSpec::Equal(spec, m_module_spec, full_match);
382 }
383
384 bool
AddressPasses(Address & address)385 SearchFilterByModule::AddressPasses (Address &address)
386 {
387 // FIXME: Not yet implemented
388 return true;
389 }
390
391
392 bool
CompUnitPasses(FileSpec & fileSpec)393 SearchFilterByModule::CompUnitPasses (FileSpec &fileSpec)
394 {
395 return true;
396 }
397
398 bool
CompUnitPasses(CompileUnit & compUnit)399 SearchFilterByModule::CompUnitPasses (CompileUnit &compUnit)
400 {
401 return true;
402 }
403
404 void
Search(Searcher & searcher)405 SearchFilterByModule::Search (Searcher &searcher)
406 {
407 if (!m_target_sp)
408 return;
409
410 if (searcher.GetDepth() == Searcher::eDepthTarget)
411 {
412 SymbolContext empty_sc;
413 empty_sc.target_sp = m_target_sp;
414 searcher.SearchCallback (*this, empty_sc, NULL, false);
415 }
416
417 // If the module file spec is a full path, then we can just find the one
418 // filespec that passes. Otherwise, we need to go through all modules and
419 // find the ones that match the file name.
420
421 const ModuleList &target_modules = m_target_sp->GetImages();
422 Mutex::Locker modules_locker (target_modules.GetMutex());
423
424 const size_t num_modules = target_modules.GetSize ();
425 for (size_t i = 0; i < num_modules; i++)
426 {
427 Module* module = target_modules.GetModulePointerAtIndexUnlocked(i);
428 const bool full_match = (bool)m_module_spec.GetDirectory();
429 if (FileSpec::Equal (m_module_spec, module->GetFileSpec(), full_match))
430 {
431 SymbolContext matchingContext(m_target_sp, module->shared_from_this());
432 Searcher::CallbackReturn shouldContinue;
433
434 shouldContinue = DoModuleIteration(matchingContext, searcher);
435 if (shouldContinue == Searcher::eCallbackReturnStop)
436 return;
437 }
438 }
439 }
440
441 void
GetDescription(Stream * s)442 SearchFilterByModule::GetDescription (Stream *s)
443 {
444 s->PutCString(", module = ");
445 if (s->GetVerbose())
446 {
447 char buffer[2048];
448 m_module_spec.GetPath(buffer, 2047);
449 s->PutCString(buffer);
450 }
451 else
452 {
453 s->PutCString(m_module_spec.GetFilename().AsCString("<Unknown>"));
454 }
455 }
456
457 uint32_t
GetFilterRequiredItems()458 SearchFilterByModule::GetFilterRequiredItems()
459 {
460 return eSymbolContextModule;
461 }
462
463 void
Dump(Stream * s) const464 SearchFilterByModule::Dump (Stream *s) const
465 {
466
467 }
468
469 lldb::SearchFilterSP
DoCopyForBreakpoint(Breakpoint & breakpoint)470 SearchFilterByModule::DoCopyForBreakpoint (Breakpoint &breakpoint)
471 {
472 SearchFilterSP ret_sp(new SearchFilterByModule(*this));
473 return ret_sp;
474 }
475
476 //----------------------------------------------------------------------
477 // SearchFilterByModuleList:
478 // Selects a shared library matching a given file spec
479 //----------------------------------------------------------------------
480
481 //----------------------------------------------------------------------
482 // SearchFilterByModuleList constructors
483 //----------------------------------------------------------------------
484
SearchFilterByModuleList(const lldb::TargetSP & target_sp,const FileSpecList & module_list)485 SearchFilterByModuleList::SearchFilterByModuleList (const lldb::TargetSP &target_sp,
486 const FileSpecList &module_list) :
487 SearchFilter (target_sp),
488 m_module_spec_list (module_list)
489 {
490 }
491
492
493 //----------------------------------------------------------------------
494 // SearchFilterByModuleList copy constructor
495 //----------------------------------------------------------------------
SearchFilterByModuleList(const SearchFilterByModuleList & rhs)496 SearchFilterByModuleList::SearchFilterByModuleList(const SearchFilterByModuleList& rhs) :
497 SearchFilter (rhs),
498 m_module_spec_list (rhs.m_module_spec_list)
499 {
500 }
501
502 //----------------------------------------------------------------------
503 // SearchFilterByModuleList assignment operator
504 //----------------------------------------------------------------------
505 const SearchFilterByModuleList&
operator =(const SearchFilterByModuleList & rhs)506 SearchFilterByModuleList::operator=(const SearchFilterByModuleList& rhs)
507 {
508 m_target_sp = rhs.m_target_sp;
509 m_module_spec_list = rhs.m_module_spec_list;
510 return *this;
511 }
512
513 //----------------------------------------------------------------------
514 // Destructor
515 //----------------------------------------------------------------------
~SearchFilterByModuleList()516 SearchFilterByModuleList::~SearchFilterByModuleList()
517 {
518 }
519
520 bool
ModulePasses(const ModuleSP & module_sp)521 SearchFilterByModuleList::ModulePasses (const ModuleSP &module_sp)
522 {
523 if (m_module_spec_list.GetSize() == 0)
524 return true;
525
526 if (module_sp && m_module_spec_list.FindFileIndex(0, module_sp->GetFileSpec(), false) != UINT32_MAX)
527 return true;
528 else
529 return false;
530 }
531
532 bool
ModulePasses(const FileSpec & spec)533 SearchFilterByModuleList::ModulePasses (const FileSpec &spec)
534 {
535 if (m_module_spec_list.GetSize() == 0)
536 return true;
537
538 if (m_module_spec_list.FindFileIndex(0, spec, true) != UINT32_MAX)
539 return true;
540 else
541 return false;
542 }
543
544 bool
AddressPasses(Address & address)545 SearchFilterByModuleList::AddressPasses (Address &address)
546 {
547 // FIXME: Not yet implemented
548 return true;
549 }
550
551
552 bool
CompUnitPasses(FileSpec & fileSpec)553 SearchFilterByModuleList::CompUnitPasses (FileSpec &fileSpec)
554 {
555 return true;
556 }
557
558 bool
CompUnitPasses(CompileUnit & compUnit)559 SearchFilterByModuleList::CompUnitPasses (CompileUnit &compUnit)
560 {
561 return true;
562 }
563
564 void
Search(Searcher & searcher)565 SearchFilterByModuleList::Search (Searcher &searcher)
566 {
567 if (!m_target_sp)
568 return;
569
570 if (searcher.GetDepth() == Searcher::eDepthTarget)
571 {
572 SymbolContext empty_sc;
573 empty_sc.target_sp = m_target_sp;
574 searcher.SearchCallback (*this, empty_sc, NULL, false);
575 }
576
577 // If the module file spec is a full path, then we can just find the one
578 // filespec that passes. Otherwise, we need to go through all modules and
579 // find the ones that match the file name.
580
581 const ModuleList &target_modules = m_target_sp->GetImages();
582 Mutex::Locker modules_locker (target_modules.GetMutex());
583
584 const size_t num_modules = target_modules.GetSize ();
585 for (size_t i = 0; i < num_modules; i++)
586 {
587 Module* module = target_modules.GetModulePointerAtIndexUnlocked(i);
588 if (m_module_spec_list.FindFileIndex(0, module->GetFileSpec(), false) != UINT32_MAX)
589 {
590 SymbolContext matchingContext(m_target_sp, module->shared_from_this());
591 Searcher::CallbackReturn shouldContinue;
592
593 shouldContinue = DoModuleIteration(matchingContext, searcher);
594 if (shouldContinue == Searcher::eCallbackReturnStop)
595 return;
596 }
597 }
598 }
599
600 void
GetDescription(Stream * s)601 SearchFilterByModuleList::GetDescription (Stream *s)
602 {
603 size_t num_modules = m_module_spec_list.GetSize();
604 if (num_modules == 1)
605 {
606 s->Printf (", module = ");
607 if (s->GetVerbose())
608 {
609 char buffer[2048];
610 m_module_spec_list.GetFileSpecAtIndex(0).GetPath(buffer, 2047);
611 s->PutCString(buffer);
612 }
613 else
614 {
615 s->PutCString(m_module_spec_list.GetFileSpecAtIndex(0).GetFilename().AsCString("<Unknown>"));
616 }
617 }
618 else
619 {
620 s->Printf(", modules(%" PRIu64 ") = ", (uint64_t)num_modules);
621 for (size_t i = 0; i < num_modules; i++)
622 {
623 if (s->GetVerbose())
624 {
625 char buffer[2048];
626 m_module_spec_list.GetFileSpecAtIndex(i).GetPath(buffer, 2047);
627 s->PutCString(buffer);
628 }
629 else
630 {
631 s->PutCString(m_module_spec_list.GetFileSpecAtIndex(i).GetFilename().AsCString("<Unknown>"));
632 }
633 if (i != num_modules - 1)
634 s->PutCString (", ");
635 }
636 }
637 }
638
639 uint32_t
GetFilterRequiredItems()640 SearchFilterByModuleList::GetFilterRequiredItems()
641 {
642 return eSymbolContextModule;
643 }
644
645 void
Dump(Stream * s) const646 SearchFilterByModuleList::Dump (Stream *s) const
647 {
648
649 }
650
651 lldb::SearchFilterSP
DoCopyForBreakpoint(Breakpoint & breakpoint)652 SearchFilterByModuleList::DoCopyForBreakpoint (Breakpoint &breakpoint)
653 {
654 SearchFilterSP ret_sp(new SearchFilterByModuleList(*this));
655 return ret_sp;
656 }
657
658
659 //----------------------------------------------------------------------
660 // SearchFilterByModuleListAndCU:
661 // Selects a shared library matching a given file spec
662 //----------------------------------------------------------------------
663
664 //----------------------------------------------------------------------
665 // SearchFilterByModuleListAndCU constructors
666 //----------------------------------------------------------------------
667
SearchFilterByModuleListAndCU(const lldb::TargetSP & target_sp,const FileSpecList & module_list,const FileSpecList & cu_list)668 SearchFilterByModuleListAndCU::SearchFilterByModuleListAndCU (const lldb::TargetSP &target_sp,
669 const FileSpecList &module_list,
670 const FileSpecList &cu_list) :
671 SearchFilterByModuleList (target_sp, module_list),
672 m_cu_spec_list (cu_list)
673 {
674 }
675
676
677 //----------------------------------------------------------------------
678 // SearchFilterByModuleListAndCU copy constructor
679 //----------------------------------------------------------------------
SearchFilterByModuleListAndCU(const SearchFilterByModuleListAndCU & rhs)680 SearchFilterByModuleListAndCU::SearchFilterByModuleListAndCU(const SearchFilterByModuleListAndCU& rhs) :
681 SearchFilterByModuleList (rhs),
682 m_cu_spec_list (rhs.m_cu_spec_list)
683 {
684 }
685
686 //----------------------------------------------------------------------
687 // SearchFilterByModuleListAndCU assignment operator
688 //----------------------------------------------------------------------
689 const SearchFilterByModuleListAndCU&
operator =(const SearchFilterByModuleListAndCU & rhs)690 SearchFilterByModuleListAndCU::operator=(const SearchFilterByModuleListAndCU& rhs)
691 {
692 if (&rhs != this)
693 {
694 m_target_sp = rhs.m_target_sp;
695 m_module_spec_list = rhs.m_module_spec_list;
696 m_cu_spec_list = rhs.m_cu_spec_list;
697 }
698 return *this;
699 }
700
701 //----------------------------------------------------------------------
702 // Destructor
703 //----------------------------------------------------------------------
~SearchFilterByModuleListAndCU()704 SearchFilterByModuleListAndCU::~SearchFilterByModuleListAndCU()
705 {
706 }
707
708 bool
AddressPasses(Address & address)709 SearchFilterByModuleListAndCU::AddressPasses (Address &address)
710 {
711 return true;
712 }
713
714
715 bool
CompUnitPasses(FileSpec & fileSpec)716 SearchFilterByModuleListAndCU::CompUnitPasses (FileSpec &fileSpec)
717 {
718 return m_cu_spec_list.FindFileIndex(0, fileSpec, false) != UINT32_MAX;
719 }
720
721 bool
CompUnitPasses(CompileUnit & compUnit)722 SearchFilterByModuleListAndCU::CompUnitPasses (CompileUnit &compUnit)
723 {
724 bool in_cu_list = m_cu_spec_list.FindFileIndex(0, compUnit, false) != UINT32_MAX;
725 if (in_cu_list)
726 {
727 ModuleSP module_sp(compUnit.GetModule());
728 if (module_sp)
729 {
730 bool module_passes = SearchFilterByModuleList::ModulePasses(module_sp);
731 return module_passes;
732 }
733 else
734 return true;
735 }
736 else
737 return false;
738 }
739
740 void
Search(Searcher & searcher)741 SearchFilterByModuleListAndCU::Search (Searcher &searcher)
742 {
743 if (!m_target_sp)
744 return;
745
746 if (searcher.GetDepth() == Searcher::eDepthTarget)
747 {
748 SymbolContext empty_sc;
749 empty_sc.target_sp = m_target_sp;
750 searcher.SearchCallback (*this, empty_sc, NULL, false);
751 }
752
753 // If the module file spec is a full path, then we can just find the one
754 // filespec that passes. Otherwise, we need to go through all modules and
755 // find the ones that match the file name.
756
757 ModuleList matching_modules;
758 const ModuleList &target_images = m_target_sp->GetImages();
759 Mutex::Locker modules_locker(target_images.GetMutex());
760
761 const size_t num_modules = target_images.GetSize ();
762 bool no_modules_in_filter = m_module_spec_list.GetSize() == 0;
763 for (size_t i = 0; i < num_modules; i++)
764 {
765 lldb::ModuleSP module_sp = target_images.GetModuleAtIndexUnlocked(i);
766 if (no_modules_in_filter || m_module_spec_list.FindFileIndex(0, module_sp->GetFileSpec(), false) != UINT32_MAX)
767 {
768 SymbolContext matchingContext(m_target_sp, module_sp);
769 Searcher::CallbackReturn shouldContinue;
770
771 if (searcher.GetDepth() == Searcher::eDepthModule)
772 {
773 shouldContinue = DoModuleIteration(matchingContext, searcher);
774 if (shouldContinue == Searcher::eCallbackReturnStop)
775 return;
776 }
777 else
778 {
779 const size_t num_cu = module_sp->GetNumCompileUnits();
780 for (size_t cu_idx = 0; cu_idx < num_cu; cu_idx++)
781 {
782 CompUnitSP cu_sp = module_sp->GetCompileUnitAtIndex(cu_idx);
783 matchingContext.comp_unit = cu_sp.get();
784 if (matchingContext.comp_unit)
785 {
786 if (m_cu_spec_list.FindFileIndex(0, *matchingContext.comp_unit, false) != UINT32_MAX)
787 {
788 shouldContinue = DoCUIteration(module_sp, matchingContext, searcher);
789 if (shouldContinue == Searcher::eCallbackReturnStop)
790 return;
791 }
792 }
793 }
794 }
795 }
796 }
797 }
798
799 void
GetDescription(Stream * s)800 SearchFilterByModuleListAndCU::GetDescription (Stream *s)
801 {
802 size_t num_modules = m_module_spec_list.GetSize();
803 if (num_modules == 1)
804 {
805 s->Printf (", module = ");
806 if (s->GetVerbose())
807 {
808 char buffer[2048];
809 m_module_spec_list.GetFileSpecAtIndex(0).GetPath(buffer, 2047);
810 s->PutCString(buffer);
811 }
812 else
813 {
814 s->PutCString(m_module_spec_list.GetFileSpecAtIndex(0).GetFilename().AsCString("<Unknown>"));
815 }
816 }
817 else if (num_modules > 0)
818 {
819 s->Printf (", modules(%" PRIu64 ") = ", static_cast<uint64_t>(num_modules));
820 for (size_t i = 0; i < num_modules; i++)
821 {
822 if (s->GetVerbose())
823 {
824 char buffer[2048];
825 m_module_spec_list.GetFileSpecAtIndex(i).GetPath(buffer, 2047);
826 s->PutCString(buffer);
827 }
828 else
829 {
830 s->PutCString(m_module_spec_list.GetFileSpecAtIndex(i).GetFilename().AsCString("<Unknown>"));
831 }
832 if (i != num_modules - 1)
833 s->PutCString (", ");
834 }
835 }
836 }
837
838 uint32_t
GetFilterRequiredItems()839 SearchFilterByModuleListAndCU::GetFilterRequiredItems()
840 {
841 return eSymbolContextModule | eSymbolContextCompUnit;
842 }
843
844 void
Dump(Stream * s) const845 SearchFilterByModuleListAndCU::Dump (Stream *s) const
846 {
847
848 }
849
850 lldb::SearchFilterSP
DoCopyForBreakpoint(Breakpoint & breakpoint)851 SearchFilterByModuleListAndCU::DoCopyForBreakpoint (Breakpoint &breakpoint)
852 {
853 SearchFilterSP ret_sp(new SearchFilterByModuleListAndCU(*this));
854 return ret_sp;
855 }
856
857