@@ -4,7 +4,7 @@ use crate::scan_expr::scan_expr;
44use crate :: unraw:: { IdentUnraw , MemberUnraw } ;
55use proc_macro2:: { Delimiter , TokenStream , TokenTree } ;
66use quote:: { format_ident, quote, quote_spanned} ;
7- use std:: collections:: { BTreeSet , HashMap , HashSet } ;
7+ use std:: collections:: { BTreeSet , HashMap } ;
88use std:: iter;
99use syn:: ext:: IdentExt ;
1010use syn:: parse:: discouraged:: Speculative ;
@@ -34,7 +34,7 @@ impl Display<'_> {
3434 let mut infinite_recursive = false ;
3535 let mut implied_bounds = BTreeSet :: new ( ) ;
3636 let mut bindings = Vec :: new ( ) ;
37- let mut macro_named_args = HashSet :: new ( ) ;
37+ let mut macro_named_args = BTreeSet :: new ( ) ;
3838
3939 self . requires_fmt_machinery = self . requires_fmt_machinery || fmt. contains ( '}' ) ;
4040
@@ -85,15 +85,11 @@ impl Display<'_> {
8585 }
8686 _ => continue ,
8787 } ;
88- let binding_value = match & member {
89- MemberUnraw :: Unnamed ( index) => format_ident ! ( "_{}" , index) ,
90- MemberUnraw :: Named ( ident) => ident. to_local ( ) ,
91- } ;
92- let mut wrapped_binding_value = quote ! ( :: thiserror:: __private:: Var ( #binding_value) ) ;
9388 let end_spec = match read. find ( '}' ) {
9489 Some ( end_spec) => end_spec,
9590 None => return Ok ( ( ) ) ,
9691 } ;
92+ let mut bonus_display = false ;
9793 let bound = match read[ ..end_spec] . chars ( ) . next_back ( ) {
9894 Some ( '?' ) => Trait :: Debug ,
9995 Some ( 'o' ) => Trait :: Octal ,
@@ -105,10 +101,7 @@ impl Display<'_> {
105101 Some ( 'E' ) => Trait :: UpperExp ,
106102 Some ( _) => Trait :: Display ,
107103 None => {
108- has_bonus_display = true ;
109- wrapped_binding_value = quote_spanned ! { span=>
110- #binding_value. as_display( )
111- } ;
104+ bonus_display = true ;
112105 Trait :: Display
113106 }
114107 } ;
@@ -119,19 +112,36 @@ impl Display<'_> {
119112 out += & member. to_string ( ) ;
120113 continue ;
121114 }
115+ let formatvar_prefix = if bonus_display {
116+ "__display"
117+ } else {
118+ "__field"
119+ } ;
122120 let mut formatvar = IdentUnraw :: new ( match & member {
123- MemberUnraw :: Unnamed ( index) => format_ident ! ( "__field{}" , index) ,
124- MemberUnraw :: Named ( ident) => format_ident ! ( "__field_{}" , ident. to_string( ) ) ,
121+ MemberUnraw :: Unnamed ( index) => format_ident ! ( "{}{}" , formatvar_prefix, index) ,
122+ MemberUnraw :: Named ( ident) => {
123+ format_ident ! ( "{}_{}" , formatvar_prefix, ident. to_string( ) )
124+ }
125125 } ) ;
126126 while user_named_args. contains ( & formatvar) {
127127 formatvar = IdentUnraw :: new ( format_ident ! ( "_{}" , formatvar. to_string( ) ) ) ;
128128 }
129129 out += & formatvar. to_string ( ) ;
130- if macro_named_args. insert ( member) {
131- bindings. push ( ( formatvar. to_local ( ) , wrapped_binding_value) ) ;
132- } else {
130+ if !macro_named_args. insert ( formatvar. clone ( ) ) {
133131 // Already added to bindings by a previous use.
132+ continue ;
134133 }
134+ let binding_value = match & member {
135+ MemberUnraw :: Unnamed ( index) => format_ident ! ( "_{}" , index) ,
136+ MemberUnraw :: Named ( ident) => ident. to_local ( ) ,
137+ } ;
138+ let wrapped_binding_value = if bonus_display {
139+ quote_spanned ! ( span=> #binding_value. as_display( ) )
140+ } else {
141+ quote ! ( :: thiserror:: __private:: Var ( #binding_value) )
142+ } ;
143+ has_bonus_display |= bonus_display;
144+ bindings. push ( ( formatvar. to_local ( ) , wrapped_binding_value) ) ;
135145 }
136146
137147 out += read;
0 commit comments