Class InnerAssignmentCheck

  • All Implemented Interfaces:
    Configurable, Contextualizable

    public class InnerAssignmentCheck
    extends AbstractCheck

    Checks for assignments in subexpressions, such as in String s = Integer.toString(i = 2);.

    Rationale: With the exception of for iterators, all assignments should occur in their own top-level statement to increase readability. With inner assignments like the above it is difficult to see all places where a variable is set.

    • Field Detail

      • MSG_KEY

        public static final java.lang.String MSG_KEY
        A key is pointing to the warning message text in "messages.properties" file.
        See Also:
        Constant Field Values
      • ALLOWED_ASSIGNMENT_CONTEXT

        private static final int[][] ALLOWED_ASSIGNMENT_CONTEXT
        List of allowed AST types from an assignment AST node towards the root.
      • CONTROL_CONTEXT

        private static final int[][] CONTROL_CONTEXT
        List of allowed AST types from an assignment AST node towards the root.
      • ALLOWED_ASSIGNMENT_IN_COMPARISON_CONTEXT

        private static final int[][] ALLOWED_ASSIGNMENT_IN_COMPARISON_CONTEXT
        List of allowed AST types from a comparison node (above an assignment) towards the root.
      • COMPARISON_TYPES

        private static final int[] COMPARISON_TYPES
        The token types that identify comparison operators.
    • Constructor Detail

      • InnerAssignmentCheck

        public InnerAssignmentCheck()
    • Method Detail

      • getDefaultTokens

        public int[] getDefaultTokens()
        Description copied from class: AbstractCheck
        Returns the default token a check is interested in. Only used if the configuration for a check does not define the tokens.
        Specified by:
        getDefaultTokens in class AbstractCheck
        Returns:
        the default tokens
        See Also:
        TokenTypes
      • getAcceptableTokens

        public int[] getAcceptableTokens()
        Description copied from class: AbstractCheck
        The configurable token set. Used to protect Checks against malicious users who specify an unacceptable token set in the configuration file. The default implementation returns the check's default tokens.
        Specified by:
        getAcceptableTokens in class AbstractCheck
        Returns:
        the token set this check is designed for.
        See Also:
        TokenTypes
      • getRequiredTokens

        public int[] getRequiredTokens()
        Description copied from class: AbstractCheck
        The tokens that this check must be registered for.
        Specified by:
        getRequiredTokens in class AbstractCheck
        Returns:
        the token set this must be registered for.
        See Also:
        TokenTypes
      • isInNoBraceControlStatement

        private static boolean isInNoBraceControlStatement​(DetailAST ast)
        Determines if ast is in the body of a flow control statement without braces. An example of such a statement would be

         if (y < 0)
             x = y;
         

        This leads to the following AST structure:

         LITERAL_IF
             LPAREN
             EXPR // test
             RPAREN
             EXPR // body
             SEMI
         

        We need to ensure that ast is in the body and not in the test.

        Parameters:
        ast - an assignment operator AST
        Returns:
        whether ast is in the body of a flow control statement
      • isInWhileIdiom

        private static boolean isInWhileIdiom​(DetailAST ast)
        Tests whether the given AST is used in the "assignment in while" idiom.
         String line;
         while ((line = bufferedReader.readLine()) != null) {
            // process the line
         }
         
        Assignment inside a condition is not a problem here, as the assignment is surrounded by an extra pair of parentheses. The comparison is != null and there is no chance that intention was to write line == reader.readLine().
        Parameters:
        ast - assignment AST
        Returns:
        whether the context of the assignment AST indicates the idiom
      • isComparison

        private static boolean isComparison​(DetailAST ast)
        Checks if an AST is a comparison operator.
        Parameters:
        ast - the AST to check
        Returns:
        true iff ast is a comparison operator.
      • isInContext

        private static boolean isInContext​(DetailAST ast,
                                           int[]... contextSet)
        Tests whether the provided AST is in one of the given contexts.
        Parameters:
        ast - the AST from which to start walking towards root
        contextSet - the contexts to test against.
        Returns:
        whether the parents nodes of ast match one of the allowed type paths.