Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/mobile
Path: blob/master/src/java.instrument/share/classes/java/lang/instrument/Instrumentation.java
41159 views
1
/*
2
* Copyright (c) 2003, 2019, 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. Oracle designates this
8
* particular file as subject to the "Classpath" exception as provided
9
* by Oracle in the LICENSE file that accompanied this code.
10
*
11
* This code is distributed in the hope that it will be useful, but WITHOUT
12
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14
* version 2 for more details (a copy is included in the LICENSE file that
15
* accompanied this code).
16
*
17
* You should have received a copy of the GNU General Public License version
18
* 2 along with this work; if not, write to the Free Software Foundation,
19
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20
*
21
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22
* or visit www.oracle.com if you need additional information or have any
23
* questions.
24
*/
25
26
package java.lang.instrument;
27
28
import java.security.ProtectionDomain;
29
import java.util.List;
30
import java.util.Map;
31
import java.util.Set;
32
import java.util.jar.JarFile;
33
34
/*
35
* Copyright 2003 Wily Technology, Inc.
36
*/
37
38
/**
39
* This class provides services needed to instrument Java
40
* programming language code.
41
* Instrumentation is the addition of byte-codes to methods for the
42
* purpose of gathering data to be utilized by tools.
43
* Since the changes are purely additive, these tools do not modify
44
* application state or behavior.
45
* Examples of such benign tools include monitoring agents, profilers,
46
* coverage analyzers, and event loggers.
47
*
48
* <P>
49
* There are two ways to obtain an instance of the
50
* <code>Instrumentation</code> interface:
51
*
52
* <ol>
53
* <li><p> When a JVM is launched in a way that indicates an agent
54
* class. In that case an <code>Instrumentation</code> instance
55
* is passed to the <code>premain</code> method of the agent class.
56
* </p></li>
57
* <li><p> When a JVM provides a mechanism to start agents sometime
58
* after the JVM is launched. In that case an <code>Instrumentation</code>
59
* instance is passed to the <code>agentmain</code> method of the
60
* agent code. </p> </li>
61
* </ol>
62
* <p>
63
* These mechanisms are described in the
64
* {@linkplain java.lang.instrument package specification}.
65
* <p>
66
* Once an agent acquires an <code>Instrumentation</code> instance,
67
* the agent may call methods on the instance at any time.
68
*
69
* @apiNote This interface is not intended to be implemented outside of
70
* the java.instrument module.
71
*
72
* @since 1.5
73
*/
74
public interface Instrumentation {
75
/**
76
* Registers the supplied transformer. All future class definitions
77
* will be seen by the transformer, except definitions of classes upon which any
78
* registered transformer is dependent.
79
* The transformer is called when classes are loaded, when they are
80
* {@linkplain #redefineClasses redefined}. and if <code>canRetransform</code> is true,
81
* when they are {@linkplain #retransformClasses retransformed}.
82
* {@link ClassFileTransformer} defines the order of transform calls.
83
*
84
* If a transformer throws
85
* an exception during execution, the JVM will still call the other registered
86
* transformers in order. The same transformer may be added more than once,
87
* but it is strongly discouraged -- avoid this by creating a new instance of
88
* transformer class.
89
* <P>
90
* This method is intended for use in instrumentation, as described in the
91
* {@linkplain Instrumentation class specification}.
92
*
93
* @param transformer the transformer to register
94
* @param canRetransform can this transformer's transformations be retransformed
95
* @throws java.lang.NullPointerException if passed a <code>null</code> transformer
96
* @throws java.lang.UnsupportedOperationException if <code>canRetransform</code>
97
* is true and the current configuration of the JVM does not allow
98
* retransformation ({@link #isRetransformClassesSupported} is false)
99
* @since 1.6
100
*/
101
void
102
addTransformer(ClassFileTransformer transformer, boolean canRetransform);
103
104
/**
105
* Registers the supplied transformer.
106
* <P>
107
* Same as <code>addTransformer(transformer, false)</code>.
108
*
109
* @param transformer the transformer to register
110
* @throws java.lang.NullPointerException if passed a <code>null</code> transformer
111
* @see #addTransformer(ClassFileTransformer,boolean)
112
*/
113
void
114
addTransformer(ClassFileTransformer transformer);
115
116
/**
117
* Unregisters the supplied transformer. Future class definitions will
118
* not be shown to the transformer. Removes the most-recently-added matching
119
* instance of the transformer. Due to the multi-threaded nature of
120
* class loading, it is possible for a transformer to receive calls
121
* after it has been removed. Transformers should be written defensively
122
* to expect this situation.
123
*
124
* @param transformer the transformer to unregister
125
* @return true if the transformer was found and removed, false if the
126
* transformer was not found
127
* @throws java.lang.NullPointerException if passed a <code>null</code> transformer
128
*/
129
boolean
130
removeTransformer(ClassFileTransformer transformer);
131
132
/**
133
* Returns whether or not the current JVM configuration supports retransformation
134
* of classes.
135
* The ability to retransform an already loaded class is an optional capability
136
* of a JVM.
137
* Retransformation will only be supported if the
138
* <code>Can-Retransform-Classes</code> manifest attribute is set to
139
* <code>true</code> in the agent JAR file (as described in the
140
* {@linkplain java.lang.instrument package specification}) and the JVM supports
141
* this capability.
142
* During a single instantiation of a single JVM, multiple calls to this
143
* method will always return the same answer.
144
* @return true if the current JVM configuration supports retransformation of
145
* classes, false if not.
146
* @see #retransformClasses
147
* @since 1.6
148
*/
149
boolean
150
isRetransformClassesSupported();
151
152
/**
153
* Retransform the supplied set of classes.
154
*
155
* <P>
156
* This function facilitates the instrumentation
157
* of already loaded classes.
158
* When classes are initially loaded or when they are
159
* {@linkplain #redefineClasses redefined},
160
* the initial class file bytes can be transformed with the
161
* {@link java.lang.instrument.ClassFileTransformer ClassFileTransformer}.
162
* This function reruns the transformation process
163
* (whether or not a transformation has previously occurred).
164
* This retransformation follows these steps:
165
* <ul>
166
* <li>starting from the initial class file bytes
167
* </li>
168
* <li>for each transformer that was added with <code>canRetransform</code>
169
* false, the bytes returned by
170
* {@link ClassFileTransformer#transform(Module,ClassLoader,String,Class,ProtectionDomain,byte[])
171
* transform} during the last class load or redefine are
172
* reused as the output of the transformation; note that this is
173
* equivalent to reapplying the previous transformation, unaltered;
174
* except that {@code transform} method is not called.
175
* </li>
176
* <li>for each transformer that was added with <code>canRetransform</code>
177
* true, the
178
* {@link ClassFileTransformer#transform(Module,ClassLoader,String,Class,ProtectionDomain,byte[])
179
* transform} method is called in these transformers
180
* </li>
181
* <li>the transformed class file bytes are installed as the new
182
* definition of the class
183
* </li>
184
* </ul>
185
* <P>
186
*
187
* The order of transformation is described in {@link ClassFileTransformer}.
188
* This same order is used in the automatic reapplication of
189
* retransformation incapable transforms.
190
* <P>
191
*
192
* The initial class file bytes represent the bytes passed to
193
* {@link java.lang.ClassLoader#defineClass ClassLoader.defineClass} or
194
* {@link #redefineClasses redefineClasses}
195
* (before any transformations
196
* were applied), however they might not exactly match them.
197
* The constant pool might not have the same layout or contents.
198
* The constant pool may have more or fewer entries.
199
* Constant pool entries may be in a different order; however,
200
* constant pool indices in the bytecodes of methods will correspond.
201
* Some attributes may not be present.
202
* Where order is not meaningful, for example the order of methods,
203
* order might not be preserved.
204
*
205
* <P>
206
* This method operates on
207
* a set in order to allow interdependent changes to more than one class at the same time
208
* (a retransformation of class A can require a retransformation of class B).
209
*
210
* <P>
211
* If a retransformed method has active stack frames, those active frames continue to
212
* run the bytecodes of the original method.
213
* The retransformed method will be used on new invokes.
214
*
215
* <P>
216
* This method does not cause any initialization except that which would occur
217
* under the customary JVM semantics. In other words, redefining a class
218
* does not cause its initializers to be run. The values of static variables
219
* will remain as they were prior to the call.
220
*
221
* <P>
222
* Instances of the retransformed class are not affected.
223
*
224
* <P>
225
* The supported class file changes are described in
226
* <a href="{@docRoot}/../specs/jvmti.html#RetransformClasses">JVM TI RetransformClasses</a>.
227
* The class file bytes are not checked, verified and installed
228
* until after the transformations have been applied, if the resultant bytes are in
229
* error this method will throw an exception.
230
*
231
* <P>
232
* If this method throws an exception, no classes have been retransformed.
233
* <P>
234
* This method is intended for use in instrumentation, as described in the
235
* {@linkplain Instrumentation class specification}.
236
*
237
* @param classes array of classes to retransform;
238
* a zero-length array is allowed, in this case, this method does nothing
239
* @throws java.lang.instrument.UnmodifiableClassException if a specified class cannot be modified
240
* ({@link #isModifiableClass} would return <code>false</code>)
241
* @throws java.lang.UnsupportedOperationException if the current configuration of the JVM does not allow
242
* retransformation ({@link #isRetransformClassesSupported} is false) or the retransformation attempted
243
* to make unsupported changes
244
* @throws java.lang.ClassFormatError if the data did not contain a valid class
245
* @throws java.lang.NoClassDefFoundError if the name in the class file is not equal to the name of the class
246
* @throws java.lang.UnsupportedClassVersionError if the class file version numbers are not supported
247
* @throws java.lang.ClassCircularityError if the new classes contain a circularity
248
* @throws java.lang.LinkageError if a linkage error occurs
249
* @throws java.lang.NullPointerException if the supplied classes array or any of its components
250
* is <code>null</code>.
251
*
252
* @see #isRetransformClassesSupported
253
* @see #addTransformer
254
* @see java.lang.instrument.ClassFileTransformer
255
* @since 1.6
256
*/
257
void
258
retransformClasses(Class<?>... classes) throws UnmodifiableClassException;
259
260
/**
261
* Returns whether or not the current JVM configuration supports redefinition
262
* of classes.
263
* The ability to redefine an already loaded class is an optional capability
264
* of a JVM.
265
* Redefinition will only be supported if the
266
* <code>Can-Redefine-Classes</code> manifest attribute is set to
267
* <code>true</code> in the agent JAR file (as described in the
268
* {@linkplain java.lang.instrument package specification}) and the JVM supports
269
* this capability.
270
* During a single instantiation of a single JVM, multiple calls to this
271
* method will always return the same answer.
272
* @return true if the current JVM configuration supports redefinition of classes,
273
* false if not.
274
* @see #redefineClasses
275
*/
276
boolean
277
isRedefineClassesSupported();
278
279
/**
280
* Redefine the supplied set of classes using the supplied class files.
281
*
282
* <P>
283
* This method is used to replace the definition of a class without reference
284
* to the existing class file bytes, as one might do when recompiling from source
285
* for fix-and-continue debugging.
286
* Where the existing class file bytes are to be transformed (for
287
* example in bytecode instrumentation)
288
* {@link #retransformClasses retransformClasses}
289
* should be used.
290
*
291
* <P>
292
* This method operates on
293
* a set in order to allow interdependent changes to more than one class at the same time
294
* (a redefinition of class A can require a redefinition of class B).
295
*
296
* <P>
297
* If a redefined method has active stack frames, those active frames continue to
298
* run the bytecodes of the original method.
299
* The redefined method will be used on new invokes.
300
*
301
* <P>
302
* This method does not cause any initialization except that which would occur
303
* under the customary JVM semantics. In other words, redefining a class
304
* does not cause its initializers to be run. The values of static variables
305
* will remain as they were prior to the call.
306
*
307
* <P>
308
* Instances of the redefined class are not affected.
309
*
310
* <P>
311
* The supported class file changes are described in
312
* <a href="{@docRoot}/../specs/jvmti.html#RedefineClasses">JVM TI RedefineClasses</a>.
313
* The class file bytes are not checked, verified and installed
314
* until after the transformations have been applied, if the resultant bytes are in
315
* error this method will throw an exception.
316
*
317
* <P>
318
* If this method throws an exception, no classes have been redefined.
319
* <P>
320
* This method is intended for use in instrumentation, as described in the
321
* {@linkplain Instrumentation class specification}.
322
*
323
* @param definitions array of classes to redefine with corresponding definitions;
324
* a zero-length array is allowed, in this case, this method does nothing
325
* @throws java.lang.instrument.UnmodifiableClassException if a specified class cannot be modified
326
* ({@link #isModifiableClass} would return <code>false</code>)
327
* @throws java.lang.UnsupportedOperationException if the current configuration of the JVM does not allow
328
* redefinition ({@link #isRedefineClassesSupported} is false) or the redefinition attempted
329
* to make unsupported changes
330
* @throws java.lang.ClassFormatError if the data did not contain a valid class
331
* @throws java.lang.NoClassDefFoundError if the name in the class file is not equal to the name of the class
332
* @throws java.lang.UnsupportedClassVersionError if the class file version numbers are not supported
333
* @throws java.lang.ClassCircularityError if the new classes contain a circularity
334
* @throws java.lang.LinkageError if a linkage error occurs
335
* @throws java.lang.NullPointerException if the supplied definitions array or any of its components
336
* is <code>null</code>
337
* @throws java.lang.ClassNotFoundException Can never be thrown (present for compatibility reasons only)
338
*
339
* @see #isRedefineClassesSupported
340
* @see #addTransformer
341
* @see java.lang.instrument.ClassFileTransformer
342
*/
343
void
344
redefineClasses(ClassDefinition... definitions)
345
throws ClassNotFoundException, UnmodifiableClassException;
346
347
348
/**
349
* Tests whether a class is modifiable by
350
* {@linkplain #retransformClasses retransformation}
351
* or {@linkplain #redefineClasses redefinition}.
352
* If a class is modifiable then this method returns <code>true</code>.
353
* If a class is not modifiable then this method returns <code>false</code>.
354
* <P>
355
* For a class to be retransformed, {@link #isRetransformClassesSupported} must also be true.
356
* But the value of <code>isRetransformClassesSupported()</code> does not influence the value
357
* returned by this function.
358
* For a class to be redefined, {@link #isRedefineClassesSupported} must also be true.
359
* But the value of <code>isRedefineClassesSupported()</code> does not influence the value
360
* returned by this function.
361
* <P>
362
* Primitive classes (for example, <code>java.lang.Integer.TYPE</code>)
363
* and array classes are never modifiable.
364
*
365
* @param theClass the class to check for being modifiable
366
* @return whether or not the argument class is modifiable
367
* @throws java.lang.NullPointerException if the specified class is <code>null</code>.
368
*
369
* @see #retransformClasses
370
* @see #isRetransformClassesSupported
371
* @see #redefineClasses
372
* @see #isRedefineClassesSupported
373
* @since 1.6
374
*/
375
boolean
376
isModifiableClass(Class<?> theClass);
377
378
/**
379
* Returns an array of all classes currently loaded by the JVM.
380
* The returned array includes all classes and interfaces, including
381
* {@linkplain Class#isHidden hidden classes or interfaces}, and array classes
382
* of all types.
383
*
384
* @return an array containing all the classes loaded by the JVM, zero-length if there are none
385
*/
386
@SuppressWarnings("rawtypes")
387
Class[]
388
getAllLoadedClasses();
389
390
/**
391
* Returns an array of all classes which {@code loader} can find by name
392
* via {@link ClassLoader#loadClass(String, boolean) ClassLoader::loadClass},
393
* {@link Class#forName(String) Class::forName} and bytecode linkage.
394
* That is, all classes for which {@code loader} has been recorded as
395
* an initiating loader. If the supplied {@code loader} is {@code null},
396
* classes that the bootstrap class loader can find by name are returned.
397
* <p>
398
* The returned array does not include {@linkplain Class#isHidden()
399
* hidden classes or interfaces} or array classes whose
400
* {@linkplain Class#componentType() element type} is a
401
* {@linkplain Class#isHidden() hidden class or interface}.
402
* as they cannot be discovered by any class loader.
403
*
404
* @param loader the loader whose initiated class list will be returned
405
* @return an array containing all classes which {@code loader} can find by name;
406
* zero-length if there are none
407
*/
408
@SuppressWarnings("rawtypes")
409
Class[]
410
getInitiatedClasses(ClassLoader loader);
411
412
/**
413
* Returns an implementation-specific approximation of the amount of storage consumed by
414
* the specified object. The result may include some or all of the object's overhead,
415
* and thus is useful for comparison within an implementation but not between implementations.
416
*
417
* The estimate may change during a single invocation of the JVM.
418
*
419
* @param objectToSize the object to size
420
* @return an implementation-specific approximation of the amount of storage consumed by the specified object
421
* @throws java.lang.NullPointerException if the supplied Object is <code>null</code>.
422
*/
423
long
424
getObjectSize(Object objectToSize);
425
426
427
/**
428
* Specifies a JAR file with instrumentation classes to be defined by the
429
* bootstrap class loader.
430
*
431
* <p> When the virtual machine's built-in class loader, known as the "bootstrap
432
* class loader", unsuccessfully searches for a class, the entries in the {@link
433
* java.util.jar.JarFile JAR file} will be searched as well.
434
*
435
* <p> This method may be used multiple times to add multiple JAR files to be
436
* searched in the order that this method was invoked.
437
*
438
* <p> The agent should take care to ensure that the JAR does not contain any
439
* classes or resources other than those to be defined by the bootstrap
440
* class loader for the purpose of instrumentation.
441
* Failure to observe this warning could result in unexpected
442
* behavior that is difficult to diagnose. For example, suppose there is a
443
* loader L, and L's parent for delegation is the bootstrap class loader.
444
* Furthermore, a method in class C, a class defined by L, makes reference to
445
* a non-public accessor class C$1. If the JAR file contains a class C$1 then
446
* the delegation to the bootstrap class loader will cause C$1 to be defined
447
* by the bootstrap class loader. In this example an <code>IllegalAccessError</code>
448
* will be thrown that may cause the application to fail. One approach to
449
* avoiding these types of issues, is to use a unique package name for the
450
* instrumentation classes.
451
*
452
* <p>
453
* <cite>The Java Virtual Machine Specification</cite>
454
* specifies that a subsequent attempt to resolve a symbolic
455
* reference that the Java virtual machine has previously unsuccessfully attempted
456
* to resolve always fails with the same error that was thrown as a result of the
457
* initial resolution attempt. Consequently, if the JAR file contains an entry
458
* that corresponds to a class for which the Java virtual machine has
459
* unsuccessfully attempted to resolve a reference, then subsequent attempts to
460
* resolve that reference will fail with the same error as the initial attempt.
461
*
462
* @param jarfile
463
* The JAR file to be searched when the bootstrap class loader
464
* unsuccessfully searches for a class.
465
*
466
* @throws NullPointerException
467
* If <code>jarfile</code> is <code>null</code>.
468
*
469
* @see #appendToSystemClassLoaderSearch
470
* @see java.lang.ClassLoader
471
* @see java.util.jar.JarFile
472
*
473
* @since 1.6
474
*/
475
void
476
appendToBootstrapClassLoaderSearch(JarFile jarfile);
477
478
/**
479
* Specifies a JAR file with instrumentation classes to be defined by the
480
* system class loader.
481
*
482
* When the system class loader for delegation (see
483
* {@link java.lang.ClassLoader#getSystemClassLoader getSystemClassLoader()})
484
* unsuccessfully searches for a class, the entries in the {@link
485
* java.util.jar.JarFile JarFile} will be searched as well.
486
*
487
* <p> This method may be used multiple times to add multiple JAR files to be
488
* searched in the order that this method was invoked.
489
*
490
* <p> The agent should take care to ensure that the JAR does not contain any
491
* classes or resources other than those to be defined by the system class
492
* loader for the purpose of instrumentation.
493
* Failure to observe this warning could result in unexpected
494
* behavior that is difficult to diagnose (see
495
* {@link #appendToBootstrapClassLoaderSearch
496
* appendToBootstrapClassLoaderSearch}).
497
*
498
* <p> The system class loader supports adding a JAR file to be searched if
499
* it implements a method named <code>appendToClassPathForInstrumentation</code>
500
* which takes a single parameter of type <code>java.lang.String</code>. The
501
* method is not required to have <code>public</code> access. The name of
502
* the JAR file is obtained by invoking the {@link java.util.zip.ZipFile#getName
503
* getName()} method on the <code>jarfile</code> and this is provided as the
504
* parameter to the <code>appendToClassPathForInstrumentation</code> method.
505
*
506
* <p>
507
* <cite>The Java Virtual Machine Specification</cite>
508
* specifies that a subsequent attempt to resolve a symbolic
509
* reference that the Java virtual machine has previously unsuccessfully attempted
510
* to resolve always fails with the same error that was thrown as a result of the
511
* initial resolution attempt. Consequently, if the JAR file contains an entry
512
* that corresponds to a class for which the Java virtual machine has
513
* unsuccessfully attempted to resolve a reference, then subsequent attempts to
514
* resolve that reference will fail with the same error as the initial attempt.
515
*
516
* <p> This method does not change the value of <code>java.class.path</code>
517
* {@link java.lang.System#getProperties system property}.
518
*
519
* @param jarfile
520
* The JAR file to be searched when the system class loader
521
* unsuccessfully searches for a class.
522
*
523
* @throws UnsupportedOperationException
524
* If the system class loader does not support appending a
525
* a JAR file to be searched.
526
*
527
* @throws NullPointerException
528
* If <code>jarfile</code> is <code>null</code>.
529
*
530
* @see #appendToBootstrapClassLoaderSearch
531
* @see java.lang.ClassLoader#getSystemClassLoader
532
* @see java.util.jar.JarFile
533
* @since 1.6
534
*/
535
void
536
appendToSystemClassLoaderSearch(JarFile jarfile);
537
538
/**
539
* Returns whether the current JVM configuration supports
540
* {@linkplain #setNativeMethodPrefix(ClassFileTransformer,String)
541
* setting a native method prefix}.
542
* The ability to set a native method prefix is an optional
543
* capability of a JVM.
544
* Setting a native method prefix will only be supported if the
545
* <code>Can-Set-Native-Method-Prefix</code> manifest attribute is set to
546
* <code>true</code> in the agent JAR file (as described in the
547
* {@linkplain java.lang.instrument package specification}) and the JVM supports
548
* this capability.
549
* During a single instantiation of a single JVM, multiple
550
* calls to this method will always return the same answer.
551
* @return true if the current JVM configuration supports
552
* setting a native method prefix, false if not.
553
* @see #setNativeMethodPrefix
554
* @since 1.6
555
*/
556
boolean
557
isNativeMethodPrefixSupported();
558
559
/**
560
* This method modifies the failure handling of
561
* native method resolution by allowing retry
562
* with a prefix applied to the name.
563
* When used with the
564
* {@link java.lang.instrument.ClassFileTransformer ClassFileTransformer},
565
* it enables native methods to be
566
* instrumented.
567
* <p>
568
* Since native methods cannot be directly instrumented
569
* (they have no bytecodes), they must be wrapped with
570
* a non-native method which can be instrumented.
571
* For example, if we had:
572
* <pre>
573
* native boolean foo(int x);</pre>
574
* <p>
575
* We could transform the class file (with the
576
* ClassFileTransformer during the initial definition
577
* of the class) so that this becomes:
578
* <pre>
579
* boolean foo(int x) {
580
* <i>... record entry to foo ...</i>
581
* return wrapped_foo(x);
582
* }
583
*
584
* native boolean wrapped_foo(int x);</pre>
585
* <p>
586
* Where <code>foo</code> becomes a wrapper for the actual native
587
* method with the appended prefix "wrapped_". Note that
588
* "wrapped_" would be a poor choice of prefix since it
589
* might conceivably form the name of an existing method
590
* thus something like "$$$MyAgentWrapped$$$_" would be
591
* better but would make these examples less readable.
592
* <p>
593
* The wrapper will allow data to be collected on the native
594
* method call, but now the problem becomes linking up the
595
* wrapped method with the native implementation.
596
* That is, the method <code>wrapped_foo</code> needs to be
597
* resolved to the native implementation of <code>foo</code>,
598
* which might be:
599
* <pre>
600
* Java_somePackage_someClass_foo(JNIEnv* env, jint x)</pre>
601
* <p>
602
* This function allows the prefix to be specified and the
603
* proper resolution to occur.
604
* Specifically, when the standard resolution fails, the
605
* resolution is retried taking the prefix into consideration.
606
* There are two ways that resolution occurs, explicit
607
* resolution with the JNI function <code>RegisterNatives</code>
608
* and the normal automatic resolution. For
609
* <code>RegisterNatives</code>, the JVM will attempt this
610
* association:
611
* <pre>{@code
612
* method(foo) -> nativeImplementation(foo)
613
* }</pre>
614
* <p>
615
* When this fails, the resolution will be retried with
616
* the specified prefix prepended to the method name,
617
* yielding the correct resolution:
618
* <pre>{@code
619
* method(wrapped_foo) -> nativeImplementation(foo)
620
* }</pre>
621
* <p>
622
* For automatic resolution, the JVM will attempt:
623
* <pre>{@code
624
* method(wrapped_foo) -> nativeImplementation(wrapped_foo)
625
* }</pre>
626
* <p>
627
* When this fails, the resolution will be retried with
628
* the specified prefix deleted from the implementation name,
629
* yielding the correct resolution:
630
* <pre>{@code
631
* method(wrapped_foo) -> nativeImplementation(foo)
632
* }</pre>
633
* <p>
634
* Note that since the prefix is only used when standard
635
* resolution fails, native methods can be wrapped selectively.
636
* <p>
637
* Since each <code>ClassFileTransformer</code>
638
* can do its own transformation of the bytecodes, more
639
* than one layer of wrappers may be applied. Thus each
640
* transformer needs its own prefix. Since transformations
641
* are applied in order, the prefixes, if applied, will
642
* be applied in the same order
643
* (see {@link #addTransformer(ClassFileTransformer,boolean) addTransformer}).
644
* Thus if three transformers applied
645
* wrappers, <code>foo</code> might become
646
* <code>$trans3_$trans2_$trans1_foo</code>. But if, say,
647
* the second transformer did not apply a wrapper to
648
* <code>foo</code> it would be just
649
* <code>$trans3_$trans1_foo</code>. To be able to
650
* efficiently determine the sequence of prefixes,
651
* an intermediate prefix is only applied if its non-native
652
* wrapper exists. Thus, in the last example, even though
653
* <code>$trans1_foo</code> is not a native method, the
654
* <code>$trans1_</code> prefix is applied since
655
* <code>$trans1_foo</code> exists.
656
*
657
* @param transformer
658
* The ClassFileTransformer which wraps using this prefix.
659
* @param prefix
660
* The prefix to apply to wrapped native methods when
661
* retrying a failed native method resolution. If prefix
662
* is either <code>null</code> or the empty string, then
663
* failed native method resolutions are not retried for
664
* this transformer.
665
* @throws java.lang.NullPointerException if passed a <code>null</code> transformer.
666
* @throws java.lang.UnsupportedOperationException if the current configuration of
667
* the JVM does not allow setting a native method prefix
668
* ({@link #isNativeMethodPrefixSupported} is false).
669
* @throws java.lang.IllegalArgumentException if the transformer is not registered
670
* (see {@link #addTransformer(ClassFileTransformer,boolean) addTransformer}).
671
*
672
* @since 1.6
673
*/
674
void
675
setNativeMethodPrefix(ClassFileTransformer transformer, String prefix);
676
677
/**
678
* Redefine a module to expand the set of modules that it reads, the set of
679
* packages that it exports or opens, or the services that it uses or
680
* provides. This method facilitates the instrumentation of code in named
681
* modules where that instrumentation requires changes to the set of modules
682
* that are read, the packages that are exported or open, or the services
683
* that are used or provided.
684
*
685
* <p> This method cannot reduce the set of modules that a module reads, nor
686
* reduce the set of packages that it exports or opens, nor reduce the set
687
* of services that it uses or provides. This method is a no-op when invoked
688
* to redefine an unnamed module. </p>
689
*
690
* <p> When expanding the services that a module uses or provides then the
691
* onus is on the agent to ensure that the service type will be accessible at
692
* each instrumentation site where the service type is used. This method
693
* does not check if the service type is a member of the module or in a
694
* package exported to the module by another module that it reads. </p>
695
*
696
* <p> The {@code extraExports} parameter is the map of additional packages
697
* to export. The {@code extraOpens} parameter is the map of additional
698
* packages to open. In both cases, the map key is the fully-qualified name
699
* of the package as defined in section 6.5.3 of
700
* <cite>The Java Language Specification </cite>, for example, {@code
701
* "java.lang"}. The map value is the non-empty set of modules that the
702
* package should be exported or opened to. </p>
703
*
704
* <p> The {@code extraProvides} parameter is the additional service providers
705
* for the module to provide. The map key is the service type. The map value
706
* is the non-empty list of implementation types, each of which is a member
707
* of the module and an implementation of the service. </p>
708
*
709
* <p> This method is safe for concurrent use and so allows multiple agents
710
* to instrument and update the same module at around the same time. </p>
711
*
712
* @param module the module to redefine
713
* @param extraReads the possibly-empty set of additional modules to read
714
* @param extraExports the possibly-empty map of additional packages to export
715
* @param extraOpens the possibly-empty map of additional packages to open
716
* @param extraUses the possibly-empty set of additional services to use
717
* @param extraProvides the possibly-empty map of additional services to provide
718
*
719
* @throws IllegalArgumentException
720
* If {@code extraExports} or {@code extraOpens} contains a key
721
* that is not a package in the module; if {@code extraExports} or
722
* {@code extraOpens} maps a key to an empty set; if a value in the
723
* {@code extraProvides} map contains a service provider type that
724
* is not a member of the module or an implementation of the service;
725
* or {@code extraProvides} maps a key to an empty list
726
* @throws UnmodifiableModuleException if the module cannot be modified
727
* @throws NullPointerException if any of the arguments are {@code null} or
728
* any of the Sets or Maps contains a {@code null} key or value
729
*
730
* @see #isModifiableModule(Module)
731
* @since 9
732
*/
733
void redefineModule(Module module,
734
Set<Module> extraReads,
735
Map<String, Set<Module>> extraExports,
736
Map<String, Set<Module>> extraOpens,
737
Set<Class<?>> extraUses,
738
Map<Class<?>, List<Class<?>>> extraProvides);
739
740
/**
741
* Tests whether a module can be modified with {@link #redefineModule
742
* redefineModule}. If a module is modifiable then this method returns
743
* {@code true}. If a module is not modifiable then this method returns
744
* {@code false}. This method always returns {@code true} when the module
745
* is an unnamed module (as redefining an unnamed module is a no-op).
746
*
747
* @param module the module to test if it can be modified
748
* @return {@code true} if the module is modifiable, otherwise {@code false}
749
* @throws NullPointerException if the module is {@code null}
750
*
751
* @since 9
752
*/
753
boolean isModifiableModule(Module module);
754
}
755
756