2012-07-27 26 views
0

我正在研究64位Linux機器上的一個程序,它需要將多個任意長度的數據數組映射到我無法控制的固定內存地址。我覺得mmap()的與MAP_FIXED和MAP_ANONYMOUS是要走的路,例如:將多個數據數組映射到任意固定內存地址

mmap((void *) 0x401000, 0x18e, PROT_NONE, MAP_ANONYMOUS | MAP_FIXED, -1, 0); 

不過,我每次調用此函數時,會返回MAP_FAILED。我已經將fd設置爲-1,我知道這對某些系統是必需的,地址是我的頁面大小(4096)的倍數,並且長度是非負值,所以我想知道是否0x401000是已經被我的系統使用;我也試過0x402000,0x403000和0x404000,結果相同。

有什麼我錯過了關於mmap(),或者有沒有辦法找出這個地址已經有什麼?更妙的是,由於我無法控制我需要的地址,有沒有更好的方法來避免遇到現有的映射?

編輯:檢查errno後,我發現,我得到的代碼是一個無效的參數,因此,根據手冊頁,「我們不喜歡地址,長度或偏移(例如,他們太大或者不在頁面邊界上對齊)。「不過,我還不知道哪一個是問題所在。

回答

1

鑑於0x400000似乎是.text地址在我的amd64 Debian的系統進程(x86是不同的),我懷疑你要失敗的,因爲你試圖映射在現有的東西,因爲你想。不確定(編程)確定哪些段被映射/可用的最佳方式,但是您可以通過檢查/proc/<pid>/maps來查看大量「典型」進程,以查看系統如何爲程序和庫分配地址範圍。地址空間隨機化會在那裏引發一些額外的皺紋,以及...

+0

我發現我的代碼失敗了,並給出了無效的參數錯誤,因爲我沒有在'flags'參數中指定'MAP_FIXED'或'MAP_SHARED'。在我解決這個問題之後,只有映射到0x401000纔會失敗,並且只有在使用了MAP_FIXED時,它看起來好像有些東西佔用了那個地址。謝謝你的幫助! – nosuchthingasstars 2012-07-30 14:44:03

0

下面是我寫了一段很久以前寫的一個例子,它是一個固定地址的mmap。它映射幀緩衝區設置/清除像素的宗旨:

http://stromberg.dnsalias.org/~strombrg/pbmonherc.html

videoBase = (unsigned char *) mmap((caddr_t) videoBase, VideoRamLength, 
        PROT_READ | PROT_WRITE, 
        MAP_SHARED | MAP_FIXED, 
        fd, VideoRamStart); 

fd是開到/ dev/MEM。

+0

打開fd到'/ dev/mem'的意義是什麼?據我所知,這是我們的代碼之間唯一重要的區別,我從來沒有見過這樣做過。 – nosuchthingasstars 2012-07-29 15:54:27

+0

ISTR/dev/mem是一個能夠查看機器物理內存的文件。 – user1277476 2012-07-30 16:58:29