7

Considering this code:

limit = sizeof(str1)-strlen(str1)-1;
strncat(str1,str2,limit);

If str2 length is greater than limit, does strncat Nul terminates str1 or I have to add this code, like in the case of strncpy?

str1[sizeof(str1)-1] = '\0'
Sourav Ghosh
  • 127,934
  • 16
  • 167
  • 234
Demetrio
  • 457
  • 1
  • 6
  • 18
  • You make sure `str1` is of array type, right? – Sourav Ghosh Jan 14 '17 at 16:23
  • not wrong, incomplete. You __had__ to mention that `str1` is an array. – Sourav Ghosh Jan 14 '17 at 16:24
  • How is `str1` declared? We can guess, but be aware that someone unfamiliar with the possible problems will use your code and ... get problems. As it is, your code will fail (possibly spectacularly) if `str1` is a `char *`. – Jongware Jan 14 '17 at 16:24
  • I wrote that code to give a generic example. I assumed that str1 was an array – Demetrio Jan 14 '17 at 16:30
  • Note that `strncat` is *not* designed to be a safer version of `strcat`. – Dietrich Epp Jan 14 '17 at 16:33
  • @DietrichEpp I'd say the same about `strcpy()` but how about in this case? – Sourav Ghosh Jan 14 '17 at 17:27
  • 1
    @SouravGhosh: The `strncpy` function truncates strings, the `strcpy` function does not. They are different functions with different purposes, and it makes no sense to use either one to replace the other. If you don't want to silently truncate strings, but you're using `strncpy` because it's "safer", you should reevaluate your code security policies. The `strcat_s` function *is* designed to be a safer version of `strcat` but general consensus is that it has failed to achieve this goal, and that a combination alternative techniques (like code instrumentation) should be used instead. – Dietrich Epp Jan 14 '17 at 20:10

2 Answers2

8

It always null-terminate.

Quoting C11, chapter §7.24.3.2, (emphasis mine)

The strncat function appends not more than n characters (a null character and characters that follow it are not appended) from the array pointed to by s2 to the end of the string pointed to by s1. The initial character of s2 overwrites the null character at the end of s1. A terminating null character is always appended to the result.

and, the footnote

Thus, the maximum number of characters that can end up in the array pointed to by s1 is strlen(s1)+n+1.

Sourav Ghosh
  • 127,934
  • 16
  • 167
  • 234
  • 3
    strncat may be confusing because the 'n' relates to source string not to destination buffer. So this function is still unsafe and can cause overflow. Most other 'n' variants were created to prevent overflow which is what got me confused in the past. – Petr Nov 14 '19 at 14:43
-2

C++ version lower than C11 doesn't append null character in Case like when your source string has not enough space inside for destination string.

char str[5];
str="Ami"

char str2[10];
str2="NotGoing"

str has 2 free space but needed is 7 to concat str2 and 1 for the null character. strncat(str,str2,);// case with no null termination.

now if str don't have space to write the whole destination (str2) inside it along with str pre-written data so in this case, it will not add a null char at the end

char str[10];
str="Ami"

char str2[3];

str2="Hello"

str got enough space for str2 inside it. so will add a null character at the end.

strncat(str,str2,);// case with null termination.

Formal I made to check on my own

length allocated to str >= strlen(str)+ strlen(str2)+1 ;

if this condition satisfies you will have a null terminated result otherwise you not.**

gsamaras
  • 66,800
  • 33
  • 152
  • 256
  • 1
    C11 is C standard, C++ is C++. The part `C++ version lower then C11` is syntantically incorrent, no version of C++ standard will ever be higher or lower then any version of C standard. C++ [documentation on strncat](https://en.cppreference.com/w/cpp/string/byte/strncat) states `The resulting byte string is null-terminated.`. If your implementation does not do that, your `strncat` implementation is not standard. If you are passing not enough memory to the first pointer to `strncat` you are experiencing undefined behavior and accessing an array out of bounds and the program is illformed. – KamilCuk Jan 10 '19 at 08:06
  • As far as I know there will a buffer overflow but still, the answer is it will not add null char at the end – Amit Sharma Jan 10 '19 at 08:10
  • 1
    In case of buffer overflow undefined behavior happens, so `strncat` spawns [demons](https://en.wikipedia.org/wiki/Undefined_behavior) in your room. Making any assumption on what should/will happen in case of undefined behavior is wrong. I would argue that any implementation _may_ write a null terminating character if it wanted to in case of undefined behavior. If you assume something will happen in undefined behavior, you are no longer talking about a C language. – KamilCuk Jan 10 '19 at 08:13
  • I am telling you because I am facing this in my current project. Can't disclose the code tho. – Amit Sharma Jan 10 '19 at 09:02
  • You were right Kamil Cuk that issue has comes in case of strncpy. My Apologies. – Amit Sharma Jan 10 '19 at 09:38