comparison src/cpu/x86/vm/sharedRuntime_x86_64.cpp @ 10998:e7f5651d459c

8003268: SharedRuntime::generate_native_wrapper doesn't save all registers across runtime tracing calls for JNI critical native methods Reviewed-by: kvn
author twisti
date Tue, 11 Jun 2013 11:13:09 -0700
parents e961c11b85fe
children 6b0fd0964b87 fca8f4799229 6a936747b569
comparison
equal deleted inserted replaced
10997:46c544b8fbfc 10998:e7f5651d459c
1427 assert(!body_arg.first()->is_Register() || body_arg.first()->as_Register() != tmp_reg, 1427 assert(!body_arg.first()->is_Register() || body_arg.first()->as_Register() != tmp_reg,
1428 "possible collision"); 1428 "possible collision");
1429 assert(!length_arg.first()->is_Register() || length_arg.first()->as_Register() != tmp_reg, 1429 assert(!length_arg.first()->is_Register() || length_arg.first()->as_Register() != tmp_reg,
1430 "possible collision"); 1430 "possible collision");
1431 1431
1432 __ block_comment("unpack_array_argument {");
1433
1432 // Pass the length, ptr pair 1434 // Pass the length, ptr pair
1433 Label is_null, done; 1435 Label is_null, done;
1434 VMRegPair tmp; 1436 VMRegPair tmp;
1435 tmp.set_ptr(tmp_reg->as_VMReg()); 1437 tmp.set_ptr(tmp_reg->as_VMReg());
1436 if (reg.first()->is_stack()) { 1438 if (reg.first()->is_stack()) {
1451 // Pass zeros 1453 // Pass zeros
1452 __ xorptr(tmp_reg, tmp_reg); 1454 __ xorptr(tmp_reg, tmp_reg);
1453 move_ptr(masm, tmp, body_arg); 1455 move_ptr(masm, tmp, body_arg);
1454 move32_64(masm, tmp, length_arg); 1456 move32_64(masm, tmp, length_arg);
1455 __ bind(done); 1457 __ bind(done);
1458
1459 __ block_comment("} unpack_array_argument");
1456 } 1460 }
1457 1461
1458 1462
1459 // Different signatures may require very different orders for the move 1463 // Different signatures may require very different orders for the move
1460 // to avoid clobbering other arguments. There's no simple way to 1464 // to avoid clobbering other arguments. There's no simple way to
2168 default: 2172 default:
2169 move32_64(masm, in_regs[i], out_regs[c_arg]); 2173 move32_64(masm, in_regs[i], out_regs[c_arg]);
2170 } 2174 }
2171 } 2175 }
2172 2176
2173 // point c_arg at the first arg that is already loaded in case we 2177 int c_arg;
2174 // need to spill before we call out
2175 int c_arg = total_c_args - total_in_args;
2176 2178
2177 // Pre-load a static method's oop into r14. Used both by locking code and 2179 // Pre-load a static method's oop into r14. Used both by locking code and
2178 // the normal JNI call code. 2180 // the normal JNI call code.
2179 if (method->is_static() && !is_critical_native) { 2181 if (!is_critical_native) {
2180 2182 // point c_arg at the first arg that is already loaded in case we
2181 // load oop into a register 2183 // need to spill before we call out
2182 __ movoop(oop_handle_reg, JNIHandles::make_local(method->method_holder()->java_mirror())); 2184 c_arg = total_c_args - total_in_args;
2183 2185
2184 // Now handlize the static class mirror it's known not-null. 2186 if (method->is_static()) {
2185 __ movptr(Address(rsp, klass_offset), oop_handle_reg); 2187
2186 map->set_oop(VMRegImpl::stack2reg(klass_slot_offset)); 2188 // load oop into a register
2187 2189 __ movoop(oop_handle_reg, JNIHandles::make_local(method->method_holder()->java_mirror()));
2188 // Now get the handle 2190
2189 __ lea(oop_handle_reg, Address(rsp, klass_offset)); 2191 // Now handlize the static class mirror it's known not-null.
2190 // store the klass handle as second argument 2192 __ movptr(Address(rsp, klass_offset), oop_handle_reg);
2191 __ movptr(c_rarg1, oop_handle_reg); 2193 map->set_oop(VMRegImpl::stack2reg(klass_slot_offset));
2192 // and protect the arg if we must spill 2194
2193 c_arg--; 2195 // Now get the handle
2196 __ lea(oop_handle_reg, Address(rsp, klass_offset));
2197 // store the klass handle as second argument
2198 __ movptr(c_rarg1, oop_handle_reg);
2199 // and protect the arg if we must spill
2200 c_arg--;
2201 }
2202 } else {
2203 // For JNI critical methods we need to save all registers in save_args.
2204 c_arg = 0;
2194 } 2205 }
2195 2206
2196 // Change state to native (we save the return address in the thread, since it might not 2207 // Change state to native (we save the return address in the thread, since it might not
2197 // be pushed on the stack when we do a a stack traversal). It is enough that the pc() 2208 // be pushed on the stack when we do a a stack traversal). It is enough that the pc()
2198 // points into the right code segment. It does not have to be the correct return pc. 2209 // points into the right code segment. It does not have to be the correct return pc.