Mercurial > hg > truffle
comparison src/share/vm/graal/graalCodeInstaller.cpp @ 6521:2a0c9f20baa1
consolidated framework for runtime and stub calls and moved declaration of descriptors for such calls to the source file in which they are used
author | Doug Simon <doug.simon@oracle.com> |
---|---|
date | Fri, 05 Oct 2012 17:55:12 +0200 |
parents | e722fa145b37 |
children | 2463eb24b644 |
comparison
equal
deleted
inserted
replaced
6520:14d158886ce0 | 6521:2a0c9f20baa1 |
---|---|
527 record_scope(pc_offset, code_pos, new GrowableArray<ScopeValue*>()); | 527 record_scope(pc_offset, code_pos, new GrowableArray<ScopeValue*>()); |
528 | 528 |
529 _debug_recorder->end_safepoint(pc_offset); | 529 _debug_recorder->end_safepoint(pc_offset); |
530 } | 530 } |
531 | 531 |
532 address CodeInstaller::runtime_call_target_address(oop runtime_call) { | |
533 address target_addr = 0x0; | |
534 if (runtime_call == RuntimeCall::Debug()) { | |
535 TRACE_graal_3("RuntimeCall::Debug()"); | |
536 } else if (runtime_call == RuntimeCall::UnwindException()) { | |
537 target_addr = Runtime1::entry_for(Runtime1::graal_unwind_exception_call_id); | |
538 TRACE_graal_3("RuntimeCall::UnwindException()"); | |
539 } else if (runtime_call == RuntimeCall::SetDeoptInfo()) { | |
540 target_addr = Runtime1::entry_for(Runtime1::graal_set_deopt_info_id); | |
541 TRACE_graal_3("RuntimeCall::SetDeoptInfo()"); | |
542 } else if (runtime_call == RuntimeCall::CreateNullPointerException()) { | |
543 target_addr = Runtime1::entry_for(Runtime1::graal_create_null_pointer_exception_id); | |
544 TRACE_graal_3("RuntimeCall::CreateNullPointerException()"); | |
545 } else if (runtime_call == RuntimeCall::CreateOutOfBoundsException()) { | |
546 target_addr = Runtime1::entry_for(Runtime1::graal_create_out_of_bounds_exception_id); | |
547 TRACE_graal_3("RuntimeCall::CreateOutOfBoundsException()"); | |
548 } else if (runtime_call == RuntimeCall::JavaTimeMillis()) { | |
549 target_addr = CAST_FROM_FN_PTR(address, os::javaTimeMillis); | |
550 TRACE_graal_3("RuntimeCall::JavaTimeMillis()"); | |
551 } else if (runtime_call == RuntimeCall::JavaTimeNanos()) { | |
552 target_addr = CAST_FROM_FN_PTR(address, os::javaTimeNanos); | |
553 TRACE_graal_3("RuntimeCall::JavaTimeNanos()"); | |
554 } else if (runtime_call == RuntimeCall::ArithmeticFrem()) { | |
555 target_addr = Runtime1::entry_for(Runtime1::graal_arithmetic_frem_id); | |
556 TRACE_graal_3("RuntimeCall::ArithmeticFrem()"); | |
557 } else if (runtime_call == RuntimeCall::ArithmeticDrem()) { | |
558 target_addr = Runtime1::entry_for(Runtime1::graal_arithmetic_drem_id); | |
559 TRACE_graal_3("RuntimeCall::ArithmeticDrem()"); | |
560 } else if (runtime_call == RuntimeCall::ArithmeticSin()) { | |
561 target_addr = CAST_FROM_FN_PTR(address, SharedRuntime::dsin); | |
562 TRACE_graal_3("RuntimeCall::ArithmeticSin()"); | |
563 } else if (runtime_call == RuntimeCall::ArithmeticCos()) { | |
564 target_addr = CAST_FROM_FN_PTR(address, SharedRuntime::dcos); | |
565 TRACE_graal_3("RuntimeCall::ArithmeticCos()"); | |
566 } else if (runtime_call == RuntimeCall::ArithmeticTan()) { | |
567 target_addr = CAST_FROM_FN_PTR(address, SharedRuntime::dtan); | |
568 TRACE_graal_3("RuntimeCall::ArithmeticTan()"); | |
569 } else if (runtime_call == RuntimeCall::RegisterFinalizer()) { | |
570 target_addr = Runtime1::entry_for(Runtime1::register_finalizer_id); | |
571 TRACE_graal_3("RuntimeCall::RegisterFinalizer()"); | |
572 } else if (runtime_call == RuntimeCall::Deoptimize()) { | |
573 target_addr = SharedRuntime::deopt_blob()->uncommon_trap(); | |
574 TRACE_graal_3("RuntimeCall::Deoptimize()"); | |
575 } else if (runtime_call == RuntimeCall::GenericCallback()) { | |
576 target_addr = Runtime1::entry_for(Runtime1::graal_generic_callback_id); | |
577 TRACE_graal_3("RuntimeCall::GenericCallback()"); | |
578 } else if (runtime_call == RuntimeCall::LogPrimitive()) { | |
579 target_addr = Runtime1::entry_for(Runtime1::graal_log_primitive_id); | |
580 TRACE_graal_3("RuntimeCall::LogPrimitive()"); | |
581 } else if (runtime_call == RuntimeCall::LogPrintf()) { | |
582 target_addr = Runtime1::entry_for(Runtime1::graal_log_printf_id); | |
583 TRACE_graal_3("RuntimeCall::LogPrintf()"); | |
584 } else if (runtime_call == RuntimeCall::LogObject()) { | |
585 target_addr = Runtime1::entry_for(Runtime1::graal_log_object_id); | |
586 TRACE_graal_3("RuntimeCall::LogObject()"); | |
587 } else { | |
588 runtime_call->print(); | |
589 fatal("runtime_call not implemented"); | |
590 } | |
591 return target_addr; | |
592 } | |
593 | |
594 void CodeInstaller::site_Call(CodeBuffer& buffer, jint pc_offset, oop site) { | 532 void CodeInstaller::site_Call(CodeBuffer& buffer, jint pc_offset, oop site) { |
595 oop target = InstalledCode_Call::target(site); | 533 oop target = InstalledCode_Call::target(site); |
596 instanceKlass* target_klass = instanceKlass::cast(target->klass()); | 534 instanceKlass* target_klass = instanceKlass::cast(target->klass()); |
597 | 535 |
598 oop runtime_call = NULL; // RuntimeCall | |
599 oop hotspot_method = NULL; // JavaMethod | 536 oop hotspot_method = NULL; // JavaMethod |
600 oop global_stub = NULL; | 537 oop global_stub = NULL; |
601 | 538 |
602 if (target_klass->is_subclass_of(SystemDictionary::Long_klass())) { | 539 if (target_klass->is_subclass_of(SystemDictionary::Long_klass())) { |
603 global_stub = target; | 540 global_stub = target; |
604 } else if (target->is_a(RuntimeCall::klass())) { | |
605 runtime_call = target; | |
606 } else { | 541 } else { |
607 hotspot_method = target; | 542 hotspot_method = target; |
608 } | 543 } |
609 | 544 |
610 oop debug_info = InstalledCode_Call::debugInfo(site); | 545 oop debug_info = InstalledCode_Call::debugInfo(site); |
611 | 546 |
612 assert((runtime_call ? 1 : 0) + (hotspot_method ? 1 : 0) + (global_stub ? 1 : 0) == 1, "Call site needs exactly one type"); | 547 assert((hotspot_method ? 1 : 0) + (global_stub ? 1 : 0) == 1, "Call site needs exactly one type"); |
613 | 548 |
614 NativeInstruction* inst = nativeInstruction_at(_instructions->start() + pc_offset); | 549 NativeInstruction* inst = nativeInstruction_at(_instructions->start() + pc_offset); |
615 jint next_pc_offset = 0x0; | 550 jint next_pc_offset = 0x0; |
616 bool is_call_reg = false; | 551 bool is_call_reg = false; |
617 if (inst->is_call() || inst->is_jump()) { | 552 if (inst->is_call() || inst->is_jump()) { |
628 assert(hotspot_method != NULL, "only valid for virtual calls"); | 563 assert(hotspot_method != NULL, "only valid for virtual calls"); |
629 is_call_reg = true; | 564 is_call_reg = true; |
630 next_pc_offset = pc_offset + ((NativeCallReg *) inst)->next_instruction_offset(); | 565 next_pc_offset = pc_offset + ((NativeCallReg *) inst)->next_instruction_offset(); |
631 } else { | 566 } else { |
632 tty->print_cr("at pc_offset %d", pc_offset); | 567 tty->print_cr("at pc_offset %d", pc_offset); |
633 runtime_call->print(); | |
634 fatal("unsupported type of instruction for call site"); | 568 fatal("unsupported type of instruction for call site"); |
635 } | 569 } |
636 | 570 |
637 if (target->is_a(SystemDictionary::HotSpotCompiledMethod_klass())) { | 571 if (target->is_a(SystemDictionary::HotSpotCompiledMethod_klass())) { |
638 assert(inst->is_jump(), "jump expected"); | 572 assert(inst->is_jump(), "jump expected"); |
648 oop frame = DebugInfo::bytecodePosition(debug_info); | 582 oop frame = DebugInfo::bytecodePosition(debug_info); |
649 _debug_recorder->add_safepoint(next_pc_offset, BytecodeFrame::leafGraphId(frame), create_oop_map(_total_frame_size, _parameter_count, debug_info)); | 583 _debug_recorder->add_safepoint(next_pc_offset, BytecodeFrame::leafGraphId(frame), create_oop_map(_total_frame_size, _parameter_count, debug_info)); |
650 record_scope(next_pc_offset, frame, new GrowableArray<ScopeValue*>()); | 584 record_scope(next_pc_offset, frame, new GrowableArray<ScopeValue*>()); |
651 } | 585 } |
652 | 586 |
653 if (runtime_call != NULL) { | 587 if (global_stub != NULL) { |
654 if (runtime_call != RuntimeCall::Debug()) { | |
655 address target_addr = runtime_call_target_address(runtime_call); | |
656 | |
657 if (inst->is_call()) { | |
658 // NOTE: for call without a mov, the offset must fit a 32-bit immediate | |
659 // see also CompilerToVM.getMaxCallTargetOffset() | |
660 NativeCall* call = nativeCall_at(_instructions->start() + pc_offset); | |
661 call->set_destination(target_addr); | |
662 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand); | |
663 } else if (inst->is_mov_literal64()) { | |
664 NativeMovConstReg* mov = nativeMovConstReg_at(_instructions->start() + pc_offset); | |
665 mov->set_data((intptr_t) target_addr); | |
666 _instructions->relocate(mov->instruction_address(), runtime_call_Relocation::spec(), Assembler::imm_operand); | |
667 } else { | |
668 runtime_call->print(); | |
669 fatal("unknown type of instruction for runtime call"); | |
670 } | |
671 } | |
672 } else if (global_stub != NULL) { | |
673 assert(java_lang_boxing_object::is_instance(global_stub, T_LONG), "global_stub needs to be of type Long"); | 588 assert(java_lang_boxing_object::is_instance(global_stub, T_LONG), "global_stub needs to be of type Long"); |
674 | 589 |
675 if (inst->is_call()) { | 590 if (inst->is_call()) { |
676 nativeCall_at((address)inst)->set_destination(VmIds::getStub(global_stub)); | 591 // NOTE: for call without a mov, the offset must fit a 32-bit immediate |
592 // see also CompilerToVM.getMaxCallTargetOffset() | |
593 NativeCall* call = nativeCall_at((address) (inst)); | |
594 call->set_destination(VmIds::getStub(global_stub)); | |
595 _instructions->relocate(call->instruction_address(), runtime_call_Relocation::spec(), Assembler::call32_operand); | |
596 } else if (inst->is_mov_literal64()) { | |
597 NativeMovConstReg* mov = nativeMovConstReg_at((address) (inst)); | |
598 mov->set_data((intptr_t) VmIds::getStub(global_stub)); | |
599 _instructions->relocate(mov->instruction_address(), runtime_call_Relocation::spec(), Assembler::imm_operand); | |
677 } else { | 600 } else { |
678 nativeJump_at((address)inst)->set_jump_destination(VmIds::getStub(global_stub)); | 601 NativeJump* jump = nativeJump_at((address) (inst)); |
679 } | 602 jump->set_jump_destination(VmIds::getStub(global_stub)); |
680 _instructions->relocate((address)inst, runtime_call_Relocation::spec(), Assembler::call32_operand); | 603 _instructions->relocate((address)inst, runtime_call_Relocation::spec(), Assembler::call32_operand); |
604 } | |
681 TRACE_graal_3("relocating (stub) at %016x", inst); | 605 TRACE_graal_3("relocating (stub) at %016x", inst); |
682 } else { // method != NULL | 606 } else { // method != NULL |
683 assert(hotspot_method != NULL, "unexpected JavaMethod"); | 607 assert(hotspot_method != NULL, "unexpected JavaMethod"); |
684 assert(debug_info != NULL, "debug info expected"); | 608 assert(debug_info != NULL, "debug info expected"); |
685 | 609 |