SMARTFUSION从FPGA到ARM(------)——MSS_TIMER定时器的使用

文章目录


系列教程:SmartFusion从FPGA到ARM系列教程

1.定时器资源简介

SmartFusion片上MUC有两个32位的定时器,可以分别独立使用,也可以两个合并成一个64位定时器来使用。

驱动库只有一个mss_timer.h文件,库函数也比较简单。之前几篇文章,我们介绍了MSS_GPIO的使用SysTick定时器的使用,使用SysTick内核定时器可以精确控制延时,使用外设定时器也能实现定时。

本篇文章介绍MSS_TIMER定时器的使用和配置,演示定时器周期溢出中断,单次溢出中断,自定义波形功能。

固件库下载地址:Firmware_MSS_Timer_Driver_v2.3.102

官方使用文档路径:X:\Microsemi\common\vault\Components\Actel\Firmware\MSS_Timer_Driver\2.3.102\fs\p2f0\docs

2.MSS_TIMER库函数简介

MSS_TIMER库函数整体可分为三种:初始化,定时器配置和中断控制

其中TIMx可为TIM1、TIM2或TIM64,其中TIM64是把TIM1和TIM2合成一个64位的定时来使用。

初始化函数,初始化完成之后,定时器将会停止,禁止中断,并设置工作模式。

/* 配置定时器的工作方式,单次中断还是周期性中断 */
void MSS_TIMx_init( mss_timer_mode_t mode )

mode支持的取值:

/* 周期性溢出中断模式 */
MSS_TIMER_PERIODIC_MODE
/* 单次溢出中断模式 */
MSS_TIMER_ONE_SHOT_MODE 

配置函数:

/* 设置溢出值,立即生效 */
void MSS_TIMx_load_immediate(uint32_t load_value);
/* 指定下次计时的溢出值 */
void MSS_TIMx_load_background(uint32_t load_value);
/* 获取当前计数值 */
uint32_t MSS_TIMx_get_current_value();
/* 获取64位定时器的当前值,高32位和低32位 */
void MSS_TIM64_get_current_value(uint32_t * load_value_u, uint32_t * load_value_l)
/* 启动定时器 */
void MSS_TIMx_start(void);
/* 停止计数器 */ 
void MSS_TIMx_stop(void);

中断控制函数

/* 使能中断 */
void MSS_TIMx_enable_irq(void);
/* 禁止中断 */
void MSS_TIMx_disable_irq(void);
/* 清除中断 */
void MSS_TIMx_clear_irq(void);

了解了定时器操作的相关函数,下面来演示几个定时器的使用方法。

3.简单的周期性中断

GPIO每隔250ms翻转一次。

/* TIM1配置成周期中断,中断时间250ms */
MSS_TIM1_init(MSS_TIMER_PERIODIC_MODE);
MSS_TIM1_load_immediate(SystemCoreClock/4);
MSS_TIM1_start();
MSS_TIM1_enable_irq();

/* 定时器中断服务函数 */
void Timer1_IRQHandler(void)
{
    static uint8_t status = 0;
    status = !status;
    
    MSS_IO_OUT(1) = status;
    
    MSS_TIM1_clear_irq();
}
4.自定义产生波形

产生20ms、40ms、60ms、80ms、100ms高低电平相间的波形。

#define SEQUENCE_LENGTH 5

static const uint32_t g_delays_list[SEQUENCE_LENGTH] =
{
    20, 40, 60, 80, 100
};

int main()
{
	。。。。。。。。。。。。。。
    /* TIM1配置成周期中断,中断时间250ms */
    MSS_TIM1_init(MSS_TIMER_PERIODIC_MODE);
    MSS_TIM1_load_immediate(g_delays_list[0]);
    MSS_TIM1_start();
    MSS_TIM1_enable_irq();
    
    while(1)
    {
		。。。。。。
    }
}

void Timer1_IRQHandler(void)
{
    static uint8_t idx = 0;
    static uint8_t status = 0;
    
    status = !status;
    MSS_IO_OUT(1) = status;

    /* 指定下次计时溢出值 */
    MSS_TIM1_load_background( g_delays_list[idx] * (SystemCoreClock/1000));
    
    if(idx < SEQUENCE_LENGTH)
        idx++;
    else 
        idx = 0;

    MSS_TIM1_clear_irq();
}

5.64位定时器的使用

两个32位的定时器可以组成1个64位的定时器,64位定时器和TIM1共用一个中断服务函数。按键按下时,LED停止闪烁,松开继续闪烁。

#include "main.h"

int main()
{
    uint8_t key;
    
    delay_init();       /* 更新系统时钟 */
    MSS_WD_disable();
    
    MSS_GPIO_init();
    
    /* GPIO_0 & GPIO_1 配置成输出模式 */
    MSS_GPIO_config(MSS_GPIO_0, MSS_GPIO_OUTPUT_MODE);
    MSS_GPIO_config(MSS_GPIO_1, MSS_GPIO_OUTPUT_MODE);
    
    /* GPIO_2配置成输入模式 */
    MSS_GPIO_config(MSS_GPIO_2, MSS_GPIO_INPUT_MODE);
    
    /* TIM64配置成周期中断,中断时间250ms */
    MSS_TIM64_init(MSS_TIMER_PERIODIC_MODE);
    MSS_TIM64_load_immediate(0, SystemCoreClock/4);
    MSS_TIM64_start();
    MSS_TIM64_enable_irq();
    
    while(1)
    {
        key = MSS_IO_IN(2);
        
        if(key == 1)    /* 按键按下暂停 */
        {
            MSS_TIM64_stop();
            while(MSS_IO_IN(2) == 1);     /* 等待释放 */
            MSS_TIM64_start();  /* 释放继续计时 */
        }
    }
}

/* TIM64与TIM1共用一个中断服务函数 */
void Timer1_IRQHandler(void)
{
    static uint8_t status = 0;
    
    status = !status;
    MSS_IO_OUT(1) = status;

    MSS_TIM64_clear_irq();
}
6.单次中断模式

使用ONE_SHOT模式,可以配置只产生一次溢出中断。按键每按下启动一次定时器,产生一次中断,4s之后LED状态翻转,即按键控制LED时,延时4s。

#include "main.h"

int main()
{
    uint8_t key;
    
    delay_init();       /* 更新系统时钟 */
    MSS_WD_disable();
    
    MSS_GPIO_init();
    /* GPIO_0 & GPIO_1 配置成输出模式 */
    MSS_GPIO_config(MSS_GPIO_0, MSS_GPIO_OUTPUT_MODE);
    MSS_GPIO_config(MSS_GPIO_1, MSS_GPIO_OUTPUT_MODE);
    
    /* GPIO_2配置成输入模式 */
    MSS_GPIO_config(MSS_GPIO_2, MSS_GPIO_INPUT_MODE);
    
    /* TIM1配置成单次中断模式 */
    MSS_TIM1_init(MSS_TIMER_ONE_SHOT_MODE);

    while(1)
    {
        key = MSS_IO_IN(2);
        
        if(key == 1)    /* 按键按下中断一次 */
        {
            MSS_TIM1_load_immediate(SystemCoreClock*4);
            MSS_TIM1_enable_irq();
            MSS_TIM1_start();
            while(MSS_IO_IN(2) == 1);   /* 等待释放 */
        }
    }
}

/* TIM1中断服务函数 */
void Timer1_IRQHandler(void)
{
    static uint8_t status = 0;
    
    status = !status;
    MSS_IO_OUT(1) = status;

    MSS_TIM1_clear_irq();
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
SmartFusion是一款集成了FPGAARM处理器的可编程逻辑器件。在使用SmartFusion进行FPGAARM的衔接过程中,首先我们可以通过MSS(Microcontroller Subsystem)模块的GPIO(General Purpose Input/Output)功能来实现点灯。 MSSSmartFusion芯片中的一个微控制器子系统,它包含了ARM Cortex-M3处理器以及与之相关的外设。GPIO是MSS提供的一种功能,它允许我们通过配置相关引脚的输入输出状态来进行数字信号的输入输出。 在使用MSS_GPIO点灯的过程中,首先我们需要使用SmartFusion的设计工具进行硬件电路的设计。接着,我们需要在软件开发环境中编写ARM处理器的代码来控制MSS_GPIO。 在代码中,我们需要进行以下步骤来实现点灯功能: 1. 配置MSS_GPIO控制的引脚作为输出引脚。我们可以通过设置相应的寄存器来实现这一步骤。例如,我们可以将寄存器的特定位设置为1来将某个引脚设置为输出模式。 2. 设置输出引脚的电平状态。通过编写相应的代码,我们可以将输出引脚的电平配置为高电平或低电平。这将决定LED是否点亮。 3. 可以加入延时函数来控制点亮和熄灭的时间间隔,以及闪烁的频率。 以上就是使用SmartFusionMSS_GPIO模块实现点灯的简要过程。通过编写ARM处理器的代码,配置相关的寄存器,我们可以通过控制MSS_GPIO模块的引脚状态来实现LED的点亮和熄灭。这个简单的示例展示了SmartFusion芯片中FPGAARM之间的协同工作能力,为我们实现更复杂的功能提供了基础。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值