diff --git a/src/asm_x64.c b/src/asm_x64.c index 39658d4..0d25af1 100644 --- a/src/asm_x64.c +++ b/src/asm_x64.c @@ -304,6 +304,7 @@ static const uint8_t call_regs[] = {RDI, RSI, RDX, RCX, R8, R9}; static void assign_call_registers(uint16_t op, trace_s *trace, int *slot, uint32_t *next_spill, int arg) { + assert(arg < 6); // all in reg if (!ir_is_const(op)) { auto cop = &trace->ops[op]; if (cop->op == IR_CARG) { diff --git a/src/record.c b/src/record.c index 52137e3..391f80c 100644 --- a/src/record.c +++ b/src/record.c @@ -1584,6 +1584,23 @@ bool record_instr(uint32_t *pc, gc_obj *frame, int64_t argcnt) { // No stack top tracking break; } + case STRING_COPY: { + auto slot = INS_A(i); + auto arg4 = push_ir(trace, IR_CARG, record_stack_load(slot+3, frame), + record_stack_load(slot+4, frame), UNDEFINED_TAG); + auto arg3 = push_ir(trace, IR_CARG, + record_stack_load(slot+2, frame), arg4, UNDEFINED_TAG); + auto arg2 = push_ir(trace, IR_CARG, + record_stack_load(slot+1, frame), arg3, UNDEFINED_TAG); + auto arg1 = push_ir(trace, IR_CARG, + record_stack_load(slot, frame), arg2, UNDEFINED_TAG); + auto knum = arrlen(trace->consts); + arrput(trace->consts, tag_ptr(vm_string_copy)); + push_ir(trace, IR_CALLXS, arg1, knum | IR_CONST_BIAS, UNDEFINED_TAG); + stack_top = INS_A(i); + add_snap(regs_list, regs - regs_list - 1, trace, pc + 1, depth, stack_top); + break; + } case READ: { port_s *port = to_port(frame[INS_B(i)]); uint8_t type = CHAR_TAG; diff --git a/src/vm.c b/src/vm.c index 919c3b0..9f3fb84 100644 --- a/src/vm.c +++ b/src/vm.c @@ -811,9 +811,8 @@ LIBRARY_FUNC_B(CLOSURE) { auto fun = to_func(frame[ra]); if (fun->poly_cnt < 50) { if (fun->poly_cnt == 1) { - printf("Make polymorphic %s\n", fun->name); for (uint32_t i = 0; i < hmlen(fun->lst); i++) { - printf("POLYMORPHIC %s flush of trace %i\n", fun->name, fun->lst[i].key); + //printf("POLYMORPHIC %s flush of trace %i\n", fun->name, fun->lst[i].key); trace_flush(trace_cache_get(fun->lst[i].key), true); } hmfree(fun->lst); @@ -1222,6 +1221,12 @@ LIBRARY_FUNC_BC_LOAD_NAME("STRING-SET!", STRING_SET) { } END_LIBRARY_FUNC +void vm_string_copy(gc_obj tostr, gc_obj tostart, gc_obj fromstr, gc_obj fromstart, gc_obj fromend) { + auto len = to_fixnum(fromend) - to_fixnum(fromstart); + memcpy(&to_string(tostr)->str[to_fixnum(tostart)], + &to_string(fromstr)->str[to_fixnum(fromstart)], len); +} + LIBRARY_FUNC_NAME("STRING-COPY", STRING_COPY) { // TODO(djwatson) Some of this is already checked in bootstrap? LOAD_TYPE_WITH_CHECK(tostr, string_s, frame[ra], STRING_TAG); diff --git a/src/vm.h b/src/vm.h index ac88e48..02208ba 100644 --- a/src/vm.h +++ b/src/vm.h @@ -32,6 +32,7 @@ gc_obj vm_length(gc_obj fb); gc_obj vm_memq(gc_obj fb, gc_obj fc); gc_obj vm_assq(gc_obj fb, gc_obj fc); gc_obj vm_assv(gc_obj fb, gc_obj fc); +void vm_string_copy(gc_obj tostr, gc_obj tostart, gc_obj fromstr, gc_obj fromstart, gc_obj fromend); static inline uint32_t hotmap_hash(const uint32_t *pc) { return (((uint64_t)pc) >> 2) & hotmap_mask;