...
Failure to properly terminate null-terminated byte strings can result in buffer overflows and other undefined behavior.
...
Non-Compliant Code Example (strncpy()
)
Wiki Markup |
---|
The standard {{strncpy()}} function does not guarantee that the resulting string is null terminated \[[ISO/IEC 9899-1999|AA. C References#ISO/IEC 9899-1999]\]. If there is no null character in the first {{n}} characters of the {{source}} array, the result may not be null terminated. |
In the first non-compliant coding example, ntbs
is null terminated before the call to strncpy()
. However, the subsequent execution of strncpy()
may overwrite the null-termination character.
Code Block |
---|
|
char ntbs[NTBS_SIZE];
ntbs[sizeof(ntbs)-1] = '\0';
strncpy(ntbs, source, sizeof(ntbs));
|
Wiki Markup |
---|
In the second non-compliant code example, {{memset()}} is used to clear the destination buffer; unfortunately, the third argument incorrectly specifies the size of the destination array \[[Schwarz 05|AA. C References#Schwarz 05]\]. |
Code Block |
---|
|
char ntbs[NTBS_SIZE];
memset(ntbs, 0, sizeof(ntbs)-1);
strncpy(ntbs, source, sizeof(ntbs)-1);
|
Compliant Solution (Truncation)
The correct solution depends on the programmer's intent. If the intent was to truncate a string but ensure that the result remains a null-terminated string, this solution can be used:
Code Block |
---|
|
char ntbs[NTBS_SIZE];
strncpy(ntbs, source, sizeof(ntbs)-1);
ntbs[sizeof(ntbs)-1] = '\0';
|
Compliant Solution (Copy without Truncation)
If the intent is to copy without truncation, this example copies the data and guarantee that the resulting null-terminated byte string is null terminated. If the string cannot be copied, it is handled as an error condition.
Code Block |
---|
|
char *source = "0123456789abcdef";
char ntbs[NTBS_SIZE];
/* ... */
if (source) {
if (strlen(source) < sizeof(ntbs)) {
strcpy(ntbs, source);
}
else {
/* handle string too large condition */
}
}
else {
/* handle null string condition */
}
|
Compliant Solution (strncpy_s()
)
Wiki Markup |
---|
The {{strncpy_s()}} function copies up to {{n}} characters from the source array to a destination array \[[TR 24731|AA. C References#ISO/IEC TR 24731-1-2007]\]. If no null character was copied from the source array, then the {{n{}}}th position in the destination array is set to a null character, guaranteeing that the resulting string is null-terminated. |
This compliant solution also guarantees that the string is null terminated.
Code Block |
---|
|
char *source;
char a[NTBS_SIZE];
/* ... */
if (source) {
errno_t err;
if ((err = strncpy_s(a, sizeof(a), source, 5)) != 0) {
/* handle error */
}
}
else {
/* handle null string condition */
}
|
...
Non-Compliant Code Example (realloc()
)
...