Exactly where string literals get stored is largely up to the individual implementation; the only requirement is that the literal be visible to the entire program, and that it be allocated at program start and held until the program terminates.
Some platforms may store the literal in a different memory segment (such as .rodata
).
As far as the difference between
char *name = "Adam";
and
char name2[] = "Adam";
a picture might help. Here's how things play out on my particular system:
Item Address 00 01 02 03
---- ------- -- -- -- --
"Adam" 0x400ac0 41 64 61 6d Adam
0x400ac4 00 22 41 64 ."Ad
name 0x7fff39dbdb78 c0 0a 40 00 ..@.
0x7fff39dbdb7c 00 00 00 00 ....
name2 0x7fff39dbdb70 41 64 61 6d Adam
0x7fff39dbdb74 00 7f 00 00 ....
The string literal "Adam"
is stored as an array of char
starting at address 0x400ac0 (which is in the .rodata
segment on my system).
The variable name
is a pointer to char
and contains the address of the string literal (my system is little-endian, so the address reads "backwards").
The variable name2
is an array of char
whose contents are copied from the string literal.
Edit
What might help more is looking at generated machine code. Take the following program:
#include <stdio.h>
int main( void )
{
char *name = "Adam";
char name2[] = "Adam";
printf("name = %s, name2 = %s\n", name, name2 );
return 0;
}
I compiled it on a SLES 10 system with gcc
as follows:
gcc -o name2 -std=c99 -pedantic -Wall -Werror name2.c -Wa,-aldh=name2.lst
which gave me the following assembler output in name2.lst:
GAS LISTING /tmp/ccuuqqGI.s page 1
1 .file "name2.c"
2 .section .rodata
3 .LC0:
4 0000 4164616D .string "Adam"
4 00
5 .LC1:
6 0005 6E616D65 .string "name = %s, name2 = %s\n"
6 203D2025
6 732C206E
6 616D6532
6 203D2025
7 .text
8 .globl main
10 main:
11 .LFB2:
12 0000 55 pushq %rbp
13 .LCFI0:
14 0001 4889E5 movq %rsp, %rbp
15 .LCFI1:
16 0004 4883EC10 subq $16, %rsp
17 .LCFI2:
18 0008 48C745F8 movq $.LC0, -8(%rbp)
18 00000000
19 0010 8B050000 movl .LC0(%rip), %eax
19 0000
20 0016 8945F0 movl %eax, -16(%rbp)
21 0019 0FB60500 movzbl .LC0+4(%rip), %eax
21 000000
22 0020 8845F4 movb %al, -12(%rbp)
23 0023 488D55F0 leaq -16(%rbp), %rdx
24 0027 488B75F8 movq -8(%rbp), %rsi
25 002b BF000000 movl $.LC1, %edi
25 00
26 0030 B8000000 movl $0, %eax
26 00
27 0035 E8000000 call printf
27 00
28 003a B8000000 movl $0, %eax
28 00
29 003f C9 leave
30 0040 C3 ret
31 .LFE2:
As you can see, the string literals "Adam"
and "name = %s, name2 = %s\n"
are stored in the .rodata
section (for read-only data items). Line 18 copies the address of the string literal to name
, while lines 19 through 22 copy the contents of the string literal to name2.