2012年11月6日火曜日
2012年10月14日日曜日
AC'97 Codecを制御してみる 4
DRAMコントローラとクライアントモジュールとのI/FはMPIFという独自I/Fになっており、これは通常のREAD,WRITEコマンドの他にFILLとSWAPコマンドがある。

SWAPは同一アドレスへのREADとWRITEをアトミックに実行できるコマンドで、マルチCPU構成時のMutex制御(排他制御)等での使用を想定して設けたコマンドだが、それ以外にも使用できそうだ。
今作成中のDMACはREADを使っているが、SWAPを使うようにすればDMAバッファをリードした後にゼロクリアしたり、あるいは、マイクやLINE IN等の録音データで置き換えることができる。
バッファをcirculationモード、即ちリングバッファとして使用すれば、録音データの遅延再生機能を実現できる。LM4550は下図に示すとおり入力データをDACデータと合成して出力する機能もあるので、この機能と合わせるとリバーブレータ(残響効果器)のようなことができそうだ。

レジスタ仕様は以下のように変更した。

以下はシミュレーションの様子 (clear_to_zero 選択時)

replace_to_ADC_data モードで、遅延が250uS, 10mS, 100mS, 500mSになるようにして、動かしてみた。
250uS
10mS
100mS
500mS

SWAPは同一アドレスへのREADとWRITEをアトミックに実行できるコマンドで、マルチCPU構成時のMutex制御(排他制御)等での使用を想定して設けたコマンドだが、それ以外にも使用できそうだ。
今作成中のDMACはREADを使っているが、SWAPを使うようにすればDMAバッファをリードした後にゼロクリアしたり、あるいは、マイクやLINE IN等の録音データで置き換えることができる。
バッファをcirculationモード、即ちリングバッファとして使用すれば、録音データの遅延再生機能を実現できる。LM4550は下図に示すとおり入力データをDACデータと合成して出力する機能もあるので、この機能と合わせるとリバーブレータ(残響効果器)のようなことができそうだ。

レジスタ仕様は以下のように変更した。

以下はシミュレーションの様子 (clear_to_zero 選択時)

replace_to_ADC_data モードで、遅延が250uS, 10mS, 100mS, 500mSになるようにして、動かしてみた。
250uS
10mS
100mS
500mS
2012年10月9日火曜日
AC'97 Codecを制御してみる 3
AC'97 Codec用の制御回路を作成して、信号を出したり音楽データを再生させることはできた。
元々はCodecをDACやADCとして使ってみようと考えていたのだが、意外と出力のノイズが目立つので方針を変更して、本来のAC'97用コントローラの形にまとめてみることにした。
以下にブロック図を示す。

このコントローラは3つのブロックで構成される。 CodecへのPCMデータの出力はDMAによる方法とCPUによるレジスタへの書き込みによる方法を選べる。
DMAの場合、DRAM上にバッファ領域を確保しそのアドレスをレジスタに設定する。

DMACにはバッファの使い方で2つのモードを持たせた。1つはBEGINからENDまで転送したら動作完了となる non-circulation モードで、もう1つはENDに達したらBEGINから再び転送を行う circulation モードである。 前回の実験では音楽データ1曲分をDRAMに展開して再生させたが、これだと非常に大きなメモリ空間を占有してしまうことになる。 音楽データ全体はフラッシュメモリや外部記憶上にあり、そこから少しずつDRAM上のバッファに転送して出力するというやり方が一般的だろうと思う。 ただし、この場合はソフトウェアの介在が不可欠で、DMACのバッファからの読出しに同期してバッファのデータを更新する必要がある。このコントローラの場合は、DMACのポインタがTHRESHOLDレジスタで示すアドレスを通過したタイミングと、ENDレジスタで示すアドレスを通過したタイミングで割込みを発生できる。THRESHOLD通過割込みが発生した場合、BEGINからTHRESHOLD間のデータは転送済みなので、ソフトウェアはその領域を次のデータで更新する。同様にして、END通過割込みではTHRESHOLDからEND間のデータを更新する。もちろんこの方法の場合はDMACをcirculationモードで使用する。
全体的な外部仕様(レジスタ仕様)は以下のとおりだ。

元々はCodecをDACやADCとして使ってみようと考えていたのだが、意外と出力のノイズが目立つので方針を変更して、本来のAC'97用コントローラの形にまとめてみることにした。
以下にブロック図を示す。

このコントローラは3つのブロックで構成される。 CodecへのPCMデータの出力はDMAによる方法とCPUによるレジスタへの書き込みによる方法を選べる。
DMAの場合、DRAM上にバッファ領域を確保しそのアドレスをレジスタに設定する。

DMACにはバッファの使い方で2つのモードを持たせた。1つはBEGINからENDまで転送したら動作完了となる non-circulation モードで、もう1つはENDに達したらBEGINから再び転送を行う circulation モードである。 前回の実験では音楽データ1曲分をDRAMに展開して再生させたが、これだと非常に大きなメモリ空間を占有してしまうことになる。 音楽データ全体はフラッシュメモリや外部記憶上にあり、そこから少しずつDRAM上のバッファに転送して出力するというやり方が一般的だろうと思う。 ただし、この場合はソフトウェアの介在が不可欠で、DMACのバッファからの読出しに同期してバッファのデータを更新する必要がある。このコントローラの場合は、DMACのポインタがTHRESHOLDレジスタで示すアドレスを通過したタイミングと、ENDレジスタで示すアドレスを通過したタイミングで割込みを発生できる。THRESHOLD通過割込みが発生した場合、BEGINからTHRESHOLD間のデータは転送済みなので、ソフトウェアはその領域を次のデータで更新する。同様にして、END通過割込みではTHRESHOLDからEND間のデータを更新する。もちろんこの方法の場合はDMACをcirculationモードで使用する。
全体的な外部仕様(レジスタ仕様)は以下のとおりだ。

2012年9月29日土曜日
AC'97 Codecを制御してみる 2
だいぶ間が空いてしまった。
DIGILENT社のSpatan6 評価ボードであるAtlysに実装されているAC'97 odec (LM4550)を制御してみている。 LM4550とFPGA間のI/FはAC LinkというシリアルI/Fであり、256bitからなるフレームは、16bitまたは20bit長の全部で13固のスロットで構成される。これは、前回のブログに書いた。 FPGA側は素直に256bit長のparallel to serial変換回路を実装するのが安直であるが、13個のスロットには仕様上予約となっている項目や今回の実装では使用しない項目等があり、これらは全て0が設定するので、256bitのparallel to serial回路では無駄が多い気がして、以下のような回路にした。
送信部

受信部

この送受信部はCodecから出力されるクロック(12.288MHz)で動作するが、その上位の回路(送信データの供給元や受信データを格納先)は100MHzと50MHzとかの別のクロックで動作させたい。したがって、これら領域は異種クロックで動作することになるため、やりとりするデータのクロックの乗替えが必要になる。これは非同期FIFOを使うことにした。
送信用

受信用

回路としては大体こんな感じだが、例えば音を出すためには音源データが必要であり、以前作成したFunction Generator用のRTLを若干変更して組み込んだ。また、LM4550は初期状態では全てのボリュームがMute状態になっているため、必要なボリュームレジスタのMuteを解除する必要がある。Codec内部レジスタは本AC97コントローラのレジスタ経由でソフトウェアからアクセスできるようにしているので、Function Generator用のソフトウェアにその処理を追加した。
wavファイルデータをDRAMに展開しFunction GeneratorのLBUFの機能を使って再生させてみた。
(注意:曲が流れます。)
また、DDSで単一周波数信号(例えば1KHz)を出力させても音はでるが、オシロスコープで波形をみると輝線が太く波形的には汚い。どうも水晶発振器出力の24.576MHzが重畳しているようだ。
これは実装(基板設計)の問題と思われるのでRTLではどうしようもない。
DIGILENT社のSpatan6 評価ボードであるAtlysに実装されているAC'97 odec (LM4550)を制御してみている。 LM4550とFPGA間のI/FはAC LinkというシリアルI/Fであり、256bitからなるフレームは、16bitまたは20bit長の全部で13固のスロットで構成される。これは、前回のブログに書いた。 FPGA側は素直に256bit長のparallel to serial変換回路を実装するのが安直であるが、13個のスロットには仕様上予約となっている項目や今回の実装では使用しない項目等があり、これらは全て0が設定するので、256bitのparallel to serial回路では無駄が多い気がして、以下のような回路にした。
送信部

受信部

この送受信部はCodecから出力されるクロック(12.288MHz)で動作するが、その上位の回路(送信データの供給元や受信データを格納先)は100MHzと50MHzとかの別のクロックで動作させたい。したがって、これら領域は異種クロックで動作することになるため、やりとりするデータのクロックの乗替えが必要になる。これは非同期FIFOを使うことにした。
送信用

受信用

回路としては大体こんな感じだが、例えば音を出すためには音源データが必要であり、以前作成したFunction Generator用のRTLを若干変更して組み込んだ。また、LM4550は初期状態では全てのボリュームがMute状態になっているため、必要なボリュームレジスタのMuteを解除する必要がある。Codec内部レジスタは本AC97コントローラのレジスタ経由でソフトウェアからアクセスできるようにしているので、Function Generator用のソフトウェアにその処理を追加した。
wavファイルデータをDRAMに展開しFunction GeneratorのLBUFの機能を使って再生させてみた。
(注意:曲が流れます。)
また、DDSで単一周波数信号(例えば1KHz)を出力させても音はでるが、オシロスコープで波形をみると輝線が太く波形的には汚い。どうも水晶発振器出力の24.576MHzが重畳しているようだ。
これは実装(基板設計)の問題と思われるのでRTLではどうしようもない。
2012年8月31日金曜日
AC'97 Codecを制御してみる
AtlysボードにはNational SemiconductorのLM4550というAC'97 Codecが搭載されている。
Wikipediaによると、AC'97はIntelが提唱したサウンドインタフェースの標準規格で機能的には論理コントローラとアナログコーデックがありこれらがAC-Linkという5線式の双方向シリアルインターフェースバスで接続される。 LM4550は機能的にはアナログコーデックであり、今回これを制御する論理コントローラを作ってみようという訳だ。
LM4550のブロック図をデータシートから以下に引用する。

出力はLINE_OUT~MONO_OUTの3系統、入力はMIC~PHONEの7系統があるが、Atlysボードで使用できるのは出力はLINE_OUTとHP_OUT、入力はLINE_INとMIC1のみとなっている。

AC_LinkはBIT_CLK、SYNC、SDATA_OUT、SDATA_IN、RESET#からなるシリアルインターフェースで、SDATA_xxxがデータ信号であり、IN/OUTは論理コントローラ側からみた方向付けになっている。つまり、SDATA_OUTは論理コントローラ→コーデック、SDATA_INはコーデック→論理コントローラ。BIT_CLKは文字通りのビットクロックでSDATA_xxxはこのクロックに同期して転送される。このクロック信号はコーデックが駆動する。 SDATA_xxxで送受されるデータは以下のようなフレーム構造で全体のビット長は256ビットである。通常はフレーム周期は出力側のサンプリングレートに一致するので、BIT_CLKはサンプリングレートの256倍の周波数になる。
SDATA_OUTラインのデータフレーム構造は以下のようになっている。
1フレームは13個のSLOTで構成され、SLOT0は16ビット長のTAG情報、SLOT1~12は20ビット長で図に示す情報となっている。オーディオ情報とコーデック制御情報が多重化されていて、フレームサイズは固定長であるが、TAG SLOTのビットで有効・無効を表示できるようになっている。

SDATA_INラインのデータフレームは以下のようになっている。

今回は、以前作成したDDS IPからコーデックに出力したりDRAM上に何か音楽データを置いてコーデックに出力(再生)させたり、LINE_INにアナログ信号を入れてキャプチャしてみたりしてみたいと考えている。
AC'97の論理コントローラIPについて確固としたイメージを持っている訳でも無く、どちらかというとDAC/ADCとして使う感じなので、このプロジェクトのタイトルは「AC'97 IPの作成」とはしていない。
まずは、AC-Link I/Fのシリパラ変換部を作る必要がある。
Wikipediaによると、AC'97はIntelが提唱したサウンドインタフェースの標準規格で機能的には論理コントローラとアナログコーデックがありこれらがAC-Linkという5線式の双方向シリアルインターフェースバスで接続される。 LM4550は機能的にはアナログコーデックであり、今回これを制御する論理コントローラを作ってみようという訳だ。
LM4550のブロック図をデータシートから以下に引用する。

出力はLINE_OUT~MONO_OUTの3系統、入力はMIC~PHONEの7系統があるが、Atlysボードで使用できるのは出力はLINE_OUTとHP_OUT、入力はLINE_INとMIC1のみとなっている。

AC_LinkはBIT_CLK、SYNC、SDATA_OUT、SDATA_IN、RESET#からなるシリアルインターフェースで、SDATA_xxxがデータ信号であり、IN/OUTは論理コントローラ側からみた方向付けになっている。つまり、SDATA_OUTは論理コントローラ→コーデック、SDATA_INはコーデック→論理コントローラ。BIT_CLKは文字通りのビットクロックでSDATA_xxxはこのクロックに同期して転送される。このクロック信号はコーデックが駆動する。 SDATA_xxxで送受されるデータは以下のようなフレーム構造で全体のビット長は256ビットである。通常はフレーム周期は出力側のサンプリングレートに一致するので、BIT_CLKはサンプリングレートの256倍の周波数になる。
SDATA_OUTラインのデータフレーム構造は以下のようになっている。
1フレームは13個のSLOTで構成され、SLOT0は16ビット長のTAG情報、SLOT1~12は20ビット長で図に示す情報となっている。オーディオ情報とコーデック制御情報が多重化されていて、フレームサイズは固定長であるが、TAG SLOTのビットで有効・無効を表示できるようになっている。

SDATA_INラインのデータフレームは以下のようになっている。

今回は、以前作成したDDS IPからコーデックに出力したりDRAM上に何か音楽データを置いてコーデックに出力(再生)させたり、LINE_INにアナログ信号を入れてキャプチャしてみたりしてみたいと考えている。
AC'97の論理コントローラIPについて確固としたイメージを持っている訳でも無く、どちらかというとDAC/ADCとして使う感じなので、このプロジェクトのタイトルは「AC'97 IPの作成」とはしていない。
まずは、AC-Link I/Fのシリパラ変換部を作る必要がある。
登録:
投稿 (Atom)
ERROR: Failed to spawn fakeroot worker to run ...
なにかと忙しくてなかなか趣味の時間を確保できない。 ...orz 家の開発機のOSはLinux Mintなのだが、最近バージョンを22に更新したところ、myCNC用のpetalinuxをビルドできなくなってしまった。ビルドの途中で ERROR: Failed to spawn ...
-
FT232RというUSB-UART変換ICがある。このICにはBit Bang Modeという機能があって、UART用の端子がGPIO的制御が可能になる。 FT232Rを搭載したUSB-UART変換基板は秋月電子やマルツパーツ等色んなところで売られていて私もSparkfunのF...
-
これまではTCM8230MDの出力形式はRGB565にしていたが、画像もちゃんと表示できるようになってきたのでYUV422形式も扱えるようにして両者の画像の違いを見てみた。 まずTCM8230MDの出力をcolor bar出力にして、取り込んだ値に変換式を適用してどんな感じの...