单片机GD32F303RCT6 (Macos环境)开发 (三十二)—— GD32 SPI主从实验 中断模式

news2024/12/29 9:52:22

GD32 SPI主从实验 中断模式

1、接线

  SPI0 PA4  PA5   PA6   PA7
  SPI1 PB12 PB14  PB14  PB15
  采用全双工模式
              SPI0               SPI1
      CS      PA4----------------PB12
      CLK	  PA5----------------PB13
      MISO    PA6----------------PB14
      MOSI    PA7----------------PB15

2、spi0 主设备设置

主设备还是采用轮询方式去发送数据,本来想在从设备中断中收到数据立即用从设备返回一个数据,但是后来发现,主设备在收数据的时候总是错开一个,第一次收到的数据为0 ,第二次才能收到正常的数据,不知道为什么。

void spi_master_slave_fullduplex_poll(void)
{
    uint8_t master_tx_buf[16] = {0};
    uint8_t master_rx_buf[16] = {0};
    uint8_t slave_tx_buf[16] = {0};
    uint8_t slave_rx_buf[16] = {0};
    
    for(uint8_t i = 0; i < 16; ++i)
    {
        master_tx_buf[i] = 0x20 + i;
        slave_tx_buf[i] = 0x10 + i;
    }
    
    printf("Master have sended : ");
    for(uint8_t i = 0; i < 16; ++i)
    {
        printf("%x ", master_tx_buf[i]);
    }
    printf("\r\n");
    
    for(uint8_t i = 0; i < 16; ++i)
    {
        while(RESET == spi_i2s_flag_get(SPI0, SPI_FLAG_TBE));
        spi_i2s_data_transmit(SPI0, master_tx_buf[i]);
        while(RESET == spi_i2s_flag_get(SPI0, SPI_FLAG_RBNE));
        master_rx_buf[i] = spi_i2s_data_receive(SPI0);
    }
    
    printf("Master received  : ");
    for(uint8_t i = 0; i < 16; ++i)
    {
        printf("%x ", master_rx_buf[i]);
    }
    printf("\r\n");
    
}

发送读取数据函数。

void spi_master_slave_fullduplex_poll(void)
{
    uint8_t master_tx_buf[16] = {0};
    uint8_t master_rx_buf[16] = {0};
    uint8_t slave_tx_buf[16] = {0};
    uint8_t slave_rx_buf[16] = {0};
    
    for(uint8_t i = 0; i < 16; ++i)
    {
        master_tx_buf[i] = 0x20 + i;
        slave_tx_buf[i] = 0x10 + i;
    }
    
    printf("Master have sended : ");
    for(uint8_t i = 0; i < 16; ++i)
    {
        printf("%x ", master_tx_buf[i]);
    }
    printf("\r\n");
    
    for(uint8_t i = 0; i < 16; ++i)
    {
        while(RESET == spi_i2s_flag_get(SPI0, SPI_FLAG_TBE));
        spi_i2s_data_transmit(SPI0, master_tx_buf[i]);
        while(RESET == spi_i2s_flag_get(SPI0, SPI_FLAG_RBNE));
        master_rx_buf[i] = spi_i2s_data_receive(SPI0);
    }
    
    printf("Master received  : ");
    for(uint8_t i = 0; i < 16; ++i)
    {
        printf("%x ", master_rx_buf[i]);
    }
    printf("\r\n");
    
}

3、SPI1从设备设置

从设备采用中断方式去接收数据。

void spi1_slave_config(void)
{
    spi_parameter_struct spi_init_struct;

    rcu_periph_clock_enable(RCU_GPIOB);
    rcu_periph_clock_enable(RCU_SPI1);
    rcu_periph_clock_enable(RCU_AF);

    /* SPI1 GPIO config:SCK/PB13, MISO/PB14, MOSI/PB15 */
    gpio_init(GPIOB, GPIO_MODE_IN_FLOATING, GPIO_OSPEED_50MHZ, GPIO_PIN_13 | GPIO_PIN_15);
    gpio_init(GPIOB, GPIO_MODE_AF_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_14);
    /* PB12 as NSS */
    gpio_init(GPIOB, GPIO_MODE_IN_FLOATING, GPIO_OSPEED_50MHZ, GPIO_PIN_12);

    /* SPI1 parameter config */
    spi_init_struct.trans_mode           = SPI_TRANSMODE_FULLDUPLEX;
    spi_init_struct.device_mode          = SPI_SLAVE;
    spi_init_struct.frame_size           = SPI_FRAMESIZE_8BIT;
    spi_init_struct.clock_polarity_phase = SPI_CK_PL_LOW_PH_1EDGE;
    spi_init_struct.nss                  = SPI_NSS_HARD;
    spi_init_struct.prescale             = SPI_PSC_16; //速率
    spi_init_struct.endian               = SPI_ENDIAN_MSB;
    spi_init(SPI1, &spi_init_struct);

    nvic_irq_enable(SPI1_IRQn,2,0);
    /* SPI int enable */
    //spi_i2s_interrupt_enable(SPI1, SPI_I2S_INT_TBE);
    spi_i2s_interrupt_enable(SPI1, SPI_I2S_INT_RBNE);
    spi_enable(SPI1);
}

中断处理函数:

#if SPI_MODE == SPI_MASTER_SLAVE_MODE_INT
uint8_t spi1_receive_array[128] = {0};
uint8_t receive_n = 0;
uint8_t slave_tx_buf[16] = {0x90,0x98,0x99,0x10,0x12,0x4,0x5,0x6,0x7,0x8,0x3,0x2,0x4,0x5,0x1,0x3};
uint8_t tx_n = 0;


void SPI1_IRQHandler(void)
{
    /* receive data */
    if(RESET != spi_i2s_interrupt_flag_get(SPI1,SPI_I2S_INT_FLAG_RBNE)) 
    {
        spi1_receive_array[receive_n++] = spi_i2s_data_receive(SPI1);

        while(RESET == spi_i2s_flag_get(SPI1, SPI_FLAG_TBE));
	    spi_i2s_data_transmit(SPI1, slave_tx_buf[tx_n++]);
        if (receive_n == 16)
        {  
            handle_spi1_message(spi1_receive_array,16);
            receive_n = 0;
        }
    }
}
#endif

中断处理函数每收到一个数据就回跑一次,按理说我收一个发一个,数据spi0收到的数据也应该是对的,但是实验发现,总是差一个数据。

4、 实验结果

在这里插入图片描述
master received 第一个数据应该为0x90,但是这里每次都是0x00,不晓得什么原因。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/599852.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

chatgpt赋能python:Python简单游戏开发入门

Python简单游戏开发入门 Python作为一门流行的编程语言&#xff0c;可以用来开发各种各样的应用&#xff0c;包括游戏。虽然Python不是游戏开发的主流语言&#xff0c;但我们可以用它来制作一些简单而有趣的游戏。在这篇文章中&#xff0c;我们将介绍如何用Python创建一个简单…

批量剪辑视频工具源码开发搭建分享

搭建步骤 1. 首先需要根据自身产品确定视频类型及需要实现的视频效果 2. 根据预期视频效果选择视频上传模式&#xff0c;并将视频素材进行上传 3. 添加音频、字幕&#xff0c;标题等与素材进行组合。 4. 设置投放计划&#xff0c;包括&#xff1a;视频标题、视频话题等 5.…

Are Emergent Abilities of Large Language Models a Mirage?

Paper name Are Emergent Abilities of Large Language Models a Mirage? Paper Reading Note Paper URL: https://arxiv.org/pdf/2304.15004.pdf Video URL: https://www.youtube.com/watch?vhZspGdApDIo TL;DR 2023 年斯坦福的研究&#xff0c;探索大语言模型表现出涌…

LeetCode 1552. Magnetic Force Between Two Balls【二分,排序,贪心】中等

本文属于「征服LeetCode」系列文章之一&#xff0c;这一系列正式开始于2021/08/12。由于LeetCode上部分题目有锁&#xff0c;本系列将至少持续到刷完所有无锁题之日为止&#xff1b;由于LeetCode还在不断地创建新题&#xff0c;本系列的终止日期可能是永远。在这一系列刷题文章…

内存栈与CPU栈机制

1. 内存栈: 先入后出,LIFO(LAST IN FIRST OUT) 入栈:将一个新的元素放到栈顶 出栈:从栈顶取出一个元素 栈顶元素总是最后一个入栈,需要时出栈. 2.CPU栈机制 8086CPU提供相关指令以栈方式来访问内存空间.相当于将一段内存当做栈来使用 8086CPU提供的入栈指令为:PUSH ,出栈指令为…

【Linux】序列化和反序列化

目录 &#x1f308;前言&#x1f338;1、应用层&#x1f33a;2、重谈协议&#x1f341;3、网络计算器&#x1f361;3.1、定制协议&#x1f362;3.2、样例代码 &#x1f308;前言 这篇文章给大家带来序列化和反序列化的学习&#xff01;&#xff01;&#xff01; &#x1f338;…

chatgpt赋能python:Python倒序for:如何优化循环遍历

Python倒序for&#xff1a;如何优化循环遍历 Python作为一门高级编程语言&#xff0c;一直以来都在开发者中得到广泛的应用。在日常的编程工作中&#xff0c;遍历列表&#xff08;List&#xff09;和元组&#xff08;Tuple&#xff09;是很常见的操作。而对于列表或元组的倒序…

NLP(五十四)tiktoken的使用

tiktoken是OpenAI于近期开源的Python第三方模块&#xff0c;该模块主要实现了tokenizer的BPE&#xff08;Byte pair encoding&#xff09;算法&#xff0c;并对运行性能做了极大的优化。本文将介绍tiktoken模块的使用。 tiktoken简介 BPE(Byte pair encoding)算法是NLP中常见的…

Redis系列---Redis网络模型1

我们都知道&#xff0c;redis的高性能是具有多方面的因数&#xff0c;如&#xff1a;运行在内存上&#xff0c;单线程命令&#xff0c;io多路复用技术等&#xff0c;对于redis高性能的探究&#xff0c;就需要深入的研究其工作原理&#xff0c;这就涉及到redis的网络模型了&…

python实现单链表、双链表、反转链表(二)

一、链表概述 链表是有元素组成的数据结构&#xff0c;每个元素都是单独对象&#xff0c;包含数据和指针信息 链表中的每个元素称为节点&#xff0c;如下所示&#xff0c;第一个节点称为Head(头节点)&#xff0c;为链表的入口点&#xff0c;如果链表为空&#xff0c;则Head指…

Vue.js 比较重要知识点总结二

概述 vue3 组合式API生命周期钩子函数有变化吗&#xff1f;Composition API 与 Options API 有什么区别&#xff1f;watch 和 watchEffect 的区别&#xff1f;vue2 如何升级到 vue3 ? vue3 组合式API生命周期钩子函数有变化吗&#xff1f; 选项式API 和 组合式API 生命周期…

Java的继承性

1.为什么要有类的继承性&#xff1f;(继承性的好处&#xff09; ① 减少了代码的冗余&#xff0c;提高了代码的复用性② 便于功能的扩展③ 为之后多态性的使用&#xff0c;提供了前提 2.子类继承父类以后有哪些不同&#xff1f; 2.1体现&#xff1a; 一旦子类A继承父类B以…

汇编基础学习

1. 利用ldr向寄存器里面写较大数据&#xff0c;和设置寄存器的某些位 2. 这个lable 不对呢 验证宏值加载到寄存器里是正确的。 pc 的地址是0x80594 当前pc指针加上宏定义值的地址值。 3 打印字符串 字符串加载了8个字节到寄存器里面&#xff0c; 如何调试打印出来呢&#xff1…

数据库设计的原则有哪些

数据库设计是程序开发的核心部分&#xff0c;标准的数据库设计原则和步骤能有效提高开发进度和效率。 数据库设计(Database Design)是指对于一个给定的应用环境&#xff0c;构造最优的数据库模式&#xff0c;建立数据库及其应用系统&#xff0c;使之能够有效地存储数据&#xf…

RK3588平台开发系列讲解(驱动基础篇)中断相关函数

平台内核版本安卓版本RK3588Linux 5.10Android 12文章目录 一、获取中断号相关函数二、申请中断函数三、free_irq 函数四、中断处理函数五、中断使能和禁止函数沉淀、分享、成长,让自己和他人都能有所收获!😄 📢 Linux 中断有专门的中断子系统,其实现原理很复杂,但是驱…

Git详解——安装、使用、搭建、IDEA集成

Git 看目录&#xff0c;越往后面越重要 目录一、git是什么&#xff1f;二、为什么要使用Git&#xff1f;三、版本控制工具四、git下载安装以及环境配置五、git基本命令六、git项目搭建七、远程仓库怎么搞&#xff1f;git,gitlab,github,gitee区别八、idea集成Git 一、Git是什…

HBase2.2.2安装(单机、伪分布)

系列文章目录 Ubuntu常见基本问题 Hadoop3.1.3安装&#xff08;单机、伪分布&#xff09; Hadoop集群搭建 HBase2.2.2安装&#xff08;单机、伪分布&#xff09; Zookeeper集群搭建 文章目录 系列文章目录前置条件一、HBase2.2.2安装二、配置环境变量1、问题 三、单机模式1、修…

浅谈数字化

一、数字化转型 数字化转型&#xff08;Digital transformation&#xff09;是建立在数字化转换&#xff08;Digitization&#xff09;、数字化升级&#xff08;Digitalization&#xff09;基础上&#xff0c;进一步触及公司核心业务&#xff0c;以新建一种商业模式为目标的高…

仙人掌之歌——权力的游戏(3)

像疯子一样死去 陈速没想到李通是在香山深处一所疗养院里休养&#xff0c;军方的岗位森严&#xff0c;进去还得把身份证押在门卫室。李通穿着病号服悠哉地晃过来把陈速领了进去。 “通哥&#xff0c;这儿真是个好地方啊。” 陈速由衷地赞叹着&#xff0c;望着大院里古树参天&…

九、Spring Cloud—gateway网关

一、引言 每个微服务都需和前端进行通信&#xff0c;解决每个微服务请求时的鉴权、限流、权限校验、跨域等逻辑&#xff0c;放在一个统一的地方进行使用。 在微服务架构中&#xff0c;网关是一个重要的组件&#xff0c;它作为系统的入口&#xff0c;负责接收所有的客户端请求…