ASMを採用したAtmelAVRでDDSプロジェクトを完了したところ、8ビットルックアップテーブルと8ビットDACが低周波数で量子化歪みを大きくしすぎるという結論に達しました。より良い表現がないため、オシロスコープにラダー効果のある正弦波が発生しています。
明らかに、大きなLPFで波形を平滑化すると、より高い周波数での振幅に問題が生じます。
理論的には、8ビットから12ビットDACにアップグレードし、最下位4ビットで補間を使用すると、フィルターのカットオフポイントを十分に上げて、より高い周波数での波形振幅の問題を軽減できます。私の問題は、これを行う方法がわからないこと、またはジッパー効果を削除する簡単な方法があるかどうかです。おそらく12ビットのルックアップテーブルですか?
これまで、無限ループを作成しました。ループがサイクルを完了するたびに、ルックアップテーブルに関連するポインターの位置に基づいて値がDACに送信されます。ここで私は混乱します。私はこれに関するたくさんの情報を読みましたが、まだ実用的な例を見つけていません。無限ループがある場合、テーブルルックアップ値の間に補間値を詰め込むにはどうすればよいですか?私が考えることができる最高のものについては(a + b)/ 2; おそらくこれを実装して、512ポイントのルックアップテーブルに相当する追加のビットを取得できますが、より簡単な方法またはより良い結果をもたらす可能性のあるものがあると思います。Cや使い方はわかりませんが、賢明な方はやってみます。
現在、私の時計は1MHZで、必要に応じて16MHZに行くことができます。
これが私のコードのサンプルです:
; 正弦波出力をデフォルトとして設定
ldi ZH, High(sine*2); setup Z pointer hi
ldi ZL, Low(sine*2) ; setup Z pointer lo
; クリアアキュムレータ
clr r29 ; clear accumulator
; 加算器レジスタの設定
ldi r24,0x50 ; Fine adder value change register
ldi r25,0x08 ; Middle adder value change register
ldi r26,0x00 ; Coarse adder value change register
ループ1:
add r28,r24 ; 1 Adder values carry over to higher registers. Higher registers raise freq. in larger steps
adc r29,r25 ; 1
adc r30,r26 ; 1 r30 is database address pointer for Z register
lpm r0, Z ; 3 (Load Program Memory) Reads byte from database into the destination register based on Z pointer
out PORTD,r0
rjmp LOOP1 ; 2 => 9 cycles