Skip to content

Commit

Permalink
Cleaning up old decrypt code
Browse files Browse the repository at this point in the history
The decrypt() method was a holdover from v0.6 and it's serving
a special purpose of decrypting the enrollment challenge from
the v0.6 member service. So this is not needed any longer.

Some point down the road we'll re-implement the encrypt/decrypt
methods but it's optional since the platform doesn't support
built-in encryption any longer.

Change-Id: I2e87dd71945dcf3654e1d9ac278109836dc5f74f
Signed-off-by: Jim Zhang <jzhang@us.ibm.com>
  • Loading branch information
jimthematrix committed Jan 4, 2017
1 parent 5786857 commit e6a2572
Show file tree
Hide file tree
Showing 2 changed files with 2 additions and 173 deletions.
134 changes: 2 additions & 132 deletions hfc/lib/impl/CryptoSuite_ECDSA_AES.js
Original file line number Diff line number Diff line change
Expand Up @@ -278,139 +278,9 @@ var CryptoSuite_ECDSA_AES = class extends api.CryptoSuite {
* The opts argument should be appropriate for the algorithm used.
*/
decrypt(key, cipherText, opts) {
key = key._key;
var self = this;

var level = key.ecparams.keylen;

if (this._keySize !== level) {
throw Error(util.format('Invalid key. It\'s security %s does not match the current security level represented by the key size %s', level, this._keySize));
}
//cipherText = ephemeralPubKeyBytes + encryptedTokBytes + macBytes
//ephemeralPubKeyBytes = first ((384+7)/8)*2 + 1 bytes = first 97 bytes
//hmac is sha3_384 = 48 bytes or sha3_256 = 32 bytes
var Rb_len = Math.floor((level + 7) / 8) * 2 + 1;
var D_len = level >> 3;
var ct_len = cipherText.length;

if (ct_len <= Rb_len + D_len)
throw new Error('Illegal cipherText length: ' + ct_len + ' must be > ' + (Rb_len + D_len));

var Rb = cipherText.slice(0, Rb_len); // ephemeral public key bytes
var EM = cipherText.slice(Rb_len, ct_len - D_len); // encrypted content bytes
var D = cipherText.slice(ct_len - D_len);

logger.debug('Rb :\n%s', new Buffer(Rb).toString('hex'));
logger.debug('EM :\n%s', new Buffer(EM).toString('hex'));
logger.debug('D :\n%s', new Buffer(D).toString('hex'));

//convert bytes to usable key object
var ephPubKey = this._ecdsa.keyFromPublic(new Buffer(Rb, 'hex'), 'hex');
var privKey = this._ecdsa.keyFromPrivate(key.prvKeyHex, 'hex');
logger.debug('computing Z... %s, %s', privKey, ephPubKey);

var Z = privKey.derive(ephPubKey.pub);
logger.debug('Z computed: %s', Z);
logger.debug('Shared secret: ', new Buffer(Z.toArray(), 'hex'));
var kdfOutput = self._hkdf(Z.toArray(), ECIESKDFOutput, null, null);
// obtain the encryption key used to decrypt the token bytes
var aesKey = kdfOutput.slice(0, AESKeyLength);
// obtain the hashing key for verifying the token bytes with MAC
var hmacKey = kdfOutput.slice(AESKeyLength, AESKeyLength + HMACKeyLength);
logger.debug('aesKey: ', new Buffer(aesKey, 'hex'));
logger.debug('hmacKey: ', new Buffer(hmacKey, 'hex'));

var recoveredD = self._hmac(hmacKey, EM);
logger.debug('recoveredD: ', new Buffer(recoveredD).toString('hex'));

if (D.compare(new Buffer(recoveredD)) != 0) {
// debug('D='+D.toString('hex')+' vs '+new Buffer(recoveredD).toString('hex'));
throw new Error('HMAC verify failed when trying to decrypt token challenge during user enrollment');
}
var iv = EM.slice(0, IVLength);
var cipher = crypto.createDecipheriv('aes-256-cfb', new Buffer(aesKey), iv);
var decryptedBytes = cipher.update(EM.slice(IVLength));
logger.debug('decryptedBytes: ',new Buffer(decryptedBytes).toString('hex'));
return decryptedBytes;
}

_hkdf(ikm, keyBitLength, salt, info) {

if (!salt)
salt = _zeroBuffer(this._hashOutputSize);

if (!info)
info = '';

var key = CryptoSuite_ECDSA_AES._hkdf2(bytesToBits(new Buffer(ikm)), keyBitLength, bytesToBits(salt), info, this._hashFunctionKeyDerivation);

return bitsToBytes(key);

}


_hmac(key, bytes) {
logger.debug('HMAC key: ', JSON.stringify(key));
logger.debug('bytes to digest: ', JSON.stringify(bytes));

var hmac = new sjcl.misc.hmac(bytesToBits(key), this._hashFunctionKeyDerivation);
hmac.update(bytesToBits(bytes));
var result = hmac.digest();
logger.debug('HMAC digest: ', bitsToBytes(result));
return bitsToBytes(result);
}

/** HKDF with the specified hash function.
* @param {bitArray} ikm The input keying material.
* @param {Number} keyBitLength The output key length, in bits.
* @param {String|bitArray} salt The salt for HKDF.
* @param {String|bitArray} info The info for HKDF.
* @param {Object} [Hash=sjcl.hash.sha256] The hash function to use.
* @return {bitArray} derived key.
* @ignore
*/
static _hkdf2(ikm, keyBitLength, salt, info, Hash) {
var hmac, key, i, hashLen, loops, curOut, ret = [];

// Hash = Hash || sjcl.hash.sha256;
if (typeof info === 'string') {
info = sjcl.codec.utf8String.toBits(info);
} else if (!info) {
info = sjcl.codec.utf8String.toBits('');
}
if (typeof salt === 'string') {
salt = sjcl.codec.utf8String.toBits(salt);
} else if (!salt) {
salt = [];
}

hmac = new sjcl.misc.hmac(salt, Hash);
//key = hmac.mac(ikm);
hmac.update(ikm);
key = hmac.digest();
// debug('prk: %j', new Buffer(bitsToBytes(key)).toString('hex'));
hashLen = sjcl.bitArray.bitLength(key);

loops = Math.ceil(keyBitLength / hashLen);
if (loops > 255) {
throw new sjcl.exception.invalid('key bit length is too large for hkdf');
}

curOut = [];
for (i = 1; i <= loops; i++) {
hmac = new sjcl.misc.hmac(key, Hash);
hmac.update(curOut);
hmac.update(info);
// debug('sjcl.bitArray.partial(8, i): %j', sjcl.bitArray.partial(8, i));
hmac.update(bytesToBits([i]));

// hmac.update([sjcl.bitArray.partial(8, i)]);
curOut = hmac.digest();
ret = sjcl.bitArray.concat(ret, curOut);
}
return sjcl.bitArray.clamp(ret, keyBitLength);
throw new Error('Not implemented yet');
}
}; // end Crypto class
};

function _zeroBuffer(length) {
var buf = new Buffer(length);
Expand Down
41 changes: 0 additions & 41 deletions test/unit/headless-tests.js
Original file line number Diff line number Diff line change
Expand Up @@ -1187,47 +1187,6 @@ test('\n\n ** CryptoSuite_ECDSA_AES - function tests **\n\n', function (t) {
return cryptoUtils.generateKey();
})
.then(function (key) {
t.throws(
function () {
utils.setConfigSetting('crypto-keysize', 384);
cryptoUtils = utils.getCryptoSuite();
cryptoUtils.decrypt(key, 'fakeCipherText');
},
/^Error: Invalid key./,
'CryptoSuite_ECDSA_AES function tests: decrypt should throw ' +
'"Error: Invalid key. It\'s security does not match the current security level 384 256"'
);

utils.setConfigSetting('crypto-keysize', 256);
utils.setConfigSetting('crypto-hash-algo', 'SHA3');
cryptoUtils = utils.getCryptoSuite();
return cryptoUtils.generateKey();
})
.then(function (key) {
t.throws(
function () {
cryptoUtils.decrypt(key, 'fakeCipherText');
},
/^Error: Illegal cipherText length/,
'CryptoSuite_ECDSA_AES function tests: decrypt should throw ' +
'"Error: Illegal cipherText length: 14 must be > 97"'
);

utils.setConfigSetting('crypto-keysize', 256);
utils.setConfigSetting('crypto-hash-algo', 'SHA3');
cryptoUtils = utils.getCryptoSuite();
return cryptoUtils.generateKey();
})
.then(function (key) {
t.throws(
function () {
cryptoUtils.decrypt(key, '66616b654369706865725465787431323334353637383930313233343536373839303132333435363738393031323334353637383930313233343536373839303132333435363738393031323334353637383930313233343536373839303132333435363738393031323334353637383930');
},
/^TypeError: Invalid hex string/,
'CryptoSuite_ECDSA_AES function tests: sign() should throw ' +
'"TypeError: Invalid hex string"'
);

t.throws(
function () {
cryptoUtils.sign();
Expand Down

0 comments on commit e6a2572

Please sign in to comment.