# HG changeset patch # User sspitsyn # Date 1574417241 0 # Node ID f16e4154dd7b8d9e3c18d002c2b9908b32223f00 # Parent f4f60bb75ee4caf7bc9d7635d2f49af2f70958fc 8169467: GetLocalInstance returns JVMTI_ERROR_TYPE_MISMATCH (rather than JVMTI_ERROR_INVALID_SLOT) on static method Summary: Add necessary check to GetLocalInstance implementation Reviewed-by: amenkov, cjplummer diff -r f4f60bb75ee4 -r f16e4154dd7b src/hotspot/share/prims/jvmtiImpl.cpp --- a/src/hotspot/share/prims/jvmtiImpl.cpp Fri Nov 22 10:03:38 2019 +0100 +++ b/src/hotspot/share/prims/jvmtiImpl.cpp Fri Nov 22 10:07:21 2019 +0000 @@ -724,13 +724,17 @@ NULL_CHECK(_jvf, false); Method* method_oop = _jvf->method(); - if (method_oop->is_native()) { - if (getting_receiver() && !method_oop->is_static()) { - return true; - } else { - _result = JVMTI_ERROR_OPAQUE_FRAME; + if (getting_receiver()) { + if (method_oop->is_static()) { + _result = JVMTI_ERROR_INVALID_SLOT; return false; } + return true; + } + + if (method_oop->is_native()) { + _result = JVMTI_ERROR_OPAQUE_FRAME; + return false; } if (!check_slot_type_no_lvt(_jvf)) { diff -r f4f60bb75ee4 -r f16e4154dd7b test/hotspot/jtreg/vmTestbase/nsk/jvmti/unit/GetLocalVariable/getlocal003.java --- a/test/hotspot/jtreg/vmTestbase/nsk/jvmti/unit/GetLocalVariable/getlocal003.java Fri Nov 22 10:03:38 2019 +0100 +++ b/test/hotspot/jtreg/vmTestbase/nsk/jvmti/unit/GetLocalVariable/getlocal003.java Fri Nov 22 10:07:21 2019 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2003, 2018, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2003, 2019, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -203,9 +203,11 @@ public double meth01() { float f = 6.0f; double d = 7.0; + instMeth(); return d + f; } + native void instMeth(); native static void getMeth(); native static void checkLoc(Thread thr); native static int getRes(); diff -r f4f60bb75ee4 -r f16e4154dd7b test/hotspot/jtreg/vmTestbase/nsk/jvmti/unit/GetLocalVariable/getlocal003/getlocal003.cpp --- a/test/hotspot/jtreg/vmTestbase/nsk/jvmti/unit/GetLocalVariable/getlocal003/getlocal003.cpp Fri Nov 22 10:03:38 2019 +0100 +++ b/test/hotspot/jtreg/vmTestbase/nsk/jvmti/unit/GetLocalVariable/getlocal003/getlocal003.cpp Fri Nov 22 10:07:21 2019 +0000 @@ -231,8 +231,44 @@ } JNIEXPORT void JNICALL +Java_nsk_jvmti_unit_GetLocalVariable_getlocal003_instMeth(JNIEnv *env, jobject inst) { + jvmtiError err; + jobject obj = NULL; + + printf("\n Native instMeth: started\n"); + + // Test GetLocalInstance with native instance method instMeth() frame + err = jvmti->GetLocalInstance(NULL, 0, &obj); + printf(" Native instMeth: GetLocalInstance: %s (%d)\n", TranslateError(err), err); + if (err != JVMTI_ERROR_NONE) { + printf("FAIL: GetLocalInstance failed to get instance for native instance method frame\n"); + result = STATUS_FAILED; + } + if (env->IsSameObject(inst, obj) == JNI_FALSE) { + printf("FAIL: GetLocalInstance returned unexpected instance for native instance method frame\n"); + result = STATUS_FAILED; + } + + // Test GetLocalInstance with java instance method meth01() frame + err = jvmti->GetLocalInstance(NULL, 1, &obj); + printf(" Native instMeth: GetLocalInstance: %s (%d)\n", TranslateError(err), err); + if (err != JVMTI_ERROR_NONE) { + printf("FAIL: GetLocalInstance failed to get instance for java instance method frame\n"); + result = STATUS_FAILED; + } + if (env->IsSameObject(inst, obj) == JNI_FALSE) { + printf("FAIL: GetLocalInstance returned unexpected instance for java instance method frame\n"); + result = STATUS_FAILED; + } + printf(" Native instMeth: finished\n\n"); +} + +JNIEXPORT void JNICALL Java_nsk_jvmti_unit_GetLocalVariable_getlocal003_getMeth(JNIEnv *env, jclass cls) { jvmtiError err; + jobject obj = NULL; + + printf("\n Native getMeth: started\n"); if (jvmti == NULL) { printf("JVMTI client was not properly loaded!\n"); @@ -261,6 +297,24 @@ TranslateError(err), err); result = STATUS_FAILED; } + + // Test GetLocalInstance with native static method getMeth() frame + err = jvmti->GetLocalInstance(NULL, 0, &obj); + printf(" Native getMeth: GetLocalInstance: %s (%d)\n", TranslateError(err), err); + if (err != JVMTI_ERROR_INVALID_SLOT) { + printf("FAIL: GetLocalInstance failed to return JVMTI_ERROR_INVALID_SLOT for native static method frame\n"); + result = STATUS_FAILED; + } + + // Test GetLocalInstance with java static method run() frame + err = jvmti->GetLocalInstance(NULL, 1, &obj); + printf(" Native getMeth: GetLocalInstance: %s (%d)\n", TranslateError(err), err); + if (err != JVMTI_ERROR_INVALID_SLOT) { + printf("FAIL: GetLocalInstance failed to return JVMTI_ERROR_INVALID_SLOT for java static method frame\n"); + result = STATUS_FAILED; + } + + printf(" Native getMeth: finished\n\n"); fflush(stdout); }