>> for now, I'll stick with putting the function body definition along with its declaration
That seems to be the most practical work-around.
Code:
struct A {}; // a type
struct B {}; // a trait value
template < class T > struct C { typedef B type; }; // a trait class

// template < class T >
// void f( T a, typename C<T>::type b = typename C<T>::type() );

template < class T >
void f( T a, typename C<T>::type b = typename C<T>::type() ) { /* whatever */ }

int main(){ A a; f(a); }
That works with GCC and MSVC.
GCC wanted the extra typename, but that didn't help MSVC - neither did the variable names.

gg