mirror of
https://github.com/corda/corda.git
synced 2025-01-05 20:54:13 +00:00
control flow bugfixes
This commit is contained in:
parent
ab7314e526
commit
b19c52b501
@ -1709,6 +1709,8 @@ compile(MyThread* t, Frame* initialFrame, unsigned ip,
|
|||||||
handleEntrance(t, frame);
|
handleEntrance(t, frame);
|
||||||
} else if (exceptionHandler) {
|
} else if (exceptionHandler) {
|
||||||
exceptionHandler = false;
|
exceptionHandler = false;
|
||||||
|
|
||||||
|
frame->pushObject();
|
||||||
|
|
||||||
c->call
|
c->call
|
||||||
(c->constant(reinterpret_cast<intptr_t>(gcIfNecessary)),
|
(c->constant(reinterpret_cast<intptr_t>(gcIfNecessary)),
|
||||||
@ -3850,15 +3852,15 @@ finish(MyThread* t, Context* context)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// for debugging:
|
// for debugging:
|
||||||
if (false and
|
if (//false and
|
||||||
strcmp
|
strcmp
|
||||||
(reinterpret_cast<const char*>
|
(reinterpret_cast<const char*>
|
||||||
(&byteArrayBody(t, className(t, methodClass(t, context->method)), 0)),
|
(&byteArrayBody(t, className(t, methodClass(t, context->method)), 0)),
|
||||||
"Misc") == 0 and
|
"java/lang/String") == 0 and
|
||||||
strcmp
|
strcmp
|
||||||
(reinterpret_cast<const char*>
|
(reinterpret_cast<const char*>
|
||||||
(&byteArrayBody(t, methodName(t, context->method), 0)),
|
(&byteArrayBody(t, methodName(t, context->method), 0)),
|
||||||
"main") == 0)
|
"getBytes") == 0)
|
||||||
{
|
{
|
||||||
asm("int3");
|
asm("int3");
|
||||||
}
|
}
|
||||||
@ -3951,8 +3953,6 @@ compile(MyThread* t, Context* context)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
frame2.pushObject();
|
|
||||||
|
|
||||||
for (unsigned i = 1;
|
for (unsigned i = 1;
|
||||||
i < codeMaxStack(t, methodCode(t, context->method));
|
i < codeMaxStack(t, methodCode(t, context->method));
|
||||||
++i)
|
++i)
|
||||||
|
304
src/compiler.cpp
304
src/compiler.cpp
@ -81,9 +81,9 @@ class State {
|
|||||||
class LogicalInstruction {
|
class LogicalInstruction {
|
||||||
public:
|
public:
|
||||||
unsigned visits;
|
unsigned visits;
|
||||||
|
Event* firstEvent;
|
||||||
Event* lastEvent;
|
Event* lastEvent;
|
||||||
unsigned machineOffset;
|
unsigned machineOffset;
|
||||||
int predecessor;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
class Register {
|
class Register {
|
||||||
@ -151,16 +151,18 @@ class Context {
|
|||||||
zone(zone),
|
zone(zone),
|
||||||
logicalIp(-1),
|
logicalIp(-1),
|
||||||
state(new (zone->allocate(sizeof(State))) State(0)),
|
state(new (zone->allocate(sizeof(State))) State(0)),
|
||||||
firstEvent(0),
|
|
||||||
lastEvent(0),
|
|
||||||
logicalCode(0),
|
logicalCode(0),
|
||||||
logicalCodeLength(0),
|
logicalCodeLength(0),
|
||||||
stackOffset(0),
|
stackOffset(0),
|
||||||
registers(static_cast<Register*>
|
registers(static_cast<Register*>
|
||||||
(zone->allocate(sizeof(Register) * assembler->registerCount()))),
|
(zone->allocate(sizeof(Register) * assembler->registerCount()))),
|
||||||
|
freeRegisterCount(assembler->registerCount() - 3),
|
||||||
|
freeRegisters(static_cast<int*>
|
||||||
|
(zone->allocate(sizeof(int) * freeRegisterCount))),
|
||||||
firstConstant(0),
|
firstConstant(0),
|
||||||
lastConstant(0),
|
lastConstant(0),
|
||||||
constantCount(0),
|
constantCount(0),
|
||||||
|
nextSequence(0),
|
||||||
junctions(0),
|
junctions(0),
|
||||||
machineCode(0)
|
machineCode(0)
|
||||||
{
|
{
|
||||||
@ -172,6 +174,13 @@ class Context {
|
|||||||
registers[assembler->stack()].reserved = true;
|
registers[assembler->stack()].reserved = true;
|
||||||
registers[assembler->thread()].refCount = 1;
|
registers[assembler->thread()].refCount = 1;
|
||||||
registers[assembler->thread()].reserved = true;
|
registers[assembler->thread()].reserved = true;
|
||||||
|
|
||||||
|
unsigned fri = 0;
|
||||||
|
for (int i = assembler->registerCount() - 1; i >= 0; --i) {
|
||||||
|
if (not registers[i].reserved) {
|
||||||
|
freeRegisters[fri++] = i;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
System* system;
|
System* system;
|
||||||
@ -179,15 +188,16 @@ class Context {
|
|||||||
Zone* zone;
|
Zone* zone;
|
||||||
int logicalIp;
|
int logicalIp;
|
||||||
State* state;
|
State* state;
|
||||||
Event* firstEvent;
|
|
||||||
Event* lastEvent;
|
|
||||||
LogicalInstruction* logicalCode;
|
LogicalInstruction* logicalCode;
|
||||||
unsigned logicalCodeLength;
|
unsigned logicalCodeLength;
|
||||||
unsigned stackOffset;
|
unsigned stackOffset;
|
||||||
Register* registers;
|
Register* registers;
|
||||||
|
unsigned freeRegisterCount;
|
||||||
|
int* freeRegisters;
|
||||||
ConstantPoolNode* firstConstant;
|
ConstantPoolNode* firstConstant;
|
||||||
ConstantPoolNode* lastConstant;
|
ConstantPoolNode* lastConstant;
|
||||||
unsigned constantCount;
|
unsigned constantCount;
|
||||||
|
unsigned nextSequence;
|
||||||
Junction* junctions;
|
Junction* junctions;
|
||||||
uint8_t* machineCode;
|
uint8_t* machineCode;
|
||||||
};
|
};
|
||||||
@ -284,24 +294,22 @@ class Event {
|
|||||||
public:
|
public:
|
||||||
Event(Context* c):
|
Event(Context* c):
|
||||||
next(0), stack(c->state->stack), promises(0), reads(0),
|
next(0), stack(c->state->stack), promises(0), reads(0),
|
||||||
logicalIp(c->logicalIp)
|
sequence(c->nextSequence++)
|
||||||
{
|
{
|
||||||
assert(c, c->logicalIp >= 0);
|
assert(c, c->logicalIp >= 0);
|
||||||
|
|
||||||
if (c->lastEvent) {
|
LogicalInstruction* i = c->logicalCode + c->logicalIp;
|
||||||
c->lastEvent->next = this;
|
if (i->lastEvent) {
|
||||||
sequence = c->lastEvent->sequence + 1;
|
i->lastEvent->next = this;
|
||||||
} else {
|
} else {
|
||||||
c->firstEvent = this;
|
i->firstEvent = this;
|
||||||
sequence = 0;
|
|
||||||
}
|
}
|
||||||
|
i->lastEvent = this;
|
||||||
c->lastEvent = this;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Event(Context*, Event* next):
|
Event(Context*, Event* next):
|
||||||
next(next), stack(next->stack), promises(0), reads(0),
|
next(next), stack(next->stack), promises(0), reads(0),
|
||||||
sequence(next->sequence), logicalIp(next->logicalIp)
|
sequence(next->sequence)
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
virtual ~Event() { }
|
virtual ~Event() { }
|
||||||
@ -313,7 +321,6 @@ class Event {
|
|||||||
CodePromise* promises;
|
CodePromise* promises;
|
||||||
Read* reads;
|
Read* reads;
|
||||||
unsigned sequence;
|
unsigned sequence;
|
||||||
unsigned logicalIp;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
bool
|
bool
|
||||||
@ -337,11 +344,12 @@ addSite(Context* c, Stack* stack, unsigned size, Value* v, Site* s)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
removeSite(Context*, Value* v, Site* s)
|
removeSite(Context* c, Value* v, Site* s)
|
||||||
{
|
{
|
||||||
for (Site** p = &(v->sites); *p;) {
|
for (Site** p = &(v->sites); *p;) {
|
||||||
if (s == *p) {
|
if (s == *p) {
|
||||||
fprintf(stderr, "remove site %p from %p\n", s, v);
|
fprintf(stderr, "remove site %p from %p\n", s, v);
|
||||||
|
s->release(c);
|
||||||
*p = (*p)->next;
|
*p = (*p)->next;
|
||||||
break;
|
break;
|
||||||
} else {
|
} else {
|
||||||
@ -350,15 +358,23 @@ removeSite(Context*, Value* v, Site* s)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
clearSites(Context* c, Value* v)
|
||||||
|
{
|
||||||
|
for (Site* s = v->sites; s; s = s->next) {
|
||||||
|
s->release(c);
|
||||||
|
}
|
||||||
|
v->sites = 0;
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
nextRead(Context* c, Value* v)
|
nextRead(Context* c, Value* v)
|
||||||
{
|
{
|
||||||
fprintf(stderr, "pop read %p from %p; next: %p\n", v->reads, v, v->reads->next);
|
fprintf(stderr, "pop read %p from %p\n", v->reads, v);
|
||||||
|
|
||||||
v->reads = v->reads->next;
|
v->reads = v->reads->next;
|
||||||
if (v->reads == 0) {
|
if (v->reads == 0) {
|
||||||
for (Site* s = v->sites; s; s = s->next) {
|
clearSites(c, v);
|
||||||
s->release(c);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -493,6 +509,22 @@ registerSite(Context* c, int low, int high = NoRegister)
|
|||||||
RegisterSite*
|
RegisterSite*
|
||||||
freeRegister(Context* c, unsigned size, bool allowAcquired);
|
freeRegister(Context* c, unsigned size, bool allowAcquired);
|
||||||
|
|
||||||
|
void
|
||||||
|
increment(Context* c, int r)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "increment %d\n", r);
|
||||||
|
++ c->registers[r].refCount;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
decrement(Context* c, int r)
|
||||||
|
{
|
||||||
|
assert(c, c->registers[r].refCount > 0);
|
||||||
|
assert(c, c->registers[r].refCount > 1 or (not c->registers[r].reserved));
|
||||||
|
fprintf(stderr, "decrement %d\n", r);
|
||||||
|
-- c->registers[r].refCount;
|
||||||
|
}
|
||||||
|
|
||||||
class MemorySite: public Site {
|
class MemorySite: public Site {
|
||||||
public:
|
public:
|
||||||
MemorySite(int base, int offset, int index, unsigned scale):
|
MemorySite(int base, int offset, int index, unsigned scale):
|
||||||
@ -515,20 +547,16 @@ class MemorySite: public Site {
|
|||||||
}
|
}
|
||||||
|
|
||||||
virtual void acquire(Context* c, Stack*, unsigned, Value*, Site*) {
|
virtual void acquire(Context* c, Stack*, unsigned, Value*, Site*) {
|
||||||
fprintf(stderr, "increment ref count for %d\n", value.base);
|
increment(c, value.base);
|
||||||
++ c->registers[value.base].refCount;
|
|
||||||
if (value.index != NoRegister) {
|
if (value.index != NoRegister) {
|
||||||
fprintf(stderr, "increment ref count for %d\n", value.index);
|
increment(c, value.index);
|
||||||
++ c->registers[value.index].refCount;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void release(Context* c) {
|
virtual void release(Context* c) {
|
||||||
fprintf(stderr, "decrement ref count for %d\n", value.base);
|
decrement(c, value.base);
|
||||||
-- c->registers[value.base].refCount;
|
|
||||||
if (value.index != NoRegister) {
|
if (value.index != NoRegister) {
|
||||||
fprintf(stderr, "decrement ref count for %d\n", value.index);
|
decrement(c, value.index);
|
||||||
-- c->registers[value.index].refCount;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -831,9 +859,10 @@ insertRead(Context* c, Event* thisEvent, Event* before, Value* v,
|
|||||||
{
|
{
|
||||||
Read* r = new (c->zone->allocate(sizeof(Read)))
|
Read* r = new (c->zone->allocate(sizeof(Read)))
|
||||||
Read(size, v, target, 0, thisEvent, thisEvent->reads);
|
Read(size, v, target, 0, thisEvent, thisEvent->reads);
|
||||||
fprintf(stderr, "add read %p to %p\n", r, v);
|
|
||||||
thisEvent->reads = r;
|
thisEvent->reads = r;
|
||||||
|
|
||||||
|
fprintf(stderr, "add read %p to %p\n", r, v);
|
||||||
|
|
||||||
if (before) {
|
if (before) {
|
||||||
for (Read** p = &(v->reads); *p;) {
|
for (Read** p = &(v->reads); *p;) {
|
||||||
if ((*p)->event->sequence >= before->sequence) {
|
if ((*p)->event->sequence >= before->sequence) {
|
||||||
@ -859,7 +888,7 @@ insertRead(Context* c, Event* thisEvent, Event* before, Value* v,
|
|||||||
void
|
void
|
||||||
addRead(Context* c, Value* v, unsigned size, Site* target)
|
addRead(Context* c, Value* v, unsigned size, Site* target)
|
||||||
{
|
{
|
||||||
insertRead(c, c->lastEvent, 0, v, size, target);
|
insertRead(c, c->logicalCode[c->logicalIp].lastEvent, 0, v, size, target);
|
||||||
}
|
}
|
||||||
|
|
||||||
Site*
|
Site*
|
||||||
@ -867,23 +896,26 @@ pushSite(Context*, PushEvent*);
|
|||||||
|
|
||||||
class PushEvent: public Event {
|
class PushEvent: public Event {
|
||||||
public:
|
public:
|
||||||
PushEvent(Context* c):
|
PushEvent(Context* c, Stack* s):
|
||||||
Event(c), active(false)
|
Event(c), s(s), active(false)
|
||||||
{
|
{
|
||||||
stack->pushEvent = this;
|
assert(c, s->pushEvent == 0);
|
||||||
addRead(c, stack->value, stack->size * BytesPerWord, pushSite(c, this));
|
|
||||||
|
s->pushEvent = this;
|
||||||
|
addRead(c, s->value, s->size * BytesPerWord, pushSite(c, this));
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void compile(Context* c) {
|
virtual void compile(Context* c) {
|
||||||
fprintf(stderr, "PushEvent.compile\n");
|
fprintf(stderr, "PushEvent.compile\n");
|
||||||
|
|
||||||
if (active) {
|
if (active) {
|
||||||
syncStack(c, stack);
|
syncStack(c, s);
|
||||||
}
|
}
|
||||||
|
|
||||||
nextRead(c, stack->value);
|
nextRead(c, s->value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Stack* s;
|
||||||
bool active;
|
bool active;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -919,10 +951,6 @@ class CallEvent: public Event {
|
|||||||
s = s->next;
|
s = s->next;
|
||||||
}
|
}
|
||||||
|
|
||||||
for (Stack* s = stack; s; s = s->next) {
|
|
||||||
s->pushEvent->active = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
addRead(c, address, BytesPerWord,
|
addRead(c, address, BytesPerWord,
|
||||||
(indirection ? registerSite(c, c->assembler->returnLow()) : 0));
|
(indirection ? registerSite(c, c->assembler->returnLow()) : 0));
|
||||||
}
|
}
|
||||||
@ -938,11 +966,15 @@ class CallEvent: public Event {
|
|||||||
apply(c, type, BytesPerWord, address->source);
|
apply(c, type, BytesPerWord, address->source);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (Stack* s = stack; s; s = s->next) {
|
||||||
|
clearSites(c, s->value);
|
||||||
|
}
|
||||||
|
|
||||||
for (Read* r = reads; r; r = r->eventNext) {
|
for (Read* r = reads; r; r = r->eventNext) {
|
||||||
nextRead(c, r->value);
|
nextRead(c, r->value);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (resultSize) {
|
if (resultSize and result->reads) {
|
||||||
addSite(c, 0, 0, result, registerSite
|
addSite(c, 0, 0, result, registerSite
|
||||||
(c, c->assembler->returnLow(),
|
(c, c->assembler->returnLow(),
|
||||||
resultSize > BytesPerWord ?
|
resultSize > BytesPerWord ?
|
||||||
@ -955,7 +987,7 @@ class CallEvent: public Event {
|
|||||||
CodePromise(c, c->assembler->length()));
|
CodePromise(c, c->assembler->length()));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (argumentFootprint) {
|
if (argumentFootprint and ((flags & Compiler::NoReturn) == 0)) {
|
||||||
Assembler::Register stack(c->assembler->stack());
|
Assembler::Register stack(c->assembler->stack());
|
||||||
Assembler::Constant offset
|
Assembler::Constant offset
|
||||||
(resolved(c, argumentFootprint * BytesPerWord));
|
(resolved(c, argumentFootprint * BytesPerWord));
|
||||||
@ -1059,7 +1091,7 @@ class MoveEvent: public Event {
|
|||||||
|
|
||||||
nextRead(c, src);
|
nextRead(c, src);
|
||||||
|
|
||||||
addSite(c, stack, size, dst, target);
|
if (dst->reads) addSite(c, stack, size, dst, target);
|
||||||
}
|
}
|
||||||
|
|
||||||
BinaryOperation type;
|
BinaryOperation type;
|
||||||
@ -1168,7 +1200,7 @@ class CombineEvent: public Event {
|
|||||||
nextRead(c, second);
|
nextRead(c, second);
|
||||||
|
|
||||||
removeSite(c, second, second->source);
|
removeSite(c, second, second->source);
|
||||||
addSite(c, 0, 0, result, second->source);
|
if (result->reads) addSite(c, 0, 0, result, second->source);
|
||||||
}
|
}
|
||||||
|
|
||||||
BinaryOperation type;
|
BinaryOperation type;
|
||||||
@ -1205,7 +1237,7 @@ class TranslateEvent: public Event {
|
|||||||
nextRead(c, value);
|
nextRead(c, value);
|
||||||
|
|
||||||
removeSite(c, value, value->source);
|
removeSite(c, value, value->source);
|
||||||
addSite(c, 0, 0, result, value->source);
|
if (result->reads) addSite(c, 0, 0, result, value->source);
|
||||||
}
|
}
|
||||||
|
|
||||||
UnaryOperation type;
|
UnaryOperation type;
|
||||||
@ -1277,23 +1309,38 @@ appendMemory(Context* c, Value* base, int displacement, Value* index,
|
|||||||
Site*
|
Site*
|
||||||
stackSyncSite(Context* c, unsigned index, unsigned size)
|
stackSyncSite(Context* c, unsigned index, unsigned size)
|
||||||
{
|
{
|
||||||
int high = NoRegister;
|
assert(c, index + size <= c->freeRegisterCount);
|
||||||
for (int i = c->assembler->registerCount() - 1; i >= 0; --i) {
|
|
||||||
if (not c->registers[i].reserved) {
|
return registerSite
|
||||||
if (index == 0) {
|
(c, c->freeRegisters[index],
|
||||||
if (size == 1) {
|
size == 2 ? c->freeRegisters[index + 1] : NoRegister);
|
||||||
return registerSite(c, i, high);
|
}
|
||||||
} else {
|
|
||||||
high = i;
|
Stack*
|
||||||
-- size;
|
stack(Context* c, Value* value, unsigned size, unsigned index, Stack* next)
|
||||||
}
|
{
|
||||||
} else {
|
return new (c->zone->allocate(sizeof(Stack)))
|
||||||
-- index;
|
Stack(value, size, index, next);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
resetStack(Context* c)
|
||||||
|
{
|
||||||
|
unsigned i = 0;
|
||||||
|
Stack* p = 0;
|
||||||
|
for (Stack* s = c->state->stack; s; s = s->next) {
|
||||||
|
Stack* n = stack
|
||||||
|
(c, value(c, stackSyncSite(c, i, s->size)), s->size, s->index, 0);
|
||||||
|
|
||||||
|
if (p) {
|
||||||
|
p->next = n;
|
||||||
|
} else {
|
||||||
|
c->state->stack = n;
|
||||||
}
|
}
|
||||||
|
p = n;
|
||||||
|
|
||||||
|
i += s->size;
|
||||||
}
|
}
|
||||||
|
|
||||||
abort(c);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class StackSyncEvent: public Event {
|
class StackSyncEvent: public Event {
|
||||||
@ -1307,6 +1354,8 @@ class StackSyncEvent: public Event {
|
|||||||
stackSyncSite(c, i, s->size));
|
stackSyncSite(c, i, s->size));
|
||||||
i += s->size;
|
i += s->size;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
resetStack(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
StackSyncEvent(Context* c, Event* next):
|
StackSyncEvent(Context* c, Event* next):
|
||||||
@ -1325,8 +1374,6 @@ class StackSyncEvent: public Event {
|
|||||||
|
|
||||||
for (Read* r = reads; r; r = r->eventNext) {
|
for (Read* r = reads; r; r = r->eventNext) {
|
||||||
nextRead(c, r->value);
|
nextRead(c, r->value);
|
||||||
r->value->sites = r->target;
|
|
||||||
r->target->next = 0;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
@ -1361,11 +1408,28 @@ pushSite(Context* c, PushEvent* e)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
appendPush(Context* c)
|
appendPush(Context* c, Stack* s)
|
||||||
{
|
{
|
||||||
fprintf(stderr, "appendPush\n");
|
fprintf(stderr, "appendPush\n");
|
||||||
|
|
||||||
new (c->zone->allocate(sizeof(PushEvent))) PushEvent(c);
|
new (c->zone->allocate(sizeof(PushEvent))) PushEvent(c, s);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
appendPush(Context* c)
|
||||||
|
{
|
||||||
|
appendPush(c, c->state->stack);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
ignore(Context* c, unsigned count)
|
||||||
|
{
|
||||||
|
if (count) {
|
||||||
|
Assembler::Register stack(c->assembler->stack());
|
||||||
|
Assembler::Constant offset(resolved(c, count * BytesPerWord));
|
||||||
|
c->assembler->apply
|
||||||
|
(Add, BytesPerWord, ConstantOperand, &offset, RegisterOperand, &stack);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
@ -1376,7 +1440,7 @@ popNow(Context* c, Event* event, Stack* stack, unsigned count, bool ignore)
|
|||||||
for (unsigned i = count; i;) {
|
for (unsigned i = count; i;) {
|
||||||
if (s->pushed) {
|
if (s->pushed) {
|
||||||
if (s->value->reads and (not ignore)) {
|
if (s->value->reads and (not ignore)) {
|
||||||
assert(c, ignored == 0);
|
::ignore(c, ignored);
|
||||||
|
|
||||||
fprintf(stderr, "pop %p\n", s);
|
fprintf(stderr, "pop %p\n", s);
|
||||||
|
|
||||||
@ -1402,12 +1466,7 @@ popNow(Context* c, Event* event, Stack* stack, unsigned count, bool ignore)
|
|||||||
s = s->next;
|
s = s->next;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ignored) {
|
::ignore(c, ignored);
|
||||||
Assembler::Register stack(c->assembler->stack());
|
|
||||||
Assembler::Constant offset(resolved(c, ignored * BytesPerWord));
|
|
||||||
c->assembler->apply
|
|
||||||
(Add, BytesPerWord, ConstantOperand, &offset, RegisterOperand, &stack);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
@ -1497,20 +1556,24 @@ compile(Context* c)
|
|||||||
RegisterOperand, &stack);
|
RegisterOperand, &stack);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (Event* e = c->firstEvent; e; e = e->next) {
|
for (unsigned i = 0; i < c->logicalCodeLength; ++i) {
|
||||||
fprintf(stderr, "ip: %d\n", e->logicalIp);
|
LogicalInstruction* li = c->logicalCode + i;
|
||||||
|
if (li->firstEvent) {
|
||||||
|
li->machineOffset = a->length();
|
||||||
|
|
||||||
LogicalInstruction* li = c->logicalCode + e->logicalIp;
|
fprintf(stderr, "ip: %d\n", i);
|
||||||
li->machineOffset = a->length();
|
|
||||||
|
|
||||||
for (Read* r = e->reads; r; r = r->eventNext) {
|
for (Event* e = li->firstEvent; e; e = e->next) {
|
||||||
r->value->source = readSource(c, e->stack, r, e);
|
for (Read* r = e->reads; r; r = r->eventNext) {
|
||||||
}
|
r->value->source = readSource(c, e->stack, r, e);
|
||||||
|
}
|
||||||
|
|
||||||
e->compile(c);
|
e->compile(c);
|
||||||
|
|
||||||
for (CodePromise* p = e->promises; p; p = p->next) {
|
for (CodePromise* p = e->promises; p; p = p->next) {
|
||||||
p->offset = a->length();
|
p->offset = a->length();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1538,13 +1601,8 @@ popState(Context* c)
|
|||||||
{
|
{
|
||||||
c->state = new (c->zone->allocate(sizeof(State)))
|
c->state = new (c->zone->allocate(sizeof(State)))
|
||||||
State(c->state->next);
|
State(c->state->next);
|
||||||
}
|
|
||||||
|
|
||||||
Stack*
|
resetStack(c);
|
||||||
stack(Context* c, Value* value, unsigned size, unsigned index, Stack* next)
|
|
||||||
{
|
|
||||||
return new (c->zone->allocate(sizeof(Stack)))
|
|
||||||
Stack(value, size, index, next);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Stack*
|
Stack*
|
||||||
@ -1581,12 +1639,13 @@ updateJunctions(Context* c)
|
|||||||
for (Junction* j = c->junctions; j; j = j->next) {
|
for (Junction* j = c->junctions; j; j = j->next) {
|
||||||
LogicalInstruction* i = c->logicalCode + j->logicalIp;
|
LogicalInstruction* i = c->logicalCode + j->logicalIp;
|
||||||
|
|
||||||
if (i->predecessor >= 0) {
|
for (int ip = j->logicalIp - 1; ip >= 0; --ip) {
|
||||||
LogicalInstruction* p = c->logicalCode + i->predecessor;
|
LogicalInstruction* p = c->logicalCode + ip;
|
||||||
|
if (p->lastEvent) {
|
||||||
p->lastEvent = p->lastEvent->next
|
i->lastEvent = i->lastEvent->next
|
||||||
= new (c->zone->allocate(sizeof(StackSyncEvent)))
|
= new (c->zone->allocate(sizeof(StackSyncEvent)))
|
||||||
StackSyncEvent(c, p->lastEvent->next);
|
StackSyncEvent(c, 0);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1600,14 +1659,14 @@ used(Context* c, int r)
|
|||||||
return v and findSite(c, v, c->registers[r].site);
|
return v and findSite(c, v, c->registers[r].site);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
// bool
|
||||||
usedExclusively(Context* c, int r)
|
// usedExclusively(Context* c, int r)
|
||||||
{
|
// {
|
||||||
Value* v = c->registers[r].value;
|
// Value* v = c->registers[r].value;
|
||||||
return used(c, r)
|
// return used(c, r)
|
||||||
and v->pushCount == 0
|
// and v->pushCount == 0
|
||||||
and v->sites->next == 0;
|
// and v->sites->next == 0;
|
||||||
}
|
// }
|
||||||
|
|
||||||
int
|
int
|
||||||
freeRegisterExcept(Context* c, int except, bool allowAcquired)
|
freeRegisterExcept(Context* c, int except, bool allowAcquired)
|
||||||
@ -1621,14 +1680,14 @@ freeRegisterExcept(Context* c, int except, bool allowAcquired)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
for (int i = c->assembler->registerCount() - 1; i >= 0; --i) {
|
// for (int i = c->assembler->registerCount() - 1; i >= 0; --i) {
|
||||||
if (i != except
|
// if (i != except
|
||||||
and c->registers[i].refCount == 0
|
// and c->registers[i].refCount == 0
|
||||||
and (not usedExclusively(c, i)))
|
// and (not usedExclusively(c, i)))
|
||||||
{
|
// {
|
||||||
return i;
|
// return i;
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
|
|
||||||
if (allowAcquired) {
|
if (allowAcquired) {
|
||||||
for (int i = c->assembler->registerCount() - 1; i >= 0; --i) {
|
for (int i = c->assembler->registerCount() - 1; i >= 0; --i) {
|
||||||
@ -1673,13 +1732,12 @@ class Client: public Assembler::Client {
|
|||||||
expect(c, c->registers[r].refCount == 0);
|
expect(c, c->registers[r].refCount == 0);
|
||||||
expect(c, c->registers[r].value == 0);
|
expect(c, c->registers[r].value == 0);
|
||||||
}
|
}
|
||||||
++ c->registers[r].refCount;
|
increment(c, r);
|
||||||
fprintf(stderr, "acquire temporary: %d\n", r);
|
|
||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void releaseTemporary(int r) {
|
virtual void releaseTemporary(int r) {
|
||||||
-- c->registers[r].refCount;
|
decrement(c, r);
|
||||||
}
|
}
|
||||||
|
|
||||||
Context* c;
|
Context* c;
|
||||||
@ -1710,17 +1768,14 @@ class MyCompiler: public Compiler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
virtual void visitLogicalIp(unsigned logicalIp) {
|
virtual void visitLogicalIp(unsigned logicalIp) {
|
||||||
if ((++ c.logicalCode[logicalIp].visits) == 1) {
|
if ((++ c.logicalCode[logicalIp].visits) == 2) {
|
||||||
c.junctions = new (c.zone->allocate(sizeof(Junction)))
|
c.junctions = new (c.zone->allocate(sizeof(Junction)))
|
||||||
Junction(logicalIp, c.junctions);
|
Junction(logicalIp, c.junctions);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void startLogicalIp(unsigned logicalIp) {
|
virtual void startLogicalIp(unsigned logicalIp) {
|
||||||
if (c.logicalIp >= 0) {
|
fprintf(stderr, "ip: %d\n", logicalIp);
|
||||||
c.logicalCode[c.logicalIp].lastEvent = c.lastEvent;
|
|
||||||
}
|
|
||||||
|
|
||||||
c.logicalIp = logicalIp;
|
c.logicalIp = logicalIp;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1809,8 +1864,9 @@ class MyCompiler: public Compiler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
Promise* machineIp() {
|
Promise* machineIp() {
|
||||||
return c.lastEvent->promises = new (c.zone->allocate(sizeof(CodePromise)))
|
Event* e = c.logicalCode[c.logicalIp].lastEvent;
|
||||||
CodePromise(&c, c.lastEvent->promises);
|
return e->promises = new (c.zone->allocate(sizeof(CodePromise)))
|
||||||
|
CodePromise(&c, e->promises);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void mark(Operand* label) {
|
virtual void mark(Operand* label) {
|
||||||
@ -1890,9 +1946,15 @@ class MyCompiler: public Compiler {
|
|||||||
|
|
||||||
va_end(a);
|
va_end(a);
|
||||||
|
|
||||||
|
for (Stack* s = c.state->stack; s; s = s->next) {
|
||||||
|
if (s->pushEvent == 0) {
|
||||||
|
appendPush(&c, s);
|
||||||
|
}
|
||||||
|
s->pushEvent->active = true;
|
||||||
|
}
|
||||||
|
|
||||||
Stack* oldStack = c.state->stack;
|
Stack* oldStack = c.state->stack;
|
||||||
|
|
||||||
fprintf(stderr, "argument count: %d\n", argumentCount);
|
|
||||||
for (int i = argumentCount - 1; i >= 0; --i) {
|
for (int i = argumentCount - 1; i >= 0; --i) {
|
||||||
::push(&c, argumentSizes[i], arguments[i]);
|
::push(&c, argumentSizes[i], arguments[i]);
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user