98 import java.security.PrivilegedAction; |
98 import java.security.PrivilegedAction; |
99 import jdk.dynalink.CallSiteDescriptor; |
99 import jdk.dynalink.CallSiteDescriptor; |
100 import jdk.dynalink.SecureLookupSupplier; |
100 import jdk.dynalink.SecureLookupSupplier; |
101 import jdk.dynalink.internal.AccessControlContextFactory; |
101 import jdk.dynalink.internal.AccessControlContextFactory; |
102 import jdk.dynalink.linker.support.Lookup; |
102 import jdk.dynalink.linker.support.Lookup; |
103 import jdk.internal.module.Modules; |
|
104 import jdk.internal.reflect.CallerSensitive; |
103 import jdk.internal.reflect.CallerSensitive; |
105 |
104 |
106 |
105 |
107 /** |
106 /** |
108 * A dynamic method bound to exactly one Java method or constructor that is caller sensitive. Since the target method is |
107 * A dynamic method bound to exactly one Java method or constructor that is caller sensitive. Since the target method is |
178 boolean isConstructor() { |
177 boolean isConstructor() { |
179 return target instanceof Constructor; |
178 return target instanceof Constructor; |
180 } |
179 } |
181 |
180 |
182 private static MethodHandle unreflect(final MethodHandles.Lookup lookup, final Method m) { |
181 private static MethodHandle unreflect(final MethodHandles.Lookup lookup, final Method m) { |
183 try { |
182 return Lookup.unreflect(lookup, m); |
184 return Lookup.unreflect(lookup, m); |
|
185 } catch (final IllegalAccessError iae) { |
|
186 if (addModuleRead(lookup, m)) { |
|
187 try { |
|
188 return Lookup.unreflect(lookup, m); |
|
189 } catch (final IllegalAccessError e2) { |
|
190 // fall through and throw original error as cause |
|
191 } |
|
192 } |
|
193 throw iae; |
|
194 } |
|
195 } |
183 } |
196 |
184 |
197 private static MethodHandle unreflectConstructor(final MethodHandles.Lookup lookup, final Constructor<?> c) { |
185 private static MethodHandle unreflectConstructor(final MethodHandles.Lookup lookup, final Constructor<?> c) { |
198 try { |
186 return Lookup.unreflectConstructor(lookup, c); |
199 return Lookup.unreflectConstructor(lookup, c); |
|
200 } catch (final IllegalAccessError iae) { |
|
201 if (addModuleRead(lookup, c)) { |
|
202 try { |
|
203 return Lookup.unreflectConstructor(lookup, c); |
|
204 } catch (final IllegalAccessError e2) { |
|
205 // fall through and throw original error as cause |
|
206 } |
|
207 } |
|
208 throw iae; |
|
209 } |
|
210 } |
|
211 |
|
212 |
|
213 private static boolean addModuleRead(final MethodHandles.Lookup lookup, final Executable e) { |
|
214 // Don't add module read link if this is not a CallerSensitive member |
|
215 if (!e.isAnnotationPresent(CallerSensitive.class)) { |
|
216 return false; |
|
217 } |
|
218 |
|
219 // If the lookup is public lookup, don't bother adding module read link! |
|
220 // public lookup cannot unreflect caller sensitives anyway! |
|
221 if (lookup == MethodHandles.publicLookup()) { |
|
222 return false; |
|
223 } |
|
224 |
|
225 // try to add missing module read from using module to declararing module! |
|
226 final Class<?> declClass = e.getDeclaringClass(); |
|
227 final Module useModule = lookup.lookupClass().getModule(); |
|
228 final Module declModule = declClass.getModule(); |
|
229 if (useModule != null && declModule != null && declModule.isExported(declClass.getPackageName())) { |
|
230 Modules.addReads(useModule, declModule); |
|
231 return true; |
|
232 } |
|
233 |
|
234 return false; |
|
235 } |
187 } |
236 } |
188 } |