[ Index ]

PHP Cross Reference of WordPress

title

Body

[close]

/wp-includes/sodium_compat/src/Core32/Poly1305/ -> State.php (source)

   1  <?php
   2  
   3  if (class_exists('ParagonIE_Sodium_Core32_Poly1305_State', false)) {
   4      return;
   5  }
   6  
   7  /**
   8   * Class ParagonIE_Sodium_Core32_Poly1305_State
   9   */
  10  class ParagonIE_Sodium_Core32_Poly1305_State extends ParagonIE_Sodium_Core32_Util
  11  {
  12      /**
  13       * @var array<int, int>
  14       */
  15      protected $buffer = array();
  16  
  17      /**
  18       * @var bool
  19       */
  20      protected $final = false;
  21  
  22      /**
  23       * @var array<int, ParagonIE_Sodium_Core32_Int32>
  24       */
  25      public $h;
  26  
  27      /**
  28       * @var int
  29       */
  30      protected $leftover = 0;
  31  
  32      /**
  33       * @var array<int, ParagonIE_Sodium_Core32_Int32>
  34       */
  35      public $r;
  36  
  37      /**
  38       * @var array<int, ParagonIE_Sodium_Core32_Int64>
  39       */
  40      public $pad;
  41  
  42      /**
  43       * ParagonIE_Sodium_Core32_Poly1305_State constructor.
  44       *
  45       * @internal You should not use this directly from another application
  46       *
  47       * @param string $key
  48       * @throws InvalidArgumentException
  49       * @throws SodiumException
  50       * @throws TypeError
  51       */
  52      public function __construct($key = '')
  53      {
  54          if (self::strlen($key) < 32) {
  55              throw new InvalidArgumentException(
  56                  'Poly1305 requires a 32-byte key'
  57              );
  58          }
  59          /* r &= 0xffffffc0ffffffc0ffffffc0fffffff */
  60          $this->r = array(
  61              // st->r[0] = ...
  62              ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($key, 0, 4))
  63                  ->setUnsignedInt(true)
  64                  ->mask(0x3ffffff),
  65              // st->r[1] = ...
  66              ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($key, 3, 4))
  67                  ->setUnsignedInt(true)
  68                  ->shiftRight(2)
  69                  ->mask(0x3ffff03),
  70              // st->r[2] = ...
  71              ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($key, 6, 4))
  72                  ->setUnsignedInt(true)
  73                  ->shiftRight(4)
  74                  ->mask(0x3ffc0ff),
  75              // st->r[3] = ...
  76              ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($key, 9, 4))
  77                  ->setUnsignedInt(true)
  78                  ->shiftRight(6)
  79                  ->mask(0x3f03fff),
  80              // st->r[4] = ...
  81              ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($key, 12, 4))
  82                  ->setUnsignedInt(true)
  83                  ->shiftRight(8)
  84                  ->mask(0x00fffff)
  85          );
  86  
  87          /* h = 0 */
  88          $this->h = array(
  89              new ParagonIE_Sodium_Core32_Int32(array(0, 0), true),
  90              new ParagonIE_Sodium_Core32_Int32(array(0, 0), true),
  91              new ParagonIE_Sodium_Core32_Int32(array(0, 0), true),
  92              new ParagonIE_Sodium_Core32_Int32(array(0, 0), true),
  93              new ParagonIE_Sodium_Core32_Int32(array(0, 0), true)
  94          );
  95  
  96          /* save pad for later */
  97          $this->pad = array(
  98              ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($key, 16, 4))
  99                  ->setUnsignedInt(true)->toInt64(),
 100              ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($key, 20, 4))
 101                  ->setUnsignedInt(true)->toInt64(),
 102              ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($key, 24, 4))
 103                  ->setUnsignedInt(true)->toInt64(),
 104              ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($key, 28, 4))
 105                  ->setUnsignedInt(true)->toInt64(),
 106          );
 107  
 108          $this->leftover = 0;
 109          $this->final = false;
 110      }
 111  
 112      /**
 113       * @internal You should not use this directly from another application
 114       *
 115       * @param string $message
 116       * @return self
 117       * @throws SodiumException
 118       * @throws TypeError
 119       */
 120      public function update($message = '')
 121      {
 122          $bytes = self::strlen($message);
 123  
 124          /* handle leftover */
 125          if ($this->leftover) {
 126              /** @var int $want */
 127              $want = ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE - $this->leftover;
 128              if ($want > $bytes) {
 129                  $want = $bytes;
 130              }
 131              for ($i = 0; $i < $want; ++$i) {
 132                  $mi = self::chrToInt($message[$i]);
 133                  $this->buffer[$this->leftover + $i] = $mi;
 134              }
 135              // We snip off the leftmost bytes.
 136              $message = self::substr($message, $want);
 137              $bytes = self::strlen($message);
 138              $this->leftover += $want;
 139              if ($this->leftover < ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE) {
 140                  // We still don't have enough to run $this->blocks()
 141                  return $this;
 142              }
 143  
 144              $this->blocks(
 145                  self::intArrayToString($this->buffer),
 146                  ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE
 147              );
 148              $this->leftover = 0;
 149          }
 150  
 151          /* process full blocks */
 152          if ($bytes >= ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE) {
 153              /** @var int $want */
 154              $want = $bytes & ~(ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE - 1);
 155              if ($want >= ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE) {
 156                  /** @var string $block */
 157                  $block = self::substr($message, 0, $want);
 158                  if (self::strlen($block) >= ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE) {
 159                      $this->blocks($block, $want);
 160                      $message = self::substr($message, $want);
 161                      $bytes = self::strlen($message);
 162                  }
 163              }
 164          }
 165  
 166          /* store leftover */
 167          if ($bytes) {
 168              for ($i = 0; $i < $bytes; ++$i) {
 169                  $mi = self::chrToInt($message[$i]);
 170                  $this->buffer[$this->leftover + $i] = $mi;
 171              }
 172              $this->leftover = (int) $this->leftover + $bytes;
 173          }
 174          return $this;
 175      }
 176  
 177      /**
 178       * @internal You should not use this directly from another application
 179       *
 180       * @param string $message
 181       * @param int $bytes
 182       * @return self
 183       * @throws SodiumException
 184       * @throws TypeError
 185       */
 186      public function blocks($message, $bytes)
 187      {
 188          if (self::strlen($message) < 16) {
 189              $message = str_pad($message, 16, "\x00", STR_PAD_RIGHT);
 190          }
 191          $hibit = ParagonIE_Sodium_Core32_Int32::fromInt((int) ($this->final ? 0 : 1 << 24)); /* 1 << 128 */
 192          $hibit->setUnsignedInt(true);
 193          $zero = new ParagonIE_Sodium_Core32_Int64(array(0, 0, 0, 0), true);
 194          /**
 195           * @var ParagonIE_Sodium_Core32_Int64 $d0
 196           * @var ParagonIE_Sodium_Core32_Int64 $d1
 197           * @var ParagonIE_Sodium_Core32_Int64 $d2
 198           * @var ParagonIE_Sodium_Core32_Int64 $d3
 199           * @var ParagonIE_Sodium_Core32_Int64 $d4
 200           * @var ParagonIE_Sodium_Core32_Int64 $r0
 201           * @var ParagonIE_Sodium_Core32_Int64 $r1
 202           * @var ParagonIE_Sodium_Core32_Int64 $r2
 203           * @var ParagonIE_Sodium_Core32_Int64 $r3
 204           * @var ParagonIE_Sodium_Core32_Int64 $r4
 205           *
 206           * @var ParagonIE_Sodium_Core32_Int32 $h0
 207           * @var ParagonIE_Sodium_Core32_Int32 $h1
 208           * @var ParagonIE_Sodium_Core32_Int32 $h2
 209           * @var ParagonIE_Sodium_Core32_Int32 $h3
 210           * @var ParagonIE_Sodium_Core32_Int32 $h4
 211           */
 212          $r0 = $this->r[0]->toInt64();
 213          $r1 = $this->r[1]->toInt64();
 214          $r2 = $this->r[2]->toInt64();
 215          $r3 = $this->r[3]->toInt64();
 216          $r4 = $this->r[4]->toInt64();
 217  
 218          $s1 = $r1->toInt64()->mulInt(5, 3);
 219          $s2 = $r2->toInt64()->mulInt(5, 3);
 220          $s3 = $r3->toInt64()->mulInt(5, 3);
 221          $s4 = $r4->toInt64()->mulInt(5, 3);
 222  
 223          $h0 = $this->h[0];
 224          $h1 = $this->h[1];
 225          $h2 = $this->h[2];
 226          $h3 = $this->h[3];
 227          $h4 = $this->h[4];
 228  
 229          while ($bytes >= ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE) {
 230              /* h += m[i] */
 231              $h0 = $h0->addInt32(
 232                  ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($message, 0, 4))
 233                      ->mask(0x3ffffff)
 234              )->toInt64();
 235              $h1 = $h1->addInt32(
 236                  ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($message, 3, 4))
 237                      ->shiftRight(2)
 238                      ->mask(0x3ffffff)
 239              )->toInt64();
 240              $h2 = $h2->addInt32(
 241                  ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($message, 6, 4))
 242                      ->shiftRight(4)
 243                      ->mask(0x3ffffff)
 244              )->toInt64();
 245              $h3 = $h3->addInt32(
 246                  ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($message, 9, 4))
 247                      ->shiftRight(6)
 248                      ->mask(0x3ffffff)
 249              )->toInt64();
 250              $h4 = $h4->addInt32(
 251                  ParagonIE_Sodium_Core32_Int32::fromReverseString(self::substr($message, 12, 4))
 252                      ->shiftRight(8)
 253                      ->orInt32($hibit)
 254              )->toInt64();
 255  
 256              /* h *= r */
 257              $d0 = $zero
 258                  ->addInt64($h0->mulInt64($r0, 25))
 259                  ->addInt64($s4->mulInt64($h1, 26))
 260                  ->addInt64($s3->mulInt64($h2, 26))
 261                  ->addInt64($s2->mulInt64($h3, 26))
 262                  ->addInt64($s1->mulInt64($h4, 26));
 263  
 264              $d1 = $zero
 265                  ->addInt64($h0->mulInt64($r1, 25))
 266                  ->addInt64($h1->mulInt64($r0, 25))
 267                  ->addInt64($s4->mulInt64($h2, 26))
 268                  ->addInt64($s3->mulInt64($h3, 26))
 269                  ->addInt64($s2->mulInt64($h4, 26));
 270  
 271              $d2 = $zero
 272                  ->addInt64($h0->mulInt64($r2, 25))
 273                  ->addInt64($h1->mulInt64($r1, 25))
 274                  ->addInt64($h2->mulInt64($r0, 25))
 275                  ->addInt64($s4->mulInt64($h3, 26))
 276                  ->addInt64($s3->mulInt64($h4, 26));
 277  
 278              $d3 = $zero
 279                  ->addInt64($h0->mulInt64($r3, 25))
 280                  ->addInt64($h1->mulInt64($r2, 25))
 281                  ->addInt64($h2->mulInt64($r1, 25))
 282                  ->addInt64($h3->mulInt64($r0, 25))
 283                  ->addInt64($s4->mulInt64($h4, 26));
 284  
 285              $d4 = $zero
 286                  ->addInt64($h0->mulInt64($r4, 25))
 287                  ->addInt64($h1->mulInt64($r3, 25))
 288                  ->addInt64($h2->mulInt64($r2, 25))
 289                  ->addInt64($h3->mulInt64($r1, 25))
 290                  ->addInt64($h4->mulInt64($r0, 25));
 291  
 292              /* (partial) h %= p */
 293              $c = $d0->shiftRight(26);
 294              $h0 = $d0->toInt32()->mask(0x3ffffff);
 295              $d1 = $d1->addInt64($c);
 296  
 297              $c = $d1->shiftRight(26);
 298              $h1 = $d1->toInt32()->mask(0x3ffffff);
 299              $d2 = $d2->addInt64($c);
 300  
 301              $c = $d2->shiftRight(26);
 302              $h2 = $d2->toInt32()->mask(0x3ffffff);
 303              $d3 = $d3->addInt64($c);
 304  
 305              $c = $d3->shiftRight(26);
 306              $h3 = $d3->toInt32()->mask(0x3ffffff);
 307              $d4 = $d4->addInt64($c);
 308  
 309              $c = $d4->shiftRight(26);
 310              $h4 = $d4->toInt32()->mask(0x3ffffff);
 311              $h0 = $h0->addInt32($c->toInt32()->mulInt(5, 3));
 312  
 313              $c = $h0->shiftRight(26);
 314              $h0 = $h0->mask(0x3ffffff);
 315              $h1 = $h1->addInt32($c);
 316  
 317              // Chop off the left 32 bytes.
 318              $message = self::substr(
 319                  $message,
 320                  ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE
 321              );
 322              $bytes -= ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE;
 323          }
 324  
 325          /** @var array<int, ParagonIE_Sodium_Core32_Int32> $h */
 326          $this->h = array($h0, $h1, $h2, $h3, $h4);
 327          return $this;
 328      }
 329  
 330      /**
 331       * @internal You should not use this directly from another application
 332       *
 333       * @return string
 334       * @throws SodiumException
 335       * @throws TypeError
 336       */
 337      public function finish()
 338      {
 339          /* process the remaining block */
 340          if ($this->leftover) {
 341              $i = $this->leftover;
 342              $this->buffer[$i++] = 1;
 343              for (; $i < ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE; ++$i) {
 344                  $this->buffer[$i] = 0;
 345              }
 346              $this->final = true;
 347              $this->blocks(
 348                  self::substr(
 349                      self::intArrayToString($this->buffer),
 350                      0,
 351                      ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE
 352                  ),
 353                  $b = ParagonIE_Sodium_Core32_Poly1305::BLOCK_SIZE
 354              );
 355          }
 356  
 357          /**
 358           * @var ParagonIE_Sodium_Core32_Int32 $f
 359           * @var ParagonIE_Sodium_Core32_Int32 $g0
 360           * @var ParagonIE_Sodium_Core32_Int32 $g1
 361           * @var ParagonIE_Sodium_Core32_Int32 $g2
 362           * @var ParagonIE_Sodium_Core32_Int32 $g3
 363           * @var ParagonIE_Sodium_Core32_Int32 $g4
 364           * @var ParagonIE_Sodium_Core32_Int32 $h0
 365           * @var ParagonIE_Sodium_Core32_Int32 $h1
 366           * @var ParagonIE_Sodium_Core32_Int32 $h2
 367           * @var ParagonIE_Sodium_Core32_Int32 $h3
 368           * @var ParagonIE_Sodium_Core32_Int32 $h4
 369           */
 370          $h0 = $this->h[0];
 371          $h1 = $this->h[1];
 372          $h2 = $this->h[2];
 373          $h3 = $this->h[3];
 374          $h4 = $this->h[4];
 375  
 376          $c = $h1->shiftRight(26);           # $c = $h1 >> 26;
 377          $h1 = $h1->mask(0x3ffffff);         # $h1 &= 0x3ffffff;
 378  
 379          $h2 = $h2->addInt32($c);            # $h2 += $c;
 380          $c = $h2->shiftRight(26);           # $c = $h2 >> 26;
 381          $h2 = $h2->mask(0x3ffffff);         # $h2 &= 0x3ffffff;
 382  
 383          $h3 = $h3->addInt32($c);            # $h3 += $c;
 384          $c = $h3->shiftRight(26);           # $c = $h3 >> 26;
 385          $h3 = $h3->mask(0x3ffffff);         # $h3 &= 0x3ffffff;
 386  
 387          $h4 = $h4->addInt32($c);            # $h4 += $c;
 388          $c = $h4->shiftRight(26);           # $c = $h4 >> 26;
 389          $h4 = $h4->mask(0x3ffffff);         # $h4 &= 0x3ffffff;
 390  
 391          $h0 = $h0->addInt32($c->mulInt(5, 3)); # $h0 += self::mul($c, 5);
 392          $c = $h0->shiftRight(26);           # $c = $h0 >> 26;
 393          $h0 = $h0->mask(0x3ffffff);         # $h0 &= 0x3ffffff;
 394          $h1 = $h1->addInt32($c);            # $h1 += $c;
 395  
 396          /* compute h + -p */
 397          $g0 = $h0->addInt(5);
 398          $c  = $g0->shiftRight(26);
 399          $g0 = $g0->mask(0x3ffffff);
 400          $g1 = $h1->addInt32($c);
 401          $c  = $g1->shiftRight(26);
 402          $g1 = $g1->mask(0x3ffffff);
 403          $g2 = $h2->addInt32($c);
 404          $c  = $g2->shiftRight(26);
 405          $g2 = $g2->mask(0x3ffffff);
 406          $g3 = $h3->addInt32($c);
 407          $c  = $g3->shiftRight(26);
 408          $g3 = $g3->mask(0x3ffffff);
 409          $g4 = $h4->addInt32($c)->subInt(1 << 26);
 410  
 411          # $mask = ($g4 >> 31) - 1;
 412          /* select h if h < p, or h + -p if h >= p */
 413          $mask = (int) (($g4->toInt() >> 31) + 1);
 414  
 415          $g0 = $g0->mask($mask);
 416          $g1 = $g1->mask($mask);
 417          $g2 = $g2->mask($mask);
 418          $g3 = $g3->mask($mask);
 419          $g4 = $g4->mask($mask);
 420  
 421          /** @var int $mask */
 422          $mask = ~$mask;
 423  
 424          $h0 = $h0->mask($mask)->orInt32($g0);
 425          $h1 = $h1->mask($mask)->orInt32($g1);
 426          $h2 = $h2->mask($mask)->orInt32($g2);
 427          $h3 = $h3->mask($mask)->orInt32($g3);
 428          $h4 = $h4->mask($mask)->orInt32($g4);
 429  
 430          /* h = h % (2^128) */
 431          $h0 = $h0->orInt32($h1->shiftLeft(26));
 432          $h1 = $h1->shiftRight(6)->orInt32($h2->shiftLeft(20));
 433          $h2 = $h2->shiftRight(12)->orInt32($h3->shiftLeft(14));
 434          $h3 = $h3->shiftRight(18)->orInt32($h4->shiftLeft(8));
 435  
 436          /* mac = (h + pad) % (2^128) */
 437          $f = $h0->toInt64()->addInt64($this->pad[0]);
 438          $h0 = $f->toInt32();
 439          $f = $h1->toInt64()->addInt64($this->pad[1])->addInt($h0->overflow);
 440          $h1 = $f->toInt32();
 441          $f = $h2->toInt64()->addInt64($this->pad[2])->addInt($h1->overflow);
 442          $h2 = $f->toInt32();
 443          $f = $h3->toInt64()->addInt64($this->pad[3])->addInt($h2->overflow);
 444          $h3 = $f->toInt32();
 445  
 446          return $h0->toReverseString() .
 447              $h1->toReverseString() .
 448              $h2->toReverseString() .
 449              $h3->toReverseString();
 450      }
 451  }


Generated: Thu Apr 25 01:00:03 2024 Cross-referenced by PHPXref 0.7.1