|  |  | @ -17,6 +17,8 @@ | 
			
		
	
		
		
			
				
					
					|  |  |  | window.textsecure = window.textsecure || {}; |  |  |  | window.textsecure = window.textsecure || {}; | 
			
		
	
		
		
			
				
					
					|  |  |  | 
 |  |  |  | 
 | 
			
		
	
		
		
			
				
					
					|  |  |  | window.textsecure.crypto = function() { |  |  |  | window.textsecure.crypto = function() { | 
			
		
	
		
		
			
				
					
					|  |  |  |  |  |  |  | 	'use strict'; | 
			
		
	
		
		
			
				
					
					|  |  |  |  |  |  |  | 
 | 
			
		
	
		
		
			
				
					
					|  |  |  | 	var self = {}; |  |  |  | 	var self = {}; | 
			
		
	
		
		
			
				
					
					|  |  |  | 	// functions exposed for replacement and direct calling in test code
 |  |  |  | 	// functions exposed for replacement and direct calling in test code
 | 
			
		
	
		
		
			
				
					
					|  |  |  | 	var testing_only = {}; |  |  |  | 	var testing_only = {}; | 
			
		
	
	
		
		
			
				
					|  |  | @ -28,16 +30,12 @@ window.textsecure.crypto = function() { | 
			
		
	
		
		
			
				
					
					|  |  |  | 	var MESSAGE_LOST_THRESHOLD_MS = 1000*60*60*24*7; |  |  |  | 	var MESSAGE_LOST_THRESHOLD_MS = 1000*60*60*24*7; | 
			
		
	
		
		
			
				
					
					|  |  |  | 
 |  |  |  | 
 | 
			
		
	
		
		
			
				
					
					|  |  |  | 	var getRandomBytes = function(size) { |  |  |  | 	var getRandomBytes = function(size) { | 
			
		
	
		
		
			
				
					
					|  |  |  | 		//TODO: Better random (https://www.grc.com/r&d/js.htm?)
 |  |  |  | 		// At some point we might consider XORing in hashes of random
 | 
			
				
				
			
		
	
		
		
			
				
					
					|  |  |  | 		try { |  |  |  | 		// UI events to strengthen ourselves against RNG flaws in crypto.getRandomValues
 | 
			
				
				
			
		
	
		
		
			
				
					
					|  |  |  | 			var buffer = new ArrayBuffer(size); |  |  |  | 		// ie maybe take a look at how Gibson does it at https://www.grc.com/r&d/js.htm
 | 
			
				
				
			
		
	
		
		
			
				
					
					|  |  |  | 			var array = new Uint8Array(buffer); |  |  |  | 		var array = new Uint8Array(size); | 
			
				
				
			
		
	
		
		
	
		
		
	
		
		
	
		
		
	
		
		
			
				
					
					|  |  |  | 		window.crypto.getRandomValues(array); |  |  |  | 		window.crypto.getRandomValues(array); | 
			
		
	
		
		
			
				
					
					|  |  |  | 			return buffer; |  |  |  | 		return array.buffer; | 
			
				
				
			
		
	
		
		
			
				
					
					|  |  |  | 		} catch (err) { |  |  |  |  | 
			
		
	
		
		
			
				
					
					|  |  |  | 			//TODO: ummm...wat?
 |  |  |  |  | 
			
		
	
		
		
			
				
					
					|  |  |  | 			throw err; |  |  |  |  | 
			
		
	
		
		
			
				
					
					|  |  |  | 		} |  |  |  |  | 
			
		
	
		
		
	
		
		
			
				
					
					|  |  |  | 	} |  |  |  | 	} | 
			
		
	
		
		
			
				
					
					|  |  |  | 	self.getRandomBytes = getRandomBytes; |  |  |  | 	self.getRandomBytes = getRandomBytes; | 
			
		
	
		
		
			
				
					
					|  |  |  | 
 |  |  |  | 
 | 
			
		
	
	
		
		
			
				
					|  |  | @ -392,7 +390,9 @@ window.textsecure.crypto = function() { | 
			
		
	
		
		
			
				
					
					|  |  |  | 	var closeSession = function(session) { |  |  |  | 	var closeSession = function(session) { | 
			
		
	
		
		
			
				
					
					|  |  |  | 		// Clear any data which would allow session continuation:
 |  |  |  | 		// Clear any data which would allow session continuation:
 | 
			
		
	
		
		
			
				
					
					|  |  |  | 		// Lock down current receive ratchet
 |  |  |  | 		// Lock down current receive ratchet
 | 
			
		
	
		
		
			
				
					
					|  |  |  | 		// TODO: Some kind of delete chainKey['key']
 |  |  |  | 		for (key in session) | 
			
				
				
			
		
	
		
		
	
		
		
			
				
					
					|  |  |  |  |  |  |  | 			if (key.chainKey !== undefined && key.chainKey.key !== undefined) | 
			
		
	
		
		
			
				
					
					|  |  |  |  |  |  |  | 				delete key.chainKey.key; | 
			
		
	
		
		
			
				
					
					|  |  |  | 		// Delete current sending ratchet
 |  |  |  | 		// Delete current sending ratchet
 | 
			
		
	
		
		
			
				
					
					|  |  |  | 		delete session[getString(session.currentRatchet.ephemeralKeyPair.pubKey)]; |  |  |  | 		delete session[getString(session.currentRatchet.ephemeralKeyPair.pubKey)]; | 
			
		
	
		
		
			
				
					
					|  |  |  | 		// Delete current root key and our ephemeral key pair
 |  |  |  | 		// Delete current root key and our ephemeral key pair
 | 
			
		
	
	
		
		
			
				
					|  |  | @ -535,7 +535,7 @@ window.textsecure.crypto = function() { | 
			
		
	
		
		
			
				
					
					|  |  |  | 		var previousRatchet = session[getString(ratchet.lastRemoteEphemeralKey)]; |  |  |  | 		var previousRatchet = session[getString(ratchet.lastRemoteEphemeralKey)]; | 
			
		
	
		
		
			
				
					
					|  |  |  | 		if (previousRatchet !== undefined) { |  |  |  | 		if (previousRatchet !== undefined) { | 
			
		
	
		
		
			
				
					
					|  |  |  | 			return fillMessageKeys(previousRatchet, previousCounter).then(function() { |  |  |  | 			return fillMessageKeys(previousRatchet, previousCounter).then(function() { | 
			
		
	
		
		
			
				
					
					|  |  |  | 				delete previousRatchet.chainKey['key']; |  |  |  | 				delete previousRatchet.chainKey.key; | 
			
				
				
			
		
	
		
		
	
		
		
			
				
					
					|  |  |  | 				if (!objectContainsKeys(previousRatchet.messageKeys)) |  |  |  | 				if (!objectContainsKeys(previousRatchet.messageKeys)) | 
			
		
	
		
		
			
				
					
					|  |  |  | 					delete session[getString(ratchet.lastRemoteEphemeralKey)]; |  |  |  | 					delete session[getString(ratchet.lastRemoteEphemeralKey)]; | 
			
		
	
		
		
			
				
					
					|  |  |  | 				else |  |  |  | 				else | 
			
		
	
	
		
		
			
				
					|  |  | 
 |