• <menu id="w2i4a"></menu>
  • logo Parasoft C/C++test 使用教程

    文檔首頁>>Parasoft C/C++test 使用教程>>1個技巧教你如何應對緩沖區(qū)溢出和其他內(nèi)存管理錯誤

    1個技巧教你如何應對緩沖區(qū)溢出和其他內(nèi)存管理錯誤



    內(nèi)存管理充滿危險,尤其是在C和C++中。實際上,與內(nèi)存管理弱點相關的錯誤占CWE Top 25的很大一部分。前25名中的八個與緩沖區(qū)溢出、不良指針和內(nèi)存管理直接相關。

    最大的軟件弱點是CWE-119,“內(nèi)存緩沖區(qū)范圍內(nèi)的操作限制不當”。這些類型的錯誤在各種軟件的安全性和安全性問題中占主導地位,包括汽車,醫(yī)療設備和航空電子設備中的安全關鍵型應用程序。

    以下是與CWE Top 25中常見的漏洞枚舉有關的內(nèi)存錯誤:


    盡管這些錯誤困擾了C,C++和其他語言數(shù)十年,但如今它們?nèi)栽谝栽絹碓蕉嗟臄?shù)量出現(xiàn)。就質(zhì)量、安全性和可靠性的后果而言,它們是危險的錯誤,并且它們的存在是導致安全漏洞的主要原因。


    安全漏洞的主要原因

    Microsoft發(fā)現(xiàn),在過去的12年中,其產(chǎn)品中超過70%的安全漏洞是由于內(nèi)存安全問題引起的。這些類型的錯誤是其應用程序的最大攻擊面,黑客正在使用它。根據(jù)他們的研究,安全攻擊的最根本原因是堆越界,釋放后使用和未初始化的使用。正如他們指出的那樣,漏洞類別已經(jīng)存在了20年或更長時間,并且在今天仍然很流行。

    谷歌以類似的方式發(fā)現(xiàn),Chromium項目(Chrome瀏覽器的開源基礎)中70%的安全漏洞是由于這些相同的內(nèi)存管理問題引起的。它們的最根本原因還在于免檢后使用,其次是其他不安全的內(nèi)存管理。

    考慮到這些實際發(fā)現(xiàn)的示例,軟件團隊必須認真對待這些類型的錯誤,這一點至關重要。幸運的是,有一些方法可以通過有效而有效的靜態(tài)分析來預防和檢測這些類型的問題。


    內(nèi)存管理錯誤如何變成安全漏洞

    在大多數(shù)情況下,內(nèi)存管理錯誤是由于不良的編程習慣所導致的,原因是在C/C++中使用了指針并直接訪問了內(nèi)存。在其他情況下,這與對數(shù)據(jù)的長度和內(nèi)容做出錯誤的假設有關。

    這些軟件弱點最常被污染數(shù)據(jù)利用,這些數(shù)據(jù)來自應用程序外部,未經(jīng)檢查其長度或格式。臭名昭著的Heartbleed漏洞是利用緩沖區(qū)溢出的一種情況。從技術上講,這是緩沖區(qū)溢出。正如我們在上一個博客中有關SQL注入的討論中所討論的那樣,使用未經(jīng)檢查和不受約束的輸入會帶來安全風險。

    讓我們考慮一下內(nèi)存管理軟件弱點的一些主要類別。最重要的一個是CWE-119:在內(nèi)存緩沖區(qū)范圍內(nèi)對操作的不當限制。

    緩沖區(qū)溢出

    允許直接訪問內(nèi)存并且不自動驗證訪問的位置是否有效且容易發(fā)生內(nèi)存損壞錯誤的編程語言(通常為C和C++)。這種損壞可能發(fā)生在內(nèi)存的數(shù)據(jù)和代碼區(qū)域中,從而可能暴露敏感信息,導致意外的代碼執(zhí)行或?qū)е聭贸绦虮罎ⅰ?

    以下示例顯示了CWE-120緩沖區(qū)溢出的經(jīng)典情況:

    char last_name[20];
    printf ("Enter your last name: ");
    scanf ("%s", last_name);

    在這種情況下,對來自scanf()的用戶輸入沒有任何限制,但last_name的長度限制為20個字符。輸入超過20個字符的姓氏,最終會將用戶輸入復制到內(nèi)存中,超出了緩沖區(qū)last_name的限制。這是CWE-119的一個更微妙的示例:

    void host_lookup(char *user_supplied_addr){
    struct hostent *hp;
    in_addr_t *addr;
    char hostname[64];
    in_addr_t inet_addr(const char *cp);
    
    /*routine that ensures user_supplied_addr is in the right format for conversion */
    
    validate_addr_form(user_supplied_addr);
    addr = inet_addr(user_supplied_addr);
    hp = gethostbyaddr( addr, sizeof(struct in_addr), AF_INET);
    strcpy(hostname, hp->h_name);
    }

    此函數(shù)采用用戶提供的包含IP地址(例如127.0.0.1)的字符串,并檢索其主機名。

    該函數(shù)驗證用戶輸入(好!),但不檢查gethostbyaddr()的輸出(不好!)。 在這種情況下,較長的主機名足以溢出當前僅限于64個字符的主機名緩沖區(qū)。 請注意,如果在找不到主機名時gethostaddr()返回null,那么也會出現(xiàn)null指針取消引用錯誤!

    釋放后使用錯誤

    有趣的是,Microsoft在他們的研究中發(fā)現(xiàn),售后使用錯誤是他們面臨的最常見的內(nèi)存管理問題。顧名思義,該錯誤與訪問先前釋放的內(nèi)存的指針(對于C/C++)有關。C和C++通常依靠開發(fā)人員來管理內(nèi)存分配,這對于完全正確地進行操作通常很棘手。如以下示例(來自CWE-416)所示,通常很容易假設指針仍然有效:

    char* ptr = (char*)malloc (SIZE);
    if (err) {
    abrt = 1;
    free(ptr);
    }
    ...
    if (abrt) {
    logError("operation aborted before commit", ptr);
    }

    在上面的示例中,如果err為true,則指針ptr是空閑的,但是如果abrt為true(則設置為true,如果err為true),則在釋放之后,指針ptr稍后將被取消引用。這似乎是人為的,但是如果這兩個代碼段之間有很多代碼,則很容易忽略。此外,這可能僅在未經(jīng)過正確測試的錯誤情況下發(fā)生。

    空指針解除引用

    軟件的另一個常見弱點是使用預期有效但為NULL的指針(或C++Java中的對象)。盡管這些取消引用在Java之類的語言中被視為異常,但它們可能導致應用程序停止、退出或崩潰。以Java為例,從CWE-476中獲取以下示例:

    String cmd = System.getProperty("cmd");
    cmd = cmd.trim();

    由于開發(fā)人員可能會假定getProperty()方法始終返回某些內(nèi)容,因此這看起來很無害。實際上,如果屬性“cmd”不存在,則返回NULL,在使用該屬性時會導致NULL解除引用異常。盡管這聽起來不錯,但卻可能導致災難性的后果。

    在極少數(shù)情況下,當NULL等于0x0內(nèi)存地址并且特權代碼可以訪問它時,就可以寫入或讀取內(nèi)存,這可能導致代碼執(zhí)行。


    緩解措施

    開發(fā)人員應實施幾種緩解措施。首先,開發(fā)人員需要通過經(jīng)過驗證的邏輯和全面檢查,確保指針對C和C++等語言有效。

    對于所有語言,任何操作內(nèi)存的代碼或庫都必須驗證輸入?yún)?shù),以防止越界訪問。以下是一些可用的緩解措施。但是開發(fā)人員不應依靠它們來彌補不良的編程習慣。

    編程語言選擇

    某些語言提供了針對溢出的內(nèi)置保護,例如Ada和C#。

    安全庫的使用

    可以使用諸如Safe C字符串庫之類的提供內(nèi)置檢查以防止內(nèi)存錯誤的庫。但是,并非所有緩沖區(qū)溢出都是字符串操作的結果。除此以外,程序員應始終使用以緩沖區(qū)長度作為參數(shù)的函數(shù),例如strncpy()與strcpy()。

    編譯和運行時強化

    這種方法利用了編譯選項,這些選項將代碼添加到應用程序中以監(jiān)視指針的使用情況。此添加的代碼可以防止在運行時發(fā)生溢出錯誤。

    執(zhí)行環(huán)境強化

    操作系統(tǒng)具有防止在應用程序的數(shù)據(jù)區(qū)域中執(zhí)行代碼的選項,例如帶有代碼注入的堆棧溢出。還有一些選項可以隨機排列內(nèi)存映射,以防止黑客預測可利用代碼的位置。

    盡管有這些緩解措施,但還是沒有替代適當?shù)木幋a實踐來避免緩沖區(qū)溢出的問題。因此,檢測和預防對于降低這些軟件漏洞的風險至關重要。


    轉移檢測和消除緩沖區(qū)溢出

    在軟件開發(fā)中采用DevSecOps方法意味著將安全性集成到DevOps管道的各個方面。正如在SDLC中盡早推動代碼分析和單元測試之類的質(zhì)量過程一樣,安全性也是如此。

    如果開發(fā)團隊更廣泛地采用這種方法,則緩沖區(qū)溢出和其他內(nèi)存管理錯誤可能已成為過去。正如Google和Microsoft的研究表明的那樣,這些錯誤仍占其安全漏洞的70%。無論如何,讓我們概述一種可以盡早阻止它們的方法。

    與修補已發(fā)布的應用程序相比,查找和修復內(nèi)存管理錯誤可節(jié)省大量時間。下面概述的檢測和阻止方法基于將緩沖區(qū)溢出的緩解向左轉移到開發(fā)的最早階段。并通過靜態(tài)代碼分析進行檢測來增強這一點。

    偵測

    檢測內(nèi)存管理錯誤依賴于靜態(tài)分析以在源代碼中找到這些類型的漏洞。檢測發(fā)生在開發(fā)人員的桌面和構建系統(tǒng)中。它可以包括現(xiàn)有的、舊的和第三方代碼。

    連續(xù)檢測安全問題可確保找到以下所有問題:

    • 開發(fā)人員錯過了IDE。
    • 存在于比您的新的檢測預防方法還早的代碼中。

    推薦的方法是信任但驗證模型。安全性分析是在IDE級別上完成的,開發(fā)人員在該級別上根據(jù)所獲得的報告做出實時決策。接下來,在構建級別進行驗證。理想情況下,構建級別的目標不是找到漏洞。這是為了驗證系統(tǒng)是否干凈。

    Parasoft C/C++test包括針對這些類型的內(nèi)存管理錯誤(包括緩沖區(qū)溢出)的靜態(tài)分析檢查器??紤]以下示例,該示例取自C/C++測試。

    Parasoft C/C++test示例:檢測越界內(nèi)存訪問

    xx:Parasoft C/C++test示例,顯示了對越界內(nèi)存訪問的檢測。

    放大細節(jié),函數(shù)printMessage()錯誤會檢測到錯誤:

    Parasoft-C/C++test錯誤示例

    Parasoft C/C++test還提供有關該工具如何出現(xiàn)此警告的跟蹤信息:

    跟蹤信息的Parasoft C/C++test示例

    邊欄顯示有關如何修復此漏洞的詳細信息以及適當?shù)膮⒖迹?

    修復的ParasoftC/C++test示例

    準確的檢測以及支持信息和補救建議對于使靜態(tài)分析和對這些漏洞的早期檢測非常有用,并使開發(fā)人員可立即采取行動至關重要。

    防止緩沖區(qū)溢出和其他內(nèi)存管理錯誤

    防止緩沖區(qū)溢出的理想時間和地點是開發(fā)人員在其IDE中編寫代碼時。采納安全編碼標準的團隊,例如C和C++SEI CERT C和Java和.NET的OWASP Top 10或CWE的Top 25,都具有警告內(nèi)存管理錯誤的準則。

    例如,CERT C包括以下有關內(nèi)存管理的建議:

    CERT C REC 08內(nèi)存管理(MEM)列表

    這些建議包括預防性編碼技術,這些技術可首先避免內(nèi)存管理錯誤。每套建議都包括風險評估和修復成本,使軟件團隊可以按以下優(yōu)先級排列準則:

    CERT C REC 08內(nèi)存管理(MEM)表

    一項關鍵的預防策略是采用符合SEI CERT等行業(yè)準則的編碼標準,并在以后的編碼中強制執(zhí)行。通過更好的編碼實踐來預防這些漏洞更便宜、風險更低,并且投資回報率最高。

    對新創(chuàng)建的代碼進行靜態(tài)分析既快速又簡單。團隊很容易將其集成到桌面IDE和CI/CD流程中。為了防止將此代碼寫入到內(nèi)部版本中,最好在此階段調(diào)查所有安全警告和不安全的編碼做法。

    安全警告的Parasoft C/C++test示例

    Parasoft集成到Eclipse IDE中的屏幕截圖,它將預防和檢測漏洞帶到開發(fā)人員的桌面。

    檢測不良編碼實踐的同等重要的部分是報告的實用性。了解靜態(tài)分析違規(guī)的根本原因很重要,以便快速、有效地解決它們。這就是ParasoftC/C++test,dotTESTJtest等商業(yè)工具的發(fā)源地。

    Parasoft的自動測試工具可對警告進行完整跟蹤,在IDE中進行說明,并連續(xù)收集構建信息和其他信息。這些收集的數(shù)據(jù)以及測試結果和指標可提供對團隊編碼標準合規(guī)性以及總體質(zhì)量和安全狀態(tài)的全面了解。

    開發(fā)人員可以基于其他上下文信息(例如項目中的元數(shù)據(jù)、代碼的年齡以及負責代碼的開發(fā)人員或團隊)進一步過濾發(fā)現(xiàn)。帶有人工智能(AI)和機器學習(ML)的Parasoft之類的工具使用此信息來幫助進一步確定最關鍵的問題。

    儀表板和報告包括風險模型,這些模型是OWASP、CERT和CWE提供的信息的一部分。這樣,開發(fā)人員可以更好地了解該工具報告的潛在漏洞的影響以及應優(yōu)先考慮哪些漏洞。在IDE級別生成的所有數(shù)據(jù)都與上面概述的下游活動相關。


    總結

    緩沖區(qū)溢出和其他內(nèi)存管理錯誤繼續(xù)困擾著應用程序。它們?nèi)匀皇前踩┒吹闹饕颉1M管知道它是如何工作和被利用的,但它仍然很普遍。有關最新示例,請參考IoT Hall of Shame。

    我們提出了一種預防和檢測方法來補充主動安全性測試,該方法可以防止緩沖區(qū)溢出在SDLC中盡早將其寫入代碼之前。防止在IDE上出現(xiàn)此類內(nèi)存管理錯誤并在CI/CD管道中檢測到這些錯誤,是將其從軟件中路由出去的關鍵。

    智能軟件團隊可以最大程度地減少內(nèi)存管理錯誤。他們可以通過其現(xiàn)有工作流程中正確的流程、工具和自動化來對質(zhì)量和安全性產(chǎn)生影響。


    掃碼咨詢


    添加微信 立即咨詢

    電話咨詢

    客服熱線
    023-68661681

    TOP
    三级成人熟女影院,欧美午夜成人精品视频,亚洲国产成人乱色在线观看,色中色成人论坛 (function(){ var bp = document.createElement('script'); var curProtocol = window.location.protocol.split(':')[0]; if (curProtocol === 'https') { bp.src = 'https://zz.bdstatic.com/linksubmit/push.js'; } else { bp.src = 'http://push.zhanzhang.baidu.com/push.js'; } var s = document.getElementsByTagName("script")[0]; s.parentNode.insertBefore(bp, s); })();