/****************************************************************************** 版权所有: 文件名称: pit.c 文件版本: 01.01 创建作者: sunxi 创建日期: 2008-06-25 功能说明: 可编程中断定时器程序。 其它说明: 修改记录: */ /*------------------------------- 头文件 -------------------------------------- */ #include "bsp.h" #include "rt.h" #include "head.h" /*------------------------------- 宏定义 -------------------------------------- */ /*------------------------------ 全局变量 ------------------------------------- */ unsigned int g_count_156us; FN_PIT_CALLBACK g_pit_callback_5ms; FN_PIT_CALLBACK g_pit_callback_156us; struct rt_stat g_stat_156us; struct rt_stat g_stat_5ms; extern struct rt_stat g_stat_periodus_5ms; void pit_156us_isr(void); void pit_5ms_isr(void); //void pit_250us_isr(void); // sunxi 20190425 added int pit_500us_isr(int irq, void *data); /*------------------------------ 外部函数 ------------------------------------- */ /****************************************************************************** 函数名称: pit_init 函数版本: 01.01 创建作者: sunxi 创建日期: 2008-06-25 函数说明: pit初始化。目前使用PIT0产生1ms中断。 参数说明: 无 返回值: 无 修改记录: */ int pit_init(void) { pit_stat_reset(); return 0; } int pit_exit(void) { rt_free_irq(CFG_PIT_VECTOR_BEGIN+CFG_PIT_5MS); // 释放5ms中断 rt_free_irq(CFG_PIT_VECTOR_BEGIN+CFG_PIT_SAMPLE); // 释放156us中断 return 0; } /****************************************************************************** 函数名称: pit_regester_callback 函数版本: 01.01 创建作者: sunxi 创建日期: 2011-04-22 函数说明: 登记PIT的定时回调函数。 参数说明: period_us: 定时周期,以us为单位。 fn: 回调函数。 返回值: 成功返回0,失败返回负数。 修改记录: */ int pit_regester_callback(int period_us,FN_PIT_CALLBACK fn) { switch(period_us) { case 5000: g_pit_callback_5ms = fn; break; case 156: g_pit_callback_156us = fn; break; default: return -1; } return 0; } /****************************************************************************** 函数名称: pit_156us_period_set 函数版本: 01.01 创建作者: sunxi 创建日期: 2012-12-05 函数说明: 通过测得的线路频率,修改采样周期。 参数说明: hz: 通过测频电路测得的线路频率。Q16定点数。 返回值: 成功返回0,失败返回负数。 修改记录: */ int pit_156us_period_set(float hz) { unsigned short pmr; hz *= CFG_ADC_DOTS_PER_PERIOD*4;// 128点采样 // 根据公式计算pmr。 pmr = (unsigned short)rt_round((CFG_CPU_CLK/2)/hz); pmr -= 2; //设置定时周期。 // MCF_PIT3_PMR = pmr; //rt_printf("pit_156us_period:hz=%s,pmr=0x%04x\r\n",q16_to_str(hz/128),pmr); return 0; } /****************************************************************************** 函数名称: pit_5ms_isr 函数版本: 01.01 创建作者: sunxi 创建日期: 2008-06-25 函数说明: pit0中断服务程序。 参数说明: 无 返回值: 无 修改记录: */ void pit_5ms_isr(void) { // 统计中断延时 // rt_stat_in(&g_stat_5ms,(uint32_t)(PIT_PERIOD_5MS - MCF_PIT2_PCNTR)); // 先清除中断 // MCF_PIT2_PCSR |= MCF_PIT_PCSR_PIF; //5ms主回调函数 if(g_pit_callback_5ms) { g_pit_callback_5ms(0); } //软件狗喂狗 watchdog_feed_protect(); } /****************************************************************************** 函数名称: pit_156us_isr 函数版本: 01.01 创建作者: sunxi 创建日期: 2011-04-22 函数说明: pit1中断服务程序。 参数说明: 无 返回值: 无 修改记录: */ //extern struct rt_irq_node g_rt_irq_list[RT_IRQS_NUM]; void dido_soe_gen(void); void pit_156us_isr(void) { #if 0 int mod; uint32_t count; uint32_t us0; count = (uint32_t)(MCF_PIT3_PMR - MCF_PIT3_PCNTR); rt_stat_in(&g_stat_156us,count); us0 = ustimer_get_origin(); // 先清除中断。 MCF_PIT3_PCSR |= MCF_PIT_PCSR_PIF; //根据g_count_156us统一计算mod和is625us,保证两者的同步。 mod = (int)(g_count_156us &0x03); // is625us = (mod == 0x03) ? 1:0; //调用ADC中断处理函数 adc_isr(mod); // SOE发生器 dido_soe_gen(); // 遥信扫描 dido_di_poll(); //回调156us应用处理函数 if (g_pit_callback_156us != NULL) { g_pit_callback_156us(mod); } //计数器加一。 g_count_156us++; // 喂ADC看门狗 watchdog_feed_adc(); // 由于针对采样中断的入口进行了优化,所以将时间统计放在这儿。 rt_stat_in(&g_rt_irq_list[CFG_PIT_VECTOR_BEGIN+3].stat,ustimer_get_duration(us0)); #endif } int pit_stat_reset(void) { rt_stat_init(&g_stat_156us,"pit_156us_isr(8ns)"); rt_stat_init(&g_stat_5ms,"pit_5ms_isr(128ns)"); rt_stat_init(&g_stat_periodus_5ms, "pit_5ms_priod(1us)"); return 0; } int pit_stat_printf(void) { rt_printf("\r\n[实时中断延时统计(单位:见各行)]\r\n"); rt_stat_printf(&g_stat_156us); rt_stat_printf(&g_stat_5ms); rt_stat_printf(&g_stat_periodus_5ms); return 0; } int pit_500us_isr(int irq, void *data) { // 清除中断标志 //MCF_PIT1_PCSR |= MCF_PIT_PCSR_PIF; //goose_timer_handle(); return 0; } /*------------------------------ 测试函数 ------------------------------------- */ //#ifdef CFG_BSP_DEBUG #if 0 #include "ustimer.h" int pit_test(void) { uint32_t t,t0; t=0; t0 = ustimer_get_origin(); sti(0); while(1) { rt_printf("pit(t=%04d):5ms:%06d,156us:%08d,[156us-t*6400:%d],[5ms-t*200:%d]!\r\n", t, g_count_5ms, g_count_156us, g_count_156us -t*6400, g_count_5ms -t*200); watchdog_feed_software_5s(); t++; ustimer_delay_origin(t0,t*USTIMER_SEC); } } #endif /*------------------------------ 文件结束 ------------------------------------- */