2012-04-26 29 views
1

我正在讀上段故障維基百科來通過下面的代碼和語句。該程序的可執行文件標記爲只讀

int main(void) 
{ 
    char *s = "hello world"; 
    *s = 'H'; 
} 

當被編譯包含該代碼的程序,字符串「hello 世界」被放置在程序可執行文件的部分標記 爲只讀;加載時,操作系統將其他 字符串和常量數據放在只讀內存段中。當 執行,可變,S被設定爲指向串的位置,並 試圖通過可變的H字符寫入 存儲器,導致一個分段錯誤。編譯這樣的程序 用編譯器不檢查在編譯時只讀 位置的分配。

我的問題是文件權限,即當可執行文件標記爲只讀,以及讀寫時 等等?

我想知道所有有關文件permissions.Can我們明確地更改文件權限?

+0

當它說的文件,這是否意味着堆在這裏? – noMAD 2012-04-26 03:18:36

+2

正在運行的程序中的文件訪問權限和內存訪問權限不相關。將可執行程序標記爲可寫,不會導致其文本頁面被映射爲可讀/寫;相反,將其標記爲只讀不會導致其數據頁被意外映射爲只讀。 – geekosaur 2012-04-26 03:19:35

+0

我不確定文件權限是如何相關的 - 維基文章指的是內存頁*的權限。可以按照系統特定的方式更改頁面權限,例如POSIX系統上的mprotect()。 – FatalError 2012-04-26 03:20:01

回答

5

的「Hello World」存儲在只讀的內存部分。寫入可執行文件的指定部分的能力與寫入磁盤可執行文件的能力無關。

+0

都存儲在只讀內存部分的可執行文件? – IndieProgrammer 2012-04-26 03:29:54

+0

並非所有可執行文件的內存都是隻讀的。例如,如果你有像'i = 0; i = 2',那麼'i'將被存儲在讀寫存儲器中(假設編譯器沒有將其優化爲一個賦值)。 – Venge 2012-04-26 03:31:26

+0

@IndieProgrammer默認情況下,是的。它是可執行文件中可加載段的屬性;默認情況下,文本(=代碼)段被標記爲只讀,但您可以覆蓋它。只讀段的好處不僅在於防止錯誤代碼,而且可以更輕鬆地在多個正在運行的實例的內存映像之間共享它們。 – geekosaur 2012-04-26 03:32:47

2

有3個你在這個問題談論無關的概念:

  • 文件屬性(由一些操作系統支持,即Windows)中 - 其中之一是隻讀的。管理如何正常打開文件,具有修改文件權限的用戶可以隨意更改文件屬性。
  • 文件權限(大多數操作系統支持)。如果給定用戶有權限訪問/修改,並且在某些系統中執行該文件。
  • 內存頁面上的內存保護屬性。由大多數實現虛擬內存的操作系統支持。存儲器的每個頁面(即4Kb塊)獲得由OS的memeory管理部分與CPU一起設置和執行的一組屬性(即讀取,寫入,執行)。大多數現代CPU直接使用這個頁面屬性來驗證內存操作。

即在Windows上,您可以使用VirtualProtect函數來指定在程序的地址空間中分配的給定內存塊應具有的屬性。

相關問題