[ Index ] |
PHP Cross Reference of WordPress |
[Summary view] [Print] [Text view]
1 <?php 2 3 /** 4 * Class ParagonIE_Sodium_Core32_Int32 5 * 6 * Encapsulates a 32-bit integer. 7 * 8 * These are immutable. It always returns a new instance. 9 */ 10 class ParagonIE_Sodium_Core32_Int32 11 { 12 /** 13 * @var array<int, int> - two 16-bit integers 14 * 15 * 0 is the higher 16 bits 16 * 1 is the lower 16 bits 17 */ 18 public $limbs = array(0, 0); 19 20 /** 21 * @var int 22 */ 23 public $overflow = 0; 24 25 /** 26 * @var bool 27 */ 28 public $unsignedInt = false; 29 30 /** 31 * ParagonIE_Sodium_Core32_Int32 constructor. 32 * @param array $array 33 * @param bool $unsignedInt 34 */ 35 public function __construct($array = array(0, 0), $unsignedInt = false) 36 { 37 $this->limbs = array( 38 (int) $array[0], 39 (int) $array[1] 40 ); 41 $this->overflow = 0; 42 $this->unsignedInt = $unsignedInt; 43 } 44 45 /** 46 * Adds two int32 objects 47 * 48 * @param ParagonIE_Sodium_Core32_Int32 $addend 49 * @return ParagonIE_Sodium_Core32_Int32 50 */ 51 public function addInt32(ParagonIE_Sodium_Core32_Int32 $addend) 52 { 53 $i0 = $this->limbs[0]; 54 $i1 = $this->limbs[1]; 55 $j0 = $addend->limbs[0]; 56 $j1 = $addend->limbs[1]; 57 58 $r1 = $i1 + ($j1 & 0xffff); 59 $carry = $r1 >> 16; 60 61 $r0 = $i0 + ($j0 & 0xffff) + $carry; 62 $carry = $r0 >> 16; 63 64 $r0 &= 0xffff; 65 $r1 &= 0xffff; 66 67 $return = new ParagonIE_Sodium_Core32_Int32( 68 array($r0, $r1) 69 ); 70 $return->overflow = $carry; 71 $return->unsignedInt = $this->unsignedInt; 72 return $return; 73 } 74 75 /** 76 * Adds a normal integer to an int32 object 77 * 78 * @param int $int 79 * @return ParagonIE_Sodium_Core32_Int32 80 * @throws SodiumException 81 * @throws TypeError 82 */ 83 public function addInt($int) 84 { 85 ParagonIE_Sodium_Core32_Util::declareScalarType($int, 'int', 1); 86 /** @var int $int */ 87 $int = (int) $int; 88 89 $int = (int) $int; 90 91 $i0 = $this->limbs[0]; 92 $i1 = $this->limbs[1]; 93 94 $r1 = $i1 + ($int & 0xffff); 95 $carry = $r1 >> 16; 96 97 $r0 = $i0 + (($int >> 16) & 0xffff) + $carry; 98 $carry = $r0 >> 16; 99 $r0 &= 0xffff; 100 $r1 &= 0xffff; 101 $return = new ParagonIE_Sodium_Core32_Int32( 102 array($r0, $r1) 103 ); 104 $return->overflow = $carry; 105 $return->unsignedInt = $this->unsignedInt; 106 return $return; 107 } 108 109 /** 110 * @param int $b 111 * @return int 112 */ 113 public function compareInt($b = 0) 114 { 115 $gt = 0; 116 $eq = 1; 117 118 $i = 2; 119 $j = 0; 120 while ($i > 0) { 121 --$i; 122 /** @var int $x1 */ 123 $x1 = $this->limbs[$i]; 124 /** @var int $x2 */ 125 $x2 = ($b >> ($j << 4)) & 0xffff; 126 /** @var int $gt */ 127 $gt |= (($x2 - $x1) >> 8) & $eq; 128 /** @var int $eq */ 129 $eq &= (($x2 ^ $x1) - 1) >> 8; 130 } 131 return ($gt + $gt - $eq) + 1; 132 } 133 134 /** 135 * @param int $m 136 * @return ParagonIE_Sodium_Core32_Int32 137 */ 138 public function mask($m = 0) 139 { 140 /** @var int $hi */ 141 $hi = ($m >> 16) & 0xffff; 142 /** @var int $lo */ 143 $lo = ($m & 0xffff); 144 return new ParagonIE_Sodium_Core32_Int32( 145 array( 146 (int) ($this->limbs[0] & $hi), 147 (int) ($this->limbs[1] & $lo) 148 ), 149 $this->unsignedInt 150 ); 151 } 152 153 /** 154 * @param array<int, int> $a 155 * @param array<int, int> $b 156 * @param int $baseLog2 157 * @return array<int, int> 158 */ 159 public function multiplyLong(array $a, array $b, $baseLog2 = 16) 160 { 161 $a_l = count($a); 162 $b_l = count($b); 163 /** @var array<int, int> $r */ 164 $r = array_fill(0, $a_l + $b_l + 1, 0); 165 $base = 1 << $baseLog2; 166 for ($i = 0; $i < $a_l; ++$i) { 167 $a_i = $a[$i]; 168 for ($j = 0; $j < $a_l; ++$j) { 169 $b_j = $b[$j]; 170 $product = ($a_i * $b_j) + $r[$i + $j]; 171 $carry = ($product >> $baseLog2 & 0xffff); 172 $r[$i + $j] = ($product - (int) ($carry * $base)) & 0xffff; 173 $r[$i + $j + 1] += $carry; 174 } 175 } 176 return array_slice($r, 0, 5); 177 } 178 179 /** 180 * @param int $int 181 * @return ParagonIE_Sodium_Core32_Int32 182 */ 183 public function mulIntFast($int) 184 { 185 // Handle negative numbers 186 $aNeg = ($this->limbs[0] >> 15) & 1; 187 $bNeg = ($int >> 31) & 1; 188 $a = array_reverse($this->limbs); 189 $b = array( 190 $int & 0xffff, 191 ($int >> 16) & 0xffff 192 ); 193 if ($aNeg) { 194 for ($i = 0; $i < 2; ++$i) { 195 $a[$i] = ($a[$i] ^ 0xffff) & 0xffff; 196 } 197 ++$a[0]; 198 } 199 if ($bNeg) { 200 for ($i = 0; $i < 2; ++$i) { 201 $b[$i] = ($b[$i] ^ 0xffff) & 0xffff; 202 } 203 ++$b[0]; 204 } 205 // Multiply 206 $res = $this->multiplyLong($a, $b); 207 208 // Re-apply negation to results 209 if ($aNeg !== $bNeg) { 210 for ($i = 0; $i < 2; ++$i) { 211 $res[$i] = (0xffff ^ $res[$i]) & 0xffff; 212 } 213 // Handle integer overflow 214 $c = 1; 215 for ($i = 0; $i < 2; ++$i) { 216 $res[$i] += $c; 217 $c = $res[$i] >> 16; 218 $res[$i] &= 0xffff; 219 } 220 } 221 222 // Return our values 223 $return = new ParagonIE_Sodium_Core32_Int32(); 224 $return->limbs = array( 225 $res[1] & 0xffff, 226 $res[0] & 0xffff 227 ); 228 if (count($res) > 2) { 229 $return->overflow = $res[2] & 0xffff; 230 } 231 $return->unsignedInt = $this->unsignedInt; 232 return $return; 233 } 234 235 /** 236 * @param ParagonIE_Sodium_Core32_Int32 $right 237 * @return ParagonIE_Sodium_Core32_Int32 238 */ 239 public function mulInt32Fast(ParagonIE_Sodium_Core32_Int32 $right) 240 { 241 $aNeg = ($this->limbs[0] >> 15) & 1; 242 $bNeg = ($right->limbs[0] >> 15) & 1; 243 244 $a = array_reverse($this->limbs); 245 $b = array_reverse($right->limbs); 246 if ($aNeg) { 247 for ($i = 0; $i < 2; ++$i) { 248 $a[$i] = ($a[$i] ^ 0xffff) & 0xffff; 249 } 250 ++$a[0]; 251 } 252 if ($bNeg) { 253 for ($i = 0; $i < 2; ++$i) { 254 $b[$i] = ($b[$i] ^ 0xffff) & 0xffff; 255 } 256 ++$b[0]; 257 } 258 $res = $this->multiplyLong($a, $b); 259 if ($aNeg !== $bNeg) { 260 if ($aNeg !== $bNeg) { 261 for ($i = 0; $i < 2; ++$i) { 262 $res[$i] = ($res[$i] ^ 0xffff) & 0xffff; 263 } 264 $c = 1; 265 for ($i = 0; $i < 2; ++$i) { 266 $res[$i] += $c; 267 $c = $res[$i] >> 16; 268 $res[$i] &= 0xffff; 269 } 270 } 271 } 272 $return = new ParagonIE_Sodium_Core32_Int32(); 273 $return->limbs = array( 274 $res[1] & 0xffff, 275 $res[0] & 0xffff 276 ); 277 if (count($res) > 2) { 278 $return->overflow = $res[2]; 279 } 280 return $return; 281 } 282 283 /** 284 * @param int $int 285 * @param int $size 286 * @return ParagonIE_Sodium_Core32_Int32 287 * @throws SodiumException 288 * @throws TypeError 289 */ 290 public function mulInt($int = 0, $size = 0) 291 { 292 ParagonIE_Sodium_Core32_Util::declareScalarType($int, 'int', 1); 293 ParagonIE_Sodium_Core32_Util::declareScalarType($size, 'int', 2); 294 if (ParagonIE_Sodium_Compat::$fastMult) { 295 return $this->mulIntFast((int) $int); 296 } 297 /** @var int $int */ 298 $int = (int) $int; 299 /** @var int $size */ 300 $size = (int) $size; 301 302 if (!$size) { 303 $size = 31; 304 } 305 /** @var int $size */ 306 307 $a = clone $this; 308 $return = new ParagonIE_Sodium_Core32_Int32(); 309 $return->unsignedInt = $this->unsignedInt; 310 311 // Initialize: 312 $ret0 = 0; 313 $ret1 = 0; 314 $a0 = $a->limbs[0]; 315 $a1 = $a->limbs[1]; 316 317 /** @var int $size */ 318 /** @var int $i */ 319 for ($i = $size; $i >= 0; --$i) { 320 $m = (int) (-($int & 1)); 321 $x0 = $a0 & $m; 322 $x1 = $a1 & $m; 323 324 $ret1 += $x1; 325 $c = $ret1 >> 16; 326 327 $ret0 += $x0 + $c; 328 329 $ret0 &= 0xffff; 330 $ret1 &= 0xffff; 331 332 $a1 = ($a1 << 1); 333 $x1 = $a1 >> 16; 334 $a0 = ($a0 << 1) | $x1; 335 $a0 &= 0xffff; 336 $a1 &= 0xffff; 337 $int >>= 1; 338 } 339 $return->limbs[0] = $ret0; 340 $return->limbs[1] = $ret1; 341 return $return; 342 } 343 344 /** 345 * @param ParagonIE_Sodium_Core32_Int32 $int 346 * @param int $size 347 * @return ParagonIE_Sodium_Core32_Int32 348 * @throws SodiumException 349 * @throws TypeError 350 */ 351 public function mulInt32(ParagonIE_Sodium_Core32_Int32 $int, $size = 0) 352 { 353 ParagonIE_Sodium_Core32_Util::declareScalarType($size, 'int', 2); 354 if (ParagonIE_Sodium_Compat::$fastMult) { 355 return $this->mulInt32Fast($int); 356 } 357 if (!$size) { 358 $size = 31; 359 } 360 /** @var int $size */ 361 362 $a = clone $this; 363 $b = clone $int; 364 $return = new ParagonIE_Sodium_Core32_Int32(); 365 $return->unsignedInt = $this->unsignedInt; 366 367 // Initialize: 368 $ret0 = 0; 369 $ret1 = 0; 370 $a0 = $a->limbs[0]; 371 $a1 = $a->limbs[1]; 372 $b0 = $b->limbs[0]; 373 $b1 = $b->limbs[1]; 374 375 /** @var int $size */ 376 /** @var int $i */ 377 for ($i = $size; $i >= 0; --$i) { 378 $m = (int) (-($b1 & 1)); 379 $x0 = $a0 & $m; 380 $x1 = $a1 & $m; 381 382 $ret1 += $x1; 383 $c = $ret1 >> 16; 384 385 $ret0 += $x0 + $c; 386 387 $ret0 &= 0xffff; 388 $ret1 &= 0xffff; 389 390 $a1 = ($a1 << 1); 391 $x1 = $a1 >> 16; 392 $a0 = ($a0 << 1) | $x1; 393 $a0 &= 0xffff; 394 $a1 &= 0xffff; 395 396 $x0 = ($b0 & 1) << 16; 397 $b0 = ($b0 >> 1); 398 $b1 = (($b1 | $x0) >> 1); 399 400 $b0 &= 0xffff; 401 $b1 &= 0xffff; 402 403 } 404 $return->limbs[0] = $ret0; 405 $return->limbs[1] = $ret1; 406 407 return $return; 408 } 409 410 /** 411 * OR this 32-bit integer with another. 412 * 413 * @param ParagonIE_Sodium_Core32_Int32 $b 414 * @return ParagonIE_Sodium_Core32_Int32 415 */ 416 public function orInt32(ParagonIE_Sodium_Core32_Int32 $b) 417 { 418 $return = new ParagonIE_Sodium_Core32_Int32(); 419 $return->unsignedInt = $this->unsignedInt; 420 $return->limbs = array( 421 (int) ($this->limbs[0] | $b->limbs[0]), 422 (int) ($this->limbs[1] | $b->limbs[1]) 423 ); 424 /** @var int overflow */ 425 $return->overflow = $this->overflow | $b->overflow; 426 return $return; 427 } 428 429 /** 430 * @param int $b 431 * @return bool 432 */ 433 public function isGreaterThan($b = 0) 434 { 435 return $this->compareInt($b) > 0; 436 } 437 438 /** 439 * @param int $b 440 * @return bool 441 */ 442 public function isLessThanInt($b = 0) 443 { 444 return $this->compareInt($b) < 0; 445 } 446 447 /** 448 * @param int $c 449 * @return ParagonIE_Sodium_Core32_Int32 450 * @throws SodiumException 451 * @throws TypeError 452 * @psalm-suppress MixedArrayAccess 453 */ 454 public function rotateLeft($c = 0) 455 { 456 ParagonIE_Sodium_Core32_Util::declareScalarType($c, 'int', 1); 457 /** @var int $c */ 458 $c = (int) $c; 459 460 $return = new ParagonIE_Sodium_Core32_Int32(); 461 $return->unsignedInt = $this->unsignedInt; 462 $c &= 31; 463 if ($c === 0) { 464 // NOP, but we want a copy. 465 $return->limbs = $this->limbs; 466 } else { 467 /** @var int $c */ 468 469 /** @var int $idx_shift */ 470 $idx_shift = ($c >> 4) & 1; 471 472 /** @var int $sub_shift */ 473 $sub_shift = $c & 15; 474 475 /** @var array<int, int> $limbs */ 476 $limbs =& $return->limbs; 477 478 /** @var array<int, int> $myLimbs */ 479 $myLimbs =& $this->limbs; 480 481 for ($i = 1; $i >= 0; --$i) { 482 /** @var int $j */ 483 $j = ($i + $idx_shift) & 1; 484 /** @var int $k */ 485 $k = ($i + $idx_shift + 1) & 1; 486 $limbs[$i] = (int) ( 487 ( 488 ((int) ($myLimbs[$j]) << $sub_shift) 489 | 490 ((int) ($myLimbs[$k]) >> (16 - $sub_shift)) 491 ) & 0xffff 492 ); 493 } 494 } 495 return $return; 496 } 497 498 /** 499 * Rotate to the right 500 * 501 * @param int $c 502 * @return ParagonIE_Sodium_Core32_Int32 503 * @throws SodiumException 504 * @throws TypeError 505 * @psalm-suppress MixedArrayAccess 506 */ 507 public function rotateRight($c = 0) 508 { 509 ParagonIE_Sodium_Core32_Util::declareScalarType($c, 'int', 1); 510 /** @var int $c */ 511 $c = (int) $c; 512 513 $return = new ParagonIE_Sodium_Core32_Int32(); 514 $return->unsignedInt = $this->unsignedInt; 515 $c &= 31; 516 /** @var int $c */ 517 if ($c === 0) { 518 // NOP, but we want a copy. 519 $return->limbs = $this->limbs; 520 } else { 521 /** @var int $c */ 522 523 /** @var int $idx_shift */ 524 $idx_shift = ($c >> 4) & 1; 525 526 /** @var int $sub_shift */ 527 $sub_shift = $c & 15; 528 529 /** @var array<int, int> $limbs */ 530 $limbs =& $return->limbs; 531 532 /** @var array<int, int> $myLimbs */ 533 $myLimbs =& $this->limbs; 534 535 for ($i = 1; $i >= 0; --$i) { 536 /** @var int $j */ 537 $j = ($i - $idx_shift) & 1; 538 /** @var int $k */ 539 $k = ($i - $idx_shift - 1) & 1; 540 $limbs[$i] = (int) ( 541 ( 542 ((int) ($myLimbs[$j]) >> (int) ($sub_shift)) 543 | 544 ((int) ($myLimbs[$k]) << (16 - (int) ($sub_shift))) 545 ) & 0xffff 546 ); 547 } 548 } 549 return $return; 550 } 551 552 /** 553 * @param bool $bool 554 * @return self 555 */ 556 public function setUnsignedInt($bool = false) 557 { 558 $this->unsignedInt = !empty($bool); 559 return $this; 560 } 561 562 /** 563 * @param int $c 564 * @return ParagonIE_Sodium_Core32_Int32 565 * @throws SodiumException 566 * @throws TypeError 567 */ 568 public function shiftLeft($c = 0) 569 { 570 ParagonIE_Sodium_Core32_Util::declareScalarType($c, 'int', 1); 571 /** @var int $c */ 572 $c = (int) $c; 573 574 $return = new ParagonIE_Sodium_Core32_Int32(); 575 $return->unsignedInt = $this->unsignedInt; 576 $c &= 63; 577 /** @var int $c */ 578 if ($c === 0) { 579 $return->limbs = $this->limbs; 580 } elseif ($c < 0) { 581 /** @var int $c */ 582 return $this->shiftRight(-$c); 583 } else { 584 /** @var int $c */ 585 /** @var int $tmp */ 586 $tmp = $this->limbs[1] << $c; 587 $return->limbs[1] = (int)($tmp & 0xffff); 588 /** @var int $carry */ 589 $carry = $tmp >> 16; 590 591 /** @var int $tmp */ 592 $tmp = ($this->limbs[0] << $c) | ($carry & 0xffff); 593 $return->limbs[0] = (int) ($tmp & 0xffff); 594 } 595 return $return; 596 } 597 598 /** 599 * @param int $c 600 * @return ParagonIE_Sodium_Core32_Int32 601 * @throws SodiumException 602 * @throws TypeError 603 * @psalm-suppress MixedAssignment 604 * @psalm-suppress MixedOperand 605 */ 606 public function shiftRight($c = 0) 607 { 608 ParagonIE_Sodium_Core32_Util::declareScalarType($c, 'int', 1); 609 /** @var int $c */ 610 $c = (int) $c; 611 612 $return = new ParagonIE_Sodium_Core32_Int32(); 613 $return->unsignedInt = $this->unsignedInt; 614 $c &= 63; 615 /** @var int $c */ 616 if ($c >= 16) { 617 $return->limbs = array( 618 (int) ($this->overflow & 0xffff), 619 (int) ($this->limbs[0]) 620 ); 621 $return->overflow = $this->overflow >> 16; 622 return $return->shiftRight($c & 15); 623 } 624 if ($c === 0) { 625 $return->limbs = $this->limbs; 626 } elseif ($c < 0) { 627 /** @var int $c */ 628 return $this->shiftLeft(-$c); 629 } else { 630 if (!is_int($c)) { 631 throw new TypeError(); 632 } 633 /** @var int $c */ 634 // $return->limbs[0] = (int) (($this->limbs[0] >> $c) & 0xffff); 635 $carryLeft = (int) ($this->overflow & ((1 << ($c + 1)) - 1)); 636 $return->limbs[0] = (int) ((($this->limbs[0] >> $c) | ($carryLeft << (16 - $c))) & 0xffff); 637 $carryRight = (int) ($this->limbs[0] & ((1 << ($c + 1)) - 1)); 638 $return->limbs[1] = (int) ((($this->limbs[1] >> $c) | ($carryRight << (16 - $c))) & 0xffff); 639 $return->overflow >>= $c; 640 } 641 return $return; 642 } 643 644 /** 645 * Subtract a normal integer from an int32 object. 646 * 647 * @param int $int 648 * @return ParagonIE_Sodium_Core32_Int32 649 * @throws SodiumException 650 * @throws TypeError 651 */ 652 public function subInt($int) 653 { 654 ParagonIE_Sodium_Core32_Util::declareScalarType($int, 'int', 1); 655 /** @var int $int */ 656 $int = (int) $int; 657 658 $return = new ParagonIE_Sodium_Core32_Int32(); 659 $return->unsignedInt = $this->unsignedInt; 660 661 /** @var int $tmp */ 662 $tmp = $this->limbs[1] - ($int & 0xffff); 663 /** @var int $carry */ 664 $carry = $tmp >> 16; 665 $return->limbs[1] = (int) ($tmp & 0xffff); 666 667 /** @var int $tmp */ 668 $tmp = $this->limbs[0] - (($int >> 16) & 0xffff) + $carry; 669 $return->limbs[0] = (int) ($tmp & 0xffff); 670 return $return; 671 } 672 673 /** 674 * Subtract two int32 objects from each other 675 * 676 * @param ParagonIE_Sodium_Core32_Int32 $b 677 * @return ParagonIE_Sodium_Core32_Int32 678 */ 679 public function subInt32(ParagonIE_Sodium_Core32_Int32 $b) 680 { 681 $return = new ParagonIE_Sodium_Core32_Int32(); 682 $return->unsignedInt = $this->unsignedInt; 683 684 /** @var int $tmp */ 685 $tmp = $this->limbs[1] - ($b->limbs[1] & 0xffff); 686 /** @var int $carry */ 687 $carry = $tmp >> 16; 688 $return->limbs[1] = (int) ($tmp & 0xffff); 689 690 /** @var int $tmp */ 691 $tmp = $this->limbs[0] - ($b->limbs[0] & 0xffff) + $carry; 692 $return->limbs[0] = (int) ($tmp & 0xffff); 693 return $return; 694 } 695 696 /** 697 * XOR this 32-bit integer with another. 698 * 699 * @param ParagonIE_Sodium_Core32_Int32 $b 700 * @return ParagonIE_Sodium_Core32_Int32 701 */ 702 public function xorInt32(ParagonIE_Sodium_Core32_Int32 $b) 703 { 704 $return = new ParagonIE_Sodium_Core32_Int32(); 705 $return->unsignedInt = $this->unsignedInt; 706 $return->limbs = array( 707 (int) ($this->limbs[0] ^ $b->limbs[0]), 708 (int) ($this->limbs[1] ^ $b->limbs[1]) 709 ); 710 return $return; 711 } 712 713 /** 714 * @param int $signed 715 * @return self 716 * @throws SodiumException 717 * @throws TypeError 718 */ 719 public static function fromInt($signed) 720 { 721 ParagonIE_Sodium_Core32_Util::declareScalarType($signed, 'int', 1);; 722 /** @var int $signed */ 723 $signed = (int) $signed; 724 725 return new ParagonIE_Sodium_Core32_Int32( 726 array( 727 (int) (($signed >> 16) & 0xffff), 728 (int) ($signed & 0xffff) 729 ) 730 ); 731 } 732 733 /** 734 * @param string $string 735 * @return self 736 * @throws SodiumException 737 * @throws TypeError 738 */ 739 public static function fromString($string) 740 { 741 ParagonIE_Sodium_Core32_Util::declareScalarType($string, 'string', 1); 742 $string = (string) $string; 743 if (ParagonIE_Sodium_Core32_Util::strlen($string) !== 4) { 744 throw new RangeException( 745 'String must be 4 bytes; ' . ParagonIE_Sodium_Core32_Util::strlen($string) . ' given.' 746 ); 747 } 748 $return = new ParagonIE_Sodium_Core32_Int32(); 749 750 $return->limbs[0] = (int) ((ParagonIE_Sodium_Core32_Util::chrToInt($string[0]) & 0xff) << 8); 751 $return->limbs[0] |= (ParagonIE_Sodium_Core32_Util::chrToInt($string[1]) & 0xff); 752 $return->limbs[1] = (int) ((ParagonIE_Sodium_Core32_Util::chrToInt($string[2]) & 0xff) << 8); 753 $return->limbs[1] |= (ParagonIE_Sodium_Core32_Util::chrToInt($string[3]) & 0xff); 754 return $return; 755 } 756 757 /** 758 * @param string $string 759 * @return self 760 * @throws SodiumException 761 * @throws TypeError 762 */ 763 public static function fromReverseString($string) 764 { 765 ParagonIE_Sodium_Core32_Util::declareScalarType($string, 'string', 1); 766 $string = (string) $string; 767 if (ParagonIE_Sodium_Core32_Util::strlen($string) !== 4) { 768 throw new RangeException( 769 'String must be 4 bytes; ' . ParagonIE_Sodium_Core32_Util::strlen($string) . ' given.' 770 ); 771 } 772 $return = new ParagonIE_Sodium_Core32_Int32(); 773 774 $return->limbs[0] = (int) ((ParagonIE_Sodium_Core32_Util::chrToInt($string[3]) & 0xff) << 8); 775 $return->limbs[0] |= (ParagonIE_Sodium_Core32_Util::chrToInt($string[2]) & 0xff); 776 $return->limbs[1] = (int) ((ParagonIE_Sodium_Core32_Util::chrToInt($string[1]) & 0xff) << 8); 777 $return->limbs[1] |= (ParagonIE_Sodium_Core32_Util::chrToInt($string[0]) & 0xff); 778 return $return; 779 } 780 781 /** 782 * @return array<int, int> 783 */ 784 public function toArray() 785 { 786 return array((int) ($this->limbs[0] << 16 | $this->limbs[1])); 787 } 788 789 /** 790 * @return string 791 * @throws TypeError 792 */ 793 public function toString() 794 { 795 return 796 ParagonIE_Sodium_Core32_Util::intToChr(($this->limbs[0] >> 8) & 0xff) . 797 ParagonIE_Sodium_Core32_Util::intToChr($this->limbs[0] & 0xff) . 798 ParagonIE_Sodium_Core32_Util::intToChr(($this->limbs[1] >> 8) & 0xff) . 799 ParagonIE_Sodium_Core32_Util::intToChr($this->limbs[1] & 0xff); 800 } 801 802 /** 803 * @return int 804 */ 805 public function toInt() 806 { 807 return (int) ( 808 (($this->limbs[0] & 0xffff) << 16) 809 | 810 ($this->limbs[1] & 0xffff) 811 ); 812 } 813 814 /** 815 * @return ParagonIE_Sodium_Core32_Int32 816 */ 817 public function toInt32() 818 { 819 $return = new ParagonIE_Sodium_Core32_Int32(); 820 $return->limbs[0] = (int) ($this->limbs[0] & 0xffff); 821 $return->limbs[1] = (int) ($this->limbs[1] & 0xffff); 822 $return->unsignedInt = $this->unsignedInt; 823 $return->overflow = (int) ($this->overflow & 0x7fffffff); 824 return $return; 825 } 826 827 /** 828 * @return ParagonIE_Sodium_Core32_Int64 829 */ 830 public function toInt64() 831 { 832 $return = new ParagonIE_Sodium_Core32_Int64(); 833 $return->unsignedInt = $this->unsignedInt; 834 if ($this->unsignedInt) { 835 $return->limbs[0] += (($this->overflow >> 16) & 0xffff); 836 $return->limbs[1] += (($this->overflow) & 0xffff); 837 } else { 838 $neg = -(($this->limbs[0] >> 15) & 1); 839 $return->limbs[0] = (int)($neg & 0xffff); 840 $return->limbs[1] = (int)($neg & 0xffff); 841 } 842 $return->limbs[2] = (int) ($this->limbs[0] & 0xffff); 843 $return->limbs[3] = (int) ($this->limbs[1] & 0xffff); 844 return $return; 845 } 846 847 /** 848 * @return string 849 * @throws TypeError 850 */ 851 public function toReverseString() 852 { 853 return ParagonIE_Sodium_Core32_Util::intToChr($this->limbs[1] & 0xff) . 854 ParagonIE_Sodium_Core32_Util::intToChr(($this->limbs[1] >> 8) & 0xff) . 855 ParagonIE_Sodium_Core32_Util::intToChr($this->limbs[0] & 0xff) . 856 ParagonIE_Sodium_Core32_Util::intToChr(($this->limbs[0] >> 8) & 0xff); 857 } 858 859 /** 860 * @return string 861 */ 862 public function __toString() 863 { 864 try { 865 return $this->toString(); 866 } catch (TypeError $ex) { 867 // PHP engine can't handle exceptions from __toString() 868 return ''; 869 } 870 } 871 }
title
Description
Body
title
Description
Body
title
Description
Body
title
Body
Generated: Mon Mar 1 01:00:03 2021 | Cross-referenced by PHPXref 0.7.1 |