一个函数 mcu_ad_cov_sig() 用于AD转换,,,,
在主函数中调用 AD转换函数
void main(void)
{
。。。。。。。
。。。。。。。
for(i=0;i<count;i++)
{
ad[i] = mcu_ad_cov_sig(ch_num);
sum = sum + ad[i];
for(j=0;j<25000;j++)
{
asm("nop");
asm("nop");
}
}
。。。。。。。。。。
。。。。。。。。。。
}
问题也就在调用AD的时侯,如果没有空指令延时或者延时便小,FOR循环中,第一次的AD调用转换值是正确的,但后面的几次,全部便小,便小的值接近一致;
如果按照这样的转换速度,效率也太低了,不知是不是我设置的问题,我的时钟速度是2MHZ
int mcu_ad_cov_sig(unsigned char ch_num)
{
unsigned int i;
unsigned int ad_result;
CLK_PCKENR2 = CLK_PCKENR2 | 0X01; //使能外设ADC的时钟,之后对ADC的寄存器操作有效
ADC1_CR1 = 0X01; //开启AD模块电源,使用Sing mode;
ADC1_CR2 = 0X02; //使用MCU系统时钟频率作ADC的时钟;
//AD转换软启动;
//AD采样时间24个系统时钟;
ADC1_SQR1_DMAOFF = 1; //禁止DMA传输;
switch (ch_num)
{
case 0:{ADC1_SQR4 = 0X02; break;} //测量充放电流值,in1
case 1:{ADC1_SQR4 = 0X10; break;} //测量BAT1,in4
case 2:{ADC1_SQR4 = 0X20; break;} //测量BAT2,in5
case 3:{ADC1_SQR4 = 0X40; break;} //测量BAT3,in6
case 4:{ADC1_SQR3 = 0X04; break;} //测量BAT4,in10
case 5:{ADC1_SQR3 = 0X08; break;} //测量BAT5,in11
case 6:{ADC1_SQR3 = 0X10; break;} //测量BAT6,in12
case 7:{ADC1_SQR3 = 0X20; break;} //测量BAT7,in13
case 8:{ADC1_SQR3 = 0X40; break;} //测量BAT8,in14
case 9:{ADC1_SQR3 = 0X80; break;} //测量BAT9,in15
case 10:{ADC1_SQR2 = 0X01; break;} //测量BAT10,in16
case 11:{ADC1_SQR2 = 0X02; break;} //测量BAT11,in17
case 12:{ADC1_SQR2 = 0X04; break;} //测量BAT12,in18
case 13:{ADC1_SQR2 = 0X08; break;} //测量BAT13,in19
case 14:{ADC1_SQR2 = 0X10; break;} //测量BAT14,in20
case 15:{ADC1_SQR2 = 0X20; break;} //测量BAT15,in21
case 16:{ADC1_SQR2 = 0X40; break;} //测量BAT16,in22
}
ADC1_CR1_START = 1; //启动AD转换
for(i=0;i<15;i++) //加入固定延时,等待AD转换完成
{asm("nop");}
ad_result = ADC1_DRH << 8 ;
ad_result = ad_result + ADC1_DRL; //读取AD转换值
ADC1_SQR4 = 0x00;
ADC1_SQR3 = 0x00;
ADC1_SQR2 = 0x00; //AD转换完成后,清除AD选中的通道
ADC1_CR1 = 0x00; //关闭AD模块电源
CLK_PCKENR2 = CLK_PCKENR2 & 0xFE; //关闭AD时钟
return ad_result; //返回AD值
}
|