ADC读取数据写SD卡过程问题
在使用定时器触发ADC读取数据写入SD卡过程中,每完成一次ADC进入一次ADC中断,中断中读取数据,代码如下
void ADC1_2_IRQHandler(void)
{
if (ADC_GetITStatus(ADC1, ADC_IT_EOC))
{
GPIO_WriteBit(GPIOE, GPIO_Pin_0, (i == 0) ? (i = Bit_SET) : (i = Bit_RESET));
if(number2<1400)
{
if(flag%2==0)
{
//BUF =ADC_GetConversionValue(ADC1);//ADC中断中读取数据寄存器的值
DMA_Cmd( DMA1_Channel1, ENABLE );
buf1[number2]=BUF[0]&0XFF;
buf1[number2+1]=(BUF[0]>>8)&0XFF;
DMA_Cmd( DMA1_Channel1, DISABLE );
number2=number2+2;
ADC_ClearITPendingBit(ADC1, ADC_IT_EOC);
}
if(flag%2==1)
{
//BUF =ADC_GetConversionValue(ADC1);//ADC中断中读取数据寄存器的值
DMA_Cmd( DMA1_Channel1, ENABLE );
buf1_ex[number2]=BUF[0]&0XFF;
buf1_ex[number2+1]=(BUF[0]>>8)&0XFF;
DMA_Cmd( DMA1_Channel1, DISABLE );
number2=number2+2;
ADC_ClearITPendingBit(ADC1, ADC_IT_EOC);
}
}
if(number2>1400)
{
number2=2;
printf("01\r\n");
ADC_ClearITPendingBit(ADC1, ADC_IT_EOC);
}
}
ADC_ClearITPendingBit(ADC1, ADC_IT_EOC);
}
}
每进入一次中断GPIO翻转一次,计数到1400后写卡
if(number2==1400)
{
number2=2;
flag=flag+1;
if(flag%2==1)
{
counter=counter+0X0001;
f_write(&fnew,buf1,sizeof(buf1),&fnum);
buf1[1]=counter&0xff;
buf1[0]=((counter>>8)&0XFF);
}
if(flag%2==0)
{
counter=counter+0X0001;
f_write(&fnew,buf1_ex,sizeof(buf1_ex),&fnum);
buf1_ex[1]=counter&0xff;
buf1_ex[0]=((counter>>8)&0XFF);
}
}
实际上用逻辑分析仪得到的波形如下
从你的描述来看,这确实可能是一个经典的嵌入式系统问题,也就是一个资源(在这个例子中是CPU)被一个过程(写SD卡)过度使用,从而阻止了其他重要的过程(ADC读取)的执行。这样的问题在实时系统中尤其常见,因为它们经常需要同时处理多个任务。
解决此类问题的一个常见方法是将写SD卡的任务放到一个单独的低优先级线程或任务中去执行。这样,只要ADC需要执行,它就能立即抢占CPU,而SD卡写入任务则会在ADC读取完成后再继续。这种技术需要你的系统支持多任务或多线程,如RTOS(实时操作系统)。
另一种解决方案是通过使用DMA(直接内存访问)来写SD卡。DMA控制器可以在CPU执行其他任务时自动完成数据的传输,这样可以有效地释放CPU资源。
最后,也可以考虑优化SD卡写入的代码,尽量减少写操作的时间。例如,可以尽量缓存数据,然后一次性将大块数据写入SD卡,而不是频繁地写入小块数据。
需要注意的是,每种解决方案都有其优点和缺点,需要根据具体的系统需求和约束来选择最合适的方案。
可以查一下写SD卡的函数f_write,里面是否关闭了中断。如果是的话,再看关闭中断的范围,是否可以缩小。
估计现在写的顺序是:1.关中断 -> 2.擦除待写的数据块 -> 3.写全部数据 -> 4.开中断。
可以修改为: 1.擦除待写的数据块 -> 2.关中断 -> 3.写一部分数据 -> 4.开中断 -> 5.重复1-4直到所有数据写完.
注意因为写入过程中开了中断,会导致写入循环过程中数据出现变化。原始代码中用flag控制adc采样保存的位置在buf1或buf_ex,但是采样数据写和SD卡写,用的是同一个数据块。可以让采样数据填满buf1之后,修改flag,使得采样数据往buf_ex写。同时启动sd看写入过程,将buf1的数据写入sd卡。这样就可以避免sd卡写入过程中数据出现变化。