comparison src/cpu/x86/vm/assembler_x86.cpp @ 623:9adddb8c0fc8

6812831: factor duplicated assembly code for megamorphic invokeinterface (for 6655638) Summary: Code in vtableStubs and templateTable moved into MacroAssembler. Reviewed-by: kvn
author jrose
date Fri, 06 Mar 2009 21:36:50 -0800
parents 56aae7be60d4
children 337400e7a5dd
comparison
equal deleted inserted replaced
622:56aae7be60d4 623:9adddb8c0fc8
7074 pop(tmp); 7074 pop(tmp);
7075 } 7075 }
7076 } 7076 }
7077 7077
7078 7078
7079 // Look up the method for a megamorphic invokeinterface call.
7080 // The target method is determined by <intf_klass, itable_index>.
7081 // The receiver klass is in recv_klass.
7082 // On success, the result will be in method_result, and execution falls through.
7083 // On failure, execution transfers to the given label.
7084 void MacroAssembler::lookup_interface_method(Register recv_klass,
7085 Register intf_klass,
7086 RegisterConstant itable_index,
7087 Register method_result,
7088 Register scan_temp,
7089 Label& L_no_such_interface) {
7090 assert_different_registers(recv_klass, intf_klass, method_result, scan_temp);
7091 assert(itable_index.is_constant() || itable_index.as_register() == method_result,
7092 "caller must use same register for non-constant itable index as for method");
7093
7094 // Compute start of first itableOffsetEntry (which is at the end of the vtable)
7095 int vtable_base = instanceKlass::vtable_start_offset() * wordSize;
7096 int itentry_off = itableMethodEntry::method_offset_in_bytes();
7097 int scan_step = itableOffsetEntry::size() * wordSize;
7098 int vte_size = vtableEntry::size() * wordSize;
7099 Address::ScaleFactor times_vte_scale = Address::times_ptr;
7100 assert(vte_size == wordSize, "else adjust times_vte_scale");
7101
7102 movl(scan_temp, Address(recv_klass, instanceKlass::vtable_length_offset() * wordSize));
7103
7104 // %%% Could store the aligned, prescaled offset in the klassoop.
7105 lea(scan_temp, Address(recv_klass, scan_temp, times_vte_scale, vtable_base));
7106 if (HeapWordsPerLong > 1) {
7107 // Round up to align_object_offset boundary
7108 // see code for instanceKlass::start_of_itable!
7109 round_to(scan_temp, BytesPerLong);
7110 }
7111
7112 // Adjust recv_klass by scaled itable_index, so we can free itable_index.
7113 assert(itableMethodEntry::size() * wordSize == wordSize, "adjust the scaling in the code below");
7114 lea(recv_klass, Address(recv_klass, itable_index, Address::times_ptr, itentry_off));
7115
7116 // for (scan = klass->itable(); scan->interface() != NULL; scan += scan_step) {
7117 // if (scan->interface() == intf) {
7118 // result = (klass + scan->offset() + itable_index);
7119 // }
7120 // }
7121 Label search, found_method;
7122
7123 for (int peel = 1; peel >= 0; peel--) {
7124 movptr(method_result, Address(scan_temp, itableOffsetEntry::interface_offset_in_bytes()));
7125 cmpptr(intf_klass, method_result);
7126
7127 if (peel) {
7128 jccb(Assembler::equal, found_method);
7129 } else {
7130 jccb(Assembler::notEqual, search);
7131 // (invert the test to fall through to found_method...)
7132 }
7133
7134 if (!peel) break;
7135
7136 bind(search);
7137
7138 // Check that the previous entry is non-null. A null entry means that
7139 // the receiver class doesn't implement the interface, and wasn't the
7140 // same as when the caller was compiled.
7141 testptr(method_result, method_result);
7142 jcc(Assembler::zero, L_no_such_interface);
7143 addptr(scan_temp, scan_step);
7144 }
7145
7146 bind(found_method);
7147
7148 // Got a hit.
7149 movl(scan_temp, Address(scan_temp, itableOffsetEntry::offset_offset_in_bytes()));
7150 movptr(method_result, Address(recv_klass, scan_temp, Address::times_1));
7151 }
7152
7153
7079 void MacroAssembler::ucomisd(XMMRegister dst, AddressLiteral src) { 7154 void MacroAssembler::ucomisd(XMMRegister dst, AddressLiteral src) {
7080 ucomisd(dst, as_Address(src)); 7155 ucomisd(dst, as_Address(src));
7081 } 7156 }
7082 7157
7083 void MacroAssembler::ucomiss(XMMRegister dst, AddressLiteral src) { 7158 void MacroAssembler::ucomiss(XMMRegister dst, AddressLiteral src) {