clang 22.0.0git
SourceLocation.cpp
Go to the documentation of this file.
1//===- SourceLocation.cpp - Compact identifier for Source Files -----------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file defines accessor methods for the FullSourceLoc class.
10//
11//===----------------------------------------------------------------------===//
12
14#include "clang/Basic/LLVM.h"
17#include "llvm/ADT/DenseMapInfo.h"
18#include "llvm/ADT/FoldingSet.h"
19#include "llvm/Support/Compiler.h"
20#include "llvm/Support/raw_ostream.h"
21#include <cassert>
22#include <string>
23#include <utility>
24
25using namespace clang;
26
27//===----------------------------------------------------------------------===//
28// PrettyStackTraceLoc
29//===----------------------------------------------------------------------===//
30
31void PrettyStackTraceLoc::print(raw_ostream &OS) const {
32 if (Loc.isValid()) {
33 Loc.print(OS, SM);
34 OS << ": ";
35 }
36 OS << Message << '\n';
37}
38
39//===----------------------------------------------------------------------===//
40// SourceLocation
41//===----------------------------------------------------------------------===//
42
43static_assert(std::is_trivially_destructible_v<SourceLocation>,
44 "SourceLocation must be trivially destructible because it is "
45 "used in unions");
46
47static_assert(std::is_trivially_destructible_v<SourceRange>,
48 "SourceRange must be trivially destructible because it is "
49 "used in unions");
50
52 return llvm::DenseMapInfo<UIntTy>::getHashValue(ID);
53}
54
56 const SourceLocation &X, llvm::FoldingSetNodeID &ID) {
57 ID.AddInteger(X.ID);
58}
59
60void SourceLocation::print(raw_ostream &OS, const SourceManager &SM)const{
61 if (!isValid()) {
62 OS << "<invalid loc>";
63 return;
64 }
65
66 if (isFileID()) {
67 PresumedLoc PLoc = SM.getPresumedLoc(*this);
68
69 if (PLoc.isInvalid()) {
70 OS << "<invalid>";
71 return;
72 }
73 // The macro expansion and spelling pos is identical for file locs.
74 OS << PLoc.getFilename() << ':' << PLoc.getLine()
75 << ':' << PLoc.getColumn();
76 return;
77 }
78
79 SM.getExpansionLoc(*this).print(OS, SM);
80
81 OS << " <Spelling=";
82 SM.getSpellingLoc(*this).print(OS, SM);
83 OS << '>';
84}
85
86LLVM_DUMP_METHOD std::string
88 std::string S;
89 llvm::raw_string_ostream OS(S);
90 print(OS, SM);
91 return S;
92}
93
94LLVM_DUMP_METHOD void SourceLocation::dump(const SourceManager &SM) const {
95 print(llvm::errs(), SM);
96 llvm::errs() << '\n';
97}
98
99LLVM_DUMP_METHOD void SourceRange::dump(const SourceManager &SM) const {
100 print(llvm::errs(), SM);
101 llvm::errs() << '\n';
102}
103
104static PresumedLoc PrintDifference(raw_ostream &OS, const SourceManager &SM,
106 if (Loc.isFileID()) {
107
108 PresumedLoc PLoc = SM.getPresumedLoc(Loc);
109
110 if (PLoc.isInvalid()) {
111 OS << "<invalid sloc>";
112 return Previous;
113 }
114
115 if (Previous.isInvalid() ||
116 strcmp(PLoc.getFilename(), Previous.getFilename()) != 0) {
117 OS << PLoc.getFilename() << ':' << PLoc.getLine() << ':'
118 << PLoc.getColumn();
119 } else if (Previous.isInvalid() || PLoc.getLine() != Previous.getLine()) {
120 OS << "line" << ':' << PLoc.getLine() << ':' << PLoc.getColumn();
121 } else {
122 OS << "col" << ':' << PLoc.getColumn();
123 }
124 return PLoc;
125 }
126 auto PrintedLoc = PrintDifference(OS, SM, SM.getExpansionLoc(Loc), Previous);
127
128 OS << " <Spelling=";
129 PrintedLoc = PrintDifference(OS, SM, SM.getSpellingLoc(Loc), PrintedLoc);
130 OS << '>';
131 return PrintedLoc;
132}
133
134void SourceRange::print(raw_ostream &OS, const SourceManager &SM) const {
135
136 OS << '<';
137 auto PrintedLoc = PrintDifference(OS, SM, B, {});
138 if (B != E) {
139 OS << ", ";
140 PrintDifference(OS, SM, E, PrintedLoc);
141 }
142 OS << '>';
143}
144
145LLVM_DUMP_METHOD std::string
147 std::string S;
148 llvm::raw_string_ostream OS(S);
149 print(OS, SM);
150 return S;
151}
152
153//===----------------------------------------------------------------------===//
154// FullSourceLoc
155//===----------------------------------------------------------------------===//
156
158 assert(isValid());
159 return SrcMgr->getFileID(*this);
160}
161
163 assert(isValid());
164 return FullSourceLoc(SrcMgr->getExpansionLoc(*this), *SrcMgr);
165}
166
168 return SrcMgr->getDecomposedExpansionLoc(*this);
169}
170
172 assert(isValid());
173 return FullSourceLoc(SrcMgr->getSpellingLoc(*this), *SrcMgr);
174}
175
177 assert(isValid());
178 return FullSourceLoc(SrcMgr->getFileLoc(*this), *SrcMgr);
179}
180
181PresumedLoc FullSourceLoc::getPresumedLoc(bool UseLineDirectives) const {
182 if (!isValid())
183 return PresumedLoc();
184
185 return SrcMgr->getPresumedLoc(*this, UseLineDirectives);
186}
187
189 assert(isValid());
190 return SrcMgr->isMacroArgExpansion(*this, StartLoc);
191}
192
194 assert(isValid());
195 return FullSourceLoc(SrcMgr->getImmediateMacroCallerLoc(*this), *SrcMgr);
196}
197
198std::pair<FullSourceLoc, StringRef> FullSourceLoc::getModuleImportLoc() const {
199 if (!isValid())
200 return std::make_pair(FullSourceLoc(), StringRef());
201
202 std::pair<SourceLocation, StringRef> ImportLoc =
203 SrcMgr->getModuleImportLoc(*this);
204 return std::make_pair(FullSourceLoc(ImportLoc.first, *SrcMgr),
205 ImportLoc.second);
206}
207
209 assert(isValid());
210 return SrcMgr->getFileOffset(*this);
211}
212
214 assert(isValid());
215 return SrcMgr->getLineNumber(getFileID(), getFileOffset(), Invalid);
216}
217
219 assert(isValid());
220 return SrcMgr->getColumnNumber(getFileID(), getFileOffset(), Invalid);
221}
222
224 assert(isValid());
225 return SrcMgr->getFileEntryForID(getFileID());
226}
227
229 assert(isValid());
230 return SrcMgr->getFileEntryRefForID(getFileID());
231}
232
234 assert(isValid());
235 return SrcMgr->getExpansionLineNumber(*this, Invalid);
236}
237
239 assert(isValid());
240 return SrcMgr->getExpansionColumnNumber(*this, Invalid);
241}
242
244 assert(isValid());
245 return SrcMgr->getSpellingLineNumber(*this, Invalid);
246}
247
249 assert(isValid());
250 return SrcMgr->getSpellingColumnNumber(*this, Invalid);
251}
252
254 assert(isValid());
255 return SrcMgr->isInSystemHeader(*this);
256}
257
259 assert(isValid());
260 return SrcMgr->isBeforeInTranslationUnit(*this, Loc);
261}
262
263LLVM_DUMP_METHOD void FullSourceLoc::dump() const {
264 SourceLocation::dump(*SrcMgr);
265}
266
267const char *FullSourceLoc::getCharacterData(bool *Invalid) const {
268 assert(isValid());
269 return SrcMgr->getCharacterData(*this, Invalid);
270}
271
272StringRef FullSourceLoc::getBufferData(bool *Invalid) const {
273 assert(isValid());
274 return SrcMgr->getBufferData(SrcMgr->getFileID(*this), Invalid);
275}
276
278 return SrcMgr->getDecomposedLoc(*this);
279}
#define X(type, name)
Definition: Value.h:145
Forward-declares and imports various common LLVM datatypes that clang wants to use unqualified.
#define SM(sm)
Definition: OffloadArch.cpp:16
Defines the PrettyStackTraceEntry class, which is used to make crashes give more contextual informati...
SourceLocation Loc
Definition: SemaObjC.cpp:754
static PresumedLoc PrintDifference(raw_ostream &OS, const SourceManager &SM, SourceLocation Loc, PresumedLoc Previous)
Defines the clang::SourceLocation class and associated facilities.
Defines the SourceManager interface.
StateNode * Previous
Cached information about one file (either on disk or in the virtual file system).
Definition: FileEntry.h:306
An opaque identifier used by SourceManager which refers to a source file (MemoryBuffer) along with it...
A SourceLocation and its associated SourceManager.
FullSourceLoc getFileLoc() const
unsigned getColumnNumber(bool *Invalid=nullptr) const
FileIDAndOffset getDecomposedExpansionLoc() const
Decompose the underlying SourceLocation into a raw (FileID + Offset) pair, after walking through all ...
FullSourceLoc getExpansionLoc() const
unsigned getLineNumber(bool *Invalid=nullptr) const
FullSourceLoc getSpellingLoc() const
std::pair< FullSourceLoc, StringRef > getModuleImportLoc() const
FileID getFileID() const
OptionalFileEntryRef getFileEntryRef() const
unsigned getSpellingLineNumber(bool *Invalid=nullptr) const
FullSourceLoc getImmediateMacroCallerLoc() const
const char * getCharacterData(bool *Invalid=nullptr) const
unsigned getExpansionColumnNumber(bool *Invalid=nullptr) const
StringRef getBufferData(bool *Invalid=nullptr) const
Return a StringRef to the source buffer data for the specified FileID.
void dump() const
Prints information about this FullSourceLoc to stderr.
bool isInSystemHeader() const
const FileEntry * getFileEntry() const
unsigned getFileOffset() const
FullSourceLoc()=default
Creates a FullSourceLoc where isValid() returns false.
PresumedLoc getPresumedLoc(bool UseLineDirectives=true) const
FileIDAndOffset getDecomposedLoc() const
Decompose the specified location into a raw FileID + Offset pair.
bool isMacroArgExpansion(FullSourceLoc *StartLoc=nullptr) const
unsigned getExpansionLineNumber(bool *Invalid=nullptr) const
bool isBeforeInTranslationUnitThan(SourceLocation Loc) const
Determines the order of 2 source locations in the translation unit.
unsigned getSpellingColumnNumber(bool *Invalid=nullptr) const
Represents an unpacked "presumed" location which can be presented to the user.
unsigned getColumn() const
Return the presumed column number of this location.
const char * getFilename() const
Return the presumed filename of this location.
unsigned getLine() const
Return the presumed line number of this location.
bool isInvalid() const
Return true if this object is invalid or uninitialized.
void print(raw_ostream &OS) const override
Encodes a location in the source.
std::string printToString(const SourceManager &SM) const
void dump(const SourceManager &SM) const
bool isValid() const
Return true if this is a valid SourceLocation object.
void print(raw_ostream &OS, const SourceManager &SM) const
unsigned getHashValue() const
This class handles loading and caching of source files into memory.
FileIDAndOffset getDecomposedExpansionLoc(SourceLocation Loc) const
Decompose the specified location into a raw FileID + Offset pair.
FileIDAndOffset getDecomposedLoc(SourceLocation Loc) const
Decompose the specified location into a raw FileID + Offset pair.
FileID getFileID(SourceLocation SpellingLoc) const
Return the FileID for a SourceLocation.
unsigned getColumnNumber(FileID FID, unsigned FilePos, bool *Invalid=nullptr) const
Return the column # for the specified file position.
unsigned getFileOffset(SourceLocation SpellingLoc) const
Returns the offset from the start of the file that the specified SourceLocation represents.
PresumedLoc getPresumedLoc(SourceLocation Loc, bool UseLineDirectives=true) const
Returns the "presumed" location of a SourceLocation specifies.
OptionalFileEntryRef getFileEntryRefForID(FileID FID) const
Returns the FileEntryRef for the provided FileID.
SourceLocation getFileLoc(SourceLocation Loc) const
Given Loc, if it is a macro location return the expansion location or the spelling location,...
unsigned getExpansionColumnNumber(SourceLocation Loc, bool *Invalid=nullptr) const
StringRef getBufferData(FileID FID, bool *Invalid=nullptr) const
Return a StringRef to the source buffer data for the specified FileID.
bool isMacroArgExpansion(SourceLocation Loc, SourceLocation *StartLoc=nullptr) const
Tests whether the given source location represents a macro argument's expansion into the function-lik...
SourceLocation getSpellingLoc(SourceLocation Loc) const
Given a SourceLocation object, return the spelling location referenced by the ID.
SourceLocation getImmediateMacroCallerLoc(SourceLocation Loc) const
Gets the location of the immediate macro caller, one level up the stack toward the initial macro type...
const char * getCharacterData(SourceLocation SL, bool *Invalid=nullptr) const
Return a pointer to the start of the specified location in the appropriate spelling MemoryBuffer.
unsigned getSpellingLineNumber(SourceLocation Loc, bool *Invalid=nullptr) const
unsigned getLineNumber(FileID FID, unsigned FilePos, bool *Invalid=nullptr) const
Given a SourceLocation, return the spelling line number for the position indicated.
unsigned getSpellingColumnNumber(SourceLocation Loc, bool *Invalid=nullptr) const
bool isInSystemHeader(SourceLocation Loc) const
Returns if a SourceLocation is in a system header.
unsigned getExpansionLineNumber(SourceLocation Loc, bool *Invalid=nullptr) const
std::pair< SourceLocation, StringRef > getModuleImportLoc(SourceLocation Loc) const
const FileEntry * getFileEntryForID(FileID FID) const
Returns the FileEntry record for the provided FileID.
SourceLocation getExpansionLoc(SourceLocation Loc) const
Given a SourceLocation object Loc, return the expansion location referenced by the ID.
bool isBeforeInTranslationUnit(SourceLocation LHS, SourceLocation RHS) const
Determines the order of 2 source locations in the translation unit.
std::string printToString(const SourceManager &SM) const
void dump(const SourceManager &SM) const
void print(raw_ostream &OS, const SourceManager &SM) const
The JSON file list parser is used to communicate input to InstallAPI.
std::pair< FileID, unsigned > FileIDAndOffset