Como posso fazer com que o apache solicite um certificado SSL de cliente sem precisar verificá-lo em relação a uma CA conhecida?

9

Estou usando o apache2 (2.2.3) para servir um site onde gostaria de ter clientes autenticados com certificados. Como eu só preciso verificar se um usuário que apresenta um certificado específico é o mesmo usuário que apresentou esse certificado no passado, a CA que está assinando o certificado é irrelevante. No entanto, parece que usar SSLVerifyClient require requer SSLCACertificateFile ... (ou SSLCACertificatePath ... ) e, em seguida, o apache aceitará somente certificados assinados por uma autoridade de certificação nesse arquivo / caminho. Existe uma maneira de obter o apache para aceitar qualquer certificado de cliente, independentemente da autoridade de emissão / voz? (isto é, verifique se o cliente tem a chave privada correspondente à chave pública apresentada, mas não se preocupe em verificar a CA de emissão / assinatura)

    
por Isaac 21.04.2012 / 22:16

2 respostas

10

Como você descobriu, é possível desativar a verificação de certificado no nível de handshake SSL / TLS no Apache Httpd usando SSLVerifyCLient optional_no_ca .

O segundo problema que você vai enfrentar com o que você está tentando fazer é fazer com que o cliente envie o certificado. Como o seu certificado não se destina a estar dentro de uma PKI, eles podem ser auto-assinados e ter vários emissores.

Ao solicitar um certificado de cliente, o servidor envia uma % mensagem% TLS para o cliente durante o handhsake. Esta mensagem contém a lista CertificateRequest :

A list of the distinguished names of acceptable certificate authorities. These distinguished names may specify a desired distinguished name for a root CA or for a subordinate CA; thus, this message can be used to describe both known roots and a desired authorization space. If the certificate_authorities list is empty then the client MAY send any certificate of the appropriate ClientCertificateType, unless there is some external arrangement to the contrary.

Os navegadores usam isso para escolher qual certificado de cliente deve ser enviado (se houver).

(Observe que a parte sobre a lista vazia está apenas na especificação do TLS 1.1 em diante. O SSL 3.0 e o TLS 1.0 são silenciosos sobre isso e, na prática, ele também funcionará.)

Você tem duas opções para isso.

  • Se os certificados do cliente que você espera serão autoassinados, todos eles terão emissores diferentes. Como você não sabe o que esperar, o servidor precisará enviar uma lista vazia. Para fazer isso, use a certificate_authorities diretiva e aponte-a para um arquivo que contenha apenas uma linha vazia (se bem me lembro, não funciona com um arquivo completamente vazio).

  • A segunda opção (menos limpa). É concordar com um DN do Emissor comum a todos os certificados de cliente que você espera, independentemente de terem ou não sido emitidos por esse certificado de autoridade de certificação (ou se essa CA existe ou não). Ao fazer isso, você estaria quebrando o modelo PKI consideravelmente (mais).

    Se você concordar com um DN do Emissor, como SSLCADNRequestFile (por exemplo). Qualquer pessoa pode criar um certificado auto-assinado usando CN=Dummy CA como Assunto DN (e DN do Emissor), possivelmente com chaves diferentes. Embora a diretiva CN=Dummy CA espere ser configurada com certificados para construir a lista, eles não são usados para verificar o certificado do cliente, é apenas uma maneira complicada (mas natural no contexto das outras diretivas) de configurar o SSLCADNRequestFile list. Se você, como um serviço, colocar um certificado autoassinado com esses nomes em certificate_authorities , isso fará com que a mensagem SSLCADNRequestFile TLS use CertificateRequest na lista CN=Dummy CA (esses são apenas nomes, não certs neste palco). O cliente poderá então obter seu próprio certificado com o Emissor DN certificate_authorities , independentemente de sua assinatura poder ou não ser verificada por esse certificado (mesmas chaves) ou não, já que nenhuma verificação de assinatura está envolvida nessas etapas.

Dito isto, lembre-se que com CN=Dummy CA , nenhuma verificação de certificado real é feita (suponho que você poderia verificar a variável SSLVerifyCLient optional_no_ca se sua verificação manual é apenas uma solução alternativa para uma PKI que você configurou). Tudo o que você saberá nesse estágio é que o cliente tem a chave privada para o certificado de chave pública que ele apresentou (garantido pela mensagem TLS SSL_CLIENT_VERIFY ): você precisará executar alguma forma de verificação se quiser que haja autenticação de algum tipo. (Você não pode confiar em nenhum conteúdo do certificado, isto é, qualquer ligação entre sua chave pública e os nomes / atributos que contém.)

Isso não funciona bem para arquivos, mas você pode fazer isso para um aplicativo (por exemplo, PHP / CGI / ... mesmo Java, se passar o certificado para o servidor Java com proxy). Uma forma básica seria ter uma lista pré-conhecida de chaves públicas, ou você poderia ver as ideias em FOAF + SSL / WebID .

    
por 22.04.2012 / 20:49
2

Usar SSLVerifyCLient optional_no_ca (em vez de require ) faz com que o apache não marque a CA de emissão (e, portanto, não precisa de um arquivo ou caminho de certificado de autoridade de certificação). Ele permite que o cliente / usuário não envie um certificado, portanto, verificar se um certificado foi usado deve ser feito separadamente.

(Aparentemente, eu não consegui ler atentamente a documentação de mod_ssl .)

    
por 22.04.2012 / 05:54