Skip to content

Commit 4205310

Browse files
committed
AST: Add Evaluator::getInnermostSourceLoc()
1 parent fe00f87 commit 4205310

File tree

5 files changed

+39
-1
lines changed

5 files changed

+39
-1
lines changed

include/swift/AST/AnyRequest.h

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,9 @@ struct AnyRequestVTable {
5858
static void noteCycleStep(const void *ptr, DiagnosticEngine &diags) {
5959
static_cast<const Request *>(ptr)->noteCycleStep(diags);
6060
}
61+
static SourceLoc getNearestLoc(const void *ptr) {
62+
return static_cast<const Request *>(ptr)->getNearestLoc();
63+
}
6164
};
6265

6366
const uint64_t typeID;
@@ -66,6 +69,7 @@ struct AnyRequestVTable {
6669
const std::function<void(const void *, llvm::raw_ostream &)> simpleDisplay;
6770
const std::function<void(const void *, DiagnosticEngine &)> diagnoseCycle;
6871
const std::function<void(const void *, DiagnosticEngine &)> noteCycleStep;
72+
const std::function<SourceLoc(const void *)> getNearestLoc;
6973

7074
template <typename Request>
7175
static const AnyRequestVTable *get() {
@@ -75,7 +79,8 @@ struct AnyRequestVTable {
7579
&Impl<Request>::isEqual,
7680
&Impl<Request>::simpleDisplay,
7781
&Impl<Request>::diagnoseCycle,
78-
&Impl<Request>::noteCycleStep
82+
&Impl<Request>::noteCycleStep,
83+
&Impl<Request>::getNearestLoc
7984
};
8085
return &vtable;
8186
}
@@ -173,6 +178,11 @@ class AnyRequestBase {
173178
getVTable()->noteCycleStep(getRawStorage(), diags);
174179
}
175180

181+
/// Get the best source location describing the parameters to this request.
182+
SourceLoc getNearestLoc() const {
183+
return getVTable()->getNearestLoc(getRawStorage());
184+
}
185+
176186
/// Compare two instances for equality.
177187
friend bool operator==(const AnyRequestBase<Derived> &lhs,
178188
const AnyRequestBase<Derived> &rhs) {
@@ -224,6 +234,8 @@ class AnyRequestBase {
224234
/// - Cycle diagnostics operations:
225235
/// void diagnoseCycle(DiagnosticEngine &diags) const;
226236
/// void noteCycleStep(DiagnosticEngine &diags) const;
237+
/// - Source location information:
238+
/// SourceLoc getNearestLoc() const;
227239
///
228240
class ActiveRequest final : public AnyRequestBase<ActiveRequest> {
229241
template <typename T>

include/swift/AST/Evaluator.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -229,6 +229,11 @@ class Evaluator {
229229
/// diagnostics through the given diagnostics engine.
230230
Evaluator(DiagnosticEngine &diags, const LangOptions &opts);
231231

232+
/// For last-ditch diagnostics, get a good approximate source location for
233+
/// the thing we're currently type checking by searching for a request whose
234+
/// source location matches the predicate.
235+
SourceLoc getInnermostSourceLoc(llvm::function_ref<bool(SourceLoc)> fn);
236+
232237
/// Emit GraphViz output visualizing the request graph.
233238
void emitRequestEvaluatorGraphViz(llvm::StringRef graphVizPath);
234239

include/swift/AST/Expr.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6403,6 +6403,8 @@ void simple_display(llvm::raw_ostream &out, const DefaultArgumentExpr *expr);
64036403
void simple_display(llvm::raw_ostream &out, const Expr *expr);
64046404

64056405
SourceLoc extractNearestSourceLoc(const DefaultArgumentExpr *expr);
6406+
SourceLoc extractNearestSourceLoc(const MacroExpansionExpr *expr);
6407+
SourceLoc extractNearestSourceLoc(const ClosureExpr *expr);
64066408

64076409
} // end namespace swift
64086410

lib/AST/Evaluator.cpp

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,17 @@ Evaluator::Evaluator(DiagnosticEngine &diags, const LangOptions &opts)
6060
debugDumpCycles(opts.DebugDumpCycles),
6161
recorder(opts.RecordRequestReferences) {}
6262

63+
SourceLoc Evaluator::getInnermostSourceLoc(
64+
llvm::function_ref<bool(SourceLoc)> fn) {
65+
for (auto request : llvm::reverse(activeRequests)) {
66+
SourceLoc loc = request.getNearestLoc();
67+
if (fn(loc))
68+
return loc;
69+
}
70+
71+
return SourceLoc();
72+
}
73+
6374
bool Evaluator::checkDependency(const ActiveRequest &request) {
6475
// Record this as an active request.
6576
if (activeRequests.insert(request)) {

lib/AST/Expr.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2835,10 +2835,18 @@ void swift::simple_display(llvm::raw_ostream &out,
28352835
out << "expression";
28362836
}
28372837

2838+
SourceLoc swift::extractNearestSourceLoc(const ClosureExpr *expr) {
2839+
return expr->getLoc();
2840+
}
2841+
28382842
SourceLoc swift::extractNearestSourceLoc(const DefaultArgumentExpr *expr) {
28392843
return expr->getLoc();
28402844
}
28412845

2846+
SourceLoc swift::extractNearestSourceLoc(const MacroExpansionExpr *expr) {
2847+
return expr->getLoc();
2848+
}
2849+
28422850
// See swift/Basic/Statistic.h for declaration: this enables tracing Exprs, is
28432851
// defined here to avoid too much layering violation / circular linkage
28442852
// dependency.

0 commit comments

Comments
 (0)