riscv中gd32vf103的中断行为分析

发布者:温馨的家庭最新更新时间:2024-07-09 来源: elecfans关键字:gd32vf103  中断 手机看文章 扫描二维码
随时随地手机看文章

从riscv底层原理分析gd32vf103的中断行为

1.概述

2.中断向量表初始化

3.详细分析一下irq_entry

4.关于gd32vf103中断编程模型的理解

1.概述在处理riscv处理器中断的时候,需要弄清楚两个概念:

1.向量中断

2.非向量中断

对于向量中断,其中断发生后,pc指针会根据中断的类型跳转到基地址+中断号*4的地址处去执行中断处理程序,做过stm32的,应该比较清楚向量中断的大概样子。当然,riscv也是支持这种向量中断,这样每个地址处会安排一个特定的中断处理函数,当中断发生后,跳转到特定的函数去执行即可。

对于非向量中断,则表示中断发生后只有一个入口,需要在这一个中断中去判断具体中断号,这种行为可以在常见的mips处理器、sparc处理器中看到。

既然riscv支持这两种中断处理方式,正好gd32vf103的库函数也实现了这两种机制,那么就彻底的分析一下实现的策略。

2.中断向量表初始化任何代码在最初的汇编级别的初始化时,都会指定向量的基地址。当然riscv也不例外。

对于向量中断来说

/*

* Intialize ECLIC vector interrupt

* base address mtvt to vector_base

*/

la t0, vector_base

csrw CSR_MTVT, t0

这里的理解就向mtvt寄存器中存放vector_base,该处存放向量地址入口,每个向量中断发生,则根据偏移执行对应的函数。

.globl vector_base

.type vector_base, @object

vector_base:

#if defined(DOWNLOAD_MODE) && (DOWNLOAD_MODE != DOWNLOAD_MODE_FLASH)

j _start /* 0: Reserved, Jump to _start when reset for ILM/FlashXIP mode.*/

.align LOG_REGBYTES /* Need to align 4 byte for RV32, 8 Byte for RV64 */

#else

DECLARE_INT_HANDLER default_intexc_handler /* 0: Reserved, default handler for Flash download mode */

#endif

DECLARE_INT_HANDLER default_intexc_handler /* 1: Reserved */

DECLARE_INT_HANDLER default_intexc_handler /* 2: Reserved */

DECLARE_INT_HANDLER eclic_msip_handler /* 3: Machine software interrupt */

DECLARE_INT_HANDLER default_intexc_handler /* 4: Reserved */

DECLARE_INT_HANDLER default_intexc_handler /* 5: Reserved */

对于向量函数的处理,不用过多介绍。

下面非向量中断的入口

/*

* Set ECLIC non-vector entry to be controlled

* by mtvt2 CSR register.

* Intialize ECLIC non-vector interrupt

* base address mtvt2 to irq_entry.

*/

la t0, irq_entry

csrw CSR_MTVT2, t0

csrs CSR_MTVT2, 0x1

其中irq_entry表示了非向量的处理过程。csrs CSR_MTVT2, 0x1该指令的解析如下:

mtvt2[0] = 1 mtvt2[0]为0时,中断入口使用mtvec寄存器,mtvt2[0]为1时,中断入口为mtvt2[31:2]。

3.详细分析一下irq_entry分析非向量中断的行为,可以更好的理解riscv的中断底层的处理机制。

.global irq_entry

/* This label will be set to MTVT2 register */

irq_entry:

/* Save the caller saving registers (context) */

SAVE_CONTEXT

/* Save the necessary CSR registers */

SAVE_CSR_CONTEXT

/* This special CSR read/write operation, which is actually

* claim the CLIC to find its pending highest ID, if the ID

* is not 0, then automatically enable the mstatus.MIE, and

* jump to its vector-entry-label, and update the link register

*/

csrrw ra, CSR_JALMNXTI, ra

/* Critical section with interrupts disabled */

DISABLE_MIE

/* Restore the necessary CSR registers */

RESTORE_CSR_CONTEXT

/* Restore the caller saving registers (context) */

RESTORE_CONTEXT

/* Return to regular code */

mret

从中断处理的原理上来讲,中断处理分三部分:

1.保存当前现场

2.进入中断处理函数

3.恢复现场

其中SAVE_CONTEXT确实是保存上下文现场的方式。

.macro SAVE_CONTEXT

csrrw sp, CSR_MSCRATCHCSWL, sp

/* Allocate stack space for context saving */

#ifndef __riscv_32e

addi sp, sp, -20*REGBYTES

#else

addi sp, sp, -14*REGBYTES

#endif /* __riscv_32e */

STORE x1, 0*REGBYTES(sp)

STORE x4, 1*REGBYTES(sp)

STORE x5, 2*REGBYTES(sp)

STORE x6, 3*REGBYTES(sp)

STORE x7, 4*REGBYTES(sp)

STORE x10, 5*REGBYTES(sp)

STORE x11, 6*REGBYTES(sp)

STORE x12, 7*REGBYTES(sp)

STORE x13, 8*REGBYTES(sp)

STORE x14, 9*REGBYTES(sp)

STORE x15, 10*REGBYTES(sp)

#ifndef __riscv_32e

STORE x16, 14*REGBYTES(sp)

STORE x17, 15*REGBYTES(sp)

STORE x28, 16*REGBYTES(sp)

STORE x29, 17*REGBYTES(sp)

STORE x30, 18*REGBYTES(sp)

STORE x31, 19*REGBYTES(sp)

#endif /* __riscv_32e */

.endm

按照riscv的数据模型,又分为I数据模型和E数据模型,这部分在riscv的MISA寄存器中有描述。简而言之,E数据模型会比I数据模型少一半的寄存器,E数据模型是专门针对嵌入式应用场景的,更少的寄存器意味着更快速的压栈和出栈,实时性相应会更加优秀。

I数据模型一共有32个寄存器,而E数据模型是16个寄存器。

所以在进行中断入栈的时候,E数据模型会压入10个寄存器。

1e2c2764-9d0e-11eb-8b86-12bb97331649.png?imageView2/2/w/1000

caller代表中断上层函数可以使用的寄存器,所以

x1,x5,x6,x7,x10,x11,x12,x13,x14,x15

这10个寄存器会保存,上述程序多保存了x4。

下面理解一下中断的处理,通过csrrw ra, CSR_JALMNXTI, ra该指令进行分析。

不难发现,这个是个芯来自定义扩展指令,CSR_JALMNXTI寄存器通过gdb解析可以看到如下的数据

213dce62-9d0e-11eb-8b86-12bb97331649.png?imageView2/2/w/1000

其中0x7ed则是该寄存器的地址。

那么一条指令是如何实现中断的处理的呢?

实际上该指令首先会判断当前eclic中是否有挂起未处理的中断,如果没有,那这条指令向下执行,并不会处理任何事情,一旦存在,那么会跳转到eclic的中断向量的入口,这里便是关键的地方了。

另外需要注意的是,默认进入中断时,保存现场时,此处是关闭中断的,当执行这条语句,中断便会开启,然后判断是否还有中断未响应,这样可以达到中断咬尾的效果。

并且当中断处理函数执行完成后,又会回到该指令执行一次,判断是否还需要处理中断。这一切的行为都是由硬件完成,大大提高中断处理的效率。

现场恢复则是中断处理的逆过程,这里不赘述。

4.关于gd32vf103中断编程模型的理解对于cortex-m3等处理器来说,riscv的底层模型似乎更加复杂一些,但是实际上弄清楚riscv中断处理模型,eclic中断处理机制,以及向量中断,非向量中断和一条中断处理指令csrrw ra, CSR_JALMNXTI, ra后,也不会觉得十分的难以理解。

玩gd32vf103,其riscv底层汇编级别的中断处理一般都不会太多需要修改的,理解就可以。需要使用好的是eclic配置,还有相关的gpio的中断引脚的配置即可。将中断线、eclic配置完成,具体中断处理函数中实现自己的业务逻辑即可,不需要有许多学习成本。


关键字:gd32vf103  中断 引用地址:riscv中gd32vf103的中断行为分析

上一篇:IAP编程的流程及IAP的应用场所
下一篇:如何利用外部中断和定时器测量信号频率

推荐阅读最新更新时间:2026-03-20 10:36

riscvgd32vf103中断行为分析
从riscv底层原理分析gd32vf103的中断行为 1.概述 2.中断向量表初始化 3.详细分析一下irq_entry 4.关于gd32vf103中断编程模型的理解 1.概述在处理riscv处理器中断的时候,需要弄清楚两个概念: 1.向量中断 2.非向量中断 对于向量中断,其中断发生后,pc指针会根据中断的类型跳转到基地址+中断号*4的地址处去执行中断处理程序,做过stm32的,应该比较清楚向量中断的大概样子。当然,riscv也是支持这种向量中断,这样每个地址处会安排一个特定的中断处理函数,当中断发生后,跳转到特定的函数去执行即可。 对于非向量中断,则表示中断发生后只有一个入口,需要在这一个中断中去判断具体中断号,这种行为可以在
[单片机]
<font color='red'>riscv</font>中<font color='red'>gd32vf103</font>的<font color='red'>中断</font>行为分析
GD32VF103:采用RISC-V内核设计的MCU
GD32VF103 开发板 去年九月份的时候 RT-Thread 的 Andy Chen 组织定做了一块 GD32V 开发板,托 Andy 的福,我也搭车买了一块。 这块开发板小巧精美,供电、烧录、调试信息打印都是通过一个 Type-C USB 接口进行,更重要的是它所搭载的主控芯片 GD32VF103 是一颗采用 RISC-V 内核设计的 MCU,这对于对 RISC-V 感兴趣的同学来说,具有十足的吸引力。 GD32VF103 系列 SOC 是兆易创新与芯来科技合作,基于 RISC-V 架构设计的一款面向 IOT 领域的 MCU,主频最高 108 MHZ,根据定位差异,片内 Flash 16~128 KB,片上 SRAM 8
[单片机]
<font color='red'>GD32VF103</font>:采用RISC-V内核设计的MCU
ARM64硬件中断处理机制深度解析
一、先搞懂:什么是硬件中断? 你正在用刷视频,突然收到微信消息 —— 这就是生活中的 “ 中断 ” 。对 64 (手机、服务器、设备的核心)来说, 硬件中断是外设(如键盘、网卡、)向 发送的 “ 紧急请求 ” :比如网卡收到数据要处理、到点要触发任务、按键被按下要响应,这些都需要 CPU 暂停当前工作,优先处理紧急事务。 没有中断机制的话, CPU 只能 “ 轮询 ” 外设(挨个问 “ 有没有事? ” ),既浪费资源又反应迟钝。而中断就像 “ 快递敲门 ” , CPU 不用一直等,收到再
[嵌入式]
ARM64硬件<font color='red'>中断</font>处理机制深度解析
51单片机开发(五)--中断1
一、中断源 80C51单片机共有5个中断源,分为三类,外部中断,定时器中断和串口中断。 (1)外部中断2个,INT0和INT1,由外部引脚P3.2和P3.3输入 (2)定时器中断2个,T0和T1,当使用脉冲计数时,要由外部引脚P3.4和P3.5引入 (3)串口中断1个,RX/TX,由外部引脚P3.0和P3.1引入 二、中断系统结构 2.1中断允许寄存器(IE,可位寻址) 2.2中断优先级控制寄存器(IP,可位寻址) 2.3定时器/计数器0/1控制寄存器(TCON,可位寻址) 2.4串行口控制寄存器(SCON,可位寻址)
[单片机]
STM32定时器中断详解(HAL库实战讲解)
1、定时器简单介绍 以STM32F103C8T6中几个定时器为例: TIM1:这是一个高级定时器,不仅具备基本的定时中断功能,还拥有内外时钟源选择、输入捕获、输出比较、编码器接口以及主从触发模式等多种功能。这使得TIM1能够适用于各种复杂的应用场景,为开发者提供强大的时间控制和信号处理能力。 TIM2、TIM3和TIM4:这些是通用定时器,同样具有定时功能,但在功能上与高级定时器有所区别。通用定时器通常用于实现一些基本的定时任务,如LED闪烁、脉冲宽度测量等。 每个定时器都由一个**16位计数器、预分频器和自动重装寄存器的时基单元组成。**预分频器可以对时钟进行分频,计数器则对预分频后的时钟进行计数。当计数器的值达到设定值时,
[单片机]
STM32定时器<font color='red'>中断</font>详解(HAL库实战讲解)
STM32的EXTI外部中断踩坑经验分享
一、EXTI(Extern Interrupt)简介 1、中断系统 中断:在主程序运行过程中,出现了特定的中断触发条件(中断源),使得CPU暂停当前正在运行的程序,转而去处理中断程序,处理完成后又返回原来被暂停的位置继续运行 中断优先级:当有多个中断源同时申请中断时,CPU会根据中断源的轻重缓急进行裁决,优先响应更加紧急的中断源 中断嵌套:当一个中断程序正在运行时,又有新的更高优先级的中断源申请中断,CPU再次暂停当前中断程序,转而去处理新的中断程序,处理完成后依次进行返回 2、stm32中断 68个可屏蔽中断通道,包含EXTI、TIM、ADC、USART、SPI、I2C、RTC等多个外设(几乎所有外设都可以申请中断)
[单片机]
STM32的EXTI外部<font color='red'>中断</font>踩坑经验分享
STM32中DMA传输中断功能的关闭方法详解
一、为什么我们要关中断功能呢? 1.在撰写类似DMA相关串口传输程序时,我们会使用到队列指针的操作,而这个操作绝对不可以被任何行为打断,打断就寄。 2. 因此我们要在进行队列指针的数据处理时,将全局的中断全部关闭。(很快,就一瞬间开关一下) 3.举个例子: 例如在某一串口传输函数中,以下操作需原子性: ENTER_CRITICAL(); if (队列未满) { txHead = next_head; // 更新队列头 if (UART空闲) { 启动DMA发送(); // 更新txTail和isUART3Busy } } EXIT_CRITICAL(); 若此处不关闭中断,DMA完成回
[单片机]
STM32中DMA传输<font color='red'>中断</font>功能的关闭方法详解
51单片机笔记6 -- 中断1 寄存器、定时器
定时器与中断是整个单片机学习过程中比较重要的知识点,而且应用非常广泛,几乎可以说没有中断的程序都是新手练习用的。学习中断之前先了解一下寄存器这个概念,寄存器简单来说就是个宾馆,可以暂时存储一些数据,脉冲信号等等,在80C51中有一类寄存器叫做特殊功能寄存器,总共定义了21个,在80C52中又增加了5个,所以,80C52中总共有26个。今天讲一下里面几种常用的寄存器,第一个是TMOD寄存器,这个寄存器既可以做定时器也可以做计数器,总共有4中工作模式,前期用的比较多的是模式1,写成TMOD = 0X01;需要注意一下,这些寄存器的名称是不用定义的,也不可以更改。 选择模式的方法很简单,就是把M1,M0组合起来,图片已经给出,用到哪
[单片机]
小广播
最新单片机文章
何立民专栏 单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

厂商技术中心

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

 
机器人开发圈

电子工程世界版权所有 京ICP证060456号 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2026 EEWORLD.com.cn, Inc. All rights reserved