#include "ADC.h"
#include "iostm8l151f2.h"
#include "stdbool.h"
#include "stdint.h"
uint16_t Vbat1=0;
uint16_t Vbat0=0;
uint16_t Vusbin=0;
uint16_t Vbutton0=0;
uint16_t Vbat=0;
static uint16_t temp=0;
void delay_500ms(void) //粗略延時程序
{
uint16_t i,j;
for(i=0;i<1000;i++)//2*1000個指令周期
for(j=0;j<500;j++);//2*500個指令周期
//1000*2*500+2*500=1.001M,延遲1/16s=62.5ms
//16M 一個指令周期為1/16us
}
void ADC1_Init()
{
CLK_PCKENR2_PCKEN20=1; //開啟ADC1外設時鐘
ADC1_CR1_ADON=1; //wakes up the ADC from Power down mode
ADC1_CR1_CONT=0; //單次轉換模式
ADC1_CR2_PRESC=1;//Select a sample time of 1μs // 0: f(ADC_CLK) = CK
// 1: f(ADC_CLK) = CK/2 //系統時鐘此時為默認的16M/8=2M,這里分頻后,fadc=2M/2=1M
ADC1_SQR1_DMAOFF=1; //關閉DMA通道
//ADC1_CR3_SMTP2=0x06; //設置內部參考電壓通道的采樣時間
ADC1_CR2_SMTP1=0x03;//外部0-23通道的采樣時間為24 ADC clock cycles,也就是24*1us=24us
// ADC1_CR1_EOCIE=1; //中斷
}
//#pragma vector=COMP_EF2_vector
//__interrupt void ADC1_ISR(void
//測量VDD
uint16_t get_VDD()
{
Vbat=0;
ADC1_SQR1_CHSEL_S28=1; //選擇ADC通道28,內部參考電壓通道
ADC1_TRIGR1_VREFINTON=1;//打開內部參考電壓源1.225v
for(char j=0;j<10;j++)
{
ADC1_CR1_START=1 ;//開始轉換
while(!(ADC1_SR_EOC==1));//等待轉換結束,清除標志位
temp = ADC1_DRH;
temp = (temp<<8)+ADC1_DRL;
temp=(uint32_t)2400*4096/temp; //由于VREF與VDD接在同一引腳上,內部參考電壓輸出通道實際電壓不知,
//因此無法采用內部參考電壓測量VDD,用電壓表多點測量的方法測得實際VDD=1.790V
Vbat+=temp;
}
Vbat = Vbat/10;
asm("nop");
ADC1_SQR1_CHSEL_S28=0; //關閉通道
return Vbat;
}
uint16_t get_Vbat1()
{
Vbat1=0;
static uint16_t temp1=0;
ADC1_SQR3_CHSEL_S11=1; //選擇ADC通道11
ADC1_TRIGR3_TRIG11=1; //關閉通道11的施密特觸發器
for(char j=0;j<10;j++)
{
ADC1_CR1_START=1 ;//開始轉換
while(!(ADC1_SR_EOC==1));
temp1 = ADC1_DRH;
temp1 = (temp1<<8)+ADC1_DRL;
temp1=(uint32_t)1800*temp1/4096;
Vbat1+=temp1;
}
Vbat1 = Vbat1/10;
Vbat1=3*Vbat1;//實際電壓值為3倍的AD電壓值
ADC1_SQR3_CHSEL_S11=0;
asm("nop");
return Vbat1;
}
uint16_t get_Vbat0()
{
Vbat0=0;
static uint16_t temp0=0;
ADC1_SQR3_CHSEL_S12=1; //打開ADC通道12
ADC1_TRIGR3_TRIG12=1; //關閉通道12的施密特觸發器
for(char k=0;k<10;k++)
{
ADC1_CR1_START=1 ;//開始轉換
while(!(ADC1_SR_EOC==1));
temp0 = ADC1_DRH;
temp0 = (temp0<<8)+ADC1_DRL;
temp0=(uint32_t)1800*temp0/4096;
Vbat0+=temp0;
}
Vbat0 = Vbat0/10;
Vbat0=3*Vbat0;
asm("nop");
ADC1_SQR3_CHSEL_S12=0;
return Vbat0;
}
uint16_t get_Vusbin()
{
Vusbin=0;
static uint16_t temp2=0;
ADC1_SQR4_CHSEL_S4=1; //打開ADC通道4
ADC1_TRIGR4_TRIG4=1; //關閉通道4的施密特觸發器
for(char k=0;k<10;k++)
{
ADC1_CR1_START=1 ;//開始轉換
while(!(ADC1_SR_EOC==1));//等待轉換完成
temp2 = ADC1_DRH; //先存MSB
temp2 = (temp2<<8)+ADC1_DRL; //(MSB)*256+LSB
temp2=(uint32_t)1800*temp2/4096; // VDD/4096=Vx/AD值
Vusbin+=temp2;
}
Vusbin = Vusbin/10;
Vusbin =3*Vusbin;//USB輸入電壓
asm("nop");
ADC1_SQR4_CHSEL_S4=0;
return Vusbin;
}
uint16_t get_Vbutton0()
{
Vbutton0=0;
static uint16_t temp3=0;
ADC1_SQR3_CHSEL_S13=1; //打開ADC通道13
ADC1_TRIGR3_TRIG13=1; //關閉通道13的施密特觸發器
for(char k=0;k<10;k++)
{
ADC1_CR1_START=1 ;//開始轉換
while(!(ADC1_SR_EOC==1));
temp3= ADC1_DRH;
temp3 = (temp3<<8)+ADC1_DRL;
temp3=(uint32_t)1800*temp3/4096;
Vbutton0+=temp3;
}
Vbutton0 =Vbutton0/10; //button0對應的電壓值
asm("nop");
ADC1_SQR3_CHSEL_S13=0; //關閉通道
return Vbutton0;
}
/*
void main()
{
// CLK_Init();
ADC1_Init();
delay_500ms();
delay_500ms();
delay_500ms();//延時等待ADC穩定之后再進行轉換,能夠準確讀取對應通道的電壓
get_Vusbin();
delay_500ms();
delay_500ms();
get_Vbat0();
delay_500ms();
get_Vbutton0();
delay_500ms();
get_Vbat1();
while(1)
{
}
}
*/
|