Possible Duplicate:
Why should you use strncpy instead of strcpy?
I’m reading a book about computers/cryptographic etc. And often the writer use thing such as strncpy(dest, src, strlen(src)); instead of strcpy(dest, src); it makes no much sense for me.. Well, I’m a professional programmer.
The question is: It make really a real difference? real applications use something like this?
The author is almost certainly abusing the
strn*functions. Unfortunately, there is almost never a good reason to usestrn*functions, since they don’t actually do what you want.Let’s take a look at
strcpyandstrncpy:The
strcpyfunction copiessrcintodest, including a trailing\0. It is only rarely useful:Unless you know the source string fits in the destination buffer, you have a buffer overflow. Buffer overflows are security hazards, they can crash your program, and cause it to behave incorrectly.
If you do know the size of the source string and destination buffer, you might as well use
memcpy.By comparison, the
strncpycopies at mostnbytes ofsrcintodestand then pads the rest with\0. It is only rarely useful:Unless you know the source string is smaller than the destination buffer, you cannot be certain that the resulting buffer will be nul-terminated. This can cause errors elsewhere in the program, if you assume the result is nul-terminated.
If you do know the source string is smaller, again, you might as well use
memcpy.You can simply terminate the string after you call
strncpy, but are you sure that you want to silently truncate the result? I’d imagine most of the time, you’d rather have an error message.Why do these functions exist?
The
strcpyfunction is occasionally handy, but it is mostly a relic of an era where people did not care very much about validating input. Feeding a string that is too large to a program would crash it, and the advice was “don’t do that”.The
strncpyfunction is useful when you want to transmit data in fixed-size fields, and you don’t want to put garbage in the remainder of the field. This is mostly a relic of an era where people used fixed-size fields.So you will rarely see
strcatorstrncpyin modern C software.A worse problem
However, your example combines the worst of both worlds. Let’s examine this piece of source code:
This copies
srcintodest, without a\0terminator and without bounds checking. It combines the worst aspect ofstrcpy(no bounds checking) with the worst aspect ofstrncpy(no terminator). If you see code like this, run away.How to work with strings
Good C code typically uses one of a few options for working with strings:
Use fixed buffers and
snprintf, as long as you don’t mind fixed buffers.Use bounded string functions like
strlcpyandstrlcat. These are BSD extensions.Use a custom string point which tracks string lengths, and write your own functions using
memcpyandmalloc.