• 正文
    • 1.?策略模式
    • 2.?參考代碼
  • 推薦器件
  • 相關(guān)推薦
申請入駐 產(chǎn)業(yè)圖譜

設(shè)計模式在芯片驗證中的應(yīng)用——策略

2024/06/12
1709
加入交流群
掃碼加入
獲取工程師必備禮包
參與熱點資訊討論

1.?策略模式

策略模式是一種行為設(shè)計模式, 它能讓你定義一系列算法, 并將每種算法分別放入獨立的類中, 以使算法的對象能夠相互替換。

在RTL設(shè)計中可能包含了復(fù)雜的多個訪問仲裁邏輯,使用了多種算法來確定訪問內(nèi)存優(yōu)先級順序,包括規(guī)定優(yōu)先級、輪詢仲裁等等。仲裁器的輸入是多個請求者信號,以及選擇要使用的仲裁算法的配置。根據(jù)選擇的類型和請求者信號的值,仲裁器確定具有最高優(yōu)先級的請求源,并授予它訪問內(nèi)存的權(quán)利。如下圖所示,仲裁類型可以動態(tài)配置,這就是為什么該特性適合使用策略設(shè)計模式進(jìn)行建模。

在該模式中,可以在testcase運行中從提供的一系列算法中選擇要應(yīng)用的特定算法。此外,還可以直接為仲裁添加新算法,而無需修改之前代碼。值得注意的是,之前講到的裝飾器設(shè)計模式也可用于動態(tài)更改行為,關(guān)鍵的區(qū)別在于,裝飾器模式在原功能基礎(chǔ)上添加額外的功能,而策略者模式直接更改原先功能??偟脕碚f,策略模式可以讓你改變對象的內(nèi)部結(jié)構(gòu),裝飾器模式允許你更改對象的皮膚。

策略設(shè)計模式主要包括以下幾個組件:

策略(Strategy):定義了所有具體策略(Concrete Strategies)的通用接口,它聲明了一個上下文(Context)用于執(zhí)行策略的方法。在這個例子中,策略定義了仲裁的接口函數(shù)arb_winner()。

具體策略(Concrete Strategies):實現(xiàn)了上下文所用算法的各種不同變體。在這個例子中,對于每個必要的算法,定義了一個具體策略類,提供特定算法的實現(xiàn)。將每個算法包裝到一個單獨的類中可以提高代碼的可讀性和可擴(kuò)展性。

上下文(Context):維護(hù)指向具體策略的引用,且僅通過策略接口與該對象進(jìn)行交流。比如UVM scoreboard組件依賴于Strategy,檢查RTL內(nèi)的仲裁邏輯是否正確實現(xiàn),那么UVM scoreboard可以被認(rèn)為是Context。

客戶端(Client):會創(chuàng)建一個特定策略對象并將其傳遞給上下文。上下文則會提供一個設(shè)置函數(shù)以便客戶端在運行時替換相關(guān)聯(lián)的策略。當(dāng)上下文需要運行算法時,它會在其已連接的策略對象上調(diào)用執(zhí)行方法。上下文并不清楚其所涉及的策略類型與算法的執(zhí)行方式。本例的客戶端是example_application。

下圖為策略設(shè)計模式在仲裁中應(yīng)用的UML類圖。

策略模式讓你能將不同行為抽取到一個獨立類層次結(jié)構(gòu)中, 并將原始類組合成同一個, 從而減少重復(fù)代碼。而且讓你能將各種算法的代碼、 內(nèi)部數(shù)據(jù)和依賴關(guān)系與其他代碼隔離開來。不同客戶端可通過一個簡單接口執(zhí)行算法, 并能在運行時進(jìn)行切換。

2.?參考代碼

仲裁處理的策略設(shè)計模式參考代碼如下:

virtual class strategy;    pure virtual function int arb_winner(ref bit req_arr[3]);endclass : strategy

class strategy_low_priority extends strategy;
    virtual function int arb_winner(ref bit req_arr[3]);        for (int i=0; i<3; i++) begin            if (req_arr[i] == 1) begin                return i;            end        end        return -1;    endfunction : arb_winner
endclass : strategy_low_priority

class strategy_high_priority extends strategy;
    virtual function int arb_winner(ref bit req_arr[3]);        for (int i=2; i>=0; i++) begin            if (req_arr[i] == 1) begin                return i;            end        end        return -1;    endfunction : arb_winner
endclass : strategy_high_priority
class my_context;
    local strategy m_strategy;
    function void set_strategy(strategy _m);        m_strategy = _m;    endfunction : set_strategy
    function int execute_strategy(ref bit req_arr[3]);        return m_strategy.arb_winner(req_arr);    endfunction : execute_strategy
endclass : my_context

模擬測試代碼如下:

class example_application;
    rand bit low_priority;    rand bit high_priority;
    constraint p_cons { low_priority + high_priority >= 1; }
    function void main();        int result;        bit req_arrary[3] = '{1'b0, 1'b1, 1'b1};        strategy stg;        my_context m_ctx = new();        `uvm_info("strategy", $psprintf("low_priority:%b, high_priority:%b", low_priority, high_priority), UVM_LOW)        $display("The input req0:%b, req1:%b, req2:%b", req_arrary[0], req_arrary[1], req_arrary[2]);        if ( low_priority ) begin            stg = strategy_low_priority::new();            m_ctx.set_strategy(stg);            result = m_ctx.execute_strategy(req_arrary);            $display("For low priority, the result is: %0d", result);        end        if ( high_priority ) begin            stg = strategy_high_priority::new();            m_ctx.set_strategy(stg);            result = m_ctx.execute_strategy(req_arrary);            $display("For high priority, the result is: %0d", result);        end
    endfunction : main
endclass : example_application

輸出仿真日志如下:

 | # [strategy] low_priority:1, high_priority:1 | # The input req0:0, req1:1, req2:1 | # For low priority, the result is: 1 | # For high priority, the result is: 2

從仿真結(jié)果可知,low_priority為1,high_priority為1,因此example_application類選取了strategy_low_priority類和strategy_high_priority類兩個算法。

在strategy_low_priority類中,輸入信號中,req0=0,req1=1,req2=1,req1輸入口被選中,因此輸出的結(jié)果是1。

在strategy_high_priority類中,輸入信號中,req0=0,req1=1,req2=1,req2輸入口被選中,因此輸出的結(jié)果是2。

微信號|chip_yes,微信公眾號|專芯致志er

推薦器件

更多器件
器件型號 數(shù)量 器件廠商 器件描述 數(shù)據(jù)手冊 ECAD模型 風(fēng)險等級 參考價格 更多信息
NC7WZ14P6X 1 Fairchild Semiconductor Corporation Inverter, LVC/LCX/Z Series, 2-Func, 1-Input, CMOS, PDSO6, 1.25 MM, ROHS COMPLIANT, EIAJ, SC-88A, SC-70, 6 PIN
$0.34 查看
ECS-250-18-23A-EN-TR 1 ECS International Inc Parallel - Fundamental Quartz Crystal, 25MHz Nom, ROHS COMPLIANT, MINIATURE, SMD, 2 PIN
$0.89 查看
S25FL512SAGMFIR10 1 Spansion Flash, 512MX1, PDSO16, 0.300 INCH, LEAD FREE, PLASTIC, MO-013EAA, SOIC-16
$11.03 查看

相關(guān)推薦

登錄即可解鎖
  • 海量技術(shù)文章
  • 設(shè)計資源下載
  • 產(chǎn)業(yè)鏈客戶資源
  • 寫文章/發(fā)需求
立即登錄