--- a/wp/wp-includes/sodium_compat/src/Crypto32.php Tue Oct 22 16:11:46 2019 +0200
+++ b/wp/wp-includes/sodium_compat/src/Crypto32.php Tue Dec 15 13:49:49 2020 +0100
@@ -777,6 +777,53 @@
}
/**
+ * Initialize a hashing context for BLAKE2b.
+ *
+ * @internal Do not use this directly. Use ParagonIE_Sodium_Compat.
+ *
+ * @param string $key
+ * @param int $outputLength
+ * @param string $salt
+ * @param string $personal
+ * @return string
+ * @throws RangeException
+ * @throws SodiumException
+ * @throws TypeError
+ */
+ public static function generichash_init_salt_personal(
+ $key = '',
+ $outputLength = 32,
+ $salt = '',
+ $personal = ''
+ ) {
+ // This ensures that ParagonIE_Sodium_Core32_BLAKE2b::$iv is initialized
+ ParagonIE_Sodium_Core32_BLAKE2b::pseudoConstructor();
+
+ $k = null;
+ if (!empty($key)) {
+ $k = ParagonIE_Sodium_Core32_BLAKE2b::stringToSplFixedArray($key);
+ if ($k->count() > ParagonIE_Sodium_Core32_BLAKE2b::KEYBYTES) {
+ throw new RangeException('Invalid key size');
+ }
+ }
+ if (!empty($salt)) {
+ $s = ParagonIE_Sodium_Core32_BLAKE2b::stringToSplFixedArray($salt);
+ } else {
+ $s = null;
+ }
+ if (!empty($salt)) {
+ $p = ParagonIE_Sodium_Core32_BLAKE2b::stringToSplFixedArray($personal);
+ } else {
+ $p = null;
+ }
+
+ /** @var SplFixedArray $ctx */
+ $ctx = ParagonIE_Sodium_Core32_BLAKE2b::init($k, $outputLength, $s, $p);
+
+ return ParagonIE_Sodium_Core32_BLAKE2b::contextToString($ctx);
+ }
+
+ /**
* Update a hashing context for BLAKE2b with $message
*
* @internal Do not use this directly. Use ParagonIE_Sodium_Compat.
@@ -1185,6 +1232,362 @@
}
/**
+ * @param string $key
+ * @return array<int, string> Returns a state and a header.
+ * @throws Exception
+ * @throws SodiumException
+ */
+ public static function secretstream_xchacha20poly1305_init_push($key)
+ {
+ # randombytes_buf(out, crypto_secretstream_xchacha20poly1305_HEADERBYTES);
+ $out = random_bytes(24);
+
+ # crypto_core_hchacha20(state->k, out, k, NULL);
+ $subkey = ParagonIE_Sodium_Core32_HChaCha20::hChaCha20($out, $key);
+ $state = new ParagonIE_Sodium_Core32_SecretStream_State(
+ $subkey,
+ ParagonIE_Sodium_Core32_Util::substr($out, 16, 8) . str_repeat("\0", 4)
+ );
+
+ # _crypto_secretstream_xchacha20poly1305_counter_reset(state);
+ $state->counterReset();
+
+ # memcpy(STATE_INONCE(state), out + crypto_core_hchacha20_INPUTBYTES,
+ # crypto_secretstream_xchacha20poly1305_INONCEBYTES);
+ # memset(state->_pad, 0, sizeof state->_pad);
+ return array(
+ $state->toString(),
+ $out
+ );
+ }
+
+ /**
+ * @param string $key
+ * @param string $header
+ * @return string Returns a state.
+ * @throws Exception
+ */
+ public static function secretstream_xchacha20poly1305_init_pull($key, $header)
+ {
+ # crypto_core_hchacha20(state->k, in, k, NULL);
+ $subkey = ParagonIE_Sodium_Core32_HChaCha20::hChaCha20(
+ ParagonIE_Sodium_Core32_Util::substr($header, 0, 16),
+ $key
+ );
+ $state = new ParagonIE_Sodium_Core32_SecretStream_State(
+ $subkey,
+ ParagonIE_Sodium_Core32_Util::substr($header, 16)
+ );
+ $state->counterReset();
+ # memcpy(STATE_INONCE(state), in + crypto_core_hchacha20_INPUTBYTES,
+ # crypto_secretstream_xchacha20poly1305_INONCEBYTES);
+ # memset(state->_pad, 0, sizeof state->_pad);
+ # return 0;
+ return $state->toString();
+ }
+
+ /**
+ * @param string $state
+ * @param string $msg
+ * @param string $aad
+ * @param int $tag
+ * @return string
+ * @throws SodiumException
+ */
+ public static function secretstream_xchacha20poly1305_push(&$state, $msg, $aad = '', $tag = 0)
+ {
+ $st = ParagonIE_Sodium_Core32_SecretStream_State::fromString($state);
+ # crypto_onetimeauth_poly1305_state poly1305_state;
+ # unsigned char block[64U];
+ # unsigned char slen[8U];
+ # unsigned char *c;
+ # unsigned char *mac;
+
+ $msglen = ParagonIE_Sodium_Core32_Util::strlen($msg);
+ $aadlen = ParagonIE_Sodium_Core32_Util::strlen($aad);
+
+ if ((($msglen + 63) >> 6) > 0xfffffffe) {
+ throw new SodiumException(
+ 'message cannot be larger than SODIUM_CRYPTO_SECRETSTREAM_XCHACHA20POLY1305_MESSAGEBYTES_MAX bytes'
+ );
+ }
+
+ # if (outlen_p != NULL) {
+ # *outlen_p = 0U;
+ # }
+ # if (mlen > crypto_secretstream_xchacha20poly1305_MESSAGEBYTES_MAX) {
+ # sodium_misuse();
+ # }
+
+ # crypto_stream_chacha20_ietf(block, sizeof block, state->nonce, state->k);
+ # crypto_onetimeauth_poly1305_init(&poly1305_state, block);
+ # sodium_memzero(block, sizeof block);
+ $auth = new ParagonIE_Sodium_Core32_Poly1305_State(
+ ParagonIE_Sodium_Core32_ChaCha20::ietfStream(32, $st->getCombinedNonce(), $st->getKey())
+ );
+
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, ad, adlen);
+ $auth->update($aad);
+
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, _pad0,
+ # (0x10 - adlen) & 0xf);
+ $auth->update(str_repeat("\0", ((0x10 - $aadlen) & 0xf)));
+
+ # memset(block, 0, sizeof block);
+ # block[0] = tag;
+ # crypto_stream_chacha20_ietf_xor_ic(block, block, sizeof block,
+ # state->nonce, 1U, state->k);
+ $block = ParagonIE_Sodium_Core32_ChaCha20::ietfStreamXorIc(
+ ParagonIE_Sodium_Core32_Util::intToChr($tag) . str_repeat("\0", 63),
+ $st->getCombinedNonce(),
+ $st->getKey(),
+ ParagonIE_Sodium_Core32_Util::store64_le(1)
+ );
+
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, block, sizeof block);
+ $auth->update($block);
+
+ # out[0] = block[0];
+ $out = $block[0];
+ # c = out + (sizeof tag);
+ # crypto_stream_chacha20_ietf_xor_ic(c, m, mlen, state->nonce, 2U, state->k);
+ $cipher = ParagonIE_Sodium_Core32_ChaCha20::ietfStreamXorIc(
+ $msg,
+ $st->getCombinedNonce(),
+ $st->getKey(),
+ ParagonIE_Sodium_Core32_Util::store64_le(2)
+ );
+
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, c, mlen);
+ $auth->update($cipher);
+
+ $out .= $cipher;
+ unset($cipher);
+
+ # crypto_onetimeauth_poly1305_update
+ # (&poly1305_state, _pad0, (0x10 - (sizeof block) + mlen) & 0xf);
+ $auth->update(str_repeat("\0", ((0x10 - 64 + $msglen) & 0xf)));
+
+ # STORE64_LE(slen, (uint64_t) adlen);
+ $slen = ParagonIE_Sodium_Core32_Util::store64_le($aadlen);
+
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, slen, sizeof slen);
+ $auth->update($slen);
+
+ # STORE64_LE(slen, (sizeof block) + mlen);
+ $slen = ParagonIE_Sodium_Core32_Util::store64_le(64 + $msglen);
+
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, slen, sizeof slen);
+ $auth->update($slen);
+
+ # mac = c + mlen;
+ # crypto_onetimeauth_poly1305_final(&poly1305_state, mac);
+ $mac = $auth->finish();
+ $out .= $mac;
+
+ # sodium_memzero(&poly1305_state, sizeof poly1305_state);
+ unset($auth);
+
+
+ # XOR_BUF(STATE_INONCE(state), mac,
+ # crypto_secretstream_xchacha20poly1305_INONCEBYTES);
+ $st->xorNonce($mac);
+
+ # sodium_increment(STATE_COUNTER(state),
+ # crypto_secretstream_xchacha20poly1305_COUNTERBYTES);
+ $st->incrementCounter();
+ // Overwrite by reference:
+ $state = $st->toString();
+
+ /** @var bool $rekey */
+ $rekey = ($tag & ParagonIE_Sodium_Compat::CRYPTO_SECRETSTREAM_XCHACHA20POLY1305_TAG_REKEY) !== 0;
+ # if ((tag & crypto_secretstream_xchacha20poly1305_TAG_REKEY) != 0 ||
+ # sodium_is_zero(STATE_COUNTER(state),
+ # crypto_secretstream_xchacha20poly1305_COUNTERBYTES)) {
+ # crypto_secretstream_xchacha20poly1305_rekey(state);
+ # }
+ if ($rekey || $st->needsRekey()) {
+ // DO REKEY
+ self::secretstream_xchacha20poly1305_rekey($state);
+ }
+ # if (outlen_p != NULL) {
+ # *outlen_p = crypto_secretstream_xchacha20poly1305_ABYTES + mlen;
+ # }
+ return $out;
+ }
+
+ /**
+ * @param string $state
+ * @param string $cipher
+ * @param string $aad
+ * @return bool|array{0: string, 1: int}
+ * @throws SodiumException
+ */
+ public static function secretstream_xchacha20poly1305_pull(&$state, $cipher, $aad = '')
+ {
+ $st = ParagonIE_Sodium_Core32_SecretStream_State::fromString($state);
+
+ $cipherlen = ParagonIE_Sodium_Core32_Util::strlen($cipher);
+ # mlen = inlen - crypto_secretstream_xchacha20poly1305_ABYTES;
+ $msglen = $cipherlen - ParagonIE_Sodium_Compat::CRYPTO_SECRETSTREAM_XCHACHA20POLY1305_ABYTES;
+ $aadlen = ParagonIE_Sodium_Core32_Util::strlen($aad);
+
+ # if (mlen > crypto_secretstream_xchacha20poly1305_MESSAGEBYTES_MAX) {
+ # sodium_misuse();
+ # }
+ if ((($msglen + 63) >> 6) > 0xfffffffe) {
+ throw new SodiumException(
+ 'message cannot be larger than SODIUM_CRYPTO_SECRETSTREAM_XCHACHA20POLY1305_MESSAGEBYTES_MAX bytes'
+ );
+ }
+
+ # crypto_stream_chacha20_ietf(block, sizeof block, state->nonce, state->k);
+ # crypto_onetimeauth_poly1305_init(&poly1305_state, block);
+ # sodium_memzero(block, sizeof block);
+ $auth = new ParagonIE_Sodium_Core32_Poly1305_State(
+ ParagonIE_Sodium_Core32_ChaCha20::ietfStream(32, $st->getCombinedNonce(), $st->getKey())
+ );
+
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, ad, adlen);
+ $auth->update($aad);
+
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, _pad0,
+ # (0x10 - adlen) & 0xf);
+ $auth->update(str_repeat("\0", ((0x10 - $aadlen) & 0xf)));
+
+
+ # memset(block, 0, sizeof block);
+ # block[0] = in[0];
+ # crypto_stream_chacha20_ietf_xor_ic(block, block, sizeof block,
+ # state->nonce, 1U, state->k);
+ $block = ParagonIE_Sodium_Core32_ChaCha20::ietfStreamXorIc(
+ $cipher[0] . str_repeat("\0", 63),
+ $st->getCombinedNonce(),
+ $st->getKey(),
+ ParagonIE_Sodium_Core32_Util::store64_le(1)
+ );
+ # tag = block[0];
+ # block[0] = in[0];
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, block, sizeof block);
+ $tag = ParagonIE_Sodium_Core32_Util::chrToInt($block[0]);
+ $block[0] = $cipher[0];
+ $auth->update($block);
+
+
+ # c = in + (sizeof tag);
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, c, mlen);
+ $auth->update(ParagonIE_Sodium_Core32_Util::substr($cipher, 1, $msglen));
+
+ # crypto_onetimeauth_poly1305_update
+ # (&poly1305_state, _pad0, (0x10 - (sizeof block) + mlen) & 0xf);
+ $auth->update(str_repeat("\0", ((0x10 - 64 + $msglen) & 0xf)));
+
+ # STORE64_LE(slen, (uint64_t) adlen);
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, slen, sizeof slen);
+ $slen = ParagonIE_Sodium_Core32_Util::store64_le($aadlen);
+ $auth->update($slen);
+
+ # STORE64_LE(slen, (sizeof block) + mlen);
+ # crypto_onetimeauth_poly1305_update(&poly1305_state, slen, sizeof slen);
+ $slen = ParagonIE_Sodium_Core32_Util::store64_le(64 + $msglen);
+ $auth->update($slen);
+
+ # crypto_onetimeauth_poly1305_final(&poly1305_state, mac);
+ # sodium_memzero(&poly1305_state, sizeof poly1305_state);
+ $mac = $auth->finish();
+
+ # stored_mac = c + mlen;
+ # if (sodium_memcmp(mac, stored_mac, sizeof mac) != 0) {
+ # sodium_memzero(mac, sizeof mac);
+ # return -1;
+ # }
+
+ $stored = ParagonIE_Sodium_Core32_Util::substr($cipher, $msglen + 1, 16);
+ if (!ParagonIE_Sodium_Core32_Util::hashEquals($mac, $stored)) {
+ return false;
+ }
+
+ # crypto_stream_chacha20_ietf_xor_ic(m, c, mlen, state->nonce, 2U, state->k);
+ $out = ParagonIE_Sodium_Core32_ChaCha20::ietfStreamXorIc(
+ ParagonIE_Sodium_Core32_Util::substr($cipher, 1, $msglen),
+ $st->getCombinedNonce(),
+ $st->getKey(),
+ ParagonIE_Sodium_Core32_Util::store64_le(2)
+ );
+
+ # XOR_BUF(STATE_INONCE(state), mac,
+ # crypto_secretstream_xchacha20poly1305_INONCEBYTES);
+ $st->xorNonce($mac);
+
+ # sodium_increment(STATE_COUNTER(state),
+ # crypto_secretstream_xchacha20poly1305_COUNTERBYTES);
+ $st->incrementCounter();
+
+ # if ((tag & crypto_secretstream_xchacha20poly1305_TAG_REKEY) != 0 ||
+ # sodium_is_zero(STATE_COUNTER(state),
+ # crypto_secretstream_xchacha20poly1305_COUNTERBYTES)) {
+ # crypto_secretstream_xchacha20poly1305_rekey(state);
+ # }
+
+ // Overwrite by reference:
+ $state = $st->toString();
+
+ /** @var bool $rekey */
+ $rekey = ($tag & ParagonIE_Sodium_Compat::CRYPTO_SECRETSTREAM_XCHACHA20POLY1305_TAG_REKEY) !== 0;
+ if ($rekey || $st->needsRekey()) {
+ // DO REKEY
+ self::secretstream_xchacha20poly1305_rekey($state);
+ }
+ return array($out, $tag);
+ }
+
+ /**
+ * @param string $state
+ * @return void
+ * @throws SodiumException
+ */
+ public static function secretstream_xchacha20poly1305_rekey(&$state)
+ {
+ $st = ParagonIE_Sodium_Core32_SecretStream_State::fromString($state);
+ # unsigned char new_key_and_inonce[crypto_stream_chacha20_ietf_KEYBYTES +
+ # crypto_secretstream_xchacha20poly1305_INONCEBYTES];
+ # size_t i;
+ # for (i = 0U; i < crypto_stream_chacha20_ietf_KEYBYTES; i++) {
+ # new_key_and_inonce[i] = state->k[i];
+ # }
+ $new_key_and_inonce = $st->getKey();
+
+ # for (i = 0U; i < crypto_secretstream_xchacha20poly1305_INONCEBYTES; i++) {
+ # new_key_and_inonce[crypto_stream_chacha20_ietf_KEYBYTES + i] =
+ # STATE_INONCE(state)[i];
+ # }
+ $new_key_and_inonce .= ParagonIE_Sodium_Core32_Util::substR($st->getNonce(), 0, 8);
+
+ # crypto_stream_chacha20_ietf_xor(new_key_and_inonce, new_key_and_inonce,
+ # sizeof new_key_and_inonce,
+ # state->nonce, state->k);
+
+ $st->rekey(ParagonIE_Sodium_Core32_ChaCha20::ietfStreamXorIc(
+ $new_key_and_inonce,
+ $st->getCombinedNonce(),
+ $st->getKey(),
+ ParagonIE_Sodium_Core32_Util::store64_le(0)
+ ));
+
+ # for (i = 0U; i < crypto_stream_chacha20_ietf_KEYBYTES; i++) {
+ # state->k[i] = new_key_and_inonce[i];
+ # }
+ # for (i = 0U; i < crypto_secretstream_xchacha20poly1305_INONCEBYTES; i++) {
+ # STATE_INONCE(state)[i] =
+ # new_key_and_inonce[crypto_stream_chacha20_ietf_KEYBYTES + i];
+ # }
+ # _crypto_secretstream_xchacha20poly1305_counter_reset(state);
+ $st->counterReset();
+
+ $state = $st->toString();
+ }
+
+ /**
* Detached Ed25519 signature.
*
* @internal Do not use this directly. Use ParagonIE_Sodium_Compat.