Skip to content

Commit 5c35857

Browse files
authored
Merge pull request #307 from scratchcpp/reg_count_limit
Fix #178: Remove register count limit
2 parents 043704a + 4e41f1e commit 5c35857

File tree

3 files changed

+44
-9
lines changed

3 files changed

+44
-9
lines changed

src/engine/virtualmachine_p.cpp

Lines changed: 14 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -10,11 +10,16 @@
1010
#include "virtualmachine_p.h"
1111
#include "internal/randomgenerator.h"
1212

13-
#define MAX_REG_COUNT 1024
14-
1513
#define DISPATCH() goto *dispatch_table[*++pos]
1614
#define FREE_REGS(count) regCount -= count
17-
#define ADD_RET_VALUE(value) *regs[regCount++] = value
15+
#define ADD_RET_VALUE(value) \
16+
if (regCount + 1 >= regsVector.size()) { \
17+
regsVector.reserve(regsVector.size() + 1024); \
18+
for (size_t i = 0; i < 1024; i++) \
19+
regsVector.push_back(new Value()); \
20+
regs = regsVector.data(); \
21+
} \
22+
*regs[regCount++] = value
1823
#define REPLACE_RET_VALUE(value, offset) *regs[regCount - offset] = value
1924
#define GET_NEXT_ARG() constValues[*++pos]
2025
#define READ_REG(index, count) regs[regCount - count + index]
@@ -103,9 +108,10 @@ VirtualMachinePrivate::VirtualMachinePrivate(VirtualMachine *vm, Target *target,
103108
engine(engine),
104109
script(script)
105110
{
106-
regs = new Value *[MAX_REG_COUNT];
107-
for (int i = 0; i < MAX_REG_COUNT; i++)
108-
regs[i] = new Value();
111+
regsVector.reserve(1024);
112+
for (int i = 0; i < 1024; i++)
113+
regsVector.push_back(new Value());
114+
regs = regsVector.data();
109115
loops.reserve(256);
110116
callTree.reserve(1024);
111117

@@ -115,9 +121,8 @@ VirtualMachinePrivate::VirtualMachinePrivate(VirtualMachine *vm, Target *target,
115121

116122
VirtualMachinePrivate::~VirtualMachinePrivate()
117123
{
118-
for (int i = 0; i < MAX_REG_COUNT; i++)
119-
delete regs[i];
120-
delete regs;
124+
for (int i = 0; i < regsVector.size(); i++)
125+
delete regsVector[i];
121126
}
122127

123128
unsigned int *VirtualMachinePrivate::run(unsigned int *pos, bool reset)

src/engine/virtualmachine_p.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,7 @@ struct VirtualMachinePrivate
6666
std::vector<List *> listsVector;
6767

6868
Value **regs = nullptr;
69+
std::vector<Value *> regsVector;
6970
size_t regCount = 0;
7071

7172
static IRandomGenerator *rng;

test/virtual_machine/virtual_machine_test.cpp

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -133,6 +133,35 @@ TEST(VirtualMachineTest, MinimalScript)
133133
ASSERT_EQ(vm.registerCount(), 0);
134134
}
135135

136+
TEST(VirtualMachineTest, RegCountLimit)
137+
{
138+
static unsigned int bytecode[20482] = { OP_START };
139+
140+
for (int i = 0; i < 10240; i++) {
141+
bytecode[2 * i + 1] = OP_CONST;
142+
bytecode[2 * i + 2] = 0;
143+
}
144+
145+
bytecode[20481] = OP_HALT;
146+
147+
static Value constValues[] = { 1 };
148+
149+
VirtualMachine vm;
150+
vm.setBytecode(bytecode);
151+
vm.setConstValues(constValues);
152+
vm.run();
153+
ASSERT_EQ(vm.registerCount(), 10240);
154+
155+
for (int i = 1; i < 10240; i++)
156+
bytecode[i] = OP_ADD;
157+
158+
bytecode[10240] = OP_HALT;
159+
vm.setBytecode(bytecode);
160+
vm.run();
161+
ASSERT_EQ(vm.registerCount(), 1);
162+
ASSERT_EQ(vm.getInput(0, 1)->toInt(), 10240);
163+
}
164+
136165
TEST(VirtualMachineTest, OP_CONST)
137166
{
138167
static unsigned int bytecode[] = { OP_START, OP_CONST, 0, OP_HALT };

0 commit comments

Comments
 (0)