為什麼 Bash 的原始碼不需要執行位元?

為什麼 Bash 的原始碼不需要執行位元?

使用 Bashsource可以在沒有設定執行位的情況下執行腳本。這是有記錄的和預期的行為,但這不是違反執行位的使用嗎?

我知道,這source不會創建子外殼。

答案1

source或同等但標準的.不執行腳本,但是腳本檔案中的命令,然後在目前 shell 環境中逐行執行它們。

沒有什麼反對使用執行位,因為 shell 只需要讀取文件內容的權限。

僅當您執行時才需要執行位跑步劇本。這裡 shell 將fork()新進程然後使用execve()函數從腳本建立新的進程映像,該映像需要是常規的可執行檔。

答案2

Bash 是解譯者;它接受輸入並做任何它想做的事。它不需要注意可執行位。事實上,Bash 是可移植的,並且可以在沒有任何可執行位元概念的作業系統和檔案系統上運行。

關心可執行位元的是作業系統核心。exec例如,當 Linux 核心執行操作時,它會檢查檔案系統是否未使用noexec選項掛載,它會檢查程式檔案的可執行位,並強制執行安全模組(例如 SELinux 或 AppArmor)施加的任何要求。

請注意,可執行位是一種相當隨意的控制。例如,在 Linux x86-64 系統上,您可以透過以下方式繞過核心對可執行位的驗證/lib/x86_64-linux-gnu/ld-linux-x86-64.so.2作為解釋器明確調用:

cp /bin/ls /tmp/
chmod -x /tmp/ls
/lib/x86_64-linux-gnu/ld-linux-x86-64.so.2 /tmp/ls

這有點類似於在 Bash 中取得 Bash 原始碼,只不過它ld.so是解釋器,而且它執行的程式碼是 ELF 格式的機器碼。

答案3

nonsetuid 和 nonsetguid 檔案上的可執行位元(與其他位元不同)並不是安全機制。任何你能讀取的東西,你都可以間接運行,Linux 會讓你間接讀取任何你能運行但不能直接讀取的東西(這應該足以在非set(g)uid x 位元是一個概念上打一個洞)安全措施)。

這更方便:如果設定了該位,讓系統直接為我運行它,否則我需要間接執行它(bash the_script;或某些駭客取得無讀權限可執行檔的記憶體映像)。

如果您打算內源化並執行您的非資源,您可以設定它以方便起見。

然而,顯然,許多共享庫實現者都同意您的想法,因此,許多系統確實需要將共享庫(本質上是 shell insourcables 的本機等效項)標記為可執行才能使用。看為什麼共享庫可執行?

答案4

對於作業系統而言,包含 shell 腳本的檔案只是資料。如果將此類資料檔案的名稱傳遞給命令source或在命令列上將其傳遞給 bash shell 的調用,則作業系統看到的只是一個恰好與包含資料的檔案名稱一致的字串。

在這種情況下,執行位有何相關性?

相關內容