From 97ef40ee88b19ab1a85448cd83581da92f8a2618 Mon Sep 17 00:00:00 2001 From: Jeremy Chen Date: Fri, 9 Jun 2017 03:38:23 +0000 Subject: [PATCH] stylo: make font-variant-* longhands parsing more tolerant. Avoid early returning Err() in parsers, so we could let the the caller of the parsers to handle the rest of input, and return error if it requires parsing entirely. The point is let returning Err() stay inside input.try(), so we can count on input.try() to restore the position when parsing invalid idents. From gecko bug: Bug 1356134 (https://bugzilla.mozilla.org/show_bug.cgi?id=1356134) --- .../style/properties/longhand/font.mako.rs | 75 ++++++++----------- 1 file changed, 33 insertions(+), 42 deletions(-) diff --git a/components/style/properties/longhand/font.mako.rs b/components/style/properties/longhand/font.mako.rs index ed0da5f44c7..023caef6469 100644 --- a/components/style/properties/longhand/font.mako.rs +++ b/components/style/properties/longhand/font.mako.rs @@ -1376,21 +1376,21 @@ ${helpers.single_keyword_system("font-kerning", return Ok(SpecifiedValue::Value(result)) } - while let Ok(ident) = input.try(|input| input.expect_ident()) { - let flag = match_ignore_ascii_case! { &ident, - "stylistic" => Some(STYLISTIC), - "historical-forms" => Some(HISTORICAL_FORMS), - "styleset" => Some(STYLESET), - "character-variant" => Some(CHARACTER_VARIANT), - "swash" => Some(SWASH), - "ornaments" => Some(ORNAMENTS), - "annotation" => Some(ANNOTATION), - _ => None, - }; - let flag = match flag { - Some(flag) if !result.intersects(flag) => flag, - _ => return Err(SelectorParseError::UnexpectedIdent(ident).into()), - }; + while let Ok(flag) = input.try(|input| { + Ok(match_ignore_ascii_case! { &input.expect_ident().map_err(|_| ())?, + "stylistic" => STYLISTIC, + "historical-forms" => HISTORICAL_FORMS, + "styleset" => STYLESET, + "character-variant" => CHARACTER_VARIANT, + "swash" => SWASH, + "ornaments" => ORNAMENTS, + "annotation" => ANNOTATION, + _ => return Err(()), + }) + }) { + if result.intersects(flag) { + return Err(StyleParseError::UnspecifiedError.into()) + } result.insert(flag); } @@ -1406,9 +1406,9 @@ ${helpers.single_keyword_system("font-kerning", macro_rules! exclusive_value { (($value:ident, $set:expr) => $ident:ident) => { if $value.intersects($set) { - None + return Err(()) } else { - Some($ident) + $ident } } } @@ -1521,8 +1521,8 @@ macro_rules! exclusive_value { return Ok(SpecifiedValue::Value(result)) } - while let Ok(ident) = input.try(|input| input.expect_ident()) { - let flag = match_ignore_ascii_case! { &ident, + while let Ok(flag) = input.try(|input| { + Ok(match_ignore_ascii_case! { &input.expect_ident().map_err(|_| ())?, "jis78" => exclusive_value!((result, ${east_asian_variant_values}) => JIS78), "jis83" => @@ -1541,12 +1541,9 @@ macro_rules! exclusive_value { exclusive_value!((result, ${east_asian_width_values}) => PROPORTIONAL_WIDTH), "ruby" => exclusive_value!((result, RUBY) => RUBY), - _ => None, - }; - let flag = match flag { - Some(flag) => flag, - None => return Err(SelectorParseError::UnexpectedIdent(ident).into()), - }; + _ => return Err(()), + }) + }) { result.insert(flag); } @@ -1681,8 +1678,8 @@ macro_rules! exclusive_value { return Ok(SpecifiedValue::Value(NONE)) } - while let Ok(ident) = input.try(|input| input.expect_ident()) { - let flag = match_ignore_ascii_case! { &ident, + while let Ok(flag) = input.try(|input| { + Ok(match_ignore_ascii_case! { &input.expect_ident().map_err(|_| ())?, "common-ligatures" => exclusive_value!((result, ${common_lig_values}) => COMMON_LIGATURES), "no-common-ligatures" => @@ -1699,12 +1696,9 @@ macro_rules! exclusive_value { exclusive_value!((result, ${contextual_alt_values}) => CONTEXTUAL), "no-contextual" => exclusive_value!((result, ${contextual_alt_values}) => NO_CONTEXTUAL), - _ => None, - }; - let flag = match flag { - Some(flag) => flag, - None => return Err(SelectorParseError::UnexpectedIdent(ident).into()), - }; + _ => return Err(()), + }) + }) { result.insert(flag); } @@ -1832,14 +1826,14 @@ macro_rules! exclusive_value { return Ok(SpecifiedValue::Value(result)) } - while let Ok(ident) = input.try(|input| input.expect_ident()) { - let flag = match_ignore_ascii_case! { &ident, + while let Ok(flag) = input.try(|input| { + Ok(match_ignore_ascii_case! { &input.expect_ident().map_err(|_| ())?, "ordinal" => exclusive_value!((result, ORDINAL) => ORDINAL), "slashed-zero" => exclusive_value!((result, SLASHED_ZERO) => SLASHED_ZERO), "lining-nums" => - exclusive_value!((result, ${numeric_figure_values}) => LINING_NUMS ), + exclusive_value!((result, ${numeric_figure_values}) => LINING_NUMS), "oldstyle-nums" => exclusive_value!((result, ${numeric_figure_values}) => OLDSTYLE_NUMS), "proportional-nums" => @@ -1850,12 +1844,9 @@ macro_rules! exclusive_value { exclusive_value!((result, ${numeric_fraction_values}) => DIAGONAL_FRACTIONS), "stacked-fractions" => exclusive_value!((result, ${numeric_fraction_values}) => STACKED_FRACTIONS), - _ => None, - }; - let flag = match flag { - Some(flag) => flag, - None => return Err(SelectorParseError::UnexpectedIdent(ident).into()), - }; + _ => return Err(()), + }) + }) { result.insert(flag); }