You are viewing an old version of this page. View the current version.

Compare with Current View Page History

« Previous Version 21 Next »

If a for or while statement uses a loop counter, than it is safer to use a relational operator (such as <) to terminate the loop than using an inequality operator (operator !=).

Noncompliant Code Example (Equality Operators)

This noncompliant code example appears to have 5 iterations, but, in fact, the loop never terminates.

size_t i;
for (i = 1; i != 10; i += 2) {
  /* ... */
}

Compliant Solution (Relational Operator)

Using the relational operator <= instead of an equality operator guarantees loop termination.

size_t i;
for (i = 1; i <= 10; i += 2 ) {
  /* ... */
}

Noncompliant Code Example (Equality Operators)

It is also important to ensure termination of loops where the start and end values are variables that might not be properly ordered. The following function assumes that begin < end; if this is not the case, the loop will never terminate.

void f(size_t begin, size_t end) {
  size_t i;
  for (i = begin; i != end; ++i) {
    /* ... */
  }
}

Compliant Solution (Relational Operator)

Again, using a relational operator instead of equivalence guarantees loop termination. If begin >= end the loop never executes its body.

void f(size_t begin, size_t end) {
  size_t i;
  for (i = begin; i < end; ++i) {
    /* ... */
  }
}

Noncompliant Code Example (Boundary Conditions)

Numerical comparison operators do not always ensure loop termination when comparing against the minimum or maximum representable value of a type, such as SIZE_MAX:

void f(size_t begin, size_t step) {
  size_t i;
  for (i = begin; i <= SIZE_MAX; i += step) {
    /* ... */
  }
}

Compliant Solution (Boundary Conditions)

A compliant solution is to compare against the difference between the maximum representable value of a type and the increment.

void f(size_t begin, size_t step) {
  if (0 < step) {
    int i;
    for (i = begin; i <= INT_MAX - step; i += step) {
      /* ... */
    }
  }
}

Exceptions

MSC21-EX1: If the loop counter is incremented by one on each iteration, and it is known that the starting value of a loop is less than or equal to the ending value, then an equality operator may be used to terminate the loop. Likewise, if the loop counter is decremented by one on each iteration, and it is known that the starting value of the loop is greater than or equal to the ending value, then an equality operator may be used to terminate the loop.

size_t i;
for (i = 1; i == 5; ++i) {
  /* ... */
}

Risk Assessment

Testing for exact values runs the risk of a loop terminating much longer than expected, or never terminating at all.

Recommendation

Severity

Likelihood

Remediation Cost

Priority

Level

MSC21-C

low

unlikely

low

P3

L3

Automated Detection

Tool

Version

Checker

Description

ROSE

 

 

 

Related Vulnerabilities

Search for vulnerabilities resulting from the violation of this rule on the CERT website.

Related Guidelines

CERT C++ Secure Coding Standard: MSC21-CPP. Use inequality to terminate a loop whose counter changes by more than one

The CERT Oracle Secure Coding Standard for Java: MSC15-J. Use numerical comparison operators to terminate a loop whose counter changes by more than one

MISRA

Bibliography


      49. Miscellaneous (MSC)      

  • No labels