Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why C11 standard doesn't drop unsafe strcat(),strcpy() functions?

Tags:

c

c11

strcpy

strcat

C11 & C++14 standards have dropped gets() function that is inherently insecure & leads to security problems because it doesn't performs bounds checking results in buffer overflow. Then why C11 standard doesn't drop strcat() & strcpy() functions? strcat() function doesn't check to see whether second string will fit in the 1st array. strcpy() function also contains no provision for checking boundary of target array. What if the source array has more characters than destination array can hold? Most probably program will crash at runtime.

So, wouldn't it be nice if these two unsafe functions completely removed from the language? Why they are still exist? What is the reason? Wouldn't it is fine to have only functions like strncat(),strncpy()? If I am not wrong Microsoft C & C++ compiler provides safe versions of these functions strcpy_s(),strcat_s(). Then why they aren't officially implemented by other C compilers to provide safety?

like image 666
Destructor Avatar asked Dec 01 '22 00:12

Destructor


2 Answers

gets() is inherently unsafe, because in general it can overflow the target if too much data is received on stdin. This:

char s[MANY];
gets(s);

will cause undefined behavior if more than MANY characters are entered, and there is typically nothing the program can do to prevent it.

strcpy() and strcat() can be used completely safely, since they can overflow the target only if the source string is too long to be contained in the target array. The source string is contained in an array object that is under the control of the program itself, not of any external input. For example, this:

char s[100];
strcpy(s, "hello");
strcat(s, ", ");
strcat(s, "world");

cannot possibly overflow unless the program itself is modified.

strncat() can be used as a safer version of strcat() -- as long as you specify the third argument correctly. One problem with strncat() is that it only gives you one way of handling the case where there's not enough room in the target array: it silently truncates the string. Sometimes that might be what you want, but sometimes you might want to detect the overflow and do something about it.

As for strncpy(), it is not simply a safer version of strcpy(). It's not inherently dangerous, but if you're not very careful you can easily leave the target array without a terminating '\0' null character, leading to undefined behavior next time you pass it to a function expecting a pointer to a string. As it happens, I've written about this.

like image 113
Keith Thompson Avatar answered Dec 05 '22 07:12

Keith Thompson


strcpy and strcat aren't similar to gets. The problem of gets is, it's used to read from input, so it's out of the programmer's control whether there will be buffer overflow.


C99 Rational explains strncpy as:

Rationale for International Standard — Programming Languages — C §7.21.2.4 The strncpy function

strncpy was initially introduced into the C library to deal with fixed-length name fields in structures such as directory entries. Such fields are not used in the same way as strings: the trailing null is unnecessary for a maximum-length field, and setting trailing bytes for shorter 5 names to null assures efficient field-wise comparisons. strncpy is not by origin a “bounded strcpy,” and the Committee preferred to recognize existing practice rather than alter the function to better suit it to such use.

like image 38
Yu Hao Avatar answered Dec 05 '22 06:12

Yu Hao