- Home /
How to validate SSL certificates when using HttpWebRequest
I am attempting to use the RestSharp library to call a REST API. RestSharp uses HttpWebRequest under the covers. Calling the API works fine when using HTTP, however I need to use the HTTPS protocol when calling the API. The API server has a valid certificate that is trusted in all browsers.
When I attempt to use the HTTPS protocol to call the API, I get a TlsException
with the message "Invalid certificate received from server. Error code: 0xffffffff800b010a
"
The solutions I have found to solve this problem involve setting a callback on ServicePointManager.ServerCertificateValidationCallback
that always returns true. This is unacceptable in production as it introduces a security vulnerability.
I understand that Mono doesn't have any root certificates contained in it's Trust Store by default (http://www.mono-project.com/docs/faq/security). It is possible to import the root certificates used by Mozilla products into the Trust Store by using the mozroots command, however it seems that the implementation of Mono that ships with Unity is missing this tool. Can Unity actually use certificates contained in a Trust Store?
What a hot mess. Unity apps should always validate against the client computer's CA trust store directly on all platforms. $$anonymous$$eeping that current is the end-user's responsibility, and if it fails, tell the user why and how to update. For self-signed test certs, we create those, and we can deploy them to our test machines and/or to testers's machines. "There can be only one...." CA trust.
Unity's WWW class (does use the OS's CA store)[http://luz.4science.co/unity-android-and-ssl-sslhandshakeexceptioncertpathvalidatorexception/]. Not sure about RestSharp.
Answer by nig · Jan 15, 2015 at 03:57 PM
Yes it can.
Look at http://www.mono-project.com/docs/faq/security/
".. Use the mozroots.exe tool (included in Mono 1.1.10 and later) to download and install all Mozilla’s root certificates (i.e. the ones used in FireFox and other Mozilla’s softwares). It’s easier than finding a specific root but it’s also less granular to make a decision about which one(s) you install or not. .."
There are two reasons why certificate is rejcectd:
X509ChainStatusFlags.UntrustedRoot
X509ChainStatusFlags.RevocationStatusUnknown
Using the mozroots.exe tool to import CA list to Mono/Unity Trust Store fixes first reason.
I found a solution that works for me:
ServicePointManager.ServerCertificateValidationCallback = MyRemoteCertificateValidationCallback;
public bool MyRemoteCertificateValidationCallback(System.Object sender, X509Certificate certificate, X509Chain chain, SslPolicyErrors sslPolicyErrors) {
bool isOk = true;
// If there are errors in the certificate chain, look at each error to determine the cause.
if (sslPolicyErrors != SslPolicyErrors.None) {
for(int i=0; i<chain.ChainStatus.Length; i++) {
if(chain.ChainStatus[i].Status != X509ChainStatusFlags.RevocationStatusUnknown) {
chain.ChainPolicy.RevocationFlag = X509RevocationFlag.EntireChain;
chain.ChainPolicy.RevocationMode = X509RevocationMode.Online;
chain.ChainPolicy.UrlRetrievalTimeout = new TimeSpan(0, 1, 0);
chain.ChainPolicy.VerificationFlags = X509VerificationFlags.AllFlags;
bool chainIsValid = chain.Build((X509Certificate2)certificate);
if(!chainIsValid) {
isOk = false;
}
}
}
}
return isOk;
}
Holy smokes, this just saved me. thanks so much! I've been banging my head for 15 hours trying to get .Net 4.6 working in Unity 2017, and then an Imgur api. The imgur endpoint used https and was failing until I tried the provided $$anonymous$$yRemoteCertificateValidationCallback code.
That code effectively disables SSL certificate verification (e.g. it'll allow https://self-signed.badssl.com/). You might as well simply do return true;
.
Answer by zlSimon · Jun 22, 2016 at 05:09 AM
I have the same issue however when I want to import CA's using the mozroot.exe I always get a null reference exception:
Downloading from 'http://anduin.linuxfromscratch.org/BLFS/other/certdata.txt'...
Importing certificates into user store...
Error: System.NullReferenceException: Der Objektverweis wurde nicht auf eine Objektinstanz festgelegt.
bei Mono.Security.X509.X509Certificate.get_Hash()
bei Mono.Security.X509.X509CertificateCollection.IndexOf(X509Certificate value)
bei Mono.Tools.MozRoots.Process()
bei Mono.Tools.MozRoots.Main(String[] args)
When I try to build the X509Chain I also dont get X509ChainStatusFlags.UntrustedRoot instead I get RevocationStatusUnknown and OfflineRevocation.
Is there anyone who managed to get a propper SSL certificate validation including Chain-of-trust verification, hostname verification and CRL verification?