4784 __ delayed()->stf(FloatRegisterImpl::D, F14, state, 0x38); |
4784 __ delayed()->stf(FloatRegisterImpl::D, F14, state, 0x38); |
4785 |
4785 |
4786 return start; |
4786 return start; |
4787 } |
4787 } |
4788 |
4788 |
|
4789 /* Single and multi-block ghash operations */ |
|
4790 address generate_ghash_processBlocks() { |
|
4791 __ align(CodeEntryAlignment); |
|
4792 Label L_ghash_loop, L_aligned, L_main; |
|
4793 StubCodeMark mark(this, "StubRoutines", "ghash_processBlocks"); |
|
4794 address start = __ pc(); |
|
4795 |
|
4796 Register state = I0; |
|
4797 Register subkeyH = I1; |
|
4798 Register data = I2; |
|
4799 Register len = I3; |
|
4800 |
|
4801 __ save_frame(0); |
|
4802 |
|
4803 __ ldx(state, 0, O0); |
|
4804 __ ldx(state, 8, O1); |
|
4805 |
|
4806 // Loop label for multiblock operations |
|
4807 __ BIND(L_ghash_loop); |
|
4808 |
|
4809 // Check if 'data' is unaligned |
|
4810 __ andcc(data, 7, G1); |
|
4811 __ br(Assembler::zero, false, Assembler::pt, L_aligned); |
|
4812 __ delayed()->nop(); |
|
4813 |
|
4814 Register left_shift = L1; |
|
4815 Register right_shift = L2; |
|
4816 Register data_ptr = L3; |
|
4817 |
|
4818 // Get left and right shift values in bits |
|
4819 __ sll(G1, LogBitsPerByte, left_shift); |
|
4820 __ mov(64, right_shift); |
|
4821 __ sub(right_shift, left_shift, right_shift); |
|
4822 |
|
4823 // Align to read 'data' |
|
4824 __ sub(data, G1, data_ptr); |
|
4825 |
|
4826 // Load first 8 bytes of 'data' |
|
4827 __ ldx(data_ptr, 0, O4); |
|
4828 __ sllx(O4, left_shift, O4); |
|
4829 __ ldx(data_ptr, 8, O5); |
|
4830 __ srlx(O5, right_shift, G4); |
|
4831 __ bset(G4, O4); |
|
4832 |
|
4833 // Load second 8 bytes of 'data' |
|
4834 __ sllx(O5, left_shift, O5); |
|
4835 __ ldx(data_ptr, 16, G4); |
|
4836 __ srlx(G4, right_shift, G4); |
|
4837 __ ba(L_main); |
|
4838 __ delayed()->bset(G4, O5); |
|
4839 |
|
4840 // If 'data' is aligned, load normally |
|
4841 __ BIND(L_aligned); |
|
4842 __ ldx(data, 0, O4); |
|
4843 __ ldx(data, 8, O5); |
|
4844 |
|
4845 __ BIND(L_main); |
|
4846 __ ldx(subkeyH, 0, O2); |
|
4847 __ ldx(subkeyH, 8, O3); |
|
4848 |
|
4849 __ xor3(O0, O4, O0); |
|
4850 __ xor3(O1, O5, O1); |
|
4851 |
|
4852 __ xmulxhi(O0, O3, G3); |
|
4853 __ xmulx(O0, O2, O5); |
|
4854 __ xmulxhi(O1, O2, G4); |
|
4855 __ xmulxhi(O1, O3, G5); |
|
4856 __ xmulx(O0, O3, G1); |
|
4857 __ xmulx(O1, O3, G2); |
|
4858 __ xmulx(O1, O2, O3); |
|
4859 __ xmulxhi(O0, O2, O4); |
|
4860 |
|
4861 __ mov(0xE1, O0); |
|
4862 __ sllx(O0, 56, O0); |
|
4863 |
|
4864 __ xor3(O5, G3, O5); |
|
4865 __ xor3(O5, G4, O5); |
|
4866 __ xor3(G5, G1, G1); |
|
4867 __ xor3(G1, O3, G1); |
|
4868 __ srlx(G2, 63, O1); |
|
4869 __ srlx(G1, 63, G3); |
|
4870 __ sllx(G2, 63, O3); |
|
4871 __ sllx(G2, 58, O2); |
|
4872 __ xor3(O3, O2, O2); |
|
4873 |
|
4874 __ sllx(G1, 1, G1); |
|
4875 __ or3(G1, O1, G1); |
|
4876 |
|
4877 __ xor3(G1, O2, G1); |
|
4878 |
|
4879 __ sllx(G2, 1, G2); |
|
4880 |
|
4881 __ xmulxhi(G1, O0, O1); |
|
4882 __ xmulx(G1, O0, O2); |
|
4883 __ xmulxhi(G2, O0, O3); |
|
4884 __ xmulx(G2, O0, G1); |
|
4885 |
|
4886 __ xor3(O4, O1, O4); |
|
4887 __ xor3(O5, O2, O5); |
|
4888 __ xor3(O5, O3, O5); |
|
4889 |
|
4890 __ sllx(O4, 1, O2); |
|
4891 __ srlx(O5, 63, O3); |
|
4892 |
|
4893 __ or3(O2, O3, O0); |
|
4894 |
|
4895 __ sllx(O5, 1, O1); |
|
4896 __ srlx(G1, 63, O2); |
|
4897 __ or3(O1, O2, O1); |
|
4898 __ xor3(O1, G3, O1); |
|
4899 |
|
4900 __ deccc(len); |
|
4901 __ br(Assembler::notZero, true, Assembler::pt, L_ghash_loop); |
|
4902 __ delayed()->add(data, 16, data); |
|
4903 |
|
4904 __ stx(O0, I0, 0); |
|
4905 __ stx(O1, I0, 8); |
|
4906 |
|
4907 __ ret(); |
|
4908 __ delayed()->restore(); |
|
4909 |
|
4910 return start; |
|
4911 } |
|
4912 |
4789 void generate_initial() { |
4913 void generate_initial() { |
4790 // Generates all stubs and initializes the entry points |
4914 // Generates all stubs and initializes the entry points |
4791 |
4915 |
4792 //------------------------------------------------------------------------------------------------------------------------ |
4916 //------------------------------------------------------------------------------------------------------------------------ |
4793 // entry points that exist in all platforms |
4917 // entry points that exist in all platforms |