jQuery in Action, 2nd edition*
The moose likes Web Services and the fly likes 2-way ssl not working: bad certificate Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login


JavaRanch » Java Forums » Java » Web Services
Bookmark "2-way ssl not working: bad certificate" Watch "2-way ssl not working: bad certificate" New topic
Author

2-way ssl not working: bad certificate

Nicky Eng
Ranch Hand

Joined: Mar 26, 2005
Posts: 378
I created one simple test java application to connect to a web service over HTTP/SSL.

The webservice provider given us 3 certificates for testing purpose:
1. Client Test Certificate with private key: abctest.p12
2. Client Test Certificate with public key: abctest.cer
3. Provider Test Certificate with public key: abc.cer

I've added these 3 certificate into "cacerts" truststore using java 'keytool'.
for 3 certificates, i created 3 different alias name: abcp12, abctest & abc in "cacerts" truststore.

And then I test the program, for 1way SSL connection, my program works fine(request to them, they return response).

But when i try to use 2 ways SSL connection, my program does not work. It gives me this error: "received fatal error: bad_certificate"

I've googled but doesn't help me at all.
I've added 3 certificates into my truststore.
I checked the list with command "keytool -list -v" and all the certs are there.
1way ssl is working but 2ways ssl is NOT working with receiving bad certificate error.

Can anyone please help me? Why bad certificate? Something wrong with the way I add the cert into truststore file?
Or is there any way in java coding to IGNORE this 'bad_certificate' exception?


Here is some error I get:


From NickyEng
Diploma in Computer Studies
SCJP 1.4
SCWCD 1.4
Formula 1 app by Maxis (Playbook)
Ivan Krizsan
Ranch Hand

Joined: Oct 04, 2006
Posts: 2198
    
    1
Hi!
If you care for an example showing how to set up mutual authentication between a web service deployed in GlassFish and a web service client, then do take a look at section 8.3 in the following document: http://www.slideshare.net/krizsan/scdjws-5-study-notes-3085287
Best wishes!
Nicky Eng
Ranch Hand

Joined: Mar 26, 2005
Posts: 378
hi Ivan,

thanks for your suggestion. I've noticed most of this related thread you had post a similar reply to all. I would appreciate if you or any members here can at least know my situation here and post a short answer.

I have went through your notes but it still doesn't help me and i'm not working with Glassfish. Mine is just pure java environmental runtime with NO tomcat server.
Appreciate if anyone can help...

Thanks in advance.
Ivan Krizsan
Ranch Hand

Joined: Oct 04, 2006
Posts: 2198
    
    1
Hi!
Nicky Eng wrote:I've noticed most of this related thread you had post a similar reply to all. I would appreciate if you or any members here can at least know my situation here and post a short answer.

You caught me red-handed, I must admit! I am slightly lazy, so I prefer referring to existing documents when answering questions.
Your problem, as far as I understand, is not a simple one - I recall spending quite some time investigating that area before being able to write my notes.

I have went through your notes but it still doesn't help me and i'm not working with Glassfish.

I feared this much. Well, then I cannot help you, I am sorry.
Best wishes!
Nicky Eng
Ranch Hand

Joined: Mar 26, 2005
Posts: 378
My java program makes RPC call through SOAP to a server method over SSL-2ways.

It works in 1way (https://xxxx:88453/abc), which 88453 port is for 1way SSL.

but it doesn't work in 2way (https://xxxx:88454/abc), 88454 port is for 2way SSL.

Anyone can help ? Its urgently needed.
R Srini
Ranch Hand

Joined: Feb 19, 2010
Posts: 215
Hello. What version of Axis are using? Axis1 or Axis2? If Axis2, have you looked at these links:

- http://ws.apache.org/axis2/1_5/http-transport.html#httpsupport
- http://hc.apache.org/httpclient-3.x/sslguide.html

Also, per this link, http://forums.sun.com/thread.jspa?threadID=784869 , "The server has to trust the client's certificates too. As they are self-signed they have to be added to the server's truststore." Is this applicable to your situation?

Also, you can check this: http://stackoverflow.com/questions/2759911/java-certificate-based-authentication . It is still applicable if the service you are calling is hosted on tomcat. Have all of the steps here been performed: http://tomcat.apache.org/tomcat-6.0-doc/ssl-howto.html ? Please do every single step. You might have missed one. I see a lot of questions about this on the web, but no one posts a solution

Here is a primer on 2-way ssl authentication: http://publib.boulder.ibm.com/infocenter/tivihelp/v5r1/index.jsp?topic=/com.ibm.itim.infocenter.doc/cpt/cpt_ic_security_ssl_authent2way.html . "Two-way SSL authentication is also referred to as client authentication because the application acting as an SSL client presents its certificate to the SSL server after the SSL server authenticates itself to the SSL client."

Please be sure to post the solution once you figure this out!
Nicky Eng
Ranch Hand

Joined: Mar 26, 2005
Posts: 378
may I start again from the beginning...

WebService provider gives me 3 certificates (testing purpose)
1. client testing certificate with private key: abctest.p12 (password: abctest)
2. client testing certificate with public key: abctest.cer
3. provider-server certificate with public key: abc.cer

----------------
Step 1:

I added abc.cer into my cacerts file by using following command:


Result: successfully added.


Step 2:

I add abctest.cer into my cacerts file by using following command:


Result: successfully added.


Step 3:

I add abctest.p12 into my cacerts file by using following command:




I do not understand, adding abctest.p12 into cacerts need an existing alias name ? Even if i pick one of the alias name, it would ask me to overwrite it..shall i overwrite it ? and which alias name shall i overwrite?

I'm confused. abctest.p12 comes with private key ---> is a cert chain ?

anyone help ?
R Srini
Ranch Hand

Joined: Feb 19, 2010
Posts: 215
Its good you provided this information. So the last keytool command is causing problems. Please go to Installing and Configuring SSL Support and look at the section "Creating a Client Certificate for Mutual Authentication" where the example uses the -client-alias option. Just read through it, follow the instructions from beginning to end and let us know if that helps. I think this should help.

There is also a mutual authentication example here, but please follow instructions at the above link first. Best of luck!
Nicky Eng
Ranch Hand

Joined: Mar 26, 2005
Posts: 378
I have tried this:

Step 3:


So all certificate given by my provider, I already successfully imported into my java jre's cacerts. I run again my java program, it stuck again with this:




Since i already have imported server cert( abc.cer ), client cert(abctest.cer), and private key client cert(abctest.p12) into cacerts... How come I still can get "bad certificate" ?

Gosh
Already 1 week passed I still stuck with this issue.
Nicky Eng
Ranch Hand

Joined: Mar 26, 2005
Posts: 378
just to provide more details here:

I have java jre, I DO NOT have tomcat running.

Will the missing of tomcat resulting in 'bad certificate' error when using SOAP to call webservice over HTTPS ?

anyone help?
R Srini
Ranch Hand

Joined: Feb 19, 2010
Posts: 215
Nicky, by "tomcat", I mean the "server" side. So if you are calling an external web service beyond your control, then we can assume that they have done the necessary setup. Per the tutorial link from my earlier post, there are two main steps:
1. Create a server certificate and have it signed by a CA
2. Creating a Client Certificate for Mutual Authentication

We will assume that step 1 was done by your certificate provider. Now, in the section Creating a Client Certificate for Mutual Authentication, the tutorial says "In client authentication, clients are required to submit certificates that are issued by a certificate authority that you choose to accept.". So it looks like the server is not able to verify your certificate. Did you actually follow the instructions from the url in my earlier post? The very first step in the link is to generate the client certificate using this command:

1. Generate the client certificate:
<JAVA_HOME>\bin\keytool -genkey -alias client-alias -keyalg RSA -keypass changeit -storepass changeit -keystore keystore.jks
2. Export the generated client certificate into the file client.cer
<JAVA_HOME>\bin\keytool -export -alias client-alias -storepass changeit -file client.cer -keystore keystore.jks
3. Add the certificate to the trust-store file <J2EE_HOME>/domains/domain1/config/cacerts.jks:
<JAVA_HOME>\bin\keytool -import -v -trustcacerts
-alias client-alias -file client.cer
-keystore <J2EE_HOME>/domains/domain1/config/cacerts.jks
-keypass changeit -storepass changeit

Some questions:
1. Did you do steps 2 and 3 above? I did not see any reference to "export" in your posts. The keytool command options you have used are somewhat different that the one in the tutorial link.
2. Is your client a plain java program running on it own? What is the environment & technology? JAX-WS? JAX-RS? GlassFish? JBoss? HttpClient? What all is involved?

Anyway, I found this example: http://javasecurity.wikidot.com/example-item-1 . Hope it helps. And this also: http://stackoverflow.com/questions/2240931/mutual-authentication-with-web-services

Frankly, I don't think this is going to lead anywhere unless you first try to get a tutorial running. The tutorial assumes a certain environment, and you need to have all of that setup. If you are ok with using Netbeans/Glassfish, then this is all much simpler: http://netbeans.org/kb/docs/websvc/wsit.html
Nicky Eng
Ranch Hand

Joined: Mar 26, 2005
Posts: 378
hi Srini,

Thank you so much for your posting.

I've skipped step 1 and 2 because I thought client certificate has been provided to us by our webservice provider(WSDL) for testing purpose. So there is no need to generate my own(i'm the client in this case) right?
If i generate my own, then what's the point of 'abctest.cer' certificate provided to me by webservice provider?


I can't change/know anything in the server side because i'm just a client who trying to call provider's webservice's function over HTTPS.
So, if the server insist want 2ways SSL, then in my program, there is no way to ignore/skip SSL authentication process......


Answer to your question:
2. My program (client program) use only plain java stand alone with axis.jar. I generated java source code from a WSDL file by using wsdltojava tool. and then i created a engine to call webservice function. Binding to wsdl is fine, but when my engine calling one of the function, it start doing ssl handshake process, and resulted the server (webservice provider) give me alert 'bad certificate'. No tomcat.


the link you posted earlier, i had read them all and i gained better knowledge on ceritificate but not with this 'bad certificate' error though.
So what's next shall i do ?
R Srini
Ranch Hand

Joined: Feb 19, 2010
Posts: 215
The only other thing I found (from the first link below) is to set the trust store and key store properties as JVM arguments when calling your client program:

Before you run the client that access a web service with SSL, you need to set the value of the environment variable, VMARGS. After that, you can run the application as usual. For SSL, set the value of VMARGS to:

-Djavax.net.ssl.trustStore=${truststore.location}
-Djavax.net.ssl.trustStorePassword=${ssl.password}

For SSL mutual authentication, set the value of VMARGS to:

-Djavax.net.ssl.trustStore=${truststore.location}
-Djavax.net.ssl.trustStorePassword=${ssl.password}
-Djavax.net.ssl.keyStore =${keystore.location}
-Djavax.net.ssl.keyStorePassword=${ssl.password}


Here are more links. Hopefully, this is what you need:
- http://www.java-tips.org/java-ee-tips/java-api-for-xml-web-services/using-jax-ws-based-web-services-wit.html
- http://stackoverflow.com/questions/537040/how-to-connect-to-a-secure-website-using-ssl-in-java-with-a-pkcs12-file
- http://www.artima.com/forums/flat.jsp?forum=46&thread=106915
- http://db.apache.org/derby/docs/dev/adminguide/cadminsslclient.html

If after setting the four system properties, you still have trouble, then I would suggest getting the Netbeans example from the 1st link above to work. Then go from there.
R Srini
Ranch Hand

Joined: Feb 19, 2010
Posts: 215
Nicky: Any progress on this? I am curious about how you resolved it. If you haven't yet, then please see this excellent link for a complete step-by-step tutorial on client (mutual) authentication: http://www.herongyang.com/JDK/ssl_client_auth.html. I have tried it myself and it works. Of course, you will have to adapt it a little by providing your own certificates, etc.

Having said that ... I still agree with Ivan. I think a good way to approach it is:
1. Download Netbeans
2. Download Glassfish
3. Follow the tutorial or, as Ivan suggested, section 8.3 of the excellent and well-researched of Ivan's notes which has absolutely everything you need, get it running (independent of your application), and then just use that client instead of developing your own client from scratch (like in the above link).

This path will be easier for you, and the net result is the same ... a working client application ... with the difference that instead of you writing custom code (like in the above link) to handle the SSL part, you focus on your actual problem and let Axis handle that for you.
Nicky Eng
Ranch Hand

Joined: Mar 26, 2005
Posts: 378
I have tried all steps already and i found out the exception is not just 'bad certificate' but also at the end of the stack trace, it said "java.lang.NullPointerException" as show below




what possible could caused this bad_certificate & NULL pointer Exception ?

the process of SSL handshake is this:
1. Server Hello
2. Client Hello
3. Certificate chain
4. found trusted certificate
5. Certificate request
6. Server Hello done.
7. Certificate chain
8. ClientKeyExchange, RSA PreMasterSecret, TLSv1 <-- finished
9. verify_data <-- this process hit error when it reach below process :




what else i can do ?
R Srini
Ranch Hand

Joined: Feb 19, 2010
Posts: 215
Well, have you actually tried - step by step - the tutorial linked I posted earlier: http://www.herongyang.com/JDK/ssl_client_auth.html and actually got it to work? I am asking because it worked for me. I would suggest that you put your program aside for a moment, and try the tutorial if you haven't already. First, get that to work with the certificates created in that tutorial. Then, use your certificates with that program. See if you still get an error.

A couple of more thoughts:

1. We are assuming that the server already has added your client cert to the server's trust store. But this may not be the case. So maybe you can confirm with the web service provider to make sure that your client cert is indeed added to the server.
2. Your client test certificate has a .p12 extension, meaning that its a PKCS12 certificate. So when getting the keystore, you probably need to get the keystore like this: KeyStore.getInstance("PKCS12"). Is this the issue?

If you still have issues, then I would suggest you attach your bare minimum code to your next post and I can try it with some certificates I have. Without the actual code that throws the NullPointerException ... it is difficult to help.
Nicky Eng
Ranch Hand

Joined: Mar 26, 2005
Posts: 378
Many thanks to Srini here for your kind advice.

The main problem having the 'bad certificate' simply because of our provider did not import the certificate into the correct server, in this case is the test-server.

The problem is resolved after we had arranged meeting with their technical team.
I'm so happy that now its clear.



Still, many thanks to Srini. You have been very helpful here.

Regards
Nick
R Srini
Ranch Hand

Joined: Feb 19, 2010
Posts: 215
Excellent news, Nicky! All the best.
Bhaskar ramaiah
Greenhorn

Joined: Jun 26, 2012
Posts: 2
Hi Team,

I am also getting same bad_certificate problem. Below is the log sniffet, please help me to come out of this issue.

My server is tomcat (client) and other party is TIBCO web server (server)

Regards,

Bhaskar

06/2012 09:48:07:190 INFO - I/O exception (org.apache.axis2.AxisFault) caught when processing request: Received fatal alert: bad_certificate
26/06/2012 09:48:07:190 DEBUG - Received fatal alert: bad_certificate
org.apache.axis2.AxisFault: Received fatal alert: bad_certificate
at org.apache.axis2.AxisFault.makeFault(AxisFault.java:430)
at org.apache.axis2.transport.http.SOAPMessageFormatter.writeTo(SOAPMessageFormatter.java:83)
at org.apache.axis2.transport.http.AxisRequestEntity.writeRequest(AxisRequestEntity.java:84)
at org.apache.commons.httpclient.methods.EntityEnclosingMethod.writeRequestBody(EntityEnclosingMethod.java:499)
at org.apache.commons.httpclient.HttpMethodBase.writeRequest(HttpMethodBase.java:2114)
at org.apache.commons.httpclient.HttpMethodBase.execute(HttpMethodBase.java:1096)
at org.apache.commons.httpclient.HttpMethodDirector.executeWithRetry(HttpMethodDirector.java:398)
at org.apache.commons.httpclient.HttpMethodDirector.executeMethod(HttpMethodDirector.java:171)
at org.apache.commons.httpclient.HttpClient.executeMethod(HttpClient.java:397)
at org.apache.commons.httpclient.HttpClient.executeMethod(HttpClient.java:346)
at org.apache.axis2.transport.http.AbstractHTTPSender.executeMethod(AbstractHTTPSender.java:550)
at org.apache.axis2.transport.http.HTTPSender.sendViaPost(HTTPSender.java:189)
at org.apache.axis2.transport.http.HTTPSender.send(HTTPSender.java:75)
at org.apache.axis2.transport.http.CommonsHTTPTransportSender.writeMessageWithCommons(CommonsHTTPTransportSender.java:389)
at org.apache.axis2.transport.http.CommonsHTTPTransportSender.invoke(CommonsHTTPTransportSender.java:222)
at org.apache.axis2.engine.AxisEngine.send(AxisEngine.java:435)
at org.apache.axis2.description.OutInAxisOperationClient.send(OutInAxisOperation.java:402)
at org.apache.axis2.description.OutInAxisOperationClient.executeImpl(OutInAxisOperation.java:229)
at org.apache.axis2.client.OperationClient.execute(OperationClient.java:165)
at connectivity.ws.beans.QIIBServiceStub.cREDIT_CARD_BALANCE(QIIBServiceStub.java:479)
at flow.CallWSForBalance.servletImplementation(CallWSForBalance.java:113)
at com.avaya.sce.runtime.BasicServlet.handleRequest(BasicServlet.java:99)
at com.avaya.sce.runtime.AppServlet.processRequest(AppServlet.java:96)
at com.avaya.sce.runtime.SCEServlet.requestHandler(SCEServlet.java:282)
at com.avaya.sce.runtime.SCEServlet.doPost(SCEServlet.java:189)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:637)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at org.apache.catalina.core.ApplicationDispatcher.invoke(ApplicationDispatcher.java:646)
at org.apache.catalina.core.ApplicationDispatcher.processRequest(ApplicationDispatcher.java:436)
at org.apache.catalina.core.ApplicationDispatcher.doForward(ApplicationDispatcher.java:374)
at org.apache.catalina.core.ApplicationDispatcher.forward(ApplicationDispatcher.java:302)
at com.avaya.sce.runtime.SCEServlet.forward(SCEServlet.java:1303)
at com.avaya.sce.runtime.Data.evaluateActions(Data.java:211)
at flow.CardNo.executeDataActions(CardNo.java:94)
at com.avaya.sce.runtime.Data.handleRequest(Data.java:104)
at com.avaya.sce.runtime.AppServlet.processRequest(AppServlet.java:96)
at com.avaya.sce.runtime.SCEServlet.requestHandler(SCEServlet.java:282)
at com.avaya.sce.runtime.SCEServlet.doPost(SCEServlet.java:189)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:637)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:298)
at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:857)
at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:588)
at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:489)
at java.lang.Thread.run(Unknown Source)
Caused by: com.ctc.wstx.exc.WstxIOException: Received fatal alert: bad_certificate
at com.ctc.wstx.sw.BaseStreamWriter.flush(BaseStreamWriter.java:313)
at org.apache.axiom.om.impl.MTOMXMLStreamWriter.flush(MTOMXMLStreamWriter.java:168)
at org.apache.axis2.databinding.utils.writer.MTOMAwareXMLSerializer.flush(MTOMAwareXMLSerializer.java:79)
at org.apache.axis2.databinding.ADBDataSource.serialize(ADBDataSource.java:94)
at org.apache.axiom.om.impl.llom.OMSourcedElementImpl.internalSerializeAndConsume(OMSourcedElementImpl.java:738)
at org.apache.axiom.om.impl.llom.OMElementImpl.internalSerialize(OMElementImpl.java:966)
at org.apache.axiom.om.impl.llom.OMElementImpl.internalSerializeAndConsume(OMElementImpl.java:995)
at org.apache.axiom.soap.impl.llom.SOAPEnvelopeImpl.serializeInternally(SOAPEnvelopeImpl.java:254)
at org.apache.axiom.soap.impl.llom.SOAPEnvelopeImpl.internalSerialize(SOAPEnvelopeImpl.java:242)
at org.apache.axiom.om.impl.llom.OMElementImpl.internalSerializeAndConsume(OMElementImpl.java:995)
at org.apache.axiom.om.impl.llom.OMNodeImpl.serializeAndConsume(OMNodeImpl.java:486)
at org.apache.axis2.transport.http.SOAPMessageFormatter.writeTo(SOAPMessageFormatter.java:79)
... 52 more
Caused by: javax.net.ssl.SSLHandshakeException: Received fatal alert: bad_certificate
at com.sun.net.ssl.internal.ssl.Alerts.getSSLException(Unknown Source)
at com.sun.net.ssl.internal.ssl.Alerts.getSSLException(Unknown Source)
at com.sun.net.ssl.internal.ssl.SSLSocketImpl.recvAlert(Unknown Source)
at com.sun.net.ssl.internal.ssl.SSLSocketImpl.readRecord(Unknown Source)
at com.sun.net.ssl.internal.ssl.SSLSocketImpl.performInitialHandshake(Unknown Source)
at com.sun.net.ssl.internal.ssl.SSLSocketImpl.writeRecord(Unknown Source)
at com.sun.net.ssl.internal.ssl.AppOutputStream.write(Unknown Source)
at java.io.BufferedOutputStream.flushBuffer(Unknown Source)
at java.io.BufferedOutputStream.flush(Unknown Source)
at java.io.FilterOutputStream.flush(Unknown Source)
at org.apache.commons.httpclient.ChunkedOutputStream.flush(ChunkedOutputStream.java:191)
R Srini
Ranch Hand

Joined: Feb 19, 2010
Posts: 215
Hello Bhaskar, Have you tried turning on debug mode to see what is going on?

Please see here for an example: http://docs.oracle.com/javase/1.5.0/docs/guide/security/jsse/ReadDebug.html

And here for options: http://docs.oracle.com/javase/6/docs/technotes/guides/security/jsse/JSSERefGuide.html#Debug

When running your application, start it with -Djavax.net.debug=all or or one of the other allowed options. You will
be able to figure out the problem yourself.

Best regards,
Srini
Bhaskar ramaiah
Greenhorn

Joined: Jun 26, 2012
Posts: 2
Thanks for the reply Shrini, that problem got resolved after a long strugle, other party was expecting private key and certificate information apart from keystore value, hence we specified both in server.xml, it started working.

SSLCertificateFile="D:\ivrcertificate.pem"
SSLCertificateKeyFile="D:\ivrcertificate.pem"
Azahrudhin Mohammad
Greenhorn

Joined: Sep 04, 2012
Posts: 18

Hi Guys,
I wanted to consume secure webservice. , implementing the digital certificate at Webservice client, Please share the views If any.

01. I have generated the client code using Axis2 (WebServiceStub extends org.apache.axis2.client.Stub)
%AXIS2_HOME%\bin\WSDL2Java -uri wsdlURL -p pkgName -d xmlbeans -s
02. I have a certificate MyCertificate.cer generated as per the instructions from the Webservice Provider.
Generated KeyStore
keytool -genkey -alias mykeystore1-keyalg RSA -keystore mykeystore.jks
03. Imported the certificate to the jks file
keytool -import -trustcacerts -alias unicert -file MyCertificate.cer -keystore mykeystore.jks
04. Please help to write the client program using cert file.

If any can write the process of accessing the webservice using cert file would be appreciated , I am cracking my head towards the problem no clue , please help me.

Thanks and Regards,
azahrudhin.mohd@gmail.com
 
I agree. Here's the link: http://aspose.com/file-tools
 
subject: 2-way ssl not working: bad certificate