예제 #1
0
    @Override
    public boolean visitIfExpression(@NotNull UIfExpression node) {
      UExpression condition = node.getCondition();
      UExpression body = node.getThenBranch();
      UElement elseBody = node.getElseBranch();
      condition.accept(this);

      if (body != null) {
        boolean wasReachable = mReachable;
        body.accept(this);
        mReachable = wasReachable;
      }
      if (elseBody != null) {
        boolean wasReachable = mReachable;
        elseBody.accept(this);
        mReachable = wasReachable;
      }

      return false;
    }
예제 #2
0
  private static int calculateValue(UastAndroidContext context, UExpression expression) {
    // This function assumes that the only inputs to the expression are static integer
    // flags that combined via bitwise operands.
    if (UastLiteralUtils.isIntegralLiteral(expression)) {
      return (int) UastLiteralUtils.getLongValue((ULiteralExpression) expression);
    }

    if (expression instanceof UResolvable) {
      UDeclaration resolvedNode = ((UResolvable) expression).resolve(context);
      if (resolvedNode instanceof UVariable) {
        UExpression initializer = ((UVariable) resolvedNode).getInitializer();
        if (initializer != null) {
          Object value = initializer.evaluate();
          if (value instanceof Integer) {
            return (Integer) value;
          }
        }
      }
    }

    if (expression instanceof UBinaryExpression) {
      UBinaryExpression binaryExpression = (UBinaryExpression) expression;
      UastBinaryOperator operator = binaryExpression.getOperator();
      int leftValue = calculateValue(context, binaryExpression.getLeftOperand());
      int rightValue = calculateValue(context, binaryExpression.getRightOperand());

      if (operator == UastBinaryOperator.BITWISE_OR) {
        return leftValue | rightValue;
      }
      if (operator == UastBinaryOperator.BITWISE_AND) {
        return leftValue & rightValue;
      }
      if (operator == UastBinaryOperator.BITWISE_XOR) {
        return leftValue ^ rightValue;
      }
    }

    return 0;
  }
예제 #3
0
  @Override
  public void visitCall(UastAndroidContext context, UCallExpression node) {
    String lhs = getLhs(node);
    if (lhs == null) {
      return;
    }

    UFunction method = UastUtils.getContainingFunction(node);
    if (method == null) {
      return;
    } else if (method != mLastMethod) {
      mIds = Maps.newHashMap();
      mLhs = Maps.newHashMap();
      mCallOperands = Maps.newHashMap();
      mLastMethod = method;
    }

    UElement parent = node.getParent();
    String callOperand = "";
    if (parent instanceof UQualifiedExpression) {
      callOperand = ((UQualifiedExpression) parent).getReceiver().renderString();
    }

    UExpression first = node.getValueArguments().get(0);
    if (first instanceof UQualifiedExpression) {
      UQualifiedExpression select = (UQualifiedExpression) first;
      String id = select.getSelector().renderString();
      UExpression operand = select.getReceiver();
      if (operand instanceof UQualifiedExpression) {
        UQualifiedExpression type = (UQualifiedExpression) operand;
        if (type.getSelector().renderString().equals(RESOURCE_CLZ_ID)) {
          if (mIds.containsKey(id)) {
            if (lhs.equals(mLhs.get(id))) {
              return;
            }
            if (!callOperand.equals(mCallOperands.get(id))) {
              return;
            }
            UCallExpression earlierCall = mIds.get(id);
            if (!isReachableFrom(method, earlierCall, node)) {
              return;
            }
            Location location = context.getLocation(node);
            Location secondary = context.getLocation(earlierCall);
            if (location != null && secondary != null) {
              secondary.setMessage("First usage here");
              location.setSecondary(secondary);
              context.report(
                  ISSUE,
                  node,
                  location,
                  String.format(
                      "The id `%1$s` has already been looked up in this method; possible "
                          + "cut & paste error?",
                      first.toString()));
            }
          } else {
            mIds.put(id, node);
            mLhs.put(id, lhs);
            mCallOperands.put(id, callOperand);
          }
        }
      }
    }
  }