Skip to content

Commit e9e8514

Browse files
committed
add Span information into Qself
1 parent d034ae5 commit e9e8514

File tree

5 files changed

+57
-10
lines changed

5 files changed

+57
-10
lines changed

src/librustc_resolve/lib.rs

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3139,6 +3139,17 @@ impl<'a> Resolver<'a> {
31393139
span: Span,
31403140
global_by_default: bool)
31413141
-> Option<PathResolution> {
3142+
debug!(
3143+
"resolve_qpath(id={:?}, qself={:?}, path={:?}, \
3144+
ns={:?}, span={:?}, global_by_default={:?})",
3145+
id,
3146+
qself,
3147+
path,
3148+
ns,
3149+
span,
3150+
global_by_default,
3151+
);
3152+
31423153
if let Some(qself) = qself {
31433154
if qself.position == 0 {
31443155
// FIXME: Create some fake resolution that can't possibly be a type.
@@ -3231,6 +3242,15 @@ impl<'a> Resolver<'a> {
32313242
let mut allow_super = true;
32323243
let mut second_binding = None;
32333244

3245+
debug!(
3246+
"resolve_path(path={:?}, opt_ns={:?}, record_used={:?}, path_span={:?}, crate_lint={:?})",
3247+
path,
3248+
opt_ns,
3249+
record_used,
3250+
path_span,
3251+
crate_lint,
3252+
);
3253+
32343254
for (i, &ident) in path.iter().enumerate() {
32353255
debug!("resolve_path ident {} {:?}", i, ident);
32363256
let is_last = i == path.len() - 1;
@@ -4454,6 +4474,7 @@ pub enum MakeGlobMap {
44544474
No,
44554475
}
44564476

4477+
#[derive(Debug)]
44574478
enum CrateLint {
44584479
/// Do not issue the lint
44594480
No,

src/libsyntax/ast.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1211,6 +1211,11 @@ pub enum ExprKind {
12111211
#[derive(Clone, PartialEq, Eq, RustcEncodable, RustcDecodable, Hash, Debug)]
12121212
pub struct QSelf {
12131213
pub ty: P<Ty>,
1214+
1215+
/// The span of `a::b::Trait` in a path like `<Vec<T> as
1216+
/// a::b::Trait>::AssociatedItem`; in the case where `position ==
1217+
/// 0`, this is an empty span.
1218+
pub path_span: Span,
12141219
pub position: usize
12151220
}
12161221

src/libsyntax/ext/build.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -373,6 +373,7 @@ impl<'a> AstBuilder for ExtCtxt<'a> {
373373

374374
(ast::QSelf {
375375
ty: self_type,
376+
path_span: path.span,
376377
position: path.segments.len() - 1
377378
}, path)
378379
}

src/libsyntax/fold.rs

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -390,9 +390,10 @@ pub fn noop_fold_ty<T: Folder>(t: P<Ty>, fld: &mut T) -> P<Ty> {
390390
TyKind::Tup(tys) => TyKind::Tup(tys.move_map(|ty| fld.fold_ty(ty))),
391391
TyKind::Paren(ty) => TyKind::Paren(fld.fold_ty(ty)),
392392
TyKind::Path(qself, path) => {
393-
let qself = qself.map(|QSelf { ty, position }| {
393+
let qself = qself.map(|QSelf { ty, path_span, position }| {
394394
QSelf {
395395
ty: fld.fold_ty(ty),
396+
path_span: fld.new_span(path_span),
396397
position,
397398
}
398399
});
@@ -1131,7 +1132,11 @@ pub fn noop_fold_pat<T: Folder>(p: P<Pat>, folder: &mut T) -> P<Pat> {
11311132
}
11321133
PatKind::Path(opt_qself, pth) => {
11331134
let opt_qself = opt_qself.map(|qself| {
1134-
QSelf { ty: folder.fold_ty(qself.ty), position: qself.position }
1135+
QSelf {
1136+
ty: folder.fold_ty(qself.ty),
1137+
path_span: folder.new_span(qself.path_span),
1138+
position: qself.position,
1139+
}
11351140
});
11361141
PatKind::Path(opt_qself, folder.fold_path(pth))
11371142
}
@@ -1292,9 +1297,10 @@ pub fn noop_fold_expr<T: Folder>(Expr {id, node, span, attrs}: Expr, folder: &mu
12921297
lim)
12931298
}
12941299
ExprKind::Path(qself, path) => {
1295-
let qself = qself.map(|QSelf { ty, position }| {
1300+
let qself = qself.map(|QSelf { ty, path_span, position }| {
12961301
QSelf {
12971302
ty: folder.fold_ty(ty),
1303+
path_span: folder.new_span(path_span),
12981304
position,
12991305
}
13001306
});

src/libsyntax/parse/parser.rs

Lines changed: 21 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1715,8 +1715,11 @@ impl<'a> Parser<'a> {
17151715
self.parse_path_segments(&mut segments, T::PATH_STYLE, true)?;
17161716

17171717
let span = ty.span.to(self.prev_span);
1718-
let recovered =
1719-
base.to_recovered(Some(QSelf { ty, position: 0 }), ast::Path { segments, span });
1718+
let path_span = span.to(span); // use an empty path since `position` == 0
1719+
let recovered = base.to_recovered(
1720+
Some(QSelf { ty, path_span, position: 0 }),
1721+
ast::Path { segments, span },
1722+
);
17201723

17211724
self.diagnostic()
17221725
.struct_span_err(span, "missing angle brackets in associated item path")
@@ -1905,21 +1908,32 @@ impl<'a> Parser<'a> {
19051908
/// `qualified_path = <type [as trait_ref]>::path`
19061909
///
19071910
/// # Examples
1911+
/// `<T>::default`
19081912
/// `<T as U>::a`
19091913
/// `<T as U>::F::a<S>` (without disambiguator)
19101914
/// `<T as U>::F::a::<S>` (with disambiguator)
19111915
fn parse_qpath(&mut self, style: PathStyle) -> PResult<'a, (QSelf, ast::Path)> {
19121916
let lo = self.prev_span;
19131917
let ty = self.parse_ty()?;
1914-
let mut path = if self.eat_keyword(keywords::As) {
1915-
self.parse_path(PathStyle::Type)?
1918+
1919+
// `path` will contain the prefix of the path up to the `>`,
1920+
// if any (e.g., `U` in the `<T as U>::*` examples
1921+
// above). `path_span` has the span of that path, or an empty
1922+
// span in the case of something like `<T>::Bar`.
1923+
let (mut path, path_span);
1924+
if self.eat_keyword(keywords::As) {
1925+
let path_lo = self.span;
1926+
path = self.parse_path(PathStyle::Type)?;
1927+
path_span = path_lo.to(self.prev_span);
19161928
} else {
1917-
ast::Path { segments: Vec::new(), span: syntax_pos::DUMMY_SP }
1918-
};
1929+
path = ast::Path { segments: Vec::new(), span: syntax_pos::DUMMY_SP };
1930+
path_span = self.span.to(self.span);
1931+
}
1932+
19191933
self.expect(&token::Gt)?;
19201934
self.expect(&token::ModSep)?;
19211935

1922-
let qself = QSelf { ty, position: path.segments.len() };
1936+
let qself = QSelf { ty, path_span, position: path.segments.len() };
19231937
self.parse_path_segments(&mut path.segments, style, true)?;
19241938

19251939
Ok((qself, ast::Path { segments: path.segments, span: lo.to(self.prev_span) }))

0 commit comments

Comments
 (0)