S32K144 + FreeRTOS + SPI + IAR

开发环境:IAR 8.30

FreeRTOS版本:10.1

 

  • 一、移植FreeRTOS
  • 二、配置IAR
  • 三、配置IO、使能DMA、SPI
  • 四、创建任务、开启任务调度

一、移植FreeRTOS

  1. 从官网下载FreeRTOS源码
  2. 将..\FreeRTOS_v10_1_0\Source目录下的FreeRTOS源码复制到工程目录下
  3. 将..\FreeRTOS_v10_1_0\Source\portable\IAR\ARM_CM4F下的文件添加到工程目录下
  4. 将..\FreeRTOS_v10_1_0\Source\portable\MemMang下的一种内存管理文件添加到工程目录下
  5. 打开S32DS下FreeRTOS例程的文件夹,复制其中的FreeRTOSConfig.h到工程目录下
  6. 复制S32DS中的连接文件以及脚本文件

  

二、配置IAR

 三、配置IO、使能DMA、SPI

配置IO

       PINS_DRV_Init(NUM_OF_CONFIGURED_PINS, g_pin_mux_InitConfigArr);

使能DMA

#define EDMA_CHN0_NUMBER   0U
#define EDMA_CHN1_NUMBER   1U
#define EDMA_CHN2_NUMBER   2U
#define EDMA_CHN3_NUMBER   3U
#define EDMA_CONFIGURED_CHANNELS_COUNT   4U

edma_state_t dmaController1_State;
edma_chn_state_t dmaController1Chn0_State;
edma_chn_state_t dmaController1Chn1_State;
edma_chn_state_t dmaController1Chn2_State;
edma_chn_state_t dmaController1Chn3_State;
edma_chn_state_t * const edmaChnStateArray[] = {
    &dmaController1Chn0_State,
    &dmaController1Chn1_State,
    &dmaController1Chn2_State,
    &dmaController1Chn3_State
};
void SPI_EDMA_init(void)
{
    edma_channel_config_t dmaController1Chn0_Config = {
        .channelPriority = EDMA_CHN_DEFAULT_PRIORITY,
        .virtChnConfig = EDMA_CHN0_NUMBER,
        .source = EDMA_REQ_LPSPI0_RX,
        .callback = NULL,
        .callbackParam = NULL
    };
    
    edma_channel_config_t dmaController1Chn1_Config = {
        .channelPriority = EDMA_CHN_DEFAULT_PRIORITY,
        .virtChnConfig = EDMA_CHN1_NUMBER,
        .source = EDMA_REQ_LPSPI0_TX,
        .callback = NULL,
        .callbackParam = NULL
    };
    
    edma_channel_config_t dmaController1Chn2_Config = {
        .channelPriority = EDMA_CHN_DEFAULT_PRIORITY,
        .virtChnConfig = EDMA_CHN2_NUMBER,
        .source = EDMA_REQ_LPSPI1_RX,
        .callback = NULL,
        .callbackParam = NULL
    };
    
    edma_channel_config_t dmaController1Chn3_Config = {
        .channelPriority = EDMA_CHN_DEFAULT_PRIORITY,
        .virtChnConfig = EDMA_CHN3_NUMBER,
        .source = EDMA_REQ_LPSPI1_TX,
        .callback = NULL,
        .callbackParam = NULL
    };
    
    const edma_channel_config_t * const edmaChnConfigArray[] = {
        &dmaController1Chn0_Config,
        &dmaController1Chn1_Config,
        &dmaController1Chn2_Config,
        &dmaController1Chn3_Config
    };
    
    const edma_user_config_t dmaController1_InitConfig0 = {
      .chnArbitration = EDMA_ARBITRATION_FIXED_PRIORITY,
      .notHaltOnError = false,
    };
    
    EDMA_DRV_Init(&dmaController1_State, &dmaController1_InitConfig0, edmaChnStateArray, 
                 edmaChnConfigArray, EDMA_CONFIGURED_CHANNELS_COUNT);
}

初始化Master--SPI

lpspi_state_t SendState;
void SPIMasterInit(void)
{
	uint32_t ret = 0;
	
	const lpspi_master_config_t Send_MasterConfig0 = {
	  .bitsPerSec = 10000000U,
	  .whichPcs = LPSPI_PCS0,
	  .pcsPolarity = LPSPI_ACTIVE_HIGH,
	  .isPcsContinuous = false,
	  .bitcount = 8U,
	  .lpspiSrcClk = 48000000U,
	  .clkPhase = LPSPI_CLOCK_PHASE_1ST_EDGE,
	  .clkPolarity = LPSPI_SCK_ACTIVE_HIGH,
	  .lsbFirst = false,
	  .transferType = LPSPI_USING_DMA,
	  .rxDMAChannel = 0U,
	  .txDMAChannel = 1U,
	  .callback = NULL,
	  .callbackParam = NULL,
	};
	
	/* SPI master configuration: clock speed: 500 kHz, 8 bits/frame, MSB first */
	ret = LPSPI_DRV_MasterInit(0, &SendState, &Send_MasterConfig0);
	
	printf("\r\n SPI Master Init : 0x%x ", ret);
	
	/* Configure delay between transfer, delay between SCK and PCS and delay between PCS 
       and SCK */
	LPSPI_DRV_MasterSetDelay(0, 1, 1, 1);
}

初始化Slave--SPI

lpspi_state_t ReceiveState;
void SPISlaveInit(void)
{
	uint32_t ret = 0;
	
	const lpspi_slave_config_t Receive_SlaveConfig0 = {
      .pcsPolarity = LPSPI_ACTIVE_HIGH,
      .bitcount = 8U,
      .clkPhase = LPSPI_CLOCK_PHASE_1ST_EDGE,
      .whichPcs = LPSPI_PCS0,
      .clkPolarity = LPSPI_SCK_ACTIVE_HIGH,
      .lsbFirst = false,
      .transferType = LPSPI_USING_DMA,
      .rxDMAChannel = 2U,
      .txDMAChannel = 3U,
      .callback = NULL,
      .callbackParam = NULL,
    };
	
	
	ret = LPSPI_DRV_SlaveInit(0, &ReceiveState, &Receive_SlaveConfig0);
	
	printf("\r\n SPI SlaveInit : 0x%x ", ret);
}

四、创建任务、开启任务调度

特别注意:

    1、关于systick:由于FreeRTOS中的时间片调度已经使能设置了systick,故不必在设置

    2、设置中断的组别:NVIC_SetPriorityGrouping(0x3);

    3、由于FreeRTOS的中断优先级较低,会影响到正常的信号量的获取等,故需在程序刚开始时调用INT_SYS_SetPriority();修改系统中所有中断的优先级

创建任务

    xTaskCreate((TaskFunction_t )IPC_task,               //任务函数 
                (const char*    )"IPC_task",             //任务名称
                (uint16_t       )IPC_TASK_STK_SIZE,      //任务堆栈大小
                (void*          )NULL,                   //传递给任务函数的参数
                (UBaseType_t    )IPC_TASK_STK_PRIO,      //任务优先级       
                (TaskHandle_t*  )&IPC_Task_Handler);     //任务句柄    

    vTaskStartScheduler();                               //开启任务调度

Master--SPI任务函数

void IPC_task(void *pvParameters)
{
    uint8_t TXBuffer[10] = {0,1,2,3,4,5,6,7,8,9};
    uint8_t RXBuffer[10] = {0};
    
    while(1)
    {
        LPSPI_DRV_MasterTransferBlocking(0, TXBuffer, RXBuffer, sizeof(TXBuffer), 10U);
        printf("\r\n Master recever 0x%x 0x%x 0x%x 0x%x ", RXBuffer[0], RXBuffer[1], 
                                                           RXBuffer[2], RXBuffer[3]);
        vTaskDelay(1000);
    }
}

Slave--SPI任务函数

void IPC_task(void *pvParameters)
{
    uint8_t TXBuffer[10] = {9,8,7,6,5,4,3,2,1,0};
    uint8_t RXBuffer[10] = {0};
    
    while(1)
    {
        LPSPI_DRV_SlaveTransfer(0, TXBuffer, RXBuffer, sizeof(RXBuffer), 10U);
        printf("\r\n Master recever 0x%x 0x%x 0x%x 0x%x ", RXBuffer[0], RXBuffer[1], 
                                                           RXBuffer[2], RXBuffer[3]);
        vTaskDelay(1000);
    }
}

 

 

  • 7
    点赞
  • 31
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
S32K144是封装了32位ARM Cortex-M4内核的微控制器系列,可以用于汽车和工业控制等领域。FreeRTOS是一种流行的开源实时操作系统,用于管理任务和资源,并提供通信和同步机制。SPI是一种全双工的串行通信接口,通常用于连接微控制器和外部设备,例如传感器、存储器和显示器等。在S32K144微控制器上,可以使用FreeRTOSSPI接口来实现各种应用。 首先,为使用SPI接口,需要配置SPI控制器和外设。这包括设置SPI时钟、数据传输速率、数据格式和通信模式等。通常会使用SPI驱动程序来简化此过程,并确保与外设的正确通信。启用FreeRTOS后,可以创建多个任务来运行不同的操作,例如发送和接收数据,同时保持对更高级别任务的响应。可以使用FreeRTOS提供的信号量和队列等机制来实现任务间同步和互斥访问。 例如,S32K144可以使用FreeRTOSSPI接口来实现温度传感器读取。该功能涉及读取外设中的温度,并将其传输到主机控制器中。使用FreeRTOS,可以创建两个任务,一个用于读取温度传感器并将结果发送到队列中,另一个用于从队列中接收数据并将其格式化为可读的温度值并输出到串行通信接口。SPI驱动程序可确保与温度传感器的正确通信。 总之,S32K144和FreeRTOS可以结合使用SPI接口以实现各种应用,从而简化操作、提高效率和减少错误。但在使用此技术时,需了解SPIFreeRTOS的基础知识,并了解如何正确配置和管理它们。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值