Función de plantilla sobrecargada con firmas idénticas, ¿por qué funciona esto?

Programa mínimo:

#include <stdio.h>

#include <type_traits>

template<typename S, typename T>
int foo(typename T::type s) {
    return 1;
}

template<typename S, typename T>
int foo(S s) {
    return 2;
}

int main(int argc, char* argv[]) {
    int x = 3;
    printf("%d\n", foo<int, std::enable_if<true, int>>(x));

    return 0;
}

salida:

    1 

¿Por qué esto no da un error de compilación? Cuando se genera el código de la plantilla, ¿no serían las funcionesint foo(typename T::type search)&nbsp;yint foo(S& search)&nbsp;tiene la misma firma?

Si cambia un poco las firmas de la función de plantilla, todavía funciona (como es de esperar en el ejemplo anterior):

template<typename S, typename T>
void foo(typename T::type s) {
    printf("a\n");
}

template<typename S, typename T>
void foo(S s) {
    printf("b\n");
}

Sin embargo, esto no es así y, sin embargo, la única diferencia es que uno tiene una firma int y el otro está definido por el primer parámetro de plantilla.

template<typename S, typename T>
void foo(typename T::type s) {
    printf("a\n");
}

template<typename S, typename T>
void foo(int s) {
    printf("b\n");
}

Error del compilador (Clang):

test.cpp:26:2: error: call to 'foo' is ambiguous
foo<std::enable_if<true, int>>(3);
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
test.cpp:16:6: note: candidate function [with T = std::__1::enable_if<true, int>]
void foo(typename T::type s) {
        ^
test.cpp:21:6: note: candidate function [with T = std::__1::enable_if<true, int>]
void foo(int s) {
        ^
1 error generated.

Estoy usando un código similar a este para un proyecto en el que estoy trabajando y me temo que hay un lenguaje sutil que no entiendo que causará un comportamiento indefinido en ciertos casos. También debo mencionar que se compila tanto en Clang como en VS11, así que no creo que sea solo un error del compilador.

Edición: Segundo caso corregido (error tipográfico); añadido mensaje de error de Clang.

Edición # 2: Para aquellos de ustedes que preguntaron qué significa T :: type.

Desdehttp://en.cppreference.com/w/cpp/types/enable_if:

plantilla <bool B, clase T = void> struct enable_if;

Si B es verdadero, std :: enable_if tiene un tipo de typedef de miembro público, igual a T; De lo contrario, no hay miembro typedef.

enable_if es una estructura. Básicamente, si la expresión evaluada en el primer parámetro de plantilla de enable_if es verdadera (y en el caso de mis ejemplos anteriores, lo es), entonces habrá un miembro públicotype&nbsp;que tiene el mismo tipo que el segundo parámetro de plantilla.

En el caso deenable_if<true, int>, enable_if :: type tiene un tipo de int.