Merge pull request #6193 from ytmimi/subtree-push-nightly-2024-06-13
subtree-push nightly-2024-06-13
This commit is contained in:
commit
3ffd7d46a9
1
.github/workflows/integration.yml
vendored
1
.github/workflows/integration.yml
vendored
@ -19,7 +19,6 @@ jobs:
|
||||
matrix:
|
||||
integration: [
|
||||
bitflags,
|
||||
error-chain,
|
||||
log,
|
||||
mdbook,
|
||||
packed_simd,
|
||||
|
11
CHANGELOG.md
11
CHANGELOG.md
@ -3,6 +3,17 @@
|
||||
## [Unreleased]
|
||||
|
||||
- Updating `dirs 4.0.0 -> 5.0.1` and `cargo_metadata 0.15.4 -> 0.18.0` [#6033] (https://github.com/rust-lang/rustfmt/issues/6033)
|
||||
- Bumped bytecount `0.6.4` -> `0.6.8` to fix compilation issues with the `generic-simd` feature. See [bytecount#92] and [bytecount#93]
|
||||
|
||||
[bytecount#92]: https://github.com/llogiq/bytecount/pull/92
|
||||
[bytecount#93]: https://github.com/llogiq/bytecount/pull/93
|
||||
|
||||
- Output correct syntax for type ascription builtin [#6159](https://github.com/rust-lang/rustfmt/issues/6159)
|
||||
```rust
|
||||
fn main() {
|
||||
builtin # type_ascribe(10, usize)
|
||||
}
|
||||
```
|
||||
|
||||
## [1.7.0] 2023-10-22
|
||||
|
||||
|
33
Cargo.lock
generated
33
Cargo.lock
generated
@ -98,12 +98,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "bytecount"
|
||||
version = "0.6.4"
|
||||
version = "0.6.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ad152d03a2c813c80bb94fedbf3a3f02b28f793e39e7c214c8a0bcc196343de7"
|
||||
dependencies = [
|
||||
"packed_simd",
|
||||
]
|
||||
checksum = "5ce89b21cab1437276d2650d57e971f9d548a2d9037cc231abdc0562b97498ce"
|
||||
|
||||
[[package]]
|
||||
name = "camino"
|
||||
@ -369,12 +366,6 @@ version = "0.2.141"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3304a64d199bb964be99741b7a14d26972741915b3649639149b2479bb46f4b5"
|
||||
|
||||
[[package]]
|
||||
name = "libm"
|
||||
version = "0.2.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4ec2a862134d2a7d32d7983ddcdd1c4923530833c9f2ea1a44fc5fa473989058"
|
||||
|
||||
[[package]]
|
||||
name = "log"
|
||||
version = "0.4.16"
|
||||
@ -409,16 +400,6 @@ dependencies = [
|
||||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "num-traits"
|
||||
version = "0.2.17"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "39e3200413f237f41ab11ad6d161bc7239c84dcb631773ccd7de3dfe4b5c267c"
|
||||
dependencies = [
|
||||
"autocfg",
|
||||
"libm",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "once_cell"
|
||||
version = "1.17.1"
|
||||
@ -437,16 +418,6 @@ version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b15813163c1d831bf4a13c3610c05c0d03b39feb07f7e09fa234dac9b15aaf39"
|
||||
|
||||
[[package]]
|
||||
name = "packed_simd"
|
||||
version = "0.3.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1f9f08af0c877571712e2e3e686ad79efad9657dbf0f7c3c8ba943ff6c38932d"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"num-traits",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "pin-project-lite"
|
||||
version = "0.2.9"
|
||||
|
@ -35,7 +35,7 @@ generic-simd = ["bytecount/generic-simd"]
|
||||
[dependencies]
|
||||
annotate-snippets = { version = "0.9", features = ["color"] }
|
||||
anyhow = "1.0"
|
||||
bytecount = "0.6.4"
|
||||
bytecount = "0.6.8"
|
||||
cargo_metadata = "0.18"
|
||||
clap = { version = "4.4.2", features = ["derive"] }
|
||||
clap-cargo = "0.12.0"
|
||||
|
@ -104,7 +104,7 @@ case ${INTEGRATION} in
|
||||
check_fmt_with_all_tests
|
||||
cd -
|
||||
;;
|
||||
error-chain | tempdir)
|
||||
tempdir)
|
||||
git clone --depth=1 https://github.com/rust-lang-deprecated/${INTEGRATION}.git
|
||||
cd ${INTEGRATION}
|
||||
show_head
|
||||
|
@ -68,7 +68,11 @@ fn get_name_value_str_lit(attr: &syn::Attribute, name: &str) -> Option<String> {
|
||||
match &attr.meta {
|
||||
syn::Meta::NameValue(syn::MetaNameValue {
|
||||
path,
|
||||
value: syn::Expr::Lit(syn::ExprLit { lit: syn::Lit::Str(lit_str), .. }),
|
||||
value:
|
||||
syn::Expr::Lit(syn::ExprLit {
|
||||
lit: syn::Lit::Str(lit_str),
|
||||
..
|
||||
}),
|
||||
..
|
||||
}) if path.is_ident(name) => Some(lit_str.value()),
|
||||
_ => None,
|
||||
|
@ -1,3 +1,3 @@
|
||||
[toolchain]
|
||||
channel = "nightly-2023-12-28"
|
||||
channel = "nightly-2024-06-13"
|
||||
components = ["llvm-tools", "rustc-dev"]
|
||||
|
18
src/attr.rs
18
src/attr.rs
@ -26,7 +26,7 @@ pub(crate) fn get_attrs_from_stmt(stmt: &ast::Stmt) -> &[ast::Attribute] {
|
||||
|
||||
pub(crate) fn get_span_without_attrs(stmt: &ast::Stmt) -> Span {
|
||||
match stmt.kind {
|
||||
ast::StmtKind::Local(ref local) => local.span,
|
||||
ast::StmtKind::Let(ref local) => local.span,
|
||||
ast::StmtKind::Item(ref item) => item.span,
|
||||
ast::StmtKind::Expr(ref expr) | ast::StmtKind::Semi(ref expr) => expr.span,
|
||||
ast::StmtKind::MacCall(ref mac_stmt) => mac_stmt.mac.span(),
|
||||
@ -353,10 +353,18 @@ impl Rewrite for ast::Attribute {
|
||||
|
||||
// 1 = `[`
|
||||
let shape = shape.offset_left(prefix.len() + 1)?;
|
||||
Some(
|
||||
meta.rewrite(context, shape)
|
||||
.map_or_else(|| snippet.to_owned(), |rw| format!("{}[{}]", prefix, rw)),
|
||||
)
|
||||
Some(meta.rewrite(context, shape).map_or_else(
|
||||
|| snippet.to_owned(),
|
||||
|rw| match &self.kind {
|
||||
ast::AttrKind::Normal(normal_attr) => match normal_attr.item.unsafety {
|
||||
// For #![feature(unsafe_attributes)]
|
||||
// See https://github.com/rust-lang/rust/issues/123757
|
||||
ast::Safety::Unsafe(_) => format!("{}[unsafe({})]", prefix, rw),
|
||||
_ => format!("{}[{}]", prefix, rw),
|
||||
},
|
||||
_ => format!("{}[{}]", prefix, rw),
|
||||
},
|
||||
))
|
||||
} else {
|
||||
Some(snippet.to_owned())
|
||||
}
|
||||
|
@ -1714,10 +1714,10 @@ pub(crate) fn recover_comment_removed(
|
||||
// We missed some comments. Warn and keep the original text.
|
||||
if context.config.error_on_unformatted() {
|
||||
context.report.append(
|
||||
context.parse_sess.span_to_filename(span),
|
||||
context.psess.span_to_filename(span),
|
||||
vec![FormattingError::from_span(
|
||||
span,
|
||||
context.parse_sess,
|
||||
context.psess,
|
||||
ErrorKind::LostComment,
|
||||
)],
|
||||
);
|
||||
|
@ -1,6 +1,7 @@
|
||||
use crate::config::StyleEdition;
|
||||
|
||||
/// Defines the default value for the given style edition
|
||||
#[allow(dead_code)]
|
||||
pub(crate) trait StyleEditionDefault {
|
||||
type ConfigType;
|
||||
fn style_edition_default(style_edition: StyleEdition) -> Self::ConfigType;
|
||||
|
21
src/expr.rs
21
src/expr.rs
@ -3,7 +3,7 @@ use std::cmp::min;
|
||||
|
||||
use itertools::Itertools;
|
||||
use rustc_ast::token::{Delimiter, Lit, LitKind};
|
||||
use rustc_ast::{ast, ptr, token, ForLoopKind};
|
||||
use rustc_ast::{ast, ptr, token, ForLoopKind, MatchKind};
|
||||
use rustc_span::{BytePos, Span};
|
||||
|
||||
use crate::chains::rewrite_chain;
|
||||
@ -180,8 +180,8 @@ pub(crate) fn format_expr(
|
||||
}
|
||||
}
|
||||
}
|
||||
ast::ExprKind::Match(ref cond, ref arms) => {
|
||||
rewrite_match(context, cond, arms, shape, expr.span, &expr.attrs)
|
||||
ast::ExprKind::Match(ref cond, ref arms, kind) => {
|
||||
rewrite_match(context, cond, arms, shape, expr.span, &expr.attrs, kind)
|
||||
}
|
||||
ast::ExprKind::Path(ref qself, ref path) => {
|
||||
rewrite_path(context, PathContext::Expr, qself, path, shape)
|
||||
@ -263,14 +263,6 @@ pub(crate) fn format_expr(
|
||||
shape,
|
||||
SeparatorPlace::Front,
|
||||
),
|
||||
ast::ExprKind::Type(ref expr, ref ty) => rewrite_pair(
|
||||
&**expr,
|
||||
&**ty,
|
||||
PairParts::infix(": "),
|
||||
context,
|
||||
shape,
|
||||
SeparatorPlace::Back,
|
||||
),
|
||||
ast::ExprKind::Index(ref expr, ref index, _) => {
|
||||
rewrite_index(&**expr, &**index, context, shape)
|
||||
}
|
||||
@ -412,6 +404,7 @@ pub(crate) fn format_expr(
|
||||
}
|
||||
ast::ExprKind::Underscore => Some("_".to_owned()),
|
||||
ast::ExprKind::FormatArgs(..)
|
||||
| ast::ExprKind::Type(..)
|
||||
| ast::ExprKind::IncludedBytes(..)
|
||||
| ast::ExprKind::OffsetOf(..) => {
|
||||
// These don't normally occur in the AST because macros aren't expanded. However,
|
||||
@ -420,7 +413,7 @@ pub(crate) fn format_expr(
|
||||
// Also, rustfmt might get passed the output from `-Zunpretty=expanded`.
|
||||
None
|
||||
}
|
||||
ast::ExprKind::Err => None,
|
||||
ast::ExprKind::Err(_) | ast::ExprKind::Dummy => None,
|
||||
};
|
||||
|
||||
expr_rw
|
||||
@ -641,7 +634,7 @@ pub(crate) fn rewrite_cond(
|
||||
shape: Shape,
|
||||
) -> Option<String> {
|
||||
match expr.kind {
|
||||
ast::ExprKind::Match(ref cond, _) => {
|
||||
ast::ExprKind::Match(ref cond, _, MatchKind::Prefix) => {
|
||||
// `match `cond` {`
|
||||
let cond_shape = match context.config.indent_style() {
|
||||
IndentStyle::Visual => shape.shrink_left(6).and_then(|s| s.sub_width(2))?,
|
||||
@ -1963,7 +1956,7 @@ fn rewrite_unary_op(
|
||||
}
|
||||
|
||||
pub(crate) enum RhsAssignKind<'ast> {
|
||||
Expr(&'ast ast::ExprKind, Span),
|
||||
Expr(&'ast ast::ExprKind, #[allow(dead_code)] Span),
|
||||
Bounds,
|
||||
Ty,
|
||||
}
|
||||
|
@ -79,7 +79,7 @@ fn should_skip_module<T: FormatHandler>(
|
||||
// FIXME(calebcartwright) - we need to determine how we'll handle the
|
||||
// `format_generated_files` option with stdin based input.
|
||||
if !input_is_stdin && !config.format_generated_files() {
|
||||
let source_file = context.parse_session.span_to_file_contents(module.span);
|
||||
let source_file = context.psess.span_to_file_contents(module.span);
|
||||
let src = source_file.src.as_ref().expect("SourceFile without src");
|
||||
|
||||
if is_generated_file(src, config) {
|
||||
@ -109,15 +109,16 @@ fn format_project<T: FormatHandler>(
|
||||
let main_file = input.file_name();
|
||||
let input_is_stdin = main_file == FileName::Stdin;
|
||||
|
||||
let parse_session = ParseSess::new(config)?;
|
||||
if config.skip_children() && parse_session.ignore_file(&main_file) {
|
||||
let psess = ParseSess::new(config)?;
|
||||
if config.skip_children() && psess.ignore_file(&main_file) {
|
||||
return Ok(FormatReport::new());
|
||||
}
|
||||
|
||||
// Parse the crate.
|
||||
let mut report = FormatReport::new();
|
||||
let directory_ownership = input.to_directory_ownership();
|
||||
let krate = match Parser::parse_crate(input, &parse_session) {
|
||||
|
||||
let krate = match Parser::parse_crate(input, &psess) {
|
||||
Ok(krate) => krate,
|
||||
// Surface parse error via Session (errors are merged there from report)
|
||||
Err(e) => {
|
||||
@ -130,9 +131,9 @@ fn format_project<T: FormatHandler>(
|
||||
}
|
||||
};
|
||||
|
||||
let mut context = FormatContext::new(&krate, report, parse_session, config, handler);
|
||||
let mut context = FormatContext::new(&krate, report, psess, config, handler);
|
||||
let files = modules::ModResolver::new(
|
||||
&context.parse_session,
|
||||
&context.psess,
|
||||
directory_ownership.unwrap_or(DirectoryOwnership::UnownedViaBlock),
|
||||
!input_is_stdin && !config.skip_children(),
|
||||
)
|
||||
@ -147,16 +148,11 @@ fn format_project<T: FormatHandler>(
|
||||
timer = timer.done_parsing();
|
||||
|
||||
// Suppress error output if we have to do any further parsing.
|
||||
context.parse_session.set_silent_emitter();
|
||||
context.psess.set_silent_emitter();
|
||||
|
||||
for (path, module) in files {
|
||||
if input_is_stdin && contains_skip(module.attrs()) {
|
||||
return echo_back_stdin(
|
||||
context
|
||||
.parse_session
|
||||
.snippet_provider(module.span)
|
||||
.entire_snippet(),
|
||||
);
|
||||
return echo_back_stdin(context.psess.snippet_provider(module.span).entire_snippet());
|
||||
}
|
||||
should_emit_verbose(input_is_stdin, config, || println!("Formatting {}", path));
|
||||
context.format_file(path, &module, is_macro_def)?;
|
||||
@ -178,7 +174,7 @@ fn format_project<T: FormatHandler>(
|
||||
struct FormatContext<'a, T: FormatHandler> {
|
||||
krate: &'a ast::Crate,
|
||||
report: FormatReport,
|
||||
parse_session: ParseSess,
|
||||
psess: ParseSess,
|
||||
config: &'a Config,
|
||||
handler: &'a mut T,
|
||||
}
|
||||
@ -187,21 +183,21 @@ impl<'a, T: FormatHandler + 'a> FormatContext<'a, T> {
|
||||
fn new(
|
||||
krate: &'a ast::Crate,
|
||||
report: FormatReport,
|
||||
parse_session: ParseSess,
|
||||
psess: ParseSess,
|
||||
config: &'a Config,
|
||||
handler: &'a mut T,
|
||||
) -> Self {
|
||||
FormatContext {
|
||||
krate,
|
||||
report,
|
||||
parse_session,
|
||||
psess,
|
||||
config,
|
||||
handler,
|
||||
}
|
||||
}
|
||||
|
||||
fn ignore_file(&self, path: &FileName) -> bool {
|
||||
self.parse_session.ignore_file(path)
|
||||
self.psess.ignore_file(path)
|
||||
}
|
||||
|
||||
// Formats a single file/module.
|
||||
@ -211,9 +207,9 @@ impl<'a, T: FormatHandler + 'a> FormatContext<'a, T> {
|
||||
module: &Module<'_>,
|
||||
is_macro_def: bool,
|
||||
) -> Result<(), ErrorKind> {
|
||||
let snippet_provider = self.parse_session.snippet_provider(module.span);
|
||||
let mut visitor = FmtVisitor::from_parse_sess(
|
||||
&self.parse_session,
|
||||
let snippet_provider = self.psess.snippet_provider(module.span);
|
||||
let mut visitor = FmtVisitor::from_psess(
|
||||
&self.psess,
|
||||
self.config,
|
||||
&snippet_provider,
|
||||
self.report.clone(),
|
||||
@ -256,7 +252,7 @@ impl<'a, T: FormatHandler + 'a> FormatContext<'a, T> {
|
||||
.add_non_formatted_ranges(visitor.skipped_range.borrow().clone());
|
||||
|
||||
self.handler.handle_formatted_file(
|
||||
&self.parse_session,
|
||||
&self.psess,
|
||||
path,
|
||||
visitor.buffer.to_owned(),
|
||||
&mut self.report,
|
||||
@ -268,7 +264,7 @@ impl<'a, T: FormatHandler + 'a> FormatContext<'a, T> {
|
||||
trait FormatHandler {
|
||||
fn handle_formatted_file(
|
||||
&mut self,
|
||||
parse_session: &ParseSess,
|
||||
psess: &ParseSess,
|
||||
path: FileName,
|
||||
result: String,
|
||||
report: &mut FormatReport,
|
||||
@ -279,14 +275,14 @@ impl<'b, T: Write + 'b> FormatHandler for Session<'b, T> {
|
||||
// Called for each formatted file.
|
||||
fn handle_formatted_file(
|
||||
&mut self,
|
||||
parse_session: &ParseSess,
|
||||
psess: &ParseSess,
|
||||
path: FileName,
|
||||
result: String,
|
||||
report: &mut FormatReport,
|
||||
) -> Result<(), ErrorKind> {
|
||||
if let Some(ref mut out) = self.out {
|
||||
match source_file::write_file(
|
||||
Some(parse_session),
|
||||
Some(psess),
|
||||
&path,
|
||||
&result,
|
||||
out,
|
||||
@ -317,17 +313,13 @@ pub(crate) struct FormattingError {
|
||||
}
|
||||
|
||||
impl FormattingError {
|
||||
pub(crate) fn from_span(
|
||||
span: Span,
|
||||
parse_sess: &ParseSess,
|
||||
kind: ErrorKind,
|
||||
) -> FormattingError {
|
||||
pub(crate) fn from_span(span: Span, psess: &ParseSess, kind: ErrorKind) -> FormattingError {
|
||||
FormattingError {
|
||||
line: parse_sess.line_of_byte_pos(span.lo()),
|
||||
line: psess.line_of_byte_pos(span.lo()),
|
||||
is_comment: kind.is_comment(),
|
||||
kind,
|
||||
is_string: false,
|
||||
line_buffer: parse_sess.span_to_first_line_string(span),
|
||||
line_buffer: psess.span_to_first_line_string(span),
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -458,7 +458,9 @@ impl UseTree {
|
||||
version,
|
||||
});
|
||||
}
|
||||
UseTreeKind::Nested(ref list) => {
|
||||
UseTreeKind::Nested {
|
||||
items: ref list, ..
|
||||
} => {
|
||||
// Extract comments between nested use items.
|
||||
// This needs to be done before sorting use items.
|
||||
let items = itemize_list(
|
||||
|
64
src/items.rs
64
src/items.rs
@ -247,7 +247,7 @@ fn allow_single_line_let_else_block(result: &str, block: &ast::Block) -> bool {
|
||||
#[allow(dead_code)]
|
||||
#[derive(Debug)]
|
||||
struct Item<'a> {
|
||||
unsafety: ast::Unsafe,
|
||||
safety: ast::Safety,
|
||||
abi: Cow<'static, str>,
|
||||
vis: Option<&'a ast::Visibility>,
|
||||
body: Vec<BodyElement<'a>>,
|
||||
@ -257,7 +257,7 @@ struct Item<'a> {
|
||||
impl<'a> Item<'a> {
|
||||
fn from_foreign_mod(fm: &'a ast::ForeignMod, span: Span, config: &Config) -> Item<'a> {
|
||||
Item {
|
||||
unsafety: fm.unsafety,
|
||||
safety: fm.safety,
|
||||
abi: format_extern(
|
||||
ast::Extern::from_abi(fm.abi, DUMMY_SP),
|
||||
config.force_explicit_abi(),
|
||||
@ -290,7 +290,7 @@ pub(crate) struct FnSig<'a> {
|
||||
coroutine_kind: Cow<'a, Option<ast::CoroutineKind>>,
|
||||
constness: ast::Const,
|
||||
defaultness: ast::Defaultness,
|
||||
unsafety: ast::Unsafe,
|
||||
safety: ast::Safety,
|
||||
visibility: &'a ast::Visibility,
|
||||
}
|
||||
|
||||
@ -301,7 +301,7 @@ impl<'a> FnSig<'a> {
|
||||
visibility: &'a ast::Visibility,
|
||||
) -> FnSig<'a> {
|
||||
FnSig {
|
||||
unsafety: method_sig.header.unsafety,
|
||||
safety: method_sig.header.safety,
|
||||
coroutine_kind: Cow::Borrowed(&method_sig.header.coroutine_kind),
|
||||
constness: method_sig.header.constness,
|
||||
defaultness: ast::Defaultness::Final,
|
||||
@ -330,7 +330,7 @@ impl<'a> FnSig<'a> {
|
||||
constness: fn_sig.header.constness,
|
||||
coroutine_kind: Cow::Borrowed(&fn_sig.header.coroutine_kind),
|
||||
defaultness,
|
||||
unsafety: fn_sig.header.unsafety,
|
||||
safety: fn_sig.header.safety,
|
||||
visibility: vis,
|
||||
},
|
||||
_ => unreachable!(),
|
||||
@ -345,7 +345,7 @@ impl<'a> FnSig<'a> {
|
||||
result.push_str(format_constness(self.constness));
|
||||
self.coroutine_kind
|
||||
.map(|coroutine_kind| result.push_str(format_coro(&coroutine_kind)));
|
||||
result.push_str(format_unsafety(self.unsafety));
|
||||
result.push_str(format_safety(self.safety));
|
||||
result.push_str(&format_extern(
|
||||
self.ext,
|
||||
context.config.force_explicit_abi(),
|
||||
@ -356,7 +356,7 @@ impl<'a> FnSig<'a> {
|
||||
|
||||
impl<'a> FmtVisitor<'a> {
|
||||
fn format_item(&mut self, item: &Item<'_>) {
|
||||
self.buffer.push_str(format_unsafety(item.unsafety));
|
||||
self.buffer.push_str(format_safety(item.safety));
|
||||
self.buffer.push_str(&item.abi);
|
||||
|
||||
let snippet = self.snippet(item.span);
|
||||
@ -735,7 +735,9 @@ impl<'a> FmtVisitor<'a> {
|
||||
(Const(..), Const(..)) | (MacCall(..), MacCall(..)) => {
|
||||
a.ident.as_str().cmp(b.ident.as_str())
|
||||
}
|
||||
(Fn(..), Fn(..)) => a.span.lo().cmp(&b.span.lo()),
|
||||
(Fn(..), Fn(..)) | (Delegation(..), Delegation(..)) => {
|
||||
a.span.lo().cmp(&b.span.lo())
|
||||
}
|
||||
(Type(ty), _) if is_type(&ty.ty) => Ordering::Less,
|
||||
(_, Type(ty)) if is_type(&ty.ty) => Ordering::Greater,
|
||||
(Type(..), _) => Ordering::Less,
|
||||
@ -744,6 +746,8 @@ impl<'a> FmtVisitor<'a> {
|
||||
(_, Const(..)) => Ordering::Greater,
|
||||
(MacCall(..), _) => Ordering::Less,
|
||||
(_, MacCall(..)) => Ordering::Greater,
|
||||
(Delegation(..), _) | (DelegationMac(..), _) => Ordering::Less,
|
||||
(_, Delegation(..)) | (_, DelegationMac(..)) => Ordering::Greater,
|
||||
});
|
||||
let mut prev_kind = None;
|
||||
for (buf, item) in buffer {
|
||||
@ -929,7 +933,7 @@ fn format_impl_ref_and_type(
|
||||
offset: Indent,
|
||||
) -> Option<String> {
|
||||
let ast::Impl {
|
||||
unsafety,
|
||||
safety,
|
||||
polarity,
|
||||
defaultness,
|
||||
constness,
|
||||
@ -942,7 +946,7 @@ fn format_impl_ref_and_type(
|
||||
|
||||
result.push_str(&format_visibility(context, &item.vis));
|
||||
result.push_str(format_defaultness(defaultness));
|
||||
result.push_str(format_unsafety(unsafety));
|
||||
result.push_str(format_safety(safety));
|
||||
|
||||
let shape = if context.config.version() == Version::Two {
|
||||
Shape::indented(offset + last_line_width(&result), context.config)
|
||||
@ -1142,7 +1146,7 @@ pub(crate) fn format_trait(
|
||||
};
|
||||
let ast::Trait {
|
||||
is_auto,
|
||||
unsafety,
|
||||
safety,
|
||||
ref generics,
|
||||
ref bounds,
|
||||
ref items,
|
||||
@ -1152,7 +1156,7 @@ pub(crate) fn format_trait(
|
||||
let header = format!(
|
||||
"{}{}{}trait ",
|
||||
format_visibility(context, &item.vis),
|
||||
format_unsafety(unsafety),
|
||||
format_safety(safety),
|
||||
format_auto(is_auto),
|
||||
);
|
||||
result.push_str(&header);
|
||||
@ -1656,8 +1660,7 @@ struct TyAliasRewriteInfo<'c, 'g>(
|
||||
&'c RewriteContext<'c>,
|
||||
Indent,
|
||||
&'g ast::Generics,
|
||||
(ast::TyAliasWhereClause, ast::TyAliasWhereClause),
|
||||
usize,
|
||||
ast::TyAliasWhereClauses,
|
||||
symbol::Ident,
|
||||
Span,
|
||||
);
|
||||
@ -1677,7 +1680,6 @@ pub(crate) fn rewrite_type_alias<'a, 'b>(
|
||||
ref bounds,
|
||||
ref ty,
|
||||
where_clauses,
|
||||
where_predicates_split,
|
||||
} = *ty_alias_kind;
|
||||
let ty_opt = ty.as_ref();
|
||||
let (ident, vis) = match visitor_kind {
|
||||
@ -1685,15 +1687,7 @@ pub(crate) fn rewrite_type_alias<'a, 'b>(
|
||||
AssocTraitItem(i) | AssocImplItem(i) => (i.ident, &i.vis),
|
||||
ForeignItem(i) => (i.ident, &i.vis),
|
||||
};
|
||||
let rw_info = &TyAliasRewriteInfo(
|
||||
context,
|
||||
indent,
|
||||
generics,
|
||||
where_clauses,
|
||||
where_predicates_split,
|
||||
ident,
|
||||
span,
|
||||
);
|
||||
let rw_info = &TyAliasRewriteInfo(context, indent, generics, where_clauses, ident, span);
|
||||
let op_ty = opaque_ty(ty);
|
||||
// Type Aliases are formatted slightly differently depending on the context
|
||||
// in which they appear, whether they are opaque, and whether they are associated.
|
||||
@ -1729,19 +1723,11 @@ fn rewrite_ty<R: Rewrite>(
|
||||
vis: &ast::Visibility,
|
||||
) -> Option<String> {
|
||||
let mut result = String::with_capacity(128);
|
||||
let TyAliasRewriteInfo(
|
||||
context,
|
||||
indent,
|
||||
generics,
|
||||
where_clauses,
|
||||
where_predicates_split,
|
||||
ident,
|
||||
span,
|
||||
) = *rw_info;
|
||||
let TyAliasRewriteInfo(context, indent, generics, where_clauses, ident, span) = *rw_info;
|
||||
let (before_where_predicates, after_where_predicates) = generics
|
||||
.where_clause
|
||||
.predicates
|
||||
.split_at(where_predicates_split);
|
||||
.split_at(where_clauses.split);
|
||||
if !after_where_predicates.is_empty() {
|
||||
return None;
|
||||
}
|
||||
@ -1776,7 +1762,7 @@ fn rewrite_ty<R: Rewrite>(
|
||||
let where_clause_str = rewrite_where_clause(
|
||||
context,
|
||||
before_where_predicates,
|
||||
where_clauses.0.1,
|
||||
where_clauses.before.span,
|
||||
context.config.brace_style(),
|
||||
Shape::legacy(where_budget, indent),
|
||||
false,
|
||||
@ -1800,7 +1786,7 @@ fn rewrite_ty<R: Rewrite>(
|
||||
let comment_span = context
|
||||
.snippet_provider
|
||||
.opt_span_before(span, "=")
|
||||
.map(|op_lo| mk_sp(where_clauses.0.1.hi(), op_lo));
|
||||
.map(|op_lo| mk_sp(where_clauses.before.span.hi(), op_lo));
|
||||
|
||||
let lhs = match comment_span {
|
||||
Some(comment_span)
|
||||
@ -3348,11 +3334,11 @@ impl Rewrite for ast::ForeignItem {
|
||||
.map(|(s, _, _)| format!("{};", s))
|
||||
}
|
||||
}
|
||||
ast::ForeignItemKind::Static(ref ty, mutability, _) => {
|
||||
ast::ForeignItemKind::Static(ref static_foreign_item) => {
|
||||
// FIXME(#21): we're dropping potential comments in between the
|
||||
// function kw here.
|
||||
let vis = format_visibility(context, &self.vis);
|
||||
let mut_str = format_mutability(mutability);
|
||||
let mut_str = format_mutability(static_foreign_item.mutability);
|
||||
let prefix = format!(
|
||||
"{}static {}{}:",
|
||||
vis,
|
||||
@ -3363,7 +3349,7 @@ impl Rewrite for ast::ForeignItem {
|
||||
rewrite_assign_rhs(
|
||||
context,
|
||||
prefix,
|
||||
&**ty,
|
||||
&static_foreign_item.ty,
|
||||
&RhsAssignKind::Ty,
|
||||
shape.sub_width(1)?,
|
||||
)
|
||||
|
@ -137,8 +137,8 @@ fn return_macro_parse_failure_fallback(
|
||||
}
|
||||
|
||||
context.skipped_range.borrow_mut().push((
|
||||
context.parse_sess.line_of_byte_pos(span.lo()),
|
||||
context.parse_sess.line_of_byte_pos(span.hi()),
|
||||
context.psess.line_of_byte_pos(span.lo()),
|
||||
context.psess.line_of_byte_pos(span.hi()),
|
||||
));
|
||||
|
||||
// Return the snippet unmodified if the macro is not block-like
|
||||
@ -1092,7 +1092,7 @@ fn next_space(tok: &TokenKind) -> SpaceState {
|
||||
| TokenKind::DotDotEq
|
||||
| TokenKind::Question => SpaceState::Punctuation,
|
||||
|
||||
TokenKind::ModSep
|
||||
TokenKind::PathSep
|
||||
| TokenKind::Pound
|
||||
| TokenKind::Dollar
|
||||
| TokenKind::OpenDelim(_)
|
||||
|
@ -2,7 +2,7 @@
|
||||
|
||||
use std::iter::repeat;
|
||||
|
||||
use rustc_ast::{ast, ptr};
|
||||
use rustc_ast::{ast, ptr, MatchKind};
|
||||
use rustc_span::{BytePos, Span};
|
||||
|
||||
use crate::comment::{combine_strs_with_missing_comments, rewrite_comment, FindUncommented};
|
||||
@ -72,6 +72,7 @@ pub(crate) fn rewrite_match(
|
||||
shape: Shape,
|
||||
span: Span,
|
||||
attrs: &[ast::Attribute],
|
||||
match_kind: MatchKind,
|
||||
) -> Option<String> {
|
||||
// Do not take the rhs overhead from the upper expressions into account
|
||||
// when rewriting match condition.
|
||||
@ -135,15 +136,27 @@ pub(crate) fn rewrite_match(
|
||||
}
|
||||
} else {
|
||||
let span_after_cond = mk_sp(cond.span.hi(), span.hi());
|
||||
Some(format!(
|
||||
"match {}{}{{\n{}{}{}\n{}}}",
|
||||
cond_str,
|
||||
block_sep,
|
||||
inner_attrs_str,
|
||||
nested_indent_str,
|
||||
rewrite_match_arms(context, arms, shape, span_after_cond, open_brace_pos)?,
|
||||
shape.indent.to_string(context.config),
|
||||
))
|
||||
|
||||
match match_kind {
|
||||
MatchKind::Prefix => Some(format!(
|
||||
"match {}{}{{\n{}{}{}\n{}}}",
|
||||
cond_str,
|
||||
block_sep,
|
||||
inner_attrs_str,
|
||||
nested_indent_str,
|
||||
rewrite_match_arms(context, arms, shape, span_after_cond, open_brace_pos)?,
|
||||
shape.indent.to_string(context.config),
|
||||
)),
|
||||
MatchKind::Postfix => Some(format!(
|
||||
"{}.match{}{{\n{}{}{}\n{}}}",
|
||||
cond_str,
|
||||
block_sep,
|
||||
inner_attrs_str,
|
||||
nested_indent_str,
|
||||
rewrite_match_arms(context, arms, shape, span_after_cond, open_brace_pos)?,
|
||||
shape.indent.to_string(context.config),
|
||||
)),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -91,7 +91,7 @@ impl<'a> FmtVisitor<'a> {
|
||||
assert!(
|
||||
start < end,
|
||||
"Request to format inverted span: {}",
|
||||
self.parse_sess.span_to_debug_info(mk_sp(start, end)),
|
||||
self.psess.span_to_debug_info(mk_sp(start, end)),
|
||||
);
|
||||
|
||||
self.last_pos = end;
|
||||
@ -166,8 +166,8 @@ impl<'a> FmtVisitor<'a> {
|
||||
// Trim whitespace from the right hand side of each line.
|
||||
// Annoyingly, the library functions for splitting by lines etc. are not
|
||||
// quite right, so we must do it ourselves.
|
||||
let line = self.parse_sess.line_of_byte_pos(span.lo());
|
||||
let file_name = &self.parse_sess.span_to_filename(span);
|
||||
let line = self.psess.line_of_byte_pos(span.lo());
|
||||
let file_name = &self.psess.span_to_filename(span);
|
||||
let mut status = SnippetStatus::new(line);
|
||||
|
||||
let snippet = &*transform_missing_snippet(self.config, old_snippet);
|
||||
|
@ -57,8 +57,8 @@ impl<'a> Module<'a> {
|
||||
}
|
||||
|
||||
/// Maps each module to the corresponding file.
|
||||
pub(crate) struct ModResolver<'ast, 'sess> {
|
||||
parse_sess: &'sess ParseSess,
|
||||
pub(crate) struct ModResolver<'ast, 'psess> {
|
||||
psess: &'psess ParseSess,
|
||||
directory: Directory,
|
||||
file_map: FileModMap<'ast>,
|
||||
recursive: bool,
|
||||
@ -99,10 +99,10 @@ enum SubModKind<'a, 'ast> {
|
||||
Internal(&'a ast::Item),
|
||||
}
|
||||
|
||||
impl<'ast, 'sess, 'c> ModResolver<'ast, 'sess> {
|
||||
impl<'ast, 'psess, 'c> ModResolver<'ast, 'psess> {
|
||||
/// Creates a new `ModResolver`.
|
||||
pub(crate) fn new(
|
||||
parse_sess: &'sess ParseSess,
|
||||
psess: &'psess ParseSess,
|
||||
directory_ownership: DirectoryOwnership,
|
||||
recursive: bool,
|
||||
) -> Self {
|
||||
@ -112,7 +112,7 @@ impl<'ast, 'sess, 'c> ModResolver<'ast, 'sess> {
|
||||
ownership: directory_ownership,
|
||||
},
|
||||
file_map: BTreeMap::new(),
|
||||
parse_sess,
|
||||
psess,
|
||||
recursive,
|
||||
}
|
||||
}
|
||||
@ -122,7 +122,7 @@ impl<'ast, 'sess, 'c> ModResolver<'ast, 'sess> {
|
||||
mut self,
|
||||
krate: &'ast ast::Crate,
|
||||
) -> Result<FileModMap<'ast>, ModuleResolutionError> {
|
||||
let root_filename = self.parse_sess.span_to_filename(krate.spans.inner_span);
|
||||
let root_filename = self.psess.span_to_filename(krate.spans.inner_span);
|
||||
self.directory.path = match root_filename {
|
||||
FileName::Real(ref p) => p.parent().unwrap_or(Path::new("")).to_path_buf(),
|
||||
_ => PathBuf::new(),
|
||||
@ -133,7 +133,7 @@ impl<'ast, 'sess, 'c> ModResolver<'ast, 'sess> {
|
||||
self.visit_mod_from_ast(&krate.items)?;
|
||||
}
|
||||
|
||||
let snippet_provider = self.parse_sess.snippet_provider(krate.spans.inner_span);
|
||||
let snippet_provider = self.psess.snippet_provider(krate.spans.inner_span);
|
||||
|
||||
self.file_map.insert(
|
||||
root_filename,
|
||||
@ -149,7 +149,7 @@ impl<'ast, 'sess, 'c> ModResolver<'ast, 'sess> {
|
||||
|
||||
/// Visit `cfg_if` macro and look for module declarations.
|
||||
fn visit_cfg_if(&mut self, item: Cow<'ast, ast::Item>) -> Result<(), ModuleResolutionError> {
|
||||
let mut visitor = visitor::CfgIfVisitor::new(self.parse_sess);
|
||||
let mut visitor = visitor::CfgIfVisitor::new(self.psess);
|
||||
visitor.visit_item(&item);
|
||||
for module_item in visitor.mods() {
|
||||
if let ast::ItemKind::Mod(_, ref sub_mod_kind) = module_item.item.kind {
|
||||
@ -338,10 +338,10 @@ impl<'ast, 'sess, 'c> ModResolver<'ast, 'sess> {
|
||||
DirectoryOwnership::UnownedViaBlock => None,
|
||||
};
|
||||
if let Some(path) = Parser::submod_path_from_attr(attrs, &self.directory.path) {
|
||||
if self.parse_sess.is_file_parsed(&path) {
|
||||
if self.psess.is_file_parsed(&path) {
|
||||
return Ok(None);
|
||||
}
|
||||
return match Parser::parse_file_as_module(self.parse_sess, &path, sub_mod.span) {
|
||||
return match Parser::parse_file_as_module(self.psess, &path, sub_mod.span) {
|
||||
Ok((ref attrs, _, _)) if contains_skip(attrs) => Ok(None),
|
||||
Ok((attrs, items, span)) => Ok(Some(SubModKind::External(
|
||||
path,
|
||||
@ -368,7 +368,7 @@ impl<'ast, 'sess, 'c> ModResolver<'ast, 'sess> {
|
||||
let mut mods_outside_ast = self.find_mods_outside_of_ast(attrs, sub_mod);
|
||||
|
||||
match self
|
||||
.parse_sess
|
||||
.psess
|
||||
.default_submod_path(mod_name, relative, &self.directory.path)
|
||||
{
|
||||
Ok(ModulePathSuccess {
|
||||
@ -380,7 +380,7 @@ impl<'ast, 'sess, 'c> ModResolver<'ast, 'sess> {
|
||||
let should_insert = !mods_outside_ast
|
||||
.iter()
|
||||
.any(|(outside_path, _, _)| outside_path == &file_path);
|
||||
if self.parse_sess.is_file_parsed(&file_path) {
|
||||
if self.psess.is_file_parsed(&file_path) {
|
||||
if outside_mods_empty {
|
||||
return Ok(None);
|
||||
} else {
|
||||
@ -390,7 +390,7 @@ impl<'ast, 'sess, 'c> ModResolver<'ast, 'sess> {
|
||||
return Ok(Some(SubModKind::MultiExternal(mods_outside_ast)));
|
||||
}
|
||||
}
|
||||
match Parser::parse_file_as_module(self.parse_sess, &file_path, sub_mod.span) {
|
||||
match Parser::parse_file_as_module(self.psess, &file_path, sub_mod.span) {
|
||||
Ok((ref attrs, _, _)) if contains_skip(attrs) => Ok(None),
|
||||
Ok((attrs, items, span)) if outside_mods_empty => {
|
||||
Ok(Some(SubModKind::External(
|
||||
@ -517,7 +517,7 @@ impl<'ast, 'sess, 'c> ModResolver<'ast, 'sess> {
|
||||
if !actual_path.exists() {
|
||||
continue;
|
||||
}
|
||||
if self.parse_sess.is_file_parsed(&actual_path) {
|
||||
if self.psess.is_file_parsed(&actual_path) {
|
||||
// If the specified file is already parsed, then we just use that.
|
||||
result.push((
|
||||
actual_path,
|
||||
@ -527,7 +527,7 @@ impl<'ast, 'sess, 'c> ModResolver<'ast, 'sess> {
|
||||
continue;
|
||||
}
|
||||
let (attrs, items, span) =
|
||||
match Parser::parse_file_as_module(self.parse_sess, &actual_path, sub_mod.span) {
|
||||
match Parser::parse_file_as_module(self.psess, &actual_path, sub_mod.span) {
|
||||
Ok((ref attrs, _, _)) if contains_skip(attrs) => continue,
|
||||
Ok(m) => m,
|
||||
Err(..) => continue,
|
||||
|
@ -12,15 +12,15 @@ pub(crate) struct ModItem {
|
||||
|
||||
/// Traverse `cfg_if!` macro and fetch modules.
|
||||
pub(crate) struct CfgIfVisitor<'a> {
|
||||
parse_sess: &'a ParseSess,
|
||||
psess: &'a ParseSess,
|
||||
mods: Vec<ModItem>,
|
||||
}
|
||||
|
||||
impl<'a> CfgIfVisitor<'a> {
|
||||
pub(crate) fn new(parse_sess: &'a ParseSess) -> CfgIfVisitor<'a> {
|
||||
pub(crate) fn new(psess: &'a ParseSess) -> CfgIfVisitor<'a> {
|
||||
CfgIfVisitor {
|
||||
mods: vec![],
|
||||
parse_sess,
|
||||
psess,
|
||||
}
|
||||
}
|
||||
|
||||
@ -62,7 +62,7 @@ impl<'a, 'ast: 'a> CfgIfVisitor<'a> {
|
||||
}
|
||||
};
|
||||
|
||||
let items = parse_cfg_if(self.parse_sess, mac)?;
|
||||
let items = parse_cfg_if(self.psess, mac)?;
|
||||
self.mods
|
||||
.append(&mut items.into_iter().map(|item| ModItem { item }).collect());
|
||||
|
||||
|
@ -7,5 +7,5 @@ use crate::rewrite::RewriteContext;
|
||||
pub(crate) fn parse_asm(context: &RewriteContext<'_>, mac: &ast::MacCall) -> Option<AsmArgs> {
|
||||
let ts = mac.args.tokens.clone();
|
||||
let mut parser = super::build_parser(context, ts);
|
||||
parse_asm_args(&mut parser, context.parse_sess.inner(), mac.span(), false).ok()
|
||||
parse_asm_args(&mut parser, mac.span(), false).ok()
|
||||
}
|
||||
|
@ -9,10 +9,10 @@ use crate::parse::macros::build_stream_parser;
|
||||
use crate::parse::session::ParseSess;
|
||||
|
||||
pub(crate) fn parse_cfg_if<'a>(
|
||||
sess: &'a ParseSess,
|
||||
psess: &'a ParseSess,
|
||||
mac: &'a ast::MacCall,
|
||||
) -> Result<Vec<ast::Item>, &'static str> {
|
||||
match catch_unwind(AssertUnwindSafe(|| parse_cfg_if_inner(sess, mac))) {
|
||||
match catch_unwind(AssertUnwindSafe(|| parse_cfg_if_inner(psess, mac))) {
|
||||
Ok(Ok(items)) => Ok(items),
|
||||
Ok(err @ Err(_)) => err,
|
||||
Err(..) => Err("failed to parse cfg_if!"),
|
||||
@ -20,11 +20,11 @@ pub(crate) fn parse_cfg_if<'a>(
|
||||
}
|
||||
|
||||
fn parse_cfg_if_inner<'a>(
|
||||
sess: &'a ParseSess,
|
||||
psess: &'a ParseSess,
|
||||
mac: &'a ast::MacCall,
|
||||
) -> Result<Vec<ast::Item>, &'static str> {
|
||||
let ts = mac.args.tokens.clone();
|
||||
let mut parser = build_stream_parser(sess.inner(), ts);
|
||||
let mut parser = build_stream_parser(psess.inner(), ts);
|
||||
|
||||
let mut items = vec![];
|
||||
let mut process_if_cfg = true;
|
||||
@ -67,7 +67,7 @@ fn parse_cfg_if_inner<'a>(
|
||||
Ok(None) => continue,
|
||||
Err(err) => {
|
||||
err.cancel();
|
||||
parser.sess.dcx.reset_err_count();
|
||||
parser.psess.dcx.reset_err_count();
|
||||
return Err(
|
||||
"Expected item inside cfg_if block, but failed to parse it as an item",
|
||||
);
|
||||
|
@ -16,8 +16,8 @@ pub(crate) fn parse_lazy_static(
|
||||
($method:ident $(,)* $($arg:expr),* $(,)*) => {
|
||||
match parser.$method($($arg,)*) {
|
||||
Ok(val) => {
|
||||
if parser.sess.dcx.has_errors().is_some() {
|
||||
parser.sess.dcx.reset_err_count();
|
||||
if parser.psess.dcx.has_errors().is_some() {
|
||||
parser.psess.dcx.reset_err_count();
|
||||
return None;
|
||||
} else {
|
||||
val
|
||||
@ -25,7 +25,7 @@ pub(crate) fn parse_lazy_static(
|
||||
}
|
||||
Err(err) => {
|
||||
err.cancel();
|
||||
parser.sess.dcx.reset_err_count();
|
||||
parser.psess.dcx.reset_err_count();
|
||||
return None;
|
||||
}
|
||||
}
|
||||
|
@ -1,8 +1,8 @@
|
||||
use rustc_ast::token::{Delimiter, TokenKind};
|
||||
use rustc_ast::token::{Delimiter, NonterminalKind, TokenKind};
|
||||
use rustc_ast::tokenstream::TokenStream;
|
||||
use rustc_ast::{ast, ptr};
|
||||
use rustc_parse::parser::{ForceCollect, Parser};
|
||||
use rustc_parse::{stream_to_parser, MACRO_ARGUMENTS};
|
||||
use rustc_parse::parser::{ForceCollect, Parser, Recovery};
|
||||
use rustc_parse::MACRO_ARGUMENTS;
|
||||
use rustc_session::parse::ParseSess;
|
||||
use rustc_span::symbol::{self, kw};
|
||||
use rustc_span::Symbol;
|
||||
@ -14,31 +14,33 @@ pub(crate) mod asm;
|
||||
pub(crate) mod cfg_if;
|
||||
pub(crate) mod lazy_static;
|
||||
|
||||
fn build_stream_parser<'a>(sess: &'a ParseSess, tokens: TokenStream) -> Parser<'a> {
|
||||
stream_to_parser(sess, tokens, MACRO_ARGUMENTS)
|
||||
fn build_stream_parser<'a>(psess: &'a ParseSess, tokens: TokenStream) -> Parser<'a> {
|
||||
Parser::new(psess, tokens, MACRO_ARGUMENTS).recovery(Recovery::Forbidden)
|
||||
}
|
||||
|
||||
fn build_parser<'a>(context: &RewriteContext<'a>, tokens: TokenStream) -> Parser<'a> {
|
||||
build_stream_parser(context.parse_sess.inner(), tokens)
|
||||
build_stream_parser(context.psess.inner(), tokens)
|
||||
}
|
||||
|
||||
fn parse_macro_arg<'a, 'b: 'a>(parser: &'a mut Parser<'b>) -> Option<MacroArg> {
|
||||
macro_rules! parse_macro_arg {
|
||||
($macro_arg:ident, $parser:expr, $f:expr) => {
|
||||
($macro_arg:ident, $nt_kind:expr, $try_parse:expr, $then:expr) => {
|
||||
let mut cloned_parser = (*parser).clone();
|
||||
match $parser(&mut cloned_parser) {
|
||||
Ok(x) => {
|
||||
if parser.sess.dcx.has_errors().is_some() {
|
||||
parser.sess.dcx.reset_err_count();
|
||||
} else {
|
||||
// Parsing succeeded.
|
||||
*parser = cloned_parser;
|
||||
return Some(MacroArg::$macro_arg($f(x)?));
|
||||
if Parser::nonterminal_may_begin_with($nt_kind, &cloned_parser.token) {
|
||||
match $try_parse(&mut cloned_parser) {
|
||||
Ok(x) => {
|
||||
if parser.psess.dcx.has_errors().is_some() {
|
||||
parser.psess.dcx.reset_err_count();
|
||||
} else {
|
||||
// Parsing succeeded.
|
||||
*parser = cloned_parser;
|
||||
return Some(MacroArg::$macro_arg($then(x)?));
|
||||
}
|
||||
}
|
||||
Err(e) => {
|
||||
e.cancel();
|
||||
parser.psess.dcx.reset_err_count();
|
||||
}
|
||||
}
|
||||
Err(e) => {
|
||||
e.cancel();
|
||||
parser.sess.dcx.reset_err_count();
|
||||
}
|
||||
}
|
||||
};
|
||||
@ -46,23 +48,27 @@ fn parse_macro_arg<'a, 'b: 'a>(parser: &'a mut Parser<'b>) -> Option<MacroArg> {
|
||||
|
||||
parse_macro_arg!(
|
||||
Expr,
|
||||
|parser: &mut rustc_parse::parser::Parser<'b>| parser.parse_expr(),
|
||||
NonterminalKind::Expr,
|
||||
|parser: &mut Parser<'b>| parser.parse_expr(),
|
||||
|x: ptr::P<ast::Expr>| Some(x)
|
||||
);
|
||||
parse_macro_arg!(
|
||||
Ty,
|
||||
|parser: &mut rustc_parse::parser::Parser<'b>| parser.parse_ty(),
|
||||
NonterminalKind::Ty,
|
||||
|parser: &mut Parser<'b>| parser.parse_ty(),
|
||||
|x: ptr::P<ast::Ty>| Some(x)
|
||||
);
|
||||
parse_macro_arg!(
|
||||
Pat,
|
||||
|parser: &mut rustc_parse::parser::Parser<'b>| parser.parse_pat_no_top_alt(None, None),
|
||||
NonterminalKind::PatParam { inferred: false },
|
||||
|parser: &mut Parser<'b>| parser.parse_pat_no_top_alt(None, None),
|
||||
|x: ptr::P<ast::Pat>| Some(x)
|
||||
);
|
||||
// `parse_item` returns `Option<ptr::P<ast::Item>>`.
|
||||
parse_macro_arg!(
|
||||
Item,
|
||||
|parser: &mut rustc_parse::parser::Parser<'b>| parser.parse_item(ForceCollect::No),
|
||||
NonterminalKind::Item,
|
||||
|parser: &mut Parser<'b>| parser.parse_item(ForceCollect::No),
|
||||
|x: Option<ptr::P<ast::Item>>| x
|
||||
);
|
||||
|
||||
|
@ -3,8 +3,9 @@ use std::path::{Path, PathBuf};
|
||||
|
||||
use rustc_ast::token::TokenKind;
|
||||
use rustc_ast::{ast, attr, ptr};
|
||||
use rustc_errors::Diagnostic;
|
||||
use rustc_parse::{new_parser_from_file, parser::Parser as RawParser};
|
||||
use rustc_errors::Diag;
|
||||
use rustc_parse::parser::Parser as RawParser;
|
||||
use rustc_parse::{new_parser_from_file, new_parser_from_source_str, unwrap_or_emit_fatal};
|
||||
use rustc_span::{sym, Span};
|
||||
use thin_vec::ThinVec;
|
||||
|
||||
@ -29,7 +30,7 @@ pub(crate) struct Parser<'a> {
|
||||
/// A builder for the `Parser`.
|
||||
#[derive(Default)]
|
||||
pub(crate) struct ParserBuilder<'a> {
|
||||
sess: Option<&'a ParseSess>,
|
||||
psess: Option<&'a ParseSess>,
|
||||
input: Option<Input>,
|
||||
}
|
||||
|
||||
@ -39,23 +40,20 @@ impl<'a> ParserBuilder<'a> {
|
||||
self
|
||||
}
|
||||
|
||||
pub(crate) fn sess(mut self, sess: &'a ParseSess) -> ParserBuilder<'a> {
|
||||
self.sess = Some(sess);
|
||||
pub(crate) fn psess(mut self, psess: &'a ParseSess) -> ParserBuilder<'a> {
|
||||
self.psess = Some(psess);
|
||||
self
|
||||
}
|
||||
|
||||
pub(crate) fn build(self) -> Result<Parser<'a>, ParserError> {
|
||||
let sess = self.sess.ok_or(ParserError::NoParseSess)?;
|
||||
let psess = self.psess.ok_or(ParserError::NoParseSess)?;
|
||||
let input = self.input.ok_or(ParserError::NoInput)?;
|
||||
|
||||
let parser = match Self::parser(sess.inner(), input) {
|
||||
let parser = match Self::parser(psess.inner(), input) {
|
||||
Ok(p) => p,
|
||||
Err(db) => {
|
||||
if let Some(diagnostics) = db {
|
||||
sess.emit_diagnostics(diagnostics);
|
||||
return Err(ParserError::ParserCreationError);
|
||||
}
|
||||
return Err(ParserError::ParsePanicError);
|
||||
Err(diagnostics) => {
|
||||
psess.emit_diagnostics(diagnostics);
|
||||
return Err(ParserError::ParserCreationError);
|
||||
}
|
||||
};
|
||||
|
||||
@ -63,20 +61,16 @@ impl<'a> ParserBuilder<'a> {
|
||||
}
|
||||
|
||||
fn parser(
|
||||
sess: &'a rustc_session::parse::ParseSess,
|
||||
psess: &'a rustc_session::parse::ParseSess,
|
||||
input: Input,
|
||||
) -> Result<rustc_parse::parser::Parser<'a>, Option<Vec<Diagnostic>>> {
|
||||
) -> Result<RawParser<'a>, Vec<Diag<'a>>> {
|
||||
match input {
|
||||
Input::File(ref file) => catch_unwind(AssertUnwindSafe(move || {
|
||||
new_parser_from_file(sess, file, None)
|
||||
}))
|
||||
.map_err(|_| None),
|
||||
Input::Text(text) => rustc_parse::maybe_new_parser_from_source_str(
|
||||
sess,
|
||||
Input::File(ref file) => new_parser_from_file(psess, file, None),
|
||||
Input::Text(text) => new_parser_from_source_str(
|
||||
psess,
|
||||
rustc_span::FileName::Custom("stdin".to_owned()),
|
||||
text,
|
||||
)
|
||||
.map_err(Some),
|
||||
),
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -106,27 +100,28 @@ impl<'a> Parser<'a> {
|
||||
}
|
||||
|
||||
pub(crate) fn parse_file_as_module(
|
||||
sess: &'a ParseSess,
|
||||
psess: &'a ParseSess,
|
||||
path: &Path,
|
||||
span: Span,
|
||||
) -> Result<(ast::AttrVec, ThinVec<ptr::P<ast::Item>>, Span), ParserError> {
|
||||
let result = catch_unwind(AssertUnwindSafe(|| {
|
||||
let mut parser = new_parser_from_file(sess.inner(), path, Some(span));
|
||||
let mut parser =
|
||||
unwrap_or_emit_fatal(new_parser_from_file(psess.inner(), path, Some(span)));
|
||||
match parser.parse_mod(&TokenKind::Eof) {
|
||||
Ok((a, i, spans)) => Some((a, i, spans.inner_span)),
|
||||
Err(mut e) => {
|
||||
Err(e) => {
|
||||
e.emit();
|
||||
if sess.can_reset_errors() {
|
||||
sess.reset_errors();
|
||||
if psess.can_reset_errors() {
|
||||
psess.reset_errors();
|
||||
}
|
||||
None
|
||||
}
|
||||
}
|
||||
}));
|
||||
match result {
|
||||
Ok(Some(m)) if !sess.has_errors() => Ok(m),
|
||||
Ok(Some(m)) if sess.can_reset_errors() => {
|
||||
sess.reset_errors();
|
||||
Ok(Some(m)) if !psess.has_errors() => Ok(m),
|
||||
Ok(Some(m)) if psess.can_reset_errors() => {
|
||||
psess.reset_errors();
|
||||
Ok(m)
|
||||
}
|
||||
Ok(_) => Err(ParserError::ParseError),
|
||||
@ -137,39 +132,39 @@ impl<'a> Parser<'a> {
|
||||
|
||||
pub(crate) fn parse_crate(
|
||||
input: Input,
|
||||
sess: &'a ParseSess,
|
||||
psess: &'a ParseSess,
|
||||
) -> Result<ast::Crate, ParserError> {
|
||||
let krate = Parser::parse_crate_inner(input, sess)?;
|
||||
if !sess.has_errors() {
|
||||
let krate = Parser::parse_crate_inner(input, psess)?;
|
||||
if !psess.has_errors() {
|
||||
return Ok(krate);
|
||||
}
|
||||
|
||||
if sess.can_reset_errors() {
|
||||
sess.reset_errors();
|
||||
if psess.can_reset_errors() {
|
||||
psess.reset_errors();
|
||||
return Ok(krate);
|
||||
}
|
||||
|
||||
Err(ParserError::ParseError)
|
||||
}
|
||||
|
||||
fn parse_crate_inner(input: Input, sess: &'a ParseSess) -> Result<ast::Crate, ParserError> {
|
||||
fn parse_crate_inner(input: Input, psess: &'a ParseSess) -> Result<ast::Crate, ParserError> {
|
||||
ParserBuilder::default()
|
||||
.input(input)
|
||||
.sess(sess)
|
||||
.psess(psess)
|
||||
.build()?
|
||||
.parse_crate_mod()
|
||||
}
|
||||
|
||||
fn parse_crate_mod(&mut self) -> Result<ast::Crate, ParserError> {
|
||||
let mut parser = AssertUnwindSafe(&mut self.parser);
|
||||
|
||||
let err = Err(ParserError::ParsePanicError);
|
||||
match catch_unwind(move || parser.parse_crate_mod()) {
|
||||
Ok(Ok(k)) => Ok(k),
|
||||
Ok(Err(mut db)) => {
|
||||
Ok(Err(db)) => {
|
||||
db.emit();
|
||||
Err(ParserError::ParseError)
|
||||
err
|
||||
}
|
||||
Err(_) => Err(ParserError::ParsePanicError),
|
||||
Err(_) => err,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -2,9 +2,9 @@ use std::path::Path;
|
||||
use std::sync::atomic::{AtomicBool, Ordering};
|
||||
|
||||
use rustc_data_structures::sync::{IntoDynSyncSend, Lrc};
|
||||
use rustc_errors::emitter::{DynEmitter, Emitter, EmitterWriter};
|
||||
use rustc_errors::emitter::{stderr_destination, DynEmitter, Emitter, HumanEmitter, SilentEmitter};
|
||||
use rustc_errors::translation::Translate;
|
||||
use rustc_errors::{ColorConfig, DiagCtxt, Diagnostic, Level as DiagnosticLevel};
|
||||
use rustc_errors::{ColorConfig, Diag, DiagCtxt, DiagInner, Level as DiagnosticLevel};
|
||||
use rustc_session::parse::ParseSess as RawParseSess;
|
||||
use rustc_span::{
|
||||
source_map::{FilePathMapping, SourceMap},
|
||||
@ -22,36 +22,11 @@ use crate::{Config, ErrorKind, FileName};
|
||||
|
||||
/// ParseSess holds structs necessary for constructing a parser.
|
||||
pub(crate) struct ParseSess {
|
||||
parse_sess: RawParseSess,
|
||||
raw_psess: RawParseSess,
|
||||
ignore_path_set: Lrc<IgnorePathSet>,
|
||||
can_reset_errors: Lrc<AtomicBool>,
|
||||
}
|
||||
|
||||
/// Emitter which discards every error.
|
||||
struct SilentEmitter;
|
||||
|
||||
impl Translate for SilentEmitter {
|
||||
fn fluent_bundle(&self) -> Option<&Lrc<rustc_errors::FluentBundle>> {
|
||||
None
|
||||
}
|
||||
|
||||
fn fallback_fluent_bundle(&self) -> &rustc_errors::FluentBundle {
|
||||
panic!("silent emitter attempted to translate a diagnostic");
|
||||
}
|
||||
}
|
||||
|
||||
impl Emitter for SilentEmitter {
|
||||
fn source_map(&self) -> Option<&Lrc<SourceMap>> {
|
||||
None
|
||||
}
|
||||
|
||||
fn emit_diagnostic(&mut self, _db: &Diagnostic) {}
|
||||
}
|
||||
|
||||
fn silent_emitter() -> Box<DynEmitter> {
|
||||
Box::new(SilentEmitter {})
|
||||
}
|
||||
|
||||
/// Emit errors against every files expect ones specified in the `ignore_path_set`.
|
||||
struct SilentOnIgnoredFilesEmitter {
|
||||
ignore_path_set: IntoDynSyncSend<Lrc<IgnorePathSet>>,
|
||||
@ -62,10 +37,10 @@ struct SilentOnIgnoredFilesEmitter {
|
||||
}
|
||||
|
||||
impl SilentOnIgnoredFilesEmitter {
|
||||
fn handle_non_ignorable_error(&mut self, db: &Diagnostic) {
|
||||
fn handle_non_ignoreable_error(&mut self, diag: DiagInner) {
|
||||
self.has_non_ignorable_parser_errors = true;
|
||||
self.can_reset.store(false, Ordering::Release);
|
||||
self.emitter.emit_diagnostic(db);
|
||||
self.emitter.emit_diagnostic(diag);
|
||||
}
|
||||
}
|
||||
|
||||
@ -84,11 +59,11 @@ impl Emitter for SilentOnIgnoredFilesEmitter {
|
||||
None
|
||||
}
|
||||
|
||||
fn emit_diagnostic(&mut self, db: &Diagnostic) {
|
||||
if db.level() == DiagnosticLevel::Fatal {
|
||||
return self.handle_non_ignorable_error(db);
|
||||
fn emit_diagnostic(&mut self, diag: DiagInner) {
|
||||
if diag.level() == DiagnosticLevel::Fatal {
|
||||
return self.handle_non_ignoreable_error(diag);
|
||||
}
|
||||
if let Some(primary_span) = &db.span.primary_span() {
|
||||
if let Some(primary_span) = &diag.span.primary_span() {
|
||||
let file_name = self.source_map.span_to_filename(*primary_span);
|
||||
if let rustc_span::FileName::Real(rustc_span::RealFileName::LocalPath(ref path)) =
|
||||
file_name
|
||||
@ -104,7 +79,7 @@ impl Emitter for SilentOnIgnoredFilesEmitter {
|
||||
}
|
||||
};
|
||||
}
|
||||
self.handle_non_ignorable_error(db);
|
||||
self.handle_non_ignoreable_error(diag);
|
||||
}
|
||||
}
|
||||
|
||||
@ -132,16 +107,26 @@ fn default_dcx(
|
||||
ColorConfig::Never
|
||||
};
|
||||
|
||||
let emitter = if !show_parse_errors {
|
||||
silent_emitter()
|
||||
let fallback_bundle = rustc_errors::fallback_fluent_bundle(
|
||||
rustc_driver::DEFAULT_LOCALE_RESOURCES.to_vec(),
|
||||
false,
|
||||
);
|
||||
let emitter = Box::new(
|
||||
HumanEmitter::new(stderr_destination(emit_color), fallback_bundle.clone())
|
||||
.sm(Some(source_map.clone())),
|
||||
);
|
||||
|
||||
let emitter: Box<DynEmitter> = if !show_parse_errors {
|
||||
Box::new(SilentEmitter {
|
||||
fallback_bundle,
|
||||
fatal_dcx: DiagCtxt::new(emitter),
|
||||
fatal_note: None,
|
||||
emit_fatal_diagnostic: false,
|
||||
})
|
||||
} else {
|
||||
let fallback_bundle = rustc_errors::fallback_fluent_bundle(
|
||||
rustc_driver::DEFAULT_LOCALE_RESOURCES.to_vec(),
|
||||
false,
|
||||
);
|
||||
Box::new(EmitterWriter::stderr(emit_color, fallback_bundle).sm(Some(source_map.clone())))
|
||||
emitter
|
||||
};
|
||||
DiagCtxt::with_emitter(Box::new(SilentOnIgnoredFilesEmitter {
|
||||
DiagCtxt::new(Box::new(SilentOnIgnoredFilesEmitter {
|
||||
has_non_ignorable_parser_errors: false,
|
||||
source_map,
|
||||
emitter,
|
||||
@ -166,10 +151,10 @@ impl ParseSess {
|
||||
config.show_parse_errors(),
|
||||
config.color(),
|
||||
);
|
||||
let parse_sess = RawParseSess::with_dcx(dcx, source_map);
|
||||
let raw_psess = RawParseSess::with_dcx(dcx, source_map);
|
||||
|
||||
Ok(ParseSess {
|
||||
parse_sess,
|
||||
raw_psess,
|
||||
ignore_path_set,
|
||||
can_reset_errors,
|
||||
})
|
||||
@ -188,14 +173,14 @@ impl ParseSess {
|
||||
relative: Option<symbol::Ident>,
|
||||
dir_path: &Path,
|
||||
) -> Result<ModulePathSuccess, ModError<'_>> {
|
||||
rustc_expand::module::default_submod_path(&self.parse_sess, id, relative, dir_path).or_else(
|
||||
rustc_expand::module::default_submod_path(&self.raw_psess, id, relative, dir_path).or_else(
|
||||
|e| {
|
||||
// If resolving a module relative to {dir_path}/{symbol} fails because a file
|
||||
// could not be found, then try to resolve the module relative to {dir_path}.
|
||||
// If we still can't find the module after searching for it in {dir_path},
|
||||
// surface the original error.
|
||||
if matches!(e, ModError::FileNotFound(..)) && relative.is_some() {
|
||||
rustc_expand::module::default_submod_path(&self.parse_sess, id, None, dir_path)
|
||||
rustc_expand::module::default_submod_path(&self.raw_psess, id, None, dir_path)
|
||||
.map_err(|_| e)
|
||||
} else {
|
||||
Err(e)
|
||||
@ -205,7 +190,7 @@ impl ParseSess {
|
||||
}
|
||||
|
||||
pub(crate) fn is_file_parsed(&self, path: &Path) -> bool {
|
||||
self.parse_sess
|
||||
self.raw_psess
|
||||
.source_map()
|
||||
.get_source_file(&rustc_span::FileName::Real(
|
||||
rustc_span::RealFileName::LocalPath(path.to_path_buf()),
|
||||
@ -218,21 +203,28 @@ impl ParseSess {
|
||||
}
|
||||
|
||||
pub(crate) fn set_silent_emitter(&mut self) {
|
||||
self.parse_sess.dcx = DiagCtxt::with_emitter(silent_emitter());
|
||||
// Ideally this invocation wouldn't be necessary and the fallback bundle in
|
||||
// `self.parse_sess.dcx` could be used, but the lock in `DiagCtxt` prevents this.
|
||||
// See `<rustc_errors::SilentEmitter as Translate>::fallback_fluent_bundle`.
|
||||
let fallback_bundle = rustc_errors::fallback_fluent_bundle(
|
||||
rustc_driver::DEFAULT_LOCALE_RESOURCES.to_vec(),
|
||||
false,
|
||||
);
|
||||
self.raw_psess.dcx.make_silent(fallback_bundle, None, false);
|
||||
}
|
||||
|
||||
pub(crate) fn span_to_filename(&self, span: Span) -> FileName {
|
||||
self.parse_sess.source_map().span_to_filename(span).into()
|
||||
self.raw_psess.source_map().span_to_filename(span).into()
|
||||
}
|
||||
|
||||
pub(crate) fn span_to_file_contents(&self, span: Span) -> Lrc<rustc_span::SourceFile> {
|
||||
self.parse_sess
|
||||
self.raw_psess
|
||||
.source_map()
|
||||
.lookup_source_file(span.data().lo)
|
||||
}
|
||||
|
||||
pub(crate) fn span_to_first_line_string(&self, span: Span) -> String {
|
||||
let file_lines = self.parse_sess.source_map().span_to_lines(span).ok();
|
||||
let file_lines = self.raw_psess.source_map().span_to_lines(span).ok();
|
||||
|
||||
match file_lines {
|
||||
Some(fl) => fl
|
||||
@ -244,7 +236,7 @@ impl ParseSess {
|
||||
}
|
||||
|
||||
pub(crate) fn line_of_byte_pos(&self, pos: BytePos) -> usize {
|
||||
self.parse_sess.source_map().lookup_char_pos(pos).line
|
||||
self.raw_psess.source_map().lookup_char_pos(pos).line
|
||||
}
|
||||
|
||||
// TODO(calebcartwright): Preemptive, currently unused addition
|
||||
@ -257,15 +249,15 @@ impl ParseSess {
|
||||
}
|
||||
|
||||
pub(crate) fn span_to_debug_info(&self, span: Span) -> String {
|
||||
self.parse_sess.source_map().span_to_diagnostic_string(span)
|
||||
self.raw_psess.source_map().span_to_diagnostic_string(span)
|
||||
}
|
||||
|
||||
pub(crate) fn inner(&self) -> &RawParseSess {
|
||||
&self.parse_sess
|
||||
&self.raw_psess
|
||||
}
|
||||
|
||||
pub(crate) fn snippet_provider(&self, span: Span) -> SnippetProvider {
|
||||
let source_file = self.parse_sess.source_map().lookup_char_pos(span.lo()).file;
|
||||
let source_file = self.raw_psess.source_map().lookup_char_pos(span.lo()).file;
|
||||
SnippetProvider::new(
|
||||
source_file.start_pos,
|
||||
source_file.end_position(),
|
||||
@ -274,7 +266,7 @@ impl ParseSess {
|
||||
}
|
||||
|
||||
pub(crate) fn get_original_snippet(&self, file_name: &FileName) -> Option<Lrc<String>> {
|
||||
self.parse_sess
|
||||
self.raw_psess
|
||||
.source_map()
|
||||
.get_source_file(&file_name.into())
|
||||
.and_then(|source_file| source_file.src.clone())
|
||||
@ -283,9 +275,9 @@ impl ParseSess {
|
||||
|
||||
// Methods that should be restricted within the parse module.
|
||||
impl ParseSess {
|
||||
pub(super) fn emit_diagnostics(&self, diagnostics: Vec<Diagnostic>) {
|
||||
pub(super) fn emit_diagnostics(&self, diagnostics: Vec<Diag<'_>>) {
|
||||
for diagnostic in diagnostics {
|
||||
self.parse_sess.dcx.emit_diagnostic(diagnostic);
|
||||
diagnostic.emit();
|
||||
}
|
||||
}
|
||||
|
||||
@ -294,23 +286,23 @@ impl ParseSess {
|
||||
}
|
||||
|
||||
pub(super) fn has_errors(&self) -> bool {
|
||||
self.parse_sess.dcx.has_errors().is_some()
|
||||
self.raw_psess.dcx.has_errors().is_some()
|
||||
}
|
||||
|
||||
pub(super) fn reset_errors(&self) {
|
||||
self.parse_sess.dcx.reset_err_count();
|
||||
self.raw_psess.dcx.reset_err_count();
|
||||
}
|
||||
}
|
||||
|
||||
impl LineRangeUtils for ParseSess {
|
||||
fn lookup_line_range(&self, span: Span) -> LineRange {
|
||||
let snippet = self
|
||||
.parse_sess
|
||||
.raw_psess
|
||||
.source_map()
|
||||
.span_to_snippet(span)
|
||||
.unwrap_or_default();
|
||||
let lo = self.parse_sess.source_map().lookup_line(span.lo()).unwrap();
|
||||
let hi = self.parse_sess.source_map().lookup_line(span.hi()).unwrap();
|
||||
let lo = self.raw_psess.source_map().lookup_line(span.lo()).unwrap();
|
||||
let hi = self.raw_psess.source_map().lookup_line(span.hi()).unwrap();
|
||||
|
||||
debug_assert_eq!(
|
||||
lo.sf.name, hi.sf.name,
|
||||
@ -363,13 +355,14 @@ mod tests {
|
||||
None
|
||||
}
|
||||
|
||||
fn emit_diagnostic(&mut self, _db: &Diagnostic) {
|
||||
fn emit_diagnostic(&mut self, _diag: DiagInner) {
|
||||
self.num_emitted_errors.fetch_add(1, Ordering::Release);
|
||||
}
|
||||
}
|
||||
|
||||
fn build_diagnostic(level: DiagnosticLevel, span: Option<MultiSpan>) -> Diagnostic {
|
||||
let mut diag = Diagnostic::new(level, "");
|
||||
fn build_diagnostic(level: DiagnosticLevel, span: Option<MultiSpan>) -> DiagInner {
|
||||
#[allow(rustc::untranslatable_diagnostic)] // no translation needed for empty string
|
||||
let mut diag = DiagInner::new(level, "");
|
||||
diag.messages.clear();
|
||||
if let Some(span) = span {
|
||||
diag.span = span;
|
||||
@ -422,7 +415,7 @@ mod tests {
|
||||
);
|
||||
let span = MultiSpan::from_span(mk_sp(BytePos(0), BytePos(1)));
|
||||
let fatal_diagnostic = build_diagnostic(DiagnosticLevel::Fatal, Some(span));
|
||||
emitter.emit_diagnostic(&fatal_diagnostic);
|
||||
emitter.emit_diagnostic(fatal_diagnostic);
|
||||
assert_eq!(num_emitted_errors.load(Ordering::Acquire), 1);
|
||||
assert_eq!(can_reset_errors.load(Ordering::Acquire), false);
|
||||
}
|
||||
@ -446,8 +439,8 @@ mod tests {
|
||||
Some(ignore_list),
|
||||
);
|
||||
let span = MultiSpan::from_span(mk_sp(BytePos(0), BytePos(1)));
|
||||
let non_fatal_diagnostic = build_diagnostic(DiagnosticLevel::Warning(None), Some(span));
|
||||
emitter.emit_diagnostic(&non_fatal_diagnostic);
|
||||
let non_fatal_diagnostic = build_diagnostic(DiagnosticLevel::Warning, Some(span));
|
||||
emitter.emit_diagnostic(non_fatal_diagnostic);
|
||||
assert_eq!(num_emitted_errors.load(Ordering::Acquire), 0);
|
||||
assert_eq!(can_reset_errors.load(Ordering::Acquire), true);
|
||||
}
|
||||
@ -470,8 +463,8 @@ mod tests {
|
||||
None,
|
||||
);
|
||||
let span = MultiSpan::from_span(mk_sp(BytePos(0), BytePos(1)));
|
||||
let non_fatal_diagnostic = build_diagnostic(DiagnosticLevel::Warning(None), Some(span));
|
||||
emitter.emit_diagnostic(&non_fatal_diagnostic);
|
||||
let non_fatal_diagnostic = build_diagnostic(DiagnosticLevel::Warning, Some(span));
|
||||
emitter.emit_diagnostic(non_fatal_diagnostic);
|
||||
assert_eq!(num_emitted_errors.load(Ordering::Acquire), 1);
|
||||
assert_eq!(can_reset_errors.load(Ordering::Acquire), false);
|
||||
}
|
||||
@ -507,12 +500,12 @@ mod tests {
|
||||
);
|
||||
let bar_span = MultiSpan::from_span(mk_sp(BytePos(0), BytePos(1)));
|
||||
let foo_span = MultiSpan::from_span(mk_sp(BytePos(21), BytePos(22)));
|
||||
let bar_diagnostic = build_diagnostic(DiagnosticLevel::Warning(None), Some(bar_span));
|
||||
let foo_diagnostic = build_diagnostic(DiagnosticLevel::Warning(None), Some(foo_span));
|
||||
let bar_diagnostic = build_diagnostic(DiagnosticLevel::Warning, Some(bar_span));
|
||||
let foo_diagnostic = build_diagnostic(DiagnosticLevel::Warning, Some(foo_span));
|
||||
let fatal_diagnostic = build_diagnostic(DiagnosticLevel::Fatal, None);
|
||||
emitter.emit_diagnostic(&bar_diagnostic);
|
||||
emitter.emit_diagnostic(&foo_diagnostic);
|
||||
emitter.emit_diagnostic(&fatal_diagnostic);
|
||||
emitter.emit_diagnostic(bar_diagnostic);
|
||||
emitter.emit_diagnostic(foo_diagnostic);
|
||||
emitter.emit_diagnostic(fatal_diagnostic);
|
||||
assert_eq!(num_emitted_errors.load(Ordering::Acquire), 2);
|
||||
assert_eq!(can_reset_errors.load(Ordering::Acquire), false);
|
||||
}
|
||||
|
114
src/patterns.rs
114
src/patterns.rs
@ -1,6 +1,4 @@
|
||||
use rustc_ast::ast::{
|
||||
self, BindingAnnotation, ByRef, Pat, PatField, PatKind, RangeEnd, RangeSyntax,
|
||||
};
|
||||
use rustc_ast::ast::{self, BindingMode, ByRef, Pat, PatField, PatKind, RangeEnd, RangeSyntax};
|
||||
use rustc_ast::ptr;
|
||||
use rustc_span::{BytePos, Span};
|
||||
|
||||
@ -40,9 +38,11 @@ pub(crate) fn is_short_pattern(pat: &ast::Pat, pat_str: &str) -> bool {
|
||||
|
||||
fn is_short_pattern_inner(pat: &ast::Pat) -> bool {
|
||||
match pat.kind {
|
||||
ast::PatKind::Rest | ast::PatKind::Never | ast::PatKind::Wild | ast::PatKind::Lit(_) => {
|
||||
true
|
||||
}
|
||||
ast::PatKind::Rest
|
||||
| ast::PatKind::Never
|
||||
| ast::PatKind::Wild
|
||||
| ast::PatKind::Err(_)
|
||||
| ast::PatKind::Lit(_) => true,
|
||||
ast::PatKind::Ident(_, _, ref pat) => pat.is_none(),
|
||||
ast::PatKind::Struct(..)
|
||||
| ast::PatKind::MacCall(..)
|
||||
@ -53,9 +53,10 @@ fn is_short_pattern_inner(pat: &ast::Pat) -> bool {
|
||||
ast::PatKind::TupleStruct(_, ref path, ref subpats) => {
|
||||
path.segments.len() <= 1 && subpats.len() <= 1
|
||||
}
|
||||
ast::PatKind::Box(ref p) | ast::PatKind::Ref(ref p, _) | ast::PatKind::Paren(ref p) => {
|
||||
is_short_pattern_inner(&*p)
|
||||
}
|
||||
ast::PatKind::Box(ref p)
|
||||
| PatKind::Deref(ref p)
|
||||
| ast::PatKind::Ref(ref p, _)
|
||||
| ast::PatKind::Paren(ref p) => is_short_pattern_inner(&*p),
|
||||
PatKind::Or(ref pats) => pats.iter().all(|p| is_short_pattern_inner(p)),
|
||||
}
|
||||
}
|
||||
@ -103,19 +104,20 @@ impl Rewrite for Pat {
|
||||
write_list(&items, &fmt)
|
||||
}
|
||||
PatKind::Box(ref pat) => rewrite_unary_prefix(context, "box ", &**pat, shape),
|
||||
PatKind::Ident(BindingAnnotation(by_ref, mutability), ident, ref sub_pat) => {
|
||||
let prefix = match by_ref {
|
||||
ByRef::Yes => "ref",
|
||||
ByRef::No => "",
|
||||
PatKind::Ident(BindingMode(by_ref, mutability), ident, ref sub_pat) => {
|
||||
let mut_prefix = format_mutability(mutability).trim();
|
||||
|
||||
let (ref_kw, mut_infix) = match by_ref {
|
||||
ByRef::Yes(rmutbl) => ("ref", format_mutability(rmutbl).trim()),
|
||||
ByRef::No => ("", ""),
|
||||
};
|
||||
let mut_infix = format_mutability(mutability).trim();
|
||||
let id_str = rewrite_ident(context, ident);
|
||||
let sub_pat = match *sub_pat {
|
||||
Some(ref p) => {
|
||||
// 2 - `@ `.
|
||||
let width = shape
|
||||
.width
|
||||
.checked_sub(prefix.len() + mut_infix.len() + id_str.len() + 2)?;
|
||||
let width = shape.width.checked_sub(
|
||||
mut_prefix.len() + ref_kw.len() + mut_infix.len() + id_str.len() + 2,
|
||||
)?;
|
||||
let lo = context.snippet_provider.span_after(self.span, "@");
|
||||
combine_strs_with_missing_comments(
|
||||
context,
|
||||
@ -129,33 +131,55 @@ impl Rewrite for Pat {
|
||||
None => "".to_owned(),
|
||||
};
|
||||
|
||||
// combine prefix and mut
|
||||
let (first_lo, first) = if !prefix.is_empty() && !mut_infix.is_empty() {
|
||||
let hi = context.snippet_provider.span_before(self.span, "mut");
|
||||
let lo = context.snippet_provider.span_after(self.span, "ref");
|
||||
(
|
||||
// combine prefix and ref
|
||||
let (first_lo, first) = match (mut_prefix.is_empty(), ref_kw.is_empty()) {
|
||||
(false, false) => {
|
||||
let lo = context.snippet_provider.span_after(self.span, "mut");
|
||||
let hi = context.snippet_provider.span_before(self.span, "ref");
|
||||
(
|
||||
context.snippet_provider.span_after(self.span, "ref"),
|
||||
combine_strs_with_missing_comments(
|
||||
context,
|
||||
mut_prefix,
|
||||
ref_kw,
|
||||
mk_sp(lo, hi),
|
||||
shape,
|
||||
true,
|
||||
)?,
|
||||
)
|
||||
}
|
||||
(false, true) => (
|
||||
context.snippet_provider.span_after(self.span, "mut"),
|
||||
combine_strs_with_missing_comments(
|
||||
context,
|
||||
prefix,
|
||||
mut_infix,
|
||||
mk_sp(lo, hi),
|
||||
shape,
|
||||
true,
|
||||
)?,
|
||||
)
|
||||
} else if !prefix.is_empty() {
|
||||
(
|
||||
mut_prefix.to_owned(),
|
||||
),
|
||||
(true, false) => (
|
||||
context.snippet_provider.span_after(self.span, "ref"),
|
||||
prefix.to_owned(),
|
||||
)
|
||||
} else if !mut_infix.is_empty() {
|
||||
(
|
||||
context.snippet_provider.span_after(self.span, "mut"),
|
||||
mut_infix.to_owned(),
|
||||
)
|
||||
} else {
|
||||
(self.span.lo(), "".to_owned())
|
||||
ref_kw.to_owned(),
|
||||
),
|
||||
(true, true) => (self.span.lo(), "".to_owned()),
|
||||
};
|
||||
|
||||
// combine result of above and mut
|
||||
let (second_lo, second) = match (first.is_empty(), mut_infix.is_empty()) {
|
||||
(false, false) => {
|
||||
let lo = context.snippet_provider.span_after(self.span, "ref");
|
||||
let end_span = mk_sp(first_lo, self.span.hi());
|
||||
let hi = context.snippet_provider.span_before(end_span, "mut");
|
||||
(
|
||||
context.snippet_provider.span_after(end_span, "mut"),
|
||||
combine_strs_with_missing_comments(
|
||||
context,
|
||||
&first,
|
||||
mut_infix,
|
||||
mk_sp(lo, hi),
|
||||
shape,
|
||||
true,
|
||||
)?,
|
||||
)
|
||||
}
|
||||
(false, true) => (first_lo, first),
|
||||
(true, false) => unreachable!("mut_infix necessarily follows a ref"),
|
||||
(true, true) => (self.span.lo(), "".to_owned()),
|
||||
};
|
||||
|
||||
let next = if !sub_pat.is_empty() {
|
||||
@ -174,9 +198,9 @@ impl Rewrite for Pat {
|
||||
|
||||
combine_strs_with_missing_comments(
|
||||
context,
|
||||
&first,
|
||||
&second,
|
||||
&next,
|
||||
mk_sp(first_lo, ident.span.lo()),
|
||||
mk_sp(second_lo, ident.span.lo()),
|
||||
shape,
|
||||
true,
|
||||
)
|
||||
@ -274,6 +298,8 @@ impl Rewrite for Pat {
|
||||
PatKind::Paren(ref pat) => pat
|
||||
.rewrite(context, shape.offset_left(1)?.sub_width(1)?)
|
||||
.map(|inner_pat| format!("({})", inner_pat)),
|
||||
PatKind::Err(_) => None,
|
||||
PatKind::Deref(_) => None,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -263,13 +263,13 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
item_kind: ReorderableItemKind,
|
||||
in_group: bool,
|
||||
) -> usize {
|
||||
let mut last = self.parse_sess.lookup_line_range(items[0].span());
|
||||
let mut last = self.psess.lookup_line_range(items[0].span());
|
||||
let item_length = items
|
||||
.iter()
|
||||
.take_while(|ppi| {
|
||||
item_kind.is_same_item_kind(&***ppi)
|
||||
&& (!in_group || {
|
||||
let current = self.parse_sess.lookup_line_range(ppi.span());
|
||||
let current = self.psess.lookup_line_range(ppi.span());
|
||||
let in_same_group = current.lo < last.hi + 2;
|
||||
last = current;
|
||||
in_same_group
|
||||
|
@ -26,7 +26,7 @@ impl<T: Rewrite> Rewrite for ptr::P<T> {
|
||||
|
||||
#[derive(Clone)]
|
||||
pub(crate) struct RewriteContext<'a> {
|
||||
pub(crate) parse_sess: &'a ParseSess,
|
||||
pub(crate) psess: &'a ParseSess,
|
||||
pub(crate) config: &'a Config,
|
||||
pub(crate) inside_macro: Rc<Cell<bool>>,
|
||||
// Force block indent style even if we are using visual indent style.
|
||||
|
@ -49,7 +49,7 @@ where
|
||||
}
|
||||
|
||||
pub(crate) fn write_file<T>(
|
||||
parse_sess: Option<&ParseSess>,
|
||||
psess: Option<&ParseSess>,
|
||||
filename: &FileName,
|
||||
formatted_text: &str,
|
||||
out: &mut T,
|
||||
@ -66,6 +66,7 @@ where
|
||||
}
|
||||
}
|
||||
|
||||
#[allow(non_local_definitions)]
|
||||
impl From<&FileName> for rustc_span::FileName {
|
||||
fn from(filename: &FileName) -> rustc_span::FileName {
|
||||
match filename {
|
||||
@ -89,7 +90,7 @@ where
|
||||
let original_text = if newline_style != NewlineStyle::Auto && *filename != FileName::Stdin {
|
||||
Lrc::new(fs::read_to_string(ensure_real_path(filename))?)
|
||||
} else {
|
||||
match parse_sess.and_then(|sess| sess.get_original_snippet(filename)) {
|
||||
match psess.and_then(|psess| psess.get_original_snippet(filename)) {
|
||||
Some(ori) => ori,
|
||||
None => Lrc::new(fs::read_to_string(ensure_real_path(filename))?),
|
||||
}
|
||||
|
@ -61,7 +61,7 @@ implement_spanned!(ast::Local);
|
||||
impl Spanned for ast::Stmt {
|
||||
fn span(&self) -> Span {
|
||||
match self.kind {
|
||||
ast::StmtKind::Local(ref local) => mk_sp(local.span().lo(), self.span.hi()),
|
||||
ast::StmtKind::Let(ref local) => mk_sp(local.span().lo(), self.span.hi()),
|
||||
ast::StmtKind::Item(ref item) => mk_sp(item.span().lo(), self.span.hi()),
|
||||
ast::StmtKind::Expr(ref expr) | ast::StmtKind::Semi(ref expr) => {
|
||||
mk_sp(expr.span().lo(), self.span.hi())
|
||||
|
@ -115,7 +115,7 @@ fn format_stmt(
|
||||
skip_out_of_file_lines_range!(context, stmt.span());
|
||||
|
||||
let result = match stmt.kind {
|
||||
ast::StmtKind::Local(ref local) => local.rewrite(context, shape),
|
||||
ast::StmtKind::Let(ref local) => local.rewrite(context, shape),
|
||||
ast::StmtKind::Expr(ref ex) | ast::StmtKind::Semi(ref ex) => {
|
||||
let suffix = if semicolon_for_stmt(context, stmt, is_last_expr) {
|
||||
";"
|
||||
|
@ -391,12 +391,24 @@ fn self_tests() {
|
||||
files.push(path);
|
||||
}
|
||||
// for crates that need to be included but lies outside src
|
||||
let external_crates = vec!["check_diff"];
|
||||
let external_crates = vec!["check_diff", "config_proc_macro"];
|
||||
for external_crate in external_crates {
|
||||
let mut path = PathBuf::from(external_crate);
|
||||
path.push("src");
|
||||
path.push("main.rs");
|
||||
files.push(path);
|
||||
let directory = fs::read_dir(&path).unwrap();
|
||||
let search_files = directory.filter_map(|file| {
|
||||
file.ok().and_then(|f| {
|
||||
let name = f.file_name();
|
||||
if matches!(name.as_os_str().to_str(), Some("main.rs" | "lib.rs")) {
|
||||
Some(f.path())
|
||||
} else {
|
||||
None
|
||||
}
|
||||
})
|
||||
});
|
||||
for file in search_files {
|
||||
files.push(file);
|
||||
}
|
||||
}
|
||||
files.push(PathBuf::from("src/lib.rs"));
|
||||
|
||||
|
@ -55,3 +55,17 @@ fn crate_parsing_errors_on_unclosed_delims() {
|
||||
let filename = "tests/parser/unclosed-delims/issue_4466.rs";
|
||||
assert_parser_error(filename);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn crate_parsing_stashed_diag() {
|
||||
// See also https://github.com/rust-lang/rust/issues/121450
|
||||
let filename = "tests/parser/stashed-diag.rs";
|
||||
assert_parser_error(filename);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn crate_parsing_stashed_diag2() {
|
||||
// See also https://github.com/rust-lang/rust/issues/121517
|
||||
let filename = "tests/parser/stashed-diag2.rs";
|
||||
assert_parser_error(filename);
|
||||
}
|
||||
|
53
src/types.rs
53
src/types.rs
@ -142,7 +142,7 @@ pub(crate) enum SegmentParam<'a> {
|
||||
Const(&'a ast::AnonConst),
|
||||
LifeTime(&'a ast::Lifetime),
|
||||
Type(&'a ast::Ty),
|
||||
Binding(&'a ast::AssocConstraint),
|
||||
Binding(&'a ast::AssocItemConstraint),
|
||||
}
|
||||
|
||||
impl<'a> SegmentParam<'a> {
|
||||
@ -177,9 +177,9 @@ impl<'a> Rewrite for SegmentParam<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
impl Rewrite for ast::AssocConstraint {
|
||||
impl Rewrite for ast::AssocItemConstraint {
|
||||
fn rewrite(&self, context: &RewriteContext<'_>, shape: Shape) -> Option<String> {
|
||||
use ast::AssocConstraintKind::{Bound, Equality};
|
||||
use ast::AssocItemConstraintKind::{Bound, Equality};
|
||||
|
||||
let mut result = String::with_capacity(128);
|
||||
result.push_str(rewrite_ident(context, self.ident));
|
||||
@ -207,14 +207,14 @@ impl Rewrite for ast::AssocConstraint {
|
||||
}
|
||||
}
|
||||
|
||||
impl Rewrite for ast::AssocConstraintKind {
|
||||
impl Rewrite for ast::AssocItemConstraintKind {
|
||||
fn rewrite(&self, context: &RewriteContext<'_>, shape: Shape) -> Option<String> {
|
||||
match self {
|
||||
ast::AssocConstraintKind::Equality { term } => match term {
|
||||
ast::AssocItemConstraintKind::Equality { term } => match term {
|
||||
Term::Ty(ty) => ty.rewrite(context, shape),
|
||||
Term::Const(c) => c.rewrite(context, shape),
|
||||
},
|
||||
ast::AssocConstraintKind::Bound { bounds } => bounds.rewrite(context, shape),
|
||||
ast::AssocItemConstraintKind::Bound { bounds } => bounds.rewrite(context, shape),
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -539,18 +539,29 @@ impl Rewrite for ast::Lifetime {
|
||||
impl Rewrite for ast::GenericBound {
|
||||
fn rewrite(&self, context: &RewriteContext<'_>, shape: Shape) -> Option<String> {
|
||||
match *self {
|
||||
ast::GenericBound::Trait(ref poly_trait_ref, modifiers) => {
|
||||
ast::GenericBound::Trait(
|
||||
ref poly_trait_ref,
|
||||
ast::TraitBoundModifiers {
|
||||
constness,
|
||||
asyncness,
|
||||
polarity,
|
||||
},
|
||||
) => {
|
||||
let snippet = context.snippet(self.span());
|
||||
let has_paren = snippet.starts_with('(') && snippet.ends_with(')');
|
||||
let mut constness = modifiers.constness.as_str().to_string();
|
||||
let mut constness = constness.as_str().to_string();
|
||||
if !constness.is_empty() {
|
||||
constness.push(' ');
|
||||
}
|
||||
let polarity = modifiers.polarity.as_str();
|
||||
let mut asyncness = asyncness.as_str().to_string();
|
||||
if !asyncness.is_empty() {
|
||||
asyncness.push(' ');
|
||||
}
|
||||
let polarity = polarity.as_str();
|
||||
let shape = shape.offset_left(constness.len() + polarity.len())?;
|
||||
poly_trait_ref
|
||||
.rewrite(context, shape)
|
||||
.map(|s| format!("{constness}{polarity}{s}"))
|
||||
.map(|s| format!("{constness}{asyncness}{polarity}{s}"))
|
||||
.map(|s| if has_paren { format!("({})", s) } else { s })
|
||||
}
|
||||
ast::GenericBound::Outlives(ref lifetime) => lifetime.rewrite(context, shape),
|
||||
@ -810,8 +821,8 @@ impl Rewrite for ast::Ty {
|
||||
ast::TyKind::Tup(ref items) => {
|
||||
rewrite_tuple(context, items.iter(), self.span, shape, items.len() == 1)
|
||||
}
|
||||
ast::TyKind::AnonStruct(_) => Some(context.snippet(self.span).to_owned()),
|
||||
ast::TyKind::AnonUnion(_) => Some(context.snippet(self.span).to_owned()),
|
||||
ast::TyKind::AnonStruct(..) => Some(context.snippet(self.span).to_owned()),
|
||||
ast::TyKind::AnonUnion(..) => Some(context.snippet(self.span).to_owned()),
|
||||
ast::TyKind::Path(ref q_self, ref path) => {
|
||||
rewrite_path(context, PathContext::Type, q_self, path, shape)
|
||||
}
|
||||
@ -836,7 +847,11 @@ impl Rewrite for ast::Ty {
|
||||
rewrite_macro(mac, None, context, shape, MacroPosition::Expression)
|
||||
}
|
||||
ast::TyKind::ImplicitSelf => Some(String::from("")),
|
||||
ast::TyKind::ImplTrait(_, ref it) => {
|
||||
ast::TyKind::ImplTrait(_, ref it, ref captures) => {
|
||||
// FIXME(precise_capturing): Implement formatting.
|
||||
if captures.is_some() {
|
||||
return None;
|
||||
}
|
||||
// Empty trait is not a parser error.
|
||||
if it.is_empty() {
|
||||
return Some("impl".to_owned());
|
||||
@ -852,7 +867,7 @@ impl Rewrite for ast::Ty {
|
||||
})
|
||||
}
|
||||
ast::TyKind::CVarArgs => Some("...".to_owned()),
|
||||
ast::TyKind::Err => Some(context.snippet(self.span).to_owned()),
|
||||
ast::TyKind::Dummy | ast::TyKind::Err(_) => Some(context.snippet(self.span).to_owned()),
|
||||
ast::TyKind::Typeof(ref anon_const) => rewrite_call(
|
||||
context,
|
||||
"typeof",
|
||||
@ -860,6 +875,11 @@ impl Rewrite for ast::Ty {
|
||||
self.span,
|
||||
shape,
|
||||
),
|
||||
ast::TyKind::Pat(ref ty, ref pat) => {
|
||||
let ty = ty.rewrite(context, shape)?;
|
||||
let pat = pat.rewrite(context, shape)?;
|
||||
Some(format!("{ty} is {pat}"))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -883,7 +903,7 @@ fn rewrite_bare_fn(
|
||||
result.push_str("> ");
|
||||
}
|
||||
|
||||
result.push_str(crate::utils::format_unsafety(bare_fn.unsafety));
|
||||
result.push_str(crate::utils::format_safety(bare_fn.safety));
|
||||
|
||||
result.push_str(&format_extern(
|
||||
bare_fn.ext,
|
||||
@ -1094,7 +1114,8 @@ fn join_bounds_inner(
|
||||
|
||||
pub(crate) fn opaque_ty(ty: &Option<ptr::P<ast::Ty>>) -> Option<&ast::GenericBounds> {
|
||||
ty.as_ref().and_then(|t| match &t.kind {
|
||||
ast::TyKind::ImplTrait(_, bounds) => Some(bounds),
|
||||
// FIXME(precise_capturing): Implement support here
|
||||
ast::TyKind::ImplTrait(_, bounds, _) => Some(bounds),
|
||||
_ => None,
|
||||
})
|
||||
}
|
||||
|
12
src/utils.rs
12
src/utils.rs
@ -108,10 +108,11 @@ pub(crate) fn format_defaultness(defaultness: ast::Defaultness) -> &'static str
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub(crate) fn format_unsafety(unsafety: ast::Unsafe) -> &'static str {
|
||||
pub(crate) fn format_safety(unsafety: ast::Safety) -> &'static str {
|
||||
match unsafety {
|
||||
ast::Unsafe::Yes(..) => "unsafe ",
|
||||
ast::Unsafe::No => "",
|
||||
ast::Safety::Unsafe(..) => "unsafe ",
|
||||
ast::Safety::Safe(..) => "safe ",
|
||||
ast::Safety::Default => "",
|
||||
}
|
||||
}
|
||||
|
||||
@ -362,7 +363,7 @@ macro_rules! out_of_file_lines_range {
|
||||
&& !$self
|
||||
.config
|
||||
.file_lines()
|
||||
.intersects(&$self.parse_sess.lookup_line_range($span))
|
||||
.intersects(&$self.psess.lookup_line_range($span))
|
||||
};
|
||||
}
|
||||
|
||||
@ -497,7 +498,8 @@ pub(crate) fn is_block_expr(context: &RewriteContext<'_>, expr: &ast::Expr, repr
|
||||
| ast::ExprKind::Break(..)
|
||||
| ast::ExprKind::Cast(..)
|
||||
| ast::ExprKind::Continue(..)
|
||||
| ast::ExprKind::Err
|
||||
| ast::ExprKind::Dummy
|
||||
| ast::ExprKind::Err(_)
|
||||
| ast::ExprKind::Field(..)
|
||||
| ast::ExprKind::IncludedBytes(..)
|
||||
| ast::ExprKind::InlineAsm(..)
|
||||
|
@ -24,7 +24,7 @@ use crate::source_map::{LineRangeUtils, SpanUtils};
|
||||
use crate::spanned::Spanned;
|
||||
use crate::stmt::Stmt;
|
||||
use crate::utils::{
|
||||
self, contains_skip, count_newlines, depr_skip_annotation, format_unsafety, inner_attributes,
|
||||
self, contains_skip, count_newlines, depr_skip_annotation, format_safety, inner_attributes,
|
||||
last_line_width, mk_sp, ptr_vec_to_ref_vec, rewrite_ident, starts_with_newline, stmt_expr,
|
||||
};
|
||||
use crate::{ErrorKind, FormatReport, FormattingError};
|
||||
@ -71,7 +71,7 @@ impl SnippetProvider {
|
||||
|
||||
pub(crate) struct FmtVisitor<'a> {
|
||||
parent_context: Option<&'a RewriteContext<'a>>,
|
||||
pub(crate) parse_sess: &'a ParseSess,
|
||||
pub(crate) psess: &'a ParseSess,
|
||||
pub(crate) buffer: String,
|
||||
pub(crate) last_pos: BytePos,
|
||||
// FIXME: use an RAII util or closure for indenting
|
||||
@ -113,10 +113,7 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
}
|
||||
|
||||
fn visit_stmt(&mut self, stmt: &Stmt<'_>, include_empty_semi: bool) {
|
||||
debug!(
|
||||
"visit_stmt: {}",
|
||||
self.parse_sess.span_to_debug_info(stmt.span())
|
||||
);
|
||||
debug!("visit_stmt: {}", self.psess.span_to_debug_info(stmt.span()));
|
||||
|
||||
if stmt.is_empty() {
|
||||
// If the statement is empty, just skip over it. Before that, make sure any comment
|
||||
@ -153,7 +150,7 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
self.visit_item(item);
|
||||
self.last_pos = stmt.span().hi();
|
||||
}
|
||||
ast::StmtKind::Local(..) | ast::StmtKind::Expr(..) | ast::StmtKind::Semi(..) => {
|
||||
ast::StmtKind::Let(..) | ast::StmtKind::Expr(..) | ast::StmtKind::Semi(..) => {
|
||||
let attrs = get_attrs_from_stmt(stmt.as_ast_node());
|
||||
if contains_skip(attrs) {
|
||||
self.push_skipped_with_span(
|
||||
@ -217,10 +214,7 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
inner_attrs: Option<&[ast::Attribute]>,
|
||||
has_braces: bool,
|
||||
) {
|
||||
debug!(
|
||||
"visit_block: {}",
|
||||
self.parse_sess.span_to_debug_info(b.span),
|
||||
);
|
||||
debug!("visit_block: {}", self.psess.span_to_debug_info(b.span));
|
||||
|
||||
// Check if this block has braces.
|
||||
let brace_compensation = BytePos(if has_braces { 1 } else { 0 });
|
||||
@ -523,9 +517,9 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
self.visit_enum(item.ident, &item.vis, def, generics, item.span);
|
||||
self.last_pos = source!(self, item.span).hi();
|
||||
}
|
||||
ast::ItemKind::Mod(unsafety, ref mod_kind) => {
|
||||
ast::ItemKind::Mod(safety, ref mod_kind) => {
|
||||
self.format_missing_with_indent(source!(self, item.span).lo());
|
||||
self.format_mod(mod_kind, unsafety, &item.vis, item.span, item.ident, attrs);
|
||||
self.format_mod(mod_kind, safety, &item.vis, item.span, item.ident, attrs);
|
||||
}
|
||||
ast::ItemKind::MacCall(ref mac) => {
|
||||
self.visit_mac(mac, Some(item.ident), MacroPosition::Item);
|
||||
@ -592,6 +586,11 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
);
|
||||
self.push_rewrite(item.span, rewrite);
|
||||
}
|
||||
ast::ItemKind::Delegation(..) | ast::ItemKind::DelegationMac(..) => {
|
||||
// TODO: rewrite delegation items once syntax is established.
|
||||
// For now, leave the contents of the Span unformatted.
|
||||
self.push_rewrite(item.span, None)
|
||||
}
|
||||
};
|
||||
}
|
||||
self.skip_context = skip_context_saved;
|
||||
@ -739,10 +738,10 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
// do not take into account the lines with attributes as part of the skipped range
|
||||
let attrs_end = attrs
|
||||
.iter()
|
||||
.map(|attr| self.parse_sess.line_of_byte_pos(attr.span.hi()))
|
||||
.map(|attr| self.psess.line_of_byte_pos(attr.span.hi()))
|
||||
.max()
|
||||
.unwrap_or(1);
|
||||
let first_line = self.parse_sess.line_of_byte_pos(main_span.lo());
|
||||
let first_line = self.psess.line_of_byte_pos(main_span.lo());
|
||||
// Statement can start after some newlines and/or spaces
|
||||
// or it can be on the same line as the last attribute.
|
||||
// So here we need to take a minimum between the two.
|
||||
@ -753,8 +752,8 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
}
|
||||
|
||||
pub(crate) fn from_context(ctx: &'a RewriteContext<'_>) -> FmtVisitor<'a> {
|
||||
let mut visitor = FmtVisitor::from_parse_sess(
|
||||
ctx.parse_sess,
|
||||
let mut visitor = FmtVisitor::from_psess(
|
||||
ctx.psess,
|
||||
ctx.config,
|
||||
ctx.snippet_provider,
|
||||
ctx.report.clone(),
|
||||
@ -764,8 +763,8 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
visitor
|
||||
}
|
||||
|
||||
pub(crate) fn from_parse_sess(
|
||||
parse_session: &'a ParseSess,
|
||||
pub(crate) fn from_psess(
|
||||
psess: &'a ParseSess,
|
||||
config: &'a Config,
|
||||
snippet_provider: &'a SnippetProvider,
|
||||
report: FormatReport,
|
||||
@ -781,7 +780,7 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
skip_context.macros.extend(macro_names);
|
||||
FmtVisitor {
|
||||
parent_context: None,
|
||||
parse_sess: parse_session,
|
||||
psess,
|
||||
buffer: String::with_capacity(snippet_provider.big_snippet.len() * 2),
|
||||
last_pos: BytePos(0),
|
||||
block_indent: Indent::empty(),
|
||||
@ -809,12 +808,12 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
pub(crate) fn visit_attrs(&mut self, attrs: &[ast::Attribute], style: ast::AttrStyle) -> bool {
|
||||
for attr in attrs {
|
||||
if attr.has_name(depr_skip_annotation()) {
|
||||
let file_name = self.parse_sess.span_to_filename(attr.span);
|
||||
let file_name = self.psess.span_to_filename(attr.span);
|
||||
self.report.append(
|
||||
file_name,
|
||||
vec![FormattingError::from_span(
|
||||
attr.span,
|
||||
self.parse_sess,
|
||||
self.psess,
|
||||
ErrorKind::DeprecatedAttr,
|
||||
)],
|
||||
);
|
||||
@ -823,12 +822,12 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
ast::AttrKind::Normal(ref normal)
|
||||
if self.is_unknown_rustfmt_attr(&normal.item.path.segments) =>
|
||||
{
|
||||
let file_name = self.parse_sess.span_to_filename(attr.span);
|
||||
let file_name = self.psess.span_to_filename(attr.span);
|
||||
self.report.append(
|
||||
file_name,
|
||||
vec![FormattingError::from_span(
|
||||
attr.span,
|
||||
self.parse_sess,
|
||||
self.psess,
|
||||
ErrorKind::BadAttr,
|
||||
)],
|
||||
);
|
||||
@ -914,7 +913,7 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
fn format_mod(
|
||||
&mut self,
|
||||
mod_kind: &ast::ModKind,
|
||||
unsafety: ast::Unsafe,
|
||||
safety: ast::Safety,
|
||||
vis: &ast::Visibility,
|
||||
s: Span,
|
||||
ident: symbol::Ident,
|
||||
@ -922,7 +921,7 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
) {
|
||||
let vis_str = utils::format_visibility(&self.get_context(), vis);
|
||||
self.push_str(&*vis_str);
|
||||
self.push_str(format_unsafety(unsafety));
|
||||
self.push_str(format_safety(safety));
|
||||
self.push_str("mod ");
|
||||
// Calling `to_owned()` to work around borrow checker.
|
||||
let ident_str = rewrite_ident(&self.get_context(), ident).to_owned();
|
||||
@ -1002,7 +1001,7 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
|
||||
|
||||
pub(crate) fn get_context(&self) -> RewriteContext<'_> {
|
||||
RewriteContext {
|
||||
parse_sess: self.parse_sess,
|
||||
psess: self.psess,
|
||||
config: self.config,
|
||||
inside_macro: Rc::new(Cell::new(false)),
|
||||
use_block: Cell::new(false),
|
||||
|
3
tests/parser/stashed-diag.rs
Normal file
3
tests/parser/stashed-diag.rs
Normal file
@ -0,0 +1,3 @@
|
||||
#![u={static N;}]
|
||||
|
||||
fn main() {}
|
3
tests/parser/stashed-diag2.rs
Normal file
3
tests/parser/stashed-diag2.rs
Normal file
@ -0,0 +1,3 @@
|
||||
trait Trait<'1> { s> {}
|
||||
|
||||
fn main() {}
|
@ -180,10 +180,11 @@ fn dont_emit_ICE() {
|
||||
"tests/target/issue_5728.rs",
|
||||
"tests/target/issue_5729.rs",
|
||||
"tests/target/issue-5885.rs",
|
||||
"tests/target/issue_6082.rs",
|
||||
"tests/target/issue_6069.rs",
|
||||
"tests/target/issue-6105.rs",
|
||||
];
|
||||
|
||||
|
||||
for file in files {
|
||||
let args = [file];
|
||||
let (_stdout, stderr) = rustfmt(&args);
|
||||
|
@ -1,7 +1,8 @@
|
||||
#![feature(coroutines)]
|
||||
|
||||
unsafe fn foo() {
|
||||
let mut ga = static || {
|
||||
let mut ga = #[coroutine]
|
||||
static || {
|
||||
yield 1;
|
||||
};
|
||||
}
|
||||
|
1
tests/source/macros/rewrite-const-item.rs
Normal file
1
tests/source/macros/rewrite-const-item.rs
Normal file
@ -0,0 +1 @@
|
||||
m!(const N: usize = 0;);
|
10
tests/source/mut_ref.rs
Normal file
10
tests/source/mut_ref.rs
Normal file
@ -0,0 +1,10 @@
|
||||
#![feature(mut_ref)]
|
||||
fn mut_ref() {
|
||||
if let Some(mut /*a*/ ref /*def*/ mut /*abc*/ state)= /*abc*/foo{
|
||||
println!(
|
||||
"asdfasdfasdf"); }
|
||||
|
||||
if let Some(mut /*a*/ ref /*def*/ /*mut*/ state)= /*abc*/foo{
|
||||
println!(
|
||||
"asdfasdfasdf"); }
|
||||
}
|
20
tests/source/postfix-match/pf-match.rs
Normal file
20
tests/source/postfix-match/pf-match.rs
Normal file
@ -0,0 +1,20 @@
|
||||
#![feature(postfix_match)]
|
||||
|
||||
fn main() {
|
||||
let val = Some(42);
|
||||
|
||||
val.match {
|
||||
Some(_) => 2,
|
||||
_ => 1
|
||||
};
|
||||
|
||||
Some(2).match {
|
||||
Some(_) => true,
|
||||
None => false
|
||||
}.match {
|
||||
false => "ferris is cute",
|
||||
true => "I turn cats in to petted cats",
|
||||
}.match {
|
||||
_ => (),
|
||||
}
|
||||
}
|
@ -16,4 +16,16 @@ struct Foo {
|
||||
e: f32,
|
||||
}
|
||||
|
||||
// Test for https://github.com/rust-lang/rust/issues/117942
|
||||
struct Foo {
|
||||
_: union {
|
||||
#[rustfmt::skip]
|
||||
f: String,
|
||||
},
|
||||
#[rustfmt::skip]
|
||||
_: struct {
|
||||
g: i32,
|
||||
},
|
||||
}
|
||||
|
||||
fn main() {}
|
||||
|
3
tests/target/asyncness.rs
Normal file
3
tests/target/asyncness.rs
Normal file
@ -0,0 +1,3 @@
|
||||
// rustfmt-edition: 2018
|
||||
|
||||
fn foo() -> impl async Fn() {}
|
@ -1,7 +1,8 @@
|
||||
#![feature(coroutines)]
|
||||
|
||||
unsafe fn foo() {
|
||||
let mut ga = static || {
|
||||
let mut ga = #[coroutine]
|
||||
static || {
|
||||
yield 1;
|
||||
};
|
||||
}
|
||||
|
5
tests/target/issue_6082.rs
Normal file
5
tests/target/issue_6082.rs
Normal file
@ -0,0 +1,5 @@
|
||||
macro_rules! test {
|
||||
($T:ident, $b:lifetime) => {
|
||||
Box<$T<$b>>
|
||||
};
|
||||
}
|
3
tests/target/issue_6159.rs
Normal file
3
tests/target/issue_6159.rs
Normal file
@ -0,0 +1,3 @@
|
||||
fn main() {
|
||||
builtin # type_ascribe(10, usize)
|
||||
}
|
3
tests/target/macros/rewrite-const-item.rs
Normal file
3
tests/target/macros/rewrite-const-item.rs
Normal file
@ -0,0 +1,3 @@
|
||||
m!(
|
||||
const N: usize = 0;
|
||||
);
|
10
tests/target/mut_ref.rs
Normal file
10
tests/target/mut_ref.rs
Normal file
@ -0,0 +1,10 @@
|
||||
#![feature(mut_ref)]
|
||||
fn mut_ref() {
|
||||
if let Some(mut /*a*/ ref /*def*/ mut /*abc*/ state) = /*abc*/ foo {
|
||||
println!("asdfasdfasdf");
|
||||
}
|
||||
|
||||
if let Some(mut /*a*/ ref /*def*/ /*mut*/ state) = /*abc*/ foo {
|
||||
println!("asdfasdfasdf");
|
||||
}
|
||||
}
|
20
tests/target/postfix-match/pf-match.rs
Normal file
20
tests/target/postfix-match/pf-match.rs
Normal file
@ -0,0 +1,20 @@
|
||||
#![feature(postfix_match)]
|
||||
|
||||
fn main() {
|
||||
let val = Some(42);
|
||||
|
||||
val.match {
|
||||
Some(_) => 2,
|
||||
_ => 1,
|
||||
};
|
||||
|
||||
Some(2).match {
|
||||
Some(_) => true,
|
||||
None => false,
|
||||
}.match {
|
||||
false => "ferris is cute",
|
||||
true => "I turn cats in to petted cats",
|
||||
}.match {
|
||||
_ => (),
|
||||
}
|
||||
}
|
34
tests/target/unsafe_attributes.rs
Normal file
34
tests/target/unsafe_attributes.rs
Normal file
@ -0,0 +1,34 @@
|
||||
#![feature(unsafe_attributes)]
|
||||
// https://github.com/rust-lang/rust/issues/123757
|
||||
//
|
||||
#![simple_ident]
|
||||
#![simple::path]
|
||||
#![simple_ident_expr = ""]
|
||||
#![simple::path::Expr = ""]
|
||||
#![simple_ident_tt(a b c)]
|
||||
#![simple_ident_tt[a b c]]
|
||||
#![simple_ident_tt{a b c}]
|
||||
#![simple::path::tt(a b c)]
|
||||
#![simple::path::tt[a b c]]
|
||||
#![simple::path::tt{a b c}]
|
||||
#![unsafe(simple_ident)]
|
||||
#![unsafe(simple::path)]
|
||||
#![unsafe(simple_ident_expr = "")]
|
||||
#![unsafe(simple::path::Expr = "")]
|
||||
#![unsafe(simple_ident_tt(a b c))]
|
||||
#![unsafe(simple_ident_tt[a b c])]
|
||||
#![unsafe(simple_ident_tt{a b c})]
|
||||
#![unsafe(simple::path::tt(a b c))]
|
||||
#![unsafe(simple::path::tt[a b c])]
|
||||
#![unsafe(simple::path::tt{a b c})]
|
||||
// I don't think `safe` attributes are a thing, but adding these formatting cases here just in case
|
||||
#![safe(simple_ident)]
|
||||
#![safe(simple::path)]
|
||||
#![safe(simple_ident_expr = "")]
|
||||
#![safe(simple::path::Expr = "")]
|
||||
#![safe(simple_ident_tt(a b c))]
|
||||
#![safe(simple_ident_tt[a b c])]
|
||||
#![safe(simple_ident_tt{a b c})]
|
||||
#![safe(simple::path::tt(a b c))]
|
||||
#![safe(simple::path::tt[a b c])]
|
||||
#![safe(simple::path::tt{a b c})]
|
Loading…
x
Reference in New Issue
Block a user