|
|
|||
File indexing completed on 2026-05-10 08:42:57
0001 //===-- FileSpec.h ----------------------------------------------*- C++ -*-===// 0002 // 0003 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 0004 // See https://llvm.org/LICENSE.txt for license information. 0005 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 0006 // 0007 //===----------------------------------------------------------------------===// 0008 0009 #ifndef LLDB_UTILITY_FILESPEC_H 0010 #define LLDB_UTILITY_FILESPEC_H 0011 0012 #include <functional> 0013 #include <optional> 0014 #include <string> 0015 0016 #include "lldb/Utility/ConstString.h" 0017 0018 #include "llvm/ADT/StringRef.h" 0019 #include "llvm/Support/FileSystem.h" 0020 #include "llvm/Support/FormatVariadic.h" 0021 #include "llvm/Support/Path.h" 0022 0023 #include <cstddef> 0024 #include <cstdint> 0025 0026 namespace lldb_private { 0027 class Stream; 0028 } 0029 namespace llvm { 0030 class Triple; 0031 } 0032 namespace llvm { 0033 class raw_ostream; 0034 } 0035 namespace llvm { 0036 template <typename T> class SmallVectorImpl; 0037 } 0038 0039 namespace lldb_private { 0040 0041 /// \class FileSpec FileSpec.h "lldb/Utility/FileSpec.h" 0042 /// A file utility class. 0043 /// 0044 /// A file specification class that divides paths up into a directory 0045 /// and basename. These string values of the paths are put into uniqued string 0046 /// pools for fast comparisons and efficient memory usage. 0047 /// 0048 /// Another reason the paths are split into the directory and basename is to 0049 /// allow efficient debugger searching. Often in a debugger the user types in 0050 /// the basename of the file, for example setting a breakpoint by file and 0051 /// line, or specifying a module (shared library) to limit the scope in which 0052 /// to execute a command. The user rarely types in a full path. When the paths 0053 /// are already split up, it makes it easy for us to compare only the 0054 /// basenames of a lot of file specifications without having to split up the 0055 /// file path each time to get to the basename. 0056 class FileSpec { 0057 public: 0058 using Style = llvm::sys::path::Style; 0059 0060 FileSpec(); 0061 0062 /// Constructor with path. 0063 /// 0064 /// Takes a path to a file which can be just a filename, or a full path. If 0065 /// \a path is not nullptr or empty, this function will call 0066 /// FileSpec::SetFile (const char *path). 0067 /// 0068 /// \param[in] path 0069 /// The full or partial path to a file. 0070 /// 0071 /// \param[in] style 0072 /// The style of the path 0073 /// 0074 /// \see FileSpec::SetFile (const char *path) 0075 explicit FileSpec(llvm::StringRef path, Style style = Style::native); 0076 0077 explicit FileSpec(llvm::StringRef path, const llvm::Triple &triple); 0078 0079 bool DirectoryEquals(const FileSpec &other) const; 0080 0081 bool FileEquals(const FileSpec &other) const; 0082 0083 /// Equal to operator 0084 /// 0085 /// Tests if this object is equal to \a rhs. 0086 /// 0087 /// \param[in] rhs 0088 /// A const FileSpec object reference to compare this object 0089 /// to. 0090 /// 0091 /// \return 0092 /// \b true if this object is equal to \a rhs, \b false 0093 /// otherwise. 0094 bool operator==(const FileSpec &rhs) const; 0095 0096 /// Not equal to operator 0097 /// 0098 /// Tests if this object is not equal to \a rhs. 0099 /// 0100 /// \param[in] rhs 0101 /// A const FileSpec object reference to compare this object 0102 /// to. 0103 /// 0104 /// \return 0105 /// \b true if this object is equal to \a rhs, \b false 0106 /// otherwise. 0107 bool operator!=(const FileSpec &rhs) const; 0108 0109 /// Less than to operator 0110 /// 0111 /// Tests if this object is less than \a rhs. 0112 /// 0113 /// \param[in] rhs 0114 /// A const FileSpec object reference to compare this object 0115 /// to. 0116 /// 0117 /// \return 0118 /// \b true if this object is less than \a rhs, \b false 0119 /// otherwise. 0120 bool operator<(const FileSpec &rhs) const; 0121 0122 /// Convert to pointer operator. 0123 /// 0124 /// This allows code to check a FileSpec object to see if it contains 0125 /// anything valid using code such as: 0126 /// 0127 /// \code 0128 /// FileSpec file_spec(...); 0129 /// if (file_spec) 0130 /// { ... 0131 /// \endcode 0132 /// 0133 /// \return 0134 /// A pointer to this object if either the directory or filename 0135 /// is valid, nullptr otherwise. 0136 explicit operator bool() const; 0137 0138 /// Logical NOT operator. 0139 /// 0140 /// This allows code to check a FileSpec object to see if it is invalid 0141 /// using code such as: 0142 /// 0143 /// \code 0144 /// FileSpec file_spec(...); 0145 /// if (!file_spec) 0146 /// { ... 0147 /// \endcode 0148 /// 0149 /// \return 0150 /// Returns \b true if the object has an empty directory and 0151 /// filename, \b false otherwise. 0152 bool operator!() const; 0153 0154 /// Clears the object state. 0155 /// 0156 /// Clear this object by releasing both the directory and filename string 0157 /// values and reverting them to empty strings. 0158 void Clear(); 0159 0160 /// Compare two FileSpec objects. 0161 /// 0162 /// If \a full is true, then both the directory and the filename must match. 0163 /// If \a full is false, then the directory names for \a lhs and \a rhs are 0164 /// only compared if they are both not empty. This allows a FileSpec object 0165 /// to only contain a filename and it can match FileSpec objects that have 0166 /// matching filenames with different paths. 0167 /// 0168 /// \param[in] lhs 0169 /// A const reference to the Left Hand Side object to compare. 0170 /// 0171 /// \param[in] rhs 0172 /// A const reference to the Right Hand Side object to compare. 0173 /// 0174 /// \param[in] full 0175 /// If true, then both the directory and filenames will have to 0176 /// match for a compare to return zero (equal to). If false 0177 /// and either directory from \a lhs or \a rhs is empty, then 0178 /// only the filename will be compared, else a full comparison 0179 /// is done. 0180 /// 0181 /// \return -1 if \a lhs is less than \a rhs, 0 if \a lhs is equal to \a rhs, 0182 /// 1 if \a lhs is greater than \a rhs 0183 static int Compare(const FileSpec &lhs, const FileSpec &rhs, bool full); 0184 0185 static bool Equal(const FileSpec &a, const FileSpec &b, bool full); 0186 0187 /// Match FileSpec \a pattern against FileSpec \a file. If \a pattern has a 0188 /// directory component, then the \a file must have the same directory 0189 /// component. Otherwise, just it matches just the filename. An empty \a 0190 /// pattern matches everything. 0191 static bool Match(const FileSpec &pattern, const FileSpec &file); 0192 0193 /// Attempt to guess path style for a given path string. It returns a style, 0194 /// if it was able to make a reasonable guess, or std::nullopt if it wasn't. 0195 /// The guess will be correct if the input path was a valid absolute path on 0196 /// the system which produced it. On other paths the result of this function 0197 /// is unreliable (e.g. "c:\foo.txt" is a valid relative posix path). 0198 static std::optional<Style> GuessPathStyle(llvm::StringRef absolute_path); 0199 0200 /// Case sensitivity of path. 0201 /// 0202 /// \return 0203 /// \b true if the file path is case sensitive (POSIX), false 0204 /// if case insensitive (Windows). 0205 bool IsCaseSensitive() const { return is_style_posix(m_style); } 0206 0207 /// Dump this object to a Stream. 0208 /// 0209 /// Dump the object to the supplied stream \a s. If the object contains a 0210 /// valid directory name, it will be displayed followed by a directory 0211 /// delimiter, and the filename. 0212 /// 0213 /// \param[in] s 0214 /// The stream to which to dump the object description. 0215 void Dump(llvm::raw_ostream &s) const; 0216 0217 Style GetPathStyle() const; 0218 0219 /// Directory string const get accessor. 0220 /// 0221 /// \return 0222 /// A const reference to the directory string object. 0223 const ConstString &GetDirectory() const { return m_directory; } 0224 0225 /// Directory string set accessor. 0226 /// 0227 /// \param[in] directory 0228 /// The value to replace the directory with. 0229 void SetDirectory(ConstString directory); 0230 void SetDirectory(llvm::StringRef directory); 0231 0232 /// Clear the directory in this object. 0233 void ClearDirectory(); 0234 0235 0236 /// Filename string const get accessor. 0237 /// 0238 /// \return 0239 /// A const reference to the filename string object. 0240 const ConstString &GetFilename() const { return m_filename; } 0241 0242 /// Filename string set accessor. 0243 /// 0244 /// \param[in] filename 0245 /// The const string to replace the directory with. 0246 void SetFilename(ConstString filename); 0247 void SetFilename(llvm::StringRef filename); 0248 0249 /// Clear the filename in this object. 0250 void ClearFilename(); 0251 0252 /// Returns true if the filespec represents an implementation source file 0253 /// (files with a ".c", ".cpp", ".m", ".mm" (many more) extension). 0254 /// 0255 /// \return 0256 /// \b true if the FileSpec represents an implementation source 0257 /// file, \b false otherwise. 0258 bool IsSourceImplementationFile() const; 0259 0260 /// Returns true if the filespec represents a relative path. 0261 /// 0262 /// \return 0263 /// \b true if the filespec represents a relative path, 0264 /// \b false otherwise. 0265 bool IsRelative() const; 0266 0267 /// Returns true if the filespec represents an absolute path. 0268 /// 0269 /// \return 0270 /// \b true if the filespec represents an absolute path, 0271 /// \b false otherwise. 0272 bool IsAbsolute() const; 0273 0274 /// Make the FileSpec absolute by treating it relative to \a dir. Absolute 0275 /// FileSpecs are never changed by this function. 0276 void MakeAbsolute(const FileSpec &dir); 0277 0278 /// Temporary helper for FileSystem change. 0279 void SetPath(llvm::StringRef p) { SetFile(p); } 0280 0281 /// Extract the full path to the file. 0282 /// 0283 /// Extract the directory and path into a fixed buffer. This is needed as 0284 /// the directory and path are stored in separate string values. 0285 /// 0286 /// \param[out] path 0287 /// The buffer in which to place the extracted full path. 0288 /// 0289 /// \param[in] max_path_length 0290 /// The maximum length of \a path. 0291 /// 0292 /// \return 0293 /// Returns the number of characters that would be needed to 0294 /// properly copy the full path into \a path. If the returned 0295 /// number is less than \a max_path_length, then the path is 0296 /// properly copied and terminated. If the return value is 0297 /// >= \a max_path_length, then the path was truncated (but is 0298 /// still NULL terminated). 0299 size_t GetPath(char *path, size_t max_path_length, 0300 bool denormalize = true) const; 0301 0302 /// Extract the full path to the file. 0303 /// 0304 /// Extract the directory and path into a std::string, which is returned. 0305 /// 0306 /// \return 0307 /// Returns a std::string with the directory and filename 0308 /// concatenated. 0309 std::string GetPath(bool denormalize = true) const; 0310 0311 /// Get the full path as a ConstString. 0312 /// 0313 /// This method should only be used when you need a ConstString or the 0314 /// const char * from a ConstString to ensure permanent lifetime of C string. 0315 /// Anyone needing the path temporarily should use the GetPath() method that 0316 /// returns a std:string. 0317 ConstString GetPathAsConstString(bool denormalize = true) const; 0318 0319 /// Extract the full path to the file. 0320 /// 0321 /// Extract the directory and path into an llvm::SmallVectorImpl<> 0322 void GetPath(llvm::SmallVectorImpl<char> &path, 0323 bool denormalize = true) const; 0324 0325 /// Extract the extension of the file. 0326 /// 0327 /// Returns a ConstString that represents the extension of the filename for 0328 /// this FileSpec object. If this object does not represent a file, or the 0329 /// filename has no extension, ConstString(nullptr) is returned. The dot 0330 /// ('.') character is the first character in the returned string. 0331 /// 0332 /// \return Returns the extension of the file as a StringRef. 0333 llvm::StringRef GetFileNameExtension() const; 0334 0335 /// Return the filename without the extension part 0336 /// 0337 /// Returns a ConstString that represents the filename of this object 0338 /// without the extension part (e.g. for a file named "foo.bar", "foo" is 0339 /// returned) 0340 /// 0341 /// \return Returns the filename without extension as a ConstString object. 0342 ConstString GetFileNameStrippingExtension() const; 0343 0344 /// Get the memory cost of this object. 0345 /// 0346 /// Return the size in bytes that this object takes in memory. This returns 0347 /// the size in bytes of this object, not any shared string values it may 0348 /// refer to. 0349 /// 0350 /// \return 0351 /// The number of bytes that this object occupies in memory. 0352 size_t MemorySize() const; 0353 0354 /// Change the file specified with a new path. 0355 /// 0356 /// Update the contents of this object with a new path. The path will be 0357 /// split up into a directory and filename and stored as uniqued string 0358 /// values for quick comparison and efficient memory usage. 0359 /// 0360 /// \param[in] path 0361 /// A full, partial, or relative path to a file. 0362 /// 0363 /// \param[in] style 0364 /// The style for the given path. 0365 void SetFile(llvm::StringRef path, Style style); 0366 0367 /// Change the file specified with a new path. 0368 /// 0369 /// Update the contents of this object with a new path. The path will be 0370 /// split up into a directory and filename and stored as uniqued string 0371 /// values for quick comparison and efficient memory usage. 0372 /// 0373 /// \param[in] path 0374 /// A full, partial, or relative path to a file. 0375 /// 0376 /// \param[in] triple 0377 /// The triple which is used to set the Path style. 0378 void SetFile(llvm::StringRef path, const llvm::Triple &triple); 0379 0380 FileSpec CopyByAppendingPathComponent(llvm::StringRef component) const; 0381 FileSpec CopyByRemovingLastPathComponent() const; 0382 0383 void PrependPathComponent(llvm::StringRef component); 0384 void PrependPathComponent(const FileSpec &new_path); 0385 0386 void AppendPathComponent(llvm::StringRef component); 0387 void AppendPathComponent(const FileSpec &new_path); 0388 0389 /// Removes the last path component by replacing the current path with its 0390 /// parent. When the current path has no parent, this is a no-op. 0391 /// 0392 /// \return 0393 /// A boolean value indicating whether the path was updated. 0394 bool RemoveLastPathComponent(); 0395 0396 /// Gets the components of the FileSpec's path. 0397 /// For example, given the path: 0398 /// /System/Library/PrivateFrameworks/UIFoundation.framework/UIFoundation 0399 /// 0400 /// This function returns: 0401 /// {"System", "Library", "PrivateFrameworks", "UIFoundation.framework", 0402 /// "UIFoundation"} 0403 /// \return 0404 /// A std::vector of llvm::StringRefs for each path component. 0405 /// The lifetime of the StringRefs is tied to the lifetime of the FileSpec. 0406 std::vector<llvm::StringRef> GetComponents() const; 0407 0408 protected: 0409 // Convenience method for setting the file without changing the style. 0410 void SetFile(llvm::StringRef path); 0411 0412 /// Called anytime m_directory or m_filename is changed to clear any cached 0413 /// state in this object. 0414 void PathWasModified() { m_absolute = Absolute::Calculate; } 0415 0416 enum class Absolute : uint8_t { 0417 Calculate, 0418 Yes, 0419 No 0420 }; 0421 0422 /// The unique'd directory path. 0423 ConstString m_directory; 0424 0425 /// The unique'd filename path. 0426 ConstString m_filename; 0427 0428 /// Cache whether this path is absolute. 0429 mutable Absolute m_absolute = Absolute::Calculate; 0430 0431 /// The syntax that this path uses. (e.g. Windows / Posix) 0432 Style m_style; 0433 }; 0434 0435 /// Dump a FileSpec object to a stream 0436 Stream &operator<<(Stream &s, const FileSpec &f); 0437 } // namespace lldb_private 0438 0439 namespace llvm { 0440 0441 /// Implementation of format_provider<T> for FileSpec. 0442 /// 0443 /// The options string of a FileSpec has the grammar: 0444 /// 0445 /// file_spec_options :: (empty) | F | D 0446 /// 0447 /// ======================================================= 0448 /// | style | Meaning | Example | 0449 /// ------------------------------------------------------- 0450 /// | | | Input | Output | 0451 /// ======================================================= 0452 /// | F | Only print filename | /foo/bar | bar | 0453 /// | D | Only print directory | /foo/bar | /foo/ | 0454 /// | (empty) | Print file and dir | | | 0455 /// ======================================================= 0456 /// 0457 /// Any other value is considered an invalid format string. 0458 /// 0459 template <> struct format_provider<lldb_private::FileSpec> { 0460 static void format(const lldb_private::FileSpec &F, llvm::raw_ostream &Stream, 0461 StringRef Style); 0462 }; 0463 0464 } // namespace llvm 0465 0466 #endif // LLDB_UTILITY_FILESPEC_H
| [ Source navigation ] | [ Diff markup ] | [ Identifier search ] | [ general search ] |
|
This page was automatically generated by the 2.3.7 LXR engine. The LXR team |
|