title: Integrate type name in static_assert output?
body: <p>I like to give helpful errors / messages, and I also want to do so for my <code>static_assert</code>s. The problem is, that they depend on template parameters. Normally, those parameters will get displayed on way or an other due to the error raised, but they are either obscure or not grouped so they make sense. Example:</p>
  
  <pre><code>template&lt;class T&gt;
  struct fake_dependency{
    static bool const value = false;
  };
  
  template&lt;class T, class Tag&gt;
  struct Foo{
    Foo(){}
  
    template&lt;class OtherTag&gt;
    Foo(Foo&lt;T, OtherTag&gt; const&amp;){
      static_assert(fake_dependency&lt;T&gt;::value, "Cannot create Foo&lt;T,Tag&gt; from Foo&lt;T,OtherTag&gt;.");
    }
  };
  
  int main(){
      Foo&lt;int, struct TagA&gt; fA;
      Foo&lt;int, struct TagB&gt; fB(fA);
  }
  </code></pre>
  
  <p>Output on MSVC:</p>
  
  <pre><code>src\main.cpp(74): error C2338: Cannot create Foo&lt;T,Tag&gt; from Foo&lt;T,OtherTag&gt;.
            src\main.cpp(84) : see reference to function template instantiation 'Foo&lt;T,Tag&gt;::Foo&lt;main::TagA&gt;(const Foo&lt;T,main::TagA&gt; &amp;)' being compiled
            with
            [
                T=int,
                Tag=main::TagB
            ]
  </code></pre>
  
  <p>One tag is mentioned in the function template itself, the other below with the class template. Not so nice. Lets see what <a href="http://ideone.com/ElIm1" rel="noreferrer">GCC outputs</a>:</p>
  
  <pre><code>prog.cpp: In constructor 'Foo&lt;T, Tag&gt;::Foo(const Foo&lt;T, OtherTag&gt;&amp;) [with OtherTag = main()::TagA, T = int, Tag = main()::TagB]':
  prog.cpp:18:32:   instantiated from here
  prog.cpp:12:5: error: static assertion failed: "Cannot create Foo&lt;T,Tag&gt; from Foo&lt;T,OtherTag&gt;."
  </code></pre>
  
  <p>Much better, but still not really where the <code>static_assert</code> is. And now imagine some more parameters, or more templates, or both. <em>shivers</em></p>
  
  <p>One way to work around that is to use an intermediate struct, which takes both Tags as template parameters:</p>
  
  <pre><code>template&lt;class Tag, class OtherTag&gt;
  struct static_Foo_assert{
      static_assert(fake_dependency&lt;Tag&gt;::value, "Cannot create Foo&lt;T,Tag&gt; from Foo&lt;T,OtherTag&gt;.");
  };
  
  template&lt;class T, class Tag&gt;
  struct Foo{
    Foo(){}
  
    template&lt;class OtherTag&gt;
    Foo(Foo&lt;T, OtherTag&gt; const&amp;){
        static_Foo_assert&lt;Tag, OtherTag&gt; x;
    }
  };
  </code></pre>
  
  <p>Now lets see the output again:</p>
  
  <pre><code>src\main.cpp(70): error C2338: Cannot create Foo&lt;T,Tag&gt; from Foo&lt;T,OtherTag&gt;.
            src\main.cpp(79) : see reference to class template instantiation 'static_Foo_assert&lt;Tag,OtherTag&gt;' being compiled
            with
            [
                Tag=main::TagB,
                OtherTag=main::TagA
            ]
  </code></pre>
  
  <p>Much better! Here's what <a href="http://ideone.com/pHLAq" rel="noreferrer">GCC says</a>:</p>
  
  <pre><code>prog.cpp: In instantiation of 'static_Foo_assert&lt;main()::TagB, main()::TagA&gt;':
  prog.cpp:17:40:   instantiated from 'Foo&lt;T, Tag&gt;::Foo(const Foo&lt;T, OtherTag&gt;&amp;) [with OtherTag = main()::TagA, T = int, Tag = main()::TagB]'
  prog.cpp:23:32:   instantiated from here
  prog.cpp:8:5: error: static assertion failed: "Cannot create Foo&lt;T,Tag&gt; from Foo&lt;T,OtherTag&gt;."
  </code></pre>
  
  <p>Looks not bad. The problem: I need to create such a struct for every template, since the error message in <code>static_assert</code> needs to be a string literal...</p>
  
  <p>Now, for my question: Can we somehow include the type names directly into the <code>static_assert</code>? Like</p>
  
  <pre><code>static_assert(..., "Cannot create Foo&lt;" T "," Tag "&gt; from Foo&lt;" T "," OtherTag "&gt;.");
  </code></pre>
  
  <p>Example output:</p>
  
  <blockquote>
    <p>Cannot create <code>Foo&lt;int,main::TagA&gt;</code> from <code>Foo&lt;int,main::TagB&gt;</code>.</p>
  </blockquote>
  
  <p>Or, if that isn't achievable, can we somehow make the error message an extra template parameter, as to make it passable?</p>