1

In the chapter 5 of K&R C (2nd edition), the following two statements are given and said to have a subtle difference (I am pasting the text as it is)

There is an important difference between these definitions:

char amessage[] = "now is the time"; /* an array */

char *pmessage = "now is the time"; /* a pointer */

amessage is an array, just big enough to hold the sequence of characters and '\0' that initializes it. Individual characters within the array may be changed but amessage will always refer to the same storage. On the other hand, pmessage is a pointer, initialized to point to a string constant; the pointer may subsequently be modified to point elsewhere, but the result is undefined if you try to modify the string contents.

I am not able to understand what they want to imply here. It says that for pmessage, the result is undefined if you try to modify the string constants. What is the result they are talking about, how can we modify the string constants and why will the result be undefined ?

Also it says that amessage always points to the same storage. Is this storage the storage the array is allocated when it gets defined?

Can someone please explain in a better way ? I would be very grateful !!

Devolus
  • 21,661
  • 13
  • 66
  • 113
  • 2
    Does this help? https://stackoverflow.com/a/1704433/10622916 – Bodo Mar 01 '21 at 09:37
  • 2
    Does this answer your question? [What is the difference between char s\[\] and char \*s?](https://stackoverflow.com/questions/1704407/what-is-the-difference-between-char-s-and-char-s) – Damien Mar 01 '21 at 10:05

3 Answers3

1

The reason why this is undefined is, because it can not be guaranteed on every architecture.

On older machines (like i.e. Amiga 1000) you don't have an MMU, so if you write to "forbidden area" it will work. On modern platforms (like Linux or Windows, etc.) there is an MMU, which can prevent writing to certain areas. Normally such string constants are put into a read-only area, which will cause an exception if the platform supports it. That's why it is undefined. The language can not guarantee it in all cases that a certain behavior will happen, so it may, or may not work.

Putting it in an array, will always make that guarantee, but using a string literal with a pointer, can not.

Devolus
  • 21,661
  • 13
  • 66
  • 113
  • It's certainly possible to guarantee a certain behavior, but the standard does not enforce it in order to allow optimizations. – klutt Mar 04 '21 at 07:24
1

What is the result they are talking about, how can we modify the string constants and why will the result be undefined ?

Undefined behavior does not have a specific result, there are no requirements for an ill-formed program that invokes undefined behavior, meaning that it can do whatever. A program that tries to modify a string constant is an example of such a program.

You can check C11 definition of undefined behavior here

Also it says that amessage always points to the same storage. Is this storage the storage the array is allocated when it gets defined?

amessage is what's called a fixed size array, it is an alias for a given memory address, once it's initialized to that memory address it cannot change until the variable lifetime ends, the points part is not what I would use, it's arguably bad wording because amessage is not a pointer, more on that here.

*pmessage on the other hand is a pointer, and as such you can make it point to some other memory address, you can even make it point to amessage i.e. pmessage = amessage, now pmessage is pointing to the exact same location as amessage, amessage can now be accessed or modified through that pointer, but amessage = pmessage is not possible.

anastaciu
  • 23,467
  • 7
  • 28
  • 53
  • Dear Anastaiu,thanks again ! Also thank you for giving the link on how to accept an answer. I am new to this platform and hence did not have any idea about it – Ashutosh Mishra Mar 04 '21 at 07:08
0

What is the result they are talking about,

The result of running the code. It may work, and it may crash, and a lot of other things.

how can we modify the string constants

You cannot, unless the compiler offers this by some extension. Don't use a string literal if it needs to be modified.

and why will the result be undefined ?

Because the standard says so

It can be mentioned that in C++, the type of string literals is const char[] but in C it's char[]. This is for historical reasons.

klutt
  • 30,332
  • 17
  • 55
  • 95