新手入门
- 积分
- 17
- 金钱
- 17
- 注册时间
- 2019-11-17
- 在线时间
- 5 小时
|
1金钱
各位大虾好,小弟刚接触STM32,菜鸟一个,请大家多多指教
最近用到STM32F103C8T6的双ADC模式,同步规则采样两个通道PA0和PA1,ADC1用EXTI11触发。结果发现实际动作和手册上讲的貌似有些出入。
手册上讲使用regular simultaneous mode时,转换结果会全都放在ADC1_DR里,高16位是ADC2的结果,低16位是ADC1的结果。但我开启中断,在中断服务里读ADC1_DR时只能读出ADC1的结果,高16位全是0。抱着试一试的心态在中断服务里读了一下ADC2_DR,发现结果是对的!!那也就是说在regular simultaneous mode时两个ADC的结果还是分开的?
附上ADC配置和中断的代码,请各位大侠过目:
void ADC_Config(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0|GPIO_Pin_1;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN;
GPIO_Init(GPIOA, &GPIO_InitStructure);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1|RCC_APB2Periph_ADC2, ENABLE);
RCC_ADCCLKConfig(RCC_PCLK2_Div8);
ADC1->CR1|=0X00060000; //DUAL Mode: regular simultaneous
ADC1->CR1|=1<<5; //interrupt enabled
ADC1->CR1&=~(1<<8); //reset SCAN
ADC1->CR2&=~(1<<1); //reset CONT
ADC1->CR2|=3<<18; //trigger source:EXTI11 event
ADC1->CR2|=1<<20; //external trigger selected
ADC1->CR2&=~(1<<11); //Right Alignment
ADC1->SQR1&=~(0XF<<20);
ADC1->SQR1|=0<<20; //only one channel in the sequence
ADC1->SMPR2|=7<<0; //sample time:239.5 cycles
ADC1->SQR3=0x00000000; //channel 0 is input pin of ADC1
ADC1->CR2|=1<<0; //ADC1 ON
ADC1->CR2|=1<<3; //RSTCAL
while(ADC1->CR2&1<<3); //wait until RSTCAL is reseted
ADC1->CR2|=1<<2; //CAL
while(ADC1->CR2&1<<2); //wait until CAL is reseted
ADC2->CR1|=0X00060000; //DUAL Mode: regular simultaneous
ADC2->CR1&=~(1<<8); //reset SCAN
ADC2->CR2&=~(1<<1); //reset CONT
ADC2->CR2|=7<<17; //trigger source:SWSTART(trigged by ADC1)
ADC2->CR2&=~(1<<11); //Right Alignment
ADC2->CR2|=(1<<20); //external trigger selected(ADC2 is slave of ADC1)
ADC2->SQR1&=~(0XF<<20);
ADC2->SQR1|=0<<20; //only one channel in the sequence
ADC2->SMPR2|=7<<0; //sample time:239.5 cycles
ADC2->SQR3=0x00000001; //channel 1 is input pin of ADC2
ADC2->CR2|=1<<0; //ADC2 ON
ADC2->CR2|=1<<3; //RSTCAL
while(ADC2->CR2&1<<3); //wait until RSTCAL is reseted
ADC2->CR2|=1<<2; //CAL
while(ADC2->CR2&1<<2); //wait until CAL is reseted
}
中断服务:
void ADC1_2_IRQHandler(void)
{
u16 res1,res2;
res1=ADC1->DR&0xFFFF;
res2=ADC2->DR&0xFFFF; //这样写结果就对了!!如果写res2=(ADC1->DR>>16)&0xFFFF,读出来永远是0
send_res(res1); //send_res是通过串口发送结果的子程序
send_res(res2);
USART_SendChar('\n'); //USART_SendChar是通过串口发送字符的子程序
}
感谢各位百忙之中抽空帮忙。谢谢!
|
最佳答案
查看完整内容[请看2#楼]
找到问题了。下午又重新读了几遍手册,RM0008第228页上写了:In dual ADC mode, to read the slave converted data on the master data register, the DMA bit must be enabled even if it is not used to transfer converted regular channel data.
就是为了让ADC1和ADC2的结果在一起,即使不使用DMA也要开启ADC1的DMA功能。加上一句ADC1->CR2|=1
|