break;
case Bsub1:
case Badd1:
+ case Bnegate:
case Breturn:
new_bb = true;
break;
{
/* (FIXNUMP (TOP) && XFIXNUM (TOP) != MOST_NEGATIVE_FIXNUM
- ? make_fixnum (XFIXNUM (TOP) - 1)
- : Fsub1 (TOP)) */
+ ? make_fixnum (XFIXNUM (TOP) - 1)
+ : Fsub1 (TOP)) */
gcc_jit_block *sub1_inline_block =
gcc_jit_function_new_block (comp.func, "inline_sub1");
{
/* (FIXNUMP (TOP) && XFIXNUM (TOP) != MOST_POSITIVE_FIXNUM
- ? make_fixnum (XFIXNUM (TOP) + 1)
- : Fadd (TOP)) */
+ ? make_fixnum (XFIXNUM (TOP) + 1)
+ : Fadd (TOP)) */
gcc_jit_block *add1_inline_block =
gcc_jit_function_new_block (comp.func, "inline_add1");
EMIT_SCRATCH_CALL_N ("Fminus", 2);
break;
case Bnegate:
- error ("Bnegate unsupported bytecode\n");
+ {
+
+ /* (FIXNUMP (TOP) && XFIXNUM (TOP) != MOST_NEGATIVE_FIXNUM
+ ? make_fixnum (- XFIXNUM (TOP))
+ : Fminus (1, &TOP)) */
+
+ gcc_jit_block *negate_inline_block =
+ gcc_jit_function_new_block (comp.func, "inline_negate");
+ gcc_jit_block *negate_fcall_block =
+ gcc_jit_function_new_block (comp.func, "fcall_negate");
+
+ gcc_jit_rvalue *tos_as_num =
+ comp_XFIXNUM (gcc_jit_lvalue_as_rvalue (TOS));
+
+ comp_emit_cond_jump (
+ gcc_jit_context_new_binary_op (
+ comp.ctxt,
+ NULL,
+ GCC_JIT_BINARY_OP_LOGICAL_AND,
+ comp.bool_type,
+ comp_cast (comp.bool_type,
+ comp_FIXNUMP (gcc_jit_lvalue_as_rvalue (TOS))),
+ gcc_jit_context_new_comparison (comp.ctxt,
+ NULL,
+ GCC_JIT_COMPARISON_NE,
+ tos_as_num,
+ comp.most_negative_fixnum)),
+ negate_inline_block,
+ negate_fcall_block);
+
+ gcc_jit_rvalue *negate_inline_res =
+ gcc_jit_context_new_unary_op (comp.ctxt,
+ NULL,
+ GCC_JIT_UNARY_OP_MINUS,
+ comp.long_long_type,
+ tos_as_num);
+
+ gcc_jit_block_add_assignment (negate_inline_block,
+ NULL,
+ TOS,
+ comp_make_fixnum (negate_inline_block,
+ negate_inline_res));
+ basic_block_t bb_orig = *comp.bblock;
+
+ comp.bblock->gcc_bb = negate_fcall_block;
+ EMIT_SCRATCH_CALL_N ("Fminus", 1);
+ *comp.bblock = bb_orig;
+
+ gcc_jit_block_end_with_jump (negate_inline_block, NULL,
+ bb_map[pc].gcc_bb);
+ gcc_jit_block_end_with_jump (negate_fcall_block, NULL,
+ bb_map[pc].gcc_bb);
+ }
break;
case Bplus:
EMIT_SCRATCH_CALL_N ("Fplus", 2);
(ert-deftest comp-tests-fixnum ()
"Testing some fixnum inline operation."
- (defun comp-tests-fixnum-1--f (x)
+ (defun comp-tests-fixnum-1-minus-f (x)
+ ;; Bsub1
(1- x))
- (defun comp-tests-fixnum-1+-f (x)
+ (defun comp-tests-fixnum-1-plus-f (x)
+ ;; Badd1
(1+ x))
-
- (byte-compile #'comp-tests-fixnum-1--f)
- (byte-compile #'comp-tests-fixnum-1+-f)
- ;; (native-compile #'comp-tests-fixnum-1--f)
- (native-compile #'comp-tests-fixnum-1+-f)
-
- (should (= (comp-tests-fixnum-1--f 10) 9))
- (should (= (comp-tests-fixnum-1--f most-negative-fixnum)
+ (defun comp-tests-fixnum-minus-f (x)
+ ;; Bnegate
+ (- x))
+
+ (byte-compile #'comp-tests-fixnum-1-minus-f)
+ (byte-compile #'comp-tests-fixnum-1-plus-f)
+ (byte-compile #'comp-tests-fixnum-minus-f)
+ (native-compile #'comp-tests-fixnum-1-minus-f)
+ (native-compile #'comp-tests-fixnum-1-plus-f)
+ (native-compile #'comp-tests-fixnum-minus-f)
+
+ (should (= (comp-tests-fixnum-1-minus-f 10) 9))
+ (should (= (comp-tests-fixnum-1-minus-f most-negative-fixnum)
(1- most-negative-fixnum)))
(should (equal (condition-case err
- (comp-tests-fixnum-1--f 'a)
+ (comp-tests-fixnum-1-minus-f 'a)
(error err))
'(wrong-type-argument number-or-marker-p a)))
- (should (= (comp-tests-fixnum-1+-f 10) 11))
- (should (= (comp-tests-fixnum-1+-f most-positive-fixnum)
+ (should (= (comp-tests-fixnum-1-plus-f 10) 11))
+ (should (= (comp-tests-fixnum-1-plus-f most-positive-fixnum)
(1+ most-positive-fixnum)))
(should (equal (condition-case err
- (comp-tests-fixnum-1+-f 'a)
+ (comp-tests-fixnum-1-plus-f 'a)
+ (error err))
+ '(wrong-type-argument number-or-marker-p a)))
+ (should (= (comp-tests-fixnum-minus-f 10) -10))
+ (should (= (comp-tests-fixnum-minus-f most-negative-fixnum)
+ (- most-negative-fixnum)))
+ (should (equal (condition-case err
+ (comp-tests-fixnum-minus-f 'a)
(error err))
'(wrong-type-argument number-or-marker-p a))))