Verilator を使用した Verilog lint

9217c5e18fc45e85fd429adcfcf74421.png

FPGA の設計は非情であるため、入手可能なソフトウェアを使用してチェックする必要があります。Verilator は、lint (設計上の問題の静的分析) もサポートする Verilog シミュレーターです。Verilator は、合成ツールが見逃す可能性のある問題を検出するだけでなく、高速に実行します。Verilator は、SDL を使用したグラフィックス シミュレーションにも適しています。

ベリレーターをインストールする

Linux

Verilator はほとんどの Linux ディストリビューション リポジトリで利用でき、Windows ゲスト Linux システムでの実行に適しています。

Debian および Ubuntu ベースのディストリビューションの場合、apt を使用して Verilator をインストールできます。

apt update
apt install verilator

アップルシステム

macOS では、Homebrew パッケージ マネージャーを介して Verilator の最新バージョンをインストールできます。

brew install verilator

他のプラットフォーム (FreeBSD など) に Verilator をインストールするには、公式 Verilator インストール ガイドを参照してください。

基本的なリンティング

スタンドアロン モジュールの場合、lint 自体は簡単です。

verilator --lint-only -Wall foo.v
--lint-only- 告诉 Verilator 进行 lint 但不生成任何仿真输出
-Wall- 打开额外的风格检查

すべてがうまくいけば、Verilator からのメッセージは表示されません。

Verilator が潜在的な問題を検出した場合、警告を無効にする方法を含む明確な推奨事項を提供します。Verilator マニュアルには、考えられる警告のリストが含まれています。

単純な「追加」モジュールを作成し、いくつかの問題を設定してから、lint を実行しましょう。

`default_nettype none

module add (
    input  wire clk,
    input  wire [3:0] x,
    input  wire [3:0] y,
    output reg z,
    output reg c
    );

    always @(posedge clk) begin
        z <= x + y;
    end
endmodule

糸くずチェックを実行する

$ verilator --lint-only -Wall add.v
%Warning-WIDTH: add.v:12:11: Operator ASSIGNDLY expects 1 bits on the Assign RHS, but Assign RHS's ADD generates 4 bits.
                           : ... In instance add
   12 |         z <= x + y;
      |           ^~
                ... Use "/* verilator lint_off WIDTH */" and lint_on around source to disable this message.
%Warning-UNDRIVEN: add.v:8:16: Signal is not driven: 'c'
                             : ... In instance add
    8 |     output reg c
      |                ^
%Error: Exiting due to 2 warning(s)

最初の問題は幅です。x と y は 4 ビット幅ですが、z には明示的な幅がないため、1 ビット幅しかありません。

これを行うことで幅の警告を無視できます。

always @(posedge clk) begin
        /* verilator lint_off WIDTH */
        z <= x + y;
        /* verilator lint_on WIDTH */
    end

これは、何もせずに問題を隠すだけです。

代わりに、z の幅を 4 に設定することで問題を解決できます。

output reg [3:0] z,

これにより Verilator の警告は表示されなくなりますが、問題が完全に解決されるわけではありません。

たとえば、x と y が両方とも 4'b1000 の場合はどうなりますか? 加算がオーバーフローして、4'b0000 の z 値が計算されます。この例は、lint の制限の 1 つを示しています。lint はさまざまな信号の幅を調べることはできますが、信号に適用されるすべてのロジックを考慮することはできません。

したがって、z の幅を固定する代わりに、それを c キャリー信号として使用することもできます。これにより、「信号が駆動されていません」という警告も解決されます。

always @(posedge clk) begin
        {c,z} <= x + y;
    end

依存関係とパス

あるモジュールが別のモジュールに依存している場合はどうなりますか? Verilator は、現在のパスで一致するモジュールを検索します。モジュール検索パスに追加のディレクトリを追加したい場合は、-I を使用できます。たとえば、top.v が ../maths ディレクトリ内のモジュールに依存している場合:

verilator --lint-only -Wall -I../maths top.v

複数の -I パラメータを使用して、複数のディレクトリを含めることができます。

ブラックボックスと空のモジュール

ほとんどのデザインは、PLL を使用してクロックを生成するなど、ソースのないベンダー プリミティブまたは IP コアに依存しています。ベンダー プリミティブを参照するモジュールを lint しようとすると、次のようなエラーが表示されます。

%Error: clock_pix.sv:29:5: Cannot find file containing module: 'MMCME2_BASE'
   29 |     MMCME2_BASE #(
      |     ^~~~~~~~~~~
%Error: clock_pix.sv:29:5: This may be because there's no search path specified with -I<dir>.
   29 |     MMCME2_BASE #(
      |     ^~~~~~~~~~~
        ... Looked in:
             MMCME2_BASE
             MMCME2_BASE.v
             MMCME2_BASE.sv
             obj_dir/MMCME2_BASE
             obj_dir/MMCME2_BASE.v
             obj_dir/MMCME2_BASE.sv

最初のアイデアは、MMCME2_BASElint を除外する方法を見つけることかもしれません。残念ながら、Verilog は「慎重に設計しないとチェックできず、設計全体が必要です」。この問題は、プリミティブ用の空のモジュールを作成することで解決できます。空のモジュールには IO が含まれますが、ロジックは含まれません。

たとえば、ザイリンクスの BUFG プリミティブ用に空のモジュールが作成されます。

module BUFG (
    input  wire logic I,
    output      logic O
    );

    // NULL MODULE

endmodule

空のモジュールを作成するのは少し面倒ですが、デザイン全体を確認することができます。null モジュールを使用するには、それが Verilator の検索パスにあることを確認してください (前のセクションを参照)。

リンティングの免除

大規模なデザインやサードパーティのソースを使用したデザインのリンター警告を排除する必要がある場合、/* verilator lint_off */ コメントが機能しない可能性があります。Verilator 4.028 以降では、ソース コードに触れることなく警告を処理するための Waivers を作成できるようになりました。詳細については、Stefan Wallentowitz の投稿 Verilator Waivers (https://wallento.cs.hm.edu/post/20200612-verilator-waivers/) を参照してください。

リンティングシェルスクリプト

多数のトップレベル モジュールやインクルード ディレクトリがある場合は、Makefile または単純なシェル スクリプトを使用して自動的にチェックできます。

次のシェル スクリプトは、このスクリプトと同じディレクトリ内のすべてのトップレベル モジュールを lint します。

#!/bin/sh

DIR=`dirname $0`

echo "## Linting top modules in ${DIR}"
for f in ${DIR}/top_*\.*v; do
    echo "##   Checking ${f}";
    verilator --lint-only -Wall -I${DIR} -I${DIR}/../common $f;
done

-I パラメータは、独自の設定に合わせて調整できます。top_*.*v は、拡張子 .v および .sv を持つファイルをキャプチャします。

要約する

今日はVerilatorについてのVerilog Lintの紹介ですが、これは強力なツールなので興味のある方はぜひ試してみてください〜

おすすめ

転載: blog.csdn.net/Pieces_thinking/article/details/133110044