@@ -132,12 +132,16 @@ QueryRef QueryParser::endQuery(QueryRef Q) {
132
132
return Q;
133
133
}
134
134
135
+ namespace {
136
+
135
137
enum ParsedQueryKind {
136
138
PQK_Invalid,
137
139
PQK_NoOp,
138
140
PQK_Help,
141
+ PQK_Let,
139
142
PQK_Match,
140
- PQK_Set
143
+ PQK_Set,
144
+ PQK_Unlet,
141
145
};
142
146
143
147
enum ParsedQueryVariable {
@@ -146,46 +150,89 @@ enum ParsedQueryVariable {
146
150
PQV_BindRoot
147
151
};
148
152
153
+ QueryRef makeInvalidQueryFromDiagnostics (const Diagnostics &Diag) {
154
+ std::string ErrStr;
155
+ llvm::raw_string_ostream OS (ErrStr);
156
+ Diag.printToStreamFull (OS);
157
+ return new InvalidQuery (OS.str ());
158
+ }
159
+
160
+ class QuerySessionSema : public Parser ::RegistrySema {
161
+ public:
162
+ QuerySessionSema (const QuerySession &QS) : QS(QS) {}
163
+
164
+ ast_matchers::dynamic::VariantValue getNamedValue (StringRef Name) override {
165
+ return QS.NamedValues .lookup (Name);
166
+ }
167
+
168
+ private:
169
+ const QuerySession &QS;
170
+ };
171
+
172
+ } // namespace
173
+
174
+ QueryRef QueryParser::completeMatcherExpression () {
175
+ std::vector<MatcherCompletion> Comps = Parser::completeExpression (
176
+ StringRef (Begin, End - Begin), CompletionPos - Begin);
177
+ for (std::vector<MatcherCompletion>::iterator I = Comps.begin (),
178
+ E = Comps.end ();
179
+ I != E; ++I) {
180
+ Completions.push_back (LineEditor::Completion (I->TypedText , I->MatcherDecl ));
181
+ }
182
+ return QueryRef ();
183
+ }
184
+
149
185
QueryRef QueryParser::doParse () {
150
186
StringRef CommandStr;
151
187
ParsedQueryKind QKind = lexOrCompleteWord<ParsedQueryKind>(CommandStr)
152
188
.Case (" " , PQK_NoOp)
153
189
.Case (" help" , PQK_Help)
154
190
.Case (" m" , PQK_Match, /* IsCompletion=*/ false )
191
+ .Case (" let" , PQK_Let)
155
192
.Case (" match" , PQK_Match)
156
193
.Case (" set" , PQK_Set)
194
+ .Case (" unlet" , PQK_Unlet)
157
195
.Default (PQK_Invalid);
158
196
197
+ QuerySessionSema S (QS);
198
+
159
199
switch (QKind) {
160
200
case PQK_NoOp:
161
201
return new NoOpQuery;
162
202
163
203
case PQK_Help:
164
204
return endQuery (new HelpQuery);
165
205
206
+ case PQK_Let: {
207
+ StringRef Name = lexWord ();
208
+
209
+ if (Name.empty ())
210
+ return new InvalidQuery (" expected variable name" );
211
+
212
+ if (CompletionPos)
213
+ return completeMatcherExpression ();
214
+
215
+ Diagnostics Diag;
216
+ ast_matchers::dynamic::VariantValue Value;
217
+ if (!Parser::parseExpression (StringRef (Begin, End - Begin), &S, &Value,
218
+ &Diag)) {
219
+ return makeInvalidQueryFromDiagnostics (Diag);
220
+ }
221
+
222
+ return new LetQuery (Name, Value);
223
+ }
224
+
166
225
case PQK_Match: {
167
- if (CompletionPos) {
168
- std::vector<MatcherCompletion> Comps = Parser::completeExpression (
169
- StringRef (Begin, End - Begin), CompletionPos - Begin);
170
- for (std::vector<MatcherCompletion>::iterator I = Comps.begin (),
171
- E = Comps.end ();
172
- I != E; ++I) {
173
- Completions.push_back (
174
- LineEditor::Completion (I->TypedText , I->MatcherDecl ));
175
- }
176
- return QueryRef ();
177
- } else {
178
- Diagnostics Diag;
179
- Optional<DynTypedMatcher> Matcher =
180
- Parser::parseMatcherExpression (StringRef (Begin, End - Begin), &Diag);
181
- if (!Matcher) {
182
- std::string ErrStr;
183
- llvm::raw_string_ostream OS (ErrStr);
184
- Diag.printToStreamFull (OS);
185
- return new InvalidQuery (OS.str ());
186
- }
187
- return new MatchQuery (*Matcher);
226
+ if (CompletionPos)
227
+ return completeMatcherExpression ();
228
+
229
+ Diagnostics Diag;
230
+ Optional<DynTypedMatcher> Matcher = Parser::parseMatcherExpression (
231
+ StringRef (Begin, End - Begin), &S, &Diag);
232
+ if (!Matcher) {
233
+ return makeInvalidQueryFromDiagnostics (Diag);
188
234
}
235
+ return new MatchQuery (*Matcher);
189
236
}
190
237
191
238
case PQK_Set: {
@@ -214,20 +261,29 @@ QueryRef QueryParser::doParse() {
214
261
return endQuery (Q);
215
262
}
216
263
264
+ case PQK_Unlet: {
265
+ StringRef Name = lexWord ();
266
+
267
+ if (Name.empty ())
268
+ return new InvalidQuery (" expected variable name" );
269
+
270
+ return endQuery (new LetQuery (Name, {}));
271
+ }
272
+
217
273
case PQK_Invalid:
218
274
return new InvalidQuery (" unknown command: " + CommandStr);
219
275
}
220
276
221
277
llvm_unreachable (" Invalid query kind" );
222
278
}
223
279
224
- QueryRef QueryParser::parse (StringRef Line) {
225
- return QueryParser (Line).doParse ();
280
+ QueryRef QueryParser::parse (StringRef Line, const QuerySession &QS ) {
281
+ return QueryParser (Line, QS ).doParse ();
226
282
}
227
283
228
- std::vector<LineEditor::Completion> QueryParser::complete (StringRef Line,
229
- size_t Pos ) {
230
- QueryParser P (Line);
284
+ std::vector<LineEditor::Completion>
285
+ QueryParser::complete (StringRef Line, size_t Pos, const QuerySession &QS ) {
286
+ QueryParser P (Line, QS );
231
287
P.CompletionPos = Line.data () + Pos;
232
288
233
289
P.doParse ();
0 commit comments