1 /*
2  * Copyright (c) 2007, 2018, 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 #include <jni.h>
25 #include <stdio.h>
26 #include "jni_tools.h"
27 
28 extern "C" {
29 
30 #define FIND_CLASS(_class, _className)\
31     if (!NSK_JNI_VERIFY(env, (_class = \
32             env->FindClass(_className)) != NULL))\
33         return
34 
35 #define GET_OBJECT_CLASS(_class, _obj)\
36     if (!NSK_JNI_VERIFY(env, (_class = \
37             env->GetObjectClass(_obj)) != NULL))\
38         return
39 
40 #define GET_STATIC_FIELD_ID(_fieldID, _class, _fieldName, _fieldSig)\
41     if (!NSK_JNI_VERIFY(env, (_fieldID = \
42             env->GetStaticFieldID(_class, _fieldName, _fieldSig)) != NULL))\
43         return
44 
45 #define GET_STATIC_OBJ_FIELD(_value, _class, _fieldName, _fieldSig)\
46     GET_STATIC_FIELD_ID(field, _class, _fieldName, _fieldSig);\
47     _value = env->GetStaticObjectField(_class, field)
48 
49 #define GET_STATIC_BOOL_FIELD(_value, _class, _fieldName)\
50     GET_STATIC_FIELD_ID(field, _class, _fieldName, "Z");\
51     _value = env->GetStaticBooleanField(_class, field)
52 
53 #define GET_FIELD_ID(_fieldID, _class, _fieldName, _fieldSig)\
54     if (!NSK_JNI_VERIFY(env, (_fieldID = \
55             env->GetFieldID(_class, _fieldName, _fieldSig)) != NULL))\
56         return
57 
58 #define GET_INT_FIELD(_value, _obj, _class, _fieldName)\
59     GET_FIELD_ID(field, _class, _fieldName, "I");\
60     _value = env->GetIntField(_obj, field)
61 
62 #define GET_LONG_FIELD(_value, _obj, _class, _fieldName)\
63     GET_FIELD_ID(field, _class, _fieldName, "J");\
64     _value = env->GetLongField(_obj, field)
65 
66 #define GET_STATIC_INT_FIELD(_value, _class, _fieldName)\
67     GET_STATIC_FIELD_ID(field, _class, _fieldName, "I");\
68     _value = env->GetStaticIntField(_class, field)
69 
70 #define SET_INT_FIELD(_obj, _class, _fieldName, _newValue)\
71     GET_FIELD_ID(field, _class, _fieldName, "I");\
72     env->SetIntField(_obj, field, _newValue)
73 
74 #define GET_OBJ_FIELD(_value, _obj, _class, _fieldName, _fieldSig)\
75     GET_FIELD_ID(field, _class, _fieldName, _fieldSig);\
76     _value = env->GetObjectField(_obj, field)
77 
78 
79 #define GET_ARR_ELEMENT(_arr, _index)\
80     env->GetObjectArrayElement(_arr, _index)
81 
82 #define SET_ARR_ELEMENT(_arr, _index, _newValue)\
83     env->SetObjectArrayElement(_arr, _index, _newValue)
84 
85 #define GET_STATIC_METHOD_ID(_methodID, _class, _methodName, _sig)\
86     if (!NSK_JNI_VERIFY(env, (_methodID = \
87             env->GetStaticMethodID(_class, _methodName, _sig)) != NULL))\
88         return
89 
90 #define GET_METHOD_ID(_methodID, _class, _methodName, _sig)\
91     if (!NSK_JNI_VERIFY(env, (_methodID = \
92             env->GetMethodID(_class, _methodName, _sig)) != NULL))\
93         return
94 
95 #define CALL_STATIC_VOID_NOPARAM(_class, _methodName)\
96     GET_STATIC_METHOD_ID(method, _class, _methodName, "()V");\
97     if (!NSK_JNI_VERIFY_VOID(env, env->CallStaticVoidMethod(_class, method)))\
98         return
99 
100 #define CALL_STATIC_VOID(_class, _methodName, _sig, _param)\
101     GET_STATIC_METHOD_ID(method, _class, _methodName, _sig);\
102     if (!NSK_JNI_VERIFY_VOID(env, env->CallStaticVoidMethod(_class, method, _param)))\
103         return
104 
105 #define CALL_VOID_NOPARAM(_obj, _class, _methodName)\
106     GET_METHOD_ID(method, _class, _methodName, "()V");\
107     if (!NSK_JNI_VERIFY_VOID(env, env->CallVoidMethod(_obj, method)))\
108         return
109 
110 #define CALL_VOID(_obj, _class, _methodName, _sig, _param)\
111     GET_METHOD_ID(method, _class, _methodName, _sig);\
112     if (!NSK_JNI_VERIFY_VOID(env, env->CallVoidMethod(_obj, method, _param)))\
113         return
114 
115 #define CALL_VOID2(_obj, _class, _methodName, _sig, _param1, _param2)\
116     GET_METHOD_ID(method, _class, _methodName, _sig);\
117     if (!NSK_JNI_VERIFY_VOID(env, env->CallVoidMethod(_obj, method, _param1, _param2)))\
118         return
119 
120 #define CALL_INT_NOPARAM(_value, _obj, _class, _methodName)\
121     GET_METHOD_ID(method, _class, _methodName, "()I");\
122     _value = env->CallIntMethod(_obj, method)
123 
124 #define NEW_OBJ(_obj, _class, _constructorName, _sig, _params)\
125     GET_METHOD_ID(method, _class, _constructorName, _sig);\
126     if (!NSK_JNI_VERIFY(env, (_obj = \
127             env->NewObject(_class, method, _params)) != NULL))\
128         return
129 
130 #define MONITOR_ENTER(x) \
131     NSK_JNI_VERIFY(env, env->MonitorEnter(x) == 0)
132 
133 #define MONITOR_EXIT(x) \
134     NSK_JNI_VERIFY(env, env->MonitorExit(x) == 0)
135 
136 #define TRACE(msg)\
137    GET_OBJ_FIELD(logger, obj, threadClass, "logger", "Lnsk/share/Log$Logger;");\
138    jmsg = env->NewStringUTF(msg);\
139    CALL_VOID2(logger, loggerClass, "trace",\
140                            "(ILjava/lang/String;)V", 50, jmsg)
141 
142 
143 /*
144  * Class:     nsk_monitoring_share_thread_RecursiveMonitoringThread
145  * Method:    nativeRecursiveMethod
146  * Signature: (IZ)V
147  */
Java_nsk_monitoring_share_thread_RecursiveMonitoringThread_nativeRecursiveMethod(JNIEnv * env,jobject o,jint currentDepth,jboolean pureNative)148 JNIEXPORT void JNICALL Java_nsk_monitoring_share_thread_RecursiveMonitoringThread_nativeRecursiveMethod
149 (JNIEnv *env, jobject o, jint currentDepth, jboolean pureNative) {
150         jclass klass;
151         jmethodID method;
152 
153         GET_OBJECT_CLASS(klass, o);
154         if (currentDepth-- > 0) {
155 /*              printf("Current depth: %d\n", currentDepth); */
156                 CALL_STATIC_VOID_NOPARAM(klass, "yield");
157                 if (pureNative == JNI_TRUE) {
158                         CALL_VOID2(o, klass, "nativeRecursiveMethod", "(IZ)V", currentDepth, pureNative);
159                 } else {
160                         CALL_VOID(o, klass, "recursiveMethod", "(I)V", currentDepth);
161                 }
162         } else {
163                 CALL_VOID_NOPARAM(o, klass, "runInside");
164         }
165 }
166 
167 }
168 
169