Skip to content

Commit 721a182

Browse files
authored
Merge pull request #22997 from github/hvitved-rust-parenthesized-entities
Rust: Skip parentheses in extraction
2 parents 128da06 + bbeda86 commit 721a182

68 files changed

Lines changed: 16377 additions & 1207 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

‎misc/codegen/lib/schemadefs.py‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -252,7 +252,7 @@ def __getitem__(self, item):
252252

253253
use_for_null = _ClassPragma("null")
254254

255-
qltest.add(_ClassPragma("skip"))
255+
qltest.add(_Pragma("skip"))
256256
qltest.add(_ClassPragma("collapse_hierarchy"))
257257
qltest.add(_ClassPragma("uncollapse_hierarchy"))
258258
qltest.add(

‎rust/ast-generator/src/main.rs‎

Lines changed: 23 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,8 @@ fn should_enum_be_skipped(name: &str) -> bool {
7676
fn should_node_be_skipped(name: &str) -> bool {
7777
name == "TypeAnchor" // we flatten TypeAnchor into PathSegment in the extractor
7878
|| name == "MacroStmts" // we workaround a getter bug in the extractor
79+
|| name == "ParenExpr" // parenthesized expressions are extracted as their inner expression
80+
|| name == "ParenPat" // parenthesized patterns are extracted as their inner pattern
7981
}
8082

8183
fn should_node_be_skipped_in_extractor(name: &str) -> bool {
@@ -133,6 +135,7 @@ fn get_additional_fields(node_name: &str) -> Vec<FieldInfo> {
133135
FieldInfo::body("body", "TokenTree"),
134136
],
135137
"MacroCall" => vec![FieldInfo::body("token_tree", "TokenTree")],
138+
"MacroExpr" | "RecordExpr" => vec![FieldInfo::list("attrs", "AnyAttr")],
136139
"FormatArgsExpr" => vec![FieldInfo::list("args", "FormatArgsArg")],
137140
"ArgList" => vec![FieldInfo::list("args", "Expr")],
138141
"Fn" => vec![FieldInfo::body("body", "BlockExpr")],
@@ -349,6 +352,7 @@ struct EnumVariantInfo {
349352
name: String,
350353
snake_case_name: String,
351354
variant_ast_name: String,
355+
emission: String,
352356
}
353357

354358
#[derive(Serialize)]
@@ -365,6 +369,8 @@ struct ExtractorNodeFieldInfo {
365369
name: String,
366370
method: String,
367371
snake_case_ty: String,
372+
attributes: bool,
373+
parenthesized_attrs: bool,
368374
string: bool,
369375
predicate: bool,
370376
optional: bool,
@@ -399,10 +405,16 @@ fn enum_to_extractor_info(node: &AstEnumSrc) -> ExtractorEnumInfo {
399405
.map(|v| {
400406
let name = class_name(v);
401407
let snake_case_name = to_lower_snake_case(v);
408+
let emission = match v.as_str() {
409+
"ParenExpr" => "self.emit_parenthesized_expr(inner)".to_owned(),
410+
"ParenPat" => "self.emit_parenthesized_pat(inner)".to_owned(),
411+
_ => format!("self.emit_{snake_case_name}(inner).map(Into::into)"),
412+
};
402413
EnumVariantInfo {
403414
name,
404415
snake_case_name,
405416
variant_ast_name: v.to_string(),
417+
emission,
406418
}
407419
})
408420
.collect(),
@@ -412,6 +424,7 @@ fn enum_to_extractor_info(node: &AstEnumSrc) -> ExtractorEnumInfo {
412424

413425
fn field_info_to_extractor_info(name: &str, field: &FieldInfo) -> ExtractorNodeFieldInfo {
414426
let name = property_name(name, &field.name);
427+
let attributes = name == "attrs";
415428
match &field.ty {
416429
FieldType::String => ExtractorNodeFieldInfo {
417430
name,
@@ -440,6 +453,7 @@ fn field_info_to_extractor_info(name: &str, field: &FieldInfo) -> ExtractorNodeF
440453
},
441454
FieldType::List(ty) => ExtractorNodeFieldInfo {
442455
name,
456+
attributes,
443457
method: if ty == "AnyAttr" {
444458
"attrs_with_doc".to_owned()
445459
} else {
@@ -453,12 +467,19 @@ fn field_info_to_extractor_info(name: &str, field: &FieldInfo) -> ExtractorNodeF
453467
}
454468
fn node_to_extractor_info(node: &AstNodeSrc) -> ExtractorNodeInfo {
455469
let fields = get_fields(node);
456-
let has_attrs = fields.iter().any(|f| f.name == "attrs");
470+
let parenthesized_attrs = matches!(node.name.as_str(), "MacroExpr" | "RecordExpr");
457471
let name = class_name(&node.name);
458-
let fields = fields
472+
let fields: Vec<_> = fields
459473
.iter()
460474
.map(|f| field_info_to_extractor_info(&name, f))
475+
.map(|mut f| {
476+
f.parenthesized_attrs = parenthesized_attrs && f.name == "attrs";
477+
f
478+
})
461479
.collect();
480+
let has_attrs = fields
481+
.iter()
482+
.any(|f| f.name == "attrs" && !f.parenthesized_attrs);
462483
ExtractorNodeInfo {
463484
name,
464485
snake_case_name: to_lower_snake_case(&node.name),

‎rust/ast-generator/templates/extractor.mustache‎

Lines changed: 19 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ impl Translator<'_> {
1818
{{>pre_emission}}
1919
let label = match node {
2020
{{#variants}}
21-
ast::{{ast_name}}::{{variant_ast_name}}(inner) => self.emit_{{snake_case_name}}(inner).map(Into::into),
21+
ast::{{ast_name}}::{{variant_ast_name}}(inner) => {{{emission}}},
2222
{{/variants}}
2323
}?;
2424
{{>post_emission}}
@@ -33,6 +33,18 @@ impl Translator<'_> {
3333
if self.should_be_excluded(node) { return None; }
3434
{{/has_attrs}}
3535
{{#fields}}
36+
{{#attributes}}
37+
{{#parenthesized_attrs}}
38+
let attrs = self.take_parenthesized_expr_attrs(node.syntax());
39+
{{/parenthesized_attrs}}
40+
{{^parenthesized_attrs}}
41+
let mut attrs = self.take_parenthesized_expr_attrs(node.syntax());
42+
attrs.extend(node.{{method}}().filter_map(|x| self.emit_{{snake_case_ty}}(&x)));
43+
{{/parenthesized_attrs}}
44+
{{/attributes}}
45+
{{/fields}}
46+
{{#fields}}
47+
{{^attributes}}
3648
let {{name}} =
3749
{{#predicate}}
3850
node.{{method}}().is_some()
@@ -50,11 +62,17 @@ impl Translator<'_> {
5062
if self.should_skip_bodies() { None } else { node.{{method}}().and_then(|x| self.emit_{{snake_case_ty}}(&x)) }
5163
{{/body}}
5264
;
65+
{{/attributes}}
5366
{{/fields}}
5467
let label = self.trap.emit(generated::{{name}} {
5568
id: TrapId::Star,
5669
{{#fields}}
70+
{{#attributes}}
71+
attrs,
72+
{{/attributes}}
73+
{{^attributes}}
5774
{{name}},
75+
{{/attributes}}
5876
{{/fields}}
5977
});
6078
self.emit_location(label, node);

0 commit comments

Comments
 (0)