I. 介紹II. 背景A. 開發(fā)流程B. 谷歌的程序分析III. 谷歌程序分析理念A. 0誤報率B. 授權(quán)用戶做出貢獻(xiàn)C. 改進(jìn)數(shù)據(jù)驅(qū)動的可用性D. 工作流集成是關(guān)鍵E. 項(xiàng)目級別定制笤虫,而不是用戶定制IV. 實(shí)現(xiàn)A. 架構(gòu)B. 插件模型C. 分析器D. 修復(fù)E. 反饋V. 成果a)可用性:b)代碼庫影響:c)擴(kuò)展性:d)可伸縮性:VI.相關(guān)工作VII. 探討VIII. 致謝引用
譯者的話
????許多公司痛苦于將如何將SDL落地到企業(yè)開發(fā)流程中,而代碼審計(jì)的環(huán)節(jié)相對容易實(shí)踐起來超歌。在對標(biāo)學(xué)習(xí)期間順手翻譯了這篇google的最佳實(shí)踐顷编,當(dāng)然Google绳矩、Netflix、SAP、salesfore拌消、Amazon這類公司不會稱其為SDLC,使用了DevSecOps的方法論這種說法,推行起來對于人員要求也較高安券,但是面臨著行業(yè)的痛點(diǎn)是共性墩崩。知易行難氓英,大家可以參考指標(biāo)以避免走彎路,去做正確的事情鹦筹。
其他關(guān)聯(lián)閱讀資料:
*?[為什么Google上十億行代碼都放在同一個倉庫里?](https://zhuanlan.zhihu.com/p/28524745)
*?[Google?如何建立程序分析生態(tài)系統(tǒng)](https://wenku.baidu.com/view/067d99eea0c7aa00b52acfc789eb172ded639975.html)?
原文鏈接:
[Tricorder:?Building?a?Program?Analysis?Ecosystem](https://static.googleusercontent.com/media/research.google.com/en//pubs/archive/43322.pdf)?
以下是正文:
????簡介-靜態(tài)分析工具幫助開發(fā)人員發(fā)現(xiàn)bug铝阐,提高代碼可讀性,并確保整個項(xiàng)目的風(fēng)格一致铐拐。然而當(dāng)擴(kuò)展到大型代碼庫時徘键,這些工具之間很難相互順利集成進(jìn)入開發(fā)流程中。我們提出了一個程序分析平臺TRICORDER遍蟋,旨在圍繞程序分析構(gòu)建一個數(shù)據(jù)驅(qū)動的生態(tài)系統(tǒng)吹害。我們?yōu)槲覀兊某绦蚍治龉ぞ咛峁┝艘惶字笇?dǎo)原則,并為實(shí)現(xiàn)這些原則的分析平臺提供了可伸縮的架構(gòu)虚青。我們對Google開發(fā)人員所使用的工具在實(shí)際的落地到生產(chǎn)系統(tǒng)進(jìn)行驗(yàn)證赠制,以顯示出該平臺的實(shí)用性和影響力。
I. 介紹
????靜態(tài)分析工具提供了一種很有前瞻性的方法挟憔,可以在程序的bug出現(xiàn)在生產(chǎn)系統(tǒng)之前找到它們钟些。開發(fā)者可以在源代碼上運(yùn)行分析程序來發(fā)現(xiàn)問題,甚至在合入代碼之前也可以绊谭。雖然對靜態(tài)分析工具[3]政恍、[14]、[16]等已有了詳盡的研究达传,但這些工具在實(shí)際應(yīng)用中往往沒有得到有效的落地篙耗。誤報率高凫岖、輸出混亂崖媚、與開發(fā)流程的整合性差,這些都導(dǎo)致了在日常開發(fā)活動[23]淳附、[27]中缺乏使用搂妻。
????除了發(fā)現(xiàn)bug之外蒙保,工具還必須考慮到開發(fā)人員對[26]時間的緊迫要求。任何由自動化工具產(chǎn)生的中斷輸出都會迫使開發(fā)人員從主要目標(biāo)[27]停頓下來欲主。成功的靜態(tài)分析工具可以增加高價值邓厕,同時最大限度地減少對已經(jīng)很繁忙的軟件工程師的干擾。
????我們過去使用靜態(tài)分析工具的經(jīng)驗(yàn)還表明扁瓢,其中許多工具無法擴(kuò)展到谷歌規(guī)模的代碼庫详恼。分析不能假定它們可以訪問整個源存儲庫或所有編譯結(jié)果;單個機(jī)器的數(shù)據(jù)太多了。?因此引几,分析必須是可分片的昧互,并且能夠作為分布式計(jì)算的一部分運(yùn)行,只包含部分信息。判斷分析必須非吵ň颍快叽掘,并在幾分鐘內(nèi)提供結(jié)果。在我們之前在谷歌的經(jīng)驗(yàn)中渐逃,現(xiàn)有的分析平臺無法以這種方式擴(kuò)展伸縮够掠。
????我們還發(fā)現(xiàn)現(xiàn)有的平臺和工具沒有足夠的可擴(kuò)展性。谷歌有許多專門的框架和語言茄菊,理想的系統(tǒng)應(yīng)該為所有這些框架和語言提供靜態(tài)分析疯潭。我們理想的系統(tǒng)將允許領(lǐng)域?qū)<揖帉懽约旱姆治觯鵁o需承擔(dān)構(gòu)建或維護(hù)整個端到端環(huán)節(jié)的成本面殖。例如竖哩,編寫c++庫的團(tuán)隊(duì)可以編寫檢查,以確保開發(fā)人員正確使用這些庫脊僚,而不必?fù)?dān)心運(yùn)行大型生產(chǎn)系統(tǒng)所固有的問題相叁。
????在谷歌上試錯了各種商業(yè)和開源程序分析工具之后(有關(guān)更多細(xì)節(jié),請參閱第二部分)辽幌,我們一再遇到工具可伸縮性或可用性方面的問題增淹。基于這些經(jīng)驗(yàn)教訓(xùn)乌企,我們想創(chuàng)建一個靜態(tài)分析平臺虑润,它將:
?開發(fā)人員廣泛而積極地使用它來修復(fù)代碼中的問題,而不需要得到一小群擁護(hù)者或管理層的鼓勵加酵。
?順利地集成到現(xiàn)有的軟件開發(fā)流程中拳喻。
?擴(kuò)展到海量代碼庫規(guī)模。
?使開發(fā)人員猪腕,甚至非軟件分析專家能夠編寫和部署他們自己的靜態(tài)分析規(guī)則冗澈。
????在本文中,我們介紹了TRICORDER陋葡,一個程序分析平臺亚亲,旨在圍繞靜態(tài)分析構(gòu)建數(shù)據(jù)驅(qū)動的生態(tài)系統(tǒng)。TRICORDER將靜態(tài)分析集成到谷歌開發(fā)人員的工作流程中脖岛,在開發(fā)人員和分析器編寫人員之間提供反饋循環(huán)朵栖,并簡化了分析工具發(fā)現(xiàn)的修復(fù)問題。為了實(shí)現(xiàn)這一點(diǎn)柴梆,TRICORDER利用微服務(wù)體系結(jié)構(gòu)來擴(kuò)展到谷歌的代碼庫,并且每天生成大約93,000個分析結(jié)果终惑。除了開發(fā)平臺的開源版本之外绍在,一個由2-3人組成的小團(tuán)隊(duì)維護(hù)著TRICORDER及其周圍的生態(tài)系統(tǒng)[35]。TRICORDER的插件模型允許整個公司的團(tuán)隊(duì)成員加入Google的程序分析社區(qū)
????本文的貢獻(xiàn)包括:
?一套指導(dǎo)原則,使谷歌的程序分析平臺獲得成功偿渡,得到廣泛應(yīng)用臼寄。(第三節(jié))
?程序分析平臺的可擴(kuò)展架構(gòu)。該平臺通過工作流程集成溜宽,支持貢獻(xiàn)者吉拳,響應(yīng)反饋和自動修復(fù)來構(gòu)建程序分析生態(tài)系統(tǒng)。(第四節(jié))
?基于開發(fā)人員在正常工作流程中對分析的響應(yīng)适揉,對平臺的效用進(jìn)行實(shí)證和現(xiàn)場驗(yàn)證留攒。(第五部分)
II. 背景
A. 開發(fā)流程
????在谷歌中,大多數(shù)工程師都在一個非常大的代碼庫中工作嫉嘀,在這個代碼庫中炼邀,大多數(shù)軟件開發(fā)都是在head里進(jìn)行的。在谷歌剪侮,每個工作日拭宁,工程師執(zhí)行超過800k構(gòu)建,運(yùn)行100萬個測試用例瓣俯,生成2PB的構(gòu)建輸出杰标,并發(fā)送30k變更列表快照(patch?diffs)供評審。
????大型代碼庫有很多好處彩匕,包括代碼復(fù)用的易用性和以原子粒度地進(jìn)行大規(guī)模重構(gòu)的能力腔剂。由于代碼復(fù)用很常見,大多數(shù)代碼依賴于一組核心庫推掸,對這些基本庫進(jìn)行更改可能會影響許多項(xiàng)目桶蝎。為了確保變更不會破壞其他項(xiàng)目,谷歌擁有強(qiáng)大的測試文化谅畅,并由持續(xù)測試基礎(chǔ)設(shè)施[43]登渣、[15]為后盾。
????谷歌工程師使用標(biāo)準(zhǔn)化的分布式構(gòu)建系統(tǒng)從源代碼[20]生成獨(dú)立構(gòu)建毡泻。一組專門的工程師集中維護(hù)這個基礎(chǔ)設(shè)施胜茧,提供了一個插入分析工具的通用配置。因?yàn)楣雀韫こ處熓褂孟嗤姆植际綐?gòu)建環(huán)境仇味,所以他們可以使用自己選擇的編輯器呻顽。編輯器的選擇包括但不限于Eclipse、IntelliJ丹墨、emacs和vim[38]廊遍。作為一種強(qiáng)大的代碼評審文化的一部分,每一個新的補(bǔ)丁贩挣,稱為變更列表喉前,在簽入之前都會由其他人的人來評審没酣。工程師使用類似Gerrit[19]的內(nèi)部代碼審查工具執(zhí)行這些審查。此工具提供了對代碼行進(jìn)行注釋卵迂,回復(fù)現(xiàn)有注釋裕便,上載正在審閱的代碼(作者)的新快照以及批準(zhǔn)更改列表(審閱者)的功能。
????繁忙的工程師測試(并分析)他們自己的代碼见咒,而不是使用單獨(dú)的QA流程偿衰。這意味著分析結(jié)果必須以工程師為目標(biāo),并且這些工程師必須易于運(yùn)行和響應(yīng)分析程序改览。因?yàn)榇蠖鄶?shù)要發(fā)布的代碼都是服務(wù)器代碼下翎,所以推出新版本的成本非常低,使得在代碼發(fā)布后修復(fù)bug相對容易恃疯。
B. 谷歌的程序分析
????為了將程序分析工具集成到谷歌開發(fā)工作流中漏设,已經(jīng)進(jìn)行了幾次嘗試。特別是findbugs[18]在谷歌[5]今妄、[3]郑口、[4]以及Coverity[12]、Klocwork[24]盾鳞、故障預(yù)測[28]等分析工具上都有很長的實(shí)驗(yàn)歷史犬性。由于工作流集成、可伸縮性和誤報方面的問題腾仅,所有這些工具在很大程度上已經(jīng)不再使用乒裆。有些工具顯示結(jié)果太遲,使得開發(fā)人員在提交代碼后不太可能修復(fù)問題推励。另一些人過早地顯示結(jié)果鹤耍,而開發(fā)人員仍然在編輯器中使用他們的代碼⊙榇牵基于編輯器的工具也遇到了擴(kuò)展問題:它們對交互使用的延遲需求無法跟上代碼庫的大小稿黄。幾乎所有的工具都必須作為一個獨(dú)立的步驟來運(yùn)行,并且很難與標(biāo)準(zhǔn)編譯器工具鏈集成跌造。我們一再發(fā)現(xiàn)杆怕,當(dāng)開發(fā)人員必須導(dǎo)航到儀表板或運(yùn)行獨(dú)立的命令行工具時,分析使用率就會下降壳贪。
????即使在開發(fā)人員運(yùn)行這些工具時陵珍,它們也常常產(chǎn)生很高的誤報率和無法執(zhí)行的結(jié)果[28]。這些經(jīng)驗(yàn)與之前的研究一致违施,說明了為什么開發(fā)人員不使用靜態(tài)分析工具[23]互纯。最后,很少有開發(fā)人員使用我們之前試驗(yàn)過的任何工具磕蒲,甚至在最引人注目的分析中-FindBugs伟姐,這個命令行工具在2014年也只被35個開發(fā)人員使用過(其中只有20個開發(fā)人員使用過一次)收苏。我們之前確實(shí)在代碼評審[3]中顯示了FindBugs結(jié)果亿卤,但是這個嘗試遇到了伸縮性問題(導(dǎo)致結(jié)果陳舊或延遲)愤兵,【譯者注:關(guān)于這一篇,可以看到《
【翻譯】Google在構(gòu)建靜態(tài)代碼分析工具方面的經(jīng)驗(yàn)教訓(xùn)
》】并且產(chǎn)生了許多開發(fā)人員不感興趣的結(jié)果排吴。相比之下秆乳,TRICORDER將成功作為標(biāo)準(zhǔn)開發(fā)流程的一部分。III. 谷歌程序分析理念
A. 0誤報率
????“0誤報”可能有點(diǎn)夸張钻哩,但我們嚴(yán)格限制了允許分析產(chǎn)生的誤報數(shù)量屹堰。誤報對可用性和采用[8]、[23]街氢、[33]都是不利的扯键。
關(guān)于“誤報”一詞的確切含義存在分歧。對于分析者來說珊肃,誤報是他們的分析工具產(chǎn)生的不正確的報告荣刑。然而,對于開發(fā)人員來說伦乔,任何他們不想看到[5]的報告都是誤報厉亏。
????我們傾向于使用“有效誤報率”這個術(shù)語來概括開發(fā)人員的觀點(diǎn)。我們將有效的誤報定義為來自工具的任何報告烈和,其中用戶選擇不采取行動來解決該報告爱只。作為一個例子,一些谷歌開發(fā)人員使用靜態(tài)注釋檢查系統(tǒng)(例如用于數(shù)據(jù)競爭檢測[34])招刹。當(dāng)一個注釋檢查工具正確地報告一個問題,它可能意味著有一個錯誤在源代碼中(例如,變量實(shí)際上不受鎖定保護(hù)),或者代碼實(shí)際上是正常的但是注釋集合不是足夠詳盡的工具恬试。通常在程序分析研究中,后者不被認(rèn)為是誤報——開發(fā)人員需要向工具提供額外的信息疯暑。然而训柴,一些開發(fā)人員認(rèn)為這些問題是“誤報”的,因?yàn)樗鼈儾淮泶a[36]中的錯誤缰儿。
????相反畦粮,我們發(fā)現(xiàn)如果分析錯誤地報告錯誤,但是提出建議的修復(fù)將提高代碼可讀性乖阵,這不被視為誤報宣赔。易讀性和文檔分析經(jīng)常被開發(fā)人員所接受,特別是當(dāng)他們提出改進(jìn)建議時瞪浸。值得注意的是儒将,某些分析可能在理論上有錯誤的假設(shè),但在實(shí)踐中卻沒有对蒲。例如钩蚊,只有當(dāng)程序以不尋常的方式構(gòu)建時贡翘,分析才可能具有誤報,但實(shí)際上砰逻,從未見過這樣的程序鸣驱。這樣的分析可能具有理論誤報,但在具有嚴(yán)格執(zhí)行的風(fēng)格指南的環(huán)境中蝠咆,它實(shí)際上將具有零誤報踊东。
????最重要的是,開發(fā)人員將決定分析工具是否具有高影響力刚操,以及誤報是什么闸翅。
B. 授權(quán)用戶做出貢獻(xiàn)
????在使用各種語言和自定義API的公司中,沒有任何一個團(tuán)隊(duì)擁有編寫所有必要分析所需的領(lǐng)域知識菊霜。整個公司的開發(fā)人員之間都存在相關(guān)的專業(yè)知識和動力坚冀,我們希望通過授權(quán)開發(fā)人員貢獻(xiàn)自己的分析來利用這些現(xiàn)有的知識。開發(fā)人員的貢獻(xiàn)既豐富了可用的分析集鉴逞,又使用戶對分析結(jié)果的貢獻(xiàn)更大记某。
然而,盡管這些貢獻(xiàn)者是他們領(lǐng)域內(nèi)的專家华蜒,但他們可能沒有足夠的知識或技能來有效地將他們的分析集成到開發(fā)人員工作流程中辙纬。理想情況下,使分析啟動并運(yùn)行所需的工作流集成和模板文件不應(yīng)該是分析作者所關(guān)心的叭喜。這就是TRICORDER的用武之地贺拣,它是一個可插入的程序分析平臺,支持整個公司的分析貢獻(xiàn)者捂蕴。
????為了保持分析程序的高質(zhì)量譬涡,我們與分析程序的編寫有一個“合同”,關(guān)于我們什么時候可以從TRICORDER中移除他們的分析程序的權(quán)利啥辨。也就是說涡匀,如果:
沒有人正在修復(fù)針對分析程序提交的bug。溉知。
資源使用(例如CPU?/磁盤/內(nèi)存)正在影響TRI-CORDER性能陨瘩。在這種情況下,分析器編寫器需要開始維護(hù)TRI-CORDER調(diào)用的獨(dú)立服務(wù)(有關(guān)詳細(xì)信息级乍,請參閱第四節(jié)a)舌劳。
分析器的結(jié)果讓開發(fā)人員很惱火(有關(guān)如何計(jì)算該值,請參見第IV-E節(jié))玫荣。
我們的經(jīng)驗(yàn)是甚淡,工作中的自豪感加上禁用分析程序的威脅捅厂,使得作者非常積極地解決分析程序發(fā)現(xiàn)的問題贯卦。
C. 改進(jìn)數(shù)據(jù)驅(qū)動的可用性
????回應(yīng)反饋很重要资柔。開發(fā)人員使用分析工具構(gòu)建信任,如果他們不理解工具的輸出[8]撵割,這種信任很快就會丟失贿堰。我們還發(fā)現(xiàn)(通過收集針對分析程序的bug報告),許多分析結(jié)果都有令人困惑的文字信息;這通常是一個容易解決的問題睁枕。例如官边,對于一個分析人員來說,來自TRICORDER的針對該工具的所有bug中外遇,75%是由于對結(jié)果措辭的錯誤解釋造成的,并通過更新消息文本和/或鏈接到其他文檔來修復(fù)契吉。建立反饋循環(huán)以提高分析結(jié)果的可用性可以顯著提高分析工具的實(shí)用性
D. 工作流集成是關(guān)鍵
????將開發(fā)人員的工作流程集成到有效的[23]程序分析工具中是一個關(guān)鍵方面跳仿。如果一個分析工具是開發(fā)人員希望運(yùn)行的獨(dú)立二進(jìn)制文件,那么它就不會像預(yù)期的那樣頻繁地運(yùn)行捐晶。我們認(rèn)為分析應(yīng)該由開發(fā)人員事件自動觸發(fā)菲语,例如編輯代碼,運(yùn)行構(gòu)建惑灵,創(chuàng)建/更新更改列表或提交更改列表山上。分析結(jié)果應(yīng)該在代碼檢入之前顯示,因?yàn)楫?dāng)工程師必須修改(可能工作的)提交代碼時英支,權(quán)衡是不同的佩憾。我們調(diào)查開發(fā)人員向他們發(fā)送更改列表以修復(fù)我們計(jì)劃在編譯器錯誤時打開的代碼中的錯誤,以及他們在編譯器錯誤中遇到這些錯誤時干花。當(dāng)遇到編譯器錯誤時妄帘,開發(fā)人員認(rèn)為錯誤代表重大錯誤的可能性是其兩倍。早期顯示結(jié)果的重要性與以前使用Find-Bugs?[3]的經(jīng)驗(yàn)相匹配池凄。
????如果可能抡驼,我們將靜態(tài)分析集成到構(gòu)建[2]中。我們支持基于ErrorProne的javac擴(kuò)展[17]和Clang編譯器[10]構(gòu)建的各種分析肿仑。這些分析在發(fā)現(xiàn)問題時會中斷構(gòu)建致盟,因此有效誤報率必須基本為零【譯者注:源代碼分析可以發(fā)現(xiàn)質(zhì)量、安全尤慰、測試類的問題馏锡,是否中斷構(gòu)建取決于企業(yè)質(zhì)量門的閾值】。它們也不能顯著地降低編譯速度割择,因此必須有<?5%的開銷眷篇。理想情況下,我們只顯示導(dǎo)致構(gòu)建失敗的結(jié)果荔泳,就像我們發(fā)現(xiàn)構(gòu)建經(jīng)常被忽略時顯示的警告一樣蕉饼。然而虐杯,構(gòu)建集成并不總是實(shí)用的,
????例如當(dāng)誤報率過高時昧港,分析過于耗時擎椰,或者僅在新編輯的代碼行上顯示結(jié)果是值得的。
????TRICORDER介紹了一個顯示警告的有效位置创肥。由于谷歌的所有開發(fā)人員在提交更改之前都使用代碼評審工具达舒,所以TRICORDER的主要用途是在代碼評審時提供分析結(jié)果。這樣做的另一個好處是啟用了對等的問責(zé)機(jī)制叹侄,審查人員將看到作者是否選擇忽略分析結(jié)果巩搏。我們?nèi)匀粓?zhí)行非常低的有效誤報率(<?10%)。此外趾代,默認(rèn)情況下贯底,我們只顯示更改行的大多數(shù)分析結(jié)果;這使得分析結(jié)果與手頭上的代碼評審保持一致。在代碼評審時完成的分析可能比中斷構(gòu)建的分析花費(fèi)更長的時間撒强,但是結(jié)果必須在評審結(jié)束前可用禽捆。審查多行的平均時間大于1小時;我們通常希望分析在不到5?10分鐘內(nèi)完成(理想情況下要少得多),因?yàn)殚_發(fā)人員可能在等待結(jié)果飘哨。
????對于程序分析胚想,還有其他潛在的集成點(diǎn)。許多ide包含各種靜態(tài)分析芽隆。然而浊服,大多數(shù)谷歌開發(fā)人員不使用ide,或者不使用ide來完成所有[38]任務(wù)摆马,這使得ide集成成為不可能臼闻。盡管如此,IDE并不排除IDE集成囤采,因?yàn)镮DE可以向TRICORDER服務(wù)發(fā)出rpc述呐。我們還利用測試來運(yùn)行動態(tài)分析工具,比如ThreadSanitizer?[39]蕉毯,[40]或AddressSanitizer[1]乓搬。這些工具通常沒有誤報和<10x的減速。TRICORDER還將谷歌的代碼搜索工具中的一些分析結(jié)果夜間顯示為可選圖層代虾。雖然大多數(shù)開發(fā)人員不使用該功能进肯,但對于誤報率較高的分析和具有專門的清理團(tuán)隊(duì)來篩選結(jié)果的分析來說十分有效。
E. 項(xiàng)目級別定制棉磨,而不是用戶定制
????谷歌過去的經(jīng)驗(yàn)表明江掩,允許特定于用戶的定制會導(dǎo)致團(tuán)隊(duì)內(nèi)部和團(tuán)隊(duì)之間的差異,并導(dǎo)致工具使用率下降。我們觀察了這樣的團(tuán)隊(duì):當(dāng)發(fā)現(xiàn)團(tuán)隊(duì)成員提交了包含該工具標(biāo)記的警告的新代碼時环形,開發(fā)人員放棄了他們最初使用的工具策泣。我們努力消除每個用戶對分析結(jié)果的定制。
為了實(shí)現(xiàn)這一點(diǎn)抬吟,我們?nèi)∠怂蟹治鼋Y(jié)果的優(yōu)先級或嚴(yán)重性評級萨咕。相反,我們試圖只顯示高優(yōu)先/嚴(yán)重程度的結(jié)果火本,并且當(dāng)結(jié)果被標(biāo)記為不重要時危队,我們會改進(jìn)我們的分析工具。在對分析是否有有用的結(jié)果存在爭議的情況下钙畔,我們可以選擇性地進(jìn)行分析茫陆。開發(fā)人員仍然能夠顯式地觸發(fā)可選分析器,但是默認(rèn)情況下它們不會運(yùn)行刃鳄。取消優(yōu)先級有幾個好處:
?我們能夠刪除或改進(jìn)沒有什么好處的低優(yōu)先級檢查盅弛。
?我們沒有讓開發(fā)人員過濾掉分析器的結(jié)果,而是開始得到關(guān)于錯誤的分析器的bug報告叔锐。例如,我們發(fā)現(xiàn)c++?linter也在linting?Objective-C文件见秽,并修復(fù)了這個問題;以前Objective-C開發(fā)人員只是隱藏了所有l(wèi)inter結(jié)果愉烙。
?我們大大減少了對某些結(jié)果出現(xiàn)的抱怨,或?qū)Σ煌^點(diǎn)不一致的抱怨解取。
我們允許有限的定制步责,但是定制是基于項(xiàng)目的,而不是基于用戶的禀苦。例如蔓肯,團(tuán)隊(duì)可以選擇在默認(rèn)情況下對所有代碼運(yùn)行可選分析。我們還禁用了不適用的分析程序;例如振乏,我們不會在具有不同代碼約定的第三方開放源代碼上運(yùn)行代碼樣式檢查器蔗包。
IV. 實(shí)現(xiàn)
A. 架構(gòu)
????為了在變更列表創(chuàng)建和編輯上有效地提供分析結(jié)果,TRICORDER利用了微服務(wù)架構(gòu)[29]慧邮。從服務(wù)的角度考慮問題會產(chǎn)生一種鼓勵可伸縮性和模塊化的思維方式调限。此外,TRICORDER利用了微服務(wù)架構(gòu)的設(shè)計(jì)假定了系統(tǒng)的某些部分會出現(xiàn)故障误澳,這意味著分析人員被設(shè)計(jì)成可復(fù)制的無狀態(tài)的耻矮,以使系統(tǒng)具有可靠性和可擴(kuò)展性。使用代碼評審工具的注釋系統(tǒng)忆谓,分析結(jié)果將作為機(jī)器人注釋(簡稱robocomments)出現(xiàn)在代碼評審中裆装。
????分析服務(wù)實(shí)現(xiàn)相同的API?(Section?IV-B)。該API使用協(xié)議緩沖區(qū)[31]定義為一種多語言序列化協(xié)議,并使用特定于google的RPC庫進(jìn)行通信哨免。TRICORDER包含一系列用不同語言?(Java茎活、c++、Python和Go)編寫的分析器工作服務(wù)铁瞒,這些語言實(shí)現(xiàn)了這種與語言無關(guān)的協(xié)議緩沖API妙色。這些服務(wù)為分析器提供了一個特定于語言的接口,以實(shí)現(xiàn)抽象處理RPC的細(xì)節(jié);分析作者可以用最有意義的語言實(shí)現(xiàn)分析器慧耍。TRICORDER還包括特定于編譯器的分析服務(wù)身辨,提供了一種插入jscompiler、javac和Clang的方法芍碧。此外煌珊,我們還有一個二進(jìn)制多路復(fù)用器Linter工作者服務(wù),支持用任意語言編寫的字符串泌豆。
????TRICORDER有三個階段定庵,在這三個階段中,它調(diào)用分析服務(wù);每個階段都有更多的信息踪危。
?圖1:TRICORDER體系結(jié)構(gòu)的概述蔬浙。實(shí)體框?qū)?yīng)于作為作業(yè)運(yùn)行的微服務(wù),虛線框區(qū)分作業(yè)的不同部分贞远。實(shí)箭頭對應(yīng)于在TRICORDER中發(fā)送的RPC畴博,而虛線指的是指向外部系統(tǒng)和服務(wù)的RPC。
在FILES階段蓝仲,分析程序可以訪問組成更改的文件的內(nèi)容俱病。例如,在這個階段可以運(yùn)行來檢查諸如“l(fā)ine?is?over?80?characters”之類的屬性袱结。在DEPS(構(gòu)建依賴關(guān)系的縮寫)階段亮隙,分析人員還知道所有由變更影響的構(gòu)建目標(biāo)的列表。例如垢夹,可以在此階段運(yùn)行一個分析程序溢吻,該程序報告何時有大量目標(biāo)受到影響。最后棚饵,在編譯階段煤裙,分析人員可以使用完全解析的類型和隱式表達(dá)式訪問整個程序的完整AST。將分析劃分為多個階段有幾個實(shí)際的好處:
?我們可以在早期階段為分析提供更快的結(jié)果噪漾,因?yàn)樗鼈儾恍枰却龢?gòu)建硼砰。?我們可以在成本較高的階段通過速率限制分析來減少資源使用。
?我們依賴的基礎(chǔ)架構(gòu)問題(例如構(gòu)建服務(wù))不會影響早期階段的分析欣硼。?TRICORDER的整體架構(gòu)如圖1所示
????TRICORDER的主循環(huán)發(fā)生在分析驅(qū)動程序中题翰。驅(qū)動程序調(diào)用特定于語言或編譯器的分析器工作人員來運(yùn)行分析,然后將結(jié)果作為注釋發(fā)送到代碼評審系統(tǒng)。在每個worker中豹障,傳入的分析請求被分派到一組分析器冯事。此外,分析作者可以選擇使用analyzer?worker?API實(shí)現(xiàn)他們自己的獨(dú)立服務(wù)血公。對于pipeline的不同階段昵仅,分析驅(qū)動程序被分成不同的部分:Snapshot?Listener向FILES分析器發(fā)送請求,Targets?Listener向DEPS分析器發(fā)送請求累魔,Build?Listener向COMPILATION分析器發(fā)送請求摔笤。過程如下:
1)當(dāng)生成一個新的變更列表快照時,變更列表快照通知器(通過發(fā)布者/訂閱者模型)向TRICORDER發(fā)出信號垦写,表示有一個新的快照吕世。此消息包含關(guān)于快照的元數(shù)據(jù)(例如作者、變更列表描述和文件列表)梯投,以及一個源上下文(存儲庫名稱命辖、修訂等),可以使用該上下文讀取更改中已編輯的文件分蓖,并在稍后發(fā)布關(guān)于更改的機(jī)器人評論尔艇。當(dāng)TRICORDER收到一個快照提醒時,它會發(fā)出幾個異步調(diào)用:
?tricorder向文件分析器發(fā)送分析請求么鹤。當(dāng)它收到結(jié)果時漓帚,它將結(jié)果轉(zhuǎn)發(fā)給代碼評審系統(tǒng)。
?tricorder向dependencies服務(wù)發(fā)出請求午磁,以計(jì)算哪些構(gòu)建目標(biāo)受到更改的影響2)Dependencies?Service在完成計(jì)算依賴關(guān)系后通知TRICORDER,TRI-CORDER進(jìn)行以下異步調(diào)用:
?TRICORDER向DEPS分析器發(fā)送分析請求毡们,并附帶受變更影響的依賴項(xiàng)列表迅皇。當(dāng)TRICORDER收到分析結(jié)果時,它會將它們轉(zhuǎn)發(fā)給代碼審查服務(wù)衙熔。
?TRICORDER請求Build?Service啟動直接受更改影響的所有目標(biāo)的構(gòu)建登颓。3)構(gòu)建服務(wù)在每個獨(dú)立的編譯單元構(gòu)建時通知TRICORDER。構(gòu)建用于捕獲所有支持語言中每個編譯器調(diào)用所需的所有輸入红氯。保留這組輸入(例如jar文件框咙,編譯器參數(shù),標(biāo)題等)以供分析器以后使用痢甘。
當(dāng)一條消息到達(dá)時喇嘱,它向完成的編譯單元發(fā)出信號坑资,TRICORDER將RPC發(fā)送到COMPILATION分析器眯牧。特定于編譯器的工作程序使用添加的分析通道重放編譯(使用構(gòu)建期間生成的輸入)改基。?COMPILATION分析器可以訪問AST和編譯器提供的所有其他信息。當(dāng)TRICORDER從分析器接收結(jié)果時闻坚,它們將被轉(zhuǎn)發(fā)到代碼審查服務(wù)。
異步通信的使用使TRICORDER能夠更有效地利用其機(jī)器資源振湾。早期的分析可以在運(yùn)行構(gòu)建時并行運(yùn)行暇务,并且編譯單元也都是并行分析的。即使是最慢的分析也能在幾分鐘內(nèi)提供結(jié)果拿撩。
B. 插件模型
????TRICORDER支持跨語言的插件模型衣厘。分析器可以用任何語言編寫;目前c++、Java压恒、Python和Go都有最好的支持影暴。分析器可以分析任何語言,甚至有各種各樣的分析器關(guān)注于開發(fā)過程涎显,而不是編程語言(Section?IV-C)坤检。
所有分析器服務(wù)都實(shí)現(xiàn)分析器RPC?API。大多數(shù)分析程序作為分析worker之一的一部分運(yùn)行期吓,并實(shí)現(xiàn)特定于語言的接口早歇。每個分析器必須支持以下操作:
1)?getcategory返回該分析器生成的一組類別。分析器的類別是一個獨(dú)特的人類可讀的名稱讨勤,顯示為它生成的robocomments的一部分箭跳。
2)?getstage返回這個分析器應(yīng)該運(yùn)行的階段。
3)?分析接收有關(guān)更改的信息潭千,并重新生成一個記錄列表谱姓。
Notes包括有關(guān)分析結(jié)果的主要資料,包括:
分析結(jié)果的類別(以及可選的子類別)刨晴。
分析結(jié)果在代碼中的位置屉来,例如文件和該文件中的范圍(行/列)。
錯誤消息狈癞。
包含關(guān)于分析器和/或消息的更詳細(xì)信息的URL茄靠。
修復(fù)程序的有序列表。
生成的注釋隨后作為robocomments發(fā)布到谷歌的內(nèi)部代碼審查工具中蝶桶。由于結(jié)構(gòu)化輸出是靈活的慨绳,所以它們還可以用于其他上下文(例如瀏覽源代碼時)。在開源版本的Tricorder,?Ship-?shape[35]中可以獲得這個API的更詳細(xì)的信息真竖。Shipshape有一個不同的體系結(jié)構(gòu)來支持開源項(xiàng)目的需求脐雪,但是API和設(shè)計(jì)深受TRICORDER的影響。
C. 分析器
圖2顯示了一個選擇的16個分析器恢共,目前運(yùn)行在TRICORDER(目前大約有30個战秋,每個月都會有更多的上線)。
這個表中的六個分析器本身就是框架旁振。例如获询,容易出錯的[17]和ClangTidy[11]都分別基于Java和c++程序的AST匹配找到bug模式涨岁。它們都啟用了各種單獨(dú)的檢查,每個檢查都作為插件實(shí)現(xiàn)吉嚣。另一個例子是Linter分析器梢薪。該分析器由超過35個獨(dú)立的插件組成,所有這些插件都是通過linter二進(jìn)制多路復(fù)用器調(diào)用的尝哆。插件可以用任何語言實(shí)現(xiàn)秉撇。多路復(fù)用器使用配置文件來確定要將特定文件發(fā)送到哪個linter(基于文件擴(kuò)展名和路徑),以及如何解析linter輸出(通過正則表達(dá)式)秋泄。linter?檢查器包括google配置的流行外部插件版本琐馆,如Java?Checkstyle?linter[9]和Pylint?Python?linter[32],以及許多自定義內(nèi)部檢查器恒序。
圖2:30臺分析器中有16個以TRICORDER方式運(yùn)行瘦麸。第四和第五列報告了隱含語言和目標(biāo)語言,區(qū)別。第六列報告了提供內(nèi)部插件機(jī)制的分析器的插件數(shù)量歧胁。第七列顯示每天的平均結(jié)果滋饲。最后兩列報告惟一用戶的數(shù)量。誰在2014年點(diǎn)擊了請修復(fù)或無用(見第四-?e節(jié))喊巍。
幾種分析器(目前有7種)是領(lǐng)域?qū)S玫?它們只針對代碼庫的一部分屠缭。這包括AndroidLint,它可以發(fā)現(xiàn)Android項(xiàng)目中特定的bug和樣式?jīng)_突崭参,以及一些特定于項(xiàng)目的配置模式的驗(yàn)證器呵曹。其他幾個分析程序(另外7個)是關(guān)于向變更列表提交元數(shù)據(jù)的。例如何暮,一個分析人員警告變更列表是否需要與head合并奄喂,而另一個分析人員警告變更列表是否會暫時影響谷歌代碼的很大一部分。
為了決定一個分析器是否有意義海洼,包括在TRICORDER砍聊,我們有新的分析器的標(biāo)準(zhǔn),從我們的經(jīng)驗(yàn)和理論的靜態(tài)分析(第三節(jié)):
1)警告應(yīng)該易于理解贰军,修復(fù)應(yīng)該清晰。當(dāng)被指出時蟹肘,問題應(yīng)該是明顯的和可操作的词疼。例如,圈復(fù)雜度或基于位置的故障預(yù)測不滿足這個標(biāo)準(zhǔn)帘腹。
2)警告應(yīng)該有很少的誤報贰盗。?開發(fā)人員應(yīng)該認(rèn)為我們至少有90%的時間都在指出實(shí)際問題。為了衡量這一點(diǎn)阳欲,我們在現(xiàn)有代碼上運(yùn)行分析器舵盈,并手動檢查結(jié)果的統(tǒng)計(jì)樣本大小陋率。
3)警告應(yīng)該針對可能產(chǎn)生重大影響的事情。?我們希望警告足夠重要秽晚,以便當(dāng)開發(fā)人員看到它們時瓦糟,他們會認(rèn)真對待并經(jīng)常選擇修復(fù)它們。?為了確定這一點(diǎn)赴蝇,以語言為中心的分析器由語言專家進(jìn)行審查菩浙。
4)警告應(yīng)以較小但可通知的頻率發(fā)生。檢測從未真正發(fā)生過的警告是沒有意義的句伶,但是如果警告發(fā)生得太頻繁劲蜻,它很可能不會導(dǎo)致任何真正的問題。我們不想給人們太多的警告考余。
分析開發(fā)人員可以首先嘗試對一小組白名單用戶進(jìn)行新的分析先嬉,這些用戶首先會自愿查看實(shí)驗(yàn)結(jié)果。一些分析也可以在MapReduce上運(yùn)行楚堤,覆蓋所有現(xiàn)有代碼疫蔓,以在部署之前檢查誤報率。
D. 修復(fù)
????分析工具的兩個常見問題是钾军,它們可能不會產(chǎn)生可執(zhí)行的結(jié)果鳄袍,而且繁忙的開發(fā)人員需要花費(fèi)精力來修復(fù)突出顯示的問題。為了解決這些問題吏恭,我們鼓勵分析開發(fā)者在分析結(jié)果中提供修復(fù)建議拗小。可以在代碼評審工具中查看和應(yīng)用這些修復(fù)程序樱哼。圖3顯示了由TRICORDER生成的示例注釋哀九。單擊“show”鏈接后就可以看到修復(fù)程序(圖4)。請注意搅幅,這里的修復(fù)程序沒有綁定到特定的IDE阅束,它們是每個分析的一部分與語言無關(guān)。讓分析程序提供修復(fù)有幾個好處:修復(fù)程序可以為分析結(jié)果提供額外的澄清茄唐,能夠直接應(yīng)用修復(fù)程序意味著處理分析結(jié)果不需要更改上下文息裸,而工具提供的修復(fù)程序降低了修復(fù)代碼中問題的門檻。為了應(yīng)用補(bǔ)丁沪编,我們利用了一個系統(tǒng)的可用性呼盆,該系統(tǒng)使變更列表的內(nèi)容可用于編輯。也就是說蚁廓,編輯就像應(yīng)用補(bǔ)丁一樣访圃,可以直接對變更列表中的代碼進(jìn)行修改,修改后的代碼將出現(xiàn)在變更列表所有者的工作區(qū)中相嵌。要實(shí)現(xiàn)與Gerrit類似的東西腿时,可以利用現(xiàn)有api將補(bǔ)丁作為補(bǔ)丁應(yīng)用于正在審查的代碼况脆。
圖3:分析結(jié)果的屏幕截圖;?更改列表審閱者視圖。?在這種情況下批糟,有兩個結(jié)果:一個來自Java?Lint工具(checkstyle?[9]的配置版本)格了,另一個來自ErrorProne?[17]。?如果分析結(jié)果有問題跃赚,審閱者可以單擊NOT?USEFUL鏈接笆搓。?他們也可以點(diǎn)擊PLEASE?FIX來表明作者應(yīng)該修復(fù)結(jié)果。?他們還可以查看附加的修復(fù)程序(圖4)纬傲。
圖4:圖3中ErrorProne警告的預(yù)覽修復(fù)視圖的屏幕截圖
E. 反饋
????為了快速響應(yīng)分析程序的問題满败,我們構(gòu)建了一個反饋機(jī)制,跟蹤開發(fā)人員如何與代碼評審中生成的robocomments交互叹括。如圖3和圖4所示算墨,開發(fā)人員可以點(diǎn)擊四個鏈接:
?沒有用給開發(fā)人員機(jī)會提交關(guān)于robocomment的bug。
?請修復(fù)創(chuàng)建一個評論評論汁雷,要求作者修復(fù)robocomment净嘀,并且只對評論者可用。
?預(yù)覽修復(fù)(圖3中的“show”)顯示了建議修復(fù)的差異視圖侠讯,當(dāng)robocomment附帶修復(fù)時可用挖藏。
?Apply?FIX(圖4中的“Apply”)將建議的修復(fù)應(yīng)用于代碼,只有當(dāng)robocomment附帶修復(fù)時厢漩,作者才能使用它膜眠。此選項(xiàng)只能在使用預(yù)覽修復(fù)后才能看到。
????我們將分析器的“無用率”定義為:
NOT USEFUL/(NOT USEFUL + PLEASE FIX + APPLY FIX)
????分析作者需要通過我們提供的儀表板檢查這些數(shù)字溜嗜。一個≥10%的比率使分析器處于試用狀態(tài)宵膨,分析作者必須在解決問題方面顯示出進(jìn)展。如果速率超過25%炸宵,我們可能決定立即關(guān)閉分析器辟躏。在實(shí)踐中,我們通常與分析程序編寫人員一起解決問題土全,而不是立即禁用分析程序捎琐。一些分析程序只影響一小部分開發(fā)人員,因此我們不太擔(dān)心出現(xiàn)暫時性的誤報裹匙。盡管如此野哭,有一個合適的策略已經(jīng)被證明是非常寶貴的,可以讓分析人員清楚地了解預(yù)期幻件。
V. 成果
a)可用性:
????我們通過無效的點(diǎn)擊率和每種類型的點(diǎn)擊次數(shù)來衡量TRICORDER的可用性,無論是對于整個TRICORDER還是對于特定的分析器蛔溃。
????圖2顯示開發(fā)人員通過點(diǎn)擊積極參與分析绰沥。圖2列出了2014年為每個分析器點(diǎn)擊了至少一次的FIXASE?FIX或者USEFUL的唯一用戶數(shù)篱蝇。可以看出,Linter已經(jīng)在2014年從超過18,000名用戶那里獲得了PLEASE?FIX點(diǎn)擊徽曲。所有類別中點(diǎn)擊“不好用”的用戶數(shù)量大幅下降零截。
????我們的點(diǎn)擊率表明,開發(fā)人員通常對靜態(tài)分析工具的結(jié)果感到滿意秃臣。圖5
顯示了所有TRICORDER分析器的一周;最近幾個月涧衙,它通常在5%左右。當(dāng)我們移除正在試用的分析器時奥此,這個數(shù)字會下降到4%以下弧哎。
????圖6顯示了幾種Java分析器的無用速率的比較。?Checkstyle稚虎,ErrorProne和Unused-Deps分析都相當(dāng)穩(wěn)定撤嫩,并且具有較低的not-useful;?ErrorProne的數(shù)據(jù)由于產(chǎn)生的結(jié)果數(shù)量較少而具有更多的差異。?DocComments更有趣;該分析器最初處于試用期蠢终,開發(fā)人員努力將not-useful率降至10%以下序攘。但是,第24周引入了一個錯誤寻拂,導(dǎo)致NOT?USEULUL點(diǎn)擊量急劇增加程奠。開發(fā)人員能夠使用我們提供的錯誤報告和點(diǎn)擊日志來確定問題的根源,修復(fù)程序最終在第33周發(fā)布祭钉。
分析器開發(fā)者還可以分析每周的原始點(diǎn)擊量瞄沙。圖7
顯示了用于易出錯分析的單擊類型的細(xì)分。有趣的是注意到PLEASE?FIX與PREVIEW?FIX是多么相關(guān);我們假設(shè)很多次朴皆,審核人單擊PLEASE?FIX帕识,然后作者單擊PREVIEW?FIX查看問題是什么。APPLY?FIX的點(diǎn)擊量要低得多遂铡。基于開發(fā)人員的觀察肮疗,我們假設(shè)許多開發(fā)者選擇在他們自己的編輯器中修復(fù)代碼,而不是使用代碼審查工具來實(shí)現(xiàn)這一目的扒接,特別是當(dāng)他們已經(jīng)在編輯器中處理其他審查者的評論時伪货。請注意,提供修復(fù)方案有兩個目的;一個是讓開發(fā)人員輕松應(yīng)用修復(fù)钾怔,而另一個是分析結(jié)果的進(jìn)一步解釋碱呼。
????點(diǎn)擊是對分析器質(zhì)量的一種不完善的衡量:
許多開發(fā)人員在他們的review人員看到問題之前就報告修復(fù)問題,所以PLEASE?FIX的數(shù)量是已知的較低的宗侦。
許多開發(fā)人員報告在他們自己的編輯器中修復(fù)問題愚臀,而不是通過APPLY?FIX,所以這些數(shù)量也很低矾利。
開發(fā)人員可能會忽略他們不打算修復(fù)的結(jié)果姑裂,而不是點(diǎn)擊NOT?USEFUL馋袜。這可能只是一個信號,表明開發(fā)人員對這個問題的感受有多強(qiáng)烈舶斧。
開發(fā)人員可能會偶然點(diǎn)擊“NOT?USEFUL”欣鳖。
盡管有這些缺點(diǎn),但點(diǎn)擊一直是“開發(fā)人員煩惱”的好信號茴厉。我們最成功的分析儀的有效率在0-3%之間泽台。
當(dāng)開發(fā)人員單擊“NOT?USEFUL”時,會出現(xiàn)一個鏈接矾缓,將我們的問題跟蹤系統(tǒng)中的一個bug提交給負(fù)責(zé)該分析器的項(xiàng)目;這個bug預(yù)先填充了關(guān)于robocomment的所有必要信息怀酷,并為開發(fā)人員提供了一個機(jī)會來評論為什么他們點(diǎn)擊了NOT?USEFUL。根據(jù)分析程序的不同而账,每次NOT?USEFUL點(diǎn)擊的錯誤率在10-60%之間.
b)代碼庫影響:
????隨著時間的推移胰坟,TRICORDER減少了代碼庫中違規(guī)實(shí)例的數(shù)量。對于ClangTidy分析器泞辐,我們可以看到笔横,在代碼評審中顯示結(jié)果不僅可以防止新問題進(jìn)入代碼庫,而且當(dāng)人們了解新的檢查時咐吼,還可以減少問題的總數(shù)吹缔。圖8
顯示了每周發(fā)生ClangTidy?misc-冗余-smartpt?-get檢查的次數(shù);此檢查標(biāo)識了對智能指針不需要“.get()”調(diào)用的情況。垂直的線是這個檢查開始在TRICORDER中顯示的時候锯茄。在將check添加到TRI-?CORDER之后厢塘,隨著開發(fā)人員認(rèn)識到不適當(dāng)?shù)腸od-?ing模式、停止在新代碼中犯這樣的錯誤肌幽,以及修復(fù)代碼中其他地方出現(xiàn)的錯誤晚碾,代碼庫中的實(shí)例數(shù)量急劇減少。圖8還顯示了其他ClangTidy修復(fù)的趨勢線示例;在TRICORDER中啟用檢查后喂急,它們都顯示了類似的下拉模式或水平下拉模式格嘁。只有水平的檢查通常使用更復(fù)雜的非本地修復(fù)程序進(jìn)行檢查。
c)擴(kuò)展性:
????TRICORDER擴(kuò)展方便廊移。我們通過證明各種分析已經(jīng)成功地插入糕簿,來評估這一點(diǎn)。正如IV-C節(jié)所討論的狡孔,有超過30種不同的分析采用TRICORDER懂诗。圖2顯示了選擇的16臺分析器;這些分析者跨越了廣泛的語言和突出的問題。這個表中的16個分析程序中有13個(除了Formatter苗膝、Build-?Deprecation和Builder之外)是由其他10多個團(tuán)隊(duì)的成員提供的殃恒。許多其他開發(fā)人員向易出錯、ClangTidy或Linter等分析程序提供了插件。
d)可伸縮性:
????TRICORDER可以擴(kuò)展到非常大的代碼庫离唐。為了評估這一點(diǎn)隆嗅,我們對每天在谷歌生成的所有變更列表快照運(yùn)行TRICORDER。圖9
顯示了TRICORDER的幾個伸縮指標(biāo)的平均值侯繁、中值和最大值。
平均每天泡躯,我們對31K個快照運(yùn)行TRICORDER贮竟,每個快照的平均大小為12個文件,我們報告幾個類別和語言的結(jié)果较剃。相比之下咕别,ReviewBot[7]對34個評審請求(對應(yīng)于變更列表)進(jìn)行了評估,而我們用于評估TRICORDER的請求有數(shù)百萬個写穴。平均而言惰拱,每個快照包含來自一種語言的文件,最多22種語言啊送〕ザ蹋總共一天,我們報告了大約30個類別的93K個結(jié)果馋没。TRICORDER每天也運(yùn)行接近5K的構(gòu)建昔逗。每天,Review人員點(diǎn)擊PLEASE?FIX平均716項(xiàng)發(fā)現(xiàn)(來自Linters的416項(xiàng))篷朵,但只有48項(xiàng)發(fā)現(xiàn)沒有得到有用的點(diǎn)擊勾怒。一個普通的CL有兩次“please-fix?”點(diǎn)擊和沒有not-useful?的點(diǎn)擊。盡管我們的搜索結(jié)果比點(diǎn)擊量要多得多声旺,但大多數(shù)搜索結(jié)果并沒有顯示在評論中笔链,因?yàn)樗鼈冿@示在未修改的行上.
VI.相關(guān)工作
????之前的一項(xiàng)研究調(diào)查了為什么開發(fā)人員不使用靜態(tài)分析工具來發(fā)現(xiàn)bug,并從20個開發(fā)人員的[23]視圖中收集結(jié)果腮猖。本研究的許多結(jié)論與我們使用之前的程序分析工具進(jìn)行實(shí)驗(yàn)的經(jīng)驗(yàn)相吻合鉴扫。TRICORDER解決了本研究發(fā)現(xiàn)的主要痛點(diǎn)。例如缚够,通過維護(hù)一個緊密的反饋循環(huán)幔妨,TRICORDER不斷地確保工具輸出得到改進(jìn),并且結(jié)果是可以理解的谍椅。TRICORDER還支持通過代碼評審集成工具結(jié)果的協(xié)作;review者可以對靜態(tài)分析結(jié)果提出建議或建議误堡。本研究還強(qiáng)調(diào)了工作流程集成的重要性,這是TRICORDER的一個主要設(shè)計(jì)要點(diǎn)雏吭。
????靜態(tài)分析工具的研究非常廣泛;我們只能在這里描述現(xiàn)有工具的一部分锁施。FindBugs[18]是一個基于啟發(fā)式的bug查找工具,它運(yùn)行在Java字節(jié)碼上。Coverity[12]悉抵、Klocwork[24]和Semmle[37]肩狂、[14]是專注于靜態(tài)分析的商業(yè)工具。Linting工具如Checkstyle?(java)和Pylint?(Python)主要關(guān)注樣式問題(間距姥饰、換行位置等)[9]傻谁、[32]。
????在Eclipse[41]和Intellij[22]等ide中列粪,分析結(jié)果和快速修復(fù)程序也常常是表面的审磁。我們也可以通過在IDE中調(diào)用我們的service來在這里顯示TRICORDER結(jié)果。許多商業(yè)工具還以看板格式[12]岂座、[37]态蒂、[24]顯示結(jié)果;雖然我們確實(shí)有dashboard,但我們發(fā)現(xiàn)费什,這只對分析程序編寫者有用钾恢,幫助他們提高分析程序的質(zhì)量。其他大公司鸳址,如微軟瘩蚪,也在積極探索將靜態(tài)分析集成到開發(fā)人員工作流[25]中的方法。Ebay開發(fā)了評估和比較不同靜態(tài)分析工具在[21]實(shí)驗(yàn)中的價值的方法氯质。IBM還試驗(yàn)了基于服務(wù)的靜態(tài)分析方法[30]募舟。這項(xiàng)工作是通過與IBM的幾個團(tuán)隊(duì)進(jìn)行的試點(diǎn)和調(diào)查進(jìn)行評估的,他們確定了幾個需要改進(jìn)的領(lǐng)域闻察。TRICORDER解決了這些改進(jìn)中的每一個:它被集成到開發(fā)人員工作流中(而不是以批處理模式運(yùn)行)拱礁,它是可插拔的,并且支持由其他團(tuán)隊(duì)編寫的分析辕漂,它還包含一個反饋循環(huán)呢灶,供分析作者使用改進(jìn)平臺和分析器。
????之前發(fā)布的一個名為ReviewBot的系統(tǒng)在代碼評審[6]和[7]中顯示了靜態(tài)分析結(jié)果钉嘹。ReviewBot與TRICORDER的不同之處在于審閱人員必須顯式地調(diào)用ReviewBot鸯乃,分析結(jié)果不會顯示給審閱人員,目前只支持三種(Java)靜態(tài)分析工具跋涣。ReviewBot還增加了提供修復(fù)功能;這個修正系統(tǒng)與分析結(jié)果完全解耦缨睡。相反,TRICORDER修復(fù)程序是由分析程序生成的陈辱,而我們應(yīng)用修復(fù)程序的機(jī)制(來自結(jié)構(gòu)化分析結(jié)果)是與語言無關(guān)的奖年。
????與之前的工作不同,我們在開發(fā)人員工作流期間評估了TRICORDER沛贪,而不是作為對開發(fā)人員在其工作環(huán)境之外生成和看到的結(jié)果的調(diào)查陋守。這種評估風(fēng)格使我們能夠看到開發(fā)人員在實(shí)際環(huán)境中的反應(yīng)震贵,而不是在實(shí)驗(yàn)室環(huán)境中。
VII. 探討
????TRICORDER自2013年7月開始投入生產(chǎn)水评。通過實(shí)現(xiàn)猩系、啟動和監(jiān)視TRICORDER,我們了解了一些關(guān)于如何使程序分析工作的有趣的事情中燥。在第三節(jié)中寇甸,我們概述了我們的理念,包括我們系統(tǒng)的目標(biāo)和從過去經(jīng)驗(yàn)中吸取的教訓(xùn)×粕妫現(xiàn)在我們重新審視我們的目標(biāo)和提出的評估幽纷。
????改進(jìn)數(shù)據(jù)驅(qū)動的可用性。最后博敬,開發(fā)者將決定一個分析工具是否具有高影響力,以及他們認(rèn)為什么是誤報峰尝。開發(fā)人員不喜歡誤報偏窝。這就是為什么聽取開發(fā)人員的反饋并采取行動是很重要的。平均每天有93K個發(fā)現(xiàn)武学,平均收到716個“請修復(fù)”和48個無用的點(diǎn)擊祭往。我們密切關(guān)注這些點(diǎn)擊,如果需要火窒,我們會讓分析人員試用硼补。我們討論了分析器作者的改進(jìn),并鼓勵他們改進(jìn)他們的分析器——這種改進(jìn)可能僅僅是更新結(jié)果的措辭熏矿。
授權(quán)用戶進(jìn)行貢獻(xiàn)已骇。TRICORDER通過提供一個可插入的框架來實(shí)現(xiàn)這一點(diǎn),該框架允許開發(fā)人員在其專業(yè)領(lǐng)域內(nèi)輕松地貢獻(xiàn)分析票编。事實(shí)上褪储,在TRICORDER中運(yùn)行的大多數(shù)分析都是由管理TRICORDER本身的團(tuán)隊(duì)之外的開發(fā)人員提供的分析。
????集成工作流程是關(guān)鍵慧域。與VMWare[7]以前的預(yù)感知工具一樣鲤竹,我們發(fā)現(xiàn)代碼重新查看是顯示分析結(jié)果的絕佳時機(jī)。開發(fā)者在簽入更改之前接收反饋昔榴,并且顯示分析結(jié)果的機(jī)制是統(tǒng)一的——不管以前使用的是哪種IDE或開發(fā)環(huán)境辛藻。評審人員還可以看到并響應(yīng)分析結(jié)果,從而承擔(dān)同行責(zé)任;審稿人每周平均點(diǎn)擊“請修復(fù)”5117次互订。
????項(xiàng)目級別定制吱肌,而不是用戶定制。根據(jù)經(jīng)驗(yàn)屁奏,我們發(fā)現(xiàn)項(xiàng)目級的定制比用戶級的定制更成功岩榆。這提供了靈活性错负,這樣開發(fā)團(tuán)隊(duì)就可以用一種聯(lián)合的方法來開發(fā)項(xiàng)目的代碼,并且避免了開發(fā)人員之間關(guān)于分析結(jié)果的分歧勇边,這可能會導(dǎo)致結(jié)果被忽略犹撒。除了上述內(nèi)容之外,還應(yīng)該提到一些關(guān)于復(fù)雜性粒褒、可伸縮性和修復(fù)的內(nèi)容识颊。圖2中描述的所有檢查都相對簡單。我們不使用任何控制或數(shù)據(jù)流信息奕坟、指針分析祥款、整個程序分析、抽象解釋或其他類似的技術(shù)月杉。盡管如此刃跛,他們還是為開發(fā)人員發(fā)現(xiàn)了真正的問題,并提供了良好的回報苛萎。也就是說桨昙,相對簡單的檢查有很大的影響‰缜福總的來說蛙酪,我們在提供建議的修復(fù)方案的分析上取得了更大的成功。分析工具應(yīng)該修復(fù)bug翘盖,而不僅僅是發(fā)現(xiàn)它們桂塞。對于如何解決這個問題,沒有太多的困惑馍驯,而且自動應(yīng)用該工具提供的修復(fù)程序的能力降低了對上下文切換的需要阁危。最后,為了確保分析能夠在谷歌的范圍內(nèi)運(yùn)行汰瘫,程序分析工具應(yīng)該是可分割的欲芹。把分析工具想象成跨大型程序集的map-reduce。
????最后的想法吟吝。在本文中菱父,我們提出了一個靜態(tài)分析平臺,同時也對如何創(chuàng)建這樣一個平臺形式提出了自己的見解剑逃。我們的目標(biāo)是鼓勵分析作者在創(chuàng)建新工具和他們的工具的所有權(quán)衡時考慮這種理念浙宜,而不僅僅是技術(shù)上定義的誤報率或分析的速度。我們也鼓勵其他公司蛹磺,即使他們已經(jīng)嘗試過程序分析工具之前粟瞬,再嘗試與此理念的思想。雖然我們多年來也沒有廣泛使用靜態(tài)分析工具萤捆,但是最終正確使用靜態(tài)分析工具會帶來很大的回報裙品。
VIII. 致謝
????特別感謝所有幫助實(shí)現(xiàn)Tricorder的谷歌開發(fā)人員俗批,包括Alex?Eagle、Eddie?Af-?tandilian市怎、Ambrose?Feinstein岁忘、Alexander?Kornienko和Mark?Knichel,以及所有繼續(xù)確保平臺成功的分析人員区匠。
引用
[1]????AddressSanitizer????Team.???AddressSanitizer.?http://clang.llvm.org/docs/AddressSanitizer.html,?2012.
[2] ? ?E. Aftandilian, R. Sauciuc, S. Priya, and S. Krishnan. Building useful program analysis tools using an extensible compiler. In Workshop on Source Code Analysis and Manipulation (SCAM), 2012.
[3]????N.?Ayewah,?D.?Hovemeyer,?J.?D.?Morgenthaler,?J.?Penix,?and?W.?Pugh.?Using?static?analysis?to?find?bugs.?IEEE?Software,?25(5):22–29,?2008.
[4] ? ?N. Ayewah and W. Pugh. The Google FindBugs fixit. In International Symposium on Software Testing and Analysis (ISSTA), pages 241–252, 2010.
[5] ? ?N. Ayewah, W. Pugh, J. D. Morgenthaler, J. Penix, and Y. Zhou. Evalu- ating static analysis defect warnings on production software. In Program Analysis for Software Tools and Engineering (PASTE), 2007.
[6]????V.?Balachandran.?Fix-it:?An?extensible?code?auto-fix?component?in?re-?view?bot.?In?Source?Code?Analysis?and?Manipulation?(SCAM),?2013?IEEE?13th?International?Working?Conference?on,?pages?167–172,?Sept?2013.
[7] ? ?V. Balachandran. Reducing human effort and improving quality in peer code reviews using automatic static analysis and reviewer recommenda- tion. In Proceedings of the 2013 International Conference on Software Engineering, ICSE ’13, pages 931–940, Piscataway, NJ, USA, 2013. IEEE Press.
[8]????A.?Bessey,?K.?Block,?B.?Chelf,?A.?Chou,?B.?Fulton,?S.?Hallem,?C.?Henri-?Gros,?A.?Kamsky,?S.?McPeak,?,?and?D.?Engler.?A?few?billion?lines?of?code?later.?Communications?of?the?ACM,?53(2):66–75,?2010.
[9]????Checkstyle?Java?Linter.?http://checkstyle.sourceforge.net/,?August?2014.
[10]????Clang?compiler.?http://clang.llvm.org,?August?2014.
[11]????ClangTidy.?http://clang.llvm.org/extra/clang-tidy.html,?August?2014.
[12]????Coverity.?http://www.coverity.com/.
[13]????Coverity?????2012????scan????report.????http://www.coverity.com/press-?releases/annual-coverity-scan-report-finds-open-source-and-?proprietary-software-quality-better-than-industry-average-for-second-?consecutive-year/.?Accessed:?2015-02-11.
[14]????O.?de?Moor,?D.?Sereni,?M.?Verbaere,?E.?Hajiyev,?P.?Avgustinov,?T.?Ek-?man,?N.?Ongkingco,?and?J.?Tibble.?.QL:?Object-Oriented?Queries?Made?Easy.?In?GTTSE,?pages?78–133,?2007.
[15] ? ?S. Elbaum, G. Rothermel, and J. Penix. Techniques for improving re- gression testing in continuous integration development environments. ? In International Symposium on Foundations of Software Engineering (FSE), 2014.
[16]????P.?Emanuelsson?and?U.?Nilsson.?A?comparative?study??of??industrial?static?analysis?tools.?Electronic?Notes?in?Theoretical?Computer?Science,?217(0):5?–?21,?2008.?Proceedings?of?the?3rd?International?Workshop?on?Systems?Software?Verification?(SSV?2008).
[17]????error-prone:?Catch?common?Java?mistakes?as?compile-time?errors.?http://code.google.com/p/error-prone/,?August?2014.
[18]????FindBugs.?http://findbugs.sourceforge.net/.
[19]????Gerrit?code?review.?http://code.google.com/p/gerrit/,?August?2014.
[20]????Google.?Build?in?the?cloud:?How?the?build?system?works.?Available?from?http://http://google-engtools.blogspot.com/2011/08,?August?2011.?Accessed:?2014-11-14.
[21] ? ?C. Jaspan, I.-C. Chen, and A. Sharma. Understanding the value of program analysis tools. In Companion to the 22Nd ACM SIGPLAN Conference on Object-oriented Programming Systems and Applications Companion, pages 963–970, New York, NY, USA, 2007. ACM.
[22] ? ?Jetbrains. ?IntelliJ ? ?IDEA. ? Available ? at
http://www.jetbrains.com/idea/,?2014.
[23]????B.?Johnson,?Y.?Song,?E.?R.?Murphy-Hill,?and?R.?W.?Bowdidge.?Why?don’t?software?developers?use?static?analysis?tools?to?find?bugs??In?International?Conference?on?Software?Engineering?(ICSE),?pages?672–?681,?2013.
[24]????Klocwork.?http://www.klocwork.com/.
[25]????J.?Larus,?T.?Ball,?M.?Das,?R.?DeLine,?M.?Fahndrich,?J.?Pincus,?S.?Ra-?jamani,?and?R.?Venkatapathy.?Righting?software.?Software,?IEEE,?21(3):92–100,?May?2004.
[26]????T.?D.?LaToza,?G.?Venolia,?and?R.?DeLine.?Maintaining?mental?models:?A?study?of?developer?work?habits.?In?International?Conference?on?Software?Engineering?(ICSE),?pages?492–501,?New?York,?NY,?USA,?2006.?ACM.
[27]????L.?Layman,?L.?Williams,?and?R.?Amant.?Toward?reducing?fault?fix?time:?Understanding?developer?behavior?for?the?design?of?automated?fault?de-?tection?tools.?In?Empirical?Software?Engineering?and?Measurement,2007?ESEM?2007.?First?International?Symposium?on,?pages?176–185,Sept?2007.
[28]????C.?Lewis,?Z.?Lin,?C.?Sadowski,?X.?Zhu,?R.?Ou,?and?E.?J.?W.?Jr.??Does??bug?prediction?support?human?developers??findings?from?a?google?case?study.?In?International?Conference?on?Software?Engineering?(ICSE),?2013.
[29]????J.?Lewis?and?M.?Fowler.?Microservices.?http://martinfowler.com/article/?microservices.html,?25?March?2014.
[30] ? ?M. Nanda, M. Gupta, S. Sinha, S. Chandra, D. Schmidt, and P. Bal- achandran. Making defect-finding tools work for you. In International Conference on Software Engineering (ICSE), volume 2, pages 99–108, May 2010.
[31]????Protocol?Buffers.?http://code.google.com/p/protobuf/,?August?2014.
[32]????Pylint?python?linter.?http://www.pylint.org/,?August?2014.
[33]????J.?Ruthruff,?J.?Penix,?J.?D.?Morgenthaler,?S.?Elbaum,?and?G.?Rothermel.?Predicting?accurate?and?actionable?static?analysis?warnings:?An?experi-?mental?approach.?In?International?Conference?on?Software?Engineering?(ICSE),?pages?341–350,?2008.
[34]????C.???Sadowski???and?D.??Hutchins.???Thread-safety?annotation?checking.??Available?from?http://clang.llvm.org/docs/?LanguageExtensions.html#threadsafety,?2011.
[35]????C.?Sadowski,?C.?Jaspan,?E.?S?derberg,?C.?Winter,?and?J.?van?Gogh.?Ship-?shape?program?analysis?platform.?https://github.com/google/shipshape.?Accessed:?2015-2-11.
[36] ? ?C. Sadowski and J. Yi. ?How developers use data race detection tools. ?In Evaluation and Usability of Programming Languages and Tools (PLATEAU), 2014.
[37]????Semmle.?https://semmle.com/.
[38]????H.?Seo,?C.?Sadowski,?S.?G.?Elbaum,?E.?Aftandilian,?and?R.?W.?Bowdidge.?Programmers’?build?errors:?a?case?study?(at?google).?In?International?Conference?on?Software?Engineering?(ICSE),?pages?724–734,?2014.
[39]????K.?Serebryany?and?T.?Iskhodzhanov.?ThreadSanitizer:?Data?race?detec-?tion?in?practice.?In?Workshop?on?Binary?Instrumentation?and?Applica-?tions?(WBIA),?2009.
[40] ? ?K. Serebryany, A. Potapenko, T. Iskhodzhanov, and D. Vyukov. Dy- namic race detection with LLVM compiler. In International Workshop on Runtime Verification (RV), 2011.
[41]????The?Eclipse?Foundation.?The?Eclipse?Software?Development?Kit.?Avail-?able?at?http://www.eclipse.org/,?2009.
[42] ? ?L. Wasserman. Scalable, example-based refactorings with refaster. In
Workshop on Refactoring Tools, 2013.
[43] ? ?J. Whittaker, J. Arbon, and J. Carollo. How Google Tests Software. Always learning. Addison-Wesley, 2012.