From d98409eadb7e27f5c7e9a9872d0d5506f9794e0a Mon Sep 17 00:00:00 2001 From: Coleen Phillimore Date: Wed, 3 Feb 2016 17:26:36 +0000 Subject: [PATCH] 8146984: SIGBUS: bool Method::has_method_vptr(const void*)+0xc Add address check and use SafeFetchN for Method* vptr access when Method* may be bad pointer. Reviewed-by: dcubed, mgronlun --- hotspot/src/share/vm/oops/method.cpp | 25 ++++++++++++++++--------- 1 file changed, 16 insertions(+), 9 deletions(-) diff --git a/hotspot/src/share/vm/oops/method.cpp b/hotspot/src/share/vm/oops/method.cpp index eebf233a555..2d06a42c10d 100644 --- a/hotspot/src/share/vm/oops/method.cpp +++ b/hotspot/src/share/vm/oops/method.cpp @@ -55,6 +55,7 @@ #include "runtime/relocator.hpp" #include "runtime/sharedRuntime.hpp" #include "runtime/signature.hpp" +#include "runtime/stubRoutines.hpp" #include "utilities/quickSort.hpp" #include "utilities/xmlstream.hpp" @@ -2098,23 +2099,29 @@ void Method::clear_jmethod_ids(ClassLoaderData* loader_data) { } bool Method::has_method_vptr(const void* ptr) { - Method m; + // Use SafeFetch to check if this is a valid pointer first // This assumes that the vtbl pointer is the first word of a C++ object. - // This assumption is also in universe.cpp patch_klass_vtble - void* vtbl2 = dereference_vptr((const void*)&m); - void* this_vtbl = dereference_vptr(ptr); - return vtbl2 == this_vtbl; + // This assumption is also in universe.cpp patch_klass_vtable + intptr_t this_vptr = SafeFetchN((intptr_t*)ptr, intptr_t(1)); + if (this_vptr == 1) { + return false; + } + Method m; + return (intptr_t)dereference_vptr(&m) == this_vptr; } // Check that this pointer is valid by checking that the vtbl pointer matches bool Method::is_valid_method() const { if (this == NULL) { return false; - } else if (!is_metaspace_object()) { - return false; - } else { - return has_method_vptr((const void*)this); } + + // Quick sanity check on pointer. + if ((intptr_t(this) & (wordSize-1)) != 0) { + return false; + } + + return has_method_vptr(this); } #ifndef PRODUCT