Skip to content

Commit 85e9f5a

Browse files
authored
Merge pull request #19559 from github/redsun82/rust-extract-libs
Rust: move body skipping logic to code generation
2 parents 649481e + 58266e6 commit 85e9f5a

File tree

4 files changed

+162
-711
lines changed

4 files changed

+162
-711
lines changed

rust/ast-generator/src/main.rs

Lines changed: 105 additions & 186 deletions
Original file line numberDiff line numberDiff line change
@@ -114,7 +114,9 @@ fn node_src_to_schema_class(
114114
let (ty, child) = match &f.ty {
115115
FieldType::String => ("optional[string]".to_string(), false),
116116
FieldType::Predicate => ("predicate".to_string(), false),
117-
FieldType::Optional(ty) => (format!("optional[\"{}\"]", class_name(ty)), true),
117+
FieldType::Optional(ty) | FieldType::Body(ty) => {
118+
(format!("optional[\"{}\"]", class_name(ty)), true)
119+
}
118120
FieldType::List(ty) => (format!("list[\"{}\"]", class_name(ty)), true),
119121
};
120122
SchemaField {
@@ -169,6 +171,7 @@ enum FieldType {
169171
String,
170172
Predicate,
171173
Optional(String),
174+
Body(String),
172175
List(String),
173176
}
174177

@@ -177,158 +180,95 @@ struct FieldInfo {
177180
ty: FieldType,
178181
}
179182

183+
impl FieldInfo {
184+
pub fn optional(name: &str, ty: &str) -> FieldInfo {
185+
FieldInfo {
186+
name: name.to_string(),
187+
ty: FieldType::Optional(ty.to_string()),
188+
}
189+
}
190+
191+
pub fn body(name: &str, ty: &str) -> FieldInfo {
192+
FieldInfo {
193+
name: name.to_string(),
194+
ty: FieldType::Body(ty.to_string()),
195+
}
196+
}
197+
198+
pub fn string(name: &str) -> FieldInfo {
199+
FieldInfo {
200+
name: name.to_string(),
201+
ty: FieldType::String,
202+
}
203+
}
204+
205+
pub fn predicate(name: &str) -> FieldInfo {
206+
FieldInfo {
207+
name: name.to_string(),
208+
ty: FieldType::Predicate,
209+
}
210+
}
211+
212+
pub fn list(name: &str, ty: &str) -> FieldInfo {
213+
FieldInfo {
214+
name: name.to_string(),
215+
ty: FieldType::List(ty.to_string()),
216+
}
217+
}
218+
}
219+
180220
fn get_additional_fields(node: &AstNodeSrc) -> Vec<FieldInfo> {
181221
match node.name.as_str() {
182-
"Name" | "NameRef" | "Lifetime" => vec![FieldInfo {
183-
name: "text".to_string(),
184-
ty: FieldType::String,
185-
}],
186-
"Abi" => vec![FieldInfo {
187-
name: "abi_string".to_string(),
188-
ty: FieldType::String,
189-
}],
190-
"Literal" => vec![FieldInfo {
191-
name: "text_value".to_string(),
192-
ty: FieldType::String,
193-
}],
194-
"PrefixExpr" => vec![FieldInfo {
195-
name: "operator_name".to_string(),
196-
ty: FieldType::String,
197-
}],
222+
"Name" | "NameRef" | "Lifetime" => vec![FieldInfo::string("text")],
223+
"Abi" => vec![FieldInfo::string("abi_string")],
224+
"Literal" => vec![FieldInfo::string("text_value")],
225+
"PrefixExpr" => vec![FieldInfo::string("operator_name")],
198226
"BinExpr" => vec![
199-
FieldInfo {
200-
name: "lhs".to_string(),
201-
ty: FieldType::Optional("Expr".to_string()),
202-
},
203-
FieldInfo {
204-
name: "rhs".to_string(),
205-
ty: FieldType::Optional("Expr".to_string()),
206-
},
207-
FieldInfo {
208-
name: "operator_name".to_string(),
209-
ty: FieldType::String,
210-
},
227+
FieldInfo::optional("lhs", "Expr"),
228+
FieldInfo::optional("rhs", "Expr"),
229+
FieldInfo::string("operator_name"),
211230
],
212231
"IfExpr" => vec![
213-
FieldInfo {
214-
name: "then_branch".to_string(),
215-
ty: FieldType::Optional("BlockExpr".to_string()),
216-
},
217-
FieldInfo {
218-
name: "else_branch".to_string(),
219-
ty: FieldType::Optional("ElseBranch".to_string()),
220-
},
221-
FieldInfo {
222-
name: "condition".to_string(),
223-
ty: FieldType::Optional("Expr".to_string()),
224-
},
232+
FieldInfo::optional("then_branch", "BlockExpr"),
233+
FieldInfo::optional("else_branch", "ElseBranch"),
234+
FieldInfo::optional("condition", "Expr"),
225235
],
226236
"RangeExpr" => vec![
227-
FieldInfo {
228-
name: "start".to_string(),
229-
ty: FieldType::Optional("Expr".to_string()),
230-
},
231-
FieldInfo {
232-
name: "end".to_string(),
233-
ty: FieldType::Optional("Expr".to_string()),
234-
},
235-
FieldInfo {
236-
name: "operator_name".to_string(),
237-
ty: FieldType::String,
238-
},
237+
FieldInfo::optional("start", "Expr"),
238+
FieldInfo::optional("end", "Expr"),
239+
FieldInfo::string("operator_name"),
239240
],
240241
"RangePat" => vec![
241-
FieldInfo {
242-
name: "start".to_string(),
243-
ty: FieldType::Optional("Pat".to_string()),
244-
},
245-
FieldInfo {
246-
name: "end".to_string(),
247-
ty: FieldType::Optional("Pat".to_string()),
248-
},
249-
FieldInfo {
250-
name: "operator_name".to_string(),
251-
ty: FieldType::String,
252-
},
242+
FieldInfo::optional("start", "Pat"),
243+
FieldInfo::optional("end", "Pat"),
244+
FieldInfo::string("operator_name"),
253245
],
254246
"IndexExpr" => vec![
255-
FieldInfo {
256-
name: "index".to_string(),
257-
ty: FieldType::Optional("Expr".to_string()),
258-
},
259-
FieldInfo {
260-
name: "base".to_string(),
261-
ty: FieldType::Optional("Expr".to_string()),
262-
},
247+
FieldInfo::optional("index", "Expr"),
248+
FieldInfo::optional("base", "Expr"),
263249
],
264250
"Impl" => vec![
265-
FieldInfo {
266-
name: "trait_".to_string(),
267-
ty: FieldType::Optional("Type".to_string()),
268-
},
269-
FieldInfo {
270-
name: "self_ty".to_string(),
271-
ty: FieldType::Optional("Type".to_string()),
272-
},
251+
FieldInfo::optional("trait_", "Type"),
252+
FieldInfo::optional("self_ty", "Type"),
273253
],
274-
"ForExpr" => vec![FieldInfo {
275-
name: "iterable".to_string(),
276-
ty: FieldType::Optional("Expr".to_string()),
277-
}],
278-
"WhileExpr" => vec![FieldInfo {
279-
name: "condition".to_string(),
280-
ty: FieldType::Optional("Expr".to_string()),
281-
}],
282-
"MatchGuard" => vec![FieldInfo {
283-
name: "condition".to_string(),
284-
ty: FieldType::Optional("Expr".to_string()),
285-
}],
254+
"ForExpr" => vec![FieldInfo::optional("iterable", "Expr")],
255+
"WhileExpr" => vec![FieldInfo::optional("condition", "Expr")],
256+
"MatchGuard" => vec![FieldInfo::optional("condition", "Expr")],
286257
"MacroDef" => vec![
287-
FieldInfo {
288-
name: "args".to_string(),
289-
ty: FieldType::Optional("TokenTree".to_string()),
290-
},
291-
FieldInfo {
292-
name: "body".to_string(),
293-
ty: FieldType::Optional("TokenTree".to_string()),
294-
},
258+
FieldInfo::body("args", "TokenTree"),
259+
FieldInfo::body("body", "TokenTree"),
295260
],
296-
"FormatArgsExpr" => vec![FieldInfo {
297-
name: "args".to_string(),
298-
ty: FieldType::List("FormatArgsArg".to_string()),
299-
}],
300-
"ArgList" => vec![FieldInfo {
301-
name: "args".to_string(),
302-
ty: FieldType::List("Expr".to_string()),
303-
}],
304-
"Fn" => vec![FieldInfo {
305-
name: "body".to_string(),
306-
ty: FieldType::Optional("BlockExpr".to_string()),
307-
}],
308-
"Const" => vec![FieldInfo {
309-
name: "body".to_string(),
310-
ty: FieldType::Optional("Expr".to_string()),
311-
}],
312-
"Static" => vec![FieldInfo {
313-
name: "body".to_string(),
314-
ty: FieldType::Optional("Expr".to_string()),
315-
}],
316-
"ClosureExpr" => vec![FieldInfo {
317-
name: "body".to_string(),
318-
ty: FieldType::Optional("Expr".to_string()),
319-
}],
320-
"ArrayExpr" => vec![FieldInfo {
321-
name: "is_semicolon".to_string(),
322-
ty: FieldType::Predicate,
323-
}],
324-
"SelfParam" => vec![FieldInfo {
325-
name: "is_amp".to_string(),
326-
ty: FieldType::Predicate,
327-
}],
328-
"UseTree" => vec![FieldInfo {
329-
name: "is_star".to_string(),
330-
ty: FieldType::Predicate,
331-
}],
261+
"MacroCall" => vec![FieldInfo::body("token_tree", "TokenTree")],
262+
"FormatArgsExpr" => vec![FieldInfo::list("args", "FormatArgsArg")],
263+
"ArgList" => vec![FieldInfo::list("args", "Expr")],
264+
"Fn" => vec![FieldInfo::body("body", "BlockExpr")],
265+
"Const" => vec![FieldInfo::body("body", "Expr")],
266+
"Static" => vec![FieldInfo::body("body", "Expr")],
267+
"Param" => vec![FieldInfo::body("pat", "Pat")],
268+
"ClosureExpr" => vec![FieldInfo::optional("body", "Expr")],
269+
"ArrayExpr" => vec![FieldInfo::predicate("is_semicolon")],
270+
"SelfParam" => vec![FieldInfo::predicate("is_amp")],
271+
"UseTree" => vec![FieldInfo::predicate("is_star")],
332272
_ => vec![],
333273
}
334274
}
@@ -352,9 +292,11 @@ fn get_fields(node: &AstNodeSrc) -> Vec<FieldInfo> {
352292
result.extend(get_additional_fields(node));
353293

354294
for field in &node.fields {
355-
match (node.name.as_str(), field.method_name().as_str()) {
295+
let name = field.method_name();
296+
match (node.name.as_str(), name.as_str()) {
356297
("ArrayExpr", "expr") // The ArrayExpr type also has an 'exprs' field
357298
| ("PathSegment", "ty" | "path_type") // these are broken, handling them manually
299+
| ("Param", "pat") | ("MacroCall", "token_tree") // handled manually to use `body`
358300
=> continue,
359301
_ => {}
360302
}
@@ -367,61 +309,30 @@ fn get_fields(node: &AstNodeSrc) -> Vec<FieldInfo> {
367309
Cardinality::Many => FieldType::List(ty.clone()),
368310
},
369311
};
370-
result.push(FieldInfo {
371-
name: field.method_name(),
372-
ty,
373-
});
312+
result.push(FieldInfo { name, ty });
374313
}
375314
for trait_ in &node.traits {
376315
match trait_.as_str() {
377-
"HasAttrs" => result.push(FieldInfo {
378-
name: "attrs".to_owned(),
379-
ty: FieldType::List("Attr".to_owned()),
380-
}),
381-
"HasName" => result.push(FieldInfo {
382-
name: "name".to_owned(),
383-
ty: FieldType::Optional("Name".to_owned()),
384-
}),
385-
"HasVisibility" => result.push(FieldInfo {
386-
name: "visibility".to_owned(),
387-
ty: FieldType::Optional("Visibility".to_owned()),
388-
}),
316+
"HasAttrs" => result.push(FieldInfo::list("attrs", "Attr")),
317+
"HasName" => result.push(FieldInfo::optional("name", "Name")),
318+
"HasVisibility" => result.push(FieldInfo::optional("visibility", "Visibility")),
389319
"HasGenericParams" => {
390-
result.push(FieldInfo {
391-
name: "generic_param_list".to_owned(),
392-
ty: FieldType::Optional("GenericParamList".to_owned()),
393-
});
394-
result.push(FieldInfo {
395-
name: "where_clause".to_owned(),
396-
ty: FieldType::Optional("WhereClause".to_owned()),
397-
})
320+
result.push(FieldInfo::optional(
321+
"generic_param_list",
322+
"GenericParamList",
323+
));
324+
result.push(FieldInfo::optional("where_clause", "WhereClause"))
325+
}
326+
"HasGenericArgs" => {
327+
result.push(FieldInfo::optional("generic_arg_list", "GenericArgList"))
398328
}
399-
"HasGenericArgs" => result.push(FieldInfo {
400-
name: "generic_arg_list".to_owned(),
401-
ty: FieldType::Optional("GenericArgList".to_owned()),
402-
}),
403-
"HasTypeBounds" => result.push(FieldInfo {
404-
name: "type_bound_list".to_owned(),
405-
ty: FieldType::Optional("TypeBoundList".to_owned()),
406-
}),
407-
"HasModuleItem" => result.push(FieldInfo {
408-
name: "items".to_owned(),
409-
ty: FieldType::List("Item".to_owned()),
410-
}),
329+
"HasTypeBounds" => result.push(FieldInfo::optional("type_bound_list", "TypeBoundList")),
330+
"HasModuleItem" => result.push(FieldInfo::list("items", "Item")),
411331
"HasLoopBody" => {
412-
result.push(FieldInfo {
413-
name: "label".to_owned(),
414-
ty: FieldType::Optional("Label".to_owned()),
415-
});
416-
result.push(FieldInfo {
417-
name: "loop_body".to_owned(),
418-
ty: FieldType::Optional("BlockExpr".to_owned()),
419-
})
332+
result.push(FieldInfo::optional("label", "Label"));
333+
result.push(FieldInfo::optional("loop_body", "BlockExpr"))
420334
}
421-
"HasArgList" => result.push(FieldInfo {
422-
name: "arg_list".to_owned(),
423-
ty: FieldType::Optional("ArgList".to_owned()),
424-
}),
335+
"HasArgList" => result.push(FieldInfo::optional("arg_list", "ArgList")),
425336
"HasDocComments" => {}
426337

427338
_ => panic!("Unknown trait {}", trait_),
@@ -455,6 +366,7 @@ struct ExtractorNodeFieldInfo {
455366
predicate: bool,
456367
optional: bool,
457368
list: bool,
369+
body: bool,
458370
}
459371

460372
#[derive(Serialize)]
@@ -518,6 +430,13 @@ fn field_info_to_extractor_info(name: &str, field: &FieldInfo) -> ExtractorNodeF
518430
optional: true,
519431
..Default::default()
520432
},
433+
FieldType::Body(ty) => ExtractorNodeFieldInfo {
434+
name,
435+
method: field.name.clone(),
436+
snake_case_ty: to_lower_snake_case(ty),
437+
body: true,
438+
..Default::default()
439+
},
521440
FieldType::List(ty) => ExtractorNodeFieldInfo {
522441
name,
523442
method: field.name.clone(),

0 commit comments

Comments
 (0)