comparison src/share/vm/graal/graalCodeInstaller.cpp @ 2891:75a99b4f1c98

Rebranded C++ part from C1X to Graal.
author Thomas Wuerthinger <thomas@wuerthinger.net>
date Wed, 08 Jun 2011 14:01:51 +0200
parents c23d45daff9b
children d577d07cedec
comparison
equal deleted inserted replaced
2890:c23d45daff9b 2891:75a99b4f1c98
20 * or visit www.oracle.com if you need additional information or have any 20 * or visit www.oracle.com if you need additional information or have any
21 * questions. 21 * questions.
22 */ 22 */
23 23
24 #include "precompiled.hpp" 24 #include "precompiled.hpp"
25 #include "c1x/c1x_Compiler.hpp" 25 #include "graal/graalCompiler.hpp"
26 #include "c1x/c1x_CodeInstaller.hpp" 26 #include "graal/graalCodeInstaller.hpp"
27 #include "c1x/c1x_JavaAccess.hpp" 27 #include "graal/graalJavaAccess.hpp"
28 #include "c1x/c1x_VmIds.hpp" 28 #include "graal/graalVmIds.hpp"
29 #include "c1/c1_Runtime1.hpp" 29 #include "c1/c1_Runtime1.hpp"
30 #include "classfile/vmSymbols.hpp" 30 #include "classfile/vmSymbols.hpp"
31 #include "vmreg_x86.inline.hpp" 31 #include "vmreg_x86.inline.hpp"
32 32
33 33
38 XMMRegister XMM_REGS[] = { xmm0, xmm1, xmm2, xmm3, xmm4, xmm5, xmm6, xmm7, xmm8, xmm9, xmm10, xmm11, xmm12, xmm13, xmm14, xmm15 }; 38 XMMRegister XMM_REGS[] = { xmm0, xmm1, xmm2, xmm3, xmm4, xmm5, xmm6, xmm7, xmm8, xmm9, xmm10, xmm11, xmm12, xmm13, xmm14, xmm15 };
39 const static int NUM_XMM_REGS = sizeof(XMM_REGS) / sizeof(XMMRegister); 39 const static int NUM_XMM_REGS = sizeof(XMM_REGS) / sizeof(XMMRegister);
40 const static int NUM_REGS = NUM_CPU_REGS + NUM_XMM_REGS; 40 const static int NUM_REGS = NUM_CPU_REGS + NUM_XMM_REGS;
41 const static jlong NO_REF_MAP = 0x8000000000000000L; 41 const static jlong NO_REF_MAP = 0x8000000000000000L;
42 42
43 // convert c1x register indices (as used in oop maps) to hotspot registers 43 // convert graal register indices (as used in oop maps) to hotspot registers
44 VMReg get_hotspot_reg(jint c1x_reg) { 44 VMReg get_hotspot_reg(jint graal_reg) {
45 45
46 assert(c1x_reg >= 0 && c1x_reg < NUM_REGS, "invalid register number"); 46 assert(graal_reg >= 0 && graal_reg < NUM_REGS, "invalid register number");
47 if (c1x_reg < NUM_CPU_REGS) { 47 if (graal_reg < NUM_CPU_REGS) {
48 return CPU_REGS[c1x_reg]->as_VMReg(); 48 return CPU_REGS[graal_reg]->as_VMReg();
49 } else { 49 } else {
50 return XMM_REGS[c1x_reg - NUM_CPU_REGS]->as_VMReg(); 50 return XMM_REGS[graal_reg - NUM_CPU_REGS]->as_VMReg();
51 } 51 }
52 } 52 }
53 53
54 static bool is_bit_set(oop bit_map, int i) { 54 static bool is_bit_set(oop bit_map, int i) {
55 const int MapWordBits = 64; 55 const int MapWordBits = 64;
103 } 103 }
104 104
105 return map; 105 return map;
106 } 106 }
107 107
108 // TODO: finish this - c1x doesn't provide any scope values at the moment 108 // TODO: finish this - graal doesn't provide any scope values at the moment
109 static ScopeValue* get_hotspot_value(oop value, int frame_size) { 109 static ScopeValue* get_hotspot_value(oop value, int frame_size) {
110 if (value == CiValue::IllegalValue()) { 110 if (value == CiValue::IllegalValue()) {
111 return new LocationValue(Location::new_stk_loc(Location::invalid, 0)); 111 return new LocationValue(Location::new_stk_loc(Location::invalid, 0));
112 } 112 }
113 113
114 BasicType type = C1XCompiler::kindToBasicType(CiKind::typeChar(CiValue::kind(value))); 114 BasicType type = GraalCompiler::kindToBasicType(CiKind::typeChar(CiValue::kind(value)));
115 Location::Type locationType = Location::normal; 115 Location::Type locationType = Location::normal;
116 if (type == T_OBJECT || type == T_ARRAY) locationType = Location::oop; 116 if (type == T_OBJECT || type == T_ARRAY) locationType = Location::oop;
117 if (value->is_a(CiRegisterValue::klass())) { 117 if (value->is_a(CiRegisterValue::klass())) {
118 jint number = CiRegister::number(CiRegisterValue::reg(value)); 118 jint number = CiRegister::number(CiRegisterValue::reg(value));
119 if (number < 16) { 119 if (number < 16) {
170 ciMethodObject = (ciMethod *) _env->get_object(method); 170 ciMethodObject = (ciMethod *) _env->get_object(method);
171 _parameter_count = method->size_of_parameters(); 171 _parameter_count = method->size_of_parameters();
172 } 172 }
173 173
174 // (very) conservative estimate: each site needs a relocation 174 // (very) conservative estimate: each site needs a relocation
175 //CodeBuffer buffer("temp c1x method", _total_size, _sites->length() * relocInfo::length_limit); 175 //CodeBuffer buffer("temp graal method", _total_size, _sites->length() * relocInfo::length_limit);
176 CodeBuffer buffer(CompilerThread::current()->get_buffer_blob()); 176 CodeBuffer buffer(CompilerThread::current()->get_buffer_blob());
177 initialize_buffer(buffer); 177 initialize_buffer(buffer);
178 process_exception_handlers(); 178 process_exception_handlers();
179 179
180 int stack_slots = (_frame_size / HeapWordSize) + 2; // conversion to words, need to add two slots for ret address and frame pointer 180 int stack_slots = (_frame_size / HeapWordSize) + 2; // conversion to words, need to add two slots for ret address and frame pointer
181 ThreadToNativeFromVM t((JavaThread*) Thread::current()); 181 ThreadToNativeFromVM t((JavaThread*) Thread::current());
182 _env->register_method(ciMethodObject, -1, &_offsets, _custom_stack_area_offset, &buffer, stack_slots, _debug_recorder->_oopmaps, &_exception_handler_table, 182 _env->register_method(ciMethodObject, -1, &_offsets, _custom_stack_area_offset, &buffer, stack_slots, _debug_recorder->_oopmaps, &_exception_handler_table,
183 &_implicit_exception_table, C1XCompiler::instance(), _env->comp_level(), false, false); 183 &_implicit_exception_table, GraalCompiler::instance(), _env->comp_level(), false, false);
184 184
185 } 185 }
186 186
187 // constructor used to create a stub 187 // constructor used to create a stub
188 CodeInstaller::CodeInstaller(Handle target_method, jlong& id) { 188 CodeInstaller::CodeInstaller(Handle target_method, jlong& id) {
196 CodeBuffer buffer(CompilerThread::current()->get_buffer_blob()); 196 CodeBuffer buffer(CompilerThread::current()->get_buffer_blob());
197 initialize_buffer(buffer); 197 initialize_buffer(buffer);
198 198
199 const char* cname = java_lang_String::as_utf8_string(_name); 199 const char* cname = java_lang_String::as_utf8_string(_name);
200 BufferBlob* blob = BufferBlob::create(strdup(cname), &buffer); // this is leaking strings... but only a limited number of stubs will be created 200 BufferBlob* blob = BufferBlob::create(strdup(cname), &buffer); // this is leaking strings... but only a limited number of stubs will be created
201 IF_TRACE_C1X_3 Disassembler::decode((CodeBlob*) blob); 201 IF_TRACE_graal_3 Disassembler::decode((CodeBlob*) blob);
202 id = VmIds::addStub(blob->code_begin()); 202 id = VmIds::addStub(blob->code_begin());
203 } 203 }
204 204
205 void CodeInstaller::initialize_fields(Handle target_method) { 205 void CodeInstaller::initialize_fields(Handle target_method) {
206 _citarget_method = HotSpotTargetMethod::targetMethod(target_method); 206 _citarget_method = HotSpotTargetMethod::targetMethod(target_method);
258 for (int i = 0; i < _sites->length(); i++) { 258 for (int i = 0; i < _sites->length(); i++) {
259 oop site = sites[i]; 259 oop site = sites[i];
260 jint pc_offset = CiTargetMethod_Site::pcOffset(site); 260 jint pc_offset = CiTargetMethod_Site::pcOffset(site);
261 261
262 if (site->is_a(CiTargetMethod_Safepoint::klass())) { 262 if (site->is_a(CiTargetMethod_Safepoint::klass())) {
263 TRACE_C1X_4("safepoint at %i", pc_offset); 263 TRACE_graal_4("safepoint at %i", pc_offset);
264 site_Safepoint(buffer, pc_offset, site); 264 site_Safepoint(buffer, pc_offset, site);
265 } else if (site->is_a(CiTargetMethod_Call::klass())) { 265 } else if (site->is_a(CiTargetMethod_Call::klass())) {
266 TRACE_C1X_4("call at %i", pc_offset); 266 TRACE_graal_4("call at %i", pc_offset);
267 site_Call(buffer, pc_offset, site); 267 site_Call(buffer, pc_offset, site);
268 } else if (site->is_a(CiTargetMethod_DataPatch::klass())) { 268 } else if (site->is_a(CiTargetMethod_DataPatch::klass())) {
269 TRACE_C1X_4("datapatch at %i", pc_offset); 269 TRACE_graal_4("datapatch at %i", pc_offset);
270 site_DataPatch(buffer, pc_offset, site); 270 site_DataPatch(buffer, pc_offset, site);
271 } else if (site->is_a(CiTargetMethod_Mark::klass())) { 271 } else if (site->is_a(CiTargetMethod_Mark::klass())) {
272 TRACE_C1X_4("mark at %i", pc_offset); 272 TRACE_graal_4("mark at %i", pc_offset);
273 site_Mark(buffer, pc_offset, site); 273 site_Mark(buffer, pc_offset, site);
274 } else { 274 } else {
275 fatal("unexpected Site subclass"); 275 fatal("unexpected Site subclass");
276 } 276 }
277 } 277 }
409 } else { 409 } else {
410 Bytecodes::Code code = Bytecodes::java_code_at(method, method->bcp_from(bci)); 410 Bytecodes::Code code = Bytecodes::java_code_at(method, method->bcp_from(bci));
411 reexecute = Interpreter::bytecode_should_reexecute(code); 411 reexecute = Interpreter::bytecode_should_reexecute(code);
412 } 412 }
413 413
414 if (TraceC1X >= 2) { 414 if (Tracegraal >= 2) {
415 tty->print_cr("Recording scope pc_offset=%d bci=%d frame=%d", pc_offset, bci, frame); 415 tty->print_cr("Recording scope pc_offset=%d bci=%d frame=%d", pc_offset, bci, frame);
416 } 416 }
417 417
418 if (frame != NULL) { 418 if (frame != NULL) {
419 jint local_count = CiFrame::numLocals(frame); 419 jint local_count = CiFrame::numLocals(frame);
425 425
426 GrowableArray<ScopeValue*>* locals = new GrowableArray<ScopeValue*> (); 426 GrowableArray<ScopeValue*>* locals = new GrowableArray<ScopeValue*> ();
427 GrowableArray<ScopeValue*>* expressions = new GrowableArray<ScopeValue*> (); 427 GrowableArray<ScopeValue*>* expressions = new GrowableArray<ScopeValue*> ();
428 GrowableArray<MonitorValue*>* monitors = new GrowableArray<MonitorValue*> (); 428 GrowableArray<MonitorValue*>* monitors = new GrowableArray<MonitorValue*> ();
429 429
430 if (TraceC1X >= 2) { 430 if (Tracegraal >= 2) {
431 tty->print_cr("Scope at bci %d with %d values", bci, values->length()); 431 tty->print_cr("Scope at bci %d with %d values", bci, values->length());
432 tty->print_cr("%d locals %d expressions, %d monitors", local_count, expression_count, monitor_count); 432 tty->print_cr("%d locals %d expressions, %d monitors", local_count, expression_count, monitor_count);
433 } 433 }
434 434
435 for (jint i = 0; i < values->length(); i++) { 435 for (jint i = 0; i < values->length(); i++) {
491 } 491 }
492 492
493 if (runtime_call != NULL) { 493 if (runtime_call != NULL) {
494 NativeCall* call = nativeCall_at(_instructions->start() + pc_offset); 494 NativeCall* call = nativeCall_at(_instructions->start() + pc_offset);
495 if (runtime_call == CiRuntimeCall::Debug()) { 495 if (runtime_call == CiRuntimeCall::Debug()) {
496 TRACE_C1X_3("CiRuntimeCall::Debug()"); 496 TRACE_graal_3("CiRuntimeCall::Debug()");
497 } else if (runtime_call == CiRuntimeCall::UnwindException()) { 497 } else if (runtime_call == CiRuntimeCall::UnwindException()) {
498 call->set_destination(Runtime1::entry_for(Runtime1::c1x_unwind_exception_call_id)); 498 call->set_destination(Runtime1::entry_for(Runtime1::graal_unwind_exception_call_id));
499 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand); 499 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand);
500 TRACE_C1X_3("CiRuntimeCall::UnwindException()"); 500 TRACE_graal_3("CiRuntimeCall::UnwindException()");
501 } else if (runtime_call == CiRuntimeCall::HandleException()) { 501 } else if (runtime_call == CiRuntimeCall::HandleException()) {
502 call->set_destination(Runtime1::entry_for(Runtime1::c1x_handle_exception_id)); 502 call->set_destination(Runtime1::entry_for(Runtime1::graal_handle_exception_id));
503 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand); 503 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand);
504 TRACE_C1X_3("CiRuntimeCall::HandleException()"); 504 TRACE_graal_3("CiRuntimeCall::HandleException()");
505 } else if (runtime_call == CiRuntimeCall::JavaTimeMillis()) { 505 } else if (runtime_call == CiRuntimeCall::JavaTimeMillis()) {
506 call->set_destination((address)os::javaTimeMillis); 506 call->set_destination((address)os::javaTimeMillis);
507 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand); 507 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand);
508 TRACE_C1X_3("CiRuntimeCall::JavaTimeMillis()"); 508 TRACE_graal_3("CiRuntimeCall::JavaTimeMillis()");
509 } else if (runtime_call == CiRuntimeCall::JavaTimeNanos()) { 509 } else if (runtime_call == CiRuntimeCall::JavaTimeNanos()) {
510 call->set_destination((address)os::javaTimeNanos); 510 call->set_destination((address)os::javaTimeNanos);
511 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand); 511 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand);
512 TRACE_C1X_3("CiRuntimeCall::JavaTimeNanos()"); 512 TRACE_graal_3("CiRuntimeCall::JavaTimeNanos()");
513 } else if (runtime_call == CiRuntimeCall::ArithmeticFrem()) { 513 } else if (runtime_call == CiRuntimeCall::ArithmeticFrem()) {
514 call->set_destination(Runtime1::entry_for(Runtime1::c1x_arithmetic_frem_id)); 514 call->set_destination(Runtime1::entry_for(Runtime1::graal_arithmetic_frem_id));
515 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand); 515 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand);
516 TRACE_C1X_3("CiRuntimeCall::ArithmeticFrem()"); 516 TRACE_graal_3("CiRuntimeCall::ArithmeticFrem()");
517 } else if (runtime_call == CiRuntimeCall::ArithmeticDrem()) { 517 } else if (runtime_call == CiRuntimeCall::ArithmeticDrem()) {
518 call->set_destination(Runtime1::entry_for(Runtime1::c1x_arithmetic_drem_id)); 518 call->set_destination(Runtime1::entry_for(Runtime1::graal_arithmetic_drem_id));
519 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand); 519 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand);
520 TRACE_C1X_3("CiRuntimeCall::ArithmeticDrem()"); 520 TRACE_graal_3("CiRuntimeCall::ArithmeticDrem()");
521 } else if (runtime_call == CiRuntimeCall::RegisterFinalizer()) { 521 } else if (runtime_call == CiRuntimeCall::RegisterFinalizer()) {
522 call->set_destination(Runtime1::entry_for(Runtime1::register_finalizer_id)); 522 call->set_destination(Runtime1::entry_for(Runtime1::register_finalizer_id));
523 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand); 523 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand);
524 } else if (runtime_call == CiRuntimeCall::Deoptimize()) { 524 } else if (runtime_call == CiRuntimeCall::Deoptimize()) {
525 call->set_destination(SharedRuntime::deopt_blob()->uncommon_trap()); 525 call->set_destination(SharedRuntime::deopt_blob()->uncommon_trap());
536 nativeCall_at((address)inst)->set_destination(VmIds::getStub(global_stub)); 536 nativeCall_at((address)inst)->set_destination(VmIds::getStub(global_stub));
537 } else { 537 } else {
538 nativeJump_at((address)inst)->set_jump_destination(VmIds::getStub(global_stub)); 538 nativeJump_at((address)inst)->set_jump_destination(VmIds::getStub(global_stub));
539 } 539 }
540 _instructions->relocate((address)inst, runtime_call_Relocation::spec(), Assembler::call32_operand); 540 _instructions->relocate((address)inst, runtime_call_Relocation::spec(), Assembler::call32_operand);
541 TRACE_C1X_3("relocating (stub) at %016x", inst); 541 TRACE_graal_3("relocating (stub) at %016x", inst);
542 } else if (symbol != NULL) { 542 } else if (symbol != NULL) {
543 fatal("symbol"); 543 fatal("symbol");
544 } else { // method != NULL 544 } else { // method != NULL
545 NativeCall* call = nativeCall_at(_instructions->start() + pc_offset); 545 NativeCall* call = nativeCall_at(_instructions->start() + pc_offset);
546 assert(hotspot_method != NULL, "unexpected RiMethod"); 546 assert(hotspot_method != NULL, "unexpected RiMethod");
549 methodOop method = NULL; 549 methodOop method = NULL;
550 if (hotspot_method->is_a(HotSpotMethodResolved::klass())) method = VmIds::get<methodOop>(HotSpotMethodResolved::vmId(hotspot_method)); 550 if (hotspot_method->is_a(HotSpotMethodResolved::klass())) method = VmIds::get<methodOop>(HotSpotMethodResolved::vmId(hotspot_method));
551 551
552 assert(debug_info != NULL, "debug info expected"); 552 assert(debug_info != NULL, "debug info expected");
553 553
554 TRACE_C1X_3("method call"); 554 TRACE_graal_3("method call");
555 switch (_next_call_type) { 555 switch (_next_call_type) {
556 case MARK_INVOKEVIRTUAL: 556 case MARK_INVOKEVIRTUAL:
557 case MARK_INVOKEINTERFACE: { 557 case MARK_INVOKEINTERFACE: {
558 assert(method == NULL || !method->is_static(), "cannot call static method with invokeinterface"); 558 assert(method == NULL || !method->is_static(), "cannot call static method with invokeinterface");
559 559
619 long disp = dest - next_instruction; 619 long disp = dest - next_instruction;
620 assert(disp == (jint) disp, "disp doesn't fit in 32 bits"); 620 assert(disp == (jint) disp, "disp doesn't fit in 32 bits");
621 *((jint*) operand) = (jint) disp; 621 *((jint*) operand) = (jint) disp;
622 622
623 _instructions->relocate(instruction, section_word_Relocation::spec((address) dest, CodeBuffer::SECT_CONSTS), Assembler::disp32_operand); 623 _instructions->relocate(instruction, section_word_Relocation::spec((address) dest, CodeBuffer::SECT_CONSTS), Assembler::disp32_operand);
624 TRACE_C1X_3("relocating (%c) at %016x/%016x with destination at %016x (%d)", typeChar, instruction, operand, dest, size); 624 TRACE_graal_3("relocating (%c) at %016x/%016x with destination at %016x (%d)", typeChar, instruction, operand, dest, size);
625 break; 625 break;
626 } 626 }
627 case 'a': { 627 case 'a': {
628 address operand = Assembler::locate_operand(instruction, Assembler::imm_operand); 628 address operand = Assembler::locate_operand(instruction, Assembler::imm_operand);
629 Handle obj = CiConstant::object(constant); 629 Handle obj = CiConstant::object(constant);
630 630
631 if (obj->is_a(HotSpotTypeResolved::klass())) { 631 if (obj->is_a(HotSpotTypeResolved::klass())) {
632 assert(!obj.is_null(), ""); 632 assert(!obj.is_null(), "");
633 *((jobject*) operand) = JNIHandles::make_local(java_lang_Class::as_klassOop(HotSpotTypeResolved::javaMirror(obj))); 633 *((jobject*) operand) = JNIHandles::make_local(java_lang_Class::as_klassOop(HotSpotTypeResolved::javaMirror(obj)));
634 _instructions->relocate(instruction, oop_Relocation::spec_for_immediate(), Assembler::imm_operand); 634 _instructions->relocate(instruction, oop_Relocation::spec_for_immediate(), Assembler::imm_operand);
635 TRACE_C1X_3("relocating (HotSpotType) at %016x/%016x", instruction, operand); 635 TRACE_graal_3("relocating (HotSpotType) at %016x/%016x", instruction, operand);
636 } else { 636 } else {
637 jobject value; 637 jobject value;
638 if (obj() == HotSpotProxy::DUMMY_CONSTANT_OBJ()) { 638 if (obj() == HotSpotProxy::DUMMY_CONSTANT_OBJ()) {
639 value = (jobject) Universe::non_oop_word(); 639 value = (jobject) Universe::non_oop_word();
640 } else { 640 } else {
641 value = JNIHandles::make_local(obj()); 641 value = JNIHandles::make_local(obj());
642 } 642 }
643 *((jobject*) operand) = value; 643 *((jobject*) operand) = value;
644 _instructions->relocate(instruction, oop_Relocation::spec_for_immediate(), Assembler::imm_operand); 644 _instructions->relocate(instruction, oop_Relocation::spec_for_immediate(), Assembler::imm_operand);
645 TRACE_C1X_3("relocating (oop constant) at %016x/%016x", instruction, operand); 645 TRACE_graal_3("relocating (oop constant) at %016x/%016x", instruction, operand);
646 } 646 }
647 break; 647 break;
648 } 648 }
649 default: 649 default:
650 fatal("unexpected CiKind in DataPatch"); 650 fatal("unexpected CiKind in DataPatch");