1 /*
2 * Copyright (c) 1998, 2016, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 *
23 */
24
25 #include "precompiled.hpp"
26 #include "classfile/systemDictionary.hpp"
27 #include "logging/log.hpp"
28 #include "memory/iterator.hpp"
29 #include "oops/oop.inline.hpp"
30 #include "prims/jvmtiExport.hpp"
31 #include "runtime/jniHandles.hpp"
32 #include "runtime/mutexLocker.hpp"
33 #include "runtime/thread.inline.hpp"
34
35 JNIHandleBlock* JNIHandles::_global_handles = NULL;
36 JNIHandleBlock* JNIHandles::_weak_global_handles = NULL;
37 oop JNIHandles::_deleted_handle = NULL;
38
39
40 jobject JNIHandles::make_local(oop obj) {
41 if (obj == NULL) {
42 return NULL; // ignore null handles
43 } else {
44 Thread* thread = Thread::current();
45 assert(Universe::heap()->is_in_reserved(obj), "sanity check");
46 return thread->active_handles()->allocate_handle(obj);
47 }
48 }
49
50
51 // optimized versions
52
53 jobject JNIHandles::make_local(Thread* thread, oop obj) {
75 assert(!Universe::heap()->is_gc_active(), "can't extend the root set during GC");
76 jobject res = NULL;
77 if (!obj.is_null()) {
78 // ignore null handles
79 MutexLocker ml(JNIGlobalHandle_lock);
80 assert(Universe::heap()->is_in_reserved(obj()), "sanity check");
81 res = _global_handles->allocate_handle(obj());
82 } else {
83 CHECK_UNHANDLED_OOPS_ONLY(Thread::current()->clear_unhandled_oops());
84 }
85
86 return res;
87 }
88
89
90 jobject JNIHandles::make_weak_global(Handle obj) {
91 assert(!Universe::heap()->is_gc_active(), "can't extend the root set during GC");
92 jobject res = NULL;
93 if (!obj.is_null()) {
94 // ignore null handles
95 MutexLocker ml(JNIGlobalHandle_lock);
96 assert(Universe::heap()->is_in_reserved(obj()), "sanity check");
97 res = _weak_global_handles->allocate_handle(obj());
98 } else {
99 CHECK_UNHANDLED_OOPS_ONLY(Thread::current()->clear_unhandled_oops());
100 }
101 return res;
102 }
103
104
105 void JNIHandles::destroy_global(jobject handle) {
106 if (handle != NULL) {
107 assert(is_global_handle(handle), "Invalid delete of global JNI handle");
108 *((oop*)handle) = deleted_handle(); // Mark the handle as deleted, allocate will reuse it
109 }
110 }
111
112
113 void JNIHandles::destroy_weak_global(jobject handle) {
114 if (handle != NULL) {
115 assert(!CheckJNICalls || is_weak_global_handle(handle), "Invalid delete of weak global JNI handle");
116 *((oop*)handle) = deleted_handle(); // Mark the handle as deleted, allocate will reuse it
117 }
118 }
119
120
121 void JNIHandles::oops_do(OopClosure* f) {
122 f->do_oop(&_deleted_handle);
123 _global_handles->oops_do(f);
124 }
125
126
127 void JNIHandles::weak_oops_do(BoolObjectClosure* is_alive, OopClosure* f) {
128 _weak_global_handles->weak_oops_do(is_alive, f);
129 }
130
131
132 void JNIHandles::weak_oops_do(OopClosure* f) {
133 AlwaysTrueClosure always_true;
134 weak_oops_do(&always_true, f);
135 }
136
|
1 /*
2 * Copyright (c) 1998, 2017, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 *
23 */
24
25 #include "precompiled.hpp"
26 #include "classfile/systemDictionary.hpp"
27 #include "logging/log.hpp"
28 #include "memory/iterator.hpp"
29 #include "oops/oop.inline.hpp"
30 #include "prims/jvmtiExport.hpp"
31 #include "runtime/jniHandles.hpp"
32 #include "runtime/mutexLocker.hpp"
33 #include "runtime/thread.inline.hpp"
34 #if INCLUDE_ALL_GCS
35 #include "gc/g1/g1SATBCardTableModRefBS.hpp"
36 #endif
37
38 JNIHandleBlock* JNIHandles::_global_handles = NULL;
39 JNIHandleBlock* JNIHandles::_weak_global_handles = NULL;
40 oop JNIHandles::_deleted_handle = NULL;
41
42
43 jobject JNIHandles::make_local(oop obj) {
44 if (obj == NULL) {
45 return NULL; // ignore null handles
46 } else {
47 Thread* thread = Thread::current();
48 assert(Universe::heap()->is_in_reserved(obj), "sanity check");
49 return thread->active_handles()->allocate_handle(obj);
50 }
51 }
52
53
54 // optimized versions
55
56 jobject JNIHandles::make_local(Thread* thread, oop obj) {
78 assert(!Universe::heap()->is_gc_active(), "can't extend the root set during GC");
79 jobject res = NULL;
80 if (!obj.is_null()) {
81 // ignore null handles
82 MutexLocker ml(JNIGlobalHandle_lock);
83 assert(Universe::heap()->is_in_reserved(obj()), "sanity check");
84 res = _global_handles->allocate_handle(obj());
85 } else {
86 CHECK_UNHANDLED_OOPS_ONLY(Thread::current()->clear_unhandled_oops());
87 }
88
89 return res;
90 }
91
92
93 jobject JNIHandles::make_weak_global(Handle obj) {
94 assert(!Universe::heap()->is_gc_active(), "can't extend the root set during GC");
95 jobject res = NULL;
96 if (!obj.is_null()) {
97 // ignore null handles
98 {
99 MutexLocker ml(JNIGlobalHandle_lock);
100 assert(Universe::heap()->is_in_reserved(obj()), "sanity check");
101 res = _weak_global_handles->allocate_handle(obj());
102 }
103 // Add weak tag.
104 assert(is_ptr_aligned(res, weak_tag_alignment), "invariant");
105 char* tptr = reinterpret_cast<char*>(res) + weak_tag_value;
106 res = reinterpret_cast<jobject>(tptr);
107 } else {
108 CHECK_UNHANDLED_OOPS_ONLY(Thread::current()->clear_unhandled_oops());
109 }
110 return res;
111 }
112
113 template<bool external_guard>
114 oop JNIHandles::resolve_jweak(jweak handle) {
115 assert(is_jweak(handle), "precondition");
116 oop result = jweak_ref(handle);
117 result = guard_value<external_guard>(result);
118 #if INCLUDE_ALL_GCS
119 if (result != NULL && UseG1GC) {
120 G1SATBCardTableModRefBS::enqueue(result);
121 }
122 #endif // INCLUDE_ALL_GCS
123 return result;
124 }
125
126 template oop JNIHandles::resolve_jweak<true>(jweak);
127 template oop JNIHandles::resolve_jweak<false>(jweak);
128
129 void JNIHandles::destroy_global(jobject handle) {
130 if (handle != NULL) {
131 assert(is_global_handle(handle), "Invalid delete of global JNI handle");
132 jobject_ref(handle) = deleted_handle();
133 }
134 }
135
136
137 void JNIHandles::destroy_weak_global(jobject handle) {
138 if (handle != NULL) {
139 jweak_ref(handle) = deleted_handle();
140 }
141 }
142
143
144 void JNIHandles::oops_do(OopClosure* f) {
145 f->do_oop(&_deleted_handle);
146 _global_handles->oops_do(f);
147 }
148
149
150 void JNIHandles::weak_oops_do(BoolObjectClosure* is_alive, OopClosure* f) {
151 _weak_global_handles->weak_oops_do(is_alive, f);
152 }
153
154
155 void JNIHandles::weak_oops_do(OopClosure* f) {
156 AlwaysTrueClosure always_true;
157 weak_oops_do(&always_true, f);
158 }
159
|