公開日:2021/04/03
title.png

14th Season


#14-9 手作りtiny AD変換器の評価

 前回完成させたATtiny2313外付けtiny AD変換器の変換精度を評価してみようと思います。
 以下、AD変換器を搭載していないATtiny2313の外付けに、コンデンサと抵抗を接続してAD変換器を構成したブレッドボードの実装例です。

a148_tinyadc.jpg

 回路図はこちら

変換精度を評価してみよう

 さて、前回作成した4ビットAD変換器が「ちゃんとAD変換器になっているの?」まで含めて、いきなり変換精度の評価を実施してしまいましょう。乱暴ですが、それが手っ取り早いです。

 変換精度の評価には、ATtiny2313+tiny_adc_4b.inoの他に、ホストとしてArduino UNO等、別な機体と、12ビットDA変換器モジュール(MCP4725、下図)が必要となります。

ar79_dac12.jpg

 以下接続表に従って、接続してください。

ATtiny2313(ターゲット) 接続 UNO(ホスト) 接続 MCP4725
20 VCC 5V VCC
10 GND GND GND
19 D16(SCL) A5(SCL) SCL
17 D14(SDA) A4(SDA) SDA
12 D9(AIN0) OUT

※ATtiny2313には、こちらの回路図を実装しておく必要があります。回路については前回解説済みです。

 ホスト(UNO)側プログラムは、「#8-2 逐次比較型AD変換器を作る」で作成した物を拡張してあります。以下のプログラムを書き込んでおいてください。

  ホスト側プログラム:test_adc_4b.ino

 I2C接続したATtiny2313のAD変換器を評価できるように、シリアルモニタから受け付ける以下コマンドを追加してあります。

 以下、評価中の様子です。

a149_expr.jpg


  実験サンプル:【 】内はUNOシリアルモニタからの送信データ
  【evat】
  0,0
  1,0
  2,0
    :
    : (中略)
    :
  4093,15
  4094,15
  4095,15
  OK: evat

 Excelでグラフ化すると、以下の様になりました。

a149_eval.png

 横軸に測定対象のアナログ電圧[V]、縦軸にAD変換後のデジタル値[LSB]を取りました。赤い破線は測定値の一次回帰直線です。一次回帰直線の数式より、オフセット電圧Vofs≒0.294V、フルスケール電圧Vful≒4.934Vだと判りました。

 以下図は各ポイントの測定値から計算した絶対精度(AE)のプロットです。

a149_accur.png

 横軸に測定対象のアナログ電圧[V]、縦軸に測定したデジタル値と理想値との絶対精度(誤差)[LSB]を取っています。ワースト値は−1.520LSBでした。先行評価で観られたAEの低下ポイントは全く見られず、綺麗な特性が得られました。対策が功を奏した様です。

 非直線性誤差、DNLとINLに関しては以下表の通りです。

D
[LSB]
A[D]
[V]
DNL
[LSB]
INL
[LSB]
0 0.000   0.000
1 0.446 0.426 0.426
2 0.778 0.063 0.488
3 1.083 −0.023 0.465
4 1.406 0.035 0.500
5 1.720 0.004 0.504
6 2.023 −0.031 0.473
7 2.336 0.004 0.477
8 2.640 −0.027 0.449
9 2.950 −0.008 0.441
10 3.251 −0.039 0.402
11 3.550 −0.043 0.359
12 3.842 −0.066 0.293
13 4.147 −0.023 0.270
14 4.435 −0.078 0.191
15 4.735 −0.039 0.152

 最後に変換精度の各指標をまとめておきます。

※指標の意味や計算方法に関しては「#8-2 逐次比較型AD変換器を作る」をご覧ください。

  雑感:

 まとめてみると、外付けにコンデンサと抵抗を追加しただけのAD変換器としては、実用レベルな変換精度が得られたと思います。

蛇足?8ビットAD変換器

 adc4_read()関数の先頭付近に定数N=4が宣言されていて、これによってNビットAD変換が実行されています。DA変換を担うPWMタイマの設定では、デューティを0〜255の8ビット値で指定しているので、原理上、今回のPWM型DA変換器は8ビットの解像度を持っています。

  const int N=4;  // ADC bits

 従って、これ(↑)をN=8に変更してみると、adc4_read()関数は8ビットAD変換を実行する様になります。
 8ビットAD変換器の変換精度を評価してみた結果は以下図です。

a149_eval8bit.png

 絶対精度AEのワースト値−10.6LSBと、まあ、誤差が大きすぎですね。log2(abs(AE))≒3.4ビット相当ですので、折角の8ビット解像度の内、3.4ビット分は誤差だということになります。つまり、実質8−3.4=4.6ビットAD変換器相当の情報量しか無いと言っても良いでしょう。
 今回の回路構成では、4〜5ビットAD変換器を形成するのが精いっぱいだ、ということが判りました(1^−^;)。実はそれを知りたかったわけでは無くて、この評価結果を使って、PWM型DA変換器の校正を実行しようと考えたのです。

 PWM型DA変換器の出力信号はギザギザ波形なので、PWM周期に同期していつも同じタイミングで参照することで精度を確保しています。従って、これを校正するためには、PWM周期に同期してDA変換器出力を測定する必要があるのですが、その評価を実現する良い方法が思い浮かびませんでした。
 上のグラフをよく観察してみると、測定値(青色プロット)と一次回帰直線(赤破線)に関して、(1)傾きが異なっている、(2)0.5V以下の範囲で大きく乖離している、ことが解ります。これは、基準電圧として使ったPWM型DA変換器の特性を反映したもの、と見ることが出来ます。

 要するに、上の8ビットAD変換結果が、理想的なAD変換結果になるためには、DA変換器の出力がどうであったら良かったのか?と、遡って校正するのです。

 手元のATtiny2313+コンデンサ+抵抗で校正したPWM型DA変換器の校正テーブルctbl[16]は、以下の様になりました。

    // This is a calibration table for Digital to Duty conversion.
    static const uint8 PROGMEM ctbl[16]=
    {
  #ifdef __ARDUINO_1YEN__
      0,11,24,39,55,71,87,103,120,136,152,169,186,202,220,236  // calibrated
  #else // __ARDUINO_1YEN__
      0,16,32,48,64,80,96,112,128,144,160,176,192,208,224,240  // linear
  #warning "Digital To Duty calibration table was not applied."
  #endif // __ARDUINO_1YEN__
    };

    // dac output
    noInterrupts ();
    OCR1A=pgm_read_byte (ctbl + anlg);
    interrupts ();


 手元の環境で校正した結果であって、一般に適用できるかどうかが不明(※)なので、#ifdefで通常は選択されない様に除外してあります。良く確認してから使用して見てください。あるいはご自身の手で校正する等。

※少なくとも、この校正結果には手持ちMCP4725の特性が含まれています。少し特性の異なるMCP4725を使うだけで、異なる校正結果になる可能性もあります。「一般に適用できない」と考えるのが自然でしょう。

 手持ちの環境で上の校正テーブルを適用した結果、変換精度は以下の様になりました。

a149_evalcali.png

 めっちゃ、綺麗🌈です。直線性も向上しましたし、何より、絶対精度AEのワースト値で−1.016LSBは立派です。だって、アナログ値を離散的なデジタル値に変換した段階で、必ず量子化誤差−1.0LSBが発生するので、その理論的誤差をはみ出した部分はたったの−0.016LSBなのですから。

※同じことを8ビットAD変換でも実施すると、変換精度は格段に向上するとお考えかも知れませんが、それは否定的です。8ビットのデジタル値DGTを8ビットのデューティ値DTYに対応させることで、複数のDGTに対して同じ校正値となってしまうケースが出現します。これは、ミッシングコードなど好まれない特性を示す原因となります。


 校正後の各指標を以下にまとめます。

 「#8-2 逐次比較型AD変換器を作る」で作った4ビットAD変換器では、基準電圧を作り出すDA変換器は抵抗ストリング型なので、ハードウェアで作りつけです。よって、ソフトウェアの様に簡単に校正する訳には行かないのですが、今回はPWMでアナログ波形を作り出すPWM型DA変換器を使ったので、ソフトウェアで簡単に校正することが出来ました。
 「#8-2 逐次比較型AD変換器を作る」の絶対精度AE=−1.238LSBに比べても、校正後のAE=−1.160LSBと、極小量の外付け回路で作ったにもかかわらず、高精度なAD変換器になっていることを確認しました。

まとめ

 最後に、今まで手作りしてきた4ビットAD変換器の特性を以下表で比較します。

指標 ΔΣ型 逐次比較型
抵抗ストリング型 PWM型 PWM型校正後
オフセット
エラー(OE)
0.080LSB 0.525LSB 0.942LSB 0.442LSB
フルスケール
エラー(FE)
1.074LSB 0.683LSB 0.789LSB 0.457LSB
微分非直線
性誤差(DNL)
−0.238 〜
0.465LSB
−0.113 〜
0.141LSB
−0.078 〜
 0.426LSB
−0.082 〜
 0.063LSB
積分非直線
性誤差(INL)
0.672LSB 0.242LSB 0.504LSB 0.102LSB
絶対精度(AE) −1.668LSB −1.238LSB −1.520LSB −1.016LSB
変換時間 約3,200μs 約400μs 約2,048μs 約2,048μs

※一般的に「良い特性」とされるものを水色、「悪い特性」とされるものをピンク色に着色した。誤差に関しては良=小さい/悪=大きい、変換速度に関しては良=速い/悪=遅い。


 「PWMで出力するDA変換器では、デジタルノイズなどの影響で精度が出ないのではないか?」と、心配していたのですが、それ以上に、デューティ(ソフトウェア)によって出力電圧を校正できるPWM型DA変換器を使ったおかげで、高精度なAD変換器を作ることが出来てしまいました。外部回路もコンデンサと抵抗だけなので、かなり実用的なAD変換器かと思われます。


btn_arduino.png

btn_prev.png btn_next.png

home