@@ -66,7 +66,7 @@ public static class Options {
6666 public static final RuntimeOptionKey <String > RecordMetadata = new RuntimeOptionKey <>("" );
6767 }
6868
69- private ConfigurationSet config ;
69+ private volatile ConfigurationSet config ;
7070
7171 private Path recordMetadataPath ;
7272
@@ -75,36 +75,75 @@ public static MetadataTracer singleton() {
7575 return ImageSingletons .lookup (MetadataTracer .class );
7676 }
7777
78+ /**
79+ * Returns whether tracing is enabled at run time (using {@code -XX:RecordMetadata=path}).
80+ */
7881 public boolean enabled () {
7982 VMError .guarantee (Options .MetadataTracingSupport .getValue ());
80- return config != null ;
83+ return recordMetadataPath != null ;
8184 }
8285
86+ /**
87+ * Marks the given type as reachable from reflection.
88+ *
89+ * @return the corresponding {@link ConfigurationType} or {@code null} if tracing is not active
90+ * (e.g., during shutdown).
91+ */
8392 public ConfigurationType traceReflectionType (String className ) {
8493 assert enabled ();
85- return config .getReflectionConfiguration ().getOrCreateType (UnresolvedConfigurationCondition .alwaysTrue (), new NamedConfigurationTypeDescriptor (className ));
94+ ConfigurationSet configurationSet = config ;
95+ if (configurationSet != null ) {
96+ return configurationSet .getReflectionConfiguration ().getOrCreateType (UnresolvedConfigurationCondition .alwaysTrue (), new NamedConfigurationTypeDescriptor (className ));
97+ }
98+ return null ;
8699 }
87100
101+ /**
102+ * Marks the given type as reachable from JNI.
103+ *
104+ * @return the corresponding {@link ConfigurationType} or {@code null} if tracing is not active
105+ * (e.g., during shutdown).
106+ */
88107 public ConfigurationType traceJNIType (String className ) {
89108 assert enabled ();
90109 ConfigurationType result = traceReflectionType (className );
91- result .setJniAccessible ();
110+ if (result != null ) {
111+ result .setJniAccessible ();
112+ }
92113 return result ;
93114 }
94115
116+ /**
117+ * Marks the given resource within the given (optional) module as reachable.
118+ */
95119 public void traceResource (String resourceName , String moduleName ) {
96120 assert enabled ();
97- config .getResourceConfiguration ().addGlobPattern (UnresolvedConfigurationCondition .alwaysTrue (), resourceName , moduleName );
121+ ConfigurationSet configurationSet = config ;
122+ if (configurationSet != null ) {
123+ configurationSet .getResourceConfiguration ().addGlobPattern (UnresolvedConfigurationCondition .alwaysTrue (), resourceName , moduleName );
124+ }
98125 }
99126
127+ /**
128+ * Marks the given resource bundle within the given locale as reachable.
129+ */
100130 public void traceResourceBundle (String baseName ) {
101131 assert enabled ();
102- config .getResourceConfiguration ().addBundle (UnresolvedConfigurationCondition .alwaysTrue (), baseName , List .of ());
132+ ConfigurationSet configurationSet = config ;
133+ if (configurationSet != null ) {
134+ configurationSet .getResourceConfiguration ().addBundle (UnresolvedConfigurationCondition .alwaysTrue (), baseName , List .of ());
135+ }
103136 }
104137
138+ /**
139+ * Marks the given type as serializable.
140+ */
105141 public void traceSerializationType (String className ) {
106142 assert enabled ();
107- config .getReflectionConfiguration ().getOrCreateType (UnresolvedConfigurationCondition .alwaysTrue (), new NamedConfigurationTypeDescriptor (className )).setSerializable ();
143+ ConfigurationSet configurationSet = config ;
144+ if (configurationSet != null ) {
145+ configurationSet .getReflectionConfiguration ().getOrCreateType (UnresolvedConfigurationCondition .alwaysTrue (), new NamedConfigurationTypeDescriptor (className )).setSerializable ();
146+ }
108147 }
109148
110149 private static void initialize () {
@@ -128,6 +167,7 @@ private static void shutdown() {
128167 assert Options .MetadataTracingSupport .getValue ();
129168 MetadataTracer singleton = MetadataTracer .singleton ();
130169 ConfigurationSet config = singleton .config ;
170+ singleton .config = null ; // clear config so that shutdown events are not traced.
131171 if (config != null ) {
132172 try {
133173 config .writeConfiguration (configFile -> singleton .recordMetadataPath .resolve (configFile .getFileName ()));
0 commit comments