Branch data Line data Source code
1 : : // Copyright (c) 2022-present 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 <test/fuzz/FuzzedDataProvider.h>
6 : : #include <test/fuzz/fuzz.h>
7 : : #include <test/fuzz/util.h>
8 : : #include <test/util/setup_common.h>
9 : : #include <wallet/coincontrol.h>
10 : : #include <wallet/test/util.h>
11 : :
12 : : namespace wallet {
13 : : namespace {
14 : :
15 : : const TestingSetup* g_setup;
16 : :
17 : 1 : void initialize_coincontrol()
18 : : {
19 [ + - + - : 1 : static const auto testing_setup = MakeNoLogFileContext<const TestingSetup>();
+ - ]
20 : 1 : g_setup = testing_setup.get();
21 : 1 : }
22 : :
23 [ + - ]: 1274 : FUZZ_TARGET(coincontrol, .init = initialize_coincontrol)
24 : : {
25 : 798 : FuzzedDataProvider fuzzed_data_provider(buffer.data(), buffer.size());
26 : 798 : const auto& node = g_setup->m_node;
27 : 798 : ArgsManager& args = *node.args;
28 : :
29 : : // for GetBoolArg to return true sometimes
30 [ + + + - : 1827 : args.ForceSetArg("-avoidpartialspends", fuzzed_data_provider.ConsumeBool()?"1":"0");
+ - ]
31 : :
32 : 798 : CCoinControl coin_control;
33 : 798 : COutPoint out_point;
34 : :
35 [ + + + + ]: 532530 : LIMITED_WHILE (fuzzed_data_provider.ConsumeBool(), 10000) {
36 [ + - ]: 531732 : CallOneOf(
37 : : fuzzed_data_provider,
38 : 22892 : [&] {
39 : 22892 : std::optional<COutPoint> optional_out_point = ConsumeDeserializable<COutPoint>(fuzzed_data_provider);
40 [ + + ]: 22892 : if (!optional_out_point) {
41 : : return;
42 : : }
43 : 5700 : out_point = *optional_out_point;
44 : : },
45 : 27596 : [&] {
46 : 27596 : (void)coin_control.HasSelected();
47 : 27596 : },
48 : 5495 : [&] {
49 : 5495 : (void)coin_control.IsSelected(out_point);
50 : 5495 : },
51 : 13952 : [&] {
52 : 13952 : (void)coin_control.IsExternalSelected(out_point);
53 : 13952 : },
54 : 69609 : [&] {
55 : 69609 : (void)coin_control.GetExternalOutput(out_point);
56 : 69609 : },
57 : 62186 : [&] {
58 : 62186 : (void)coin_control.Select(out_point);
59 [ - + ]: 62186 : assert(coin_control.IsSelected(out_point));
60 : 62186 : },
61 : 23972 : [&] {
62 [ + - ]: 23972 : const CTxOut tx_out{ConsumeMoney(fuzzed_data_provider), ConsumeScript(fuzzed_data_provider)};
63 [ + - ]: 23972 : auto& input = coin_control.Select(out_point);
64 : 23972 : const auto set_tx_out{fuzzed_data_provider.ConsumeBool()};
65 [ + + ]: 23972 : if (set_tx_out) {
66 [ + - ]: 21035 : input.SetTxOut(tx_out);
67 : : }
68 [ + - ]: 23972 : auto has_tx_out{input.HasTxOut()};
69 [ + - ]: 23972 : auto is_external_selected{coin_control.IsExternalSelected(out_point)};
70 [ + + ]: 23972 : if (set_tx_out) {
71 [ - + ]: 21035 : assert(has_tx_out);
72 [ + - - + ]: 21035 : assert(input.GetTxOut() == tx_out);
73 [ - + ]: 21035 : assert(is_external_selected);
74 [ + + ]: 2937 : } else if (!has_tx_out) {
75 [ - + ]: 704 : assert(!is_external_selected);
76 : : }
77 : 23972 : },
78 : 29558 : [&] {
79 : 29558 : coin_control.UnSelect(out_point);
80 [ - + ]: 29558 : assert(!coin_control.IsSelected(out_point));
81 : 29558 : },
82 : 24727 : [&] {
83 : 24727 : coin_control.UnSelectAll();
84 [ - + ]: 24727 : assert(!coin_control.HasSelected());
85 : 24727 : },
86 : 5163 : [&] {
87 : 5163 : const std::vector<COutPoint> selected = coin_control.ListSelected();
88 [ + + ]: 15243 : for (const auto& out : selected) {
89 [ + - - + ]: 10080 : assert(coin_control.IsSelected(out));
90 : : }
91 : 5163 : },
92 : 7521 : [&] {
93 : 7521 : int64_t weight{fuzzed_data_provider.ConsumeIntegral<int64_t>()};
94 : 7521 : coin_control.SetInputWeight(out_point, weight);
95 [ + - ]: 7521 : assert(coin_control.GetInputWeight(out_point) == weight);
96 : 7521 : },
97 : 7085 : [&] {
98 : 7085 : const bool is_selected = coin_control.IsSelected(out_point);
99 [ + + - + ]: 7085 : assert(!coin_control.GetInputWeight(out_point) || is_selected);
100 [ + + - + ]: 7085 : assert(!coin_control.GetSequence(out_point) || is_selected);
101 : 7085 : },
102 : 79727 : [&] {
103 : 79727 : const auto scripts = coin_control.GetScripts(out_point);
104 [ + - + + : 79727 : assert(coin_control.IsSelected(out_point) || (!scripts.first && !scripts.second));
+ - - + ]
105 : 79727 : },
106 : 27522 : [&] {
107 [ + + - + ]: 27522 : assert(coin_control.HasSelectedOrder() || !coin_control.GetSelectionPos(out_point));
108 : 27522 : },
109 : 13150 : [&] {
110 [ + + - + ]: 13150 : assert(!coin_control.GetSelectionPos(out_point) || coin_control.IsSelected(out_point));
111 : 13150 : },
112 : 30996 : [&] {
113 : 30996 : auto& input = coin_control.Select(out_point);
114 : 30996 : uint32_t sequence{fuzzed_data_provider.ConsumeIntegral<uint32_t>()};
115 : 30996 : input.SetSequence(sequence);
116 [ + - ]: 30996 : assert(input.GetSequence() == sequence);
117 [ + - ]: 30996 : assert(coin_control.GetSequence(out_point) == sequence);
118 : 30996 : },
119 : 51669 : [&] {
120 : 51669 : auto& input = coin_control.Select(out_point);
121 : 51669 : const CScript script{ConsumeScript(fuzzed_data_provider)};
122 [ + - ]: 51669 : input.SetScriptSig(script);
123 [ + - - + ]: 51669 : assert(input.HasScripts());
124 [ + - - + ]: 51669 : assert(input.GetScripts().first == script);
125 [ + - - + ]: 103338 : assert(coin_control.GetScripts(out_point).first == script);
126 : 51669 : },
127 : 23903 : [&] {
128 : 23903 : auto& input = coin_control.Select(out_point);
129 : 23903 : const CScriptWitness script_wit{ConsumeScriptWitness(fuzzed_data_provider)};
130 [ + - ]: 23903 : input.SetScriptWitness(script_wit);
131 [ + - - + ]: 23903 : assert(input.HasScripts());
132 [ + - - + ]: 23903 : assert(input.GetScripts().second->stack == script_wit.stack);
133 [ + - - + ]: 47806 : assert(coin_control.GetScripts(out_point).second->stack == script_wit.stack);
134 : 23903 : },
135 : 5009 : [&] {
136 : 5009 : auto& input = coin_control.Select(out_point);
137 : 5009 : unsigned int pos{fuzzed_data_provider.ConsumeIntegral<unsigned int>()};
138 : 5009 : input.SetPosition(pos);
139 [ + - ]: 5009 : assert(input.GetPosition() == pos);
140 [ + - ]: 5009 : assert(coin_control.GetSelectionPos(out_point) == pos);
141 : 5009 : });
142 : : }
143 : 798 : }
144 : : } // namespace
145 : : } // namespace wallet
|