Skip to content

Commit 93d42c5

Browse files
authored
Merge branch 'master' into overflow
2 parents 7f81d8f + 642ebda commit 93d42c5

19 files changed

+229
-200
lines changed

.clang-tidy

+64-64
Original file line numberDiff line numberDiff line change
@@ -1,70 +1,70 @@
11
FormatStyle: file
22
HeaderFilterRegex: 'lib/evmone/|test/state/'
33
WarningsAsErrors: '*'
4-
Checks: >
5-
bugprone-*,
6-
-bugprone-assignment-in-if-condition,
7-
-bugprone-easily-swappable-parameters,
8-
-bugprone-implicit-widening-of-multiplication-result,
9-
-bugprone-unchecked-optional-access,
10-
cert-dcl21-cpp,
11-
cert-dcl50-cpp,
12-
cert-dcl58-cpp,
13-
cert-env33-c,
14-
cert-err33-c,
15-
cert-err34-c,
16-
cert-err52-cpp,
17-
cert-err60-cpp,
18-
cert-flp30-c,
19-
cert-mem57-cpp,
20-
cert-msc50-cpp,
21-
cert-msc51-cpp,
22-
cert-oop57-cpp,
23-
cert-oop58-cpp,
24-
clang-analyzer-*,
25-
cppcoreguidelines-*,
26-
-cppcoreguidelines-avoid-c-arrays,
27-
-cppcoreguidelines-avoid-const-or-ref-data-members,
28-
-cppcoreguidelines-avoid-goto,
29-
-cppcoreguidelines-avoid-magic-numbers,
30-
-cppcoreguidelines-avoid-non-const-global-variables,
31-
-cppcoreguidelines-macro-usage,
32-
-cppcoreguidelines-no-malloc,
33-
-cppcoreguidelines-non-private-member-variables-in-classes,
34-
-cppcoreguidelines-owning-memory,
35-
-cppcoreguidelines-pro-bounds-array-to-pointer-decay,
36-
-cppcoreguidelines-pro-bounds-constant-array-index,
37-
-cppcoreguidelines-pro-bounds-pointer-arithmetic,
38-
-cppcoreguidelines-pro-type-reinterpret-cast,
39-
-cppcoreguidelines-pro-type-static-cast-downcast,
40-
-cppcoreguidelines-pro-type-union-access,
41-
-cppcoreguidelines-pro-type-vararg,
42-
-cppcoreguidelines-special-member-functions,
43-
google-global-names-in-headers,
44-
google-runtime-int,
45-
hicpp-exception-baseclass,
46-
hicpp-multiway-paths-covered,
47-
hicpp-no-assembler,
48-
misc-*,
49-
-misc-include-cleaner,
50-
-misc-non-private-member-variables-in-classes,
51-
-misc-use-anonymous-namespace,
52-
modernize-*,
53-
-modernize-avoid-c-arrays,
54-
-modernize-use-trailing-return-type,
55-
performance-*,
56-
-performance-enum-size,
57-
portability-*,
58-
readability-*,
59-
-readability-braces-around-statements,
60-
-readability-else-after-return,
61-
-readability-function-cognitive-complexity,
62-
-readability-function-size,
63-
-readability-identifier-length,
64-
-readability-magic-numbers,
65-
-readability-named-parameter,
66-
-readability-qualified-auto,
67-
-readability-uppercase-literal-suffix,
4+
Checks:
5+
- "bugprone-*"
6+
- "-bugprone-assignment-in-if-condition"
7+
- "-bugprone-easily-swappable-parameters"
8+
- "-bugprone-implicit-widening-of-multiplication-result"
9+
- "-bugprone-unchecked-optional-access"
10+
- "cert-dcl21-cpp"
11+
- "cert-dcl50-cpp"
12+
- "cert-dcl58-cpp"
13+
- "cert-env33-c"
14+
- "cert-err33-c"
15+
- "cert-err34-c"
16+
- "cert-err52-cpp"
17+
- "cert-err60-cpp"
18+
- "cert-flp30-c"
19+
- "cert-mem57-cpp"
20+
- "cert-msc50-cpp"
21+
- "cert-msc51-cpp"
22+
- "cert-oop57-cpp"
23+
- "cert-oop58-cpp"
24+
- "clang-analyzer-*"
25+
- "cppcoreguidelines-*"
26+
- "-cppcoreguidelines-avoid-c-arrays"
27+
- "-cppcoreguidelines-avoid-const-or-ref-data-members"
28+
- "-cppcoreguidelines-avoid-goto"
29+
- "-cppcoreguidelines-avoid-magic-numbers"
30+
- "-cppcoreguidelines-avoid-non-const-global-variables"
31+
- "-cppcoreguidelines-macro-usage"
32+
- "-cppcoreguidelines-no-malloc"
33+
- "-cppcoreguidelines-non-private-member-variables-in-classes"
34+
- "-cppcoreguidelines-owning-memory"
35+
- "-cppcoreguidelines-pro-bounds-array-to-pointer-decay"
36+
- "-cppcoreguidelines-pro-bounds-constant-array-index"
37+
- "-cppcoreguidelines-pro-bounds-pointer-arithmetic"
38+
- "-cppcoreguidelines-pro-type-reinterpret-cast"
39+
- "-cppcoreguidelines-pro-type-static-cast-downcast"
40+
- "-cppcoreguidelines-pro-type-union-access"
41+
- "-cppcoreguidelines-pro-type-vararg"
42+
- "-cppcoreguidelines-special-member-functions"
43+
- "google-global-names-in-headers"
44+
- "google-runtime-int"
45+
- "hicpp-exception-baseclass"
46+
- "hicpp-multiway-paths-covered"
47+
- "hicpp-no-assembler"
48+
- "misc-*"
49+
- "-misc-include-cleaner"
50+
- "-misc-non-private-member-variables-in-classes"
51+
- "-misc-use-anonymous-namespace"
52+
- "modernize-*"
53+
- "-modernize-avoid-c-arrays"
54+
- "-modernize-use-trailing-return-type"
55+
- "performance-*"
56+
- "-performance-enum-size"
57+
- "portability-*"
58+
- "readability-*"
59+
- "-readability-braces-around-statements"
60+
- "-readability-else-after-return"
61+
- "-readability-function-cognitive-complexity"
62+
- "-readability-function-size"
63+
- "-readability-identifier-length"
64+
- "-readability-magic-numbers"
65+
- "-readability-named-parameter"
66+
- "-readability-qualified-auto"
67+
- "-readability-uppercase-literal-suffix"
6868

6969
CheckOptions:
7070
readability-identifier-naming.ClassCase: CamelCase

lib/evmone/advanced_analysis.hpp

+16-51
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
#pragma once
55

66
#include "execution_state.hpp"
7+
#include "instructions.hpp"
78
#include "instructions_opcodes.hpp"
89
#include <evmc/evmc.hpp>
910
#include <evmc/utils.h>
@@ -30,74 +31,38 @@ struct BlockInfo
3031
};
3132
static_assert(sizeof(BlockInfo) == 8);
3233

33-
/// The view/controller for EVM stack.
34-
class Stack
35-
{
36-
public:
37-
/// The pointer to the top item.
38-
/// This is never null.
39-
uint256* top_item = nullptr;
40-
41-
private:
42-
/// The pointer to the stack space "bottom".
43-
uint256* m_bottom = nullptr;
44-
45-
public:
46-
/// Init with the provided stack space.
47-
explicit Stack(uint256* stack_space_bottom) noexcept { reset(stack_space_bottom); }
48-
49-
/// The current number of items on the stack.
50-
[[nodiscard]] int size() const noexcept { return static_cast<int>(top_item - m_bottom); }
51-
52-
/// Returns the reference to the top item.
53-
// NOLINTNEXTLINE(readability-make-member-function-const)
54-
[[nodiscard]] uint256& top() noexcept { return *top_item; }
55-
56-
/// Returns the reference to the stack item on given position from the stack top.
57-
// NOLINTNEXTLINE(readability-make-member-function-const)
58-
[[nodiscard]] uint256& operator[](int index) noexcept { return *(top_item - index); }
59-
60-
/// Returns the const reference to the stack item on given position from the stack top.
61-
[[nodiscard]] const uint256& operator[](int index) const noexcept
62-
{
63-
return *(top_item - index);
64-
}
65-
66-
/// Pushes an item on the stack. The stack limit is not checked.
67-
void push(const uint256& item) noexcept { *++top_item = item; }
68-
69-
/// Returns an item popped from the top of the stack.
70-
uint256 pop() noexcept { return *top_item--; }
71-
72-
/// Empties the stack by resetting the top item pointer to the new provided stack space.
73-
void reset(uint256* stack_space_bottom) noexcept
74-
{
75-
m_bottom = stack_space_bottom;
76-
top_item = m_bottom;
77-
}
78-
};
7934

8035
/// The execution state specialized for the Advanced interpreter.
8136
struct AdvancedExecutionState : ExecutionState
8237
{
8338
int64_t gas_left = 0;
84-
Stack stack;
39+
40+
/// Pointer to the stack top.
41+
StackTop stack = stack_space.bottom();
8542

8643
/// The gas cost of the current block.
8744
///
8845
/// This is only needed to correctly calculate the "current gas left" value.
8946
uint32_t current_block_cost = 0;
9047

91-
AdvancedExecutionState() noexcept : stack{stack_space.bottom()} {}
48+
AdvancedExecutionState() noexcept = default;
9249

9350
AdvancedExecutionState(const evmc_message& message, evmc_revision revision,
9451
const evmc_host_interface& host_interface, evmc_host_context* host_ctx, bytes_view _code,
9552
bytes_view _data) noexcept
9653
: ExecutionState{message, revision, host_interface, host_ctx, _code, _data},
97-
gas_left{message.gas},
98-
stack{stack_space.bottom()}
54+
gas_left{message.gas}
9955
{}
10056

57+
/// Computes the current EVM stack height.
58+
[[nodiscard]] int stack_size() noexcept
59+
{
60+
return static_cast<int>((&stack.top() - stack_space.bottom()));
61+
}
62+
63+
/// Adjust the EVM stack height by given change.
64+
void adjust_stack_size(int change) noexcept { stack = &stack.top() + change; }
65+
10166
/// Terminates the execution with the given status code.
10267
const Instruction* exit(evmc_status_code status_code) noexcept
10368
{
@@ -112,7 +77,7 @@ struct AdvancedExecutionState : ExecutionState
11277
{
11378
ExecutionState::reset(message, revision, host_interface, host_ctx, _code, _data);
11479
gas_left = message.gas;
115-
stack.reset(stack_space.bottom());
80+
stack = stack_space.bottom();
11681
analysis.advanced = nullptr; // For consistency with previous behavior.
11782
current_block_cost = 0;
11883
}

lib/evmone/advanced_instructions.cpp

+22-23
Original file line numberDiff line numberDiff line change
@@ -17,40 +17,40 @@ using namespace evmone::instr;
1717
template <Opcode Op, void CoreFn(StackTop) noexcept = core::impl<Op>>
1818
inline void impl(AdvancedExecutionState& state) noexcept
1919
{
20-
CoreFn(state.stack.top_item);
21-
state.stack.top_item += instr::traits[Op].stack_height_change;
20+
CoreFn(state.stack);
21+
state.adjust_stack_size(instr::traits[Op].stack_height_change);
2222
}
2323

2424
template <Opcode Op, void CoreFn(StackTop, ExecutionState&) noexcept = core::impl<Op>>
2525
inline void impl(AdvancedExecutionState& state) noexcept
2626
{
27-
CoreFn(state.stack.top_item, state);
28-
state.stack.top_item += instr::traits[Op].stack_height_change;
27+
CoreFn(state.stack, state);
28+
state.adjust_stack_size(instr::traits[Op].stack_height_change);
2929
}
3030

3131
template <Opcode Op, evmc_status_code CoreFn(StackTop, ExecutionState&) noexcept = core::impl<Op>>
3232
inline evmc_status_code impl(AdvancedExecutionState& state) noexcept
3333
{
34-
const auto status = CoreFn(state.stack.top_item, state);
35-
state.stack.top_item += instr::traits[Op].stack_height_change;
34+
const auto status = CoreFn(state.stack, state);
35+
state.adjust_stack_size(instr::traits[Op].stack_height_change);
3636
return status;
3737
}
3838

3939
template <Opcode Op,
4040
evmc_status_code CoreFn(StackTop, int64_t&, ExecutionState&) noexcept = core::impl<Op>>
4141
inline evmc_status_code impl(AdvancedExecutionState& state) noexcept
4242
{
43-
const auto status = CoreFn(state.stack.top_item, state.gas_left, state);
44-
state.stack.top_item += instr::traits[Op].stack_height_change;
43+
const auto status = CoreFn(state.stack, state.gas_left, state);
44+
state.adjust_stack_size(instr::traits[Op].stack_height_change);
4545
return status;
4646
}
4747

4848
template <Opcode Op, Result CoreFn(StackTop, int64_t, ExecutionState&) noexcept = core::impl<Op>>
4949
inline evmc_status_code impl(AdvancedExecutionState& state) noexcept
5050
{
51-
const auto status = CoreFn(state.stack.top_item, state.gas_left, state);
51+
const auto status = CoreFn(state.stack, state.gas_left, state);
5252
state.gas_left = status.gas_left;
53-
state.stack.top_item += instr::traits[Op].stack_height_change;
53+
state.adjust_stack_size(instr::traits[Op].stack_height_change);
5454
return status.status;
5555
}
5656

@@ -59,39 +59,39 @@ template <Opcode Op,
5959
inline TermResult impl(AdvancedExecutionState& state) noexcept
6060
{
6161
// Stack height adjustment may be omitted.
62-
return CoreFn(state.stack.top_item, state.gas_left, state);
62+
return CoreFn(state.stack, state.gas_left, state);
6363
}
6464

6565
template <Opcode Op,
6666
Result CoreFn(StackTop, int64_t, ExecutionState&, code_iterator&) noexcept = core::impl<Op>>
6767
inline Result impl(AdvancedExecutionState& state, code_iterator pos) noexcept
6868
{
6969
// Stack height adjustment may be omitted.
70-
return CoreFn(state.stack.top_item, state.gas_left, state, pos);
70+
return CoreFn(state.stack, state.gas_left, state, pos);
7171
}
7272

7373
template <Opcode Op,
7474
TermResult CoreFn(StackTop, int64_t, ExecutionState&, code_iterator) noexcept = core::impl<Op>>
7575
inline TermResult impl(AdvancedExecutionState& state, code_iterator pos) noexcept
7676
{
7777
// Stack height adjustment may be omitted.
78-
return CoreFn(state.stack.top_item, state.gas_left, state, pos);
78+
return CoreFn(state.stack, state.gas_left, state, pos);
7979
}
8080

8181
template <Opcode Op,
8282
code_iterator CoreFn(StackTop, ExecutionState&, code_iterator) noexcept = core::impl<Op>>
8383
inline code_iterator impl(AdvancedExecutionState& state, code_iterator pos) noexcept
8484
{
85-
const auto new_pos = CoreFn(state.stack.top_item, state, pos);
86-
state.stack.top_item += instr::traits[Op].stack_height_change;
85+
const auto new_pos = CoreFn(state.stack, state, pos);
86+
state.adjust_stack_size(instr::traits[Op].stack_height_change);
8787
return new_pos;
8888
}
8989

9090
template <Opcode Op, code_iterator CoreFn(StackTop, code_iterator) noexcept = core::impl<Op>>
9191
inline code_iterator impl(AdvancedExecutionState& state, code_iterator pos) noexcept
9292
{
93-
const auto new_pos = CoreFn(state.stack.top_item, pos);
94-
state.stack.top_item += instr::traits[Op].stack_height_change;
93+
const auto new_pos = CoreFn(state.stack, pos);
94+
state.adjust_stack_size(instr::traits[Op].stack_height_change);
9595
return new_pos;
9696
}
9797
/// @}
@@ -163,10 +163,9 @@ const Instruction* opx_beginblock(const Instruction* instr, AdvancedExecutionSta
163163
if ((state.gas_left -= block.gas_cost) < 0)
164164
return state.exit(EVMC_OUT_OF_GAS);
165165

166-
if (static_cast<int>(state.stack.size()) < block.stack_req)
166+
if (const auto stack_size = state.stack_size(); stack_size < block.stack_req)
167167
return state.exit(EVMC_STACK_UNDERFLOW);
168-
169-
if (static_cast<int>(state.stack.size()) + block.stack_max_growth > StackSpace::limit)
168+
else if (stack_size + block.stack_max_growth > StackSpace::limit)
170169
return state.exit(EVMC_STACK_OVERFLOW);
171170

172171
state.current_block_cost = block.gas_cost;
@@ -189,12 +188,12 @@ const Instruction* op_jumpi(const Instruction* instr, AdvancedExecutionState& st
189188
if (state.stack[1] != 0)
190189
{
191190
instr = op_jump(instr, state); // target
192-
state.stack.pop(); // condition
191+
(void)state.stack.pop(); // condition
193192
}
194193
else
195194
{
196-
state.stack.pop(); // target
197-
state.stack.pop(); // condition
195+
(void)state.stack.pop(); // target
196+
(void)state.stack.pop(); // condition
198197
instr = opx_beginblock(instr, state); // follow-by block
199198
}
200199
return instr;

lib/evmone/baseline.hpp

+1-3
Original file line numberDiff line numberDiff line change
@@ -7,13 +7,11 @@
77
#include <evmc/evmc.h>
88
#include <evmc/utils.h>
99
#include <memory>
10-
#include <string_view>
1110
#include <vector>
1211

1312
namespace evmone
1413
{
15-
using bytes_view = std::basic_string_view<uint8_t>;
16-
14+
using evmc::bytes_view;
1715
class ExecutionState;
1816
class VM;
1917

0 commit comments

Comments
 (0)