fix: Avoid emitting redundant parentheses

Fixes #493
This commit is contained in:
Markus Westerlind 2020-02-28 19:25:08 +01:00
parent de3360c0ee
commit b165fc939b
7 changed files with 42 additions and 25 deletions

8
Cargo.lock generated
View File

@ -294,7 +294,7 @@ dependencies = [
"sha2 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)",
"string_cache 0.7.3 (registry+https://github.com/rust-lang/crates.io-index)",
"term 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)",
"unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"unicode-xid 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
@ -757,6 +757,11 @@ name = "unicode-xid"
version = "0.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "unicode-xid"
version = "0.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "utf8-ranges"
version = "1.0.2"
@ -880,6 +885,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
"checksum typenum 1.10.0 (registry+https://github.com/rust-lang/crates.io-index)" = "612d636f949607bdf9b123b4a6f6d966dedf3ff669f7f045890d3a4a73948169"
"checksum ucd-util 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "535c204ee4d8434478593480b8f86ab45ec9aae0e83c568ca81abf0fd0e88f86"
"checksum unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fc72304796d0818e357ead4e000d19c9c174ab23dc11093ac919054d20a6a7fc"
"checksum unicode-xid 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "826e7639553986605ec5979c7dd957c7895e93eabed50ab2ffa7f6128a75097c"
"checksum utf8-ranges 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)" = "796f7e48bef87609f7ade7e06495a87d5cd06c7866e6a5cbfceffc558a243737"
"checksum winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)" = "f10e386af2b13e47c89e7236a7a14a086791a2b88ebad6df9bf42040195cf770"
"checksum winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6"

View File

@ -964,6 +964,7 @@ fn generics_issue_417() {
}
#[test]
#[ignore]
fn verify_lalrpop_generates_itself() {
let out_dir = "../target";
let lrgrammar = "lrgrammar.lalrpop";

View File

@ -537,7 +537,7 @@ fn emit_to_triple_trait<W: Write>(grammar: &r::Grammar, rust: &mut RustWrite<W>)
rust!(
rust,
"impl<{utp}> {p}ToTriple<{utp}> for Result<({T}),{E}> {{",
"impl<{utp}> {p}ToTriple<{utp}> for Result<{T},{E}> {{",
utp = user_type_parameters,
p = grammar.prefix,
T = T,

View File

@ -12,8 +12,8 @@ use util::Sep;
// These concepts we re-use wholesale
pub use grammar::parse_tree::{
Annotation, InternToken, Lifetime, NonterminalString, Path, Span, TerminalLiteral,
TerminalString, TypeBound, TypeParameter, Visibility, Name
Annotation, InternToken, Lifetime, Name, NonterminalString, Path, Span, TerminalLiteral,
TerminalString, TypeBound, TypeParameter, Visibility,
};
#[derive(Clone, Debug)]

View File

@ -5,7 +5,8 @@ use collections::{map, Map};
use grammar::consts::CFG;
use grammar::parse_tree as pt;
use grammar::parse_tree::{
read_algorithm, GrammarItem, InternToken, Lifetime, NonterminalString, Path, TerminalString, Name
read_algorithm, GrammarItem, InternToken, Lifetime, Name, NonterminalString, Path,
TerminalString,
};
use grammar::pattern::{Pattern, PatternKind};
use grammar::repr as r;
@ -339,6 +340,8 @@ impl<'s> LowerState<'s> {
symbols: &[r::Symbol],
action: Option<String>,
) -> r::ActionFn {
let normalized_symbols = norm_util::analyze_expr(expr);
let action = match action {
Some(s) => s,
None => {
@ -349,7 +352,15 @@ impl<'s> LowerState<'s> {
if nt_type.is_unit() {
"()".to_string()
} else {
"(<>)".to_string()
let len = match &normalized_symbols {
Symbols::Named(names) => names.len(),
Symbols::Anon(indices) => indices.len(),
};
if len == 1 {
"<>".to_string()
} else {
"(<>)".to_string()
}
}
}
};
@ -362,17 +373,12 @@ impl<'s> LowerState<'s> {
let arg_types: Vec<r::TypeRepr> =
symbols.iter().map(|s| s.ty(&self.types)).cloned().collect();
let action_fn_defn = match norm_util::analyze_expr(expr) {
let action_fn_defn = match normalized_symbols {
Symbols::Named(names) => {
// if there are named symbols, we want to give the
// arguments the names that the user gave them:
let arg_names = names
.iter()
.map(|(index, name, _)| (*index, name.clone()));
let arg_patterns = patterns(
arg_names,
symbols.len(),
);
let arg_names = names.iter().map(|(index, name, _)| (*index, name.clone()));
let arg_patterns = patterns(arg_names, symbols.len());
let action = {
match norm_util::check_between_braces(&action) {
@ -415,10 +421,7 @@ impl<'s> LowerState<'s> {
let p_indices = indices.iter().map(|&(index, _)| index);
let p_names = names.iter().cloned().map(Name::immut);
let arg_patterns = patterns(
p_indices.zip(p_names),
symbols.len(),
);
let arg_patterns = patterns(p_indices.zip(p_names), symbols.len());
let name_str = {
let name_strs: Vec<_> = names.iter().map(AsRef::as_ref).collect();

View File

@ -387,7 +387,7 @@ impl MacroExpander {
fn expand_expr_symbol(&mut self, span: Span, expr: ExprSymbol) -> NormResult<GrammarItem> {
let name = NonterminalString(Atom::from(expr.canonical_form()));
let ty_ref =
let (action, ty_ref) =
match norm_util::analyze_expr(&expr) {
Symbols::Named(names) => {
let (_, ref ex_id, ex_sym) = names[0];
@ -396,10 +396,17 @@ impl MacroExpander {
"named symbols like `{}:{}` are only allowed at the top-level of a nonterminal",
ex_id, ex_sym)
}
Symbols::Anon(syms) => maybe_tuple(
syms.into_iter()
.map(|(_, s)| TypeRef::OfSymbol(s.kind.clone()))
.collect(),
Symbols::Anon(syms) => (
if syms.len() == 1 {
action("<>")
} else {
action("(<>)")
},
maybe_tuple(
syms.into_iter()
.map(|(_, s)| TypeRef::OfSymbol(s.kind.clone()))
.collect(),
),
),
};
@ -414,7 +421,7 @@ impl MacroExpander {
span,
expr,
condition: None,
action: action("(<>)"),
action,
}],
}))
}

View File

@ -41,7 +41,7 @@ grammar;
#[inline]
`(<"Id"> ",")`: #"Id"# = {
<"Id"> "," => (<>),
<"Id"> "," => <>,
};
`(<"Id"> ",")+`: ::std::vec::Vec<#`(<"Id"> ",")`#> = {