JIT: inline string=? and bytes=?
This commit is contained in:
parent
79738d3bf6
commit
152787cb0e
|
@ -359,6 +359,8 @@ struct scheme_jit_common_record {
|
|||
void *with_immed_mark_code;
|
||||
void *apply_to_list_tail_code, *apply_to_list_code, *apply_to_list_multi_ok_code;
|
||||
void *eqv_code, *eqv_branch_code;
|
||||
void *bad_string_eq_2_code;
|
||||
void *bad_bytes_eq_2_code;
|
||||
void *proc_arity_includes_code;
|
||||
|
||||
#ifdef CAN_INLINE_ALLOC
|
||||
|
|
|
@ -91,6 +91,8 @@ define_ts_s_s(scheme_extflvector_length, FSRC_MARKS)
|
|||
define_ts_s_s(scheme_fxvector_length, FSRC_MARKS)
|
||||
define_ts_s_s(scheme_string_length, FSRC_MARKS)
|
||||
define_ts_s_s(scheme_byte_string_length, FSRC_MARKS)
|
||||
define_ts_ss_s(scheme_string_eq_2, FSRC_MARKS)
|
||||
define_ts_ss_s(scheme_byte_string_eq_2, FSRC_MARKS)
|
||||
define_ts_s_s(scheme_unbox, FSRC_MARKS)
|
||||
define_ts_si_s(scheme_struct_ref, FSRC_MARKS)
|
||||
define_ts_sis_v(scheme_struct_set, FSRC_MARKS)
|
||||
|
@ -218,6 +220,8 @@ define_ts_s_s(scheme_box, FSRC_OTHER)
|
|||
# define ts_scheme_struct_ref scheme_struct_ref
|
||||
# define ts_scheme_struct_set scheme_struct_set
|
||||
# define ts_scheme_equal scheme_equal
|
||||
# define ts_scheme_string_eq_2 scheme_string_eq_2
|
||||
# define ts_scheme_byte_string_eq_2 scheme_byte_string_eq_2
|
||||
# define ts_extract_one_cc_mark_to_tag extract_one_cc_mark_to_tag
|
||||
# define ts_tail_call_with_values_from_multiple_result tail_call_with_values_from_multiple_result
|
||||
# define ts_raise_bad_call_with_values raise_bad_call_with_values
|
||||
|
|
|
@ -629,6 +629,30 @@ static int common1b(mz_jit_state *jitter, void *_data)
|
|||
CHECK_LIMIT();
|
||||
scheme_jit_register_sub_func(jitter, sjc.bad_bytes_length_code, scheme_false);
|
||||
|
||||
/* *** bad_string_eq_2_code *** */
|
||||
/* R0 and R1 are arguments */
|
||||
sjc.bad_string_eq_2_code = jit_get_ip();
|
||||
mz_prolog(JIT_R2);
|
||||
JIT_UPDATE_THREAD_RSPTR();
|
||||
jit_prepare(2);
|
||||
jit_pusharg_p(JIT_R1);
|
||||
jit_pusharg_p(JIT_R0);
|
||||
(void)mz_finish_lwe(ts_scheme_string_eq_2, ref);
|
||||
CHECK_LIMIT();
|
||||
scheme_jit_register_sub_func(jitter, sjc.bad_string_eq_2_code, scheme_false);
|
||||
|
||||
/* *** bad_bytes_eq_2_code *** */
|
||||
/* R0 and R1 are arguments */
|
||||
sjc.bad_bytes_eq_2_code = jit_get_ip();
|
||||
mz_prolog(JIT_R2);
|
||||
JIT_UPDATE_THREAD_RSPTR();
|
||||
jit_prepare(2);
|
||||
jit_pusharg_p(JIT_R1);
|
||||
jit_pusharg_p(JIT_R0);
|
||||
(void)mz_finish_lwe(ts_scheme_byte_string_eq_2, ref);
|
||||
CHECK_LIMIT();
|
||||
scheme_jit_register_sub_func(jitter, sjc.bad_bytes_eq_2_code, scheme_false);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
|
|
@ -2717,6 +2717,187 @@ int scheme_generate_inlined_binary(mz_jit_state *jitter, Scheme_App3_Rec *app, i
|
|||
|
||||
__END_SHORT_JUMPS__(branch_short);
|
||||
|
||||
return 1;
|
||||
} else if (IS_NAMED_PRIM(rator, "string=?")
|
||||
|| IS_NAMED_PRIM(rator, "bytes=?")) {
|
||||
GC_CAN_IGNORE jit_insn *ref_fx1, *ref_fx2, *ref_fail1, *ref_fail2, *ref_ucnofail;
|
||||
GC_CAN_IGNORE jit_insn *ref_false1, *ref_false2 = NULL;
|
||||
GC_CAN_IGNORE jit_insn *ref_true1, *ref_true2, *ref_ucfinish;
|
||||
GC_CAN_IGNORE jit_insn *ref_loop;
|
||||
int is_str1, is_str2, len = 0;
|
||||
int string, string_type;
|
||||
void * sjc_bad_code;
|
||||
intptr_t string_len_val, string_val;
|
||||
|
||||
if ((IS_NAMED_PRIM(rator, "string=?"))) {
|
||||
string = 1;
|
||||
string_type = scheme_char_string_type;
|
||||
sjc_bad_code = sjc.bad_string_eq_2_code;
|
||||
string_len_val = (intptr_t)&SCHEME_CHAR_STRLEN_VAL(0x0);
|
||||
string_val = (intptr_t)&SCHEME_CHAR_STR_VAL(0x0);
|
||||
} else if (IS_NAMED_PRIM(rator, "bytes=?")) {
|
||||
string = 0;
|
||||
string_type = scheme_byte_string_type;
|
||||
sjc_bad_code = sjc.bad_bytes_eq_2_code;
|
||||
string_len_val = (intptr_t)&SCHEME_BYTE_STRLEN_VAL(0x0);
|
||||
string_val = (intptr_t)&SCHEME_BYTE_STR_VAL(0x0);
|
||||
}
|
||||
|
||||
is_str1 = (SAME_TYPE(SCHEME_TYPE(app->rand1), string_type));
|
||||
is_str2 = (SAME_TYPE(SCHEME_TYPE(app->rand2), string_type));
|
||||
if (string) {
|
||||
if (is_str1) {
|
||||
len = SCHEME_CHAR_STRLEN_VAL(app->rand1);
|
||||
} else if (is_str2) {
|
||||
len = SCHEME_CHAR_STRLEN_VAL(app->rand2);
|
||||
}
|
||||
} else {
|
||||
if (is_str1) {
|
||||
len = SCHEME_BYTE_STRLEN_VAL(app->rand1);
|
||||
} else if (is_str2) {
|
||||
len = SCHEME_BYTE_STRLEN_VAL(app->rand2);
|
||||
}
|
||||
}
|
||||
|
||||
scheme_generate_two_args(app->rand1, app->rand2, jitter, 1, 2);
|
||||
CHECK_LIMIT();
|
||||
|
||||
if (need_sync) mz_rs_sync();
|
||||
|
||||
if (for_branch) {
|
||||
__START_SHORT_JUMPS__(branch_short);
|
||||
scheme_prepare_branch_jump(jitter, for_branch);
|
||||
CHECK_LIMIT();
|
||||
__END_SHORT_JUMPS__(branch_short);
|
||||
}
|
||||
|
||||
__START_TINY_JUMPS__(1);
|
||||
/* fail if either is not a string */
|
||||
if (!is_str1) {
|
||||
ref_fx1 = jit_bmsi_ul(jit_forward(), JIT_R0, 0x1);
|
||||
jit_ldxi_s(JIT_R2, JIT_R0, &((Scheme_Object *)0x0)->type);
|
||||
ref_fail1 = jit_bnei_i(jit_forward(), JIT_R2, string_type);
|
||||
}
|
||||
if (!is_str2) {
|
||||
ref_fx2 = jit_bmsi_ul(jit_forward(), JIT_R1, 0x1);
|
||||
jit_ldxi_s(JIT_V1, JIT_R1, &((Scheme_Object *)0x0)->type);
|
||||
ref_fail2 = jit_bnei_i(jit_forward(), JIT_V1, string_type);
|
||||
}
|
||||
ref_ucnofail = jit_jmpi(jit_forward());
|
||||
CHECK_LIMIT();
|
||||
|
||||
/* fail */
|
||||
if (!is_str1) {
|
||||
mz_patch_branch(ref_fx1);
|
||||
mz_patch_branch(ref_fail1);
|
||||
}
|
||||
if (!is_str2) {
|
||||
mz_patch_branch(ref_fx2);
|
||||
mz_patch_branch(ref_fail2);
|
||||
}
|
||||
__END_TINY_JUMPS__(1);
|
||||
|
||||
(void)jit_calli(sjc_bad_code);
|
||||
CHECK_LIMIT();
|
||||
|
||||
/* main */
|
||||
__START_TINY_JUMPS__(1);
|
||||
mz_patch_ucbranch(ref_ucnofail);
|
||||
__END_TINY_JUMPS__(1);
|
||||
|
||||
if (result_ignored)
|
||||
return 1;
|
||||
|
||||
/* false if they have different length */
|
||||
__START_TINY_OR_SHORT_JUMPS__(!for_branch, branch_short);
|
||||
if (is_str1) {
|
||||
jit_ldxi_l(JIT_R2, JIT_R1, string_len_val);
|
||||
ref_false1 = jit_bnei_l(jit_forward(), JIT_R2, len);
|
||||
} else if (is_str2) {
|
||||
jit_ldxi_l(JIT_R2, JIT_R0, string_len_val);
|
||||
ref_false1 = jit_bnei_l(jit_forward(), JIT_R2, len);
|
||||
} else {
|
||||
jit_ldxi_l(JIT_R2, JIT_R0, string_len_val);
|
||||
jit_ldxi_l(JIT_V1, JIT_R1, string_len_val);
|
||||
ref_false1 = jit_bner_l(jit_forward(), JIT_R2, JIT_V1);
|
||||
}
|
||||
__END_TINY_OR_SHORT_JUMPS__(!for_branch, branch_short);
|
||||
|
||||
if ((!is_str1 && !is_str2) || len) {
|
||||
__START_TINY_JUMPS__(1);
|
||||
/* true if both have length zero or are eq?*/
|
||||
ref_true1 = jit_beqi_l(jit_forward(), JIT_R2, 0);
|
||||
ref_true2 = jit_beqr_p(jit_forward(), JIT_R0, JIT_R1);
|
||||
|
||||
/* initialize loop*/
|
||||
jit_ldxi_p(JIT_R0, JIT_R0, string_val);
|
||||
jit_ldxi_p(JIT_R1, JIT_R1, string_val);
|
||||
CHECK_LIMIT();
|
||||
|
||||
/* main loop*/
|
||||
if (string) {
|
||||
ref_loop = jit_get_ip();
|
||||
mz_set_local_p(JIT_R0, JIT_LOCAL3);
|
||||
jit_ldr_i(JIT_R0, JIT_R0);
|
||||
jit_ldr_i(JIT_V1, JIT_R1);
|
||||
__END_TINY_JUMPS__(1);
|
||||
__START_TINY_OR_SHORT_JUMPS__(!for_branch, branch_short);
|
||||
ref_false2 = jit_bner_i(jit_forward(), JIT_R0, JIT_V1);
|
||||
__END_TINY_OR_SHORT_JUMPS__(!for_branch, branch_short);
|
||||
__START_TINY_JUMPS__(1);
|
||||
mz_get_local_p(JIT_R0, JIT_LOCAL3);
|
||||
jit_addi_p(JIT_R0, JIT_R0, 1 << LOG_MZCHAR_SIZE);
|
||||
jit_addi_p(JIT_R1, JIT_R1, 1 << LOG_MZCHAR_SIZE);
|
||||
jit_subi_l(JIT_R2, JIT_R2, 1);
|
||||
(void)jit_bnei_l(ref_loop, JIT_R2, 0);
|
||||
} else {
|
||||
ref_loop = jit_get_ip();
|
||||
mz_set_local_p(JIT_R0, JIT_LOCAL3);
|
||||
jit_ldr_c(JIT_R0, JIT_R0);
|
||||
jit_ldr_c(JIT_V1, JIT_R1);
|
||||
__END_TINY_JUMPS__(1);
|
||||
__START_TINY_OR_SHORT_JUMPS__(!for_branch, branch_short);
|
||||
jit_extr_c_i(JIT_R0, JIT_R0);
|
||||
jit_extr_c_i(JIT_V1, JIT_V1);
|
||||
ref_false2 = jit_bner_i(jit_forward(), JIT_R0, JIT_V1);
|
||||
__END_TINY_OR_SHORT_JUMPS__(!for_branch, branch_short);
|
||||
__START_TINY_JUMPS__(1);
|
||||
mz_get_local_p(JIT_R0, JIT_LOCAL3);
|
||||
jit_addi_p(JIT_R0, JIT_R0, 1);
|
||||
jit_addi_p(JIT_R1, JIT_R1, 1);
|
||||
jit_subi_l(JIT_R2, JIT_R2, 1);
|
||||
(void)jit_bnei_l(ref_loop, JIT_R2, 0);
|
||||
}
|
||||
CHECK_LIMIT();
|
||||
|
||||
/* true */
|
||||
mz_patch_branch(ref_true1);
|
||||
mz_patch_branch(ref_true2);
|
||||
__END_TINY_JUMPS__(1);
|
||||
}
|
||||
|
||||
if (for_branch) {
|
||||
__START_SHORT_JUMPS__(branch_short);
|
||||
scheme_add_branch_false(for_branch, ref_false1);
|
||||
if (ref_false2)
|
||||
scheme_add_branch_false(for_branch, ref_false2);
|
||||
scheme_branch_for_true(jitter, for_branch);
|
||||
__END_SHORT_JUMPS__(branch_short);
|
||||
} else {
|
||||
__START_TINY_JUMPS__(1);
|
||||
jit_movi_p(dest, scheme_true);
|
||||
ref_ucfinish = jit_jmpi(jit_forward());
|
||||
/* false */
|
||||
mz_patch_branch(ref_false1);
|
||||
if (ref_false2)
|
||||
mz_patch_branch(ref_false2);
|
||||
jit_movi_p(dest, scheme_false);
|
||||
/* finish */
|
||||
mz_patch_ucbranch(ref_ucfinish);
|
||||
__END_TINY_JUMPS__(1);
|
||||
}
|
||||
CHECK_LIMIT();
|
||||
|
||||
return 1;
|
||||
} else if (IS_NAMED_PRIM(rator, "=")) {
|
||||
scheme_generate_arith(jitter, rator, app->rand1, app->rand2, 2, 0, CMP_EQUAL, 0, for_branch, branch_short, 0, 0, NULL, dest);
|
||||
|
@ -3147,7 +3328,7 @@ int scheme_generate_inlined_binary(mz_jit_state *jitter, Scheme_App3_Rec *app, i
|
|||
} else {
|
||||
if (unsafe) {
|
||||
jit_rshi_ul(JIT_R1, JIT_R1, 1);
|
||||
jit_ldxi_p(JIT_R0, JIT_R0, &SCHEME_CHAR_STR_VAL((Scheme_Object *)0x0));
|
||||
jit_ldxi_p(JIT_R0, JIT_R0, &SCHEME_BYTE_STR_VAL((Scheme_Object *)0x0));
|
||||
jit_ldxr_c(JIT_R0, JIT_R0, JIT_R1);
|
||||
jit_extr_uc_ul(JIT_R0, JIT_R0);
|
||||
jit_fixnum_l(dest, JIT_R0);
|
||||
|
@ -3207,7 +3388,7 @@ int scheme_generate_inlined_binary(mz_jit_state *jitter, Scheme_App3_Rec *app, i
|
|||
}
|
||||
} else {
|
||||
if (unsafe) {
|
||||
jit_ldxi_p(JIT_R0, JIT_R0, &SCHEME_CHAR_STR_VAL((Scheme_Object *)0x0));
|
||||
jit_ldxi_p(JIT_R0, JIT_R0, &SCHEME_BYTE_STR_VAL((Scheme_Object *)0x0));
|
||||
jit_ldxr_c(JIT_R0, JIT_R0, JIT_V1);
|
||||
jit_extr_uc_ul(JIT_R0, JIT_R0);
|
||||
jit_fixnum_l(dest, JIT_R0);
|
||||
|
@ -4221,7 +4402,7 @@ int scheme_generate_inlined_nary(mz_jit_state *jitter, Scheme_App_Rec *app, int
|
|||
}
|
||||
} else {
|
||||
if (unsafe) {
|
||||
jit_ldxi_p(JIT_R0, JIT_R0, &SCHEME_CHAR_STR_VAL((Scheme_Object *)0x0));
|
||||
jit_ldxi_p(JIT_R0, JIT_R0, &SCHEME_BYTE_STR_VAL((Scheme_Object *)0x0));
|
||||
jit_rshi_ul(JIT_R2, JIT_R2, 1);
|
||||
jit_stxr_c(JIT_V1, JIT_R0, JIT_R2);
|
||||
if (!result_ignored)
|
||||
|
|
|
@ -4121,9 +4121,11 @@ Scheme_Object *scheme_checked_set_mcdr (int argc, Scheme_Object *argv[]);
|
|||
Scheme_Object *scheme_checked_vector_ref(int argc, Scheme_Object **argv);
|
||||
Scheme_Object *scheme_checked_vector_set(int argc, Scheme_Object **argv);
|
||||
Scheme_Object *scheme_string_length(Scheme_Object *v);
|
||||
Scheme_Object *scheme_string_eq_2(Scheme_Object *str1, Scheme_Object *str2);
|
||||
Scheme_Object *scheme_checked_string_ref(int argc, Scheme_Object *argv[]);
|
||||
Scheme_Object *scheme_checked_string_set(int argc, Scheme_Object *argv[]);
|
||||
Scheme_Object *scheme_byte_string_length(Scheme_Object *v);
|
||||
Scheme_Object *scheme_byte_string_eq_2(Scheme_Object *str1, Scheme_Object *str2);
|
||||
Scheme_Object *scheme_checked_byte_string_ref(int argc, Scheme_Object *argv[]);
|
||||
Scheme_Object *scheme_checked_byte_string_set(int argc, Scheme_Object *argv[]);
|
||||
Scheme_Object *scheme_checked_syntax_e(int argc, Scheme_Object **argv);
|
||||
|
|
|
@ -510,11 +510,10 @@ scheme_init_string (Scheme_Env *env)
|
|||
SCHEME_PRIM_PROC_FLAGS(p) |= scheme_intern_prim_opt_flags(SCHEME_PRIM_IS_NARY_INLINED);
|
||||
scheme_add_global_constant("string-set!", p, env);
|
||||
|
||||
scheme_add_global_constant("string=?",
|
||||
scheme_make_immed_prim(string_eq,
|
||||
"string=?",
|
||||
2, -1),
|
||||
env);
|
||||
p = scheme_make_immed_prim(string_eq, "string=?", 2, -1);
|
||||
SCHEME_PRIM_PROC_FLAGS(p) |= scheme_intern_prim_opt_flags(SCHEME_PRIM_IS_BINARY_INLINED);
|
||||
scheme_add_global_constant("string=?", p, env);
|
||||
|
||||
scheme_add_global_constant("string-locale=?",
|
||||
scheme_make_immed_prim(string_locale_eq,
|
||||
"string-locale=?",
|
||||
|
@ -788,11 +787,10 @@ scheme_init_string (Scheme_Env *env)
|
|||
SCHEME_PRIM_PROC_FLAGS(p) |= scheme_intern_prim_opt_flags(SCHEME_PRIM_IS_NARY_INLINED);
|
||||
scheme_add_global_constant("bytes-set!", p, env);
|
||||
|
||||
scheme_add_global_constant("bytes=?",
|
||||
scheme_make_immed_prim(byte_string_eq,
|
||||
"bytes=?",
|
||||
2, -1),
|
||||
env);
|
||||
p = scheme_make_immed_prim(byte_string_eq, "bytes=?", 2, -1);
|
||||
SCHEME_PRIM_PROC_FLAGS(p) |= scheme_intern_prim_opt_flags(SCHEME_PRIM_IS_BINARY_INLINED);
|
||||
scheme_add_global_constant("bytes=?", p, env);
|
||||
|
||||
scheme_add_global_constant("bytes<?",
|
||||
scheme_make_immed_prim(byte_string_lt,
|
||||
"bytes<?",
|
||||
|
@ -1202,6 +1200,14 @@ GEN_STRING_COMP(string_locale_ci_eq, "string-locale-ci=?", mz_char_strcmp_ci, ==
|
|||
GEN_STRING_COMP(string_locale_ci_lt, "string-locale-ci<?", mz_char_strcmp_ci, <, 1, 0)
|
||||
GEN_STRING_COMP(string_locale_ci_gt, "string-locale-ci>?", mz_char_strcmp_ci, >, 1, 0)
|
||||
|
||||
Scheme_Object *scheme_string_eq_2(Scheme_Object *str1, Scheme_Object *str2)
|
||||
{
|
||||
Scheme_Object *a[2];
|
||||
a[0] = str1;
|
||||
a[1] = str2;
|
||||
return string_eq(2, a);
|
||||
}
|
||||
|
||||
/**********************************************************************/
|
||||
/* byte strings */
|
||||
/**********************************************************************/
|
||||
|
@ -1268,6 +1274,14 @@ GEN_BYTE_STRING_COMP(byte_string_gt, "bytes>?", mz_strcmp, >)
|
|||
|
||||
GEN_BYTE_STRING_PATH_COMP(path_lt, "path<?", mz_strcmp, <, SCHEME_PATHP, "path?")
|
||||
|
||||
Scheme_Object *scheme_byte_string_eq_2(Scheme_Object *str1, Scheme_Object *str2)
|
||||
{
|
||||
Scheme_Object *a[2];
|
||||
a[0] = str1;
|
||||
a[1] = str2;
|
||||
return byte_string_eq(2, a);
|
||||
}
|
||||
|
||||
/**********************************************************************/
|
||||
/* byte string <-> char string */
|
||||
/**********************************************************************/
|
||||
|
|
Loading…
Reference in New Issue
Block a user