« 中華製CVCC電源に付属してきたDC出力コード | トップページ | 歯医者の残物:ICレコーダ、Walkman、BGM再生装置 いりませんか? »

2025年12月23日 (火)

ATtiny1614 DAC出力とADC入力を見る

ATtiny1614のDAC出力とADC入力を試してみます。

DACはアナログ値を8bitでDAC0:PA6に出力。
D12_20251223100201
ADCはあれこれアナログ値を10bitで入力できる
ようになってます。
D13_20251223100201
DACもADCも「0.55V~4.3V」の内蔵基準電圧が使えます。
D14_20251223100301
ただし、DACは電源(VDD)や外部基準電圧(VREFA)
入力は使えません。
電源や外部を使えるのはADCだけ。

DACとADCを同じ基準電圧に設定し、DACで
出力した電圧をADCで読ませれば同じ値(8bitと
10bitだから4倍して)が出てくるはずです。
  DACで「128」(基準電圧の1/2)を出力すれば
  その4倍の「512」がADCで読めるはず。
これを確かめてみました。

こんな回路。
D11_20251223100801
実験した電源電圧は5V。
PA6(DAC0出力)とPA4(AIN4入力)を接続。
この接続はDACブロック図にある出力バッファを
通ります。
もう一つの経路がADC入力マルチプレクサを切り替
えれば読める「DAC」。
DAC0の出力バッファを通らずにA-D変換できます。

その結果です。 左から
  基準電圧 0.55V~4.3V
  DAC出力データ(8bit) 0~255、16stepで
  AIN4入力A-D値(10bit)
    DACデータのと差
  DAC入力A-D値(10bit)  DAC0バッファを通っていない
    DACデータのと差

#Ref D-A AIN4 diff  DAC0 diff
0.55 0 3 3 3 3
0.55 16 52 -12 67 3
0.55 32 117 -11 131 3
0.55 48 181 -11 194 2
0.55 64 245 -11 258 2
0.55 80 309 -11 322 2
0.55 96 373 -11 386 2
0.55 112 437 -11 449 1
0.55 128 501 -11 514 2
0.55 144 565 -11 578 2
0.55 160 629 -11 642 2
0.55 176 693 -11 706 2
0.55 192 757 -11 769 1
0.55 208 821 -11 834 2
0.55 224 885 -11 898 2
0.55 240 949 -11 961 1
0.55 255 1009 -11 1021 1

1.1 0 1 1 2 2
1.1 16 58 -6 65 1
1.1 32 122 -6 129 1
1.1 48 186 -6 193 1
1.1 64 250 -6 256 0
1.1 80 314 -6 320 0
1.1 96 378 -6 384 0
1.1 112 441 -7 448 0
1.1 128 505 -7 512 0
1.1 144 569 -7 576 0
1.1 160 633 -7 640 0
1.1 176 697 -7 704 0
1.1 192 761 -7 768 0
1.1 208 825 -7 832 0
1.1 224 889 -7 896 0
1.1 240 953 -7 959 -1
1.1 255 1013 -7 1019 -1

1.5 0 0 0 1 1
1.5 16 59 -5 65 1
1.5 32 123 -5 128 0
1.5 48 187 -5 192 0
1.5 64 251 -5 256 0
1.5 80 315 -5 320 0
1.5 96 378 -6 383 -1
1.5 112 442 -6 447 -1
1.5 128 506 -6 511 -1
1.5 144 570 -6 575 -1
1.5 160 634 -6 639 -1
1.5 176 698 -6 703 -1
1.5 192 762 -6 767 -1
1.5 208 826 -6 831 -1
1.5 224 890 -6 895 -1
1.5 240 953 -7 958 -2
1.5 255 1013 -7 1018 -2

2.5 0 0 0 0 0
2.5 16 61 -3 64 0
2.5 32 125 -3 128 0
2.5 48 188 -4 191 -1
2.5 64 251 -5 255 -1
2.5 80 315 -5 318 -2
2.5 96 379 -5 382 -2
2.5 112 442 -6 445 -3
2.5 128 506 -6 509 -3
2.5 144 570 -6 573 -3
2.5 160 634 -6 637 -3
2.5 176 698 -6 701 -3
2.5 192 761 -7 764 -4
2.5 208 825 -7 828 -4
2.5 224 889 -7 892 -4
2.5 240 953 -7 956 -4
2.5 255 1012 -8 1016 -4

4.3 0 0 0 0 0
4.3 16 62 -2 64 0
4.3 32 125 -3 127 -1
4.3 48 189 -3 191 -1
4.3 64 253 -3 254 -2
4.3 80 316 -4 318 -2
4.3 96 380 -4 382 -2
4.3 112 444 -4 445 -3
4.3 128 508 -4 510 -2
4.3 144 572 -4 574 -2
4.3 160 636 -4 637 -3
4.3 176 700 -4 701 -3
4.3 192 763 -5 765 -3
4.3 208 827 -5 829 -3
4.3 224 891 -5 893 -3
4.3 240 954 -6 956 -4
4.3 255 1014 -6 1016 -4

これを見ると、
 DAC0出力バッファを通った電圧は
 一定のオフセット(マイナス目)が出ている。

 DACの直接入力は、まぁこんなもん。
  Vref=1.1Vなんかエエ感じ。

てなところでしょうか。

「DAC0出力を使えばVrefが外に出せる」と
記したことがありましたが、「要調整」という
注意書きが必要なようです。

テストに使ったのはこんなスケッチ。
・analogReadは使っていない。
・アナログデータの累積加算機能(32回)を使って
 平均値を算出。
・フリーランさせて変換。
・Serial.printf()が使えるぞ!

/*****************************************/
/* ATtiny1614 D-A出力とA-D入力のテスト */
/*****************************************/
// "AD_DA_test01.ino"
// Vref値を変えながらD-A(0~255)を出力してA-D入力
// DAC0出力(DAOUT) PA6 8bit
// ADC0入力(AIN4) PA4 10bit
// ADIN MPXを切り替えてDAC0直入力もテスト
// クロックは10MHz
// delay(),Serial.printを使っている
#define DA_STEP 16 // D-A増減値 0~255で設定
// 配列のデータ数を返すマクロ
#define DIMSIZ(a) (sizeof(a)/sizeof(*a))
/***** VREF テーブル *****/
struct st_vref{
const char *s; // 区分文字列
const byte v; // VREF選択コード
};
const st_vref vref_tbl[]={
{ "0.55" , 0b00000000, }, // 0
{ " 1.1" , 0b00010001, }, // 1
{ " 1.5" , 0b01000100, }, // 2
{ " 2.5" , 0b00100010, }, // 3
{ " 4.3" , 0b00110011, }, // 4
// ||| +++--- DAC0REF
// +++------- ADC0REF
};

/***** SETUP *****/
void setup()
{
Serial.begin(9600);
DAC0.CTRLA = 0b01000001; // D-A出力有効
// || +---- ENABLE DAC許可
// |+---------- OUTEN 出力する(PA6)
// +----------- RUNSTBY
// A/D変換 ADC0:AIN4:PA4 2pin
// クロックは50kHz~1.5MHzに
// 32回累積 フリーラン変換で
ADC0.CTRLA = 0b00000011;
// | ||+--- ENABLE 許可
// | |+---- FREERUN 自由走行で
// | +----- RESEL 10bit
// +---------- RUNSTDBY
ADC0.CTRLB = 0b00000101; // サンプル回数
// +++--- 32回 15bit (max 32736)
ADC0.CTRLC = 0b01000101;
// ||| +++--- PRESC 10MHz/64=156kHz
// |++------- REFSEL 内部Vref (VREF.CTRLA)
// +--------- SMAPCAP Hiレベル
ADC0.MUXPOS = 0b00000100; // MPX
// +++++--- AIN4:PA4 2pin
ADC0.COMMAND = 1; // STCONV 変換開始
// デジタル入力禁止
PORTA.PIN4CTRL = 0x04; // PA4:AIN4 in デジタル入力禁止
PORTA.PIN6CTRL = 0x04; // PA6:DAC0 out
}

/***** LOOP *****/
void loop()
{
byte exc = 0; // 実行区分
byte vref_d; // Vref選択
int da_d; // D-A出力データ 0~255
int ad_ain4; // AIN4 A-D入力データ 0~1023
int ad_dac0; // DAC0直接のA-D入力データ 0~1023
Serial.println("#Test D-A,A-D");
delay(100);
while(1){ // ここでloop
switch(exc){
case 0: // Vref値 最初から
vref_d = 0; // 最初は0.55V
Serial.println("#Ref D-A AIN4 diff DAC0 diff");
exc++;
break;
case 1: // Vref値設定してD-A出力値0Vから
VREF.CTRLA = vref_tbl[vref_d].v; // ADC0,DAC0 VREF電圧設定
da_d = 0; // DAC0 = 0V
DAC0.DATA = da_d; // D-A出力して
delay(100); // ちょっと時間待ち
exc++;
break;
case 2: // D-A 0~255可変
DAC0.DATA = da_d; // 0~255のD-A出力
ADC0.MUXPOS = 0x04; // MPX AIN4入力で
delay(100); // ちょっと時間待ち
exc++;
break;
case 3: // AIN4からのA-D入力
ad_ain4 = ADC0.RES; // 変換結果 (1023*32):0~32736
ad_ain4 /= 32; // 1/32して0~1023に
ADC0.MUXPOS = 0x1C; // MPX DAC0入力に切り替え
delay(100); // ちょっと時間待ち
exc++;
break;
case 4: // DAC0直接入力
ad_dac0 = ADC0.RES; // 変換結果 (1023*32):0~32736
ad_dac0 /= 32; // DAC0データも1/32
Serial.printf("%s %3d %4d%5d %4d%5d\r\n", // シリアル出力
vref_tbl[vref_d].s, // Vref値
da_d, // D-A値 0~255
ad_ain4, ad_ain4 - (4 * da_d), // AIN4 差分
ad_dac0, ad_dac0 - (4 * da_d)); // DAC0 差分
if(da_d == 255){ // D-A出力255でおわり
Serial.println(); // 2つ改行
Serial.println();
vref_d++; // 次のVref
if(vref_d >= DIMSIZ(vref_tbl)){ // 4.3Vでおわり
exc = 0; // 最初から
}
else{ // 0.5V~4.3V
exc = 1; // Vref設定へ
}
}
else{ // 次D-A値
da_d += DA_STEP; // +16
if(da_d > 255) da_d = 255; // maxが255
exc = 2; // D-A出力から
}
break;
}
}
}

電源電圧5Vで試しましたが、電源電圧を変えると
状態が変わります。
電源3.3Vなら基準電圧4.3Vは無意味ですし。
  というかDACもADCも基準が電源電圧に
  なるかも。

Serial.printfはこの設定でしょ
D16

Da15

※電源電圧3.3Vでの結果

#Ref D-A AIN4 diff  DAC0 diff
0.55 0 0 0 0 0
0.55 16 50 -14 64 0
0.55 32 114 -14 128 0
0.55 48 178 -14 192 0
0.55 64 242 -14 256 0
0.55 80 306 -14 319 -1
0.55 96 370 -14 382 -2
0.55 112 434 -14 447 -1
0.55 128 498 -14 511 -1
0.55 144 562 -14 575 -1
0.55 160 626 -14 640 0
0.55 176 690 -14 703 -1
0.55 192 753 -15 767 -1
0.55 208 818 -14 831 -1
0.55 224 882 -14 895 -1
0.55 240 946 -14 959 -1
0.55 255 1006 -14 1018 -2

1.1 0 0 0 0 0
1.1 16 57 -7 64 0
1.1 32 121 -7 128 0
1.1 48 185 -7 191 -1
1.1 64 248 -8 255 -1
1.1 80 312 -8 319 -1
1.1 96 375 -9 382 -2
1.1 112 440 -8 446 -2
1.1 128 504 -8 510 -2
1.1 144 568 -8 575 -1
1.1 160 632 -8 639 -1
1.1 176 696 -8 702 -2
1.1 192 759 -9 766 -2
1.1 208 824 -8 830 -2
1.1 224 888 -8 894 -2
1.1 240 951 -9 958 -2
1.1 255 1011 -9 1018 -2

1.5 0 0 0 0 0
1.5 16 58 -6 64 0
1.5 32 122 -6 127 -1
1.5 48 186 -6 191 -1
1.5 64 250 -6 255 -1
1.5 80 313 -7 318 -2
1.5 96 377 -7 382 -2
1.5 112 441 -7 446 -2
1.5 128 505 -7 510 -2
1.5 144 569 -7 574 -2
1.5 160 633 -7 638 -2
1.5 176 697 -7 702 -2
1.5 192 761 -7 766 -2
1.5 208 825 -7 830 -2
1.5 224 889 -7 894 -2
1.5 240 953 -7 957 -3
1.5 255 1012 -8 1017 -3

2.5 0 0 0 0 0
2.5 16 60 -4 63 -1
2.5 32 124 -4 127 -1
2.5 48 187 -5 190 -2
2.5 64 251 -5 254 -2
2.5 80 315 -5 318 -2
2.5 96 378 -6 381 -3
2.5 112 442 -6 445 -3
2.5 128 506 -6 509 -3
2.5 144 569 -7 573 -3
2.5 160 633 -7 636 -4
2.5 176 697 -7 700 -4
2.5 192 761 -7 764 -4
2.5 208 824 -8 828 -4
2.5 224 888 -8 892 -4
2.5 240 952 -8 955 -5
2.5 255 1011 -9 1015 -5

4.3 0 0 0 0 0
4.3 16 61 -3 64 0
4.3 32 125 -3 128 0
4.3 48 189 -3 191 -1
4.3 64 253 -3 255 -1
4.3 80 317 -3 319 -1
4.3 96 380 -4 383 -1
4.3 112 444 -4 447 -1
4.3 128 509 -3 511 -1
4.3 144 573 -3 576 0
4.3 160 637 -3 640 0
4.3 176 701 -3 704 0
4.3 192 765 -3 768 0
4.3 208 829 -3 832 0
4.3 224 893 -3 896 0
4.3 240 956 -4 960 0
4.3 255 1010 -10 1020 0

Vref 4.3Vは電源電圧が低いので出力できない。
DAC、ADCとも電源電圧が目一杯の基準電圧
として使われているのではないかと推測。

|

« 中華製CVCC電源に付属してきたDC出力コード | トップページ | 歯医者の残物:ICレコーダ、Walkman、BGM再生装置 いりませんか? »

ATtiny」カテゴリの記事

コメント

コメントを書く



(ウェブ上には掲載しません)




« 中華製CVCC電源に付属してきたDC出力コード | トップページ | 歯医者の残物:ICレコーダ、Walkman、BGM再生装置 いりませんか? »