Add interpolated_or_expr_span macro and pass lo to newly added parse_dot_suffix
This commit is contained in:
parent
1bde18d60c
commit
2bc8f4ff80
2 changed files with 39 additions and 31 deletions
|
@ -233,6 +233,21 @@ macro_rules! maybe_whole {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Uses $parse_expr to parse an expression and returns the span of the interpolated
|
||||||
|
/// token or the span of the parsed expression, if it was not interpolated
|
||||||
|
macro_rules! interpolated_or_expr_span {
|
||||||
|
($p:expr, $parse_expr:expr) => {
|
||||||
|
{
|
||||||
|
let is_interpolated = $p.token.is_interpolated();
|
||||||
|
let e = $parse_expr;
|
||||||
|
if is_interpolated {
|
||||||
|
($p.last_span, e)
|
||||||
|
} else {
|
||||||
|
(e.span, e)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn maybe_append(mut lhs: Vec<Attribute>, rhs: Option<Vec<Attribute>>)
|
fn maybe_append(mut lhs: Vec<Attribute>, rhs: Option<Vec<Attribute>>)
|
||||||
-> Vec<Attribute> {
|
-> Vec<Attribute> {
|
||||||
|
@ -2323,14 +2338,8 @@ impl<'a> Parser<'a> {
|
||||||
-> PResult<'a, P<Expr>> {
|
-> PResult<'a, P<Expr>> {
|
||||||
let attrs = try!(self.parse_or_use_outer_attributes(already_parsed_attrs));
|
let attrs = try!(self.parse_or_use_outer_attributes(already_parsed_attrs));
|
||||||
|
|
||||||
let is_interpolated = self.token.is_interpolated();
|
let (span, b) = interpolated_or_expr_span!(self, try!(self.parse_bottom_expr()));
|
||||||
let b = try!(self.parse_bottom_expr());
|
self.parse_dot_or_call_expr_with(b, span.lo, attrs)
|
||||||
let lo = if is_interpolated {
|
|
||||||
self.last_span.lo
|
|
||||||
} else {
|
|
||||||
b.span.lo
|
|
||||||
};
|
|
||||||
self.parse_dot_or_call_expr_with(b, lo, attrs)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn parse_dot_or_call_expr_with(&mut self,
|
pub fn parse_dot_or_call_expr_with(&mut self,
|
||||||
|
@ -2368,7 +2377,8 @@ impl<'a> Parser<'a> {
|
||||||
fn parse_dot_suffix(&mut self,
|
fn parse_dot_suffix(&mut self,
|
||||||
ident: Ident,
|
ident: Ident,
|
||||||
ident_span: Span,
|
ident_span: Span,
|
||||||
self_value: P<Expr>)
|
self_value: P<Expr>,
|
||||||
|
lo: BytePos)
|
||||||
-> PResult<'a, P<Expr>> {
|
-> PResult<'a, P<Expr>> {
|
||||||
let (_, tys, bindings) = if self.eat(&token::ModSep) {
|
let (_, tys, bindings) = if self.eat(&token::ModSep) {
|
||||||
try!(self.expect_lt());
|
try!(self.expect_lt());
|
||||||
|
@ -2382,8 +2392,6 @@ impl<'a> Parser<'a> {
|
||||||
self.span_err(last_span, "type bindings are only permitted on trait paths");
|
self.span_err(last_span, "type bindings are only permitted on trait paths");
|
||||||
}
|
}
|
||||||
|
|
||||||
let lo = self_value.span.lo;
|
|
||||||
|
|
||||||
Ok(match self.token {
|
Ok(match self.token {
|
||||||
// expr.f() method call.
|
// expr.f() method call.
|
||||||
token::OpenDelim(token::Paren) => {
|
token::OpenDelim(token::Paren) => {
|
||||||
|
@ -2428,7 +2436,7 @@ impl<'a> Parser<'a> {
|
||||||
hi = self.span.hi;
|
hi = self.span.hi;
|
||||||
self.bump();
|
self.bump();
|
||||||
|
|
||||||
e = try!(self.parse_dot_suffix(i, mk_sp(dot_pos, hi), e));
|
e = try!(self.parse_dot_suffix(i, mk_sp(dot_pos, hi), e, lo));
|
||||||
}
|
}
|
||||||
token::Literal(token::Integer(n), suf) => {
|
token::Literal(token::Integer(n), suf) => {
|
||||||
let sp = self.span;
|
let sp = self.span;
|
||||||
|
@ -2481,7 +2489,7 @@ impl<'a> Parser<'a> {
|
||||||
let dot_pos = self.last_span.hi;
|
let dot_pos = self.last_span.hi;
|
||||||
e = try!(self.parse_dot_suffix(special_idents::invalid,
|
e = try!(self.parse_dot_suffix(special_idents::invalid,
|
||||||
mk_sp(dot_pos, dot_pos),
|
mk_sp(dot_pos, dot_pos),
|
||||||
e));
|
e, lo));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
continue;
|
continue;
|
||||||
|
@ -2716,31 +2724,31 @@ impl<'a> Parser<'a> {
|
||||||
let ex = match self.token {
|
let ex = match self.token {
|
||||||
token::Not => {
|
token::Not => {
|
||||||
self.bump();
|
self.bump();
|
||||||
let (interpolated, prev_span) = (self.token.is_interpolated(), self.span);
|
let (span, e) = interpolated_or_expr_span!(self,
|
||||||
let e = try!(self.parse_prefix_expr(None));
|
try!(self.parse_prefix_expr(None)));
|
||||||
hi = if interpolated { prev_span.hi } else { e.span.hi };
|
hi = span.hi;
|
||||||
self.mk_unary(UnNot, e)
|
self.mk_unary(UnNot, e)
|
||||||
}
|
}
|
||||||
token::BinOp(token::Minus) => {
|
token::BinOp(token::Minus) => {
|
||||||
self.bump();
|
self.bump();
|
||||||
let (interpolated, prev_span) = (self.token.is_interpolated(), self.span);
|
let (span, e) = interpolated_or_expr_span!(self,
|
||||||
let e = try!(self.parse_prefix_expr(None));
|
try!(self.parse_prefix_expr(None)));
|
||||||
hi = if interpolated { prev_span.hi } else { e.span.hi };
|
hi = span.hi;
|
||||||
self.mk_unary(UnNeg, e)
|
self.mk_unary(UnNeg, e)
|
||||||
}
|
}
|
||||||
token::BinOp(token::Star) => {
|
token::BinOp(token::Star) => {
|
||||||
self.bump();
|
self.bump();
|
||||||
let (interpolated, prev_span) = (self.token.is_interpolated(), self.span);
|
let (span, e) = interpolated_or_expr_span!(self,
|
||||||
let e = try!(self.parse_prefix_expr(None));
|
try!(self.parse_prefix_expr(None)));
|
||||||
hi = if interpolated { prev_span.hi } else { e.span.hi };
|
hi = span.hi;
|
||||||
self.mk_unary(UnDeref, e)
|
self.mk_unary(UnDeref, e)
|
||||||
}
|
}
|
||||||
token::BinOp(token::And) | token::AndAnd => {
|
token::BinOp(token::And) | token::AndAnd => {
|
||||||
try!(self.expect_and());
|
try!(self.expect_and());
|
||||||
let m = try!(self.parse_mutability());
|
let m = try!(self.parse_mutability());
|
||||||
let (interpolated, prev_span) = (self.token.is_interpolated(), self.span);
|
let (span, e) = interpolated_or_expr_span!(self,
|
||||||
let e = try!(self.parse_prefix_expr(None));
|
try!(self.parse_prefix_expr(None)));
|
||||||
hi = if interpolated { prev_span.hi } else { e.span.hi };
|
hi = span.hi;
|
||||||
ExprAddrOf(m, e)
|
ExprAddrOf(m, e)
|
||||||
}
|
}
|
||||||
token::Ident(..) if self.token.is_keyword(keywords::In) => {
|
token::Ident(..) if self.token.is_keyword(keywords::In) => {
|
||||||
|
@ -2758,10 +2766,10 @@ impl<'a> Parser<'a> {
|
||||||
}
|
}
|
||||||
token::Ident(..) if self.token.is_keyword(keywords::Box) => {
|
token::Ident(..) if self.token.is_keyword(keywords::Box) => {
|
||||||
self.bump();
|
self.bump();
|
||||||
let (interpolated, prev_span) = (self.token.is_interpolated(), self.span);
|
let (span, e) = interpolated_or_expr_span!(self,
|
||||||
let subexpression = try!(self.parse_prefix_expr(None));
|
try!(self.parse_prefix_expr(None)));
|
||||||
hi = if interpolated { prev_span.hi } else { subexpression.span.hi };
|
hi = span.hi;
|
||||||
ExprBox(subexpression)
|
ExprBox(e)
|
||||||
}
|
}
|
||||||
_ => return self.parse_dot_or_call_expr(Some(attrs))
|
_ => return self.parse_dot_or_call_expr(Some(attrs))
|
||||||
};
|
};
|
||||||
|
@ -2825,7 +2833,7 @@ impl<'a> Parser<'a> {
|
||||||
}
|
}
|
||||||
// Special cases:
|
// Special cases:
|
||||||
if op == AssocOp::As {
|
if op == AssocOp::As {
|
||||||
let rhs = try!(self.parse_ty());
|
let rhs = try!(self.parse_ty());
|
||||||
lhs = self.mk_expr(lhs_span.lo, rhs.span.hi,
|
lhs = self.mk_expr(lhs_span.lo, rhs.span.hi,
|
||||||
ExprCast(lhs, rhs), None);
|
ExprCast(lhs, rhs), None);
|
||||||
continue
|
continue
|
||||||
|
|
|
@ -11,7 +11,7 @@
|
||||||
macro_rules! log {
|
macro_rules! log {
|
||||||
( $ctx:expr, $( $args:expr),* ) => {
|
( $ctx:expr, $( $args:expr),* ) => {
|
||||||
if $ctx.trace {
|
if $ctx.trace {
|
||||||
//~^ attempted access of field `trace` on type `&T`, but no field with that name was found
|
//~^ ERROR attempted access of field `trace` on type `&T`, but no field with that name
|
||||||
println!( $( $args, )* );
|
println!( $( $args, )* );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue