Skip to content
This repository has been archived by the owner on Dec 30, 2020. It is now read-only.

Commit

Permalink
Native EC Key Generator and AES GCM dependency updated (#151)
Browse files Browse the repository at this point in the history
* AES GCM algs updated and ECKey Generator modified
  • Loading branch information
Spomky authored Nov 22, 2016
1 parent 923b6e9 commit b3a4175
Show file tree
Hide file tree
Showing 5 changed files with 60 additions and 48 deletions.
6 changes: 3 additions & 3 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -3,16 +3,16 @@ language: php
sudo: true

matrix:
allow_failures:
- php: nightly
fast_finish: true
include:
- php: 5.6
env: deps=low
- php: 5.6
env: WITH_CRYPTO=true
- php: 7.0
env: deps=low
- php: 7.0
env: WITH_CRYPTO=true
env: deps=low
- php: 7.1
- php: hhvm
- php: hhvm
Expand Down
2 changes: 1 addition & 1 deletion composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@
"lib-openssl": "*",
"spomky-labs/base64url": "^1.0",
"spomky-labs/aes-key-wrap": "^3.0",
"spomky-labs/php-aes-gcm": "^1.0",
"spomky-labs/php-aes-gcm": "^1.2",
"beberlei/assert": "^2.4",
"symfony/polyfill-mbstring": "^1.1",
"symfony/polyfill-php70": "^1.1",
Expand Down
16 changes: 0 additions & 16 deletions src/Algorithm/ContentEncryption/AESGCM.php
Original file line number Diff line number Diff line change
Expand Up @@ -27,22 +27,6 @@ public function encryptContent($data, $cek, $iv, $aad, $encoded_protected_header
$calculated_aad .= '.'.$aad;
}

if (version_compare(PHP_VERSION, '7.1.0') >= 0) {
return openssl_encrypt($data, $this->getMode($cek), $cek, OPENSSL_RAW_DATA, $iv, $tag, $calculated_aad, 16);
} elseif (class_exists('\Crypto\Cipher')) {
$cipher = Cipher::aes(Cipher::MODE_GCM, $this->getKeySize());
$calculated_aad = $encoded_protected_header;
if (null !== $aad) {
$calculated_aad .= '.'.$aad;
}

$cipher->setAAD($calculated_aad);
$cyphertext = $cipher->encrypt($data, $cek, $iv);
$tag = $cipher->getTag();

return $cyphertext;
}

list($cyphertext, $tag) = GCM::encrypt($cek, $iv, $data, $calculated_aad);

return $cyphertext;
Expand Down
16 changes: 2 additions & 14 deletions src/Algorithm/KeyEncryption/AESGCMKW.php
Original file line number Diff line number Diff line change
Expand Up @@ -32,20 +32,8 @@ public function wrapKey(JWKInterface $key, $cek, array $complete_headers, array
$iv = random_bytes(96 / 8);
$additional_headers['iv'] = Base64Url::encode($iv);

if (version_compare(PHP_VERSION, '7.1.0') >= 0) {
$tag = null;
$encrypted_cek = openssl_encrypt($cek, $this->getMode($kek), $kek, OPENSSL_RAW_DATA, $iv, $tag, null, 16);
$additional_headers['tag'] = Base64Url::encode($tag);
} elseif (class_exists('\Crypto\Cipher')) {
$cipher = Cipher::aes(Cipher::MODE_GCM, $this->getKeySize());
$cipher->setAAD(null);
$encrypted_cek = $cipher->encrypt($cek, $kek, $iv);

$additional_headers['tag'] = Base64Url::encode($cipher->getTag());
} else {
list($encrypted_cek, $tag) = AESGCM::encrypt($kek, $iv, $cek, null);
$additional_headers['tag'] = Base64Url::encode($tag);
}
list($encrypted_cek, $tag) = AESGCM::encrypt($kek, $iv, $cek, null);
$additional_headers['tag'] = Base64Url::encode($tag);

return $encrypted_cek;
}
Expand Down
68 changes: 54 additions & 14 deletions src/Factory/JWKFactory.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@

use Assert\Assertion;
use Base64Url\Base64Url;
use Jose\KeyConverter\ECKey;
use Jose\KeyConverter\KeyConverter;
use Jose\KeyConverter\RSAKey;
use Jose\Object\JKUJWKSet;
Expand Down Expand Up @@ -119,20 +120,38 @@ public static function createECKey(array $values)
{
Assertion::keyExists($values, 'crv', 'The curve is not set.');
$curve = $values['crv'];
$curve_name = self::getNistName($curve);
$generator = CurveFactory::getGeneratorByName($curve_name);
$private_key = $generator->createPrivateKey();

$values = array_merge(
$values,
[
'kty' => 'EC',
'crv' => $curve,
'x' => self::encodeValue($private_key->getPublicKey()->getPoint()->getX()),
'y' => self::encodeValue($private_key->getPublicKey()->getPoint()->getY()),
'd' => self::encodeValue($private_key->getSecret()),
]
);
if (function_exists('openssl_get_curve_names')) {
$args = [
'curve_name' => self::getOpensslName($curve),
'private_key_type' => OPENSSL_KEYTYPE_EC,
];
$key = openssl_pkey_new($args);
$res = openssl_pkey_export($key, $out);
Assertion::true($res, 'Unable to create the key');

$rsa = new ECKey($out);
$values = array_merge(
$values,
$rsa->toArray()
);

return new JWK($values);
} else {
$curve_name = self::getNistName($curve);
$generator = CurveFactory::getGeneratorByName($curve_name);
$private_key = $generator->createPrivateKey();

$values = array_merge(
$values,
[
'kty' => 'EC',
'crv' => $curve,
'x' => self::encodeValue($private_key->getPublicKey()->getPoint()->getX()),
'y' => self::encodeValue($private_key->getPublicKey()->getPoint()->getY()),
'd' => self::encodeValue($private_key->getSecret()),
]
);
}

return new JWK($values);
}
Expand Down Expand Up @@ -233,6 +252,27 @@ private static function convertDecToBin($value)
return hex2bin($adapter->decHex($value));
}

/**
* @param string $curve
*
* @throws \InvalidArgumentException
*
* @return string
*/
private static function getOpensslName($curve)
{
switch ($curve) {
case 'P-256':
return 'prime256v1';
case 'P-384':
return 'secp384r1';
case 'P-521':
return 'secp521r1';
default:
throw new \InvalidArgumentException(sprintf('The curve "%s" is not supported.', $curve));
}
}

/**
* @param string $curve
*
Expand Down

0 comments on commit b3a4175

Please sign in to comment.