Next in my little project(stm32f407vg) is to receive can messages from another hardware(PIC 18L25K80)
I currently have working an UART to my computer so I can easily debug the chip via UART.
The problem is that I receive the message, the interruption gets triggered but what I read from rxMessage is non sense.
Test Procedure:
Simulating the emitter I use Microchip CAN BUS Analayzer, here is the screenshot of the window:
And here is what I see in the UART:
And this is what I see if I debug (I'm using Coocox 1.7.8):
Why the values of rxMessage doesn't change neither inside the HAL driver or in my code (can.c).
Thanks.
---------------------------- main.c-------------------------
#include "globals.h"
#include "stm32f4xx_hal.h"
#include "syscfg.h"
#include "can.h"
#include "usart.h"
#include "gpio.h"
#include "kernel.h"
#include <stdio.h>
int main(void){
SysIniCfg();
while (1){
kernelMotor();
usartMotor();
canMotor();
HAL_GPIO_TogglePin(LED_G_GPIO_Port,LED_G_Pin);
}
}
------------------------- end main.c -----------------------
---------------------------- syscfg.c-------------------------
#include "syscfg.h"
#include "syscfg.h"
#include "can.h"
#include "usart.h"
#include "gpio.h"
#include "kernel.h"
/*
* System Init configuration
*/
void SysIniCfg(){
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
/* Configure the system clock */
SystemClock_Config();
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_CAN1_Init();
MX_USART1_UART_Init();
/* Initialize interrupts */
MX_NVIC_Init();
kernelInit();
}
------------------------- end syscfg.c -----------------------
---------------------------- can.h-------------------------
#include "stm32f4xx_hal.h"
#include "globals.h"
/* USER CODE BEGIN Includes */
/* USER CODE END Includes */
/* USER CODE BEGIN Private defines */
typedef struct
{
CAN_HandleTypeDef Handle;
HAL_CAN_StateTypeDef *pState;
uint32_t *pErrorCode;
} t_can_control;
typedef enum{
CM_STOPPED = 0,
CM_INIT = 1,
CM_IDLE = 10,
CM_ERROR = 255
}uint8_t_canStates;
uint8_t_canStates canMotorStates;
extern CAN_HandleTypeDef hcan1;
t_can_control can_ctrl;
CanTxMsgTypeDef sTxMsg;
CanRxMsgTypeDef sRxMsg;
/* USER CODE END Private defines */
/* USER CODE BEGIN Prototypes */
extern void Error_Handler(void);
void MX_CAN1_Init(void);
------------------------- end can.h -----------------------
---------------------------- can.c-------------------------
#include "can.h"
#include "usart.h"
#include "gpio.h"
/* USER CODE BEGIN 0 */
/* USER CODE END 0 */
CAN_HandleTypeDef hcan1;
/* CAN1 init function */
void MX_CAN1_Init(void)
{
CAN_FilterConfTypeDef sFilterConfig;
canMotorStates = CM_STOPPED;
hcan1.Instance = CAN1;
hcan1.Init.Prescaler = 20;
hcan1.Init.Mode = CAN_MODE_NORMAL;
hcan1.Init.SJW = CAN_SJW_1TQ;
hcan1.Init.BS1 = CAN_BS1_13TQ;
hcan1.Init.BS2 = CAN_BS2_2TQ;
hcan1.Init.TTCM = DISABLE;
hcan1.Init.ABOM = DISABLE;
hcan1.Init.AWUM = DISABLE;
hcan1.Init.NART = DISABLE;
hcan1.Init.RFLM = DISABLE;
hcan1.Init.TXFP = DISABLE;
if (HAL_CAN_Init(&hcan1) != HAL_OK){
Error_Handler();
}
sFilterConfig.FilterNumber = 0;
sFilterConfig.FilterMode = CAN_FILTERMODE_IDMASK;
sFilterConfig.FilterScale = CAN_FILTERSCALE_16BIT;
sFilterConfig.FilterIdHigh = 0x0000;
sFilterConfig.FilterIdLow = 0x0000;
sFilterConfig.FilterMaskIdHigh = 0x0000;
sFilterConfig.FilterMaskIdLow = 0x0000;
sFilterConfig.FilterFIFOAssignment = 0;
sFilterConfig.FilterActivation = ENABLE;
sFilterConfig.BankNumber = 14;
if(HAL_CAN_ConfigFilter(&hcan1, &sFilterConfig) != HAL_OK){
Error_Handler();
}
}
void HAL_CAN_MspInit(CAN_HandleTypeDef* canHandle)
{
GPIO_InitTypeDef GPIO_InitStruct;
if(canHandle->Instance==CAN1)
{
/* USER CODE BEGIN CAN1_MspInit 0 */
/* USER CODE END CAN1_MspInit 0 */
/* Peripheral clock enable */
__HAL_RCC_CAN1_CLK_ENABLE();
/**CAN1 GPIO Configuration
PA11 ------> CAN1_RX
PA12 ------> CAN1_TX
*/
GPIO_InitStruct.Pin = GPIO_PIN_11|GPIO_PIN_12;
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH;
GPIO_InitStruct.Alternate = GPIO_AF9_CAN1;
HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);
/* USER CODE BEGIN CAN1_MspInit 1 */
canMotorStates = CM_INIT;
/* USER CODE END CAN1_MspInit 1 */
}
}
void HAL_CAN_MspDeInit(CAN_HandleTypeDef* canHandle)
{
if(canHandle->Instance==CAN1)
{
/* USER CODE BEGIN CAN1_MspDeInit 0 */
/* USER CODE END CAN1_MspDeInit 0 */
/* Peripheral clock disable */
__HAL_RCC_CAN1_CLK_DISABLE();
/**CAN1 GPIO Configuration
PA11 ------> CAN1_RX
PA12 ------> CAN1_TX
*/
HAL_GPIO_DeInit(GPIOA, GPIO_PIN_11|GPIO_PIN_12);
/* Peripheral interrupt Deinit*/
HAL_NVIC_DisableIRQ(CAN1_TX_IRQn);
HAL_NVIC_DisableIRQ(CAN1_RX0_IRQn);
HAL_NVIC_DisableIRQ(CAN1_RX1_IRQn);
HAL_NVIC_DisableIRQ(CAN1_SCE_IRQn);
}
/* USER CODE BEGIN CAN1_MspDeInit 1 */
canMotorStates = CM_STOPPED;
/* USER CODE END CAN1_MspDeInit 1 */
}
/**
* @brief Sends order for reading and reads an amount of data in no-blocking mode with Interrupt.
* @param u8can: Number of CAN instance
* @param u16std_id: CAN standard identifier
* @param pstate: Pointer to CAN state
* @param pu32error: Pointer to CAN error code
* @retval HAL status
*/
HAL_StatusTypeDef CAN_Read_wInt(uint8_t u8can, uint16_t u16std_id, HAL_CAN_StateTypeDef *pstate, uint32_t *pu32error){
HAL_StatusTypeDef status = HAL_OK;
if ((*pu32error) == HAL_CAN_ERROR_NONE)
{
/* Set Rx Message structure */
sRxMsg.StdId = (uint32_t)u16std_id;
sRxMsg.IDE = CAN_ID_STD;
sRxMsg.RTR = CAN_RTR_DATA;
sRxMsg.DLC = (uint8_t)8;
sRxMsg.FIFONumber = CAN_FIFO0;
sRxMsg.FMI = 1;
/* Put structure in the handle */
can_ctrl.Handle.pRxMsg = &sRxMsg;
/* Order to transmit in non-blocking mode */
status = HAL_CAN_Receive_IT(&hcan1, CAN_FIFO0);
if (status == HAL_OK)
{
/* Link external pointers to CAN local pointer */
can_ctrl.pState = pstate;
can_ctrl.pErrorCode = pu32error;
/* Update CAN State */
*(can_ctrl.pState) = HAL_CAN_STATE_BUSY_RX;
}
}
else
{
status = HAL_BUSY;
}
return status;
}
void HAL_CAN_RxCpltCallback(CAN_HandleTypeDef* CanHandle)
{
HAL_GPIO_TogglePin(LED_Y_GPIO_Port,LED_Y_Pin);
char canOutBuffer[100];
sprintf(canOutBuffer,"-- %d : %d --", CanHandle->pRxMsg->StdId,CanHandle->pRxMsg->Data[0]);
usartPutString(canOutBuffer);
if(HAL_CAN_Receive_IT(CanHandle, CAN_FIFO0) != HAL_OK){
Error_Handler();
}
}
------------------------- end can.c -----------------------
---------------------------- main.c------------------------- ------------------------- end main.c -----------------------
I found what I was missing, in the definition of the can handle was specified the tx and rx message, so I suppose that the HAL drivers didn't do the initialization of this structures
void MX_CAN1_Init(void) {
CAN_FilterConfTypeDef sFilterConfig;
static CanTxMsgTypeDef TxMessage;
static CanRxMsgTypeDef RxMessage;
canMotorStates = CM_STOPPED;
hcan1.Instance = CAN1;
hcan1.Init.Prescaler = 20;
hcan1.Init.Mode = CAN_MODE_NORMAL;
hcan1.Init.SJW = CAN_SJW_1TQ;
hcan1.Init.BS1 = CAN_BS1_13TQ;
hcan1.Init.BS2 = CAN_BS2_2TQ;
hcan1.Init.TTCM = DISABLE;
hcan1.Init.ABOM = DISABLE;
hcan1.Init.AWUM = DISABLE;
hcan1.Init.NART = DISABLE;
hcan1.Init.RFLM = DISABLE;
hcan1.Init.TXFP = DISABLE;
hcan1.pRxMsg = &RxMessage;
hcan1.pTxMsg = &TxMessage;
if (HAL_CAN_Init(&hcan1) != HAL_OK)
{
Error_Handler();
}
sFilterConfig.FilterNumber = 0;
sFilterConfig.FilterMode = CAN_FILTERMODE_IDMASK;
sFilterConfig.FilterScale = CAN_FILTERSCALE_16BIT;
sFilterConfig.FilterIdHigh = 0x0000;
sFilterConfig.FilterIdLow = 0x0000;
sFilterConfig.FilterMaskIdHigh = 0x0000;
sFilterConfig.FilterMaskIdLow = 0x0000;
sFilterConfig.FilterFIFOAssignment = 0;
sFilterConfig.FilterActivation = ENABLE;
sFilterConfig.BankNumber = 14;
if(HAL_CAN_ConfigFilter(&hcan1, &sFilterConfig) != HAL_OK)
{
/* Filter configuration Error */
Error_Handler();
}
}