ZHDA282 September   2026 MSPM0G5117 , MSPM0G5187

 

  1.   1
  2. 1 说明
  3. 2 所需外设
  4. 3 兼容器件
  5. 4 设计步骤
  6. 5 设计注意事项
  7. 6 软件流程图
  8. 7 应用代码
  9. 8 数据流示例
  10. 9 其他资源
  11. 10商标

设计注意事项

  1. 缓冲区大小设置:USB_FRAME_PACKAGE 默认值为 64 字节,与 USB 全速模式的最大数据包大小相匹配。每个 FIFO 队列最多可容纳 8 个任务 (USB_TX_BUF_SIZE/I2C_TX_BUF_SIZE),即每个方向可缓存 512 字节。增加队列深度可以处理突发流量,但会占用更多 RAM 资源。
    // ===== Queue Configuration =====
    #define USB_TX_BUF_SIZE     8              // Max tasks in USB→I2C queue
    #define I2C_TX_BUF_SIZE    8              // Max tasks in I2C→USB queue
    
    // ===== USB/I2C Parameters =====
    #define USB_FRAME_PACKAGE   64             // USB Full Speed max packet size (bytes)
     缓冲区结构图 5-1 缓冲区结构
    // Represents one 64-byte unit of data (one USB frame)
    typedef struct {
        uint8_t buffer[USB_FRAME_PACKAGE];   // Data payload (up to 64 bytes)
        uint16_t length;                     // Actual data length in buffer
    } TxElement_t;
    
    // ===== FIFO Queue Structure =====
    // Circular queue to manage multiple tasks
    typedef struct {
        uint16_t fifoIn;                     // Write pointer (next task to add)
        uint16_t fifoOut;                    // Read pointer (next task to process)
        uint16_t fifoCount;                  // Number of pending tasks in queue
        TxElement_t *fifoPointer;            // Pointer to task array
    } TxFIFO_t;
  2. GPIO 数据就绪信号:当 I2C 目标器件数据准备就绪供控制器读取时,其会将专用 GPIO 输出置为有效(高电平有效)。桥接器通过 GPIO 中断检测上升沿,并设置 i2ctargetDataReady 标志。主循环轮询此标志并调用 i2c2usb_pushTask() 以启动 I2C 读取事务。目标必须将 GPIO 保持在高电平,直到控制器完成读取。GPIO 引脚使用内部下拉电阻器,因此当目标没有数据时,该线路处于空闲状态。
  3. 用于 I2C TX 的 DMA:DMA 通道 CH1 在块地址到固定地址 模式下运行,并直接从任务缓冲区加载 I2C TX FIFO,而无需 CPU 参与。DMA 将最后一个字节加载到 FIFO 后,触发 DMA 完成中断。然后,桥接器动态启用 I²C STOP 条件中断。仅当触发 STOP 中断(表示总线上的最后一位已发送)时,桥接器才会释放 TX 任务并清除 i2cInProgress。
  4. 用于 I2C RX 的 DMA:DMA 通道 CH0 在固定地址到块地址 模式下运行,并将接收到的字节从 I2C RX FIFO 直接移动到任务缓冲区。接收到预期的字节数后,发生 DMA 完成中断。处理程序将任务标记为 USB 传输准备就绪,并清除 i2ctargetDataReady 和 i2cInProgress。
  5. 溢出保护:当 USB 转 I2C 队列已满时,传入的 USB 数据将读取到虚拟缓冲区中,以防止 TinyUSB RX 缓冲区停止。当 I2C 转 USB 队列已满时,i2c2usb_pushTask() 函数会立即返回,而不会启动新的 I²C 读取。对于生产设计,请添加应用层流控制或增加队列深度。