| Message |
|
|
Hello,
This output doesn't show any error.
That one looks better indeed
Since the trial version of JCAPI that I downloaded ends on the 1st of March, we can't do any other test; is there any way to extends the trial time before buying it?
Since JCAPI 1.2.0, we have changed the process of how the product can be evaluated. You can download JCAPI 1.2.0 and evaluate it for 60 days extra. After the 60 days have passed, you can still download and evaluate JCAPI when a new version of JCAPI is released (see the JCAPI FAQ). So, don't you worry about your current expiration date.
Regards,
Tommy
|
 |
|
|
Hi Marco,
I'm very interested for jcapi library, and I would like to known about to pay it, and the licence.
Thanks for your interest.
The JCAPI license can be found here:
http://pheox.com/products/jcapi/license.txt
You can also find information about our license in the JCAPI FAQ
http://pheox.com/products/jcapi/faq.html#FA.17
When you feel ready to purchase JCAPI, then just send an e-mail to sales@pheox.com and we'll gladly help you through the buying process.
Ok, regarding your problem and given info:
1. The error code "2148532266" is a "SCARD_E_INVALID_CHV" error, which shortly means that the supplied PIN is incorrect. That error is returned by the SysGillo CSP when we want to calculate the size of the buffer required to hold the signature array to be generated, and your CSP should not return an error since access to the private key is not required during that operation (since the buffer size can be calculated from the public key's modulus). A question; did you enter the wrong PIN code for that operation or was there no PIN dialog shown at all?
2. It is very hard to determine your root problem since the test programs that failed initially did fail when JCAPI tried to acquire a context, but after running my new tests, these errors suddenly vanishes and everything seem to work fine except for the last certificate in test (i.e MY|AhP5uoI6cz6/BMbFhCH1FcYXpjs=) and that one fails for a totally different reason. Do you know if that certificate (and private key) functions correctly (creating signatures & decryption) in other crypto software?
It's a tough situation trying to debug your problem without required hardware. I would suggest that we (Pheox) will try to get hold of a similar card as yours in order for us to (hopefully) re-generate the same errors as you have encountered.
Could you please send us the software I mentioned earlier (just send it to support@pheox.com)? Please make sure that it is ok to distribute them to us (copyright legal stuff).
Regards,
Tommy
|
 |
|
|
Hi,
Thanks for the info.
I'm a bit confused here since the CheckCSP.exe reports 2 found certificates (with private keys) that are managed by the SysGillo CSP, while you earlier reported 4 certificates found. The CheckCSP.exe do basically the same thing as the JCAPI test program (hmm, it might be the fact you have certificates in the MY store without any private keys associated with them).
Well, we'll do a final test.
Please download and execute the extended CheckCSP.zip file below.
Do also compile and run the following Java program and send us the output generated by both programs (make sure that you have your smart card inserted during the tests):
import java.security.*;
import java.security.interfaces.RSAPrivateKey;
import java.security.cert.X509Certificate;
import com.pheox.jcapi.*;
public class TestSignature
{
public static void main(String[] args)
{
try {
Security.addProvider(new JCAPIProvider());
KeyStore ks = KeyStore.getInstance("msks", "JCAPI");
ks.load(null, null);
String alias = "MY|Ou/w6n6D3GyRoWROzg/uDg/X7oI=";
System.out.println("Test signing with alias: " + alias);
testSign(ks, alias);
alias = "MY|F4uD2dj7GrPZ+13eLt3guZqO0oI=";
System.out.println("Test signing with alias: " + alias);
testSign(ks, alias);
alias = "MY|DKwk6QyVkiPGNxeFwg0NdVPePi8=";
System.out.println("Test signing with alias: " + alias);
testSign(ks, alias);
alias = "MY|AhP5uoI6cz6/BMbFhCH1FcYXpjs=";
System.out.println("Test signing with alias: " + alias);
testSign(ks, alias);
System.out.println("Test done!.");
} catch(Throwable t) {
System.err.println("Example program failed.");
t.printStackTrace();
}
}
static void testSign(KeyStore ks, String alias)
{
try {
System.out.println("Get certificate.");
X509Certificate cert = (X509Certificate)ks.getCertificate(alias);
if(cert == null)
throw new Exception("No cert found.");
System.out.println("Alias is a key entry: " + ks.isKeyEntry(alias));
System.out.println("Get private key.");
RSAPrivateKey privateKey = (RSAPrivateKey)ks.getKey(alias, null);
if(privateKey == null)
throw new Exception("No private key found.");
System.out.println("Create signature.");
byte[] data = {1,2,3,4,5};
Signature s = Signature.getInstance("SHA1withRSA", "JCAPI");
s.initSign(privateKey);
s.update(data);
s.sign();
System.out.println("Signature was successfully created.");
} catch(Throwable t) {
t.printStackTrace();
}
}
}
Note: please do also download and install the latest version of JCAPI (v1.2.0).
Regards,
Tommy
|
 |
|
|
Hello,
"Impossible to found a procedure" I think this driver is not compatible with standard pkcs11.
As I mentioned in my previous post, do not use usbr30.dll as your PKCS#11 file since it's most certainly meant for your card reader.
I've created a small diagnostic tool which hopefully can give some more info about your problem.
Please do the following:
1. Download and unzip CheckCSP.zip
2. Insert your card into your reader.
3. Execute CheckCSP.exe
4. Send us the output generated by the program.
Thanks.
Regards,
Tommy
|
 |
|
|
Ok, I can try put together a diagnostic tool that operates towards the CAPI layer for you.
But first, I would like you to run the HWAlias test program that I put in a previous post, but replace the name of the PKCS#11 file "C:/WINDOWS/system32/usbr30.dll" to the correct PKCS#11 DLL file supplied by your CSP i.e SysGillo. As far as I know, the usbr30.dll file is a device driver file for your acr30 reader and not a PKCS#11 file.
When you have found the correct PKCS#11 file, then you can also check your token through the example file ShowPKCS11Info.java that is located in the examples directory (don't forget to add your PKCS#11 provider into that program).
Regards,
Tommy
|
 |
|
|
Hi,
Sorry, but we need to know at least the model ID of your card so we can get an identical card from a vendor. The ACR30 reader supports a vast amount of cards, so we really need to get the same as you got.
Where have you gotten your card from?
Regards,
Tommy
|
 |
|
|
Hello,
Thank you for your information.
Ok, since you can access your certificate (stored on your smart card) through Internet Explorer, it looks like you have installed the required MS CAPI driver for your CSP.
4) Can you explain me how to do this test because I can't understand how do it.
Just compile and run the test. The test program will list all certificates found in your MY store a.k.a the Personal store. All certificates located in the MY store usually has an associated private key. If you can find your certificate (stored on your smart card) in the output generated by the test program (look for your certificate's issuer- & subject DN), then it means that:
1. You have installed your CSP's CAPI driver.
2. JCAPI can access your certificate but not its private key.
3. The problem you have is probably caused by JCAPI not being able to access the key container in which your private key(s) reside.
4. JCAPI will display the correct CSP for you certificate. Hopefully it will display " SysGillo Cryptographic Service Provider".
The best way to solve your problem is through actual hardware. We've found a vendor for the ACR30 reader, but more importantly, we need:
1. A similar, or identical, card as yours which can be handled by the SysGillo CSP.
2. The SysGillo CSP MS CAPI driver (EXE file).
3. The SysGillo PKCS#11 driver (DLL file).
4. A certificate management tool for your smart card since we need to install a cert chain and private key into the smart card for testing purpose.
Where can we get the above mentioned items? If you have a spare card to do without, then please send it to us if possible (including the drivers).
Regards,
Tommy
|
 |
|
|
Hi,
It seems like your given Cryptographic Service Provider (CSP) cannot be found. According to your source code, you used the string "Cryptographic Service Provider" as your CSP. I'm a bit sceptical that your CSP is correct. Usually the CSP vendors uses a unique name for their CSP e.g. "FTSafe ePass2000 RSA Cryptographic Service Provider".
Please note that the CSP name is associated with the MS CAPI driver for your hardware token, meaning that you can only use our PKCS#11 layer for your HW token if you have already installed the MS CAPI driver for that token, meaning that you cannot use a PKCS#11 DLL only.
Please verify the following:
1. You have installed the MS CAPI driver(s) for your HW token.
2. Can you use your HW token and access its certificates and keys through any other programs?
3. When you have plugged in your HW token to your computer, can you then see the certificate (associated with your private key) in the Personal store in Internet Explorer (Tools->Internet Options->Content->Certificates)?
4. Can you access your certificate stored on your HW token without adding your PKCS#11 DLL driver i.e can you recognise/find your certificate when we list all certificates from the Personal store in the example below (this example will also display the CSP name for each found certificate)?
import java.security.*;
import com.pheox.jcapi.*;
public class ListCertsCSP
{
public static void main(String[] args)
{
try {
Security.addProvider(new JCAPIProvider());
KeyStore ks = KeyStore.getInstance("msks", "JCAPI");
ks.load(null, null);
JCAPIProperties.getInstance().setMSCertStoreNames(new String[]{"MY"});
for(java.util.Enumeration e = ks.aliases(); e.hasMoreElements(); )
{
String alias = (String)e.nextElement();
System.out.println("Alias: " + alias);
System.out.println("CSP: " + JCAPIUtil.getCSP(alias));
System.out.println("Certificate:\n" + ks.getCertificate(alias));
System.out.println("\n**************************************************\n");
}
} catch(Throwable t) {
System.err.println("Example program failed.");
t.printStackTrace();
}
}
}
Also, can you please provide the following:
1. The output from calling method JCAPIUtil.getEnvironmentInfo().
2. What's the name/model of your HW token? Who is the vendor and manufacturer? Where can we get one (Web site, address etc)?
Regards,
Tommy
|
 |
|
|
Hi,
You cannot access the private key stored on your hardware token as you do:
char[] pin="MYPIN".toCharArray();
ks.load(null, pin);
Calling ks.load(null, pin) will just initialise/load the key store as defined in the JCE standard.
A good start to know how to access the private key is by examining and running our test program ExportPrivateKey.java that is stored in the default examples directory: C:\JCAPI\examples
When you want to access the private key directly, then you have to access/address it through its alias name. If you don't know the alias of your key, then you have to enumerate it from the JCAPI key store.
Here's an example of a test program that will print out the alias of all key entries (certificate and its associated private key) that can be found on a hardware token accessed through PKCS#11:
import java.security.*;
import com.pheox.jcapi.*;
public class HWAlias
{
public static void main(String[] args)
{
try {
Security.addProvider(new JCAPIProvider());
String cspName = "Cryptographic Service Provider";
String fileName = "C:/WINDOWS/system32/usbr30.dll";
JCAPIUtil.addPKCS11CSP(cspName, fileName);
KeyStore ks = KeyStore.getInstance("msks", "JCAPI");
ks.load(null, null);
System.out.println("Aliases of key entries stored on HW token:");
for(java.util.Enumeration e = ks.aliases(); e.hasMoreElements(); )
{
String alias = (String)e.nextElement();
if(ks.isKeyEntry(alias))
{
JCAPIRSAPrivateKey key = (JCAPIRSAPrivateKey)ks.getKey(alias, null);
if(JCAPIUtil.isPKCS11PrivateKey(key))
System.out.println(alias);
}
}
} catch(Throwable t) {
System.err.println("Example program failed.");
t.printStackTrace();
}
}
}
If the above example fails in some way, then please include your stack trace and/or your issues in your reply.
Once you have gotten your required alias, you can get its private key instance through KeyStore.getKey(String, String) (as shown above) and use it for decryption (the Cipher class) and creation of signatures (the Signature class) and more. A good starting point here is by studying the simple example files EncryptDecrypt1.java and CreateVerifySignature.java located in the examples directory as well.
Regards,
Tommy
|
 |
|
|
JCAPI version 1.2.0 has been released today.
New main features are:
- JCAPI is now supported on Java 6.
- JCAPI is now supported on Windows Vista.
- New MS CAPI based SecureRandom provider implemented.
- You can now configure what system store registry location to use. Please read chapter 5 Advanced Topics in the JCAPI User's Guide for more information.
- New method setExclusiveMSCertStore(KeyStore, String) in class JCAPIProperties to be used when you want a JCAPI KeyStore instance to operate on a specific MS CAPI certificate store regardless of other JCAPI KeyStore instances. Can, for example, be used for assigning a MS CAPI based trust store in SSL. Please read chapter 5 Advanced Topics in the JCAPI User's Guide for more information.
- The JCAPI SSL plugin now uses the new JCAPI SecureRandom provider as its default provider.
- JCAPI now automatically extracts the JCAPI.dll from inside the JCAPI.jar file and replaces an existing JCAPI.dll if they are not identical, meaning that you do not have to call JCAPIDLL.getInstance().setAlwaysOverwrite(true) any more. You can override this behaviour by calling JCAPIDLL.getInstance().setAlwaysOverwrite(false).
- More JCAPI example programs and extended SSL examples available.
Bug fixes made:
- The methods Signature.sign() and Cipher.doFinal() did not throw a JCAPIJNIInvalidPINCodeException instance when an incorrect PIN code was given during access to a private key through PKCS#11. Instead, the PIN callback was invoked again.
- JCAPI did hang when a user-defined PIN callback instance accessed the PKCS#11 token inside the getPINCode(...) method. The second access did cause the token to finalize prematurely and thus closing all resources for the JCAPI PKCS#11 layer thread invoking the callback method.
- A PKCS#11 DLL could not be found/loaded when its file name, or directory path, contained non-ASCII characters (locale support).
- Method JCAPIUtil.getPKCS11TokenInfo(String) threw a JCAPIJNIRuntimeException saying "JCAPIUtil_getPKCS11TokenInfo() - Could not get info about the PKCS#11 hardware token. Error code: 20" when a certificate stored on a PKCS#11 token had been copied into a MS CAPI system store, but the token itself was later removed/detached. Now the method returns null instead.
- Method JCAPIUtil.setCertificateFriendlyName(String,String) stored the friendly name in MS CAPI without proper Unicode EOS character.
- Patched the JCAPI SSL plugin for Java v1.3 since JSSE did create incorrect issuer distinguished names for some certificates.
- JCAPI, just like MS CAPI, now handles the system store names in a case insensitive manner to avoid problems when accessing stores such as ADDRESSBOOK/addressbook.
For a complete list of enhancements and bug fixes made, please read the version history.
The JCAPI.dll file used in the evaluation version of JCAPI has now grown a bit in size due to applied protection mechanisms since JCAPI has been exposed for software piracy actions. The commercial version do not contain these measures and is now actually smaller than ever before since we have now compressed the sections in the DLL file.
Our customers can download the commercial (unrestricted) version from the customers download page. Others are welcome to download the evaluation version from our public download page.
|
 |
|
|
Hi MN,
It looks like you've used JCAPI together with an unsigned applet.
Our test applet (just like JCAPI) is signed with a qualified Java code signing certificate (our is issued by Thawte) that is trusted by Java. The Java security model will only allow a "trusted applet" to access vital OS/Java functions. All other applets are considered untrusted and can thus only access a limited set of resources. A quick and small introduction of this subject can be viewed in section 8 Access Control at http://java.sun.com/javase/6/docs/technotes/guides/security/overview/jsoverview.html
In your current situation, there are a couple of possible solutions to overcome your problem:
- Buy yourself a qualified Java code signing certificate and use its associated private key to sign your applet.
or
- Modify your java.policy file to allow certain or all resources available in Java to your applet. This is a dirty fix solution that will only work on your local machine, but it's cheap and will allow testing of your applet until it gets signed and released to your customers. To implement this, add the following lines of code into your java.policy file (here I assume that the file is stored in " C:\Program Files\Java\jdk1.6.0\jre\lib\security" and that your applet is accessed through the URL " http://localhost/applettest". Please modify the URL below to meet your specific environment):
grant codeBase "http://localhost/applettest/-" {
permission java.security.AllPermission;
};
Btw, hope JCAPI will meet your needs, and have a nice weekend.
Regards,
Tommy
|
 |
|
|
Hi Michael,
Unfortunately, your private key must be exportable through MS CAPI when using it in Java SSL. This is not a JCAPI issue, it's a limitation in the JSSE framework.
If you want to get around this, then buy yourself a PKCS#11 hardware token, store your private key and certificate chain on the token. and then use it together with SUN's PKCS#11 provider (available in Java 5). This is also the most secure solution for you if securing your private key is of most importance.
Regards,
Tommy
|
 |
|
|
Hi,
We have now added your needed functionality into JCAPI. This is a very early release candidate of the next version (v1.2), so we have decided to not publish it on our public download page. Instead you can download it from the link below.
Note: make sure that you delete the old JCAPI DLL file before you use the new JCAPI JAR file:
C:\Documents and Settings\ your user\Local Settings\Temp\JCAPI.dll
The following new methods have been added into the JCAPIProperties class:
- void setSystemStoreRegistryLocation(JCAPISystemStoreRegistryLocation location) - Set JCAPI to use a new registry location.
- JCAPISystemStoreRegistryLocation getSystemStoreRegistryLocation() - Get current location used by JCAPI.
- void resetSystemStoreRegistryLocation() - Tell JCAPI to use the default registry location which is the current user i.e JCAPISystemStoreRegistryLocation.CERT_SYSTEM_STORE_CURRENT_USER
The new class JCAPISystemStoreRegistryLocation defines the following static registry locations for your convenience:
- CERT_SYSTEM_STORE_CURRENT_SERVICE
- CERT_SYSTEM_STORE_CURRENT_USER
- CERT_SYSTEM_STORE_CURRENT_USER_GROUP_POLICY
- CERT_SYSTEM_STORE_LOCAL_MACHINE
- CERT_SYSTEM_STORE_LOCAL_MACHINE_ENTERPRISE
- CERT_SYSTEM_STORE_LOCAL_MACHINE_GROUP_POLICY
- CERT_SYSTEM_STORE_SERVICES
- CERT_SYSTEM_STORE_USERS
In your specific case when using the local machine, you could use the following code:
JCAPISystemStoreRegistryLocation location =
new JCAPISystemStoreRegistryLocation(JCAPISystemStoreRegistryLocation.CERT_SYSTEM_STORE_LOCAL_MACHINE);
JCAPIProperties.getInstance().setSystemStoreRegistryLocation(location);
Please let us know if you encounter any problems.
Regards,
Tommy
|
 |
|
|
Hi,
The password parameter in the KeyStore.getKey() method is ignored by JCAPI, see the method description of JCE implementation class JCAPIKeyStore.engineGetKey() in the JCAPI Javadoc:
http://pheox.com/products/jcapi/javadoc/index.html
The reason for ignoring the parameter is that JCAPI has no control of the protection mechanism of the key since it is exclusively handled by Microsoft's CryptoAPI (MS CAPI). This might be more obvious when you are trying to export a private key from MS CAPI that is password protected. In these occasions, MS CAPI will launch a native GUI password dialog for the user to enter his/her password in order to access the specific private key. This dialog, and the private key decryption mechanism is not available for JCAPI. JCAPI will either receive the private key or an error code if the private key could not be exported through MS CAPI (depending on the user's given password, and if the key is exportable or not).
You can test this yourself by creating a RSA private key in Java and store it in MS CAPI through JCAPI by running the JCAPI example program CreateKeyEntry.java. The shown dialogs (that suggests different protection/security levels) are displayed by MS CAPI and is not known, neither handled, by JCAPI i.e JCAPI will not know of you choose to protect the key with a password or not.
Regards,
Tommy
|
 |
|
|
Hi,
The bad news is that JCAPI is hardcoded to use CERT_SYSTEM_STORE_CURRENT_USER as the high word of the input flags to the MS CAPI function 'CertOpenStore()', which shortly means that you can only get the certificates for the current user.
The good news is that the high word is already defined in a global variable that is OR:ed with the flags for each invocation of the CertOpenStore() function, which means that it's simple to solve your issue. We can just add a new Java method (and some constants for the different system store registry locations) which will give the user the opportunity to change the global variable via JNI.
We can add this new functionality into the next JCAPI maintenance release (which is currently under development) and supply you with a release candidate at the end of this week.
Regards,
Tommy
|
 |
|
|
|
|