public static APrivateKey getRSAPrivateKey(byte[] b) throws Exception { ASN1InputStream in = new ASN1InputStream(b); try { ASN1Primitive x = in.readObject(); RSAPrivateKey k = RSAPrivateKey.getInstance(x); return new APrivateKey(new RSAPrivateCrtKeyParameters ( k.getModulus(), k.getPublicExponent(), k.getPrivateExponent(), k.getPrime1(), k.getPrime2(), k.getExponent1(), k.getExponent2(), k.getCoefficient() )); } finally { CKit.close(in); } }
/** * Generates RSA key pair with the specified key size in bits and strength. * See http://stackoverflow.com/questions/3087049/bouncy-castle-rsa-keypair-generation-using-lightweight-api * suggested strength = 80000 * keySizeBits = 4096 */ public static AKeyPair createRSAKeyPair(int keySizeBits, int strength) throws Exception { BigInteger publicExponent = BigInteger.valueOf(0x10001); SecureRandom rnd = new SecureRandom(); RSAKeyGenerationParameters p = new RSAKeyGenerationParameters(publicExponent, rnd, keySizeBits, strength); RSAKeyPairGenerator g = new RSAKeyPairGenerator(); g.init(p); AsymmetricCipherKeyPair kp = g.generateKeyPair(); RSAPrivateCrtKeyParameters pri = (RSAPrivateCrtKeyParameters)kp.getPrivate(); RSAKeyParameters pub = (RSAKeyParameters)kp.getPublic(); return new AKeyPair(new APrivateKey(pri), new APublicKey(pub)); }
/** * Calculates the signature of a ticket and updates the given {@link Ticket} object directly. * * @throws IllegalStateException * If ticket cannot be signed. */ public void signTicket(Ticket ticket) throws IllegalStateException { byte[] serialized = TicketUtil.serialize(ticket); byte[] claimBytes = TicketUtil.deserialize(ByteBuffer.wrap(serialized)).getRight(); RSAPrivateCrtKeyParameters signingKey = keyManager.getPrivateSigningKey(); if (signingKey == null) throw new IllegalStateException("Cannot sign ticket because there is no private signing key available."); RSADigestSigner signer = new RSADigestSigner(new SHA256Digest()); signer.init(true, signingKey); signer.update(claimBytes, 0, claimBytes.length); try { byte[] signature = signer.generateSignature(); ticket.setSignature(signature); } catch (DataLengthException | CryptoException e) { throw new IllegalStateException("Cannot sign ticket", e); } }
/** * <p> * Encode (serialise) a private key in order to store it or transport it over a network. * </p><p> * <b>Important: You should keep your private key secret!</b> Thus, you might want to encrypt the result before * storing it to a file or sending it somewhere! * </p> * @param privateKey the private key to be encoded; must not be <code>null</code>. * @return the encoded (serialised) form of the private key. Can be passed to {@link #decodePrivateKey(byte[])} to * reverse this method. * @see #decodePrivateKey(byte[]) * @see #encodePublicKey(CipherParameters) */ public byte[] encodePrivateKey(final CipherParameters privateKey) { if (privateKey == null) throw new IllegalArgumentException("privateKey == null"); // TODO use a class-based map or similar registry! try { if (privateKey instanceof RSAPrivateCrtKeyParameters) { final RSAPrivateCrtKeyParameters rsaPrivateKey = (RSAPrivateCrtKeyParameters) privateKey; final PrivateKeyInfo info = new PrivateKeyInfo( new AlgorithmIdentifier(PKCSObjectIdentifiers.rsaEncryption, DERNull.INSTANCE), new RSAPrivateKey( rsaPrivateKey.getModulus(), rsaPrivateKey.getPublicExponent(), rsaPrivateKey.getExponent(), rsaPrivateKey.getP(), rsaPrivateKey.getQ(), rsaPrivateKey.getDP(), rsaPrivateKey.getDQ(), rsaPrivateKey.getQInv()).toASN1Primitive() ); return info.getEncoded(); } } catch (final IOException x) { throw new RuntimeException(x); } throw new UnsupportedOperationException("privateKey.class=\"" + privateKey.getClass().getName() + "\" not yet supported!"); }
@Override public CryptoKeyPair generateRSA1024KeyPair() { RSAKeyPairGenerator generator = new RSAKeyPairGenerator(); generator.init(new RSAKeyGenerationParameters( RSA_EXPONENT, RuntimeRandomProvider.INSTANCE, RSA_1024_STREIGHT, RSA_CERTAINITY)); Log.d("RSA", "Starting key generation..."); AsymmetricCipherKeyPair res = generator.generateKeyPair(); // Building x.509 public key RSAKeyParameters rsaPublicKey = (RSAKeyParameters) res.getPublic(); byte[] publicKey = new X509RsaPublicKey(rsaPublicKey.getModulus(), rsaPublicKey.getExponent()).serialize(); // Building PKCS#8 key RSAPrivateCrtKeyParameters parameter = (RSAPrivateCrtKeyParameters) res.getPrivate(); byte[] privateKey = new PKS8RsaPrivateKey(parameter.getModulus(), parameter.getExponent()).serialize(); return new CryptoKeyPair(publicKey, privateKey); }
private static void generateTestVector(int rsaKeyBits, int suffix) throws Exception { AsymmetricCipherKeyPair pair = generateKeyPair(rsaKeyBits); RSAPrivateCrtKeyParameters priv = (RSAPrivateCrtKeyParameters) pair.getPrivate(); byte[] message = new byte[rsaKeyBits / 8]; SECURE_RANDOM.nextBytes(message); // Clear the top bit to ensure it fits. message[0] &= 0x7F; RSAEngine encoder = new RSAEngine(); encoder.init(true, pair.getPrivate()); byte[] signed = encoder.processBlock(message, 0, message.length); RSAEngine decoder = new RSAEngine(); decoder.init(false, pair.getPublic()); byte[] decoded = decoder.processBlock(signed, 0, message.length); Assert.assertArrayEquals(message, decoded); System.out.println("public static final TestVector VECTOR" + suffix + " = "); new TestVector(new BigInteger(1, message), new BigInteger(1, signed), (RSAPrivateCrtKeyParameters) pair.getPrivate()).printJavaConstructorFor(); System.out.println(); }
private AsymmetricCipherKeyPair generateLongFixedKeys() { RSAKeyParameters pubKeySpec = new RSAKeyParameters( false, new BigInteger("a56e4a0e701017589a5187dc7ea841d156f2ec0e36ad52a44dfeb1e61f7ad991d8c51056ffedb162b4c0f283a12a88a394dff526ab7291cbb307ceabfce0b1dfd5cd9508096d5b2b8b6df5d671ef6377c0921cb23c270a70e2598e6ff89d19f105acc2d3f0cb35f29280e1386b6f64c4ef22e1e1f20d0ce8cffb2249bd9a2137",16), new BigInteger("010001",16)); RSAKeyParameters privKeySpec = new RSAPrivateCrtKeyParameters( new BigInteger("a56e4a0e701017589a5187dc7ea841d156f2ec0e36ad52a44dfeb1e61f7ad991d8c51056ffedb162b4c0f283a12a88a394dff526ab7291cbb307ceabfce0b1dfd5cd9508096d5b2b8b6df5d671ef6377c0921cb23c270a70e2598e6ff89d19f105acc2d3f0cb35f29280e1386b6f64c4ef22e1e1f20d0ce8cffb2249bd9a2137",16), new BigInteger("010001",16), new BigInteger("33a5042a90b27d4f5451ca9bbbd0b44771a101af884340aef9885f2a4bbe92e894a724ac3c568c8f97853ad07c0266c8c6a3ca0929f1e8f11231884429fc4d9ae55fee896a10ce707c3ed7e734e44727a39574501a532683109c2abacaba283c31b4bd2f53c3ee37e352cee34f9e503bd80c0622ad79c6dcee883547c6a3b325",16), new BigInteger("e7e8942720a877517273a356053ea2a1bc0c94aa72d55c6e86296b2dfc967948c0a72cbccca7eacb35706e09a1df55a1535bd9b3cc34160b3b6dcd3eda8e6443",16), new BigInteger("b69dca1cf7d4d7ec81e75b90fcca874abcde123fd2700180aa90479b6e48de8d67ed24f9f19d85ba275874f542cd20dc723e6963364a1f9425452b269a6799fd",16), new BigInteger("28fa13938655be1f8a159cbaca5a72ea190c30089e19cd274a556f36c4f6e19f554b34c077790427bbdd8dd3ede2448328f385d81b30e8e43b2fffa027861979",16), new BigInteger("1a8b38f398fa712049898d7fb79ee0a77668791299cdfa09efc0e507acb21ed74301ef5bfd48be455eaeb6e1678255827580a8e4e8e14151d1510a82a3f2e729",16), new BigInteger("27156aba4126d24a81f3a528cbfb27f56886f840a9f6e86e17a44b94fe9319584b8e22fdde1e5a2e3bd8aa5ba8d8584194eb2190acf832b847f13a3d24a79f4d",16)); return new AsymmetricCipherKeyPair(pubKeySpec, privKeySpec); }
static AsymmetricKeyParameter loadPrivateKeyResource(String resource) throws IOException { PemObject pem = loadPemResource(resource); if (pem.getType().endsWith("RSA PRIVATE KEY")) { RSAPrivateKey rsa = RSAPrivateKey.getInstance(pem.getContent()); return new RSAPrivateCrtKeyParameters(rsa.getModulus(), rsa.getPublicExponent(), rsa.getPrivateExponent(), rsa.getPrime1(), rsa.getPrime2(), rsa.getExponent1(), rsa.getExponent2(), rsa.getCoefficient()); } if (pem.getType().endsWith("PRIVATE KEY")) { return PrivateKeyFactory.createKey(pem.getContent()); } throw new IllegalArgumentException("'resource' doesn't specify a valid private key"); }
/** * construct a private key from it's org.bouncycastle.crypto equivalent. * * @param key the parameters object representing the private key. */ JCERSAPrivateCrtKey( RSAPrivateCrtKeyParameters key) { super(key); this.publicExponent = key.getPublicExponent(); this.primeP = key.getP(); this.primeQ = key.getQ(); this.primeExponentP = key.getDP(); this.primeExponentQ = key.getDQ(); this.crtCoefficient = key.getQInv(); }
/** * construct a private key from it's org.bouncycastle.crypto equivalent. * * @param key the parameters object representing the private key. */ BCRSAPrivateCrtKey( RSAPrivateCrtKeyParameters key) { super(key); this.publicExponent = key.getPublicExponent(); this.primeP = key.getP(); this.primeQ = key.getQ(); this.primeExponentP = key.getDP(); this.primeExponentQ = key.getDQ(); this.crtCoefficient = key.getQInv(); }
public KeyPair generateKeyPair() { AsymmetricCipherKeyPair pair = engine.generateKeyPair(); RSAKeyParameters pub = (RSAKeyParameters)pair.getPublic(); RSAPrivateCrtKeyParameters priv = (RSAPrivateCrtKeyParameters)pair.getPrivate(); return new KeyPair(new BCRSAPublicKey(pub), new BCRSAPrivateCrtKey(priv)); }
public static RSAKeyParameters generateRSAPrivateKeyParameter(RSAPrivateKey key) { ParamUtil.requireNonNull("key", key); if (key instanceof RSAPrivateCrtKey) { RSAPrivateCrtKey rsaKey = (RSAPrivateCrtKey) key; return new RSAPrivateCrtKeyParameters(rsaKey.getModulus(), rsaKey.getPublicExponent(), rsaKey.getPrivateExponent(), rsaKey.getPrimeP(), rsaKey.getPrimeQ(), rsaKey.getPrimeExponentP(), rsaKey.getPrimeExponentQ(), rsaKey.getCrtCoefficient()); } else { return new RSAKeyParameters(true, key.getModulus(), key.getPrivateExponent()); } }
public void performTest() throws Exception { BigInteger rsaPubMod = new BigInteger(Base64.decode("AIASoe2PQb1IP7bTyC9usjHP7FvnUMVpKW49iuFtrw/dMpYlsMMoIU2jupfifDpdFxIktSB4P+6Ymg5WjvHKTIrvQ7SR4zV4jaPTu56Ys0pZ9EDA6gb3HLjtU+8Bb1mfWM+yjKxcPDuFjwEtjGlPHg1Vq+CA9HNcMSKNn2+tW6qt")); BigInteger rsaPubExp = new BigInteger(Base64.decode("EQ==")); BigInteger rsaPrivMod = new BigInteger(Base64.decode("AIASoe2PQb1IP7bTyC9usjHP7FvnUMVpKW49iuFtrw/dMpYlsMMoIU2jupfifDpdFxIktSB4P+6Ymg5WjvHKTIrvQ7SR4zV4jaPTu56Ys0pZ9EDA6gb3HLjtU+8Bb1mfWM+yjKxcPDuFjwEtjGlPHg1Vq+CA9HNcMSKNn2+tW6qt")); BigInteger rsaPrivDP = new BigInteger(Base64.decode("JXzfzG5v+HtLJIZqYMUefJfFLu8DPuJGaLD6lI3cZ0babWZ/oPGoJa5iHpX4Ul/7l3s1PFsuy1GhzCdOdlfRcQ==")); BigInteger rsaPrivDQ = new BigInteger(Base64.decode("YNdJhw3cn0gBoVmMIFRZzflPDNthBiWy/dUMSRfJCxoZjSnr1gysZHK01HteV1YYNGcwPdr3j4FbOfri5c6DUQ==")); BigInteger rsaPrivExp = new BigInteger(Base64.decode("DxFAOhDajr00rBjqX+7nyZ/9sHWRCCp9WEN5wCsFiWVRPtdB+NeLcou7mWXwf1Y+8xNgmmh//fPV45G2dsyBeZbXeJwB7bzx9NMEAfedchyOwjR8PYdjK3NpTLKtZlEJ6Jkh4QihrXpZMO4fKZWUm9bid3+lmiq43FwW+Hof8/E=")); BigInteger rsaPrivP = new BigInteger(Base64.decode("AJ9StyTVW+AL/1s7RBtFwZGFBgd3zctBqzzwKPda6LbtIFDznmwDCqAlIQH9X14X7UPLokCDhuAa76OnDXb1OiE=")); BigInteger rsaPrivQ = new BigInteger(Base64.decode("AM3JfD79dNJ5A3beScSzPtWxx/tSLi0QHFtkuhtSizeXdkv5FSba7lVzwEOGKHmW829bRoNxThDy4ds1IihW1w0=")); BigInteger rsaPrivQinv = new BigInteger(Base64.decode("Lt0g7wrsNsQxuDdB8q/rH8fSFeBXMGLtCIqfOec1j7FEIuYA/ACiRDgXkHa0WgN7nLXSjHoy630wC5Toq8vvUg==")); RSAKeyParameters rsaPublic = new RSAKeyParameters(false, rsaPubMod, rsaPubExp); RSAPrivateCrtKeyParameters rsaPrivate = new RSAPrivateCrtKeyParameters(rsaPrivMod, rsaPubExp, rsaPrivExp, rsaPrivP, rsaPrivQ, rsaPrivDP, rsaPrivDQ, rsaPrivQinv); byte[] msg = new byte[] { 1, 6, 3, 32, 7, 43, 2, 5, 7, 78, 4, 23 }; X931Signer signer = new X931Signer(new RSAEngine(), new SHA1Digest()); signer.init(true, rsaPrivate); signer.update(msg, 0, msg.length); byte[] sig = signer.generateSignature(); signer = new X931Signer(new RSAEngine(), new SHA1Digest()); signer.init(false, rsaPublic); signer.update(msg, 0, msg.length); if (!signer.verifySignature(sig)) { fail("X9.31 Signer failed."); } shouldPassSignatureTest1(); shouldPassSignatureTest2(); shouldPassSignatureTest3(); }
private RSAPrivateCrtKeyParameters getPrivateKeyParameters(RSAPrivateCrtKey privateCrtKey) { return new RSAPrivateCrtKeyParameters(privateCrtKey.getModulus(), privateCrtKey.getPublicExponent(), privateCrtKey.getPrivateExponent(), privateCrtKey.getPrimeP(), privateCrtKey.getPrimeQ(), privateCrtKey.getPrimeExponentP(), privateCrtKey.getPrimeExponentQ(), privateCrtKey.getCrtCoefficient()); }
private static byte[] signData(ASN1ObjectIdentifier sigOID, byte[] data, RSAPrivateCrtKeyParameters privateKeyParameters, SecureRandom secureRandom) throws Exception { PrivateKey caPrivateKey = KeyFactory.getInstance("RSA").generatePrivate(getKeySpec(privateKeyParameters)); Signature signature = Signature.getInstance(sigOID.getId()); signature.initSign(caPrivateKey, secureRandom); signature.update(data); return signature.sign(); }
public static RSAPrivateKey toRSAPrivateKey(RSAPrivateCrtKeyParameters k) throws Exception { // hope this is correct return new RSAPrivateKey ( k.getModulus(), k.getPublicExponent(), k.getExponent(), k.getP(), k.getQ(), k.getDP(), k.getDQ(), k.getQInv() ); }
/** * construct a private key from it's org.bouncycastle.crypto equivalent. * * @param key the parameters object representing the private key. */ TempJCERSAPrivateCrtKey( RSAPrivateCrtKeyParameters key) { super(key); this.publicExponent = key.getPublicExponent(); this.primeP = key.getP(); this.primeQ = key.getQ(); this.primeExponentP = key.getDP(); this.primeExponentQ = key.getDQ(); this.crtCoefficient = key.getQInv(); }
public BigInteger processBlock(BigInteger input) { if (key instanceof RSAPrivateCrtKeyParameters) { // // we have the extra factors, use the Chinese Remainder Theorem - the author // wishes to express his thanks to Dirk Bonekaemper at rtsffm.com for // advice regarding the expression of this. // RSAPrivateCrtKeyParameters crtKey = (RSAPrivateCrtKeyParameters) key; BigInteger p = crtKey.getP(); BigInteger q = crtKey.getQ(); BigInteger dP = crtKey.getDP(); BigInteger dQ = crtKey.getDQ(); BigInteger qInv = crtKey.getQInv(); BigInteger mP, mQ, h, m; // mP = ((input mod p) ^ dP)) mod p mP = (input.remainder(p)).modPow(dP, p); // mQ = ((input mod q) ^ dQ)) mod q mQ = (input.remainder(q)).modPow(dQ, q); // h = qInv * (mP - mQ) mod p h = mP.subtract(mQ); h = h.multiply(qInv); h = h.mod(p); // mod (in Java) returns the positive residual // m = h * q + mQ m = h.multiply(q); m = m.add(mQ); return m; } else { return input.modPow( key.getExponent(), key.getModulus()); } }
@Test public void generates1024bitKeys() throws Exception { final AsymmetricCipherKeyPair pair = RsaKeyGenerator.rsa1024().generate(random); assertThat(pair.getPrivate()) .isInstanceOf(RSAPrivateCrtKeyParameters.class); final RSAPrivateCrtKeyParameters privateKey = (RSAPrivateCrtKeyParameters) pair.getPrivate(); assertThat(privateKey.getModulus().toByteArray().length) .isEqualTo(129); }
@Test public void generates2048bitKeys() throws Exception { final AsymmetricCipherKeyPair pair = RsaKeyGenerator.rsa2048().generate(random); assertThat(pair.getPrivate()) .isInstanceOf(RSAPrivateCrtKeyParameters.class); final RSAPrivateCrtKeyParameters privateKey = (RSAPrivateCrtKeyParameters) pair .getPrivate(); assertThat(privateKey.getModulus().toByteArray().length) .isEqualTo(257); }
@Test public void generates4096bitKeys() throws Exception { final AsymmetricCipherKeyPair pair = RsaKeyGenerator.rsa4096().generate(random); assertThat(pair.getPrivate()) .isInstanceOf(RSAPrivateCrtKeyParameters.class); final RSAPrivateCrtKeyParameters privateKey = (RSAPrivateCrtKeyParameters) pair .getPrivate(); assertThat(privateKey.getModulus().toByteArray().length) .isEqualTo(513); }
public BigInteger processBlock(BigInteger input) { if (key instanceof RSAPrivateCrtKeyParameters) { // // we have the extra factors, use the Chinese Remainder Theorem - the author // wishes to express his thanks to Dirk Bonekaemper at rtsffm.com for // advice regarding the expression of this. // RSAPrivateCrtKeyParameters crtKey = (RSAPrivateCrtKeyParameters)key; BigInteger p = crtKey.getP(); BigInteger q = crtKey.getQ(); BigInteger dP = crtKey.getDP(); BigInteger dQ = crtKey.getDQ(); BigInteger qInv = crtKey.getQInv(); BigInteger mP, mQ, h, m; // mP = ((input mod p) ^ dP)) mod p mP = (input.remainder(p)).modPow(dP, p); // mQ = ((input mod q) ^ dQ)) mod q mQ = (input.remainder(q)).modPow(dQ, q); // h = qInv * (mP - mQ) mod p h = mP.subtract(mQ); h = h.multiply(qInv); h = h.mod(p); // mod (in Java) returns the positive residual // m = h * q + mQ m = h.multiply(q); m = m.add(mQ); return m; } else { return input.modPow( key.getExponent(), key.getModulus()); } }
/** * Process a single block using the basic RSA algorithm. * * @param in the input array. * @param inOff the offset into the input buffer where the data starts. * @param inLen the length of the data to be processed. * @return the result of the RSA process. * @exception DataLengthException the input block is too large. */ public byte[] processBlock( byte[] in, int inOff, int inLen) { if (key == null) { throw new IllegalStateException("RSA engine not initialised"); } BigInteger input = core.convertInput(in, inOff, inLen); BigInteger result; if (key instanceof RSAPrivateCrtKeyParameters) { RSAPrivateCrtKeyParameters k = (RSAPrivateCrtKeyParameters)key; BigInteger e = k.getPublicExponent(); if (e != null) // can't do blinding without a public exponent { BigInteger m = k.getModulus(); BigInteger r = BigIntegers.createRandomInRange(ONE, m.subtract(ONE), random); BigInteger blindedInput = r.modPow(e, m).multiply(input).mod(m); BigInteger blindedResult = core.processBlock(blindedInput); BigInteger rInv = r.modInverse(m); result = blindedResult.multiply(rInv).mod(m); } else { result = core.processBlock(input); } } else { result = core.processBlock(input); } return core.convertOutput(result); }
/** * Process a single block using the basic RSA algorithm. * * @param in the input array. * @param inOff the offset into the input buffer where the data starts. * @param inLen the length of the data to be processed. * @return the result of the RSA process. * @exception DataLengthException the input block is too large. */ public byte[] processBlock( byte[] in, int inOff, int inLen) { if (key == null) { throw new IllegalStateException("RSA engine not initialised"); } BigInteger input = core.convertInput(in, inOff, inLen); BigInteger result; if (key instanceof RSAPrivateCrtKeyParameters) { RSAPrivateCrtKeyParameters k = (RSAPrivateCrtKeyParameters)key; BigInteger e = k.getPublicExponent(); if (e != null) // can't do blinding without a public exponent { BigInteger m = k.getModulus(); BigInteger r = BigIntegers.createRandomInRange(ONE, m.subtract(ONE), random); BigInteger blindedInput = r.modPow(e, m).multiply(input).mod(m); BigInteger blindedResult = core.processBlock(blindedInput); BigInteger rInv = r.modInverse(m); result = blindedResult.multiply(rInv).mod(m); // defence against Arjen Lenstra’s CRT attack if (!input.equals(result.modPow(e, m))) { throw new IllegalStateException("RSA engine faulty decryption/signing detected"); } } else { result = core.processBlock(input); } } else { result = core.processBlock(input); } return core.convertOutput(result); }