This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

[参考译文] MSP430FR5992:在 SPI 协议中面临发送和接收问题

Guru**** 2378650 points
Other Parts Discussed in Thread: MSP430FR5992
请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

https://e2e.ti.com/support/microcontrollers/msp-low-power-microcontrollers-group/msp430/f/msp-low-power-microcontroller-forum/1250065/msp430fr5992-facing-transmit-and-receive-issue-in-spi-protocol

器件型号:MSP430FR5992

您好、TI 团队、  

我正在使用 SPI 协议 、其中包括将 imx8作为主设备、将 msp430fr5992作为从设备。

MSP430FR5992将接收一个数据包、进行一些处理、并将处理后的数据发送回 IMX。

我们能够从 imx8接收32字节(数据包)并也对数据进行处理。 但我们无法一次传输32个字节。

以下是 SPI 配置:  

void spi_slave_init ()
{
//配置 GPIO:SEL0+SEL1
P1SEL1 |=(BIT6);//USCI_B0 MOSI
P2SEL1 |=(BIT2);//USCI_B0 CLK
P1SEL1 |=(BIT7);//USCI_B0 MISO 引脚
P1SEL1 |=(BIT3);//芯片选择引脚

P1SEL0 &=~(BIT6);//USCI_B0 MOSI
P2SEL0 &=~(BIT2);//USCI_B0 CLK
P1SEL0 &=~(BIT7);//USCI_B0 MISO 引脚
P1SEL0 &= 8 μ~(BIT3);//芯片选择引脚

PJSEL0 |= BIT4 | BIT5;

//配置 USCI_B0以进行 SPI 操作
UCB0CTLW0 = UCSWRST;//**将状态机置于复位状态**
// 4引脚8位 SPI 从属设备
UCB0CTLW0 |= UCSYNC | UCCKPL | UCMSB | UCMODE_2;//时钟极性高,msb
UCB0CTLW0 &=~μ A UCCKPH;//时钟相位=低电平
UCB0CTLW0 |= UCSSEL_0;//UCLK 用于从机模式
UCB0CTLW0 &&~UCSWRST;//**初始化 USCI 状态机**
UCB0IE |= UCRXIE;//启用 USCI_B1 RX 中断


这是我们接收数据包的方式:

for (index_spi=0;index_spi {
while (!(UCB0IFG 和 UCRXIFG)){};
SPIRxData[INDEX_SPI]= UCB0RXBUF;//将从接收缓冲区接收的数据存储到一个数组中
UCB0IFG &=~UCRXIFG;

这是传输经过处理的数据的方式:

for (INDEX_TX=0;INDEX_TX< TxLength;INDEX_TX++)//根据 Txlength 确定要传输的字节数
{
 while (!(UCB0IFG & UCTXIFG)){};  
UCB0TXBUF = SPI_TXData[INDEX_TX];//将数据发送到 IMX

在该传输函数中、我们只能传输一个字节。 我们无法发送整个数据包。 我们能够在收到下一个数据包时发送整个数据包。

如果有任何解决方案、您需要同时传输整个数据包、请告诉我。

此致

阿比塞克

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Abhisek:

    当 MSP430作为 SPI 从器件时、colock 应由主器件控制、我的意思是 IMX8、主器件是否会发送32个时钟来读取一些数据?

    您是否尝试通过示波器或逻辑分析仪捕获一些波形?

    谢谢!

    此致

    约翰逊

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Johnson:

    是的、您回答正确。 时钟由主器件控制。 我的客户在 IMX 端工作。 我没有捕获任何波形。 我会检查并告诉你。

    但如果你认为,如果我写错了任何东西,然后让我知道。

    此致

    阿比塞克

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Abhisek:

    Unknown 说:
    for (index_TX=0;index_TX< TxLength;index_TX++)//根据 Txlength 确定要传输的字节数
    {
     while (!(UCB0IFG & UCTXIFG)){};  
    UCB0TXBUF = SPI_TXData[INDEX_TX];//将数据发送到 IMX
    }

    TXLength 是否为32?

    我发现您没有启用向母版发送数据的中断、也许您可以尝试这种方法。

    谢谢!

    此致

    约翰逊

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

    是的、TXLength 是32个字节。  

    您是否在如下所述的 SPI_SLAVE_INIT ()函数中启用发送中断?

    UCB0IE |= UCTXIE;

    此致

    阿比塞克

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Abhisek:

    是的、就像这个例子:

    https://dev.ti.com/tirex/explore/node?node=A__ADeJDaaRpnLDh0uux5v45w__msp430ware__IOGqZri__LATEST

    此示例是回波接收到的数据。

    谢谢!

    此致

    约翰逊

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Johnson:

    我是否需要涉及 ISR?

    此致

    阿比塞克

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Abhisek:

     

    是的、这会更好。

    谢谢!

    此致

    约翰逊

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Johnson:

    在使用 ISR 回显接收到的数据时、我们得到的是这样的结果。 下面是 Putty 输出:- TX 由 IMX 发送、RX 由 IMX 接收。

    TX | 5A 31 33 31 32 33 34 35 36 37 38 39 31 32 33 34 35 36 37 38 39 31 32 33 34 35 36 37 38 39 31  
    RX | 00 00 5A 31 33 31 32 33 34 35 36 37 38 39 31 32 33 34 35 35 36 37 38 39 31 32 33 34 35 36 37 38 39  

    TX | 5A 31 33 31 32 33 34 35 36 37 38 39 31 32 33 34 35 36 37 38 39 31 32 33 34 35 36 37 38 39 31  
    RX | 31 0A 5A 31 33 31 32 33 34 35 36 37 38 31 32 33 34 35 35 36 37 38 39 31 32 33 34 35 36 37 38 39 |

    请让我知道回显接收的数据时为什么会发生这种2字节移位。

    此致

    阿比塞克

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    SPI 是一种全双工协议、其中 Tx 和 Rx 同时工作。 这意味着、当从器件发送其第一个字节时、它尚未接收其第一个字节。 这不是编码问题、而是一个逻辑/信息问题、并且对于所有 SPI 从器件都是通用的(以各种形式)。

    因此、对于"回显"应用、从器件以偏移量1启动、根据代码触发 Tx 的方式、在它实际加载 TXBUF 时、来自主器件的第二个字节可能已经在进行中、从而将其偏移量2倍。

    我猜"回声"不是您的最终应用、因此这可能是考虑您的目标协议的好时机。 一些从器件只是对主器件说"忽略您返回的第一个字节"。 其他的预加载 TXBUF 中包含(例如)一个带有众所周知定义的状态字节、因此第一个字节至少有一些值。  

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!  

    我们能否在 ISR 内使用循环来接收和传输数据包?

    此致

    阿比塞克

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    否、对于 ISR、您需要遵循 Hubert Hawkins 规则:

    哈布特·霍金斯:我想进去,继续走,把它移走,然后离开。 获得它?

    拉文赫斯特:明白了。

    Hubert Hawkins:很好。

    来自"法院法官"

    即、在 ISR 中花费的时间应尽可能少。 最好让 ISR 只是从缓冲区中填充或读取。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    除了字节移位外、我在您的跟踪中看不到任何缺失的字节、因此您的从器件似乎能够跟上主器件的字节速度。 关闭(至少) 1是内在函数、因为从器件不知道要为第一个字节发送什么内容。

    重新阅读您的原始帖子、似乎这种流媒体协议不是您所想到的。 我想您正在图片中(a)主器件向从器件发送32个字节(b)从器件对数据工作、而主器件暂停[时间延迟或 GPIO 信号发送](c)主器件获取结果32个字节。 为此、主器件将执行2个单独的32字节事务:对于(a)、第一个仅 Tx;对于(c)、第二个仅 Rx。 这里的关键是、在第二个(仅 Rx)事务开始时、从器件已经知道应答并且可以预加载 TXBUF。 [未经请求:DMA 很好地适应这一模式。]

    SPI 始终同时执行 Tx 和 Rx。 对 Tx-Only 我是说主器件发送32个字节、但忽略其返回的内容、Rx-Only 意味着主器件发送32个任意("虚拟")字节并捕获其返回的内容作为应答。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    在我当前正在使用的 L6470步进控制器上、您会发送一个"命令"字节、并接收所有零。 然后、主器件根据需要发送尽可能多的0字节以接收从器件发出的数据请求。 所以我这样做:

    uint32_t GetParam3(uint8_t param)
    {
    
        uint8_t rxdata = 0;
        uint32_t data = 0;
    
        // Send command
        MAP_GPIO_setOutputLowOnPin(GPIO_PORT_P2, GPIO_PIN4);
    
        SPI_transmitData(EUSCI_B0_BASE, GET_PARAM | param);
    
        while (!(SPI_getInterruptStatus(EUSCI_B0_BASE, EUSCI_SPI_TRANSMIT_INTERRUPT)));
    
        while (!(SPI_getInterruptStatus(EUSCI_B0_BASE, EUSCI_SPI_RECEIVE_INTERRUPT)));
    
        // should be 0
        rxdata = SPI_receiveData(EUSCI_B0_BASE);
    
    
        MAP_GPIO_setOutputHighOnPin(GPIO_PORT_P2, GPIO_PIN4);
        MAP_GPIO_setOutputLowOnPin(GPIO_PORT_P2, GPIO_PIN4);
    
        // Get MSB
        SPI_transmitData(EUSCI_B0_BASE, NOP);
        while (!(SPI_getInterruptStatus(EUSCI_B0_BASE, EUSCI_SPI_TRANSMIT_INTERRUPT)));
    
        while (!(SPI_getInterruptStatus(EUSCI_B0_BASE, EUSCI_SPI_RECEIVE_INTERRUPT)));
    
        rxdata = SPI_receiveData(EUSCI_B0_BASE);
        data = (rxdata << 16);
    
        MAP_GPIO_setOutputHighOnPin(GPIO_PORT_P2, GPIO_PIN4);
        MAP_GPIO_setOutputLowOnPin(GPIO_PORT_P2, GPIO_PIN4);
    
        // Get middle bit
        SPI_transmitData(EUSCI_B0_BASE, NOP);
        while (!(SPI_getInterruptStatus(EUSCI_B0_BASE, EUSCI_SPI_TRANSMIT_INTERRUPT)));
    
        while (!(SPI_getInterruptStatus(EUSCI_B0_BASE, EUSCI_SPI_RECEIVE_INTERRUPT)));
    
        rxdata = SPI_receiveData(EUSCI_B0_BASE);
        data = data | (rxdata << 8);
    
        MAP_GPIO_setOutputHighOnPin(GPIO_PORT_P2, GPIO_PIN4);
        MAP_GPIO_setOutputLowOnPin(GPIO_PORT_P2, GPIO_PIN4);
    
        // Get Second Byte
        SPI_transmitData(EUSCI_B0_BASE, NOP);
        while (!(SPI_getInterruptStatus(EUSCI_B0_BASE, EUSCI_SPI_TRANSMIT_INTERRUPT)));
    
        while (!(SPI_getInterruptStatus(EUSCI_B0_BASE, EUSCI_SPI_RECEIVE_INTERRUPT)));
    
        rxdata = SPI_receiveData(EUSCI_B0_BASE) ;
        data |= rxdata;
    
        MAP_GPIO_setOutputHighOnPin(GPIO_PORT_P2, GPIO_PIN4);
    
        return data;
    }

    其中 NOP 是所有的位0。 适用于您的器件的 YMMV

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

     在第一组 TX 和 RX 与第二组 TX 和 RX 之间、我们应该提供多大的近似时间延迟?

    此致

    阿比塞克

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您的从器件需要多长时间来处理数据(上述步骤(b))?

    如果它所做的只是发回相同的数据(逐包)、延迟可以接近0 (将接收到的数据直接放入发送缓冲区)。

    如果它在执行 FFT、则预算(至少)为几十毫秒。

    如果您有一个示波器/逻辑分析仪、一种测量计算时间的常用技术是采用一个备用 GPIO 引脚并将其在开始时设置为高电平、在结束时设置为低电平。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    产品说明书应告诉您这些信息。 如果不是、0延迟应该没有问题。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!  

    当我执行 LED 控制以及其他一些任务时、我还在代码中使用了用于 LED 控制的计时器。 我也将 ISR 用于计时器。 LED 控制的计时器有时是否会影响 SPI 数据的发送和接收?

    信标有时我们会从 MSP 微控制器获取此类数据、

    TX | 5A 31 33 35 37 FF 40 00 00 00 95 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
    RX | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
    TX | FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
    RX | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
    经过时间:0.312349s
    TX | 5A 31 33 35 37 FF 40 00 00 00 95 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF  
    RX | 00 00 55 24 33 40 10 0B 5B FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF 42 00  
    TX | FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF  
    RX | 00 00 55 24 33 40 10 0B 5B FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF 42 00  

    而不是获取如下所述的数据包:
    TX | 5A 31 33 35 37 FF 40 00 00 00 95 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
    RX | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
    TX | FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF  
    RX | 00 00 55 24 33 40 10 0B 5B FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF 42 00  

    如果我必须进行一些更改、请告诉我。

    此致

    阿比塞克

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    它不应该产生干扰。 我认为是时候扩大范围了。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    乍一看、似乎从器件的计算(步骤(b))有时要比预期时间更长。 如果主器件在读取结果之前延迟更长、情况会有所改善吗?

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    Bruce、您好!

    我会研究一下、并告诉您。

    此致

    阿比塞克

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Abhisek:

    此问题是否已得到解决? 您是否需要进一步的支持?

    但斯克!

    此致

    约翰逊

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Johnson:

    到目前为止、我没有看到任何错误。

    如果我需要进一步的支持、我会告诉您。

    此致

    阿比塞克