CPatch: New memory management
[TortoiseGit.git] / src / Utils / CertificateValidationHelper.h
blobb2ad1746c5e068a3826a01bd875d2212679b3f2b
1 // TortoiseGit - a Windows shell extension for easy version control
3 // Copyright (C) 2013-2017 - TortoiseGit
5 // This program is free software; you can redistribute it and/or
6 // modify it under the terms of the GNU General Public License
7 // as published by the Free Software Foundation; either version 2
8 // of the License, or (at your option) any later version.
10 // This program is distributed in the hope that it will be useful,
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 // GNU General Public License for more details.
15 // You should have received a copy of the GNU General Public License
16 // along with this program; if not, write to the Free Software Foundation,
17 // 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
20 #include <wincrypt.h>
21 #pragma comment(lib, "Crypt32.lib")
23 static DWORD VerifyServerCertificate(PCCERT_CONTEXT pServerCert, PTSTR pwszServerName, DWORD dwCertFlags)
25 if (pServerCert == nullptr || pwszServerName == nullptr)
26 return (DWORD)SEC_E_WRONG_PRINCIPAL;
28 LPSTR rgszUsages[] = { szOID_PKIX_KP_SERVER_AUTH, szOID_SERVER_GATED_CRYPTO, szOID_SGC_NETSCAPE };
29 DWORD cUsages = sizeof(rgszUsages) / sizeof(LPSTR);
31 // Build certificate chain.
32 CERT_CHAIN_PARA ChainPara = { 0 };
33 ChainPara.cbSize = sizeof(ChainPara);
34 ChainPara.RequestedUsage.dwType = USAGE_MATCH_TYPE_OR;
35 ChainPara.RequestedUsage.Usage.cUsageIdentifier = cUsages;
36 ChainPara.RequestedUsage.Usage.rgpszUsageIdentifier = rgszUsages;
38 PCCERT_CHAIN_CONTEXT pChainContext = nullptr;
39 if (!CertGetCertificateChain(nullptr, pServerCert, nullptr, pServerCert->hCertStore, &ChainPara, CERT_CHAIN_REVOCATION_CHECK_CHAIN_EXCLUDE_ROOT, nullptr, &pChainContext))
40 return GetLastError();
41 SCOPE_EXIT { CertFreeCertificateChain(pChainContext); };
43 // Validate certificate chain.
44 HTTPSPolicyCallbackData polHttps = { 0 };
45 polHttps.cbStruct = sizeof(HTTPSPolicyCallbackData);
46 polHttps.dwAuthType = AUTHTYPE_SERVER;
47 polHttps.fdwChecks = dwCertFlags;
48 polHttps.pwszServerName = pwszServerName;
50 CERT_CHAIN_POLICY_PARA PolicyPara = { 0 };
51 PolicyPara.cbSize = sizeof(PolicyPara);
52 PolicyPara.pvExtraPolicyPara = &polHttps;
54 CERT_CHAIN_POLICY_STATUS PolicyStatus = { 0 };
55 PolicyStatus.cbSize = sizeof(PolicyStatus);
57 if (!CertVerifyCertificateChainPolicy(CERT_CHAIN_POLICY_SSL, pChainContext, &PolicyPara, &PolicyStatus))
58 return GetLastError();
60 if (PolicyStatus.dwError)
61 return PolicyStatus.dwError;
63 return SEC_E_OK;