1254721Semaste//===-- FileSpecList.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#include "lldb/Core/FileSpecList.h"
10254721Semaste#include "lldb/Core/Stream.h"
11254721Semaste#include <algorithm>
12254721Semaste
13254721Semasteusing namespace lldb_private;
14254721Semasteusing namespace std;
15254721Semaste
16254721Semaste//------------------------------------------------------------------
17254721Semaste// Default constructor
18254721Semaste//------------------------------------------------------------------
19254721SemasteFileSpecList::FileSpecList() :
20254721Semaste    m_files()
21254721Semaste{
22254721Semaste}
23254721Semaste
24254721Semaste//------------------------------------------------------------------
25254721Semaste// Copy constructor
26254721Semaste//------------------------------------------------------------------
27254721SemasteFileSpecList::FileSpecList(const FileSpecList& rhs) :
28254721Semaste    m_files(rhs.m_files)
29254721Semaste{
30254721Semaste}
31254721Semaste
32254721Semaste//------------------------------------------------------------------
33254721Semaste// Destructor
34254721Semaste//------------------------------------------------------------------
35254721SemasteFileSpecList::~FileSpecList()
36254721Semaste{
37254721Semaste}
38254721Semaste
39254721Semaste//------------------------------------------------------------------
40254721Semaste// Assignment operator
41254721Semaste//------------------------------------------------------------------
42254721Semasteconst FileSpecList&
43254721SemasteFileSpecList::operator= (const FileSpecList& rhs)
44254721Semaste{
45254721Semaste    if (this != &rhs)
46254721Semaste        m_files = rhs.m_files;
47254721Semaste    return *this;
48254721Semaste}
49254721Semaste
50254721Semaste//------------------------------------------------------------------
51254721Semaste// Append the "file_spec" to the end of the file spec list.
52254721Semaste//------------------------------------------------------------------
53254721Semastevoid
54254721SemasteFileSpecList::Append(const FileSpec &file_spec)
55254721Semaste{
56254721Semaste    m_files.push_back(file_spec);
57254721Semaste}
58254721Semaste
59254721Semaste//------------------------------------------------------------------
60254721Semaste// Only append the "file_spec" if this list doesn't already contain
61254721Semaste// it.
62254721Semaste//
63254721Semaste// Returns true if "file_spec" was added, false if this list already
64254721Semaste// contained a copy of "file_spec".
65254721Semaste//------------------------------------------------------------------
66254721Semastebool
67254721SemasteFileSpecList::AppendIfUnique(const FileSpec &file_spec)
68254721Semaste{
69254721Semaste    collection::iterator pos, end = m_files.end();
70254721Semaste    if (find(m_files.begin(), end, file_spec) == end)
71254721Semaste    {
72254721Semaste        m_files.push_back(file_spec);
73254721Semaste        return true;
74254721Semaste    }
75254721Semaste    return false;
76254721Semaste}
77254721Semaste
78254721Semaste//------------------------------------------------------------------
79254721Semaste// Clears the file list.
80254721Semaste//------------------------------------------------------------------
81254721Semastevoid
82254721SemasteFileSpecList::Clear()
83254721Semaste{
84254721Semaste    m_files.clear();
85254721Semaste}
86254721Semaste
87254721Semaste//------------------------------------------------------------------
88254721Semaste// Dumps the file list to the supplied stream pointer "s".
89254721Semaste//------------------------------------------------------------------
90254721Semastevoid
91254721SemasteFileSpecList::Dump(Stream *s, const char *separator_cstr) const
92254721Semaste{
93254721Semaste    collection::const_iterator pos, end = m_files.end();
94254721Semaste    for (pos = m_files.begin(); pos != end; ++pos)
95254721Semaste    {
96254721Semaste        pos->Dump(s);
97254721Semaste        if (separator_cstr && ((pos + 1) != end))
98254721Semaste            s->PutCString(separator_cstr);
99254721Semaste    }
100254721Semaste}
101254721Semaste
102254721Semaste//------------------------------------------------------------------
103254721Semaste// Find the index of the file in the file spec list that matches
104254721Semaste// "file_spec" starting "start_idx" entries into the file spec list.
105254721Semaste//
106254721Semaste// Returns the valid index of the file that matches "file_spec" if
107254721Semaste// it is found, else UINT32_MAX is returned.
108254721Semaste//------------------------------------------------------------------
109254721Semastesize_t
110254721SemasteFileSpecList::FindFileIndex (size_t start_idx, const FileSpec &file_spec, bool full) const
111254721Semaste{
112254721Semaste    const size_t num_files = m_files.size();
113254721Semaste
114254721Semaste    // When looking for files, we will compare only the filename if the
115254721Semaste    // FILE_SPEC argument is empty
116254721Semaste    bool compare_filename_only = file_spec.GetDirectory().IsEmpty();
117254721Semaste
118254721Semaste    for (size_t idx = start_idx; idx < num_files; ++idx)
119254721Semaste    {
120254721Semaste        if (compare_filename_only)
121254721Semaste        {
122254721Semaste            if (m_files[idx].GetFilename() == file_spec.GetFilename())
123254721Semaste                return idx;
124254721Semaste        }
125254721Semaste        else
126254721Semaste        {
127254721Semaste            if (FileSpec::Equal (m_files[idx], file_spec, full))
128254721Semaste                return idx;
129254721Semaste        }
130254721Semaste    }
131254721Semaste
132254721Semaste    // We didn't find the file, return an invalid index
133254721Semaste    return UINT32_MAX;
134254721Semaste}
135254721Semaste
136254721Semaste//------------------------------------------------------------------
137254721Semaste// Returns the FileSpec object at index "idx". If "idx" is out of
138254721Semaste// range, then an empty FileSpec object will be returned.
139254721Semaste//------------------------------------------------------------------
140254721Semasteconst FileSpec &
141254721SemasteFileSpecList::GetFileSpecAtIndex(size_t idx) const
142254721Semaste{
143254721Semaste
144254721Semaste    if (idx < m_files.size())
145254721Semaste        return m_files[idx];
146254721Semaste    static FileSpec g_empty_file_spec;
147254721Semaste    return g_empty_file_spec;
148254721Semaste}
149254721Semaste
150254721Semasteconst FileSpec *
151254721SemasteFileSpecList::GetFileSpecPointerAtIndex(size_t idx) const
152254721Semaste{
153254721Semaste    if (idx < m_files.size())
154254721Semaste        return &m_files[idx];
155254721Semaste    return NULL;
156254721Semaste}
157254721Semaste
158254721Semaste//------------------------------------------------------------------
159254721Semaste// Return the size in bytes that this object takes in memory. This
160254721Semaste// returns the size in bytes of this object's member variables and
161254721Semaste// any FileSpec objects its member variables contain, the result
162254721Semaste// doesn't not include the string values for the directories any
163254721Semaste// filenames as those are in shared string pools.
164254721Semaste//------------------------------------------------------------------
165254721Semastesize_t
166254721SemasteFileSpecList::MemorySize () const
167254721Semaste{
168254721Semaste    size_t mem_size = sizeof(FileSpecList);
169254721Semaste    collection::const_iterator pos, end = m_files.end();
170254721Semaste    for (pos = m_files.begin(); pos != end; ++pos)
171254721Semaste    {
172254721Semaste        mem_size += pos->MemorySize();
173254721Semaste    }
174254721Semaste
175254721Semaste    return mem_size;
176254721Semaste}
177254721Semaste
178254721Semaste//------------------------------------------------------------------
179254721Semaste// Return the number of files in the file spec list.
180254721Semaste//------------------------------------------------------------------
181254721Semastesize_t
182254721SemasteFileSpecList::GetSize() const
183254721Semaste{
184254721Semaste    return m_files.size();
185254721Semaste}
186254721Semaste
187254721Semastesize_t
188254721SemasteFileSpecList::GetFilesMatchingPartialPath (const char *path, bool dir_okay, FileSpecList &matches)
189254721Semaste{
190254721Semaste#if 0  // FIXME: Just sketching...
191254721Semaste    matches.Clear();
192254721Semaste    FileSpec path_spec = FileSpec (path);
193254721Semaste    if (path_spec.Exists ())
194254721Semaste    {
195254721Semaste        FileSpec::FileType type = path_spec.GetFileType();
196254721Semaste        if (type == FileSpec::eFileTypeSymbolicLink)
197254721Semaste            // Shouldn't there be a Resolve on a file spec that real-path's it?
198254721Semaste        {
199254721Semaste        }
200254721Semaste
201254721Semaste        if (type == FileSpec::eFileTypeRegular
202254721Semaste            || (type == FileSpec::eFileTypeDirectory && dir_okay))
203254721Semaste        {
204254721Semaste            matches.Append (path_spec);
205254721Semaste            return 1;
206254721Semaste        }
207254721Semaste        else if (type == FileSpec::eFileTypeDirectory)
208254721Semaste        {
209254721Semaste            // Fill the match list with all the files in the directory:
210254721Semaste
211254721Semaste        }
212254721Semaste        else
213254721Semaste        {
214254721Semaste            return 0;
215254721Semaste        }
216254721Semaste
217254721Semaste    }
218254721Semaste    else
219254721Semaste    {
220254721Semaste        ConstString dir_name = path_spec.GetDirectory();
221254721Semaste        Constring file_name = GetFilename();
222254721Semaste        if (dir_name == NULL)
223254721Semaste        {
224254721Semaste            // Match files in the CWD.
225254721Semaste        }
226254721Semaste        else
227254721Semaste        {
228254721Semaste            // Match files in the given directory:
229254721Semaste
230254721Semaste        }
231254721Semaste    }
232254721Semaste#endif
233254721Semaste    return 0;
234254721Semaste}
235