/root/bitcoin/src/test/fuzz/strprintf.cpp
Line | Count | Source (jump to first uncovered line) |
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 <test/fuzz/FuzzedDataProvider.h> |
6 | | #include <test/fuzz/fuzz.h> |
7 | | #include <test/fuzz/util.h> |
8 | | #include <tinyformat.h> |
9 | | #include <util/strencodings.h> |
10 | | #include <util/translation.h> |
11 | | |
12 | | #include <algorithm> |
13 | | #include <cstdint> |
14 | | #include <string> |
15 | | #include <vector> |
16 | | |
17 | | template <typename... Args> |
18 | | void fuzz_fmt(const std::string& fmt, const Args&... args) |
19 | 0 | { |
20 | 0 | (void)tfm::format(tfm::RuntimeFormat{fmt}, args...); |
21 | 0 | } Unexecuted instantiation: _Z8fuzz_fmtIJNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEEvRKS5_DpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJPKcEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJaEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJhEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJcEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJbEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJfEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJdEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJsEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJtEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJiEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJjEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJlEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ Unexecuted instantiation: _Z8fuzz_fmtIJmEEvRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEDpRKT_ |
22 | | |
23 | | FUZZ_TARGET(str_printf) |
24 | 0 | { |
25 | 0 | FuzzedDataProvider fuzzed_data_provider(buffer.data(), buffer.size()); |
26 | 0 | const std::string format_string = fuzzed_data_provider.ConsumeRandomLengthString(64); |
27 | |
|
28 | 0 | const int digits_in_format_specifier = std::count_if(format_string.begin(), format_string.end(), IsDigit); |
29 | | |
30 | | // Avoid triggering the following crash bug: |
31 | | // * strprintf("%987654321000000:", 1); |
32 | | // |
33 | | // Avoid triggering the following OOM bug: |
34 | | // * strprintf("%.222222200000000$", 1.1); |
35 | | // |
36 | | // Upstream bug report: https://github.com/c42f/tinyformat/issues/70 |
37 | 0 | if (format_string.find('%') != std::string::npos && digits_in_format_specifier >= 7) { |
38 | 0 | return; |
39 | 0 | } |
40 | | |
41 | | // Avoid triggering the following crash bug: |
42 | | // * strprintf("%1$*1$*", -11111111); |
43 | | // |
44 | | // Upstream bug report: https://github.com/c42f/tinyformat/issues/70 |
45 | 0 | if (format_string.find('%') != std::string::npos && format_string.find('$') != std::string::npos && format_string.find('*') != std::string::npos && digits_in_format_specifier > 0) { |
46 | 0 | return; |
47 | 0 | } |
48 | | |
49 | | // Avoid triggering the following crash bug: |
50 | | // * strprintf("%.1s", (char*)nullptr); |
51 | | // |
52 | | // (void)strprintf(format_string, (char*)nullptr); |
53 | | // |
54 | | // Upstream bug report: https://github.com/c42f/tinyformat/issues/70 |
55 | | |
56 | 0 | try { |
57 | 0 | CallOneOf( |
58 | 0 | fuzzed_data_provider, |
59 | 0 | [&] { |
60 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeRandomLengthString(32)); |
61 | 0 | }, |
62 | 0 | [&] { |
63 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeRandomLengthString(32).c_str()); |
64 | 0 | }, |
65 | 0 | [&] { |
66 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeIntegral<signed char>()); |
67 | 0 | }, |
68 | 0 | [&] { |
69 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeIntegral<unsigned char>()); |
70 | 0 | }, |
71 | 0 | [&] { |
72 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeIntegral<char>()); |
73 | 0 | }, |
74 | 0 | [&] { |
75 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeBool()); |
76 | 0 | }); |
77 | 0 | } catch (const tinyformat::format_error&) { |
78 | 0 | } |
79 | |
|
80 | 0 | if (format_string.find('%') != std::string::npos && format_string.find('c') != std::string::npos) { |
81 | | // Avoid triggering the following: |
82 | | // * strprintf("%c", 1.31783e+38); |
83 | | // tinyformat.h:244:36: runtime error: 1.31783e+38 is outside the range of representable values of type 'char' |
84 | 0 | return; |
85 | 0 | } |
86 | | |
87 | 0 | if (format_string.find('%') != std::string::npos && format_string.find('*') != std::string::npos) { |
88 | | // Avoid triggering the following: |
89 | | // * strprintf("%*", -2.33527e+38); |
90 | | // tinyformat.h:283:65: runtime error: -2.33527e+38 is outside the range of representable values of type 'int' |
91 | | // * strprintf("%*", -2147483648); |
92 | | // tinyformat.h:763:25: runtime error: negation of -2147483648 cannot be represented in type 'int'; cast to an unsigned type to negate this value to itself |
93 | 0 | return; |
94 | 0 | } |
95 | | |
96 | 0 | try { |
97 | 0 | CallOneOf( |
98 | 0 | fuzzed_data_provider, |
99 | 0 | [&] { |
100 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeFloatingPoint<float>()); |
101 | 0 | }, |
102 | 0 | [&] { |
103 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeFloatingPoint<double>()); |
104 | 0 | }, |
105 | 0 | [&] { |
106 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeIntegral<int16_t>()); |
107 | 0 | }, |
108 | 0 | [&] { |
109 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeIntegral<uint16_t>()); |
110 | 0 | }, |
111 | 0 | [&] { |
112 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeIntegral<int32_t>()); |
113 | 0 | }, |
114 | 0 | [&] { |
115 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeIntegral<uint32_t>()); |
116 | 0 | }, |
117 | 0 | [&] { |
118 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeIntegral<int64_t>()); |
119 | 0 | }, |
120 | 0 | [&] { |
121 | 0 | fuzz_fmt(format_string, fuzzed_data_provider.ConsumeIntegral<uint64_t>()); |
122 | 0 | }); |
123 | 0 | } catch (const tinyformat::format_error&) { |
124 | 0 | } |
125 | 0 | } |