ANSI轉義序列是為終端設計的控制代碼,不是為語言模型準備的。它們可以改變顏色、隱藏文本、清屏或移動光標,人類在渲染后的終端里看不到這些代碼本身,只能看到它們產生的效果。但語言模型在讀取同一段內容時,卻能看到每一個字節。
這種差異就是整次攻擊的核心。攻擊者若能把ANSI轉義序列混入AI代理消費的文本中,就能在人類審閱輸出時隱藏指令,同時讓模型清清楚楚地讀到這些指令。這屬于輸出中性化失敗的同類缺陷:Kubernetes的kubectl曾接受Event字符串中的控制序列,可能偽造終端輸出(CVE-2021-25743);Git在打印遠端側帶消息時也未對終端控制符做中性化處理(CVE-2024-52005)。
在模型上下文協議(MCP)中,服務器會暴露工具、資源和提示,并把文本直接流式傳遞給代理,模型讀取的每個字段都可能成為注入面。這種攻擊也因此被稱作ANSI轉義序列注入(AESI)。
ANSI轉義序列的歷史可以追溯到上世紀70年代,當時各廠商的硬件終端各自使用不兼容的控制方言。ANSI X3.64標準將它們統一起來:程序只需發出一套公認的代碼,就能移動光標、清屏或設置顏色,任何符合標準的終端都會照做。這些控制能力原本是為了可移植地操控文本終端,如今卻成了此類攻擊所濫用的機制。
一段ANSI轉義序列以轉義字節(ESC,十六進制0x1B)開頭,后跟終端視為命令的控制代碼。這里涉及兩類關鍵代碼:隱藏文本的隱匿碼,以及清屏、移動光標或擦除行以消除或覆蓋正常輸出的屏幕與光標控制碼。渲染過程把這些字節從人眼中隱藏起來,模型卻處理的是原始文本。在人看來是空行或一份整潔報告的內容,對代理而言可能承載著完整的指令集。
許多MCP服務器會暴露一個抓取URL并將內容返回給模型的工具,例如“總結此頁面”或“閱讀此文檔”這類功能。這正是直接獲取型AESI的典型入口。攻擊者可以在遠端內容中植入經過精心構造的ANSI轉義序列,當模型拉取并解析時,隱藏的指令就會進入上下文。
與此并存的還有存儲型AESI:攻擊者將負載預先寫入會被多次讀取的存儲位置,比如日志、評論或文檔,隨后當代理通過工具訪問這些內容時,攻擊負載便隨之觸發。無論哪種方式,人類運維人員通過終端查看原始輸出時,往往只能看到表面正常的文本。
要捕獲這類缺陷,動態應用安全測試(DAST)是自然的路徑。Bright掃描器從外部對運行中的目標進行探測,發送精心構造的輸入,并檢查真實響應中是否存在漏洞證據,整個過程無需訪問源代碼。這種黑盒、運行時姿態恰好符合AESI檢測的需求,因為負載能否存活完全取決于實時服務器如何處理和轉發它。
在檢測過程中,掃描器會向工具參數、資源字段或提示內容注入含有隱蔽控制序列的負載,隨后在模型的響應中尋找證據,比如是否出現了本應被隱藏的指令,或者終端渲染行為是否被意外觸發。一旦發現模型執行了未對使用者可見的操作,即可判定存在注入風險。
MCP生態中,工具返回的原始文本通常不加過濾地流入模型上下文,這使得ANSI轉義序列的危害被放大。即便人類審查者事后查看日志,也可能因為控制碼被終端執行而看不到真實內容。因此,在服務器輸出進入模型之前進行輸出凈化,以及在輸入端對控制字符做嚴格過濾,是當前階段必要的防護手段。
特別聲明:以上內容(如有圖片或視頻亦包括在內)為自媒體平臺“網易號”用戶上傳并發布,本平臺僅提供信息存儲服務。
Notice: The content above (including the pictures and videos if any) is uploaded and posted by a user of NetEase Hao, which is a social media platform and only provides information storage services.