@@ -46,10 +46,25 @@ TypeRefinementContext::createRoot(SourceFile *SF,
46
46
assert (SF);
47
47
48
48
ASTContext &Ctx = SF->getASTContext ();
49
+
50
+ SourceRange range;
51
+ TypeRefinementContext *parentContext = nullptr ;
52
+ AvailabilityContext availabilityContext = Info;
53
+ if (auto parentExpansion = SF->getMacroExpansion ()) {
54
+ if (auto parentTRC =
55
+ SF->getEnclosingSourceFile ()->getTypeRefinementContext ()) {
56
+ auto charRange = Ctx.SourceMgr .getRangeForBuffer (*SF->getBufferID ());
57
+ range = SourceRange (charRange.getStart (), charRange.getEnd ());
58
+ parentContext = parentTRC->findMostRefinedSubContext (
59
+ parentExpansion.getStartLoc (), Ctx.SourceMgr );
60
+ availabilityContext = parentContext->getAvailabilityInfo ();
61
+ }
62
+ }
63
+
49
64
return new (Ctx)
50
- TypeRefinementContext (Ctx, SF,
51
- /* Parent= */ nullptr , SourceRange () ,
52
- Info, AvailabilityContext::alwaysAvailable ());
65
+ TypeRefinementContext (Ctx, SF, parentContext, range,
66
+ availabilityContext ,
67
+ AvailabilityContext::alwaysAvailable ());
53
68
}
54
69
55
70
TypeRefinementContext *
@@ -147,12 +162,34 @@ TypeRefinementContext::createForWhileStmtBody(ASTContext &Ctx, WhileStmt *S,
147
162
Ctx, S, Parent, S->getBody ()->getSourceRange (), Info, /* ExplicitInfo */ Info);
148
163
}
149
164
165
+ // / Determine whether the child location is somewhere within the parent
166
+ // / range.
167
+ static bool rangeContainsTokenLocWithGeneratedSource (
168
+ SourceManager &sourceMgr, SourceRange parentRange, SourceLoc childLoc) {
169
+ auto parentBuffer = sourceMgr.findBufferContainingLoc (parentRange.Start );
170
+ auto childBuffer = sourceMgr.findBufferContainingLoc (childLoc);
171
+ while (parentBuffer != childBuffer) {
172
+ auto info = sourceMgr.getGeneratedSourceInfo (childBuffer);
173
+ if (!info)
174
+ return false ;
175
+
176
+ childLoc = info->originalSourceRange .getStart ();
177
+ if (childLoc.isInvalid ())
178
+ return false ;
179
+
180
+ childBuffer = sourceMgr.findBufferContainingLoc (childLoc);
181
+ }
182
+
183
+ return sourceMgr.rangeContainsTokenLoc (parentRange, childLoc);
184
+ }
185
+
150
186
TypeRefinementContext *
151
187
TypeRefinementContext::findMostRefinedSubContext (SourceLoc Loc,
152
188
SourceManager &SM) {
153
189
assert (Loc.isValid ());
154
190
155
- if (SrcRange.isValid () && !SM.rangeContainsTokenLoc (SrcRange, Loc))
191
+ if (SrcRange.isValid () &&
192
+ !rangeContainsTokenLocWithGeneratedSource (SM, SrcRange, Loc))
156
193
return nullptr ;
157
194
158
195
// For the moment, we perform a linear search here, but we can and should
0 commit comments