Mercurial > hg > truffle
comparison src/cpu/zero/vm/cppInterpreter_zero.cpp @ 1514:22af4ce8dba1
6951784: Zero deoptimizer changes
Summary: The way Zero currently handles deoptimization can lead to methods being freed while they are still being executed.
Reviewed-by: twisti
Contributed-by: Gary Benson <gbenson@redhat.com>
author | twisti |
---|---|
date | Wed, 12 May 2010 03:49:52 -0700 |
parents | 0c5b3cf3c1f5 |
children | c18cbe5936b8 |
comparison
equal
deleted
inserted
replaced
1513:df736661d0c8 | 1514:22af4ce8dba1 |
---|---|
35 thread->set_last_Java_frame(); \ | 35 thread->set_last_Java_frame(); \ |
36 func; \ | 36 func; \ |
37 thread->reset_last_Java_frame(); \ | 37 thread->reset_last_Java_frame(); \ |
38 fixup_after_potential_safepoint() | 38 fixup_after_potential_safepoint() |
39 | 39 |
40 void CppInterpreter::normal_entry(methodOop method, intptr_t UNUSED, TRAPS) { | 40 int CppInterpreter::normal_entry(methodOop method, intptr_t UNUSED, TRAPS) { |
41 JavaThread *thread = (JavaThread *) THREAD; | 41 JavaThread *thread = (JavaThread *) THREAD; |
42 | 42 |
43 // Allocate and initialize our frame. | 43 // Allocate and initialize our frame. |
44 InterpreterFrame *frame = InterpreterFrame::build(method, CHECK); | 44 InterpreterFrame *frame = InterpreterFrame::build(method, CHECK_0); |
45 thread->push_zero_frame(frame); | 45 thread->push_zero_frame(frame); |
46 | 46 |
47 // Execute those bytecodes! | 47 // Execute those bytecodes! |
48 main_loop(0, THREAD); | 48 main_loop(0, THREAD); |
49 | |
50 // No deoptimized frames on the stack | |
51 return 0; | |
49 } | 52 } |
50 | 53 |
51 void CppInterpreter::main_loop(int recurse, TRAPS) { | 54 void CppInterpreter::main_loop(int recurse, TRAPS) { |
52 JavaThread *thread = (JavaThread *) THREAD; | 55 JavaThread *thread = (JavaThread *) THREAD; |
53 ZeroStack *stack = thread->zero_stack(); | 56 ZeroStack *stack = thread->zero_stack(); |
163 // Push our result | 166 // Push our result |
164 for (int i = 0; i < result_slots; i++) | 167 for (int i = 0; i < result_slots; i++) |
165 stack->push(result[-i]); | 168 stack->push(result[-i]); |
166 } | 169 } |
167 | 170 |
168 void CppInterpreter::native_entry(methodOop method, intptr_t UNUSED, TRAPS) { | 171 int CppInterpreter::native_entry(methodOop method, intptr_t UNUSED, TRAPS) { |
169 // Make sure method is native and not abstract | 172 // Make sure method is native and not abstract |
170 assert(method->is_native() && !method->is_abstract(), "should be"); | 173 assert(method->is_native() && !method->is_abstract(), "should be"); |
171 | 174 |
172 JavaThread *thread = (JavaThread *) THREAD; | 175 JavaThread *thread = (JavaThread *) THREAD; |
173 ZeroStack *stack = thread->zero_stack(); | 176 ZeroStack *stack = thread->zero_stack(); |
174 | 177 |
175 // Allocate and initialize our frame | 178 // Allocate and initialize our frame |
176 InterpreterFrame *frame = InterpreterFrame::build(method, CHECK); | 179 InterpreterFrame *frame = InterpreterFrame::build(method, CHECK_0); |
177 thread->push_zero_frame(frame); | 180 thread->push_zero_frame(frame); |
178 interpreterState istate = frame->interpreter_state(); | 181 interpreterState istate = frame->interpreter_state(); |
179 intptr_t *locals = istate->locals(); | 182 intptr_t *locals = istate->locals(); |
180 | 183 |
181 // Update the invocation counter | 184 // Update the invocation counter |
428 | 431 |
429 default: | 432 default: |
430 ShouldNotReachHere(); | 433 ShouldNotReachHere(); |
431 } | 434 } |
432 } | 435 } |
433 } | 436 |
434 | 437 // No deoptimized frames on the stack |
435 void CppInterpreter::accessor_entry(methodOop method, intptr_t UNUSED, TRAPS) { | 438 return 0; |
439 } | |
440 | |
441 int CppInterpreter::accessor_entry(methodOop method, intptr_t UNUSED, TRAPS) { | |
436 JavaThread *thread = (JavaThread *) THREAD; | 442 JavaThread *thread = (JavaThread *) THREAD; |
437 ZeroStack *stack = thread->zero_stack(); | 443 ZeroStack *stack = thread->zero_stack(); |
438 intptr_t *locals = stack->sp(); | 444 intptr_t *locals = stack->sp(); |
439 | 445 |
440 // Drop into the slow path if we need a safepoint check | 446 // Drop into the slow path if we need a safepoint check |
441 if (SafepointSynchronize::do_call_back()) { | 447 if (SafepointSynchronize::do_call_back()) { |
442 normal_entry(method, 0, THREAD); | 448 return normal_entry(method, 0, THREAD); |
443 return; | |
444 } | 449 } |
445 | 450 |
446 // Load the object pointer and drop into the slow path | 451 // Load the object pointer and drop into the slow path |
447 // if we have a NullPointerException | 452 // if we have a NullPointerException |
448 oop object = LOCALS_OBJECT(0); | 453 oop object = LOCALS_OBJECT(0); |
449 if (object == NULL) { | 454 if (object == NULL) { |
450 normal_entry(method, 0, THREAD); | 455 return normal_entry(method, 0, THREAD); |
451 return; | |
452 } | 456 } |
453 | 457 |
454 // Read the field index from the bytecode, which looks like this: | 458 // Read the field index from the bytecode, which looks like this: |
455 // 0: aload_0 | 459 // 0: aload_0 |
456 // 1: getfield | 460 // 1: getfield |
468 // Get the entry from the constant pool cache, and drop into | 472 // Get the entry from the constant pool cache, and drop into |
469 // the slow path if it has not been resolved | 473 // the slow path if it has not been resolved |
470 constantPoolCacheOop cache = method->constants()->cache(); | 474 constantPoolCacheOop cache = method->constants()->cache(); |
471 ConstantPoolCacheEntry* entry = cache->entry_at(index); | 475 ConstantPoolCacheEntry* entry = cache->entry_at(index); |
472 if (!entry->is_resolved(Bytecodes::_getfield)) { | 476 if (!entry->is_resolved(Bytecodes::_getfield)) { |
473 normal_entry(method, 0, THREAD); | 477 return normal_entry(method, 0, THREAD); |
474 return; | |
475 } | 478 } |
476 | 479 |
477 // Get the result and push it onto the stack | 480 // Get the result and push it onto the stack |
478 switch (entry->flag_state()) { | 481 switch (entry->flag_state()) { |
479 case ltos: | 482 case ltos: |
480 case dtos: | 483 case dtos: |
481 stack->overflow_check(1, CHECK); | 484 stack->overflow_check(1, CHECK_0); |
482 stack->alloc(wordSize); | 485 stack->alloc(wordSize); |
483 break; | 486 break; |
484 } | 487 } |
485 if (entry->is_volatile()) { | 488 if (entry->is_volatile()) { |
486 switch (entry->flag_state()) { | 489 switch (entry->flag_state()) { |
556 | 559 |
557 default: | 560 default: |
558 ShouldNotReachHere(); | 561 ShouldNotReachHere(); |
559 } | 562 } |
560 } | 563 } |
561 } | 564 |
562 | 565 // No deoptimized frames on the stack |
563 void CppInterpreter::empty_entry(methodOop method, intptr_t UNUSED, TRAPS) { | 566 return 0; |
567 } | |
568 | |
569 int CppInterpreter::empty_entry(methodOop method, intptr_t UNUSED, TRAPS) { | |
564 JavaThread *thread = (JavaThread *) THREAD; | 570 JavaThread *thread = (JavaThread *) THREAD; |
565 ZeroStack *stack = thread->zero_stack(); | 571 ZeroStack *stack = thread->zero_stack(); |
566 | 572 |
567 // Drop into the slow path if we need a safepoint check | 573 // Drop into the slow path if we need a safepoint check |
568 if (SafepointSynchronize::do_call_back()) { | 574 if (SafepointSynchronize::do_call_back()) { |
569 normal_entry(method, 0, THREAD); | 575 return normal_entry(method, 0, THREAD); |
570 return; | |
571 } | 576 } |
572 | 577 |
573 // Pop our parameters | 578 // Pop our parameters |
574 stack->set_sp(stack->sp() + method->size_of_parameters()); | 579 stack->set_sp(stack->sp() + method->size_of_parameters()); |
580 | |
581 // No deoptimized frames on the stack | |
582 return 0; | |
575 } | 583 } |
576 | 584 |
577 InterpreterFrame *InterpreterFrame::build(const methodOop method, TRAPS) { | 585 InterpreterFrame *InterpreterFrame::build(const methodOop method, TRAPS) { |
578 JavaThread *thread = (JavaThread *) THREAD; | 586 JavaThread *thread = (JavaThread *) THREAD; |
579 ZeroStack *stack = thread->zero_stack(); | 587 ZeroStack *stack = thread->zero_stack(); |