This repository was archived by the owner on May 28, 2025. It is now read-only.
File tree Expand file tree Collapse file tree 3 files changed +40
-1
lines changed Expand file tree Collapse file tree 3 files changed +40
-1
lines changed Original file line number Diff line number Diff line change @@ -446,7 +446,30 @@ fn expand_format_args<'hir>(
446
446
&& argmap. iter ( ) . enumerate ( ) . all ( |( i, ( & ( j, _) , _) ) | i == j)
447
447
&& arguments. iter ( ) . skip ( 1 ) . all ( |arg| !may_contain_yield_point ( & arg. expr ) ) ;
448
448
449
- let args = if use_simple_array {
449
+ let args = if arguments. is_empty ( ) {
450
+ // Generate:
451
+ // &<core::fmt::Argument>::none()
452
+ //
453
+ // Note:
454
+ // `none()` just returns `[]`. We use `none()` rather than `[]` to limit the lifetime.
455
+ //
456
+ // This makes sure that this still fails to compile, even when the argument is inlined:
457
+ //
458
+ // ```
459
+ // let f = format_args!("{}", "a");
460
+ // println!("{f}"); // error E0716
461
+ // ```
462
+ //
463
+ // Cases where keeping the object around is allowed, such as `format_args!("a")`,
464
+ // are handled above by the `allow_const` case.
465
+ let none_fn = ctx. arena . alloc ( ctx. expr_lang_item_type_relative (
466
+ macsp,
467
+ hir:: LangItem :: FormatArgument ,
468
+ sym:: none,
469
+ ) ) ;
470
+ let none = ctx. expr_call ( macsp, none_fn, & [ ] ) ;
471
+ ctx. expr ( macsp, hir:: ExprKind :: AddrOf ( hir:: BorrowKind :: Ref , hir:: Mutability :: Not , none) )
472
+ } else if use_simple_array {
450
473
// Generate:
451
474
// &[
452
475
// <core::fmt::Argument>::new_display(&arg0),
Original file line number Diff line number Diff line change @@ -1033,6 +1033,7 @@ symbols! {
1033
1033
non_exhaustive_omitted_patterns_lint,
1034
1034
non_lifetime_binders,
1035
1035
non_modrs_mods,
1036
+ none,
1036
1037
nontemporal_store,
1037
1038
noop_method_borrow,
1038
1039
noop_method_clone,
Original file line number Diff line number Diff line change @@ -152,6 +152,21 @@ impl<'a> Argument<'a> {
152
152
None
153
153
}
154
154
}
155
+
156
+ /// Used by `format_args` when all arguments are gone after inlining,
157
+ /// when using `&[]` would incorrectly allow for a bigger lifetime.
158
+ ///
159
+ /// This fails without format argument inlining, and that shouldn't be different
160
+ /// when the argument is inlined:
161
+ ///
162
+ /// ```compile_fail,E0716
163
+ /// let f = format_args!("{}", "a");
164
+ /// println!("{f}");
165
+ /// ```
166
+ #[ inline( always) ]
167
+ pub fn none ( ) -> [ Self ; 0 ] {
168
+ [ ]
169
+ }
155
170
}
156
171
157
172
/// This struct represents the unsafety of constructing an `Arguments`.
You can’t perform that action at this time.
0 commit comments