OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 7473|回复: 12

关于测频的问题的讨论

[复制链接]

16

主题

34

帖子

0

精华

初级会员

Rank: 2

积分
118
金钱
118
注册时间
2011-1-27
在线时间
0 小时
发表于 2012-3-23 13:37:06 | 显示全部楼层 |阅读模式

首先说明:我手里有两个程序,一个原理是读两个方波之间的时间,从而计算频率的,还有一个是读某一段时间内有几个上升沿,从而计算频率的,从原理上来说这两个都是对的,但是我们测的频率一般在35-65Hz之间,所以我觉得还是第一种比较好,但是同事非说第一种不对,所以两种贴上来让大家看看
首先是第一种,读两个方波之间的时间
void Drv_Fre_Cal(void)//u16 wHcSpace
{
    static u32 wTemp1,wTemp2;
    static u32 CaptureNumber=0;
    static u32  Capture;

    if(TIM_GetFlagStatus(TIM4, TIM_FLAG_CC2) != RESET) //判断捕获通道3是否有捕获?
    {
               if(CaptureNumber==0)
               {
                     wTemp1 =  TIM_GetCapture2(TIM4);    //读取捕获通道3的值 Fre of Fre2(UA)
                     CaptureNumber=1;
               }
               else if(CaptureNumber==1)
               {
                      wTemp2 =  TIM_GetCapture2(TIM4);
                      if (wTemp2 > wTemp1)
                     {
                           Capture = (wTemp2 - wTemp1);
                     }
                     else
                    {
                          Capture = (( 0xFFFF- wTemp1) + wTemp2);//
                    }

                    if ((Capture>=36363) && (Capture<=44444))                               
                             c_wFre=MulDivU32(2000000,100,Capture);
                
               CaptureNumber = 0;
              }

         TIM_ClearFlag(TIM4,TIM_FLAG_CC2);
 }
}

下面是对定时器的设置
void DRV_TIM4_Configration(void)
{

      TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
      RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE);
     
      TIM_TimeBaseStructure.TIM_Period = 0xFFFF;                //10000  这个值实际上就是TIMX->ARR,延时开始时重新设定即可
      TIM_TimeBaseStructure.TIM_Prescaler =TIM4_Prescaler ;          //  72Mhz/(TIM4_Prescaler+1)=2MHZ  计数频率为1KHz   设置TIMx_PSC寄存器
     
      TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;        // 定时器基准频率32MHz??   时钟分配
      TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;    // 向上计数
   
      TIM_TimeBaseInit(TIM4, &TIM_TimeBaseStructure);
      TIM_Cmd(TIM4, ENABLE);

}
void STM32_Fre_Configration(void)
{
   
        TIM_ICInitTypeDef  TIM_ICInitStructure;
        RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE);

        TIM_DeInit(TIM4);

        //TIM_ICInitStructure.TIM_ICMode = TIM_ICMode_ICAP;                //配置为输入捕获模式
        TIM_ICInitStructure.TIM_Channel = TIM_Channel_2;                   //选择通道1
        TIM_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_Rising;        //输入上升沿捕获
        TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI;    // 通道方向选择
        TIM_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1;              //每次检测到捕获输入就触发一次捕获

        TIM_ICInitStructure.TIM_ICFilter = 0x0;                            //滤波设置,经历几个周期跳变认定波形稳定0x0~0xF
        TIM_ICInit(TIM4, &TIM_ICInitStructure);

        TIM_PrescalerConfig(TIM4,0x23,TIM_PSCReloadMode_Immediate);

         // Select the TIM4 Input Trigger: TIFP
        TIM_SelectInputTrigger(TIM4, TIM_TS_ITR2);//          TIM_TS_TI1F_ED            //选择时钟触发源
        //从模式可以不用选择
        // Select the slave Mode: Reset Mode   复位模式,选中的触发输入的上升沿初始化计数器,并且产生一个更新信号
        //TIM_SelectSlaveMode(TIM4, TIM_SlaveMode_External1);
        //TIM_SelectSlaveMode(TIM4, TIM_SlaveMode_Reset);
        
        // Enable the Master/Slave Mode    主从模式选择
        //TIM_SelectMasterSlaveMode(TIM4, TIM_MasterSlaveMode_Enable);      //启动定时器的被动触发
        //TIM_ITConfig(TIM4, TIM_IT_CC4 , ENABLE);
        // TIM enable counter
        TIM_Cmd(TIM4, ENABLE);
}

正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

16

主题

34

帖子

0

精华

初级会员

Rank: 2

积分
118
金钱
118
注册时间
2011-1-27
在线时间
0 小时
 楼主| 发表于 2012-3-23 13:39:47 | 显示全部楼层
下面这个是第二种,在某一段时间内读方波个数(定时器设置上,我对了,都是一样的)
void Drv_Fre_Cal()//u16 wHcSpace
{
 u32 dwTimer;
 u32 wTemp2; //wTemp1,
 
  dwTimer = Os_GetmsTime();
          if(TIM_GetFlagStatus(TIM4, TIM_FLAG_CC2) != RESET) //判断捕获通道2是否有捕获?
        {
                wTemp2 =  TIM_GetCapture2(TIM4);    //读取捕获通道2的值 Fre of Fre2(UA)

// 如果频率在有效范围35Hz~65Hz)  //定时器4最大主频72M
if ((wTemp2>=30768) && (wTemp2<=57142))
{
c_wFre = LowSpeedClock/(35+1)*100/wTemp2;   
c_wFre2= c_wFre;
c_dwMsTimer = dwTimer;
}
else
{
//c_wCnt = 0;
                        c_lFreDlt = 2000000;
}
             
}
}


但是我不明白的是STM32能这么读吗?所谓捕获,捕获的应该是上升沿啊,那么可以看出他的这个程序捕获完了读的数应该还是计数器在捕获那一刻的值吧?
回复 支持 反对

使用道具 举报

16

主题

34

帖子

0

精华

初级会员

Rank: 2

积分
118
金钱
118
注册时间
2011-1-27
在线时间
0 小时
 楼主| 发表于 2012-3-23 13:41:38 | 显示全部楼层
根据这个第二种,他说变量wTemp2就是某一段时间的上升沿的个数,我对这个完全不理解,有人能给我解释一下吗?
回复 支持 反对

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165540
金钱
165540
注册时间
2010-12-1
在线时间
2117 小时
发表于 2012-3-23 14:05:31 | 显示全部楼层
自己测试一下不就知道了.
简单的计算频率,你只需要用计算上升沿就OK了.
我是开源电子网www.openedv.com站长,有关站务问题请与我联系。
正点原子STM32开发板购买店铺http://openedv.taobao.com
正点原子官方微信公众平台,点击这里关注“正点原子”
回复 支持 反对

使用道具 举报

16

主题

34

帖子

0

精华

初级会员

Rank: 2

积分
118
金钱
118
注册时间
2011-1-27
在线时间
0 小时
 楼主| 发表于 2012-3-23 14:36:23 | 显示全部楼层
回复【4楼】正点原子:
---------------------------------
比如一段要测试的方波吧,程序前面设置成捕获上升沿,那么根据第二个程序,读出来的就是当前计数器的值,对吧,然后一旦检测到有上升沿,立刻就把此时的计数值的值放到另外一个寄存器中,然后我们读出来这个计数器的数,没错吧?然后呢?这个计数器的数有什么用呢?
回复 支持 反对

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165540
金钱
165540
注册时间
2010-12-1
在线时间
2117 小时
发表于 2012-3-23 14:52:29 | 显示全部楼层
当然是统计一段时间内的上升沿个数了.
比如你统计1秒钟,以1s为基准,1s中内有3000个上升沿,那么频率就是3K
当然你也可以设置短一点,比如100ms,里面有300个上升沿,那么可以估算1s钟就是3000个,频率还是3K.
我是开源电子网www.openedv.com站长,有关站务问题请与我联系。
正点原子STM32开发板购买店铺http://openedv.taobao.com
正点原子官方微信公众平台,点击这里关注“正点原子”
回复 支持 反对

使用道具 举报

20

主题

562

帖子

0

精华

论坛大神

Rank: 7Rank: 7Rank: 7

积分
670
金钱
670
注册时间
2012-2-28
在线时间
0 小时
发表于 2012-3-23 16:24:01 | 显示全部楼层
问一下楼主:第一种和第二种的定时器设置方式一样吗????

如果是测时间,定时器时钟用的是系统时钟,然后CCRX中的值换算一下就是时间了

如果是测上升沿,那么定时器有两种设置方法,一是测试中上升沿然后进入中断,在中断中对一个全局变量加一,这个全局变量就是上升沿的个数;另一种采用外部时钟模式,这样CCRX的值就是捕获到的上升沿的个数,此时不必进入中断就可以

看不懂库函数,从原理上解决吧

努力,前进。
回复 支持 反对

使用道具 举报

20

主题

562

帖子

0

精华

论坛大神

Rank: 7Rank: 7Rank: 7

积分
670
金钱
670
注册时间
2012-2-28
在线时间
0 小时
发表于 2012-3-23 16:24:30 | 显示全部楼层
回复【6楼】正点原子:
---------------------------------
原子说的情况是建立在你用的是外部时钟模式的情况下
努力,前进。
回复 支持 反对

使用道具 举报

2

主题

4

帖子

0

精华

新手上路

积分
42
金钱
42
注册时间
2012-5-23
在线时间
3 小时
发表于 2012-5-23 22:02:17 | 显示全部楼层
回复【楼主位】玉珊瑚:
---------------------------------
你好,想问下你的测量精度能达到多少,我也在做测频的,可以交流下qq:839797720
回复 支持 反对

使用道具 举报

2

主题

4

帖子

0

精华

新手上路

积分
42
金钱
42
注册时间
2012-5-23
在线时间
3 小时
发表于 2012-5-23 22:02:35 | 显示全部楼层
回复【楼主位】玉珊瑚:
---------------------------------
你好,想问下你的测量精度能达到多少,我也在做测频的,可以交流下qq:839797720
回复 支持 反对

使用道具 举报

108

主题

1433

帖子

2

精华

论坛大神

Rank: 7Rank: 7Rank: 7

积分
2234
金钱
2234
注册时间
2012-4-30
在线时间
7 小时
发表于 2012-5-24 12:46:22 | 显示全部楼层
可以采用捕获模式做,精度非常高,而且也可以测很高的频率
回复 支持 反对

使用道具 举报

20

主题

45

帖子

0

精华

初级会员

Rank: 2

积分
145
金钱
145
注册时间
2013-3-21
在线时间
0 小时
发表于 2013-5-9 23:14:31 | 显示全部楼层
回复【11楼】lsj9383:
---------------------------------
10HZ到1MHZ精度0.1%可以到么?
回复 支持 反对

使用道具 举报

108

主题

1433

帖子

2

精华

论坛大神

Rank: 7Rank: 7Rank: 7

积分
2234
金钱
2234
注册时间
2012-4-30
在线时间
7 小时
发表于 2013-5-10 12:51:27 | 显示全部楼层
回复【12楼】溪孟:
---------------------------------
应该可以、
试一下呗、
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-7-21 11:20

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表