请教个问题,UCOSII中ADC的滤波。谢。
/****************************************Copyright (c)**************************************************** 广州周立功单片机发展有限公司
** 研 究 所
** 产品一部
**
** http://www.zlgmcu.com
**
**--------------文件信息--------------------------------------------------------------------------------
**文 件 名: ADC01.C
**创 建 人: 黄绍斌
**最后修改日期: 2004年3月25日
**描 述: 使用ADC模块的通道0、1进行电压的测量,然后将转换结果从串口输出,上位机使用EasyARM软件全仿真的DOS字
** 符窗口观察。
** 通讯格式为8位数据位,1位停止位,无奇偶校验,波特率为115200。
**--------------历史版本信息----------------------------------------------------------------------------
** 创建人:
** 版本:
** 日 期:
** 描 述:
**
**------------------------------------------------------------------------------------------------------
** 修改人:
** 版本:
** 日 期:
** 描 述:
**
**--------------当前版本修订------------------------------------------------------------------------------
** 修改人: 黄绍斌
** 日 期: 2004年3月25日
** 描 述: 在TARGET.C文件中初始化UART0。
** 说明: 将JP5、JP10短接,由W1、W2调节测量电压值;
** 将PC的COM1(或COM2)与EasyARM2100开发板的CZ2连接。
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
#include "config.h"
#define TASK_STK_SIZE 128 /* 定义任务堆栈大小 */
OS_STK TaskStartStk;
OS_STK TaskStk;
OS_EVENT *AdcDataMbox; /* 定义邮箱,用于传递ADC转换结果 */
voidTaskStart(void *data);
voidTaskAdc(void *data);
/*********************************************************************************************************
** 函数名称: main
** 功能描述: c语言的主函数,由它启动多任务环境
** 输 入: 无
** 输 出: 无
** 全局变量: 无
** 调用模块: OSInit,OSTaskCreate,OSStart
**
** 作 者: 陈明计
** 日 期: 2003年7月8日
**-------------------------------------------------------------------------------------------------------
** 修改人:
** 日 期:
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
int main (void)
{
OSInit();
OSTaskCreate(TaskStart, (void *)0, &TaskStartStk, 0);
OSStart();
return 0;
}
/*********************************************************************************************************
** 函数名称: TaskStart
** 功能描述: μCOS-II的第一个任务,通常由它初始化目标板和建立其它任务
** 输 入: 无
** 输 出: 无
** 全局变量: 无
** 调用模块:
**
** 作 者: 陈明计
** 日 期: 2003年7月8日
**-------------------------------------------------------------------------------------------------------
** 修改人:
** 日 期:
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
voidTaskStart(void *pdata)
{
uint32*cp;
uint8 err;
uint32ADC_Data;
char s;
pdata = pdata; /* 避免编译警告 */
AdcDataMbox = OSMboxCreate(NULL); /* 建立邮箱 */
if (AdcDataMbox == NULL)
{
while (1);
}
PINSEL1 = ( (PINSEL1&0xfc3fffff) | 0x01400000); /* 设置P0.27、P0.28连接到AIN0、AIN1 */
TargetInit(); /* 目标板初始化 */
OSTaskCreate(TaskAdc, (void *)0, &TaskStk, 10); /* 创建任务 */
for (;;)
{
cp = (uint32 *)OSMboxPend(AdcDataMbox, 0, &err); /* 接收数据 */
ADC_Data = (cp>>6) & 0x3FF;
ADC_Data = ADC_Data * 3300;
ADC_Data = ADC_Data / 1024;
sprintf(s, "%4dmV at VIN1", ADC_Data);
PC_DispStr(60, 23, s, DISP_FGND_YELLOW + DISP_BGND_BLUE);
ADC_Data = (cp>>6) & 0x3FF;
ADC_Data = ADC_Data * 3300;
ADC_Data = ADC_Data / 1024;
sprintf(s, "%4dmV at VIN2", ADC_Data);
PC_DispStr(60, 21, s, DISP_FGND_YELLOW + DISP_BGND_BLUE);
}
}
/*********************************************************************************************************
** 函数名称: TaskAdc
** 功能描述: μCOS-II的任务,用于进行ADC转换。
** 输 入: 无
** 输 出: 无
** 全局变量: 无
** 调用模块:
**
** 作 者: 陈明计
** 日 期: 2003年7月8日
**-------------------------------------------------------------------------------------------------------
** 修改人: 陈明计
** 日 期: 2003年7月21日
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
voidTaskAdc(void *pdata)
{
uint32 Buf;
pdata = pdata; /* 避免编译警告 */
/* 进行ADC模块设置,其中x<<n表示第n位设置为x(若x超过一位,则向高位顺延) */
ADCR = (1 < 0) | /* SEL = 1 ,选择通道0 */
((Fpclk / 1000000 - 1) < 8) | /* CLKDIV = Fpclk / 1000000 - 1 ,即转换时钟为1MHz */
(0 < 16) | /* BURST = 0 ,软件控制转换操作 */
(0 < 17) | /* CLKS = 0 ,使用11clock转换 */
(1 < 21) | /* PDN = 1 , 正常工作模式(非掉电转换模式) */
(0 < 22) | /* TEST1:0 = 00 ,正常工作模式(非测试模式) */
(1 < 24) | /* START = 1 ,直接启动ADC转换 */
(0 < 27); /* EDGE = 0 (CAP/MAT引脚下降沿触发ADC转换) */
for (;;)
{
ADCR = (ADCR&0xFFFFFF00)|0x01|(1 < 24); /* 切换通道并进行第一次转换 */
while( (ADDR&0x80000000)==0 ) /* 等待转换结束 */
{OSTimeDly(OS_TICKS_PER_SEC / 100);
}
ADCR = ADCR | (1 < 24); /* 再次启运转换 */
while( (ADDR&0x80000000)==0 )
{OSTimeDly(OS_TICKS_PER_SEC / 100);
}
Buf = ADDR; /* 读取ADC结果 */
ADCR = (ADCR&0xFFFFFF00)|0x02|(1 < 24);
while( (ADDR&0x80000000)==0 )
{OSTimeDly(OS_TICKS_PER_SEC / 100);
}
ADCR = ADCR | (1 < 24);
while( (ADDR&0x80000000)==0 )
{OSTimeDly(OS_TICKS_PER_SEC / 100);
}
Buf = ADDR;
OSMboxPost(AdcDataMbox, (void *)Buf);
OSTimeDly(OS_TICKS_PER_SEC / 10);
}
}
/*********************************************************************************************************
** End Of File
********************************************************************************************************/
这个是老周的例程,如果AD滤波,在任务里怎么滤波?
如果无OS查询的话,可以多读几次,平均。
上传一个老周的例程来讨论一下。
本帖最后由 gaolf_2012 于 2012-5-28 19:12 编辑
for (;;)
{
cp = (uint32 *)OSMboxPend(AdcDataMbox, 0, &err); /* 接收数据 */
ADC_Data = filter1(cp);
ADC_Data = ADC_Data * 3300;
ADC_Data = ADC_Data / 1024;
sprintf(s, "%4dmV at VIN1", ADC_Data);
PC_DispStr(60, 23, s, DISP_FGND_YELLOW + DISP_BGND_BLUE);
ADC_Data = filter1(cp);
ADC_Data = ADC_Data * 3300;
ADC_Data = ADC_Data / 1024;
sprintf(s, "%4dmV at VIN2", ADC_Data);
PC_DispStr(60, 21, s, DISP_FGND_YELLOW + DISP_BGND_BLUE);
}
uint32 filter1(uint32 dwData)
{
static uint32 dwpDataBuff = {0};
static unsigned char bPos=0;
uint32 dwI=0;
unsigned char bI;
dwpDataBuff = (dwData>>6) & 0x3FF;
if (bPos > 15)
{
bPos = 0;
}
for (bI=0; bI<16; bI++)
{
dwI += dwpDataBuff;
}
return (dwI >> 4);
}
uint32 filter2(uint32 dwData)
{
static uint32 dwpDataBuff = {0};
static unsigned char bPos=0;
uint32 dwI=0;
unsigned char bI;
dwpDataBuff = (dwData>>6) & 0x3FF;
if (bPos > 15)
{
bPos = 0;
}
for (bI=0; bI<16; bI++)
{
dwI += dwpDataBuff;
}
return (dwI >> 4);
}
试试看 谢谢。试试。 mark 滤波
页:
[1]