aboutsummaryrefslogtreecommitdiff
path: root/crates/ra_hir_expand
diff options
context:
space:
mode:
authorFlorian Diebold <[email protected]>2019-12-08 08:26:17 +0000
committerFlorian Diebold <[email protected]>2019-12-08 12:02:52 +0000
commit91f28e43a2686d0ac06f73b5fed11351aad428a9 (patch)
tree14e5dfa7099cfbb2e80c865d16f573405a01aaad /crates/ra_hir_expand
parent596e6db46c9c79b2b2be20a4b5461dca35d44b0f (diff)
Fix expansion of format_args
Diffstat (limited to 'crates/ra_hir_expand')
-rw-r--r--crates/ra_hir_expand/src/builtin_macro.rs19
1 files changed, 13 insertions, 6 deletions
diff --git a/crates/ra_hir_expand/src/builtin_macro.rs b/crates/ra_hir_expand/src/builtin_macro.rs
index c7071fe85..ec5ace757 100644
--- a/crates/ra_hir_expand/src/builtin_macro.rs
+++ b/crates/ra_hir_expand/src/builtin_macro.rs
@@ -208,15 +208,20 @@ fn format_args_expand(
208 _id: MacroCallId, 208 _id: MacroCallId,
209 tt: &tt::Subtree, 209 tt: &tt::Subtree,
210) -> Result<tt::Subtree, mbe::ExpandError> { 210) -> Result<tt::Subtree, mbe::ExpandError> {
211 // We expand `format_args!("", arg1, arg2)` to 211 // We expand `format_args!("", a1, a2)` to
212 // `std::fmt::Arguments::new_v1(&[], &[&arg1, &arg2])`, 212 // ```
213 // std::fmt::Arguments::new_v1(&[], &[
214 // std::fmt::ArgumentV1::new(&arg1,std::fmt::Display::fmt),
215 // std::fmt::ArgumentV1::new(&arg2,std::fmt::Display::fmt),
216 // ])
217 // ```,
213 // which is still not really correct, but close enough for now 218 // which is still not really correct, but close enough for now
214 let mut args = Vec::new(); 219 let mut args = Vec::new();
215 let mut current = Vec::new(); 220 let mut current = Vec::new();
216 for tt in tt.token_trees.iter().cloned() { 221 for tt in tt.token_trees.iter().cloned() {
217 match tt { 222 match tt {
218 tt::TokenTree::Leaf(tt::Leaf::Punct(p)) if p.char == ',' => { 223 tt::TokenTree::Leaf(tt::Leaf::Punct(p)) if p.char == ',' => {
219 args.push(tt::Subtree { delimiter: tt::Delimiter::None, token_trees: current }); 224 args.push(current);
220 current = Vec::new(); 225 current = Vec::new();
221 } 226 }
222 _ => { 227 _ => {
@@ -225,13 +230,15 @@ fn format_args_expand(
225 } 230 }
226 } 231 }
227 if !current.is_empty() { 232 if !current.is_empty() {
228 args.push(tt::Subtree { delimiter: tt::Delimiter::None, token_trees: current }); 233 args.push(current);
229 } 234 }
230 if args.is_empty() { 235 if args.is_empty() {
231 return Err(mbe::ExpandError::NoMatchingRule); 236 return Err(mbe::ExpandError::NoMatchingRule);
232 } 237 }
233 let _format_string = args.remove(0); 238 let _format_string = args.remove(0);
234 let arg_tts = args.into_iter().flat_map(|arg| (quote! { & #arg , }).token_trees); 239 let arg_tts = args.into_iter().flat_map(|arg| {
240 quote! { std::fmt::ArgumentV1::new(&(##arg), std::fmt::Display::fmt), }
241 }.token_trees).collect::<Vec<_>>();
235 let expanded = quote! { 242 let expanded = quote! {
236 std::fmt::Arguments::new_v1(&[], &[##arg_tts]) 243 std::fmt::Arguments::new_v1(&[], &[##arg_tts])
237 }; 244 };
@@ -360,6 +367,6 @@ mod tests {
360 BuiltinFnLikeExpander::FormatArgs, 367 BuiltinFnLikeExpander::FormatArgs,
361 ); 368 );
362 369
363 assert_eq!(expanded, r#"std::fmt::Arguments::new_v1(&[] ,&[&arg1(a,b,c),&arg2,])"#); 370 assert_eq!(expanded, r#"std::fmt::Arguments::new_v1(&[] ,&[std::fmt::ArgumentV1::new(&(arg1(a,b,c)),std::fmt::Display::fmt),std::fmt::ArgumentV1::new(&(arg2),std::fmt::Display::fmt),])"#);
364 } 371 }
365} 372}