什麼是SQL隱碼攻擊

利用網頁應用程式把使用者的輸入直接串接來組成SQL敘述,以輸入改變命令的意義,不當操作資料庫的攻擊。使用預留位置的參數化查詢(prepared statement)是根本的對策。

日文名稱: SQLインジェクション

「SQL隱碼攻擊」出現在1領域的3道練習題中(資訊安全基礎等)。

這個名詞所屬的領域: 資訊安全基礎

攻擊成立的機制

若應用程式以字串串接「… WHERE name = '」、輸入值與「'」來組成SQL敘述,輸入中的引號就會把字串結束,其後的部分會被解讀為SQL命令。以教科書常用的輸入 ' OR '1'='1 為例,會附加上「或'1'等於'1'」這個永遠成立的條件,使驗證被繞過。也可能導致資料被讀取、竄改或刪除。

根本的對策

根本的對策是使用預留位置的參數化查詢(prepared statement)。先確定SQL敘述的結構,之後只把輸入當作值結合進去,因此不論包含什麼字元,都不會成為命令的一部分。許多程式語言的資料庫函式庫與框架都提供此功能。從輸入去除特殊字元的方法容易有遺漏,而瀏覽器端的輸入檢查會被攻擊者繞過,因此單靠這些都不能算是對策。

縮小損害的對策

在根本對策之外,還要重疊以下對策:把應用程式連接資料庫的帳號權限設為最低限度(最小權限原則)、不對使用者顯示詳細的錯誤訊息,以及以WAF(網頁應用程式防火牆)偵測典型的攻擊字串。WAF只是輔助,無法取代應用程式本身的修正。

練習SQL隱碼攻擊的題目

作為SQL隱碼攻擊的對策,使用預留位置的參數化查詢(prepared statement),被視為比去除輸入中危險字元的方法更根本的對策。理由是什麼?

  1. A把輸入加密後再傳給資料庫,因此攻擊者無法讀取內容
  2. B在瀏覽器端檢查輸入的字元種類,因此不當的字串不會送到伺服器
  3. C先確定SQL敘述的結構,之後只把輸入當作值傳入,因此無論輸入包含什麼字元,都不會被解讀為命令的一部分
查看答案與解析

正確答案:C. 先確定SQL敘述的結構,之後只把輸入當作值傳入,因此無論輸入包含什麼字元,都不會被解讀為命令的一部分

使用參數化查詢時,先把值的部分以符號(預留位置)表示的SQL敘述,例如「SELECT … WHERE id = ? AND password = ?」,交給資料庫確定其結構,之後再把輸入只當作值結合進去(繫結)。輸入自始至終都被當作資料處理,即使包含引號,也不會成為附加條件之類的命令的一部分。去除或跳脫危險字元的方法,必須毫無遺漏地處理各種資料庫與字元編碼的細部規則,只要有一處遺漏,攻擊就會成功。此外,在瀏覽器端檢查輸入,只要攻擊者不經瀏覽器直接送出請求就能繞過,因此只是為了便利,並不是安全對策。再加上把連接資料庫的帳號權限設為最小,就能縮小損害。

常見問題

SQL隱碼攻擊能以跳脫處理防止嗎?

跳脫處理在某些情況下可以防止,但必須毫無遺漏地處理各種資料庫與字元編碼的規則,只要有一處遺漏,攻擊就會成功。因此要以使用預留位置的參數化查詢作為基本對策。

限制輸入的字數能防止SQL隱碼攻擊嗎?

不能。即使是短字串也可能改變命令的意義。限制字數或字元種類只是輔助對策,根本的對策是參數化查詢。

解析中的「SQL隱碼攻擊」

出現「SQL隱碼攻擊」的題目(3題)

  1. 作為SQL隱碼攻擊的對策,使用預留位置的參數化查詢(prepared statement),被視為比去除輸入中危險字元的方法更根本的對策。理由是什麼?
  2. 下列何者是社交工程的例子?
  3. 在某網頁應用程式的登入畫面中,只要在密碼欄位輸入 ' OR '1'='1 之類的字串,不知道密碼也能登入。這種攻擊稱為什麼?

相關名詞

SQL 社交工程 網路釣魚 公開金鑰加密 多因素驗證 訊息鑑別碼 勒索軟體 最小權限原則 跨網站指令碼(XSS) 零時差攻擊

前往名詞解釋列表