OCLint

Basic

BitwiseOperatorInConditional

Since: 0.6

Name: bitwise operator in conditional

Checks for bitwise operations in conditionals. Although being written on purpose in some rare cases, bitwise operations are considered to be too “smart”. Smart code is not easy to understand.

This rule is defined by the following class: oclint-rules/rules/basic/BitwiseOperatorInConditionalRule.cpp

Example:

void example(int a, int b)
{
    if (a | b)
    {
    }
    if (a & b)
    {
    }
}

BrokenNullCheck

Since: 0.7

Name: broken null check

The broken null check itself will crash the program.

This rule is defined by the following class: oclint-rules/rules/basic/BrokenNullCheckRule.cpp

Example:

void m(A *a, B *b)
{
    if (a != NULL || a->bar(b))
    {
    }

    if (a == NULL && a->bar(b))
    {
    }
}

BrokenNilCheck

Since: 0.7

Name: broken nil check

The broken nil check in Objective-C in some cases returns just the opposite result.

This rule is defined by the following class: oclint-rules/rules/basic/BrokenNullCheckRule.cpp

Example:

+ (void)compare:(A *)obj1 withOther:(A *)obj2
{
    if (obj1 || [obj1 isEqualTo:obj2])
    {
    }

    if (!obj1 && ![obj1 isEqualTo:obj2])
    {
    }
}

BrokenOddnessCheck

Since: 0.6

Name: broken oddness check

Checking oddness by x % 2 == 1 won’t work for negative numbers. Use x & 1 == 1, or x % 2 != 0 instead.

This rule is defined by the following class: oclint-rules/rules/basic/BrokenOddnessCheckRule.cpp

Example:

void example()
{
    if (x % 2 == 1)         // violation
    {
    }

    if (foo() % 2 == 1)     // violation
    {
    }
}

CollapsibleIfStatements

Since: 0.6

Name: collapsible if statements

This rule detects instances where the conditions of two consecutive if statements can be combined into one in order to increase code cleanness and readability.

This rule is defined by the following class: oclint-rules/rules/basic/CollapsibleIfStatementsRule.cpp

Example:

void example(bool x, bool y)
{
    if (x)              // these two if statements can be
    {
        if (y)          // combined to if (x && y)
        {
            foo();
        }
    }
}

ConstantConditionalOperator

Since: 0.6

Name: constant conditional operator

conditional operator whose conditionals are always true or always false are confusing.

This rule is defined by the following class: oclint-rules/rules/basic/ConstantConditionalOperatorRule.cpp

Example:

void example()
{
    int a = 1 == 1 ? 1 : 0;     // 1 == 1 is actually always true
}

ConstantIfExpression

Since: 0.2

Name: constant if expression

if statements whose conditionals are always true or always false are confusing.

This rule is defined by the following class: oclint-rules/rules/basic/ConstantIfExpressionRule.cpp

Example:

void example()
{
    if (true)       // always true
    {
        foo();
    }
    if (1 == 0)     // always false
    {
        bar();
    }
}

DeadCode

Since: 0.4

Name: dead code

Code after return, break, continue, and throw statements is unreachable and will never be executed.

This rule is defined by the following class: oclint-rules/rules/basic/DeadCodeRule.cpp

Example:

void example(id collection)
{
    for (id it in collection)
    {
        continue;
        int i1;                 // dead code
    }
    return;
    int i2;                     // dead code
}

DoubleNegative

Since: 0.6

Name: double negative

There is no point in using a double negative, it is always positive.

This rule is defined by the following class: oclint-rules/rules/basic/DoubleNegativeRule.cpp

Example:

void example()
{
    int b1 = !!1;
    int b2 = ~~1;
}

ForLoopShouldBeWhileLoop

Since: 0.6

Name: for loop should be while loop

Under certain circumstances, some for loops can be simplified to while loops to make code more concise.

This rule is defined by the following class: oclint-rules/rules/basic/ForLoopShouldBeWhileLoopRule.cpp

Example:

void example(int a)
{
    for (; a < 100;)
    {
        foo(a);
    }
}

GotoStatement

Since: 0.6

Name: goto statement

“Go To Statement Considered Harmful”

This rule is defined by the following class: oclint-rules/rules/basic/GotoStatementRule.cpp

Example:

void example()
{
    A:
        a();
    goto A;     // Considered Harmful
}

References:

Edsger Dijkstra (March 1968). “Go To Statement Considered Harmful”. Communications of the ACM (PDF) 11 (3): 147–148. doi:10.1145/362929.362947.

JumbledIncrementer

Since: 0.7

Name: jumbled incrementer

Jumbled incrementers are usually typos. If it’s done on purpose, it’s very confusing for code readers.

This rule is defined by the following class: oclint-rules/rules/basic/JumbledIncrementerRule.cpp

Example:

void aMethod(int a) {
    for (int i = 0; i < a; i++) {
        for (int j = 0; j < a; i++) { // references both 'i' and 'j'
        }
    }
}

MisplacedNullCheck

Since: 0.7

Name: misplaced null check

The null check is misplaced. In C and C++, sending a message to a null pointer could crash the program. When null is misplaced, either the check is useless or it’s incorrect.

This rule is defined by the following class: oclint-rules/rules/basic/MisplacedNullCheckRule.cpp

Example:

void m(A *a, B *b)
{
    if (a->bar(b) && a != NULL) // violation
    {
    }

    if (a->bar(b) || !a)        // violation
    {
    }
}

MisplacedNilCheck

Since: 0.7

Name: misplaced nil check

The nil check is misplaced. In Objective-C, sending a message to a nil pointer simply does nothing. But code readers may be confused about the misplaced nil check.

This rule is defined by the following class: oclint-rules/rules/basic/MisplacedNullCheckRule.cpp

Example:

+ (void)compare:(A *)obj1 withOther:(A *)obj2
{
    if ([obj1 isEqualTo:obj2] && obj1)
    {
    }

    if (![obj1 isEqualTo:obj2] || obj1 == nil)
    {
    }
}

MultipleUnaryOperator

Since: 0.6

Name: multiple unary operator

Multiple unary operator can always be confusing and should be simplified.

This rule is defined by the following class: oclint-rules/rules/basic/MultipleUnaryOperatorRule.cpp

Example:

void example()
{
    int b = -(+(!(~1)));
}

ReturnFromFinallyBlock

Since: 0.6

Name: return from finally block

Returning from a finally block is not recommended.

This rule is defined by the following class: oclint-rules/rules/basic/ReturnFromFinallyBlockRule.cpp

Example:

void example()
{
    @try
    {
        foo();
    }
    @catch(id ex)
    {
        bar();
    }
    @finally
    {
        return;         // this can discard exceptions.
    }
}

ThrowExceptionFromFinallyBlock

Since: 0.6

Name: throw exception from finally block

Throwing exceptions within a finally block may mask other exceptions or code defects.

This rule is defined by the following class: oclint-rules/rules/basic/ThrowExceptionFromFinallyBlockRule.cpp

Example:

void example()
{
    @try {;}
    @catch(id ex) {;}
    @finally {
        id ex1;
        @throw ex1;                              // this throws an exception
        NSException *ex2 = [NSException new];
        [ex2 raise];                             // this throws an exception, too
    }
}