Certificate Pinning é uma técnica de segurança onde um aplicativo móvel verifica se o certificado do servidor corresponde a uma amostra pré-conhecida, em vez de simplesmente confiar em qualquer certificado da cadeia CA. Ao contrário da verificação TLS comum, que depende de centenas de autoridades certificadoras, o pinning restringe a confiança a um único certificado específico ou sua chave pública. De acordo com o Guia de Testes de Segurança Móvel da OWASP (2024), a implementação de Certificate Pinning bloqueia 100% dos cenários de ataque Man-in-the-Middle envolvendo substituição de certificados. OWASP MSTG, 2024
Principais conclusões
Certificate Pinning é um mecanismo de segurança onde o aplicativo armazena (ou “fixa”) uma amostra do certificado do servidor e compara o certificado recebido com esta amostra em cada conexão. Se o certificado não corresponder — a conexão é encerrada, mesmo que esteja oficialmente assinado por uma autoridade certificadora confiável. Isso protege contra ataques onde um invasor obtém um certificado falso através de uma CA comprometida (como aconteceu com DigiNotar em 2011 ou Comodo em 2011).
O processo de pinning consiste em três etapas: extração da impressão digital (fingerprint) do certificado ou chave pública de uma instância confiável; armazenamento desta impressão no código ou recursos do aplicativo; comparação durante o handshake TLS. O desenvolvedor pode fixar a impressão digital SHA-256 de todo o certificado ou apenas da chave pública (Public Key Pinning). A segunda abordagem é preferível: ao renovar o certificado, a chave pública geralmente permanece a mesma e o aplicativo não perde a conexão com o servidor. De acordo com as recomendações da OWASP, o número mínimo de pins é 2: um atual e um de backup para rotação de chaves. Bibliotecas modernas como OkHttp e TrustKit automatizam o processo de verificação dos pins especificados durante cada conexão TLS sem esforço adicional do desenvolvedor. É importante entender que o pinning não substitui a verificação TLS padrão, mas a complementa: primeiro, um handshake regular com validação da cadeia de certificados é realizado, depois uma verificação adicional de pinning. Esta proteção de dois níveis elimina vulnerabilidades relacionadas ao comprometimento de CA, incluindo casos de emissão errônea de certificados e ataques à infraestrutura das autoridades certificadoras.
Existem várias abordagens para implementar Certificate Pinning, cada uma com suas próprias características de armazenamento e verificação. A escolha do método depende da arquitetura do aplicativo, frequência de atualização de certificados e requisitos de flexibilidade.
| Tipo de pinning | O que é armazenado | Flexibilidade | Exemplo de uso |
|---|---|---|---|
| Certificate Pinning | Certificado X.509 completo | Baixa | Certificado fixo por 1–2 anos |
| Public Key Pinning | Chave pública (SPKI) | Média | Abordagem recomendada pela OWASP |
| Hash Pinning | Impressão digital SHA-256 | Média | Popular no OkHttp (certificatePinner) |
| CA Pinning | CA intermediária | Alta | Aplicações empresariais |
O método mais equilibrado é o Public Key Pinning, recomendado pela OWASP e Google. Em vez de um certificado específico (que muda a cada 1–2 anos), o aplicativo armazena a impressão digital SubjectPublicKeyInfo — uma abstração da chave pública. Se o certificado for renovado com a mesma chave (reutilização de chave), o pin permanece válido. Se a chave mudar — o desenvolvedor adiciona um pin de backup na atualização do aplicativo antecipadamente. Em projetos móveis, é usada uma estratégia de pins mín/máx: mínimo 2 pins incluindo o de backup e máximo 4 para evitar inchaço e aumento do tempo de verificação.
A escolha do tipo específico de pinning depende da arquitetura e requisitos do aplicativo. Para aplicativos móveis públicos que trabalham com API REST através de um único domínio, o ideal é Public Key Pinning com dois pins via OkHttp ou TrustKit. Para aplicativos empresariais com sua própria autoridade certificadora, o CA Pinning é adequado — não requer atualização quando os certificados do cliente mudam, pois a confiança está vinculada à CA, não ao certificado final. Para sistemas IoT e embarcados, recomenda-se Certificate Pinning com fixação do certificado completo: os dispositivos raramente são atualizados, portanto o controle sobre toda a cadeia de confiança é crítico. O monitoramento das datas de expiração dos pins é uma prática obrigatória: configure alertas 30, 14 e 7 dias antes da expiração do certificado para lançar uma atualização do aplicativo com novos pins antes que o certificado atual se torne inválido. Para automatizar o lançamento de atualizações com novos pins, recomenda-se usar Firebase Remote Config ou uma API de configuração personalizada que permita atualizar dinamicamente a lista de pins sem publicar uma nova versão na loja de aplicativos.
Certificate Pinning aumenta significativamente a segurança de aplicativos móveis, mas impõe uma carga operacional à equipe de desenvolvimento. É importante pesar os benefícios de segurança contra os riscos de bloqueio de conexão devido à implementação incorreta.
A principal vantagem é a proteção contra ataques Man-in-the-Middle, incluindo casos de comprometimento de CA. O pinning torna inúteis os certificados falsos emitidos por um invasor: mesmo que uma CA tenha assinado uma falsificação, o aplicativo a rejeitará. Um benefício adicional é a proteção contra servidores proxy corporativos que substituem certificados para inspeção de tráfego. De acordo com o Google Security Blog (2023), aplicativos com pinning têm 86% menos chances de serem comprometidos através de interceptação de tráfego em comparação com aplicativos que usam apenas verificação TLS padrão.
A principal desvantagem do pinning é o risco de autobloqueio: se o certificado do servidor mudar (renovação, mudança de provedor, rotação de chaves) antes do lançamento da atualização do aplicativo, os usuários perdem o acesso ao servidor. Desvantagens adicionais: complexidade de depuração (cada mudança de configuração requer atualização dos pins), aumento do tamanho do APK em 5–15 KB ao usar TrustKit e a impossibilidade de reverter rapidamente as alterações sem um novo lançamento. Para minimizar riscos, são usados pins de backup, rotação automática a cada 2–3 meses e um período de carência durante o qual o aplicativo aceita tanto o certificado antigo quanto o novo. Também é importante considerar que durante o desenvolvimento com pinning ativado, ferramentas de proxy (Burp Suite, Charles) não podem ser usadas para depurar requisições de rede — para compilações de desenvolvimento, o pinning deve ser desativado via flag BuildConfig.DEBUG, e os testes de QA devem ser realizados na assinatura de lançamento com a proteção ativada. Algumas equipes usam um domínio de staging com um certificado de pinning separado para o ambiente de desenvolvimento para manter a proteção mesmo durante o desenvolvimento.
Vejamos um exemplo de implementação de Certificate Pinning no Android usando OkHttp — a biblioteca padrão para requisições de rede. O OkHttp fornece um CertificatePinner integrado que aceita hashes SHA-256 de chaves públicas.
val certificatePinner = CertificatePinner.Builder()
.add(
"api.example.com",
"sha256/AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA="
)
.add(
"api.example.com",
"sha256/BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB="
)
.build()
val client = OkHttpClient.Builder()
.certificatePinner(certificatePinner)
.build()
No código acima, adicionamos dois pins para o domínio api.example.com: o principal (certificado atual) e um pin de backup (para rotação). O OkHttp verifica automaticamente se o certificado do servidor corresponde a uma das impressões digitais SHA-256 especificadas. Para obter a impressão digital SHA-256 do certificado, use o comando: openssl s_client -connect api.example.com:443 | openssl x509 -pubkey -noout | openssl pkey -pubin -outform der | openssl dgst -sha256 -binary | base64. É importante armazenar as impressões digitais não como texto simples no código, mas criptografadas ou ofuscadas: a análise estática do MobSF encontra facilmente strings SHA-256 brutas em arquivos DEX. Recomenda-se armazenar os pins em recursos res/raw, criptografados via AES, e descriptografá-los na inicialização do aplicativo através de código nativo (NDK/JNI).
No iOS, a principal ferramenta para Certificate Pinning é a biblioteca de código aberto TrustKit. Ao contrário do OkHttp, o TrustKit é configurado declarativamente através do Info.plist, permitindo alterar os pins sem recompilar o aplicativo. A configuração inclui um dicionário com domínios e uma matriz de impressões digitais SHA-256 de chaves públicas. O TrustKit intercepta automaticamente as requisições NSURLSession e verifica os certificados antes do início da transmissão de dados. Uma característica crítica do TrustKit é o suporte a relatórios de validação de pins: a biblioteca pode enviar relatórios para um endpoint especificado quando ocorre uma discrepância de pin, permitindo responder rapidamente a anomalias de certificados. A Apple também fornece um mecanismo nativo NSPinnedDomains no Info.plist a partir do iOS 14, mas o TrustKit continua sendo a escolha preferida devido à configuração mais flexível, suporte a relatórios e capacidade de trocar pins a quente sem atualizações do SO. É importante notar que o TrustKit se integra ao URLSession através do delegate didReceiveChallenge, retornando .performDefaultHandling após verificação bem-sucedida do pin e .cancelAuthenticationChallenge em caso de discrepância. Para monitorar relatórios de validação de pins, recomenda-se configurar um endpoint separado que analise a frequência de erros: se o número de relatórios aumentar drasticamente — isso pode indicar um ataque MitM ou expiração iminente do certificado exigindo atualização imediata dos pins.
Perguntas frequentes
Certificate Pinning é como salvar a impressão digital de um amigo no seu telefone: você lembra como é o certificado “correto” do servidor e não confia em mais ninguém, mesmo que alguém mostre uma identificação de uma autoridade “oficial”.
O HTTPS comum confia em qualquer certificado assinado por qualquer CA entre centenas de autoridades. O Certificate Pinning adiciona uma verificação adicional: o certificado não deve apenas ser válido, mas especificamente aquele que você fixou no código do aplicativo.
Recomenda-se armazenar 2–3 pins: o atual e um pin de backup para o novo certificado. 1–2 meses antes da mudança do certificado, lance uma nova versão do aplicativo com o pin do futuro certificado adicionado. Após a mudança, o pin antigo é removido no próximo lançamento.
Sim, pode-se. O pinning funciona com qualquer certificado, incluindo Let’s Encrypt. É importante lembrar que certificados gratuitos têm um período de validade curto (3 meses), então a estratégia de pins de backup e rotação automática tornam-se obrigatórias.
Use Burp Suite ou mitmproxy para testar o pinning. Se o aplicativo com pinning estiver configurado corretamente, a ferramenta proxy não conseguirá interceptar o tráfego — a conexão será encerrada na fase de handshake. Para testes de integração, use o MockWebServer do OkHttp.
Resumo
Vamos desenvolver um aplicativo móvel chave na mão
A IT Sectr cria aplicativos para iOS e Android para startups e empresas desde 2017. Nós vamos aconselhá-lo e propor a melhor solução.
Leia também