mirror of
https://github.com/kremalicious/metamask-extension.git
synced 2024-12-23 09:52:26 +01:00
865321d269
This silences a warning message that was printed to the console whenever this module was loaded during tests. The API changes between these two versions were reviewed carefully for differences. The only difference made was to `PBKDF2_HMAC_SHA256.bytes`, which was replaced by `Pbkdf2HmacSha256`. The length argument no longer has a default value, so it has been set to match what the default value was in the previous version we used, which is 32 (the SHA256 hash size).
100 lines
3.4 KiB
JavaScript
100 lines
3.4 KiB
JavaScript
const asmcrypto = require('asmcrypto.js')
|
|
const Unibabel = require('browserify-unibabel')
|
|
|
|
/**
|
|
* A Microsoft Edge-specific encryption class that exposes
|
|
* the interface expected by eth-keykeyring-controller
|
|
*/
|
|
class EdgeEncryptor {
|
|
/**
|
|
* Encrypts an arbitrary object to ciphertext
|
|
*
|
|
* @param {string} password Used to generate a key to encrypt the data
|
|
* @param {Object} dataObject Data to encrypt
|
|
* @returns {Promise<string>} Promise resolving to an object with ciphertext
|
|
*/
|
|
encrypt (password, dataObject) {
|
|
var salt = this._generateSalt()
|
|
return this._keyFromPassword(password, salt)
|
|
.then(function (key) {
|
|
var data = JSON.stringify(dataObject)
|
|
var dataBuffer = Unibabel.utf8ToBuffer(data)
|
|
var vector = global.crypto.getRandomValues(new Uint8Array(16))
|
|
var resultbuffer = asmcrypto.AES_GCM.encrypt(dataBuffer, key, vector)
|
|
|
|
var buffer = new Uint8Array(resultbuffer)
|
|
var vectorStr = Unibabel.bufferToBase64(vector)
|
|
var vaultStr = Unibabel.bufferToBase64(buffer)
|
|
return JSON.stringify({
|
|
data: vaultStr,
|
|
iv: vectorStr,
|
|
salt: salt,
|
|
})
|
|
})
|
|
}
|
|
|
|
/**
|
|
* Decrypts an arbitrary object from ciphertext
|
|
*
|
|
* @param {string} password Used to generate a key to decrypt the data
|
|
* @param {string} text Ciphertext of an encrypted object
|
|
* @returns {Promise<Object>} Promise resolving to copy of decrypted object
|
|
*/
|
|
decrypt (password, text) {
|
|
const payload = JSON.parse(text)
|
|
const salt = payload.salt
|
|
return this._keyFromPassword(password, salt)
|
|
.then(function (key) {
|
|
const encryptedData = Unibabel.base64ToBuffer(payload.data)
|
|
const vector = Unibabel.base64ToBuffer(payload.iv)
|
|
return new Promise((resolve, reject) => {
|
|
var result
|
|
try {
|
|
result = asmcrypto.AES_GCM.decrypt(encryptedData, key, vector)
|
|
} catch (err) {
|
|
return reject(new Error('Incorrect password'))
|
|
}
|
|
const decryptedData = new Uint8Array(result)
|
|
const decryptedStr = Unibabel.bufferToUtf8(decryptedData)
|
|
const decryptedObj = JSON.parse(decryptedStr)
|
|
resolve(decryptedObj)
|
|
})
|
|
})
|
|
}
|
|
|
|
/**
|
|
* Retrieves a cryptographic key using a password
|
|
*
|
|
* @private
|
|
* @param {string} password Password used to unlock a cryptographic key
|
|
* @param {string} salt Random base64 data
|
|
* @returns {Promise<Object>} Promise resolving to a derived key
|
|
*/
|
|
_keyFromPassword (password, salt) {
|
|
|
|
var passBuffer = Unibabel.utf8ToBuffer(password)
|
|
var saltBuffer = Unibabel.base64ToBuffer(salt)
|
|
const iterations = 10000
|
|
const length = 32 // SHA256 hash size
|
|
return new Promise((resolve) => {
|
|
var key = asmcrypto.Pbkdf2HmacSha256(passBuffer, saltBuffer, iterations, length)
|
|
resolve(key)
|
|
})
|
|
}
|
|
|
|
/**
|
|
* Generates random base64 encoded data
|
|
*
|
|
* @private
|
|
* @returns {string} Randomized base64 encoded data
|
|
*/
|
|
_generateSalt (byteCount = 32) {
|
|
var view = new Uint8Array(byteCount)
|
|
global.crypto.getRandomValues(view)
|
|
var b64encoded = btoa(String.fromCharCode.apply(null, view))
|
|
return b64encoded
|
|
}
|
|
}
|
|
|
|
module.exports = EdgeEncryptor
|