< prev index next >

src/cpu/aarch64/vm/aarch64.ad

Print this page
rev 11237 : 8156839: aarch64: indexOf does not support CompactStrings
Summary: Add support for LL,UL and LU to indexOf intrinsic
Reviewed-by: aph


3314     return 0;  // CodeBuffer::expand failed
3315   }
3316   int offset = __ offset();
3317 
3318   __ adr(lr, __ pc());
3319   __ far_jump(RuntimeAddress(SharedRuntime::deopt_blob()->unpack()));
3320 
3321   assert(__ offset() - offset <= (int) size_deopt_handler(), "overflow");
3322   __ end_a_stub();
3323   return offset;
3324 }
3325 
3326 // REQUIRED MATCHER CODE
3327 
3328 //=============================================================================
3329 
3330 const bool Matcher::match_rule_supported(int opcode) {
3331 
3332   switch (opcode) {
3333   case Op_StrComp:
3334   case Op_StrIndexOf:
3335     if (CompactStrings)  return false;
3336     break;
3337   default:
3338     break;
3339   }
3340 
3341   if (!has_match_rule(opcode)) {
3342     return false;
3343   }
3344 
3345   return true;  // Per default match rules are supported.
3346 }
3347 
3348 const bool Matcher::match_rule_supported_vector(int opcode, int vlen) {
3349 
3350   // TODO
3351   // identify extra cases that we might want to provide match rules for
3352   // e.g. Op_ vector nodes and other intrinsics while guarding with vlen
3353   bool ret_value = match_rule_supported(opcode);
3354   // Add rules here.


14936 
14937 instruct string_compareU(iRegP_R1 str1, iRegI_R2 cnt1, iRegP_R3 str2, iRegI_R4 cnt2,
14938                         iRegI_R0 result, iRegP_R10 tmp1, rFlagsReg cr)
14939 %{
14940   predicate(((StrCompNode*)n)->encoding() == StrIntrinsicNode::UU);
14941   match(Set result (StrComp (Binary str1 cnt1) (Binary str2 cnt2)));
14942   effect(KILL tmp1, USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2, KILL cr);
14943 
14944   format %{ "String Compare $str1,$cnt1,$str2,$cnt2 -> $result   # KILL $tmp1" %}
14945   ins_encode %{
14946     // Count is in 8-bit bytes; non-Compact chars are 16 bits.
14947     __ asrw($cnt1$$Register, $cnt1$$Register, 1);
14948     __ asrw($cnt2$$Register, $cnt2$$Register, 1);
14949     __ string_compare($str1$$Register, $str2$$Register,
14950                       $cnt1$$Register, $cnt2$$Register, $result$$Register,
14951                       $tmp1$$Register);
14952   %}
14953   ins_pipe(pipe_class_memory);
14954 %}
14955 
14956 instruct string_indexof(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
14957        iRegI_R0 result, iRegI tmp1, iRegI tmp2, iRegI tmp3, iRegI tmp4, rFlagsReg cr)
14958 %{
14959   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UU);
14960   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
14961   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2,
14962          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
14963   format %{ "String IndexOf $str1,$cnt1,$str2,$cnt2 -> $result" %}
14964 
14965   ins_encode %{
14966     __ string_indexof($str1$$Register, $str2$$Register,
14967                       $cnt1$$Register, $cnt2$$Register,
14968                       $tmp1$$Register, $tmp2$$Register,
14969                       $tmp3$$Register, $tmp4$$Register,
14970                       -1, $result$$Register);
14971   %}
14972   ins_pipe(pipe_class_memory);
14973 %}
14974 
14975 instruct string_indexof_con(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,

























































14976                  immI_le_4 int_cnt2, iRegI_R0 result, iRegI tmp1, iRegI tmp2,
14977                  iRegI tmp3, iRegI tmp4, rFlagsReg cr)
14978 %{
14979   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UU);
14980   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
14981   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1,
14982          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
14983   format %{ "String IndexOf $str1,$cnt1,$str2,$int_cnt2 -> $result" %}































































14984 
14985   ins_encode %{
14986     int icnt2 = (int)$int_cnt2$$constant;
14987     __ string_indexof($str1$$Register, $str2$$Register,
14988                       $cnt1$$Register, zr,
14989                       $tmp1$$Register, $tmp2$$Register,
14990                       $tmp3$$Register, $tmp4$$Register,
14991                       icnt2, $result$$Register);
14992   %}
14993   ins_pipe(pipe_class_memory);
14994 %}
14995 
14996 instruct string_equalsL(iRegP_R1 str1, iRegP_R3 str2, iRegI_R4 cnt,
14997                         iRegI_R0 result, rFlagsReg cr)
14998 %{
14999   predicate(((StrEqualsNode*)n)->encoding() == StrIntrinsicNode::LL);
15000   match(Set result (StrEquals (Binary str1 str2) cnt));
15001   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt, KILL cr);
15002 
15003   format %{ "String Equals $str1,$str2,$cnt -> $result" %}
15004   ins_encode %{
15005     // Count is in 8-bit bytes; non-Compact chars are 16 bits.
15006     __ arrays_equals($str1$$Register, $str2$$Register,
15007                      $result$$Register, $cnt$$Register,
15008                      1, /*is_string*/true);
15009   %}
15010   ins_pipe(pipe_class_memory);
15011 %}




3314     return 0;  // CodeBuffer::expand failed
3315   }
3316   int offset = __ offset();
3317 
3318   __ adr(lr, __ pc());
3319   __ far_jump(RuntimeAddress(SharedRuntime::deopt_blob()->unpack()));
3320 
3321   assert(__ offset() - offset <= (int) size_deopt_handler(), "overflow");
3322   __ end_a_stub();
3323   return offset;
3324 }
3325 
3326 // REQUIRED MATCHER CODE
3327 
3328 //=============================================================================
3329 
3330 const bool Matcher::match_rule_supported(int opcode) {
3331 
3332   switch (opcode) {
3333   case Op_StrComp:

3334     if (CompactStrings)  return false;
3335     break;
3336   default:
3337     break;
3338   }
3339 
3340   if (!has_match_rule(opcode)) {
3341     return false;
3342   }
3343 
3344   return true;  // Per default match rules are supported.
3345 }
3346 
3347 const bool Matcher::match_rule_supported_vector(int opcode, int vlen) {
3348 
3349   // TODO
3350   // identify extra cases that we might want to provide match rules for
3351   // e.g. Op_ vector nodes and other intrinsics while guarding with vlen
3352   bool ret_value = match_rule_supported(opcode);
3353   // Add rules here.


14935 
14936 instruct string_compareU(iRegP_R1 str1, iRegI_R2 cnt1, iRegP_R3 str2, iRegI_R4 cnt2,
14937                         iRegI_R0 result, iRegP_R10 tmp1, rFlagsReg cr)
14938 %{
14939   predicate(((StrCompNode*)n)->encoding() == StrIntrinsicNode::UU);
14940   match(Set result (StrComp (Binary str1 cnt1) (Binary str2 cnt2)));
14941   effect(KILL tmp1, USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2, KILL cr);
14942 
14943   format %{ "String Compare $str1,$cnt1,$str2,$cnt2 -> $result   # KILL $tmp1" %}
14944   ins_encode %{
14945     // Count is in 8-bit bytes; non-Compact chars are 16 bits.
14946     __ asrw($cnt1$$Register, $cnt1$$Register, 1);
14947     __ asrw($cnt2$$Register, $cnt2$$Register, 1);
14948     __ string_compare($str1$$Register, $str2$$Register,
14949                       $cnt1$$Register, $cnt2$$Register, $result$$Register,
14950                       $tmp1$$Register);
14951   %}
14952   ins_pipe(pipe_class_memory);
14953 %}
14954 
14955 instruct string_indexofUU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
14956        iRegI_R0 result, iRegI tmp1, iRegI tmp2, iRegI tmp3, iRegI tmp4, rFlagsReg cr)
14957 %{
14958   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UU);
14959   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
14960   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2,
14961          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
14962   format %{ "String IndexOf $str1,$cnt1,$str2,$cnt2 -> $result (UU)" %}
14963 
14964   ins_encode %{
14965     __ string_indexof($str1$$Register, $str2$$Register,
14966                       $cnt1$$Register, $cnt2$$Register,
14967                       $tmp1$$Register, $tmp2$$Register,
14968                       $tmp3$$Register, $tmp4$$Register,
14969                       -1, $result$$Register, StrIntrinsicNode::UU);
14970   %}
14971   ins_pipe(pipe_class_memory);
14972 %}
14973 
14974 instruct string_indexofLL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
14975        iRegI_R0 result, iRegI tmp1, iRegI tmp2, iRegI tmp3, iRegI tmp4, rFlagsReg cr)
14976 %{
14977   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::LL);
14978   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
14979   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2,
14980          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
14981   format %{ "String IndexOf $str1,$cnt1,$str2,$cnt2 -> $result (LL)" %}
14982 
14983   ins_encode %{
14984     __ string_indexof($str1$$Register, $str2$$Register,
14985                       $cnt1$$Register, $cnt2$$Register,
14986                       $tmp1$$Register, $tmp2$$Register,
14987                       $tmp3$$Register, $tmp4$$Register,
14988                       -1, $result$$Register, StrIntrinsicNode::LL);
14989   %}
14990   ins_pipe(pipe_class_memory);
14991 %}
14992 
14993 instruct string_indexofUL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
14994        iRegI_R0 result, iRegI tmp1, iRegI tmp2, iRegI tmp3, iRegI tmp4, rFlagsReg cr)
14995 %{
14996   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UL);
14997   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
14998   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2,
14999          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
15000   format %{ "String IndexOf $str1,$cnt1,$str2,$cnt2 -> $result (UL)" %}
15001 
15002   ins_encode %{
15003     __ string_indexof($str1$$Register, $str2$$Register,
15004                       $cnt1$$Register, $cnt2$$Register,
15005                       $tmp1$$Register, $tmp2$$Register,
15006                       $tmp3$$Register, $tmp4$$Register,
15007                       -1, $result$$Register, StrIntrinsicNode::UL);
15008   %}
15009   ins_pipe(pipe_class_memory);
15010 %}
15011 
15012 instruct string_indexofLU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
15013        iRegI_R0 result, iRegI tmp1, iRegI tmp2, iRegI tmp3, iRegI tmp4, rFlagsReg cr)
15014 %{
15015   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::LU);
15016   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
15017   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2,
15018          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
15019   format %{ "String IndexOf $str1,$cnt1,$str2,$cnt2 -> $result (LU)" %}
15020 
15021   ins_encode %{
15022     __ string_indexof($str1$$Register, $str2$$Register,
15023                       $cnt1$$Register, $cnt2$$Register,
15024                       $tmp1$$Register, $tmp2$$Register,
15025                       $tmp3$$Register, $tmp4$$Register,
15026                       -1, $result$$Register, StrIntrinsicNode::LU);
15027   %}
15028   ins_pipe(pipe_class_memory);
15029 %}
15030 
15031 instruct string_indexof_conUU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
15032                  immI_le_4 int_cnt2, iRegI_R0 result, iRegI tmp1, iRegI tmp2,
15033                  iRegI tmp3, iRegI tmp4, rFlagsReg cr)
15034 %{
15035   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UU);
15036   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
15037   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1,
15038          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
15039   format %{ "String IndexOf $str1,$cnt1,$str2,$int_cnt2 -> $result (UU)" %}
15040 
15041   ins_encode %{
15042     int icnt2 = (int)$int_cnt2$$constant;
15043     __ string_indexof($str1$$Register, $str2$$Register,
15044                       $cnt1$$Register, zr,
15045                       $tmp1$$Register, $tmp2$$Register,
15046                       $tmp3$$Register, $tmp4$$Register,
15047                       icnt2, $result$$Register, StrIntrinsicNode::UU);
15048   %}
15049   ins_pipe(pipe_class_memory);
15050 %}
15051 
15052 instruct string_indexof_conLL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
15053                  immI_le_4 int_cnt2, iRegI_R0 result, iRegI tmp1, iRegI tmp2,
15054                  iRegI tmp3, iRegI tmp4, rFlagsReg cr)
15055 %{
15056   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::LL);
15057   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
15058   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1,
15059          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
15060   format %{ "String IndexOf $str1,$cnt1,$str2,$int_cnt2 -> $result (LL)" %}
15061 
15062   ins_encode %{
15063     int icnt2 = (int)$int_cnt2$$constant;
15064     __ string_indexof($str1$$Register, $str2$$Register,
15065                       $cnt1$$Register, zr,
15066                       $tmp1$$Register, $tmp2$$Register,
15067                       $tmp3$$Register, $tmp4$$Register,
15068                       icnt2, $result$$Register, StrIntrinsicNode::LL);
15069   %}
15070   ins_pipe(pipe_class_memory);
15071 %}
15072 
15073 instruct string_indexof_conUL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
15074                  immI_1 int_cnt2, iRegI_R0 result, iRegI tmp1, iRegI tmp2,
15075                  iRegI tmp3, iRegI tmp4, rFlagsReg cr)
15076 %{
15077   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UL);
15078   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
15079   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1,
15080          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
15081   format %{ "String IndexOf $str1,$cnt1,$str2,$int_cnt2 -> $result (UL)" %}
15082 
15083   ins_encode %{
15084     int icnt2 = (int)$int_cnt2$$constant;
15085     __ string_indexof($str1$$Register, $str2$$Register,
15086                       $cnt1$$Register, zr,
15087                       $tmp1$$Register, $tmp2$$Register,
15088                       $tmp3$$Register, $tmp4$$Register,
15089                       icnt2, $result$$Register, StrIntrinsicNode::UL);
15090   %}
15091   ins_pipe(pipe_class_memory);
15092 %}
15093 
15094 instruct string_indexof_conLU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
15095                  immI_1 int_cnt2, iRegI_R0 result, iRegI tmp1, iRegI tmp2,
15096                  iRegI tmp3, iRegI tmp4, rFlagsReg cr)
15097 %{
15098   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::LU);
15099   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
15100   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1,
15101          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
15102   format %{ "String IndexOf $str1,$cnt1,$str2,$int_cnt2 -> $result (LU)" %}
15103 
15104   ins_encode %{
15105     int icnt2 = (int)$int_cnt2$$constant;
15106     __ string_indexof($str1$$Register, $str2$$Register,
15107                       $cnt1$$Register, zr,
15108                       $tmp1$$Register, $tmp2$$Register,
15109                       $tmp3$$Register, $tmp4$$Register,
15110                       icnt2, $result$$Register, StrIntrinsicNode::LU);
15111   %}
15112   ins_pipe(pipe_class_memory);
15113 %}
15114 
15115 instruct string_equalsL(iRegP_R1 str1, iRegP_R3 str2, iRegI_R4 cnt,
15116                         iRegI_R0 result, rFlagsReg cr)
15117 %{
15118   predicate(((StrEqualsNode*)n)->encoding() == StrIntrinsicNode::LL);
15119   match(Set result (StrEquals (Binary str1 str2) cnt));
15120   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt, KILL cr);
15121 
15122   format %{ "String Equals $str1,$str2,$cnt -> $result" %}
15123   ins_encode %{
15124     // Count is in 8-bit bytes; non-Compact chars are 16 bits.
15125     __ arrays_equals($str1$$Register, $str2$$Register,
15126                      $result$$Register, $cnt$$Register,
15127                      1, /*is_string*/true);
15128   %}
15129   ins_pipe(pipe_class_memory);
15130 %}


< prev index next >