1374 } |
1374 } |
1375 } |
1375 } |
1376 return false; |
1376 return false; |
1377 } |
1377 } |
1378 |
1378 |
1379 C2V_VMENTRY(jobject, getNextStackFrame, (JNIEnv*, jobject compilerToVM, jobject hs_frame, jobjectArray methods, jint initialSkip)) |
1379 void call_interface(JavaValue* result, Klass* spec_klass, Symbol* name, Symbol* signature, JavaCallArguments* args, TRAPS) { |
|
1380 CallInfo callinfo; |
|
1381 Handle receiver = args->receiver(); |
|
1382 Klass* recvrKlass = receiver.is_null() ? (Klass*)NULL : receiver->klass(); |
|
1383 LinkInfo link_info(spec_klass, name, signature); |
|
1384 LinkResolver::resolve_interface_call( |
|
1385 callinfo, receiver, recvrKlass, link_info, true, CHECK); |
|
1386 methodHandle method = callinfo.selected_method(); |
|
1387 assert(method.not_null(), "should have thrown exception"); |
|
1388 |
|
1389 // Invoke the method |
|
1390 JavaCalls::call(result, method, args, CHECK); |
|
1391 } |
|
1392 |
|
1393 C2V_VMENTRY(jobject, iterateFrames, (JNIEnv*, jobject compilerToVM, jobjectArray initial_methods, jobjectArray match_methods, jint initialSkip, jobject visitor_handle)) |
1380 ResourceMark rm; |
1394 ResourceMark rm; |
1381 |
1395 |
1382 if (!thread->has_last_Java_frame()) return NULL; |
1396 if (!thread->has_last_Java_frame()) { |
1383 Handle result = HotSpotStackFrameReference::klass()->allocate_instance_handle(CHECK_NULL); |
1397 return NULL; |
|
1398 } |
|
1399 Handle visitor(THREAD, JNIHandles::resolve_non_null(visitor_handle)); |
|
1400 Handle frame_reference = HotSpotStackFrameReference::klass()->allocate_instance_handle(CHECK_NULL); |
1384 HotSpotStackFrameReference::klass()->initialize(CHECK_NULL); |
1401 HotSpotStackFrameReference::klass()->initialize(CHECK_NULL); |
1385 |
1402 |
1386 StackFrameStream fst(thread); |
1403 StackFrameStream fst(thread); |
1387 if (hs_frame != NULL) { |
1404 |
1388 // look for the correct stack frame if one is given |
1405 jobjectArray methods = initial_methods; |
1389 intptr_t* stack_pointer = (intptr_t*) HotSpotStackFrameReference::stackPointer(hs_frame); |
|
1390 while (fst.current()->sp() != stack_pointer && !fst.is_done()) { |
|
1391 fst.next(); |
|
1392 } |
|
1393 if (fst.current()->sp() != stack_pointer) { |
|
1394 THROW_MSG_NULL(vmSymbols::java_lang_IllegalStateException(), "stack frame not found") |
|
1395 } |
|
1396 } |
|
1397 |
1406 |
1398 int frame_number = 0; |
1407 int frame_number = 0; |
1399 vframe* vf = vframe::new_vframe(fst.current(), fst.register_map(), thread); |
1408 vframe* vf = vframe::new_vframe(fst.current(), fst.register_map(), thread); |
1400 if (hs_frame != NULL) { |
|
1401 // look for the correct vframe within the stack frame if one is given |
|
1402 int last_frame_number = HotSpotStackFrameReference::frameNumber(hs_frame); |
|
1403 while (frame_number < last_frame_number) { |
|
1404 if (vf->is_top()) { |
|
1405 THROW_MSG_NULL(vmSymbols::java_lang_IllegalStateException(), "invalid frame number") |
|
1406 } |
|
1407 vf = vf->sender(); |
|
1408 frame_number ++; |
|
1409 } |
|
1410 // move one frame forward |
|
1411 if (vf->is_top()) { |
|
1412 if (fst.is_done()) { |
|
1413 return NULL; |
|
1414 } |
|
1415 fst.next(); |
|
1416 vf = vframe::new_vframe(fst.current(), fst.register_map(), thread); |
|
1417 frame_number = 0; |
|
1418 } else { |
|
1419 vf = vf->sender(); |
|
1420 frame_number++; |
|
1421 } |
|
1422 } |
|
1423 |
1409 |
1424 while (true) { |
1410 while (true) { |
1425 // look for the given method |
1411 // look for the given method |
|
1412 bool realloc_called = false; |
1426 while (true) { |
1413 while (true) { |
1427 StackValueCollection* locals = NULL; |
1414 StackValueCollection* locals = NULL; |
1428 if (vf->is_compiled_frame()) { |
1415 if (vf->is_compiled_frame()) { |
1429 // compiled method frame |
1416 // compiled method frame |
1430 compiledVFrame* cvf = compiledVFrame::cast(vf); |
1417 compiledVFrame* cvf = compiledVFrame::cast(vf); |
1431 if (methods == NULL || matches(methods, cvf->method())) { |
1418 if (methods == NULL || matches(methods, cvf->method())) { |
1432 if (initialSkip > 0) { |
1419 if (initialSkip > 0) { |
1433 initialSkip --; |
1420 initialSkip--; |
1434 } else { |
1421 } else { |
1435 ScopeDesc* scope = cvf->scope(); |
1422 ScopeDesc* scope = cvf->scope(); |
1436 // native wrappers do not have a scope |
1423 // native wrappers do not have a scope |
1437 if (scope != NULL && scope->objects() != NULL) { |
1424 if (scope != NULL && scope->objects() != NULL) { |
1438 bool realloc_failures = Deoptimization::realloc_objects(thread, fst.current(), scope->objects(), CHECK_NULL); |
1425 GrowableArray<ScopeValue*>* objects; |
1439 Deoptimization::reassign_fields(fst.current(), fst.register_map(), scope->objects(), realloc_failures, false); |
1426 if (!realloc_called) { |
|
1427 objects = scope->objects(); |
|
1428 } else { |
|
1429 // some object might already have been re-allocated, only reallocate the non-allocated ones |
|
1430 objects = new GrowableArray<ScopeValue*>(scope->objects()->length()); |
|
1431 int ii = 0; |
|
1432 for (int i = 0; i < scope->objects()->length(); i++) { |
|
1433 ObjectValue* sv = (ObjectValue*) scope->objects()->at(i); |
|
1434 if (sv->value().is_null()) { |
|
1435 objects->at_put(ii++, sv); |
|
1436 } |
|
1437 } |
|
1438 } |
|
1439 bool realloc_failures = Deoptimization::realloc_objects(thread, fst.current(), objects, CHECK_NULL); |
|
1440 Deoptimization::reassign_fields(fst.current(), fst.register_map(), objects, realloc_failures, false); |
|
1441 realloc_called = true; |
1440 |
1442 |
1441 GrowableArray<ScopeValue*>* local_values = scope->locals(); |
1443 GrowableArray<ScopeValue*>* local_values = scope->locals(); |
1442 assert(local_values != NULL, "NULL locals"); |
1444 assert(local_values != NULL, "NULL locals"); |
1443 typeArrayOop array_oop = oopFactory::new_boolArray(local_values->length(), CHECK_NULL); |
1445 typeArrayOop array_oop = oopFactory::new_boolArray(local_values->length(), CHECK_NULL); |
1444 typeArrayHandle array(THREAD, array_oop); |
1446 typeArrayHandle array(THREAD, array_oop); |
1446 ScopeValue* value = local_values->at(i); |
1448 ScopeValue* value = local_values->at(i); |
1447 if (value->is_object()) { |
1449 if (value->is_object()) { |
1448 array->bool_at_put(i, true); |
1450 array->bool_at_put(i, true); |
1449 } |
1451 } |
1450 } |
1452 } |
1451 HotSpotStackFrameReference::set_localIsVirtual(result, array()); |
1453 HotSpotStackFrameReference::set_localIsVirtual(frame_reference, array()); |
1452 } else { |
1454 } else { |
1453 HotSpotStackFrameReference::set_localIsVirtual(result, NULL); |
1455 HotSpotStackFrameReference::set_localIsVirtual(frame_reference, NULL); |
1454 } |
1456 } |
1455 |
1457 |
1456 locals = cvf->locals(); |
1458 locals = cvf->locals(); |
1457 HotSpotStackFrameReference::set_bci(result, cvf->bci()); |
1459 HotSpotStackFrameReference::set_bci(frame_reference, cvf->bci()); |
1458 oop method = CompilerToVM::get_jvmci_method(cvf->method(), CHECK_NULL); |
1460 oop method = CompilerToVM::get_jvmci_method(cvf->method(), CHECK_NULL); |
1459 HotSpotStackFrameReference::set_method(result, method); |
1461 HotSpotStackFrameReference::set_method(frame_reference, method); |
1460 } |
1462 } |
1461 } |
1463 } |
1462 } else if (vf->is_interpreted_frame()) { |
1464 } else if (vf->is_interpreted_frame()) { |
1463 // interpreted method frame |
1465 // interpreted method frame |
1464 interpretedVFrame* ivf = interpretedVFrame::cast(vf); |
1466 interpretedVFrame* ivf = interpretedVFrame::cast(vf); |
1465 if (methods == NULL || matches(methods, ivf->method())) { |
1467 if (methods == NULL || matches(methods, ivf->method())) { |
1466 if (initialSkip > 0) { |
1468 if (initialSkip > 0) { |
1467 initialSkip --; |
1469 initialSkip--; |
1468 } else { |
1470 } else { |
1469 locals = ivf->locals(); |
1471 locals = ivf->locals(); |
1470 HotSpotStackFrameReference::set_bci(result, ivf->bci()); |
1472 HotSpotStackFrameReference::set_bci(frame_reference, ivf->bci()); |
1471 oop method = CompilerToVM::get_jvmci_method(ivf->method(), CHECK_NULL); |
1473 oop method = CompilerToVM::get_jvmci_method(ivf->method(), CHECK_NULL); |
1472 HotSpotStackFrameReference::set_method(result, method); |
1474 HotSpotStackFrameReference::set_method(frame_reference, method); |
1473 HotSpotStackFrameReference::set_localIsVirtual(result, NULL); |
1475 HotSpotStackFrameReference::set_localIsVirtual(frame_reference, NULL); |
1474 } |
1476 } |
1475 } |
1477 } |
1476 } |
1478 } |
1477 |
1479 |
1478 // locals != NULL means that we found a matching frame and result is already partially initialized |
1480 // locals != NULL means that we found a matching frame and result is already partially initialized |
1479 if (locals != NULL) { |
1481 if (locals != NULL) { |
1480 HotSpotStackFrameReference::set_compilerToVM(result, JNIHandles::resolve(compilerToVM)); |
1482 methods = match_methods; |
1481 HotSpotStackFrameReference::set_stackPointer(result, (jlong) fst.current()->sp()); |
1483 HotSpotStackFrameReference::set_compilerToVM(frame_reference, JNIHandles::resolve(compilerToVM)); |
1482 HotSpotStackFrameReference::set_frameNumber(result, frame_number); |
1484 HotSpotStackFrameReference::set_stackPointer(frame_reference, (jlong) fst.current()->sp()); |
|
1485 HotSpotStackFrameReference::set_frameNumber(frame_reference, frame_number); |
1483 |
1486 |
1484 // initialize the locals array |
1487 // initialize the locals array |
1485 objArrayOop array_oop = oopFactory::new_objectArray(locals->size(), CHECK_NULL); |
1488 objArrayOop array_oop = oopFactory::new_objectArray(locals->size(), CHECK_NULL); |
1486 objArrayHandle array(THREAD, array_oop); |
1489 objArrayHandle array(THREAD, array_oop); |
1487 for (int i = 0; i < locals->size(); i++) { |
1490 for (int i = 0; i < locals->size(); i++) { |
1488 StackValue* var = locals->at(i); |
1491 StackValue* var = locals->at(i); |
1489 if (var->type() == T_OBJECT) { |
1492 if (var->type() == T_OBJECT) { |
1490 array->obj_at_put(i, locals->at(i)->get_obj()()); |
1493 array->obj_at_put(i, locals->at(i)->get_obj()()); |
1491 } |
1494 } |
1492 } |
1495 } |
1493 HotSpotStackFrameReference::set_locals(result, array()); |
1496 HotSpotStackFrameReference::set_locals(frame_reference, array()); |
1494 |
1497 HotSpotStackFrameReference::set_objectsMaterialized(frame_reference, JNI_FALSE); |
1495 return JNIHandles::make_local(thread, result()); |
1498 |
|
1499 JavaValue result(T_OBJECT); |
|
1500 JavaCallArguments args(visitor); |
|
1501 args.push_oop(frame_reference); |
|
1502 call_interface(&result, SystemDictionary::InspectedFrameVisitor_klass(), vmSymbols::visitFrame_name(), vmSymbols::visitFrame_signature(), &args, CHECK_NULL); |
|
1503 if (result.get_jobject() != NULL) { |
|
1504 return JNIHandles::make_local(thread, (oop) result.get_jobject()); |
|
1505 } |
|
1506 assert(initialSkip == 0, "There should be no match before initialSkip == 0"); |
|
1507 if (HotSpotStackFrameReference::objectsMaterialized(frame_reference) == JNI_TRUE) { |
|
1508 // the frame has been deoptimized, we need to re-synchronize the frame and vframe |
|
1509 intptr_t* stack_pointer = (intptr_t*) HotSpotStackFrameReference::stackPointer(frame_reference); |
|
1510 fst = StackFrameStream(thread); |
|
1511 while (fst.current()->sp() != stack_pointer && !fst.is_done()) { |
|
1512 fst.next(); |
|
1513 } |
|
1514 if (fst.current()->sp() != stack_pointer) { |
|
1515 THROW_MSG_NULL(vmSymbols::java_lang_IllegalStateException(), "stack frame not found after deopt") |
|
1516 } |
|
1517 vf = vframe::new_vframe(fst.current(), fst.register_map(), thread); |
|
1518 if (!vf->is_compiled_frame()) { |
|
1519 THROW_MSG_NULL(vmSymbols::java_lang_IllegalStateException(), "compiled stack frame expected") |
|
1520 } |
|
1521 for (int i = 0; i < frame_number; i++) { |
|
1522 if (vf->is_top()) { |
|
1523 THROW_MSG_NULL(vmSymbols::java_lang_IllegalStateException(), "vframe not found after deopt") |
|
1524 } |
|
1525 vf = vf->sender(); |
|
1526 assert(vf->is_compiled_frame(), "Wrong frame type"); |
|
1527 } |
|
1528 } |
|
1529 frame_reference = HotSpotStackFrameReference::klass()->allocate_instance_handle(CHECK_NULL); |
|
1530 HotSpotStackFrameReference::klass()->initialize(CHECK_NULL); |
1496 } |
1531 } |
1497 |
1532 |
1498 if (vf->is_top()) { |
1533 if (vf->is_top()) { |
1499 break; |
1534 break; |
1500 } |
1535 } |
1824 C2V_END |
1860 C2V_END |
1825 |
1861 |
1826 #define CC (char*) /*cast a literal from (const char*)*/ |
1862 #define CC (char*) /*cast a literal from (const char*)*/ |
1827 #define FN_PTR(f) CAST_FROM_FN_PTR(void*, &(c2v_ ## f)) |
1863 #define FN_PTR(f) CAST_FROM_FN_PTR(void*, &(c2v_ ## f)) |
1828 |
1864 |
1829 #define STRING "Ljava/lang/String;" |
1865 #define STRING "Ljava/lang/String;" |
1830 #define OBJECT "Ljava/lang/Object;" |
1866 #define OBJECT "Ljava/lang/Object;" |
1831 #define CLASS "Ljava/lang/Class;" |
1867 #define CLASS "Ljava/lang/Class;" |
1832 #define EXECUTABLE "Ljava/lang/reflect/Executable;" |
1868 #define EXECUTABLE "Ljava/lang/reflect/Executable;" |
1833 #define STACK_TRACE_ELEMENT "Ljava/lang/StackTraceElement;" |
1869 #define STACK_TRACE_ELEMENT "Ljava/lang/StackTraceElement;" |
1834 #define INSTALLED_CODE "Ljdk/vm/ci/code/InstalledCode;" |
1870 #define INSTALLED_CODE "Ljdk/vm/ci/code/InstalledCode;" |
1835 #define TARGET_DESCRIPTION "Ljdk/vm/ci/code/TargetDescription;" |
1871 #define TARGET_DESCRIPTION "Ljdk/vm/ci/code/TargetDescription;" |
1836 #define BYTECODE_FRAME "Ljdk/vm/ci/code/BytecodeFrame;" |
1872 #define BYTECODE_FRAME "Ljdk/vm/ci/code/BytecodeFrame;" |
1837 #define RESOLVED_METHOD "Ljdk/vm/ci/meta/ResolvedJavaMethod;" |
1873 #define INSPECTED_FRAME_VISITOR "Ljdk/vm/ci/code/stack/InspectedFrameVisitor;" |
1838 #define HS_RESOLVED_METHOD "Ljdk/vm/ci/hotspot/HotSpotResolvedJavaMethodImpl;" |
1874 #define RESOLVED_METHOD "Ljdk/vm/ci/meta/ResolvedJavaMethod;" |
1839 #define HS_RESOLVED_KLASS "Ljdk/vm/ci/hotspot/HotSpotResolvedObjectTypeImpl;" |
1875 #define HS_RESOLVED_METHOD "Ljdk/vm/ci/hotspot/HotSpotResolvedJavaMethodImpl;" |
1840 #define HS_CONSTANT_POOL "Ljdk/vm/ci/hotspot/HotSpotConstantPool;" |
1876 #define HS_RESOLVED_KLASS "Ljdk/vm/ci/hotspot/HotSpotResolvedObjectTypeImpl;" |
1841 #define HS_COMPILED_CODE "Ljdk/vm/ci/hotspot/HotSpotCompiledCode;" |
1877 #define HS_CONSTANT_POOL "Ljdk/vm/ci/hotspot/HotSpotConstantPool;" |
1842 #define HS_CONFIG "Ljdk/vm/ci/hotspot/HotSpotVMConfig;" |
1878 #define HS_COMPILED_CODE "Ljdk/vm/ci/hotspot/HotSpotCompiledCode;" |
1843 #define HS_METADATA "Ljdk/vm/ci/hotspot/HotSpotMetaData;" |
1879 #define HS_CONFIG "Ljdk/vm/ci/hotspot/HotSpotVMConfig;" |
1844 #define HS_STACK_FRAME_REF "Ljdk/vm/ci/hotspot/HotSpotStackFrameReference;" |
1880 #define HS_METADATA "Ljdk/vm/ci/hotspot/HotSpotMetaData;" |
1845 #define HS_SPECULATION_LOG "Ljdk/vm/ci/hotspot/HotSpotSpeculationLog;" |
1881 #define HS_STACK_FRAME_REF "Ljdk/vm/ci/hotspot/HotSpotStackFrameReference;" |
1846 #define METASPACE_METHOD_DATA "J" |
1882 #define HS_SPECULATION_LOG "Ljdk/vm/ci/hotspot/HotSpotSpeculationLog;" |
|
1883 #define METASPACE_METHOD_DATA "J" |
1847 |
1884 |
1848 JNINativeMethod CompilerToVM::methods[] = { |
1885 JNINativeMethod CompilerToVM::methods[] = { |
1849 {CC "getBytecode", CC "(" HS_RESOLVED_METHOD ")[B", FN_PTR(getBytecode)}, |
1886 {CC "getBytecode", CC "(" HS_RESOLVED_METHOD ")[B", FN_PTR(getBytecode)}, |
1850 {CC "getExceptionTableStart", CC "(" HS_RESOLVED_METHOD ")J", FN_PTR(getExceptionTableStart)}, |
1887 {CC "getExceptionTableStart", CC "(" HS_RESOLVED_METHOD ")J", FN_PTR(getExceptionTableStart)}, |
1851 {CC "getExceptionTableLength", CC "(" HS_RESOLVED_METHOD ")I", FN_PTR(getExceptionTableLength)}, |
1888 {CC "getExceptionTableLength", CC "(" HS_RESOLVED_METHOD ")I", FN_PTR(getExceptionTableLength)}, |
1897 {CC "collectCounters", CC "()[J", FN_PTR(collectCounters)}, |
1934 {CC "collectCounters", CC "()[J", FN_PTR(collectCounters)}, |
1898 {CC "allocateCompileId", CC "(" HS_RESOLVED_METHOD "I)I", FN_PTR(allocateCompileId)}, |
1935 {CC "allocateCompileId", CC "(" HS_RESOLVED_METHOD "I)I", FN_PTR(allocateCompileId)}, |
1899 {CC "isMature", CC "(" METASPACE_METHOD_DATA ")Z", FN_PTR(isMature)}, |
1936 {CC "isMature", CC "(" METASPACE_METHOD_DATA ")Z", FN_PTR(isMature)}, |
1900 {CC "hasCompiledCodeForOSR", CC "(" HS_RESOLVED_METHOD "II)Z", FN_PTR(hasCompiledCodeForOSR)}, |
1937 {CC "hasCompiledCodeForOSR", CC "(" HS_RESOLVED_METHOD "II)Z", FN_PTR(hasCompiledCodeForOSR)}, |
1901 {CC "getSymbol", CC "(J)" STRING, FN_PTR(getSymbol)}, |
1938 {CC "getSymbol", CC "(J)" STRING, FN_PTR(getSymbol)}, |
1902 {CC "getNextStackFrame", CC "(" HS_STACK_FRAME_REF "[" RESOLVED_METHOD "I)" HS_STACK_FRAME_REF, FN_PTR(getNextStackFrame)}, |
1939 {CC "iterateFrames", CC "([" RESOLVED_METHOD "[" RESOLVED_METHOD "I" INSPECTED_FRAME_VISITOR ")" OBJECT, FN_PTR(iterateFrames)}, |
1903 {CC "materializeVirtualObjects", CC "(" HS_STACK_FRAME_REF "Z)V", FN_PTR(materializeVirtualObjects)}, |
1940 {CC "materializeVirtualObjects", CC "(" HS_STACK_FRAME_REF "Z)V", FN_PTR(materializeVirtualObjects)}, |
1904 {CC "shouldDebugNonSafepoints", CC "()Z", FN_PTR(shouldDebugNonSafepoints)}, |
1941 {CC "shouldDebugNonSafepoints", CC "()Z", FN_PTR(shouldDebugNonSafepoints)}, |
1905 {CC "writeDebugOutput", CC "([BII)V", FN_PTR(writeDebugOutput)}, |
1942 {CC "writeDebugOutput", CC "([BII)V", FN_PTR(writeDebugOutput)}, |
1906 {CC "flushDebugOutput", CC "()V", FN_PTR(flushDebugOutput)}, |
1943 {CC "flushDebugOutput", CC "()V", FN_PTR(flushDebugOutput)}, |
1907 {CC "methodDataProfileDataSize", CC "(JI)I", FN_PTR(methodDataProfileDataSize)}, |
1944 {CC "methodDataProfileDataSize", CC "(JI)I", FN_PTR(methodDataProfileDataSize)}, |