<meter id="pryje"><nav id="pryje"><delect id="pryje"></delect></nav></meter>
          <label id="pryje"></label>

          新聞中心

          EEPW首頁(yè) > EDA/PCB > 設(shè)計(jì)應(yīng)用 > 基于C++TCL PLI聯(lián)合仿真下的芯片驗(yàn)證方法研究

          基于C++TCL PLI聯(lián)合仿真下的芯片驗(yàn)證方法研究

          作者: 時(shí)間:2009-11-05 來(lái)源:網(wǎng)絡(luò) 收藏


          2 腳本層關(guān)鍵技術(shù)
          編寫激勵(lì)源數(shù)據(jù)屬于驗(yàn)證過(guò)程的腳本層,為了高效地生成數(shù)據(jù),使用腳本語(yǔ)言實(shí)現(xiàn)。與C/C++等編譯性語(yǔ)言的最大區(qū)別是當(dāng)語(yǔ)言編寫好之后不用通過(guò)軟件編譯就可以直接運(yùn)行,運(yùn)行一行就是“解釋”一行,“解釋”的過(guò)程通過(guò)TCL解釋器完成。TCL擁有一個(gè)固有的核心命令集,同時(shí)還具有和C/C++語(yǔ)言類似的控制結(jié)構(gòu),如if控制、循環(huán)控制和switch控制等,并支持過(guò)程的定義和調(diào)用,對(duì)數(shù)組和字符串等簡(jiǎn)單數(shù)據(jù)結(jié)構(gòu)也提供了支持,然而TCL標(biāo)準(zhǔn)庫(kù)提供的命令可能不會(huì)滿足需要.這時(shí)要針對(duì)某一特定應(yīng)用領(lǐng)域?qū)CL語(yǔ)言的核心命令集合進(jìn)行擴(kuò)展,加入適合于自己使用的擴(kuò)展命令。
          擴(kuò)展TCL命令主要采用編寫二進(jìn)制程序包的方法,二進(jìn)制程序包本身并不嵌入TCL解釋器,而是一些用C/C++編寫的擴(kuò)展命令的集合。任何標(biāo)準(zhǔn)的TCL解釋器都可以用加載的方法使用二進(jìn)制程序包中的擴(kuò)展命令,Modelsim仿真工具集成了TCL解釋器。擴(kuò)展一個(gè)TCL命令大致可以分為兩步:編寫擴(kuò)展命令對(duì)應(yīng)的C/C++過(guò)程和注冊(cè)命令。TCL擴(kuò)展命令的函數(shù)原型為:int Tcl_CmdProc(ClientData,Tcl_In-terp *interp,int argc,char *argv[]),參數(shù)clientData由TCL調(diào)用者傳人,其值在注冊(cè)擴(kuò)展函數(shù)時(shí)設(shè)置;參數(shù)interp也由TCL調(diào)用者傳入,是指向解釋器結(jié)構(gòu)的指針;參數(shù)argc和argv與標(biāo)準(zhǔn)C語(yǔ)言的命令行參數(shù)argc,argv的含義類似,其中argc是被調(diào)用參數(shù)的個(gè)數(shù),argv[0]是被調(diào)用的命令本身,argv[argc]是NULL,而argv[1]到argv[argc-1]才是真正的參數(shù)。編寫好的擴(kuò)展命令還需要注冊(cè),如果注冊(cè)成功就可以在TCL解釋器中使用了,注冊(cè)過(guò)程在初始化函數(shù)中進(jìn)行,TCL注冊(cè)函數(shù)原型為Tcl_CreateCommand(Tcl_Interp*interp,char *cmdName,Tcl_CmdProc *proc,Client-Data clientData,Tcl_CmdDeleteProc *deleteProc),cmd-Name是解釋器中使用的命令名,proc為編寫的擴(kuò)展函數(shù)名。需要注意的是TCL初始化函數(shù)的名稱必須是首字母大寫的DLL文件主文件名+一個(gè)下劃線+首字母大寫的Init組成。


          3 時(shí)序?qū)雨P(guān)鍵技術(shù)
          編寫發(fā)送器和接收器屬于驗(yàn)證過(guò)程的時(shí)序?qū)樱瑫r(shí)序?qū)右舶ū焕脑O(shè)計(jì)模塊。腳本層生成的激勵(lì)數(shù)據(jù)是用TCL語(yǔ)言編寫的,而發(fā)送器和接收器是使用硬件描述語(yǔ)言Verilog編寫,為了實(shí)現(xiàn)兩種語(yǔ)言的數(shù)據(jù)傳遞,需要使用接口編程語(yǔ)言完成兩者的結(jié)合,從而達(dá)到將激勵(lì)數(shù)據(jù)正確傳送到設(shè)計(jì)模塊和參考模型以及收集設(shè)計(jì)模塊輸出數(shù)據(jù)的目的,完成仿真這一過(guò)程。函數(shù)對(duì)應(yīng)發(fā)送器和接收器中調(diào)用的任務(wù),它使用C++語(yǔ)言擴(kuò)展,在Verilog代碼中使用,主要包括四個(gè)C++函數(shù):calltf,cheektf,sizetf,misctf函數(shù),一般情況下只需要編寫其中的三個(gè)函數(shù)checktf,misctf和calltf函數(shù)。編寫完這三個(gè)函數(shù)之后,要注冊(cè)函數(shù)對(duì)應(yīng)的Verilog代碼中使用的系統(tǒng)任務(wù)或函數(shù),提供每個(gè)系統(tǒng)任務(wù)和函數(shù)的名字以及相應(yīng)的回調(diào)函數(shù),使用結(jié)構(gòu)體s_tfeell在C++代碼中來(lái)注冊(cè)PLI函數(shù)。
          calltf函數(shù)在仿真運(yùn)行時(shí)被調(diào)用,即仿真執(zhí)行到發(fā)送器或接收器中定義好的PLI任務(wù)時(shí),就會(huì)調(diào)用該任務(wù)對(duì)應(yīng)的calltf函數(shù);checktf函數(shù)在仿真開始運(yùn)行前被仿真器調(diào)用,換句話說(shuō),在仿真時(shí)刻0,這個(gè)函數(shù)可以由仿真器的編譯器調(diào)用,checktf函數(shù)的主要目的是校驗(yàn)一個(gè)系統(tǒng)/任務(wù)是否被正確使用和加載環(huán)境設(shè)置命令;misctf函數(shù)在仿真運(yùn)行時(shí)的各種混雜事件情況下被調(diào)用,根據(jù)PLI函數(shù)調(diào)用變量的屬性選擇相應(yīng)的處理策略。
          PLI函數(shù)要實(shí)現(xiàn)的具體功能在calltf函數(shù)中編寫,在這個(gè)函數(shù)中可以通過(guò)使用tf_getp(n)和tf_putp(n,val-ue)函數(shù)讀取時(shí)序?qū)拥臄?shù)據(jù)和對(duì)時(shí)序?qū)拥臄?shù)據(jù)賦值,其中n表示變量的位置,value表示變量要賦的值。如果時(shí)序?qū)拥臄?shù)據(jù)為數(shù)組類型,使用tf_nodeinfo()函數(shù)讀取和修改Verilog內(nèi)存數(shù)組和變量數(shù)組中的內(nèi)容。當(dāng)調(diào)用tf_nodeinfo()函數(shù)來(lái)訪問(wèn)Verilog數(shù)組中的值時(shí),函數(shù)將返回一個(gè)指向仿真數(shù)據(jù)結(jié)構(gòu)中數(shù)組實(shí)際存儲(chǔ)空間的指針。一旦PLI應(yīng)用獲得了該指針,數(shù)組中的值在仿真過(guò)程中既可以被讀取也可以被修改。要訪問(wèn)數(shù)組,并不需要每次都調(diào)用tf_nodeinfo()函數(shù),只需要保存好初次調(diào)用tf_nodeinfo()獲得的數(shù)組指針,tf_nodeinfo()需要在系統(tǒng)函數(shù)/任務(wù)調(diào)用時(shí)在參數(shù)中指定一個(gè)選定的單元。



          評(píng)論


          相關(guān)推薦

          技術(shù)專區(qū)

          關(guān)閉
          看屁屁www成人影院,亚洲人妻成人图片,亚洲精品成人午夜在线,日韩在线 欧美成人 (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); })();