TripleDES, Rijndael: Fix overflow in OFB mode

This commit is contained in:
terrafrost 2013-03-03 17:30:30 -06:00
parent 7ce05ed591
commit c4b3288851
2 changed files with 33 additions and 21 deletions

View File

@ -900,8 +900,10 @@ class Crypt_Rijndael {
$xor = $this->encryptIV; $xor = $this->encryptIV;
if (strlen($buffer['xor'])) { if (strlen($buffer['xor'])) {
for ($i = 0; $i < strlen($plaintext); $i+=$block_size) { for ($i = 0; $i < strlen($plaintext); $i+=$block_size) {
if (strlen($block) > strlen($buffer['xor'])) {
$xor = $this->_encryptBlock($xor); $xor = $this->_encryptBlock($xor);
$buffer['xor'].= $xor; $buffer['xor'].= $xor;
}
$key = $this->_string_shift($buffer['xor'], $block_size); $key = $this->_string_shift($buffer['xor'], $block_size);
$ciphertext.= substr($plaintext, $i, $block_size) ^ $key; $ciphertext.= substr($plaintext, $i, $block_size) ^ $key;
} }
@ -1038,8 +1040,10 @@ class Crypt_Rijndael {
$xor = $this->decryptIV; $xor = $this->decryptIV;
if (strlen($buffer['xor'])) { if (strlen($buffer['xor'])) {
for ($i = 0; $i < strlen($ciphertext); $i+=$block_size) { for ($i = 0; $i < strlen($ciphertext); $i+=$block_size) {
if (strlen($block) > strlen($buffer['xor'])) {
$xor = $this->_encryptBlock($xor); $xor = $this->_encryptBlock($xor);
$buffer['xor'].= $xor; $buffer['xor'].= $xor;
}
$key = $this->_string_shift($buffer['xor'], $block_size); $key = $this->_string_shift($buffer['xor'], $block_size);
$plaintext.= substr($ciphertext, $i, $block_size) ^ $key; $plaintext.= substr($ciphertext, $i, $block_size) ^ $key;
} }
@ -1139,7 +1143,7 @@ class Crypt_Rijndael {
$l = ($l + 1) % $Nb; $l = ($l + 1) % $Nb;
} }
// 100% ugly switch/case code... but ~5% faster (meaning: ~half second faster de/encrypting 1MB text, tested with php5.4.9 on linux/32bit with an AMD Athlon II P360 CPU) then the commented smart code below. Don't know it's worth or not // 100% ugly switch/case code... but ~5% faster ("smart code" below commented out)
switch ($Nb) { switch ($Nb) {
case 8: case 8:
return pack('N*', $temp[0], $temp[1], $temp[2], $temp[3], $temp[4], $temp[5], $temp[6], $temp[7]); return pack('N*', $temp[0], $temp[1], $temp[2], $temp[3], $temp[4], $temp[5], $temp[6], $temp[7]);
@ -1969,10 +1973,12 @@ class Crypt_Rijndael {
if (strlen($buffer["xor"])) { if (strlen($buffer["xor"])) {
for ($i = 0; $i < $plaintext_len; $i+= '.$block_size.') { for ($i = 0; $i < $plaintext_len; $i+= '.$block_size.') {
if (strlen($block) > strlen($buffer["xor"])) {
$in = $xor; $in = $xor;
'.$_encryptBlock.' '.$_encryptBlock.'
$xor = $in; $xor = $in;
$buffer["xor"].= $xor; $buffer["xor"].= $xor;
}
$key = $self->_string_shift($buffer["xor"], '.$block_size.'); $key = $self->_string_shift($buffer["xor"], '.$block_size.');
$ciphertext.= substr($text, $i, '.$block_size.') ^ $key; $ciphertext.= substr($text, $i, '.$block_size.') ^ $key;
} }
@ -2002,10 +2008,12 @@ class Crypt_Rijndael {
if (strlen($buffer["xor"])) { if (strlen($buffer["xor"])) {
for ($i = 0; $i < $ciphertext_len; $i+= '.$block_size.') { for ($i = 0; $i < $ciphertext_len; $i+= '.$block_size.') {
if (strlen($block) > strlen($buffer["xor"])) {
$in = $xor; $in = $xor;
'.$_encryptBlock.' '.$_encryptBlock.'
$xor = $in; $xor = $in;
$buffer["xor"].= $xor; $buffer["xor"].= $xor;
}
$key = $self->_string_shift($buffer["xor"], '.$block_size.'); $key = $self->_string_shift($buffer["xor"], '.$block_size.');
$plaintext.= substr($text, $i, '.$block_size.') ^ $key; $plaintext.= substr($text, $i, '.$block_size.') ^ $key;
} }

View File

@ -669,10 +669,12 @@ class Crypt_TripleDES {
$xor = $this->encryptIV; $xor = $this->encryptIV;
if (strlen($buffer['xor'])) { if (strlen($buffer['xor'])) {
for ($i = 0; $i < strlen($plaintext); $i+=8) { for ($i = 0; $i < strlen($plaintext); $i+=8) {
if (strlen($block) > strlen($buffer['xor'])) {
$xor = $des[0]->_processBlock($xor, CRYPT_DES_ENCRYPT); $xor = $des[0]->_processBlock($xor, CRYPT_DES_ENCRYPT);
$xor = $des[1]->_processBlock($xor, CRYPT_DES_DECRYPT); $xor = $des[1]->_processBlock($xor, CRYPT_DES_DECRYPT);
$xor = $des[2]->_processBlock($xor, CRYPT_DES_ENCRYPT); $xor = $des[2]->_processBlock($xor, CRYPT_DES_ENCRYPT);
$buffer['xor'].= $xor; $buffer['xor'].= $xor;
}
$key = $this->_string_shift($buffer['xor'], 8); $key = $this->_string_shift($buffer['xor'], 8);
$ciphertext.= substr($plaintext, $i, 8) ^ $key; $ciphertext.= substr($plaintext, $i, 8) ^ $key;
} }
@ -880,10 +882,12 @@ class Crypt_TripleDES {
$xor = $this->decryptIV; $xor = $this->decryptIV;
if (strlen($buffer['xor'])) { if (strlen($buffer['xor'])) {
for ($i = 0; $i < strlen($ciphertext); $i+=8) { for ($i = 0; $i < strlen($ciphertext); $i+=8) {
if (strlen($block) > strlen($buffer['xor'])) {
$xor = $des[0]->_processBlock($xor, CRYPT_DES_ENCRYPT); $xor = $des[0]->_processBlock($xor, CRYPT_DES_ENCRYPT);
$xor = $des[1]->_processBlock($xor, CRYPT_DES_DECRYPT); $xor = $des[1]->_processBlock($xor, CRYPT_DES_DECRYPT);
$xor = $des[2]->_processBlock($xor, CRYPT_DES_ENCRYPT); $xor = $des[2]->_processBlock($xor, CRYPT_DES_ENCRYPT);
$buffer['xor'].= $xor; $buffer['xor'].= $xor;
}
$key = $this->_string_shift($buffer['xor'], 8); $key = $this->_string_shift($buffer['xor'], 8);
$plaintext.= substr($ciphertext, $i, 8) ^ $key; $plaintext.= substr($ciphertext, $i, 8) ^ $key;
} }