Как динамически создать хранилище ключей BKS + сертификат в Android - PullRequest
0 голосов
/ 09 января 2012

У меня проблема с динамическим созданием (без использования keytool) хранилища ключей BKS + сертификат в Android.

Я уже создал хранилище ключей BKS с BouncyCastle в своем настольном приложении: СМ:

public class KeyStoreGenerator {

public static void main(String[] args){
    generateKeyStore("1234567", "Burcu Cinarci", "TU Dortmund", "Informatik", "Dortmund", "NRW", "DE");
}
public static void generateKeyStore(String password, String cn, String o, String ou, String l, String st, String c) {
    try {
        Security.addProvider(new BouncyCastleProvider()); 
        final java.security.KeyPairGenerator rsaKeyPairGenerator = java.security.KeyPairGenerator.getInstance("RSA");
        rsaKeyPairGenerator.initialize(2048);
        final KeyPair rsaKeyPair = 
rsaKeyPairGenerator.generateKeyPair();

        // Generate the key store de type JCEKS
        Provider[] ps = Security.getProviders();
        for (int i = 0; i < ps.length; i++)
            System.out.println("" + ps[i].getName());

        final KeyStore ks = KeyStore.getInstance("BKS");
        ks.load(null);

        final RSAPublicKey rsaPublicKey = (RSAPublicKey) rsaKeyPair.getPublic();

        System.out.println("LOG: format "+rsaPublicKey.getFormat());
        char[] pw = password.toCharArray();

        final RSAPrivateKey rsaPrivateKey = (RSAPrivateKey) rsaKeyPair.getPrivate();
        final java.security.cert.X509Certificate certificate = makeCertificate(rsaPrivateKey, rsaPublicKey, cn, o, ou, l, st, c);
        final java.security.cert.X509Certificate[] certificateChain = { certificate };

certificateChain);
        ks.setKeyEntry("operator", rsaKeyPair.getPrivate(), pw, certificateChain);

        File keyStoreFile= new File("keyStore.ks");
        final FileOutputStream fos = new FileOutputStream(
                keyStoreFile);
        ks.store(fos, pw);
        fos.close();
        System.out.println(keyStoreFile.getAbsolutePath());

        System.setProperty("javax.net.ssl.keyStore",
                keyStoreFile.getAbsolutePath());
        System.setProperty("javax.net.ssl.keyStorePassword", "1234567");
    } catch (Exception e) {
        e.printStackTrace();
    }
}

public static X509Certificate makeCertificate(PrivateKey issuerPrivateKey,
        PublicKey subjectPublicKey, String cn, String o, String ou, String l, String st, String c) throws Exception {

    final org.bouncycastle.asn1.x509.X509Name issuerDN = new org.bouncycastle.asn1.x509.X509Name(
            "CN="+cn+", OU="+ou+", O="+o+", L="+l+", ST="+st+", C="+c);

    final org.bouncycastle.asn1.x509.X509Name subjectDN = new org.bouncycastle.asn1.x509.X509Name(
            "CN="+cn+", OU="+ou+", O="+o+", L="+l+", ST="+st+", C="+c);
    final int daysTillExpiry = 10 * 365;

    final Calendar expiry = Calendar.getInstance();
    expiry.add(Calendar.DAY_OF_YEAR, daysTillExpiry);

    final org.bouncycastle.x509.X509V3CertificateGenerator certificateGenerator = new org.bouncycastle.x509.X509V3CertificateGenerator();

    certificateGenerator.setSerialNumber(java.math.BigInteger
            .valueOf(System.currentTimeMillis()));
    certificateGenerator.setIssuerDN(issuerDN);

    certificateGenerator.setSubjectDN(subjectDN);
    certificateGenerator.setPublicKey(subjectPublicKey);
    certificateGenerator.setNotBefore(new Date());
    certificateGenerator.setNotAfter(expiry.getTime());

    certificateGenerator.setSignatureAlgorithm("MD5WithRSA");

    return certificateGenerator.generate(issuerPrivateKey);
}

}

Но в моем Android SDK я не могу добавить файл Bouncycastle-JAR, потому что он уже включен в Android. (Надувной замок как провайдер уже существует)

Но почему я не могу найти пакет "org.bouncycastle ..."?

Следующий код в методе makeCertificate, который генерирует сертификат динамически, не работает, поскольку eclipse не может найти конкретный пакет:

final org.bouncycastle.asn1.x509.X509Name subjectDN = new    org.bouncycastle.asn1.x509.X509Name("CN="+cn+", OU="+ou+", O="+o+", L="+l+", 
ST="+st+", C="+c);

Я попытался добавить файл bouncycastle.jar дополнительно, но он не работает из-за избыточности bouncycastle.


спасибо за ваш пост .. проблема все еще в том, что андроид не знает классы X509V3CertificateGenerator и X509Principal.

Android не знает ни одного класса бодрящего замка. Я могу изменить класс X509Principal на X500Principal, который существует в пакете javax.security.auth.x500, но я не могу заменить любой класс для CertificateGenerator

1020 * ТНХ *

Ответы [ 2 ]

1 голос
/ 01 сентября 2016

Надувной замок, включенный в Android, "поврежден". Если вы хотите работать с полной библиотекой bouncycastle, как в настольном приложении, взгляните на библиотеку spongycastle .

По сути, это то же самое, что и Bouncycastle, за исключением того, что все имена пакетов были перемещены из org.bouncycastle. * В org.spongycastle. *.

Итак, включите в ваш код библиотеку spongycastle и замените каждый org.bouncycastle. * На org.spongycastle. * И он должен работать как шарм.

0 голосов
/ 10 января 2012

Я не знаю, почему вы получаете это исключение, и сообщение плохо читается из-за неправильного формата, но если ваша проблема - строка:

final org.bouncycastle.asn1.x509.X509Name issuerDN = new org.bouncycastle.asn1.x509.X509Name( "CN="+cn+", OU="+ou+", O="+o+", L="+l+", ST="+st+", C="+c);

Тебе это не нужно.

Выполните следующие действия:

String dn =  "CN="+cn+", OU="+ou+", O="+o+", L="+l+", ST="+st+", C="+c;
X509V3CertificateGenerator certificateGenerator = new X509V3CertificateGenerator();
certificateGenerator.setSubjectDN(new X509Principal(dn));  

Это должно сработать для вас.

...