From e21f316583f225b05404beb17171f3fd4474a9aa Mon Sep 17 00:00:00 2001 From: Joe Groff Date: Fri, 25 Nov 2011 18:58:21 -0800 Subject: [PATCH] vm: store stack frame size in code blocks Change modify-code-heap primitive so it takes a sixth element in each array for the frame size. --- basis/compiler/codegen/codegen.factor | 3 ++- basis/cpu/x86/32/bootstrap.factor | 1 + basis/cpu/x86/64/unix/bootstrap.factor | 1 + basis/cpu/x86/64/windows/bootstrap.factor | 1 + basis/cpu/x86/bootstrap.factor | 4 +--- vm/code_blocks.cpp | 6 +++++- vm/code_blocks.hpp | 8 ++++++-- vm/code_heap.cpp | 4 +++- vm/cpu-x86.32.hpp | 5 +++++ vm/cpu-x86.cpp | 2 +- vm/debug.cpp | 4 +++- vm/free_list.hpp | 4 ---- vm/jit.cpp | 3 ++- vm/os-linux-x86.64.hpp | 6 ++++++ vm/os-macosx-x86.64.hpp | 5 +++++ vm/os-windows.64.hpp | 5 +++++ vm/vm.hpp | 4 +++- 17 files changed, 50 insertions(+), 16 deletions(-) diff --git a/basis/compiler/codegen/codegen.factor b/basis/compiler/codegen/codegen.factor index 8b2e1e643e..2d35a3ca01 100755 --- a/basis/compiler/codegen/codegen.factor +++ b/basis/compiler/codegen/codegen.factor @@ -107,7 +107,8 @@ M: ##dispatch generate-insn label-table get ] B{ } make dup check-fixup - ] call 5 narray ; inline + cfg get stack-frame>> [ total-size>> ] [ 0 ] if* + ] call 6 narray ; inline : generate ( cfg -- code ) [ diff --git a/basis/cpu/x86/32/bootstrap.factor b/basis/cpu/x86/32/bootstrap.factor index a3edd70ffb..5930ba910a 100755 --- a/basis/cpu/x86/32/bootstrap.factor +++ b/basis/cpu/x86/32/bootstrap.factor @@ -9,6 +9,7 @@ IN: bootstrap.x86 4 \ cell set +: leaf-stack-frame-size ( -- n ) 4 bootstrap-cells ; : stack-frame-size ( -- n ) 8 bootstrap-cells ; : shift-arg ( -- reg ) ECX ; : div-arg ( -- reg ) EAX ; diff --git a/basis/cpu/x86/64/unix/bootstrap.factor b/basis/cpu/x86/64/unix/bootstrap.factor index 6b7d93184c..deeb31cd77 100644 --- a/basis/cpu/x86/64/unix/bootstrap.factor +++ b/basis/cpu/x86/64/unix/bootstrap.factor @@ -5,6 +5,7 @@ cpu.x86.assembler.operands kernel layouts namespaces parser sequences system vocabs ; IN: bootstrap.x86 +: leaf-stack-frame-size ( -- n ) 4 bootstrap-cells ; : stack-frame-size ( -- n ) 4 bootstrap-cells ; : nv-regs ( -- seq ) { RBX R12 R13 R14 R15 } ; : volatile-regs ( -- seq ) { RAX RCX RDX RSI RDI R8 R9 R10 R11 } ; diff --git a/basis/cpu/x86/64/windows/bootstrap.factor b/basis/cpu/x86/64/windows/bootstrap.factor index bee1135d68..cc701a6b63 100644 --- a/basis/cpu/x86/64/windows/bootstrap.factor +++ b/basis/cpu/x86/64/windows/bootstrap.factor @@ -7,6 +7,7 @@ IN: bootstrap.x86 DEFER: stack-reg +: leaf-stack-frame-size ( -- n ) 4 bootstrap-cells ; : stack-frame-size ( -- n ) 8 bootstrap-cells ; : nv-regs ( -- seq ) { RBX RSI RDI R12 R13 R14 R15 } ; : volatile-regs ( -- seq ) { RAX RCX RDX R8 R9 R10 R11 } ; diff --git a/basis/cpu/x86/bootstrap.factor b/basis/cpu/x86/bootstrap.factor index 3c6d7ae8de..ee84ff2dbd 100644 --- a/basis/cpu/x86/bootstrap.factor +++ b/basis/cpu/x86/bootstrap.factor @@ -102,8 +102,6 @@ big-endian off 0 RET ] \ signal-handler define-sub-primitive -: leaf-frame-size ( -- n ) 4 bootstrap-cells ; - [| | jit-signal-handler-prolog :> frame-size jit-save-context @@ -111,7 +109,7 @@ big-endian off temp0 CALL frame-size jit-signal-handler-epilog ! Pop the fake leaf frame along with our return address - leaf-frame-size bootstrap-cell - RET + leaf-stack-frame-size bootstrap-cell - RET ] \ leaf-signal-handler define-sub-primitive [| | diff --git a/vm/code_blocks.cpp b/vm/code_blocks.cpp index 00bfac5133..bc3171a239 100755 --- a/vm/code_blocks.cpp +++ b/vm/code_blocks.cpp @@ -399,7 +399,9 @@ code_block *factor_vm::allot_code_block(cell size, code_block_type type) } /* Might GC */ -code_block *factor_vm::add_code_block(code_block_type type, cell code_, cell labels_, cell owner_, cell relocation_, cell parameters_, cell literals_) +code_block *factor_vm::add_code_block(code_block_type type, cell code_, cell labels_, + cell owner_, cell relocation_, cell parameters_, cell literals_, + cell frame_size_untagged) { data_root code(code_,this); data_root labels(labels_,this); @@ -431,6 +433,8 @@ code_block *factor_vm::add_code_block(code_block_type type, cell code_, cell lab if(to_boolean(labels.value())) fixup_labels(labels.as().untagged(),compiled); + compiled->stack_frame_size = frame_size_untagged; + /* Once we are ready, fill in literal and word references in this code block's instruction operands. In most cases this is done right after this method returns, except when compiling words with the non-optimizing diff --git a/vm/code_blocks.hpp b/vm/code_blocks.hpp index 8c3a6c1c80..099b793866 100644 --- a/vm/code_blocks.hpp +++ b/vm/code_blocks.hpp @@ -4,10 +4,16 @@ namespace factor /* The compiled code heap is structured into blocks. */ struct code_block { + // header format (bits indexed with least significant as zero): + // bit 0 : free? + // bits 1- 2: type (as a code_block_type) + // bits 4- : code size / 16 cell header; cell owner; /* tagged pointer to word, quotation or f */ cell parameters; /* tagged pointer to array or f */ cell relocation; /* tagged pointer to byte-array or f */ + cell stack_frame_size; + cell pad; bool free_p() const { @@ -37,9 +43,7 @@ struct code_block cell size() const { cell size = header & ~7; -#ifdef FACTOR_DEBUG FACTOR_ASSERT(size > 0); -#endif return size; } diff --git a/vm/code_heap.cpp b/vm/code_heap.cpp index 5f6967535a..da8477ef76 100755 --- a/vm/code_heap.cpp +++ b/vm/code_heap.cpp @@ -231,6 +231,7 @@ void factor_vm::primitive_modify_code_heap() cell relocation = array_nth(compiled_data,2); cell labels = array_nth(compiled_data,3); cell code = array_nth(compiled_data,4); + cell frame_size = untag_fixnum(array_nth(compiled_data,5)); code_block *compiled = add_code_block( code_block_optimized, @@ -239,7 +240,8 @@ void factor_vm::primitive_modify_code_heap() word.value(), relocation, parameters, - literals); + literals, + frame_size); word->entry_point = compiled->entry_point(); } diff --git a/vm/cpu-x86.32.hpp b/vm/cpu-x86.32.hpp index 6143631abc..0bc90416f1 100644 --- a/vm/cpu-x86.32.hpp +++ b/vm/cpu-x86.32.hpp @@ -3,4 +3,9 @@ namespace factor #define FACTOR_CPU_STRING "x86.32" +/* Must match the leaf-stack-frame-size stack-frame-size constants in +cpu/x86/32/bootstrap.factor */ +static const unsigned LEAF_FRAME_SIZE = 16; +static const unsigned JIT_FRAME_SIZE = 32; + } diff --git a/vm/cpu-x86.cpp b/vm/cpu-x86.cpp index 28b289e34c..1687becedb 100644 --- a/vm/cpu-x86.cpp +++ b/vm/cpu-x86.cpp @@ -53,7 +53,7 @@ void factor_vm::dispatch_signal_handler(cell *sp, cell *pc, cell handler) code_block *leaf_block = code->code_block_for_address(*pc); FACTOR_ASSERT(leaf_block != NULL); - cell newsp = *sp - 4*sizeof(cell); + cell newsp = *sp - LEAF_FRAME_SIZE; *(cell*)(newsp + 3*sizeof(cell)) = 4*sizeof(cell); *(cell*)(newsp + 2*sizeof(cell)) = (cell)leaf_block->entry_point(); *(cell*) newsp = *pc; diff --git a/vm/debug.cpp b/vm/debug.cpp index b3e179f636..17363a526c 100755 --- a/vm/debug.cpp +++ b/vm/debug.cpp @@ -417,7 +417,9 @@ struct code_block_printer { std::cout << std::hex << (cell)scan << std::dec << " "; std::cout << std::hex << size << std::dec << " "; - std::cout << status << std::endl; + std::cout << status << " "; + std::cout << "stack frame " << scan->stack_frame_size; + std::cout << std::endl; } } }; diff --git a/vm/free_list.hpp b/vm/free_list.hpp index e8def2f4c2..e0c5a7063b 100755 --- a/vm/free_list.hpp +++ b/vm/free_list.hpp @@ -16,17 +16,13 @@ struct free_heap_block cell size() const { cell size = header & ~7; -#ifdef FACTOR_DEBUG FACTOR_ASSERT(size > 0); -#endif return size; } void make_free(cell size) { -#ifdef FACTOR_DEBUG FACTOR_ASSERT(size > 0); -#endif header = size | 1; } }; diff --git a/vm/jit.cpp b/vm/jit.cpp index 36c1d94a46..29eb6f19db 100644 --- a/vm/jit.cpp +++ b/vm/jit.cpp @@ -143,7 +143,8 @@ code_block *jit::to_code_block() owner.value(), relocation.elements.value(), parameters.elements.value(), - literals.elements.value()); + literals.elements.value(), + JIT_FRAME_SIZE); } } diff --git a/vm/os-linux-x86.64.hpp b/vm/os-linux-x86.64.hpp index ced11635e6..94e102c37f 100644 --- a/vm/os-linux-x86.64.hpp +++ b/vm/os-linux-x86.64.hpp @@ -27,4 +27,10 @@ inline static void uap_clear_fpu_status(void *uap) #define FUNCTION_TOC_POINTER(ptr) ptr #define UAP_STACK_POINTER_TYPE greg_t + +/* Must match the leaf-stack-frame-size and stack-frame-size constants +in basis/cpu/x86/64/unix/bootstrap.factor */ +static const unsigned LEAF_FRAME_SIZE = 32; +static const unsigned JIT_FRAME_SIZE = 32; + } diff --git a/vm/os-macosx-x86.64.hpp b/vm/os-macosx-x86.64.hpp index a9fcb9f274..d8bb821678 100644 --- a/vm/os-macosx-x86.64.hpp +++ b/vm/os-macosx-x86.64.hpp @@ -73,4 +73,9 @@ inline static void uap_clear_fpu_status(void *uap) mach_clear_fpu_status(UAP_FS(uap)); } +/* Must match the leaf-stack-frame-size and stack-frame-size constants +in basis/cpu/x86/64/unix/bootstrap.factor */ +static const unsigned LEAF_FRAME_SIZE = 32; +static const unsigned JIT_FRAME_SIZE = 32; + } diff --git a/vm/os-windows.64.hpp b/vm/os-windows.64.hpp index ff9cf4a0bb..42b4362b1a 100644 --- a/vm/os-windows.64.hpp +++ b/vm/os-windows.64.hpp @@ -8,4 +8,9 @@ namespace factor #define MXCSR(ctx) (ctx)->MxCsr +/* Must match the leaf-stack-frame-size and stack-frame-size constants +in basis/cpu/x86/64/windows/bootstrap.factor */ + +static const unsigned LEAF_FRAME_SIZE = 32; +static const unsigned JIT_FRAME_SIZE = 64; } diff --git a/vm/vm.hpp b/vm/vm.hpp index 1a96362900..ec9086ef19 100755 --- a/vm/vm.hpp +++ b/vm/vm.hpp @@ -577,7 +577,9 @@ struct factor_vm void initialize_code_block(code_block *compiled); void fixup_labels(array *labels, code_block *compiled); code_block *allot_code_block(cell size, code_block_type type); - code_block *add_code_block(code_block_type type, cell code_, cell labels_, cell owner_, cell relocation_, cell parameters_, cell literals_); + code_block *add_code_block(code_block_type type, cell code_, cell labels_, + cell owner_, cell relocation_, cell parameters_, cell literals_, + cell frame_size_untagged); //code heap inline void check_code_pointer(cell ptr) { }