Type parameter in nested macro does not match


#1

I created a minimal code to reproduce my trouble.

macro_rules! foo {
    (i32) => {{ println!("foo!"); }};
    ($t:ty) => {{ println!("oh..."); }};
}

macro_rules! bar {
    ($t:ty) => {{ foo!($t); }}
}

fn main() {
    foo!(i32);
    bar!(i32);
}

This outputs:

foo!
oh...

But I don’t know why bar!(i32) doesn’t show foo!; Invocation of foo! in bar! doesn’t match the i32 clause in foo!. My environment is OS X 10.11 and rustc 1.13.0 nightly.

Does anyone know the reason and how I fix in order to show foo! on bar!(i32)?


#2

See the Captures and Expansion Redux chapter of TLBoRM; you can scroll down to “One aspect of substitution that often surprises people is that substitution is not token-based…” and start from there.

Short version: you cannot literally match anything that’s been captured, unless you captured it as an ident or tt.


#3

Oh, I understood what had happened… So pattern matching with type in macro is not possible. I need to consider any other way. Thank you for the answer :smile: