The underlying connection was closed: Could not establish trust relationship for the SSL/TLS secure channel - web-services

I have a web service which calls make a soap request. While debugging in VS.NET 2008 the soap request is successful. However when I deploy it, I get the following error
The underlying connection was closed: Could not establish trust relationship for the SSL/TLS secure channel.
This must be some sort of security setting I need to change, but I don't know what?
I have tried to deploy the code with:
System.Security.Cryptography.X509Certificates.X509Certificate cert = null;
cert = new System.Security.Cryptography.X509Certificates.X509Certificate();
cert.Import("c:\customerCertFile.cer");
objRequest.ClientCertificates.Add(cert);
//WebProxy iBproxy = new WebProxy("196.2.124.252",true);
WebProxy iBproxy = new WebProxy("192.1.1.1", true);
iBproxy.Credentials = new NetworkCredential("username", "password");
objRequest.Proxy = iBproxy;
No luck.
Thanks in advance!

If you are attempting to use SSL with your local IIS server you'll need to configure it with a self signed certificate using makecert or a similar tool.

Related

MITM proxy, TLS 1.2 Certificate verification failed

Trying to create my own simple MITM-proxy for the specific app which using TLS 1.2 protocol and connecting to several IP addresses, however got in stuck with the error in the app log "Certificate verify failed". How to solve this problem?
The app using about the following code to check the cert:
X509* cert = SSL_get_peer_certificate( ssl );
X509_STORE_CTX * xCtx = X509_STORE_CTX_new();
X509_STORE_CTX_init( xCtx, (X509_STORE*)Store, cert, NULL );
int res = X509_verify_cert( xCtx );
if( !res ) { /*Certificate verify failed*/ };
I did the following steps to achieve the result:
Created CA root key and self-signed certificate according to this manual. It is a bit outdated, so i have made some changes like md5 to sha256, also I didn't use pass phrase, used different key size and other minor changes.
Created proxy key and certificate using the above Root CA to sign it.
Both certificates have been added to the Local Computer Certificates in Personal and Trusted Root Certification Authorities (not sure if this was necessary). Btw, I'm using Windows 10.
Wrote a simple proxy server using sample code from here. Cert.pem and Key.pem took from the second step.
Changed all IP addresses in the app to 127.0.0.1:443 to see if TLS connection established successfully and we can receive first message with an Application Data.
I believe that connection established properly, because WireShark shows common sequence for establishing a TLS connection: Client/Server hello, Certificate, Client key exchange, two encrypted handshake messages. Moreover, using OpenSSL for testing connection:
openssl s_client -connect localhost:443
allow me to write some message and later successfully receive it using SSL_Read() in proxy server. However, there are some errors:
verify error:num=20:unable to get local issuer certificate
verify return:1
verify error:num=21:unable to verify the first certificate
verify return:1
Verify return code: 21 (unable to verify the first certificate)
Using OpenSSL client to directly connect to the original IP addresses give the same errors, but application works great.
Also the output:
openssl verify -CAfile "signing-ca-1.crt" "cert.crt"
WARNING: can't open config file: /usr/local/ssl/openssl.cnf
e:\MyProg\SSL_serv\Debug\cert.crt: OK
It seems that I missed something important. Could you please tell me how to solve this problem with cert?
One of the very purposes of having certificates, along with certificate authorities, is to prevent MITM. The app you are trying trick does the proper thing and checks the certificate. And it doesn't like your's. Its really that simple.
Is it possible to circumvent it and run MITM on an app anyway? Absolutely! Is it going to be easy? Probably not. What you need to do is to patch the app and remove this certificate check.

WCF service self signed certificate invalid on localhost in iis

This is my first time creating a WCF service. I need to use HTTPS as I will be using MembershipBinding. The steps I have taken up to this point are:
Created a certificate authority using the makecert.exe application - from this I have created a server certificate and a client certificate.
Added the certificate authority to the Trusted Root Certification Authorities within Microsoft Management Console.
Added the client and server certificates to my personal certificates within Microsoft Management Console.
Created a https binding for the service in IIS using the server certificate.
Set the appropriate permissions for the app pool on the server certificate.
Defined the service certificate within the serviceBehaviours node in the web.config.
I am now testing the service using the WCF Test Client but I am getting the message:
Error: Cannot obtain Metadata from https://localhost:444/Service.svc If this is a Windows (R) Communication Foundation service to which you have access, please check that you have enabled metadata publishing at the specified address. For help enabling metadata publishing, please refer to the MSDN documentation at http://go.microsoft.com/fwlink/?LinkId=65455.WS-Metadata Exchange Error URI: https://localhost:444/Service.svc Metadata contains a reference that cannot be resolved: 'https://localhost:444/Service.svc'. Could not establish trust relationship for the SSL/TLS secure channel with authority 'localhost:444'. The underlying connection was closed: Could not establish trust relationship for the SSL/TLS secure channel. The remote certificate is invalid according to the validation procedure.HTTP GET Error URI: https://localhost:444/Service.svc There was an error downloading 'https://localhost:444/Service.svc'. The underlying connection was closed: Could not establish trust relationship for the SSL/TLS secure channel. The remote certificate is invalid according to the validation procedure.
The error suggests that there is an issue trusting the certificate but I have trusted the certificate authority used to create it so I don't know how to resolve it. The service worked fine when I was using http.
Thanks in advance.
As your certificate is self-signed, you need to add a hack to your client call :
using (MyWCFServiceClient client = new MyWCFServiceClient())
{
#if DEBUG
ServicePointManager.ServerCertificateValidationCallback = TrustAllCertificatesCallback;
#endif
client.MyCall();
}
And the definition for TrustAllCertificatesCallback :
internal static bool TrustAllCertificatesCallback(object sender, X509Certificate cert, X509Chain chain, SslPolicyErrors errors)
{
bool isValid = true;
// TODO logic to check your self-signed certifiacte
return isValid;
}
The TrustAllCertificatesCallback callback should be deactivated on your production environement.

Websphere App Server mutual SSL - obtain CN from client certificate authentication

What I have:
WAS traditional 9.0 with EJB web service;
webservice client - java application;
SSL configured for only 9449 port as described here (one way http://www.ibm.com/developerworks/webservices/tutorials/ws-radsecurity3/ws-radsecurity3.html)
I need SSL mutual authentication, so I go to Quality of protection (QoP) settings, and set Client authentication = Required.
Up to this point all works fine.
Problem is that my EJB application needs client certificate's common name to obtain a user ID, which it will use in business logic. And here I failed.
Code snippet (web service side):
MessageContext context = wsContext.getMessageContext();
HttpServletRequest req = (HttpServletRequest)context.get(MessageContext.SERVLET_REQUEST) ;
System.out.println("!! isSecure " + req.isSecure());
X509Certificate[] certificates = (X509Certificate[]) req.getAttribute("java.servlet.request.X509Certificate");
if (null != certificates && certificates.length > 0) {
...
} else {
System.out.println("!! Empty certificates");
}
isSecure returnd true, but I get "Empty certificates" message.
My guess is maybe the reason is in following. When I output the SSL configuration used on 9449 port, the first line is "com.ibm.ssl.clientAuthenticationSupported = false" while through Admin Console it is set as Required.
com.ibm.websphere.ssl.JSSEHelper jsseHelper = com.ibm.websphere.ssl.JSSEHelper.getInstance();
java.util.Properties props = jsseHelper.getProperties("WebServiceConfigure");
System.out.println("!!! WebServiceConfigure = " + props.toString());
You might want to try the "direct connect" certificate properties. This was created to address intermediate (SSL-terminating) proxies (like a web server with plug-in) that issued a certificate different than the ultimate client. This property is
com.ibm.websphere.ssl.direct_connection_peer_certificates
You can determine whether you're getting the certificate from direct connect peer or proxied peer via com.ibm.websphere.webcontainer.is_direct_connection.
See also: WAS 9 doc page.

SSL Certificate issue while accessing web service in Production

This isssue in an live environment. We communicate with a webservice in our .net application for a purpose. Most of the time the call is successfull but sometimes it fails with the below message.|
Any idea where the problem could be?
The remote certificate is invalid according to the validation procedure.#Level:Error
System.Security.Authentication.AuthenticationException: The remote certificate is invalid according to the validation procedure.#Level:Error
---> System.Net.WebException: The underlying connection was closed: Could not establish trust relationship for the SSL/TLS secure channel. ---> System.Security.Authentication.AuthenticationException: The remote certificate is invalid according to the validation procedure.

Consuming a web service through an internet proxy server, using a WCF client in C#; providing proxy server authentication

I have a client program that consumes a web service. It works quite well in a number of installations. Now I have a situation where a new customer connects to the internet via a proxy server, and my program's attempt to access the web service gets the "HTTP status 407: Proxy authentication required" error.
I thought that all the configuring of internet access, including proxy server address, port number and authentication would be done in the Control Panel Internet Options, and that I wouldn't have to worry about that in the code, or even in the app.config, of the Web Service client.
Have I got it all wrong?
What I have done in the mean time is give the user the chance to configure the proxy user name and password, and then in my code I do the following:
webServiceClient.ClientCredentials.UserName.UserName = configuredUsername;
webServiceClient.ClientCredentials.UserName.Password = configuredPassword;
But I don't know that this is the right thing. Because it seems to me that the above ClientCredentials would refer to the web service binding/security, not to the internet proxy server.
I suppose I can try it at the customer, but I'd rather be sure of what I'm doing first.
I found out how to do this thing, with the help of a contributor to another forum which in the flurry of trying all sorts of things I've forgotten. So thank you to that now forgotten person.
Here's the code that worked in the end (suitably disguised, but gives the right idea):
BasicHttpBinding binding = new BasicHttpBinding("APISoap"); /* APISoap is the name of the binding element in the app.config */
binding.Security.Mode = BasicHttpSecurityMode.TransportCredentialOnly;
binding.Security.Transport.ProxyCredentialType = HttpProxyCredentialType.Basic;
binding.UseDefaultWebProxy = false;
binding.ProxyAddress = new Uri(string.Format("http://{0}:{1}", proxyIpAddress, proxyPort));
EndpointAddress endpoint = new EndpointAddress("http://www.examplewebservice/api.asmx");
WebServiceClient client = new WebServiceClient(binding, endpoint);
client.ClientCredentials.UserName.UserName = proxyUserName;
client.ClientCredentials.UserName.Password = proxyPassword;