- * $cipher_code = array(
+ * $cipher_code = [
* 'init_crypt' => (string) '', // optional
* 'init_encrypt' => (string) '', // optional
* 'init_decrypt' => (string) '', // optional
* 'encrypt_block' => (string) '', // required
* 'decrypt_block' => (string) '' // required
- * );
+ * ];
*
*
- * @see self::_setupInlineCrypt()
+ * @see self::setupInlineCrypt()
* @see self::encrypt()
* @see self::decrypt()
* @param array $cipher_code
- * @access private
* @return string (the name of the created callback function)
*/
- function _createInlineCryptFunction($cipher_code)
+ protected function createInlineCryptFunction($cipher_code)
{
$block_size = $this->block_size;
@@ -2380,9 +2788,9 @@ abstract class Base
$_ciphertext = "";
$_plaintext_len = strlen($_text);
- for ($_i = 0; $_i < $_plaintext_len; $_i+= '.$block_size.') {
- $in = substr($_text, $_i, '.$block_size.');
- '.$encrypt_block.'
+ for ($_i = 0; $_i < $_plaintext_len; $_i+= ' . $block_size . ') {
+ $in = substr($_text, $_i, ' . $block_size . ');
+ ' . $encrypt_block . '
$_ciphertext.= $in;
}
@@ -2391,49 +2799,49 @@ abstract class Base
$decrypt = $init_decrypt . '
$_plaintext = "";
- $_text = str_pad($_text, strlen($_text) + ('.$block_size.' - strlen($_text) % '.$block_size.') % '.$block_size.', chr(0));
+ $_text = str_pad($_text, strlen($_text) + (' . $block_size . ' - strlen($_text) % ' . $block_size . ') % ' . $block_size . ', chr(0));
$_ciphertext_len = strlen($_text);
- for ($_i = 0; $_i < $_ciphertext_len; $_i+= '.$block_size.') {
- $in = substr($_text, $_i, '.$block_size.');
- '.$decrypt_block.'
+ for ($_i = 0; $_i < $_ciphertext_len; $_i+= ' . $block_size . ') {
+ $in = substr($_text, $_i, ' . $block_size . ');
+ ' . $decrypt_block . '
$_plaintext.= $in;
}
- return $self->_unpad($_plaintext);
+ return $this->unpad($_plaintext);
';
break;
case self::MODE_CTR:
$encrypt = $init_encrypt . '
$_ciphertext = "";
$_plaintext_len = strlen($_text);
- $_xor = $self->encryptIV;
- $_buffer = &$self->enbuffer;
+ $_xor = $this->encryptIV;
+ $_buffer = &$this->enbuffer;
if (strlen($_buffer["ciphertext"])) {
- for ($_i = 0; $_i < $_plaintext_len; $_i+= '.$block_size.') {
- $_block = substr($_text, $_i, '.$block_size.');
+ for ($_i = 0; $_i < $_plaintext_len; $_i+= ' . $block_size . ') {
+ $_block = substr($_text, $_i, ' . $block_size . ');
if (strlen($_block) > strlen($_buffer["ciphertext"])) {
$in = $_xor;
- '.$encrypt_block.'
- $self->_increment_str($_xor);
+ ' . $encrypt_block . '
+ \phpseclib3\Common\Functions\Strings::increment_str($_xor);
$_buffer["ciphertext"].= $in;
}
- $_key = $self->_string_shift($_buffer["ciphertext"], '.$block_size.');
+ $_key = \phpseclib3\Common\Functions\Strings::shift($_buffer["ciphertext"], ' . $block_size . ');
$_ciphertext.= $_block ^ $_key;
}
} else {
- for ($_i = 0; $_i < $_plaintext_len; $_i+= '.$block_size.') {
- $_block = substr($_text, $_i, '.$block_size.');
+ for ($_i = 0; $_i < $_plaintext_len; $_i+= ' . $block_size . ') {
+ $_block = substr($_text, $_i, ' . $block_size . ');
$in = $_xor;
- '.$encrypt_block.'
- $self->_increment_str($_xor);
+ ' . $encrypt_block . '
+ \phpseclib3\Common\Functions\Strings::increment_str($_xor);
$_key = $in;
$_ciphertext.= $_block ^ $_key;
}
}
- if ($self->continuousBuffer) {
- $self->encryptIV = $_xor;
- if ($_start = $_plaintext_len % '.$block_size.') {
+ if ($this->continuousBuffer) {
+ $this->encryptIV = $_xor;
+ if ($_start = $_plaintext_len % ' . $block_size . ') {
$_buffer["ciphertext"] = substr($_key, $_start) . $_buffer["ciphertext"];
}
}
@@ -2444,34 +2852,34 @@ abstract class Base
$decrypt = $init_encrypt . '
$_plaintext = "";
$_ciphertext_len = strlen($_text);
- $_xor = $self->decryptIV;
- $_buffer = &$self->debuffer;
+ $_xor = $this->decryptIV;
+ $_buffer = &$this->debuffer;
if (strlen($_buffer["ciphertext"])) {
- for ($_i = 0; $_i < $_ciphertext_len; $_i+= '.$block_size.') {
- $_block = substr($_text, $_i, '.$block_size.');
+ for ($_i = 0; $_i < $_ciphertext_len; $_i+= ' . $block_size . ') {
+ $_block = substr($_text, $_i, ' . $block_size . ');
if (strlen($_block) > strlen($_buffer["ciphertext"])) {
$in = $_xor;
- '.$encrypt_block.'
- $self->_increment_str($_xor);
+ ' . $encrypt_block . '
+ \phpseclib3\Common\Functions\Strings::increment_str($_xor);
$_buffer["ciphertext"].= $in;
}
- $_key = $self->_string_shift($_buffer["ciphertext"], '.$block_size.');
+ $_key = \phpseclib3\Common\Functions\Strings::shift($_buffer["ciphertext"], ' . $block_size . ');
$_plaintext.= $_block ^ $_key;
}
} else {
- for ($_i = 0; $_i < $_ciphertext_len; $_i+= '.$block_size.') {
- $_block = substr($_text, $_i, '.$block_size.');
+ for ($_i = 0; $_i < $_ciphertext_len; $_i+= ' . $block_size . ') {
+ $_block = substr($_text, $_i, ' . $block_size . ');
$in = $_xor;
- '.$encrypt_block.'
- $self->_increment_str($_xor);
+ ' . $encrypt_block . '
+ \phpseclib3\Common\Functions\Strings::increment_str($_xor);
$_key = $in;
$_plaintext.= $_block ^ $_key;
}
}
- if ($self->continuousBuffer) {
- $self->decryptIV = $_xor;
- if ($_start = $_ciphertext_len % '.$block_size.') {
+ if ($this->continuousBuffer) {
+ $this->decryptIV = $_xor;
+ if ($_start = $_ciphertext_len % ' . $block_size . ') {
$_buffer["ciphertext"] = substr($_key, $_start) . $_buffer["ciphertext"];
}
}
@@ -2482,20 +2890,20 @@ abstract class Base
case self::MODE_CFB:
$encrypt = $init_encrypt . '
$_ciphertext = "";
- $_buffer = &$self->enbuffer;
+ $_buffer = &$this->enbuffer;
- if ($self->continuousBuffer) {
- $_iv = &$self->encryptIV;
+ if ($this->continuousBuffer) {
+ $_iv = &$this->encryptIV;
$_pos = &$_buffer["pos"];
} else {
- $_iv = $self->encryptIV;
+ $_iv = $this->encryptIV;
$_pos = 0;
}
$_len = strlen($_text);
$_i = 0;
if ($_pos) {
$_orig_pos = $_pos;
- $_max = '.$block_size.' - $_pos;
+ $_max = ' . $block_size . ' - $_pos;
if ($_len >= $_max) {
$_i = $_max;
$_len-= $_max;
@@ -2508,17 +2916,17 @@ abstract class Base
$_ciphertext = substr($_iv, $_orig_pos) ^ $_text;
$_iv = substr_replace($_iv, $_ciphertext, $_orig_pos, $_i);
}
- while ($_len >= '.$block_size.') {
+ while ($_len >= ' . $block_size . ') {
$in = $_iv;
- '.$encrypt_block.';
- $_iv = $in ^ substr($_text, $_i, '.$block_size.');
+ ' . $encrypt_block . ';
+ $_iv = $in ^ substr($_text, $_i, ' . $block_size . ');
$_ciphertext.= $_iv;
- $_len-= '.$block_size.';
- $_i+= '.$block_size.';
+ $_len-= ' . $block_size . ';
+ $_i+= ' . $block_size . ';
}
if ($_len) {
$in = $_iv;
- '.$encrypt_block.'
+ ' . $encrypt_block . '
$_iv = $in;
$_block = $_iv ^ substr($_text, $_i);
$_iv = substr_replace($_iv, $_block, 0, $_len);
@@ -2530,20 +2938,20 @@ abstract class Base
$decrypt = $init_encrypt . '
$_plaintext = "";
- $_buffer = &$self->debuffer;
+ $_buffer = &$this->debuffer;
- if ($self->continuousBuffer) {
- $_iv = &$self->decryptIV;
+ if ($this->continuousBuffer) {
+ $_iv = &$this->decryptIV;
$_pos = &$_buffer["pos"];
} else {
- $_iv = $self->decryptIV;
+ $_iv = $this->decryptIV;
$_pos = 0;
}
$_len = strlen($_text);
$_i = 0;
if ($_pos) {
$_orig_pos = $_pos;
- $_max = '.$block_size.' - $_pos;
+ $_max = ' . $block_size . ' - $_pos;
if ($_len >= $_max) {
$_i = $_max;
$_len-= $_max;
@@ -2556,19 +2964,19 @@ abstract class Base
$_plaintext = substr($_iv, $_orig_pos) ^ $_text;
$_iv = substr_replace($_iv, substr($_text, 0, $_i), $_orig_pos, $_i);
}
- while ($_len >= '.$block_size.') {
+ while ($_len >= ' . $block_size . ') {
$in = $_iv;
- '.$encrypt_block.'
+ ' . $encrypt_block . '
$_iv = $in;
- $cb = substr($_text, $_i, '.$block_size.');
+ $cb = substr($_text, $_i, ' . $block_size . ');
$_plaintext.= $_iv ^ $cb;
$_iv = $cb;
- $_len-= '.$block_size.';
- $_i+= '.$block_size.';
+ $_len-= ' . $block_size . ';
+ $_i+= ' . $block_size . ';
}
if ($_len) {
$in = $_iv;
- '.$encrypt_block.'
+ ' . $encrypt_block . '
$_iv = $in;
$_plaintext.= $_iv ^ substr($_text, $_i);
$_iv = substr_replace($_iv, substr($_text, $_i), 0, $_len);
@@ -2582,20 +2990,20 @@ abstract class Base
$encrypt = $init_encrypt . '
$_ciphertext = "";
$_len = strlen($_text);
- $_iv = $self->encryptIV;
+ $_iv = $this->encryptIV;
for ($_i = 0; $_i < $_len; ++$_i) {
$in = $_iv;
- '.$encrypt_block.'
- $_ciphertext.= ($_c = $_text[$_i] ^ $in);
+ ' . $encrypt_block . '
+ $_ciphertext .= ($_c = $_text[$_i] ^ $in);
$_iv = substr($_iv, 1) . $_c;
}
- if ($self->continuousBuffer) {
- if ($_len >= '.$block_size.') {
- $self->encryptIV = substr($_ciphertext, -'.$block_size.');
+ if ($this->continuousBuffer) {
+ if ($_len >= ' . $block_size . ') {
+ $this->encryptIV = substr($_ciphertext, -' . $block_size . ');
} else {
- $self->encryptIV = substr($self->encryptIV, $_len - '.$block_size.') . substr($_ciphertext, -$_len);
+ $this->encryptIV = substr($this->encryptIV, $_len - ' . $block_size . ') . substr($_ciphertext, -$_len);
}
}
@@ -2604,20 +3012,20 @@ abstract class Base
$decrypt = $init_encrypt . '
$_plaintext = "";
$_len = strlen($_text);
- $_iv = $self->decryptIV;
+ $_iv = $this->decryptIV;
for ($_i = 0; $_i < $_len; ++$_i) {
$in = $_iv;
- '.$encrypt_block.'
- $_plaintext.= $_text[$_i] ^ $in;
+ ' . $encrypt_block . '
+ $_plaintext .= $_text[$_i] ^ $in;
$_iv = substr($_iv, 1) . $_text[$_i];
}
- if ($self->continuousBuffer) {
- if ($_len >= '.$block_size.') {
- $self->decryptIV = substr($_text, -'.$block_size.');
+ if ($this->continuousBuffer) {
+ if ($_len >= ' . $block_size . ') {
+ $this->decryptIV = substr($_text, -' . $block_size . ');
} else {
- $self->decryptIV = substr($self->decryptIV, $_len - '.$block_size.') . substr($_text, -$_len);
+ $this->decryptIV = substr($this->decryptIV, $_len - ' . $block_size . ') . substr($_text, -$_len);
}
}
@@ -2628,17 +3036,17 @@ abstract class Base
$encrypt = $init_encrypt . '
$_ciphertext = "";
$_len = strlen($_text);
- $_iv = $self->encryptIV;
+ $_iv = $this->encryptIV;
for ($_i = 0; $_i < $_len; ++$_i) {
$in = $_iv;
- '.$encrypt_block.'
+ ' . $encrypt_block . '
$_ciphertext.= $_text[$_i] ^ $in;
$_iv = substr($_iv, 1) . $in[0];
}
- if ($self->continuousBuffer) {
- $self->encryptIV = $_iv;
+ if ($this->continuousBuffer) {
+ $this->encryptIV = $_iv;
}
return $_ciphertext;
@@ -2646,17 +3054,17 @@ abstract class Base
$decrypt = $init_encrypt . '
$_plaintext = "";
$_len = strlen($_text);
- $_iv = $self->decryptIV;
+ $_iv = $this->decryptIV;
for ($_i = 0; $_i < $_len; ++$_i) {
$in = $_iv;
- '.$encrypt_block.'
+ ' . $encrypt_block . '
$_plaintext.= $_text[$_i] ^ $in;
$_iv = substr($_iv, 1) . $in[0];
}
- if ($self->continuousBuffer) {
- $self->decryptIV = $_iv;
+ if ($this->continuousBuffer) {
+ $this->decryptIV = $_iv;
}
return $_plaintext;
@@ -2666,33 +3074,33 @@ abstract class Base
$encrypt = $init_encrypt . '
$_ciphertext = "";
$_plaintext_len = strlen($_text);
- $_xor = $self->encryptIV;
- $_buffer = &$self->enbuffer;
+ $_xor = $this->encryptIV;
+ $_buffer = &$this->enbuffer;
if (strlen($_buffer["xor"])) {
- for ($_i = 0; $_i < $_plaintext_len; $_i+= '.$block_size.') {
- $_block = substr($_text, $_i, '.$block_size.');
+ for ($_i = 0; $_i < $_plaintext_len; $_i+= ' . $block_size . ') {
+ $_block = substr($_text, $_i, ' . $block_size . ');
if (strlen($_block) > strlen($_buffer["xor"])) {
$in = $_xor;
- '.$encrypt_block.'
+ ' . $encrypt_block . '
$_xor = $in;
$_buffer["xor"].= $_xor;
}
- $_key = $self->_string_shift($_buffer["xor"], '.$block_size.');
+ $_key = \phpseclib3\Common\Functions\Strings::shift($_buffer["xor"], ' . $block_size . ');
$_ciphertext.= $_block ^ $_key;
}
} else {
- for ($_i = 0; $_i < $_plaintext_len; $_i+= '.$block_size.') {
+ for ($_i = 0; $_i < $_plaintext_len; $_i+= ' . $block_size . ') {
$in = $_xor;
- '.$encrypt_block.'
+ ' . $encrypt_block . '
$_xor = $in;
- $_ciphertext.= substr($_text, $_i, '.$block_size.') ^ $_xor;
+ $_ciphertext.= substr($_text, $_i, ' . $block_size . ') ^ $_xor;
}
$_key = $_xor;
}
- if ($self->continuousBuffer) {
- $self->encryptIV = $_xor;
- if ($_start = $_plaintext_len % '.$block_size.') {
+ if ($this->continuousBuffer) {
+ $this->encryptIV = $_xor;
+ if ($_start = $_plaintext_len % ' . $block_size . ') {
$_buffer["xor"] = substr($_key, $_start) . $_buffer["xor"];
}
}
@@ -2702,33 +3110,33 @@ abstract class Base
$decrypt = $init_encrypt . '
$_plaintext = "";
$_ciphertext_len = strlen($_text);
- $_xor = $self->decryptIV;
- $_buffer = &$self->debuffer;
+ $_xor = $this->decryptIV;
+ $_buffer = &$this->debuffer;
if (strlen($_buffer["xor"])) {
- for ($_i = 0; $_i < $_ciphertext_len; $_i+= '.$block_size.') {
- $_block = substr($_text, $_i, '.$block_size.');
+ for ($_i = 0; $_i < $_ciphertext_len; $_i+= ' . $block_size . ') {
+ $_block = substr($_text, $_i, ' . $block_size . ');
if (strlen($_block) > strlen($_buffer["xor"])) {
$in = $_xor;
- '.$encrypt_block.'
+ ' . $encrypt_block . '
$_xor = $in;
$_buffer["xor"].= $_xor;
}
- $_key = $self->_string_shift($_buffer["xor"], '.$block_size.');
+ $_key = \phpseclib3\Common\Functions\Strings::shift($_buffer["xor"], ' . $block_size . ');
$_plaintext.= $_block ^ $_key;
}
} else {
- for ($_i = 0; $_i < $_ciphertext_len; $_i+= '.$block_size.') {
+ for ($_i = 0; $_i < $_ciphertext_len; $_i+= ' . $block_size . ') {
$in = $_xor;
- '.$encrypt_block.'
+ ' . $encrypt_block . '
$_xor = $in;
- $_plaintext.= substr($_text, $_i, '.$block_size.') ^ $_xor;
+ $_plaintext.= substr($_text, $_i, ' . $block_size . ') ^ $_xor;
}
$_key = $_xor;
}
- if ($self->continuousBuffer) {
- $self->decryptIV = $_xor;
- if ($_start = $_ciphertext_len % '.$block_size.') {
+ if ($this->continuousBuffer) {
+ $this->decryptIV = $_xor;
+ if ($_start = $_ciphertext_len % ' . $block_size . ') {
$_buffer["xor"] = substr($_key, $_start) . $_buffer["xor"];
}
}
@@ -2738,12 +3146,12 @@ abstract class Base
case self::MODE_STREAM:
$encrypt = $init_encrypt . '
$_ciphertext = "";
- '.$encrypt_block.'
+ ' . $encrypt_block . '
return $_ciphertext;
';
$decrypt = $init_decrypt . '
$_plaintext = "";
- '.$decrypt_block.'
+ ' . $decrypt_block . '
return $_plaintext;
';
break;
@@ -2753,16 +3161,16 @@ abstract class Base
$_ciphertext = "";
$_plaintext_len = strlen($_text);
- $in = $self->encryptIV;
+ $in = $this->encryptIV;
- for ($_i = 0; $_i < $_plaintext_len; $_i+= '.$block_size.') {
- $in = substr($_text, $_i, '.$block_size.') ^ $in;
- '.$encrypt_block.'
+ for ($_i = 0; $_i < $_plaintext_len; $_i+= ' . $block_size . ') {
+ $in = substr($_text, $_i, ' . $block_size . ') ^ $in;
+ ' . $encrypt_block . '
$_ciphertext.= $in;
}
- if ($self->continuousBuffer) {
- $self->encryptIV = $in;
+ if ($this->continuousBuffer) {
+ $this->encryptIV = $in;
}
return $_ciphertext;
@@ -2770,86 +3178,33 @@ abstract class Base
$decrypt = $init_decrypt . '
$_plaintext = "";
- $_text = str_pad($_text, strlen($_text) + ('.$block_size.' - strlen($_text) % '.$block_size.') % '.$block_size.', chr(0));
+ $_text = str_pad($_text, strlen($_text) + (' . $block_size . ' - strlen($_text) % ' . $block_size . ') % ' . $block_size . ', chr(0));
$_ciphertext_len = strlen($_text);
- $_iv = $self->decryptIV;
+ $_iv = $this->decryptIV;
- for ($_i = 0; $_i < $_ciphertext_len; $_i+= '.$block_size.') {
- $in = $_block = substr($_text, $_i, '.$block_size.');
- '.$decrypt_block.'
+ for ($_i = 0; $_i < $_ciphertext_len; $_i+= ' . $block_size . ') {
+ $in = $_block = substr($_text, $_i, ' . $block_size . ');
+ ' . $decrypt_block . '
$_plaintext.= $in ^ $_iv;
$_iv = $_block;
}
- if ($self->continuousBuffer) {
- $self->decryptIV = $_iv;
+ if ($this->continuousBuffer) {
+ $this->decryptIV = $_iv;
}
- return $self->_unpad($_plaintext);
+ return $this->unpad($_plaintext);
';
break;
}
- // Create the $inline function and return its name as string. Ready to run!
- eval('$func = function ($_action, &$self, $_text) { ' . $init_crypt . 'if ($_action == "encrypt") { ' . $encrypt . ' } else { ' . $decrypt . ' } };');
- return $func;
- }
+ // Before discrediting this, please read the following:
+ // @see https://github.com/phpseclib/phpseclib/issues/1293
+ // @see https://github.com/phpseclib/phpseclib/pull/1143
+ eval('$func = function ($_action, $_text) { ' . $init_crypt . 'if ($_action == "encrypt") { ' . $encrypt . ' } else { ' . $decrypt . ' }};');
- /**
- * Holds the lambda_functions table (classwide)
- *
- * Each name of the lambda function, created from
- * _setupInlineCrypt() && _createInlineCryptFunction()
- * is stored, classwide (!), here for reusing.
- *
- * The string-based index of $function is a classwide
- * unique value representing, at least, the $mode of
- * operation (or more... depends of the optimizing level)
- * for which $mode the lambda function was created.
- *
- * @access private
- * @return array &$functions
- */
- function &_getLambdaFunctions()
- {
- static $functions = array();
- return $functions;
- }
-
- /**
- * Generates a digest from $bytes
- *
- * @see self::_setupInlineCrypt()
- * @access private
- * @param string $bytes
- * @return string
- */
- function _hashInlineCryptFunction($bytes)
- {
- if (!isset(self::$WHIRLPOOL_AVAILABLE)) {
- self::$WHIRLPOOL_AVAILABLE = extension_loaded('hash') && in_array('whirlpool', hash_algos());
- }
-
- $result = '';
- $hash = $bytes;
-
- switch (true) {
- case self::$WHIRLPOOL_AVAILABLE:
- foreach (str_split($bytes, 64) as $t) {
- $hash = hash('whirlpool', $hash, true);
- $result .= $t ^ $hash;
- }
- return $result . hash('whirlpool', $hash, true);
- default:
- $len = strlen($bytes);
- for ($i = 0; $i < $len; $i+=20) {
- $t = substr($bytes, $i, 20);
- $hash = pack('H*', sha1($hash));
- $result .= $t ^ $hash;
- }
- return $result . pack('H*', sha1($hash));
- }
+ return \Closure::bind($func, $this, static::class);
}
/**
@@ -2857,15 +3212,19 @@ abstract class Base
*
* On ARM CPUs converting floats to ints doesn't always work
*
- * @access private
* @param string $x
* @return int
*/
- function safe_intval($x)
+ protected static function safe_intval($x)
{
if (is_int($x)) {
return $x;
}
+
+ if (self::$use_reg_intval) {
+ return PHP_INT_SIZE == 4 && PHP_VERSION_ID >= 80100 ? intval($x) : $x;
+ }
+
return (fmod($x, 0x80000000) & 0x7FFFFFFF) |
((fmod(floor($x / 0x80000000), 2) & 1) << 31);
}
@@ -2873,13 +3232,12 @@ abstract class Base
/**
* eval()'able string for in-line float to int
*
- * @access private
* @return string
*/
- function safe_intval_inline()
+ protected static function safe_intval_inline()
{
- if (CRYPT_BASE_USE_REG_INTVAL) {
- return PHP_INT_SIZE == 4 ? 'intval(%s)' : '%s';
+ if (self::$use_reg_intval) {
+ return PHP_INT_SIZE == 4 && PHP_VERSION_ID >= 80100 ? 'intval(%s)' : '%s';
}
$safeint = '(is_int($temp = %s) ? $temp : (fmod($temp, 0x80000000) & 0x7FFFFFFF) | ';
@@ -2887,21 +3245,153 @@ abstract class Base
}
/**
- * Dummy error handler to suppress mcrypt errors
+ * Sets up GCM parameters
+ *
+ * See steps 1-2 of https://nvlpubs.nist.gov/nistpubs/Legacy/SP/nistspecialpublication800-38d.pdf#page=23
+ * for more info
*
- * @access private
*/
- function do_nothing()
+ private function setupGCM()
{
+ // don't keep on re-calculating $this->h
+ if (!$this->h || $this->hKey != $this->key) {
+ $cipher = new static('ecb');
+ $cipher->setKey($this->key);
+ $cipher->disablePadding();
+
+ $this->h = self::$gcmField->newInteger(
+ Strings::switchEndianness($cipher->encrypt("\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0"))
+ );
+ $this->hKey = $this->key;
+ }
+
+ if (strlen($this->nonce) == 12) {
+ $this->iv = $this->nonce . "\0\0\0\1";
+ } else {
+ $this->iv = $this->ghash(
+ self::nullPad128($this->nonce) . str_repeat("\0", 8) . self::len64($this->nonce)
+ );
+ }
+ }
+
+ /**
+ * Performs GHASH operation
+ *
+ * See https://nvlpubs.nist.gov/nistpubs/Legacy/SP/nistspecialpublication800-38d.pdf#page=20
+ * for more info
+ *
+ * @see self::decrypt()
+ * @see self::encrypt()
+ * @param string $x
+ * @return string
+ */
+ private function ghash($x)
+ {
+ $h = $this->h;
+ $y = ["\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0"];
+ $x = str_split($x, 16);
+ $n = 0;
+ // the switchEndianness calls are necessary because the multiplication algorithm in BinaryField/Integer
+ // interprets strings as polynomials in big endian order whereas in GCM they're interpreted in little
+ // endian order per https://nvlpubs.nist.gov/nistpubs/Legacy/SP/nistspecialpublication800-38d.pdf#page=19.
+ // big endian order is what binary field elliptic curves use per http://www.secg.org/sec1-v2.pdf#page=18.
+
+ // we could switchEndianness here instead of in the while loop but doing so in the while loop seems like it
+ // might be slightly more performant
+ //$x = Strings::switchEndianness($x);
+ foreach ($x as $xn) {
+ $xn = Strings::switchEndianness($xn);
+ $t = $y[$n] ^ $xn;
+ $temp = self::$gcmField->newInteger($t);
+ $y[++$n] = $temp->multiply($h)->toBytes();
+ $y[$n] = substr($y[$n], 1);
+ }
+ $y[$n] = Strings::switchEndianness($y[$n]);
+ return $y[$n];
+ }
+
+ /**
+ * Returns the bit length of a string in a packed format
+ *
+ * @see self::decrypt()
+ * @see self::encrypt()
+ * @see self::setupGCM()
+ * @param string $str
+ * @return string
+ */
+ private static function len64($str)
+ {
+ return "\0\0\0\0" . pack('N', 8 * strlen($str));
+ }
+
+ /**
+ * NULL pads a string to be a multiple of 128
+ *
+ * @see self::decrypt()
+ * @see self::encrypt()
+ * @see self::setupGCM()
+ * @param string $str
+ * @return string
+ */
+ protected static function nullPad128($str)
+ {
+ $len = strlen($str);
+ return $str . str_repeat("\0", 16 * ceil($len / 16) - $len);
+ }
+
+ /**
+ * Calculates Poly1305 MAC
+ *
+ * On my system ChaCha20, with libsodium, takes 0.5s. With this custom Poly1305 implementation
+ * it takes 1.2s.
+ *
+ * @see self::decrypt()
+ * @see self::encrypt()
+ * @param string $text
+ * @return string
+ */
+ protected function poly1305($text)
+ {
+ $s = $this->poly1305Key; // strlen($this->poly1305Key) == 32
+ $r = Strings::shift($s, 16);
+ $r = strrev($r);
+ $r &= "\x0f\xff\xff\xfc\x0f\xff\xff\xfc\x0f\xff\xff\xfc\x0f\xff\xff\xff";
+ $s = strrev($s);
+
+ $r = self::$poly1305Field->newInteger(new BigInteger($r, 256));
+ $s = self::$poly1305Field->newInteger(new BigInteger($s, 256));
+ $a = self::$poly1305Field->newInteger(new BigInteger());
+
+ $blocks = str_split($text, 16);
+ foreach ($blocks as $block) {
+ $n = strrev($block . chr(1));
+ $n = self::$poly1305Field->newInteger(new BigInteger($n, 256));
+ $a = $a->add($n);
+ $a = $a->multiply($r);
+ }
+ $r = $a->toBigInteger()->add($s->toBigInteger());
+ $mask = "\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF";
+ return strrev($r->toBytes()) & $mask;
+ }
+
+ /**
+ * Return the mode
+ *
+ * You can do $obj instanceof AES or whatever to get the cipher but you can't do that to get the mode
+ *
+ * @return string
+ */
+ public function getMode()
+ {
+ return array_flip(self::MODE_MAP)[$this->mode];
}
/**
* Is the continuous buffer enabled?
*
- * @access public
* @return boolean
*/
- function continuousBufferEnabled()
+ public function continuousBufferEnabled()
{
return $this->continuousBuffer;
}
diff --git a/vendor/phpseclib/phpseclib/phpseclib/Crypt/Common/Traits/Fingerprint.php b/vendor/phpseclib/phpseclib/phpseclib/Crypt/Common/Traits/Fingerprint.php
new file mode 100644
index 000000000..9ca8926d3
--- /dev/null
+++ b/vendor/phpseclib/phpseclib/phpseclib/Crypt/Common/Traits/Fingerprint.php
@@ -0,0 +1,57 @@
+
+ * @copyright 2015 Jim Wigginton
+ * @license http://www.opensource.org/licenses/mit-license.html MIT License
+ * @link http://phpseclib.sourceforge.net
+ */
+
+namespace phpseclib3\Crypt\Common\Traits;
+
+use phpseclib3\Crypt\Hash;
+
+/**
+ * Fingerprint Trait for Private Keys
+ *
+ * @author Jim Wigginton ' . Strings::base64_encode($p->toBytes()) . "
\r\n" . + '' . Strings::base64_encode($q->toBytes()) . "\r\n" . + '
* createKey());
+ * $private = Crypt\RSA::createKey();
+ * $public = $private->getPublicKey();
*
- * $plaintext = 'terrafrost';
+ * $plaintext = 'terrafrost';
*
- * $rsa->loadKey($privatekey);
- * $ciphertext = $rsa->encrypt($plaintext);
+ * $ciphertext = $public->encrypt($plaintext);
*
- * $rsa->loadKey($publickey);
- * echo $rsa->decrypt($ciphertext);
+ * echo $private->decrypt($ciphertext);
* ?>
*
*
* Here's an example of how to create signatures and verify signatures with this library:
*
* createKey());
+ * $private = Crypt\RSA::createKey();
+ * $public = $private->getPublicKey();
*
- * $plaintext = 'terrafrost';
+ * $plaintext = 'terrafrost';
*
- * $rsa->loadKey($privatekey);
- * $signature = $rsa->sign($plaintext);
+ * $signature = $private->sign($plaintext);
*
- * $rsa->loadKey($publickey);
- * echo $rsa->verify($plaintext, $signature) ? 'verified' : 'unverified';
+ * echo $public->verify($plaintext, $signature) ? 'verified' : 'unverified';
* ?>
*
*
- * @category Crypt
- * @package RSA
+ * One thing to consider when using this: so phpseclib uses PSS mode by default.
+ * Technically, id-RSASSA-PSS has a different key format than rsaEncryption. So
+ * should phpseclib save to the id-RSASSA-PSS format by default or the
+ * rsaEncryption format? For stand-alone keys I figure rsaEncryption is better
+ * because SSH doesn't use PSS and idk how many SSH servers would be able to
+ * decode an id-RSASSA-PSS key. For X.509 certificates the id-RSASSA-PSS
+ * format is used by default (unless you change it up to use PKCS1 instead)
+ *
* @author Jim Wigginton ' . base64_encode($raw['prime1']) . "
\r\n" . - '' . base64_encode($raw['prime2']) . "\r\n" . - '
' . Strings::base64_encode($primes[1]->toBytes()) . "
\r\n" . + '' . Strings::base64_encode($primes[2]->toBytes()) . "\r\n" . + '