summaryrefslogtreecommitdiff
path: root/libguile/jit.c
AgeCommit message (Collapse)AuthorFilesLines
2024-08-13Fix compilation with C23Andy Wingo1-3/+3
* libguile/jit.c (is_unreachable): Rename from "unreachable", which is apparently a new reserved word in C23.
2023-11-20Add logand/immediate, ulogand/immediate primcallsAndy Wingo1-0/+19
* libguile/jit.c (compile_ulogand_immediate, compile_ulogand_immediate_slow) * libguile/vm-engine.c (ulogand_immediate): New JIT and interpreter support for ulogand/immediate. * module/language/cps/guile-vm/lower-primcalls.scm (string-ref): (vtable-vtable?): (vtable-field-boxed?): Emit ulogand/immediate. * module/language/cps/guile-vm/reify-primitives.scm (reify-primitives): Remove logand/immediate. Only emit ulogand/immediate if the immediate is a u8. Refactor mul/immediate. * module/language/cps/specialize-numbers.scm (specialize-operations): Produce ulogand/immediate if the result is a u64. * module/language/cps/effects-analysis.scm: * module/language/cps/types.scm (logand/immediate): Add effect and type inference for logand/immediate, ulogand/immediate, * module/language/cps/utils.scm (primcall-raw-representations): ulogand/immediate makes a u64. * module/language/tree-il/compile-cps.scm (convert): Generate logand/immediate if possible. * module/language/cps/compile-bytecode.scm (compile-function): * module/system/vm/assembler.scm (system): Add ulogand/immediate emitter. * libguile/loader.h (SCM_OBJCODE_MINOR_VERSION): Bump.
2023-10-02Fix branch fusingAndy Wingo1-0/+13
* libguile/jit.c (analyze): Skip over drop and pop, if present, during the analysis phase in addition to the compile phase.
2023-10-02Improve handling of push/pop/drop in jitAndy Wingo1-44/+246
Previously, these instructions were compiled directly. However, the JIT also wants to fuse comparisons with branches, and an intervening "drop" breaks that. Instead we take a different approach and rely on the compiler only emitting push/pop/drop in a peephole sort of way, and we can just simulate the temp stack space and dispatch directly. * libguile/jit.c (compile_push, compile_push_slow, compile_pop): (compile_pop_slow, compile_drop, compile_drop_slow): Crash if these are called. (COMPILE_WIDE_OP1, COMPILE_WIDE_OP2, COMPILE_WIDE_OP3, COMPILE_WIDE_OP4) (COMPILE_WIDE_OP5): (COMPILE_WIDE_DOP1, COMPILE_WIDE_DOP2, COMPILE_WIDE_DOP3) (COMPILE_WIDE_DOP4, COMPILE_WIDE_DOP5): New helpers. I didn't manage to share implementation with COMPILE_*. (COMPILE_WIDE_*): New variants of compilers that take their operands from an array instead of parsing the inline operands, relying on convention for how the compiler emits these instructions. (parse_wide_operands): New helper to parse out "wide" operands. (compile1, compile_slow_path): If we see a "push", parse wide operands. (compile): Move label capture for the slow path into compile_slow_path, because wide operands may skip some instructions.
2023-10-02Widen all jit compiler routines to take 32-bit operandsAndy Wingo1-180/+180
* libguile/jit.c (compile_*): Instead of using the minimum sized types that can represent the instruction's operand, use uint32_t. This will allow us to handle push/pop/drop without moving the SP.
2023-08-28Better compilation of calls to `raise-exception`Andy Wingo1-1/+12
Recognize `raise-exception` in the same way we recognize `throw`, though it is a bit less optimized and the boot story is not as complicated. * doc/ref/vm.texi (Non-Local Control Flow Instructions): * libguile/jit.c (compile_unreachable): (compile_unreachable_slow): * libguile/vm-engine.c (VM_NAME): * module/language/cps/compile-bytecode.scm (compile-function): * module/system/vm/assembler.scm (emit-unreachable): Add new "unreachable" instruction, inserted after a call to non-continuable `raise-exception`. * module/language/tree-il/compile-cps.scm (raise-exception): * module/language/tree-il/primitives.scm (*interesting-primitive-names*): Recognize raise-exception, and if it is called with just one argument, prune that branch of the control-flow graph.
2023-04-27Use SCM_GSUBR_MAX in place of the hardcoded numberDaniel Llorens1-2/+2
* libguile/gsubr.c (scm_apply_subr): Reference the limit. (get_subr_stub_code): As stated. * libguile/jit.c (compile_subr_call): As stated.
2022-12-20fix Apple Silicon JIT compilationAleix Conchillo FlaquƩ1-1/+24
* configure.ac: check for pthread_jit_write_protect_np. * libguile/jit.c: add support for Apple Silicon JIT compilation. Fixes https://debbugs.gnu.org/cgi/bugreport.cgi?bug=44505
2021-04-26Simplify module variable lookup slow-pathAndy Wingo1-0/+30
* libguile/intrinsics.h: * libguile/intrinsics.c (lookup_bound_public, lookup_bound_private): Two new intrinsics. (scm_bootstrap_intrinsics): Wire them up. * libguile/jit.c (compile_call_scm_from_scmn_scmn): (compile_call_scm_from_scmn_scmn_slow): (COMPILE_X8_S24__N32__N32__C32): Add JIT support for new instruction kind. * libguile/vm-engine.c (call-scm<-scmn-scmn): New instruction, takes arguments as non-immediate offsets, to avoid needless loads and register pressure. * module/language/cps/effects-analysis.scm: Add cases for new primcalls. * module/language/cps/compile-bytecode.scm (compile-function): Add new primcalls. * module/language/cps/reify-primitives.scm (cached-module-box): If the variable is bound, call lookup-bound-public / lookup-bound-private as appropriate instead of separately resolving the module, name, and doing the bound check. * module/language/tree-il/compile-bytecode.scm (emit-cached-module-box): Use new instructions. * module/system/vm/assembler.scm (define-scm<-scmn-scmn-intrinsic): (lookup-bound-public, lookup-bound-private): Add assembler support.
2021-03-13Add JIT capability for MinGWMike Gran1-13/+52
* libguile/jit.c [__MING32__]: add windows.h on Win32 (struct code_arena) [__MINGW32__]: a HANDLE for Win32 mmap (BIGENDIAN): rename to JIT_BIGENDIAN, to avoid collision with Win32 BIGENDIAN constant. All users changed (allocate_code_arena) [__MINGW32__]: add Win32 mmap allocator (emit_code) [__MINGW32__]: add Win32 munmap * libguile/lightening/lightening/lightening.c: remove unnecessary mman.h
2020-08-12Fix JIT compilation for jtableAndy Wingo1-1/+1
* libguile/jit.c (compile_jtable): Fix bounds check for index.
2020-08-03Add eq-immediate? instructionAndy Wingo1-0/+26
* libguile/jit.c (compile_eq_immediate, compile_eq_immediate_slow): Add JIT compiler. * libguile/vm-engine.c (eq_immediate): New instruction. * doc/ref/vm.texi (Comparison Instructions): Document. * module/system/vm/assembler.scm (encode-X8_S8_ZI16!/shuffle): New shuffler. * module/system/vm/disassembler.scm (code-annotation): Add eq-immediate? case.
2020-07-30Add sign-extending make-immediate instructionAndy Wingo1-0/+19
* doc/ref/vm.texi (Instruction Set, Constant Instructions): Document new instruction. * libguile/instructions.c (FOR_EACH_INSTRUCTION_WORD_TYPE): New first word kind with zi16 operand. * libguile/jit.c (compile_make_immediate, compile_make_immediate_slow): New compilers. (COMPILE_X8_S8_ZI16): New operand kind. * libguile/vm-engine.c (make-immediate): New instruction. * module/language/bytecode.scm: * module/system/vm/assembler.scm (encode-X8_S8_ZI16<-/shuffle): (signed-bits, load-constant): Support the new instruction kind. * module/system/vm/disassembler.scm (disassemblers) (sign-extended-immediate, code-annotation): Support for zi16 operands.
2020-07-30Update use of jit_begin_data APIAndy Wingo1-1/+1
* libguile/jit.c (compile_jtable): Pass computed jump table size.
2020-07-30Add JIT implementation for jtableAndy Wingo1-5/+36
* libguile/jit.c (compile_jtable): Implement.
2020-07-23Add jtable instructionAndy Wingo1-0/+41
* doc/ref/vm.texi (Instruction Set): Document new v32-x8-l24 instruction kind. (Branch Instructions): Document jtable. * libguile/instructions.c (FOR_EACH_INSTRUCTION_WORD_TYPE): Add V32_X8_L24. * libguile/jit.c (compile_jtable, compile_jtable_slow): (COMPILE_X8_S24__V32_X8_L24, analyze): Add stub JIT compiler implementation. * libguile/vm-engine.c (jtable): New instruction. * module/language/bytecode.scm (instruction-arity): Deprecate. * module/system/vm/assembler.scm (encoder, assembler): Add V32_X8_L24 case. * module/system/vm/disassembler.scm (u32-ref, s32-ref): Move definitions to expansion-time only. (define-op-handlers): New definition, replacing visit-opcodes. (disassemblers, jump-parsers, stack-effect-parsers, clobber-parsers): Rework in terms of define-op-handlers. Default case becomes #f, and add support for jtable. (disassemble-one, instruction-relative-jump-targets) (instruction-stack-size-after, instruction-slot-clobbers): Inline default case in the lookup procedure, not copied in the handler vector. (compute-labels): Add jtable case. (instruction-lengths-vector, instruction-length): Rework to allow variable-length instructions, and mark jtable as being variable-length. (instruction-has-fallthrough?): Add jtable to the no-fallthrough set.
2020-05-11Reload FP if needed in bind-rest alsoAndy Wingo1-0/+6
* libguile/jit.c (compile_bind_rest): Reload FP if needed
2020-05-11Fix JIT asserts with different code generated by baselineAndy Wingo1-5/+22
* libguile/jit.c (UNREACHABLE): New register state. (unreachable): New predicate. (ASSERT_HAS_REGISTER_STATE): Succeed when unreachable. (compile_throw, compile_throw_value, compile_throw_value_and_data): Set unreachable flag. (compile_receive_values): Reload FP if needed.
2020-04-29Add intrinsics for a baseline compilerAndy Wingo1-0/+52
Since there's no optimization in the baseline compiler, there's no sense in instruction explosion. * libguile/intrinsics.h: * libguile/intrinsics.c ($car, $cdr, $set-car!, $set-cdr!, $variable-ref, $variable-set!, $vector-length, $vector-ref, $vector-set!, $vector-ref/immediate, $vector-set!, $allocate-struct, $struct-vtable, $struct-ref, $struct-set! $struct-ref/immediate, $struct-set!): New intrinsics. * libguile/jit.c (compile_call_scm_scm, compile_call_scm_scm_slow) (compile_call_scm_scm_scm, compile_call_scm_scm_scm_slow) (compile_call_scm_uimm_scm, compile_call_scm_uimm_scm_slow): New code generators. * libguile/vm-engine.c (call-scm-scm, call-scm-scm-scm, call-scm-uimm-scm): New instructions. * module/system/vm/assembler.scm (emit-null?, emit-false?, emit-nil?): Export these. Also export emitters for the new intrinsics. (define-scm-scm-intrinsic, define-scm-uimm-scm-intrinsic) (define-scm-scm-scm-intrinsic): New helpers. * doc/ref/vm.texi (Intrinsic Call Instructions): Add new instructions.
2020-02-26Add support for perf map creationAndy Wingo1-0/+25
* libguile/jit.c (create_perf_map_once, create_perf_map, perf_map): New locals. (compute_mcode): Add an entry to perf_map for emitted JIT code.
2020-02-19Better debugging in jit.cAndy Wingo1-9/+36
* libguile/jit.c (emit_direct_tail_call): Assert self-tail call has mcode. (opcodes_seen, bitvector_ref, bitvector_set, compile1): Make the opcodes_seen set more compact, and log all instruction emissions at level 3. (compute_mcode): Don't overwrite mcode if compilation fails.
2020-01-11Fix build on 32-bit systems with JIT supportAndy Wingo1-1/+7
* libguile/intrinsics.h: Add s64->f64 intrinsic, for 32-bit targets. * libguile/jit.c (compile_s64_to_f64): Call the intrinsic for 32-bit targets.
2019-12-10Move less? slow path out of lineAndy Wingo1-32/+31
* libguile/jit.c (compile_less, compile_less_slow): Move slow path out of line.
2019-12-10Add fixnum fast-path for =Andy Wingo1-6/+29
* libguile/jit.c (compile_numerically_equal): Add fixnum fast-path. (compile_numerically_equal_slow): New slow path.
2019-12-10Move allocate-pointerless-words/immediate slow path out of lineAndy Wingo1-12/+19
* libguile/jit.c (compile_allocate_pointerless_words_immediate) (compile_allocate_pointerless_words_immediate_slow): Move slow path out of line.
2019-12-10Move allocate-words/immediate slow path out of lineAndy Wingo1-12/+19
* libguile/jit.c (compile_allocate_words_immediate) (compile_allocate_words_immediate_slow): Move slow path out of line.
2019-12-10Move assert-nargs-le slow path out of lineAndy Wingo1-10/+5
* libguile/jit.c (compile_assert_nargs_le) (compile_assert_nargs_le_slow): Move slow path out of line.
2019-12-10Add out-of-line slow path for abortAndy Wingo1-7/+3
* libguile/jit.c (compile_abort, compile_abort_slow): Move interpreter fallback to slow path.
2019-12-10Add out-of-line slow path for compose-continuationAndy Wingo1-6/+2
* libguile/jit.c (compile_compose_continuation) (compile_compose_continuation_slow): Move interpreter fallback to slow path.
2019-12-10Add subr-call out-of-line slow pathAndy Wingo1-9/+14
* libguile/jit.c (emit_branch_if_heap_object_has_tc7): New helper. (compile_subr_call, compile_subr_call_slow): Add a slow path for the values case.
2019-12-10Move alloc-frame slow path out of lineAndy Wingo1-25/+50
* libguile/jit.c (compile_alloc_frame, compile_alloc_frame_slow): Move slow path out of line. (emit_alloc_frame_for_sp_fast, emit_alloc_frame_for_sp_slow): New helpers. (emit_alloc_frame): Refactor to use the new helpers. (compile_push, compile_push_slow): Use the new helpers. (compile_assert_nargs_ee_locals, compile_assert_nargs_ee_locals_slow): Split off a slow path.
2019-12-10Move assert-nargs-ge slow path out of lineAndy Wingo1-12/+5
* libguile/jit.c (compile_assert_nargs_ge) (compile_assert_nargs_ge_slow): Move slow path out of line.
2019-12-10Move assert-nargs-ee slow path out of lineAndy Wingo1-11/+14
* libguile/jit.c (compile_assert_nargs_ee) (compile_assert_nargs_ee_slow): Move slow path out of line.
2019-12-10Move receive-values slow path out of lineAndy Wingo1-18/+10
* libguile/jit.c (compile_receive_values, compile_receive_values_slow): Move slow path out of line.
2019-12-10Move receive slow path out of lineAndy Wingo1-7/+4
* libguile/jit.c (compile_receive, compile_receive_slow): Move slow path out of line.
2019-12-10Move handle-interrupts slow path out of lineAndy Wingo1-17/+9
* libguile/jit.c (compile_handle_interrupts) (compile_handle_interrupts_slow): Move slow path out of line.
2019-12-10Move add, sub slow paths out of lineAndy Wingo1-37/+34
* libguile/jit.c (compile_call_scm_from_scm_sc) (compile_call_scm_from_scm_scm_slow): Move non-fixnum path out of line.
2019-12-10Move add/immediate, sub/immediate slow paths out of lineAndy Wingo1-29/+34
* libguile/jit.c (compile_call_scm_from_scm_uimm) (compile_call_scm_from_scm_uimm_slow): Move non-fixnum path out of line.
2019-12-10Add infrastructure for out-of-line JIT compilation of slow pathsAndy Wingo1-20/+750
* libguile/jit.c (struct pending_reloc): Rename target_vcode_offset field to target_label_offset. (inline_label_offset, slow_label_offset): New helpers. (emit_direct_tail_call): Use inline_label_offset helper. (add_pending_reloc): Factor out of add_inter_instruction_patch. (add_inter_instruction_patch): Use inline_label_offset helper. (add_slow_path_patch): New helper. (continue_after_slow_path): New helper. Add slow path compilers for all instructions. (compile_slow_path): New helper. (compile): Compile slow paths after main code. (compute_mcode): Allocate twice as many labels.
2019-12-09Remove vm->sp_min_since_gcAndy Wingo1-10/+4
* libguile/jit.c (emit_alloc_frame_for_sp): * libguile/vm-engine.c (ALLOC_FRAME, RESET_FRAME): * libguile/vm.c (vm_increase_sp, scm_i_vm_prepare_stack): (return_unused_stack_to_os, vm_expand_stack, alloc_frame): (scm_call_with_stack_overflow_handler): * libguile/vm.h (struct scm_vm): Remove sp_min_since_gc handling. It was a very minor optimization when it was centralized in vm.c, but now with JIT it's causing too much duplicate code generation.
2019-12-08Fix JIT tier-up from within loops for already-JIT-compiled functionsAndy Wingo1-26/+30
* libguile/jit.c (scm_jit_compute_mcode): If a caller wants mcode for a loop but the function already has mcode, instead of punting, just compile again.
2019-09-01Optimize fixnum or s64 -> f64 conversionsAndy Wingo1-0/+9
* libguile/intrinsics.c (scm_bootstrap_intrinsics): * libguile/intrinsics.h (SCM_FOR_ALL_VM_INTRINSICS): Add "inexact" intrinsic. * libguile/jit.c (compile_s64_to_f64): New compiler. * libguile/vm-engine.c (s64->f64): New instruction. * module/language/cps/effects-analysis.scm (heap-numbers-equal?): * module/language/cps/reify-primitives.scm (compute-known-primitives): * module/language/cps/slot-allocation.scm (compute-var-representations): * module/language/cps/specialize-numbers.scm (fixnum->f64): (specialize-operations): * module/language/cps/type-fold.scm (scm->f64, inexact): * module/language/cps/types.scm (inexact, s64->f64): * module/language/tree-il/cps-primitives.scm (exact->inexact): * module/language/tree-il/primitives.scm (*interesting-primitive-names*): (*effect-free-primitives*): * module/system/vm/assembler.scm: Recognize exact->inexact as a primitive, and optimize it. Add compiler support for new "inexact" and "s64->f64" primcalls.
2019-08-26Compiler allocates boxed flonums in unmarked spaceAndy Wingo1-0/+54
This fixes a bug whereby the compiler would sometimes allocate floats in marked space. * libguile/gc-inline.h (scm_inline_gc_malloc_pointerless_words): New internal helper. * libguile/intrinsics.h (SCM_FOR_ALL_VM_INTRINSICS): * libguile/intrinsics.c (allocate_pointerless_words): (allocate_pointerless_words_with_freelist): New intrinsics. * libguile/jit.c (compile_allocate_pointerless_words): (compile_allocate_pointerless_words_immediate): New compilers. * libguile/vm-engine.c (allocate_pointerless_words) (allocate_pointerless_words_immediate): New opcodes. * module/language/cps/compile-bytecode.scm (compile-function): * module/language/cps/effects-analysis.scm (param): * module/language/cps/reify-primitives.scm (reify-primitives): * module/language/cps/specialize-primcalls.scm (specialize-primcalls): * module/language/cps/types.scm (allocate-words): (allocate-words/immediate): * module/system/vm/assembler.scm (system): Add support for the new opcodes.
2019-08-24Unbox floor/ceiling and trigonometric functions where possibleAndy Wingo1-1/+26
* libguile/intrinsics.c (scm_atan1): New intrinsic, wrapping scm_atan. (scm_bootstrap_intrinsics): Add new intrinsics. * libguile/intrinsics.h (scm_t_f64_from_f64_f64_intrinsic): New intrinsic type. (SCM_FOR_ALL_VM_INTRINSICS): Add intrinsics for floor, ceiling, sin, cos, tan, asin, acos, atan, and their unboxed counterparts. * libguile/jit.c (sp_f64_operand): New helper. (compile_call_f64_from_f64, compile_call_f64_from_f64_f64): Call out to intrinsics. * libguile/vm-engine.c (call-f64<-f64-f64): New opcode. * module/language/cps/effects-analysis.scm: Add new intrinsics. * module/language/cps/reify-primitives.scm (compute-known-primitives): Add new intrinsics. * module/language/cps/slot-allocation.scm (compute-var-representations): Add 'f64 slot types for the new unboxed intrinsics. * module/language/cps/specialize-numbers.scm (specialize-operations): Support unboxing the new intrinsics. * module/language/cps/types.scm: Define type inferrers for the new intrinsics. * module/language/tree-il/cps-primitives.scm: Define CPS translations for the new intrinsics. * module/language/tree-il/primitives.scm (*interesting-primitive-names*): (*effect-free-primitives*, atan): Define primitive resolvers. * module/system/vm/assembler.scm: Export assemblers for the new intrinsics. (define-f64<-f64-f64-intrinsic): New helper.
2019-08-04Add support for optimized unboxed abs and sqrtAndy Wingo1-0/+26
Some components of this have been wired up for a while; this commit finishes the compiler, runtime, and JIT support. * libguile/intrinsics.h (SCM_FOR_ALL_VM_INTRINSICS): * libguile/intrinsics.c (scm_bootstrap_intrinsics): Declare the new intrinsics. * libguile/jit.c (compile_call_f64_from_f64): Define code generators for the new intrinsics. * libguile/vm-engine.c (call-f64<-f64): New instruction. * module/language/cps/effects-analysis.scm: * module/language/cps/reify-primitives.scm (compute-known-primitives): * module/language/cps/slot-allocation.scm (compute-var-representations): * module/language/cps/specialize-numbers.scm (specialize-operations): * module/language/tree-il/cps-primitives.scm (abs): * module/system/vm/assembler.scm (system, define-f64<-f64-intrinsic): (sqrt, abs, fsqrt, fabs): * module/language/cps/types.scm (fsqrt, fabs): Add new f64<-f64 primitives.
2019-08-03Fix some compiler warnings on 64-bit buildsAndy Wingo1-18/+2
2019-08-02Fix calls to handle-interrupts trampoline on ARMv7Andy Wingo1-2/+0
* libguile/jit.c (initialize_jit): Keep handle_interrupts_trampoline as an address, not a function pointer.
2019-06-20Add an inlined jit fast-path for allocate-words/immediateAndy Wingo1-7/+35
* libguile/intrinsics.c (allocate_words_with_freelist) (scm_bootstrap_intrinsics): * libguile/intrinsics.h (SCM_FOR_ALL_VM_INTRINSICS): New intrinsic. * libguile/jit.c (compile_allocate_words_immediate): Add fast-path. A marginal improvement.
2019-06-20Fix compilation on GCC 5.5Andy Wingo1-5/+8
* libguile/jit.c (OLD_FP_FOR_RETURN_TRAMPOLINE): Initialize static const var from CPP define instead of T0. (compile_return_values, emit_return_to_interpreter_trampoline): Adapt to upper-casing.
2019-06-20Use call/return instructions for non-tail callsAndy Wingo1-24/+34
This change speeds up the indirect branches at return sites by taking advantage of the CPU's return address stack. * libguile/jit.c (emit_push_frame): Don't store the mra; we do that via a trampoline. (emit_handle_interrupts_trampoline): Take MRA from link register instead of T0. (compile_call, compile_call_label): Compute MRA via the new jmpi_with_link lightening instruction. (compile_return_values): Return to caller via ret instead of jmp. (compile_handle_interrupts): Jump to handle-interrupts trampoline via jmpi_with_link, to provide the MRA. (initialize_jit): Bless the trampolines so that they are valid operands to BX on ARM.