diff options
| author | Andrea Corallo | 2019-06-16 11:21:29 +0200 |
|---|---|---|
| committer | Andrea Corallo | 2020-01-01 11:33:42 +0100 |
| commit | 2a1bb41c14fba3ecb2f7ccdb251918ea0ac30c41 (patch) | |
| tree | 34e0b7be78593888e1c9b9364417aa3e11d96112 /src | |
| parent | 0438e245a15e91aac93a5df812ce292dd1ff681b (diff) | |
| download | emacs-2a1bb41c14fba3ecb2f7ccdb251918ea0ac30c41.tar.gz emacs-2a1bb41c14fba3ecb2f7ccdb251918ea0ac30c41.zip | |
Bintegerp support
Diffstat (limited to 'src')
| -rw-r--r-- | src/comp.c | 227 |
1 files changed, 143 insertions, 84 deletions
diff --git a/src/comp.c b/src/comp.c index 1b1401caff9..f3fd8dc16bb 100644 --- a/src/comp.c +++ b/src/comp.c | |||
| @@ -187,6 +187,7 @@ typedef struct { | |||
| 187 | gcc_jit_rvalue *inttypebits; | 187 | gcc_jit_rvalue *inttypebits; |
| 188 | gcc_jit_rvalue *lisp_int0; | 188 | gcc_jit_rvalue *lisp_int0; |
| 189 | gcc_jit_function *pseudovectorp; | 189 | gcc_jit_function *pseudovectorp; |
| 190 | gcc_jit_function *bool_to_lisp_obj; | ||
| 190 | basic_block_t *bblock; /* Current basic block */ | 191 | basic_block_t *bblock; /* Current basic block */ |
| 191 | Lisp_Object func_hash; /* f_name -> gcc_func */ | 192 | Lisp_Object func_hash; /* f_name -> gcc_func */ |
| 192 | } comp_t; | 193 | } comp_t; |
| @@ -360,7 +361,7 @@ emit_call (const char *f_name, gcc_jit_type *ret_type, unsigned nargs, | |||
| 360 | 361 | ||
| 361 | INLINE static void | 362 | INLINE static void |
| 362 | emit_cond_jump (gcc_jit_rvalue *test, | 363 | emit_cond_jump (gcc_jit_rvalue *test, |
| 363 | gcc_jit_block *then_target, gcc_jit_block *else_target) | 364 | gcc_jit_block *then_target, gcc_jit_block *else_target) |
| 364 | { | 365 | { |
| 365 | gcc_jit_block_end_with_conditional (comp.bblock->gcc_bb, | 366 | gcc_jit_block_end_with_conditional (comp.bblock->gcc_bb, |
| 366 | NULL, | 367 | NULL, |
| @@ -503,72 +504,6 @@ emit_CONSP (gcc_jit_rvalue *obj) | |||
| 503 | return emit_TAGGEDP(obj, Lisp_Cons); | 504 | return emit_TAGGEDP(obj, Lisp_Cons); |
| 504 | } | 505 | } |
| 505 | 506 | ||
| 506 | /* Declare a substitute for PSEUDOVECTORP as inline function. */ | ||
| 507 | |||
| 508 | static void | ||
| 509 | declare_PSEUDOVECTORP (void) | ||
| 510 | { | ||
| 511 | gcc_jit_param *param[2] = | ||
| 512 | { gcc_jit_context_new_param (comp.ctxt, | ||
| 513 | NULL, | ||
| 514 | comp.lisp_obj_type, | ||
| 515 | "a"), | ||
| 516 | gcc_jit_context_new_param (comp.ctxt, | ||
| 517 | NULL, | ||
| 518 | comp.int_type, | ||
| 519 | "code") }; | ||
| 520 | |||
| 521 | comp.pseudovectorp = | ||
| 522 | gcc_jit_context_new_function (comp.ctxt, NULL, | ||
| 523 | GCC_JIT_FUNCTION_ALWAYS_INLINE, | ||
| 524 | comp.bool_type, | ||
| 525 | "PSEUDOVECTORP", | ||
| 526 | 2, | ||
| 527 | param, | ||
| 528 | 0); | ||
| 529 | |||
| 530 | gcc_jit_block *initial_block = | ||
| 531 | gcc_jit_function_new_block (comp.pseudovectorp, "PSEUDOVECTORP_initial_block"); | ||
| 532 | |||
| 533 | gcc_jit_block *ret_false_b = | ||
| 534 | gcc_jit_function_new_block (comp.pseudovectorp, "ret_false"); | ||
| 535 | |||
| 536 | gcc_jit_block *call_pseudovector_typep_b = | ||
| 537 | gcc_jit_function_new_block (comp.pseudovectorp, "call_pseudovector"); | ||
| 538 | |||
| 539 | /* Set current context as needed */ | ||
| 540 | basic_block_t bblock = { .gcc_bb = initial_block, | ||
| 541 | .terminated = false }; | ||
| 542 | comp.bblock = &bblock; | ||
| 543 | comp.func = comp.pseudovectorp; | ||
| 544 | |||
| 545 | emit_cond_jump ( | ||
| 546 | emit_cast (comp.bool_type, | ||
| 547 | emit_VECTORLIKEP (gcc_jit_param_as_rvalue (param[0]))), | ||
| 548 | call_pseudovector_typep_b, | ||
| 549 | ret_false_b); | ||
| 550 | |||
| 551 | comp.bblock->gcc_bb = ret_false_b; | ||
| 552 | gcc_jit_block_end_with_return (ret_false_b, | ||
| 553 | NULL, | ||
| 554 | gcc_jit_context_new_rvalue_from_int( | ||
| 555 | comp.ctxt, | ||
| 556 | comp.bool_type, | ||
| 557 | false)); | ||
| 558 | |||
| 559 | gcc_jit_rvalue *args[2] = | ||
| 560 | { gcc_jit_param_as_rvalue (param[0]), | ||
| 561 | gcc_jit_param_as_rvalue (param[1]) }; | ||
| 562 | comp.bblock->gcc_bb = call_pseudovector_typep_b; | ||
| 563 | /* FIXME XUNTAG missing here. */ | ||
| 564 | gcc_jit_block_end_with_return (call_pseudovector_typep_b, | ||
| 565 | NULL, | ||
| 566 | emit_call ("helper_PSEUDOVECTOR_TYPEP_XUNTAG", | ||
| 567 | comp.bool_type, | ||
| 568 | 2, | ||
| 569 | args)); | ||
| 570 | } | ||
| 571 | |||
| 572 | static gcc_jit_rvalue * | 507 | static gcc_jit_rvalue * |
| 573 | emit_BIGNUMP (gcc_jit_rvalue *obj) | 508 | emit_BIGNUMP (gcc_jit_rvalue *obj) |
| 574 | { | 509 | { |
| @@ -579,10 +514,11 @@ emit_BIGNUMP (gcc_jit_rvalue *obj) | |||
| 579 | comp.int_type, | 514 | comp.int_type, |
| 580 | PVEC_BIGNUM) }; | 515 | PVEC_BIGNUM) }; |
| 581 | 516 | ||
| 582 | return emit_call ("PSEUDOVECTORP", | 517 | return gcc_jit_context_new_call (comp.ctxt, |
| 583 | comp.bool_type, | 518 | NULL, |
| 584 | 2, | 519 | comp.pseudovectorp, |
| 585 | args); | 520 | 2, |
| 521 | args); | ||
| 586 | } | 522 | } |
| 587 | 523 | ||
| 588 | static gcc_jit_rvalue * | 524 | static gcc_jit_rvalue * |
| @@ -651,7 +587,8 @@ emit_INTEGERP (gcc_jit_rvalue *obj) | |||
| 651 | NULL, | 587 | NULL, |
| 652 | GCC_JIT_BINARY_OP_LOGICAL_OR, | 588 | GCC_JIT_BINARY_OP_LOGICAL_OR, |
| 653 | comp.bool_type, | 589 | comp.bool_type, |
| 654 | emit_FIXNUMP (obj), | 590 | emit_cast (comp.bool_type, |
| 591 | emit_FIXNUMP (obj)), | ||
| 655 | emit_BIGNUMP (obj)); | 592 | emit_BIGNUMP (obj)); |
| 656 | } | 593 | } |
| 657 | 594 | ||
| @@ -687,7 +624,7 @@ emit_make_fixnum (gcc_jit_block *block, gcc_jit_rvalue *obj) | |||
| 687 | } | 624 | } |
| 688 | 625 | ||
| 689 | /* Construct fill and return a lisp object form a raw pointer. */ | 626 | /* Construct fill and return a lisp object form a raw pointer. */ |
| 690 | 627 | /* TODO should we pass the bb? */ | |
| 691 | static gcc_jit_rvalue * | 628 | static gcc_jit_rvalue * |
| 692 | emit_lisp_obj_from_ptr (basic_block_t *bblock, void *p) | 629 | emit_lisp_obj_from_ptr (basic_block_t *bblock, void *p) |
| 693 | { | 630 | { |
| @@ -745,16 +682,19 @@ emit_callN (const char *f_name, unsigned nargs, gcc_jit_rvalue **args) | |||
| 745 | 682 | ||
| 746 | for (int i = 0; i < nargs; i++) { | 683 | for (int i = 0; i < nargs; i++) { |
| 747 | gcc_jit_rvalue *idx = | 684 | gcc_jit_rvalue *idx = |
| 748 | gcc_jit_context_new_rvalue_from_int (comp.ctxt, | 685 | gcc_jit_context_new_rvalue_from_int ( |
| 749 | gcc_jit_context_get_type(comp.ctxt, | 686 | comp.ctxt, |
| 750 | GCC_JIT_TYPE_UNSIGNED_INT), | 687 | gcc_jit_context_get_type(comp.ctxt, |
| 751 | i); | 688 | GCC_JIT_TYPE_UNSIGNED_INT), |
| 752 | gcc_jit_block_add_assignment (comp.bblock->gcc_bb, NULL, | 689 | i); |
| 753 | gcc_jit_context_new_array_access (comp.ctxt, | 690 | gcc_jit_block_add_assignment ( |
| 754 | NULL, | 691 | comp.bblock->gcc_bb, |
| 755 | gcc_jit_lvalue_as_rvalue(p), | 692 | NULL, |
| 756 | idx), | 693 | gcc_jit_context_new_array_access (comp.ctxt, |
| 757 | args[i]); | 694 | NULL, |
| 695 | gcc_jit_lvalue_as_rvalue(p), | ||
| 696 | idx), | ||
| 697 | args[i]); | ||
| 758 | } | 698 | } |
| 759 | 699 | ||
| 760 | args[0] = gcc_jit_context_new_rvalue_from_int(comp.ctxt, | 700 | args[0] = gcc_jit_context_new_rvalue_from_int(comp.ctxt, |
| @@ -765,6 +705,118 @@ emit_callN (const char *f_name, unsigned nargs, gcc_jit_rvalue **args) | |||
| 765 | return emit_call (f_name, comp.lisp_obj_type, 2, args); | 705 | return emit_call (f_name, comp.lisp_obj_type, 2, args); |
| 766 | } | 706 | } |
| 767 | 707 | ||
| 708 | /* Declare a substitute for PSEUDOVECTORP as inline function. */ | ||
| 709 | |||
| 710 | static void | ||
| 711 | declare_PSEUDOVECTORP (void) | ||
| 712 | { | ||
| 713 | gcc_jit_param *param[2] = | ||
| 714 | { gcc_jit_context_new_param (comp.ctxt, | ||
| 715 | NULL, | ||
| 716 | comp.lisp_obj_type, | ||
| 717 | "a"), | ||
| 718 | gcc_jit_context_new_param (comp.ctxt, | ||
| 719 | NULL, | ||
| 720 | comp.int_type, | ||
| 721 | "code") }; | ||
| 722 | |||
| 723 | comp.pseudovectorp = | ||
| 724 | gcc_jit_context_new_function (comp.ctxt, NULL, | ||
| 725 | GCC_JIT_FUNCTION_ALWAYS_INLINE, | ||
| 726 | comp.bool_type, | ||
| 727 | "PSEUDOVECTORP", | ||
| 728 | 2, | ||
| 729 | param, | ||
| 730 | 0); | ||
| 731 | |||
| 732 | gcc_jit_block *initial_block = | ||
| 733 | gcc_jit_function_new_block (comp.pseudovectorp, "PSEUDOVECTORP_initial_block"); | ||
| 734 | |||
| 735 | gcc_jit_block *ret_false_b = | ||
| 736 | gcc_jit_function_new_block (comp.pseudovectorp, "ret_false"); | ||
| 737 | |||
| 738 | gcc_jit_block *call_pseudovector_typep_b = | ||
| 739 | gcc_jit_function_new_block (comp.pseudovectorp, "call_pseudovector"); | ||
| 740 | |||
| 741 | /* Set current context as needed */ | ||
| 742 | basic_block_t bblock = { .gcc_bb = initial_block, | ||
| 743 | .terminated = false }; | ||
| 744 | comp.bblock = &bblock; | ||
| 745 | comp.func = comp.pseudovectorp; | ||
| 746 | |||
| 747 | emit_cond_jump ( | ||
| 748 | emit_cast (comp.bool_type, | ||
| 749 | emit_VECTORLIKEP (gcc_jit_param_as_rvalue (param[0]))), | ||
| 750 | call_pseudovector_typep_b, | ||
| 751 | ret_false_b); | ||
| 752 | |||
| 753 | comp.bblock->gcc_bb = ret_false_b; | ||
| 754 | gcc_jit_block_end_with_return (ret_false_b, | ||
| 755 | NULL, | ||
| 756 | gcc_jit_context_new_rvalue_from_int( | ||
| 757 | comp.ctxt, | ||
| 758 | comp.bool_type, | ||
| 759 | false)); | ||
| 760 | |||
| 761 | gcc_jit_rvalue *args[2] = | ||
| 762 | { gcc_jit_param_as_rvalue (param[0]), | ||
| 763 | gcc_jit_param_as_rvalue (param[1]) }; | ||
| 764 | comp.bblock->gcc_bb = call_pseudovector_typep_b; | ||
| 765 | /* FIXME XUNTAG missing here. */ | ||
| 766 | gcc_jit_block_end_with_return (call_pseudovector_typep_b, | ||
| 767 | NULL, | ||
| 768 | emit_call ("helper_PSEUDOVECTOR_TYPEP_XUNTAG", | ||
| 769 | comp.bool_type, | ||
| 770 | 2, | ||
| 771 | args)); | ||
| 772 | } | ||
| 773 | |||
| 774 | /* Declare a function to convert boolean into t or nil */ | ||
| 775 | |||
| 776 | static void | ||
| 777 | declare_bool_to_lisp_obj (void) | ||
| 778 | { | ||
| 779 | /* x ? Qt : Qnil */ | ||
| 780 | gcc_jit_param *param = gcc_jit_context_new_param (comp.ctxt, | ||
| 781 | NULL, | ||
| 782 | comp.bool_type, | ||
| 783 | "x"); | ||
| 784 | comp.bool_to_lisp_obj = | ||
| 785 | gcc_jit_context_new_function (comp.ctxt, NULL, | ||
| 786 | GCC_JIT_FUNCTION_ALWAYS_INLINE, | ||
| 787 | comp.lisp_obj_type, | ||
| 788 | "bool_to_lisp_obj", | ||
| 789 | 1, | ||
| 790 | ¶m, | ||
| 791 | 0); | ||
| 792 | gcc_jit_block *initial_block = | ||
| 793 | gcc_jit_function_new_block (comp.bool_to_lisp_obj, | ||
| 794 | "bool_to_lisp_obj_initial_block"); | ||
| 795 | gcc_jit_block *ret_t_block = | ||
| 796 | gcc_jit_function_new_block (comp.bool_to_lisp_obj, | ||
| 797 | "ret_t"); | ||
| 798 | gcc_jit_block *ret_nil_block = | ||
| 799 | gcc_jit_function_new_block (comp.bool_to_lisp_obj, | ||
| 800 | "ret_nil"); | ||
| 801 | /* Set current context as needed */ | ||
| 802 | basic_block_t bblock = { .gcc_bb = initial_block, | ||
| 803 | .terminated = false }; | ||
| 804 | comp.bblock = &bblock; | ||
| 805 | comp.func = comp.bool_to_lisp_obj; | ||
| 806 | |||
| 807 | emit_cond_jump (gcc_jit_param_as_rvalue (param), | ||
| 808 | ret_t_block, | ||
| 809 | ret_nil_block); | ||
| 810 | bblock.gcc_bb = ret_t_block; | ||
| 811 | gcc_jit_block_end_with_return (ret_t_block, | ||
| 812 | NULL, | ||
| 813 | emit_lisp_obj_from_ptr (&bblock, Qt)); | ||
| 814 | bblock.gcc_bb = ret_nil_block; | ||
| 815 | gcc_jit_block_end_with_return (ret_nil_block, | ||
| 816 | NULL, | ||
| 817 | emit_lisp_obj_from_ptr (&bblock, Qnil)); | ||
| 818 | } | ||
| 819 | |||
| 768 | static int | 820 | static int |
| 769 | ucmp(const void *a, const void *b) | 821 | ucmp(const void *a, const void *b) |
| 770 | { | 822 | { |
| @@ -1026,6 +1078,7 @@ init_comp (int opt_level) | |||
| 1026 | comp.func_hash = CALLN (Fmake_hash_table, QCtest, Qequal, QCweakness, Qt); | 1078 | comp.func_hash = CALLN (Fmake_hash_table, QCtest, Qequal, QCweakness, Qt); |
| 1027 | 1079 | ||
| 1028 | declare_PSEUDOVECTORP (); | 1080 | declare_PSEUDOVECTORP (); |
| 1081 | declare_bool_to_lisp_obj (); | ||
| 1029 | } | 1082 | } |
| 1030 | 1083 | ||
| 1031 | static void | 1084 | static void |
| @@ -1814,7 +1867,13 @@ compile_f (const char *f_name, ptrdiff_t bytestr_length, | |||
| 1814 | break; | 1867 | break; |
| 1815 | 1868 | ||
| 1816 | case Bintegerp: | 1869 | case Bintegerp: |
| 1817 | error ("Bintegerp not supported"); | 1870 | POP1; |
| 1871 | res = emit_INTEGERP(args[0]); | ||
| 1872 | res = gcc_jit_context_new_call (comp.ctxt, | ||
| 1873 | NULL, | ||
| 1874 | comp.bool_to_lisp_obj, | ||
| 1875 | 1, &res); | ||
| 1876 | PUSH_RVAL (res); | ||
| 1818 | break; | 1877 | break; |
| 1819 | 1878 | ||
| 1820 | case BRgoto: | 1879 | case BRgoto: |