Question:
In the various cases that a buffer is provided to the standard library's many string functions, is it guaranteed that the buffer
will not be modified beyond the null terminator? For example:
char buffer[17] = "abcdefghijklmnop";
sscanf("123", "%16s", buffer);
Is buffer
now
required to equal "123\0efghijklmnop"
?
Another example:
char buffer[10];
fgets(buffer, 10, fp);
If the read line is only 3 characters long, can one be certain that the 6th character is the same as before fgets was called?
Answer:
Each individual byte in the buffer is an object. Unless some part of the function description of sscanf
or fgets
mentions
modifying those bytes, or even implies their values may change e.g. by stating their values become unspecified, then the general rule applies: (emphasis mine)
6.2.4 Storage durations of objects
2 [...] An object exists, has a constant address, and retains its last-stored value throughout its lifetime. [...]
It's this same principle that guarantees that
#include <stdio.h>
int a = 1;
int main() {
printf ("%d\n", a);
printf ("%d\n", a);
}
attempts to print 1 twice. Even though a
is
global, printf
can
access global variables, and the description of printf
doesn't
mention not modifying a
.
Neither the description of fgets
nor
that of sscanf
mentions
modifying buffers past the bytes that actually were supposed to be written (except in the case of a read error), so those bytes don't get modified.