< prev index next > src/java.base/share/classes/java/lang/invoke/MemberName.java
Print this page
* For non-static methods or constructors, this is the type with a leading parameter,
* a reference to declaring class. For static methods, it is the same as the declared type.
*/
public MethodType getInvocationType() {
MethodType itype = getMethodOrFieldType();
- if (isConstructor() && getReferenceKind() == REF_newInvokeSpecial)
- return itype.changeReturnType(clazz);
+ Class<?> c = clazz.isPrimitiveClass() ? clazz.asValueType() : clazz;
+ if (isObjectConstructor() && getReferenceKind() == REF_newInvokeSpecial)
+ return itype.changeReturnType(c);
if (!isStatic())
- return itype.insertParameterTypes(0, clazz);
+ return itype.insertParameterTypes(0, c);
return itype;
}
/** Utility method producing the parameter types of the method type. */
public Class<?>[] getParameterTypes() {
byte refKind = getReferenceKind();
if (refKind == REF_NONE) return isType();
if (isField()) {
assert(staticIsConsistent());
assert(MethodHandleNatives.refKindIsField(refKind));
- } else if (isConstructor()) {
+ } else if (isObjectConstructor()) {
assert(refKind == REF_newInvokeSpecial || refKind == REF_invokeSpecial);
} else if (isMethod()) {
assert(staticIsConsistent());
assert(MethodHandleNatives.refKindIsMethod(refKind));
if (clazz.isInterface())
public boolean isProtected() {
return Modifier.isProtected(flags);
}
/** Utility method to query the modifier flags of this member. */
public boolean isFinal() {
+ // all fields declared in a value type are effectively final
+ assert(!clazz.isValue() || !isField() || Modifier.isFinal(flags));
return Modifier.isFinal(flags);
}
/** Utility method to query whether this member or its defining class is final. */
public boolean canBeStaticallyBound() {
return Modifier.isFinal(flags | clazz.getModifiers());
return Modifier.isNative(flags);
}
// let the rest (native, volatile, transient, etc.) be tested via Modifier.isFoo
// unofficial modifier flags, used by HotSpot:
- static final int BRIDGE = 0x00000040;
- static final int VARARGS = 0x00000080;
- static final int SYNTHETIC = 0x00001000;
- static final int ANNOTATION= 0x00002000;
- static final int ENUM = 0x00004000;
+ static final int BRIDGE = 0x00000040;
+ static final int VARARGS = 0x00000080;
+ static final int SYNTHETIC = 0x00001000;
+ static final int ANNOTATION = 0x00002000;
+ static final int ENUM = 0x00004000;
+
/** Utility method to query the modifier flags of this member; returns false if the member is not a method. */
public boolean isBridge() {
return testAllFlags(IS_METHOD | BRIDGE);
}
/** Utility method to query the modifier flags of this member; returns false if the member is not a method. */
/** Utility method to query the modifier flags of this member; returns false if the member is not a method. */
public boolean isSynthetic() {
return testAllFlags(SYNTHETIC);
}
+ /** Query whether this member is a flattened field */
+ public boolean isFlattened() { return (flags & MN_FLATTENED) == MN_FLATTENED; }
+
+ /** Query whether this member is a field of a primitive class. */
+ public boolean isInlineableField() {
+ if (isField()) {
+ Class<?> type = getFieldType();
+ return type.isPrimitiveValueType() || (type.isValue() && !type.isPrimitiveClass());
+ }
+ return false;
+ }
+
static final String CONSTRUCTOR_NAME = "<init>"; // the ever-popular
+ // modifiers exported by the JVM:
// modifiers exported by the JVM:
static final int RECOGNIZED_MODIFIERS = 0xFFFF;
// private flags, not part of RECOGNIZED_MODIFIERS:
static final int
- IS_METHOD = MN_IS_METHOD, // method (not constructor)
- IS_CONSTRUCTOR = MN_IS_CONSTRUCTOR, // constructor
- IS_FIELD = MN_IS_FIELD, // field
- IS_TYPE = MN_IS_TYPE, // nested type
- CALLER_SENSITIVE = MN_CALLER_SENSITIVE, // @CallerSensitive annotation detected
- TRUSTED_FINAL = MN_TRUSTED_FINAL; // trusted final field
+ IS_METHOD = MN_IS_METHOD, // method (not object constructor)
+ IS_OBJECT_CONSTRUCTOR = MN_IS_OBJECT_CONSTRUCTOR, // object constructor
+ IS_FIELD = MN_IS_FIELD, // field
+ IS_TYPE = MN_IS_TYPE, // nested type
+ CALLER_SENSITIVE = MN_CALLER_SENSITIVE, // @CallerSensitive annotation detected
+ TRUSTED_FINAL = MN_TRUSTED_FINAL; // trusted final field
static final int ALL_ACCESS = Modifier.PUBLIC | Modifier.PRIVATE | Modifier.PROTECTED;
- static final int ALL_KINDS = IS_METHOD | IS_CONSTRUCTOR | IS_FIELD | IS_TYPE;
- static final int IS_INVOCABLE = IS_METHOD | IS_CONSTRUCTOR;
+ static final int ALL_KINDS = IS_METHOD | IS_OBJECT_CONSTRUCTOR | IS_FIELD | IS_TYPE;
+ static final int IS_INVOCABLE = IS_METHOD | IS_OBJECT_CONSTRUCTOR;
static final int IS_FIELD_OR_METHOD = IS_METHOD | IS_FIELD;
static final int SEARCH_ALL_SUPERS = MN_SEARCH_SUPERCLASSES | MN_SEARCH_INTERFACES;
/** Utility method to query whether this member is a method or constructor. */
public boolean isInvocable() {
/** Query whether this member is a method. */
public boolean isMethod() {
return testAllFlags(IS_METHOD);
}
/** Query whether this member is a constructor. */
- public boolean isConstructor() {
- return testAllFlags(IS_CONSTRUCTOR);
+ public boolean isObjectConstructor() {
+ return testAllFlags(IS_OBJECT_CONSTRUCTOR);
+ }
+ /** Query whether this member is an object constructor or static <init> factory */
+ public boolean isObjectConstructorOrStaticInitMethod() {
+ return isObjectConstructor() || (getName().equals(CONSTRUCTOR_NAME) && testAllFlags(IS_METHOD));
}
/** Query whether this member is a field. */
public boolean isField() {
return testAllFlags(IS_FIELD);
}
throw new IllegalArgumentException(this.toString());
}
/** If this MN is not REF_newInvokeSpecial, return a clone with that ref. kind.
* In that case it must already be REF_invokeSpecial.
*/
- public MemberName asConstructor() {
+ public MemberName asObjectConstructor() {
switch (getReferenceKind()) {
case REF_invokeSpecial: return clone().changeReferenceKind(REF_newInvokeSpecial, REF_invokeSpecial);
case REF_newInvokeSpecial: return this;
}
throw new IllegalArgumentException(this.toString());
Objects.requireNonNull(ctor);
// fill in vmtarget, vmindex while we have ctor in hand:
MethodHandleNatives.init(this, ctor);
assert(isResolved() && this.clazz != null);
this.name = CONSTRUCTOR_NAME;
- if (this.type == null)
- this.type = new Object[] { void.class, ctor.getParameterTypes() };
+ if (this.type == null) {
+ Class<?> rtype = void.class;
+ if (isStatic()) { // a static init factory, not a true constructor
+ rtype = getDeclaringClass();
+ // FIXME: If it's a hidden class, this sig won't work.
+ }
+ this.type = new Object[] { rtype, ctor.getParameterTypes() };
+ }
}
/** Create a name for the given reflected field. The resulting name will be in a resolved state.
*/
public MemberName(Field fld) {
this(fld, false);
* The declaring class may be supplied as null if this is to be a bare name and type.
* The last argument is optional, a boolean which requests REF_invokeSpecial.
* The resulting name will in an unresolved state.
*/
public MemberName(Class<?> defClass, String name, MethodType type, byte refKind) {
- int initFlags = (name != null && name.equals(CONSTRUCTOR_NAME) ? IS_CONSTRUCTOR : IS_METHOD);
+ int initFlags = (name != null && name.equals(CONSTRUCTOR_NAME) && type.returnType() == void.class ? IS_OBJECT_CONSTRUCTOR : IS_METHOD);
init(defClass, name, type, flagsMods(initFlags, 0, refKind));
initResolved(false);
}
/** Create a method, constructor, or field name from the given components:
* Reference kind, declaring class, name, type.
} else if (MethodHandleNatives.refKindIsMethod(refKind)) {
kindFlags = IS_METHOD;
if (!(type instanceof MethodType))
throw newIllegalArgumentException("not a method type");
} else if (refKind == REF_newInvokeSpecial) {
- kindFlags = IS_CONSTRUCTOR;
+ kindFlags = IS_OBJECT_CONSTRUCTOR;
if (!(type instanceof MethodType) ||
!CONSTRUCTOR_NAME.equals(name))
throw newIllegalArgumentException("not a constructor type or name");
} else {
throw newIllegalArgumentException("bad reference kind "+refKind);
return new IllegalAccessException(message);
}
private String message() {
if (isResolved())
return "no access";
- else if (isConstructor())
+ else if (isObjectConstructor())
return "no such constructor";
else if (isMethod())
return "no such method";
else
return "no such field";
String message = message() + ": "+ toString();
ReflectiveOperationException ex;
if (isResolved() || !(resolution instanceof NoSuchMethodError ||
resolution instanceof NoSuchFieldError))
ex = new IllegalAccessException(message);
- else if (isConstructor())
+ else if (isObjectConstructor())
ex = new NoSuchMethodException(message);
else if (isMethod())
ex = new NoSuchMethodException(message);
else
ex = new NoSuchFieldException(message);
public List<MemberName> getMethods(Class<?> defc, boolean searchSupers,
String name, MethodType type, Class<?> lookupClass) {
int matchFlags = IS_METHOD | (searchSupers ? SEARCH_ALL_SUPERS : 0);
return getMembers(defc, name, type, matchFlags, lookupClass);
}
- /** Return a list of all constructors defined by the given class.
+ /** Return a list of all object constructors defined by the given class.
* Access checking is performed on behalf of the given {@code lookupClass}.
* Inaccessible members are not added to the last.
*/
- public List<MemberName> getConstructors(Class<?> defc, Class<?> lookupClass) {
- return getMembers(defc, null, null, IS_CONSTRUCTOR, lookupClass);
+ public List<MemberName> getObjectConstructors(Class<?> defc, Class<?> lookupClass) {
+ return getMembers(defc, null, null, IS_OBJECT_CONSTRUCTOR, lookupClass);
}
/** Return a list of all fields defined by the given class.
* Super types are searched (for inherited members) if {@code searchSupers} is true.
* Access checking is performed on behalf of the given {@code lookupClass}.
* Inaccessible members are not added to the last.
< prev index next >