← ブログに戻るCPUアーキテクチャ

命令レジスタとデコード段

教育用CPUが命令を取り込み、オペコード・レジスタ・即値フィールドを抽出し、検証済みの制御信号へ変える仕組みを、RISC-Vとx86の文脈とともに解説します。

DennyDenny
読了まで約11分
Chalkboard feature illustration for “命令レジスタとデコード段”

要約: 単純なCPUでは、命令レジスタ(IR)がフェッチした命令を取り込むため、デコード段は安定したビットを見られます。デコード段は命令形式を特定し、レジスタと即値のフィールドを抽出し、符号化が合法か確認して、後段のための制御情報を生成します。現代のプロセッサーでは、この役割が1つの文字どおりのアーキテクチャ上の「IR」ではなく、フェッチバッファとパイプラインレジスタに分散されていることがあります。

プログラムカウンタが答えるのはどこからフェッチするかです。デコード段が答えるのはフェッチしたビットが何を意味するかです。その間に教育用CPUは通常、命令レジスタを置きます。これは、制御論理が現在の命令を調べる間、その命令を保持するフリップフロップのバンクです。

このモデルは有用ですが、境界を理解する必要があります。命令レジスタはほとんどのISAでプログラマーから見えるレジスタではなく、高性能実装ではフェッチブロック、キュー、パイプラインレジスタ、デコード済み操作キャッシュに多数の命令を同時に保持することがあります。「IR」は教育用データパスでの役割の名称であり、普遍的な物理部品の名前ではありません。

教育用データパス

小さなマルチサイクルCPUは、次のように描けます。

PC → instruction memory → instruction register → field extraction → control

命令フェッチイベントでは、次が起きます。

  1. PCが命令アドレスを供給する。
  2. 命令メモリが1語の命令を返す。
  3. IRがアクティブなクロックエッジでその語を取り込む。
  4. 組合せデコード論理が保存されたビットを解釈する。

IRの書き込みイネーブルは、新しい命令を受け入れるべきときだけアサートされます。ストール中、IRは古い値を保持します。リセットまたはパイプラインフラッシュ中、コントローラーは保存された命令を無効と印付けするか、無害な操作で置き換えます。

マルチサイクルデータパスの一部では、メモリとIRの間にメモリデータレジスタを置きます。別のものではメモリ出力を直接取り込みます。どちらの順序も普遍的ではありません。必要なレジスタは、選んだメモリインターフェースのタイミングとハンドシェイクによって決まります。

小さな符号化例

8ビット教育用ISAが、次の形式を定義するとします。

7             5 4             2 1             0
┌──────────────┬───────────────┬───────────────┐
│ opcode [2:0] │ register [2:0]│ mode / small  │
│              │               │ immediate     │
└──────────────┴───────────────┴───────────────┘

正確なフィールドはISA設計の選択です。8ビットでは、大きなオペコード空間、独立した2つのレジスタオペランド、有用な即値を同時には符号化できません。そのため実際の教育用ISAでは複数の形式を使うことがよくあります。たとえば、次のようになります。

  • レジスタ命令では、ビットをソースアドレスと宛先アドレスに割り当てる。
  • 即値ロード命令では、下位ビットの大半を定数として使う。
  • 分岐命令では、同じビットをオフセットとして解釈する。

デコードはまず形式を確定し、それから残りのビットをそれに従って解釈しなければなりません。すべてのビットに永続的に1つのラベルを与えると、誤った回路になります。

固定位置のフィールド:RISC-Vの例

ベースRISC-V ISAは32ビット命令形式を使います。R型命令では、次のとおりです。

31         25 24    20 19    15 14   12 11      7 6        0
┌────────────┬────────┬────────┬───────┬─────────┬──────────┐
│   funct7   │   rs2  │   rs1  │ funct3│    rd   │  opcode  │
└────────────┴────────┴────────┴───────┴─────────┴──────────┘

レジスタフィールドはベース形式を通じて一貫した位置にあります。

opcode = IR[6:0]
rd     = IR[11:7]
funct3 = IR[14:12]
rs1    = IR[19:15]
rs2    = IR[24:20]
funct7 = IR[31:25]

これらのスライスは演算ではなく配線です。rs1 と rs2 はレジスタファイルの読み出しアドレスへ入り、rd は候補となる宛先を示し、オペコードと機能ビットは操作クラスとその変種を特定します。

即値にはより注意が必要です。いくつかのRISC-V形式では、即値ビットは意図的に命令中へ分割されています。ハードウェアは指定された順序でそれらを連結し、アーキテクチャで定義された符号ビットから符号拡張しなければなりません。これも単純な組合せ配線ですが、常に1つの連続したスライスとは限りません。

デコードはオペコードデコーダ以上のもの

8個の完全な操作を持つ玩具ISAなら、3対8デコーダによりワンホット信号を作れます。

オペコード教育用操作ワンホット結果
000NOPis_nop
001LOADis_load
010STOREis_store
011ADDis_add
100SUBis_sub
101JUMPis_jump
110BRANCH-Zis_branch_z
111HALTis_halt

すると、これらの信号から制御式を導けます。

RegWrite=is_load∨is_add∨is_sub\text{RegWrite} = \text{is\_load} \lor \text{is\_add} \lor \text{is\_sub} MemWrite=is_store\text{MemWrite} = \text{is\_store}

これはデコーダと積和形論理への有用な導入ですが、実際のデコーダの一般的構造ではありません。

より大きなISAでは、次のようになります。

  • 主オペコードは、1つの操作ではなく形式または命令ファミリーを選ぶことが多い。
  • 二次的な機能フィールドがファミリーのメンバーを区別する。
  • モードまたはプレフィックス状態がオペランドサイズと解釈を変えることがある。
  • 一部のビットパターンは予約済みまたは違法である。
  • 特権と拡張機能の可用性が合法性に影響し得る。
  • 制御出力は通常、命令ごとに専用の配線を1本設けるのではなく符号化される。

正しいデコーダは、未対応の符号化を近い合法命令として誤って扱うのではなく、拒否しなければなりません。

デコードが生成するもの

出力は、多数の無関係な配線ではなく、制御バンドルと考える方が適切です。教育用バンドルには次のフィールドを含められます。

フィールド意味
alu_op加算、減算、論理操作、比較、パススルーを選択する
src_a / src_bレジスタ、PC、即値、定数のオペランドを選ぶ
reg_write適切な後段でレジスタファイルへの書き込みを許可する
mem_read / mem_writeデータメモリ操作を要求する
result_sourceALU、メモリ、PC相対値、または別の書き戻し元を選ぶ
branch_kind分岐なし、条件分岐、直接ジャンプ、間接ジャンプを選ぶ
immediate再構成および拡張された定数
legal現在の機械状態で符号化が対応済みかを示す

これらの信号は、パイプラインの有効性と段のタイミングで修飾しなければなりません。デコードで組合せ的に reg_write = 1 となることは、レジスタファイルを直ちに更新してよいという許可ではありません。書き込みは、命令がフラッシュもフォルトもされず指定された段に到達したときだけ起こります。

固定長と可変長の命令

命令長はデコード問題の前段を変えます。

固定長の例:Arm A64

Arm A64命令は32ビット幅です。フェッチがアラインされた語を供給すれば、フィールド位置を直接調べられます。固定長により命令境界の発見は簡単になりますが、すべての操作または即値符号化が自明になるわけではありません。

圧縮命令を持つRISC-V

ベースRISC-V命令は32ビットです。オプションの圧縮拡張は16ビット命令を追加し、アーキテクチャはさらに長い符号化のための長さ符号化方式を予約しています。フェッチは、PCを進め次の命令をアラインする前に、次の命令が2、4、または別の対応バイト数を占めるかを決定しなければなりません。

可変長の例:x86

x86命令は1~15バイトで、レガシーまたは現代的なプレフィックス符号化、オペコードバイト、ModR/MおよびSIBアドレッシングバイト、変位、即値データを含み得ます。どの部分が存在するかは、先行するバイトに依存します。

したがって現代のx86フロントエンドには、意味デコードの前または並行して、命令境界と長さのデコードが必要です。実装は異なります。すべてのプロセッサーが1つの固定ブロックサイズをフェッチする、1つのキューレイアウトを使う、あるいはすべての命令を同じ経路で変換する、と主張するのは安全ではありません。Intelのアーキテクチャマニュアルはソフトウェアから見える符号化を定義しますが、正確なパイプラインはマイクロアーキテクチャ固有です。

固定長と可変長は、RISCとCISCの同義語ではありません。1つの符号化特性を表しているだけです。

ハードワイヤード制御と逐次制御

小さなCPUは、ブール論理から直接制御を生成できます。マルチサイクルコントローラーは代わりに、複数の内部ステップを記述する状態機械または制御ストアを使えます。実際のプロセッサーでは、高速なデコード経路と、より複雑な操作に対する逐次処理を組み合わせることがあります。

有用な区別は次のとおりです。

  • 組合せデコードは、現在のフィールドを初期の制御表現へ写像する。
  • 逐次制御は、時間をかけて複数の内部操作を発行する。

どちらの方法も自動的に「RISC」または「CISC」になるものではなく、マイクロコード実装が本質的に遅いわけでもありません。性能は実装全体とワークロードに依存します。

パイプライン制御:ストール、フラッシュ、有効性

複数の命令が重なると、命令ビットは状態の一部にすぎません。各パイプラインレジスタにも制御メタデータが必要です。

ストール

次段が命令を受け入れられない場合、現在のフェッチ/デコードレジスタはデータを保持するか、ready/validハンドシェイクに参加しなければなりません。有効状態がストールしている間にビットを進めると、命令と制御のアラインメントを失います。

フラッシュ

分岐予測ミス、例外、リセットは、より若い命令を無効にできます。一部のISAでは全ゼロの符号化自体が合法であり得るため、命令ビットだけを消去するより有効ビットを消去する方が堅牢です。

依存関係の処理

デコードは、ハザード検査のためにソースと宛先レジスタを特定できます。応答はストール、フォワーディング選択、レジスタリネーミング、またはほかの実装固有の操作になり得ます。フィールド抽出が識別子を提供し、後の制御がそれらをどう扱うかを決めます。

よくある設計ミス

  • メモリには常にMDRが必要だと仮定する。 普遍的な図からではなく、実際のメモリタイミングとインターフェースからレジスタを追加します。
  • 命令がまだアクティブな間にIRを変える。 デコードが安定したビットを見るよう、書き込みイネーブルまたはハンドシェイクを使います。
  • 主オペコードだけをデコードする。 機能フィールド、モード、拡張、合法性検査が必要な場合があります。
  • 数値的な図の順序で即値ビットを連結する。 ISAのビット対応に正確に従い、指定された符号ビットから拡張します。
  • 修飾されていないデコードから副作用を直接駆動する。 書き込みをパイプライン有効性、段タイミング、例外/フラッシュ状態でゲートします。
  • 任意の命令パターンへリセットする。 有効ビットまたはコントローラーのリセット状態を選び、全ゼロビットがNOPを意味すると仮定しません。
  • 教育用の波形を物理タイミングの証拠として扱う。 モデルが示せるのは論理的な順序であり、シリコンのセットアップ/ホールド収束ではありません。

教育用デコーダを構築して検証する

Sequential Instruction Executorを開き、次を特定してください。

  1. 命令を保存する要素。
  2. 各フィールドを作る配線。
  3. 各フィールドから影響を受ける制御出力。
  4. それらの出力がアーキテクチャ状態を変えることを許可される時点。

次に、コンパクトなテスト表を作ります。

テストクラス変えるもの期待結果
各合法オペコード主オペコードビット正しい操作ファミリーと副作用イネーブル
機能の変種二次フィールド正しいALUまたはアドレッシング変種
レジスタアドレスrs / rd フィールド正しいレジスタポート、操作は不変
即値の極値ゼロ、最大正、最小負正しい連結と拡張
予約済み符号化未対応のビットパターン違法命令経路、意図しない書き込みなし
ストール数クロックの間デコードを保持する命令と制御がアラインされたまま
フラッシュ実行中の命令を無効化するレジスタまたはメモリへの副作用なし

1つの例を手で切り替えるのは例示にはなりますが、十分な検証ではありません。合法なすべての操作クラスと、代表的な違法符号化を対象にします。

CPU内での位置付け

プログラムカウンタがフェッチアドレスを供給します。デコードがオペランドと制御意図を特定します。CPUフラグレジスタは、フラグベースISAでの分岐条件の候補となる1つの源です。ほかのISAはレジスタを直接比較します。制御装置が教育用データパスを逐次制御し、副作用を修飾します。

これらの要素を合わせると小さなプロセッサーの制御フローを説明できますが、そのどれか1つが「制御プレーン全体」ではありません。キャッシュ、予測、例外、特権、ハザード、パイプライン状態が、より大きな機械ではさらに制御を加えます。

一次資料

フェッチ・デコード・実行の詳細解説へ続き、教育用CPUの符号化を1つ変更して、デコーダ、テスト、ドキュメントを一緒に更新してください。

アイデアを実際に動く回路にしましょう。