Skip to content

Commit

Permalink
Migrate NameTable utilities for generating method names and ObjC type…
Browse files Browse the repository at this point in the history
…s to new type system.

	Change on 2016/11/21 by kstanger <kstanger@google.com>

-------------
Created by MOE: https://github.com/google/moe
MOE_MIGRATED_REVID=139818895
  • Loading branch information
kstanger authored and Keith Stanger committed Dec 1, 2016
1 parent 2a18c2b commit 190b34c
Show file tree
Hide file tree
Showing 2 changed files with 48 additions and 74 deletions.
Original file line number Original file line Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@


import com.google.common.base.Joiner; import com.google.common.base.Joiner;
import com.google.common.collect.ImmutableMap; import com.google.common.collect.ImmutableMap;
import com.google.common.collect.Iterables;
import com.google.common.collect.Lists; import com.google.common.collect.Lists;
import com.google.common.collect.Sets; import com.google.common.collect.Sets;
import com.google.devtools.j2objc.Options; import com.google.devtools.j2objc.Options;
Expand All @@ -43,10 +42,8 @@
import javax.lang.model.element.TypeElement; import javax.lang.model.element.TypeElement;
import javax.lang.model.element.VariableElement; import javax.lang.model.element.VariableElement;
import javax.lang.model.type.ArrayType; import javax.lang.model.type.ArrayType;
import javax.lang.model.type.TypeKind;
import javax.lang.model.type.TypeMirror; import javax.lang.model.type.TypeMirror;
import org.eclipse.jdt.core.dom.IAnnotationBinding; import org.eclipse.jdt.core.dom.IAnnotationBinding;
import org.eclipse.jdt.core.dom.IMethodBinding;
import org.eclipse.jdt.core.dom.ITypeBinding; import org.eclipse.jdt.core.dom.ITypeBinding;
import org.eclipse.jdt.core.dom.VariableDeclarationFragment; import org.eclipse.jdt.core.dom.VariableDeclarationFragment;


Expand Down Expand Up @@ -510,21 +507,17 @@ public String getMethodSelector(ExecutableElement method) {
if (ElementUtil.isInstanceMethod(method)) { if (ElementUtil.isInstanceMethod(method)) {
method = getOriginalMethod(method); method = getOriginalMethod(method);
} }
return selectorForOriginalBinding(method); selector = getRenamedMethodName(method);
return selectorForMethodName(method, selector != null ? selector : getMethodName(method));
} }


public String getMethodSelector(IMethodBinding method) { private String getRenamedMethodName(ExecutableElement method) {
return getMethodSelector(BindingConverter.getExecutableElement(method)); String selector = methodMappings.get(Mappings.getMethodKey(method, typeUtil));
}

private String getRenamedMethodName(IMethodBinding method) {
method = method.getMethodDeclaration();
String selector = methodMappings.get(BindingUtil.getMethodKey(method));
if (selector != null) { if (selector != null) {
validateMethodSelector(selector); validateMethodSelector(selector);
return selector; return selector;
} }
selector = getMethodNameFromAnnotation(BindingConverter.getExecutableElement(method)); selector = getMethodNameFromAnnotation(method);
if (selector != null) { if (selector != null) {
return selector; return selector;
} }
Expand All @@ -538,20 +531,13 @@ public String selectorForMethodName(ExecutableElement method, String name) {
return addParamNames(method, name, ':'); return addParamNames(method, name, ':');
} }


private String selectorForOriginalBinding(ExecutableElement method) {
String selector = getRenamedMethodName(BindingConverter.unwrapExecutableElement(method));
return selectorForMethodName(
method, selector != null ? selector : getMethodName(method));
}

/** /**
* Returns a "Type_method" function name for static methods, such as from * Returns a "Type_method" function name for static methods, such as from
* enum types. A combination of classname plus modified selector is * enum types. A combination of classname plus modified selector is
* guaranteed to be unique within the app. * guaranteed to be unique within the app.
*/ */
public String getFullFunctionName(ExecutableElement method) { public String getFullFunctionName(ExecutableElement method) {
return getFullName(BindingConverter.unwrapTypeElement(ElementUtil.getDeclaringClass(method))) return getFullName(ElementUtil.getDeclaringClass(method)) + '_' + getFunctionName(method);
+ '_' + getFunctionName(method);
} }


/** /**
Expand Down Expand Up @@ -600,7 +586,7 @@ public String getReleasingConstructorName(ExecutableElement method) {
public String getFunctionName(ExecutableElement method) { public String getFunctionName(ExecutableElement method) {
String name = ElementUtil.getSelector(method); String name = ElementUtil.getSelector(method);
if (name == null) { if (name == null) {
name = getRenamedMethodName(BindingConverter.unwrapExecutableElement(method)); name = getRenamedMethodName(method);
} }
if (name != null) { if (name != null) {
return name.replaceAll(":", "_"); return name.replaceAll(":", "_");
Expand All @@ -625,7 +611,7 @@ private ExecutableElement getOriginalMethod(ExecutableElement method) {
} }


/** /**
* Finds the original method binding to use for generating a selector. The method returned is the * Finds the original method element to use for generating a selector. The method returned is the
* first method found in the hierarchy while traversing in order of declared inheritance that * first method found in the hierarchy while traversing in order of declared inheritance that
* doesn't override a method from a supertype. (ie. it is the first leaf node found in the tree of * doesn't override a method from a supertype. (ie. it is the first leaf node found in the tree of
* overriding methods) * overriding methods)
Expand Down Expand Up @@ -660,65 +646,46 @@ private ExecutableElement getOriginalMethod(
} }


/** /**
* Converts a Java type to an equivalent Objective-C type, returning "id" for * Converts a Java type to an equivalent Objective-C type, returning "id" for an object type.
* an object type.
*/
public static String getPrimitiveObjCType(ITypeBinding type) {
return type.isPrimitive() ? (BindingUtil.isVoid(type) ? "void" : "j" + type.getName()) : "id";
}

/**
* Does the same, but for TypeMirrors.
*/ */
public static String getPrimitiveObjCType(TypeMirror type) { public static String getPrimitiveObjCType(TypeMirror type) {
TypeKind kind = type.getKind(); return TypeUtil.isVoid(type) ? "void"
return kind == TypeKind.VOID ? "void" : type.getKind().isPrimitive() ? "j" + TypeUtil.getName(type) : "id";
: kind.isPrimitive() ? "j" + TypeUtil.getName(type) : "id";
} }


/** /**
* Convert a Java type to an equivalent Objective-C type with type variables * Convert a Java type to an equivalent Objective-C type with type variables
* resolved to their bounds. * resolved to their bounds.
*/ */
public String getObjCType(ITypeBinding type) {
return getObjCTypeInner(type, null);
}

public String getObjCType(TypeMirror type) { public String getObjCType(TypeMirror type) {
return getObjCTypeInner(BindingConverter.unwrapTypeMirrorIntoTypeBinding(type), null); return getObjcTypeInner(type, null);
} }


public String getObjCType(VariableElement var) { public String getObjCType(VariableElement var) {
return getObjCTypeInner( return getObjcTypeInner(var.asType(), ElementUtil.getTypeQualifiers(var));
BindingConverter.unwrapTypeMirrorIntoTypeBinding(var.asType()),
ElementUtil.getTypeQualifiers(var));
} }


/** /**
* Convert a Java type into the equivalent JNI type. * Convert a Java type into the equivalent JNI type.
*/ */
public String getJniType(TypeMirror typeM) { public String getJniType(TypeMirror type) {
ITypeBinding type = BindingConverter.unwrapTypeMirrorIntoTypeBinding(typeM); if (TypeUtil.isPrimitiveOrVoid(type)) {
if (type.isPrimitive()) {
return getPrimitiveObjCType(type); return getPrimitiveObjCType(type);
} } else if (TypeUtil.isArray(type)) {
if (type.isArray()) {
return "jarray"; return "jarray";
} } else if (typeUtil.isString(type)) {
if (type.getQualifiedName().equals("java.lang.String")) {
return "jstring"; return "jstring";
} } else if (typeUtil.isClassType(type)) {
if (type.getQualifiedName().equals("java.lang.Class")) {
return "jclass"; return "jclass";
} }
return "jobject"; return "jobject";
} }


private String getObjCTypeInner(ITypeBinding type, String qualifiers) { private String getObjcTypeInner(TypeMirror type, String qualifiers) {
String objCType; String objcType;
if (type instanceof NativeType.Binding) { if (type instanceof NativeType) {
objCType = type.getName(); objcType = ((NativeType) type).getName();
} else if (type instanceof PointerType.Binding) { } else if (type instanceof PointerType) {
String pointeeQualifiers = null; String pointeeQualifiers = null;
if (qualifiers != null) { if (qualifiers != null) {
int idx = qualifiers.indexOf('*'); int idx = qualifiers.indexOf('*');
Expand All @@ -727,36 +694,31 @@ private String getObjCTypeInner(ITypeBinding type, String qualifiers) {
qualifiers = qualifiers.substring(idx + 1); qualifiers = qualifiers.substring(idx + 1);
} }
} }
objCType = getObjCTypeInner(((PointerType.Binding) type).getPointeeType(), pointeeQualifiers); objcType = getObjcTypeInner(((PointerType) type).getPointeeType(), pointeeQualifiers);
objCType = objCType.endsWith("*") ? objCType + "*" : objCType + " *"; objcType = objcType.endsWith("*") ? objcType + "*" : objcType + " *";
} else if (type.isPrimitive()) { } else if (TypeUtil.isPrimitiveOrVoid(type)) {
objCType = getPrimitiveObjCType(type); objcType = getPrimitiveObjCType(type);
} else { } else {
objCType = constructObjCType(Iterables.transform( objcType = constructObjcTypeFromBounds(type);
typeUtil.getUpperBounds(BindingConverter.getType(type)),
BindingConverter::unwrapTypeMirrorIntoTypeBinding));
} }
if (qualifiers != null) { if (qualifiers != null) {
qualifiers = qualifiers.trim(); qualifiers = qualifiers.trim();
if (!qualifiers.isEmpty()) { if (!qualifiers.isEmpty()) {
objCType += " " + qualifiers; objcType += " " + qualifiers;
} }
} }
return objCType; return objcType;
} }


private String constructObjCType(Iterable<ITypeBinding> types) { private String constructObjcTypeFromBounds(TypeMirror type) {
String classType = null; String classType = null;
List<String> interfaces = new ArrayList<>(); List<String> interfaces = new ArrayList<>();
for (ITypeBinding type : types) { for (TypeElement bound : typeUtil.getObjcUpperBounds(type)) {
if (typeEnv.isIdType(type)) { if (bound.getKind().isInterface()) {
continue; interfaces.add(getFullName(bound));
}
if (type.isInterface()) {
interfaces.add(getFullName(type));
} else { } else {
assert classType == null; // Can only have one class type. assert classType == null : "Cannot have multiple class bounds";
classType = getFullName(type); classType = getFullName(bound);
} }
} }
String protocols = interfaces.isEmpty() ? "" : "<" + Joiner.on(", ").join(interfaces) + ">"; String protocols = interfaces.isEmpty() ? "" : "<" + Joiner.on(", ").join(interfaces) + ">";
Expand Down
Original file line number Original file line Diff line number Diff line change
Expand Up @@ -162,6 +162,10 @@ public static boolean isVoid(TypeMirror t) {
return t.getKind() == TypeKind.VOID; return t.getKind() == TypeKind.VOID;
} }


public static boolean isPrimitiveOrVoid(TypeMirror t) {
return isVoid(t) || t.getKind().isPrimitive();
}

public static boolean isNone(TypeMirror t) { public static boolean isNone(TypeMirror t) {
// Check for null because BindingConverter converts null bindings to null types. // Check for null because BindingConverter converts null bindings to null types.
return t == null || t.getKind() == TypeKind.NONE; return t == null || t.getKind() == TypeKind.NONE;
Expand Down Expand Up @@ -268,6 +272,14 @@ public boolean isString(TypeMirror t) {
return isString(asTypeElement(t)); return isString(asTypeElement(t));
} }


public boolean isClassType(TypeElement e) {
return javaClass.equals(e) || IOS_CLASS.equals(e);
}

public boolean isClassType(TypeMirror t) {
return isClassType(asTypeElement(t));
}

/** /**
* Maps the given type to it's Objective-C equivalent. Array types are mapped to their equivalent * Maps the given type to it's Objective-C equivalent. Array types are mapped to their equivalent
* IOSArray type and common Java classes like String and Object are mapped to NSString and * IOSArray type and common Java classes like String and Object are mapped to NSString and
Expand Down

0 comments on commit 190b34c

Please sign in to comment.