SourceLocation.cpp revision 1.1.1.2 1 1.1 joerg //===- SourceLocation.cpp - Compact identifier for Source Files -----------===//
2 1.1 joerg //
3 1.1 joerg // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 1.1 joerg // See https://llvm.org/LICENSE.txt for license information.
5 1.1 joerg // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 1.1 joerg //
7 1.1 joerg //===----------------------------------------------------------------------===//
8 1.1 joerg //
9 1.1 joerg // This file defines accessor methods for the FullSourceLoc class.
10 1.1 joerg //
11 1.1 joerg //===----------------------------------------------------------------------===//
12 1.1 joerg
13 1.1 joerg #include "clang/Basic/SourceLocation.h"
14 1.1 joerg #include "clang/Basic/LLVM.h"
15 1.1 joerg #include "clang/Basic/PrettyStackTrace.h"
16 1.1 joerg #include "clang/Basic/SourceManager.h"
17 1.1.1.2 joerg #include "llvm/ADT/DenseMapInfo.h"
18 1.1.1.2 joerg #include "llvm/ADT/FoldingSet.h"
19 1.1 joerg #include "llvm/ADT/StringRef.h"
20 1.1 joerg #include "llvm/Support/Compiler.h"
21 1.1 joerg #include "llvm/Support/MemoryBuffer.h"
22 1.1 joerg #include "llvm/Support/raw_ostream.h"
23 1.1 joerg #include <cassert>
24 1.1 joerg #include <string>
25 1.1 joerg #include <utility>
26 1.1 joerg
27 1.1 joerg using namespace clang;
28 1.1 joerg
29 1.1 joerg //===----------------------------------------------------------------------===//
30 1.1 joerg // PrettyStackTraceLoc
31 1.1 joerg //===----------------------------------------------------------------------===//
32 1.1 joerg
33 1.1 joerg void PrettyStackTraceLoc::print(raw_ostream &OS) const {
34 1.1 joerg if (Loc.isValid()) {
35 1.1 joerg Loc.print(OS, SM);
36 1.1 joerg OS << ": ";
37 1.1 joerg }
38 1.1 joerg OS << Message << '\n';
39 1.1 joerg }
40 1.1 joerg
41 1.1 joerg //===----------------------------------------------------------------------===//
42 1.1 joerg // SourceLocation
43 1.1 joerg //===----------------------------------------------------------------------===//
44 1.1 joerg
45 1.1.1.2 joerg static_assert(std::is_trivially_destructible<SourceLocation>::value,
46 1.1.1.2 joerg "SourceLocation must be trivially destructible because it is "
47 1.1.1.2 joerg "used in unions");
48 1.1.1.2 joerg
49 1.1.1.2 joerg static_assert(std::is_trivially_destructible<SourceRange>::value,
50 1.1.1.2 joerg "SourceRange must be trivially destructible because it is "
51 1.1.1.2 joerg "used in unions");
52 1.1.1.2 joerg
53 1.1.1.2 joerg unsigned SourceLocation::getHashValue() const {
54 1.1.1.2 joerg return llvm::DenseMapInfo<unsigned>::getHashValue(ID);
55 1.1.1.2 joerg }
56 1.1.1.2 joerg
57 1.1.1.2 joerg void llvm::FoldingSetTrait<SourceLocation>::Profile(
58 1.1.1.2 joerg const SourceLocation &X, llvm::FoldingSetNodeID &ID) {
59 1.1.1.2 joerg ID.AddInteger(X.ID);
60 1.1.1.2 joerg }
61 1.1.1.2 joerg
62 1.1 joerg void SourceLocation::print(raw_ostream &OS, const SourceManager &SM)const{
63 1.1 joerg if (!isValid()) {
64 1.1 joerg OS << "<invalid loc>";
65 1.1 joerg return;
66 1.1 joerg }
67 1.1 joerg
68 1.1 joerg if (isFileID()) {
69 1.1 joerg PresumedLoc PLoc = SM.getPresumedLoc(*this);
70 1.1 joerg
71 1.1 joerg if (PLoc.isInvalid()) {
72 1.1 joerg OS << "<invalid>";
73 1.1 joerg return;
74 1.1 joerg }
75 1.1 joerg // The macro expansion and spelling pos is identical for file locs.
76 1.1 joerg OS << PLoc.getFilename() << ':' << PLoc.getLine()
77 1.1 joerg << ':' << PLoc.getColumn();
78 1.1 joerg return;
79 1.1 joerg }
80 1.1 joerg
81 1.1 joerg SM.getExpansionLoc(*this).print(OS, SM);
82 1.1 joerg
83 1.1 joerg OS << " <Spelling=";
84 1.1 joerg SM.getSpellingLoc(*this).print(OS, SM);
85 1.1 joerg OS << '>';
86 1.1 joerg }
87 1.1 joerg
88 1.1 joerg LLVM_DUMP_METHOD std::string
89 1.1 joerg SourceLocation::printToString(const SourceManager &SM) const {
90 1.1 joerg std::string S;
91 1.1 joerg llvm::raw_string_ostream OS(S);
92 1.1 joerg print(OS, SM);
93 1.1 joerg return OS.str();
94 1.1 joerg }
95 1.1 joerg
96 1.1 joerg LLVM_DUMP_METHOD void SourceLocation::dump(const SourceManager &SM) const {
97 1.1 joerg print(llvm::errs(), SM);
98 1.1 joerg llvm::errs() << '\n';
99 1.1 joerg }
100 1.1 joerg
101 1.1 joerg LLVM_DUMP_METHOD void SourceRange::dump(const SourceManager &SM) const {
102 1.1 joerg print(llvm::errs(), SM);
103 1.1 joerg llvm::errs() << '\n';
104 1.1 joerg }
105 1.1 joerg
106 1.1 joerg static PresumedLoc PrintDifference(raw_ostream &OS, const SourceManager &SM,
107 1.1 joerg SourceLocation Loc, PresumedLoc Previous) {
108 1.1 joerg if (Loc.isFileID()) {
109 1.1 joerg
110 1.1 joerg PresumedLoc PLoc = SM.getPresumedLoc(Loc);
111 1.1 joerg
112 1.1 joerg if (PLoc.isInvalid()) {
113 1.1 joerg OS << "<invalid sloc>";
114 1.1 joerg return Previous;
115 1.1 joerg }
116 1.1 joerg
117 1.1 joerg if (Previous.isInvalid() ||
118 1.1 joerg strcmp(PLoc.getFilename(), Previous.getFilename()) != 0) {
119 1.1 joerg OS << PLoc.getFilename() << ':' << PLoc.getLine() << ':'
120 1.1 joerg << PLoc.getColumn();
121 1.1 joerg } else if (Previous.isInvalid() || PLoc.getLine() != Previous.getLine()) {
122 1.1 joerg OS << "line" << ':' << PLoc.getLine() << ':' << PLoc.getColumn();
123 1.1 joerg } else {
124 1.1 joerg OS << "col" << ':' << PLoc.getColumn();
125 1.1 joerg }
126 1.1 joerg return PLoc;
127 1.1 joerg }
128 1.1 joerg auto PrintedLoc = PrintDifference(OS, SM, SM.getExpansionLoc(Loc), Previous);
129 1.1 joerg
130 1.1 joerg OS << " <Spelling=";
131 1.1 joerg PrintedLoc = PrintDifference(OS, SM, SM.getSpellingLoc(Loc), PrintedLoc);
132 1.1 joerg OS << '>';
133 1.1 joerg return PrintedLoc;
134 1.1 joerg }
135 1.1 joerg
136 1.1 joerg void SourceRange::print(raw_ostream &OS, const SourceManager &SM) const {
137 1.1 joerg
138 1.1 joerg OS << '<';
139 1.1 joerg auto PrintedLoc = PrintDifference(OS, SM, B, {});
140 1.1 joerg if (B != E) {
141 1.1 joerg OS << ", ";
142 1.1 joerg PrintDifference(OS, SM, E, PrintedLoc);
143 1.1 joerg }
144 1.1 joerg OS << '>';
145 1.1 joerg }
146 1.1 joerg
147 1.1 joerg LLVM_DUMP_METHOD std::string
148 1.1 joerg SourceRange::printToString(const SourceManager &SM) const {
149 1.1 joerg std::string S;
150 1.1 joerg llvm::raw_string_ostream OS(S);
151 1.1 joerg print(OS, SM);
152 1.1 joerg return OS.str();
153 1.1 joerg }
154 1.1 joerg
155 1.1 joerg //===----------------------------------------------------------------------===//
156 1.1 joerg // FullSourceLoc
157 1.1 joerg //===----------------------------------------------------------------------===//
158 1.1 joerg
159 1.1 joerg FileID FullSourceLoc::getFileID() const {
160 1.1 joerg assert(isValid());
161 1.1 joerg return SrcMgr->getFileID(*this);
162 1.1 joerg }
163 1.1 joerg
164 1.1 joerg FullSourceLoc FullSourceLoc::getExpansionLoc() const {
165 1.1 joerg assert(isValid());
166 1.1 joerg return FullSourceLoc(SrcMgr->getExpansionLoc(*this), *SrcMgr);
167 1.1 joerg }
168 1.1 joerg
169 1.1 joerg FullSourceLoc FullSourceLoc::getSpellingLoc() const {
170 1.1 joerg assert(isValid());
171 1.1 joerg return FullSourceLoc(SrcMgr->getSpellingLoc(*this), *SrcMgr);
172 1.1 joerg }
173 1.1 joerg
174 1.1 joerg FullSourceLoc FullSourceLoc::getFileLoc() const {
175 1.1 joerg assert(isValid());
176 1.1 joerg return FullSourceLoc(SrcMgr->getFileLoc(*this), *SrcMgr);
177 1.1 joerg }
178 1.1 joerg
179 1.1 joerg PresumedLoc FullSourceLoc::getPresumedLoc(bool UseLineDirectives) const {
180 1.1 joerg if (!isValid())
181 1.1 joerg return PresumedLoc();
182 1.1 joerg
183 1.1 joerg return SrcMgr->getPresumedLoc(*this, UseLineDirectives);
184 1.1 joerg }
185 1.1 joerg
186 1.1 joerg bool FullSourceLoc::isMacroArgExpansion(FullSourceLoc *StartLoc) const {
187 1.1 joerg assert(isValid());
188 1.1 joerg return SrcMgr->isMacroArgExpansion(*this, StartLoc);
189 1.1 joerg }
190 1.1 joerg
191 1.1 joerg FullSourceLoc FullSourceLoc::getImmediateMacroCallerLoc() const {
192 1.1 joerg assert(isValid());
193 1.1 joerg return FullSourceLoc(SrcMgr->getImmediateMacroCallerLoc(*this), *SrcMgr);
194 1.1 joerg }
195 1.1 joerg
196 1.1 joerg std::pair<FullSourceLoc, StringRef> FullSourceLoc::getModuleImportLoc() const {
197 1.1 joerg if (!isValid())
198 1.1 joerg return std::make_pair(FullSourceLoc(), StringRef());
199 1.1 joerg
200 1.1 joerg std::pair<SourceLocation, StringRef> ImportLoc =
201 1.1 joerg SrcMgr->getModuleImportLoc(*this);
202 1.1 joerg return std::make_pair(FullSourceLoc(ImportLoc.first, *SrcMgr),
203 1.1 joerg ImportLoc.second);
204 1.1 joerg }
205 1.1 joerg
206 1.1 joerg unsigned FullSourceLoc::getFileOffset() const {
207 1.1 joerg assert(isValid());
208 1.1 joerg return SrcMgr->getFileOffset(*this);
209 1.1 joerg }
210 1.1 joerg
211 1.1 joerg unsigned FullSourceLoc::getLineNumber(bool *Invalid) const {
212 1.1 joerg assert(isValid());
213 1.1 joerg return SrcMgr->getLineNumber(getFileID(), getFileOffset(), Invalid);
214 1.1 joerg }
215 1.1 joerg
216 1.1 joerg unsigned FullSourceLoc::getColumnNumber(bool *Invalid) const {
217 1.1 joerg assert(isValid());
218 1.1 joerg return SrcMgr->getColumnNumber(getFileID(), getFileOffset(), Invalid);
219 1.1 joerg }
220 1.1 joerg
221 1.1 joerg const FileEntry *FullSourceLoc::getFileEntry() const {
222 1.1 joerg assert(isValid());
223 1.1 joerg return SrcMgr->getFileEntryForID(getFileID());
224 1.1 joerg }
225 1.1 joerg
226 1.1 joerg unsigned FullSourceLoc::getExpansionLineNumber(bool *Invalid) const {
227 1.1 joerg assert(isValid());
228 1.1 joerg return SrcMgr->getExpansionLineNumber(*this, Invalid);
229 1.1 joerg }
230 1.1 joerg
231 1.1 joerg unsigned FullSourceLoc::getExpansionColumnNumber(bool *Invalid) const {
232 1.1 joerg assert(isValid());
233 1.1 joerg return SrcMgr->getExpansionColumnNumber(*this, Invalid);
234 1.1 joerg }
235 1.1 joerg
236 1.1 joerg unsigned FullSourceLoc::getSpellingLineNumber(bool *Invalid) const {
237 1.1 joerg assert(isValid());
238 1.1 joerg return SrcMgr->getSpellingLineNumber(*this, Invalid);
239 1.1 joerg }
240 1.1 joerg
241 1.1 joerg unsigned FullSourceLoc::getSpellingColumnNumber(bool *Invalid) const {
242 1.1 joerg assert(isValid());
243 1.1 joerg return SrcMgr->getSpellingColumnNumber(*this, Invalid);
244 1.1 joerg }
245 1.1 joerg
246 1.1 joerg bool FullSourceLoc::isInSystemHeader() const {
247 1.1 joerg assert(isValid());
248 1.1 joerg return SrcMgr->isInSystemHeader(*this);
249 1.1 joerg }
250 1.1 joerg
251 1.1 joerg bool FullSourceLoc::isBeforeInTranslationUnitThan(SourceLocation Loc) const {
252 1.1 joerg assert(isValid());
253 1.1 joerg return SrcMgr->isBeforeInTranslationUnit(*this, Loc);
254 1.1 joerg }
255 1.1 joerg
256 1.1 joerg LLVM_DUMP_METHOD void FullSourceLoc::dump() const {
257 1.1 joerg SourceLocation::dump(*SrcMgr);
258 1.1 joerg }
259 1.1 joerg
260 1.1 joerg const char *FullSourceLoc::getCharacterData(bool *Invalid) const {
261 1.1 joerg assert(isValid());
262 1.1 joerg return SrcMgr->getCharacterData(*this, Invalid);
263 1.1 joerg }
264 1.1 joerg
265 1.1 joerg StringRef FullSourceLoc::getBufferData(bool *Invalid) const {
266 1.1 joerg assert(isValid());
267 1.1.1.2 joerg return SrcMgr->getBufferData(SrcMgr->getFileID(*this), Invalid);
268 1.1 joerg }
269 1.1 joerg
270 1.1 joerg std::pair<FileID, unsigned> FullSourceLoc::getDecomposedLoc() const {
271 1.1 joerg return SrcMgr->getDecomposedLoc(*this);
272 1.1 joerg }
273