2013-07-06 111 views
1

爲什麼mmap()返回64位地址,而malloc()返回32位地址?mmap()vs malloc()返回地址

char *a = (char *)mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0); 
printf("%p\n", a); // example: 0x7fbfbb065000 

char *b = (char *)malloc(10); // example: 0x23bf010 
printf("%p\n", b); 
+2

你並不需要把返回C程序中'malloc'(或'mmap')的值。 –

+1

這完全依賴於實現並且沒有趣味。 – 2013-07-06 16:18:04

+0

嘗試獲得並再次檢查 –

回答

1

內核將內存堆放置在較低的4GB內,這就是爲什麼malloc(3)返回一個64位地址並清除所有高32位的結果。

您可以在代碼末尾添加休眠,並重新編譯&再次運行該程序。然後閱讀 「的/ proc/PROCESS_ID /地圖」,你會看到堆在較低4GB:

%執行cat/proc/26375 /圖

 
00400000-00401000 r-xp 00000000 ca:01 46177        /root/c/a.out 
00600000-00601000 r--p 00000000 ca:01 46177        /root/c/a.out 
00601000-00602000 rw-p 00001000 ca:01 46177        /root/c/a.out 
01e03000-01e24000 rw-p 00000000 00:00 0         [heap] 
7f654038c000-7f6540541000 r-xp 00000000 ca:01 395503      /lib/x86_64-linux-gnu/libc-2.15.so 
7f6540541000-7f6540740000 ---p 001b5000 ca:01 395503      /lib/x86_64-linux-gnu/libc-2.15.so 
7f6540740000-7f6540744000 r--p 001b4000 ca:01 395503      /lib/x86_64-linux-gnu/libc-2.15.so 
7f6540744000-7f6540746000 rw-p 001b8000 ca:01 395503      /lib/x86_64-linux-gnu/libc-2.15.so 
7f6540746000-7f654074b000 rw-p 00000000 00:00 0 
7f654074b000-7f654076d000 r-xp 00000000 ca:01 395517      /lib/x86_64-linux-gnu/ld-2.15.so 
7f6540960000-7f6540963000 rw-p 00000000 00:00 0 
7f654096a000-7f654096d000 rw-p 00000000 00:00 0 
7f654096d000-7f654096e000 r--p 00022000 ca:01 395517      /lib/x86_64-linux-gnu/ld-2.15.so 
7f654096e000-7f6540970000 rw-p 00023000 ca:01 395517      /lib/x86_64-linux-gnu/ld-2.15.so 
7fff4445e000-7fff4447f000 rw-p 00000000 00:00 0       [stack] 
7fff44500000-7fff44501000 r-xp 00000000 00:00 0       [vdso] 
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0     [vsyscall] 
0

如果您的系統有64位指針,則返回一個64位地址。它只是發生,malloc是讓你回到前32位設置爲0.爲什麼這是完全依賴於你的實現 - 因爲你的問題被標記爲linux,你可以去找出來的源頭找出!

2

這實際上只是您的malloc()mmap()實現的實現細節。嘗試將分配大小更改爲16 MiB,您可能會看到與mmap()malloc()非常相似的結果。

在Unix系統中,分配的內存通常來自於兩個系統的一個電話:sbrk()mmap(),所以malloc()實施通常會調用這兩個功能之一。函數malloc()是一個庫函數,不是系統調用,您可以看到(這解釋了爲什麼在手冊的第3部分中,而sbrk()mmap()在第2節中)。

對於小分配(例如在您的示例中爲10個字節),malloc()通常會將許多分配歸入一個較大的分配,並且某些實現使用sbrk()。對於大型分配,例如我的示例中的16 MiB,malloc()將只需撥打mmap()並完成它。