1、緩沖區下溢
本文將描述另一種緩沖區溢出情況,即緩沖區下溢。在前續專題(見第7期)中已對緩沖區上溢進行了分析。原因同樣適用于緩沖區下溢,所以在本文中不再重復介紹導致緩沖區上溢的因素。說得簡單點,緩沖區下溢是指填充數據溢出時,下一級緩沖區被覆蓋的情況。本文將描述緩沖區下溢的危害、在源代碼中顯露的跡象以及如何解決這個問題。
2、 緩沖區下溢的危害
在 C/c++ 程序中,緩沖區下溢是一種嚴重的漏洞類型,可能導致程序崩潰或執行惡意代碼等后果。從2018年1月到10月,共涉及494條CVE漏洞信息。部分漏洞如下:
CVE | 漏洞概述 |
---|---|
CVE-2018-1000001 | Libc Realpath 緩沖區下溢漏洞,漏洞的產生是由于 gnu C 庫沒有正確處理 getcwd() 系統調用返回的相對路徑,其他庫也很可能受此影響。在受影響的系統中,通過 SUID binary 可以獲得 root 權限。 |
CVE-2018-1000637?? | zutils 是一款壓縮文件處理實用程序包。該程序支持壓縮/解壓縮、壓縮文件比較和壓縮文件完整性校驗等功能。zcat 是其中的一個解壓縮實用程序。zutils 1.8-pre2 之前版本中的 zcat 存在緩沖區溢出漏洞。攻擊者可借助特制的壓縮文件利用該漏洞造成拒絕服務或執行任意代碼。 |
CVE-2018-5388 | strongSwan 5.6.3 之前版本在實現上存在緩沖區下溢漏洞,攻擊者利用此漏洞可耗盡資源,導致拒絕服務。 |
3、示例代碼
示例源于 Samate Juliet Test Suite for C/C++ v1.3 (https://samate.nist.gov/SARD/testsuite.php),源文件名:CWE121_Stack_Based_Buffer_Overflow__CWE193_char_alloca_cpy_01.c。
3.1 缺陷代碼
在上述示例代碼中,在第36行對指針 data 進行賦值,通過賦值操作可以看出指針 data 指向 dataBadBuffer,當第41行使用 strcpy() 進行內存拷貝時,源緩沖區長度大于目的緩沖區長度從而產生溢出,溢出部分超出了 dataBadBuffer 的下邊界,導致緩沖區下溢問題。
立即學習“C++免費學習筆記(深入)”;
使用360代碼衛士對上述示例代碼進行檢測,可以檢出“緩沖區下溢”缺陷,顯示等級為高。如圖1所示:
圖1:緩沖區下溢檢測示例
3.2 修復代碼
在上述修復代碼中,Samate 給出的修復方式為:在第37行對指針 data 進行賦值,將 data指向 dataGoodBuffer,此時 data 的長度與 source 一致,當第42行使用 strcpy() 進行拷貝操作時,源緩沖區與目的緩沖區長度相同,從而避免了緩沖區下溢的問題。該問題也可以通過對邊界進行檢查等其他方法來進行避免。
使用360代碼衛士對修復后的代碼進行檢測,可以看到已不存在“緩沖區下溢”缺陷。如圖2:
圖2:修復后檢測結果
4?、如何避免緩沖區下溢
要避免緩沖區下溢,需要注意以下幾點:
(1)盡量避免使用不安全的內存操作函數。(2)對返回值有明確指示意義的內存操作函數,應對函數返回值進行有效判斷,從而判斷操作是否成功。(3)在向緩沖區中填充數據時必須進行邊界檢查。