CWE Glossary
- CWE-22: Path Traversal
- CWE-78: OS Command Injection
- CWE-79: Cross-Site Scripting
- CWE-89: SQL Injection
- CWE-90: LDAP Injection
- CWE-91: XML Injection
- CWE-94: Code Injection
- CWE-98: PHP File Inclusion
- CWE-113: HTTP Response Splitting
- CWE-119: Buffer Errors
- CWE-130: Improper Handling of Length Parameter Inconsistency
- CWE-193: Off-by-one Error
- CWE-200: Information Exposure
- CWE-211: Information Exposure Through Externally-Generated Error Message
- CWE-236: Improper Handling of Undefined Parameters
- CWE-276: Incorrect Default Permissions
- CWE-284: Improper Access Control
- CWE-285: Improper Authorization
- CWE-287: Improper Authentication
- CWE-297: Improper Validation of Certificate with Host Mismatch
- CWE-306: Missing Authentication for Critical Function
- CWE-312: Cleartext Storage of Sensitive Information
- CWE-345: Insufficient Verification of Data Authenticity
- CWE-352: Cross-Site Request Forgery
- CWE-384: Session Fixation
- CWE-427: Uncontrolled Search Path Element
- CWE-434: Unrestricted Upload of File with Dangerous Type
- CWE-476: NULL Pointer Dereference
- CWE-521: Weak Password Requirements
- CWE-601: Open Redirect
- CWE-611: Improper Restriction of XML External Entity Reference ('XXE')
- CWE-613: Insufficient Session Expiration
- CWE-618: Exposed Unsafe ActiveX Method
- CWE-671: Lack of Administrator Control over Security
- CWE-798: Use of Hard-coded Credentials
- CWE-799: Improper Control of Interaction Frequency
- CWE-822: Untrusted Pointer Dereference
- CWE-835: Infinite Loop
- CWE-918: Server-Side Request Forgery (SSRF)
- CWE-942: Overly Permissive Cross-domain Whitelist
CWE is a trademark of the MITRE Corporation.
Off-by-one Error [CWE-193]
Off-by-one Error occurs when a program uses an improper maximum or minimum value that is one more or one less than the proper value.
Created: February 25, 2013
Latest Update: December 15, 2020
Table of Content
- Description
- Potential impact
- Affected software
- Mitigations
- Severity and CVSS Scoring
- References
- Latest Related Security Advisories
Want to have an in-depth understanding of all modern aspects of Off-by-one Error [CWE-193]? Read carefully this article and bookmark it to get back later, we regularly update this page.
1. Description
An off-by-one condition is a logic error in size calculation when working with strings and arrays. It usually produces a boundary condition, which may lead to memory corruption.
Off-by-one errors are often a result of incorrect null-termination of string sequence, which usually starts at zero rather than one. This scenario typically arises when software performs loop iteration a number of times that is greater or less than expected.
When an off-by-one condition occurs, the program is able to read or write beyond the bounds of allocated memory, which can result in data corruption, application crash, or even lead to code execution.
The following example in C language uses a loop to read characters from an array:
- #include <stdio.h>
- #define MAX_CHARS 19
- int main ()
- {
- int x;
- int ite_loop = 0;
- char filename[MAX_CHARS] = "My mother loves me.";
- printf("Length of filename array: %d\n",strlen(filename));
- for (x = 0; x <= MAX_CHARS; x++) {
- printf("%c",filename[x]);
- ite_loop += 1;
- }
- printf("\nIterations: %d\n",ite_loop);
- return 0;
- }
However the exit loop condition "x <= MAX_CHARS"
is incorrectly defined; therefore the loop reads one byte beyond the bounds of the array. Consider the following example:
- #include <stdio.h>
- #define MAX_CHAR 19
- #define MAX_VALUE 30
- int main ()
- {
- int x;
- int ite_loop = 0;
- char filename[MAX_CHAR] = "My mother loves me.";
- printf("Length of filename array: %d\n",strlen(filename));
- for (x = 0; x <= MAX_VALUE; x++) {
- printf("%c",filename[x]);
- ite_loop += 1;
- }
- printf("\nIterations: %d\n",ite_loop);
- return 0;
- }
In the previous code, the programmer has specified the wrong define directive variable in order to read the filename array. This mistake forces the code to read a few bytes beyond the bounds of the filename array; consequently it prints random data to memory:
An off-by-one error can be also introduced by improper usage of certain library functions. The following example uses the strncat function that always null-terminates its output string:
- strcpy(buf, "buffer:");
- strncat(buf, input, sizeof(buf)-strlen(buf));
The improper usage of the strncat function (third argument) produces an off-by-one condition, which depending on application architecture, may lead to code execution.
2. Potential impact
Off-by-one error leads to an unpredictable behavior of application, depending on nature of the vulnerability, and in most cases results in application crash or infinite loop. This weakness can also lead to buffer overflow and memory corruption. In cases of a heap-based buffer overflow, the most obvious result is the application crash. If off-by-one error leads to a stack-based buffer overflow, successful code execution is more likely.
3. Affected software
Software written in languages such as C and C++ that do not perform memory management is potentially vulnerable to this weakness.
4. Mitigations
Developers should pay extra attention to correct size parameter accounting for null terminator when copying character arrays or performing manipulations on arrays.
5. Severity and CVSS Scoring
Off-by-one errors can be used to cause application crash, data tampering or execution of arbitrary code. Depending on software and vulnerable code, these weaknesses could be locally or remotely exploitable.
A common CVSSv3 score for locally exploitable vulnerability in application would look like this:
3.3 [CVSS:3.0/AV:L/AC:L/PR:L/UI:N/S:U/C:N/I:N/A:L] – Low severity.
In cases of remote code execution, it is usually scored as:
10.0 [CVSS:3.0/AV:N/AC:L/PR:N/UI:N/S:C/C:H/I:H/A:H] – High severity.
6. References
- CWE-193: Off-by-one Error [cwe.mitre.org]
- Off-by-one error [wikipedia.org]
- The Shellcoder's Handbook: Discovering and Exploiting Security Holes [www.amazon.com]
7. Off-by-one Error Vulnerabilities, Exploits and Examples
Copyright Disclaimer: Any above-mentioned content can be copied and used for non-commercial purposes only if proper credit to ImmuniWeb is given.
↑ Back to Top