< prev index next >

src/hotspot/cpu/aarch64/stubGenerator_aarch64.cpp

Print this page

  11  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  12  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  13  * version 2 for more details (a copy is included in the LICENSE file that
  14  * accompanied this code).
  15  *
  16  * You should have received a copy of the GNU General Public License version
  17  * 2 along with this work; if not, write to the Free Software Foundation,
  18  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  19  *
  20  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  21  * or visit www.oracle.com if you need additional information or have any
  22  * questions.
  23  *
  24  */
  25 
  26 #include "precompiled.hpp"
  27 #include "asm/macroAssembler.hpp"
  28 #include "asm/macroAssembler.inline.hpp"
  29 #include "asm/register.hpp"
  30 #include "atomic_aarch64.hpp"

  31 #include "compiler/oopMap.hpp"
  32 #include "gc/shared/barrierSet.hpp"
  33 #include "gc/shared/barrierSetAssembler.hpp"
  34 #include "gc/shared/gc_globals.hpp"
  35 #include "gc/shared/tlab_globals.hpp"
  36 #include "interpreter/interpreter.hpp"
  37 #include "memory/universe.hpp"
  38 #include "nativeInst_aarch64.hpp"
  39 #include "oops/instanceOop.hpp"
  40 #include "oops/method.hpp"
  41 #include "oops/objArrayKlass.hpp"
  42 #include "oops/oop.inline.hpp"
  43 #include "prims/methodHandles.hpp"
  44 #include "prims/upcallLinker.hpp"
  45 #include "runtime/arguments.hpp"
  46 #include "runtime/atomic.hpp"
  47 #include "runtime/continuation.hpp"
  48 #include "runtime/continuationEntry.inline.hpp"
  49 #include "runtime/frame.inline.hpp"
  50 #include "runtime/handles.inline.hpp"

4659     __ fmovd(temp1, vs2acc);
4660     __ add(s1, s1, temp0);
4661     __ add(s2, s2, temp1);
4662   }
4663 
4664   /**
4665    *  Arguments:
4666    *
4667    *  Input:
4668    *    c_rarg0   - x address
4669    *    c_rarg1   - x length
4670    *    c_rarg2   - y address
4671    *    c_rarg3   - y length
4672    *    c_rarg4   - z address
4673    */
4674   address generate_multiplyToLen() {
4675     __ align(CodeEntryAlignment);
4676     StubCodeMark mark(this, "StubRoutines", "multiplyToLen");
4677 
4678     address start = __ pc();




4679     const Register x     = r0;
4680     const Register xlen  = r1;
4681     const Register y     = r2;
4682     const Register ylen  = r3;
4683     const Register z     = r4;
4684 
4685     const Register tmp0  = r5;
4686     const Register tmp1  = r10;
4687     const Register tmp2  = r11;
4688     const Register tmp3  = r12;
4689     const Register tmp4  = r13;
4690     const Register tmp5  = r14;
4691     const Register tmp6  = r15;
4692     const Register tmp7  = r16;
4693 
4694     BLOCK_COMMENT("Entry:");
4695     __ enter(); // required for proper stackwalking of RuntimeStub frame
4696     __ multiply_to_len(x, xlen, y, ylen, z, tmp0, tmp1, tmp2, tmp3, tmp4, tmp5, tmp6, tmp7);
4697     __ leave(); // required for proper stackwalking of RuntimeStub frame
4698     __ ret(lr);
4699 

4700     return start;
4701   }
4702 
4703   address generate_squareToLen() {
4704     // squareToLen algorithm for sizes 1..127 described in java code works
4705     // faster than multiply_to_len on some CPUs and slower on others, but
4706     // multiply_to_len shows a bit better overall results
4707     __ align(CodeEntryAlignment);
4708     StubCodeMark mark(this, "StubRoutines", "squareToLen");
4709     address start = __ pc();
4710 



4711     const Register x     = r0;
4712     const Register xlen  = r1;
4713     const Register z     = r2;
4714     const Register y     = r4; // == x
4715     const Register ylen  = r5; // == xlen
4716 
4717     const Register tmp0  = r3;
4718     const Register tmp1  = r10;
4719     const Register tmp2  = r11;
4720     const Register tmp3  = r12;
4721     const Register tmp4  = r13;
4722     const Register tmp5  = r14;
4723     const Register tmp6  = r15;
4724     const Register tmp7  = r16;
4725 
4726     RegSet spilled_regs = RegSet::of(y, ylen);
4727     BLOCK_COMMENT("Entry:");
4728     __ enter();
4729     __ push(spilled_regs, sp);
4730     __ mov(y, x);
4731     __ mov(ylen, xlen);
4732     __ multiply_to_len(x, xlen, y, ylen, z, tmp0, tmp1, tmp2, tmp3, tmp4, tmp5, tmp6, tmp7);
4733     __ pop(spilled_regs, sp);
4734     __ leave();
4735     __ ret(lr);


4736     return start;
4737   }
4738 
4739   address generate_mulAdd() {
4740     __ align(CodeEntryAlignment);
4741     StubCodeMark mark(this, "StubRoutines", "mulAdd");
4742 
4743     address start = __ pc();
4744 



4745     const Register out     = r0;
4746     const Register in      = r1;
4747     const Register offset  = r2;
4748     const Register len     = r3;
4749     const Register k       = r4;
4750 
4751     BLOCK_COMMENT("Entry:");
4752     __ enter();
4753     __ mul_add(out, in, offset, len, k);
4754     __ leave();
4755     __ ret(lr);
4756 

4757     return start;
4758   }
4759 
4760   // Arguments:
4761   //
4762   // Input:
4763   //   c_rarg0   - newArr address
4764   //   c_rarg1   - oldArr address
4765   //   c_rarg2   - newIdx
4766   //   c_rarg3   - shiftCount
4767   //   c_rarg4   - numIter
4768   //
4769   address generate_bigIntegerRightShift() {
4770     __ align(CodeEntryAlignment);
4771     StubCodeMark mark(this,  "StubRoutines", "bigIntegerRightShiftWorker");
4772     address start = __ pc();
4773 
4774     Label ShiftSIMDLoop, ShiftTwoLoop, ShiftThree, ShiftTwo, ShiftOne, Exit;
4775 
4776     Register newArr        = c_rarg0;

  11  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  12  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  13  * version 2 for more details (a copy is included in the LICENSE file that
  14  * accompanied this code).
  15  *
  16  * You should have received a copy of the GNU General Public License version
  17  * 2 along with this work; if not, write to the Free Software Foundation,
  18  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  19  *
  20  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  21  * or visit www.oracle.com if you need additional information or have any
  22  * questions.
  23  *
  24  */
  25 
  26 #include "precompiled.hpp"
  27 #include "asm/macroAssembler.hpp"
  28 #include "asm/macroAssembler.inline.hpp"
  29 #include "asm/register.hpp"
  30 #include "atomic_aarch64.hpp"
  31 #include "code/SCCache.hpp"
  32 #include "compiler/oopMap.hpp"
  33 #include "gc/shared/barrierSet.hpp"
  34 #include "gc/shared/barrierSetAssembler.hpp"
  35 #include "gc/shared/gc_globals.hpp"
  36 #include "gc/shared/tlab_globals.hpp"
  37 #include "interpreter/interpreter.hpp"
  38 #include "memory/universe.hpp"
  39 #include "nativeInst_aarch64.hpp"
  40 #include "oops/instanceOop.hpp"
  41 #include "oops/method.hpp"
  42 #include "oops/objArrayKlass.hpp"
  43 #include "oops/oop.inline.hpp"
  44 #include "prims/methodHandles.hpp"
  45 #include "prims/upcallLinker.hpp"
  46 #include "runtime/arguments.hpp"
  47 #include "runtime/atomic.hpp"
  48 #include "runtime/continuation.hpp"
  49 #include "runtime/continuationEntry.inline.hpp"
  50 #include "runtime/frame.inline.hpp"
  51 #include "runtime/handles.inline.hpp"

4660     __ fmovd(temp1, vs2acc);
4661     __ add(s1, s1, temp0);
4662     __ add(s2, s2, temp1);
4663   }
4664 
4665   /**
4666    *  Arguments:
4667    *
4668    *  Input:
4669    *    c_rarg0   - x address
4670    *    c_rarg1   - x length
4671    *    c_rarg2   - y address
4672    *    c_rarg3   - y length
4673    *    c_rarg4   - z address
4674    */
4675   address generate_multiplyToLen() {
4676     __ align(CodeEntryAlignment);
4677     StubCodeMark mark(this, "StubRoutines", "multiplyToLen");
4678 
4679     address start = __ pc();
4680  
4681     if (SCCache::load_stub(this, vmIntrinsics::_multiplyToLen, "multiplyToLen", start)) {
4682       return start;
4683     }
4684     const Register x     = r0;
4685     const Register xlen  = r1;
4686     const Register y     = r2;
4687     const Register ylen  = r3;
4688     const Register z     = r4;
4689 
4690     const Register tmp0  = r5;
4691     const Register tmp1  = r10;
4692     const Register tmp2  = r11;
4693     const Register tmp3  = r12;
4694     const Register tmp4  = r13;
4695     const Register tmp5  = r14;
4696     const Register tmp6  = r15;
4697     const Register tmp7  = r16;
4698 
4699     BLOCK_COMMENT("Entry:");
4700     __ enter(); // required for proper stackwalking of RuntimeStub frame
4701     __ multiply_to_len(x, xlen, y, ylen, z, tmp0, tmp1, tmp2, tmp3, tmp4, tmp5, tmp6, tmp7);
4702     __ leave(); // required for proper stackwalking of RuntimeStub frame
4703     __ ret(lr);
4704 
4705     SCCache::store_stub(this, vmIntrinsics::_multiplyToLen, "multiplyToLen", start);
4706     return start;
4707   }
4708 
4709   address generate_squareToLen() {
4710     // squareToLen algorithm for sizes 1..127 described in java code works
4711     // faster than multiply_to_len on some CPUs and slower on others, but
4712     // multiply_to_len shows a bit better overall results
4713     __ align(CodeEntryAlignment);
4714     StubCodeMark mark(this, "StubRoutines", "squareToLen");
4715     address start = __ pc();
4716 
4717     if (SCCache::load_stub(this, vmIntrinsics::_squareToLen, "squareToLen", start)) {
4718       return start;
4719     }
4720     const Register x     = r0;
4721     const Register xlen  = r1;
4722     const Register z     = r2;
4723     const Register y     = r4; // == x
4724     const Register ylen  = r5; // == xlen
4725 
4726     const Register tmp0  = r3;
4727     const Register tmp1  = r10;
4728     const Register tmp2  = r11;
4729     const Register tmp3  = r12;
4730     const Register tmp4  = r13;
4731     const Register tmp5  = r14;
4732     const Register tmp6  = r15;
4733     const Register tmp7  = r16;
4734 
4735     RegSet spilled_regs = RegSet::of(y, ylen);
4736     BLOCK_COMMENT("Entry:");
4737     __ enter();
4738     __ push(spilled_regs, sp);
4739     __ mov(y, x);
4740     __ mov(ylen, xlen);
4741     __ multiply_to_len(x, xlen, y, ylen, z, tmp0, tmp1, tmp2, tmp3, tmp4, tmp5, tmp6, tmp7);
4742     __ pop(spilled_regs, sp);
4743     __ leave();
4744     __ ret(lr);
4745 
4746     SCCache::store_stub(this, vmIntrinsics::_squareToLen, "squareToLen", start);
4747     return start;
4748   }
4749 
4750   address generate_mulAdd() {
4751     __ align(CodeEntryAlignment);
4752     StubCodeMark mark(this, "StubRoutines", "mulAdd");
4753 
4754     address start = __ pc();
4755 
4756     if (SCCache::load_stub(this, vmIntrinsics::_mulAdd, "mulAdd", start)) {
4757       return start;
4758     }
4759     const Register out     = r0;
4760     const Register in      = r1;
4761     const Register offset  = r2;
4762     const Register len     = r3;
4763     const Register k       = r4;
4764 
4765     BLOCK_COMMENT("Entry:");
4766     __ enter();
4767     __ mul_add(out, in, offset, len, k);
4768     __ leave();
4769     __ ret(lr);
4770 
4771     SCCache::store_stub(this, vmIntrinsics::_mulAdd, "mulAdd", start);
4772     return start;
4773   }
4774 
4775   // Arguments:
4776   //
4777   // Input:
4778   //   c_rarg0   - newArr address
4779   //   c_rarg1   - oldArr address
4780   //   c_rarg2   - newIdx
4781   //   c_rarg3   - shiftCount
4782   //   c_rarg4   - numIter
4783   //
4784   address generate_bigIntegerRightShift() {
4785     __ align(CodeEntryAlignment);
4786     StubCodeMark mark(this,  "StubRoutines", "bigIntegerRightShiftWorker");
4787     address start = __ pc();
4788 
4789     Label ShiftSIMDLoop, ShiftTwoLoop, ShiftThree, ShiftTwo, ShiftOne, Exit;
4790 
4791     Register newArr        = c_rarg0;
< prev index next >