FPGA 版 FM 音源 (72) -- FPGA 版 EG (16)

前々回の記事で述べたように、スロット・アドレスの割り付けには 8 バイト中に 2 バイトの「穴」(未使用領域) があり、これをどう扱うかで次の 3 つの方法が考えられます。

  1. 2 ポート RAM の書き込み側で「穴」をスキップして連続アドレスに詰め込む
  1. 2 ポート RAM の書き込み側では「穴」のあるまま書き込んで、読み出し側で「穴」の領域をスキップする
  1. 書き込み側、読み出し側のいずれも特別な処理はせず、「穴」をそのまま温存する

1. では書き込み時に「穴」を潰すので、読み出しは単に連続したアドレスを発生させれば済みます。

ただし、書き込みのアドレスはシーケンシャルではなくランダムに発生するので、書き込み時の「アドレス変換」は ROM やランダム・ロジックを使って行なう必要があり、回路が複雑化します。
2. では、書き込み時の変換は左の図のようにビットの「ローテート」だけで済みます。
読み出し側の「穴」のスキップは、左の図のように 32 ビット幅の読み出しアドレスの b0 〜 b2 は 6 進カウンタ、b3 〜 b4 は 3 進カウンタ、b5 は固定の「0」、b6 は 2 進カウンタという構成で実現できます。
3. では、書き込み/読み出し、いずれの側でも「穴」に対して特別な処理は行ないません。
1. および 2. では「穴」を潰して「スロット・メモリ」のハードウェア・リソースも、「タイム・スロット」の時間的リソースも割り当てず、「ハードウェア」としては存在しないものとして扱います。
それに対し、3. では「穴」に対してもスロット・メモリを割り付け、タイム・スロットも割り当て、「ハードウェア」として実体化するものの、単に「使わない」という選択をします。
リソースに余裕があるのなら、3. の方法が最も簡単です。
OPL3 (YMF262) を例にすると、マスター・クロックとして NTSC 色副搬送波の 3.579545 MHz の 4 倍の 14.31818 MHz を使い、

  14.31818 [MHz] / 288 = 49.7159 [kHz]

のサンプリング周波数を得ています。
この「288」というファクターは、

  288 = (8 × 36) = (6 × 48)

と表現できます。
OPL3 の持つオペレータの総数は 36 なので、おそらく、1 スロットあたり 8 マスター・クロック、1 サンプリング周期が 36 スロットで構成されているものと思われます。
外付け DAC 用のクロックが 1 サンプリング周期あたり 36 波なので、回路の簡略化のためにスロット計算も 1 サンプリング周期あたり 36 回になっていると見るのが妥当でしょう。
この構成を継承する場合、スロット数に余裕がないので 1. あるいは 2. の方法による必要があります。
マスター・クロックとサンプリング周波数の比率を同じに保ちながら、1 スロットあたり 6 マスター・クロック、1 サンプリング周期を48 スロットで構成することもできます。 その場合には 3. の方法が使えます。
今回の回路では、128 fs を必要とする SPDIF Tx モジュールを使用している関係で、サンプリング周波数 48 kHz とするためにマスター・クロックは 384 fs の 18.432 MHz に選んでいます。
マスター・クロックを分周してサンプリング周波数を得る過程に「36」というファクターは含まれないので、前述の 1. および 2. の方法は取れません。

  384 = (8 × 48) = (6 × 64)

なので、1 サンプリング周期あたり 48 スロット、あるいは 64 スロットの構成で、3. の方法を取ることができます。