...
This compliant solution performs a precondition test of the operands of the addition to ensure no overflow occurs, assuming two's complement representation.:
Code Block | ||||
---|---|---|---|---|
| ||||
signed int si1, si2, sum; /* Initialize si1 and si2 */ if ( ((si1^si2) | (((si1^(~(si1^si2) & INT_MIN)) + si2)^si2)) >= 0) { /* Handle error condition */ } else { sum = si1 + si2; } |
...
This compliant solution tests the suspect addition operation to ensure no overflow occurs regardless of representation.:
Code Block | ||||
---|---|---|---|---|
| ||||
signed int si1, si2, sum; /* Initialize si1 and si2 */ if (((si2>0) && (si1 > (INT_MAX-si2))) || ((si2<0) && (si1 < (INT_MIN-si2)))) { /* Handle error condition */ } else { sum = si1 + si2; } |
...
This compliant solution tests the operands of the subtraction to guarantee there is no possibility of signed overflow, presuming two's complement representation.:
Code Block | ||||
---|---|---|---|---|
| ||||
signed int si1, si2, result; /* Initialize si1 and si2 */ if (((si1^si2) & (((si1 ^ ((si1^si2) & (1 << (sizeof(int)*CHAR_BIT-1))))-si2)^si2)) < 0) { /* Handle error condition */ } else { result = si1 - si2; } |
...
This compliant solution tests the operands of the subtraction to guarantee there is no possibility of signed overflow, regardless of representation.:
Code Block | ||||
---|---|---|---|---|
| ||||
signed int si1, si2, result; /* Initialize si1 and si2 */ if ((si2 > 0 && si1 < INT_MIN + si2) || (si2 < 0 && si1 > INT_MAX + si2)) { /* Handle error condition */ } else { result = si1 - si2; } |
...
This compliant solution guarantees there is no possibility of signed overflow on systems where long long
is at least twice the size of int
.:
Code Block | ||||
---|---|---|---|---|
| ||||
signed int si1, si2, result; /* Initialize si1 and si2 */ static_assert( sizeof(long long) >= 2 * sizeof(int), "Unable to detect overflow after multiplication" ); signed long long tmp = (signed long long)si1 * (signed long long)si2; /* * If the product cannot be represented as a 32-bit integer, * handle as an error condition. */ if ( (tmp > INT_MAX) || (tmp < INT_MIN) ) { /* Handle error condition */ } else { result = (int)tmp; } |
...
On systems where this relationship does not exist, the following compliant solution may be used to ensure signed overflow does not occur.:
Code Block | ||||
---|---|---|---|---|
| ||||
signed int si1, si2, result; /* Initialize si1 and si2 */ if (si1 > 0){ /* si1 is positive */ if (si2 > 0) { /* si1 and si2 are positive */ if (si1 > (INT_MAX / si2)) { /* Handle error condition */ } } /* end if si1 and si2 are positive */ else { /* si1 positive, si2 non-positive */ if (si2 < (INT_MIN / si1)) { /* Handle error condition */ } } /* si1 positive, si2 non-positive */ } /* end if si1 is positive */ else { /* si1 is non-positive */ if (si2 > 0) { /* si1 is non-positive, si2 is positive */ if (si1 < (INT_MIN / si2)) { /* Handle error condition */ } } /* end if si1 is non-positive, si2 is positive */ else { /* si1 and si2 are non-positive */ if ( (si1 != 0) && (si2 < (INT_MAX / si1))) { /* Handle error condition */ } } /* end if si1 and si2 are non-positive */ } /* end if si1 is non-positive */ result = si1 * si2; |
...
This compliant solution guarantees there is no possibility of signed overflow or divide-by-zero errors.:
Code Block | ||||
---|---|---|---|---|
| ||||
signed long sl1, sl2, result; /* Initialize sl1 and sl2 */ if ( (sl2 == 0) || ( (sl1 == LONG_MIN) && (sl2 == -1) ) ) { /* Handle error condition */ } else { result = sl1 / sl2; } |
...
This compliant solution tests the modulo operand to guarantee there is no possibility of a divide-by-zero error or an (internal) overflow error.:
Code Block | ||||
---|---|---|---|---|
| ||||
signed long sl1, sl2, result; /* Initialize sl1 and sl2 */ if ( (sl2 == 0 ) || ( (sl1 == LONG_MIN) && (sl2 == -1) ) ) { /* Handle error condition */ } else { result = sl1 % sl2; } |
...
This compliant solution is based on the fact that both the division and modulo operators truncate toward zero0, as specified in Section section 6.5.5, footnote 105, of the C Standard [ISO/IEC 9899:2011]. This guarantees that
...
Furthermore, it guarantees that the minimum signed value modulo −1 yields 0.:
Code Block | ||||
---|---|---|---|---|
| ||||
signed long sl1, sl2, result; /* Initialize sl1 and sl2 */ if (sl2 == 0) { /* Handle error condition */ } else { if ((sl2 < 0) && (sl2 != LONG_MIN)) { sl2 = -sl2; } result = sl1 % sl2; } |
...
This noncompliant code example can result in a signed integer overflow during the unary negation of the signed operand si1
.:
Code Block | ||||
---|---|---|---|---|
| ||||
signed int si1, result; /* Initialize si1 */ result = -si1; |
...
This compliant solution tests the suspect negation operation to guarantee there is no possibility of signed overflow.:
Code Block | ||||
---|---|---|---|---|
| ||||
signed int si1, result; /* Initialize si1 */ if (si1 == INT_MIN) { /* Handle error condition */ } else result = -si1; } |
...
This noncompliant code example can result in signed integer overflow.:
Code Block | ||||
---|---|---|---|---|
| ||||
int si1, si2, sresult; /* Initialize si1 and si2 */ sresult = si1 << si2; |
...
This compliant solution eliminates the possibility of overflow resulting from a left-shift operation.:
Code Block | ||||
---|---|---|---|---|
| ||||
int si1, si2, sresult; /* Initialize si1 and si2 */ if ( (si1 < 0) || (si2 < 0) || (si2 >= sizeof(int)*CHAR_BIT) || (si1 > (INT_MAX >> si2)) ) { /* Handle error condition */ } else { sresult = si1 << si2; } |
...
This noncompliant code example using atomic integers can result in unexpected signed integer overflow.:
Code Block | ||||
---|---|---|---|---|
| ||||
atomic_int i; int si1; /* Initialize i, si1 */ atomic_fetch_add(&i, si1); |
...
This compliant solution tests the operands to guarantee there is no possibility of signed overflow. It loads the value stored in the atomic integer and tests for possible overflow before performing the addition.:
Code Block | ||||
---|---|---|---|---|
| ||||
atomic_int i; int si1; /* Initialize si1, i */ int si2 = atomic_load(&i); if (((si2>0) && (si1 > (INT_MAX-si2))) || ((si2<0) && (si1 < (INT_MIN-si2)))) { /* Handle error condition */ } else { atomic_fetch_add(&i, si1); } |
...
Tool | Version | Checker | Description | ||||||
---|---|---|---|---|---|---|---|---|---|
Coverity | 6.5 | TAINTED_STATIC | Fully Implemented. | ||||||
Fortify SCA | 5.0 | Can detect violations of this rule with CERT C Rule Pack. Specifically, it checks to ensure that the operand of a unary negation | |||||||
| 43 D | Partially implemented. | |||||||
PRQA QA-C |
| 0278 | Fully implemented. |
Related Vulnerabilities
Search for vulnerabilities resulting from the violation of this rule on the CERT website.
...