今天要和大家介紹的是MSP430的ADC功能, 首先我們先來看一下ADC的運作流程圖:

ADC1.jpg

要先決定CPU的參考電壓值 (圖右上角), 才能讓ADC能夠比較目前的輸入的電壓值為何.  這邊可以選擇使用預設值 (VCC VSS)或是使用參考電壓值 (VeREF+ VeREF-), 但注意, 如果要使用參考電壓值, 在設定完之後要等待30us, 電壓才會穩定.

 

接下來, 要決定使用哪一個pin腳當作ADC的輸入, 然後會透過一個sample and hold的電路, 把input pin瞬間的電壓值給儲存下來. 然後選擇是要透過CPU (ADC10SC) 或著是TimerA (OUT1, OUT2 and OUT3) 來傳送Conversion的訊號, 當ADC收到Conversion的訊號後, 就會把儲存到的電壓值轉換成10 bits的數值, 並且把轉換出來的數值儲存在ADC10MEM裡面,最後產生一個interrupt (ADC10IFG) 來通知CPU.

 

有了一些基本的概念, 我們再來看一下這次的範例程式:

ADC10CTL0 = ADC10SHT_2 + ADC10ON + ADC10IE;

設定ADC10SHT讓sample and hold的電路能夠儲存電壓值16個CLKs 時間

設定ADC10ON打開ADC10

設定ADC10IE打開ADC10的interrupt

ADC2.jpg

 

ADC10CTL1 = INCH_1;

選擇使用A1 (P1.1) 當作ADC的input pin.

 

其他沒有寫出來的就是使用預設值0, 像是透過CPU來傳送conversion的訊號, 以及只做一次ADC轉換.

ADC3.jpg

 

 

ADC10AE0 |= 0x02;

把A1 (P1.1) 這支腳設為Analog的input

 

P1DIR |= 0x01;

把 P1.0這隻腳設為output, 我們希望可以透過LED燈來顯示我們的結果.

 

接著, 進入了一個無窮迴圈裡面, 設定ADC要準備開始做轉換了.

ADC10CTL0 |= ENC + ADC10SC;

 

 

__bis_SR_register(CPUOFF + GIE); // SLEEP

然後, 讓CPU進入休眠狀態, 並把interrupt打開. 之後CPU不會繼續往下一行執行, 而是等待interrupt的發生. 什麼時候會發生interrupt呢? 還記得前面有提過, 當ADC做完一次轉換後, 會把10個bits的值儲存在ADCMEM裡面, 並送出一個interrupt給CPU.

 

__bic_SR_register_on_exit(CPUOFF);

所以, 當ADC做完一次轉換後, 發生interrupt後, 進入了interrupt service routine (ISR), 此時便會把CPU喚醒. 然後CPU就會判斷這次ADC的值是否大於0.5VCC. 因為10個bit的ADC會有1024的值, 所以我們這邊和0x1FF (511)來比較, 就可以知道是大於還小於0.5VCC了.

 

燒錄完程式碼的讀者, 可以試著把A1 (P1.1)這隻pin腳和板子上的GND或是VCC短路, 試試看會發生什麼事情?

 

 

 

[備忘錄] 啟動ADC的三個步驟:

1. ADC10ON: 叫ADC開始啟動, 把電路打開 (ex: 總開關)

2. ENC: 允許被Trigger (ex: 門鈴)

3. ADC10SC: Trigger的訊號 (ex: 按門鈴的信號)

創作者介紹
創作者 學無止境 的頭像
kuojed

學無止境

kuojed 發表在 痞客邦 留言(1) 人氣( 3635 )