Skip to content

Commit

Permalink
Converts OperatorRewriter to new type system.
Browse files Browse the repository at this point in the history
	Change on 2016/11/07 by kstanger <kstanger@google.com>

-------------
Created by MOE: https://github.com/google/moe
MOE_MIGRATED_REVID=138407890
  • Loading branch information
kstanger authored and tomball committed Nov 7, 2016
1 parent 33b6ed8 commit 6ff9222
Show file tree
Hide file tree
Showing 8 changed files with 68 additions and 62 deletions.
Expand Up @@ -499,7 +499,7 @@ public boolean visit(QualifiedName node) {
@Override
public void endVisit(SimpleName node) {
VariableElement var = TreeUtil.getVariableElement(node);
if (var != null && ElementUtil.isField(var)) {
if (var != null && var.getKind().isField()) {
// Convert name to self->name.
node.replaceWith(new QualifiedName(var, new SimpleName(selfParam)));
}
Expand Down
Expand Up @@ -428,7 +428,7 @@ private String getTypeName(TypeMirror type) {
} else if (TypeUtil.isArray(type)) {
return "[" + getTypeName(((ArrayType) type).getComponentType());
} else {
return typeUtil.getBinaryName(type);
return TypeUtil.getBinaryName(type);
}
}

Expand Down
Expand Up @@ -38,23 +38,20 @@
import com.google.devtools.j2objc.ast.UnitTreeVisitor;
import com.google.devtools.j2objc.ast.VariableDeclarationFragment;
import com.google.devtools.j2objc.ast.VariableDeclarationStatement;
import com.google.devtools.j2objc.jdt.BindingConverter;
import com.google.devtools.j2objc.types.FunctionElement;
import com.google.devtools.j2objc.types.GeneratedVariableBinding;
import com.google.devtools.j2objc.util.BindingUtil;
import com.google.devtools.j2objc.types.GeneratedVariableElement;
import com.google.devtools.j2objc.util.ElementUtil;
import com.google.devtools.j2objc.util.NameTable;
import com.google.devtools.j2objc.util.TranslationUtil;
import com.google.devtools.j2objc.util.TypeUtil;
import com.google.devtools.j2objc.util.UnicodeUtils;
import com.google.j2objc.annotations.RetainedLocalRef;
import java.util.Collections;
import java.util.Iterator;
import java.util.List;
import javax.lang.model.element.ElementKind;
import javax.lang.model.element.VariableElement;
import javax.lang.model.type.TypeKind;
import javax.lang.model.type.TypeMirror;
import org.eclipse.jdt.core.dom.ITypeBinding;
import org.eclipse.jdt.core.dom.IVariableBinding;

/**
* Rewrites certain operators, such as object assignment, into appropriate
Expand Down Expand Up @@ -85,14 +82,15 @@ private boolean isStringAppend(TreeNode node) {
}
Assignment assignment = (Assignment) node;
return assignment.getOperator() == Assignment.Operator.PLUS_ASSIGN
&& typeEnv.resolveJavaType("java.lang.String").isAssignmentCompatible(
assignment.getLeftHandSide().getTypeBinding());
&& typeUtil.isAssignable(
typeEnv.resolveJavaTypeMirror("java.lang.String"),
assignment.getLeftHandSide().getTypeMirror());
}

@Override
public void endVisit(InfixExpression node) {
InfixExpression.Operator op = node.getOperator();
ITypeBinding nodeType = node.getTypeBinding();
TypeMirror nodeType = node.getTypeMirror();
String funcName = getInfixFunction(op, nodeType);
if (funcName != null) {
Iterator<Expression> operandIter = node.getOperands().iterator();
Expand Down Expand Up @@ -158,8 +156,7 @@ public boolean visit(VariableDeclarationFragment node) {
}

private void handleRetainedLocal(VariableElement var, Expression rhs) {
if (var.getKind() == ElementKind.LOCAL_VARIABLE
&& ElementUtil.hasAnnotation(var, RetainedLocalRef.class)
if (ElementUtil.isLocalVariable(var) && ElementUtil.hasAnnotation(var, RetainedLocalRef.class)
&& Options.useReferenceCounting()) {
FunctionElement element = new FunctionElement(
"JreRetainedLocalValue", typeEnv.getIdTypeMirror(), null);
Expand All @@ -170,8 +167,8 @@ private void handleRetainedLocal(VariableElement var, Expression rhs) {
}

private void rewriteVolatileLoad(Expression node) {
IVariableBinding var = TreeUtil.getVariableBinding(node);
if (var != null && BindingUtil.isVolatile(var) && !TranslationUtil.isAssigned(node)) {
VariableElement var = TreeUtil.getVariableElement(node);
if (var != null && ElementUtil.isVolatile(var) && !TranslationUtil.isAssigned(node)) {
TypeMirror type = node.getTypeMirror();
TypeMirror idType = typeEnv.getIdTypeMirror();
TypeMirror declaredType = type.getKind().isPrimitive() ? type : idType;
Expand All @@ -186,14 +183,14 @@ private void rewriteVolatileLoad(Expression node) {
}

private String getAssignmentFunctionName(
Assignment node, IVariableBinding var, boolean isRetainedWith) {
if (!var.isField() || var.isEnumConstant()) {
Assignment node, VariableElement var, boolean isRetainedWith) {
if (!ElementUtil.isField(var)) {
return null;
}
ITypeBinding type = var.getType();
boolean isPrimitive = type.isPrimitive();
boolean isStrong = !isPrimitive && !BindingUtil.isWeakReference(var);
boolean isVolatile = BindingUtil.isVolatile(var);
TypeMirror type = var.asType();
boolean isPrimitive = type.getKind().isPrimitive();
boolean isStrong = !isPrimitive && !ElementUtil.isWeakReference(var);
boolean isVolatile = ElementUtil.isVolatile(var);

if (isRetainedWith) {
return isVolatile ? "JreVolatileRetainedWithAssign" : "JreRetainedWithAssign";
Expand All @@ -216,7 +213,8 @@ private String getAssignmentFunctionName(
}

if (isVolatile) {
return "JreAssignVolatile" + (isPrimitive ? NameTable.capitalize(type.getName()) : "Id");
return "JreAssignVolatile"
+ (isPrimitive ? NameTable.capitalize(TypeUtil.getName(type)) : "Id");
}
return null;
}
Expand All @@ -225,16 +223,16 @@ private String getAssignmentFunctionName(
private int rwCount = 0;

// Gets the target object for a call to the RetainedWith wrapper.
private Expression getRetainedWithTarget(Assignment node, IVariableBinding var) {
private Expression getRetainedWithTarget(Assignment node, VariableElement var) {
Expression lhs = node.getLeftHandSide();
if (!(lhs instanceof FieldAccess)) {
return new ThisExpression(var.getDeclaringClass());
return new ThisExpression(ElementUtil.getDeclaringClass(var).asType());
}
// To avoid duplicating the target expression we must save the result to a local variable.
FieldAccess fieldAccess = (FieldAccess) lhs;
Expression target = fieldAccess.getExpression();
GeneratedVariableBinding targetVar = new GeneratedVariableBinding(
"__rw$" + rwCount++, 0, target.getTypeBinding(), false, false, null, null);
VariableElement targetVar = GeneratedVariableElement.newLocalVar(
"__rw$" + rwCount++, target.getTypeMirror(), null);
TreeUtil.asStatementList(TreeUtil.getOwningStatement(lhs))
.add(0, new VariableDeclarationStatement(targetVar, null));
fieldAccess.setExpression(new SimpleName(targetVar));
Expand All @@ -246,12 +244,12 @@ private Expression getRetainedWithTarget(Assignment node, IVariableBinding var)
}

private void rewriteRegularAssignment(Assignment node) {
IVariableBinding var = TreeUtil.getVariableBinding(node.getLeftHandSide());
VariableElement var = TreeUtil.getVariableElement(node.getLeftHandSide());
if (var == null) {
return;
}
handleRetainedLocal(BindingConverter.getVariableElement(var), node.getRightHandSide());
boolean isRetainedWith = BindingUtil.isRetainedWithField(var);
handleRetainedLocal(var, node.getRightHandSide());
boolean isRetainedWith = ElementUtil.isRetainedWithField(var);
String funcName = getAssignmentFunctionName(node, var, isRetainedWith);
if (funcName == null) {
return;
Expand All @@ -275,24 +273,23 @@ private void rewriteRegularAssignment(Assignment node) {
node.replaceWith(invocation);
}

private static String intOrLong(ITypeBinding type) {
switch (type.getBinaryName().charAt(0)) {
case 'I':
return "32";
case 'J':
return "64";
private static String intOrLong(TypeMirror type) {
switch (type.getKind()) {
case INT: return "32";
case LONG: return "64";
default:
throw new AssertionError("Type expected to be int or long but was: " + type.getName());
throw new AssertionError("Type expected to be int or long but was: " + type);
}
}

private static String getInfixFunction(InfixExpression.Operator op, ITypeBinding nodeType) {
private static String getInfixFunction(InfixExpression.Operator op, TypeMirror nodeType) {
switch (op) {
case REMAINDER:
if (BindingUtil.isFloatingPoint(nodeType)) {
return nodeType.getName().equals("float") ? "fmodf" : "fmod";
switch (nodeType.getKind()) {
case FLOAT: return "fmodf";
case DOUBLE: return "fmod";
default: return null;
}
return null;
case LEFT_SHIFT:
return "JreLShift" + intOrLong(nodeType);
case RIGHT_SHIFT_SIGNED:
Expand All @@ -305,14 +302,14 @@ private static String getInfixFunction(InfixExpression.Operator op, ITypeBinding
}

private static boolean isVolatile(Expression varNode) {
IVariableBinding var = TreeUtil.getVariableBinding(varNode);
return var != null && BindingUtil.isVolatile(var);
VariableElement var = TreeUtil.getVariableElement(varNode);
return var != null && ElementUtil.isVolatile(var);
}

private static boolean shouldRewriteCompoundAssign(Assignment node) {
Expression lhs = node.getLeftHandSide();
ITypeBinding lhsType = lhs.getTypeBinding();
ITypeBinding rhsType = node.getRightHandSide().getTypeBinding();
TypeMirror lhsType = lhs.getTypeMirror();
TypeMirror rhsType = node.getRightHandSide().getTypeMirror();
switch (node.getOperator()) {
case LEFT_SHIFT_ASSIGN:
case RIGHT_SHIFT_SIGNED_ASSIGN:
Expand All @@ -323,8 +320,8 @@ private static boolean shouldRewriteCompoundAssign(Assignment node) {
case TIMES_ASSIGN:
case DIVIDE_ASSIGN:
case REMAINDER_ASSIGN:
return isVolatile(lhs) || BindingUtil.isFloatingPoint(lhsType)
|| BindingUtil.isFloatingPoint(rhsType);
return isVolatile(lhs) || TypeUtil.isFloatingPoint(lhsType)
|| TypeUtil.isFloatingPoint(rhsType);
default:
return isVolatile(lhs);
}
Expand All @@ -351,15 +348,15 @@ private static String getPromotionSuffix(Assignment node) {
if (!needsPromotionSuffix(node.getOperator())) {
return "";
}
char lhs = node.getLeftHandSide().getTypeBinding().getBinaryName().charAt(0);
char rhs = node.getRightHandSide().getTypeBinding().getBinaryName().charAt(0);
if (lhs == 'D' || rhs == 'D') {
TypeKind lhsKind = node.getLeftHandSide().getTypeMirror().getKind();
TypeKind rhsKind = node.getRightHandSide().getTypeMirror().getKind();
if (lhsKind == TypeKind.DOUBLE || rhsKind == TypeKind.DOUBLE) {
return "D";
}
if (lhs == 'F' || rhs == 'F') {
if (lhsKind == TypeKind.FLOAT || rhsKind == TypeKind.FLOAT) {
return "F";
}
if (lhs == 'J' || rhs == 'J') {
if (lhsKind == TypeKind.LONG || rhsKind == TypeKind.LONG) {
return "J";
}
return "I";
Expand Down Expand Up @@ -399,12 +396,12 @@ private void rewriteStringConcatenation(InfixExpression node) {
TreeUtil.moveList(childOperands, operands);

operands = coalesceStringLiterals(operands);
if (operands.size() == 1 && typeEnv.isStringType(operands.get(0).getTypeBinding())) {
if (operands.size() == 1 && typeEnv.isStringType(operands.get(0).getTypeMirror())) {
node.replaceWith(operands.get(0));
return;
}

ITypeBinding stringType = typeEnv.resolveIOSType("NSString");
TypeMirror stringType = typeEnv.resolveJavaTypeMirror("java.lang.String");
FunctionElement element = new FunctionElement("JreStrcat", stringType, null)
.addParameters(typeEnv.getPointerType(typeEnv.resolveJavaTypeMirror("char")))
.setIsVarargs(true);
Expand All @@ -417,7 +414,7 @@ private void rewriteStringConcatenation(InfixExpression node) {

private List<Expression> getStringAppendOperands(Assignment node) {
Expression rhs = node.getRightHandSide();
if (rhs instanceof InfixExpression && typeEnv.isStringType(rhs.getTypeBinding())) {
if (rhs instanceof InfixExpression && typeEnv.isStringType(rhs.getTypeMirror())) {
InfixExpression infixExpr = (InfixExpression) rhs;
if (infixExpr.getOperator() == InfixExpression.Operator.PLUS) {
List<Expression> operands = infixExpr.getOperands();
Expand Down Expand Up @@ -506,9 +503,9 @@ private static String getLiteralStringValue(Expression expr) {
* the primitives.
*/
private char getStringConcatenationTypeCharacter(Expression operand) {
ITypeBinding operandType = operand.getTypeBinding();
if (operandType.isPrimitive()) {
return operandType.getBinaryName().charAt(0);
TypeMirror operandType = operand.getTypeMirror();
if (operandType.getKind().isPrimitive()) {
return TypeUtil.getBinaryName(operandType).charAt(0);
} else if (typeEnv.isStringType(operandType)) {
return '$';
} else {
Expand Down
Expand Up @@ -421,7 +421,7 @@ public boolean visit(SimpleName node) {
Expression path = null;
if (ElementUtil.isInstanceVar(var)) {
path = getPathForField(var);
} else if (!ElementUtil.isField(var)) {
} else if (!var.getKind().isField()) {
path = getPathForLocalVar(var);
}
if (path != null) {
Expand Down
Expand Up @@ -233,7 +233,7 @@ public void endVisit(FieldDeclaration node) {
public boolean visit(QualifiedName node) {
VariableElement var = TreeUtil.getVariableElement(node);
Expression qualifier = node.getQualifier();
if (var != null && ElementUtil.isField(var) && TreeUtil.getVariableElement(qualifier) != null) {
if (var != null && var.getKind().isField() && TreeUtil.getVariableElement(qualifier) != null) {
// FieldAccess nodes are more easily mutated than QualifiedName.
FieldAccess fieldAccess = new FieldAccess(var, TreeUtil.remove(qualifier));
node.replaceWith(fieldAccess);
Expand Down
Expand Up @@ -300,7 +300,11 @@ public static boolean isVariable(Element element) {
}

public static boolean isField(Element element) {
return element.getKind().isField();
return element.getKind() == ElementKind.FIELD;
}

public static boolean isLocalVariable(Element element) {
return element.getKind() == ElementKind.LOCAL_VARIABLE;
}

public static boolean isMethod(Element element) {
Expand Down
Expand Up @@ -373,7 +373,7 @@ public String getVariableShortName(IVariableBinding var) {

public String getVariableShortName(VariableElement var) {
String baseName = getVariableBaseName(var);
if (ElementUtil.isField(var) && !ElementUtil.isGlobalVar(var)) {
if (var.getKind().isField() && !ElementUtil.isGlobalVar(var)) {
return baseName + '_';
}
return baseName;
Expand Down
Expand Up @@ -95,6 +95,11 @@ public static boolean isArray(TypeMirror t) {
return t.getKind() == TypeKind.ARRAY;
}

public static boolean isFloatingPoint(TypeMirror t) {
TypeKind kind = t.getKind();
return kind == TypeKind.FLOAT || kind == TypeKind.DOUBLE;
}

// Ugly, but we can't have it actually implement IntersectionType or return TypeKind.INTERSECTION
// until Java 8.
public static boolean isIntersection(TypeMirror t) {
Expand Down Expand Up @@ -371,7 +376,7 @@ public String getSignatureName(TypeMirror t) {
/**
* Returns the binary name for a primitive or void type.
*/
public String getBinaryName(TypeMirror t) {
public static String getBinaryName(TypeMirror t) {
switch (t.getKind()) {
case BOOLEAN: return "Z";
case BYTE: return "B";
Expand Down

0 comments on commit 6ff9222

Please sign in to comment.