comparison src/cpu/x86/vm/methodHandles_x86.cpp @ 1304:76c1d7d13ec5

6932091: JSR 292 x86 code cleanup Summary: Some code cleanups found during the JSR 292 SPARC port. Reviewed-by: kvn, never
author twisti
date Thu, 18 Mar 2010 09:56:51 +0100
parents 51db1e4b379d
children 4a9cc99938e3
comparison
equal deleted inserted replaced
1303:c047da02984c 1304:76c1d7d13ec5
58 58
59 return me; 59 return me;
60 } 60 }
61 61
62 #ifdef ASSERT 62 #ifdef ASSERT
63 static void verify_argslot(MacroAssembler* _masm, Register rax_argslot, 63 static void verify_argslot(MacroAssembler* _masm, Register argslot_reg,
64 const char* error_message) { 64 const char* error_message) {
65 // Verify that argslot lies within (rsp, rbp]. 65 // Verify that argslot lies within (rsp, rbp].
66 Label L_ok, L_bad; 66 Label L_ok, L_bad;
67 __ cmpptr(rax_argslot, rbp); 67 __ cmpptr(argslot_reg, rbp);
68 __ jccb(Assembler::above, L_bad); 68 __ jccb(Assembler::above, L_bad);
69 __ cmpptr(rsp, rax_argslot); 69 __ cmpptr(rsp, argslot_reg);
70 __ jccb(Assembler::below, L_ok); 70 __ jccb(Assembler::below, L_ok);
71 __ bind(L_bad); 71 __ bind(L_bad);
72 __ stop(error_message); 72 __ stop(error_message);
73 __ bind(L_ok); 73 __ bind(L_ok);
74 } 74 }
176 __ jccb(Assembler::less, loop); 176 __ jccb(Assembler::less, loop);
177 } 177 }
178 178
179 // Now move the argslot down, to point to the opened-up space. 179 // Now move the argslot down, to point to the opened-up space.
180 __ lea(rax_argslot, Address(rax_argslot, arg_slots, Address::times_ptr)); 180 __ lea(rax_argslot, Address(rax_argslot, arg_slots, Address::times_ptr));
181
182 if (TaggedStackInterpreter && arg_mask != _INSERT_NO_MASK) {
183 // The caller has specified a bitmask of tags to put into the opened space.
184 // This only works when the arg_slots value is an assembly-time constant.
185 int constant_arg_slots = arg_slots.as_constant() / stack_move_unit();
186 int tag_offset = Interpreter::tag_offset_in_bytes() - Interpreter::value_offset_in_bytes();
187 for (int slot = 0; slot < constant_arg_slots; slot++) {
188 BasicType slot_type = ((arg_mask & (1 << slot)) == 0 ? T_OBJECT : T_INT);
189 int slot_offset = Interpreter::stackElementSize() * slot;
190 Address tag_addr(rax_argslot, slot_offset + tag_offset);
191 __ movptr(tag_addr, frame::tag_for_basic_type(slot_type));
192 }
193 // Note that the new argument slots are tagged properly but contain
194 // garbage at this point. The value portions must be initialized
195 // by the caller. (Especially references!)
196 }
197 } 181 }
198 182
199 // Helper to remove argument slots from the stack. 183 // Helper to remove argument slots from the stack.
200 // arg_slots must be a multiple of stack_move_unit() and >= 0 184 // arg_slots must be a multiple of stack_move_unit() and >= 0
201 void MethodHandles::remove_arg_slots(MacroAssembler* _masm, 185 void MethodHandles::remove_arg_slots(MacroAssembler* _masm,
204 Register rbx_temp, Register rdx_temp) { 188 Register rbx_temp, Register rdx_temp) {
205 assert_different_registers(rax_argslot, rbx_temp, rdx_temp, 189 assert_different_registers(rax_argslot, rbx_temp, rdx_temp,
206 (!arg_slots.is_register() ? rsp : arg_slots.as_register())); 190 (!arg_slots.is_register() ? rsp : arg_slots.as_register()));
207 191
208 #ifdef ASSERT 192 #ifdef ASSERT
209 { 193 // Verify that [argslot..argslot+size) lies within (rsp, rbp).
210 // Verify that [argslot..argslot+size) lies within (rsp, rbp). 194 __ lea(rbx_temp, Address(rax_argslot, arg_slots, Address::times_ptr));
211 Label L_ok, L_bad; 195 verify_argslot(_masm, rbx_temp, "deleted argument(s) must fall within current frame");
212 __ lea(rbx_temp, Address(rax_argslot, arg_slots, Address::times_ptr));
213 __ cmpptr(rbx_temp, rbp);
214 __ jccb(Assembler::above, L_bad);
215 __ cmpptr(rsp, rax_argslot);
216 __ jccb(Assembler::below, L_ok);
217 __ bind(L_bad);
218 __ stop("deleted argument(s) must fall within current frame");
219 __ bind(L_ok);
220 }
221 if (arg_slots.is_register()) { 196 if (arg_slots.is_register()) {
222 Label L_ok, L_bad; 197 Label L_ok, L_bad;
223 __ cmpptr(arg_slots.as_register(), (int32_t) NULL_WORD); 198 __ cmpptr(arg_slots.as_register(), (int32_t) NULL_WORD);
224 __ jccb(Assembler::less, L_bad); 199 __ jccb(Assembler::less, L_bad);
225 __ testl(arg_slots.as_register(), -stack_move_unit() - 1); 200 __ testl(arg_slots.as_register(), -stack_move_unit() - 1);
319 Address rcx_amh_vmargslot( rcx_recv, sun_dyn_AdapterMethodHandle::vmargslot_offset_in_bytes() ); 294 Address rcx_amh_vmargslot( rcx_recv, sun_dyn_AdapterMethodHandle::vmargslot_offset_in_bytes() );
320 Address rcx_amh_argument( rcx_recv, sun_dyn_AdapterMethodHandle::argument_offset_in_bytes() ); 295 Address rcx_amh_argument( rcx_recv, sun_dyn_AdapterMethodHandle::argument_offset_in_bytes() );
321 Address rcx_amh_conversion( rcx_recv, sun_dyn_AdapterMethodHandle::conversion_offset_in_bytes() ); 296 Address rcx_amh_conversion( rcx_recv, sun_dyn_AdapterMethodHandle::conversion_offset_in_bytes() );
322 Address vmarg; // __ argument_address(vmargslot) 297 Address vmarg; // __ argument_address(vmargslot)
323 298
324 int tag_offset = -1;
325 if (TaggedStackInterpreter) {
326 tag_offset = Interpreter::tag_offset_in_bytes() - Interpreter::value_offset_in_bytes();
327 assert(tag_offset = wordSize, "stack grows as expected");
328 }
329
330 const int java_mirror_offset = klassOopDesc::klass_part_offset_in_bytes() + Klass::java_mirror_offset_in_bytes(); 299 const int java_mirror_offset = klassOopDesc::klass_part_offset_in_bytes() + Klass::java_mirror_offset_in_bytes();
331 300
332 if (have_entry(ek)) { 301 if (have_entry(ek)) {
333 __ nop(); // empty stubs make SG sick 302 __ nop(); // empty stubs make SG sick
334 return; 303 return;
370 __ pop(rdi_pc); // caller PC 339 __ pop(rdi_pc); // caller PC
371 340
372 __ mov(rsp, rsi); // cut the stack back to where the caller started 341 __ mov(rsp, rsi); // cut the stack back to where the caller started
373 342
374 // Repush the arguments as if coming from the interpreter. 343 // Repush the arguments as if coming from the interpreter.
375 if (TaggedStackInterpreter) __ push(frame::tag_for_basic_type(T_INT));
376 __ push(rdx_code); 344 __ push(rdx_code);
377 if (TaggedStackInterpreter) __ push(frame::tag_for_basic_type(T_OBJECT));
378 __ push(rcx_fail); 345 __ push(rcx_fail);
379 if (TaggedStackInterpreter) __ push(frame::tag_for_basic_type(T_OBJECT));
380 __ push(rax_want); 346 __ push(rax_want);
381 347
382 Register rbx_method = rbx_temp; 348 Register rbx_method = rbx_temp;
383 Label no_method; 349 Label no_method;
384 // FIXME: fill in _raise_exception_method with a suitable sun.dyn method 350 // FIXME: fill in _raise_exception_method with a suitable sun.dyn method
395 361
396 // If we get here, the Java runtime did not do its job of creating the exception. 362 // If we get here, the Java runtime did not do its job of creating the exception.
397 // Do something that is at least causes a valid throw from the interpreter. 363 // Do something that is at least causes a valid throw from the interpreter.
398 __ bind(no_method); 364 __ bind(no_method);
399 __ pop(rax_want); 365 __ pop(rax_want);
400 if (TaggedStackInterpreter) __ pop(rcx_fail);
401 __ pop(rcx_fail); 366 __ pop(rcx_fail);
402 __ push(rax_want); 367 __ push(rax_want);
403 __ push(rcx_fail); 368 __ push(rcx_fail);
404 __ jump(ExternalAddress(Interpreter::throw_WrongMethodType_entry())); 369 __ jump(ExternalAddress(Interpreter::throw_WrongMethodType_entry()));
405 } 370 }
508 case _bound_ref_direct_mh: 473 case _bound_ref_direct_mh:
509 case _bound_int_direct_mh: 474 case _bound_int_direct_mh:
510 case _bound_long_direct_mh: 475 case _bound_long_direct_mh:
511 { 476 {
512 bool direct_to_method = (ek >= _bound_ref_direct_mh); 477 bool direct_to_method = (ek >= _bound_ref_direct_mh);
513 BasicType arg_type = T_ILLEGAL; 478 BasicType arg_type = T_ILLEGAL;
514 if (ek == _bound_long_mh || ek == _bound_long_direct_mh) { 479 int arg_mask = _INSERT_NO_MASK;
515 arg_type = T_LONG; 480 int arg_slots = -1;
516 } else if (ek == _bound_int_mh || ek == _bound_int_direct_mh) { 481 get_ek_bound_mh_info(ek, arg_type, arg_mask, arg_slots);
517 arg_type = T_INT;
518 } else {
519 assert(ek == _bound_ref_mh || ek == _bound_ref_direct_mh, "must be ref");
520 arg_type = T_OBJECT;
521 }
522 int arg_slots = type2size[arg_type];
523 int arg_mask = (arg_type == T_OBJECT ? _INSERT_REF_MASK :
524 arg_slots == 1 ? _INSERT_INT_MASK : _INSERT_LONG_MASK);
525 482
526 // make room for the new argument: 483 // make room for the new argument:
527 __ movl(rax_argslot, rcx_bmh_vmargslot); 484 __ movl(rax_argslot, rcx_bmh_vmargslot);
528 __ lea(rax_argslot, __ argument_address(rax_argslot)); 485 __ lea(rax_argslot, __ argument_address(rax_argslot));
529 insert_arg_slots(_masm, arg_slots * stack_move_unit(), arg_mask, 486 insert_arg_slots(_masm, arg_slots * stack_move_unit(), arg_mask,
658 // the low bits will be correct, but the high bits may need cleaning. 615 // the low bits will be correct, but the high bits may need cleaning.
659 // The vminfo will guide us to clean those bits. 616 // The vminfo will guide us to clean those bits.
660 } 617 }
661 break; 618 break;
662 default: 619 default:
663 assert(false, ""); 620 ShouldNotReachHere();
664 } 621 }
665 goto finish_int_conversion; 622
666 } 623 // Do the requested conversion and store the value.
667
668 finish_int_conversion:
669 {
670 Register rbx_vminfo = rbx_temp; 624 Register rbx_vminfo = rbx_temp;
671 __ movl(rbx_vminfo, rcx_amh_conversion); 625 __ movl(rbx_vminfo, rcx_amh_conversion);
672 assert(CONV_VMINFO_SHIFT == 0, "preshifted"); 626 assert(CONV_VMINFO_SHIFT == 0, "preshifted");
673 627
674 // get the new MH: 628 // get the new MH:
690 __ bind(zero_extend); 644 __ bind(zero_extend);
691 // this is taken for int->char 645 // this is taken for int->char
692 __ shrl(rdx_temp /*, rcx*/); 646 __ shrl(rdx_temp /*, rcx*/);
693 647
694 __ bind(done); 648 __ bind(done);
695 __ movl(vmarg, rdx_temp); 649 __ movl(vmarg, rdx_temp); // Store the value.
696 __ xchgptr(rcx, rbx_vminfo); // restore rcx_recv 650 __ xchgptr(rcx, rbx_vminfo); // restore rcx_recv
697 651
698 __ jump_to_method_handle_entry(rcx_recv, rdx_temp); 652 __ jump_to_method_handle_entry(rcx_recv, rdx_temp);
699 } 653 }
700 break; 654 break;
742 __ movl(vmarg2, rdx_temp); 696 __ movl(vmarg2, rdx_temp);
743 #endif 697 #endif
744 } 698 }
745 break; 699 break;
746 default: 700 default:
747 assert(false, ""); 701 ShouldNotReachHere();
748 } 702 }
749 703
750 __ movptr(rcx_recv, rcx_mh_vmtarget); 704 __ movptr(rcx_recv, rcx_mh_vmtarget);
751 __ jump_to_method_handle_entry(rcx_recv, rdx_temp); 705 __ jump_to_method_handle_entry(rcx_recv, rdx_temp);
752 } 706 }
776 } 730 }
777 #else //_LP64 731 #else //_LP64
778 if (ek == _adapter_opt_f2d) { 732 if (ek == _adapter_opt_f2d) {
779 __ fld_s(vmarg); // load float to ST0 733 __ fld_s(vmarg); // load float to ST0
780 __ fstp_s(vmarg); // store single 734 __ fstp_s(vmarg); // store single
781 } else if (!TaggedStackInterpreter) { 735 } else {
782 __ fld_d(vmarg); // load double to ST0 736 __ fld_d(vmarg); // load double to ST0
783 __ fstp_s(vmarg); // store single
784 } else {
785 Address vmarg_tag = vmarg.plus_disp(tag_offset);
786 Address vmarg2 = vmarg.plus_disp(Interpreter::stackElementSize());
787 // vmarg2_tag does not participate in this code
788 Register rbx_tag = rbx_temp;
789 __ movl(rbx_tag, vmarg_tag); // preserve tag
790 __ movl(rdx_temp, vmarg2); // get second word of double
791 __ movl(vmarg_tag, rdx_temp); // align with first word
792 __ fld_d(vmarg); // load double to ST0
793 __ movl(vmarg_tag, rbx_tag); // restore tag
794 __ fstp_s(vmarg); // store single 737 __ fstp_s(vmarg); // store single
795 } 738 }
796 #endif //_LP64 739 #endif //_LP64
797 740
798 if (ek == _adapter_opt_d2f) { 741 if (ek == _adapter_opt_d2f) {
820 case _adapter_opt_rot_1_up: 763 case _adapter_opt_rot_1_up:
821 case _adapter_opt_rot_1_down: 764 case _adapter_opt_rot_1_down:
822 case _adapter_opt_rot_2_up: 765 case _adapter_opt_rot_2_up:
823 case _adapter_opt_rot_2_down: 766 case _adapter_opt_rot_2_down:
824 { 767 {
825 int rotate = 0, swap_slots = 0; 768 int swap_bytes = 0, rotate = 0;
826 switch ((int)ek) { 769 get_ek_adapter_opt_swap_rot_info(ek, swap_bytes, rotate);
827 case _adapter_opt_swap_1: swap_slots = 1; break;
828 case _adapter_opt_swap_2: swap_slots = 2; break;
829 case _adapter_opt_rot_1_up: swap_slots = 1; rotate++; break;
830 case _adapter_opt_rot_1_down: swap_slots = 1; rotate--; break;
831 case _adapter_opt_rot_2_up: swap_slots = 2; rotate++; break;
832 case _adapter_opt_rot_2_down: swap_slots = 2; rotate--; break;
833 default: assert(false, "");
834 }
835
836 // the real size of the move must be doubled if TaggedStackInterpreter:
837 int swap_bytes = (int)( swap_slots * Interpreter::stackElementWords() * wordSize );
838 770
839 // 'argslot' is the position of the first argument to swap 771 // 'argslot' is the position of the first argument to swap
840 __ movl(rax_argslot, rcx_amh_vmargslot); 772 __ movl(rax_argslot, rcx_amh_vmargslot);
841 __ lea(rax_argslot, __ argument_address(rax_argslot)); 773 __ lea(rax_argslot, __ argument_address(rax_argslot));
842 774
1022 case _adapter_opt_spread_0: 954 case _adapter_opt_spread_0:
1023 case _adapter_opt_spread_1: 955 case _adapter_opt_spread_1:
1024 case _adapter_opt_spread_more: 956 case _adapter_opt_spread_more:
1025 { 957 {
1026 // spread an array out into a group of arguments 958 // spread an array out into a group of arguments
1027 int length_constant = -1; 959 int length_constant = get_ek_adapter_opt_spread_info(ek);
1028 switch (ek) {
1029 case _adapter_opt_spread_0: length_constant = 0; break;
1030 case _adapter_opt_spread_1: length_constant = 1; break;
1031 }
1032 960
1033 // find the address of the array argument 961 // find the address of the array argument
1034 __ movl(rax_argslot, rcx_amh_vmargslot); 962 __ movl(rax_argslot, rcx_amh_vmargslot);
1035 __ lea(rax_argslot, __ argument_address(rax_argslot)); 963 __ lea(rax_argslot, __ argument_address(rax_argslot));
1036 964
1122 Label loop; 1050 Label loop;
1123 __ bind(loop); 1051 __ bind(loop);
1124 __ movptr(rbx_temp, Address(rsi_source, 0)); 1052 __ movptr(rbx_temp, Address(rsi_source, 0));
1125 __ movptr(Address(rax_argslot, 0), rbx_temp); 1053 __ movptr(Address(rax_argslot, 0), rbx_temp);
1126 __ addptr(rsi_source, type2aelembytes(elem_type)); 1054 __ addptr(rsi_source, type2aelembytes(elem_type));
1127 if (TaggedStackInterpreter) {
1128 __ movptr(Address(rax_argslot, tag_offset),
1129 frame::tag_for_basic_type(elem_type));
1130 }
1131 __ addptr(rax_argslot, Interpreter::stackElementSize()); 1055 __ addptr(rax_argslot, Interpreter::stackElementSize());
1132 __ cmpptr(rax_argslot, rdx_argslot_limit); 1056 __ cmpptr(rax_argslot, rdx_argslot_limit);
1133 __ jccb(Assembler::less, loop); 1057 __ jccb(Assembler::less, loop);
1134 } else if (length_constant == 0) { 1058 } else if (length_constant == 0) {
1135 __ bind(skip_array_check); 1059 __ bind(skip_array_check);
1139 int slot_offset = 0; 1063 int slot_offset = 0;
1140 for (int index = 0; index < length_constant; index++) { 1064 for (int index = 0; index < length_constant; index++) {
1141 __ movptr(rbx_temp, Address(rsi_array, elem_offset)); 1065 __ movptr(rbx_temp, Address(rsi_array, elem_offset));
1142 __ movptr(Address(rax_argslot, slot_offset), rbx_temp); 1066 __ movptr(Address(rax_argslot, slot_offset), rbx_temp);
1143 elem_offset += type2aelembytes(elem_type); 1067 elem_offset += type2aelembytes(elem_type);
1144 if (TaggedStackInterpreter) {
1145 __ movptr(Address(rax_argslot, slot_offset + tag_offset),
1146 frame::tag_for_basic_type(elem_type));
1147 }
1148 slot_offset += Interpreter::stackElementSize(); 1068 slot_offset += Interpreter::stackElementSize();
1149 } 1069 }
1150 } 1070 }
1151 1071
1152 // Arguments are spread. Move to next method handle. 1072 // Arguments are spread. Move to next method handle.