CWE-192, Integer Coercion Error, is an umbrella for flaws with the type casting, extension or truncation of primitive data types. The language quietly converts a number from one type to another, and the value that comes out is not the value that went in.
It is relevant in C, C++, Java and C#, the platforms MITRE lists.
How it happens
Several specific errors fall under this heading. Signed to unsigned conversion, unsigned to signed conversion, sign extension and truncation are all examples. MITRE notes that, for the most part, these errors on their own lead to availability and integrity problems, but in some circumstances they result in more complicated flaws such as buffer overflows.
A common shape:
// Vulnerable: return value is int, error is -1, but the caller stores it as unsigned
unsigned int n = read_length(fd); // -1 becomes 4294967295
char *buf = malloc(n);
// Fixed: keep the signed value until you have checked it
int r = read_length(fd);
if (r < 0) {
return -1;
}
size_t n = (size_t)r;
The record gives CVE-2022-2639 as an example: a chain where an integer coercion error prevented a return value from indicating an error, leading to an out of bounds write.
What an attacker gains
MITRE lists:
- Availability: infinite loops or crashes.
- Integrity, confidentiality and availability: execution of unauthorized code in some cases, through buffer overflow.
- Integrity: an incorrect value stored for the variable in question.
How to find it
MITRE says automated static analysis (SAST) can find some instances by modelling data flow. Turn on compiler warnings for sign conversion and narrowing, and treat them as errors on security sensitive code.
How to fix it
The record lists no mitigations, so these are general steps.
- Use one consistent type for sizes and lengths.
- Check the range before any conversion that could lose or reinterpret a value.
- Do not mix error codes and data in one return value without checking first.
- Enable the compiler's conversion warnings.
Quick check
Why is storing a function's -1 in an unsigned variable dangerous?
It becomes a huge positive number, so an error looks like a valid, very large size.