0% found this document useful (0 votes)
17 views8 pages

code

The document contains a C program for a microcontroller that initializes and configures a CAN (Controller Area Network) interface to send and receive OBD-II data. It simulates engine speed and sends this data over CAN while also setting up a filter for incoming messages. The program includes functions for system clock configuration, GPIO initialization, and error handling.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
17 views8 pages

code

The document contains a C program for a microcontroller that initializes and configures a CAN (Controller Area Network) interface to send and receive OBD-II data. It simulates engine speed and sends this data over CAN while also setting up a filter for incoming messages. The program includes functions for system clock configuration, GPIO initialization, and error handling.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
You are on page 1/ 8

/* USER CODE BEGIN Header */

/**
******************************************************************************
* @file : main.c
* @brief : Main program body
******************************************************************************
* @attention
*
* Copyright (c) 2025 STMicroelectronics.
* All rights reserved.
*
* This software is licensed under terms that can be found in the LICENSE file
* in the root directory of this software component.
* If no LICENSE file comes with this software, it is provided AS-IS.
*
******************************************************************************
*/
/* USER CODE END Header */
/* Includes ------------------------------------------------------------------*/
#include "main.h"

/* Private variables ---------------------------------------------------------*/


CAN_HandleTypeDef hcan;
CAN_TxHeaderTypeDef TxHeader;
CAN_RxHeaderTypeDef RxHeader;
uint8_t TxData[8];
uint8_t RxData[8];
uint32_t TxMailbox;

/* Private function prototypes -----------------------------------------------*/


void SystemClock_Config(void);
static void MX_GPIO_Init(void);
static void MX_CAN_Init(void);
static void CAN_ConfigFilter(void);
static void CAN_SendOBD2Data(uint8_t pid, uint8_t value);

/* USER CODE BEGIN 0 */

/* USER CODE END 0 */

/**
* @brief The application entry point.
* @retval int
*/
int main(void)
{
/* MCU Configuration--------------------------------------------------------*/
HAL_Init();
SystemClock_Config();
MX_GPIO_Init();
MX_CAN_Init();
CAN_ConfigFilter();

/* Start CAN */
HAL_CAN_Start(&hcan);

/* Activate CAN RX interrupt */


HAL_CAN_ActivateNotification(&hcan, CAN_IT_RX_FIFO0_MSG_PENDING);

/* USER CODE BEGIN WHILE */


int x=0;
while (1)
{
/* Giả lập tốc độ động cơ 1500 RPM (OBD-II PID: 0x0D) */
CAN_SendOBD2Data(0x0D, (60+x)); // 60 km/h
x++;
HAL_Delay(200);
if(x==1000) x=0;
}
/* USER CODE END WHILE */
}

/**
* @brief Cấu hình bộ lọc CAN
*/
static void CAN_ConfigFilter(void)
{
CAN_FilterTypeDef canFilter;

canFilter.FilterBank = 0;
canFilter.FilterMode = CAN_FILTERMODE_IDMASK;
canFilter.FilterScale = CAN_FILTERSCALE_32BIT;
canFilter.FilterIdHigh = 0x7DF << 5; // ID của máy chẩn đoán gửi đến ECU
canFilter.FilterIdLow = 0;
canFilter.FilterMaskIdHigh = 0x7FF << 5;
canFilter.FilterMaskIdLow = 0;
canFilter.FilterFIFOAssignment = CAN_RX_FIFO0;
canFilter.FilterActivation = ENABLE;

HAL_CAN_ConfigFilter(&hcan, &canFilter);
}

/**
* @brief Hàm gửi dữ liệu OBD-II qua CAN
* @param pid: Mã PID OBD-II
* @param value: Giá trị của PID
*/
static void CAN_SendOBD2Data(uint8_t pid, uint8_t value)
{
TxHeader.StdId = 0x7E8; // ECU phản hồi (ID tiêu chuẩn)
TxHeader.ExtId = 0;
TxHeader.RTR = CAN_RTR_DATA;
TxHeader.IDE = CAN_ID_STD;
TxHeader.DLC = 4;

TxData[0] = 0x03; // Số byte dữ liệu (2 byte)


TxData[1] = 0x41; // Phản hồi OBD-II (41 = phản hồi của 01 - yêu cầu)
TxData[2] = pid; // PID phản hồi
TxData[3] = value; // Giá trị của PID (ví dụ tốc độ xe km/h)

HAL_CAN_AddTxMessage(&hcan, &TxHeader, TxData, &TxMailbox);


}

/**
* @brief Callback khi nhận được dữ liệu CAN
*/
/* void HAL_CAN_RxFifo0MsgPendingCallback(CAN_HandleTypeDef *hcan)
{
HAL_CAN_GetRxMessage(hcan, CAN_RX_FIFO0, &RxHeader, RxData);
if (RxHeader.StdId == 0x7DF) // Máy chẩn đoán gửi yêu cầu
{
if (RxData[1] == 0x10) // Yêu cầu dữ liệu OBD-II
{
uint8_t requested_pid = RxData[2];

if (requested_pid == 0x0D) // Yêu cầu tốc độ xe


{
CAN_SendOBD2Data(0x0D, 3C); // Phản hồi tốc độ 60 km/h
}
}
}
} */
// Phản hồi tốc độ 60 km/h
void HAL_CAN_RxFifo0MsgPendingCallback(CAN_HandleTypeDef *hcan)
{
HAL_CAN_GetRxMessage(hcan, CAN_RX_FIFO0, &RxHeader, RxData);
CAN_SendOBD2Data(0x0D, 60); }// Phản hồi tốc độ 60 km/h
/*if (RxHeader.StdId == 0x7DF) // Máy chẩn đoán gửi yêu cầu
{

CAN_SendOBD2Data(0x0D, 60); // Phản hồi tốc độ 60 km/h

}
}*/
/**
* @brief CAN Initialization Function
*/
static void MX_CAN_Init(void)
{
hcan.Instance = CAN1;
hcan.Init.Prescaler = 18;
hcan.Init.Mode = CAN_MODE_NORMAL;
hcan.Init.SyncJumpWidth = CAN_SJW_1TQ;
hcan.Init.TimeSeg1 = CAN_BS1_2TQ;
hcan.Init.TimeSeg2 = CAN_BS2_1TQ;
hcan.Init.TimeTriggeredMode = DISABLE;
hcan.Init.AutoBusOff = DISABLE;
hcan.Init.AutoWakeUp = DISABLE;
hcan.Init.AutoRetransmission = DISABLE;
hcan.Init.ReceiveFifoLocked = DISABLE;
hcan.Init.TransmitFifoPriority = DISABLE;

if (HAL_CAN_Init(&hcan) != HAL_OK)
{
Error_Handler();
}
}

/**
* @brief GPIO Initialization Function
*/
static void MX_GPIO_Init(void)
{
GPIO_InitTypeDef GPIO_InitStruct = {0};

__HAL_RCC_GPIOC_CLK_ENABLE();
__HAL_RCC_GPIOA_CLK_ENABLE();
/*Configure GPIO pin Output Level */
HAL_GPIO_WritePin(GPIOC, GPIO_PIN_13, GPIO_PIN_RESET);

/*Configure GPIO pin : PC13 */


GPIO_InitStruct.Pin = GPIO_PIN_13;
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
HAL_GPIO_Init(GPIOC, &GPIO_InitStruct);
}

/**
* @brief System Clock Configuration
*/
void SystemClock_Config(void)
{
RCC_OscInitTypeDef RCC_OscInitStruct = {0};
RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};

RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSE;
RCC_OscInitStruct.HSEState = RCC_HSE_ON;
RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSE;
RCC_OscInitStruct.PLL.PLLMUL = RCC_PLL_MUL9;
if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
{
Error_Handler();
}
RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK | RCC_CLOCKTYPE_SYSCLK |
RCC_CLOCKTYPE_PCLK1 | RCC_CLOCKTYPE_PCLK2;
RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV2;
RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;

if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_2) != HAL_OK)


{
Error_Handler();
}
}

/**
* @brief Error Handler
*/
void Error_Handler(void)
{
__disable_irq();
while (1)
{
}
}

You might also like