檢查shellshock指令的解釋

檢查shellshock指令的解釋

以下是我用來檢查 bash shell 是否存在 Shellshock bug 的指令:

env x='() { :;}; echo vulnerable' bash -c "echo this is a test"

誰能詳細解釋一下該命令嗎?

答案1

這個答案是一個衍生的Fedora 雜誌上的原文文章由馬修米勒 (Matthew Miller) 授權,知識分享署名-相同方式分享 4.0執照。

讓我解釋:

env x='() { :;}; echo OOPS' bash -c :

這將在易受攻擊的系統上列印“OOPS”,但如果 bash 已修補,則會靜默退出。

env x='() { :;}; echo OOPS' bash -c "echo this is a test"

這將在易受攻擊的系統上列印“OOPS”,但“this is a test”如果 bash 已修補則列印。

您可能聽說過它與環境變數有關。但是,為什麼環境變數中的程式碼會被執行呢?嗯,它不應該是這樣的——但是,由於我很想稱其為有點過於聰明的功能,因此存在一些缺陷的空間。 Bash 是您所看到的終端提示符,但它也是一種腳本語言,並且具有定義函數的能力。你這樣做:

$ Ubuntu()  { echo "Ubuntu is awesome."; }

然後你就有了一個新指令。請記住,echo這裡還沒有真正運行;它只是保存為我們運行新命令時會發生的情況。稍後這將很重要!

$ Ubuntu
 Ubuntu is awesome.

有用!但是,假設出於某種原因,我們需要執行一個新的 bash 實例作為子進程,並希望在該實例下運行我很棒的新命令。該語句bash -c somecommand正是這樣做的:在新 shell 中執行給定的命令:

$ bash -c Ubuntu
  bash: Ubuntu: command not found

哦。傷心。孩子沒有繼承函數定義。但是,它確實具有固有的環境——從 shell 導出的鍵值對的集合。 (這是一個完整的概念;如果您對此不熟悉,請暫時相信我。)而且,事實證明,bash 也可以導出函數。所以:

$ export -f Ubuntu
$ bash -c Ubuntu
  Ubuntu is awesome.

這一切都很好——除了實現這一點的機制是有點狡猾。基本上,由於沒有 Linux/Unix 魔法可以在環境變數中執行函數,因此導出函數實際上只是建立一個包含函數定義的常規環境變數。然後,當第二個 shell 讀取「傳入」環境並遇到內容看起來像函數的變數時,它會對其進行求值。

理論上,這是萬無一失,因為,記住,定義一個函數實際上並不執行它。除了——這就是我們在這裡的原因——程式碼中存在一個錯誤,即到達函數定義末尾時求值沒有停止。它就這樣繼續下去。

當儲存在環境變數中的函數是使用export -f.但是,為什麼要合法呢?攻擊者可以偽造任何舊的環境變量,如果它看起來像函數,新的 bash shell 就會認為它是函數!

所以,在我們的第一個例子中:

env x='() { :;}; echo OOPS' bash -c "echo this is a test"

env命令運行具有給定變數集的命令。在本例中,我們設定x的值看起來像是函數。這個函數只是一個單一的:,它實際上是一個簡單的命令,被定義為不執行任何操作。但是,在semi-colon表示函數定義結束的which 之後,有一個echo命令。那不應該在那裡,但沒有什麼可以阻止我們這樣做。

然後,在這個新環境中運行的命令是一個新的 bash shell,同樣帶有“ echo this is a test”或“不執行任何操作:”命令,之後它將完全無害地退出。

但是——哎呀!當新的 shell 啟動並讀取環境時,它會獲取該x變量,並且由於它看起來像函數,因此它會對其進行評估。函數定義被無害地載入——然後我們的惡意負載也會被觸發。因此,如果您在易受攻擊的系統上運行上述內容,您將會收到“OOPS”列印訊息。或者,攻擊者可能會做比僅僅列印內容更糟糕的事情。

答案2

未打補丁的版本bash它將導出的函數定義儲存為環境變數。

將函數儲存x為,

$ x() { bar; }
$ export -f x

並檢查其定義為,

$ env | grep -A1 x
x=() {  bar
}

因此,人們可以透過定義自己的環境變數來利用這一點,並將它們解釋為函數定義。例如env x='() { :;}'將被視為

x() { :;
}

檢查 shellshock 的指令有什麼作用,

env x='() { :;}; echo vulnerable' bash -c "echo this is a test"

man env

  1. env- 在修改後的環境下執行程式。

  2. :除了以 exit status 退出之外什麼也不做0。看更多的

  3. 當未修補的 bash 的新實例作為 啟動時bash -c "echo this is a test",精心設計的環境變數將被視為函數並載入。因此得到輸出

    易受傷害的
    這是一個測試

筆記:bash 啟動期間,函數定義以外的 echo 被意外執行。函數定義只是進行評估和利用的一個步驟,函數定義本身和使用的環境變數是任意的。 shell 查看環境變量,看到 x,它看起來滿足它所知道的函數定義的約束,並且它評估該行,無意中還執行了 echo(可能是任何命令,無論是否惡意) 。另請參閱

相關內容