rustc_parse: More precise spans for tuple.0.0
This commit is contained in:
parent
b1af43bc63
commit
dee704930d
@ -16,6 +16,7 @@ use rustc_ast_pretty::pprust;
|
||||
use rustc_errors::{Applicability, DiagnosticBuilder, PResult};
|
||||
use rustc_span::source_map::{self, Span, Spanned};
|
||||
use rustc_span::symbol::{kw, sym, Ident, Symbol};
|
||||
use rustc_span::{BytePos, Pos};
|
||||
use std::mem;
|
||||
use tracing::debug;
|
||||
|
||||
@ -839,9 +840,10 @@ impl<'a> Parser<'a> {
|
||||
}
|
||||
use FloatComponent::*;
|
||||
|
||||
let float_str = float.as_str();
|
||||
let mut components = Vec::new();
|
||||
let mut ident_like = String::new();
|
||||
for c in float.as_str().chars() {
|
||||
for c in float_str.chars() {
|
||||
if c == '_' || c.is_ascii_alphanumeric() {
|
||||
ident_like.push(c);
|
||||
} else if matches!(c, '.' | '+' | '-') {
|
||||
@ -857,8 +859,13 @@ impl<'a> Parser<'a> {
|
||||
components.push(IdentLike(ident_like));
|
||||
}
|
||||
|
||||
// FIXME: Make the span more precise.
|
||||
// With proc macros the span can refer to anything, the source may be too short,
|
||||
// or too long, or non-ASCII. It only makes sense to break our span into components
|
||||
// if its underlying text is identical to our float literal.
|
||||
let span = self.token.span;
|
||||
let can_take_span_apart =
|
||||
|| self.span_to_snippet(span).as_deref() == Ok(float_str).as_deref();
|
||||
|
||||
match &*components {
|
||||
// 1e2
|
||||
[IdentLike(i)] => {
|
||||
@ -866,21 +873,40 @@ impl<'a> Parser<'a> {
|
||||
}
|
||||
// 1.
|
||||
[IdentLike(i), Punct('.')] => {
|
||||
let (ident_span, dot_span) = if can_take_span_apart() {
|
||||
let (span, ident_len) = (span.data(), BytePos::from_usize(i.len()));
|
||||
let ident_span = span.with_hi(span.lo + ident_len);
|
||||
let dot_span = span.with_lo(span.lo + ident_len);
|
||||
(ident_span, dot_span)
|
||||
} else {
|
||||
(span, span)
|
||||
};
|
||||
assert!(suffix.is_none());
|
||||
let symbol = Symbol::intern(&i);
|
||||
self.token = Token::new(token::Ident(symbol, false), span);
|
||||
let next_token = Token::new(token::Dot, span);
|
||||
self.token = Token::new(token::Ident(symbol, false), ident_span);
|
||||
let next_token = Token::new(token::Dot, dot_span);
|
||||
self.parse_tuple_field_access_expr(lo, base, symbol, None, Some(next_token))
|
||||
}
|
||||
// 1.2 | 1.2e3
|
||||
[IdentLike(i1), Punct('.'), IdentLike(i2)] => {
|
||||
let (ident1_span, dot_span, ident2_span) = if can_take_span_apart() {
|
||||
let (span, ident1_len) = (span.data(), BytePos::from_usize(i1.len()));
|
||||
let ident1_span = span.with_hi(span.lo + ident1_len);
|
||||
let dot_span = span
|
||||
.with_lo(span.lo + ident1_len)
|
||||
.with_hi(span.lo + ident1_len + BytePos(1));
|
||||
let ident2_span = self.token.span.with_lo(span.lo + ident1_len + BytePos(1));
|
||||
(ident1_span, dot_span, ident2_span)
|
||||
} else {
|
||||
(span, span, span)
|
||||
};
|
||||
let symbol1 = Symbol::intern(&i1);
|
||||
self.token = Token::new(token::Ident(symbol1, false), span);
|
||||
let next_token1 = Token::new(token::Dot, span);
|
||||
self.token = Token::new(token::Ident(symbol1, false), ident1_span);
|
||||
let next_token1 = Token::new(token::Dot, dot_span);
|
||||
let base1 =
|
||||
self.parse_tuple_field_access_expr(lo, base, symbol1, None, Some(next_token1));
|
||||
let symbol2 = Symbol::intern(&i2);
|
||||
let next_token2 = Token::new(token::Ident(symbol2, false), span);
|
||||
let next_token2 = Token::new(token::Ident(symbol2, false), ident2_span);
|
||||
self.bump_with(next_token2); // `.`
|
||||
self.parse_tuple_field_access_expr(lo, base1, symbol2, suffix, None)
|
||||
}
|
||||
|
@ -271,10 +271,10 @@ LL | s.1e1;
|
||||
= note: available fields are: `0`, `1`
|
||||
|
||||
error[E0609]: no field `1e1` on type `(u8, u8)`
|
||||
--> $DIR/float-field.rs:9:7
|
||||
--> $DIR/float-field.rs:9:9
|
||||
|
|
||||
LL | s.1.1e1;
|
||||
| ^^^^^
|
||||
| ^^^
|
||||
|
||||
error[E0609]: no field `0x1e1` on type `S`
|
||||
--> $DIR/float-field.rs:24:7
|
||||
@ -288,7 +288,7 @@ error[E0609]: no field `0x1` on type `S`
|
||||
--> $DIR/float-field.rs:25:7
|
||||
|
|
||||
LL | s.0x1.;
|
||||
| ^^^^ unknown field
|
||||
| ^^^ unknown field
|
||||
|
|
||||
= note: available fields are: `0`, `1`
|
||||
|
||||
@ -296,7 +296,7 @@ error[E0609]: no field `0x1` on type `S`
|
||||
--> $DIR/float-field.rs:28:7
|
||||
|
|
||||
LL | s.0x1.1;
|
||||
| ^^^^^ unknown field
|
||||
| ^^^ unknown field
|
||||
|
|
||||
= note: available fields are: `0`, `1`
|
||||
|
||||
@ -304,7 +304,7 @@ error[E0609]: no field `0x1` on type `S`
|
||||
--> $DIR/float-field.rs:30:7
|
||||
|
|
||||
LL | s.0x1.1e1;
|
||||
| ^^^^^^^ unknown field
|
||||
| ^^^ unknown field
|
||||
|
|
||||
= note: available fields are: `0`, `1`
|
||||
|
||||
|
@ -2,19 +2,19 @@ error[E0609]: no field `1` on type `(((),),)`
|
||||
--> $DIR/index-invalid.rs:2:22
|
||||
|
|
||||
LL | let _ = (((),),).1.0;
|
||||
| ^^^
|
||||
| ^
|
||||
|
||||
error[E0609]: no field `1` on type `((),)`
|
||||
--> $DIR/index-invalid.rs:4:22
|
||||
--> $DIR/index-invalid.rs:4:24
|
||||
|
|
||||
LL | let _ = (((),),).0.1;
|
||||
| ^^^
|
||||
| ^
|
||||
|
||||
error[E0609]: no field `000` on type `(((),),)`
|
||||
--> $DIR/index-invalid.rs:6:22
|
||||
|
|
||||
LL | let _ = (((),),).000.000;
|
||||
| ^^^^^^^
|
||||
| ^^^
|
||||
|
||||
error: aborting due to 3 previous errors
|
||||
|
||||
|
@ -29,7 +29,7 @@ error: not automatically applying `DerefMut` on `ManuallyDrop` union field
|
||||
--> $DIR/union-deref.rs:23:14
|
||||
|
|
||||
LL | unsafe { u.f.0.0 = Vec::new() };
|
||||
| ^^^^^^^
|
||||
| ^^^^^
|
||||
|
|
||||
= help: writing to this reference calls the destructor for the old value
|
||||
= help: add an explicit `*` if that is desired, or call `ptr::write` to not run the destructor
|
||||
@ -38,7 +38,7 @@ error: not automatically applying `DerefMut` on `ManuallyDrop` union field
|
||||
--> $DIR/union-deref.rs:25:19
|
||||
|
|
||||
LL | unsafe { &mut u.f.0.0 };
|
||||
| ^^^^^^^
|
||||
| ^^^^^
|
||||
|
|
||||
= help: writing to this reference calls the destructor for the old value
|
||||
= help: add an explicit `*` if that is desired, or call `ptr::write` to not run the destructor
|
||||
@ -47,7 +47,7 @@ error: not automatically applying `DerefMut` on `ManuallyDrop` union field
|
||||
--> $DIR/union-deref.rs:27:14
|
||||
|
|
||||
LL | unsafe { u.f.0.0.push(0) };
|
||||
| ^^^^^^^
|
||||
| ^^^^^
|
||||
|
|
||||
= help: writing to this reference calls the destructor for the old value
|
||||
= help: add an explicit `*` if that is desired, or call `ptr::write` to not run the destructor
|
||||
|
Loading…
Reference in New Issue
Block a user