org.whispersystems.libsignal.util.ByteUtil Java Examples
The following examples show how to use
org.whispersystems.libsignal.util.ByteUtil.
You can vote up the ones you like or vote down the ones you don't like,
and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: ProfileCipher.java From mollyim-android with GNU General Public License v3.0 | 6 votes |
public byte[] encryptName(byte[] input, int paddedLength) { try { byte[] inputPadded = new byte[paddedLength]; if (input.length > inputPadded.length) { throw new IllegalArgumentException("Input is too long: " + new String(input)); } System.arraycopy(input, 0, inputPadded, 0, input.length); byte[] nonce = Util.getSecretBytes(12); Cipher cipher = Cipher.getInstance("AES/GCM/NoPadding"); cipher.init(Cipher.ENCRYPT_MODE, new SecretKeySpec(key.serialize(), "AES"), new GCMParameterSpec(128, nonce)); return ByteUtil.combine(nonce, cipher.doFinal(inputPadded)); } catch (NoSuchAlgorithmException | InvalidAlgorithmParameterException | BadPaddingException | NoSuchPaddingException | IllegalBlockSizeException | InvalidKeyException e) { throw new AssertionError(e); } }
Example #2
Source File: NumericFingerprintGenerator.java From libsignal-protocol-java with GNU General Public License v3.0 | 6 votes |
private byte[] getFingerprint(int iterations, byte[] stableIdentifier, List<IdentityKey> unsortedIdentityKeys) { try { MessageDigest digest = MessageDigest.getInstance("SHA-512"); byte[] publicKey = getLogicalKeyBytes(unsortedIdentityKeys); byte[] hash = ByteUtil.combine(ByteUtil.shortToByteArray(FINGERPRINT_VERSION), publicKey, stableIdentifier); for (int i=0;i<iterations;i++) { digest.update(hash); hash = digest.digest(publicKey); } return hash; } catch (NoSuchAlgorithmException e) { throw new AssertionError(e); } }
Example #3
Source File: ScannableFingerprint.java From libsignal-protocol-java with GNU General Public License v3.0 | 6 votes |
ScannableFingerprint(int version, byte[] localFingerprintData, byte[] remoteFingerprintData) { LogicalFingerprint localFingerprint = LogicalFingerprint.newBuilder() .setContent(ByteString.copyFrom(ByteUtil.trim(localFingerprintData, 32))) .build(); LogicalFingerprint remoteFingerprint = LogicalFingerprint.newBuilder() .setContent(ByteString.copyFrom(ByteUtil.trim(remoteFingerprintData, 32))) .build(); this.version = version; this.fingerprints = CombinedFingerprints.newBuilder() .setVersion(version) .setLocalFingerprint(localFingerprint) .setRemoteFingerprint(remoteFingerprint) .build(); }
Example #4
Source File: ContactDiscoveryCipher.java From libsignal-service-java with GNU General Public License v3.0 | 6 votes |
public DiscoveryRequest createDiscoveryRequest(List<String> addressBook, RemoteAttestation remoteAttestation) { try { ByteArrayOutputStream requestDataStream = new ByteArrayOutputStream(); for (String address : addressBook) { requestDataStream.write(ByteUtil.longToByteArray(Long.parseLong(address))); } byte[] requestData = requestDataStream.toByteArray(); byte[] nonce = Util.getSecretBytes(12); Cipher cipher = Cipher.getInstance("AES/GCM/NoPadding"); cipher.init(Cipher.ENCRYPT_MODE, new SecretKeySpec(remoteAttestation.getKeys().getClientKey(), "AES"), new GCMParameterSpec(TAG_LENGTH_BITS, nonce)); cipher.updateAAD(remoteAttestation.getRequestId()); byte[] cipherText = cipher.doFinal(requestData); byte[][] parts = ByteUtil.split(cipherText, cipherText.length - TAG_LENGTH_BYTES, TAG_LENGTH_BYTES); return new DiscoveryRequest(addressBook.size(), remoteAttestation.getRequestId(), nonce, parts[0], parts[1]); } catch (IOException | NoSuchAlgorithmException | InvalidKeyException | NoSuchPaddingException | InvalidAlgorithmParameterException | IllegalBlockSizeException | BadPaddingException e) { throw new AssertionError(e); } }
Example #5
Source File: ProfileCipher.java From libsignal-service-java with GNU General Public License v3.0 | 6 votes |
public byte[] encryptName(byte[] input, int paddedLength) { try { byte[] inputPadded = new byte[paddedLength]; if (input.length > inputPadded.length) { throw new IllegalArgumentException("Input is too long: " + new String(input)); } System.arraycopy(input, 0, inputPadded, 0, input.length); byte[] nonce = Util.getSecretBytes(12); Cipher cipher = Cipher.getInstance("AES/GCM/NoPadding"); cipher.init(Cipher.ENCRYPT_MODE, new SecretKeySpec(key, "AES"), new GCMParameterSpec(128, nonce)); return ByteUtil.combine(nonce, cipher.doFinal(inputPadded)); } catch (NoSuchAlgorithmException | InvalidAlgorithmParameterException | BadPaddingException | NoSuchPaddingException | IllegalBlockSizeException | InvalidKeyException e) { throw new AssertionError(e); } }
Example #6
Source File: SenderKeyMessage.java From libsignal-protocol-java with GNU General Public License v3.0 | 6 votes |
public SenderKeyMessage(int keyId, int iteration, byte[] ciphertext, ECPrivateKey signatureKey) { byte[] version = {ByteUtil.intsToByteHighAndLow(CURRENT_VERSION, CURRENT_VERSION)}; byte[] message = SignalProtos.SenderKeyMessage.newBuilder() .setId(keyId) .setIteration(iteration) .setCiphertext(ByteString.copyFrom(ciphertext)) .build().toByteArray(); byte[] signature = getSignature(signatureKey, ByteUtil.combine(version, message)); this.serialized = ByteUtil.combine(version, message, signature); this.messageVersion = CURRENT_VERSION; this.keyId = keyId; this.iteration = iteration; this.ciphertext = ciphertext; }
Example #7
Source File: ProfileCipher.java From bcm-android with GNU General Public License v3.0 | 6 votes |
public byte[] encryptName(byte[] input, int paddedLength) { try { byte[] inputPadded = new byte[paddedLength]; if (input.length > inputPadded.length) { throw new IllegalArgumentException("Input is too long: " + new String(input)); } System.arraycopy(input, 0, inputPadded, 0, input.length); byte[] nonce = Util.getSecretBytes(12); GCMBlockCipher cipher = new GCMBlockCipher(new AESFastEngine()); cipher.init(true, new AEADParameters(new KeyParameter(key), 128, nonce)); byte[] ciphertext = new byte[cipher.getUpdateOutputSize(inputPadded.length)]; cipher.processBytes(inputPadded, 0, inputPadded.length, ciphertext, 0); byte[] tag = new byte[cipher.getOutputSize(0)]; cipher.doFinal(tag, 0); return ByteUtil.combine(nonce, ciphertext, tag); } catch (InvalidCipherTextException e) { throw new AssertionError(e); } }
Example #8
Source File: SignalMessage.java From libsignal-protocol-java with GNU General Public License v3.0 | 6 votes |
public SignalMessage(int messageVersion, SecretKeySpec macKey, ECPublicKey senderRatchetKey, int counter, int previousCounter, byte[] ciphertext, IdentityKey senderIdentityKey, IdentityKey receiverIdentityKey) { byte[] version = {ByteUtil.intsToByteHighAndLow(messageVersion, CURRENT_VERSION)}; byte[] message = SignalProtos.SignalMessage.newBuilder() .setRatchetKey(ByteString.copyFrom(senderRatchetKey.serialize())) .setCounter(counter) .setPreviousCounter(previousCounter) .setCiphertext(ByteString.copyFrom(ciphertext)) .build().toByteArray(); byte[] mac = getMac(senderIdentityKey, receiverIdentityKey, macKey, ByteUtil.combine(version, message)); this.serialized = ByteUtil.combine(version, message, mac); this.senderRatchetKey = senderRatchetKey; this.counter = counter; this.previousCounter = previousCounter; this.ciphertext = ciphertext; this.messageVersion = messageVersion; }
Example #9
Source File: FullBackupBase.java From mollyim-android with GNU General Public License v3.0 | 6 votes |
static @NonNull byte[] getBackupKey(@NonNull String passphrase, @Nullable byte[] salt) { try { EventBus.getDefault().post(new BackupEvent(BackupEvent.Type.PROGRESS, 0)); MessageDigest digest = MessageDigest.getInstance("SHA-512"); byte[] input = passphrase.replace(" ", "").getBytes(); byte[] hash = input; if (salt != null) digest.update(salt); for (int i=0;i<250000;i++) { if (i % 1000 == 0) EventBus.getDefault().post(new BackupEvent(BackupEvent.Type.PROGRESS, 0)); digest.update(hash); hash = digest.digest(input); } return ByteUtil.trim(hash, 32); } catch (NoSuchAlgorithmException e) { throw new AssertionError(e); } }
Example #10
Source File: SignalMessage.java From libsignal-protocol-java with GNU General Public License v3.0 | 6 votes |
private byte[] getMac(IdentityKey senderIdentityKey, IdentityKey receiverIdentityKey, SecretKeySpec macKey, byte[] serialized) { try { Mac mac = Mac.getInstance("HmacSHA256"); mac.init(macKey); mac.update(senderIdentityKey.getPublicKey().serialize()); mac.update(receiverIdentityKey.getPublicKey().serialize()); byte[] fullMac = mac.doFinal(serialized); return ByteUtil.trim(fullMac, MAC_LENGTH); } catch (NoSuchAlgorithmException | java.security.InvalidKeyException e) { throw new AssertionError(e); } }
Example #11
Source File: DeviceConsistencyCommitment.java From libsignal-protocol-java with GNU General Public License v3.0 | 6 votes |
public DeviceConsistencyCommitment(int generation, List<IdentityKey> identityKeys) { try { ArrayList<IdentityKey> sortedIdentityKeys = new ArrayList<>(identityKeys); Collections.sort(sortedIdentityKeys, new IdentityKeyComparator()); MessageDigest messageDigest = MessageDigest.getInstance("SHA-512"); messageDigest.update(VERSION.getBytes()); messageDigest.update(ByteUtil.intToByteArray(generation)); for (IdentityKey commitment : sortedIdentityKeys) { messageDigest.update(commitment.getPublicKey().serialize()); } this.generation = generation; this.serialized = messageDigest.digest(); } catch (NoSuchAlgorithmException e) { throw new AssertionError(e); } }
Example #12
Source File: DeviceConsistencyCodeGenerator.java From libsignal-protocol-java with GNU General Public License v3.0 | 6 votes |
public static String generateFor(DeviceConsistencyCommitment commitment, List<DeviceConsistencySignature> signatures) { try { ArrayList<DeviceConsistencySignature> sortedSignatures = new ArrayList<>(signatures); Collections.sort(sortedSignatures, new SignatureComparator()); MessageDigest messageDigest = MessageDigest.getInstance("SHA-512"); messageDigest.update(ByteUtil.shortToByteArray(CODE_VERSION)); messageDigest.update(commitment.toByteArray()); for (DeviceConsistencySignature signature : sortedSignatures) { messageDigest.update(signature.getVrfOutput()); } byte[] hash = messageDigest.digest(); String digits = getEncodedChunk(hash, 0) + getEncodedChunk(hash, 5); return digits.substring(0, 6); } catch (NoSuchAlgorithmException e) { throw new AssertionError(e); } }
Example #13
Source File: AESCipher.java From mollyim-android with GNU General Public License v3.0 | 6 votes |
static AESEncryptedResult encrypt(byte[] key, byte[] aad, byte[] requestData) { try { byte[] iv = Util.getSecretBytes(12); Cipher cipher = Cipher.getInstance("AES/GCM/NoPadding"); cipher.init(Cipher.ENCRYPT_MODE, new SecretKeySpec(key, "AES"), new GCMParameterSpec(TAG_LENGTH_BITS, iv)); cipher.updateAAD(aad); byte[] cipherText = cipher.doFinal(requestData); byte[][] parts = ByteUtil.split(cipherText, cipherText.length - TAG_LENGTH_BYTES, TAG_LENGTH_BYTES); byte[] mac = parts[1]; byte[] data = parts[0]; return new AESEncryptedResult(iv, data, mac, aad); } catch (NoSuchAlgorithmException | InvalidKeyException | NoSuchPaddingException | InvalidAlgorithmParameterException | IllegalBlockSizeException | BadPaddingException e) { throw new AssertionError(e); } }
Example #14
Source File: ContactDiscoveryCipher.java From mollyim-android with GNU General Public License v3.0 | 6 votes |
public static DiscoveryRequest createDiscoveryRequest(List<String> addressBook, RemoteAttestation remoteAttestation) { try { ByteArrayOutputStream requestDataStream = new ByteArrayOutputStream(); for (String address : addressBook) { requestDataStream.write(ByteUtil.longToByteArray(Long.parseLong(address))); } byte[] clientKey = remoteAttestation.getKeys().getClientKey(); byte[] requestData = requestDataStream.toByteArray(); byte[] aad = remoteAttestation.getRequestId(); AESCipher.AESEncryptedResult aesEncryptedResult = AESCipher.encrypt(clientKey, aad, requestData); return new DiscoveryRequest(addressBook.size(), aesEncryptedResult.aad, aesEncryptedResult.iv, aesEncryptedResult.data, aesEncryptedResult.mac); } catch (IOException e) { throw new AssertionError(e); } }
Example #15
Source File: SignalMessage.java From libsignal-protocol-java with GNU General Public License v3.0 | 5 votes |
public void verifyMac(IdentityKey senderIdentityKey, IdentityKey receiverIdentityKey, SecretKeySpec macKey) throws InvalidMessageException { byte[][] parts = ByteUtil.split(serialized, serialized.length - MAC_LENGTH, MAC_LENGTH); byte[] ourMac = getMac(senderIdentityKey, receiverIdentityKey, macKey, parts[0]); byte[] theirMac = parts[1]; if (!MessageDigest.isEqual(ourMac, theirMac)) { throw new InvalidMessageException("Bad Mac!"); } }
Example #16
Source File: DerivedMessageSecrets.java From libsignal-protocol-java with GNU General Public License v3.0 | 5 votes |
public DerivedMessageSecrets(byte[] okm) { try { byte[][] keys = ByteUtil.split(okm, CIPHER_KEY_LENGTH, MAC_KEY_LENGTH, IV_LENGTH); this.cipherKey = new SecretKeySpec(keys[0], "AES"); this.macKey = new SecretKeySpec(keys[1], "HmacSHA256"); this.iv = new IvParameterSpec(keys[2]); } catch (ParseException e) { throw new AssertionError(e); } }
Example #17
Source File: SignalMessage.java From libsignal-protocol-java with GNU General Public License v3.0 | 5 votes |
public SignalMessage(byte[] serialized) throws InvalidMessageException, LegacyMessageException { try { byte[][] messageParts = ByteUtil.split(serialized, 1, serialized.length - 1 - MAC_LENGTH, MAC_LENGTH); byte version = messageParts[0][0]; byte[] message = messageParts[1]; byte[] mac = messageParts[2]; if (ByteUtil.highBitsToInt(version) < CURRENT_VERSION) { throw new LegacyMessageException("Legacy message: " + ByteUtil.highBitsToInt(version)); } if (ByteUtil.highBitsToInt(version) > CURRENT_VERSION) { throw new InvalidMessageException("Unknown version: " + ByteUtil.highBitsToInt(version)); } SignalProtos.SignalMessage whisperMessage = SignalProtos.SignalMessage.parseFrom(message); if (!whisperMessage.hasCiphertext() || !whisperMessage.hasCounter() || !whisperMessage.hasRatchetKey()) { throw new InvalidMessageException("Incomplete message."); } this.serialized = serialized; this.senderRatchetKey = Curve.decodePoint(whisperMessage.getRatchetKey().toByteArray(), 0); this.messageVersion = ByteUtil.highBitsToInt(version); this.counter = whisperMessage.getCounter(); this.previousCounter = whisperMessage.getPreviousCounter(); this.ciphertext = whisperMessage.getCiphertext().toByteArray(); } catch (InvalidProtocolBufferException | InvalidKeyException | ParseException e) { throw new InvalidMessageException(e); } }
Example #18
Source File: SenderKeyMessage.java From libsignal-protocol-java with GNU General Public License v3.0 | 5 votes |
public void verifySignature(ECPublicKey signatureKey) throws InvalidMessageException { try { byte[][] parts = ByteUtil.split(serialized, serialized.length - SIGNATURE_LENGTH, SIGNATURE_LENGTH); if (!Curve.verifySignature(signatureKey, parts[0], parts[1])) { throw new InvalidMessageException("Invalid signature!"); } } catch (InvalidKeyException e) { throw new InvalidMessageException(e); } }
Example #19
Source File: SenderKeyMessage.java From libsignal-protocol-java with GNU General Public License v3.0 | 5 votes |
public SenderKeyMessage(byte[] serialized) throws InvalidMessageException, LegacyMessageException { try { byte[][] messageParts = ByteUtil.split(serialized, 1, serialized.length - 1 - SIGNATURE_LENGTH, SIGNATURE_LENGTH); byte version = messageParts[0][0]; byte[] message = messageParts[1]; byte[] signature = messageParts[2]; if (ByteUtil.highBitsToInt(version) < 3) { throw new LegacyMessageException("Legacy message: " + ByteUtil.highBitsToInt(version)); } if (ByteUtil.highBitsToInt(version) > CURRENT_VERSION) { throw new InvalidMessageException("Unknown version: " + ByteUtil.highBitsToInt(version)); } SignalProtos.SenderKeyMessage senderKeyMessage = SignalProtos.SenderKeyMessage.parseFrom(message); if (!senderKeyMessage.hasId() || !senderKeyMessage.hasIteration() || !senderKeyMessage.hasCiphertext()) { throw new InvalidMessageException("Incomplete message."); } this.serialized = serialized; this.messageVersion = ByteUtil.highBitsToInt(version); this.keyId = senderKeyMessage.getId(); this.iteration = senderKeyMessage.getIteration(); this.ciphertext = senderKeyMessage.getCiphertext().toByteArray(); } catch (InvalidProtocolBufferException | ParseException e) { throw new InvalidMessageException(e); } }
Example #20
Source File: UnidentifiedAccess.java From mollyim-android with GNU General Public License v3.0 | 5 votes |
public static byte[] deriveAccessKeyFrom(ProfileKey profileKey) { try { byte[] nonce = new byte[12]; byte[] input = new byte[16]; Cipher cipher = Cipher.getInstance("AES/GCM/NoPadding"); cipher.init(Cipher.ENCRYPT_MODE, new SecretKeySpec(profileKey.serialize(), "AES"), new GCMParameterSpec(128, nonce)); byte[] ciphertext = cipher.doFinal(input); return ByteUtil.trim(ciphertext, 16); } catch (NoSuchAlgorithmException | InvalidKeyException | NoSuchPaddingException | InvalidAlgorithmParameterException | BadPaddingException | IllegalBlockSizeException e) { throw new AssertionError(e); } }
Example #21
Source File: PreKeySignalMessage.java From libsignal-protocol-java with GNU General Public License v3.0 | 5 votes |
public PreKeySignalMessage(int messageVersion, int registrationId, Optional<Integer> preKeyId, int signedPreKeyId, ECPublicKey baseKey, IdentityKey identityKey, SignalMessage message) { this.version = messageVersion; this.registrationId = registrationId; this.preKeyId = preKeyId; this.signedPreKeyId = signedPreKeyId; this.baseKey = baseKey; this.identityKey = identityKey; this.message = message; SignalProtos.PreKeySignalMessage.Builder builder = SignalProtos.PreKeySignalMessage.newBuilder() .setSignedPreKeyId(signedPreKeyId) .setBaseKey(ByteString.copyFrom(baseKey.serialize())) .setIdentityKey(ByteString.copyFrom(identityKey.serialize())) .setMessage(ByteString.copyFrom(message.serialize())) .setRegistrationId(registrationId); if (preKeyId.isPresent()) { builder.setPreKeyId(preKeyId.get()); } byte[] versionBytes = {ByteUtil.intsToByteHighAndLow(this.version, CURRENT_VERSION)}; byte[] messageBytes = builder.build().toByteArray(); this.serialized = ByteUtil.combine(versionBytes, messageBytes); }
Example #22
Source File: PreKeySignalMessage.java From libsignal-protocol-java with GNU General Public License v3.0 | 5 votes |
public PreKeySignalMessage(byte[] serialized) throws InvalidMessageException, InvalidVersionException { try { this.version = ByteUtil.highBitsToInt(serialized[0]); if (this.version > CiphertextMessage.CURRENT_VERSION) { throw new InvalidVersionException("Unknown version: " + this.version); } if (this.version < CiphertextMessage.CURRENT_VERSION) { throw new LegacyMessageException("Legacy version: " + this.version); } SignalProtos.PreKeySignalMessage preKeyWhisperMessage = SignalProtos.PreKeySignalMessage.parseFrom(ByteString.copyFrom(serialized, 1, serialized.length-1)); if (!preKeyWhisperMessage.hasSignedPreKeyId() || !preKeyWhisperMessage.hasBaseKey() || !preKeyWhisperMessage.hasIdentityKey() || !preKeyWhisperMessage.hasMessage()) { throw new InvalidMessageException("Incomplete message."); } this.serialized = serialized; this.registrationId = preKeyWhisperMessage.getRegistrationId(); this.preKeyId = preKeyWhisperMessage.hasPreKeyId() ? Optional.of(preKeyWhisperMessage.getPreKeyId()) : Optional.<Integer>absent(); this.signedPreKeyId = preKeyWhisperMessage.hasSignedPreKeyId() ? preKeyWhisperMessage.getSignedPreKeyId() : -1; this.baseKey = Curve.decodePoint(preKeyWhisperMessage.getBaseKey().toByteArray(), 0); this.identityKey = new IdentityKey(Curve.decodePoint(preKeyWhisperMessage.getIdentityKey().toByteArray(), 0)); this.message = new SignalMessage(preKeyWhisperMessage.getMessage().toByteArray()); } catch (InvalidProtocolBufferException | InvalidKeyException | LegacyMessageException e) { throw new InvalidMessageException(e); } }
Example #23
Source File: SenderKeyDistributionMessage.java From libsignal-protocol-java with GNU General Public License v3.0 | 5 votes |
public SenderKeyDistributionMessage(byte[] serialized) throws LegacyMessageException, InvalidMessageException { try { byte[][] messageParts = ByteUtil.split(serialized, 1, serialized.length - 1); byte version = messageParts[0][0]; byte[] message = messageParts[1]; if (ByteUtil.highBitsToInt(version) < CiphertextMessage.CURRENT_VERSION) { throw new LegacyMessageException("Legacy message: " + ByteUtil.highBitsToInt(version)); } if (ByteUtil.highBitsToInt(version) > CURRENT_VERSION) { throw new InvalidMessageException("Unknown version: " + ByteUtil.highBitsToInt(version)); } SignalProtos.SenderKeyDistributionMessage distributionMessage = SignalProtos.SenderKeyDistributionMessage.parseFrom(message); if (!distributionMessage.hasId() || !distributionMessage.hasIteration() || !distributionMessage.hasChainKey() || !distributionMessage.hasSigningKey()) { throw new InvalidMessageException("Incomplete message."); } this.serialized = serialized; this.id = distributionMessage.getId(); this.iteration = distributionMessage.getIteration(); this.chainKey = distributionMessage.getChainKey().toByteArray(); this.signatureKey = Curve.decodePoint(distributionMessage.getSigningKey().toByteArray(), 0); } catch (InvalidProtocolBufferException | InvalidKeyException e) { throw new InvalidMessageException(e); } }
Example #24
Source File: SenderKeyDistributionMessage.java From libsignal-protocol-java with GNU General Public License v3.0 | 5 votes |
public SenderKeyDistributionMessage(int id, int iteration, byte[] chainKey, ECPublicKey signatureKey) { byte[] version = {ByteUtil.intsToByteHighAndLow(CURRENT_VERSION, CURRENT_VERSION)}; byte[] protobuf = SignalProtos.SenderKeyDistributionMessage.newBuilder() .setId(id) .setIteration(iteration) .setChainKey(ByteString.copyFrom(chainKey)) .setSigningKey(ByteString.copyFrom(signatureKey.serialize())) .build().toByteArray(); this.id = id; this.iteration = iteration; this.chainKey = chainKey; this.signatureKey = signatureKey; this.serialized = ByteUtil.combine(version, protobuf); }
Example #25
Source File: RatchetingSession.java From libsignal-protocol-java with GNU General Public License v3.0 | 5 votes |
private static DerivedKeys calculateDerivedKeys(byte[] masterSecret) { HKDF kdf = new HKDFv3(); byte[] derivedSecretBytes = kdf.deriveSecrets(masterSecret, "WhisperText".getBytes(), 64); byte[][] derivedSecrets = ByteUtil.split(derivedSecretBytes, 32, 32); return new DerivedKeys(new RootKey(kdf, derivedSecrets[0]), new ChainKey(kdf, derivedSecrets[1], 0)); }
Example #26
Source File: FullBackupExporter.java From mollyim-android with GNU General Public License v3.0 | 5 votes |
private BackupFrameOutputStream(@NonNull File output, @NonNull String passphrase) throws IOException { try { byte[] salt = Util.getSecretBytes(32); byte[] key = getBackupKey(passphrase, salt); byte[] derived = new HKDFv3().deriveSecrets(key, "Backup Export".getBytes(), 64); byte[][] split = ByteUtil.split(derived, 32, 32); this.cipherKey = split[0]; this.macKey = split[1]; this.cipher = Cipher.getInstance("AES/CTR/NoPadding"); this.mac = Mac.getInstance("HmacSHA256"); this.outputStream = new FileOutputStream(output); this.iv = Util.getSecretBytes(16); this.counter = Conversions.byteArrayToInt(iv); mac.init(new SecretKeySpec(macKey, "HmacSHA256")); byte[] header = BackupProtos.BackupFrame.newBuilder().setHeader(BackupProtos.Header.newBuilder() .setIv(ByteString.copyFrom(iv)) .setSalt(ByteString.copyFrom(salt))) .build().toByteArray(); outputStream.write(Conversions.intToByteArray(header.length)); outputStream.write(header); } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException e) { throw new AssertionError(e); } }
Example #27
Source File: RemoteAttestationCipher.java From mollyim-android with GNU General Public License v3.0 | 5 votes |
public static void verifyIasSignature(KeyStore trustStore, String certificates, String signatureBody, String signature, Quote quote) throws SignatureException { if (certificates == null || certificates.isEmpty()) { throw new SignatureException("No certificates."); } try { SigningCertificate signingCertificate = new SigningCertificate(certificates, trustStore); signingCertificate.verifySignature(signatureBody, signature); SignatureBodyEntity signatureBodyEntity = JsonUtil.fromJson(signatureBody, SignatureBodyEntity.class); if (signatureBodyEntity.getVersion() != SIGNATURE_BODY_VERSION) { throw new SignatureException("Unexpected signed quote version " + signatureBodyEntity.getVersion()); } if (!MessageDigest.isEqual(ByteUtil.trim(signatureBodyEntity.getIsvEnclaveQuoteBody(), 432), ByteUtil.trim(quote.getQuoteBytes(), 432))) { throw new SignatureException("Signed quote is not the same as RA quote: " + Hex.toStringCondensed(signatureBodyEntity.getIsvEnclaveQuoteBody()) + " vs " + Hex.toStringCondensed(quote.getQuoteBytes())); } if (!"OK".equals(signatureBodyEntity.getIsvEnclaveQuoteStatus())) { throw new SignatureException("Quote status is: " + signatureBodyEntity.getIsvEnclaveQuoteStatus()); } if (Instant.from(ZonedDateTime.of(LocalDateTime.from(DateTimeFormatter.ofPattern("yyy-MM-dd'T'HH:mm:ss.SSSSSS").parse(signatureBodyEntity.getTimestamp())), ZoneId.of("UTC"))) .plus(Period.ofDays(1)) .isBefore(Instant.now())) { throw new SignatureException("Signature is expired"); } } catch (CertificateException | CertPathValidatorException | IOException e) { throw new SignatureException(e); } }
Example #28
Source File: RemoteAttestationKeys.java From mollyim-android with GNU General Public License v3.0 | 5 votes |
public RemoteAttestationKeys(Curve25519KeyPair keyPair, byte[] serverPublicEphemeral, byte[] serverPublicStatic) { byte[] ephemeralToEphemeral = Curve25519.getInstance(Curve25519.BEST).calculateAgreement(serverPublicEphemeral, keyPair.getPrivateKey()); byte[] ephemeralToStatic = Curve25519.getInstance(Curve25519.BEST).calculateAgreement(serverPublicStatic, keyPair.getPrivateKey()); byte[] masterSecret = ByteUtil.combine(ephemeralToEphemeral, ephemeralToStatic ); byte[] publicKeys = ByteUtil.combine(keyPair.getPublicKey(), serverPublicEphemeral, serverPublicStatic); HKDFv3 generator = new HKDFv3(); byte[] keys = generator.deriveSecrets(masterSecret, publicKeys, null, clientKey.length + serverKey.length); System.arraycopy(keys, 0, clientKey, 0, clientKey.length); System.arraycopy(keys, clientKey.length, serverKey, 0, serverKey.length); }
Example #29
Source File: FullBackupImporter.java From mollyim-android with GNU General Public License v3.0 | 5 votes |
private BackupFrame readFrame(InputStream in) throws IOException { try { byte[] length = new byte[4]; Util.readFully(in, length); byte[] frame = new byte[Conversions.byteArrayToInt(length)]; Util.readFully(in, frame); byte[] theirMac = new byte[10]; System.arraycopy(frame, frame.length - 10, theirMac, 0, theirMac.length); mac.update(frame, 0, frame.length - 10); byte[] ourMac = ByteUtil.trim(mac.doFinal(), 10); if (!MessageDigest.isEqual(ourMac, theirMac)) { throw new IOException("Bad MAC"); } Conversions.intToByteArray(iv, 0, counter++); cipher.init(Cipher.DECRYPT_MODE, new SecretKeySpec(cipherKey, "AES"), new IvParameterSpec(iv)); byte[] plaintext = cipher.doFinal(frame, 0, frame.length - 10); return BackupFrame.parseFrom(plaintext); } catch (InvalidKeyException | InvalidAlgorithmParameterException | IllegalBlockSizeException | BadPaddingException e) { throw new AssertionError(e); } }
Example #30
Source File: BackupUtil.java From mollyim-android with GNU General Public License v3.0 | 5 votes |
public static @NonNull String[] generateBackupPassphrase() { String[] result = new String[6]; byte[] random = new byte[30]; new SecureRandom().nextBytes(random); for (int i=0;i<30;i+=5) { result[i/5] = String.format("%05d", ByteUtil.byteArray5ToLong(random, i) % 100000); } return result; }