diff --git a/src/libsyntax/ext/quote.rs b/src/libsyntax/ext/quote.rs index c11ffe66e6c39..2f609d86f39ff 100644 --- a/src/libsyntax/ext/quote.rs +++ b/src/libsyntax/ext/quote.rs @@ -171,10 +171,12 @@ pub mod rt { } } + impl_to_source! { ast::Path, path_to_string } impl_to_source! { ast::Ty, ty_to_string } impl_to_source! { ast::Block, block_to_string } impl_to_source! { ast::Arg, arg_to_string } impl_to_source! { Generics, generics_to_string } + impl_to_source! { ast::WhereClause, where_clause_to_string } impl_to_source! { P, item_to_string } impl_to_source! { P, impl_item_to_string } impl_to_source! { P, trait_item_to_string } @@ -309,6 +311,7 @@ pub mod rt { } impl_to_tokens! { ast::Ident } + impl_to_tokens! { ast::Path } impl_to_tokens! { P } impl_to_tokens! { P } impl_to_tokens! { P } @@ -318,6 +321,7 @@ pub mod rt { impl_to_tokens! { ast::Ty } impl_to_tokens_lifetime! { &'a [ast::Ty] } impl_to_tokens! { Generics } + impl_to_tokens! { ast::WhereClause } impl_to_tokens! { P } impl_to_tokens! { P } impl_to_tokens! { ast::Block } diff --git a/src/libsyntax/parse/parser.rs b/src/libsyntax/parse/parser.rs index 4ae5e0faa3105..023f6e69945ab 100644 --- a/src/libsyntax/parse/parser.rs +++ b/src/libsyntax/parse/parser.rs @@ -1126,7 +1126,7 @@ impl<'a> Parser<'a> { p.parse_arg_general(false) }); - p.parse_where_clause(&mut generics); + generics.where_clause = p.parse_where_clause(); let sig = ast::MethodSig { unsafety: style, decl: d, @@ -3932,9 +3932,14 @@ impl<'a> Parser<'a> { /// ``` /// where T : Trait + 'b, 'a : 'b /// ``` - fn parse_where_clause(&mut self, generics: &mut ast::Generics) { + fn parse_where_clause(&mut self) -> ast::WhereClause { + let mut where_clause = WhereClause { + id: ast::DUMMY_NODE_ID, + predicates: Vec::new(), + }; + if !self.eat_keyword(keywords::Where) { - return + return where_clause; } let mut parsed_something = false; @@ -3957,7 +3962,7 @@ impl<'a> Parser<'a> { let hi = self.span.hi; let span = mk_sp(lo, hi); - generics.where_clause.predicates.push(ast::WherePredicate::RegionPredicate( + where_clause.predicates.push(ast::WherePredicate::RegionPredicate( ast::WhereRegionPredicate { span: span, lifetime: bounded_lifetime, @@ -3992,7 +3997,7 @@ impl<'a> Parser<'a> { at least one bound in it"); } - generics.where_clause.predicates.push(ast::WherePredicate::BoundPredicate( + where_clause.predicates.push(ast::WherePredicate::BoundPredicate( ast::WhereBoundPredicate { span: span, bound_lifetimes: bound_lifetimes, @@ -4005,7 +4010,7 @@ impl<'a> Parser<'a> { // let ty = self.parse_ty(); let hi = self.span.hi; let span = mk_sp(lo, hi); - // generics.where_clause.predicates.push( + // where_clause.predicates.push( // ast::WherePredicate::EqPredicate(ast::WhereEqPredicate { // id: ast::DUMMY_NODE_ID, // span: span, @@ -4036,6 +4041,8 @@ impl<'a> Parser<'a> { "a `where` clause must have at least one predicate \ in it"); } + + where_clause } fn parse_fn_args(&mut self, named_args: bool, allow_variadic: bool) @@ -4354,7 +4361,7 @@ impl<'a> Parser<'a> { fn parse_item_fn(&mut self, unsafety: Unsafety, abi: abi::Abi) -> ItemInfo { let (ident, mut generics) = self.parse_fn_header(); let decl = self.parse_fn_decl(false); - self.parse_where_clause(&mut generics); + generics.where_clause = self.parse_where_clause(); let (inner_attrs, body) = self.parse_inner_attrs_and_block(); (ident, ItemFn(decl, unsafety, abi, generics, body), Some(inner_attrs)) } @@ -4439,7 +4446,7 @@ impl<'a> Parser<'a> { let (explicit_self, decl) = self.parse_fn_decl_with_self(|p| { p.parse_arg() }); - self.parse_where_clause(&mut generics); + generics.where_clause = self.parse_where_clause(); let (inner_attrs, body) = self.parse_inner_attrs_and_block(); (ident, inner_attrs, MethodImplItem(ast::MethodSig { generics: generics, @@ -4460,7 +4467,7 @@ impl<'a> Parser<'a> { // Parse supertrait bounds. let bounds = self.parse_colon_then_ty_param_bounds(BoundParsingMode::Bare); - self.parse_where_clause(&mut tps); + tps.where_clause = self.parse_where_clause(); let meths = self.parse_trait_items(); (ident, ItemTrait(unsafety, tps, bounds, meths), None) @@ -4531,7 +4538,7 @@ impl<'a> Parser<'a> { if opt_trait.is_some() { ty = self.parse_ty_sum(); } - self.parse_where_clause(&mut generics); + generics.where_clause = self.parse_where_clause(); self.expect(&token::OpenDelim(token::Brace)); let attrs = self.parse_inner_attributes(); @@ -4603,7 +4610,7 @@ impl<'a> Parser<'a> { // struct. let (fields, ctor_id) = if self.token.is_keyword(keywords::Where) { - self.parse_where_clause(&mut generics); + generics.where_clause = self.parse_where_clause(); if self.eat(&token::Semi) { // If we see a: `struct Foo where T: Copy;` style decl. (Vec::new(), Some(ast::DUMMY_NODE_ID)) @@ -4684,12 +4691,12 @@ impl<'a> Parser<'a> { token::get_ident(class_name.clone()))); } - self.parse_where_clause(generics); + generics.where_clause = self.parse_where_clause(); self.expect(&token::Semi); fields // This is the case where we just see struct Foo where T: Copy; } else if self.token.is_keyword(keywords::Where) { - self.parse_where_clause(generics); + generics.where_clause = self.parse_where_clause(); self.expect(&token::Semi); Vec::new() // This case is where we see: `struct Foo;` @@ -4937,7 +4944,7 @@ impl<'a> Parser<'a> { let (ident, mut generics) = self.parse_fn_header(); let decl = self.parse_fn_decl(true); - self.parse_where_clause(&mut generics); + generics.where_clause = self.parse_where_clause(); let hi = self.span.hi; self.expect(&token::Semi); P(ast::ForeignItem { @@ -5082,7 +5089,7 @@ impl<'a> Parser<'a> { fn parse_item_type(&mut self) -> ItemInfo { let ident = self.parse_ident(); let mut tps = self.parse_generics(); - self.parse_where_clause(&mut tps); + tps.where_clause = self.parse_where_clause(); self.expect(&token::Eq); let ty = self.parse_ty_sum(); self.expect(&token::Semi); @@ -5182,7 +5189,7 @@ impl<'a> Parser<'a> { fn parse_item_enum(&mut self) -> ItemInfo { let id = self.parse_ident(); let mut generics = self.parse_generics(); - self.parse_where_clause(&mut generics); + generics.where_clause = self.parse_where_clause(); self.expect(&token::OpenDelim(token::Brace)); let enum_definition = self.parse_enum_def(&generics); diff --git a/src/libsyntax/print/pprust.rs b/src/libsyntax/print/pprust.rs index 828d085fd432e..ddcdcf4e1b8fa 100644 --- a/src/libsyntax/print/pprust.rs +++ b/src/libsyntax/print/pprust.rs @@ -367,6 +367,10 @@ pub fn generics_to_string(generics: &ast::Generics) -> String { $to_string(|s| s.print_generics(generics)) } +pub fn where_clause_to_string(i: &ast::WhereClause) -> String { + $to_string(|s| s.print_where_clause(i)) +} + pub fn fn_block_to_string(p: &ast::FnDecl) -> String { $to_string(|s| s.print_fn_block_args(p)) } @@ -912,7 +916,7 @@ impl<'a> State<'a> { try!(space(&mut self.s)); try!(self.word_space("=")); try!(self.print_type(&**ty)); - try!(self.print_where_clause(params)); + try!(self.print_where_clause(¶ms.where_clause)); try!(word(&mut self.s, ";")); try!(self.end()); // end the outer ibox } @@ -975,7 +979,7 @@ impl<'a> State<'a> { } try!(self.print_type(&**ty)); - try!(self.print_where_clause(generics)); + try!(self.print_where_clause(&generics.where_clause)); try!(space(&mut self.s)); try!(self.bopen()); @@ -1003,7 +1007,7 @@ impl<'a> State<'a> { } } try!(self.print_bounds(":", &real_bounds[..])); - try!(self.print_where_clause(generics)); + try!(self.print_where_clause(&generics.where_clause)); try!(word(&mut self.s, " ")); try!(self.bopen()); for trait_item in trait_items { @@ -1061,7 +1065,7 @@ impl<'a> State<'a> { try!(self.head(&visibility_qualified(visibility, "enum"))); try!(self.print_ident(ident)); try!(self.print_generics(generics)); - try!(self.print_where_clause(generics)); + try!(self.print_where_clause(&generics.where_clause)); try!(space(&mut self.s)); self.print_variants(&enum_definition.variants, span) } @@ -1115,12 +1119,12 @@ impl<'a> State<'a> { )); try!(self.pclose()); } - try!(self.print_where_clause(generics)); + try!(self.print_where_clause(&generics.where_clause)); try!(word(&mut self.s, ";")); try!(self.end()); self.end() // close the outer-box } else { - try!(self.print_where_clause(generics)); + try!(self.print_where_clause(&generics.where_clause)); try!(self.nbsp()); try!(self.bopen()); try!(self.hardbreak_if_not_bol()); @@ -2343,7 +2347,7 @@ impl<'a> State<'a> { } try!(self.print_generics(generics)); try!(self.print_fn_args_and_ret(decl, opt_explicit_self)); - self.print_where_clause(generics) + self.print_where_clause(&generics.where_clause) } pub fn print_fn_args(&mut self, decl: &ast::FnDecl, @@ -2526,19 +2530,16 @@ impl<'a> State<'a> { } } - pub fn print_where_clause(&mut self, generics: &ast::Generics) + pub fn print_where_clause(&mut self, where_clause: &ast::WhereClause) -> io::Result<()> { - if generics.where_clause.predicates.len() == 0 { + if where_clause.predicates.len() == 0 { return Ok(()) } try!(space(&mut self.s)); try!(self.word_space("where")); - for (i, predicate) in generics.where_clause - .predicates - .iter() - .enumerate() { + for (i, predicate) in where_clause.predicates.iter().enumerate() { if i != 0 { try!(self.word_space(",")); }