1*c9af18a5SGreg Clayton //===-- CommandCompletions.cpp ----------------------------------*- C++ -*-===//
2*c9af18a5SGreg Clayton //
3*c9af18a5SGreg Clayton //                     The LLVM Compiler Infrastructure
4*c9af18a5SGreg Clayton //
5*c9af18a5SGreg Clayton // This file is distributed under the University of Illinois Open Source
6*c9af18a5SGreg Clayton // License. See LICENSE.TXT for details.
7*c9af18a5SGreg Clayton //
8*c9af18a5SGreg Clayton //===----------------------------------------------------------------------===//
9*c9af18a5SGreg Clayton 
10*c9af18a5SGreg Clayton 
11*c9af18a5SGreg Clayton // C Includes
12*c9af18a5SGreg Clayton // C++ Includes
13*c9af18a5SGreg Clayton // Other libraries and framework includes
14*c9af18a5SGreg Clayton // Project includes
15*c9af18a5SGreg Clayton #include "lldb/Core/Args.h"
16*c9af18a5SGreg Clayton #include "lldb/Interpreter/CommandInterpreter.h"
17*c9af18a5SGreg Clayton #include "lldb/Core/FileSpecList.h"
18*c9af18a5SGreg Clayton #include "lldb/Target/Target.h"
19*c9af18a5SGreg Clayton #include "lldb/Interpreter/CommandCompletions.h"
20*c9af18a5SGreg Clayton 
21*c9af18a5SGreg Clayton 
22*c9af18a5SGreg Clayton using namespace lldb_private;
23*c9af18a5SGreg Clayton 
24*c9af18a5SGreg Clayton CommandCompletions::CommonCompletionElement
25*c9af18a5SGreg Clayton CommandCompletions::g_common_completions[] =
26*c9af18a5SGreg Clayton {
27*c9af18a5SGreg Clayton     {eCustomCompletion,     NULL},
28*c9af18a5SGreg Clayton     {eSourceFileCompletion, CommandCompletions::SourceFiles},
29*c9af18a5SGreg Clayton     {eDiskFileCompletion,   NULL},
30*c9af18a5SGreg Clayton     {eSymbolCompletion,     CommandCompletions::Symbols},
31*c9af18a5SGreg Clayton     {eModuleCompletion,     CommandCompletions::Modules},
32*c9af18a5SGreg Clayton     {eNoCompletion,         NULL}      // This one has to be last in the list.
33*c9af18a5SGreg Clayton };
34*c9af18a5SGreg Clayton 
35*c9af18a5SGreg Clayton bool
36*c9af18a5SGreg Clayton CommandCompletions::InvokeCommonCompletionCallbacks (uint32_t completion_mask,
37*c9af18a5SGreg Clayton                                                 const char *completion_str,
38*c9af18a5SGreg Clayton                                                 int match_start_point,
39*c9af18a5SGreg Clayton                                                 int max_return_elements,
40*c9af18a5SGreg Clayton                                                 lldb_private::CommandInterpreter *interpreter,
41*c9af18a5SGreg Clayton                                                 SearchFilter *searcher,
42*c9af18a5SGreg Clayton                                                 lldb_private::StringList &matches)
43*c9af18a5SGreg Clayton {
44*c9af18a5SGreg Clayton     bool handled = false;
45*c9af18a5SGreg Clayton 
46*c9af18a5SGreg Clayton     if (completion_mask & eCustomCompletion)
47*c9af18a5SGreg Clayton         return false;
48*c9af18a5SGreg Clayton 
49*c9af18a5SGreg Clayton     for (int i = 0; ; i++)
50*c9af18a5SGreg Clayton     {
51*c9af18a5SGreg Clayton         if (g_common_completions[i].type == eNoCompletion)
52*c9af18a5SGreg Clayton             break;
53*c9af18a5SGreg Clayton          else if ((g_common_completions[i].type & completion_mask) == g_common_completions[i].type
54*c9af18a5SGreg Clayton                    && g_common_completions[i].callback != NULL)
55*c9af18a5SGreg Clayton          {
56*c9af18a5SGreg Clayton             handled = true;
57*c9af18a5SGreg Clayton             g_common_completions[i].callback (completion_str,
58*c9af18a5SGreg Clayton                                               match_start_point,
59*c9af18a5SGreg Clayton                                               max_return_elements,
60*c9af18a5SGreg Clayton                                               interpreter,
61*c9af18a5SGreg Clayton                                               searcher,
62*c9af18a5SGreg Clayton                                               matches);
63*c9af18a5SGreg Clayton         }
64*c9af18a5SGreg Clayton     }
65*c9af18a5SGreg Clayton     return handled;
66*c9af18a5SGreg Clayton }
67*c9af18a5SGreg Clayton 
68*c9af18a5SGreg Clayton int
69*c9af18a5SGreg Clayton CommandCompletions::SourceFiles (const char *partial_file_name,
70*c9af18a5SGreg Clayton                     int match_start_point,
71*c9af18a5SGreg Clayton                     int max_return_elements,
72*c9af18a5SGreg Clayton                     lldb_private::CommandInterpreter *interpreter,
73*c9af18a5SGreg Clayton                     SearchFilter *searcher,
74*c9af18a5SGreg Clayton                     lldb_private::StringList &matches)
75*c9af18a5SGreg Clayton {
76*c9af18a5SGreg Clayton     // Find some way to switch "include support files..."
77*c9af18a5SGreg Clayton     SourceFileCompleter completer (false, partial_file_name, match_start_point, max_return_elements, interpreter,
78*c9af18a5SGreg Clayton                                    matches);
79*c9af18a5SGreg Clayton 
80*c9af18a5SGreg Clayton     if (searcher == NULL)
81*c9af18a5SGreg Clayton     {
82*c9af18a5SGreg Clayton         lldb::TargetSP target_sp = interpreter->Context()->GetTarget()->GetSP();
83*c9af18a5SGreg Clayton         SearchFilter null_searcher (target_sp);
84*c9af18a5SGreg Clayton         completer.DoCompletion (&null_searcher);
85*c9af18a5SGreg Clayton     }
86*c9af18a5SGreg Clayton     else
87*c9af18a5SGreg Clayton     {
88*c9af18a5SGreg Clayton         completer.DoCompletion (searcher);
89*c9af18a5SGreg Clayton     }
90*c9af18a5SGreg Clayton     return matches.GetSize();
91*c9af18a5SGreg Clayton }
92*c9af18a5SGreg Clayton 
93*c9af18a5SGreg Clayton int
94*c9af18a5SGreg Clayton CommandCompletions::Modules (const char *partial_file_name,
95*c9af18a5SGreg Clayton                     int match_start_point,
96*c9af18a5SGreg Clayton                     int max_return_elements,
97*c9af18a5SGreg Clayton                     lldb_private::CommandInterpreter *interpreter,
98*c9af18a5SGreg Clayton                     SearchFilter *searcher,
99*c9af18a5SGreg Clayton                     lldb_private::StringList &matches)
100*c9af18a5SGreg Clayton {
101*c9af18a5SGreg Clayton     ModuleCompleter completer(partial_file_name, match_start_point, max_return_elements, interpreter, matches);
102*c9af18a5SGreg Clayton 
103*c9af18a5SGreg Clayton     if (searcher == NULL)
104*c9af18a5SGreg Clayton     {
105*c9af18a5SGreg Clayton         lldb::TargetSP target_sp = interpreter->Context()->GetTarget()->GetSP();
106*c9af18a5SGreg Clayton         SearchFilter null_searcher (target_sp);
107*c9af18a5SGreg Clayton         completer.DoCompletion (&null_searcher);
108*c9af18a5SGreg Clayton     }
109*c9af18a5SGreg Clayton     else
110*c9af18a5SGreg Clayton     {
111*c9af18a5SGreg Clayton         completer.DoCompletion (searcher);
112*c9af18a5SGreg Clayton     }
113*c9af18a5SGreg Clayton     return matches.GetSize();
114*c9af18a5SGreg Clayton }
115*c9af18a5SGreg Clayton 
116*c9af18a5SGreg Clayton int
117*c9af18a5SGreg Clayton CommandCompletions::Symbols (const char *partial_file_name,
118*c9af18a5SGreg Clayton                     int match_start_point,
119*c9af18a5SGreg Clayton                     int max_return_elements,
120*c9af18a5SGreg Clayton                     lldb_private::CommandInterpreter *interpreter,
121*c9af18a5SGreg Clayton                     SearchFilter *searcher,
122*c9af18a5SGreg Clayton                     lldb_private::StringList &matches)
123*c9af18a5SGreg Clayton {
124*c9af18a5SGreg Clayton     SymbolCompleter completer(partial_file_name, match_start_point, max_return_elements, interpreter, matches);
125*c9af18a5SGreg Clayton 
126*c9af18a5SGreg Clayton     if (searcher == NULL)
127*c9af18a5SGreg Clayton     {
128*c9af18a5SGreg Clayton         lldb::TargetSP target_sp = interpreter->Context()->GetTarget()->GetSP();
129*c9af18a5SGreg Clayton         SearchFilter null_searcher (target_sp);
130*c9af18a5SGreg Clayton         completer.DoCompletion (&null_searcher);
131*c9af18a5SGreg Clayton     }
132*c9af18a5SGreg Clayton     else
133*c9af18a5SGreg Clayton     {
134*c9af18a5SGreg Clayton         completer.DoCompletion (searcher);
135*c9af18a5SGreg Clayton     }
136*c9af18a5SGreg Clayton     return matches.GetSize();
137*c9af18a5SGreg Clayton }
138*c9af18a5SGreg Clayton 
139*c9af18a5SGreg Clayton CommandCompletions::Completer::Completer (
140*c9af18a5SGreg Clayton     const char *completion_str,
141*c9af18a5SGreg Clayton     int match_start_point,
142*c9af18a5SGreg Clayton     int max_return_elements,
143*c9af18a5SGreg Clayton     CommandInterpreter *interpreter,
144*c9af18a5SGreg Clayton     StringList &matches
145*c9af18a5SGreg Clayton ) :
146*c9af18a5SGreg Clayton     m_completion_str (completion_str),
147*c9af18a5SGreg Clayton     m_match_start_point (match_start_point),
148*c9af18a5SGreg Clayton     m_max_return_elements (max_return_elements),
149*c9af18a5SGreg Clayton     m_interpreter (interpreter),
150*c9af18a5SGreg Clayton     m_matches (matches)
151*c9af18a5SGreg Clayton {
152*c9af18a5SGreg Clayton }
153*c9af18a5SGreg Clayton 
154*c9af18a5SGreg Clayton CommandCompletions::Completer::~Completer ()
155*c9af18a5SGreg Clayton {
156*c9af18a5SGreg Clayton 
157*c9af18a5SGreg Clayton }
158*c9af18a5SGreg Clayton 
159*c9af18a5SGreg Clayton //----------------------------------------------------------------------
160*c9af18a5SGreg Clayton // SourceFileCompleter
161*c9af18a5SGreg Clayton //----------------------------------------------------------------------
162*c9af18a5SGreg Clayton 
163*c9af18a5SGreg Clayton CommandCompletions::SourceFileCompleter::SourceFileCompleter (
164*c9af18a5SGreg Clayton     bool include_support_files,
165*c9af18a5SGreg Clayton     const char *completion_str,
166*c9af18a5SGreg Clayton     int match_start_point,
167*c9af18a5SGreg Clayton     int max_return_elements,
168*c9af18a5SGreg Clayton     CommandInterpreter *interpreter,
169*c9af18a5SGreg Clayton     StringList &matches
170*c9af18a5SGreg Clayton ) :
171*c9af18a5SGreg Clayton     CommandCompletions::Completer (completion_str, match_start_point, max_return_elements, interpreter, matches),
172*c9af18a5SGreg Clayton     m_include_support_files (include_support_files),
173*c9af18a5SGreg Clayton     m_matching_files()
174*c9af18a5SGreg Clayton {
175*c9af18a5SGreg Clayton     FileSpec partial_spec (m_completion_str.c_str());
176*c9af18a5SGreg Clayton     m_file_name = partial_spec.GetFilename().GetCString();
177*c9af18a5SGreg Clayton     m_dir_name = partial_spec.GetDirectory().GetCString();
178*c9af18a5SGreg Clayton }
179*c9af18a5SGreg Clayton 
180*c9af18a5SGreg Clayton Searcher::Depth
181*c9af18a5SGreg Clayton CommandCompletions::SourceFileCompleter::GetDepth()
182*c9af18a5SGreg Clayton {
183*c9af18a5SGreg Clayton     return eDepthCompUnit;
184*c9af18a5SGreg Clayton }
185*c9af18a5SGreg Clayton 
186*c9af18a5SGreg Clayton Searcher::CallbackReturn
187*c9af18a5SGreg Clayton CommandCompletions::SourceFileCompleter::SearchCallback (
188*c9af18a5SGreg Clayton     SearchFilter &filter,
189*c9af18a5SGreg Clayton     SymbolContext &context,
190*c9af18a5SGreg Clayton     Address *addr,
191*c9af18a5SGreg Clayton     bool complete
192*c9af18a5SGreg Clayton )
193*c9af18a5SGreg Clayton {
194*c9af18a5SGreg Clayton     if (context.comp_unit != NULL)
195*c9af18a5SGreg Clayton     {
196*c9af18a5SGreg Clayton         if (m_include_support_files)
197*c9af18a5SGreg Clayton         {
198*c9af18a5SGreg Clayton             FileSpecList supporting_files = context.comp_unit->GetSupportFiles();
199*c9af18a5SGreg Clayton             for (size_t sfiles = 0; sfiles < supporting_files.GetSize(); sfiles++)
200*c9af18a5SGreg Clayton             {
201*c9af18a5SGreg Clayton                 const FileSpec &sfile_spec = supporting_files.GetFileSpecAtIndex(sfiles);
202*c9af18a5SGreg Clayton                 const char *sfile_file_name = sfile_spec.GetFilename().GetCString();
203*c9af18a5SGreg Clayton                 const char *sfile_dir_name = sfile_spec.GetFilename().GetCString();
204*c9af18a5SGreg Clayton                 bool match = false;
205*c9af18a5SGreg Clayton                 if (m_file_name && sfile_file_name
206*c9af18a5SGreg Clayton                     && strstr (sfile_file_name, m_file_name) == sfile_file_name)
207*c9af18a5SGreg Clayton                     match = true;
208*c9af18a5SGreg Clayton                 if (match && m_dir_name && sfile_dir_name
209*c9af18a5SGreg Clayton                     && strstr (sfile_dir_name, m_dir_name) != sfile_dir_name)
210*c9af18a5SGreg Clayton                     match = false;
211*c9af18a5SGreg Clayton 
212*c9af18a5SGreg Clayton                 if (match)
213*c9af18a5SGreg Clayton                 {
214*c9af18a5SGreg Clayton                     m_matching_files.AppendIfUnique(sfile_spec);
215*c9af18a5SGreg Clayton                 }
216*c9af18a5SGreg Clayton             }
217*c9af18a5SGreg Clayton 
218*c9af18a5SGreg Clayton         }
219*c9af18a5SGreg Clayton         else
220*c9af18a5SGreg Clayton         {
221*c9af18a5SGreg Clayton             const char *cur_file_name = context.comp_unit->GetFilename().GetCString();
222*c9af18a5SGreg Clayton             const char *cur_dir_name = context.comp_unit->GetDirectory().GetCString();
223*c9af18a5SGreg Clayton 
224*c9af18a5SGreg Clayton             bool match = false;
225*c9af18a5SGreg Clayton             if (m_file_name && cur_file_name
226*c9af18a5SGreg Clayton                 && strstr (cur_file_name, m_file_name) == cur_file_name)
227*c9af18a5SGreg Clayton                 match = true;
228*c9af18a5SGreg Clayton 
229*c9af18a5SGreg Clayton             if (match && m_dir_name && cur_dir_name
230*c9af18a5SGreg Clayton                 && strstr (cur_dir_name, m_dir_name) != cur_dir_name)
231*c9af18a5SGreg Clayton                 match = false;
232*c9af18a5SGreg Clayton 
233*c9af18a5SGreg Clayton             if (match)
234*c9af18a5SGreg Clayton             {
235*c9af18a5SGreg Clayton                 m_matching_files.AppendIfUnique(context.comp_unit);
236*c9af18a5SGreg Clayton             }
237*c9af18a5SGreg Clayton         }
238*c9af18a5SGreg Clayton     }
239*c9af18a5SGreg Clayton     return Searcher::eCallbackReturnContinue;
240*c9af18a5SGreg Clayton }
241*c9af18a5SGreg Clayton 
242*c9af18a5SGreg Clayton size_t
243*c9af18a5SGreg Clayton CommandCompletions::SourceFileCompleter::DoCompletion (SearchFilter *filter)
244*c9af18a5SGreg Clayton {
245*c9af18a5SGreg Clayton     filter->Search (*this);
246*c9af18a5SGreg Clayton     // Now convert the filelist to completions:
247*c9af18a5SGreg Clayton     for (size_t i = 0; i < m_matching_files.GetSize(); i++)
248*c9af18a5SGreg Clayton     {
249*c9af18a5SGreg Clayton         m_matches.AppendString (m_matching_files.GetFileSpecAtIndex(i).GetFilename().GetCString());
250*c9af18a5SGreg Clayton     }
251*c9af18a5SGreg Clayton     return m_matches.GetSize();
252*c9af18a5SGreg Clayton 
253*c9af18a5SGreg Clayton }
254*c9af18a5SGreg Clayton 
255*c9af18a5SGreg Clayton //----------------------------------------------------------------------
256*c9af18a5SGreg Clayton // SymbolCompleter
257*c9af18a5SGreg Clayton //----------------------------------------------------------------------
258*c9af18a5SGreg Clayton 
259*c9af18a5SGreg Clayton static bool
260*c9af18a5SGreg Clayton regex_chars (const char comp)
261*c9af18a5SGreg Clayton {
262*c9af18a5SGreg Clayton     if (comp == '[' || comp == ']' || comp == '(' || comp == ')')
263*c9af18a5SGreg Clayton         return true;
264*c9af18a5SGreg Clayton     else
265*c9af18a5SGreg Clayton         return false;
266*c9af18a5SGreg Clayton }
267*c9af18a5SGreg Clayton CommandCompletions::SymbolCompleter::SymbolCompleter (
268*c9af18a5SGreg Clayton     const char *completion_str,
269*c9af18a5SGreg Clayton     int match_start_point,
270*c9af18a5SGreg Clayton     int max_return_elements,
271*c9af18a5SGreg Clayton     CommandInterpreter *interpreter,
272*c9af18a5SGreg Clayton     StringList &matches
273*c9af18a5SGreg Clayton ) :
274*c9af18a5SGreg Clayton     CommandCompletions::Completer (completion_str, match_start_point, max_return_elements, interpreter, matches)
275*c9af18a5SGreg Clayton {
276*c9af18a5SGreg Clayton     std::string regex_str ("^");
277*c9af18a5SGreg Clayton     regex_str.append(completion_str);
278*c9af18a5SGreg Clayton     regex_str.append(".*");
279*c9af18a5SGreg Clayton     std::string::iterator pos;
280*c9af18a5SGreg Clayton 
281*c9af18a5SGreg Clayton     pos = find_if(regex_str.begin(), regex_str.end(), regex_chars);
282*c9af18a5SGreg Clayton     while (pos < regex_str.end()) {
283*c9af18a5SGreg Clayton         pos = regex_str.insert(pos, '\\');
284*c9af18a5SGreg Clayton         pos += 2;
285*c9af18a5SGreg Clayton         pos = find_if(pos, regex_str.end(), regex_chars);
286*c9af18a5SGreg Clayton     }
287*c9af18a5SGreg Clayton     m_regex.Compile(regex_str.c_str());
288*c9af18a5SGreg Clayton }
289*c9af18a5SGreg Clayton 
290*c9af18a5SGreg Clayton Searcher::Depth
291*c9af18a5SGreg Clayton CommandCompletions::SymbolCompleter::GetDepth()
292*c9af18a5SGreg Clayton {
293*c9af18a5SGreg Clayton     return eDepthModule;
294*c9af18a5SGreg Clayton }
295*c9af18a5SGreg Clayton 
296*c9af18a5SGreg Clayton Searcher::CallbackReturn
297*c9af18a5SGreg Clayton CommandCompletions::SymbolCompleter::SearchCallback (
298*c9af18a5SGreg Clayton     SearchFilter &filter,
299*c9af18a5SGreg Clayton     SymbolContext &context,
300*c9af18a5SGreg Clayton     Address *addr,
301*c9af18a5SGreg Clayton     bool complete
302*c9af18a5SGreg Clayton )
303*c9af18a5SGreg Clayton {
304*c9af18a5SGreg Clayton     SymbolContextList func_list;
305*c9af18a5SGreg Clayton     SymbolContextList sym_list;
306*c9af18a5SGreg Clayton 
307*c9af18a5SGreg Clayton     if (context.module_sp != NULL)
308*c9af18a5SGreg Clayton     {
309*c9af18a5SGreg Clayton         if (context.module_sp)
310*c9af18a5SGreg Clayton         {
311*c9af18a5SGreg Clayton             context.module_sp->FindSymbolsMatchingRegExAndType (m_regex, lldb::eSymbolTypeCode, sym_list);
312*c9af18a5SGreg Clayton             context.module_sp->FindFunctions (m_regex, true, func_list);
313*c9af18a5SGreg Clayton         }
314*c9af18a5SGreg Clayton 
315*c9af18a5SGreg Clayton         SymbolContext sc;
316*c9af18a5SGreg Clayton         // Now add the functions & symbols to the list - only add if unique:
317*c9af18a5SGreg Clayton         for (int i = 0; i < func_list.GetSize(); i++)
318*c9af18a5SGreg Clayton         {
319*c9af18a5SGreg Clayton             if (func_list.GetContextAtIndex(i, sc))
320*c9af18a5SGreg Clayton             {
321*c9af18a5SGreg Clayton                 if (sc.function)
322*c9af18a5SGreg Clayton                 {
323*c9af18a5SGreg Clayton                     m_match_set.insert (sc.function->GetMangled().GetDemangledName());
324*c9af18a5SGreg Clayton                 }
325*c9af18a5SGreg Clayton             }
326*c9af18a5SGreg Clayton         }
327*c9af18a5SGreg Clayton 
328*c9af18a5SGreg Clayton         for (int i = 0; i < sym_list.GetSize(); i++)
329*c9af18a5SGreg Clayton         {
330*c9af18a5SGreg Clayton             if (sym_list.GetContextAtIndex(i, sc))
331*c9af18a5SGreg Clayton             {
332*c9af18a5SGreg Clayton                 if (sc.symbol && sc.symbol->GetAddressRangePtr())
333*c9af18a5SGreg Clayton                 {
334*c9af18a5SGreg Clayton                     m_match_set.insert (sc.symbol->GetMangled().GetDemangledName());
335*c9af18a5SGreg Clayton                 }
336*c9af18a5SGreg Clayton             }
337*c9af18a5SGreg Clayton         }
338*c9af18a5SGreg Clayton     }
339*c9af18a5SGreg Clayton     return Searcher::eCallbackReturnContinue;
340*c9af18a5SGreg Clayton }
341*c9af18a5SGreg Clayton 
342*c9af18a5SGreg Clayton size_t
343*c9af18a5SGreg Clayton CommandCompletions::SymbolCompleter::DoCompletion (SearchFilter *filter)
344*c9af18a5SGreg Clayton {
345*c9af18a5SGreg Clayton     filter->Search (*this);
346*c9af18a5SGreg Clayton     collection::iterator pos = m_match_set.begin(), end = m_match_set.end();
347*c9af18a5SGreg Clayton     for (pos = m_match_set.begin(); pos != end; pos++)
348*c9af18a5SGreg Clayton         m_matches.AppendString((*pos).GetCString());
349*c9af18a5SGreg Clayton 
350*c9af18a5SGreg Clayton     return m_matches.GetSize();
351*c9af18a5SGreg Clayton }
352*c9af18a5SGreg Clayton 
353*c9af18a5SGreg Clayton //----------------------------------------------------------------------
354*c9af18a5SGreg Clayton // ModuleCompleter
355*c9af18a5SGreg Clayton //----------------------------------------------------------------------
356*c9af18a5SGreg Clayton CommandCompletions::ModuleCompleter::ModuleCompleter (
357*c9af18a5SGreg Clayton     const char *completion_str,
358*c9af18a5SGreg Clayton     int match_start_point,
359*c9af18a5SGreg Clayton     int max_return_elements,
360*c9af18a5SGreg Clayton     CommandInterpreter *interpreter,
361*c9af18a5SGreg Clayton     StringList &matches
362*c9af18a5SGreg Clayton ) :
363*c9af18a5SGreg Clayton     CommandCompletions::Completer (completion_str, match_start_point, max_return_elements, interpreter, matches)
364*c9af18a5SGreg Clayton {
365*c9af18a5SGreg Clayton     FileSpec partial_spec (m_completion_str.c_str());
366*c9af18a5SGreg Clayton     m_file_name = partial_spec.GetFilename().GetCString();
367*c9af18a5SGreg Clayton     m_dir_name = partial_spec.GetDirectory().GetCString();
368*c9af18a5SGreg Clayton }
369*c9af18a5SGreg Clayton 
370*c9af18a5SGreg Clayton Searcher::Depth
371*c9af18a5SGreg Clayton CommandCompletions::ModuleCompleter::GetDepth()
372*c9af18a5SGreg Clayton {
373*c9af18a5SGreg Clayton     return eDepthModule;
374*c9af18a5SGreg Clayton }
375*c9af18a5SGreg Clayton 
376*c9af18a5SGreg Clayton Searcher::CallbackReturn
377*c9af18a5SGreg Clayton CommandCompletions::ModuleCompleter::SearchCallback (
378*c9af18a5SGreg Clayton     SearchFilter &filter,
379*c9af18a5SGreg Clayton     SymbolContext &context,
380*c9af18a5SGreg Clayton     Address *addr,
381*c9af18a5SGreg Clayton     bool complete
382*c9af18a5SGreg Clayton )
383*c9af18a5SGreg Clayton {
384*c9af18a5SGreg Clayton     if (context.module_sp != NULL)
385*c9af18a5SGreg Clayton     {
386*c9af18a5SGreg Clayton         const char *cur_file_name = context.module_sp->GetFileSpec().GetFilename().GetCString();
387*c9af18a5SGreg Clayton         const char *cur_dir_name = context.module_sp->GetFileSpec().GetDirectory().GetCString();
388*c9af18a5SGreg Clayton 
389*c9af18a5SGreg Clayton         bool match = false;
390*c9af18a5SGreg Clayton         if (m_file_name && cur_file_name
391*c9af18a5SGreg Clayton             && strstr (cur_file_name, m_file_name) == cur_file_name)
392*c9af18a5SGreg Clayton             match = true;
393*c9af18a5SGreg Clayton 
394*c9af18a5SGreg Clayton         if (match && m_dir_name && cur_dir_name
395*c9af18a5SGreg Clayton             && strstr (cur_dir_name, m_dir_name) != cur_dir_name)
396*c9af18a5SGreg Clayton             match = false;
397*c9af18a5SGreg Clayton 
398*c9af18a5SGreg Clayton         if (match)
399*c9af18a5SGreg Clayton         {
400*c9af18a5SGreg Clayton             m_matches.AppendString (cur_file_name);
401*c9af18a5SGreg Clayton         }
402*c9af18a5SGreg Clayton     }
403*c9af18a5SGreg Clayton     return Searcher::eCallbackReturnContinue;
404*c9af18a5SGreg Clayton }
405*c9af18a5SGreg Clayton 
406*c9af18a5SGreg Clayton size_t
407*c9af18a5SGreg Clayton CommandCompletions::ModuleCompleter::DoCompletion (SearchFilter *filter)
408*c9af18a5SGreg Clayton {
409*c9af18a5SGreg Clayton     filter->Search (*this);
410*c9af18a5SGreg Clayton     return m_matches.GetSize();
411*c9af18a5SGreg Clayton }
412*c9af18a5SGreg Clayton 
413*c9af18a5SGreg Clayton 
414*c9af18a5SGreg Clayton 
415