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.

[参考译文] MSP430FR5994:MSP430 TI-RTOS 的 SPI 配置

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

https://e2e.ti.com/support/microcontrollers/msp-low-power-microcontrollers-group/msp430/f/msp-low-power-microcontroller-forum/979821/msp430fr5994-spi-configuration-with-msp430-ti-rtos

器件型号:MSP430FR5994
主题中讨论的其他器件:CC1352R

您好!

我尝试在 MSP430FR5994 (主器件)和 CC1352R (从器件)之间设置 SPI 通信。 我正在尝试复制 CC1352R 的 TI Resource Explorer/TI 驱动程序中给出的 SPI 示例。 CC1352R 主从示例在两个 CC1352R 板上对我有效。 现在、我想用 MSP430FR5994主器件替换 CC1352R 主器件。 我想我有一些配置问题、我怀疑 halHwi1Params.arg = 3。 我的应用在 SPI_TRANSFRA传输 进行过程中卡住。

编译器版本- 16.9.11.LTS

TI-RTOS 版本- 2.20.0.06

XDCTools 版本- 3.32.0.06_CORE

我的配置-  

var halHwi0Params = new halHwi.Params ();
halHwi0Params.arg = 0;
halHwi0Params.instance.name ="halHwi0";
halHwi0Params.priority = 1;
Program.global.halHwi0 = halHwi.create (48、 "&UARTEUSCI_hwiIntFxn"、halHwi0Params);

var halHwi1Params = new halHwi.Params ();
halHwi1Params.instance.name ="halHwi1";
halHwi1Params.arg = 3;
halHwi1Params.priority = 3;
Program.global.halHwi1 = 24、halHwi1 = halHwiCreate "&MSP_EXP430FR5994_isrDMA"、halHwi1Params);

var halHwi2Params = new halHwi.Params ();
halHwi2Params.arg = 4;
halHwi2Params.priority = 5;
Program.globalHwi2 = halHwi.create (32、"&Intwi_Hwi_GPIO" halHwi2Params); 

在 msp430fr5994.c 中、MSP_EXP430FR5994_isrDMA 看起来是这样的

/*
================================================ DMA ================================================
//
/*
=== MSP_EXP430FR5994_isrDMA ===
*这是一个应用程序定义的 DMA ISR。 此 ISR 必须映射并调用
*相应的 Driver_event (handle) API 以指示完成的 DMA 传输。
*/
void MSP_EXP430FR5994_isrDMA (UARg arg)
{
/*调用 SPI DMA 函数、传递用于 WiFi 的 SPI 句柄*/
SPI_serviceISR ((SPI_Handle)&(SPI_CONFIG[0]));
}

我的 SPI 主任务如下所示:

void MasterspiFxn (UArg0、UArgarg1){
uint32_t 一;
布尔 转让;
字符 uartStr[10];

/*配置 SPI 主从就绪 GPIO 引脚*/
GPIO_setConfig (CONFIG_SPI_MASTER_READY、GPIO_CFG_OUTPUT | GPIO_CFG_OUT_LOW);
GPIO_setConfig (CONFIG_SPI_SLAVE_READY、GPIO_CFG_INPUT);

/*设置主器件就绪引脚*/
GPIO_WRITE (CONFIG_SPI_MASTER_READY、1);
UART_WRITE (UART、"CONFIG_SPI_MASTER_READY\n"、sizeof ("CONFIG_SPI_MASTER_READY\n");

/*等待从设备准备就绪*/
while (GPIO_Read (CONFIG_SPI_SLAVE_READY)= 0){}
UART_WRITE (UART、"握手完成! \n"sizeof ("握手完成! \n");

//握手完成;现在在 CONFIG_SPI_SLAVE_READY 上配置中断*/
GPIO_setConfig (CONFIG_SPI_SLAVE_READY、GPIO_CFG_IN_pu | GPIO_CFG_IN_INT_INT_FALLING);
GPIO_setCallback (CONFIG_SPI_SLAVE_READY、slaveReadyFxn);
GPIO_enableInt (CONFIG_SPI_SLAVE_READY);
UART_WRITE (UART、"在从设备上配置中断\n"、sizeof ("在从设备上配置中断\n"));

/*创建一个信标;主器件将等待这个信标
*直到从设备就绪。 *
Semaphore_Params 参数;
ERROR_Block EB;
/* Init 参数*/
Semaphore_Params_init (&params);
ERROR_INIT (&EB);
/*创建信标实例*/
masterSem = Semaphore_create (0、&params、&EB);
if (masterSem ==空)
{
System_printf ("信标创建失败");
system_flush();
}

/*将 SPI 作为主器件打开*/
SPI_Params_init (&spiParams);
spiParams.frameFormat = SPI_POL0_PHA1;
spiParams.mode = SPI_MASTER;
spiParams.bitrate = 1000000;
masterSpi = SPI_open (Board_SPI0、&spiParams);

if (masterSpi == NULL){
UART_WRITE (UART、"初始化主 SPI\n"时出错、sizeof ("初始化主 SPI\n"时出错);
while (1);
}
否则{
UART_WRITE (UART、"Master SPI initialized\n"、sizeof ("Master SPI initialized\n"));
}

/*
*主器件已打开 CONFIG_SPI_MASTER;将 CONFIG_SPI_MASTER_READY 设置为低电平
*通知从属方。
*
GPIO_WRITE (CONFIG_SPI_MASTER_READY、0);

/*将消息复制到发送缓冲区*/
strncpy ((char *) masterTxBuffer、master_MSG、SPI_MSG_LENGTH);

对于(I = 0;I < MAX_LOOP;I++){
/*
*等待从器件准备好传输;从器件将拉取
* CONFIG_SPI_SLAVE_READY 低电平。
*
UART_WRITE (UART、"等待 MASTER_SEM\n"、sizeof ("等待 MASTER_SEM\n");
Semaphore_pend (masterSem、BIOS_wait_forever);

UART_WRITE (UART、"创建事务\n"、sizeof ("创建事务\n"));

/*初始化主 SPI 事务结构*/
masterTxBuffer[sizeof (master_MSG)- 1]=(i % 10)+'0';
memset ((void *) masterRxBuffer、0、SPI_MSG_LENGTH);
transaction.count = SPI_MSG_length;
transaction.txBuf =(void *) masterTxBuffer;
transaction.rxBuf =(void *) masterRxBuffer;

/*切换用户 LED、指示正在进行 SPI 传输*/
UART_WRITE (UART、"正在传输\n"、sizeof ("正在传输\n");
GPIO_TOGGLE (Board_LED1);

/*执行 SPI 传输*/
transferOK = SPI_transfer (masterSpi、事务);

sprintf (uartStr、"%d"、transferOK);
UART_WRITE (UART、"transfer ok ="、sizeof ("transfer ok ="));
UART_WRITE (UART、uartStr、sizeof (uartStr));

if (transferOK){
UART_WRITE (UART、"\n 已接收的主设备\n"、sizeof ("已接收的主设备\n");
}
否则{
UART_WRITE (UART、"\n 接收到成功的主设备\n"、sizeof ("接收到失败的主设备\n");
}

/*在开始下一个 SPI 传输前睡眠一位*/
Task_sleep (100);
}

SPI_CLOSE (masterSpi);

/*示例完成-将引脚设置为已知状态*/
GPIO_disableInt (CONFIG_SPI_SLAVE_READY);
GPIO_setConfig (CONFIG_SPI_SLAVE_READY、GPIO_CFG_OUTPUT | GPIO_CFG_OUT_LOW);
GPIO_WRITE (CONFIG_SPI_MASTER_READY、0);

UART_WRITE (UART、"Done!\n"、sizeof ("done!\n"));
} 

如果您需要更多信息、请告诉我。 谢谢。

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

    另一条信息-

    当我调试代码时、我发现它正在等待一个信标、因为我正在使用一个阻塞传输模式。  

    停留在- Semaphore_pend (Semaphore_handle (&(object->transferComplete))、BIOS_wait_forever); 

    *==== SPIEUSCIADA_TRANSFER ===
    *@PRE 函数假设 handle 和事务不为 NULL
    */
    bool SPIEUSCIADA_transfer (SPI_Handle handle、SPI_Transaction * transaction)
    {
    unsigned int 密钥;
    SPIEUSCIADA_Object *object = handle->object;
    SPIEUSCIADA_HWAttrs const *hwattrs = handle->hwAttrs;
    
    /*检查事务参数*/
    如果(交易->计数=0)||
    !(事务->rxBuf ||事务->txBuf)||
    (!(transaction->rxBuf && transaction->txBuf)&&!hwattrs->scratchBufPtr)){
    返回(false);
    }
    
    /*检查传输是否正在进行中*/
    KEY = Hwi_disable();
    if (object->transaction){
    Hwi_restore (key);
    
    log_error1 ("SPI:(%p)事务仍在进行中"、
    hwattrs->baseAddr);
    
    /*传输正在进行中*/
    返回(false);
    }
    否则{
    /*保存事务的指针*/
    object->transaction = transaction;
    }
    Hwi_restore (key);
    
    SPIEUSCIADA_CONFIGDMA (句柄、事务);
    
    if (object->transferMode = SPI_MODE_BLOCKING){
    Log_Print1 (Diags_User1、
    "SPI:(%p)传输完成信标上的传输挂起"、
    hwattrs->baseAddr);
    
    Semaphore_pend (Semaphore_handle (&(object->transferComplete)))、
    BIOS_wait_forever);
    }
    
    返回(true);
    } 

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

    建议简化代码以仅检查  MSP430FR5994 (主器件)和 CC1352R (从器件)。  

    1.您是否已检查  MSP430FR5994 (主器件)和 CC1352R (主器件)之间的差异? 时钟设置和寄存器设置可能不同。  

    2、可以     首先尝试使 MSP430FR5994 (主)和 MSP430FR5994 (从)正常工作、并将 MSP430FR5994 (从)替换为 CC1352R (从)。  

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

    Lixin、您好!

    我尝试使 MSP430FR5994 (主器件)和 CC1352R (主器件)中的设置相同。  

    让我检查时钟设置。

    2.    我今天将尝试设置 MSP430FR5994 (主设备)和 MSP430FR5994 (从设备)、并检查其是否正常工作。

    我会回来的。 谢谢。

    Vishal

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

    因此、我已经尝试过 MSP430FR5994 (主器件)和 MSP430FR5994 (从器件)设置、两者都运行相同的 TI-RTOS 版本。

    它仍然无法正常工作、并且卡在与我之前所示相同的位置。

    我仍然怀疑这是配置问题。

    我不确定我的当前配置有什么问题、或者我需要添加更多配置。

    下面是主设备位于内部时的屏幕截图  

    bool SPIEUSCIADA_transfer (SPI_Handle handle、SPI_Transaction *事务) 

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

    另一个更新:我已经修改了 SPI 的寄存器级示例、以便与 MSP430FR5994上的 e_USCIU3配合使用、并且它在 MSP430FR5994 (主器件)和 MSP430FR5994 (从器件)之间正常工作。  

    现在、我非常确定这是 TI-RTOS 驱动程序或我使用的配置的问题。

    请在这里帮我一点忙。 谢谢。

    Vishal

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

    您能否检查 SPI 波形以了解问题并查看哪个信号存在问题?  

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

    您好!

    我不确定是否因为您无法同时在 MSP430上启用 DMA 和 CPU。 我建议您首先不要使用 DMA 来运行 SPI。

    我的建议是、您可以在调试模式下检查 SPI 波形或 SPI 寄存器、以了解 SPI 外设已完成的工作。

    伊斯天  

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

    我找到了问题。  

    在 MSP430-TI-RTOS 空示例中、针对 TX 和 RX 缓冲器的 DMA 通道配置被反转。 下面是我为解决它所做的操作。

    首先、我更新了.cfg 文件中的配置、以使用 DMA 中断矢量编号、即 MSP430FR5994的42。

    var halHwi1Params = new halHwi.Params ();
    halHwi1Params.instance.name ="halHwi1";
    halHwi1Params.arg = 0;
    halHwi1Params.priority = 3;
    Program.global.halHwi1 = halHwi.create (42、 "&MSP_EXP430FR5994_isrDMA"、halHwi1Params); 

    然后、在 MSP_EXP430FR5994.c 文件中、我调换了 DMA 通道并触发了 RX 和 TX 缓冲器。

    CONST SPIEUSCIADA_HWAttrs spiEUSCIADMAHWAttrs[MSP_EXP430FR5994_SPICOUNT]={
    {
    baseAddr = EUSCI_A3_base、
    时钟源= EUSCI_A_SPI_CLOCKSOURCE_SMCLK、
    .bitOrder = EUSCI_A_SPI_MSB_FIRST、
    .scratchBufPtr =&spiEUSCIADMAscratchBuf[0]、
    defaultTxBufValue = 0、
    
    /* DMA */
    .dmaBaseAddr = dma_BASE、
    /* Rx 通道*/
    .rxDMAChannelIndex = DMA_CHANGE_4、
    .rxDMASourcedTrigger = DMA_TRIGGERSOURCE_16、
    /* Tx 通道*/
    TxDMAChannelIndex = DMA_CHANGE_5、
    TxDMASourcedTrigger = DMA_TRIGGERSOURCE_17
    }
    }; 

    现在、我有一个工作中的 MSP430FR5994 (主设备和从设备)工作正常。 接下来、我将继续介绍 MSP430FR5994作为主器件、CC1352R 作为从器件。

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

    更新了:上述配置修复了 MSP430上的问题。 现在、我有一个运行 TI-RTOS 的 MSP430FR5994 (主器件)和 CC1352R (从器件)之间 SPI 通信的工作示例。 如果有人需要解决方案、他们可以查看 GitHub 报告。