1

I am trying to concat two strings in the function foo(). I expect the content of string to be abc after both the first and second calls to foo(). The output which I get after the first call is abc but the second call prints abcabc (the third call prints abcabcabc and so on). The string buffer is not getting cleared. It will be helpful if someone could share how it works internally - how the memory is assigned to the string and why the string buffer is not cleared between subsequent calls of the function.

Here is the code I used:

#include <stdio.h>
#include <string.h>

int foo(){
    unsigned char string[100];
    unsigned char text[10] = "abc";
    strcat(string, text);
    printf("%s\n", string);
}

int main(){
    foo();
    foo();
    return 0;
}
phuclv
  • 37,963
  • 15
  • 156
  • 475
mcgusty
  • 1,354
  • 15
  • 21
  • There is no C runtime. Memory is not cleared between function calls. Someone has to do it. In your case you might want `memset(string, 0, strlen(text))` at the end of the function. That being said you probably also want to be using `strcpy` instead of `strcat`. The way you have it now `string` is never initialized so `strcat`'s length finding could you to read memory you don't have permissions to. – Noah Jun 03 '21 at 05:18
  • looking at your code, it seems pretty obvious that the result which you got, was what the function was doing, as you've not initialised the `string`: invokes [Undefined behaviour](https://stackoverflow.com/q/2397984/8484779) – DeBARtha Jun 03 '21 at 05:23
  • 2
    The documentation for [`strcat`](https://en.cppreference.com/w/c/string/byte/strcat) is self-explanatory. It requires the first argument be (a) a null-terminated string (b) with buffer space of sufficient capacity to house the current string, the addendum string, *and* a terminating nullchar. Your code does not deliver on the first of those requirements, and therefore you invoke *undefined behavior*. Read and understand how the library functions you're using work. – WhozCraig Jun 03 '21 at 05:27
  • 1
    "why the string buffer is not cleared between subsequent calls of the function": Because there is nothing in the language that ever claimed that it would be cleared. If you thought there was, I'm afraid you're misled. Uninitialized local variables have *indeterminate* contents, and that includes the possibility of seeing leftover data from previous calls. – Nate Eldredge Jun 03 '21 at 06:13

2 Answers2

1

You forgot to initialize the string variable. This is the reason for all your problems. Trying to access the value of an uninitialized variable causes Undefined behavior.

Refer to (Why) is using an uninitialized variable undefined behavior?.

#include <stdio.h>
#include <string.h>

int foo(){
    unsigned char string[100] = "";
    unsigned char text[10] = "abc";
    strcat(string, text);
    printf("%s\n", string);
}

int main(){
    foo();
    foo();
    return 0;
}
Kitswas
  • 1,134
  • 1
  • 13
  • 30
1

string hasn't been initialized so doesn't contain a valid string. As a result when strcat reads it to find the null terminator it invokes undefined behavior. You must initialize it before using

unsigned char string[100] = { 0 };
phuclv
  • 37,963
  • 15
  • 156
  • 475