Search in sources :

Example 26 with MethodInvocationTree

use of com.sun.source.tree.MethodInvocationTree in project error-prone by google.

the class AbstractReturnValueIgnored method describe.

/**
   * Fixes the error by assigning the result of the call to the receiver reference, or deleting the
   * method call.
   */
public Description describe(MethodInvocationTree methodInvocationTree, VisitorState state) {
    // Find the root of the field access chain, i.e. a.intern().trim() ==> a.
    ExpressionTree identifierExpr = ASTHelpers.getRootAssignable(methodInvocationTree);
    String identifierStr = null;
    Type identifierType = null;
    if (identifierExpr != null) {
        identifierStr = identifierExpr.toString();
        if (identifierExpr instanceof JCIdent) {
            identifierType = ((JCIdent) identifierExpr).sym.type;
        } else if (identifierExpr instanceof JCFieldAccess) {
            identifierType = ((JCFieldAccess) identifierExpr).sym.type;
        } else {
            throw new IllegalStateException("Expected a JCIdent or a JCFieldAccess");
        }
    }
    Type returnType = ASTHelpers.getReturnType(((JCMethodInvocation) methodInvocationTree).getMethodSelect());
    Fix fix;
    if (identifierStr != null && !"this".equals(identifierStr) && returnType != null && state.getTypes().isAssignable(returnType, identifierType)) {
        // Fix by assigning the assigning the result of the call to the root receiver reference.
        fix = SuggestedFix.prefixWith(methodInvocationTree, identifierStr + " = ");
    } else {
        // Unclear what the programmer intended.  Delete since we don't know what else to do.
        Tree parent = state.getPath().getParentPath().getLeaf();
        fix = SuggestedFix.delete(parent);
    }
    return describeMatch(methodInvocationTree, fix);
}
Also used : Type(com.sun.tools.javac.code.Type) JCIdent(com.sun.tools.javac.tree.JCTree.JCIdent) Fix(com.google.errorprone.fixes.Fix) SuggestedFix(com.google.errorprone.fixes.SuggestedFix) JCFieldAccess(com.sun.tools.javac.tree.JCTree.JCFieldAccess) ExpressionTree(com.sun.source.tree.ExpressionTree) MethodInvocationTree(com.sun.source.tree.MethodInvocationTree) IdentifierTree(com.sun.source.tree.IdentifierTree) Tree(com.sun.source.tree.Tree) ExpressionTree(com.sun.source.tree.ExpressionTree) StatementTree(com.sun.source.tree.StatementTree)

Example 27 with MethodInvocationTree

use of com.sun.source.tree.MethodInvocationTree in project error-prone by google.

the class Matchers method receiverSameAsArgument.

/**
   * Matches when the receiver of an instance method is the same reference as a particular argument to the method.
   * For example, receiverSameAsArgument(1) would match {@code obj.method("", obj)}
   *
   * @param argNum The number of the argument to compare against (zero-based.
   */
public static Matcher<? super MethodInvocationTree> receiverSameAsArgument(final int argNum) {
    return new Matcher<MethodInvocationTree>() {

        @Override
        public boolean matches(MethodInvocationTree t, VisitorState state) {
            List<? extends ExpressionTree> args = t.getArguments();
            if (args.size() <= argNum) {
                return false;
            }
            ExpressionTree arg = args.get(argNum);
            JCExpression methodSelect = (JCExpression) t.getMethodSelect();
            if (methodSelect instanceof JCFieldAccess) {
                JCFieldAccess fieldAccess = (JCFieldAccess) methodSelect;
                return ASTHelpers.sameVariable(fieldAccess.getExpression(), arg);
            } else if (methodSelect instanceof JCIdent) {
                // A bare method call: "equals(foo)".  Receiver is implicitly "this".
                return "this".equals(arg.toString());
            }
            return false;
        }
    };
}
Also used : JCIdent(com.sun.tools.javac.tree.JCTree.JCIdent) JCExpression(com.sun.tools.javac.tree.JCTree.JCExpression) InstanceMethodMatcher(com.google.errorprone.matchers.method.MethodMatchers.InstanceMethodMatcher) AnyMethodMatcher(com.google.errorprone.matchers.method.MethodMatchers.AnyMethodMatcher) StaticMethodMatcher(com.google.errorprone.matchers.method.MethodMatchers.StaticMethodMatcher) ConstructorMatcher(com.google.errorprone.matchers.method.MethodMatchers.ConstructorMatcher) VisitorState(com.google.errorprone.VisitorState) JCFieldAccess(com.sun.tools.javac.tree.JCTree.JCFieldAccess) MethodInvocationTree(com.sun.source.tree.MethodInvocationTree) ExpressionTree(com.sun.source.tree.ExpressionTree)

Example 28 with MethodInvocationTree

use of com.sun.source.tree.MethodInvocationTree in project error-prone by google.

the class IsLoggableTagLength method matchMethodInvocation.

@Override
public Description matchMethodInvocation(MethodInvocationTree tree, VisitorState state) {
    if (!IS_LOGGABLE_CALL.matches(tree, state)) {
        return NO_MATCH;
    }
    ExpressionTree tagArg = tree.getArguments().get(0);
    // Check for constant value.
    String tagConstantValue = ASTHelpers.constValue(tagArg, String.class);
    if (tagConstantValue != null) {
        return isValidTag(tagConstantValue) ? NO_MATCH : describeMatch(tagArg);
    }
    // Check for class literal simple name (e.g. MyClass.class.getSimpleName().
    ExpressionTree tagExpr = tagArg;
    // If the tag argument is a final field, retrieve the initializer.
    if (kindIs(IDENTIFIER).matches(tagArg, state)) {
        VariableTree declaredField = findEnclosingIdentifier((IdentifierTree) tagArg, state);
        if (declaredField == null || !hasModifier(FINAL).matches(declaredField, state)) {
            return NO_MATCH;
        }
        tagExpr = declaredField.getInitializer();
    }
    if (GET_SIMPLE_NAME_CALL.matches(tagExpr, state) && RECEIVER_IS_CLASS_LITERAL.matches((MethodInvocationTree) tagExpr, state)) {
        String tagName = getSymbol(getReceiver(getReceiver(tagExpr))).getSimpleName().toString();
        return isValidTag(tagName) ? NO_MATCH : describeMatch(tagArg);
    }
    return NO_MATCH;
}
Also used : MethodInvocationTree(com.sun.source.tree.MethodInvocationTree) VariableTree(com.sun.source.tree.VariableTree) ExpressionTree(com.sun.source.tree.ExpressionTree)

Example 29 with MethodInvocationTree

use of com.sun.source.tree.MethodInvocationTree in project error-prone by google.

the class RestrictedApiChecker method matchMethodInvocation.

@Override
public Description matchMethodInvocation(MethodInvocationTree tree, VisitorState state) {
    RestrictedApi annotation = ASTHelpers.getAnnotation(tree, RestrictedApi.class);
    if (annotation != null) {
        return checkRestriction(annotation, tree, state);
    }
    MethodSymbol methSymbol = ASTHelpers.getSymbol(tree);
    if (methSymbol == null) {
        // This shouldn't happen, but has. (See b/33758055)
        return Description.NO_MATCH;
    }
    // Try each super method for @RestrictedApi
    Optional<MethodSymbol> superWithRestrictedApi = ASTHelpers.findSuperMethods(methSymbol, state.getTypes()).stream().filter((t) -> ASTHelpers.hasAnnotation(t, RestrictedApi.class, state)).findFirst();
    if (!superWithRestrictedApi.isPresent()) {
        return Description.NO_MATCH;
    }
    return checkRestriction(ASTHelpers.getAnnotation(superWithRestrictedApi.get(), RestrictedApi.class), tree, state);
}
Also used : RestrictedApi(com.google.errorprone.annotations.RestrictedApi) MethodSymbol(com.sun.tools.javac.code.Symbol.MethodSymbol) TypeElement(javax.lang.model.element.TypeElement) Suppressibility(com.google.errorprone.BugPattern.Suppressibility) NewClassTreeMatcher(com.google.errorprone.bugpatterns.BugChecker.NewClassTreeMatcher) ArrayList(java.util.ArrayList) MirroredTypesException(javax.lang.model.type.MirroredTypesException) VisitorState(com.google.errorprone.VisitorState) MethodInvocationTree(com.sun.source.tree.MethodInvocationTree) NewClassTree(com.sun.source.tree.NewClassTree) BugPattern(com.google.errorprone.BugPattern) Category(com.google.errorprone.BugPattern.Category) Matcher(com.google.errorprone.matchers.Matcher) Tree(com.sun.source.tree.Tree) JavacProcessingEnvironment(com.sun.tools.javac.processing.JavacProcessingEnvironment) Nullable(javax.annotation.Nullable) MethodInvocationTreeMatcher(com.google.errorprone.bugpatterns.BugChecker.MethodInvocationTreeMatcher) RestrictedApi(com.google.errorprone.annotations.RestrictedApi) JCCompilationUnit(com.sun.tools.javac.tree.JCTree.JCCompilationUnit) List(java.util.List) TypeMirror(javax.lang.model.type.TypeMirror) Matchers(com.google.errorprone.matchers.Matchers) Description(com.google.errorprone.matchers.Description) Annotation(java.lang.annotation.Annotation) Optional(java.util.Optional) Pattern(java.util.regex.Pattern) SeverityLevel(com.google.errorprone.BugPattern.SeverityLevel) ASTHelpers(com.google.errorprone.util.ASTHelpers) MethodSymbol(com.sun.tools.javac.code.Symbol.MethodSymbol)

Example 30 with MethodInvocationTree

use of com.sun.source.tree.MethodInvocationTree in project error-prone by google.

the class SizeGreaterThanOrEqualsZero method matchBinary.

@Override
public Description matchBinary(BinaryTree tree, VisitorState state) {
    // Easy stuff: needs to be a binary expression of the form foo >= 0 or 0 <= foo
    ExpressionType expressionType = isGreaterThanEqualToZero(tree);
    if (expressionType == ExpressionType.MISMATCH) {
        return Description.NO_MATCH;
    }
    ExpressionTree operand = expressionType == ExpressionType.GREATER_THAN_EQUAL ? tree.getLeftOperand() : tree.getRightOperand();
    if (operand instanceof MethodInvocationTree) {
        MethodInvocationTree callToSize = (MethodInvocationTree) operand;
        if (INSTANCE_METHOD_MATCHER.matches(callToSize, state)) {
            return provideReplacementForMethodInvocation(tree, callToSize, state, expressionType);
        } else if (STATIC_METHOD_MATCHER.matches(callToSize, state)) {
            return provideReplacementForStaticMethodInvocation(tree, callToSize, state, expressionType);
        }
    } else if (operand instanceof MemberSelectTree) {
        if (ARRAY_LENGTH_MATCHER.matches((MemberSelectTree) operand, state)) {
            return removeEqualsFromComparison(tree, state, expressionType);
        }
    }
    return Description.NO_MATCH;
}
Also used : MethodInvocationTree(com.sun.source.tree.MethodInvocationTree) MemberSelectTree(com.sun.source.tree.MemberSelectTree) ExpressionTree(com.sun.source.tree.ExpressionTree)

Aggregations

MethodInvocationTree (com.sun.source.tree.MethodInvocationTree)35 ExpressionTree (com.sun.source.tree.ExpressionTree)24 Tree (com.sun.source.tree.Tree)13 IdentifierTree (com.sun.source.tree.IdentifierTree)10 MemberSelectTree (com.sun.source.tree.MemberSelectTree)9 VariableTree (com.sun.source.tree.VariableTree)9 JCTree (com.sun.tools.javac.tree.JCTree)9 ExpressionStatementTree (com.sun.source.tree.ExpressionStatementTree)8 MethodTree (com.sun.source.tree.MethodTree)8 JCFieldAccess (com.sun.tools.javac.tree.JCTree.JCFieldAccess)8 VisitorState (com.google.errorprone.VisitorState)7 StatementTree (com.sun.source.tree.StatementTree)7 MethodSymbol (com.sun.tools.javac.code.Symbol.MethodSymbol)7 BinaryTree (com.sun.source.tree.BinaryTree)5 BlockTree (com.sun.source.tree.BlockTree)5 NewClassTree (com.sun.source.tree.NewClassTree)5 ReturnTree (com.sun.source.tree.ReturnTree)5 AssignmentTree (com.sun.source.tree.AssignmentTree)4 ClassTree (com.sun.source.tree.ClassTree)4 Description (com.google.errorprone.matchers.Description)3