Question

this is an example of what I wanna do I have the following list

[token]
[token1]
[token22]
[token99]
[8token]
[3token3]

and I wanna remove "[" and "]" then replace the word token with my own word. so I have the following code:

char *getToken(char *repl, char *mysrc)
{
    const char *p1 = strstr(mysrc,"[")+1;
    const char *p2 = strstr(p1,"]");
    size_t len = p2-p1;
    char *src = (char*)malloc(sizeof(char)*(len+1));
    strncpy(src,p1,len);
    src[len] = '\0';

    char *find = "token";
    char *found;
    if(strcmp(src,find) == 0)
        return src;
    char *res = malloc(strlen(src) + strlen(repl) + 1);
    if (res == NULL)
        return src;
    found = strstr(src, find);
    /* Search string not found, return the whole of the source */
    if (found == NULL){
        strcpy(res, src);
        return res;
    }
    /* Paste the replacement string in */
    strncpy(res, src, (size_t)(found - src));
    strcat(res, repl);
    strcat(res, found + strlen(find));
    free(src);
    return res;
}

which is working fine except that in some situations I get an X or H in front of the result. like this: Xtest22 instead of test22

Did I do something wrong with strlen? I can't seem to find out where I'm doing wrong.

Was it helpful?

Solution

This could happen when the "token" string ends up at the beginning of the string after the removal of the square brackets: in this case, (size_t)(found - src) evaluates to zero, so the call of

strncpy(res, src, (size_t)(found - src));

does not change the res string at all, leaving whatever junk that was there for the following call of strcat to skip before appending. You get lucky that the junk in the res happens to be a short null-terminated string, such as an "X" or an "H". Otherwise, you could get a much longer string of arbitrary characters.

In addition to fixing the above undefined behavior, you should fix a few more things:

  • Your code does not check the return value of the first malloc.
  • Your code miscalculates the length of the result: you should subtractl the length of the word "token", because you replace it with the content of repl, i.e. it should be malloc(strlen(src) + strlen(repl) - strlen(find) + 1)
  • You do not need to cast the return value of malloc in C
  • You do not need to multiply the length by sizeof(char) (only one of your two mallocs does that)
  • Your second early return leaks memory.
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top