Cosmos-Reason1-7B部署教程:国产统信UOS+海光DCU GPU兼容性适配记录

核心内容摘要

飞跨电容型NPC逆变器仿真(SPWM) 仿真包含FCNPC拓扑、LCL滤波器、三相纯阻性负载构...
C++二分细节敲定规则

5大突破重构华硕笔记本控制体验:G-Helper轻量工具全维度性能调校指南

代码说明该I2C驱动实现了完整的硬件I2C配置包括GPIO引脚设置、时钟配置和模式配置包含全面的异常处理机制能够检测和处理超时、NACK、总线忙、仲裁丢失等异常情况提供了多种I2C操作函数包括单字节读写和多字节读写操作实现了超时检测机制防止程序在异常情况下无限等待主函数中包含了完整的测试流程通过LED指示不同的通信状态代码模块化设计将I2C驱动分为头文件和实现文件便于维护和复用//i2c_deriver.h #ifndef __I2C_DRIVER_H #define __I2C_DRIVER_H #include gd32f10x.h // I2C配置参数 #define I2C_PERIPH I2C0 #define I2C_SPEED 100000 #define I2C_SCL_PIN GPIO_PIN_6 #define I2C_SDA_PIN GPIO_PIN_7 #define I2C_GPIO_PORT GPIOB #define I2C_TIMEOUT 0xFFFFF // I2C状态码定义 typedef enum { I2C_OK 0, I2C_ERROR_TIMEOUT, I2C_ERROR_NACK, I2C_ERROR_BUS_BUSY, I2C_ERROR_ARBITRATION_LOST, I2C_ERROR_UNKNOWN } i2c_status_t; // 函数声明 i2c_status_t i2c_master_init(void); i2c_status_t i2c_master_write(uint8_t device_addr, uint8_t reg_addr, uint8_t *data, uint16_t length); i2c_status_t i2c_master_read(uint8_t device_addr, uint8_t reg_addr, uint8_t *data, uint16_t length); i2c_status_t i2c_master_write_byte(uint8_t device_addr, uint8_t data); i2c_status_t i2c_master_read_byte(uint8_t device_addr, uint8_t *data); void i2c_deinit(void); #endif /* __I2C_DRIVER_H *///i2c_driver.c #include i2c_driver.h /** * brief I2C超时检查函数 * param flag: 要检查的标志位 * param timeout: 超时计数 * return i2c_status_t: 操作状态 */ static i2c_status_t i2c_wait_flag_timeout(uint32_t flag, uint32_t timeout) { while(!i2c_flag_get(I2C_PERIPH, flag)) { if((timeout--)

{ return I2C_ERROR_TIMEOUT; } } return I2C_OK; } /** * brief I2C主模式初始化 * return i2c_status_t: 初始化状态 */ i2c_status_t i2c_master_init(void) { uint32_t timeout I2C_TIMEOUT; // 使能GPIO和I2C时钟 rcu_periph_clock_enable(RCU_GPIOB); rcu_periph_clock_enable(RCU_I2C

; // 配置I2C引脚 gpio_init(I2C_GPIO_PORT, GPIO_MODE_AF_OD, GPIO_OSPEED_50MHZ, I2C_SCL_PIN); gpio_init(I2C_GPIO_PORT, GPIO_MODE_AF_OD, GPIO_OSPEED_50MHZ, I2C_SDA_PIN); // 复位I2C i2c_deinit(I2C_PERIPH); // 配置I2C参数 i2c_clock_config(I2C_PERIPH, I2C_SPEED, I2C_DTCY_

; i2c_mode_addr_config(I2C_PERIPH, I2C_I2CMODE_ENABLE, I2C_ADDFORMAT_7BITS, 0x

; i2c_ack_config(I2C_PERIPH, I2C_ACK_ENABLE); // 使能I2C i2c_enable(I2C_PERIPH); // 等待I2C就绪 while(!i2c_flag_get(I2C_PERIPH, I2C_FLAG_I2CBSY)) { if((timeout--)

{ return I2C_ERROR_TIMEOUT; } } return I2C_OK; } /** * brief I2C主发送数据 * param device_addr: 设备地址 * param reg_addr: 寄存器地址 * param data: 数据指针 * param length: 数据长度 * return i2c_status_t: 发送状态 */ i2c_status_t i2c_master_write(uint8_t device_addr, uint8_t reg_addr, uint8_t *data, uint16_t length) { i2c_status_t status; uint32_t timeout I2C_TIMEOUT; // 检查总线是否空闲 if(i2c_flag_get(I2C_PERIPH, I2C_FLAG_I2CBSY)) { return I2C_ERROR_BUS_BUSY; } // 发送起始信号 i2c_start_on_bus(I2C_PERIPH); status i2c_wait_flag_timeout(I2C_FLAG_SBSEND, timeout); if(status ! I2C_OK) return status; // 发送设备地址(写) i2c_master_addressing(I2C_PERIPH, device_addr, I2C_TRANSMITTER); status i2c_wait_flag_timeout(I2C_FLAG_ADDSEND, timeout); if(status ! I2C_OK) { // 检查是否收到NACK if(i2c_flag_get(I2C_PERIPH, I2C_FLAG_AERR)) { i2c_flag_clear(I2C_PERIPH, I2C_FLAG_AERR); return I2C_ERROR_NACK; } return status; } i2c_flag_clear(I2C_PERIPH, I2C_FLAG_ADDSEND); // 发送寄存器地址 status i2c_wait_flag_timeout(I2C_FLAG_TBE, timeout); if(status ! I2C_OK) return status; i2c_data_transmit(I2C_PERIPH, reg_addr); status i2c_wait_flag_timeout(I2C_FLAG_BTC, timeout); if(status ! I2C_OK) return status; // 发送数据 for(uint16_t i 0; i length; i) { status i2c_wait_flag_timeout(I2C_FLAG_TBE, timeout); if(status ! I2C_OK) return status; i2c_data_transmit(I2C_PERIPH, data[i]); status i2c_wait_flag_timeout(I2C_FLAG_BTC, timeout); if(status ! I2C_OK) return status; } // 发送停止信号 i2c_stop_on_bus(I2C_PERIPH); // 等待停止信号完成 timeout I2C_TIMEOUT; while(I2C_CTL0(I2C_PERIPH) 0x

{ if((timeout--)

{ return I2C_ERROR_TIMEOUT; } } return I2C_OK; } /** * brief I2C主接收数据 * param device_addr: 设备地址 * param reg_addr: 寄存器地址 * param data: 数据指针 * param length: 数据长度 * return i2c_status_t: 接收状态 */ i2c_status_t i2c_master_read(uint8_t device_addr, uint8_t reg_addr, uint8_t *data, uint16_t length) { i2c_status_t status; uint32_t timeout I2C_TIMEOUT; // 检查总线是否空闲 if(i2c_flag_get(I2C_PERIPH, I2C_FLAG_I2CBSY)) { return I2C_ERROR_BUS_BUSY; } // 第一阶段发送寄存器地址 // 发送起始信号 i2c_start_on_bus(I2C_PERIPH); status i2c_wait_flag_timeout(I2C_FLAG_SBSEND, timeout); if(status ! I2C_OK) return status; // 发送设备地址(写) i2c_master_addressing(I2C_PERIPH, device_addr, I2C_TRANSMITTER); status i2c_wait_flag_timeout(I2C_FLAG_ADDSEND, timeout); if(status ! I2C_OK) { if(i2c_flag_get(I2C_PERIPH, I2C_FLAG_AERR)) { i2c_flag_clear(I2C_PERIPH, I2C_FLAG_AERR); return I2C_ERROR_NACK; } return status; } i2c_flag_clear(I2C_PERIPH, I2C_FLAG_ADDSEND); // 发送寄存器地址 status i2c_wait_flag_timeout(I2C_FLAG_TBE, timeout); if(status ! I2C_OK) return status; i2c_data_transmit(I2C_PERIPH, reg_addr); status i2c_wait_flag_timeout(I2C_FLAG_BTC, timeout); if(status ! I2C_OK) return status; // 第二阶段读取数据 // 发送重复起始信号 i2c_start_on_bus(I2C_PERIPH); status i2c_wait_flag_timeout(I2C_FLAG_SBSEND, timeout); if(status ! I2C_OK) return status; // 发送设备地址(读) i2c_master_addressing(I2C_PERIPH, device_addr, I2C_RECEIVER); status i2c_wait_flag_timeout(I2C_FLAG_ADDSEND, timeout); if(status ! I2C_OK) { if(i2c_flag_get(I2C_PERIPH, I2C_FLAG_AERR)) { i2c_flag_clear(I2C_PERIPH, I2C_FLAG_AERR); return I2C_ERROR_NACK; } return status; } i2c_flag_clear(I2C_PERIPH, I2C_FLAG_ADDSEND); // 接收数据 for(uint16_t i 0; i length; i) { // 最后一个字节前关闭ACK if(i (length -

) { i2c_ack_config(I2C_PERIPH, I2C_ACK_DISABLE); } status i2c_wait_flag_timeout(I2C_FLAG_RBNE, timeout); if(status ! I2C_OK) return status; data[i] i2c_data_receive(I2C_PERIPH); } // 重新使能ACK i2c_ack_config(I2C_PERIPH, I2C_ACK_ENABLE); // 发送停止信号 i2c_stop_on_bus(I2C_PERIPH); // 等待停止信号完成 timeout I2C_TIMEOUT; while(I2C_CTL0(I2C_PERIPH) 0x

{ if((timeout--)

{ return I2C_ERROR_TIMEOUT; } } return I2C_OK; } /** * brief I2C主发送单字节数据 * param device_addr: 设备地址 * param data: 数据 * return i2c_status_t: 发送状态 */ i2c_status_t i2c_master_write_byte(uint8_t device_addr, uint8_t data) { return i2c_master_write(device_addr, 0x00, data,

; } /** * brief I2C主接收单字节数据 * param device_addr: 设备地址 * param data: 数据指针 * return i2c_status_t: 接收状态 */ i2c_status_t i2c_master_read_byte(uint8_t device_addr, uint8_t *data) { return i2c_master_read(device_addr, 0x00, data,

; } /** * brief I2C去初始化 */ void i2c_deinit(void) { i2c_disable(I2C_PERIPH); rcu_periph_clock_disable(RCU_I2C

; }//main.c #include i2c_driver.h /** * brief I2C超时检查函数 * param flag: 要检查的标志位 * param timeout: 超时计数 * return i2c_status_t: 操作状态 */ static i2c_status_t i2c_wait_flag_timeout(uint32_t flag, uint32_t timeout) { while(!i2c_flag_get(I2C_PERIPH, flag)) { if((timeout--)

{ return I2C_ERROR_TIMEOUT; } } return I2C_OK; } /** * brief I2C主模式初始化 * return i2c_status_t: 初始化状态 */ i2c_status_t i2c_master_init(void) { uint32_t timeout I2C_TIMEOUT; // 使能GPIO和I2C时钟 rcu_periph_clock_enable(RCU_GPIOB); rcu_periph_clock_enable(RCU_I2C

; // 配置I2C引脚 gpio_init(I2C_GPIO_PORT, GPIO_MODE_AF_OD, GPIO_OSPEED_50MHZ, I2C_SCL_PIN); gpio_init(I2C_GPIO_PORT, GPIO_MODE_AF_OD, GPIO_OSPEED_50MHZ, I2C_SDA_PIN); // 复位I2C i2c_deinit(I2C_PERIPH); // 配置I2C参数 i2c_clock_config(I2C_PERIPH, I2C_SPEED, I2C_DTCY_

; i2c_mode_addr_config(I2C_PERIPH, I2C_I2CMODE_ENABLE, I2C_ADDFORMAT_7BITS, 0x

; i2c_ack_config(I2C_PERIPH, I2C_ACK_ENABLE); // 使能I2C i2c_enable(I2C_PERIPH); // 等待I2C就绪 while(!i2c_flag_get(I2C_PERIPH, I2C_FLAG_I2CBSY)) { if((timeout--)

{ return I2C_ERROR_TIMEOUT; } } return I2C_OK; } /** * brief I2C主发送数据 * param device_addr: 设备地址 * param reg_addr: 寄存器地址 * param data: 数据指针 * param length: 数据长度 * return i2c_status_t: 发送状态 */ i2c_status_t i2c_master_write(uint8_t device_addr, uint8_t reg_addr, uint8_t *data, uint16_t length) { i2c_status_t status; uint32_t timeout I2C_TIMEOUT; // 检查总线是否空闲 if(i2c_flag_get(I2C_PERIPH, I2C_FLAG_I2CBSY)) { return I2C_ERROR_BUS_BUSY; } // 发送起始信号 i2c_start_on_bus(I2C_PERIPH); status i2c_wait_flag_timeout(I2C_FLAG_SBSEND, timeout); if(status ! I2C_OK) return status; // 发送设备地址(写) i2c_master_addressing(I2C_PERIPH, device_addr, I2C_TRANSMITTER); status i2c_wait_flag_timeout(I2C_FLAG_ADDSEND, timeout); if(status ! I2C_OK) { // 检查是否收到NACK if(i2c_flag_get(I2C_PERIPH, I2C_FLAG_AERR)) { i2c_flag_clear(I2C_PERIPH, I2C_FLAG_AERR); return I2C_ERROR_NACK; } return status; } i2c_flag_clear(I2C_PERIPH, I2C_FLAG_ADDSEND); // 发送寄存器地址 status i2c_wait_flag_timeout(I2C_FLAG_TBE, timeout); if(status ! I2C_OK) return status; i2c_data_transmit(I2C_PERIPH, reg_addr); status i2c_wait_flag_timeout(I2C_FLAG_BTC, timeout); if(status ! I2C_OK) return status; // 发送数据 for(uint16_t i 0; i length; i) { status i2c_wait_flag_timeout(I2C_FLAG_TBE, timeout); if(status ! I2C_OK) return status; i2c_data_transmit(I2C_PERIPH, data[i]); status i2c_wait_flag_timeout(I2C_FLAG_BTC, timeout); if(status ! I2C_OK) return status; } // 发送停止信号 i2c_stop_on_bus(I2C_PERIPH); // 等待停止信号完成 timeout I2C_TIMEOUT; while(I2C_CTL0(I2C_PERIPH) 0x

{ if((timeout--)

{ return I2C_ERROR_TIMEOUT; } } return I2C_OK; } /** * brief I2C主接收数据 * param device_addr: 设备地址 * param reg_addr: 寄存器地址 * param data: 数据指针 * param length: 数据长度 * return i2c_status_t: 接收状态 */ i2c_status_t i2c_master_read(uint8_t device_addr, uint8_t reg_addr, uint8_t *data, uint16_t length) { i2c_status_t status; uint32_t timeout I2C_TIMEOUT; // 检查总线是否空闲 if(i2c_flag_get(I2C_PERIPH, I2C_FLAG_I2CBSY)) { return I2C_ERROR_BUS_BUSY; } // 第一阶段发送寄存器地址 // 发送起始信号 i2c_start_on_bus(I2C_PERIPH); status i2c_wait_flag_timeout(I2C_FLAG_SBSEND, timeout); if(status ! I2C_OK) return status; // 发送设备地址(写) i2c_master_addressing(I2C_PERIPH, device_addr, I2C_TRANSMITTER); status i2c_wait_flag_timeout(I2C_FLAG_ADDSEND, timeout); if(status ! I2C_OK) { if(i2c_flag_get(I2C_PERIPH, I2C_FLAG_AERR)) { i2c_flag_clear(I2C_PERIPH, I2C_FLAG_AERR); return I2C_ERROR_NACK; } return status; } i2c_flag_clear(I2C_PERIPH, I2C_FLAG_ADDSEND); // 发送寄存器地址 status i2c_wait_flag_timeout(I2C_FLAG_TBE, timeout); if(status ! I2C_OK) return status; i2c_data_transmit(I2C_PERIPH, reg_addr); status i2c_wait_flag_timeout(I2C_FLAG_BTC, timeout); if(status ! I2C_OK) return status; // 第二阶段读取数据 // 发送重复起始信号 i2c_start_on_bus(I2C_PERIPH); status i2c_wait_flag_timeout(I2C_FLAG_SBSEND, timeout); if(status ! I2C_OK) return status; // 发送设备地址(读) i2c_master_addressing(I2C_PERIPH, device_addr, I2C_RECEIVER); status i2c_wait_flag_timeout(I2C_FLAG_ADDSEND, timeout); if(status ! I2C_OK) { if(i2c_flag_get(I2C_PERIPH, I2C_FLAG_AERR)) { i2c_flag_clear(I2C_PERIPH, I2C_FLAG_AERR); return I2C_ERROR_NACK; } return status; } i2c_flag_clear(I2C_PERIPH, I2C_FLAG_ADDSEND); // 接收数据 for(uint16_t i 0; i length; i) { // 最后一个字节前关闭ACK if(i (length -

) { i2c_ack_config(I2C_PERIPH, I2C_ACK_DISABLE); } status i2c_wait_flag_timeout(I2C_FLAG_RBNE, timeout); if(status ! I2C_OK) return status; data[i] i2c_data_receive(I2C_PERIPH); } // 重新使能ACK i2c_ack_config(I2C_PERIPH, I2C_ACK_ENABLE); // 发送停止信号 i2c_stop_on_bus(I2C_PERIPH); // 等待停止信号完成 timeout I2C_TIMEOUT; while(I2C_CTL0(I2C_PERIPH) 0x

{ if((timeout--)

{ return I2C_ERROR_TIMEOUT; } } return I2C_OK; } /** * brief I2C主发送单字节数据 * param device_addr: 设备地址 * param data: 数据 * return i2c_status_t: 发送状态 */ i2c_status_t i2c_master_write_byte(uint8_t device_addr, uint8_t data) { return i2c_master_write(device_addr, 0x00, data,

; } /** * brief I2C主接收单字节数据 * param device_addr: 设备地址 * param data: 数据指针 * return i2c_status_t: 接收状态 */ i2c_status_t i2c_master_read_byte(uint8_t device_addr, uint8_t *data) { return i2c_master_read(device_addr, 0x00, data,

; } /** * brief I2C去初始化 */ void i2c_deinit(void) { i2c_disable(I2C_PERIPH); rcu_periph_clock_disable(RCU_I2C

; }代码下载地址 https://gitee.com/gd_15/gd32f103_i2c_driver.git

荷花1777.tⅴknow2298下载-荷花1777.tⅴknow2298下载应用

百度百家号客服电话人工服务

123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123 123