Attempting to take the address of a member function template succeeds when the enclosing class is hardcoded but fails when it is passed to a template. The code:

Code:
struct AType 
  {
  double SomeFunc(int,long *,double &) { double ret(0); return ret; }
  template<class X,class Y,class Z,short AA> double SomeFuncTemplate(X,Y *,Z &) { double ret(AA); return ret; }
  };

template
  <
  class T
  > 
struct TTest
  {
  typedef char Bad;
  struct Good { char x[2]; };
  template<T> struct helper;
  static Good check(helper<&AType::template SomeFuncTemplate<int,long,double,50> > *);
  static Bad check(...);
  static const bool value=sizeof(check(0))==sizeof(Good);
  };
  
template
  <
  class T,
  class C
  > 
struct TTest1
  {
  typedef char Bad;
  struct Good { char x[2]; };
  template<T> struct helper;
  template<class U> static Good check(helper<&U::SomeFunc> *);
  template<class U> static Bad check(...);
  static const bool value=sizeof(check<C>(0))==sizeof(Good);
  };
  
template
  <
  class T,
  class C
  > 
struct TTest2
  {
  typedef char Bad;
  struct Good { char x[2]; };
  template<T> struct helper;
  template<class U> static Good check(helper<&U::template SomeFuncTemplate<int,long,double,50> > *);
  template<class U> static Bad check(...);
  static const bool value=sizeof(check<C>(0))==sizeof(Good);
  };
  
int main()
  {
  
  static_assert(TTest
                  <
                  double (AType::*)(int,long *,double &)
                  >::value,
                "failure in TTest"
               );
            
  static_assert(TTest1
                  <
                  double (AType::*)(int,long *,double &),
                  AType
                  >::value,
                "failure in TTest1"
               );
            
  static_assert(TTest2
                  <
                  double (AType::*)(int,long *,double &),
                  AType
                  >::value,
                "failure in TTest2"
               );
            
  return 0;
  
  }
A static assert occurs for TTest2 of "failure in TTest2" but there is no static assert for TTest0 or TTest1. Tried wth gcc 4.5.2 and msvc 10.0.

The TTest1 shows that the same technique used in the failing TTest2 is used with a regular member function, and succeeds.

Why is this failure occuring ? Is it a bug in both compilers or is my code for TTest2 incorrect somehow ?