8288327: Executable.hasRealParameterData should not be volatile
Reviewed-by: plevart
This commit is contained in:
parent
d4a795d75a
commit
aa557b9b01
@ -25,16 +25,16 @@
|
|||||||
|
|
||||||
package java.lang.reflect;
|
package java.lang.reflect;
|
||||||
|
|
||||||
import java.lang.annotation.*;
|
import java.lang.annotation.Annotation;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
import java.util.StringJoiner;
|
import java.util.StringJoiner;
|
||||||
import java.util.stream.Stream;
|
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
import jdk.internal.access.SharedSecrets;
|
import jdk.internal.access.SharedSecrets;
|
||||||
|
import jdk.internal.vm.annotation.Stable;
|
||||||
import sun.reflect.annotation.AnnotationParser;
|
import sun.reflect.annotation.AnnotationParser;
|
||||||
import sun.reflect.annotation.AnnotationSupport;
|
import sun.reflect.annotation.AnnotationSupport;
|
||||||
import sun.reflect.annotation.TypeAnnotationParser;
|
import sun.reflect.annotation.TypeAnnotationParser;
|
||||||
@ -382,7 +382,7 @@ public abstract sealed class Executable extends AccessibleObject
|
|||||||
// Need to copy the cached array to prevent users from messing
|
// Need to copy the cached array to prevent users from messing
|
||||||
// with it. Since parameters are immutable, we can
|
// with it. Since parameters are immutable, we can
|
||||||
// shallow-copy.
|
// shallow-copy.
|
||||||
return privateGetParameters().clone();
|
return parameterData().parameters.clone();
|
||||||
}
|
}
|
||||||
|
|
||||||
private Parameter[] synthesizeAllParams() {
|
private Parameter[] synthesizeAllParams() {
|
||||||
@ -421,46 +421,40 @@ public abstract sealed class Executable extends AccessibleObject
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private Parameter[] privateGetParameters() {
|
|
||||||
// Use tmp to avoid multiple writes to a volatile.
|
|
||||||
Parameter[] tmp = parameters;
|
|
||||||
|
|
||||||
if (tmp == null) {
|
|
||||||
|
|
||||||
// Otherwise, go to the JVM to get them
|
|
||||||
try {
|
|
||||||
tmp = getParameters0();
|
|
||||||
} catch(IllegalArgumentException e) {
|
|
||||||
// Rethrow ClassFormatErrors
|
|
||||||
throw new MalformedParametersException("Invalid constant pool index");
|
|
||||||
}
|
|
||||||
|
|
||||||
// If we get back nothing, then synthesize parameters
|
|
||||||
if (tmp == null) {
|
|
||||||
hasRealParameterData = false;
|
|
||||||
tmp = synthesizeAllParams();
|
|
||||||
} else {
|
|
||||||
hasRealParameterData = true;
|
|
||||||
verifyParameters(tmp);
|
|
||||||
}
|
|
||||||
|
|
||||||
parameters = tmp;
|
|
||||||
}
|
|
||||||
|
|
||||||
return tmp;
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean hasRealParameterData() {
|
boolean hasRealParameterData() {
|
||||||
// If this somehow gets called before parameters gets
|
return parameterData().isReal;
|
||||||
// initialized, force it into existence.
|
|
||||||
if (parameters == null) {
|
|
||||||
privateGetParameters();
|
|
||||||
}
|
|
||||||
return hasRealParameterData;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private transient volatile boolean hasRealParameterData;
|
private ParameterData parameterData() {
|
||||||
private transient volatile Parameter[] parameters;
|
ParameterData parameterData = this.parameterData;
|
||||||
|
if (parameterData != null) {
|
||||||
|
return parameterData;
|
||||||
|
}
|
||||||
|
|
||||||
|
Parameter[] tmp;
|
||||||
|
// Go to the JVM to get them
|
||||||
|
try {
|
||||||
|
tmp = getParameters0();
|
||||||
|
} catch (IllegalArgumentException e) {
|
||||||
|
// Rethrow ClassFormatErrors
|
||||||
|
throw new MalformedParametersException("Invalid constant pool index");
|
||||||
|
}
|
||||||
|
|
||||||
|
// If we get back nothing, then synthesize parameters
|
||||||
|
if (tmp == null) {
|
||||||
|
tmp = synthesizeAllParams();
|
||||||
|
parameterData = new ParameterData(tmp, false);
|
||||||
|
} else {
|
||||||
|
verifyParameters(tmp);
|
||||||
|
parameterData = new ParameterData(tmp, true);
|
||||||
|
}
|
||||||
|
return this.parameterData = parameterData;
|
||||||
|
}
|
||||||
|
|
||||||
|
private transient @Stable ParameterData parameterData;
|
||||||
|
|
||||||
|
record ParameterData(@Stable Parameter[] parameters, boolean isReal) {}
|
||||||
|
|
||||||
private native Parameter[] getParameters0();
|
private native Parameter[] getParameters0();
|
||||||
native byte[] getTypeAnnotationBytes0();
|
native byte[] getTypeAnnotationBytes0();
|
||||||
|
Loading…
x
Reference in New Issue
Block a user