] unit-test
{
- { { 0 { 0 -1 } } { 0 { } } }
+ { { 0 { 0 } } { 0 { } } }
} [
V{
T{ ##replace { src 10 } { loc D 0 } }
] unit-test
{
- { { 0 { -1 } } { 0 { } } }
+ { { 0 { } } { 0 { } } }
} [
V{
T{ ##inc f D 1 }
}
{
3 V{
+ T{ ##peek { dst 0 } { loc D 0 } }
+ T{ ##peek { dst 0 } { loc D 1 } }
T{ ##inc f D 2 }
- T{ ##peek { dst 0 } { loc D 2 } }
- T{ ##peek { dst 0 } { loc D 3 } }
T{ ##replace { src 0 } { loc D 2 } }
T{ ##replace { src 0 } { loc D 3 } }
T{ ##replace { src 0 } { loc D 1 } }
}
{
8 V{
+ T{ ##peek { dst 0 } { loc D 2 } }
+ T{ ##peek { dst 0 } { loc D 1 } }
T{ ##inc f D 3 }
- T{ ##peek { dst 0 } { loc D 5 } }
T{ ##replace { src 0 } { loc D 0 } }
- T{ ##replace { src 0 } { loc D 3 } }
- T{ ##peek { dst 0 } { loc D 4 } }
T{ ##replace { src 0 } { loc D 1 } }
T{ ##replace { src 0 } { loc D 2 } }
+ T{ ##replace { src 0 } { loc D 3 } }
}
}
{
10 V{
T{ ##inc f D -3 }
- T{ ##peek { dst 0 } { loc D -3 } }
+ T{ ##peek { dst 0 } { loc D 0 } }
T{ ##alien-invoke { gc-map T{ gc-map { scrub-d { } } } } }
}
}
{ 5 { { 2 { 1 } } { 0 { } } } }
{ 6 { { 2 { 1 0 } } { 0 { } } } }
{ 7 { { 2 { 1 0 } } { 0 { } } } }
- { 8 { { 4 { 3 2 } } { 0 { } } } }
- { 9 { { 4 { 3 2 } } { 0 { } } } }
+ { 8 { { 2 { 1 0 } } { 0 { } } } }
+ { 9 { { 2 { 1 0 } } { 0 { } } } }
{ 10 { { 4 { 3 2 } } { 0 { } } } }
{ 11 { { 4 { 3 2 } } { 0 { } } } }
{ 12 { { 4 { 3 2 } } { 0 { } } } }
{ 13 { { 4 { 3 2 1 } } { 0 { } } } }
- { 14 { { 7 { 6 5 4 } } { 0 { } } } }
- { 15 { { 7 { 6 5 4 } } { 0 { } } } }
- { 16 { { 7 { 6 5 4 0 } } { 0 { } } } }
- { 17 { { 7 { 6 5 4 0 3 } } { 0 { } } } }
- { 18 { { 7 { 6 5 4 0 3 } } { 0 { } } } }
- { 19 { { 7 { 6 5 4 0 3 1 } } { 0 { } } } }
- { 20 { { 7 { 6 5 4 0 3 1 2 } } { 0 { } } } }
- { 21 { { 4 { 3 2 1 -3 0 -2 -1 } } { 0 { } } } }
- { 22 { { 4 { 3 2 1 -3 0 -2 -1 } } { 0 { } } } }
+ { 14 { { 4 { 3 2 1 } } { 0 { } } } }
+ { 15 { { 4 { 3 2 1 } } { 0 { } } } }
+ { 16 { { 7 { 6 5 4 } } { 0 { } } } }
+ { 17 { { 7 { 6 5 4 0 } } { 0 { } } } }
+ { 18 { { 7 { 6 5 4 0 1 } } { 0 { } } } }
+ { 19 { { 7 { 6 5 4 0 1 2 } } { 0 { } } } }
+ { 20 { { 7 { 6 5 4 0 1 2 3 } } { 0 { } } } }
+ { 21 { { 4 { 3 2 1 0 } } { 0 { } } } }
+ { 22 { { 4 { 3 2 1 0 } } { 0 { } } } }
}
} [
bug1021-cfg trace-stack-state
M: ##inc visit-insn ( state insn -- state' )
[ first2 ] dip insn>location
- [ rot adjust-stack swap ] [ swap adjust-stack ] if 2array ;
+ [ rot adjust-stack swap ] [ swap adjust-stack ] if 2array
+ ! Negative out-of stack locations immediately becomes garbage.
+ [ first2 [ 0 >= ] filter 2array ] map ;
M: ##replace-imm visit-insn mark-location ;
M: ##replace visit-insn mark-location ;
-M: ##call visit-insn ( state insn -- state' )
- ! A call instruction may increase the stack height. Then issue a
- ! minor-gc with some of the stack locations scrubbed which would
- ! overwrite the overinitialized locations we're tracking. That is
- ! why they need to be cleared here.
- drop [ first2 [ 0 >= ] filter 2array ] map ;
-
ERROR: vacant-peek insn ;
: underflowable-peek? ( state peek -- ? )
So for each call frame:
- scrub some uninitialized locations
- - trace some overinitialized locations
- trace roots in spill slots
*/
template <typename Fixup> struct call_frame_slot_visitor {
- factor_vm* parent;
slot_visitor<Fixup>* visitor;
/* NULL in case we're a visitor for a callstack object. */
context* ctx;
- void check_stack(cell stack, uint8_t* bitmap, cell base, uint32_t count) {
- for (uint32_t loc = 0; loc < count; loc++) {
- if (bitmap_p(bitmap, base + loc)) {
-#ifdef DEBUG_GC_MAPS
- std::cout << "checking stack location " << loc << std::endl;
-#endif
- cell* value_ptr = ((cell*)stack + loc + 1);
- visitor->visit_handle(value_ptr);
- }
- }
- }
-
void scrub_stack(cell stack, uint8_t* bitmap, cell base, uint32_t count) {
for (cell loc = 0; loc < count; loc++) {
if (bitmap_p(bitmap, base + loc)) {
}
}
- call_frame_slot_visitor(factor_vm* parent,
- slot_visitor<Fixup>* visitor,
- context* ctx)
- : parent(parent), visitor(visitor), ctx(ctx) {}
+ call_frame_slot_visitor(slot_visitor<Fixup>* visitor, context* ctx)
+ : visitor(visitor), ctx(ctx) {}
/*
frame top -> [return address]
bitmap,
info->callsite_scrub_r(callsite),
info->scrub_r_count);
-
- /* Trace overinitialized stack locations. */
- check_stack(ctx->datastack,
- bitmap,
- info->callsite_check_d(callsite),
- info->check_d_count);
- check_stack(ctx->retainstack,
- bitmap,
- info->callsite_check_r(callsite),
- info->check_r_count);
}
/* Subtract old value of base pointer from every derived pointer. */
template <typename Fixup>
void slot_visitor<Fixup>::visit_callstack_object(callstack* stack) {
- call_frame_slot_visitor<Fixup> call_frame_visitor(parent, this, NULL);
+ call_frame_slot_visitor<Fixup> call_frame_visitor(this, NULL);
parent->iterate_callstack_object(stack, call_frame_visitor, fixup);
}
template <typename Fixup>
void slot_visitor<Fixup>::visit_callstack(context* ctx) {
- call_frame_slot_visitor<Fixup> call_frame_visitor(parent, this, ctx);
+ call_frame_slot_visitor<Fixup> call_frame_visitor(this, ctx);
parent->iterate_callstack(ctx, call_frame_visitor, fixup);
}
}
template <typename Fixup> struct call_frame_code_block_visitor {
- factor_vm* parent;
Fixup fixup;
- call_frame_code_block_visitor(factor_vm* parent, Fixup fixup)
- : parent(parent), fixup(fixup) {}
+ call_frame_code_block_visitor(Fixup fixup)
+ : fixup(fixup) {}
void operator()(cell frame_top, cell size, code_block* owner, cell addr) {
code_block* compiled =
}
case CALLSTACK_TYPE: {
callstack* stack = (callstack*)obj;
- call_frame_code_block_visitor<Fixup> call_frame_visitor(parent, fixup);
+ call_frame_code_block_visitor<Fixup> call_frame_visitor(fixup);
parent->iterate_callstack_object(stack, call_frame_visitor, fixup);
break;
}
template <typename Fixup>
void slot_visitor<Fixup>::visit_context_code_blocks() {
- call_frame_code_block_visitor<Fixup> call_frame_visitor(parent, fixup);
+ call_frame_code_block_visitor<Fixup> call_frame_visitor(fixup);
std::set<context*>::const_iterator begin = parent->active_contexts.begin();
std::set<context*>::const_iterator end = parent->active_contexts.end();
while (begin != end) {
- parent->iterate_callstack(*begin++, call_frame_visitor, fixup);
+ parent->iterate_callstack(*begin, call_frame_visitor, fixup);
+ begin++;
}
}