Branch data Line data Source code
1 : : // Copyright (c) 2020-2021 The Bitcoin Core developers
2 : : // Distributed under the MIT software license, see the accompanying
3 : : // file COPYING or http://www.opensource.org/licenses/mit-license.php.
4 : :
5 : : #include <script/script.h>
6 : : #include <test/fuzz/FuzzedDataProvider.h>
7 : : #include <test/fuzz/fuzz.h>
8 : : #include <test/fuzz/util.h>
9 : :
10 : : #include <cassert>
11 : : #include <cstdint>
12 : : #include <limits>
13 : : #include <vector>
14 : :
15 : : namespace {
16 : 288976 : bool IsValidAddition(const CScriptNum& lhs, const CScriptNum& rhs)
17 : : {
18 [ + + + + : 288976 : return rhs == 0 || (rhs > 0 && lhs <= CScriptNum{std::numeric_limits<int64_t>::max()} - rhs) || (rhs < 0 && lhs >= CScriptNum{std::numeric_limits<int64_t>::min()} - rhs);
+ + + + +
+ ]
19 : : }
20 : :
21 : 301161 : bool IsValidSubtraction(const CScriptNum& lhs, const CScriptNum& rhs)
22 : : {
23 [ + + + + : 301161 : return rhs == 0 || (rhs > 0 && lhs >= CScriptNum{std::numeric_limits<int64_t>::min()} + rhs) || (rhs < 0 && lhs <= CScriptNum{std::numeric_limits<int64_t>::max()} + rhs);
+ + + + +
+ ]
24 : : }
25 : : } // namespace
26 : :
27 [ + - ]: 587 : FUZZ_TARGET(scriptnum_ops)
28 : : {
29 : 175 : FuzzedDataProvider fuzzed_data_provider(buffer.data(), buffer.size());
30 : 175 : CScriptNum script_num = ConsumeScriptNum(fuzzed_data_provider);
31 [ + + + - ]: 440000 : LIMITED_WHILE(fuzzed_data_provider.remaining_bytes() > 0, 1000000) {
32 : 439825 : CallOneOf(
33 : : fuzzed_data_provider,
34 : 227995 : [&] {
35 : 227995 : const int64_t i = fuzzed_data_provider.ConsumeIntegral<int64_t>();
36 [ - + ]: 227995 : assert((script_num == i) != (script_num != i));
37 [ - + ]: 227995 : assert((script_num <= i) != (script_num > i));
38 [ - + ]: 227995 : assert((script_num >= i) != (script_num < i));
39 : : // Avoid signed integer overflow:
40 : : // script/script.h:264:93: runtime error: signed integer overflow: -2261405121394637306 + -9223372036854775802 cannot be represented in type 'long'
41 [ + + ]: 227995 : if (IsValidAddition(script_num, CScriptNum{i})) {
42 : 105435 : assert((script_num + i) - i == script_num);
43 : : }
44 : : // Avoid signed integer overflow:
45 : : // script/script.h:265:93: runtime error: signed integer overflow: 9223371895120855039 - -9223372036854710486 cannot be represented in type 'long'
46 [ + + ]: 227995 : if (IsValidSubtraction(script_num, CScriptNum{i})) {
47 : 133800 : assert((script_num - i) + i == script_num);
48 : : }
49 : 227995 : },
50 : 12629 : [&] {
51 : 12629 : const CScriptNum random_script_num = ConsumeScriptNum(fuzzed_data_provider);
52 [ - + ]: 12629 : assert((script_num == random_script_num) != (script_num != random_script_num));
53 [ - + ]: 12629 : assert((script_num <= random_script_num) != (script_num > random_script_num));
54 [ - + ]: 12629 : assert((script_num >= random_script_num) != (script_num < random_script_num));
55 : : // Avoid signed integer overflow:
56 : : // script/script.h:264:93: runtime error: signed integer overflow: -9223126527765971126 + -9223372036854756825 cannot be represented in type 'long'
57 [ + + ]: 12629 : if (IsValidAddition(script_num, random_script_num)) {
58 : 8133 : assert((script_num + random_script_num) - random_script_num == script_num);
59 : : }
60 : : // Avoid signed integer overflow:
61 : : // script/script.h:265:93: runtime error: signed integer overflow: 6052837899185946624 - -9223372036854775808 cannot be represented in type 'long'
62 [ + + ]: 12629 : if (IsValidSubtraction(script_num, random_script_num)) {
63 : 8643 : assert((script_num - random_script_num) + random_script_num == script_num);
64 : : }
65 : 12629 : },
66 : 30102 : [&] {
67 : 30102 : const CScriptNum random_script_num = ConsumeScriptNum(fuzzed_data_provider);
68 [ + + ]: 30102 : if (!IsValidAddition(script_num, random_script_num)) {
69 : : // Avoid assertion failure:
70 : : // ./script/script.h:292: CScriptNum &CScriptNum::operator+=(const int64_t &): Assertion `rhs == 0 || (rhs > 0 && m_value <= std::numeric_limits<int64_t>::max() - rhs) || (rhs < 0 && m_value >= std::numeric_limits<int64_t>::min() - rhs)' failed.
71 : : return;
72 : : }
73 : 22236 : script_num += random_script_num;
74 : : },
75 : 43543 : [&] {
76 : 43543 : const CScriptNum random_script_num = ConsumeScriptNum(fuzzed_data_provider);
77 [ + + ]: 43543 : if (!IsValidSubtraction(script_num, random_script_num)) {
78 : : // Avoid assertion failure:
79 : : // ./script/script.h:300: CScriptNum &CScriptNum::operator-=(const int64_t &): Assertion `rhs == 0 || (rhs > 0 && m_value >= std::numeric_limits<int64_t>::min() + rhs) || (rhs < 0 && m_value <= std::numeric_limits<int64_t>::max() + rhs)' failed.
80 : : return;
81 : : }
82 : 21543 : script_num -= random_script_num;
83 : : },
84 : 10365 : [&] {
85 : 10365 : script_num = script_num & fuzzed_data_provider.ConsumeIntegral<int64_t>();
86 : 10365 : },
87 : 9108 : [&] {
88 : 9108 : script_num = script_num & ConsumeScriptNum(fuzzed_data_provider);
89 : 9108 : },
90 : 8271 : [&] {
91 : 8271 : script_num &= ConsumeScriptNum(fuzzed_data_provider);
92 : 8271 : },
93 : 43685 : [&] {
94 [ + + ]: 43685 : if (script_num == CScriptNum{std::numeric_limits<int64_t>::min()}) {
95 : : // Avoid assertion failure:
96 : : // ./script/script.h:279: CScriptNum CScriptNum::operator-() const: Assertion `m_value != std::numeric_limits<int64_t>::min()' failed.
97 : : return;
98 : : }
99 : 42187 : script_num = -script_num;
100 : : },
101 : 12986 : [&] {
102 : 12986 : script_num = fuzzed_data_provider.ConsumeIntegral<int64_t>();
103 : 12986 : },
104 : 18250 : [&] {
105 : 18250 : const int64_t random_integer = fuzzed_data_provider.ConsumeIntegral<int64_t>();
106 [ + + ]: 18250 : if (!IsValidAddition(script_num, CScriptNum{random_integer})) {
107 : : // Avoid assertion failure:
108 : : // ./script/script.h:292: CScriptNum &CScriptNum::operator+=(const int64_t &): Assertion `rhs == 0 || (rhs > 0 && m_value <= std::numeric_limits<int64_t>::max() - rhs) || (rhs < 0 && m_value >= std::numeric_limits<int64_t>::min() - rhs)' failed.
109 : : return;
110 : : }
111 : 13181 : script_num += random_integer;
112 : : },
113 : 16994 : [&] {
114 : 16994 : const int64_t random_integer = fuzzed_data_provider.ConsumeIntegral<int64_t>();
115 [ + + ]: 16994 : if (!IsValidSubtraction(script_num, CScriptNum{random_integer})) {
116 : : // Avoid assertion failure:
117 : : // ./script/script.h:300: CScriptNum &CScriptNum::operator-=(const int64_t &): Assertion `rhs == 0 || (rhs > 0 && m_value >= std::numeric_limits<int64_t>::min() + rhs) || (rhs < 0 && m_value <= std::numeric_limits<int64_t>::max() + rhs)' failed.
118 : : return;
119 : : }
120 : 9959 : script_num -= random_integer;
121 : : },
122 : 5897 : [&] {
123 : 5897 : script_num &= fuzzed_data_provider.ConsumeIntegral<int64_t>();
124 : 5897 : });
125 : 439825 : (void)script_num.getint();
126 : 439825 : (void)script_num.getvch();
127 : : }
128 : 175 : }
|