Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(374)

Side by Side Diff: base/numerics/safe_numerics_unittest.cc

Issue 2528243002: Fix silent truncations when extracting values from CheckedNumeric (Closed)
Patch Set: compile cleanup and fix Created 4 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2013 The Chromium Authors. All rights reserved. 1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include <stddef.h> 5 #include <stddef.h>
6 #include <stdint.h> 6 #include <stdint.h>
7 7
8 #include <limits> 8 #include <limits>
9 #include <type_traits> 9 #include <type_traits>
10 10
(...skipping 19 matching lines...) Expand all
30 using base::CheckMod; 30 using base::CheckMod;
31 using base::CheckLsh; 31 using base::CheckLsh;
32 using base::CheckRsh; 32 using base::CheckRsh;
33 using base::checked_cast; 33 using base::checked_cast;
34 using base::IsValueInRangeForNumericType; 34 using base::IsValueInRangeForNumericType;
35 using base::IsValueNegative; 35 using base::IsValueNegative;
36 using base::SizeT; 36 using base::SizeT;
37 using base::StrictNumeric; 37 using base::StrictNumeric;
38 using base::saturated_cast; 38 using base::saturated_cast;
39 using base::strict_cast; 39 using base::strict_cast;
40 using base::StrictNumeric;
40 using base::internal::MaxExponent; 41 using base::internal::MaxExponent;
41 using base::internal::RANGE_VALID; 42 using base::internal::RANGE_VALID;
42 using base::internal::RANGE_INVALID; 43 using base::internal::RANGE_INVALID;
43 using base::internal::RANGE_OVERFLOW; 44 using base::internal::RANGE_OVERFLOW;
44 using base::internal::RANGE_UNDERFLOW; 45 using base::internal::RANGE_UNDERFLOW;
45 using base::internal::SignedIntegerForSize; 46 using base::internal::SignedIntegerForSize;
46 47
47 // These tests deliberately cause arithmetic boundary errors. If the compiler is 48 // These tests deliberately cause arithmetic boundary errors. If the compiler is
48 // aggressive enough, it can const detect these errors, so we disable warnings. 49 // aggressive enough, it can const detect these errors, so we disable warnings.
49 #if defined(OS_WIN) 50 #if defined(OS_WIN)
(...skipping 354 matching lines...) Expand 10 before | Expand all | Expand 10 after
404 template <typename Dst, typename Src, NumericConversionType conversion> 405 template <typename Dst, typename Src, NumericConversionType conversion>
405 struct TestNumericConversion {}; 406 struct TestNumericConversion {};
406 407
407 // EXPECT_EQ wrappers providing specific detail on test failures. 408 // EXPECT_EQ wrappers providing specific detail on test failures.
408 #define TEST_EXPECTED_RANGE(expected, actual) \ 409 #define TEST_EXPECTED_RANGE(expected, actual) \
409 EXPECT_EQ(expected, base::internal::DstRangeRelationToSrcRange<Dst>(actual)) \ 410 EXPECT_EQ(expected, base::internal::DstRangeRelationToSrcRange<Dst>(actual)) \
410 << "Conversion test: " << src << " value " << actual << " to " << dst \ 411 << "Conversion test: " << src << " value " << actual << " to " << dst \
411 << " on line " << line 412 << " on line " << line
412 413
413 template <typename Dst, typename Src> 414 template <typename Dst, typename Src>
415 void TestStrictComparison() {
416 typedef numeric_limits<Dst> DstLimits;
417 typedef numeric_limits<Src> SrcLimits;
418 static_assert(StrictNumeric<Src>(SrcLimits::min()) < DstLimits::max(), "");
419 static_assert(StrictNumeric<Src>(SrcLimits::min()) < SrcLimits::max(), "");
420 static_assert(!(StrictNumeric<Src>(SrcLimits::min()) >= DstLimits::max()),
421 "");
422 static_assert(!(StrictNumeric<Src>(SrcLimits::min()) >= SrcLimits::max()),
423 "");
424 static_assert(StrictNumeric<Src>(SrcLimits::min()) <= DstLimits::max(), "");
425 static_assert(StrictNumeric<Src>(SrcLimits::min()) <= SrcLimits::max(), "");
426 static_assert(!(StrictNumeric<Src>(SrcLimits::min()) > DstLimits::max()), "");
427 static_assert(!(StrictNumeric<Src>(SrcLimits::min()) > SrcLimits::max()), "");
428 static_assert(StrictNumeric<Src>(SrcLimits::max()) > DstLimits::min(), "");
429 static_assert(StrictNumeric<Src>(SrcLimits::max()) > SrcLimits::min(), "");
430 static_assert(!(StrictNumeric<Src>(SrcLimits::max()) <= DstLimits::min()),
431 "");
432 static_assert(!(StrictNumeric<Src>(SrcLimits::max()) <= SrcLimits::min()),
433 "");
434 static_assert(StrictNumeric<Src>(SrcLimits::max()) >= DstLimits::min(), "");
435 static_assert(StrictNumeric<Src>(SrcLimits::max()) >= SrcLimits::min(), "");
436 static_assert(!(StrictNumeric<Src>(SrcLimits::max()) < DstLimits::min()), "");
437 static_assert(!(StrictNumeric<Src>(SrcLimits::max()) < SrcLimits::min()), "");
438 static_assert(StrictNumeric<Src>(static_cast<Src>(1)) == static_cast<Dst>(1),
439 "");
440 static_assert(StrictNumeric<Src>(static_cast<Src>(1)) != static_cast<Dst>(0),
441 "");
442 static_assert(StrictNumeric<Src>(SrcLimits::max()) != static_cast<Dst>(0),
443 "");
444 static_assert(StrictNumeric<Src>(SrcLimits::max()) != DstLimits::min(), "");
445 static_assert(
446 !(StrictNumeric<Src>(static_cast<Src>(1)) != static_cast<Dst>(1)), "");
447 static_assert(
448 !(StrictNumeric<Src>(static_cast<Src>(1)) == static_cast<Dst>(0)), "");
449
450 base::internal::TestCompileTimeConstantSupport();
451 }
452
453 template <typename Dst, typename Src>
414 struct TestNumericConversion<Dst, Src, SIGN_PRESERVING_VALUE_PRESERVING> { 454 struct TestNumericConversion<Dst, Src, SIGN_PRESERVING_VALUE_PRESERVING> {
415 static void Test(const char *dst, const char *src, int line) { 455 static void Test(const char *dst, const char *src, int line) {
416 typedef numeric_limits<Src> SrcLimits; 456 typedef numeric_limits<Src> SrcLimits;
417 typedef numeric_limits<Dst> DstLimits; 457 typedef numeric_limits<Dst> DstLimits;
418 // Integral to floating. 458 // Integral to floating.
419 static_assert((DstLimits::is_iec559 && SrcLimits::is_integer) || 459 static_assert((DstLimits::is_iec559 && SrcLimits::is_integer) ||
420 // Not floating to integral and... 460 // Not floating to integral and...
421 (!(DstLimits::is_integer && SrcLimits::is_iec559) && 461 (!(DstLimits::is_integer && SrcLimits::is_iec559) &&
422 // Same sign, same numeric, source is narrower or same. 462 // Same sign, same numeric, source is narrower or same.
423 ((SrcLimits::is_signed == DstLimits::is_signed && 463 ((SrcLimits::is_signed == DstLimits::is_signed &&
424 sizeof(Dst) >= sizeof(Src)) || 464 sizeof(Dst) >= sizeof(Src)) ||
425 // Or signed destination and source is smaller 465 // Or signed destination and source is smaller
426 (DstLimits::is_signed && sizeof(Dst) > sizeof(Src)))), 466 (DstLimits::is_signed && sizeof(Dst) > sizeof(Src)))),
427 "Comparison must be sign preserving and value preserving"); 467 "Comparison must be sign preserving and value preserving");
428 468
469 TestStrictComparison<Dst, Src>();
470
429 const CheckedNumeric<Dst> checked_dst = SrcLimits::max(); 471 const CheckedNumeric<Dst> checked_dst = SrcLimits::max();
430 TEST_EXPECTED_SUCCESS(checked_dst); 472 TEST_EXPECTED_SUCCESS(checked_dst);
431 if (MaxExponent<Dst>::value > MaxExponent<Src>::value) { 473 if (MaxExponent<Dst>::value > MaxExponent<Src>::value) {
432 if (MaxExponent<Dst>::value >= MaxExponent<Src>::value * 2 - 1) { 474 if (MaxExponent<Dst>::value >= MaxExponent<Src>::value * 2 - 1) {
433 // At least twice larger type. 475 // At least twice larger type.
434 TEST_EXPECTED_SUCCESS(SrcLimits::max() * checked_dst); 476 TEST_EXPECTED_SUCCESS(SrcLimits::max() * checked_dst);
435 477
436 } else { // Larger, but not at least twice as large. 478 } else { // Larger, but not at least twice as large.
437 TEST_EXPECTED_FAILURE(SrcLimits::max() * checked_dst); 479 TEST_EXPECTED_FAILURE(SrcLimits::max() * checked_dst);
438 TEST_EXPECTED_SUCCESS(checked_dst + 1); 480 TEST_EXPECTED_SUCCESS(checked_dst + 1);
(...skipping 20 matching lines...) Expand all
459 struct TestNumericConversion<Dst, Src, SIGN_PRESERVING_NARROW> { 501 struct TestNumericConversion<Dst, Src, SIGN_PRESERVING_NARROW> {
460 static void Test(const char *dst, const char *src, int line) { 502 static void Test(const char *dst, const char *src, int line) {
461 typedef numeric_limits<Src> SrcLimits; 503 typedef numeric_limits<Src> SrcLimits;
462 typedef numeric_limits<Dst> DstLimits; 504 typedef numeric_limits<Dst> DstLimits;
463 static_assert(SrcLimits::is_signed == DstLimits::is_signed, 505 static_assert(SrcLimits::is_signed == DstLimits::is_signed,
464 "Destination and source sign must be the same"); 506 "Destination and source sign must be the same");
465 static_assert(sizeof(Dst) < sizeof(Src) || 507 static_assert(sizeof(Dst) < sizeof(Src) ||
466 (DstLimits::is_integer && SrcLimits::is_iec559), 508 (DstLimits::is_integer && SrcLimits::is_iec559),
467 "Destination must be narrower than source"); 509 "Destination must be narrower than source");
468 510
511 TestStrictComparison<Dst, Src>();
512
469 const CheckedNumeric<Dst> checked_dst; 513 const CheckedNumeric<Dst> checked_dst;
470 TEST_EXPECTED_FAILURE(checked_dst + SrcLimits::max()); 514 TEST_EXPECTED_FAILURE(checked_dst + SrcLimits::max());
471 TEST_EXPECTED_VALUE(1, checked_dst + static_cast<Src>(1)); 515 TEST_EXPECTED_VALUE(1, checked_dst + static_cast<Src>(1));
472 TEST_EXPECTED_FAILURE(checked_dst - SrcLimits::max()); 516 TEST_EXPECTED_FAILURE(checked_dst - SrcLimits::max());
473 517
474 TEST_EXPECTED_RANGE(RANGE_OVERFLOW, SrcLimits::max()); 518 TEST_EXPECTED_RANGE(RANGE_OVERFLOW, SrcLimits::max());
475 TEST_EXPECTED_RANGE(RANGE_VALID, static_cast<Src>(1)); 519 TEST_EXPECTED_RANGE(RANGE_VALID, static_cast<Src>(1));
476 if (SrcLimits::is_iec559) { 520 if (SrcLimits::is_iec559) {
477 TEST_EXPECTED_RANGE(RANGE_UNDERFLOW, SrcLimits::max() * -1); 521 TEST_EXPECTED_RANGE(RANGE_UNDERFLOW, SrcLimits::max() * -1);
478 TEST_EXPECTED_RANGE(RANGE_VALID, static_cast<Src>(-1)); 522 TEST_EXPECTED_RANGE(RANGE_VALID, static_cast<Src>(-1));
(...skipping 26 matching lines...) Expand all
505 template <typename Dst, typename Src> 549 template <typename Dst, typename Src>
506 struct TestNumericConversion<Dst, Src, SIGN_TO_UNSIGN_WIDEN_OR_EQUAL> { 550 struct TestNumericConversion<Dst, Src, SIGN_TO_UNSIGN_WIDEN_OR_EQUAL> {
507 static void Test(const char *dst, const char *src, int line) { 551 static void Test(const char *dst, const char *src, int line) {
508 typedef numeric_limits<Src> SrcLimits; 552 typedef numeric_limits<Src> SrcLimits;
509 typedef numeric_limits<Dst> DstLimits; 553 typedef numeric_limits<Dst> DstLimits;
510 static_assert(sizeof(Dst) >= sizeof(Src), 554 static_assert(sizeof(Dst) >= sizeof(Src),
511 "Destination must be equal or wider than source."); 555 "Destination must be equal or wider than source.");
512 static_assert(SrcLimits::is_signed, "Source must be signed"); 556 static_assert(SrcLimits::is_signed, "Source must be signed");
513 static_assert(!DstLimits::is_signed, "Destination must be unsigned"); 557 static_assert(!DstLimits::is_signed, "Destination must be unsigned");
514 558
559 TestStrictComparison<Dst, Src>();
560
515 const CheckedNumeric<Dst> checked_dst; 561 const CheckedNumeric<Dst> checked_dst;
516 TEST_EXPECTED_VALUE(SrcLimits::max(), checked_dst + SrcLimits::max()); 562 TEST_EXPECTED_VALUE(SrcLimits::max(), checked_dst + SrcLimits::max());
517 TEST_EXPECTED_FAILURE(checked_dst + static_cast<Src>(-1)); 563 TEST_EXPECTED_FAILURE(checked_dst + static_cast<Src>(-1));
518 TEST_EXPECTED_FAILURE(checked_dst + -SrcLimits::max()); 564 TEST_EXPECTED_FAILURE(checked_dst + -SrcLimits::max());
519 565
520 TEST_EXPECTED_RANGE(RANGE_UNDERFLOW, SrcLimits::min()); 566 TEST_EXPECTED_RANGE(RANGE_UNDERFLOW, SrcLimits::min());
521 TEST_EXPECTED_RANGE(RANGE_VALID, SrcLimits::max()); 567 TEST_EXPECTED_RANGE(RANGE_VALID, SrcLimits::max());
522 TEST_EXPECTED_RANGE(RANGE_VALID, static_cast<Src>(1)); 568 TEST_EXPECTED_RANGE(RANGE_VALID, static_cast<Src>(1));
523 TEST_EXPECTED_RANGE(RANGE_UNDERFLOW, static_cast<Src>(-1)); 569 TEST_EXPECTED_RANGE(RANGE_UNDERFLOW, static_cast<Src>(-1));
524 } 570 }
525 }; 571 };
526 572
527 template <typename Dst, typename Src> 573 template <typename Dst, typename Src>
528 struct TestNumericConversion<Dst, Src, SIGN_TO_UNSIGN_NARROW> { 574 struct TestNumericConversion<Dst, Src, SIGN_TO_UNSIGN_NARROW> {
529 static void Test(const char *dst, const char *src, int line) { 575 static void Test(const char *dst, const char *src, int line) {
530 typedef numeric_limits<Src> SrcLimits; 576 typedef numeric_limits<Src> SrcLimits;
531 typedef numeric_limits<Dst> DstLimits; 577 typedef numeric_limits<Dst> DstLimits;
532 static_assert((DstLimits::is_integer && SrcLimits::is_iec559) || 578 static_assert((DstLimits::is_integer && SrcLimits::is_iec559) ||
533 (sizeof(Dst) < sizeof(Src)), 579 (sizeof(Dst) < sizeof(Src)),
534 "Destination must be narrower than source."); 580 "Destination must be narrower than source.");
535 static_assert(SrcLimits::is_signed, "Source must be signed."); 581 static_assert(SrcLimits::is_signed, "Source must be signed.");
536 static_assert(!DstLimits::is_signed, "Destination must be unsigned."); 582 static_assert(!DstLimits::is_signed, "Destination must be unsigned.");
537 583
584 TestStrictComparison<Dst, Src>();
585
538 const CheckedNumeric<Dst> checked_dst; 586 const CheckedNumeric<Dst> checked_dst;
539 TEST_EXPECTED_VALUE(1, checked_dst + static_cast<Src>(1)); 587 TEST_EXPECTED_VALUE(1, checked_dst + static_cast<Src>(1));
540 TEST_EXPECTED_FAILURE(checked_dst + SrcLimits::max()); 588 TEST_EXPECTED_FAILURE(checked_dst + SrcLimits::max());
541 TEST_EXPECTED_FAILURE(checked_dst + static_cast<Src>(-1)); 589 TEST_EXPECTED_FAILURE(checked_dst + static_cast<Src>(-1));
542 TEST_EXPECTED_FAILURE(checked_dst + -SrcLimits::max()); 590 TEST_EXPECTED_FAILURE(checked_dst + -SrcLimits::max());
543 591
544 TEST_EXPECTED_RANGE(RANGE_OVERFLOW, SrcLimits::max()); 592 TEST_EXPECTED_RANGE(RANGE_OVERFLOW, SrcLimits::max());
545 TEST_EXPECTED_RANGE(RANGE_VALID, static_cast<Src>(1)); 593 TEST_EXPECTED_RANGE(RANGE_VALID, static_cast<Src>(1));
546 TEST_EXPECTED_RANGE(RANGE_UNDERFLOW, static_cast<Src>(-1)); 594 TEST_EXPECTED_RANGE(RANGE_UNDERFLOW, static_cast<Src>(-1));
547 if (SrcLimits::is_iec559) { 595 if (SrcLimits::is_iec559) {
(...skipping 22 matching lines...) Expand all
570 template <typename Dst, typename Src> 618 template <typename Dst, typename Src>
571 struct TestNumericConversion<Dst, Src, UNSIGN_TO_SIGN_NARROW_OR_EQUAL> { 619 struct TestNumericConversion<Dst, Src, UNSIGN_TO_SIGN_NARROW_OR_EQUAL> {
572 static void Test(const char *dst, const char *src, int line) { 620 static void Test(const char *dst, const char *src, int line) {
573 typedef numeric_limits<Src> SrcLimits; 621 typedef numeric_limits<Src> SrcLimits;
574 typedef numeric_limits<Dst> DstLimits; 622 typedef numeric_limits<Dst> DstLimits;
575 static_assert(sizeof(Dst) <= sizeof(Src), 623 static_assert(sizeof(Dst) <= sizeof(Src),
576 "Destination must be narrower or equal to source."); 624 "Destination must be narrower or equal to source.");
577 static_assert(!SrcLimits::is_signed, "Source must be unsigned."); 625 static_assert(!SrcLimits::is_signed, "Source must be unsigned.");
578 static_assert(DstLimits::is_signed, "Destination must be signed."); 626 static_assert(DstLimits::is_signed, "Destination must be signed.");
579 627
628 TestStrictComparison<Dst, Src>();
629
580 const CheckedNumeric<Dst> checked_dst; 630 const CheckedNumeric<Dst> checked_dst;
581 TEST_EXPECTED_VALUE(1, checked_dst + static_cast<Src>(1)); 631 TEST_EXPECTED_VALUE(1, checked_dst + static_cast<Src>(1));
582 TEST_EXPECTED_FAILURE(checked_dst + SrcLimits::max()); 632 TEST_EXPECTED_FAILURE(checked_dst + SrcLimits::max());
583 TEST_EXPECTED_VALUE(SrcLimits::min(), checked_dst + SrcLimits::min()); 633 TEST_EXPECTED_VALUE(SrcLimits::min(), checked_dst + SrcLimits::min());
584 634
585 TEST_EXPECTED_RANGE(RANGE_VALID, SrcLimits::min()); 635 TEST_EXPECTED_RANGE(RANGE_VALID, SrcLimits::min());
586 TEST_EXPECTED_RANGE(RANGE_OVERFLOW, SrcLimits::max()); 636 TEST_EXPECTED_RANGE(RANGE_OVERFLOW, SrcLimits::max());
587 TEST_EXPECTED_RANGE(RANGE_VALID, static_cast<Src>(1)); 637 TEST_EXPECTED_RANGE(RANGE_VALID, static_cast<Src>(1));
588 } 638 }
589 }; 639 };
(...skipping 157 matching lines...) Expand 10 before | Expand all | Expand 10 after
747 float not_a_number = std::numeric_limits<float>::infinity() - 797 float not_a_number = std::numeric_limits<float>::infinity() -
748 std::numeric_limits<float>::infinity(); 798 std::numeric_limits<float>::infinity();
749 EXPECT_TRUE(std::isnan(not_a_number)); 799 EXPECT_TRUE(std::isnan(not_a_number));
750 EXPECT_EQ(0, saturated_cast<int>(not_a_number)); 800 EXPECT_EQ(0, saturated_cast<int>(not_a_number));
751 801
752 // Test the CheckedNumeric value extractions functions. 802 // Test the CheckedNumeric value extractions functions.
753 auto int8_min = CheckNum(numeric_limits<int8_t>::min()); 803 auto int8_min = CheckNum(numeric_limits<int8_t>::min());
754 auto int8_max = CheckNum(numeric_limits<int8_t>::max()); 804 auto int8_max = CheckNum(numeric_limits<int8_t>::max());
755 auto double_max = CheckNum(numeric_limits<double>::max()); 805 auto double_max = CheckNum(numeric_limits<double>::max());
756 static_assert( 806 static_assert(
757 std::is_same<int16_t, decltype(int8_min.ValueOrDie<int16_t>())>::value, 807 std::is_same<int16_t,
808 decltype(int8_min.ValueOrDie<int16_t>())::type>::value,
758 "ValueOrDie returning incorrect type."); 809 "ValueOrDie returning incorrect type.");
759 static_assert( 810 static_assert(
760 std::is_same<int16_t, 811 std::is_same<int16_t,
761 decltype(int8_min.ValueOrDefault<int16_t>(0))>::value, 812 decltype(int8_min.ValueOrDefault<int16_t>(0))::type>::value,
762 "ValueOrDefault returning incorrect type."); 813 "ValueOrDefault returning incorrect type.");
763 static_assert( 814 static_assert(
764 std::is_same<float, decltype(double_max.ValueFloating<float>())>::value, 815 std::is_same<float,
816 decltype(double_max.ValueFloating<float>())::type>::value,
765 "ValueFloating returning incorrect type."); 817 "ValueFloating returning incorrect type.");
766 EXPECT_FALSE(int8_min.template IsValid<uint8_t>()); 818 EXPECT_FALSE(int8_min.template IsValid<uint8_t>());
767 EXPECT_TRUE(int8_max.template IsValid<uint8_t>()); 819 EXPECT_TRUE(int8_max.template IsValid<uint8_t>());
768 EXPECT_EQ(static_cast<int>(numeric_limits<int8_t>::min()), 820 EXPECT_EQ(static_cast<int>(numeric_limits<int8_t>::min()),
769 int8_min.template ValueOrDie<int>()); 821 int8_min.template ValueOrDie<int>());
770 EXPECT_TRUE(int8_max.template IsValid<uint32_t>()); 822 EXPECT_TRUE(int8_max.template IsValid<uint32_t>());
771 EXPECT_EQ(static_cast<int>(numeric_limits<int8_t>::max()), 823 EXPECT_EQ(static_cast<int>(numeric_limits<int8_t>::max()),
772 int8_max.template ValueOrDie<int>()); 824 int8_max.template ValueOrDie<int>());
773 uint8_t uint8_dest = 0; 825 uint8_t uint8_dest = 0;
774 int16_t int16_dest = 0; 826 int16_t int16_dest = 0;
(...skipping 114 matching lines...) Expand 10 before | Expand all | Expand 10 after
889 too_large += d; 941 too_large += d;
890 EXPECT_FALSE(too_large.IsValid()); 942 EXPECT_FALSE(too_large.IsValid());
891 too_large -= d; 943 too_large -= d;
892 EXPECT_FALSE(too_large.IsValid()); 944 EXPECT_FALSE(too_large.IsValid());
893 too_large /= d; 945 too_large /= d;
894 EXPECT_FALSE(too_large.IsValid()); 946 EXPECT_FALSE(too_large.IsValid());
895 } 947 }
896 948
897 TEST(SafeNumerics, VariadicNumericOperations) { 949 TEST(SafeNumerics, VariadicNumericOperations) {
898 auto a = CheckAdd(1, 2UL, CheckNum(3LL), 4).ValueOrDie(); 950 auto a = CheckAdd(1, 2UL, CheckNum(3LL), 4).ValueOrDie();
899 EXPECT_EQ(static_cast<decltype(a)>(10), a); 951 EXPECT_EQ(static_cast<decltype(a)::type>(10), a);
900 auto b = CheckSub(CheckNum(20.0), 2UL, 4).ValueOrDie(); 952 auto b = CheckSub(CheckNum(20.0), 2UL, 4).ValueOrDie();
901 EXPECT_EQ(static_cast<decltype(b)>(14.0), b); 953 EXPECT_EQ(static_cast<decltype(b)::type>(14.0), b);
902 auto c = CheckMul(20.0, CheckNum(1), 5, 3UL).ValueOrDie(); 954 auto c = CheckMul(20.0, CheckNum(1), 5, 3UL).ValueOrDie();
903 EXPECT_EQ(static_cast<decltype(c)>(300.0), c); 955 EXPECT_EQ(static_cast<decltype(c)::type>(300.0), c);
904 auto d = CheckDiv(20.0, 2.0, CheckNum(5LL), -4).ValueOrDie(); 956 auto d = CheckDiv(20.0, 2.0, CheckNum(5LL), -4).ValueOrDie();
905 EXPECT_EQ(static_cast<decltype(d)>(-.5), d); 957 EXPECT_EQ(static_cast<decltype(d)::type>(-.5), d);
906 auto e = CheckMod(CheckNum(20), 3).ValueOrDie(); 958 auto e = CheckMod(CheckNum(20), 3).ValueOrDie();
907 EXPECT_EQ(static_cast<decltype(e)>(2), e); 959 EXPECT_EQ(static_cast<decltype(e)::type>(2), e);
908 auto f = CheckLsh(1, CheckNum(2)).ValueOrDie(); 960 auto f = CheckLsh(1, CheckNum(2)).ValueOrDie();
909 EXPECT_EQ(static_cast<decltype(f)>(4), f); 961 EXPECT_EQ(static_cast<decltype(f)::type>(4), f);
910 auto g = CheckRsh(4, CheckNum(2)).ValueOrDie(); 962 auto g = CheckRsh(4, CheckNum(2)).ValueOrDie();
911 EXPECT_EQ(static_cast<decltype(g)>(1), g); 963 EXPECT_EQ(static_cast<decltype(g)::type>(1), g);
912 auto h = CheckRsh(CheckAdd(1, 1, 1, 1), CheckSub(4, 2)).ValueOrDie(); 964 auto h = CheckRsh(CheckAdd(1, 1, 1, 1), CheckSub(4, 2)).ValueOrDie();
913 EXPECT_EQ(static_cast<decltype(h)>(1), h); 965 EXPECT_EQ(static_cast<decltype(h)::type>(1), h);
914 } 966 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698