VerilogHDLのデバッグをVSCodeでテストベンチを使わずにやる

## はじめに
### 趣旨
DigitalJSで手軽にVerilogHDLをデバッグする環境を構築する方法を共有したい
### 内容
Visual Studio Code（以降、VSCode）でDigitalJSを使ってVerilogHDLをデバッグする環境を整える手順

## 導入
### FPGA開発の流れ
FPGAの開発をしたい場合、VerilogHDL/SystemVerilogやVHDLといった言語で回路を記述する（回路のひとまとまりをモジュールと呼ぶ。詳細は割愛）。モジュール作成後、安全のためやデバッグのしにくさから、実機に乗せる前に検証のために論理シミュレーションを行い、動作検証を行う。その際、基本的にはテストベンチと呼ばれるシミュレーション用のモジュールを作成し、波形を確認しながら検証する。
### 問題点
テストベンチ用のモジュールは独特でわざわざ書き方を覚える必要があるし、初心者にはちょっととっつきにくい。また、大体の論理シミュレーションの環境構築とツールの操作がとっつきにくい印象。
### そこで
[DigitalJS](https://github.com/tilk/digitaljs)というJavascriptで論理シミュレーションを実装しているプロジェクトを利用すれば、手軽に回路のシミュレーションができる。これにより、テストベンチを書かずとも記述した回路のシミュレーションが可能かつ、論理回路図も確認することができる。2022年に**VSCodeの拡張機能**としても利用できるようになっていたので、環境構築の手順を次節以降に記載。
いきなりFPGA動かす前にちょっとHDL勉強してみようかなと思ったときや、経験者でもテストベンチわざわざ書かなくてもいいかなと思ったときなどのために、パッとシミュレーションする環境ほしいなと思ったとき使いやすいのではないかと思う。

## 構築手順
1. VSCodeをインストール
    - [こちら](https://code.visualstudio.com/download)から
1. VSCodeの拡張機能アイコンをクリックし、「digitaljs」で検索
1. DigitalJSをインストール
![スクリーンショット 2022-12-14 224817.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109639/88710ae5-85f3-a792-5e60-b9b16c5dedae.png)
    - Version Historyを見ると、DigitalJS-VSCよりもDigitalJSの方が新しいので赤矢印の方でいいと思う
1. VerilogHDLのファイルを作成
    - 以降、下記のファイルでテスト
    ```verilog:state_machine.v
    module state_machine (clk, in, reset, out);
        input   clk, in, reset;
        output  [1:0]out;
        reg     [1:0]out;
        reg     [1:0]state;
        parameter S0 = 0, S1 = 1, S2 = 2;
    
        always @ (posedge clk) begin
            case (state)
                S0:
                    out = 2'b01;
                S1:
                    out = 2'b10;
                S2:
                    out = 2'b11;
                default:
                    out = 2'b00;
            endcase
        end
        always @ (posedge clk) begin
            if (reset)
                state <= S0;
            else
            case (state)
                S0:
                    state <= S1;
                S1:
                    if (in)
                        state <= S2;
                    else
                        state <= S1;
                S2:
                    if (in)
                        state <= S0;
                    else
                        state <= S1;
            endcase
        end
    endmodule
    ```
1. `.v`ファイルをVSCodeで開くと右上にDigitalJSのアイコンが現れるのでそれをクリック
![スクリーンショット 2022-12-14 225032.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109639/3b7da6bd-37c7-2053-c47d-783f3856b690.png)
1. 右下に、「Add (ファイル名) to a new circuit?」みたいなアラートが出るので、Yesをクリック
1. 初回はNo active circuit.という表示が出るので、Synthesizeをクリック
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109639/7d536b24-2423-0923-4551-843ae72f33a8.png)
    - モジュールに記述ミスがあった場合、Synthesis errorとして右下に表示される
1. Synthesizeに成功したら下記のような画面が表示され、デバッグできる
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109639/ba3c2e37-5d02-a1e7-a65a-c184f3aed2de.png)

## デバッグ手順
### やること概要
基本的には左下のCONTROLというビューを操作して入力を変化させたり、時間を進めて、回路図の見たい部分をクリックして値を確かめたり、トリガーを設定して波形を確認しながら動作検証をする。

Synthesize完了後、下図のような外観で自動で時間が進んでいる（図の11999の数字が増え続けている）ので、デバッグする場合はとりあえず一時停止ボタン（図のCONTROLのすぐ下のボタン）を押してシミュレーションを止めといたらいい。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109639/6ca3919c-a40f-6db3-5e50-a3427800d063.png)

すべての機能を確認・検証してないので、最低限これぐらい知っとけば軽いシミュレーションはできるという情報のみ共有する（後日詳細をまとめる予定）。

### CONTROLビューについて
一時停止時のCONTROLビューは下記の外観になる
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109639/8c6590ae-2c29-fd48-3534-864aeefc178e.png)
- 上部四つのボタン（下記、左から順番）
    - Startボタン：シミュレーションを再開し、トリガーまで進める
    - Fast-forward：シミュレーションを再開、トリガーまで進める（時間が早く進む）
    - Single Step：時間を1ずつ進める
    - Run until next event：回路でどこかの値が変わるタイミングまで時間を進める
- 時計マーク：現在の時間（単位不明）
- clk：レジスタの動作クロック（数字はクロック周期）
- in/reset：モジュールのinput（設定可）
- out：モジュールのoutput（設定不可）
### 回路図のビューについて
- 要素をドラッグドロップで移動できる
- wireにカーソルを持っていくと値が見れる
- wireの値が変わると色が変化する
    - 灰色がX（不定）
    - 赤が0
    - 緑が1以上
- 虫眼鏡マークをクリックすると次節の波形ビューで波形が確認できる
- wireを削除もできるが、効率的な使い方は不明

### 波形のビューについて
- Synthesize完了後は回路図のビューの下に隠れているので、バーをドラッグして表示させる
![スクリーンショット 2022-12-15 005848.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109639/d21f1621-fde4-3b65-3e93-215b2d6f2029.png)
![スクリーンショット 2022-12-15 005911.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109639/5eb4fb3b-005a-1d55-67fb-468a979229ab.png)
- 左上の+ - ボタンで波形の拡大/縮小が可能（scaleの値が変化する）
- ▷ボタンはLive plotで、ONにしているとシミュレーション中に波形をアニメーションで見れる
- 例えば、clkのwireを波形ビューに追加したとき
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109639/95f8eb94-e6c7-cb23-412d-19eaffc52122.png)
    - wire名の横のボックスでトリガー設定できる
        - none: トリガーなし
        - ↑：0から1に変化したときにトリガー
        - ↓：1から0に変化したときにトリガー
        - ↕：値が変化したときにトリガー
        - X：第1bitの値を無視（この場合トリガーなしと同義）
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109639/ab59bd58-e0b3-c1da-0398-51df55a3d139.png)
- 波形の見え方
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109639/2e10368d-5d97-50bb-29a2-d7a6d9bb9751.png)


## 所感
最近は高位合成などが活発で生のHDLを書くことは減ってきていると思うが、このツールを使えば回路も図示されてイメージしやすいのでFPGA開発の勉強になるし、簡単に論理シミュレーションをするにはいい環境と思う。
テストベンチを使った検証や、組み合わせ回路の例を[**こちら（飽和符号対応加算器）**](https://lethediana.sakura.ne.jp/tech/archives/uncategorized-ja/1660/)に掲載したので、ご興味あればご覧ください。