/* * Encrypt private key using Password-based encryption (PBE) * as defined in PKCS#5. * * NOTE: Currently pbeWithSHAAnd3-KeyTripleDES-CBC algorithmID is * used to derive the key and IV. * * @return encrypted private key encoded as EncryptedPrivateKeyInfo */ private byte[] encryptPrivateKey(byte[] data, char[] password) throws IOException, NoSuchAlgorithmException, UnrecoverableKeyException { byte[] key = null; try { // create AlgorithmParameters AlgorithmParameters algParams = getAlgorithmParameters("PBEWithSHA1AndDESede"); // Use JCE SecretKey skey = getPBEKey(password); Cipher cipher = Cipher.getInstance("PBEWithSHA1AndDESede"); cipher.init(Cipher.ENCRYPT_MODE, skey, algParams); byte[] encryptedKey = cipher.doFinal(data); // wrap encrypted private key in EncryptedPrivateKeyInfo // as defined in PKCS#8 AlgorithmId algid = new AlgorithmId(pbeWithSHAAnd3KeyTripleDESCBC_OID, algParams); EncryptedPrivateKeyInfo encrInfo = new EncryptedPrivateKeyInfo(algid, encryptedKey); key = encrInfo.getEncoded(); } catch (Exception e) { UnrecoverableKeyException uke = new UnrecoverableKeyException("Encrypt Private Key failed: " + e.getMessage()); uke.initCause(e); throw uke; } return key; }
private static byte[] gcmDecrypt(byte[] key, byte[] cipherText, byte[] aad, byte[] iv) throws AEADBadTagException { byte[] plainText = new byte[cipherText.length - BLOCK_SIZE]; try { SecretKeySpec keySpec = new SecretKeySpec(key, ALGORITHM); GCMParameterSpec gcmSpec = new GCMParameterSpec(GCM_TAG_LENGTH * 8, iv); Cipher cipher = Cipher.getInstance(ALGORITHM + "/" + MODE + "/NoPadding"); cipher.init(Cipher.DECRYPT_MODE, keySpec, gcmSpec); if (aad != null && aad.length != 0) { cipher.updateAAD(aad); } // store internally until decryptFinal is called cipher.doFinal(cipherText, 0, cipherText.length, plainText, 0); } catch (AEADBadTagException e) { System.out.println(e.getMessage()); throw e; } catch (Exception e) { System.out.println(e.getMessage()); } return plainText; }
private static byte[] gcmEncrypt(byte[] key, byte[] plainText, byte[] aad, byte[] iv) { byte[] cipherText = new byte[plainText.length + 16]; try { SecretKeySpec keySpec = new SecretKeySpec(key, ALGORITHM); GCMParameterSpec gcmSpec = new GCMParameterSpec(GCM_TAG_LENGTH * 8, iv); Cipher cipher = Cipher.getInstance(ALGORITHM + "/" + MODE + "/NoPadding"); cipher.init(Cipher.ENCRYPT_MODE, keySpec, gcmSpec); if (aad != null && aad.length != 0) { cipher.updateAAD(aad); } // if has more than one blocks, test cipher.update if (plainText.length > 16) { cipher.update(plainText, 0, 16, cipherText, 0); cipher.doFinal(plainText, 16, plainText.length - 16, cipherText, 16); } else { // doFinal(byte[] input, int inputOffset, int inputLen, byte[] output, int outputOffset) cipher.doFinal(plainText, 0, plainText.length, cipherText, 0); } } catch (Exception e) { System.out.println(e.getMessage()); } return cipherText; }
public boolean shareAESkey() { try { Envelope message = null, e = null; // Generate AES key KeyGenerator keyGen = KeyGenerator.getInstance("AES"); AESkey = keyGen.generateKey(); keyGen = KeyGenerator.getInstance("HmacSHA1"); HMACkey = keyGen.generateKey(); byte[] keyBytes = AESkey.getEncoded(); byte[] hashBytes = HMACkey.getEncoded(); System.out.println("AES key generated"); System.out.println("HMAC key generated"); System.out.println("Begin Encryption..."); // Encrypt message w/ provided public key Cipher cipher = Cipher.getInstance("RSA/ECB/PKCS1Padding"); cipher.init(Cipher.ENCRYPT_MODE, pubKey); byte[] cipherBytes = cipher.doFinal(keyBytes); byte[] cipherBytes1 = cipher.doFinal(hashBytes); System.out.println("Encryption Complete"); message = new Envelope("SKEY"); message.addObject(cipherBytes); // Add AESkey to message message.addObject(cipherBytes1); message.addObject(nonce); nonce++; byte[] messageBytes = Envelope.toByteArray(message); output.writeObject(messageBytes); byte[] inCipherBytes = (byte[]) input.readObject(); // Decrypt response cipher = Cipher.getInstance("AES"); cipher.init(Cipher.DECRYPT_MODE, AESkey); byte[] responseBytes = cipher.doFinal(inCipherBytes); Envelope response = Envelope.getEnvelopefromBytes(responseBytes); // If server indicates success, return the member list if (response.getMessage().equals("OK") && (Integer) response.getObjContents().get(0) == nonce) { return true; } else { return false; } } catch (Exception e) { System.err.println("Error: " + e.getMessage()); e.printStackTrace(System.err); return false; } }
/* * Generate PBE key */ private SecretKey getPBEKey(char[] password) throws IOException { SecretKey skey = null; try { PBEKeySpec keySpec = new PBEKeySpec(password); SecretKeyFactory skFac = SecretKeyFactory.getInstance("PBE"); skey = skFac.generateSecret(keySpec); } catch (Exception e) { IOException ioe = new IOException("getSecretKey failed: " + e.getMessage()); ioe.initCause(e); throw ioe; } return skey; }
/* * Generate PBE Algorithm Parameters */ private AlgorithmParameters getAlgorithmParameters(String algorithm) throws IOException { AlgorithmParameters algParams = null; // create PBE parameters from salt and iteration count PBEParameterSpec paramSpec = new PBEParameterSpec(getSalt(), iterationCount); try { algParams = AlgorithmParameters.getInstance(algorithm); algParams.init(paramSpec); } catch (Exception e) { IOException ioe = new IOException("getAlgorithmParameters failed: " + e.getMessage()); ioe.initCause(e); throw ioe; } return algParams; }
public void run() { try { BufferedReader br = new BufferedReader(new InputStreamReader(new FileInputStream(file), charset)); if (outputFile != null) { bw = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(outputFile), charset)); } String line; while ((line = br.readLine()) != null) { filePosition += line.length() + 2; line = line.trim(); if (!line.startsWith("#")) { String[] sides = split(line); if ((sides != null) && !sides[0].equals("key")) { if (searchPHI) { // Search the decrypted PHI for the searchText sides[0] = decrypt(sides[0]); if (sides[0].indexOf(searchText) != -1) { output(sides[0] + " = " + sides[1] + "\n"); } } else { // Search the trial ID for the searchText if (sides[1].indexOf(searchText) != -1) { sides[0] = decrypt(sides[0]); output(sides[0] + " = " + sides[1] + "\n"); } } } } } br.close(); if (bw != null) { bw.flush(); bw.close(); } } catch (Exception e) { append("\n\n" + e.getClass().getName() + ": " + e.getMessage() + "\n"); } append("\nDone.\n"); setMessage("Ready..."); }
/* * parse Algorithm Parameters */ private AlgorithmParameters parseAlgParameters(DerInputStream in) throws IOException { AlgorithmParameters algParams = null; try { DerValue params; if (in.available() == 0) { params = null; } else { params = in.getDerValue(); if (params.tag == DerValue.tag_Null) { params = null; } } if (params != null) { algParams = AlgorithmParameters.getInstance("PBE"); algParams.init(params.toByteArray()); } } catch (Exception e) { IOException ioe = new IOException("parseAlgParameters failed: " + e.getMessage()); ioe.initCause(e); throw ioe; } return algParams; }
/* * The previous caller failed for some reason, report back the * Exception. We won't worry about Error's. * * Locked by SSLEngine.this. */ void checkThrown() throws SSLException { synchronized (thrownLock) { if (thrown != null) { String msg = thrown.getMessage(); if (msg == null) { msg = "Delegated task threw Exception/Error"; } /* * See what the underlying type of exception is. We should * throw the same thing. Chain thrown to the new exception. */ Exception e = thrown; thrown = null; if (e instanceof RuntimeException) { throw (RuntimeException) new RuntimeException(msg).initCause(e); } else if (e instanceof SSLHandshakeException) { throw (SSLHandshakeException) new SSLHandshakeException(msg).initCause(e); } else if (e instanceof SSLKeyException) { throw (SSLKeyException) new SSLKeyException(msg).initCause(e); } else if (e instanceof SSLPeerUnverifiedException) { throw (SSLPeerUnverifiedException) new SSLPeerUnverifiedException(msg).initCause(e); } else if (e instanceof SSLProtocolException) { throw (SSLProtocolException) new SSLProtocolException(msg).initCause(e); } else { /* * If it's SSLException or any other Exception, * we'll wrap it in an SSLException. */ throw (SSLException) new SSLException(msg).initCause(e); } } } }
public boolean upload( String sourceFile, String destFile, String group, UserToken token, Key key, int keyNum) { if (destFile.charAt(0) != '/') { destFile = "/" + destFile; } try { FileInputStream fis = new FileInputStream(sourceFile); File encryptFile = new File(sourceFile + "_encrypt"); encryptFile.createNewFile(); FileOutputStream fos = new FileOutputStream(encryptFile); // Initial Vector must be 16 bytes byte[] initialVector = { 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7, 0x8, 0x9, 0xa, 0xb, 0xc, 0xd, 0xe, 0xf }; IvParameterSpec ivs = new IvParameterSpec(initialVector); byte[] buf = new byte[1024]; Cipher cipher = Cipher.getInstance("AES/CBC/NoPadding"); cipher.init(Cipher.ENCRYPT_MODE, key, ivs); byte[] cipherBytes; // create a new local encrypted file do { buf = new byte[1024]; int n = fis.read(buf); if (n > 0) { System.out.printf("."); } else if (n < 0) { System.out.println("Read error"); } cipherBytes = cipher.doFinal(buf); fos.write(cipherBytes); } while (fis.available() > 0); System.out.println(); // send encrypted file to server Envelope message = null, env = null; // Tell the server to return the member list message = new Envelope("UPLOADF"); message.addObject(destFile); message.addObject(group); message.addObject(token); message.addObject(keyNum); message.addObject(initialVector); String concat = destFile + group + token.toString() + keyNum + "UPLOADF" + nonce; // concatinates all of the objects in envelope byte[] hasharray = concat.getBytes(); // turn the concat into a byte array Mac mac = Mac.getInstance("HmacSHA1"); mac.init(HMACkey); mac.update(hasharray); String stringhash = new String(mac.doFinal(), "UTF8"); // turn the hash into a string for easy comparision! message.addObject(stringhash); message.addObject(nonce); nonce++; byte[] messageBytes = Envelope.toByteArray(message); // Encrypt envelope w/ AES cipher = Cipher.getInstance("AES"); cipher.init(Cipher.ENCRYPT_MODE, AESkey); cipherBytes = cipher.doFinal(messageBytes); output.writeObject(cipherBytes); byte[] responseCipherBytes = (byte[]) input.readObject(); // if response isnt ready it should check whether it was forged // Decrypt response cipher = Cipher.getInstance("AES"); cipher.init(Cipher.DECRYPT_MODE, AESkey); byte[] responseBytes = cipher.doFinal(responseCipherBytes); env = Envelope.getEnvelopefromBytes(responseBytes); if (env.getMessage().equals("READY")) { System.out.printf("Meta data upload successful\n"); } else if ((Integer) env.getObjContents().get(1) == nonce) { String hash = (String) env.getObjContents().get(0); concat = env.getMessage() + nonce; // reconstructs the hash hasharray = concat.getBytes(); mac = Mac.getInstance("HmacSHA1"); File HASHfile = new File("FHASHKey.bin"); fis = new FileInputStream(HASHfile); ObjectInputStream ois = new ObjectInputStream(fis); Key HMACkey = (Key) ois.readObject(); mac.init(HMACkey); mac.update(hasharray); String newhash = new String(mac.doFinal(), "UTF8"); nonce++; // check hashes for equality if (hash.equals(newhash) != true) { System.out.println("HASH EQUALITY FAIL2, disconnecting for your own safety"); disconnect(); return false; } } else { System.out.println("Nonce FAIL UPLOADF"); disconnect(); return false; } // If server indicates success, return the member list FileInputStream encryptFIS = new FileInputStream(encryptFile); do { if ((Integer) env.getObjContents().get(1) == nonce) { buf = new byte[1024]; if (!env.getMessage().equals("READY")) { System.out.printf("Server error: %s\n", env.getMessage()); return false; } String hash = (String) env.getObjContents().get(0); concat = env.getMessage() + nonce; // reconstructs the hash hasharray = concat.getBytes(); mac = Mac.getInstance("HmacSHA1"); File HASHfile = new File("FHASHKey.bin"); fis = new FileInputStream(HASHfile); ObjectInputStream ois = new ObjectInputStream(fis); Key HMACkey = (Key) ois.readObject(); mac.init(HMACkey); mac.update(hasharray); String newhash = new String(mac.doFinal(), "UTF8"); nonce++; ois.close(); // check hashes for equality if (hash.equals(newhash) != true) { System.out.println("HASH EQUALITY FAIL3, disconnecting for your own safety"); disconnect(); return false; } message = new Envelope("CHUNK"); int n = encryptFIS.read(buf); // can throw an IOException if (n > 0) { System.out.printf("."); } else if (n < 0) { System.out.println("Read error"); return false; } message.addObject(buf); message.addObject(new Integer(n)); concat = n + "CHUNK" + nonce; // concatinates all of the objects in envelope hasharray = concat.getBytes(); // turn the concat into a byte array mac = Mac.getInstance("HmacSHA1"); mac.init(HMACkey); mac.update(hasharray); stringhash = new String( mac.doFinal(), "UTF8"); // turn the hash into a string for easy comparision! message.addObject(stringhash); message.addObject(nonce); nonce++; messageBytes = Envelope.toByteArray(message); // Encrypt envelope w/ AES cipher = Cipher.getInstance("AES"); cipher.init(Cipher.ENCRYPT_MODE, AESkey); cipherBytes = cipher.doFinal(messageBytes); System.out.println("Concatsent" + concat); output.writeObject( cipherBytes); /////////////////////////////////////////// // HERE///////////////////////////////// responseCipherBytes = (byte[]) input.readObject(); // Decrypt response cipher.init(Cipher.DECRYPT_MODE, AESkey); responseBytes = cipher.doFinal(responseCipherBytes); env = Envelope.getEnvelopefromBytes(responseBytes); } else { System.out.println("Nonce FAIL UPLOADF"); disconnect(); return false; } } while (encryptFIS.available() > 0); encryptFIS.close(); // If server indicates success, return the member list if (env.getMessage().compareTo("READY") == 0 && (Integer) env.getObjContents().get(1) == nonce) { nonce++; message = new Envelope("EOF"); concat = "EOF" + nonce; // concatinates all of the objects in envelope hasharray = concat.getBytes(); // turn the concat into a byte array mac = Mac.getInstance("HmacSHA1"); mac.init(HMACkey); mac.update(hasharray); stringhash = new String(mac.doFinal(), "UTF8"); // turn the hash into a string for easy comparision! message.addObject(stringhash); message.addObject(nonce); System.out.println(nonce); nonce++; messageBytes = Envelope.toByteArray(message); // Encrypt envelope w/ AES cipher = Cipher.getInstance("AES"); cipher.init(Cipher.ENCRYPT_MODE, AESkey); cipherBytes = cipher.doFinal(messageBytes); output.writeObject(cipherBytes); responseCipherBytes = (byte[]) input.readObject(); // Decrypt response cipher.init(Cipher.DECRYPT_MODE, AESkey); responseBytes = cipher.doFinal(responseCipherBytes); env = Envelope.getEnvelopefromBytes(responseBytes); if (env.getMessage().compareTo("OK") == 0 && (Integer) env.getObjContents().get(1) == nonce) { System.out.printf("\nFile data upload successful\n"); } else if ((Integer) env.getObjContents().get(1) != nonce) { System.out.println("Nonce FAIL UPLOADF"); disconnect(); return false; } else { System.out.printf("\nUpload failed: %s\n", env.getMessage()); return false; } } else if ((Integer) env.getObjContents().get(1) != nonce) { System.out.println("Nonce FAIL UPLOADF"); disconnect(); return false; } else { System.out.printf("Upload failed: %s\n", env.getMessage()); return false; } } catch (Exception e1) { System.err.println("Error: " + e1.getMessage()); e1.printStackTrace(System.err); return false; } return true; }
@SuppressWarnings("unchecked") public List<String> listFiles(UserToken token) { try { Envelope env = null, e = null; // Tell the server to return the member list env = new Envelope("LFILES"); env.addObject(token); // Add requester's token String concat = token.toString() + "LFILES" + nonce; // concatinates all of the objects in envelope byte[] hasharray = concat.getBytes(); // turn the concat into a byte array Mac mac = Mac.getInstance("HmacSHA1"); mac.init(HMACkey); mac.update(hasharray); String stringhash = new String(mac.doFinal(), "UTF8"); // turn the hash into a string for easy comparision! env.addObject(stringhash); env.addObject(nonce); nonce++; byte[] envBytes = Envelope.toByteArray(env); // Encrypt envelope w/ AES Cipher cipher = Cipher.getInstance("AES"); cipher.init(Cipher.ENCRYPT_MODE, AESkey); byte[] cipherBytes = cipher.doFinal(envBytes); output.writeObject(cipherBytes); byte[] responseCipherBytes = (byte[]) input.readObject(); // Decrypt response cipher.init(Cipher.DECRYPT_MODE, AESkey); byte[] responseBytes = cipher.doFinal(responseCipherBytes); env = Envelope.getEnvelopefromBytes(responseBytes); if (env.getMessage().equals("FAIL")) { System.out.println("Error occured in ListFiles, disconnecting"); disconnect(); return null; } else if ((Integer) env.getObjContents().get(2) == nonce) { List<String> files = (List<String>) env.getObjContents().get(0); String hash = (String) env.getObjContents().get(1); concat = files.toString() + env.getMessage() + nonce; // reconstructs the hash hasharray = concat.getBytes(); mac = Mac.getInstance("HmacSHA1"); File HASHfile = new File("FHASHKey.bin"); FileInputStream fis = new FileInputStream(HASHfile); ObjectInputStream ois = new ObjectInputStream(fis); Key HMACkey = (Key) ois.readObject(); mac.init(HMACkey); mac.update(hasharray); String newhash = new String(mac.doFinal(), "UTF8"); nonce++; // check hashes for equality if (hash.equals(newhash) != true) { System.out.println("HASH EQUALITY FAIL"); disconnect(); } else { // If server indicates success, return the member list if (env.getMessage().equals("OK")) { return files; // This cast creates compiler warnings. Sorry. } } } else { System.out.println("Nonce FAIL LFILES"); disconnect(); return null; } return null; } catch (Exception e) { System.err.println("Error: " + e.getMessage()); e.printStackTrace(System.err); return null; } }
/** * Returns the key associated with the given alias, using the given password to recover it. * * @param alias the alias name * @param password the password for recovering the key. This password is used internally as the * key is exported in a PKCS12 format. * @return the requested key, or null if the given alias does not exist or does not identify a * <i>key entry</i>. * @exception NoSuchAlgorithmException if the algorithm for recovering the key cannot be found * @exception UnrecoverableKeyException if the key cannot be recovered (e.g., the given password * is wrong). */ public Key engineGetKey(String alias, char[] password) throws NoSuchAlgorithmException, UnrecoverableKeyException { permissionCheck(); // An empty password is rejected by MacOS API, no private key data // is exported. If no password is passed (as is the case when // this implementation is used as browser keystore in various // deployment scenarios like Webstart, JFX and applets), create // a dummy password so MacOS API is happy. if (password == null || password.length == 0) { // Must not be a char array with only a 0, as this is an empty // string. if (random == null) { random = new SecureRandom(); } password = Long.toString(random.nextLong()).toCharArray(); } Object entry = entries.get(alias.toLowerCase()); if (entry == null || !(entry instanceof KeyEntry)) { return null; } // This call gives us a PKCS12 bag, with the key inside it. byte[] exportedKeyInfo = _getEncodedKeyData(((KeyEntry) entry).keyRef, password); if (exportedKeyInfo == null) { return null; } PrivateKey returnValue = null; try { byte[] pkcs8KeyData = fetchPrivateKeyFromBag(exportedKeyInfo); byte[] encryptedKey; AlgorithmParameters algParams; ObjectIdentifier algOid; try { // get the encrypted private key EncryptedPrivateKeyInfo encrInfo = new EncryptedPrivateKeyInfo(pkcs8KeyData); encryptedKey = encrInfo.getEncryptedData(); // parse Algorithm parameters DerValue val = new DerValue(encrInfo.getAlgorithm().encode()); DerInputStream in = val.toDerInputStream(); algOid = in.getOID(); algParams = parseAlgParameters(in); } catch (IOException ioe) { UnrecoverableKeyException uke = new UnrecoverableKeyException( "Private key not stored as " + "PKCS#8 EncryptedPrivateKeyInfo: " + ioe); uke.initCause(ioe); throw uke; } // Use JCE to decrypt the data using the supplied password. SecretKey skey = getPBEKey(password); Cipher cipher = Cipher.getInstance(algOid.toString()); cipher.init(Cipher.DECRYPT_MODE, skey, algParams); byte[] decryptedPrivateKey = cipher.doFinal(encryptedKey); PKCS8EncodedKeySpec kspec = new PKCS8EncodedKeySpec(decryptedPrivateKey); // Parse the key algorithm and then use a JCA key factory to create the private key. DerValue val = new DerValue(decryptedPrivateKey); DerInputStream in = val.toDerInputStream(); // Ignore this -- version should be 0. int i = in.getInteger(); // Get the Algorithm ID next DerValue[] value = in.getSequence(2); AlgorithmId algId = new AlgorithmId(value[0].getOID()); String algName = algId.getName(); // Get a key factory for this algorithm. It's likely to be 'RSA'. KeyFactory kfac = KeyFactory.getInstance(algName); returnValue = kfac.generatePrivate(kspec); } catch (Exception e) { UnrecoverableKeyException uke = new UnrecoverableKeyException("Get Key failed: " + e.getMessage()); uke.initCause(e); throw uke; } return returnValue; }