2011年2月11日金曜日

A/D変換のミス

約一週間ぶりになってしまいました.お久しぶりです.パパです.
前回UPしたpfunction.c,にミスが入ってました.と,いうのはA/D変換時の「A/D変換クロック選択」を指定していなかったことです.

これは何者かといいますと,まず,A/D変換の説明からはじめなければなりません.

A/D 変換とは,端的に言えば,アナログデータをデジタルデータへ変換するものです.というのも,基本的にマイコンは,デジタルデータしか扱うことができません.具体的には,"0"と"1"の二種類ですが,時にはビミョーな値を読み取りたいといったこともでてくるでしょう.例えば,センサーがそれにあたります.温度センサーとかでも,温度が高い・低いの二種類では困りますよね.

このときに微妙な値を安易に"0","1" に分けてしまうのではなく,"0:5" や"0:95" などの値に変換
してプログラムに持ち込むのがA/D 変換です.

具体的な使い方は,他にまわすとして,このとき考え方として,A/D変換は別のハードでかけていると考えると分かりやすいと思います.ですからA/D変換をかけている最中に別の処理をすることもできますし,ただ待っている,というのでもいいと思います.

それはいいとして,A/D変換を別ハードでかけているということは,そのハードにも周波数を送ってやらないといけません.今回のミスはその周波数を設定していなかった,ということです.AVRwiki様(top)によると,50~200kHzに設定してやらないとダメみたいです.で,データシートを見ると,ADPSの2~0で周波数を設定するみたいですね.


データシートより
で,部室で使っているAVRは10MHzで動かしているので,64分周を設定しました.いままでビミョーに安定しなかったのが,これでちゃんと安定したので,ホントによかったです.

書きなおしたpfunction.cもupしておきますね.ADConvertとADstartにはaにチャンネル選択を,bにクロック選択を0~7までで入れて使ってくださいね.

/**************************************
 pfunction.c
 作成者:パパ
 ver,2.5
**************************************/
#define sbi(addr,bit)        addr|=(1<<bit)
#define cbi(addr,bit)        addr&=~(1<<bit)
#define ibi(addr,bit)        addr^=(1<<bit)
uint8_t ADConvert(uint8_t a,uint8_t b)
{
        ADMUX = 0x60|a;
        ADCSRA = 0xC0|b;
        loop_until_bit_is_clear(ADCSRA,ADSC);
        return ADCH;
}
void ADCstart(uint8_t a,uint8_t b)
{
        ADMUX = 0x60|a;
        ADCSRA = 0xC0|b;
}
uint8_t ADCfinish(void)
{
        loop_until_bit_is_clear(ADCSRA,ADSC);
        return ADCH;
}
uint16_t AbsolteValue(int a)
{
        if(a < 0)
        a = -a;
        return a;
}
ふぅ,長文書くと疲れるなぁ.

でわでわ

0 件のコメント:

コメントを投稿