文章目录
-
- 前情提要
- loadLibrary
-
- loadLibrary0
- getCallerClass
- Java_sun_reflect_Reflection_getCallerClass__
- JVM_GetCallerClass
- security_get_caller_class
- security_get_caller_frame
- at_end
- security_next
- is_ignored_by_security_stack_walk
- init_intrinsic_id
- checkLink
- checkPermission
- checkPermission
- getStackAccessControlContext
- Java_java_security_AccessController_getStackAccessControlContext
- JVM_GetStackAccessControlContext
- doPrivileged
- isOn
- JVM_DoPrivileged
前情提要
在前面已经介绍过 System与initializeSystemClass 在此不做过多解释,没有看到的希望去查看!
System源码浅析- initializeSystemClass(initProperties)
System源码浅析- initializeSystemClass(saveAndRemoveProperties)
System源码浅析- initializeSystemClass(setXXX0)
System源码浅析- initializeSystemClass(loadLibrary)
System源码浅析- initializeSystemClass(setup)
System源码浅析- initializeSystemClass( initializeOSEnvironment )
System源码浅析- initializeSystemClass( setJavaLangAccess)
loadLibrary
/**
加载由 <code>libname<code> 参数指定的本机库。
<code>libname<code> 参数不得包含任何特定于平台的前缀、文件扩展名或路径。
如果名为 <code>libname<code> 的本机库与 VM 静态链接,
则调用该库导出的 JNI_OnLoad_<code>libname<code> 函数。有关更多详细信息,
请参阅 JNI 规范。
否则,libname 参数将从系统库位置加载并以与实现相关的方式映射到本机库映像。
*/
@CallerSensitive
public static void loadLibrary(String libname) {
Runtime.getRuntime().loadLibrary0(Reflection.getCallerClass(), libname);
}
loadLibrary0
// fromClass 调用者
synchronized void loadLibrary0(Class<?> fromClass, String libname) {
SecurityManager security = System.getSecurityManager();
if (security != null) {
security.checkLink(libname);
}
if (libname.indexOf((int)File.separatorChar) != -1) {
throw new UnsatisfiedLinkError(
"Directory separator should not appear in library name: " + libname);
}
ClassLoader.loadLibrary(fromClass, libname, false);
}
getCallerClass
@CallerSensitive
public static native Class<?> getCallerClass();
Java_sun_reflect_Reflection_getCallerClass__
JNIEXPORT jclass JNICALL Java_sun_reflect_Reflection_getCallerClass__
(JNIEnv *env, jclass unused)
{
/*
返回调用 JVM_GetCallerClass 的本机方法的直接调用者类。由于反射机制,Method.invoke 和其他帧被跳过。
深度参数必须为 -1 (JVM_DEPTH)。调用者应该被标记为 sun.reflect.CallerSensitive。如果没有正确标记,JVM 将抛出错误
JVM_GetCallerClass(JNIEnv *env, int depth);
/
return JVM_GetCallerClass(env, JVM_CALLER_DEPTH);
}
JVM_GetCallerClass
// 返回调用者
JVM_ENTRY(jclass, JVM_GetCallerClass(JNIEnv* env, int depth))
JVMWrapper("JVM_GetCallerClass");
//JDK 8 之前的版本和 JDK 8 的早期版本没有 CallerSensitive 注释;或带有深度参数的 sun.reflect.Reflection.getCallerClass 临时提供给现有代码使用,直到定义替换 API。
if (SystemDictionary::reflect_CallerSensitive_klass() == NULL || depth != JVM_CALLER_DEPTH) {
// 返回“深度”的方法 java 或栈中的原生帧 用于安全检查
Klass* k = thread->security_get_caller_class(depth);
return (k == NULL) ? NULL : (jclass) JNIHandles::make_local(env, k->java_mirror());
}
// 获取调用者框架的类
//
// 此时的调用堆栈如下所示:
//
// [0] [ @CallerSensitive public sun.reflect.Reflection.getCallerClass ]
// [1] [ @CallerSensitive API.method ]
// [.] [ (skipped intermediate frames) ]
// [n] [ caller ]
vframeStream vfst(thread);
// Cf. LibraryCallKit::inline_native_Reflection_getCallerClass
for (int n = 0; !vfst.at_end(); vfst.security_next(), n++) {
Method* m = vfst.method();
assert(m != NULL, "sanity");
switch (n) {
case 0:
// 这只能从 Reflection.getCallerClass 调用
if (m->intrinsic_id() != vmIntrinsics::_getCallerClass) {
THROW_MSG_NULL(vmSymbols::java_lang_InternalError(), "JVM_GetCallerClass must only be called from Reflection.getCallerClass");
}
// fall-through
case 1:
// Frame 0 和 1 必须是调用者sensitive.
if (!m->caller_sensitive()) {
THROW_MSG_NULL(vmSymbols::java_lang_InternalError(), err_msg("CallerSensitive annotation expected at frame %d", n));
}
break;
default:
if (!m->is_ignored_by_security_stack_walk()) {
// 我们已经达到了预期的框架;返回持有者类。
return (jclass) JNIHandles::make_local(env, m->method_holder()->java_mirror());
}
break;
}
}
return NULL;
JVM_END
security_get_caller_class
Klass* JavaThread::security_get_caller_class(int depth) {
vframeStream vfst(this);
// 后退 n 帧,跳过其间的任何伪帧。该函数用于Class.forName、Class.newInstance、Method.Invoke、AccessController.doPrivileged。
vfst.security_get_caller_frame(depth);
if (!vfst.at_end()) {
return vfst.method()-><