summaryrefslogtreecommitdiffstats
path: root/src/tools/rustfmt/tests
diff options
context:
space:
mode:
Diffstat (limited to 'src/tools/rustfmt/tests')
-rw-r--r--src/tools/rustfmt/tests/rustfmt/main.rs12
-rw-r--r--src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/100.rs40
-rw-r--r--src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/50.rs40
-rw-r--r--src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/zero.rs40
-rw-r--r--src/tools/rustfmt/tests/source/configs/use_small_heuristics/default.rs10
-rw-r--r--src/tools/rustfmt/tests/source/configs/use_small_heuristics/max.rs10
-rw-r--r--src/tools/rustfmt/tests/source/configs/use_small_heuristics/off.rs10
-rw-r--r--src/tools/rustfmt/tests/source/issue-4041.rs5
-rw-r--r--src/tools/rustfmt/tests/source/issue-5234.rs51
-rw-r--r--src/tools/rustfmt/tests/source/issue-5488.rs17
-rw-r--r--src/tools/rustfmt/tests/source/issue-5586.rs164
-rw-r--r--src/tools/rustfmt/tests/source/issue_5686.rs40
-rw-r--r--src/tools/rustfmt/tests/source/itemized-blocks/no_wrap.rs36
-rw-r--r--src/tools/rustfmt/tests/source/itemized-blocks/wrap.rs36
-rw-r--r--src/tools/rustfmt/tests/source/let_else.rs161
-rw-r--r--src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/100.rs60
-rw-r--r--src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/50.rs62
-rw-r--r--src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/zero.rs66
-rw-r--r--src/tools/rustfmt/tests/target/configs/use_small_heuristics/default.rs12
-rw-r--r--src/tools/rustfmt/tests/target/configs/use_small_heuristics/max.rs10
-rw-r--r--src/tools/rustfmt/tests/target/configs/use_small_heuristics/off.rs16
-rw-r--r--src/tools/rustfmt/tests/target/doc-of-generic-item.rs18
-rw-r--r--src/tools/rustfmt/tests/target/issue-4041.rs6
-rw-r--r--src/tools/rustfmt/tests/target/issue-4210-disabled.rs15
-rw-r--r--src/tools/rustfmt/tests/target/issue-4210.rs15
-rw-r--r--src/tools/rustfmt/tests/target/issue-5234.rs47
-rw-r--r--src/tools/rustfmt/tests/target/issue-5488.rs17
-rw-r--r--src/tools/rustfmt/tests/target/issue-5586.rs177
-rw-r--r--src/tools/rustfmt/tests/target/issue_5686.rs42
-rw-r--r--src/tools/rustfmt/tests/target/issue_5691.rs16
-rw-r--r--src/tools/rustfmt/tests/target/issue_5728.rs5
-rw-r--r--src/tools/rustfmt/tests/target/issue_5729.rs5
-rw-r--r--src/tools/rustfmt/tests/target/itemized-blocks/no_wrap.rs36
-rw-r--r--src/tools/rustfmt/tests/target/itemized-blocks/wrap.rs62
-rw-r--r--src/tools/rustfmt/tests/target/let_else.rs253
35 files changed, 1606 insertions, 6 deletions
diff --git a/src/tools/rustfmt/tests/rustfmt/main.rs b/src/tools/rustfmt/tests/rustfmt/main.rs
index 7ff301e80..4936a7174 100644
--- a/src/tools/rustfmt/tests/rustfmt/main.rs
+++ b/src/tools/rustfmt/tests/rustfmt/main.rs
@@ -174,3 +174,15 @@ fn rustfmt_emits_error_on_line_overflow_true() {
"line formatted, but exceeded maximum width (maximum: 100 (see `max_width` option)"
))
}
+
+#[test]
+#[allow(non_snake_case)]
+fn dont_emit_ICE() {
+ let files = ["tests/target/issue_5728.rs", "tests/target/issue_5729.rs"];
+
+ for file in files {
+ let args = [file];
+ let (_stdout, stderr) = rustfmt(&args);
+ assert!(!stderr.contains("thread 'main' panicked"));
+ }
+}
diff --git a/src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/100.rs b/src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/100.rs
new file mode 100644
index 000000000..a73c9084b
--- /dev/null
+++ b/src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/100.rs
@@ -0,0 +1,40 @@
+// rustfmt-single_line_let_else_max_width: 100
+
+fn main() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else { return };
+
+ let Some(c) = opt else {
+ return
+ };
+
+ let Some(c) = opt else {
+ // a comment should always force the block to be multi-lined
+ return
+ };
+
+ let Some(c) = opt else { /* a comment should always force the block to be multi-lined */ return };
+
+ let Some(d) = some_very_very_very_very_long_name else { return };
+
+ let Expr::Slice(ast::ExprSlice { lower, upper, step, range: _ }) = slice.as_ref() else {
+ return
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true)? else {
+ return Ok(None)
+ };
+
+ let Some(doc_attr) = variant.attrs.iter().find(|attr| attr.path().is_ident("doc")) else {
+ return Err(Error::new(variant.span(), r#"expected a doc comment"#))
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true) else {
+ return Ok(None)
+ };
+
+ let Stmt::Expr(Expr::Call(ExprCall { args: some_args, .. }), _) = last_stmt else {
+ return Err(Error::new(last_stmt.span(), "expected last expression to be `Some(match (..) { .. })`"))
+ };
+}
diff --git a/src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/50.rs b/src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/50.rs
new file mode 100644
index 000000000..87d0583c5
--- /dev/null
+++ b/src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/50.rs
@@ -0,0 +1,40 @@
+// rustfmt-single_line_let_else_max_width: 50
+
+fn main() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else { return };
+
+ let Some(c) = opt else {
+ return
+ };
+
+ let Some(c) = opt else {
+ // a comment should always force the block to be multi-lined
+ return
+ };
+
+ let Some(c) = opt else { /* a comment should always force the block to be multi-lined */ return };
+
+ let Some(d) = some_very_very_very_very_long_name else { return };
+
+ let Expr::Slice(ast::ExprSlice { lower, upper, step, range: _ }) = slice.as_ref() else {
+ return
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true)? else {
+ return Ok(None)
+ };
+
+ let Some(doc_attr) = variant.attrs.iter().find(|attr| attr.path().is_ident("doc")) else {
+ return Err(Error::new(variant.span(), r#"expected a doc comment"#))
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true) else {
+ return Ok(None)
+ };
+
+ let Stmt::Expr(Expr::Call(ExprCall { args: some_args, .. }), _) = last_stmt else {
+ return Err(Error::new(last_stmt.span(), "expected last expression to be `Some(match (..) { .. })`"))
+ };
+}
diff --git a/src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/zero.rs b/src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/zero.rs
new file mode 100644
index 000000000..afb9e5033
--- /dev/null
+++ b/src/tools/rustfmt/tests/source/configs/single_line_let_else_max_width/zero.rs
@@ -0,0 +1,40 @@
+// rustfmt-single_line_let_else_max_width: 0
+
+fn main() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else { return };
+
+ let Some(c) = opt else {
+ return
+ };
+
+ let Some(c) = opt else {
+ // a comment should always force the block to be multi-lined
+ return
+ };
+
+ let Some(c) = opt else { /* a comment should always force the block to be multi-lined */ return };
+
+ let Some(d) = some_very_very_very_very_long_name else { return };
+
+ let Expr::Slice(ast::ExprSlice { lower, upper, step, range: _ }) = slice.as_ref() else {
+ return
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true)? else {
+ return Ok(None)
+ };
+
+ let Some(doc_attr) = variant.attrs.iter().find(|attr| attr.path().is_ident("doc")) else {
+ return Err(Error::new(variant.span(), r#"expected a doc comment"#))
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true) else {
+ return Ok(None)
+ };
+
+ let Stmt::Expr(Expr::Call(ExprCall { args: some_args, .. }), _) = last_stmt else {
+ return Err(Error::new(last_stmt.span(), "expected last expression to be `Some(match (..) { .. })`"))
+ };
+}
diff --git a/src/tools/rustfmt/tests/source/configs/use_small_heuristics/default.rs b/src/tools/rustfmt/tests/source/configs/use_small_heuristics/default.rs
index 68bc40271..95238c548 100644
--- a/src/tools/rustfmt/tests/source/configs/use_small_heuristics/default.rs
+++ b/src/tools/rustfmt/tests/source/configs/use_small_heuristics/default.rs
@@ -23,3 +23,13 @@ fn main() {
sit
};
}
+
+fn format_let_else() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else { return };
+
+ let Some(c) = opt else { return };
+
+ let Some(d) = some_very_very_very_very_long_name else { return };
+}
diff --git a/src/tools/rustfmt/tests/source/configs/use_small_heuristics/max.rs b/src/tools/rustfmt/tests/source/configs/use_small_heuristics/max.rs
index 8d30932e2..b79302e22 100644
--- a/src/tools/rustfmt/tests/source/configs/use_small_heuristics/max.rs
+++ b/src/tools/rustfmt/tests/source/configs/use_small_heuristics/max.rs
@@ -23,3 +23,13 @@ fn main() {
sit
};
}
+
+fn format_let_else() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else { return };
+
+ let Some(c) = opt else { return };
+
+ let Some(d) = some_very_very_very_very_long_name else { return };
+}
diff --git a/src/tools/rustfmt/tests/source/configs/use_small_heuristics/off.rs b/src/tools/rustfmt/tests/source/configs/use_small_heuristics/off.rs
index f76392d24..80bcdd898 100644
--- a/src/tools/rustfmt/tests/source/configs/use_small_heuristics/off.rs
+++ b/src/tools/rustfmt/tests/source/configs/use_small_heuristics/off.rs
@@ -23,3 +23,13 @@ fn main() {
sit
};
}
+
+fn format_let_else() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else { return };
+
+ let Some(c) = opt else { return };
+
+ let Some(d) = some_very_very_very_very_long_name else { return };
+}
diff --git a/src/tools/rustfmt/tests/source/issue-4041.rs b/src/tools/rustfmt/tests/source/issue-4041.rs
new file mode 100644
index 000000000..274b80f1b
--- /dev/null
+++ b/src/tools/rustfmt/tests/source/issue-4041.rs
@@ -0,0 +1,5 @@
+// rustfmt-wrap_comments: true
+//! List:
+//! - Sub list:
+//! + very long #1 blah blah blah blah blah blah blah blah blah blah blah blah foo baar baxxxxxxxx long line 1231421230912i3091238192038
+//! + very long #2 blah blah blah blah blah blah blah blah blah blah blah blah
diff --git a/src/tools/rustfmt/tests/source/issue-5234.rs b/src/tools/rustfmt/tests/source/issue-5234.rs
new file mode 100644
index 000000000..67266f485
--- /dev/null
+++ b/src/tools/rustfmt/tests/source/issue-5234.rs
@@ -0,0 +1,51 @@
+// rustfmt-format_code_in_doc_comments: true
+
+/// ```
+/// ```
+fn foo() {}
+
+/// ```
+///Something
+/// ```
+fn foo() {}
+
+/// ```
+///
+/// ```
+fn foo() {}
+
+
+/// /// ```
+fn foo() {}
+
+/// /// ```
+/// ```
+///
+/// ```
+/// ```
+fn foo() {}
+
+fn foo() {
+/// ```
+///
+/// ```
+struct bar {}
+}
+
+/// ```
+/// fn com(){
+/// let i = 5;
+///
+/// let j = 6;
+/// }
+/// ```
+fn foo() {}
+
+fn foo() {
+/// ```
+///fn com(){
+///let i = 5;
+///}
+/// ```
+struct bar {}
+}
diff --git a/src/tools/rustfmt/tests/source/issue-5488.rs b/src/tools/rustfmt/tests/source/issue-5488.rs
new file mode 100644
index 000000000..d361632e2
--- /dev/null
+++ b/src/tools/rustfmt/tests/source/issue-5488.rs
@@ -0,0 +1,17 @@
+// rustfmt-use_field_init_shorthand: true
+
+struct MyStruct(u32);
+struct AnotherStruct {
+ a: u32,
+}
+
+fn main() {
+ // Since MyStruct is a tuple struct, it should not be shorthanded to
+ // MyStruct { 0 } even if use_field_init_shorthand is enabled.
+ let instance = MyStruct { 0: 0 };
+
+ // Since AnotherStruct is not a tuple struct, the shorthand should
+ // apply.
+ let a = 10;
+ let instance = AnotherStruct { a: a };
+}
diff --git a/src/tools/rustfmt/tests/source/issue-5586.rs b/src/tools/rustfmt/tests/source/issue-5586.rs
new file mode 100644
index 000000000..9cf6c1d58
--- /dev/null
+++ b/src/tools/rustfmt/tests/source/issue-5586.rs
@@ -0,0 +1,164 @@
+// rustfmt-version: Two
+fn main() {
+ // sample 1
+ {
+ {
+ {
+ {
+ {
+ let push_ident =
+ if let Some(&node_id) = subgraph_nodes.get(pull_to_push_idx) {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+);
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+
+ // sample 2
+ {
+ {
+ {
+ {
+ {
+ let push_ident = if let Some(&node_id) =
+ subgraph_nodes.get(pull_to_push_idx)
+ {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+
+ // sample 3
+ {
+ {
+ {
+ {
+ {
+ let push_ident =
+ if let Some(&node_id) = subgraph_nodes.get(pull_to_push_idx) {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+
+ // sample 4
+ {{{{{
+ let push_ident =
+ if let Some(&node_id) = subgraph_nodes.get(pull_to_push_idx) {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }}}}}
+
+ // sample 5
+ {
+ {
+ {
+ {
+ {
+ let push_ident =
+ if let Some(&node_id) = subgraph_nodes.get(pull_to_push_idx) {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+
+ // sample 6
+ {
+ {
+ {
+ {
+ {
+ let push_ident = if let Some(&node_id) =
+ subgraph_nodes.get(pull_to_push_idx)
+ {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+
+ // sample 7
+ {
+ {
+ {
+ {
+ {
+ let push_ident =
+ if let Some(&node_id) = subgraph_nodes.get(pull_to_push_idx) {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+}
diff --git a/src/tools/rustfmt/tests/source/issue_5686.rs b/src/tools/rustfmt/tests/source/issue_5686.rs
new file mode 100644
index 000000000..3bf96f73b
--- /dev/null
+++ b/src/tools/rustfmt/tests/source/issue_5686.rs
@@ -0,0 +1,40 @@
+#[repr(u8)]
+enum MyEnum {
+ UnitWithExplicitDiscriminant = 0,
+ EmptyStructSingleLineBlockComment {
+ /* Comment */
+ } = 1,
+ EmptyStructMultiLineBlockComment {
+ /*
+ * Comment
+ */
+ } = 2,
+ EmptyStructLineComment {
+ // comment
+ } = 3,
+ EmptyTupleSingleLineBlockComment(
+ /* Comment */
+ ) = 4,
+ EmptyTupleMultiLineBlockComment(
+ /*
+ * Comment
+ */
+ ) = 5,
+ EmptyTupleLineComment(
+ // comment
+ ) = 6,
+}
+
+enum Animal {
+ Dog(/* tuple variant closer in comment -> ) */) = 1,
+ #[hello(world)]
+ Cat(/* tuple variant close in leading attribute */) = 2,
+ Bee(/* tuple variant closer on associated field attribute */ #[hello(world)] usize) = 3,
+ Fox(/* tuple variant closer on const fn call */) = some_const_fn(),
+ Ant(/* tuple variant closer on macro call */) = some_macro!(),
+ Snake {/* stuct variant closer in comment -> } */} = 6,
+ #[hell{world}]
+ Cobra {/* struct variant close in leading attribute */} = 6,
+ Eagle {/* struct variant closer on associated field attribute */ #[hell{world}]value: Sting} = 7,
+ Koala {/* struct variant closer on macro call */} = some_macro!{}
+}
diff --git a/src/tools/rustfmt/tests/source/itemized-blocks/no_wrap.rs b/src/tools/rustfmt/tests/source/itemized-blocks/no_wrap.rs
index a7b6a10a0..e5699e766 100644
--- a/src/tools/rustfmt/tests/source/itemized-blocks/no_wrap.rs
+++ b/src/tools/rustfmt/tests/source/itemized-blocks/no_wrap.rs
@@ -1,7 +1,7 @@
// rustfmt-normalize_comments: true
// rustfmt-format_code_in_doc_comments: true
-//! This is a list:
+//! This is an itemized markdown list (see also issue #3224):
//! * Outer
//! * Outer
//! * Inner
@@ -13,6 +13,40 @@
//! - when the log level is info, the level name is green and the rest of the line is white
//! - when the log level is debug, the whole line is white
//! - when the log level is trace, the whole line is gray ("bright black")
+//!
+//! This is a numbered markdown list (see also issue #5416):
+//! 1. Long long long long long long long long long long long long long long long long long line
+//! 2. Another very long long long long long long long long long long long long long long long line
+//! 3. Nested list
+//! 1. Long long long long long long long long long long long long long long long long line
+//! 2. Another very long long long long long long long long long long long long long long line
+//! 4. Last item
+//!
+//! Using the ')' instead of '.' character after the number:
+//! 1) Long long long long long long long long long long long long long long long long long line
+//! 2) Another very long long long long long long long long long long long long long long long line
+//!
+//! Deep list that mixes various bullet and number formats:
+//! 1. First level with a long long long long long long long long long long long long long long
+//! long long long line
+//! 2. First level with another very long long long long long long long long long long long long
+//! long long long line
+//! * Second level with a long long long long long long long long long long long long long
+//! long long long line
+//! * Second level with another very long long long long long long long long long long long
+//! long long long line
+//! 1) Third level with a long long long long long long long long long long long long long
+//! long long long line
+//! 2) Third level with another very long long long long long long long long long long
+//! long long long long line
+//! - Forth level with a long long long long long long long long long long long long
+//! long long long long line
+//! - Forth level with another very long long long long long long long long long long
+//! long long long long line
+//! 3) One more item at the third level
+//! 4) Last item of the third level
+//! * Last item of second level
+//! 3. Last item of first level
/// All the parameters ***except for `from_theater`*** should be inserted as sent by the remote
/// theater, i.e., as passed to [`Theater::send`] on the remote actor:
diff --git a/src/tools/rustfmt/tests/source/itemized-blocks/wrap.rs b/src/tools/rustfmt/tests/source/itemized-blocks/wrap.rs
index 955cc698b..768461a43 100644
--- a/src/tools/rustfmt/tests/source/itemized-blocks/wrap.rs
+++ b/src/tools/rustfmt/tests/source/itemized-blocks/wrap.rs
@@ -2,7 +2,7 @@
// rustfmt-format_code_in_doc_comments: true
// rustfmt-max_width: 50
-//! This is a list:
+//! This is an itemized markdown list (see also issue #3224):
//! * Outer
//! * Outer
//! * Inner
@@ -14,6 +14,40 @@
//! - when the log level is info, the level name is green and the rest of the line is white
//! - when the log level is debug, the whole line is white
//! - when the log level is trace, the whole line is gray ("bright black")
+//!
+//! This is a numbered markdown list (see also issue #5416):
+//! 1. Long long long long long long long long long long long long long long long long long line
+//! 2. Another very long long long long long long long long long long long long long long long line
+//! 3. Nested list
+//! 1. Long long long long long long long long long long long long long long long long line
+//! 2. Another very long long long long long long long long long long long long long long line
+//! 4. Last item
+//!
+//! Using the ')' instead of '.' character after the number:
+//! 1) Long long long long long long long long long long long long long long long long long line
+//! 2) Another very long long long long long long long long long long long long long long long line
+//!
+//! Deep list that mixes various bullet and number formats:
+//! 1. First level with a long long long long long long long long long long long long long long
+//! long long long line
+//! 2. First level with another very long long long long long long long long long long long long
+//! long long long line
+//! * Second level with a long long long long long long long long long long long long long
+//! long long long line
+//! * Second level with another very long long long long long long long long long long long
+//! long long long line
+//! 1) Third level with a long long long long long long long long long long long long long
+//! long long long line
+//! 2) Third level with another very long long long long long long long long long long
+//! long long long long line
+//! - Forth level with a long long long long long long long long long long long long
+//! long long long long line
+//! - Forth level with another very long long long long long long long long long long
+//! long long long long line
+//! 3) One more item at the third level
+//! 4) Last item of the third level
+//! * Last item of second level
+//! 3. Last item of first level
// This example shows how to configure fern to output really nicely colored logs
// - when the log level is error, the whole line is red
diff --git a/src/tools/rustfmt/tests/source/let_else.rs b/src/tools/rustfmt/tests/source/let_else.rs
index a6e816fb5..85b3604ad 100644
--- a/src/tools/rustfmt/tests/source/let_else.rs
+++ b/src/tools/rustfmt/tests/source/let_else.rs
@@ -1,3 +1,162 @@
+// rustfmt-single_line_let_else_max_width: 100
+
fn main() {
- let Some(1) = Some(1) else { return };
+ // Although this won't compile it still parses so make sure we can format empty else blocks
+ let Some(x) = opt else {};
+
+ // let-else may be formatted on a single line if they are "short"
+ // and only contain a single expression
+ let Some(x) = opt else { return };
+
+ let Some(x) = opt else {
+ return
+ };
+
+ let Some(x) = opt else { return; };
+
+ let Some(x) = opt else {
+ // nope
+ return;
+ };
+
+ let Some(x) = opt else { let y = 1; return y };
+
+ let Some(x) = y.foo("abc", fairly_long_identifier, "def", "123456", "string", "cheese") else { bar() };
+
+ let Some(x) = abcdef().foo("abc", some_really_really_really_long_ident, "ident", "123456").bar().baz().qux("fffffffffffffffff") else { foo_bar() };
+}
+
+fn with_comments_around_else_keyword() {
+ let Some(x) = opt /* pre else keyword block-comment */ else { return };
+
+ let Some(x) = opt else /* post else keyword block-comment */ { return };
+
+ let Some(x) = opt /* pre else keyword block-comment */ else /* post else keyword block-comment */ { return };
+
+ let Some(x) = opt // pre else keyword line-comment
+ else { return };
+
+ let Some(x) = opt else
+ // post else keyword line-comment
+ { return };
+
+ let Some(x) = opt // pre else keyword line-comment
+ else
+ // post else keyword line-comment
+ { return };
+
+}
+
+fn unbreakable_initializer_expr_pre_formatting_let_else_length_near_max_width() {
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else block;` is 100 (max_width)
+ // Post Formatting:
+ // The formatting is left unchanged!
+ let Some(x) = some_really_really_really_really_really_really_really_long_name_A else { return };
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else block;` is 100 (max_width)
+ // Post Formatting:
+ // The else keyword and opening brace remain on the same line as the initializer expr,
+ // and the else block is formatted over multiple lines because we can't fit the
+ // else block on the same line as the initializer expr.
+ let Some(x) = some_really_really_really_really_really_really_really_long_name___B else {return};
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else block;` is 100 (max_width)
+ // Post Formatting:
+ // The else keyword and opening brace remain on the same line as the initializer expr,
+ // and the else block is formatted over multiple lines because we can't fit the
+ // else block on the same line as the initializer expr.
+ let Some(x) = some_really_really_really_really_long_name_____C else {some_divergent_function()};
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else block;` is 101 (> max_width)
+ // Post Formatting:
+ // The else keyword and opening brace remain on the same line as the initializer expr,
+ // and the else block is formatted over multiple lines because we can't fit the
+ // else block on the same line as the initializer expr.
+ let Some(x) = some_really_really_really_really_really_really_really_long_name__D else { return };
+}
+
+fn unbreakable_initializer_expr_pre_formatting_length_up_to_opening_brace_near_max_width() {
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else {` is 99 (< max_width)
+ // Post Formatting:
+ // The else keyword and opening brace remain on the same line as the initializer expr,
+ // and the else block is formatted over multiple lines because we can't fit the
+ // else block on the same line as the initializer expr.
+ let Some(x) = some_really_really_really_really_really_really_really_really_long_name___E else {return};
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else {` is 101 (> max_width)
+ // Post Formatting:
+ // The else keyword and opening brace cannot fit on the same line as the initializer expr.
+ // They are formatted on the next line.
+ let Some(x) = some_really_really_really_really_really_really_really_really_long_name_____F else {return};
+}
+
+fn unbreakable_initializer_expr_pre_formatting_length_through_initializer_expr_near_max_width() {
+ // Pre Formatting:
+ // The length of `(indent)let pat = init` is 99 (< max_width)
+ // Post Formatting:
+ // The else keyword and opening brace cannot fit on the same line as the initializer expr.
+ // They are formatted on the next line.
+ let Some(x) = some_really_really_really_really_really_really_really_really_really_long_name___G else {return};
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init` is 100 (max_width)
+ // Post Formatting:
+ // Break after the `=` and put the initializer expr on it's own line.
+ // Because the initializer expr is multi-lined the else is placed on it's own line.
+ let Some(x) = some_really_really_really_really_really_really_really_really_really_long_name____H else {return};
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init` is 109 (> max_width)
+ // Post Formatting:
+ // Break after the `=` and put the initializer expr on it's own line.
+ // Because the initializer expr is multi-lined the else is placed on it's own line.
+ // The initializer expr has a length of 91, which when indented on the next line
+ // The `(indent)init` line has a lengh of 99. This is the max length that the `init` can be
+ // before we start running into max_width issues. I suspect this is becuase the shape is
+ // accounting for the `;` at the end of the `let-else` statement.
+ let Some(x) = some_really_really_really_really_really_really_really_really_really_really_long_name______I else {return};
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init` is 110 (> max_width)
+ // Post Formatting:
+ // Max length issues prevent us from formatting.
+ // The initializer expr has a length of 92, which if it would be indented on the next line
+ // the `(indent)init` line has a lengh of 100 which == max_width of 100.
+ // One might expect formatting to succeed, but I suspect the reason we hit max_width issues is
+ // because the Shape is accounting for the `;` at the end of the `let-else` statement.
+ let Some(x) = some_really_really_really_really_really_really_really_really_really_really_really_long_nameJ else {return};
+}
+
+fn long_patterns() {
+ let Foo {x: Bar(..), y: FooBar(..), z: Baz(..)} = opt else {
+ return;
+ };
+
+ // with version=One we don't wrap long array patterns
+ let [aaaaaaaaaaaaaaaa, bbbbbbbbbbbbbbb, cccccccccccccccccc, dddddddddddddddddd] = opt else {
+ return;
+ };
+
+ let ("aaaaaaaaaaaaaaaaaaa" | "bbbbbbbbbbbbbbbbb" | "cccccccccccccccccccccccc" | "dddddddddddddddd" | "eeeeeeeeeeeeeeee") = opt else {
+ return;
+ };
+
+ let Some(Ok((Message::ChangeColor(super::color::Color::Rgb(r, g, b)), Point { x, y, z }))) = opt else {
+ return;
+ };
+}
+
+fn with_trailing_try_operator() {
+ // Currently the trailing ? forces the else on the next line
+ // This may be revisited in style edition 2024
+ let Some(next_bucket) = ranking_rules[cur_ranking_rule_index].next_bucket(ctx, logger, &ranking_rule_universes[cur_ranking_rule_index])? else { return };
+
+ // Maybe this is a workaround?
+ let Ok(Some(next_bucket)) = ranking_rules[cur_ranking_rule_index].next_bucket(ctx, logger, &ranking_rule_universes[cur_ranking_rule_index]) else { return };
}
diff --git a/src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/100.rs b/src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/100.rs
new file mode 100644
index 000000000..0409124a5
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/100.rs
@@ -0,0 +1,60 @@
+// rustfmt-single_line_let_else_max_width: 100
+
+fn main() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else { return };
+
+ let Some(c) = opt else { return };
+
+ let Some(c) = opt else {
+ // a comment should always force the block to be multi-lined
+ return;
+ };
+
+ let Some(c) = opt else {
+ /* a comment should always force the block to be multi-lined */
+ return;
+ };
+
+ let Some(d) = some_very_very_very_very_long_name else { return };
+
+ let Expr::Slice(ast::ExprSlice {
+ lower,
+ upper,
+ step,
+ range: _,
+ }) = slice.as_ref()
+ else {
+ return;
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true)? else {
+ return Ok(None);
+ };
+
+ let Some(doc_attr) = variant
+ .attrs
+ .iter()
+ .find(|attr| attr.path().is_ident("doc"))
+ else {
+ return Err(Error::new(variant.span(), r#"expected a doc comment"#));
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true) else {
+ return Ok(None);
+ };
+
+ let Stmt::Expr(
+ Expr::Call(ExprCall {
+ args: some_args, ..
+ }),
+ _,
+ ) = last_stmt
+ else {
+ return Err(Error::new(
+ last_stmt.span(),
+ "expected last expression to be `Some(match (..) { .. })`",
+ ));
+ };
+}
diff --git a/src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/50.rs b/src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/50.rs
new file mode 100644
index 000000000..6afc2b6f2
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/50.rs
@@ -0,0 +1,62 @@
+// rustfmt-single_line_let_else_max_width: 50
+
+fn main() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else { return };
+
+ let Some(c) = opt else { return };
+
+ let Some(c) = opt else {
+ // a comment should always force the block to be multi-lined
+ return;
+ };
+
+ let Some(c) = opt else {
+ /* a comment should always force the block to be multi-lined */
+ return;
+ };
+
+ let Some(d) = some_very_very_very_very_long_name else {
+ return;
+ };
+
+ let Expr::Slice(ast::ExprSlice {
+ lower,
+ upper,
+ step,
+ range: _,
+ }) = slice.as_ref()
+ else {
+ return;
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true)? else {
+ return Ok(None);
+ };
+
+ let Some(doc_attr) = variant
+ .attrs
+ .iter()
+ .find(|attr| attr.path().is_ident("doc"))
+ else {
+ return Err(Error::new(variant.span(), r#"expected a doc comment"#));
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true) else {
+ return Ok(None);
+ };
+
+ let Stmt::Expr(
+ Expr::Call(ExprCall {
+ args: some_args, ..
+ }),
+ _,
+ ) = last_stmt
+ else {
+ return Err(Error::new(
+ last_stmt.span(),
+ "expected last expression to be `Some(match (..) { .. })`",
+ ));
+ };
+}
diff --git a/src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/zero.rs b/src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/zero.rs
new file mode 100644
index 000000000..b5fd0b9ed
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/configs/single_line_let_else_max_width/zero.rs
@@ -0,0 +1,66 @@
+// rustfmt-single_line_let_else_max_width: 0
+
+fn main() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else {
+ return;
+ };
+
+ let Some(c) = opt else {
+ return;
+ };
+
+ let Some(c) = opt else {
+ // a comment should always force the block to be multi-lined
+ return;
+ };
+
+ let Some(c) = opt else {
+ /* a comment should always force the block to be multi-lined */
+ return;
+ };
+
+ let Some(d) = some_very_very_very_very_long_name else {
+ return;
+ };
+
+ let Expr::Slice(ast::ExprSlice {
+ lower,
+ upper,
+ step,
+ range: _,
+ }) = slice.as_ref()
+ else {
+ return;
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true)? else {
+ return Ok(None);
+ };
+
+ let Some(doc_attr) = variant
+ .attrs
+ .iter()
+ .find(|attr| attr.path().is_ident("doc"))
+ else {
+ return Err(Error::new(variant.span(), r#"expected a doc comment"#));
+ };
+
+ let Some((base_place, current)) = self.lower_expr_as_place(current, *base, true) else {
+ return Ok(None);
+ };
+
+ let Stmt::Expr(
+ Expr::Call(ExprCall {
+ args: some_args, ..
+ }),
+ _,
+ ) = last_stmt
+ else {
+ return Err(Error::new(
+ last_stmt.span(),
+ "expected last expression to be `Some(match (..) { .. })`",
+ ));
+ };
+}
diff --git a/src/tools/rustfmt/tests/target/configs/use_small_heuristics/default.rs b/src/tools/rustfmt/tests/target/configs/use_small_heuristics/default.rs
index d67bd9aaf..ad4073923 100644
--- a/src/tools/rustfmt/tests/target/configs/use_small_heuristics/default.rs
+++ b/src/tools/rustfmt/tests/target/configs/use_small_heuristics/default.rs
@@ -24,3 +24,15 @@ fn main() {
let lorem = if ipsum { dolor } else { sit };
}
+
+fn format_let_else() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else { return };
+
+ let Some(c) = opt else { return };
+
+ let Some(d) = some_very_very_very_very_long_name else {
+ return;
+ };
+}
diff --git a/src/tools/rustfmt/tests/target/configs/use_small_heuristics/max.rs b/src/tools/rustfmt/tests/target/configs/use_small_heuristics/max.rs
index 785dfbea0..fe57f853d 100644
--- a/src/tools/rustfmt/tests/target/configs/use_small_heuristics/max.rs
+++ b/src/tools/rustfmt/tests/target/configs/use_small_heuristics/max.rs
@@ -13,3 +13,13 @@ fn main() {
let lorem = if ipsum { dolor } else { sit };
}
+
+fn format_let_else() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else { return };
+
+ let Some(c) = opt else { return };
+
+ let Some(d) = some_very_very_very_very_long_name else { return };
+}
diff --git a/src/tools/rustfmt/tests/target/configs/use_small_heuristics/off.rs b/src/tools/rustfmt/tests/target/configs/use_small_heuristics/off.rs
index f76392d24..b0b4e4ee4 100644
--- a/src/tools/rustfmt/tests/target/configs/use_small_heuristics/off.rs
+++ b/src/tools/rustfmt/tests/target/configs/use_small_heuristics/off.rs
@@ -23,3 +23,19 @@ fn main() {
sit
};
}
+
+fn format_let_else() {
+ let Some(a) = opt else {};
+
+ let Some(b) = opt else {
+ return;
+ };
+
+ let Some(c) = opt else {
+ return;
+ };
+
+ let Some(d) = some_very_very_very_very_long_name else {
+ return;
+ };
+}
diff --git a/src/tools/rustfmt/tests/target/doc-of-generic-item.rs b/src/tools/rustfmt/tests/target/doc-of-generic-item.rs
index 2efc5e09a..80886e74f 100644
--- a/src/tools/rustfmt/tests/target/doc-of-generic-item.rs
+++ b/src/tools/rustfmt/tests/target/doc-of-generic-item.rs
@@ -12,3 +12,21 @@ struct Foo<
/// doc of N
const N: item,
>;
+
+// Non-doc pre-comment of Foo
+/// doc of Foo
+// Non-doc post-comment of Foo
+struct Foo<
+ // Non-doc pre-comment of 'a
+ /// doc of 'a
+ // Non-doc post-comment of 'a
+ 'a,
+ // Non-doc pre-comment of T
+ /// doc of T
+ // Non-doc post-comment of T
+ T,
+ // Non-doc pre-comment of N
+ /// doc of N
+ // Non-doc post-comment of N
+ const N: item,
+>;
diff --git a/src/tools/rustfmt/tests/target/issue-4041.rs b/src/tools/rustfmt/tests/target/issue-4041.rs
new file mode 100644
index 000000000..e9c693836
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/issue-4041.rs
@@ -0,0 +1,6 @@
+// rustfmt-wrap_comments: true
+//! List:
+//! - Sub list:
+//! + very long #1 blah blah blah blah blah blah blah blah blah blah blah blah
+//! foo baar baxxxxxxxx long line 1231421230912i3091238192038
+//! + very long #2 blah blah blah blah blah blah blah blah blah blah blah blah
diff --git a/src/tools/rustfmt/tests/target/issue-4210-disabled.rs b/src/tools/rustfmt/tests/target/issue-4210-disabled.rs
new file mode 100644
index 000000000..3ba87aab8
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/issue-4210-disabled.rs
@@ -0,0 +1,15 @@
+// rustfmt-wrap_comments: false
+
+/// Table that is > 80 symbols:
+///
+/// | table | xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx |
+/// |-------|-----------------------------------------------------------------------------|
+/// | val | x |
+pub struct Item;
+
+/// Table value that is > 80 symbols:
+///
+/// | table | heading
+/// |----------|-----------------------------------------------------------------------------
+/// | long val | Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
+pub struct Item2;
diff --git a/src/tools/rustfmt/tests/target/issue-4210.rs b/src/tools/rustfmt/tests/target/issue-4210.rs
new file mode 100644
index 000000000..3fd966390
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/issue-4210.rs
@@ -0,0 +1,15 @@
+// rustfmt-wrap_comments: true
+
+/// Table that is > 80 symbols:
+///
+/// | table | xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx |
+/// |-------|-----------------------------------------------------------------------------|
+/// | val | x |
+pub struct Item;
+
+/// Table value that is > 80 symbols:
+///
+/// | table | heading
+/// |----------|-----------------------------------------------------------------------------
+/// | long val | Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
+pub struct Item2;
diff --git a/src/tools/rustfmt/tests/target/issue-5234.rs b/src/tools/rustfmt/tests/target/issue-5234.rs
new file mode 100644
index 000000000..7ee9e46d1
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/issue-5234.rs
@@ -0,0 +1,47 @@
+// rustfmt-format_code_in_doc_comments: true
+
+/// ```
+/// ```
+fn foo() {}
+
+/// ```
+/// Something
+/// ```
+fn foo() {}
+
+/// ```
+/// ```
+fn foo() {}
+
+/// /// ```
+fn foo() {}
+
+/// /// ```
+/// ```
+/// ```
+/// ```
+fn foo() {}
+
+fn foo() {
+ /// ```
+ /// ```
+ struct bar {}
+}
+
+/// ```
+/// fn com() {
+/// let i = 5;
+///
+/// let j = 6;
+/// }
+/// ```
+fn foo() {}
+
+fn foo() {
+ /// ```
+ /// fn com() {
+ /// let i = 5;
+ /// }
+ /// ```
+ struct bar {}
+}
diff --git a/src/tools/rustfmt/tests/target/issue-5488.rs b/src/tools/rustfmt/tests/target/issue-5488.rs
new file mode 100644
index 000000000..0cb37c56f
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/issue-5488.rs
@@ -0,0 +1,17 @@
+// rustfmt-use_field_init_shorthand: true
+
+struct MyStruct(u32);
+struct AnotherStruct {
+ a: u32,
+}
+
+fn main() {
+ // Since MyStruct is a tuple struct, it should not be shorthanded to
+ // MyStruct { 0 } even if use_field_init_shorthand is enabled.
+ let instance = MyStruct { 0: 0 };
+
+ // Since AnotherStruct is not a tuple struct, the shorthand should
+ // apply.
+ let a = 10;
+ let instance = AnotherStruct { a };
+}
diff --git a/src/tools/rustfmt/tests/target/issue-5586.rs b/src/tools/rustfmt/tests/target/issue-5586.rs
new file mode 100644
index 000000000..7033ae975
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/issue-5586.rs
@@ -0,0 +1,177 @@
+// rustfmt-version: Two
+fn main() {
+ // sample 1
+ {
+ {
+ {
+ {
+ {
+ let push_ident = if let Some(&node_id) =
+ subgraph_nodes.get(pull_to_push_idx)
+ {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+
+ // sample 2
+ {
+ {
+ {
+ {
+ {
+ let push_ident = if let Some(&node_id) =
+ subgraph_nodes.get(pull_to_push_idx)
+ {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+
+ // sample 3
+ {
+ {
+ {
+ {
+ {
+ let push_ident = if let Some(&node_id) =
+ subgraph_nodes.get(pull_to_push_idx)
+ {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+
+ // sample 4
+ {
+ {
+ {
+ {
+ {
+ let push_ident = if let Some(&node_id) =
+ subgraph_nodes.get(pull_to_push_idx)
+ {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+
+ // sample 5
+ {
+ {
+ {
+ {
+ {
+ let push_ident = if let Some(&node_id) =
+ subgraph_nodes.get(pull_to_push_idx)
+ {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+
+ // sample 6
+ {
+ {
+ {
+ {
+ {
+ let push_ident = if let Some(&node_id) =
+ subgraph_nodes.get(pull_to_push_idx)
+ {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+
+ // sample 7
+ {
+ {
+ {
+ {
+ {
+ let push_ident = if let Some(&node_id) =
+ subgraph_nodes.get(pull_to_push_idx)
+ {
+ self.node_id_as_ident(node_id, false)
+ } else {
+ // Entire subgraph is pull (except for a single send/push handoff output).
+ assert_eq!(
+ 1,
+ send_ports.len(),
+ "If entire subgraph is pull, should have only one handoff output."
+ );
+ send_ports[0].clone()
+ };
+ }
+ }
+ }
+ }
+ }
+}
diff --git a/src/tools/rustfmt/tests/target/issue_5686.rs b/src/tools/rustfmt/tests/target/issue_5686.rs
new file mode 100644
index 000000000..993f12b53
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/issue_5686.rs
@@ -0,0 +1,42 @@
+#[repr(u8)]
+enum MyEnum {
+ UnitWithExplicitDiscriminant = 0,
+ EmptyStructSingleLineBlockComment {/* Comment */} = 1,
+ EmptyStructMultiLineBlockComment {
+ /*
+ * Comment
+ */
+ } = 2,
+ EmptyStructLineComment {
+ // comment
+ } = 3,
+ EmptyTupleSingleLineBlockComment(/* Comment */) = 4,
+ EmptyTupleMultiLineBlockComment(
+ /*
+ * Comment
+ */
+ ) = 5,
+ EmptyTupleLineComment(
+ // comment
+ ) = 6,
+}
+
+enum Animal {
+ Dog(/* tuple variant closer in comment -> ) */) = 1,
+ #[hello(world)]
+ Cat(/* tuple variant close in leading attribute */) = 2,
+ Bee(
+ /* tuple variant closer on associated field attribute */ #[hello(world)] usize,
+ ) = 3,
+ Fox(/* tuple variant closer on const fn call */) = some_const_fn(),
+ Ant(/* tuple variant closer on macro call */) = some_macro!(),
+ Snake {/* stuct variant closer in comment -> } */} = 6,
+ #[hell{world}]
+ Cobra {/* struct variant close in leading attribute */} = 6,
+ Eagle {
+ /* struct variant closer on associated field attribute */
+ #[hell{world}]
+ value: Sting,
+ } = 7,
+ Koala {/* struct variant closer on macro call */} = some_macro! {},
+}
diff --git a/src/tools/rustfmt/tests/target/issue_5691.rs b/src/tools/rustfmt/tests/target/issue_5691.rs
new file mode 100644
index 000000000..e3aad15db
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/issue_5691.rs
@@ -0,0 +1,16 @@
+struct S<const C: usize>
+where
+ [(); { num_slots!(C) }]:, {
+ /* An asterisk-based, or a double-slash-prefixed, comment here is
+ required to trigger the fmt bug.
+
+ A single-line triple-slash-prefixed comment (with a field following it) is not enough - it will not trigger the fmt bug.
+
+ Side note: If you have a combination of two, or all three of the
+ above mentioned types of comments here, some of them disappear
+ after `cargo fmt`.
+
+ The bug gets triggered even if a field definition following the
+ (asterisk-based, or a double-slash-prefixed) comment, too.
+ */
+}
diff --git a/src/tools/rustfmt/tests/target/issue_5728.rs b/src/tools/rustfmt/tests/target/issue_5728.rs
new file mode 100644
index 000000000..e1355416f
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/issue_5728.rs
@@ -0,0 +1,5 @@
+cfg_if::cfg_if! {
+ if #[cfg(windows)] {
+ } else if #(&cpus) {
+ } else [libc::CTL_HW, libc::HW_NCPU, 0, 0]
+}
diff --git a/src/tools/rustfmt/tests/target/issue_5729.rs b/src/tools/rustfmt/tests/target/issue_5729.rs
new file mode 100644
index 000000000..d63c83e88
--- /dev/null
+++ b/src/tools/rustfmt/tests/target/issue_5729.rs
@@ -0,0 +1,5 @@
+cfg_if::cfg_if! {
+ if {
+ } else if #(&cpus) {
+ } else [libc::CTL_HW, libc::HW_NCPU, 0, 0]
+}
diff --git a/src/tools/rustfmt/tests/target/itemized-blocks/no_wrap.rs b/src/tools/rustfmt/tests/target/itemized-blocks/no_wrap.rs
index de8856382..86818b447 100644
--- a/src/tools/rustfmt/tests/target/itemized-blocks/no_wrap.rs
+++ b/src/tools/rustfmt/tests/target/itemized-blocks/no_wrap.rs
@@ -1,7 +1,7 @@
// rustfmt-normalize_comments: true
// rustfmt-format_code_in_doc_comments: true
-//! This is a list:
+//! This is an itemized markdown list (see also issue #3224):
//! * Outer
//! * Outer
//! * Inner
@@ -13,6 +13,40 @@
//! - when the log level is info, the level name is green and the rest of the line is white
//! - when the log level is debug, the whole line is white
//! - when the log level is trace, the whole line is gray ("bright black")
+//!
+//! This is a numbered markdown list (see also issue #5416):
+//! 1. Long long long long long long long long long long long long long long long long long line
+//! 2. Another very long long long long long long long long long long long long long long long line
+//! 3. Nested list
+//! 1. Long long long long long long long long long long long long long long long long line
+//! 2. Another very long long long long long long long long long long long long long long line
+//! 4. Last item
+//!
+//! Using the ')' instead of '.' character after the number:
+//! 1) Long long long long long long long long long long long long long long long long long line
+//! 2) Another very long long long long long long long long long long long long long long long line
+//!
+//! Deep list that mixes various bullet and number formats:
+//! 1. First level with a long long long long long long long long long long long long long long
+//! long long long line
+//! 2. First level with another very long long long long long long long long long long long long
+//! long long long line
+//! * Second level with a long long long long long long long long long long long long long
+//! long long long line
+//! * Second level with another very long long long long long long long long long long long
+//! long long long line
+//! 1) Third level with a long long long long long long long long long long long long long
+//! long long long line
+//! 2) Third level with another very long long long long long long long long long long
+//! long long long long line
+//! - Forth level with a long long long long long long long long long long long long
+//! long long long long line
+//! - Forth level with another very long long long long long long long long long long
+//! long long long long line
+//! 3) One more item at the third level
+//! 4) Last item of the third level
+//! * Last item of second level
+//! 3. Last item of first level
/// All the parameters ***except for `from_theater`*** should be inserted as sent by the remote
/// theater, i.e., as passed to [`Theater::send`] on the remote actor:
diff --git a/src/tools/rustfmt/tests/target/itemized-blocks/wrap.rs b/src/tools/rustfmt/tests/target/itemized-blocks/wrap.rs
index a4907303c..4826590ea 100644
--- a/src/tools/rustfmt/tests/target/itemized-blocks/wrap.rs
+++ b/src/tools/rustfmt/tests/target/itemized-blocks/wrap.rs
@@ -2,7 +2,8 @@
// rustfmt-format_code_in_doc_comments: true
// rustfmt-max_width: 50
-//! This is a list:
+//! This is an itemized markdown list (see also
+//! issue #3224):
//! * Outer
//! * Outer
//! * Inner
@@ -23,6 +24,65 @@
//! is white
//! - when the log level is trace, the whole line
//! is gray ("bright black")
+//!
+//! This is a numbered markdown list (see also
+//! issue #5416):
+//! 1. Long long long long long long long long
+//! long long long long long long long long
+//! long line
+//! 2. Another very long long long long long long
+//! long long long long long long long long
+//! long line
+//! 3. Nested list
+//! 1. Long long long long long long long long
+//! long long long long long long long long
+//! line
+//! 2. Another very long long long long long
+//! long long long long long long long long
+//! long line
+//! 4. Last item
+//!
+//! Using the ')' instead of '.' character after
+//! the number:
+//! 1) Long long long long long long long long
+//! long long long long long long long long
+//! long line
+//! 2) Another very long long long long long long
+//! long long long long long long long long
+//! long line
+//!
+//! Deep list that mixes various bullet and number
+//! formats:
+//! 1. First level with a long long long long long
+//! long long long long long long long long
+//! long long long long line
+//! 2. First level with another very long long
+//! long long long long long long long long
+//! long long long long long line
+//! * Second level with a long long long long
+//! long long long long long long long long
+//! long long long long line
+//! * Second level with another very long long
+//! long long long long long long long long
+//! long long long long line
+//! 1) Third level with a long long long
+//! long long long long long long long
+//! long long long long long long line
+//! 2) Third level with another very long
+//! long long long long long long long
+//! long long long long long long line
+//! - Forth level with a long long
+//! long long long long long long
+//! long long long long long long
+//! long long line
+//! - Forth level with another very
+//! long long long long long long
+//! long long long long long long
+//! long long line
+//! 3) One more item at the third level
+//! 4) Last item of the third level
+//! * Last item of second level
+//! 3. Last item of first level
// This example shows how to configure fern to
// output really nicely colored logs
diff --git a/src/tools/rustfmt/tests/target/let_else.rs b/src/tools/rustfmt/tests/target/let_else.rs
index a6e816fb5..6554a0961 100644
--- a/src/tools/rustfmt/tests/target/let_else.rs
+++ b/src/tools/rustfmt/tests/target/let_else.rs
@@ -1,3 +1,254 @@
+// rustfmt-single_line_let_else_max_width: 100
+
fn main() {
- let Some(1) = Some(1) else { return };
+ // Although this won't compile it still parses so make sure we can format empty else blocks
+ let Some(x) = opt else {};
+
+ // let-else may be formatted on a single line if they are "short"
+ // and only contain a single expression
+ let Some(x) = opt else { return };
+
+ let Some(x) = opt else { return };
+
+ let Some(x) = opt else {
+ return;
+ };
+
+ let Some(x) = opt else {
+ // nope
+ return;
+ };
+
+ let Some(x) = opt else {
+ let y = 1;
+ return y;
+ };
+
+ let Some(x) = y.foo(
+ "abc",
+ fairly_long_identifier,
+ "def",
+ "123456",
+ "string",
+ "cheese",
+ ) else {
+ bar()
+ };
+
+ let Some(x) = abcdef()
+ .foo(
+ "abc",
+ some_really_really_really_long_ident,
+ "ident",
+ "123456",
+ )
+ .bar()
+ .baz()
+ .qux("fffffffffffffffff")
+ else {
+ foo_bar()
+ };
+}
+
+fn with_comments_around_else_keyword() {
+ let Some(x) = opt
+ /* pre else keyword block-comment */
+ else {
+ return;
+ };
+
+ let Some(x) = opt else
+ /* post else keyword block-comment */
+ {
+ return;
+ };
+
+ let Some(x) = opt
+ /* pre else keyword block-comment */
+ else
+ /* post else keyword block-comment */
+ {
+ return;
+ };
+
+ let Some(x) = opt
+ // pre else keyword line-comment
+ else {
+ return;
+ };
+
+ let Some(x) = opt else
+ // post else keyword line-comment
+ {
+ return;
+ };
+
+ let Some(x) = opt
+ // pre else keyword line-comment
+ else
+ // post else keyword line-comment
+ {
+ return;
+ };
+}
+
+fn unbreakable_initializer_expr_pre_formatting_let_else_length_near_max_width() {
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else block;` is 100 (max_width)
+ // Post Formatting:
+ // The formatting is left unchanged!
+ let Some(x) = some_really_really_really_really_really_really_really_long_name_A else { return };
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else block;` is 100 (max_width)
+ // Post Formatting:
+ // The else keyword and opening brace remain on the same line as the initializer expr,
+ // and the else block is formatted over multiple lines because we can't fit the
+ // else block on the same line as the initializer expr.
+ let Some(x) = some_really_really_really_really_really_really_really_long_name___B else {
+ return;
+ };
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else block;` is 100 (max_width)
+ // Post Formatting:
+ // The else keyword and opening brace remain on the same line as the initializer expr,
+ // and the else block is formatted over multiple lines because we can't fit the
+ // else block on the same line as the initializer expr.
+ let Some(x) = some_really_really_really_really_long_name_____C else {
+ some_divergent_function()
+ };
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else block;` is 101 (> max_width)
+ // Post Formatting:
+ // The else keyword and opening brace remain on the same line as the initializer expr,
+ // and the else block is formatted over multiple lines because we can't fit the
+ // else block on the same line as the initializer expr.
+ let Some(x) = some_really_really_really_really_really_really_really_long_name__D else {
+ return;
+ };
+}
+
+fn unbreakable_initializer_expr_pre_formatting_length_up_to_opening_brace_near_max_width() {
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else {` is 99 (< max_width)
+ // Post Formatting:
+ // The else keyword and opening brace remain on the same line as the initializer expr,
+ // and the else block is formatted over multiple lines because we can't fit the
+ // else block on the same line as the initializer expr.
+ let Some(x) = some_really_really_really_really_really_really_really_really_long_name___E else {
+ return;
+ };
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init else {` is 101 (> max_width)
+ // Post Formatting:
+ // The else keyword and opening brace cannot fit on the same line as the initializer expr.
+ // They are formatted on the next line.
+ let Some(x) = some_really_really_really_really_really_really_really_really_long_name_____F
+ else {
+ return;
+ };
+}
+
+fn unbreakable_initializer_expr_pre_formatting_length_through_initializer_expr_near_max_width() {
+ // Pre Formatting:
+ // The length of `(indent)let pat = init` is 99 (< max_width)
+ // Post Formatting:
+ // The else keyword and opening brace cannot fit on the same line as the initializer expr.
+ // They are formatted on the next line.
+ let Some(x) = some_really_really_really_really_really_really_really_really_really_long_name___G
+ else {
+ return;
+ };
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init` is 100 (max_width)
+ // Post Formatting:
+ // Break after the `=` and put the initializer expr on it's own line.
+ // Because the initializer expr is multi-lined the else is placed on it's own line.
+ let Some(x) =
+ some_really_really_really_really_really_really_really_really_really_long_name____H
+ else {
+ return;
+ };
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init` is 109 (> max_width)
+ // Post Formatting:
+ // Break after the `=` and put the initializer expr on it's own line.
+ // Because the initializer expr is multi-lined the else is placed on it's own line.
+ // The initializer expr has a length of 91, which when indented on the next line
+ // The `(indent)init` line has a lengh of 99. This is the max length that the `init` can be
+ // before we start running into max_width issues. I suspect this is becuase the shape is
+ // accounting for the `;` at the end of the `let-else` statement.
+ let Some(x) =
+ some_really_really_really_really_really_really_really_really_really_really_long_name______I
+ else {
+ return;
+ };
+
+ // Pre Formatting:
+ // The length of `(indent)let pat = init` is 110 (> max_width)
+ // Post Formatting:
+ // Max length issues prevent us from formatting.
+ // The initializer expr has a length of 92, which if it would be indented on the next line
+ // the `(indent)init` line has a lengh of 100 which == max_width of 100.
+ // One might expect formatting to succeed, but I suspect the reason we hit max_width issues is
+ // because the Shape is accounting for the `;` at the end of the `let-else` statement.
+ let Some(x) = some_really_really_really_really_really_really_really_really_really_really_really_long_nameJ else {return};
+}
+
+fn long_patterns() {
+ let Foo {
+ x: Bar(..),
+ y: FooBar(..),
+ z: Baz(..),
+ } = opt
+ else {
+ return;
+ };
+
+ // with version=One we don't wrap long array patterns
+ let [aaaaaaaaaaaaaaaa, bbbbbbbbbbbbbbb, cccccccccccccccccc, dddddddddddddddddd] = opt else {
+ return;
+ };
+
+ let ("aaaaaaaaaaaaaaaaaaa"
+ | "bbbbbbbbbbbbbbbbb"
+ | "cccccccccccccccccccccccc"
+ | "dddddddddddddddd"
+ | "eeeeeeeeeeeeeeee") = opt
+ else {
+ return;
+ };
+
+ let Some(Ok((Message::ChangeColor(super::color::Color::Rgb(r, g, b)), Point { x, y, z }))) =
+ opt
+ else {
+ return;
+ };
+}
+
+fn with_trailing_try_operator() {
+ // Currently the trailing ? forces the else on the next line
+ // This may be revisited in style edition 2024
+ let Some(next_bucket) = ranking_rules[cur_ranking_rule_index].next_bucket(
+ ctx,
+ logger,
+ &ranking_rule_universes[cur_ranking_rule_index],
+ )?
+ else {
+ return;
+ };
+
+ // Maybe this is a workaround?
+ let Ok(Some(next_bucket)) = ranking_rules[cur_ranking_rule_index].next_bucket(
+ ctx,
+ logger,
+ &ranking_rule_universes[cur_ranking_rule_index],
+ ) else {
+ return;
+ };
}