0

I have a function in 'C' that is supposed to implement my own strcpy program. Here's what I wrote. However, I am not able to debug the cause of Segmentation Fault.

#include <stdio.h>
#include <stdlib.h>

char * mystrcpy(char *dest, char *src) {
    char * ptr = dest;
    while (*src != '\0'){
        *ptr = *src;
        ptr++; src++;
        //printf("Dest is \"%s\" and Source is \"%s\"\n",dest,src);
    }
    *ptr = '\0';
    return dest;
}


int main() {
    char str[] = "I rock always";
    char * dest = NULL;
    dest = mystrcpy(dest, str);
    printf("Source String %s and Destination String %s\n", str, dest);
}

Can someone explain this behavior to me ?

madth3
  • 7,275
  • 12
  • 50
  • 74
Code4Fun
  • 125
  • 3
  • 13
  • 2
    Please note that there is the one-liner K&R version of strcpy: `while( *dest++ = *str++) {;}` You might find it ugly, but it is a good way to learn to understand the precedence rules. – wildplasser Jun 24 '12 at 09:59
  • I guess, since the goal is to copy the entire string; it makes sense to escape this '\0' check, so that it gets copied into destination string. But then, the question is, when does it know to stop ? – Code4Fun Jun 24 '12 at 10:29
  • 'I am not able to debug the cause of Segmentation Fault' -- only because you clearly haven't tried. – Jim Balter Jun 24 '12 at 10:33

5 Answers5

4

You have to allocate memory for the destination string:

int main() {
    char str[] = "I rock always";
    char * dest = (char*)malloc(strlen(str) + 1);
    dest = mystrcpy(dest, str);
    printf("Source String %s and Destination String %s\n", str, dest);
}

Of course, it is good manners to free the memory eventually:

    free(dest);
rodrigo
  • 94,151
  • 12
  • 143
  • 190
  • 1
    1) the cast is not necessary. 2) the strlen() is not necessary; sizeof will do, too. – wildplasser Jun 24 '12 at 09:47
  • @wildplasser - 1) True, but may prevent a warning in pedantic compilers. 2) Also true, but this is more generic: he may want to move the `malloc` into the `mystrcpy` function, and then the `sizeof` would not work. – rodrigo Jun 24 '12 at 09:49
  • 2
    1) "pedantic compilers"? You mean C++ compilers? 2) In that case he could call his function mystrdup(). – wildplasser Jun 24 '12 at 09:52
  • Thanks rodrigo and wildpasser for your valuable comments !! I understood the root cause. – Code4Fun Jun 24 '12 at 09:53
  • @wildplasser : I have a question; Why does sizeof stop working, when the pointer reaches an external function, as you mentioned above? – Code4Fun Jun 24 '12 at 10:33
  • sizeof does not stop working. `sizeof ptr` yields the size of *the pointer*, `sizeof array` yields the size of array. When you call a function with a pointer argument, the function only "sees" the pointer, and its type: `char *ptr`, and its size `sizeof ptr`, and its value `ptr`. The function does not know about the variables of the caller, only about its arguments and local variables (and globals). – wildplasser Jun 24 '12 at 10:42
1

You never allocate any memory for *dest to point to.

It starts pointing to NULL, and then you attempt: *ptr = *src.

WW.
  • 23,793
  • 13
  • 94
  • 121
0

You must allocate memory for the destination string buffer.

Memory management is a very big part of C ... you need to be very careful that you allocate AND deallocate memory as it is used and becomes surplus to requirements. Failure to do so will result in segmentation faults (failing to allocate memory) and memory leaks (failing to free memory)

Other answers here give you examples of malloc so I won't repeat them here.

You should use the functions already available to you as much as possible, rather than writing your own. This avoids errors in implementation as somebody has already debugged and optimized it for you.

http://www.cs.cf.ac.uk/Dave/C/node19.html

Moog
  • 10,193
  • 2
  • 40
  • 66
  • Yeah ... absolutely true. I am just learning to code, so that I would be able to develop such robust libraries some day. – Code4Fun Jun 24 '12 at 09:59
0

Allocate memory and try....

         #include <stdio.h>
         #include <stdlib.h>

         char * mystrcpy(char *dest, char *src) 
         {
                     char * ptr = dest;
                     int index=0;
                     while (*src != '\0')
                     {
                         *(ptr+index) = *(src+index);
                           index++;
                     }
                     *(ptr+index) = '\0';
                     return dest;

          }




          int main() 
          {
                char str[] = "I rock always";
                char * dest = (char*)malloc((strlen(str)+1)*sizeof(char));
                dest = mystrcpy(dest, str);
                printf("Source String %s and Destination String %s\n", str, dest);
                free(dest);
                return 0;
          }
Arjun K P
  • 2,081
  • 4
  • 20
  • 33
0
#include <stdio.h>

    /* this the K&R version of strcpy */
char * mystrcpy(char *dest, char *src) {
    char *ptr = dest;
    while ( *ptr++ = *src++ ) {;}

    return dest;
}


int main(void) {
    char str[] = "I rock always";
    char dest[sizeof str];
    char *result;

    result = mystrcpy(dest, str);
    printf("Source String %s and Destination String %s and result %s\n", str, dest, result);
    return 0;
}
wildplasser
  • 43,142
  • 8
  • 66
  • 109