1 /*
2 	This file is part of solidity.
3 
4 	solidity is free software: you can redistribute it and/or modify
5 	it under the terms of the GNU General Public License as published by
6 	the Free Software Foundation, either version 3 of the License, or
7 	(at your option) any later version.
8 
9 	solidity is distributed in the hope that it will be useful,
10 	but WITHOUT ANY WARRANTY; without even the implied warranty of
11 	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12 	GNU General Public License for more details.
13 
14 	You should have received a copy of the GNU General Public License
15 	along with solidity.  If not, see <http://www.gnu.org/licenses/>.
16 */
17 // SPDX-License-Identifier: GPL-3.0
18 #include <test/tools/ossfuzz/yulFuzzerCommon.h>
19 
20 using namespace std;
21 using namespace solidity;
22 using namespace solidity::yul;
23 using namespace solidity::yul::test::yul_fuzzer;
24 
interpret(ostream & _os,shared_ptr<yul::Block> _ast,Dialect const & _dialect,bool _outputStorageOnly,size_t _maxSteps,size_t _maxTraceSize,size_t _maxExprNesting)25 yulFuzzerUtil::TerminationReason yulFuzzerUtil::interpret(
26 	ostream& _os,
27 	shared_ptr<yul::Block> _ast,
28 	Dialect const& _dialect,
29 	bool _outputStorageOnly,
30 	size_t _maxSteps,
31 	size_t _maxTraceSize,
32 	size_t _maxExprNesting
33 )
34 {
35 	InterpreterState state;
36 	state.maxTraceSize = _maxTraceSize;
37 	state.maxSteps = _maxSteps;
38 	state.maxExprNesting = _maxExprNesting;
39 	// Add 64 bytes of pseudo-randomly generated calldata so that
40 	// calldata opcodes perform non trivial work.
41 	state.calldata = {
42 		0xe9, 0x96, 0x40, 0x7d, 0xa5, 0xda, 0xb0, 0x2d,
43 		0x97, 0xf5, 0xc3, 0x44, 0xd7, 0x65, 0x0a, 0xd8,
44 		0x2c, 0x14, 0x3a, 0xf3, 0xe7, 0x40, 0x0f, 0x1e,
45 		0x67, 0xce, 0x90, 0x44, 0x2e, 0x92, 0xdb, 0x88,
46 		0xb8, 0x43, 0x9c, 0x41, 0x42, 0x08, 0xf1, 0xd7,
47 		0x65, 0xe9, 0x7f, 0xeb, 0x7b, 0xb9, 0x56, 0x9f,
48 		0xc7, 0x60, 0x5f, 0x7c, 0xcd, 0xfb, 0x92, 0xcd,
49 		0x8e, 0xf3, 0x9b, 0xe4, 0x4f, 0x6c, 0x14, 0xde
50 	};
51 
52 	TerminationReason reason = TerminationReason::None;
53 	try
54 	{
55 		Interpreter::run(state, _dialect, *_ast);
56 	}
57 	catch (StepLimitReached const&)
58 	{
59 		reason = TerminationReason::StepLimitReached;
60 	}
61 	catch (TraceLimitReached const&)
62 	{
63 		reason = TerminationReason::TraceLimitReached;
64 	}
65 	catch (ExpressionNestingLimitReached const&)
66 	{
67 		reason = TerminationReason::ExpresionNestingLimitReached;
68 	}
69 	catch (ExplicitlyTerminated const&)
70 	{
71 		reason = TerminationReason::ExplicitlyTerminated;
72 	}
73 
74 	if (_outputStorageOnly)
75 		state.dumpStorage(_os);
76 	else
77 		state.dumpTraceAndState(_os);
78 	return reason;
79 }
80 
resourceLimitsExceeded(TerminationReason _reason)81 bool yulFuzzerUtil::resourceLimitsExceeded(TerminationReason _reason)
82 {
83 	return
84 		_reason == yulFuzzerUtil::TerminationReason::StepLimitReached ||
85 		_reason == yulFuzzerUtil::TerminationReason::TraceLimitReached ||
86 		_reason == yulFuzzerUtil::TerminationReason::ExpresionNestingLimitReached;
87 }
88