]>
Commit | Line | Data |
---|---|---|
3dfed10e | 1 | use rustc_ast as ast; |
74b04a01 | 2 | use rustc_ast::tokenstream::TokenStream; |
dfeec247 XL |
3 | use rustc_expand::base::{self, DummyResult}; |
4 | use rustc_span::symbol::Symbol; | |
1a4d82fc JJ |
5 | |
6 | use std::string::String; | |
7 | ||
e1599b0c | 8 | pub fn expand_concat( |
9fa01778 | 9 | cx: &mut base::ExtCtxt<'_>, |
dfeec247 | 10 | sp: rustc_span::Span, |
e1599b0c | 11 | tts: TokenStream, |
8faf50e0 | 12 | ) -> Box<dyn base::MacResult + 'static> { |
5e7ed085 FG |
13 | let Some(es) = base::get_exprs_from_tts(cx, sp, tts) else { |
14 | return DummyResult::any(sp); | |
1a4d82fc JJ |
15 | }; |
16 | let mut accumulator = String::new(); | |
8faf50e0 | 17 | let mut missing_literal = vec![]; |
0731742a | 18 | let mut has_errors = false; |
85aaf69f | 19 | for e in es { |
e74abb32 XL |
20 | match e.kind { |
21 | ast::ExprKind::Lit(ref lit) => match lit.kind { | |
dfeec247 | 22 | ast::LitKind::Str(ref s, _) | ast::LitKind::Float(ref s, _) => { |
a2a8927a | 23 | accumulator.push_str(s.as_str()); |
1a4d82fc | 24 | } |
8faf50e0 XL |
25 | ast::LitKind::Char(c) => { |
26 | accumulator.push(c); | |
27 | } | |
ba9703b0 XL |
28 | ast::LitKind::Int( |
29 | i, | |
30 | ast::LitIntType::Unsigned(_) | |
31 | | ast::LitIntType::Signed(_) | |
32 | | ast::LitIntType::Unsuffixed, | |
33 | ) => { | |
8faf50e0 XL |
34 | accumulator.push_str(&i.to_string()); |
35 | } | |
36 | ast::LitKind::Bool(b) => { | |
37 | accumulator.push_str(&b.to_string()); | |
38 | } | |
39 | ast::LitKind::Byte(..) | ast::LitKind::ByteStr(..) => { | |
40 | cx.span_err(e.span, "cannot concatenate a byte string literal"); | |
41 | } | |
f2b60f7d | 42 | ast::LitKind::Err => { |
dc9dc135 XL |
43 | has_errors = true; |
44 | } | |
8faf50e0 | 45 | }, |
0731742a XL |
46 | ast::ExprKind::Err => { |
47 | has_errors = true; | |
48 | } | |
1a4d82fc | 49 | _ => { |
8faf50e0 | 50 | missing_literal.push(e.span); |
1a4d82fc JJ |
51 | } |
52 | } | |
53 | } | |
74b04a01 | 54 | if !missing_literal.is_empty() { |
8faf50e0 XL |
55 | let mut err = cx.struct_span_err(missing_literal, "expected a literal"); |
56 | err.note("only literals (like `\"foo\"`, `42` and `3.14`) can be passed to `concat!()`"); | |
57 | err.emit(); | |
e1599b0c | 58 | return DummyResult::any(sp); |
0731742a | 59 | } else if has_errors { |
e1599b0c | 60 | return DummyResult::any(sp); |
8faf50e0 | 61 | } |
e1599b0c | 62 | let sp = cx.with_def_site_ctxt(sp); |
476ff2be | 63 | base::MacEager::expr(cx.expr_str(sp, Symbol::intern(&accumulator))) |
1a4d82fc | 64 | } |