关于ATmega16中断问题
在这个程序中,我用TTL进行两个单片机的之间通信,将一个单片机1的信号传到另一个单片机(ATMEGA16)上,在ATmega16上还用ADC采集信号,1.所以这样在ATm...
在这个程序中,我用TTL进行两个单片机的之间通信,将一个单片机1的信号传到另一个单片机(ATMEGA16)上,在ATmega16上还用ADC采集信号,
1.所以这样在ATmega16上就用到有两个中断了,那个ADC采集我是用连续采集的,它会一直去管脚那里采集信号,这样会不会影响串行中断???????小弟在试的时候一开始采集回来的数据是正常的,当我一开户串口中断时,采集回来的数据就是想差超级远了,可以说是完全错误,十万八千里。。。。
2.然后,在ATmega16中是如何去切换通道????部分代码如下:我是通过改变CH1R的值来改变通道的,像CH1=1或2或3.。。。前面两个还正常,当3的时候就不正常了,它不能感应到3的通道,当同时开户1,2通道时,它会直接跑到3通道那里。求解!!!!!!!!!!!!谢谢谢,在线等待~~~~~~
//**************初始化AD***********
void AD_INIT(unsigned char chl)
{
if(chl<4)
{
ADMUX |= BIT(REFS0)|chl;//|BIT(ADLAR);
//设置参考电压,设置为自动转换模式,选择通道;
ADCSRA|= BIT(ADEN)|BIT(ADATE)|BIT(ADIE)|BIT(ADPS2)|BIT(ADPS1);
//AD功能使能,开启AD转换中断,设定ADC时钟分频;
SREG |= BIT(7);
//开启总中断;
ADCSRA|= BIT(ADSC);
//启动转换;
}
} 展开
1.所以这样在ATmega16上就用到有两个中断了,那个ADC采集我是用连续采集的,它会一直去管脚那里采集信号,这样会不会影响串行中断???????小弟在试的时候一开始采集回来的数据是正常的,当我一开户串口中断时,采集回来的数据就是想差超级远了,可以说是完全错误,十万八千里。。。。
2.然后,在ATmega16中是如何去切换通道????部分代码如下:我是通过改变CH1R的值来改变通道的,像CH1=1或2或3.。。。前面两个还正常,当3的时候就不正常了,它不能感应到3的通道,当同时开户1,2通道时,它会直接跑到3通道那里。求解!!!!!!!!!!!!谢谢谢,在线等待~~~~~~
//**************初始化AD***********
void AD_INIT(unsigned char chl)
{
if(chl<4)
{
ADMUX |= BIT(REFS0)|chl;//|BIT(ADLAR);
//设置参考电压,设置为自动转换模式,选择通道;
ADCSRA|= BIT(ADEN)|BIT(ADATE)|BIT(ADIE)|BIT(ADPS2)|BIT(ADPS1);
//AD功能使能,开启AD转换中断,设定ADC时钟分频;
SREG |= BIT(7);
//开启总中断;
ADCSRA|= BIT(ADSC);
//启动转换;
}
} 展开
2个回答
展开全部
ADMUX 低5位用来配置输入引脚;
其低5位为0~7的时候,配置的是单端输入的信号,对应的输入源为ADC0~ADC7;
其余值为差分输入;
如果需要配置差分输入:ADMUX低五位的值应该是11001;(ADC1为正,ADC2为负);
如果不是差分信号,那么一次只能做一个单端的ADC,是不能ADC1和ADC2同时打开的;
至于ADC的使用,我一般在需要ADC的时候开,得到结果以后就关掉ADC。不会让它一直进行转换的,一个是执行效率的问题,要考虑到采样时间越长,受到干扰的可能就越大。
其低5位为0~7的时候,配置的是单端输入的信号,对应的输入源为ADC0~ADC7;
其余值为差分输入;
如果需要配置差分输入:ADMUX低五位的值应该是11001;(ADC1为正,ADC2为负);
如果不是差分信号,那么一次只能做一个单端的ADC,是不能ADC1和ADC2同时打开的;
至于ADC的使用,我一般在需要ADC的时候开,得到结果以后就关掉ADC。不会让它一直进行转换的,一个是执行效率的问题,要考虑到采样时间越长,受到干扰的可能就越大。
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
展开全部
在采用AD转换时候,不要直接在AD初始化函数里启动AD转换,这样会堵塞其他程序的运行。最好是使用定时器,在定时器里面定时开启和关闭AD使能。比如
unsigned char AD_num;
AD_num++;
if(AD_num==50)ADCSRA|= BIT(ADSC); //开启转换
else 关闭转换
仅需开启一瞬间即可使AD进行多次取样了。
另外,在使用多路AD转换时候,首先是关闭转换,在通道切换后再开启转换,并且在AD中断服务函数中,多读几次寄存器数据,这样才会得到正确的通道值。
unsigned char AD_num;
AD_num++;
if(AD_num==50)ADCSRA|= BIT(ADSC); //开启转换
else 关闭转换
仅需开启一瞬间即可使AD进行多次取样了。
另外,在使用多路AD转换时候,首先是关闭转换,在通道切换后再开启转换,并且在AD中断服务函数中,多读几次寄存器数据,这样才会得到正确的通道值。
更多追问追答
追问
有道理哦,嗯,那定时器中断与其它中断或其它程序可不可以一起运行的??我觉得应该可以吧,对了,还有能不能在while(1)里面进行开与关再开与关之间再用上delay();来去实现?????
追答
中断当然可以同时使用,但是单片机在某一时刻执行的语句是单一的,也就是说根据中断优先级进行语句执行。单片机如果不能执行多个中断或程序,那么就称不上CPU了。
也不能说不能在while(1)里面用,但是加delay函数必然会导致单片机的效率降低,还是用中断好,对开关的控制较为准确。如我们常用的是在定时器里进行开关控制和AD端口切换,毕竟中断的效率较高。
本回答被提问者采纳
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
推荐律师服务:
若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询