tags:

views:

239

answers:

4

Possible Duplicate:
Why does simple C code receive segmentation fault?

Hey Everyone, I'm sure this is a very basic question, but apparently I'm not quite understanding something here.

I've been playing around with C a lot over winter break and just came across something that I thought would work but is giving me a segmentation fault.

if I declare a string as: char name[5] = "Mike"; I can manipulate the string: *(name+1) = 'a'; This works fine, name becomes "Make".

If I declare as: char *name = "Mike"; and then try the same thing: *(name+1) = 'a'; I get a segmentation fault. Why can't I do that?

If I malloc the space for the string: char *name = (char*)malloc(5*sizeof(char)); and then copy the string to name: strcpy(name,"Mike"); I can manipulate it like above just fine. *(name+1) = 'a'; works.

What is the difference between char *name = "Mike"', and char *name = (char*)malloc(5*sizeof(char)); strcpy(name,"Mike");? Aren't they both just pointing to memory containing the string?

Sorry for the noobish question!

+10  A: 

char name[5] = "Mike" declares a local array and copies the string "Mike" into it. char* name = "Mike" assigns a pointer to "Mike" without copying. In both cases, "Mike" is a constant string held in a read-only page, and so in the second case you are trying to modify the original constant.

Marcelo Cantos
Wouldn't a compiler flag (with at least a warning) the `char* name = "Mike"` case as discarding the `const`-ness of "Mike", since "Mike" is technically a `const char*`? Or does C not care about discarding `const`?
Mike D.
@Mike: There's no logic to it. It's just an old wart carried over from the old days for compatibility reasons.
Marcelo Cantos
+1  A: 

When you declare a character array, the memory is allocated on the stack and you can write to that.

When you later call malloc(), you allocate memory in the heap and you can write to that.

When you do the thing in the middle that crashes, you've declared a pointer to a string that lives in memory you're not allowed to change. It is static and read-only.

jeffamaphone
+2  A: 

So far everybody has said it, but I'm not sure it's clear enough.

char array[5] = "Mike"

creates a constant string "Mike", allocates an array on the stack of size 5, and copies the constant string into it ( theoretically... the compiler will probably optimize a step out )

char *array = "Mike"

creates the same constant string "Mike", but then just assigns the pointer to it instead of copying it to the local stack.

By "constant string", it may be a string allocated in memory and marked read-only by the operating system, so your attempt to modify it causes the segmentation fault.

Chris Arguin
That makes sense, thank you!
itscaleb
+3  A: 

You are trying to modify a string literal which invokes Undefined Behavior

char *array="Mike"; /* String Literal is stored in read only section of memory */

*array='P'; /* Undefined Behavior */

C99 Section 6.4.5.6 (Section-- String Literals) clearly states:

It is unspecified whether these arrays are distinct provided their elements have the appropriate values. If the program attempts to modify such an array, the behavior is undefined.

Whereas,

 char array[5] = "Mike";/*Creates a local array and copies the string "Mike" into it*/

 *array='P';/*Fine*/
Prasoon Saurav