1 Commits

Author SHA1 Message Date
2b49e0069e add 3 var 2025-09-15 03:06:58 +03:00
65 changed files with 3101 additions and 5481 deletions

4
.gitmodules vendored
View File

@@ -5,7 +5,3 @@
path = labview_proj
url = https://git.arktika.cyou/Andrey/labview_proj.git
branch = master
[submodule "core/STM32_Modbus"]
path = core/STM32_Modbus
url = https://git.arktika.cyou/set506/STM32_Modbus.git
branch = release

Binary file not shown.

File diff suppressed because one or more lines are too long

View File

@@ -1,13 +0,0 @@
#ifndef __PROJ_SETUP
#define __PROJ_SETUP
//**********BEGIN defines***********
//#define OldVer
#define MAX_SENSE 32 // НЕ ДЕЛАТЬ МЕНЬШЕ 16
//**********END defines***********
#endif

View File

@@ -20,12 +20,10 @@
/* Includes ------------------------------------------------------------------*/
#include "onewire.h"
#include "PROJ_setup.h"
/* Data Structure ------------------------------------------------------------*/
#define DS18B20_DEVICE_AMOUNT MAX_SENSE
#define DS18B20_DEVICE_AMOUNT 30
/* Register ------------------------------------------------------------------*/
#define DS18B20_CMD_CONVERT 0x44
@@ -77,7 +75,7 @@ typedef struct
{
uint8_t DevAddr[DS18B20_DEVICE_AMOUNT][8];
} DS18B20_Drv_t;
extern DS18B20_Drv_t DS;
extern DS18B20_Drv_t DS;;
extern OneWire_t OW;
/* External Function ---------------------------------------------------------*/

View File

@@ -1,12 +1,5 @@
/* USER CODE BEGIN Header */
/**
***************************************************************
* 1 2 3 4 5 6 7 8 *
* --- +++ *
* *
*****************************************************************
******************************************************************************
* @file : main.h
* @brief : Header for main.c file.
@@ -35,29 +28,9 @@ extern "C" {
/* Includes ------------------------------------------------------------------*/
#include "stm32f1xx_hal.h"
#include "modbus_data.h"
#include "PROJ_setup.h"
#include "dallas_tools.h"
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
typedef enum
{
FuncOK=0,
FuncERROR=1
}FuncStat;
typedef enum {
CONFIG_DEVICE_ID = 0,
CONFIG_BAUDRATE,
CONFIG_CALIBRATION,
CONFIG_SETTINGS
} ConfigParams;
typedef enum {
STATE_OPEN_VALVE = 0, // open
STATE_CLOSE_VALVE= 1 // close
@@ -69,19 +42,17 @@ typedef struct
uint16_t location;
uint8_t t_open;
float t_set;
uint8_t t_close;
uint8_t status_T_sense:1 ;
uint8_t t_close;
uint8_t status_T_sense:1 ;
ValveState state;
uint16_t count;
}TEMP_TypeDef;
typedef struct {
uint32_t init_tsens : 1; // Update Interrupt Flag (бит 0) — флаг переполнения/обновления
// ... (другие биты могут быть зарезервированы или использоваться в расширенных таймерах)
} Flags_TypeDef;
uint16_t count;
}TEMP;
@@ -100,16 +71,10 @@ typedef struct {
extern void handle_command(char* cmd);
typedef void (*FunctionPointer)(void);
uint16_t handle_valves(TEMP_TypeDef* temp_sense[MAX_SENSE]);
void init_setpoint_all_T_sense(TEMP_TypeDef* temp_sense, int size_array);
uint16_t handle_valves(TEMP* tmp_sense);
void init_all_T_sense(void);
void iwdg_refresh(void);
void led_blink(GPIO_TypeDef *GPIOx,uint16_t GPIO_Pin,uint8_t iter,uint16_t delay);
FuncStat Field_modbus(MB_DataStructureTypeDef* MB_DATA, Flags_TypeDef* flag);
FuncStat packStruct(MB_DataStructureTypeDef* MB_DATA,int sizeARR);
void Check_Tconnect(MB_DataStructureTypeDef* MB_DATA, Flags_TypeDef* flag ,DALLAS_HandleTypeDef* hdallas, int a[50]);
FuncStat value_control(void );
void reinit_t_sens(void);
/* USER CODE END ET */
@@ -131,8 +96,6 @@ void Error_Handler(void);
/* USER CODE END EFP */
/* Private defines -----------------------------------------------------------*/
#define Relay_dc5v_Pin GPIO_PIN_10
#define Relay_dc5v_GPIO_Port GPIOA
#define One_wire_Pin GPIO_PIN_15
#define One_wire_GPIO_Port GPIOA

View File

@@ -22,7 +22,7 @@
#define __STM32F1xx_IT_H
#ifdef __cplusplus
extern "C" {
extern "C" {
#endif
/* Private includes ----------------------------------------------------------*/

View File

@@ -7,7 +7,7 @@
//extern uint8_t devices_found ;
extern uint8_t roms[MAX_DEVICES][8];
extern char rx_buffer[64];
extern TEMP_TypeDef temp_sense[30];
extern TEMP temp_sense[30];
extern uint8_t init;
int test_var=0;
//void handle_command(char* cmd)

View File

@@ -25,7 +25,6 @@
/* USER CODE END 0 */
/*----------------------------------------------------------------------------*/
/* Configure GPIO */
/*----------------------------------------------------------------------------*/
@@ -51,26 +50,15 @@ void MX_GPIO_Init(void)
__HAL_RCC_GPIOA_CLK_ENABLE();
__HAL_RCC_GPIOB_CLK_ENABLE();
/*Configure GPIO pin Output Level */
HAL_GPIO_WritePin(GPIOC, GPIO_PIN_13, GPIO_PIN_SET);
HAL_GPIO_WritePin(GPIOC, GPIO_PIN_14, GPIO_PIN_RESET);
/*Configure GPIO pin Output Level */
HAL_GPIO_WritePin(GPIOA, GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3|GPIO_PIN_4
|GPIO_PIN_5|GPIO_PIN_6|GPIO_PIN_7|GPIO_PIN_8
|GPIO_PIN_9|Relay_dc5v_Pin|One_wire_Pin, GPIO_PIN_RESET);
|GPIO_PIN_9|GPIO_PIN_10|One_wire_Pin, GPIO_PIN_SET);
/*Configure GPIO pin Output Level */
HAL_GPIO_WritePin(GPIOB, GPIO_PIN_0|GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_10
|GPIO_PIN_11|GPIO_PIN_12|GPIO_PIN_13|GPIO_PIN_14
|GPIO_PIN_15, GPIO_PIN_RESET);
/*Configure GPIO pin : PC13 */
GPIO_InitStruct.Pin = GPIO_PIN_13|GPIO_PIN_14;
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Pull = GPIO_PULLUP;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
HAL_GPIO_Init(GPIOC, &GPIO_InitStruct);
|GPIO_PIN_15, GPIO_PIN_SET);
/*Configure GPIO pin : PA0 */
GPIO_InitStruct.Pin = GPIO_PIN_0;
@@ -80,10 +68,10 @@ void MX_GPIO_Init(void)
/*Configure GPIO pins : PA1 PA2 PA3 PA4
PA5 PA6 PA7 PA8
PA9 Relay_dc5v_Pin One_wire_Pin */
PA9 PA10 PAPin */
GPIO_InitStruct.Pin = GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3|GPIO_PIN_4
|GPIO_PIN_5|GPIO_PIN_6|GPIO_PIN_7|GPIO_PIN_8
|GPIO_PIN_9|Relay_dc5v_Pin|One_wire_Pin;
|GPIO_PIN_9|GPIO_PIN_10|One_wire_Pin;
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;

View File

@@ -27,25 +27,13 @@
#include "usart.h"
#include "gpio.h"
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include "dallas_tools.h"
#include "def.h"
#include <stdio.h>
#include "modbus.h"
#include "eeprom_emul.h"
#include "stdio.h"
#include "flash_ring.h"
#include "string.h"
#include "rs_message.h"
@@ -53,42 +41,41 @@
/* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD */
int fputc(int ch, FILE *f)
{
HAL_UART_Transmit(&huart1, (uint8_t *)&ch, 1, HAL_MAX_DELAY);
return ch;
}
/* USER CODE END PTD */
/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */
uint16_t iter, cnt = 5;
uint8_t init_retries = 5;
uint8_t ralay_5v_on_var = 0;
uint16_t iter,cnt=5;
uint8_t ralay_5v_on_var=0;
/* USER CODE END PD */
/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */
float temperature;
uint8_t roms[MAX_DEVICES][8];
Flags_TypeDef flag;
//extern uint8_t devices_found ;
uint8_t _debug_init = 0;
TEMP_TypeDef temp_sense[30];
float set_temp_old[30];
char rx_buffer[64];
uint8_t rx_index = 0;
char command_ready = 0;
uint8_t uart_byte = 0;
uint8_t first_in = 1;
DALLAS_SensorHandleTypeDef sens[30];
int init_sens = 0;
FlashRecord_t* record;
uint8_t flash_buff[RECORD_SIZE - 4];
float temperature;
extern uint8_t roms[MAX_DEVICES][8];
//extern uint8_t devices_found ;
uint8_t _debug_init=1;
//TEMP temp_sense[30];
float set_temp_old[30];
char rx_buffer[64];
uint8_t rx_index = 0;
char command_ready = 0;
uint8_t uart_byte = 0;
uint8_t first_in=1;
DALLAS_SensorHandleTypeDef sens[30];
/* USER CODE END PM */
/* Private variables ---------------------------------------------------------*/
/* USER CODE BEGIN PV */
int last_page_addr = LAST_PAGE_ADDR;
/* USER CODE END PV */
@@ -108,134 +95,150 @@ void SystemClock_Config(void);
* @retval int
*/
int main(void)
{
/* USER CODE BEGIN 1 */
/* USER CODE BEGIN 1 */
/* USER CODE END 1 */
/* USER CODE END 1 */
/* MCU Configuration--------------------------------------------------------*/
/* MCU Configuration--------------------------------------------------------*/
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
/* USER CODE BEGIN Init */
/* USER CODE END Init */
/* Configure the system clock */
SystemClock_Config();
/* USER CODE BEGIN SysInit */
/* USER CODE END SysInit */
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_TIM1_Init();
MX_USART1_UART_Init();
MX_TIM2_Init();
MX_ADC1_Init();
MX_CAN_Init();
MX_I2C1_Init();
MX_RTC_Init();
MX_SPI1_Init();
/* USER CODE BEGIN 2 */
led_blink(GPIOC, 13, rest_iter, reset_blink_delay);
MODBUS_FirstInit(&hmodbus1, &mb_huart, &mb_htim);
MODBUS_Config(&hmodbus1, MODBUS_DEVICE_ID, MODBUS_TIMEOUT, MODBUS_MODE_SLAVE);
// Запуск приема Modbus
MODBUS_SlaveStart(&hmodbus1, NULL);
uint8_t uart_byte = 0;
Dallas_BusFirstInit(&htim1);
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> (<28><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>)
reinit_t_sens();
init_setpoint_all_T_sense(temp_sense, hdallas.onewire->RomCnt);
MB_DATA.InRegs.num_Tsens = hdallas.onewire->RomCnt;
// BufferState_t buffer_state = buffer_init();
for(int i=0;i<RECORD_SIZE;i++)
{
flash_buff[i]=i;
/* USER CODE BEGIN Init */
}
/* USER CODE END 2 */
/* USER CODE END Init */
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
/* Configure the system clock */
SystemClock_Config();
/* USER CODE BEGIN SysInit */
// if (MB_DATA.Coils.relay_struct[0].state_val_bit.Temp11_relay_isOn)
// {
// MB_DATA.Coils.relay_struct[0].state_val_bit.Temp11_relay_isOn = 0;
// BufferState_t state = buffer_init();
// uint32_t idx = (state.write_index ) % RECORDS_PER_PAGE;
// FlashRecord_t* record = buffer_read_record(idx);
/* USER CODE END SysInit */
// }
// if (MB_DATA.Coils.relay_struct[0].state_val_bit.Temp10_relay_isOn)
// {
// MB_DATA.Coils.relay_struct[0].state_val_bit.Temp10_relay_isOn = 0;
// FlashRecord_t new_record;
// new_record.timestamp = HAL_GetTick();
// memcpy(new_record.data, flash_buff, sizeof(new_record.data));
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_TIM1_Init();
MX_USART1_UART_Init();
MX_TIM2_Init();
MX_ADC1_Init();
MX_CAN_Init();
MX_I2C1_Init();
MX_RTC_Init();
MX_SPI1_Init();
/* USER CODE BEGIN 2 */
// HAL_StatusTypeDef status = buffer_write_record(&new_record, &buffer_state);
led_blink(GPIOC,13,rest_iter,reset_blink_delay);
MODBUS_FirstInit();
uint8_t uart_byte = 0;
RS_Receive_IT(&hmodbus1, &MODBUS_MSG);
Dallas_BusFirstInit(&htim1);
// èíèöèàëèçàöèÿ ïî ïîðÿäêó íàéäåííûõ äàò÷èêîâ
// Èíèöèàëèçàöèÿ ïî èíäåêñó (ïîðÿäêîâîìó íîìåðó íàéäåííîãî äàò÷èêà)
for ( int i=0; i<hdallas.onewire->RomCnt;i++)
{
// Èíèöèàëèçàöèÿ ïî ROM-àäðåñó
//sens[i].Init.init_func = &Dallas_SensorInitByROM;
// sens[i].Init.InitParam.ROM = rom_address;
sens[i].Init.InitParam.Ind = i;
sens[i].Init.init_func = &Dallas_SensorInitByInd;
sens[i].Init.Resolution = DALLAS_CONFIG_9_BITS;
MB_DATA.HoldRegs.set_Temp[i] =sens[i].set_temp =20.;
MB_DATA.HoldRegs.set_hyst[i]=sens[i].hyst =1;
Dallas_AddNewSensors(&hdallas, &sens[i]);
// if (status == HAL_OK)
// {
// // printf("Record written successfully\n");
// GPIOC->ODR |= 1 << 13;
// }
}
/* USER CODE END 2 */
// }
temp_sense[0].t_close = 1;
Field_modbus(&MB_DATA, &flag);
Check_Tconnect(&MB_DATA, &flag, &hdallas, 0);
value_control();
init_setpoint_all_T_sense(temp_sense, hdallas.onewire->RomCnt);
// handle_valves(temp_sense[]);
Dallas_StartConvertTAll(&hdallas, DALLAS_WAIT_BUS, 0);
for(int i = 0; i < hdallas.onewire->RomCnt; i++)
{
if(sens[i].isLost)
{
sens[i].lost_cnt ++;
}
Dallas_ReadTemperature(&sens[i]);
MB_DATA.InRegs.sens_Temp[i] = sens[i].temperature * 10;
/////////////////////////заменить на define ralay_5v_on_var GPIOA->ODR|=1<<10;
ralay_5v_on_var = MB_DATA.Coils.coils[1].state_val_bit.state_val_05;
if (ralay_5v_on_var)
{
GPIOA->ODR |= 1 << 10;
}
else
{
GPIOA->ODR &= ~(1 << 10);
}
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
if (_debug_init||MB_DATA.Coils.init_param)
{
_debug_init=0;
MB_DATA.Coils.init_param=0;
for(int i=0;i<hdallas.onewire->RomCnt;i++)
{
sens[i].set_temp=MB_DATA.HoldRegs.set_Temp[i];
sens[i].hyst=MB_DATA.HoldRegs.set_hyst[i];
}
}
Dallas_StartConvertTAll(&hdallas,DALLAS_WAIT_BUS,0);
}
for(int i=0;i<hdallas.onewire->RomCnt;i++)
{
if(sens[i].isLost)
{
sens[i].lost_cnt ++;
}
Dallas_ReadTemperature(&sens[i]);
sens[i].set_temp = MB_DATA.HoldRegs.set_Temp[i];
MB_DATA.InRegs.sens_Temp[i]=sens[i].temperature*10;
ralay_5v_on_var=MB_DATA.Coils.coils[1].state_val_bit.state_val_05;
if (ralay_5v_on_var)
{
GPIOA->ODR|=1<<10;
}
else
{
GPIOA->ODR&=~(1<<10);
}
//// if (sens[i].temperature<sens[i].set_temp-sens[i].hyst)
////
//// {
////
//// MB_DATA.Coils.coils[0].all|=1<<i;
////
//// }
////
//// else
////
//// if (sens[i].temperature>sens[i].set_temp+sens[i].hyst)
//// {
////
//// MB_DATA.Coils.coils[0].all&=~(1<<i);
////
//// }
//// if(GPIOB11_valve)
//// {
//// GPIOB->ODR|=1<<11;
//// }
//// else
//// {
//// GPIOB->ODR&=~(1<<11);
////
//// }
}
/* USER CODE END WHILE */
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
//iwdg_refresh();
//HAL_Delay(200);
}
/* USER CODE END 3 */
/* USER CODE BEGIN 3 */
//iwdg_refresh();
//HAL_Delay(200);
}
/* USER CODE END 3 */
}
/**
@@ -244,258 +247,126 @@ for(int i=0;i<RECORD_SIZE;i++)
*/
void SystemClock_Config(void)
{
RCC_OscInitTypeDef RCC_OscInitStruct = {0};
RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};
RCC_PeriphCLKInitTypeDef PeriphClkInit = {0};
RCC_OscInitTypeDef RCC_OscInitStruct = {0};
RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};
RCC_PeriphCLKInitTypeDef PeriphClkInit = {0};
/** Initializes the RCC Oscillators according to the specified parameters
* in the RCC_OscInitTypeDef structure.
*/
RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_LSI | RCC_OSCILLATORTYPE_HSE;
RCC_OscInitStruct.HSEState = RCC_HSE_ON;
RCC_OscInitStruct.HSEPredivValue = RCC_HSE_PREDIV_DIV1;
RCC_OscInitStruct.HSIState = RCC_HSI_ON;
RCC_OscInitStruct.LSIState = RCC_LSI_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();
}
/** Initializes the RCC Oscillators according to the specified parameters
* in the RCC_OscInitTypeDef structure.
*/
RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_LSI|RCC_OSCILLATORTYPE_HSE;
RCC_OscInitStruct.HSEState = RCC_HSE_ON;
RCC_OscInitStruct.HSEPredivValue = RCC_HSE_PREDIV_DIV1;
RCC_OscInitStruct.HSIState = RCC_HSI_ON;
RCC_OscInitStruct.LSIState = RCC_LSI_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();
}
/** Initializes the CPU, AHB and APB buses clocks
*/
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;
/** Initializes the CPU, AHB and APB buses clocks
*/
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();
}
PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_RTC | RCC_PERIPHCLK_ADC;
PeriphClkInit.RTCClockSelection = RCC_RTCCLKSOURCE_LSI;
PeriphClkInit.AdcClockSelection = RCC_ADCPCLK2_DIV6;
if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK)
{
Error_Handler();
}
if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_2) != HAL_OK)
{
Error_Handler();
}
PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_RTC|RCC_PERIPHCLK_ADC;
PeriphClkInit.RTCClockSelection = RCC_RTCCLKSOURCE_LSI;
PeriphClkInit.AdcClockSelection = RCC_ADCPCLK2_DIV6;
if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK)
{
Error_Handler();
}
}
/* USER CODE BEGIN 4 */
void iwdg_refresh(void)
{
IWDG->KR = 0xAAAA; // <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
}
void led_blink(GPIO_TypeDef *GPIOx, uint16_t GPIO_Pin, uint8_t iter, uint16_t delay)
{
for(int i = 0; i < iter; i++)
{
GPIOx->ODR ^= (1 << GPIO_Pin);
HAL_Delay(delay);
}
}
void iwdg_refresh(void)
{
IWDG->KR = 0xAAAA; // Ñáðîñèòü òàéìåð
}
void led_blink(GPIO_TypeDef *GPIOx,uint16_t GPIO_Pin,uint8_t iter,uint16_t delay)
{
for(int i=0;i<iter;i++)
{
GPIOx->ODR^=(1<<GPIO_Pin);
HAL_Delay(delay);
}
}
//void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)
//{
// if (huart->Instance == USART1)
// {
// if(first_in)
// {
// first_in=0;
// rx_index = 0;
//
// }
//
//
//
// static uint8_t ch;
// HAL_UART_Receive_IT(&huart1, &ch, 1);
void Check_Tconnect(MB_DataStructureTypeDef* MB_DATA, Flags_TypeDef* flag, DALLAS_HandleTypeDef* hdallas, int a[0])
{
for(int i = 0; i < hdallas->onewire->RomCnt; i++)
{
if(sens[i].isLost)
{
//init_sens=1;
}
// if (ch == '\r' || ch == '\n')
// {
// rx_buffer[rx_index] = 0;
// command_ready = 1;
// rx_index = 0;
// first_in=1;
//
// }
// else
// {
// if (rx_index < sizeof(rx_buffer) - 1)
// {
// rx_buffer[rx_index++] = ch;
// }
// }
// }
//}
}
if (init_sens || flag->init_tsens)
{
init_sens = 0;
flag->init_tsens = 0;
//Dallas_BusFirstInit(&htim1);
DS18B20_Search(&DS, &OW) ;
reinit_t_sens();
MB_DATA->InRegs.num_Tsens = hdallas->onewire->RomCnt;
}
}
//uint16_t handle_valves(TEMP* tmp_sense )
//{
//
// if (temp_sense[0].state==STATE_OPEN_VALVE)
// {
// GPIOC->ODR|=1<<14;
// }
// else
// if (temp_sense[0].state==STATE_CLOSE_VALVE)
// {
// GPIOC->ODR&=~(1<<14);
// }
//
// return 1;
//
//}
void reinit_t_sens(void)
{
for ( int i = 0; i < hdallas.onewire->RomCnt; i++)
{
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><> ROM-<2D><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
//sens[i].Init.init_func = &Dallas_SensorInitByROM;
// sens[i].Init.InitParam.ROM = rom_address;
sens[i].Init.InitParam.Ind = i;
sens[i].Init.init_func = &Dallas_SensorInitByInd;
sens[i].Init.Resolution = DALLAS_CONFIG_9_BITS;
MB_DATA.HoldRegs.set_Temp[i] = sens[i].set_temp = 20.;
MB_DATA.HoldRegs.set_hyst[i] = sens[i].hyst = 1;
Dallas_AddNewSensors(&hdallas, &sens[i]);
}
}
FuncStat packStruct(MB_DataStructureTypeDef* MB_DATA, int sizeARR)
{
for(int i = 0; i < sizeARR; i++)
{
for(int sens_num = 0; sens_num < hdallas.onewire->RomCnt; sens_num++)
{
switch(sens_num)
{
case 0:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp1_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 1:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp2_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 2:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp3_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 3:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp4_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 4:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp5_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 5:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp6_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 6:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp7_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 7:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp8_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 8:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp9_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 9:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp10_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 10:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp11_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 11:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp12_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 12:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp13_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 13:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp14_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 14:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp15_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 15:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp16_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
}
}
}
return FuncOK;
}
FuncStat Field_modbus(MB_DataStructureTypeDef* MB_DATA, Flags_TypeDef* flag)
{
MB_DATA->InRegs.ID = *hdallas.ds_devices;
flag->init_tsens = MB_DATA->Coils.init_Tsens;
packStruct(MB_DATA, MAX_SENSE / 16);
if (_debug_init || MB_DATA->Coils.init_param)
{
_debug_init = 0;
MB_DATA->Coils.init_param = 0;
for(int i = 0; i < hdallas.onewire->RomCnt; i++)
{
sens[i].set_temp = MB_DATA->HoldRegs.set_Temp[i];
sens[i].hyst = MB_DATA->HoldRegs.set_hyst[i];
}
}
return FuncOK;
};
FuncStat value_control(void )
{
for(int i = 0; i < hdallas.onewire->RomCnt; i++)
{
if (sens[i].temperature < sens[i].set_temp - sens[i].hyst)
{
MB_DATA.Coils.relay_struct_off.all |= 1 << i;
MB_DATA.Coils.relay_struct_on.all &= ~(1 << i);
}
else
if (sens[i].temperature > sens[i].set_temp + sens[i].hyst)
{
MB_DATA.Coils.relay_struct_off.all &= ~(1 << i);
MB_DATA.Coils.relay_struct_on.all |= 1 << i;
}
else
if (sens[i].temperature == sens[i].set_temp )
{
MB_DATA.Coils.relay_struct_on.all &= ~(1 << i);
MB_DATA.Coils.relay_struct_off.all &= ~(1 << i);
}
}
return FuncOK;
}
uint16_t handle_valves(TEMP_TypeDef* temp_sense[MAX_SENSE] )
{
if (temp_sense[0]->state == STATE_OPEN_VALVE)
{
GPIOC->ODR |= 1 << 14;
}
else if (temp_sense[0]->state == STATE_CLOSE_VALVE)
{
GPIOC->ODR &= ~(1 << 14);
}
return 1;
}
void init_setpoint_all_T_sense(TEMP_TypeDef* temp_sense, int size_array)
{
//ds_search_devices();
for(int i = 0; i < size_array ; i++)
{
temp_sense[i].id[0] = roms[i][0] << 0 | roms[i][1] << 8 | roms[i][2] << 16 | roms[i][3] << 24;
temp_sense[i].id[1] = roms[i][4] << 0 | roms[i][5] << 8 | roms[i][6] << 16 | roms[i][7] << 24;
temp_sense[i].count = i + 1;
temp_sense[i].location = 1;
temp_sense[i].t_open = 22;
temp_sense[i].t_close = 18;
temp_sense[i].status_T_sense = 1;
}
}
//void init_all_T_sense(void)
//{
// //ds_search_devices();
// for(int i=0;i<hdallas.onewire->RomCnt;i++)
//{
// temp_sense[i].id[0]=roms[i][0]<<0|roms[i][1]<<8|roms[i][2]<<16|roms[i][3]<<24;
// temp_sense[i].id[1]=roms[i][4]<<0|roms[i][5]<<8|roms[i][6]<<16|roms[i][7]<<24;
// temp_sense[i].count =i+1;
// temp_sense[i].location=1;
// temp_sense[i].t_open=22;
// temp_sense[i].t_close=18;
// temp_sense[i].status_T_sense=1;
//}
//}
/* USER CODE END 4 */
/**
@@ -508,16 +379,15 @@ void init_setpoint_all_T_sense(TEMP_TypeDef* temp_sense, int size_array)
*/
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
{
/* USER CODE BEGIN Callback 0 */
/* USER CODE BEGIN Callback 0 */
/* USER CODE END Callback 0 */
if (htim->Instance == TIM3)
{
HAL_IncTick();
}
/* USER CODE BEGIN Callback 1 */
/* USER CODE END Callback 0 */
if (htim->Instance == TIM3) {
HAL_IncTick();
}
/* USER CODE BEGIN Callback 1 */
/* USER CODE END Callback 1 */
/* USER CODE END Callback 1 */
}
/**
@@ -526,15 +396,16 @@ void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
*/
void Error_Handler(void)
{
/* USER CODE BEGIN Error_Handler_Debug */
/* User can add his own implementation to report the HAL error return state */
__disable_irq();
while (1)
{
}
/* USER CODE END Error_Handler_Debug */
/* USER CODE BEGIN Error_Handler_Debug */
/* User can add his own implementation to report the HAL error return state */
__disable_irq();
while (1)
{
}
/* USER CODE END Error_Handler_Debug */
}
#ifdef USE_FULL_ASSERT
#ifdef USE_FULL_ASSERT
/**
* @brief Reports the name of the source file and the source line number
* where the assert_param error has occurred.
@@ -544,9 +415,9 @@ void Error_Handler(void)
*/
void assert_failed(uint8_t *file, uint32_t line)
{
/* USER CODE BEGIN 6 */
/* User can add his own implementation to report the file name and line number,
ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) */
/* USER CODE END 6 */
/* USER CODE BEGIN 6 */
/* User can add his own implementation to report the file name and line number,
ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) */
/* USER CODE END 6 */
}
#endif /* USE_FULL_ASSERT */

View File

@@ -1,540 +0,0 @@
/* 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"
#include "adc.h"
#include "can.h"
#include "i2c.h"
#include "rtc.h"
#include "spi.h"
#include "tim.h"
#include "usart.h"
#include "gpio.h"
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include "dallas_tools.h"
#include "def.h"
#include <stdio.h>
#include "modbus.h"
#include "eeprom_emul.h"
#include "stdio.h"
#include "flash_ring.h"
#include "string.h"
/* USER CODE END Includes */
/* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD */
/* USER CODE END PTD */
/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */
uint16_t iter, cnt = 5;
uint8_t init_retries = 5;
uint8_t ralay_5v_on_var = 0;
/* USER CODE END PD */
/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */
float temperature;
uint8_t roms[MAX_DEVICES][8];
Flags_TypeDef flag;
//extern uint8_t devices_found ;
uint8_t _debug_init = 0;
TEMP_TypeDef temp_sense[30];
float set_temp_old[30];
char rx_buffer[64];
uint8_t rx_index = 0;
char command_ready = 0;
uint8_t uart_byte = 0;
uint8_t first_in = 1;
DALLAS_SensorHandleTypeDef sens[30];
int init_sens = 0;
FlashRecord_t* record;
uint8_t flash_buff[RECORD_SIZE-4];
/* USER CODE END PM */
/* Private variables ---------------------------------------------------------*/
/* USER CODE BEGIN PV */
int last_page_addr=LAST_PAGE_ADDR;
/* USER CODE END PV */
/* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
/* USER CODE BEGIN PFP */
/* USER CODE END PFP */
/* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */
/* USER CODE END 0 */
/**
* @brief The application entry point.
* @retval int
*/
int main(void)
{
/* USER CODE BEGIN 1 */
/* USER CODE END 1 */
/* MCU Configuration--------------------------------------------------------*/
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
/* USER CODE BEGIN Init */
/* USER CODE END Init */
/* Configure the system clock */
SystemClock_Config();
/* USER CODE BEGIN SysInit */
/* USER CODE END SysInit */
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_TIM1_Init();
MX_USART1_UART_Init();
MX_TIM2_Init();
MX_ADC1_Init();
MX_CAN_Init();
MX_I2C1_Init();
MX_RTC_Init();
MX_SPI1_Init();
/* USER CODE BEGIN 2 */
led_blink(GPIOC, 13, rest_iter, reset_blink_delay);
MODBUS_FirstInit(&hmodbus1, &mb_huart, &mb_htim);
MODBUS_Config(&hmodbus1, MODBUS_DEVICE_ID, MODBUS_TIMEOUT, MODBUS_MODE_SLAVE);
// Запуск приема Modbus
MODBUS_SlaveStart(&hmodbus1, NULL);
uint8_t uart_byte = 0;
Dallas_BusFirstInit(&htim1);
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> (<28><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>)
reinit_t_sens();
init_setpoint_all_T_sense(temp_sense, hdallas.onewire->RomCnt);
MB_DATA.InRegs.num_Tsens = hdallas.onewire->RomCnt;
BufferState_t buffer_state = buffer_init();
/* USER CODE END 2 */
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
if (MB_DATA.Coils.relay_struct[0].state_val_bit.Temp11_relay_isOn)
{
MB_DATA.Coils.relay_struct[0].state_val_bit.Temp11_relay_isOn=0;
BufferState_t state = buffer_init();
uint32_t idx = (state.write_index ) % RECORDS_PER_PAGE;
FlashRecord_t* record = buffer_read_record(idx);
}
if (MB_DATA.Coils.relay_struct[0].state_val_bit.Temp10_relay_isOn)
{
MB_DATA.Coils.relay_struct[0].state_val_bit.Temp10_relay_isOn = 0;
FlashRecord_t new_record;
new_record.timestamp = HAL_GetTick();
memset(new_record.data, (uint8_t)*flash_buff, sizeof(new_record.data));
HAL_StatusTypeDef status = buffer_write_record(&new_record, &buffer_state);
if (status == HAL_OK)
{
// printf("Record written successfully\n");
GPIOC->ODR|=1<<13;
}
}
temp_sense[0].t_close = 1;
Field_modbus(&MB_DATA, &flag);
Check_Tconnect(&MB_DATA, &flag, &hdallas, 0);
value_control();
init_setpoint_all_T_sense(temp_sense, hdallas.onewire->RomCnt);
// handle_valves(temp_sense[]);
Dallas_StartConvertTAll(&hdallas, DALLAS_WAIT_BUS, 0);
for(int i = 0; i < hdallas.onewire->RomCnt; i++)
{
if(sens[i].isLost)
{
sens[i].lost_cnt ++;
}
Dallas_ReadTemperature(&sens[i]);
MB_DATA.InRegs.sens_Temp[i] = sens[i].temperature * 10;
/////////////////////////заменить на define ralay_5v_on_var GPIOA->ODR|=1<<10;
ralay_5v_on_var = MB_DATA.Coils.coils[1].state_val_bit.state_val_05;
if (ralay_5v_on_var)
{
GPIOA->ODR |= 1 << 10;
}
else
{
GPIOA->ODR &= ~(1 << 10);
}
}
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
//iwdg_refresh();
//HAL_Delay(200);
}
/* USER CODE END 3 */
}
/**
* @brief System Clock Configuration
* @retval None
*/
void SystemClock_Config(void)
{
RCC_OscInitTypeDef RCC_OscInitStruct = {0};
RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};
RCC_PeriphCLKInitTypeDef PeriphClkInit = {0};
/** Initializes the RCC Oscillators according to the specified parameters
* in the RCC_OscInitTypeDef structure.
*/
RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_LSI | RCC_OSCILLATORTYPE_HSE;
RCC_OscInitStruct.HSEState = RCC_HSE_ON;
RCC_OscInitStruct.HSEPredivValue = RCC_HSE_PREDIV_DIV1;
RCC_OscInitStruct.HSIState = RCC_HSI_ON;
RCC_OscInitStruct.LSIState = RCC_LSI_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();
}
/** Initializes the CPU, AHB and APB buses clocks
*/
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();
}
PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_RTC | RCC_PERIPHCLK_ADC;
PeriphClkInit.RTCClockSelection = RCC_RTCCLKSOURCE_LSI;
PeriphClkInit.AdcClockSelection = RCC_ADCPCLK2_DIV6;
if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK)
{
Error_Handler();
}
}
/* USER CODE BEGIN 4 */
void iwdg_refresh(void)
{
IWDG->KR = 0xAAAA; // <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
}
void led_blink(GPIO_TypeDef *GPIOx, uint16_t GPIO_Pin, uint8_t iter, uint16_t delay)
{
for(int i = 0; i < iter; i++)
{
GPIOx->ODR ^= (1 << GPIO_Pin);
HAL_Delay(delay);
}
}
void Check_Tconnect(MB_DataStructureTypeDef* MB_DATA, Flags_TypeDef* flag, DALLAS_HandleTypeDef* hdallas, int a[0])
{
for(int i = 0; i < hdallas->onewire->RomCnt; i++)
{
if(sens[i].isLost)
{
//init_sens=1;
}
}
if (init_sens || flag->init_tsens)
{
init_sens = 0;
flag->init_tsens = 0;
//Dallas_BusFirstInit(&htim1);
DS18B20_Search(&DS, &OW) ;
reinit_t_sens();
MB_DATA->InRegs.num_Tsens = hdallas->onewire->RomCnt;
}
}
void reinit_t_sens(void)
{
for ( int i = 0; i < hdallas.onewire->RomCnt; i++)
{
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><> ROM-<2D><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
//sens[i].Init.init_func = &Dallas_SensorInitByROM;
// sens[i].Init.InitParam.ROM = rom_address;
sens[i].Init.InitParam.Ind = i;
sens[i].Init.init_func = &Dallas_SensorInitByInd;
sens[i].Init.Resolution = DALLAS_CONFIG_9_BITS;
MB_DATA.HoldRegs.set_Temp[i] = sens[i].set_temp = 20.;
MB_DATA.HoldRegs.set_hyst[i] = sens[i].hyst = 1;
Dallas_AddNewSensors(&hdallas, &sens[i]);
}
}
FuncStat packStruct(MB_DataStructureTypeDef* MB_DATA, int sizeARR)
{
for(int i = 0; i < sizeARR; i++)
{
for(int sens_num = 0; sens_num < hdallas.onewire->RomCnt; sens_num++)
{
switch(sens_num)
{
case 0:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp1_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 1:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp2_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 2:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp3_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 3:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp4_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 4:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp5_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 5:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp6_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 6:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp7_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 7:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp8_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 8:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp9_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 9:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp10_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 10:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp11_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 11:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp12_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 12:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp13_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 13:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp14_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 14:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp15_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
case 15:
MB_DATA->Coils.status_tSens[i].state_val_bit.Temp16_isConnected = sens[i * 16 + sens_num ].isConnected;
break;
}
}
}
return FuncOK;
}
FuncStat Field_modbus(MB_DataStructureTypeDef* MB_DATA, Flags_TypeDef* flag)
{
MB_DATA->InRegs.ID = *hdallas.ds_devices;
flag->init_tsens = MB_DATA->Coils.init_Tsens;
packStruct(MB_DATA, MAX_SENSE / 16);
if (_debug_init || MB_DATA->Coils.init_param)
{
_debug_init = 0;
MB_DATA->Coils.init_param = 0;
for(int i = 0; i < hdallas.onewire->RomCnt; i++)
{
sens[i].set_temp = MB_DATA->HoldRegs.set_Temp[i];
sens[i].hyst = MB_DATA->HoldRegs.set_hyst[i];
}
}
return FuncOK;
};
FuncStat value_control(void )
{
for(int i = 0; i < hdallas.onewire->RomCnt; i++)
{
if (sens[i].temperature < sens[i].set_temp - sens[i].hyst)
{
MB_DATA.Coils.coils[0].all |= 1 << i;
MB_DATA.Coils.coils[1].all &= ~(1 << i);
}
else
if (sens[i].temperature > sens[i].set_temp + sens[i].hyst)
{
MB_DATA.Coils.coils[0].all &= ~(1 << i);
MB_DATA.Coils.coils[1].all |= 1 << i;
}
}
return FuncOK;
}
uint16_t handle_valves(TEMP_TypeDef* temp_sense[MAX_SENSE] )
{
if (temp_sense[0]->state == STATE_OPEN_VALVE)
{
GPIOC->ODR |= 1 << 14;
}
else if (temp_sense[0]->state == STATE_CLOSE_VALVE)
{
GPIOC->ODR &= ~(1 << 14);
}
return 1;
}
void init_setpoint_all_T_sense(TEMP_TypeDef* temp_sense, int size_array)
{
//ds_search_devices();
for(int i = 0; i < size_array ; i++)
{
temp_sense[i].id[0] = roms[i][0] << 0 | roms[i][1] << 8 | roms[i][2] << 16 | roms[i][3] << 24;
temp_sense[i].id[1] = roms[i][4] << 0 | roms[i][5] << 8 | roms[i][6] << 16 | roms[i][7] << 24;
temp_sense[i].count = i + 1;
temp_sense[i].location = 1;
temp_sense[i].t_open = 22;
temp_sense[i].t_close = 18;
temp_sense[i].status_T_sense = 1;
}
}
/* USER CODE END 4 */
/**
* @brief Period elapsed callback in non blocking mode
* @note This function is called when TIM3 interrupt took place, inside
* HAL_TIM_IRQHandler(). It makes a direct call to HAL_IncTick() to increment
* a global variable "uwTick" used as application time base.
* @param htim : TIM handle
* @retval None
*/
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
{
/* USER CODE BEGIN Callback 0 */
/* USER CODE END Callback 0 */
if (htim->Instance == TIM3)
{
HAL_IncTick();
}
/* USER CODE BEGIN Callback 1 */
/* USER CODE END Callback 1 */
}
/**
* @brief This function is executed in case of error occurrence.
* @retval None
*/
void Error_Handler(void)
{
/* USER CODE BEGIN Error_Handler_Debug */
/* User can add his own implementation to report the HAL error return state */
__disable_irq();
while (1)
{
}
/* USER CODE END Error_Handler_Debug */
}
#ifdef USE_FULL_ASSERT
/**
* @brief Reports the name of the source file and the source line number
* where the assert_param error has occurred.
* @param file: pointer to the source file name
* @param line: assert_param error line source number
* @retval None
*/
void assert_failed(uint8_t *file, uint32_t line)
{
/* USER CODE BEGIN 6 */
/* User can add his own implementation to report the file name and line number,
ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) */
/* USER CODE END 6 */
}
#endif /* USE_FULL_ASSERT */

View File

@@ -53,7 +53,7 @@ volatile uint32_t *config_reg = (OW_Pin_Numb < 8) ? &(OW->DataPort->CRL) : &(OW-
}
HAL_GPIO_Init(OW->DataPort, &GPIO_InitStruct);
#endif
#endif
#endif
}
/**
@@ -98,7 +98,7 @@ uint8_t OneWire_Pin_Read(OneWire_t* OW)
#else
#ifdef LL_Driver
return ((OW->DataPort->IDR & OW->DataPin) != 0x00U) ? 1 : 0;
#else
#else6
return HAL_GPIO_ReadPin(OW->DataPort, OW->DataPin);
#endif
#endif

View File

@@ -45,7 +45,7 @@ void MX_RTC_Init(void)
*/
hrtc.Instance = RTC;
hrtc.Init.AsynchPrediv = RTC_AUTO_1_SECOND;
hrtc.Init.OutPut = RTC_OUTPUTSOURCE_NONE;
hrtc.Init.OutPut = RTC_OUTPUTSOURCE_SECOND;
if (HAL_RTC_Init(&hrtc) != HAL_OK)
{
Error_Handler();
@@ -57,23 +57,24 @@ void MX_RTC_Init(void)
/** Initialize RTC and set the Time and Date
*/
sTime.Hours = 0x0;
sTime.Minutes = 0x0;
sTime.Seconds = 0x0;
// sTime.Hours = 0x0;
// sTime.Minutes = 0x0;
// sTime.Seconds = 0x0;
if (HAL_RTC_SetTime(&hrtc, &sTime, RTC_FORMAT_BCD) != HAL_OK)
{
Error_Handler();
}
DateToUpdate.WeekDay = RTC_WEEKDAY_MONDAY;
DateToUpdate.Month = RTC_MONTH_JANUARY;
DateToUpdate.Date = 0x1;
DateToUpdate.Year = 0x0;
// // if (HAL_RTC_SetTime(&hrtc, &sTime, RTC_FORMAT_BCD) != HAL_OK)
// {
// Error_Handler();
// }
// DateToUpdate.WeekDay = RTC_WEEKDAY_MONDAY;
// DateToUpdate.Month = RTC_MONTH_JANUARY;
// DateToUpdate.Date = 0x1;
// DateToUpdate.Year = 0x0;
if (HAL_RTC_SetDate(&hrtc, &DateToUpdate, RTC_FORMAT_BCD) != HAL_OK)
{
Error_Handler();
}
// if (HAL_RTC_SetDate(&hrtc, &DateToUpdate, RTC_FORMAT_BCD) != HAL_OK)
// {
// Error_Handler();
// }
/* USER CODE BEGIN RTC_Init 2 */
/* USER CODE END RTC_Init 2 */
@@ -119,7 +120,7 @@ void HAL_RTC_MspDeInit(RTC_HandleTypeDef* rtcHandle)
/* USER CODE BEGIN RTC_MspDeInit 1 */
/* USER CODE END RTC_MspDeInit 1 */
}
}
}
/* USER CODE BEGIN 1 */

View File

@@ -44,7 +44,7 @@ void MX_SPI1_Init(void)
hspi1.Init.CLKPolarity = SPI_POLARITY_LOW;
hspi1.Init.CLKPhase = SPI_PHASE_1EDGE;
hspi1.Init.NSS = SPI_NSS_SOFT;
hspi1.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_4;
hspi1.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_2;
hspi1.Init.FirstBit = SPI_FIRSTBIT_MSB;
hspi1.Init.TIMode = SPI_TIMODE_DISABLE;
hspi1.Init.CRCCalculation = SPI_CRCCALCULATION_DISABLE;

View File

@@ -1,3 +1,4 @@
/* USER CODE BEGIN Header */
/**
******************************************************************************

View File

@@ -46,15 +46,12 @@ HAL_StatusTypeDef HAL_InitTick(uint32_t TickPriority)
uint32_t uwPrescalerValue = 0U;
uint32_t pFLatency;
HAL_StatusTypeDef status = HAL_OK;
/* Enable TIM3 clock */
__HAL_RCC_TIM3_CLK_ENABLE();
/* Get clock configuration */
HAL_RCC_GetClockConfig(&clkconfig, &pFLatency);
/* Get APB1 prescaler */
uwAPB1Prescaler = clkconfig.APB1CLKDivider;
/* Compute TIM3 clock */
@@ -74,11 +71,12 @@ HAL_StatusTypeDef HAL_InitTick(uint32_t TickPriority)
htim3.Instance = TIM3;
/* Initialize TIMx peripheral as follow:
* Period = [(TIM3CLK/1000) - 1]. to have a (1/1000) s time base.
* Prescaler = (uwTimclock/1000000 - 1) to have a 1MHz counter clock.
* ClockDivision = 0
* Counter direction = Up
*/
+ Period = [(TIM3CLK/1000) - 1]. to have a (1/1000) s time base.
+ Prescaler = (uwTimclock/1000000 - 1) to have a 1MHz counter clock.
+ ClockDivision = 0
+ Counter direction = Up
*/
htim3.Init.Period = (1000000U / 1000U) - 1U;
htim3.Init.Prescaler = uwPrescalerValue;
htim3.Init.ClockDivision = 0;

View File

@@ -22,7 +22,7 @@
#include "stm32f1xx_it.h"
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include "modbus.h"
#include "rs_message.h"
/* USER CODE END Includes */
/* Private typedef -----------------------------------------------------------*/
@@ -281,12 +281,11 @@ void TIM1_CC_IRQHandler(void)
void TIM2_IRQHandler(void)
{
/* USER CODE BEGIN TIM2_IRQn 0 */
RS_TIM_Handler(&hmodbus1);
return;
/* USER CODE END TIM2_IRQn 0 */
HAL_TIM_IRQHandler(&htim2);
/* USER CODE BEGIN TIM2_IRQn 1 */
//RS_TIM_Handler(&hmodbus1);
RS_TIM_Handler(&hmodbus1);
/* USER CODE END TIM2_IRQn 1 */
}
@@ -314,12 +313,11 @@ static uint8_t first_in=1;
void USART1_IRQHandler(void)
{
/* USER CODE BEGIN USART1_IRQn 0 */
RS_UART_Handler(&hmodbus1);
return;
/* USER CODE END USART1_IRQn 0 */
HAL_UART_IRQHandler(&huart1);
/* USER CODE BEGIN USART1_IRQn 1 */
//RS_UART_Handler(&hmodbus1);
RS_UART_Handler(&hmodbus1);
/* USER CODE END USART1_IRQn 1 */

View File

@@ -83,7 +83,7 @@ void MX_TIM2_Init(void)
/* USER CODE END TIM2_Init 1 */
htim2.Instance = TIM2;
htim2.Init.Prescaler = 72-1;
htim2.Init.Prescaler = 7199;
htim2.Init.CounterMode = TIM_COUNTERMODE_UP;
htim2.Init.Period = 65535;
htim2.Init.ClockDivision = TIM_CLOCKDIVISION_DIV1;

View File

@@ -36,7 +36,7 @@ void MX_USART1_UART_Init(void)
/* USER CODE END USART1_Init 0 */
/* USER CODE BEGIN USART1_Init 1 */
huart1.ReceptionType=HAL_UART_RECEPTION_TOIDLE;
/* USER CODE END USART1_Init 1 */
huart1.Instance = USART1;
huart1.Init.BaudRate = 115200;

View File

@@ -1,6 +1,6 @@
/**
******************************************************************************
* @file stm32f103xb.h
* @file stm32f103x6.h
* @author MCD Application Team
* @brief CMSIS Cortex-M3 Device Peripheral Access Layer Header File.
* This file contains all the peripheral register's definitions, bits
@@ -29,12 +29,12 @@
* @{
*/
/** @addtogroup stm32f103xb
/** @addtogroup stm32f103x6
* @{
*/
#ifndef __STM32F103xB_H
#define __STM32F103xB_H
#ifndef __STM32F103x6_H
#define __STM32F103x6_H
#ifdef __cplusplus
extern "C" {
@@ -109,16 +109,11 @@ typedef enum
TIM1_CC_IRQn = 27, /*!< TIM1 Capture Compare Interrupt */
TIM2_IRQn = 28, /*!< TIM2 global Interrupt */
TIM3_IRQn = 29, /*!< TIM3 global Interrupt */
TIM4_IRQn = 30, /*!< TIM4 global Interrupt */
I2C1_EV_IRQn = 31, /*!< I2C1 Event Interrupt */
I2C1_ER_IRQn = 32, /*!< I2C1 Error Interrupt */
I2C2_EV_IRQn = 33, /*!< I2C2 Event Interrupt */
I2C2_ER_IRQn = 34, /*!< I2C2 Error Interrupt */
SPI1_IRQn = 35, /*!< SPI1 global Interrupt */
SPI2_IRQn = 36, /*!< SPI2 global Interrupt */
USART1_IRQn = 37, /*!< USART1 global Interrupt */
USART2_IRQn = 38, /*!< USART2 global Interrupt */
USART3_IRQn = 39, /*!< USART3 global Interrupt */
EXTI15_10_IRQn = 40, /*!< External Line[15:10] Interrupts */
RTC_Alarm_IRQn = 41, /*!< RTC Alarm through EXTI Line Interrupt */
USBWakeUp_IRQn = 42, /*!< USB Device WakeUp from suspend through EXTI Line Interrupt */
@@ -570,7 +565,7 @@ typedef struct
#define FLASH_BASE 0x08000000UL /*!< FLASH base address in the alias region */
#define FLASH_BANK1_END 0x0801FFFFUL /*!< FLASH END address of bank1 */
#define FLASH_BANK1_END 0x08007FFFUL /*!< FLASH END address of bank1 */
#define SRAM_BASE 0x20000000UL /*!< SRAM base address in the alias region */
#define PERIPH_BASE 0x40000000UL /*!< Peripheral base address in the alias region */
@@ -585,15 +580,11 @@ typedef struct
#define TIM2_BASE (APB1PERIPH_BASE + 0x00000000UL)
#define TIM3_BASE (APB1PERIPH_BASE + 0x00000400UL)
#define TIM4_BASE (APB1PERIPH_BASE + 0x00000800UL)
#define RTC_BASE (APB1PERIPH_BASE + 0x00002800UL)
#define WWDG_BASE (APB1PERIPH_BASE + 0x00002C00UL)
#define IWDG_BASE (APB1PERIPH_BASE + 0x00003000UL)
#define SPI2_BASE (APB1PERIPH_BASE + 0x00003800UL)
#define USART2_BASE (APB1PERIPH_BASE + 0x00004400UL)
#define USART3_BASE (APB1PERIPH_BASE + 0x00004800UL)
#define I2C1_BASE (APB1PERIPH_BASE + 0x00005400UL)
#define I2C2_BASE (APB1PERIPH_BASE + 0x00005800UL)
#define CAN1_BASE (APB1PERIPH_BASE + 0x00006400UL)
#define BKP_BASE (APB1PERIPH_BASE + 0x00006C00UL)
#define PWR_BASE (APB1PERIPH_BASE + 0x00007000UL)
@@ -603,7 +594,6 @@ typedef struct
#define GPIOB_BASE (APB2PERIPH_BASE + 0x00000C00UL)
#define GPIOC_BASE (APB2PERIPH_BASE + 0x00001000UL)
#define GPIOD_BASE (APB2PERIPH_BASE + 0x00001400UL)
#define GPIOE_BASE (APB2PERIPH_BASE + 0x00001800UL)
#define ADC1_BASE (APB2PERIPH_BASE + 0x00002400UL)
#define ADC2_BASE (APB2PERIPH_BASE + 0x00002800UL)
#define TIM1_BASE (APB2PERIPH_BASE + 0x00002C00UL)
@@ -646,15 +636,11 @@ typedef struct
#define TIM2 ((TIM_TypeDef *)TIM2_BASE)
#define TIM3 ((TIM_TypeDef *)TIM3_BASE)
#define TIM4 ((TIM_TypeDef *)TIM4_BASE)
#define RTC ((RTC_TypeDef *)RTC_BASE)
#define WWDG ((WWDG_TypeDef *)WWDG_BASE)
#define IWDG ((IWDG_TypeDef *)IWDG_BASE)
#define SPI2 ((SPI_TypeDef *)SPI2_BASE)
#define USART2 ((USART_TypeDef *)USART2_BASE)
#define USART3 ((USART_TypeDef *)USART3_BASE)
#define I2C1 ((I2C_TypeDef *)I2C1_BASE)
#define I2C2 ((I2C_TypeDef *)I2C2_BASE)
#define USB ((USB_TypeDef *)USB_BASE)
#define CAN1 ((CAN_TypeDef *)CAN1_BASE)
#define BKP ((BKP_TypeDef *)BKP_BASE)
@@ -665,7 +651,6 @@ typedef struct
#define GPIOB ((GPIO_TypeDef *)GPIOB_BASE)
#define GPIOC ((GPIO_TypeDef *)GPIOC_BASE)
#define GPIOD ((GPIO_TypeDef *)GPIOD_BASE)
#define GPIOE ((GPIO_TypeDef *)GPIOE_BASE)
#define ADC1 ((ADC_TypeDef *)ADC1_BASE)
#define ADC2 ((ADC_TypeDef *)ADC2_BASE)
#define ADC12_COMMON ((ADC_Common_TypeDef *)ADC1_BASE)
@@ -1200,9 +1185,6 @@ typedef struct
#define RCC_APB2RSTR_USART1RST RCC_APB2RSTR_USART1RST_Msk /*!< USART1 reset */
#define RCC_APB2RSTR_IOPERST_Pos (6U)
#define RCC_APB2RSTR_IOPERST_Msk (0x1UL << RCC_APB2RSTR_IOPERST_Pos) /*!< 0x00000040 */
#define RCC_APB2RSTR_IOPERST RCC_APB2RSTR_IOPERST_Msk /*!< I/O port E reset */
@@ -1235,18 +1217,6 @@ typedef struct
#define RCC_APB1RSTR_PWRRST_Msk (0x1UL << RCC_APB1RSTR_PWRRST_Pos) /*!< 0x10000000 */
#define RCC_APB1RSTR_PWRRST RCC_APB1RSTR_PWRRST_Msk /*!< Power interface reset */
#define RCC_APB1RSTR_TIM4RST_Pos (2U)
#define RCC_APB1RSTR_TIM4RST_Msk (0x1UL << RCC_APB1RSTR_TIM4RST_Pos) /*!< 0x00000004 */
#define RCC_APB1RSTR_TIM4RST RCC_APB1RSTR_TIM4RST_Msk /*!< Timer 4 reset */
#define RCC_APB1RSTR_SPI2RST_Pos (14U)
#define RCC_APB1RSTR_SPI2RST_Msk (0x1UL << RCC_APB1RSTR_SPI2RST_Pos) /*!< 0x00004000 */
#define RCC_APB1RSTR_SPI2RST RCC_APB1RSTR_SPI2RST_Msk /*!< SPI 2 reset */
#define RCC_APB1RSTR_USART3RST_Pos (18U)
#define RCC_APB1RSTR_USART3RST_Msk (0x1UL << RCC_APB1RSTR_USART3RST_Pos) /*!< 0x00040000 */
#define RCC_APB1RSTR_USART3RST RCC_APB1RSTR_USART3RST_Msk /*!< USART 3 reset */
#define RCC_APB1RSTR_I2C2RST_Pos (22U)
#define RCC_APB1RSTR_I2C2RST_Msk (0x1UL << RCC_APB1RSTR_I2C2RST_Pos) /*!< 0x00400000 */
#define RCC_APB1RSTR_I2C2RST RCC_APB1RSTR_I2C2RST_Msk /*!< I2C 2 reset */
#define RCC_APB1RSTR_USBRST_Pos (23U)
#define RCC_APB1RSTR_USBRST_Msk (0x1UL << RCC_APB1RSTR_USBRST_Pos) /*!< 0x00800000 */
@@ -1309,9 +1279,6 @@ typedef struct
#define RCC_APB2ENR_USART1EN RCC_APB2ENR_USART1EN_Msk /*!< USART1 clock enable */
#define RCC_APB2ENR_IOPEEN_Pos (6U)
#define RCC_APB2ENR_IOPEEN_Msk (0x1UL << RCC_APB2ENR_IOPEEN_Pos) /*!< 0x00000040 */
#define RCC_APB2ENR_IOPEEN RCC_APB2ENR_IOPEEN_Msk /*!< I/O port E clock enable */
@@ -1344,18 +1311,6 @@ typedef struct
#define RCC_APB1ENR_PWREN_Msk (0x1UL << RCC_APB1ENR_PWREN_Pos) /*!< 0x10000000 */
#define RCC_APB1ENR_PWREN RCC_APB1ENR_PWREN_Msk /*!< Power interface clock enable */
#define RCC_APB1ENR_TIM4EN_Pos (2U)
#define RCC_APB1ENR_TIM4EN_Msk (0x1UL << RCC_APB1ENR_TIM4EN_Pos) /*!< 0x00000004 */
#define RCC_APB1ENR_TIM4EN RCC_APB1ENR_TIM4EN_Msk /*!< Timer 4 clock enable */
#define RCC_APB1ENR_SPI2EN_Pos (14U)
#define RCC_APB1ENR_SPI2EN_Msk (0x1UL << RCC_APB1ENR_SPI2EN_Pos) /*!< 0x00004000 */
#define RCC_APB1ENR_SPI2EN RCC_APB1ENR_SPI2EN_Msk /*!< SPI 2 clock enable */
#define RCC_APB1ENR_USART3EN_Pos (18U)
#define RCC_APB1ENR_USART3EN_Msk (0x1UL << RCC_APB1ENR_USART3EN_Pos) /*!< 0x00040000 */
#define RCC_APB1ENR_USART3EN RCC_APB1ENR_USART3EN_Msk /*!< USART 3 clock enable */
#define RCC_APB1ENR_I2C2EN_Pos (22U)
#define RCC_APB1ENR_I2C2EN_Msk (0x1UL << RCC_APB1ENR_I2C2EN_Pos) /*!< 0x00400000 */
#define RCC_APB1ENR_I2C2EN RCC_APB1ENR_I2C2EN_Msk /*!< I2C 2 clock enable */
#define RCC_APB1ENR_USBEN_Pos (23U)
#define RCC_APB1ENR_USBEN_Msk (0x1UL << RCC_APB1ENR_USBEN_Pos) /*!< 0x00800000 */
@@ -2044,20 +1999,6 @@ typedef struct
#define AFIO_MAPR_USART2_REMAP_Msk (0x1UL << AFIO_MAPR_USART2_REMAP_Pos) /*!< 0x00000008 */
#define AFIO_MAPR_USART2_REMAP AFIO_MAPR_USART2_REMAP_Msk /*!< USART2 remapping */
#define AFIO_MAPR_USART3_REMAP_Pos (4U)
#define AFIO_MAPR_USART3_REMAP_Msk (0x3UL << AFIO_MAPR_USART3_REMAP_Pos) /*!< 0x00000030 */
#define AFIO_MAPR_USART3_REMAP AFIO_MAPR_USART3_REMAP_Msk /*!< USART3_REMAP[1:0] bits (USART3 remapping) */
#define AFIO_MAPR_USART3_REMAP_0 (0x1UL << AFIO_MAPR_USART3_REMAP_Pos) /*!< 0x00000010 */
#define AFIO_MAPR_USART3_REMAP_1 (0x2UL << AFIO_MAPR_USART3_REMAP_Pos) /*!< 0x00000020 */
/* USART3_REMAP configuration */
#define AFIO_MAPR_USART3_REMAP_NOREMAP 0x00000000U /*!< No remap (TX/PB10, RX/PB11, CK/PB12, CTS/PB13, RTS/PB14) */
#define AFIO_MAPR_USART3_REMAP_PARTIALREMAP_Pos (4U)
#define AFIO_MAPR_USART3_REMAP_PARTIALREMAP_Msk (0x1UL << AFIO_MAPR_USART3_REMAP_PARTIALREMAP_Pos) /*!< 0x00000010 */
#define AFIO_MAPR_USART3_REMAP_PARTIALREMAP AFIO_MAPR_USART3_REMAP_PARTIALREMAP_Msk /*!< Partial remap (TX/PC10, RX/PC11, CK/PC12, CTS/PB13, RTS/PB14) */
#define AFIO_MAPR_USART3_REMAP_FULLREMAP_Pos (4U)
#define AFIO_MAPR_USART3_REMAP_FULLREMAP_Msk (0x3UL << AFIO_MAPR_USART3_REMAP_FULLREMAP_Pos) /*!< 0x00000030 */
#define AFIO_MAPR_USART3_REMAP_FULLREMAP AFIO_MAPR_USART3_REMAP_FULLREMAP_Msk /*!< Full remap (TX/PD8, RX/PD9, CK/PD10, CTS/PD11, RTS/PD12) */
#define AFIO_MAPR_TIM1_REMAP_Pos (6U)
#define AFIO_MAPR_TIM1_REMAP_Msk (0x3UL << AFIO_MAPR_TIM1_REMAP_Pos) /*!< 0x000000C0 */
@@ -2107,9 +2048,6 @@ typedef struct
#define AFIO_MAPR_TIM3_REMAP_FULLREMAP_Msk (0x3UL << AFIO_MAPR_TIM3_REMAP_FULLREMAP_Pos) /*!< 0x00000C00 */
#define AFIO_MAPR_TIM3_REMAP_FULLREMAP AFIO_MAPR_TIM3_REMAP_FULLREMAP_Msk /*!< Full remap (CH1/PC6, CH2/PC7, CH3/PC8, CH4/PC9) */
#define AFIO_MAPR_TIM4_REMAP_Pos (12U)
#define AFIO_MAPR_TIM4_REMAP_Msk (0x1UL << AFIO_MAPR_TIM4_REMAP_Pos) /*!< 0x00001000 */
#define AFIO_MAPR_TIM4_REMAP AFIO_MAPR_TIM4_REMAP_Msk /*!< TIM4_REMAP bit (TIM4 remapping) */
#define AFIO_MAPR_CAN_REMAP_Pos (13U)
#define AFIO_MAPR_CAN_REMAP_Msk (0x3UL << AFIO_MAPR_CAN_REMAP_Pos) /*!< 0x00006000 */
@@ -9662,18 +9600,12 @@ typedef struct
#define DBGMCU_CR_DBG_TIM3_STOP_Pos (12U)
#define DBGMCU_CR_DBG_TIM3_STOP_Msk (0x1UL << DBGMCU_CR_DBG_TIM3_STOP_Pos) /*!< 0x00001000 */
#define DBGMCU_CR_DBG_TIM3_STOP DBGMCU_CR_DBG_TIM3_STOP_Msk /*!< TIM3 counter stopped when core is halted */
#define DBGMCU_CR_DBG_TIM4_STOP_Pos (13U)
#define DBGMCU_CR_DBG_TIM4_STOP_Msk (0x1UL << DBGMCU_CR_DBG_TIM4_STOP_Pos) /*!< 0x00002000 */
#define DBGMCU_CR_DBG_TIM4_STOP DBGMCU_CR_DBG_TIM4_STOP_Msk /*!< TIM4 counter stopped when core is halted */
#define DBGMCU_CR_DBG_CAN1_STOP_Pos (14U)
#define DBGMCU_CR_DBG_CAN1_STOP_Msk (0x1UL << DBGMCU_CR_DBG_CAN1_STOP_Pos) /*!< 0x00004000 */
#define DBGMCU_CR_DBG_CAN1_STOP DBGMCU_CR_DBG_CAN1_STOP_Msk /*!< Debug CAN1 stopped when Core is halted */
#define DBGMCU_CR_DBG_I2C1_SMBUS_TIMEOUT_Pos (15U)
#define DBGMCU_CR_DBG_I2C1_SMBUS_TIMEOUT_Msk (0x1UL << DBGMCU_CR_DBG_I2C1_SMBUS_TIMEOUT_Pos) /*!< 0x00008000 */
#define DBGMCU_CR_DBG_I2C1_SMBUS_TIMEOUT DBGMCU_CR_DBG_I2C1_SMBUS_TIMEOUT_Msk /*!< SMBUS timeout mode stopped when Core is halted */
#define DBGMCU_CR_DBG_I2C2_SMBUS_TIMEOUT_Pos (16U)
#define DBGMCU_CR_DBG_I2C2_SMBUS_TIMEOUT_Msk (0x1UL << DBGMCU_CR_DBG_I2C2_SMBUS_TIMEOUT_Pos) /*!< 0x00010000 */
#define DBGMCU_CR_DBG_I2C2_SMBUS_TIMEOUT DBGMCU_CR_DBG_I2C2_SMBUS_TIMEOUT_Msk /*!< SMBUS timeout mode stopped when Core is halted */
/******************************************************************************/
/* */
@@ -9846,30 +9778,6 @@ typedef struct
#define FLASH_WRP0_nWRP0_Msk (0xFFUL << FLASH_WRP0_nWRP0_Pos) /*!< 0x0000FF00 */
#define FLASH_WRP0_nWRP0 FLASH_WRP0_nWRP0_Msk /*!< Flash memory write protection complemented option bytes */
/****************** Bit definition for FLASH_WRP1 register ******************/
#define FLASH_WRP1_WRP1_Pos (16U)
#define FLASH_WRP1_WRP1_Msk (0xFFUL << FLASH_WRP1_WRP1_Pos) /*!< 0x00FF0000 */
#define FLASH_WRP1_WRP1 FLASH_WRP1_WRP1_Msk /*!< Flash memory write protection option bytes */
#define FLASH_WRP1_nWRP1_Pos (24U)
#define FLASH_WRP1_nWRP1_Msk (0xFFUL << FLASH_WRP1_nWRP1_Pos) /*!< 0xFF000000 */
#define FLASH_WRP1_nWRP1 FLASH_WRP1_nWRP1_Msk /*!< Flash memory write protection complemented option bytes */
/****************** Bit definition for FLASH_WRP2 register ******************/
#define FLASH_WRP2_WRP2_Pos (0U)
#define FLASH_WRP2_WRP2_Msk (0xFFUL << FLASH_WRP2_WRP2_Pos) /*!< 0x000000FF */
#define FLASH_WRP2_WRP2 FLASH_WRP2_WRP2_Msk /*!< Flash memory write protection option bytes */
#define FLASH_WRP2_nWRP2_Pos (8U)
#define FLASH_WRP2_nWRP2_Msk (0xFFUL << FLASH_WRP2_nWRP2_Pos) /*!< 0x0000FF00 */
#define FLASH_WRP2_nWRP2 FLASH_WRP2_nWRP2_Msk /*!< Flash memory write protection complemented option bytes */
/****************** Bit definition for FLASH_WRP3 register ******************/
#define FLASH_WRP3_WRP3_Pos (16U)
#define FLASH_WRP3_WRP3_Msk (0xFFUL << FLASH_WRP3_WRP3_Pos) /*!< 0x00FF0000 */
#define FLASH_WRP3_WRP3 FLASH_WRP3_WRP3_Msk /*!< Flash memory write protection option bytes */
#define FLASH_WRP3_nWRP3_Pos (24U)
#define FLASH_WRP3_nWRP3_Msk (0xFFUL << FLASH_WRP3_nWRP3_Pos) /*!< 0xFF000000 */
#define FLASH_WRP3_nWRP3 FLASH_WRP3_nWRP3_Msk /*!< Flash memory write protection complemented option bytes */
/**
@@ -9915,8 +9823,7 @@ typedef struct
#define IS_GPIO_ALL_INSTANCE(INSTANCE) (((INSTANCE) == GPIOA) || \
((INSTANCE) == GPIOB) || \
((INSTANCE) == GPIOC) || \
((INSTANCE) == GPIOD) || \
((INSTANCE) == GPIOE))
((INSTANCE) == GPIOD))
/**************************** GPIO Alternate Function Instances ***************/
#define IS_GPIO_AF_INSTANCE(INSTANCE) IS_GPIO_ALL_INSTANCE(INSTANCE)
@@ -9925,8 +9832,7 @@ typedef struct
#define IS_GPIO_LOCK_INSTANCE(INSTANCE) IS_GPIO_ALL_INSTANCE(INSTANCE)
/******************************** I2C Instances *******************************/
#define IS_I2C_ALL_INSTANCE(INSTANCE) (((INSTANCE) == I2C1) || \
((INSTANCE) == I2C2))
#define IS_I2C_ALL_INSTANCE(INSTANCE) ((INSTANCE) == I2C1)
/******************************* SMBUS Instances ******************************/
#define IS_SMBUS_ALL_INSTANCE IS_I2C_ALL_INSTANCE
@@ -9935,102 +9841,86 @@ typedef struct
#define IS_IWDG_ALL_INSTANCE(INSTANCE) ((INSTANCE) == IWDG)
/******************************** SPI Instances *******************************/
#define IS_SPI_ALL_INSTANCE(INSTANCE) (((INSTANCE) == SPI1) || \
((INSTANCE) == SPI2))
#define IS_SPI_ALL_INSTANCE(INSTANCE) ((INSTANCE) == SPI1)
/****************************** START TIM Instances ***************************/
/****************************** TIM Instances *********************************/
#define IS_TIM_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_ADVANCED_INSTANCE(INSTANCE) ((INSTANCE) == TIM1)
#define IS_TIM_CC1_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_CC2_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_CC3_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_CC4_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_CLOCKSOURCE_ETRMODE1_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_CLOCKSOURCE_ETRMODE2_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_CLOCKSOURCE_TIX_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_CLOCKSOURCE_ITRX_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_OCXREF_CLEAR_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_ENCODER_INTERFACE_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_XOR_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_MASTER_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_SLAVE_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_DMABURST_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_BREAK_INSTANCE(INSTANCE)\
((INSTANCE) == TIM1)
@@ -10049,12 +9939,6 @@ typedef struct
((CHANNEL) == TIM_CHANNEL_4))) \
|| \
(((INSTANCE) == TIM3) && \
(((CHANNEL) == TIM_CHANNEL_1) || \
((CHANNEL) == TIM_CHANNEL_2) || \
((CHANNEL) == TIM_CHANNEL_3) || \
((CHANNEL) == TIM_CHANNEL_4))) \
|| \
(((INSTANCE) == TIM4) && \
(((CHANNEL) == TIM_CHANNEL_1) || \
((CHANNEL) == TIM_CHANNEL_2) || \
((CHANNEL) == TIM_CHANNEL_3) || \
@@ -10069,8 +9953,7 @@ typedef struct
#define IS_TIM_COUNTER_MODE_SELECT_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_REPETITION_COUNTER_INSTANCE(INSTANCE)\
((INSTANCE) == TIM1)
@@ -10078,33 +9961,28 @@ typedef struct
#define IS_TIM_CLOCK_DIVISION_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_DMA_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_DMA_CC_INSTANCE(INSTANCE)\
(((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_COMMUTATION_EVENT_INSTANCE(INSTANCE)\
((INSTANCE) == TIM1)
#define IS_TIM_ETR_INSTANCE(INSTANCE) (((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_HALL_SENSOR_INTERFACE_INSTANCE(INSTANCE) (((INSTANCE) == TIM1) || \
((INSTANCE) == TIM2) || \
((INSTANCE) == TIM3) || \
((INSTANCE) == TIM4))
((INSTANCE) == TIM3))
#define IS_TIM_32B_COUNTER_INSTANCE(INSTANCE) 0U
@@ -10113,48 +9991,39 @@ typedef struct
/******************** USART Instances : Synchronous mode **********************/
#define IS_USART_INSTANCE(INSTANCE) (((INSTANCE) == USART1) || \
((INSTANCE) == USART2) || \
((INSTANCE) == USART3))
((INSTANCE) == USART2))
/******************** UART Instances : Asynchronous mode **********************/
#define IS_UART_INSTANCE(INSTANCE) (((INSTANCE) == USART1) || \
((INSTANCE) == USART2) || \
((INSTANCE) == USART3))
((INSTANCE) == USART2) )
/******************** UART Instances : Half-Duplex mode **********************/
#define IS_UART_HALFDUPLEX_INSTANCE(INSTANCE) (((INSTANCE) == USART1) || \
((INSTANCE) == USART2) || \
((INSTANCE) == USART3))
((INSTANCE) == USART2) )
/******************** UART Instances : LIN mode **********************/
#define IS_UART_LIN_INSTANCE(INSTANCE) (((INSTANCE) == USART1) || \
((INSTANCE) == USART2) || \
((INSTANCE) == USART3))
((INSTANCE) == USART2) )
/****************** UART Instances : Hardware Flow control ********************/
#define IS_UART_HWFLOW_INSTANCE(INSTANCE) (((INSTANCE) == USART1) || \
((INSTANCE) == USART2) || \
((INSTANCE) == USART3))
((INSTANCE) == USART2) )
/********************* UART Instances : Smard card mode ***********************/
#define IS_SMARTCARD_INSTANCE(INSTANCE) (((INSTANCE) == USART1) || \
((INSTANCE) == USART2) || \
((INSTANCE) == USART3))
((INSTANCE) == USART2) )
/*********************** UART Instances : IRDA mode ***************************/
#define IS_IRDA_INSTANCE(INSTANCE) (((INSTANCE) == USART1) || \
((INSTANCE) == USART2) || \
((INSTANCE) == USART3))
((INSTANCE) == USART2) )
/***************** UART Instances : Multi-Processor mode **********************/
#define IS_UART_MULTIPROCESSOR_INSTANCE(INSTANCE) (((INSTANCE) == USART1) || \
((INSTANCE) == USART2) || \
((INSTANCE) == USART3))
((INSTANCE) == USART2) )
/***************** UART Instances : DMA mode available **********************/
#define IS_UART_DMA_INSTANCE(INSTANCE) (((INSTANCE) == USART1) || \
((INSTANCE) == USART2) || \
((INSTANCE) == USART3))
((INSTANCE) == USART2))
/****************************** RTC Instances *********************************/
#define IS_RTC_ALL_INSTANCE(INSTANCE) ((INSTANCE) == RTC)
@@ -10185,40 +10054,40 @@ typedef struct
/* Aliases for __IRQn */
#define ADC1_IRQn ADC1_2_IRQn
#define TIM9_IRQn TIM1_BRK_IRQn
#define TIM1_BRK_TIM9_IRQn TIM1_BRK_IRQn
#define TIM1_BRK_TIM15_IRQn TIM1_BRK_IRQn
#define TIM1_TRG_COM_TIM17_IRQn TIM1_TRG_COM_IRQn
#define TIM9_IRQn TIM1_BRK_IRQn
#define TIM1_TRG_COM_TIM11_IRQn TIM1_TRG_COM_IRQn
#define TIM1_TRG_COM_TIM17_IRQn TIM1_TRG_COM_IRQn
#define TIM11_IRQn TIM1_TRG_COM_IRQn
#define TIM10_IRQn TIM1_UP_IRQn
#define TIM1_UP_TIM10_IRQn TIM1_UP_IRQn
#define TIM10_IRQn TIM1_UP_IRQn
#define TIM1_UP_TIM16_IRQn TIM1_UP_IRQn
#define OTG_FS_WKUP_IRQn USBWakeUp_IRQn
#define CEC_IRQn USBWakeUp_IRQn
#define OTG_FS_WKUP_IRQn USBWakeUp_IRQn
#define USB_HP_IRQn USB_HP_CAN1_TX_IRQn
#define CAN1_TX_IRQn USB_HP_CAN1_TX_IRQn
#define CAN1_RX0_IRQn USB_LP_CAN1_RX0_IRQn
#define USB_LP_IRQn USB_LP_CAN1_RX0_IRQn
#define CAN1_RX0_IRQn USB_LP_CAN1_RX0_IRQn
/* Aliases for __IRQHandler */
#define ADC1_IRQHandler ADC1_2_IRQHandler
#define TIM9_IRQHandler TIM1_BRK_IRQHandler
#define TIM1_BRK_TIM9_IRQHandler TIM1_BRK_IRQHandler
#define TIM1_BRK_TIM15_IRQHandler TIM1_BRK_IRQHandler
#define TIM1_TRG_COM_TIM17_IRQHandler TIM1_TRG_COM_IRQHandler
#define TIM9_IRQHandler TIM1_BRK_IRQHandler
#define TIM1_TRG_COM_TIM11_IRQHandler TIM1_TRG_COM_IRQHandler
#define TIM1_TRG_COM_TIM17_IRQHandler TIM1_TRG_COM_IRQHandler
#define TIM11_IRQHandler TIM1_TRG_COM_IRQHandler
#define TIM10_IRQHandler TIM1_UP_IRQHandler
#define TIM1_UP_TIM10_IRQHandler TIM1_UP_IRQHandler
#define TIM10_IRQHandler TIM1_UP_IRQHandler
#define TIM1_UP_TIM16_IRQHandler TIM1_UP_IRQHandler
#define OTG_FS_WKUP_IRQHandler USBWakeUp_IRQHandler
#define CEC_IRQHandler USBWakeUp_IRQHandler
#define OTG_FS_WKUP_IRQHandler USBWakeUp_IRQHandler
#define USB_HP_IRQHandler USB_HP_CAN1_TX_IRQHandler
#define CAN1_TX_IRQHandler USB_HP_CAN1_TX_IRQHandler
#define CAN1_RX0_IRQHandler USB_LP_CAN1_RX0_IRQHandler
#define USB_LP_IRQHandler USB_LP_CAN1_RX0_IRQHandler
#define CAN1_RX0_IRQHandler USB_LP_CAN1_RX0_IRQHandler
/**
@@ -10234,7 +10103,7 @@ typedef struct
}
#endif /* __cplusplus */
#endif /* __STM32F103xB_H */
#endif /* __STM32F103x6_H */

View File

@@ -1,56 +0,0 @@
#ifndef EEPROM_EMUL_H
#define EEPROM_EMUL_H
#include "stm32f1xx_hal.h"
// Адреса для эмуляции EEPROM (последние страницы Flash)
#define EEPROM_START_ADDRESS 0x0800F000 // Последний килобайт Flash
#define EEPROM_PAGE_SIZE 1024 // Размер страницы STM32F103
#define EEPROM_SIZE 1024 // Общий размер EEPROM
// Максимальное количество переменных
#define EEPROM_MAX_VARIABLES 64
// Статусы операций
typedef enum {
EEPROM_OK = 0,
EEPROM_ERROR = 1,
EEPROM_INVALID = 2,
EEPROM_FULL = 3
} EEPROM_Status;
// Структура элемента данных
#pragma pack(push, 1)
typedef struct {
uint16_t address; // Адрес переменной (0-EEPROM_MAX_VARIABLES)
uint16_t data; // Данные
uint32_t timestamp; // Временная метка
} EEPROM_Item;
#pragma pack(pop)
typedef struct {
uint8_t data[EEPROM_SIZE]; // Массив для хранения данных
uint16_t head; // Указатель на место записи
uint16_t tail; // Указатель на место чтения
} RingBuffer_t;
// Инициализация EEPROM
EEPROM_Status EEPROM_Init(void);
// Чтение данных
EEPROM_Status EEPROM_Read(uint16_t virt_address, uint16_t* data);
// Запись данных
EEPROM_Status EEPROM_Write(uint16_t virt_address, uint16_t data);
// Массовая запись
EEPROM_Status EEPROM_WriteMultiple(uint16_t virt_address, uint8_t* data, uint16_t size);
// Получение информации о EEPROM
void EEPROM_GetInfo(uint32_t* used, uint32_t* total);
// Полное форматирование
EEPROM_Status EEPROM_Format(void);
#endif

View File

@@ -1,31 +0,0 @@
#ifndef FLASH_RING_H
#define FLASH_RING_H
#include "stm32f1xx_hal.h"
//#define FLASH_PAGE_SIZE 1024
#define NUM_OF_PAGE_EEPROM 2
#define FLASH_START_ADDR 0x08000000
#define FLASH_SIZE (64 * 1024) // для STM32F103C8
#define LAST_PAGE_ADDR (FLASH_START_ADDR + FLASH_SIZE - NUM_OF_PAGE_EEPROM*FLASH_PAGE_SIZE)
#define RECORD_SIZE 255
#define RECORDS_PER_PAGE NUM_OF_PAGE_EEPROM*(FLASH_PAGE_SIZE / RECORD_SIZE) // 10 записей
#pragma pack(push, 1)
typedef struct {
uint32_t timestamp;
uint8_t data[RECORD_SIZE-4]; // 200 - 4 байта timestamp
} FlashRecord_t;
#pragma pack(pop)
typedef struct {
uint32_t write_index; // индекс следующей записи (0-9)
uint8_t initialized; // флаг инициализации
} BufferState_t;
BufferState_t buffer_init(void);
HAL_StatusTypeDef buffer_write_record(FlashRecord_t* record, BufferState_t* state);
HAL_StatusTypeDef erase_flash_page(void) ;
HAL_StatusTypeDef write_flash_record(uint32_t address, FlashRecord_t* record);
FlashRecord_t* buffer_read_record(uint32_t index);
void buffer_get_all_records(FlashRecord_t* records[], uint32_t* count);
#endif // FLASH_RING_H

View File

@@ -1,297 +0,0 @@
//#include "eeprom_emul.h"
#include <string.h>
// Внутренние переменные
static uint32_t eeprom_current_write_address = EEPROM_START_ADDRESS;
static uint8_t eeprom_initialized = 0;
// Прототипы внутренних функций
static EEPROM_Status EEPROM_FindLatestData(uint16_t virt_address, uint16_t* data);
static EEPROM_Status EEPROM_WriteItem(EEPROM_Item* item);
static EEPROM_Status EEPROM_ErasePage(uint32_t address);
static uint32_t EEPROM_FindNextWriteAddress(void);
static uint8_t EEPROM_IsPageErased(uint32_t address);
static uint32_t EEPROM_CalculateCRC(EEPROM_Item* item);
// Инициализация EEPROM
EEPROM_Status EEPROM_Init(void)
{
if (eeprom_initialized)
{
return EEPROM_OK;
}
// Находим следующий адрес для записи
eeprom_current_write_address = EEPROM_FindNextWriteAddress();
// Если вся память заполнена, выполняем сборку мусора (форматирование)
if (eeprom_current_write_address >= EEPROM_START_ADDRESS + EEPROM_SIZE)
{
EEPROM_Format();
}
else
{
eeprom_initialized = 1;
}
return EEPROM_OK;
}
// Чтение данных по виртуальному адресу
EEPROM_Status EEPROM_Read(uint16_t virt_address, uint16_t* data)
{
if (!eeprom_initialized)
{
return EEPROM_ERROR;
}
if (virt_address >= EEPROM_MAX_VARIABLES || data == NULL)
{
return EEPROM_INVALID;
}
return EEPROM_FindLatestData(virt_address, data);
}
// Запись данных по виртуальному адресу
EEPROM_Status EEPROM_Write(uint16_t virt_address, uint16_t data)
{
EEPROM_Item item;
if (!eeprom_initialized)
{
return EEPROM_ERROR;
}
if (virt_address >= EEPROM_MAX_VARIABLES)
{
return EEPROM_INVALID;
}
// Подготавливаем элемент данных
item.address = virt_address;
item.data = data;
item.timestamp = HAL_GetTick(); // Используем системный таймер
// Записываем элемент
return EEPROM_WriteItem(&item);
}
// Поиск последних данных для виртуального адреса
static EEPROM_Status EEPROM_FindLatestData(uint16_t virt_address, uint16_t* data)
{
uint32_t address = EEPROM_START_ADDRESS;
EEPROM_Item current_item;
uint32_t latest_timestamp = 0;
uint16_t latest_data = 0;
uint8_t data_found = 0;
// Сканируем всю область EEPROM
while (address < EEPROM_START_ADDRESS + EEPROM_SIZE)
{
// Читаем элемент
memcpy(&current_item, (void*)address, sizeof(EEPROM_Item));
// Проверяем, является ли это валидными данными
if (current_item.address == virt_address)
{
if (current_item.timestamp >= latest_timestamp)
{
latest_timestamp = current_item.timestamp;
latest_data = current_item.data;
data_found = 1;
}
}
address += sizeof(EEPROM_Item);
// Проверяем конец страницы
if ((address - EEPROM_START_ADDRESS) % EEPROM_PAGE_SIZE == 0)
{
address += (EEPROM_PAGE_SIZE - (sizeof(EEPROM_Item) * 2));
}
}
if (data_found)
{
*data = latest_data;
return EEPROM_OK;
}
return EEPROM_INVALID;
}
// Запись элемента в EEPROM
static EEPROM_Status EEPROM_WriteItem(EEPROM_Item* item)
{
HAL_StatusTypeDef hal_status;
// Проверяем, нужно ли стирать страницу
if ((eeprom_current_write_address - EEPROM_START_ADDRESS) % EEPROM_PAGE_SIZE == 0)
{
if (!EEPROM_IsPageErased(eeprom_current_write_address))
{
if (EEPROM_ErasePage(eeprom_current_write_address) != EEPROM_OK)
{
return EEPROM_ERROR;
}
}
}
// Разблокируем Flash
HAL_FLASH_Unlock();
// Записываем данные по словам (32 бита)
uint32_t* data_ptr = (uint32_t*)item;
for (uint8_t i = 0; i < sizeof(EEPROM_Item) / 4; i++)
{
hal_status = HAL_FLASH_Program(FLASH_TYPEPROGRAM_WORD,
eeprom_current_write_address + (i * 4),
data_ptr[i]);
if (hal_status != HAL_OK)
{
HAL_FLASH_Lock();
return EEPROM_ERROR;
}
}
// Блокируем Flash
HAL_FLASH_Lock();
// Обновляем адрес для следующей записи
eeprom_current_write_address += sizeof(EEPROM_Item);
// Проверяем переполнение
if (eeprom_current_write_address >= EEPROM_START_ADDRESS + EEPROM_SIZE)
{
// Выполняем сборку мусора (в данном случае - форматирование)
EEPROM_Format();
}
return EEPROM_OK;
}
// Стирание страницы Flash
static EEPROM_Status EEPROM_ErasePage(uint32_t address)
{
FLASH_EraseInitTypeDef erase;
uint32_t page_error;
// Определяем номер страницы
uint32_t page = (address - FLASH_BASE) / EEPROM_PAGE_SIZE;
HAL_FLASH_Unlock();
erase.TypeErase = FLASH_TYPEERASE_PAGES;
erase.PageAddress = address;
erase.NbPages = 1;
if (HAL_FLASHEx_Erase(&erase, &page_error) != HAL_OK)
{
HAL_FLASH_Lock();
return EEPROM_ERROR;
}
HAL_FLASH_Lock();
return EEPROM_OK;
}
// Поиск следующего адреса для записи
static uint32_t EEPROM_FindNextWriteAddress(void)
{
uint32_t address = EEPROM_START_ADDRESS;
EEPROM_Item item;
// Ищем первую свободную позицию
while (address < EEPROM_START_ADDRESS + EEPROM_SIZE)
{
memcpy(&item, (void*)address, sizeof(EEPROM_Item));
// Если нашли пустой элемент (все FFFF), это свободная позиция
if (item.address == 0xFFFF && item.data == 0xFFFF && item.timestamp == 0xFFFFFFFF)
{
break;
}
address += sizeof(EEPROM_Item);
// Проверяем границу страницы
if ((address - EEPROM_START_ADDRESS) % EEPROM_PAGE_SIZE == 0)
{
address += (EEPROM_PAGE_SIZE - (sizeof(EEPROM_Item) * 2));
}
}
return address;
}
// Проверка, стерта ли страница
static uint8_t EEPROM_IsPageErased(uint32_t address)
{
uint32_t* check_addr = (uint32_t*)address;
// Проверяем первые несколько слов
for (uint8_t i = 0; i < 8; i++)
{
if (check_addr[i] != 0xFFFFFFFF)
{
return 0;
}
}
return 1;
}
// Полное форматирование EEPROM
EEPROM_Status EEPROM_Format(void)
{
uint32_t address = EEPROM_START_ADDRESS;
// Стираем все страницы, используемые для EEPROM
while (address < EEPROM_START_ADDRESS + EEPROM_SIZE)
{
if (EEPROM_ErasePage(address) != EEPROM_OK)
{
return EEPROM_ERROR;
}
address += EEPROM_PAGE_SIZE;
}
eeprom_current_write_address = EEPROM_START_ADDRESS;
eeprom_initialized = 1;
return EEPROM_OK;
}
// Получение информации об использовании EEPROM
void EEPROM_GetInfo(uint32_t* used, uint32_t* total)
{
uint32_t address = EEPROM_START_ADDRESS;
uint32_t used_bytes = 0;
if (used)
{
// Подсчитываем использованные байты
while (address < EEPROM_START_ADDRESS + EEPROM_SIZE)
{
EEPROM_Item item;
memcpy(&item, (void*)address, sizeof(EEPROM_Item));
if (item.address != 0xFFFF || item.data != 0xFFFF || item.timestamp != 0xFFFFFFFF)
{
used_bytes += sizeof(EEPROM_Item);
}
address += sizeof(EEPROM_Item);
}
*used = used_bytes;
}
if (total)
{
*total = EEPROM_SIZE;
}
}

View File

@@ -1,256 +0,0 @@
#include "eeprom_emul.h"
#include <string.h>
// Внутренние переменные
static uint32_t eeprom_current_write_address = EEPROM_START_ADDRESS;
static uint8_t eeprom_initialized = 0;
// Прототипы внутренних функций
static EEPROM_Status EEPROM_FindLatestData(uint16_t virt_address, uint16_t* data);
static EEPROM_Status EEPROM_WriteItem(EEPROM_Item* item);
static EEPROM_Status EEPROM_ErasePage(uint32_t address);
static uint32_t EEPROM_FindNextWriteAddress(void);
static uint8_t EEPROM_IsPageErased(uint32_t address);
static uint32_t EEPROM_CalculateCRC(EEPROM_Item* item);
// Инициализация EEPROM
EEPROM_Status EEPROM_Init(void) {
if (eeprom_initialized) {
return EEPROM_OK;
}
// Находим следующий адрес для записи
eeprom_current_write_address = EEPROM_FindNextWriteAddress();
// Если вся память заполнена, выполняем сборку мусора (форматирование)
if (eeprom_current_write_address >= EEPROM_START_ADDRESS + EEPROM_SIZE) {
EEPROM_Format();
} else {
eeprom_initialized = 1;
}
return EEPROM_OK;
}
// Чтение данных по виртуальному адресу
EEPROM_Status EEPROM_Read(uint16_t virt_address, uint16_t* data) {
if (!eeprom_initialized) {
return EEPROM_ERROR;
}
if (virt_address >= EEPROM_MAX_VARIABLES || data == NULL) {
return EEPROM_INVALID;
}
return EEPROM_FindLatestData(virt_address, data);
}
// Запись данных по виртуальному адресу
EEPROM_Status EEPROM_Write(uint16_t virt_address, uint16_t data) {
EEPROM_Item item;
if (!eeprom_initialized) {
return EEPROM_ERROR;
}
if (virt_address >= EEPROM_MAX_VARIABLES) {
return EEPROM_INVALID;
}
// Подготавливаем элемент данных
item.address = virt_address;
item.data = data;
item.timestamp = HAL_GetTick(); // Используем системный таймер
// Записываем элемент
return EEPROM_WriteItem(&item);
}
// Поиск последних данных для виртуального адреса
static EEPROM_Status EEPROM_FindLatestData(uint16_t virt_address, uint16_t* data) {
uint32_t address = EEPROM_START_ADDRESS;
EEPROM_Item current_item;
uint32_t latest_timestamp = 0;
uint16_t latest_data = 0;
uint8_t data_found = 0;
// Сканируем всю область EEPROM
while (address < EEPROM_START_ADDRESS + EEPROM_SIZE) {
// Читаем элемент
memcpy(&current_item, (void*)address, sizeof(EEPROM_Item));
// Проверяем, является ли это валидными данными
if (current_item.address == virt_address) {
if (current_item.timestamp >= latest_timestamp) {
latest_timestamp = current_item.timestamp;
latest_data = current_item.data;
data_found = 1;
}
}
address += sizeof(EEPROM_Item);
// Проверяем конец страницы
if ((address - EEPROM_START_ADDRESS) % EEPROM_PAGE_SIZE == 0) {
address += (EEPROM_PAGE_SIZE - (sizeof(EEPROM_Item) * 2));
}
}
if (data_found) {
*data = latest_data;
return EEPROM_OK;
}
return EEPROM_INVALID;
}
// Запись элемента в EEPROM
static EEPROM_Status EEPROM_WriteItem(EEPROM_Item* item) {
HAL_StatusTypeDef hal_status;
// Проверяем, нужно ли стирать страницу
if ((eeprom_current_write_address - EEPROM_START_ADDRESS) % EEPROM_PAGE_SIZE == 0) {
if (!EEPROM_IsPageErased(eeprom_current_write_address)) {
if (EEPROM_ErasePage(eeprom_current_write_address) != EEPROM_OK) {
return EEPROM_ERROR;
}
}
}
// Разблокируем Flash
HAL_FLASH_Unlock();
// Записываем данные по словам (32 бита)
uint32_t* data_ptr = (uint32_t*)item;
for (uint8_t i = 0; i < sizeof(EEPROM_Item) / 4; i++) {
hal_status = HAL_FLASH_Program(FLASH_TYPEPROGRAM_WORD,
eeprom_current_write_address + (i * 4),
data_ptr[i]);
if (hal_status != HAL_OK) {
HAL_FLASH_Lock();
return EEPROM_ERROR;
}
}
// Блокируем Flash
HAL_FLASH_Lock();
// Обновляем адрес для следующей записи
eeprom_current_write_address += sizeof(EEPROM_Item);
// Проверяем переполнение
if (eeprom_current_write_address >= EEPROM_START_ADDRESS + EEPROM_SIZE) {
// Выполняем сборку мусора (в данном случае - форматирование)
EEPROM_Format();
}
return EEPROM_OK;
}
// Стирание страницы Flash
static EEPROM_Status EEPROM_ErasePage(uint32_t address) {
FLASH_EraseInitTypeDef erase;
uint32_t page_error;
// Определяем номер страницы
uint32_t page = (address - FLASH_BASE) / EEPROM_PAGE_SIZE;
HAL_FLASH_Unlock();
erase.TypeErase = FLASH_TYPEERASE_PAGES;
erase.PageAddress = address;
erase.NbPages = 1;
if (HAL_FLASHEx_Erase(&erase, &page_error) != HAL_OK) {
HAL_FLASH_Lock();
return EEPROM_ERROR;
}
HAL_FLASH_Lock();
return EEPROM_OK;
}
// Поиск следующего адреса для записи
static uint32_t EEPROM_FindNextWriteAddress(void) {
uint32_t address = EEPROM_START_ADDRESS;
EEPROM_Item item;
// Ищем первую свободную позицию
while (address < EEPROM_START_ADDRESS + EEPROM_SIZE) {
memcpy(&item, (void*)address, sizeof(EEPROM_Item));
// Если нашли пустой элемент (все FFFF), это свободная позиция
if (item.address == 0xFFFF && item.data == 0xFFFF && item.timestamp == 0xFFFFFFFF) {
break;
}
address += sizeof(EEPROM_Item);
// Проверяем границу страницы
if ((address - EEPROM_START_ADDRESS) % EEPROM_PAGE_SIZE == 0) {
address += (EEPROM_PAGE_SIZE - (sizeof(EEPROM_Item) * 2));
}
}
return address;
}
// Проверка, стерта ли страница
static uint8_t EEPROM_IsPageErased(uint32_t address) {
uint32_t* check_addr = (uint32_t*)address;
// Проверяем первые несколько слов
for (uint8_t i = 0; i < 8; i++) {
if (check_addr[i] != 0xFFFFFFFF) {
return 0;
}
}
return 1;
}
// Полное форматирование EEPROM
EEPROM_Status EEPROM_Format(void) {
uint32_t address = EEPROM_START_ADDRESS;
// Стираем все страницы, используемые для EEPROM
while (address < EEPROM_START_ADDRESS + EEPROM_SIZE) {
if (EEPROM_ErasePage(address) != EEPROM_OK) {
return EEPROM_ERROR;
}
address += EEPROM_PAGE_SIZE;
}
eeprom_current_write_address = EEPROM_START_ADDRESS;
eeprom_initialized = 1;
return EEPROM_OK;
}
// Получение информации об использовании EEPROM
void EEPROM_GetInfo(uint32_t* used, uint32_t* total) {
uint32_t address = EEPROM_START_ADDRESS;
uint32_t used_bytes = 0;
if (used) {
// Подсчитываем использованные байты
while (address < EEPROM_START_ADDRESS + EEPROM_SIZE) {
EEPROM_Item item;
memcpy(&item, (void*)address, sizeof(EEPROM_Item));
if (item.address != 0xFFFF || item.data != 0xFFFF || item.timestamp != 0xFFFFFFFF) {
used_bytes += sizeof(EEPROM_Item);
}
address += sizeof(EEPROM_Item);
}
*used = used_bytes;
}
if (total) {
*total = EEPROM_SIZE;
}
}

View File

@@ -1,123 +0,0 @@
#include "flash_ring.h"
extern int last_page_addr;
BufferState_t buffer_init(void) {
BufferState_t state = {0};
// Ищем последнюю записанную запись
for (int i = 0; i < RECORDS_PER_PAGE; i++) {
uint32_t record_addr = LAST_PAGE_ADDR + (i * RECORD_SIZE);
FlashRecord_t* record = (FlashRecord_t*)record_addr;
// Проверяем валидность записи (не 0xFFFFFFFF)
if (record->timestamp != 0xFFFFFFFF) {
state.write_index = i + 1;
state.initialized = 1;
} else {
break;
}
}
// Если буфер заполнен, начинаем с начала
if (state.write_index >= RECORDS_PER_PAGE) {
state.write_index = 0;
}
return state;
}
HAL_StatusTypeDef buffer_write_record(FlashRecord_t* record, BufferState_t* state) {
HAL_StatusTypeDef status;
// Если нужно стереть страницу (начало нового цикла)
if (state->write_index == 0 && state->initialized) {
status = erase_flash_page();
if (status != HAL_OK) return status;
}
// Записываем данные
uint32_t record_addr = last_page_addr + (state->write_index * RECORD_SIZE);
status = write_flash_record(record_addr, record);
if (status != HAL_OK) return status;
// Обновляем индекс
state->write_index++;
if (state->write_index >= RECORDS_PER_PAGE) {
state->write_index = 0;
}
state->initialized = 1;
return HAL_OK;
}
HAL_StatusTypeDef erase_flash_page(void) {
HAL_FLASH_Unlock();
FLASH_EraseInitTypeDef EraseInit = {
.TypeErase = FLASH_TYPEERASE_PAGES,
.PageAddress = LAST_PAGE_ADDR,
.NbPages = 1
};
uint32_t page_error;
HAL_StatusTypeDef status = HAL_FLASHEx_Erase(&EraseInit, &page_error);
HAL_FLASH_Lock();
return status;
}
// Запись одной записи
HAL_StatusTypeDef write_flash_record(uint32_t address, FlashRecord_t* record) {
HAL_FLASH_Unlock();
HAL_StatusTypeDef status = HAL_OK;
// Записываем данные по 4 байта (слово)
uint32_t* data_ptr = (uint32_t*)record;
uint32_t words_to_write = (RECORD_SIZE + 3) / 4; // округление вверх
for (uint32_t i = 0; i < words_to_write; i++) {
status = HAL_FLASH_Program(FLASH_TYPEPROGRAM_WORD,
address + (i * 4),
data_ptr[i]);
if (status != HAL_OK) break;
}
HAL_FLASH_Lock();
return status;
}
// Чтение записи по индексу
FlashRecord_t* buffer_read_record(uint32_t index) {
if (index >= RECORDS_PER_PAGE) return NULL;
uint32_t record_addr = LAST_PAGE_ADDR + (index * RECORD_SIZE);
FlashRecord_t* record = (FlashRecord_t*)record_addr;
// Проверяем что запись не пустая
if (record->timestamp == 0xFFFFFFFF) {
return NULL;
}
return record;
}
// Получение всех записей в порядке от старых к новым
void buffer_get_all_records(FlashRecord_t* records[], uint32_t* count) {
*count = 0;
BufferState_t state = buffer_init();
if (!state.initialized) return;
// Начинаем с текущего write_index (самые старые данные)
for (int i = 0; i < RECORDS_PER_PAGE; i++) {
uint32_t idx = (state.write_index + i) % RECORDS_PER_PAGE;
FlashRecord_t* record = buffer_read_record(idx);
if (record) {
records[(*count)++] = record;
}
}
}

View File

@@ -1,154 +0,0 @@
#include "flash_ring.h"
uint8_t current_page = 0; // текущая страница для записи
// Вычисление CRC16 (полином 0x8005)
static uint16_t calc_crc16(const uint8_t *data, uint32_t len)
{
uint16_t crc = 0xFFFF;
for (uint32_t i = 0; i < len; i++)
{
crc ^= data[i];
for (int j = 0; j < 8; j++)
{
if (crc & 1) crc = (crc >> 1) ^ 0xA001;
else crc >>= 1;
}
}
return crc;
}
// Проверка заголовка страницы
static bool is_page_valid(uint32_t addr)
{
PageHeader_t *hdr = (PageHeader_t *)addr;
return (hdr->valid_marker == 0xDEADBEEF);
}
// Инициализация: поиск актуальной страницы или очистка
bool FlashRing_Init(void)
{
for (uint8_t i = 0; i < PAGE_COUNT; i++)
{
uint32_t addr = FLASH_BASE_USER + i * FLASH_PAGE_SIZE_USER;
if (is_page_valid(addr))
{
current_page = i;
return true;
}
}
// Если ни одна страница не актуальна — стираем обе
if (FlashRing_EraseAll()!= 1) {
return false; // Ошибка стирания
}
current_page = 0;
return true;
}
uint16_t CalculateCRC16(const uint8_t *data, uint32_t len) {
uint16_t crc = 0xFFFF; // Начальное значение
for (uint32_t i = 0; i < len; i++) {
crc ^= data[i];
for (int j = 0; j < 8; j++) {
if (crc & 1) {
crc = (crc >> 1) ^ 0xA001; // 0xA001 = обратный полином 0x8005
} else {
crc >>= 1;
}
}
}
return crc;
}
// Стирание всех страниц
int FlashRing_EraseAll(void)
{
HAL_FLASH_Unlock();
FLASH_EraseInitTypeDef EraseInit =
{
.TypeErase = FLASH_TYPEERASE_PAGES,
.PageAddress = FLASH_BASE_USER,
.NbPages = PAGE_COUNT
};
uint32_t page_error;
HAL_FLASHEx_Erase(&EraseInit, &page_error);
// HAL_FLASHLock();
HAL_FLASH_Lock();
return 1;
}
// Запись уставки
bool FlashRing_Write(const Setpoint_t *sp)
{
uint32_t page_addr = FLASH_BASE_USER + current_page * FLASH_PAGE_SIZE_USER;
PageHeader_t *hdr = (PageHeader_t *)page_addr;
// Если страница не инициализирована или заполнена — переключаемся
if (!is_page_valid(page_addr) || hdr->count >= (FLASH_PAGE_SIZE_USER - sizeof(PageHeader_t)) / sizeof(Setpoint_t))
{
// Стираем следующую страницу
uint8_t next_page = (current_page + 1) % PAGE_COUNT;
uint32_t next_addr = FLASH_BASE_USER + next_page * FLASH_PAGE_SIZE_USER;
HAL_FLASH_Unlock();
FLASH_EraseInitTypeDef EraseInit =
{
.TypeErase = FLASH_TYPEERASE_PAGES,
.PageAddress = next_addr,
.NbPages = 1
};
uint32_t page_error;
HAL_FLASHEx_Erase(&EraseInit, &page_error);
current_page = next_page;
page_addr = next_addr;
HAL_FLASH_Program(FLASH_TYPEPROGRAM_WORD, (uint32_t)&hdr->valid_marker, 0xDEADBEEF);
HAL_FLASH_Program(FLASH_TYPEPROGRAM_HALFWORD, (uint32_t)&hdr->count, 0);
HAL_FLASH_Lock();
}
// Вычисляем смещение для новой уставки
uint8_t *data_start = (uint8_t *)page_addr + sizeof(PageHeader_t);
uint16_t idx = hdr->count;
Setpoint_t *dst = (Setpoint_t *)(data_start + idx * sizeof(Setpoint_t));
*dst = *sp;
hdr->count++;
// Обновляем CRC
hdr->crc = calc_crc16(data_start, hdr->count * sizeof(Setpoint_t));
return true;
}
// Чтение уставки по индексу
bool FlashRing_Read(uint16_t index, Setpoint_t *sp)
{
uint32_t page_addr = FLASH_BASE_USER + current_page * FLASH_PAGE_SIZE_USER;
if (!is_page_valid(page_addr)) return false;
PageHeader_t *hdr = (PageHeader_t *)page_addr;
if (index >= hdr->count) return false;
uint8_t *data_start = (uint8_t *)page_addr + sizeof(PageHeader_t);
*sp = *(Setpoint_t *)(data_start + index * sizeof(Setpoint_t));
return true;
}
// Получение числа записанных уставок
uint16_t FlashRing_GetCount(void)
{
uint32_t page_addr = FLASH_BASE_USER + current_page * FLASH_PAGE_SIZE_USER;
if (!is_page_valid(page_addr)) return 0;
PageHeader_t *hdr = (PageHeader_t *)page_addr;
return hdr->count;
}

View File

@@ -1,36 +0,0 @@
// File: STM32F101_102_103_105_107.dbgconf
// Version: 1.0.0
// Note: refer to STM32F101xx STM32F102xx STM32F103xx STM32F105xx STM32F107xx Reference manual (RM0008)
// STM32F101xx STM32F102xx STM32F103xx STM32F105xx STM32F107xx datasheets
// <<< Use Configuration Wizard in Context Menu >>>
// <h> Debug MCU configuration register (DBGMCU_CR)
// <i> Reserved bits must be kept at reset value
// <o.30> DBG_TIM11_STOP <i> TIM11 counter stopped when core is halted
// <o.29> DBG_TIM10_STOP <i> TIM10 counter stopped when core is halted
// <o.28> DBG_TIM9_STOP <i> TIM9 counter stopped when core is halted
// <o.27> DBG_TIM14_STOP <i> TIM14 counter stopped when core is halted
// <o.26> DBG_TIM13_STOP <i> TIM13 counter stopped when core is halted
// <o.25> DBG_TIM12_STOP <i> TIM12 counter stopped when core is halted
// <o.21> DBG_CAN2_STOP <i> Debug CAN2 stopped when core is halted
// <o.20> DBG_TIM7_STOP <i> TIM7 counter stopped when core is halted
// <o.19> DBG_TIM6_STOP <i> TIM6 counter stopped when core is halted
// <o.18> DBG_TIM5_STOP <i> TIM5 counter stopped when core is halted
// <o.17> DBG_TIM8_STOP <i> TIM8 counter stopped when core is halted
// <o.16> DBG_I2C2_SMBUS_TIMEOUT <i> SMBUS timeout mode stopped when core is halted
// <o.15> DBG_I2C1_SMBUS_TIMEOUT <i> SMBUS timeout mode stopped when core is halted
// <o.14> DBG_CAN1_STOP <i> Debug CAN1 stopped when Core is halted
// <o.13> DBG_TIM4_STOP <i> TIM4 counter stopped when core is halted
// <o.12> DBG_TIM3_STOP <i> TIM3 counter stopped when core is halted
// <o.11> DBG_TIM2_STOP <i> TIM2 counter stopped when core is halted
// <o.10> DBG_TIM1_STOP <i> TIM1 counter stopped when core is halted
// <o.9> DBG_WWDG_STOP <i> Debug window watchdog stopped when core is halted
// <o.8> DBG_IWDG_STOP <i> Debug independent watchdog stopped when core is halted
// <o.2> DBG_STANDBY <i> Debug standby mode
// <o.1> DBG_STOP <i> Debug stop mode
// <o.0> DBG_SLEEP <i> Debug sleep mode
// </h>
DbgMCU_CR = 0x00000007;
// <<< end of configuration section >>>

View File

@@ -1,36 +0,0 @@
// File: STM32F101_102_103_105_107.dbgconf
// Version: 1.0.0
// Note: refer to STM32F101xx STM32F102xx STM32F103xx STM32F105xx STM32F107xx Reference manual (RM0008)
// STM32F101xx STM32F102xx STM32F103xx STM32F105xx STM32F107xx datasheets
// <<< Use Configuration Wizard in Context Menu >>>
// <h> Debug MCU configuration register (DBGMCU_CR)
// <i> Reserved bits must be kept at reset value
// <o.30> DBG_TIM11_STOP <i> TIM11 counter stopped when core is halted
// <o.29> DBG_TIM10_STOP <i> TIM10 counter stopped when core is halted
// <o.28> DBG_TIM9_STOP <i> TIM9 counter stopped when core is halted
// <o.27> DBG_TIM14_STOP <i> TIM14 counter stopped when core is halted
// <o.26> DBG_TIM13_STOP <i> TIM13 counter stopped when core is halted
// <o.25> DBG_TIM12_STOP <i> TIM12 counter stopped when core is halted
// <o.21> DBG_CAN2_STOP <i> Debug CAN2 stopped when core is halted
// <o.20> DBG_TIM7_STOP <i> TIM7 counter stopped when core is halted
// <o.19> DBG_TIM6_STOP <i> TIM6 counter stopped when core is halted
// <o.18> DBG_TIM5_STOP <i> TIM5 counter stopped when core is halted
// <o.17> DBG_TIM8_STOP <i> TIM8 counter stopped when core is halted
// <o.16> DBG_I2C2_SMBUS_TIMEOUT <i> SMBUS timeout mode stopped when core is halted
// <o.15> DBG_I2C1_SMBUS_TIMEOUT <i> SMBUS timeout mode stopped when core is halted
// <o.14> DBG_CAN1_STOP <i> Debug CAN1 stopped when Core is halted
// <o.13> DBG_TIM4_STOP <i> TIM4 counter stopped when core is halted
// <o.12> DBG_TIM3_STOP <i> TIM3 counter stopped when core is halted
// <o.11> DBG_TIM2_STOP <i> TIM2 counter stopped when core is halted
// <o.10> DBG_TIM1_STOP <i> TIM1 counter stopped when core is halted
// <o.9> DBG_WWDG_STOP <i> Debug window watchdog stopped when core is halted
// <o.8> DBG_IWDG_STOP <i> Debug independent watchdog stopped when core is halted
// <o.2> DBG_STANDBY <i> Debug standby mode
// <o.1> DBG_STOP <i> Debug stop mode
// <o.0> DBG_SLEEP <i> Debug sleep mode
// </h>
DbgMCU_CR = 0x00000007;
// <<< end of configuration section >>>

View File

@@ -1,47 +0,0 @@
[BREAKPOINTS]
ForceImpTypeAny = 0
ShowInfoWin = 1
EnableFlashBP = 2
BPDuringExecution = 0
[CFI]
CFISize = 0x00
CFIAddr = 0x00
[CPU]
MonModeVTableAddr = 0xFFFFFFFF
MonModeDebug = 0
MaxNumAPs = 0
LowPowerHandlingMode = 0
OverrideMemMap = 0
AllowSimulation = 1
ScriptFile=""
[FLASH]
RMWThreshold = 0x400
Loaders=""
EraseType = 0x00
CacheExcludeSize = 0x00
CacheExcludeAddr = 0x00
MinNumBytesFlashDL = 0
SkipProgOnCRCMatch = 1
VerifyDownload = 1
AllowCaching = 1
EnableFlashDL = 2
Override = 0
Device="ARM7"
[GENERAL]
MaxNumTransfers = 0x00
WorkRAMSize = 0x00
WorkRAMAddr = 0x00
RAMUsageLimit = 0x00
[SWO]
SWOLogFile=""
[MEM]
RdOverrideOrMask = 0x00
RdOverrideAndMask = 0xFFFFFFFF
RdOverrideAddr = 0xFFFFFFFF
WrOverrideOrMask = 0x00
WrOverrideAndMask = 0xFFFFFFFF
WrOverrideAddr = 0xFFFFFFFF
[RAM]
VerifyDownload = 0x00
[DYN_MEM_MAP]
NumUserRegion = 0x00

View File

@@ -1,6 +1,7 @@
/*
* UVISION generated file: DO NOT EDIT!
* Generated by: uVision version 5.41.0.0
* Auto generated Run-Time-Environment Configuration File
* *** Do not modify ! ***
*
* Project: 'john103C6T6'
* Target: 'john103C6T6'
@@ -15,9 +16,9 @@
*/
#define CMSIS_device_header "stm32f10x.h"
/* Keil::Compiler&ARM Compiler:I/O:STDOUT&Breakpoint@1.2.0 */
/* Keil.ARM Compiler::Compiler:I/O:STDOUT:Breakpoint:1.2.0 */
#define RTE_Compiler_IO_STDOUT /* Compiler I/O: STDOUT */
#define RTE_Compiler_IO_STDOUT_BKPT /* Compiler I/O: STDOUT Breakpoint */
#define RTE_Compiler_IO_STDOUT_BKPT /* Compiler I/O: STDOUT Breakpoint */
#endif /* RTE_COMPONENTS_H */

View File

@@ -26,7 +26,7 @@
<ToolsetNumber>0x4</ToolsetNumber>
<ToolsetName>ARM-ADS</ToolsetName>
<TargetOption>
<CLKADS>12000000</CLKADS>
<CLKADS>8000000</CLKADS>
<OPTTT>
<gFlags>1</gFlags>
<BeepAtEnd>1</BeepAtEnd>
@@ -117,16 +117,6 @@
<pMon>STLink\ST-LINKIII-KEIL_SWO.dll</pMon>
</DebugOpt>
<TargetDriverDllRegistry>
<SetRegEntry>
<Number>0</Number>
<Key>UL2CM3</Key>
<Name>UL2CM3(-S0 -C0 -P0 ) -FN1 -FC1000 -FD20000000 -FF0STM32F10x_128 -FL020000 -FS08000000 -FP0($$Device:STM32F103CB$Flash\STM32F10x_128.FLM)</Name>
</SetRegEntry>
<SetRegEntry>
<Number>0</Number>
<Key>ST-LINKIII-KEIL_SWO</Key>
<Name>-U002400343233511639363634 -O206 -SF10000 -C0 -A0 -I0 -HNlocalhost -HP7184 -P1 -N00("ARM CoreSight SW-DP (ARM Core") -D00(1BA01477) -L00(0) -TO131090 -TC10000000 -TT10000000 -TP21 -TDS8007 -TDT0 -TDC1F -TIEFFFFFFFF -TIP8 -FO7 -FD20000000 -FC1000 -FN1 -FF0STM32F10x_128.FLM -FS08000000 -FL020000 -FP0($$Device:STM32F103CB$Flash\STM32F10x_128.FLM) -WA0 -WE0 -WVCE4 -WS2710 -WM0 -WP2 -WK0-R0</Name>
</SetRegEntry>
<SetRegEntry>
<Number>0</Number>
<Key>ARMRTXEVENTFLAGS</Key>
@@ -147,73 +137,118 @@
<Key>DLGUARM</Key>
<Name>(105=-1,-1,-1,-1,0)</Name>
</SetRegEntry>
<SetRegEntry>
<Number>0</Number>
<Key>UL2CM3</Key>
<Name>UL2CM3(-S0 -C0 -P0 -FD20000000 -FC1000 -FN1 -FF0STM32F10x_128 -FS08000000 -FL020000 -FP0($$Device:STM32F103C6$Flash\STM32F10x_128.FLM))</Name>
</SetRegEntry>
<SetRegEntry>
<Number>0</Number>
<Key>ST-LINKIII-KEIL_SWO</Key>
<Name>-U37FF71064E57343625581443 -O2254 -SF10000 -C0 -A0 -I0 -HNlocalhost -HP7184 -P1 -N00("ARM CoreSight SW-DP (ARM Core") -D00(1BA01477) -L00(0) -TO131090 -TC10000000 -TT10000000 -TP21 -TDS8000 -TDT0 -TDC1F -TIEFFFFFFFF -TIP8 -FO15 -FD20000000 -FC800 -FN1 -FF0STM32F10x_128.FLM -FS08000000 -FL08000 -FP0($$Device:STM32F103C6$Flash\STM32F10x_128.FLM) -WA0 -WE0 -WVCE4 -WS2710 -WM0 -WP2</Name>
</SetRegEntry>
</TargetDriverDllRegistry>
<Breakpoint/>
<WatchWindow1>
<Ww>
<count>0</count>
<WinNumber>1</WinNumber>
<ItemText>sens</ItemText>
<ItemText>sens,0x0A</ItemText>
</Ww>
<Ww>
<count>1</count>
<WinNumber>1</WinNumber>
<ItemText>MB_DATA,0x0A</ItemText>
<ItemText>hdallas</ItemText>
</Ww>
<Ww>
<count>2</count>
<WinNumber>1</WinNumber>
<ItemText>temp_sense</ItemText>
<ItemText>DS</ItemText>
</Ww>
<Ww>
<count>3</count>
<WinNumber>1</WinNumber>
<ItemText>roms</ItemText>
<ItemText>hmodbus1</ItemText>
</Ww>
<Ww>
<count>4</count>
<WinNumber>1</WinNumber>
<ItemText>state</ItemText>
<ItemText>hiwdg</ItemText>
</Ww>
<Ww>
<count>5</count>
<WinNumber>1</WinNumber>
<ItemText>last_page_addr</ItemText>
<ItemText>OW</ItemText>
</Ww>
<Ww>
<count>6</count>
<WinNumber>1</WinNumber>
<ItemText>\\john103C6T6\../EEPROM_Emul/src/flash_ring.c\buffer_write_record\record_addr</ItemText>
<ItemText>_debug_init</ItemText>
</Ww>
<Ww>
<count>7</count>
<WinNumber>1</WinNumber>
<ItemText>record</ItemText>
<ItemText>htim1,0x0A</ItemText>
</Ww>
<Ww>
<count>8</count>
<WinNumber>1</WinNumber>
<ItemText>flash_buff</ItemText>
<ItemText>DS18B20_DEVICE_AMOUNT</ItemText>
</Ww>
<Ww>
<count>9</count>
<WinNumber>1</WinNumber>
<ItemText>new_record</ItemText>
<ItemText>set_temp_old</ItemText>
</Ww>
<Ww>
<count>10</count>
<WinNumber>1</WinNumber>
<ItemText>state</ItemText>
<ItemText>hrtc.Instance,0x0A</ItemText>
</Ww>
<Ww>
<count>11</count>
<WinNumber>1</WinNumber>
<ItemText>htim</ItemText>
<ItemText>\\john103C6T6\../Modbus/modbus.c\MB_DATA,0x0A</ItemText>
</Ww>
<Ww>
<count>12</count>
<WinNumber>1</WinNumber>
<ItemText>sens[i].set_temp</ItemText>
<ItemText>sTime</ItemText>
</Ww>
<Ww>
<count>13</count>
<WinNumber>1</WinNumber>
<ItemText>ralay_5v_on_var</ItemText>
</Ww>
<Ww>
<count>14</count>
<WinNumber>1</WinNumber>
<ItemText>MB_DATA.Coils.coils[1].state_val_bit.state_val_01,0x0A</ItemText>
</Ww>
<Ww>
<count>15</count>
<WinNumber>1</WinNumber>
<ItemText>MODBUS_MSG</ItemText>
</Ww>
<Ww>
<count>16</count>
<WinNumber>1</WinNumber>
<ItemText>RS_RES</ItemText>
</Ww>
<Ww>
<count>17</count>
<WinNumber>1</WinNumber>
<ItemText>rx_buffer</ItemText>
</Ww>
<Ww>
<count>18</count>
<WinNumber>1</WinNumber>
<ItemText>RS_msg</ItemText>
</Ww>
<Ww>
<count>19</count>
<WinNumber>1</WinNumber>
<ItemText>pMessagePtr</ItemText>
</Ww>
</WatchWindow1>
<WatchWindow2>
@@ -222,20 +257,7 @@
<WinNumber>2</WinNumber>
<ItemText>resolution</ItemText>
</Ww>
<Ww>
<count>1</count>
<WinNumber>2</WinNumber>
<ItemText>hmodbus1</ItemText>
</Ww>
</WatchWindow2>
<MemoryWindow1>
<Mm>
<WinNumber>1</WinNumber>
<SubType>0</SubType>
<ItemText>0x0800f800</ItemText>
<AccSizeX>0</AccSizeX>
</Mm>
</MemoryWindow1>
<Tracepoint>
<THDelay>0</THDelay>
</Tracepoint>
@@ -244,7 +266,7 @@
<periodic>1</periodic>
<aLwin>1</aLwin>
<aCover>0</aCover>
<aSer1>0</aSer1>
<aSer1>1</aSer1>
<aSer2>0</aSer2>
<aPa>0</aPa>
<viewmode>1</viewmode>
@@ -280,16 +302,8 @@
<pMultCmdsp></pMultCmdsp>
<SystemViewers>
<Entry>
<Name>System Viewer\FLASH</Name>
<WinId>35904</WinId>
</Entry>
<Entry>
<Name>System Viewer\GPIOB</Name>
<WinId>35900</WinId>
</Entry>
<Entry>
<Name>System Viewer\GPIOC</Name>
<WinId>35905</WinId>
<Name>System Viewer\USART1</Name>
<WinId>35902</WinId>
</Entry>
</SystemViewers>
<DebugDescription>
@@ -304,7 +318,7 @@
<Group>
<GroupName>Application/MDK-ARM</GroupName>
<tvExp>1</tvExp>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<cbSel>0</cbSel>
<RteFlg>0</RteFlg>
@@ -315,8 +329,8 @@
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>.\startup_stm32f10x_md.s</PathWithFileName>
<FilenameWithoutPath>startup_stm32f10x_md.s</FilenameWithoutPath>
<PathWithFileName>startup_stm32f103x6.s</PathWithFileName>
<FilenameWithoutPath>startup_stm32f103x6.s</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
@@ -335,6 +349,18 @@
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\Core\Src\UART_TERM.c</PathWithFileName>
<FilenameWithoutPath>UART_TERM.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>3</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\Core\Src\dallas_tools.c</PathWithFileName>
<FilenameWithoutPath>dallas_tools.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
@@ -342,7 +368,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>3</FileNumber>
<FileNumber>4</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -354,7 +380,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>4</FileNumber>
<FileNumber>5</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -366,7 +392,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>5</FileNumber>
<FileNumber>6</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -378,9 +404,45 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>6</FileNumber>
<FileNumber>7</FileNumber>
<FileType>1</FileType>
<tvExp>1</tvExp>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\Modbus\crc_algs.c</PathWithFileName>
<FilenameWithoutPath>crc_algs.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>8</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\Modbus\modbus.c</PathWithFileName>
<FilenameWithoutPath>modbus.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>9</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\Modbus\rs_message.c</PathWithFileName>
<FilenameWithoutPath>rs_message.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>10</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>../Core/Src/main.c</PathWithFileName>
@@ -390,7 +452,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>7</FileNumber>
<FileNumber>11</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -402,7 +464,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>8</FileNumber>
<FileNumber>12</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -414,7 +476,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>9</FileNumber>
<FileNumber>13</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -426,7 +488,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>10</FileNumber>
<FileNumber>14</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -438,7 +500,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>11</FileNumber>
<FileNumber>15</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -450,7 +512,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>12</FileNumber>
<FileNumber>16</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -462,7 +524,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>13</FileNumber>
<FileNumber>17</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -474,7 +536,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>14</FileNumber>
<FileNumber>18</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -486,7 +548,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>15</FileNumber>
<FileNumber>19</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -498,7 +560,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>16</FileNumber>
<FileNumber>20</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -510,7 +572,7 @@
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>17</FileNumber>
<FileNumber>21</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -520,18 +582,6 @@
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>2</GroupNumber>
<FileNumber>18</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\EEPROM_Emul\src\flash_ring.c</PathWithFileName>
<FilenameWithoutPath>flash_ring.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
</Group>
<Group>
@@ -542,7 +592,7 @@
<RteFlg>0</RteFlg>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>19</FileNumber>
<FileNumber>22</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -554,31 +604,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>20</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>../Drivers/STM32F1xx_HAL_Driver/Src/stm32f1xx_hal_tim.c</PathWithFileName>
<FilenameWithoutPath>stm32f1xx_hal_tim.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>21</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>../Drivers/STM32F1xx_HAL_Driver/Src/stm32f1xx_hal_tim_ex.c</PathWithFileName>
<FilenameWithoutPath>stm32f1xx_hal_tim_ex.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>22</FileNumber>
<FileNumber>23</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -590,7 +616,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>23</FileNumber>
<FileNumber>24</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -602,7 +628,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>24</FileNumber>
<FileNumber>25</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -614,7 +640,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>25</FileNumber>
<FileNumber>26</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -626,7 +652,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>26</FileNumber>
<FileNumber>27</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -638,7 +664,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>27</FileNumber>
<FileNumber>28</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -650,7 +676,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>28</FileNumber>
<FileNumber>29</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -662,7 +688,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>29</FileNumber>
<FileNumber>30</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -674,7 +700,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>30</FileNumber>
<FileNumber>31</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -686,7 +712,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>31</FileNumber>
<FileNumber>32</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -698,7 +724,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>32</FileNumber>
<FileNumber>33</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -710,7 +736,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>33</FileNumber>
<FileNumber>34</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -722,7 +748,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>34</FileNumber>
<FileNumber>35</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -734,7 +760,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>35</FileNumber>
<FileNumber>36</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -746,7 +772,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>36</FileNumber>
<FileNumber>37</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -758,7 +784,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>37</FileNumber>
<FileNumber>38</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -770,7 +796,7 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>38</FileNumber>
<FileNumber>39</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -782,7 +808,31 @@
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>39</FileNumber>
<FileNumber>40</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>../Drivers/STM32F1xx_HAL_Driver/Src/stm32f1xx_hal_tim.c</PathWithFileName>
<FilenameWithoutPath>stm32f1xx_hal_tim.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>41</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>../Drivers/STM32F1xx_HAL_Driver/Src/stm32f1xx_hal_tim_ex.c</PathWithFileName>
<FilenameWithoutPath>stm32f1xx_hal_tim_ex.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>3</GroupNumber>
<FileNumber>42</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -796,13 +846,13 @@
<Group>
<GroupName>Drivers/CMSIS</GroupName>
<tvExp>1</tvExp>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<cbSel>0</cbSel>
<RteFlg>0</RteFlg>
<File>
<GroupNumber>4</GroupNumber>
<FileNumber>40</FileNumber>
<FileNumber>43</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
@@ -814,170 +864,6 @@
</File>
</Group>
<Group>
<GroupName>modbus</GroupName>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<cbSel>0</cbSel>
<RteFlg>0</RteFlg>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>41</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\__crc_algs.c</PathWithFileName>
<FilenameWithoutPath>__crc_algs.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>42</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\__modbus_compat.c</PathWithFileName>
<FilenameWithoutPath>__modbus_compat.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>43</FileNumber>
<FileType>1</FileType>
<tvExp>1</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\modbus.c</PathWithFileName>
<FilenameWithoutPath>modbus.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>44</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\modbus_coils.c</PathWithFileName>
<FilenameWithoutPath>modbus_coils.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>45</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\modbus_core.c</PathWithFileName>
<FilenameWithoutPath>modbus_core.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>46</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\modbus_devid.c</PathWithFileName>
<FilenameWithoutPath>modbus_devid.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>47</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\modbus_diag.c</PathWithFileName>
<FilenameWithoutPath>modbus_diag.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>48</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\modbus_holdregs.c</PathWithFileName>
<FilenameWithoutPath>modbus_holdregs.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>49</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\modbus_inputregs.c</PathWithFileName>
<FilenameWithoutPath>modbus_inputregs.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>50</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\modbus_master.c</PathWithFileName>
<FilenameWithoutPath>modbus_master.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>51</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\modbus_slave.c</PathWithFileName>
<FilenameWithoutPath>modbus_slave.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>52</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\..\core\STM32_Modbus\Src\rs_message.c</PathWithFileName>
<FilenameWithoutPath>rs_message.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
<File>
<GroupNumber>5</GroupNumber>
<FileNumber>53</FileNumber>
<FileType>1</FileType>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<bDave2>0</bDave2>
<PathWithFileName>..\Modbus\modbus_data.c</PathWithFileName>
<FilenameWithoutPath>modbus_data.c</FilenameWithoutPath>
<RteFlg>0</RteFlg>
<bShared>0</bShared>
</File>
</Group>
<Group>
<GroupName>::CMSIS</GroupName>
<tvExp>0</tvExp>
@@ -986,14 +872,6 @@
<RteFlg>1</RteFlg>
</Group>
<Group>
<GroupName>::CMSIS Driver</GroupName>
<tvExp>0</tvExp>
<tvExpOptDlg>0</tvExpOptDlg>
<cbSel>0</cbSel>
<RteFlg>1</RteFlg>
</Group>
<Group>
<GroupName>::Compiler</GroupName>
<tvExp>0</tvExp>

View File

@@ -10,21 +10,21 @@
<TargetName>john103C6T6</TargetName>
<ToolsetNumber>0x4</ToolsetNumber>
<ToolsetName>ARM-ADS</ToolsetName>
<pArmCC>6220000::V6.22::ARMCLANG</pArmCC>
<pCCUsed>6220000::V6.22::ARMCLANG</pCCUsed>
<pArmCC>6190000::V6.19::ARMCLANG</pArmCC>
<pCCUsed>6190000::V6.19::ARMCLANG</pCCUsed>
<uAC6>1</uAC6>
<TargetOption>
<TargetCommonOption>
<Device>STM32F103CB</Device>
<Device>STM32F103C6</Device>
<Vendor>STMicroelectronics</Vendor>
<PackID>Keil.STM32F1xx_DFP.2.4.0</PackID>
<PackURL>http://www.keil.com/pack/</PackURL>
<Cpu>IRAM(0x20000000,0x00005000) IROM(0x08000000,0x00020000) CPUTYPE("Cortex-M3") CLOCK(12000000) ELITTLE</Cpu>
<PackID>Keil.STM32F1xx_DFP.2.4.1</PackID>
<PackURL>https://www.keil.com/pack/</PackURL>
<Cpu>IRAM(0x20000000-0x200027FF) IROM(0x8000000-0x8007FFF) CLOCK(8000000) CPUTYPE("Cortex-M3") TZ</Cpu>
<FlashUtilSpec></FlashUtilSpec>
<StartupFile></StartupFile>
<FlashDriverDll>UL2CM3(-S0 -C0 -P0 -FD20000000 -FC1000 -FN1 -FF0STM32F10x_128 -FS08000000 -FL020000 -FP0($$Device:STM32F103CB$Flash\STM32F10x_128.FLM))</FlashDriverDll>
<FlashDriverDll></FlashDriverDll>
<DeviceId>0</DeviceId>
<RegisterFile>$$Device:STM32F103CB$Device\Include\stm32f10x.h</RegisterFile>
<RegisterFile></RegisterFile>
<MemoryEnv></MemoryEnv>
<Cmp></Cmp>
<Asm></Asm>
@@ -34,7 +34,7 @@
<SLE66CMisc></SLE66CMisc>
<SLE66AMisc></SLE66AMisc>
<SLE66LinkerMisc></SLE66LinkerMisc>
<SFDFile>$$Device:STM32F103CB$SVD\STM32F103xx.svd</SFDFile>
<SFDFile>$$Device:STM32F103C6$SVD\STM32F103xx.svd</SFDFile>
<bCustSvd>0</bCustSvd>
<UseEnv>0</UseEnv>
<BinPath></BinPath>
@@ -82,7 +82,7 @@
</BeforeMake>
<AfterMake>
<RunUserProg1>0</RunUserProg1>
<RunUserProg2>0</RunUserProg2>
<RunUserProg2>1</RunUserProg2>
<UserProg1Name></UserProg1Name>
<UserProg2Name></UserProg2Name>
<UserProg1Dos16Mode>0</UserProg1Dos16Mode>
@@ -111,7 +111,7 @@
</CommonProperty>
<DllOption>
<SimDllName>SARMCM3.DLL</SimDllName>
<SimDllArguments> -REMAP</SimDllArguments>
<SimDllArguments>-REMAP</SimDllArguments>
<SimDlgDll>DCM.DLL</SimDlgDll>
<SimDlgDllArguments>-pCM3</SimDlgDllArguments>
<TargetDllName>SARMCM3.DLL</TargetDllName>
@@ -133,13 +133,13 @@
<UseTargetDll>1</UseTargetDll>
<UseExternalTool>0</UseExternalTool>
<RunIndependent>0</RunIndependent>
<UpdateFlashBeforeDebugging>1</UpdateFlashBeforeDebugging>
<UpdateFlashBeforeDebugging>0</UpdateFlashBeforeDebugging>
<Capability>1</Capability>
<DriverSelection>4096</DriverSelection>
<DriverSelection>4101</DriverSelection>
</Flash1>
<bUseTDR>1</bUseTDR>
<Flash2>BIN\UL2CM3.DLL</Flash2>
<Flash3></Flash3>
<Flash2>STLink\ST-LINKIII-KEIL_SWO.dll</Flash2>
<Flash3>"" ()</Flash3>
<Flash4></Flash4>
<pFcarmOut></pFcarmOut>
<pFcarmGrp></pFcarmGrp>
@@ -160,7 +160,7 @@
<ldmm>1</ldmm>
<ldXref>1</ldXref>
<BigEnd>0</BigEnd>
<AdsALst>0</AdsALst>
<AdsALst>1</AdsALst>
<AdsACrf>1</AdsACrf>
<AdsANop>0</AdsANop>
<AdsANot>0</AdsANot>
@@ -196,7 +196,7 @@
<uLtcg>0</uLtcg>
<nSecure>0</nSecure>
<RoSelD>3</RoSelD>
<RwSelD>3</RwSelD>
<RwSelD>4</RwSelD>
<CodeSel>0</CodeSel>
<OptFeed>0</OptFeed>
<NoZi1>0</NoZi1>
@@ -248,12 +248,12 @@
<IRAM>
<Type>0</Type>
<StartAddress>0x20000000</StartAddress>
<Size>0x5000</Size>
<Size>0x2800</Size>
</IRAM>
<IROM>
<Type>1</Type>
<StartAddress>0x8000000</StartAddress>
<Size>0x20000</Size>
<Size>0x8000</Size>
</IROM>
<XRAM>
<Type>0</Type>
@@ -278,12 +278,12 @@
<OCR_RVCT4>
<Type>1</Type>
<StartAddress>0x8000000</StartAddress>
<Size>0x20000</Size>
<Size>0x8000</Size>
</OCR_RVCT4>
<OCR_RVCT5>
<Type>1</Type>
<StartAddress>0x0</StartAddress>
<Size>0x0</Size>
<StartAddress>0x8008000</StartAddress>
<Size>0x2000</Size>
</OCR_RVCT5>
<OCR_RVCT6>
<Type>0</Type>
@@ -303,7 +303,7 @@
<OCR_RVCT9>
<Type>0</Type>
<StartAddress>0x20000000</StartAddress>
<Size>0x5000</Size>
<Size>0x2800</Size>
</OCR_RVCT9>
<OCR_RVCT10>
<Type>0</Type>
@@ -339,9 +339,9 @@
<v6Rtti>0</v6Rtti>
<VariousControls>
<MiscControls></MiscControls>
<Define>USE_HAL_DRIVER,STM32F103xB</Define>
<Define>USE_HAL_DRIVER,STM32F103x6</Define>
<Undefine></Undefine>
<IncludePath>../Core/Inc;../Drivers/STM32F1xx_HAL_Driver/Inc;../Drivers/STM32F1xx_HAL_Driver/Inc/Legacy;../Drivers/CMSIS/Device/ST/STM32F1xx/Include;../Drivers/CMSIS/Include;../Modbus;..\EEPROM_Emul\lib;..\..\core\STM32_Modbus\Inc;..\EEPROM_Emul\lib</IncludePath>
<IncludePath>../Core/Inc;../Drivers/STM32F1xx_HAL_Driver/Inc;../Drivers/STM32F1xx_HAL_Driver/Inc/Legacy;../Drivers/CMSIS/Device/ST/STM32F1xx/Include;../Drivers/CMSIS/Include;../Modbus</IncludePath>
</VariousControls>
</Cads>
<Aads>
@@ -386,15 +386,20 @@
<GroupName>Application/MDK-ARM</GroupName>
<Files>
<File>
<FileName>startup_stm32f10x_md.s</FileName>
<FileName>startup_stm32f103x6.s</FileName>
<FileType>2</FileType>
<FilePath>.\startup_stm32f10x_md.s</FilePath>
<FilePath>startup_stm32f103x6.s</FilePath>
</File>
</Files>
</Group>
<Group>
<GroupName>Application/User/Core</GroupName>
<Files>
<File>
<FileName>UART_TERM.c</FileName>
<FileType>1</FileType>
<FilePath>..\Core\Src\UART_TERM.c</FilePath>
</File>
<File>
<FileName>dallas_tools.c</FileName>
<FileType>1</FileType>
@@ -415,6 +420,21 @@
<FileType>1</FileType>
<FilePath>..\Core\Src\ow_port.c</FilePath>
</File>
<File>
<FileName>crc_algs.c</FileName>
<FileType>1</FileType>
<FilePath>..\Modbus\crc_algs.c</FilePath>
</File>
<File>
<FileName>modbus.c</FileName>
<FileType>1</FileType>
<FilePath>..\Modbus\modbus.c</FilePath>
</File>
<File>
<FileName>rs_message.c</FileName>
<FileType>1</FileType>
<FilePath>..\Modbus\rs_message.c</FilePath>
</File>
<File>
<FileName>main.c</FileName>
<FileType>1</FileType>
@@ -730,11 +750,6 @@
<FileType>1</FileType>
<FilePath>../Core/Src/stm32f1xx_hal_timebase_tim.c</FilePath>
</File>
<File>
<FileName>flash_ring.c</FileName>
<FileType>1</FileType>
<FilePath>..\EEPROM_Emul\src\flash_ring.c</FilePath>
</File>
</Files>
</Group>
<Group>
@@ -745,16 +760,6 @@
<FileType>1</FileType>
<FilePath>../Drivers/STM32F1xx_HAL_Driver/Src/stm32f1xx_hal_gpio_ex.c</FilePath>
</File>
<File>
<FileName>stm32f1xx_hal_tim.c</FileName>
<FileType>1</FileType>
<FilePath>../Drivers/STM32F1xx_HAL_Driver/Src/stm32f1xx_hal_tim.c</FilePath>
</File>
<File>
<FileName>stm32f1xx_hal_tim_ex.c</FileName>
<FileType>1</FileType>
<FilePath>../Drivers/STM32F1xx_HAL_Driver/Src/stm32f1xx_hal_tim_ex.c</FilePath>
</File>
<File>
<FileName>stm32f1xx_hal_adc.c</FileName>
<FileType>1</FileType>
@@ -1197,6 +1202,16 @@
</FileArmAds>
</FileOption>
</File>
<File>
<FileName>stm32f1xx_hal_tim.c</FileName>
<FileType>1</FileType>
<FilePath>../Drivers/STM32F1xx_HAL_Driver/Src/stm32f1xx_hal_tim.c</FilePath>
</File>
<File>
<FileName>stm32f1xx_hal_tim_ex.c</FileName>
<FileType>1</FileType>
<FilePath>../Drivers/STM32F1xx_HAL_Driver/Src/stm32f1xx_hal_tim_ex.c</FilePath>
</File>
<File>
<FileName>stm32f1xx_hal_uart.c</FileName>
<FileType>1</FileType>
@@ -1214,82 +1229,9 @@
</File>
</Files>
</Group>
<Group>
<GroupName>modbus</GroupName>
<Files>
<File>
<FileName>__crc_algs.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\__crc_algs.c</FilePath>
</File>
<File>
<FileName>__modbus_compat.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\__modbus_compat.c</FilePath>
</File>
<File>
<FileName>modbus.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\modbus.c</FilePath>
</File>
<File>
<FileName>modbus_coils.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\modbus_coils.c</FilePath>
</File>
<File>
<FileName>modbus_core.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\modbus_core.c</FilePath>
</File>
<File>
<FileName>modbus_devid.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\modbus_devid.c</FilePath>
</File>
<File>
<FileName>modbus_diag.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\modbus_diag.c</FilePath>
</File>
<File>
<FileName>modbus_holdregs.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\modbus_holdregs.c</FilePath>
</File>
<File>
<FileName>modbus_inputregs.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\modbus_inputregs.c</FilePath>
</File>
<File>
<FileName>modbus_master.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\modbus_master.c</FilePath>
</File>
<File>
<FileName>modbus_slave.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\modbus_slave.c</FilePath>
</File>
<File>
<FileName>rs_message.c</FileName>
<FileType>1</FileType>
<FilePath>..\..\core\STM32_Modbus\Src\rs_message.c</FilePath>
</File>
<File>
<FileName>modbus_data.c</FileName>
<FileType>1</FileType>
<FilePath>..\Modbus\modbus_data.c</FilePath>
</File>
</Files>
</Group>
<Group>
<GroupName>::CMSIS</GroupName>
</Group>
<Group>
<GroupName>::CMSIS Driver</GroupName>
</Group>
<Group>
<GroupName>::Compiler</GroupName>
</Group>
@@ -1298,27 +1240,14 @@
</Targets>
<RTE>
<apis>
<api Capiversion="2.3.0" Cclass="CMSIS Driver" Cgroup="Flash" exclusive="0">
<package name="CMSIS" schemaVersion="1.7.7" url="http://www.keil.com/pack/" vendor="ARM" version="5.9.0"/>
<targetInfos>
<targetInfo name="john103C6T6"/>
</targetInfos>
</api>
</apis>
<apis/>
<components>
<component Capiversion="2.3.0" Cclass="CMSIS Driver" Cgroup="Flash" Csub="Custom" Cvendor="ARM" Cversion="1.0.0" custom="1">
<component Cclass="CMSIS" Cgroup="CORE" Cvendor="ARM" Cversion="5.6.0" condition="ARMv6_7_8-M Device">
<package name="CMSIS" schemaVersion="1.7.7" url="http://www.keil.com/pack/" vendor="ARM" version="5.9.0"/>
<targetInfos>
<targetInfo name="john103C6T6"/>
</targetInfos>
</component>
<component Cclass="CMSIS" Cgroup="CORE" Cvendor="ARM" Cversion="6.1.0" condition="ARMv6_7_8-M Device">
<package name="CMSIS" schemaVersion="1.7.36" url="https://www.keil.com/pack/" vendor="ARM" version="6.1.0"/>
<targetInfos>
<targetInfo name="john103C6T6"/>
</targetInfos>
</component>
<component Cbundle="ARM Compiler" Cclass="Compiler" Cgroup="I/O" Csub="STDOUT" Cvariant="Breakpoint" Cvendor="Keil" Cversion="1.2.0" condition="ARMCC Cortex-M">
<package name="ARM_Compiler" schemaVersion="1.7.7" url="https://www.keil.com/pack/" vendor="Keil" version="1.7.2"/>
<targetInfos>

File diff suppressed because it is too large Load Diff

View File

@@ -2,14 +2,14 @@
; *** Scatter-Loading Description File generated by uVision ***
; *************************************************************
LR_IROM1 0x08000000 0x00020000 { ; load region size_region
ER_IROM1 0x08000000 0x00020000 { ; load address = execution address
LR_IROM1 0x08000000 0x00008000 { ; load region size_region
ER_IROM1 0x08000000 0x00008000 { ; load address = execution address
*.o (RESET, +First)
*(InRoot$$Sections)
.ANY (+RO)
.ANY (+XO)
}
RW_IRAM1 0x20000000 0x00005000 { ; RW data
RW_IRAM1 0x20000000 0x00002800 { ; RW data
.ANY (+RW +ZI)
}
}

View File

@@ -1,10 +1,7 @@
;******************** (C) COPYRIGHT 2011 STMicroelectronics ********************
;* File Name : startup_stm32f10x_md.s
;******************** (C) COPYRIGHT 2017 STMicroelectronics ********************
;* File Name : startup_stm32f103x6.s
;* Author : MCD Application Team
;* Version : V3.5.1
;* Date : 08-September-2021
;* Description : STM32F10x Medium Density Devices vector table for MDK-ARM
;* toolchain.
;* Description : STM32F103x6 Devices vector table for MDK-ARM toolchain.
;* This module performs:
;* - Set the initial SP
;* - Set the initial PC == Reset_Handler
@@ -12,19 +9,19 @@
;* - Configure the clock system
;* - Branches to __main in the C library (which eventually
;* calls main()).
;* After Reset the CortexM3 processor is in Thread mode,
;* After Reset the Cortex-M3 processor is in Thread mode,
;* priority is Privileged, and the Stack is set to Main.
;* <<< Use Configuration Wizard in Context Menu >>>
;*******************************************************************************
;******************************************************************************
;* @attention
;*
;* Copyright (c) 2011 STMicroelectronics.
;* Copyright (c) 2017-2021 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.
;
;*******************************************************************************
;*
;******************************************************************************
; Amount of memory (in bytes) allocated for Stack
; Tailor this value to your application needs
@@ -32,7 +29,7 @@
; <o> Stack Size (in Bytes) <0x0-0xFFFFFFFF:8>
; </h>
Stack_Size EQU 0x00000400
Stack_Size EQU 0x400
AREA STACK, NOINIT, READWRITE, ALIGN=3
Stack_Mem SPACE Stack_Size
@@ -43,7 +40,7 @@ __initial_sp
; <o> Heap Size (in Bytes) <0x0-0xFFFFFFFF:8>
; </h>
Heap_Size EQU 0x00000200
Heap_Size EQU 0x400
AREA HEAP, NOINIT, READWRITE, ALIGN=3
__heap_base
@@ -108,18 +105,18 @@ __Vectors DCD __initial_sp ; Top of Stack
DCD TIM1_CC_IRQHandler ; TIM1 Capture Compare
DCD TIM2_IRQHandler ; TIM2
DCD TIM3_IRQHandler ; TIM3
DCD TIM4_IRQHandler ; TIM4
DCD 0 ; Reserved
DCD I2C1_EV_IRQHandler ; I2C1 Event
DCD I2C1_ER_IRQHandler ; I2C1 Error
DCD I2C2_EV_IRQHandler ; I2C2 Event
DCD I2C2_ER_IRQHandler ; I2C2 Error
DCD 0 ; Reserved
DCD 0 ; Reserved
DCD SPI1_IRQHandler ; SPI1
DCD SPI2_IRQHandler ; SPI2
DCD 0 ; Reserved
DCD USART1_IRQHandler ; USART1
DCD USART2_IRQHandler ; USART2
DCD USART3_IRQHandler ; USART3
DCD 0 ; Reserved
DCD EXTI15_10_IRQHandler ; EXTI Line 15..10
DCD RTCAlarm_IRQHandler ; RTC Alarm through EXTI Line
DCD RTC_Alarm_IRQHandler ; RTC Alarm through EXTI Line
DCD USBWakeUp_IRQHandler ; USB Wakeup from suspend
__Vectors_End
@@ -127,7 +124,7 @@ __Vectors_Size EQU __Vectors_End - __Vectors
AREA |.text|, CODE, READONLY
; Reset handler
; Reset handler routine
Reset_Handler PROC
EXPORT Reset_Handler [WEAK]
IMPORT __main
@@ -214,18 +211,13 @@ Default_Handler PROC
EXPORT TIM1_CC_IRQHandler [WEAK]
EXPORT TIM2_IRQHandler [WEAK]
EXPORT TIM3_IRQHandler [WEAK]
EXPORT TIM4_IRQHandler [WEAK]
EXPORT I2C1_EV_IRQHandler [WEAK]
EXPORT I2C1_ER_IRQHandler [WEAK]
EXPORT I2C2_EV_IRQHandler [WEAK]
EXPORT I2C2_ER_IRQHandler [WEAK]
EXPORT SPI1_IRQHandler [WEAK]
EXPORT SPI2_IRQHandler [WEAK]
EXPORT USART1_IRQHandler [WEAK]
EXPORT USART2_IRQHandler [WEAK]
EXPORT USART3_IRQHandler [WEAK]
EXPORT EXTI15_10_IRQHandler [WEAK]
EXPORT RTCAlarm_IRQHandler [WEAK]
EXPORT RTC_Alarm_IRQHandler [WEAK]
EXPORT USBWakeUp_IRQHandler [WEAK]
WWDG_IRQHandler
@@ -258,18 +250,13 @@ TIM1_TRG_COM_IRQHandler
TIM1_CC_IRQHandler
TIM2_IRQHandler
TIM3_IRQHandler
TIM4_IRQHandler
I2C1_EV_IRQHandler
I2C1_ER_IRQHandler
I2C2_EV_IRQHandler
I2C2_ER_IRQHandler
SPI1_IRQHandler
SPI2_IRQHandler
USART1_IRQHandler
USART2_IRQHandler
USART3_IRQHandler
EXTI15_10_IRQHandler
RTCAlarm_IRQHandler
RTC_Alarm_IRQHandler
USBWakeUp_IRQHandler
B .
@@ -281,7 +268,7 @@ USBWakeUp_IRQHandler
;*******************************************************************************
; User Stack and Heap initialization
;*******************************************************************************
IF :DEF:__MICROLIB
IF :DEF:__MICROLIB
EXPORT __initial_sp
EXPORT __heap_base

View File

@@ -0,0 +1,116 @@
#include "crc_algs.h"
uint32_t CRC_calc;
uint32_t CRC_ref;
//uint16_t CRC_calc;
//uint16_t CRC_ref;
// left this global for debug
uint8_t uchCRCHi = 0xFF;
uint8_t uchCRCLo = 0xFF;
unsigned uIndex;
uint32_t crc32(uint8_t *data, uint32_t data_size)
{
static const unsigned int crc32_table[] =
{
0x00000000, 0x77073096, 0xEE0E612C, 0x990951BA, 0x076DC419, 0x706AF48F, 0xE963A535, 0x9E6495A3,
0x0EDB8832, 0x79DCB8A4, 0xE0D5E91E, 0x97D2D988, 0x09B64C2B, 0x7EB17CBD, 0xE7B82D07, 0x90BF1D91,
0x1DB71064, 0x6AB020F2, 0xF3B97148, 0x84BE41DE, 0x1ADAD47D, 0x6DDDE4EB, 0xF4D4B551, 0x83D385C7,
0x136C9856, 0x646BA8C0, 0xFD62F97A, 0x8A65C9EC, 0x14015C4F, 0x63066CD9, 0xFA0F3D63, 0x8D080DF5,
0x3B6E20C8, 0x4C69105E, 0xD56041E4, 0xA2677172, 0x3C03E4D1, 0x4B04D447, 0xD20D85FD, 0xA50AB56B,
0x35B5A8FA, 0x42B2986C, 0xDBBBC9D6, 0xACBCF940, 0x32D86CE3, 0x45DF5C75, 0xDCD60DCF, 0xABD13D59,
0x26D930AC, 0x51DE003A, 0xC8D75180, 0xBFD06116, 0x21B4F4B5, 0x56B3C423, 0xCFBA9599, 0xB8BDA50F,
0x2802B89E, 0x5F058808, 0xC60CD9B2, 0xB10BE924, 0x2F6F7C87, 0x58684C11, 0xC1611DAB, 0xB6662D3D,
0x76DC4190, 0x01DB7106, 0x98D220BC, 0xEFD5102A, 0x71B18589, 0x06B6B51F, 0x9FBFE4A5, 0xE8B8D433,
0x7807C9A2, 0x0F00F934, 0x9609A88E, 0xE10E9818, 0x7F6A0DBB, 0x086D3D2D, 0x91646C97, 0xE6635C01,
0x6B6B51F4, 0x1C6C6162, 0x856530D8, 0xF262004E, 0x6C0695ED, 0x1B01A57B, 0x8208F4C1, 0xF50FC457,
0x65B0D9C6, 0x12B7E950, 0x8BBEB8EA, 0xFCB9887C, 0x62DD1DDF, 0x15DA2D49, 0x8CD37CF3, 0xFBD44C65,
0x4DB26158, 0x3AB551CE, 0xA3BC0074, 0xD4BB30E2, 0x4ADFA541, 0x3DD895D7, 0xA4D1C46D, 0xD3D6F4FB,
0x4369E96A, 0x346ED9FC, 0xAD678846, 0xDA60B8D0, 0x44042D73, 0x33031DE5, 0xAA0A4C5F, 0xDD0D7CC9,
0x5005713C, 0x270241AA, 0xBE0B1010, 0xC90C2086, 0x5768B525, 0x206F85B3, 0xB966D409, 0xCE61E49F,
0x5EDEF90E, 0x29D9C998, 0xB0D09822, 0xC7D7A8B4, 0x59B33D17, 0x2EB40D81, 0xB7BD5C3B, 0xC0BA6CAD,
0xEDB88320, 0x9ABFB3B6, 0x03B6E20C, 0x74B1D29A, 0xEAD54739, 0x9DD277AF, 0x04DB2615, 0x73DC1683,
0xE3630B12, 0x94643B84, 0x0D6D6A3E, 0x7A6A5AA8, 0xE40ECF0B, 0x9309FF9D, 0x0A00AE27, 0x7D079EB1,
0xF00F9344, 0x8708A3D2, 0x1E01F268, 0x6906C2FE, 0xF762575D, 0x806567CB, 0x196C3671, 0x6E6B06E7,
0xFED41B76, 0x89D32BE0, 0x10DA7A5A, 0x67DD4ACC, 0xF9B9DF6F, 0x8EBEEFF9, 0x17B7BE43, 0x60B08ED5,
0xD6D6A3E8, 0xA1D1937E, 0x38D8C2C4, 0x4FDFF252, 0xD1BB67F1, 0xA6BC5767, 0x3FB506DD, 0x48B2364B,
0xD80D2BDA, 0xAF0A1B4C, 0x36034AF6, 0x41047A60, 0xDF60EFC3, 0xA867DF55, 0x316E8EEF, 0x4669BE79,
0xCB61B38C, 0xBC66831A, 0x256FD2A0, 0x5268E236, 0xCC0C7795, 0xBB0B4703, 0x220216B9, 0x5505262F,
0xC5BA3BBE, 0xB2BD0B28, 0x2BB45A92, 0x5CB36A04, 0xC2D7FFA7, 0xB5D0CF31, 0x2CD99E8B, 0x5BDEAE1D,
0x9B64C2B0, 0xEC63F226, 0x756AA39C, 0x026D930A, 0x9C0906A9, 0xEB0E363F, 0x72076785, 0x05005713,
0x95BF4A82, 0xE2B87A14, 0x7BB12BAE, 0x0CB61B38, 0x92D28E9B, 0xE5D5BE0D, 0x7CDCEFB7, 0x0BDBDF21,
0x86D3D2D4, 0xF1D4E242, 0x68DDB3F8, 0x1FDA836E, 0x81BE16CD, 0xF6B9265B, 0x6FB077E1, 0x18B74777,
0x88085AE6, 0xFF0F6A70, 0x66063BCA, 0x11010B5C, 0x8F659EFF, 0xF862AE69, 0x616BFFD3, 0x166CCF45,
0xA00AE278, 0xD70DD2EE, 0x4E048354, 0x3903B3C2, 0xA7672661, 0xD06016F7, 0x4969474D, 0x3E6E77DB,
0xAED16A4A, 0xD9D65ADC, 0x40DF0B66, 0x37D83BF0, 0xA9BCAE53, 0xDEBB9EC5, 0x47B2CF7F, 0x30B5FFE9,
0xBDBDF21C, 0xCABAC28A, 0x53B39330, 0x24B4A3A6, 0xBAD03605, 0xCDD70693, 0x54DE5729, 0x23D967BF,
0xB3667A2E, 0xC4614AB8, 0x5D681B02, 0x2A6F2B94, 0xB40BBE37, 0xC30C8EA1, 0x5A05DF1B, 0x2D02EF8D
};
unsigned int crc = 0xFFFFFFFF;
while (data_size--)
{
crc = (crc >> 8) ^ crc32_table[(crc ^ *data) & 255];
data++;
}
return crc^0xFFFFFFFF;
}
uint16_t crc16(uint8_t *data, uint32_t data_size)
{
/*Table of CRC values for high order byte*/
static unsigned char auchCRCHi[]=
{
0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,
0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,
0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,
0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,
0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,
0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,
0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,
0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,
0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,
0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,
0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,
0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,
0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,
0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,
0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,
0x00,0xC1,0x81,0x40,0x01,0xC0,0x80,0x41,0x01,0xC0,0x80,0x41,0x00,0xC1,0x81,0x40,
};
/*Table of CRC values for low order byte*/
static char auchCRCLo[] =
{
0x00,0xC0,0xC1,0x01,0xC3,0x03,0x02,0xC2,0xC6,0x06,0x07,0xC7,0x05,0xC5,0xC4,0x04,
0xCC,0x0C,0x0D,0xCD,0x0F,0xCF,0xCE,0x0E,0x0A,0xCA,0xCB,0x0B,0xC9,0x09,0x08,0xC8,
0xD8,0x18,0x19,0xD9,0x1B,0xDB,0xDA,0x1A,0x1E,0xDE,0xDF,0x1F,0xDD,0x1D,0x1C,0xDC,
0x14,0xD4,0xD5,0x15,0xD7,0x17,0x16,0xD6,0xD2,0x12,0x13,0xD3,0x11,0xD1,0xD0,0x10,
0xF0,0x30,0x31,0xF1,0x33,0xF3,0xF2,0x32,0x36,0xF6,0xF7,0x37,0xF5,0x35,0x34,0xF4,
0x3C,0xFC,0xFD,0x3D,0xFF,0x3F,0x3E,0xFE,0xFA,0x3A,0x3B,0xFB,0x39,0xF9,0xF8,0x38,
0x28,0xE8,0xE9,0x29,0xEB,0x2B,0x2A,0xEA,0xEE,0x2E,0x2F,0xEF,0x2D,0xED,0xEC,0x2C,
0xE4,0x24,0x25,0xE5,0x27,0xE7,0xE6,0x26,0x22,0xE2,0xE3,0x23,0xE1,0x21,0x20,0xE0,
0xA0,0x60,0x61,0xA1,0x63,0xA3,0xA2,0x62,0x66,0xA6,0xA7,0x67,0xA5,0x65,0x64,0xA4,
0x6C,0xAC,0xAD,0x6D,0xAF,0x6F,0x6E,0xAE,0xAA,0x6A,0x6B,0xAB,0x69,0xA9,0xA8,0x68,
0x78,0xB8,0xB9,0x79,0xBB,0x7B,0x7A,0xBA,0xBE,0x7E,0x7F,0xBF,0x7D,0xBD,0xBC,0x7C,
0xB4,0x74,0x75,0xB5,0x77,0xB7,0xB6,0x76,0x72,0xB2,0xB3,0x73,0xB1,0x71,0x70,0xB0,
0x50,0x90,0x91,0x51,0x93,0x53,0x52,0x92,0x96,0x56,0x57,0x97,0x55,0x95,0x94,0x54,
0x9C,0x5C,0x5D,0x9D,0x5F,0x9F,0x9E,0x5E,0x5A,0x9A,0x9B,0x5B,0x99,0x59,0x58,0x98,
0x88,0x48,0x49,0x89,0x4B,0x8B,0x8A,0x4A,0x4E,0x8E,0x8F,0x4F,0x8D,0x4D,0x4C,0x8C,
0x44,0x84,0x85,0x45,0x87,0x47,0x46,0x86,0x82,0x42,0x43,0x83,0x41,0x81,0x80,0x40,
};
uchCRCHi = 0xFF;
uchCRCLo = 0xFF;
/* CRC Generation Function */
while( data_size--) /* pass through message buffer */
{
uIndex = uchCRCHi ^ *data++; /* calculate the CRC */
uchCRCHi = uchCRCLo ^ auchCRCHi[uIndex];
uchCRCLo = auchCRCLo[uIndex];
}
return uchCRCHi | uchCRCLo<<8;
}

View File

@@ -0,0 +1,9 @@
#include "modbus_config.h"
// extern here to use in bootloader.c
extern uint32_t CRC_calc;
extern uint32_t CRC_ref;
uint16_t crc16(uint8_t *data, uint32_t data_size);
uint32_t crc32(uint8_t *data, uint32_t data_size);

951
john103C6T6/Modbus/modbus.c Normal file
View File

@@ -0,0 +1,951 @@
/**
**************************************************************************
* @file modbus.c
* @brief Модуль для реализации MODBUS.
**************************************************************************
* @details Файл содержит реализацию функций работы с Modbus, включая:
* - доступ к coils и registers;
* - обработку команд протокола;
* - взаимодействие с RS (UART);
* - инициализацию.
*
* @section Функции и макросы
*
* ### Доступ к coils:
* - MB_Set_Coil_Local() — Установить coil по локальному адресу.
* - MB_Reset_Coil_Local() — Сбросить coil по локальному адресу.
* - MB_Toogle_Coil_Local() — Инвертировать coil по локальному адресу.
* - MB_Read_Coil_Local() — Прочитать coil по локальному адресу.
* - MB_Write_Coil_Global() — Установить/сбросить coil по глобальному адресу.
* - MB_Read_Coil_Global() — Прочитать coil по глобальному адресу.
*
* ### Обработка команд Modbus:
* - MB_DefineRegistersAddress() — Определить начальный адрес регистра.
* - MB_DefineCoilsAddress() — Определить начальный адрес coils.
* - MB_Check_Address_For_Arr() — Проверить, принадлежит ли адрес массиву.
* - Основные команды Modbus:
* - MB_Read_Coils()
* - MB_Read_Hold_Regs()
* - MB_Write_Single_Coil()
* - MB_Write_Miltuple_Coils()
* - MB_Write_Miltuple_Regs()
*
* ### Функции для работы с RS (UART):
* - RS_Parse_Message() / RS_Collect_Message() — Парсинг и сборка сообщения.
* - RS_Response() — Отправка ответа.
* - RS_Define_Size_of_RX_Message() — Определение размера принимаемого сообщения.
* - RS_Init() — Инициализация UART.
*
* ### Инициализация:
* - MODBUS_FirstInit() — Инициализация модуля Modbus.
*
* @section Структура данных Modbus
*
* #### Holding/Input Registers:
* - Регистры — 16-битные слова. Доступ к регистрам осуществляется через указатель.
* Таким образом, сами регистры могут представлять собой как массив так и структуру.
*
* #### Coils:
* - Coils — это биты, упакованные в 16-битные слова. Доступ к коилам осуществляется через указатель.
* Таким образом, сами коилы могут представлять собой как массив так и структуру.
*
* @section Инструкция по подключению
* Для корректной работы надо подключить обработчики RS_UART_Handler(), RS_TIM_Handler(),
* в соответствубщие низкоуровневые прерывания UART_IRQHandler, TIM_IRQHandler. После HAL'овского обработчика
*
* Также необходимо в modbus_config.h настроить дефайны для нужной работы UART
* После для запуска Modbus:
* @verbatim
//----------------Прием модбас----------------//
#include "rs_message.h"
MODBUS_FirstInit();
RS_Receive_IT(&hmodbus1, &MODBUS_MSG);
* @endverbatim
*
******************************************************************************/
#include "rs_message.h"
uint32_t dbg_temp, dbg_temp2, dbg_temp3; // for debug
/* MODBUS HANDLES */
extern UART_HandleTypeDef rs_huart;
extern TIM_HandleTypeDef rs_htim;
RS_HandleTypeDef hmodbus1;
/* DEFINE REGISTERS/COILS */
MB_DeviceIdentificationTypeDef MB_INFO;
MB_DataStructureTypeDef MB_DATA;
RS_MsgTypeDef MODBUS_MSG;
//-------------------------------------------------------------------
//-----------------------------FOR USER------------------------------
/**
* @brief First set up of MODBUS.
* @details Первый инит модбас. Заполняет структуры и инициализирует таймер и юарт для общения по модбас.
* @note This called from main
*/
void MODBUS_FirstInit(void)
{
MB_DevoceInentificationInit();
//-----------SETUP MODBUS-------------
// set up modbus: MB_RX_Size_NotConst and Timeout enable
hmodbus1.ID = MODBUS_DEVICE_ID;
hmodbus1.sRS_Timeout = MODBUS_TIMEOUT;
hmodbus1.sRS_Mode = SLAVE_ALWAYS_WAIT;
hmodbus1.sRS_RX_Size_Mode = RS_RX_Size_NotConst;
// INIT
hmodbus1.RS_STATUS = RS_Init(&hmodbus1, &rs_huart, &rs_htim, 0);
RS_EnableReceive();
}
/**
* @brief Set or Reset Coil at its global address.
* @param Addr - адрес коила.
* @param WriteVal - Что записать в коил: 0 или 1.
* @return ExceptionCode - Код исключения если коила по адресу не существует, и NO_ERRORS если все ок.
*
* @details Позволяет обратиться к любому коилу по его глобальному адрессу.
Вне зависимости от того как коилы размещены в памяти.
*/
MB_ExceptionTypeDef MB_Write_Coil_Global(uint16_t Addr, MB_CoilsOpTypeDef WriteVal)
{
//---------CHECK FOR ERRORS----------
MB_ExceptionTypeDef Exception = NO_ERRORS;
uint16_t *coils;
uint16_t start_shift = 0; // shift in coils register
//------------WRITE COIL-------------
Exception = MB_DefineCoilsAddress(&coils, Addr, 1, &start_shift, 1);
if(Exception == NO_ERRORS)
{
switch(WriteVal)
{
case SET_COIL:
*coils |= (1<<start_shift);
break;
case RESET_COIL:
*coils &= ~(1<<start_shift);
break;
case TOOGLE_COIL:
*coils ^= (1<<start_shift);
break;
}
}
return Exception;
}
/**
* @brief Read Coil at its global address.
* @param Addr - адрес коила.
* @param Exception - Указатель на переменную для кода исключения, в случа неудачи при чтении.
* @return uint16_t - Возвращает весь регистр с маской на запрошенном коиле.
*
* @details Позволяет обратиться к любому коилу по его глобальному адрессу.
Вне зависимости от того как коилы размещены в памяти.
*/
uint16_t MB_Read_Coil_Global(uint16_t Addr, MB_ExceptionTypeDef *Exception)
{
//---------CHECK FOR ERRORS----------
MB_ExceptionTypeDef Exception_tmp;
if(Exception == NULL) // if exception is not given to func fill it
Exception = &Exception_tmp;
uint16_t *coils;
uint16_t start_shift = 0; // shift in coils register
//------------READ COIL--------------
*Exception = MB_DefineCoilsAddress(&coils, Addr, 1, &start_shift, 0);
if(*Exception == NO_ERRORS)
{
return ((*coils)&(1<<start_shift));
}
else
{
return 0;
}
}
//-------------------------------------------------------------------
//----------------FUNCTIONS FOR PROCESSING MESSAGE-------------------
/**
* @brief Check is address valid for certain array.
* @param Addr - начальный адресс.
* @param Qnt - количество запрашиваемых элементов.
* @param R_ARR_ADDR - начальный адресс массива R_ARR.
* @param R_ARR_NUMB - количество элементов в массиве R_ARR.
* @return ExceptionCode - ILLEGAL DATA ADRESS если адресс недействителен, и NO_ERRORS если все ок.
*
* @details Позволяет определить, принадлежит ли адресс Addr массиву R_ARR:
* Если адресс Addr находится в диапазоне адрессов массива R_ARR, то возвращаем NO_ERROR.
* Если адресс Addr находится за пределами адрессов массива R_ARR - ILLEGAL_DATA_ADDRESSю.
*/
MB_ExceptionTypeDef MB_Check_Address_For_Arr(uint16_t Addr, uint16_t Qnt, uint16_t R_ARR_ADDR, uint16_t R_ARR_NUMB)
{
// if address from this array
if(Addr >= R_ARR_ADDR)
{
// if quantity too big return error
if ((Addr - R_ARR_ADDR) + Qnt > R_ARR_NUMB)
{
return ILLEGAL_DATA_ADDRESS; // return exception code
}
// if all ok - return no errors
return NO_ERRORS;
}
// if address isnt from this array return error
else
return ILLEGAL_DATA_ADDRESS; // return exception code
}
/**
* @brief Define Address Origin for Input/Holding Registers
* @param pRegs - указатель на указатель регистров.
* @param Addr - адрес начального регистра.
* @param Qnt - количество запрашиваемых регистров.
* @param WriteFlag - флаг регистр нужны для чтения или записи.
* @return ExceptionCode - Код исключения если есть, и NO_ERRORS если нет.
*
* @details Определение адреса начального регистра.
* @note WriteFlag пока не используется.
*/
MB_ExceptionTypeDef MB_DefineRegistersAddress(uint16_t **pRegs, uint16_t Addr, uint16_t Qnt, uint8_t RegisterType)
{
/* check quantity error */
if (Qnt > 125)
{
return ILLEGAL_DATA_VALUE; // return exception code
}
if(RegisterType == RegisterType_Holding)
{
// Default holding registers
if(MB_Check_Address_For_Arr(Addr, Qnt, R_HOLDING_ADDR, R_HOLDING_QNT) == NO_ERRORS)
{
*pRegs = MB_Set_Register_Ptr(&MB_DATA.HoldRegs, Addr); // указатель на выбранный по Addr регистр
}
// if address doesnt match any array - return illegal data address response
else
{
return ILLEGAL_DATA_ADDRESS;
}
}
else if(RegisterType == RegisterType_Input)
{
// Default input registers
if(MB_Check_Address_For_Arr(Addr, Qnt, R_INPUT_ADDR, R_INPUT_QNT) == NO_ERRORS)
{
*pRegs = MB_Set_Register_Ptr(&MB_DATA.InRegs, Addr); // указатель на выбранный по Addr регистр
}
// if address doesnt match any array - return illegal data address response
else
{
return ILLEGAL_DATA_ADDRESS;
}
}
else
{
return ILLEGAL_FUNCTION;
}
// if found requeried array return no err
return NO_ERRORS; // return no errors
}
/**
* @brief Define Address Origin for coils
* @param pCoils - указатель на указатель коилов.
* @param Addr - адресс начального коила.
* @param Qnt - количество запрашиваемых коилов.
* @param start_shift - указатель на переменную содержащую сдвиг внутри регистра для начального коила.
* @param WriteFlag - флаг коилы нужны для чтения или записи.
* @return ExceptionCode - Код исключения если есть, и NO_ERRORS если нет.
*
* @details Определение адреса начального регистра запрашиваемых коилов.
* @note WriteFlag используется для определния регистров GPIO: ODR или IDR.
*/
MB_ExceptionTypeDef MB_DefineCoilsAddress(uint16_t **pCoils, uint16_t Addr, uint16_t Qnt, uint16_t *start_shift, uint8_t WriteFlag)
{
/* check quantity error */
if (Qnt > 2000)
{
return ILLEGAL_DATA_VALUE; // return exception code
}
// Default coils
if(MB_Check_Address_For_Arr(Addr, Qnt, C_CONTROL_ADDR, C_CONTROL_QNT) == NO_ERRORS)
{
*pCoils = MB_Set_Coil_Reg_Ptr(&MB_DATA.Coils, Addr); // указатель на выбранный по Addr массив коилов
}
// if address doesnt match any array - return illegal data address response
else
{
return ILLEGAL_DATA_ADDRESS;
}
*start_shift = Addr % 16; // set shift to requested coil
// if found requeried array return no err
return NO_ERRORS; // return no errors
}
/**
* @brief Proccess command Read Coils (01 - 0x01).
* @param modbus_msg - указатель на структуру собщения modbus.
* @return fMessageHandled - статус о результате обработки комманды.
* @details Обработка команды Read Coils.
*/
uint8_t MB_Read_Coils(RS_MsgTypeDef *modbus_msg)
{
//---------CHECK FOR ERRORS----------
uint16_t *coils;
uint16_t start_shift = 0; // shift in coils register
modbus_msg->Except_Code = MB_DefineCoilsAddress(&coils, modbus_msg->Addr, modbus_msg->Qnt, &start_shift, 0);
if(modbus_msg->Except_Code != NO_ERRORS)
return 0;
//-----------READING COIL------------
// setup output message data size
modbus_msg->ByteCnt = Divide_Up(modbus_msg->Qnt, 8);
// create mask for coils
uint16_t mask_for_coils = 0; // mask for coils that've been chosen
uint16_t setted_coils = 0; // value of setted coils
uint16_t temp_reg = 0; // temp register for saving coils that hasnt been chosen
uint16_t coil_cnt = 0; // counter for processed coils
// cycle until all registers with requered coils would be processed
int shift = start_shift; // set shift to first coil in first register
int ind = 0; // index for coils registers and data
for(; ind <= Divide_Up(start_shift + modbus_msg->Qnt, 16); ind++)
{
//----SET MASK FOR COILS REGISTER----
mask_for_coils = 0;
for(; shift < 0x10; shift++)
{
mask_for_coils |= 1<<(shift); // choose certain coil
if(++coil_cnt >= modbus_msg->Qnt)
break;
}
shift = 0; // set shift to zero for the next step
//-----------READ COILS--------------
modbus_msg->DATA[ind] = (*(coils+ind)&mask_for_coils) >> start_shift;
if(ind > 0)
modbus_msg->DATA[ind-1] |= ((*(coils+ind)&mask_for_coils) << 16) >> start_shift;
}
// т.к. DATA 16-битная, для 8-битной передачи, надо поменять местами верхний и нижний байты
for(; ind >= 0; --ind)
modbus_msg->DATA[ind] = ByteSwap16(modbus_msg->DATA[ind]);
return 1;
}
/**
* @brief Proccess command Read Holding Registers (03 - 0x03).
* @param modbus_msg - указатель на структуру собщения modbus.
* @return fMessageHandled - статус о результате обработки комманды.
* @details Обработка команды Read Holding Registers.
*/
uint8_t MB_Read_Hold_Regs(RS_MsgTypeDef *modbus_msg)
{
//---------CHECK FOR ERRORS----------
// get origin address for data
uint16_t *pHoldRegs;
modbus_msg->Except_Code = MB_DefineRegistersAddress(&pHoldRegs, modbus_msg->Addr, modbus_msg->Qnt, RegisterType_Holding); // определение адреса регистров
if(modbus_msg->Except_Code != NO_ERRORS)
return 0;
//-----------READING REGS------------
// setup output message data size
modbus_msg->ByteCnt = modbus_msg->Qnt*2; // *2 because we transmit 8 bits, not 16 bits
// read data
int i;
for (i = 0; i<modbus_msg->Qnt; i++)
{
modbus_msg->DATA[i] = *(pHoldRegs++);
}
return 1;
}
/**
* @brief Proccess command Read Input Registers (04 - 0x04).
* @param modbus_msg - указатель на структуру собщения modbus.
* @return fMessageHandled - статус о результате обработки комманды.
* @details Обработка команды Read Input Registers.
*/
uint8_t MB_Read_Input_Regs(RS_MsgTypeDef *modbus_msg)
{
//---------CHECK FOR ERRORS----------
// get origin address for data
uint16_t *pInRegs;
modbus_msg->Except_Code = MB_DefineRegistersAddress(&pInRegs, modbus_msg->Addr, modbus_msg->Qnt, RegisterType_Input); // определение адреса регистров
if(modbus_msg->Except_Code != NO_ERRORS)
return 0;
//-----------READING REGS------------
// setup output message data size
modbus_msg->ByteCnt = modbus_msg->Qnt*2; // *2 because we transmit 8 bits, not 16 bits
// read data
int i;
for (i = 0; i<modbus_msg->Qnt; i++)
{
if(*((int16_t *)pInRegs) > 0)
modbus_msg->DATA[i] = (*pInRegs++);
else
modbus_msg->DATA[i] = (*pInRegs++);
}
return 1;
}
/**
* @brief Proccess command Write Single Coils (05 - 0x05).
* @param modbus_msg - указатель на структуру собщения modbus.
* @return fMessageHandled - статус о результате обработки комманды.
* @details Обработка команды Write Single Coils.
*/
uint8_t MB_Write_Single_Coil(RS_MsgTypeDef *modbus_msg)
{
//---------CHECK FOR ERRORS----------
if ((modbus_msg->Qnt != 0x0000) && (modbus_msg->Qnt != 0xFF00))
{
modbus_msg->Except_Code = ILLEGAL_DATA_VALUE;
return 0;
}
// define position of coil
uint16_t *coils;
uint16_t start_shift = 0; // shift in coils register
modbus_msg->Except_Code = MB_DefineCoilsAddress(&coils, modbus_msg->Addr, 0, &start_shift, 1);
if(modbus_msg->Except_Code != NO_ERRORS)
return 0;
//----------WRITTING COIL------------
if(modbus_msg->Qnt == 0xFF00)
*(coils) |= 1<<start_shift; // write flags corresponding to received data
else
*(coils) &= ~(1<<start_shift); // write flags corresponding to received data
return 1;
}
/**
* @brief Proccess command Write Single Register (06 - 0x06).
* @param modbus_msg - указатель на структуру собщения modbus.
* @return fMessageHandled - статус о результате обработки комманды.
* @details Обработка команды Write Single Register.
*/
uint8_t MB_Write_Single_Reg(RS_MsgTypeDef *modbus_msg)
{
// get origin address for data
uint16_t *pHoldRegs;
modbus_msg->Except_Code = MB_DefineRegistersAddress(&pHoldRegs, modbus_msg->Addr, 1, RegisterType_Holding); // определение адреса регистров
if(modbus_msg->Except_Code != NO_ERRORS)
return 0;
//-----------WRITTING REG------------
*(pHoldRegs) = modbus_msg->Qnt;
return 1;
}
/**
* @brief Proccess command Write Multiple Coils (15 - 0x0F).
* @param modbus_msg - указатель на структуру собщения modbus.
* @return fMessageHandled - статус о результате обработки комманды.
* @details Обработка команды Write Multiple Coils.
*/
uint8_t MB_Write_Miltuple_Coils(RS_MsgTypeDef *modbus_msg)
{
//---------CHECK FOR ERRORS----------
if (modbus_msg->ByteCnt != Divide_Up(modbus_msg->Qnt, 8))
{ // if quantity too large OR if quantity and bytes count arent match
modbus_msg->Except_Code = ILLEGAL_DATA_VALUE;
return 0;
}
// define position of coil
uint16_t *coils; // pointer to coils
uint16_t start_shift = 0; // shift in coils register
modbus_msg->Except_Code = MB_DefineCoilsAddress(&coils, modbus_msg->Addr, modbus_msg->Qnt, &start_shift, 1);
if(modbus_msg->Except_Code != NO_ERRORS)
return 0;
//----------WRITTING COILS-----------
// create mask for coils
uint16_t mask_for_coils = 0; // mask for coils that've been chosen
uint32_t setted_coils = 0; // value of setted coils
uint16_t temp_reg = 0; // temp register for saving coils that hasnt been chosen
uint16_t coil_cnt = 0; // counter for processed coils
// cycle until all registers with requered coils would be processed
int shift = start_shift; // set shift to first coil in first register
for(int ind = 0; ind <= Divide_Up(start_shift + modbus_msg->Qnt, 16); ind++)
{
//----SET MASK FOR COILS REGISTER----
mask_for_coils = 0;
for(; shift < 0x10; shift++)
{
mask_for_coils |= 1<<(shift); // choose certain coil
if(++coil_cnt >= modbus_msg->Qnt)
break;
}
shift = 0; // set shift to zero for the next step
//-----------WRITE COILS-------------
// get current coils
temp_reg = *(coils+ind);
// set coils
setted_coils = ByteSwap16(modbus_msg->DATA[ind]) << start_shift;
if(ind > 0)
{
setted_coils |= ((ByteSwap16(modbus_msg->DATA[ind-1]) << start_shift) >> 16);
}
// write coils
*(coils+ind) = setted_coils & mask_for_coils;
// restore untouched coils
*(coils+ind) |= temp_reg&(~mask_for_coils);
if(coil_cnt >= modbus_msg->Qnt) // if all coils written - break cycle
break; // *kind of unnecessary
}
return 1;
}
/**
* @brief Proccess command Write Multiple Registers (16 - 0x10).
* @param modbus_msg - указатель на структуру собщения modbus.
* @return fMessageHandled - статус о результате обработки комманды.
* @details Обработка команды Write Multiple Registers.
*/
uint8_t MB_Write_Miltuple_Regs(RS_MsgTypeDef *modbus_msg)
{
//---------CHECK FOR ERRORS----------
if (modbus_msg->Qnt*2 != modbus_msg->ByteCnt)
{ // if quantity and bytes count arent match
modbus_msg->Except_Code = 3;
return 0;
}
// get origin address for data
uint16_t *pHoldRegs;
modbus_msg->Except_Code = MB_DefineRegistersAddress(&pHoldRegs, modbus_msg->Addr, modbus_msg->Qnt, RegisterType_Holding); // определение адреса регистров
if(modbus_msg->Except_Code != NO_ERRORS)
return 0;
//-----------WRITTING REGS-----------
for (int i = 0; i<modbus_msg->Qnt; i++)
{
*(pHoldRegs++) = modbus_msg->DATA[i];
}
return 1;
}
void MB_WriteObjectToMessage(char *mbdata, unsigned *ind, MB_DeviceObjectTypeDef *obj)
{
mbdata[(*ind)++] = obj->length;
for (int i = 0; i < obj->length; i++)
{
mbdata[(*ind)++] = obj->name[i];
}
}
/**
* @brief Proccess command Read Device Identification (43/14 - 0x2B/0E).
* @param modbus_msg - указатель на структуру собщения modbus.
* @return fMessageHandled - статус о результате обработки комманды.
* @details Обработка команды Write Single Register.
*/
uint8_t MB_Read_Device_Identification(RS_MsgTypeDef *modbus_msg)
{
char *mbdata = (char *)modbus_msg->DATA;
unsigned ind = 0;
switch(modbus_msg->DevId.ReadDevId)
{
case MB_BASIC_IDENTIFICATION:
mbdata[ind++] = 0x00;
MB_WriteObjectToMessage(mbdata, &ind, &MB_INFO.VendorName);
mbdata[ind++] = 0x01;
MB_WriteObjectToMessage(mbdata, &ind, &MB_INFO.ProductCode);
mbdata[ind++] = 0x02;
MB_WriteObjectToMessage(mbdata, &ind, &MB_INFO.Revision);
modbus_msg->DevId.NumbOfObj = 3;
break;
case MB_REGULAR_IDENTIFICATION:
mbdata[ind++] = 0x03;
MB_WriteObjectToMessage(mbdata, &ind, &MB_INFO.VendorUrl);
mbdata[ind++] = 0x04;
MB_WriteObjectToMessage(mbdata, &ind, &MB_INFO.ProductName);
mbdata[ind++] = 0x05;
MB_WriteObjectToMessage(mbdata, &ind, &MB_INFO.ModelName);
mbdata[ind++] = 0x06;
MB_WriteObjectToMessage(mbdata, &ind, &MB_INFO.UserApplicationName);
modbus_msg->DevId.NumbOfObj = 4;
break;
default:
return 0;
}
modbus_msg->ByteCnt = ind;
return 1;
}
/**
* @brief Respond accord to received message.
* @param hRS - указатель на хендлер RS.
* @param RS_msg - указатель на структуру сообщения.
* @return RS_RES - статус о результате ответа на комманду.
* @details Обработка принятой комманды и ответ на неё.
*/
RS_StatusTypeDef RS_Response(RS_HandleTypeDef *hmodbus, RS_MsgTypeDef *modbus_msg)
{
RS_StatusTypeDef MB_RES = 0;
hmodbus->f.MessageHandled = 0;
hmodbus->f.EchoResponse = 0;
RS_Reset_TX_Flags(hmodbus); // reset flag for correct transmit
if(modbus_msg->Func_Code < ERR_VALUES_START)// if no errors after parsing
{
switch (modbus_msg->Func_Code)
{
// Read Coils
case MB_R_COILS:
hmodbus->f.MessageHandled = MB_Read_Coils(hmodbus->pMessagePtr);
break;
// Read Hodling Registers
case MB_R_HOLD_REGS:
hmodbus->f.MessageHandled = MB_Read_Hold_Regs(hmodbus->pMessagePtr);
break;
case MB_R_IN_REGS:
hmodbus->f.MessageHandled = MB_Read_Input_Regs(hmodbus->pMessagePtr);
break;
// Write Single Coils
case MB_W_COIL:
hmodbus->f.MessageHandled = MB_Write_Single_Coil(hmodbus->pMessagePtr);
if(hmodbus->f.MessageHandled)
{
hmodbus->f.EchoResponse = 1;
hmodbus->RS_Message_Size -= 2; // echo response if write ok (minus 2 cause of two CRC bytes)
}
break;
case MB_W_HOLD_REG:
hmodbus->f.MessageHandled = MB_Write_Single_Reg(hmodbus->pMessagePtr);
if(hmodbus->f.MessageHandled)
{
hmodbus->f.EchoResponse = 1;
hmodbus->RS_Message_Size -= 2; // echo response if write ok (minus 2 cause of two CRC bytes)
}
break;
// Write Multiple Coils
case MB_W_COILS:
hmodbus->f.MessageHandled = MB_Write_Miltuple_Coils(hmodbus->pMessagePtr);
if(hmodbus->f.MessageHandled)
{
hmodbus->f.EchoResponse = 1;
hmodbus->RS_Message_Size = 6; // echo response if write ok (withous data bytes)
}
break;
// Write Multiple Registers
case MB_W_HOLD_REGS:
hmodbus->f.MessageHandled = MB_Write_Miltuple_Regs(hmodbus->pMessagePtr);
if(hmodbus->f.MessageHandled)
{
hmodbus->f.EchoResponse = 1;
hmodbus->RS_Message_Size = 6; // echo response if write ok (withous data bytes)
}
break;
case MB_R_DEVICE_INFO:
hmodbus->f.MessageHandled = MB_Read_Device_Identification(hmodbus->pMessagePtr);
break;
/* unknown func code */
default: modbus_msg->Except_Code = 0x01; /* set exception code: illegal function */
}
if(hmodbus->f.MessageHandled == 0)
{
modbus_msg->Func_Code += ERR_VALUES_START;
}
else
{
}
}
// if we need response - check that transmit isnt busy
if( RS_Is_TX_Busy(hmodbus) )
RS_Abort(hmodbus, ABORT_TX); // if tx busy - set it free
// Transmit right there, or sets (fDeferredResponse) to transmit response in main code
MB_RES = RS_Handle_Transmit_Start(hmodbus, modbus_msg);
hmodbus->RS_STATUS = MB_RES;
return MB_RES;
}
/**
* @brief Collect message in buffer to transmit it.
* @param hRS - указатель на хендлер RS.
* @param RS_msg - указатель на структуру сообщения.
* @param msg_uart_buff - указатель на буффер UART.
* @return RS_RES - статус о результате заполнения буфера.
* @details Заполнение буффера UART из структуры сообщения.
*/
RS_StatusTypeDef RS_Collect_Message(RS_HandleTypeDef *hmodbus, RS_MsgTypeDef *modbus_msg, uint8_t *modbus_uart_buff)
{
int ind = 0; // ind for modbus-uart buffer
if(hmodbus->f.EchoResponse && hmodbus->f.MessageHandled) // if echo response need
ind = hmodbus->RS_Message_Size;
else
{
//------INFO ABOUT DATA/MESSAGE------
//-----------[first bytes]-----------
// set ID of message/user
modbus_uart_buff[ind++] = modbus_msg->MbAddr;
// set dat or err response
modbus_uart_buff[ind++] = modbus_msg->Func_Code;
if (modbus_msg->Func_Code < ERR_VALUES_START) // if no error occur
{
// fill modbus header
if(modbus_msg->Func_Code == MB_R_DEVICE_INFO) // devide identification header
{
modbus_uart_buff[ind++] = modbus_msg->DevId.MEI_Type;
modbus_uart_buff[ind++] = modbus_msg->DevId.ReadDevId;
modbus_uart_buff[ind++] = modbus_msg->DevId.Conformity;
modbus_uart_buff[ind++] = modbus_msg->DevId.MoreFollows;
modbus_uart_buff[ind++] = modbus_msg->DevId.NextObjId;
modbus_uart_buff[ind++] = modbus_msg->DevId.NumbOfObj;
if (modbus_msg->ByteCnt > DATA_SIZE*2) // if ByteCnt less than DATA_SIZE
{
return RS_COLLECT_MSG_ERR;
}
//---------------DATA----------------
//-----------[data bytes]------------
uint8_t *tmp_data_addr = (uint8_t *)modbus_msg->DATA;
for(int i = 0; i < modbus_msg->ByteCnt; i++) // filling buffer with data
{ // set data
modbus_uart_buff[ind++] = *tmp_data_addr;
tmp_data_addr++;
}
}
else // modbus data header
{
// set size of received data
if (modbus_msg->ByteCnt <= DATA_SIZE*2) // if ByteCnt less than DATA_SIZE
modbus_uart_buff[ind++] = modbus_msg->ByteCnt;
else // otherwise return data_size err
{
return RS_COLLECT_MSG_ERR;
}
//---------------DATA----------------
//-----------[data bytes]------------
uint16_t *tmp_data_addr = (uint16_t *)modbus_msg->DATA;
for(int i = 0; i < modbus_msg->ByteCnt; i++) // filling buffer with data
{ // set data
if (i%2 == 0) // HI byte
modbus_uart_buff[ind++] = (*tmp_data_addr)>>8;
else // LO byte
{
modbus_uart_buff[ind++] = *tmp_data_addr;
tmp_data_addr++;
}
}
}
}
else // if some error occur
{ // send expection code
modbus_uart_buff[ind++] = modbus_msg->Except_Code;
}
}
//---------------CRC----------------
//---------[last 16 bytes]----------
// calc crc of received data
uint16_t CRC_VALUE = crc16(modbus_uart_buff, ind);
// write crc to message structure and modbus-uart buffer
modbus_msg->MB_CRC = CRC_VALUE;
modbus_uart_buff[ind++] = CRC_VALUE;
modbus_uart_buff[ind++] = CRC_VALUE >> 8;
hmodbus->RS_Message_Size = ind;
return RS_OK; // returns ok
}
/**
* @brief Parse message from buffer to process it.
* @param hRS - указатель на хендлер RS.
* @param RS_msg - указатель на структуру сообщения.
* @param msg_uart_buff - указатель на буффер UART.
* @return RS_RES - статус о результате заполнения структуры.
* @details Заполнение структуры сообщения из буффера UART.
*/
RS_StatusTypeDef RS_Parse_Message(RS_HandleTypeDef *hmodbus, RS_MsgTypeDef *modbus_msg, uint8_t *modbus_uart_buff)
{
uint32_t check_empty_buff;
int ind = 0; // ind for modbus-uart buffer
//-----INFO ABOUT DATA/MESSAGE-------
//-----------[first bits]------------
// get ID of message/user
modbus_msg->MbAddr = modbus_uart_buff[ind++];
if(modbus_msg->MbAddr != hmodbus->ID)
return RS_SKIP;
// get func code
modbus_msg->Func_Code = modbus_uart_buff[ind++];
if(modbus_msg->Func_Code == MB_R_DEVICE_INFO) // if it device identification request
{
modbus_msg->DevId.MEI_Type = modbus_uart_buff[ind++];
modbus_msg->DevId.ReadDevId = modbus_uart_buff[ind++];
modbus_msg->DevId.NextObjId = modbus_uart_buff[ind++];
modbus_msg->ByteCnt = 0;
}
else // if its classic modbus request
{
// get address from CMD
modbus_msg->Addr = modbus_uart_buff[ind++] << 8;
modbus_msg->Addr |= modbus_uart_buff[ind++];
// get address from CMD
modbus_msg->Qnt = modbus_uart_buff[ind++] << 8;
modbus_msg->Qnt |= modbus_uart_buff[ind++];
}
if(hmodbus->f.RX_Half == 0) // if all message received
{
//---------------DATA----------------
// (optional)
if (modbus_msg->ByteCnt != 0)
{
ind++; // increment ind for data_size byte
//check that data size is correct
if (modbus_msg->ByteCnt > DATA_SIZE*2)
{
modbus_msg->Func_Code += ERR_VALUES_START;
return RS_PARSE_MSG_ERR;
}
uint16_t *tmp_data_addr = (uint16_t *)modbus_msg->DATA;
for(int i = 0; i < modbus_msg->ByteCnt; i++) // /2 because we transmit 8 bits, not 16 bits
{ // set data
if (i%2 == 0)
*tmp_data_addr = ((uint16_t)modbus_uart_buff[ind++] << 8);
else
{
*tmp_data_addr |= modbus_uart_buff[ind++];
tmp_data_addr++;
}
}
}
//---------------CRC----------------
//----------[last 16 bits]----------
// calc crc of received data
uint16_t CRC_VALUE = crc16(modbus_uart_buff, ind);
// get crc of received data
modbus_msg->MB_CRC = modbus_uart_buff[ind++];
modbus_msg->MB_CRC |= modbus_uart_buff[ind++] << 8;
// compare crc
if (modbus_msg->MB_CRC != CRC_VALUE)
{
modbus_msg->Func_Code += ERR_VALUES_START;
}
// hmodbus->MB_RESPONSE = MB_CRC_ERR; // set func code - error about wrong crc
// check is buffer empty
check_empty_buff = 0;
for(int i=0; i<ind;i++)
check_empty_buff += modbus_uart_buff[i];
// if(check_empty_buff == 0)
// hmodbus->MB_RESPONSE = MB_EMPTY_MSG; //
}
return RS_OK;
}
/**
* @brief Define size of RX Message that need to be received.
* @param hRS - указатель на хендлер RS.
* @param rx_data_size - указатель на переменную для записи кол-ва байт для принятия.
* @return RS_RES - статус о корректности рассчета кол-ва байт для принятия.
* @details Определение сколько байтов надо принять по протоколу.
*/
RS_StatusTypeDef RS_Define_Size_of_RX_Message(RS_HandleTypeDef *hmodbus, uint32_t *rx_data_size)
{
RS_StatusTypeDef MB_RES = 0;
MB_RES = RS_Parse_Message(hmodbus, hmodbus->pMessagePtr, hmodbus->pBufferPtr);
if(MB_RES == RS_SKIP) // if message not for us
return MB_RES; // return
if ((hmodbus->pMessagePtr->Func_Code & ~ERR_VALUES_START) < 0x0F)
{
hmodbus->pMessagePtr->ByteCnt = 0;
*rx_data_size = 1;
}
else
{
hmodbus->pMessagePtr->ByteCnt = hmodbus->pBufferPtr[RX_FIRST_PART_SIZE-1]; // get numb of data in command
// +1 because that defines is size, not ind.
*rx_data_size = hmodbus->pMessagePtr->ByteCnt + 2;
}
if(hmodbus->pMessagePtr->Func_Code == MB_R_DEVICE_INFO)
{
*rx_data_size = 0;
}
hmodbus->RS_Message_Size = RX_FIRST_PART_SIZE + *rx_data_size; // size of whole message
return RS_OK;
}
//-----------------------------FOR USER------------------------------
//-------------------------------------------------------------------
void MB_DevoceInentificationInit(void)
{
MB_INFO.VendorName.name = MODBUS_VENDOR_NAME;
MB_INFO.ProductCode.name = MODBUS_PRODUCT_CODE;
MB_INFO.Revision.name = MODBUS_REVISION;
MB_INFO.VendorUrl.name = MODBUS_VENDOR_URL;
MB_INFO.ProductName.name = MODBUS_PRODUCT_NAME;
MB_INFO.ModelName.name = MODBUS_MODEL_NAME;
MB_INFO.UserApplicationName.name = MODBUS_USER_APPLICATION_NAME;
MB_INFO.VendorName.length = sizeof(MODBUS_VENDOR_NAME);
MB_INFO.ProductCode.length = sizeof(MODBUS_PRODUCT_CODE);
MB_INFO.Revision.length = sizeof(MODBUS_REVISION);
MB_INFO.VendorUrl.length = sizeof(MODBUS_VENDOR_URL);
MB_INFO.ProductName.length = sizeof(MODBUS_PRODUCT_NAME);
MB_INFO.ModelName.length = sizeof(MODBUS_MODEL_NAME);
MB_INFO.UserApplicationName.length = sizeof(MODBUS_USER_APPLICATION_NAME);
}

376
john103C6T6/Modbus/modbus.h Normal file
View File

@@ -0,0 +1,376 @@
/**
**************************************************************************
* @file modbus.h
* @brief Заголовочный файл модуля MODBUS.
* @details Данный файл необходимо подключить в rs_message.h. После подключать
* rs_message.h к основному проекту.
*
* @defgroup MODBUS
* @brief Modbus stuff
*
*************************************************************************/
#ifndef __MODBUS_H_
#define __MODBUS_H_
#include "modbus_config.h"
#include "modbus_data.h"
//#include "settings.h" // for modbus settings
/**
* @addtogroup MODBUS_SETTINGS
* @ingroup MODBUS
* @brief Some defines for modbus
@{
*/
/////////////////////////////////////////////////////////////////////
//////////////////////////---SETTINGS---/////////////////////////////
// USER SETTINGS FOR MODBUS IN interface_config.h
//////////////////////////---SETTINGS---/////////////////////////////
/////////////////////////////////////////////////////////////////////
/////////////////////---USER MESSAGE DEFINES---//////////////////////
//-------------DEFINES FOR STRUCTURE----------------
/* defines for structure of modbus message */
#define MbAddr_SIZE 1 ///< size of (MbAddr)
#define Func_Code_SIZE 1 ///< size of (Func_Code)
#define Addr_SIZE 2 ///< size of (Addr)
#define Qnt_SIZE 2 ///< size of (Qnt)
#define ByteCnt_SIZE 1 ///< size of (ByteCnt)
#define DATA_SIZE 125 ///< maximum number of data: DWORD (NOT MESSAGE SIZE)
#define CRC_SIZE 2 ///< size of (MB_CRC) in bytes
/** @brief Size of whole message */
#define INFO_SIZE_MAX (MbAddr_SIZE+Func_Code_SIZE+Addr_SIZE+Qnt_SIZE+ByteCnt_SIZE)
/** @brief Size of first part of message that will be received
first receive info part of message, than defines size of rest message*/
#define RX_FIRST_PART_SIZE INFO_SIZE_MAX
/** @brief Size of buffer: max size of whole message */
#define MSG_SIZE_MAX (INFO_SIZE_MAX + DATA_SIZE*2 + CRC_SIZE) // max possible size of message
/** @brief Structure for modbus exception codes */
typedef enum //MB_ExceptionTypeDef
{
// reading
NO_ERRORS = 0x00, ///< no errors
ILLEGAL_FUNCTION = 0x01, ///< Принятый код функции не может быть обработан
ILLEGAL_DATA_ADDRESS = 0x02, ///< Адрес данных, указанный в запросе, недоступен
ILLEGAL_DATA_VALUE = 0x03, ///< Значение, содержащееся в поле данных запроса, является недопустимой величиной
SLAVE_DEVICE_FAILURE = 0x04, ///< Невосстанавливаемая ошибка имела место, пока ведомое устройство пыталось выполнить затребованное действие
// ACKNOWLEDGE = 0x05, ///< idk
// SLAVE_DEVICE_BUSY = 0x06, ///< idk
// MEMORY_PARITY_ERROR = 0x08, ///< idk
}MB_ExceptionTypeDef;
#define ERR_VALUES_START 0x80U ///< from this value starts error func codes
/** @brief Structure for modbus func codes */
typedef enum //MB_FunctonTypeDef
{
/* COMMANDS */
// reading
MB_R_COILS = 0x01, ///< Чтение битовых ячеек
MB_R_DISC_IN = 0x02, ///< Чтение дискретных входов
#ifndef MODBUS_SWITCH_COMMAND_R_IN_REGS_AND_R_HOLD_REGS
MB_R_HOLD_REGS = 0x03, ///< Чтение входных регистров
MB_R_IN_REGS = 0x04, ///< Чтение регистров хранения
#else
MB_R_HOLD_REGS = 0x04, ///< Чтение входных регистров
MB_R_IN_REGS = 0x03, ///< Чтение регистров хранения
#endif
// writting
MB_W_COIL = 0x05, ///< Запись битовой ячейки
MB_W_HOLD_REG = 0x06, ///< Запись одиночного регистра
MB_W_COILS = 0x0F, ///< Запись нескольких битовых ячеек
MB_W_HOLD_REGS = 0x10, ///< Запись нескольких регистров
MB_R_DEVICE_INFO = 0x2B, ///< Чтения информации об устройстве
/* ERRORS */
// error reading
MB_ERR_R_COILS = MB_R_COILS + ERR_VALUES_START, ///< Ошибка чтения битовых ячеек
MB_ERR_R_DISC_IN = MB_R_DISC_IN + ERR_VALUES_START, ///< Ошибка чтения дискретных входов
MB_ERR_R_IN_REGS = MB_R_IN_REGS + ERR_VALUES_START, ///< Ошибка чтения регистров хранения
MB_ERR_R_HOLD_REGS = MB_R_HOLD_REGS + ERR_VALUES_START, ///< Ошибка чтения входных регистров
// error writting
MB_ERR_W_COIL = MB_W_COIL + ERR_VALUES_START, ///< Ошибка записи битовой ячейки
MB_ERR_W_HOLD_REG = MB_W_HOLD_REG + ERR_VALUES_START, ///< Ошибка записи одиночного регистра
MB_ERR_W_COILS = MB_W_COILS + ERR_VALUES_START, ///< Ошибка записи нескольких битовых ячеек
MB_ERR_W_HOLD_REGS = MB_W_HOLD_REGS + ERR_VALUES_START, ///< Ошибка записи нескольких регистров
}MB_FunctonTypeDef;
/** @brief Structure for MEI func codes */
typedef enum //MB_FunctonTypeDef
{
MEI_DEVICE_IDENTIFICATION = 0x0E,
}MB_MEITypeDef;
/** @brief Structure for MEI func codes */
typedef enum //MB_FunctonTypeDef
{
MB_BASIC_IDENTIFICATION = 0x01,
MB_REGULAR_IDENTIFICATION = 0x02,
/* ERRORS */
MB_ERR_BASIC_IDENTIFICATION = MB_BASIC_IDENTIFICATION + ERR_VALUES_START,
MB_ERR_REGULAR_IDENTIFICATION = MB_REGULAR_IDENTIFICATION + ERR_VALUES_START,
}MB_ConformityTypeDef;
/** @brief Structure for decive identification message type */
typedef struct
{
MB_MEITypeDef MEI_Type; ///< MEI Type assigned number for Device Identification Interface
MB_ConformityTypeDef ReadDevId;
MB_ConformityTypeDef Conformity;
uint8_t MoreFollows; ///< in this library always a zero
uint8_t NextObjId;
uint8_t NumbOfObj;
}MB_DevIdMsgTypeDef;
/** @brief Structure for modbus messsage */
typedef struct // RS_MsgTypeDef
{
uint16_t Transaction_ID; ///< Modbus TCP Transaction_ID
uint16_t Protocol_ID; ///<
uint16_t Pack_length;
uint8_t MbAddr; ///< Modbus Slave Address
MB_FunctonTypeDef Func_Code; ///< Modbus Function Code
MB_DevIdMsgTypeDef DevId; ///< Read Device Identification Header struct
uint16_t Addr; ///< Modbus Address of data
uint16_t Qnt; ///< Quantity of modbus data
uint8_t ByteCnt; ///< Quantity of bytes of data in message to transmit/receive
uint16_t DATA[DATA_SIZE]; ///< Modbus Data
MB_ExceptionTypeDef Except_Code; ///< Exception Code for the command
uint16_t MB_CRC; ///< Modbus CRC
}RS_MsgTypeDef;
//--------------------------------------------------
extern RS_MsgTypeDef MODBUS_MSG;
/////////////////////---MODBUS USER SETTINGS---//////////////////////
/** MODBUS_SETTINGS
* @}
*/
/////////////////////////////////////////////////////////////////////
////////////////////---MODBUS MESSAGE DEFINES---/////////////////////
/**
* @addtogroup MODBUS_MESSAGE_DEFINES
* @ingroup MODBUS
* @brief Some defines for modbus
@{
*/
/** @brief Structure for coils operation */
typedef enum
{
SET_COIL,
RESET_COIL,
TOOGLE_COIL,
}MB_CoilsOpTypeDef;
//--------------------------------------------------
/**
* @brief Macros to set pointer to 16-bit array
* @param _arr_ - массив регистров (16-бит).
*/
#define MB_Set_Arr16_Ptr(_arr_) ((uint16_t*)(&(_arr_)))
/**
* @brief Macros to set pointer to register
* @param _parr_ - массив регистров.
* @param _addr_ - Номер регистра (его индекс) от начала массива _arr_.
*/
#define MB_Set_Register_Ptr(_parr_, _addr_) ((uint16_t *)(_parr_)+(_addr_))
/**
* @brief Macros to set pointer to a certain register that contains certain coil
* @param _parr_ - массив коилов.
* @param _coil_ - Номер коила от начала массива _arr_.
* @note Используется вместе с @ref MB_Set_Coil_Mask
@verbatim Пояснение выражений
(_coil_/16) - get index (address shift) of register that contain certain coil
Visual explanation: 30th coil in coils registers array
xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxCx
|register[0]----| |register[1]----|
|skip this------| |get this-------|
|shift to 14 bit|
@endverbatim
*/
#define MB_Set_Coil_Reg_Ptr(_parr_, _coil_) ((uint16_t *)(_parr_)+((_coil_)/16))
/**
* @brief Macros to set mask to a certain bit in coils register
* @param _coil_ - Номер коила от начала массива _arr_.
* @note Используется вместе с @ref MB_Set_Coil_Reg_Ptr
@verbatim Пояснение выражений
(16*(_coil_/16) - how many coils we need to skip. e.g. (16*30/16) - skip 16 coils from first register
_coil_-(16*(_coil_/16)) - shift to certain coil in certain register
e.g. Coil(30) gets in register[1] (30/16 = 1) coil №14 (30 - (16*30/16) = 30 - 16 = 14)
Visual explanation: 30th coil in coils registers array
xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxCx
|register[0]----| |register[1]----|
|skip this------| |get this-------|
|shift to 14 bit|
@endverbatim
*/
#define MB_Set_Coil_Mask(_coil_) (1 << ( _coil_ - (16*((_coil_)/16)) ))
/**
* @brief Read Coil at its local address.
* @param _parr_ - массив коилов.
* @param _coil_ - Номер коила от начала массива _arr_.
* @return uint16_t - Возвращает запрошенный коил на 0м бите.
*
* @details Позволяет обратиться к коилу по адресу относительно _arr_.
*/
#define MB_Read_Coil_Local(_parr_, _coil_) (( *MB_Set_Coil_Reg_Ptr(_parr_, _coil_) & MB_Set_Coil_Mask(_coil_) ) >> (_coil_))
/**
* @brief Set Coil at its local address.
* @param _parr_ - указатель на массив коилов.
* @param _coil_ - Номер коила от начала массива _arr_.
*
* @details Позволяет обратиться к коилу по адресу относительно _arr_.
*/
#define MB_Set_Coil_Local(_parr_, _coil_) *MB_Set_Coil_Reg_Ptr(_parr_, _coil_) |= MB_Set_Coil_Mask(_coil_)
/**
* @brief Reset Coil at its local address.
* @param _parr_ - указатель на массив коилов.
* @param _coil_ - Номер коила от начала массива _arr_.
*
* @details Позволяет обратиться к коилу по адресу относительно _arr_.
*/
#define MB_Reset_Coil_Local(_parr_, _coil_) *MB_Set_Coil_Reg_Ptr(_parr_, _coil_) &= ~(MB_Set_Coil_Mask(_coil_))
/**
* @brief Set Coil at its local address.
* @param _parr_ - указатель на массив коилов.
* @param _coil_ - Номер коила от начала массива _arr_.
*
* @details Позволяет обратиться к коилу по адресу относительно _arr_.
*/
#define MB_Toogle_Coil_Local(_parr_, _coil_) *MB_Set_Coil_Reg_Ptr(_parr_, _coil_) ^= MB_Set_Coil_Mask(_coil_)
//--------------------------------------------------
//------------------OTHER DEFINES-------------------
#define RegisterType_Holding 0
#define RegisterType_Input 1
#define RegisterType_Discrete 2
// create hadnles and settings for uart, tim, rs with _modbus_ name
//--------------------------------------------------
#ifndef Divide_Up
/**
* @brief Calc dividing including remainder
* @param _val_ - делимое.
* @param _div_ - делитель.
* @details Если результат деления без остатка: он возвращается как есть
Если с остатком - округляется вверх
*/
//#define Divide_Up(_val_, _div_) (((_val_)%(_div_))? (_val_)/(_div_)+1 : (_val_)/_div_) /* через тернарный оператор */
#define Divide_Up(_val_, _div_) ((_val_ - 1) / _div_) + 1 /* через мат выражение */
#endif
#ifndef ByteSwap16
/**
* @brief Swap between Little Endian and Big Endian
* @param v - Переменная для свапа.
* @return v (new) - Свапнутая переменная.
* @details Переключения между двумя типами хранения слова: HI-LO байты и LO-HI байты.
*/
#define ByteSwap16(v) (((v&0xFF00) >> (8)) | ((v&0x00FF) << (8)))
#endif
/** GENERAL_MODBUS_STUFF
* @}
*/
////////////////////---MODBUS MESSAGE DEFINES---/////////////////////
/////////////////////////////////////////////////////////////////////
/////////////////////////---FUNCTIONS---/////////////////////////////
/**
* @addtogroup MODBUS_FUNCTIONS
* @ingroup MODBUS
* @brief Function for controling modbus communication
*/
//----------------FUNCTIONS FOR USER----------------
/**
* @addtogroup MODBUS_DATA_ACCESS_FUNCTIONS
* @ingroup MODBUS_FUNCTIONS
* @brief Function for user use
@{
*/
/* First set up of MODBUS */
void MODBUS_FirstInit(void);
/* Set or Reset Coil at its global address */
MB_ExceptionTypeDef MB_Write_Coil_Global(uint16_t Addr, MB_CoilsOpTypeDef WriteVal);
/* Read Coil at its global address */
uint16_t MB_Read_Coil_Global(uint16_t Addr, MB_ExceptionTypeDef *Exception);
/** MODBUS_DATA_ACCESS_FUNCTIONS
* @}
*/
//---------PROCESS MODBUS COMMAND FUNCTIONS---------
/**
* @addtogroup MODBUS_CMD_PROCESS_FUNCTIONS
* @ingroup MODBUS_FUNCTIONS
* @brief Function process commands
@{
*/
/* Check is address valid for certain array */
MB_ExceptionTypeDef MB_Check_Address_For_Arr(uint16_t Addr, uint16_t Qnt, uint16_t R_ARR_ADDR, uint16_t R_ARR_NUMB);
/* Define Address Origin for Input/Holding Registers */
MB_ExceptionTypeDef MB_DefineRegistersAddress(uint16_t **pRegs, uint16_t Addr, uint16_t Qnt, uint8_t RegisterType);
/* Define Address Origin for coils */
MB_ExceptionTypeDef MB_DefineCoilsAddress(uint16_t **pCoils, uint16_t Addr, uint16_t Qnt, uint16_t *start_shift, uint8_t WriteFlag);
/* Proccess command Read Coils (01 - 0x01) */
uint8_t MB_Read_Coils(RS_MsgTypeDef *modbus_msg);
/* Proccess command Read Holding Registers (03 - 0x03) */
uint8_t MB_Read_Hold_Regs(RS_MsgTypeDef *modbus_msg);
/* Proccess command Read Input Registers (04 - 0x04) */
uint8_t MB_Read_Input_Regs(RS_MsgTypeDef *modbus_msg);
/* Proccess command Write Single Coils (05 - 0x05) */
uint8_t MB_Write_Single_Coil(RS_MsgTypeDef *modbus_msg);
/* Proccess command Write Multiple Coils (15 - 0x0F) */
uint8_t MB_Write_Miltuple_Coils(RS_MsgTypeDef *modbus_msg);
/* Proccess command Write Multiple Register (16 - 0x10) */
uint8_t MB_Write_Miltuple_Regs(RS_MsgTypeDef *modbus_msg);
/** MODBUS_DATA_ACCESS_FUNCTIONS
* @}
*/
/////////////////////////---FUNCTIONS---/////////////////////////////
/////////////////////////////////////////////////////////////////////
/////////////////////////---CALC DEFINES---//////////////////////////
// TRACES DEFINES
#ifndef Trace_MB_UART_Enter
#define Trace_MB_UART_Enter()
#endif //Trace_MB_UART_Enter
#ifndef Trace_MB_UART_Exit
#define Trace_MB_UART_Exit()
#endif //Trace_MB_UART_Exit
#ifndef Trace_MB_TIM_Enter
#define Trace_MB_TIM_Enter()
#endif //Trace_MB_TIM_Enter
#ifndef Trace_MB_TIM_Exit
#define Trace_MB_TIM_Exit()
#endif //Trace_MB_TIM_Exit
#endif //__MODBUS_H_

View File

@@ -1,60 +1,33 @@
/**
******************************************************************************
* @file modbus_config.h
* @brief Конфигурационные параметры Modbus устройства
******************************************************************************
@addtogroup MODBUS_CONFIGS Modbus configs
@ingroup MODBUS
@brief Конфигурация библиотеки
@{
******************************************************************************
* @details
Файл содержит настройки для работы Modbus:
- Подключение библиотек контроллера
- ID устройства и таймауты
- Строковые идентификаторы (Vendor, Product, Revision)
- Настройки периферии (UART, TIMER)
- Подключение модулей Modbus
- Опциональные функции (переключение команд 0x03/0x04)
******************************************************************************/
**************************************************************************
* @file interface_config.h
* @brief Конфигурация для модбаса
*************************************************************************/
#ifndef _MODBUS_CONFIG_H_
#define _MODBUS_CONFIG_H_
#include "stm32f1xx_hal.h"
// Общие параметры
#define MODBUS_DEVICE_ID 3 ///< Адрес устройства в сети Modbus
#define MODBUS_TIMEOUT 5000 ///< Таймаут в тиках таймера
// MODBUS PARAMS
#define MODBUS_DEVICE_ID 1 ///< девайс текущего устройства
#define MODBUS_TIMEOUT 2000 ///< максимальнйы тайтаут MB в тиках таймера
// Строковые идентификаторы устройства
// STRING OBJECTS MODBUS
#define MODBUS_VENDOR_NAME "NIO-12"
#define MODBUS_PRODUCT_CODE ""
#define MODBUS_REVISION ""
#define MODBUS_REVISION "Ver. 1.0"
#define MODBUS_VENDOR_URL ""
#define MODBUS_PRODUCT_NAME ""
#define MODBUS_MODEL_NAME ""
#define MODBUS_MODEL_NAME "STM32F103"
#define MODBUS_USER_APPLICATION_NAME ""
#define MODBUS_NUMB_OF_USEROBJECTS 0 ///< Количество пользовательских объектов
#define MODBUS_USEROBJECT_0_NAME "" ///< Строка пользовательского идентификатора 0. По аналогии можно определить строки до <=128 USEROBJECT
// PERIPH FUNCTIONS AND HANDLERS
#define RS_UART_Init MX_USART1_UART_Init //инициализация uart
#define RS_UART_DeInit HAL_UART_MspDeInit //деинициализация uart
#define RS_TIM_Init MX_TIM2_Init //инициализация таймера
#define RS_TIM_DeInit HAL_TIM_Base_MspDeInit//деинициализация таймера
#define rs_huart huart1 //используемый uart
#define rs_htim htim2 //используемый таймера
// Периферия (опционально)
#define mb_huart huart1 ///< Удобный дефайн для модбасовского uart
#define mb_htim htim2 ///< Удобный дефайн для модбасовского таймера
//#define RS_EnableReceive() ///< Функция изменения направления передачи на ПРИЕМ для RS-485
//#define RS_EnableTransmit() ///< Функция изменения направления передачи на ПЕРЕДАЧУ для RS-485
// Модули modbus
#define MODBUS_ENABLE_SLAVE ///< Включить обработку СЛЕЙВ режима
//#define MODBUS_ENABLE_MASTER ///< Включить обработку МАСТЕР режима
#define MODBUS_ENABLE_COILS ///< Включить обработку коилов
#define MODBUS_ENABLE_HOLDINGS ///< Включить обработку регистров хранения
#define MODBUS_ENABLE_INPUTS ///< Включить обработку входных регистров
#define MODBUS_ENABLE_DEVICE_IDENTIFICATIONS ///< Включить обработку идентификаторы устройства
#define MODBUS_ENABLE_DIAGNOSTICS ///< Включить обработку диагностики модбас
//#define MODBUS_PROTOCOL_TCP ///< Включить TCP-протокол, иначе - RTU
/**
* @brief Поменять комманды 0x03 и 0x04 местами (для LabView терминалки от двигателей)
@@ -68,4 +41,4 @@
#endif //_MODBUS_CONFIG_H_
#endif //_MODBUS_CONFIG_H_

View File

@@ -1,141 +0,0 @@
/**
******************************************************************************
* @file modbus_data.c
* @brief Функции доступа к данным Modbus
******************************************************************************
* @details
Модуль реализует функции валидации адресов и доступа к данным:
- Проверка корректности запрашиваемых адресов
- Определение указателей на реальные данные в памяти
- Поддержка пользовательских массивов регистров и coils
@section Валидация адресов:
- MB_Check_Address_For_Arr() - проверка принадлежности адреса массиву
- MB_DefineRegistersAddress() - получение указателя на регистры
- MB_DefineCoilsAddress() - получение указателя на coils
******************************************************************************/
#include "modbus_core.h"
#include "modbus_coils.h"
#include "modbus_holdregs.h"
#include "modbus_inputregs.h"
#include "modbus_devid.h"
/**
* @brief Check is address valid for certain array.
* @param Addr Начальный адресс.
* @param Qnt Количество запрашиваемых элементов.
* @param R_ARR_ADDR Начальный адресс массива R_ARR.
* @param R_ARR_NUMB Количество элементов в массиве R_ARR.
* @return ExceptionCode - ET_ILLEGAL_DATA_ADRESS если адресс недействителен, и ET_NO_ERRORS если все ок.
*
* @details Позволяет определить, принадлежит ли адресс Addr массиву R_ARR:
* Если адресс Addr находится в диапазоне адрессов массива R_ARR, то возвращаем NO_ERROR.
* Если адресс Addr находится за пределами адрессов массива R_ARR - ET_ILLEGAL_DATA_ADDRESSю.
*/
MB_ExceptionTypeDef MB_Check_Address_For_Arr(uint16_t Addr, uint16_t Qnt, uint16_t R_ARR_ADDR, uint16_t R_ARR_NUMB)
{
// if address from this array
if(Addr >= R_ARR_ADDR)
{
// if quantity too big return error
if ((Addr - R_ARR_ADDR) + Qnt > R_ARR_NUMB)
{
return ET_ILLEGAL_DATA_ADDRESS; // return exception code
}
// if all ok - return no errors
return ET_NO_ERRORS;
}
// if address isnt from this array return error
else
return ET_ILLEGAL_DATA_ADDRESS; // return exception code
}
/**
* @brief Define Address Origin for Input/Holding Registers
* @param pRegs Указатель на указатель регистров.
* @param Addr Адрес начального регистра.
* @param Qnt Количество запрашиваемых регистров.
* @param WriteFlag Флаг регистр нужны для чтения или записи.
* @return ExceptionCode Код исключения если есть, и ET_NO_ERRORS если нет.
*
* @details Определение адреса начального регистра.
* @note WriteFlag пока не используется.
*/
MB_ExceptionTypeDef MB_DefineRegistersAddress(uint16_t **pRegs, uint16_t Addr, uint16_t Qnt, uint8_t RegisterType)
{
/* check quantity error */
if (Qnt > DATA_SIZE)
{
return ET_ILLEGAL_DATA_VALUE; // return exception code
}
if(RegisterType == RegisterType_Holding)
{
// Default holding registers
if(MB_Check_Address_For_Arr(Addr, Qnt, R_HOLDING_ADDR, R_HOLDING_QNT) == ET_NO_ERRORS)
{
*pRegs = MB_Set_Register_Ptr(&MB_DATA.HoldRegs, Addr - R_HOLDING_ADDR); // указатель на выбранный по Addr регистр
}
// if address doesnt match any array - return illegal data address response
else
{
return ET_ILLEGAL_DATA_ADDRESS;
}
}
else if(RegisterType == RegisterType_Input)
{
// Default input registers
if(MB_Check_Address_For_Arr(Addr, Qnt, R_INPUT_ADDR, R_INPUT_QNT) == ET_NO_ERRORS)
{
*pRegs = MB_Set_Register_Ptr(&MB_DATA.InRegs, Addr - R_INPUT_ADDR); // указатель на выбранный по Addr регистр
}
// if address doesnt match any array - return illegal data address response
else
{
return ET_ILLEGAL_DATA_ADDRESS;
}
}
else
{
return ET_ILLEGAL_FUNCTION;
}
// if found requeried array return no err
return ET_NO_ERRORS; // return no errors
}
/**
* @brief Define Address Origin for coils
* @param pCoils Указатель на указатель коилов.
* @param Addr Адресс начального коила.
* @param Qnt Количество запрашиваемых коилов.
* @param start_shift Указатель на переменную содержащую сдвиг внутри регистра для начального коила.
* @param WriteFlag Флаг коилы нужны для чтения или записи.
* @return ExceptionCode Код исключения если есть, и ET_NO_ERRORS если нет.
*
* @details Определение адреса начального регистра запрашиваемых коилов.
* @note WriteFlag используется для определния регистров GPIO: ODR или IDR.
*/
MB_ExceptionTypeDef MB_DefineCoilsAddress(uint16_t **pCoils, uint16_t Addr, uint16_t Qnt, uint16_t *start_shift, uint8_t WriteFlag)
{
/* check quantity error */
if (Qnt > 2000)
{
return ET_ILLEGAL_DATA_VALUE; // return exception code
}
// Default coils
if(MB_Check_Address_For_Arr(Addr, Qnt, C_CONTROL_ADDR, C_CONTROL_QNT) == ET_NO_ERRORS)
{
*pCoils = MB_Set_Coil_Reg_Ptr(&MB_DATA.Coils, Addr - C_CONTROL_ADDR); // указатель на выбранный по Addr массив коилов
}
// if address doesnt match any array - return illegal data address response
else
{
return ET_ILLEGAL_DATA_ADDRESS;
}
*start_shift = Addr % 16; // set shift to requested coil
// if found requeried array return no err
return ET_NO_ERRORS; // return no errors
}

View File

@@ -1,125 +1,92 @@
/**
/**
**************************************************************************
* @file modbus_data.h
* @brief Заголовочный файл с описанием даты MODBUS.
* @details Данный файл необходимо подключается в rs_message.h. После rs_message.h
* @details Данный файл необходимо подключается в rs_message.h. После rs_message.h
* подключается к основному проекту.
*
*
* @defgroup MODBUS_DATA
* @ingroup MODBUS
* @brief Modbus data description
*
*************************************************************************/
#ifndef _MODBUS_DATA_H_
#define _MODBUS_DATA_H_
// DEFINES FOR INPUT REGISTERS ARRAYS
#define R_INPUT_ADDR 0
#define R_INPUT_QNT 2000
// DEFINES FOR HOLDING REGISTERS ARRAYS
#define R_HOLDING_ADDR 0
#define R_HOLDING_QNT 2000
// DEFINES FOR COIL ARRAYS
#define C_CONTROL_ADDR 0
#define C_CONTROL_QNT 1000
#include "stdint.h"
#include "ds18b20_driver.h"
#include "PROJ_setup.h"
//--------------DEFINES FOR REGISTERS---------------
// DEFINES FOR ARRAYS
/**
/**
* @addtogroup MODBUS_DATA_RERISTERS_DEFINES
* @ingroup MODBUS_DATA
* @brief Defines for registers
Структура дефайна адресов
@verbatim
@verbatim
Для массивов регистров:
R_<NAME_ARRAY>_ADDR - модбас адресс первого регистра в массиве
R_<NAME_ARRAY>_QNT - количество регистров в массиве
При добавлении новых массивов регистров, необходимо их добавить в функцию MB_DefineRegistersAddress
if(MB_Check_Address_For_Arr(Addr, Qnt, R_<NEW_ARRAY>_ADDR, R_<NEW_ARRAY>_QNT) == NO_ERRORS)
{
*pRegs = MB_Set_Register_Ptr(&<NEW_ARRAY>, Addr); // начало регистров хранения/входных
}
if(MB_Check_Address_For_Arr(Addr, Qnt, R_<NEW_ARRAY>_ADDR, R_<NEW_ARRAY>_QNT) == NO_ERRORS)
{
*pRegs = MB_Set_Register_Ptr(&<NEW_ARRAY>, Addr); // начало регистров хранения/входных
}
@endverbatim
* @{
*/
/**
/**
* @brief Регистры хранения
*/
/**
* @brief Определить размер структуры в регистрах модбас (16-бит слова)
*/
#define mb_sizeof(_struct_) (sizeof(_struct_)/sizeof(uint16_t))
/**
* @brief Определить количество резервных байт для выравнивания
* @details Выравнивает так, чтобы количество регистров в _struct_ и reserved равнялось _align_.
*
*/
#define mb_fill_rsv(_align_, _struct_) ((_align_ > mb_sizeof(_struct_)) ? (_align_ - mb_sizeof(_struct_)) : 0)
typedef __PACKED_STRUCT//MB_DataInRegsTypeDef
#define MAX_SENSE 30
typedef struct //MB_DataInRegsTypeDef
{
uint16_t sens_Temp[MAX_SENSE];
uint16_t UzptPLUS;
uint16_t UzptMINUS;
uint16_t UzptPLUS_MIN;
uint16_t sens_Temp[MAX_SENSE];
uint16_t reserve[mb_fill_rsv(1000, uint16_t[MAX_SENSE])];
DS18B20_Drv_t ID;
uint16_t reserve1[mb_fill_rsv(200, DS18B20_Drv_t)];
uint16_t num_Tsens;
}MB_DataInRegsTypeDef;
} MB_DataInRegsTypeDef;
/**
* @brief Входные регистры
/**
* @brief Входные регистры
*/
typedef __PACKED_STRUCT //MB_DataInRegsTypeDef
typedef struct //MB_DataInRegsTypeDef
{
uint16_t set_Temp[MAX_SENSE];
uint16_t reserve[mb_fill_rsv(100, uint16_t[MAX_SENSE])];
uint16_t set_hyst[MAX_SENSE];
uint16_t reserve1[mb_fill_rsv(100, uint16_t[MAX_SENSE])];
} MB_DataHoldRegsTypeDef;
uint16_t set_Temp[MAX_SENSE];
uint16_t set_hyst[MAX_SENSE];
}MB_DataHoldRegsTypeDef;
// DEFINES FOR INPUT REGISTERS ARRAYS
#define R_INPUT_ADDR 0
#define R_INPUT_QNT 40
// DEFINES FOR HOLDING REGISTERS ARRAYS
#define R_HOLDING_ADDR 0
#define R_HOLDING_QNT 40
/** MODBUS_DATA_RERISTERS_DEFINES
* @}
* @}
*/
//----------------DEFINES FOR COILS-----------------
/**
/**
* @addtogroup MODBUS_DATA_COILS_DEFINES
* @ingroup MODBUS_DATA
* @brief Defines for coils
@verbatim
@verbatim
Структура дефайна
Для массивов коилов:
C_<NAME_ARRAY>_ADDR - модбас адресс первого коила в массиве
@@ -135,149 +102,99 @@ typedef __PACKED_STRUCT //MB_DataInRegsTypeDef
@endverbatim
* @{
*/
/**
/**
* @brief Коилы
* @details Желательно с помощью reserved делать стркутуру кратной 16-битам
*/
typedef union
{
struct __packed {
unsigned state_val_01:1;
unsigned state_val_02:1;
unsigned state_val_03:1;
unsigned state_val_04:1;
unsigned state_val_05:1;
unsigned state_val_06:1;
unsigned state_val_07:1;
unsigned state_val_08:1;
unsigned state_val_09:1;
unsigned state_val_10:1;
unsigned state_val_11:1;
unsigned state_val_12:1;
unsigned state_val_13:1;
unsigned state_val_14:1;
unsigned state_val_15:1;
unsigned state_val_16:1;
} state_val_bit;
uint16_t all;
}word;
typedef struct //MB_DataCoilsTypeDef
{
__PACKED_STRUCT
{
unsigned state_val_01: 1;
unsigned state_val_02: 1;
unsigned state_val_03: 1;
unsigned state_val_04: 1;
unsigned state_val_05: 1;
unsigned state_val_06: 1;
unsigned state_val_07: 1;
unsigned state_val_08: 1;
unsigned state_val_09: 1;
unsigned state_val_10: 1;
unsigned state_val_11: 1;
unsigned state_val_12: 1;
unsigned state_val_13: 1;
unsigned state_val_14: 1;
unsigned state_val_15: 1;
unsigned state_val_16: 1;
} state_val_bit;
uint16_t all;
} word;
typedef union
{
__PACKED_STRUCT
{
unsigned Temp1_relay_isOn : 1;
unsigned Temp2_relay_isOn : 1;
unsigned Temp3_relay_isOn : 1;
unsigned Temp4_relay_isOn : 1;
unsigned Temp5_relay_isOn : 1;
unsigned Temp6_relay_isOn : 1;
unsigned Temp7_relay_isOn : 1;
unsigned Temp8_relay_isOn : 1;
unsigned Temp9_relay_isOn : 1;
unsigned Temp10_relay_isOn : 1;
unsigned Temp11_relay_isOn : 1;
unsigned Temp12_relay_isOn : 1;
unsigned Temp13_relay_isOn : 1;
unsigned Temp14_relay_isOn : 1;
unsigned Temp15_relay_isOn : 1;
unsigned Temp16_relay_isOn : 1;
} state_val_bit;
uint16_t all;
} RELAY_Struct;
typedef union
{
__PACKED_STRUCT
{
unsigned Temp1_isConnected : 1;
unsigned Temp2_isConnected : 1;
unsigned Temp3_isConnected : 1;
unsigned Temp4_isConnected : 1;
unsigned Temp5_isConnected : 1;
unsigned Temp6_isConnected : 1;
unsigned Temp7_isConnected : 1;
unsigned Temp8_isConnected : 1;
unsigned Temp9_isConnected : 1;
unsigned Temp10_isConnected : 1;
unsigned Temp11_isConnected : 1;
unsigned Temp12_isConnected : 1;
unsigned Temp13_isConnected : 1;
unsigned Temp14_isConnected : 1;
unsigned Temp15_isConnected : 1;
unsigned Temp16_isConnected : 1;
} state_val_bit;
uint16_t all;
} STATUS_TSENS;
typedef __PACKED_STRUCT
{
int temp ;
unsigned Temp_relay_on : 1;
unsigned Temp_relay_off : 1;
unsigned is_connect: 1;
} Temp_sens;
extern Temp_sens temp_sens ;
typedef __PACKED_STRUCT
{
word coils[3]; //48
uint16_t reserve_coils[mb_fill_rsv(128 / 16, word[3])];
STATUS_TSENS status_tSens[MAX_SENSE / 16]; //32
uint16_t reserve_status_tSens[mb_fill_rsv(128 / 16, STATUS_TSENS[MAX_SENSE / 16])];
RELAY_Struct relay_struct_on; //16 ON
uint16_t reserve_relay_struct_on[mb_fill_rsv(32 / 16, RELAY_Struct)];
RELAY_Struct relay_struct_off; //16 OFF
uint16_t reserve_relay_struct_off[mb_fill_rsv(32 / 16, RELAY_Struct)];
uint16_t reserve3[mb_fill_rsv(80 / 16, RELAY_Struct)];
unsigned init_param: 1; //384
unsigned init_Tsens: 1; //385
unsigned Save_Param_to_Flash: 1; //386
unsigned reserved2: 13;
} MB_DataCoilsTypeDef;
word coils[2];
unsigned init_param:1;
unsigned reserved:15;
}MB_DataCoilsTypeDef;
// DEFINES FOR COIL ARRAYS
#define C_CONTROL_ADDR 0
#define C_CONTROL_QNT 100
/** MODBUS_DATA_COILS_DEFINES
* @}
* @}
*/
//-----------MODBUS DEVICE DATA SETTING-------------
// MODBUS DATA STRUCTTURE
/**
* @brief Структура со всеми регистрами и коилами модбас
/**
* @brief Структура со всеми регистрами и коилами модбас
* @ingroup MODBUS_DATA
*/
typedef struct // tester modbus data
{
MB_DataInRegsTypeDef InRegs; ///< Modbus input registers @ref MB_DataInRegsTypeDef
MB_DataInRegsTypeDef InRegs; ///< Modbus input registers @ref MB_DataInRegsTypeDef
MB_DataCoilsTypeDef Coils; ///< Modbus coils @ref MB_DataCoilsTypeDef
MB_DataHoldRegsTypeDef HoldRegs; ///< Modbus holding registers @ref MB_DataHoldRegsTypeDef
} MB_DataStructureTypeDef;
MB_DataCoilsTypeDef Coils; ///< Modbus coils @ref MB_DataCoilsTypeDef
MB_DataHoldRegsTypeDef HoldRegs; ///< Modbus holding registers @ref MB_DataHoldRegsTypeDef
}MB_DataStructureTypeDef;
extern MB_DataStructureTypeDef MB_DATA;
/**
* @brief Структура для объекта Modbus
* @ingroup MODBUS_DATA
*/
typedef struct
{
unsigned length;
char *name;
}MB_DeviceObjectTypeDef;
/**
* @brief Структура для объектов Modbus
* @ingroup MODBUS_DATA
*/
typedef struct
{
MB_DeviceObjectTypeDef VendorName;
MB_DeviceObjectTypeDef ProductCode;
MB_DeviceObjectTypeDef Revision;
MB_DeviceObjectTypeDef VendorUrl;
MB_DeviceObjectTypeDef ProductName;
MB_DeviceObjectTypeDef ModelName;
MB_DeviceObjectTypeDef UserApplicationName;
}MB_DeviceIdentificationTypeDef;
void MB_DevoceInentificationInit(void);
#endif //_MODBUS_DATA_H_
/////////////////////////////////////////////////////////////

View File

@@ -1,282 +0,0 @@
/**
**************************************************************************
* @file modbus_data.h
* @brief Заголовочный файл с описанием даты MODBUS.
* @details Данный файл необходимо подключается в rs_message.h. После rs_message.h
* подключается к основному проекту.
*
* @defgroup MODBUS_DATA
* @ingroup MODBUS
* @brief Modbus data description
*
*************************************************************************/
#ifndef _MODBUS_DATA_H_
#define _MODBUS_DATA_H_
// DEFINES FOR INPUT REGISTERS ARRAYS
#define R_INPUT_ADDR 0
#define R_INPUT_QNT 2000
// DEFINES FOR HOLDING REGISTERS ARRAYS
#define R_HOLDING_ADDR 0
#define R_HOLDING_QNT 2000
// DEFINES FOR COIL ARRAYS
#define C_CONTROL_ADDR 0
#define C_CONTROL_QNT 1000
#include "stdint.h"
#include "ds18b20_driver.h"
#include "PROJ_setup.h"
//--------------DEFINES FOR REGISTERS---------------
// DEFINES FOR ARRAYS
/**
* @addtogroup MODBUS_DATA_RERISTERS_DEFINES
* @ingroup MODBUS_DATA
* @brief Defines for registers
Структура дефайна адресов
@verbatim
Для массивов регистров:
R_<NAME_ARRAY>_ADDR - модбас адресс первого регистра в массиве
R_<NAME_ARRAY>_QNT - количество регистров в массиве
При добавлении новых массивов регистров, необходимо их добавить в функцию MB_DefineRegistersAddress
if(MB_Check_Address_For_Arr(Addr, Qnt, R_<NEW_ARRAY>_ADDR, R_<NEW_ARRAY>_QNT) == NO_ERRORS)
{
*pRegs = MB_Set_Register_Ptr(&<NEW_ARRAY>, Addr); // начало регистров хранения/входных
}
@endverbatim
* @{
*/
/**
* @brief Регистры хранения
*/
/**
* @brief Определить размер структуры в регистрах модбас (16-бит слова)
*/
#define mb_sizeof(_struct_) (sizeof(_struct_)/sizeof(uint16_t))
/**
* @brief Определить количество резервных байт для выравнивания
* @details Выравнивает так, чтобы количество регистров в _struct_ и reserved равнялось _align_.
*
*/
#define mb_fill_rsv(_align_, _struct_) ((_align_ > mb_sizeof(_struct_)) ? (_align_ - mb_sizeof(_struct_)) : 0)
typedef __PACKED_STRUCT//MB_DataInRegsTypeDef
{
uint16_t sens_Temp[MAX_SENSE];
uint16_t reserve[mb_fill_rsv(1000, uint16_t[MAX_SENSE])];
DS18B20_Drv_t ID;
uint16_t reserve1[mb_fill_rsv(200, DS18B20_Drv_t)];
uint16_t num_Tsens;
} MB_DataInRegsTypeDef;
/**
* @brief Входные регистры
*/
typedef __PACKED_STRUCT //MB_DataInRegsTypeDef
{
uint16_t set_Temp[MAX_SENSE];
uint16_t reserve[mb_fill_rsv(100, uint16_t[MAX_SENSE])];
uint16_t set_hyst[MAX_SENSE];
uint16_t reserve1[mb_fill_rsv(100, uint16_t[MAX_SENSE])];
} MB_DataHoldRegsTypeDef;
/** MODBUS_DATA_RERISTERS_DEFINES
* @}
*/
//----------------DEFINES FOR COILS-----------------
/**
* @addtogroup MODBUS_DATA_COILS_DEFINES
* @ingroup MODBUS_DATA
* @brief Defines for coils
@verbatim
Структура дефайна
Для массивов коилов:
C_<NAME_ARRAY>_ADDR - модбас адресс первого коила в массиве
C_<NAME_ARRAY>_QNT - количество коилов в массиве (минимум 16)
При добавлении новых массивов коилов, необходимо их добавить в функцию MB_DefineCoilsAddress
if(MB_Check_Address_For_Arr(Addr, Qnt, C_<NEW_ARRAY>_ADDR, C_<NEW_ARRAY>_QNT) == NO_ERRORS)
{
*pCoils = MB_Set_Coil_Reg_Ptr(&<NEW_ARRAY>, Addr);
}
@endverbatim
* @{
*/
/**
* @brief Коилы
* @details Желательно с помощью reserved делать стркутуру кратной 16-битам
*/
typedef union
{
__PACKED_STRUCT
{
unsigned state_val_01: 1;
unsigned state_val_02: 1;
unsigned state_val_03: 1;
unsigned state_val_04: 1;
unsigned state_val_05: 1;
unsigned state_val_06: 1;
unsigned state_val_07: 1;
unsigned state_val_08: 1;
unsigned state_val_09: 1;
unsigned state_val_10: 1;
unsigned state_val_11: 1;
unsigned state_val_12: 1;
unsigned state_val_13: 1;
unsigned state_val_14: 1;
unsigned state_val_15: 1;
unsigned state_val_16: 1;
} state_val_bit;
uint16_t all;
} word;
typedef union
{
__PACKED_STRUCT
{
unsigned Temp1_relay_isOn : 1;
unsigned Temp2_relay_isOn : 1;
unsigned Temp3_relay_isOn : 1;
unsigned Temp4_relay_isOn : 1;
unsigned Temp5_relay_isOn : 1;
unsigned Temp6_relay_isOn : 1;
unsigned Temp7_relay_isOn : 1;
unsigned Temp8_relay_isOn : 1;
unsigned Temp9_relay_isOn : 1;
unsigned Temp10_relay_isOn : 1;
unsigned Temp11_relay_isOn : 1;
unsigned Temp12_relay_isOn : 1;
unsigned Temp13_relay_isOn : 1;
unsigned Temp14_relay_isOn : 1;
unsigned Temp15_relay_isOn : 1;
unsigned Temp16_relay_isOn : 1;
} state_val_bit;
uint16_t all;
} RELAY_Struct;
typedef union
{
__PACKED_STRUCT
{
unsigned Temp1_isConnected : 1;
unsigned Temp2_isConnected : 1;
unsigned Temp3_isConnected : 1;
unsigned Temp4_isConnected : 1;
unsigned Temp5_isConnected : 1;
unsigned Temp6_isConnected : 1;
unsigned Temp7_isConnected : 1;
unsigned Temp8_isConnected : 1;
unsigned Temp9_isConnected : 1;
unsigned Temp10_isConnected : 1;
unsigned Temp11_isConnected : 1;
unsigned Temp12_isConnected : 1;
unsigned Temp13_isConnected : 1;
unsigned Temp14_isConnected : 1;
unsigned Temp15_isConnected : 1;
unsigned Temp16_isConnected : 1;
} state_val_bit;
uint16_t all;
} STATUS_TSENS;
typedef __PACKED_STRUCT
{
int temp ;
unsigned Temp_relay_on : 1;
unsigned Temp_relay_off : 1;
unsigned is_connect: 1;
} Temp_sens;
extern Temp_sens temp_sens ;
typedef __PACKED_STRUCT
{
word coils[3]; //48
uint16_t reserve1[mb_fill_rsv(128 / 16, word[3])];
STATUS_TSENS status_tSens[MAX_SENSE / 16]; //32
uint16_t reserve2[mb_fill_rsv(128 / 16, STATUS_TSENS[MAX_SENSE / 16])];
RELAY_Struct relay_struct_on; //16 ON
RELAY_Struct relay_struct_off; //16 OFF
uint16_t reserve3[mb_fill_rsv(128 / 16, RELAY_Struct[MAX_SENSE / 16 * 2])];
unsigned init_param: 1; //384
unsigned init_Tsens: 1; //385
unsigned Save_Param_to_Flash: 1; //386
unsigned reserved2: 13;
} MB_DataCoilsTypeDef;
/** MODBUS_DATA_COILS_DEFINES
* @}
*/
//-----------MODBUS DEVICE DATA SETTING-------------
// MODBUS DATA STRUCTTURE
/**
* @brief Структура со всеми регистрами и коилами модбас
* @ingroup MODBUS_DATA
*/
typedef struct // tester modbus data
{
MB_DataInRegsTypeDef InRegs; ///< Modbus input registers @ref MB_DataInRegsTypeDef
MB_DataCoilsTypeDef Coils; ///< Modbus coils @ref MB_DataCoilsTypeDef
MB_DataHoldRegsTypeDef HoldRegs; ///< Modbus holding registers @ref MB_DataHoldRegsTypeDef
} MB_DataStructureTypeDef;
extern MB_DataStructureTypeDef MB_DATA;
#endif //_MODBUS_DATA_H_
/////////////////////////////////////////////////////////////
///////////////////////TEMP/OUTDATE/OTHER////////////////////

View File

@@ -0,0 +1,555 @@
/**
**************************************************************************
* @file rs_message.c
* @brief Модуль для реализации протоколов по RS/UART.
**************************************************************************\
* @details
* Данный модуль реализует основные функции для приема и передачи сообщений
* по протоколу RS через UART в режиме прерываний. Реализована обработка
* приема и передачи данных, управление состояниями RS, а также функции для
* инициализации и управления периферией.
*
* Реализованы следующие функции:
* - RS_Receive_IT() — запуск приема данных в прерывании по UART.
* - RS_Transmit_IT() — запуск передачи данных в прерывании по UART.
* - RS_Init() — инициализация структуры RS и привязка периферии.
* - RS_ReInit_UART() — переинициализация UART и перезапуск приема данных.
* - RS_Abort() — остановка работы RS/UART с очисткой флагов и структур.
* - RS_Handle_Receive_Start() — обработка старта приема данных по RS.
*
* В модуле также определен буфер RS_Buffer[] для хранения принимаемых/передаваемых данных.
*
* @note
* Для корректной работы модуля предполагается использование соответствующих
* обработчиков прерываний UART и таймера (RS_UART_Handler(), RS_TIM_Handler()),
* которые надо вызывать с обработчиках используемой периферии
@verbatim
//-------------------Функции-------------------//
Functions: users
- RS_Parse_Message/RS_Collect_Message Заполнение структуры сообщения и буфера
- RS_Response Ответ на сообщение
- RS_Define_Size_of_RX_Message Определение размера принимаемых данных
Functions: general
- RS_Receive_IT Ожидание комманды и ответ на неё
- RS_Transmit_IT Отправление комманды и ожидание ответа
- RS_Init Инициализация переферии и структуры для RS
- RS_ReInit_UART Реинициализация UART для RS
- RS_Abort Отмена приема/передачи по ЮАРТ
- RS_Init Инициализация периферии и modbus handler
Functions: callback/handler
- RS_Handle_Receive_Start Функция для запуска приема или остановки RS
- RS_Handle_Transmit_Start Функция для запуска передачи или остановки RS
- RS_UART_RxCpltCallback Коллбек при окончании приема или передачи
RS_UART_TxCpltCallback
- RS_UART_Handler Обработчик прерывания для UART
- RS_TIM_Handler Обработчик прерывания для TIM
@endverbatim
*************************************************************************/
#include "rs_message.h"
uint8_t RS_Buffer[MSG_SIZE_MAX]; // uart buffer
extern void RS_UART_Init(void);
extern void RS_UART_DeInit(UART_HandleTypeDef *huart);
extern void RS_TIM_Init(void);
extern void RS_TIM_DeInit(TIM_HandleTypeDef *htim);
//-------------------------------------------------------------------
//-------------------------GENERAL FUNCTIONS-------------------------
/**
* @brief Start receive IT.
* @param hRS - указатель на хендлер RS.
* @param RS_msg - указатель на структуру сообщения.
* @return RS_RES - статус о состоянии RS после инициализации приема.
*/
RS_StatusTypeDef RS_Receive_IT(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg)
{
RS_StatusTypeDef RS_RES = 0;
HAL_StatusTypeDef uart_res = 0;
//-------------CHECK RS LINE----------------
// check that receive isnt busy
if( RS_Is_RX_Busy(hRS) ) // if tx busy - return busy status
return RS_BUSY;
//-----------INITIALIZE RECEIVE-------------
// if all OK: start receiving
RS_EnableReceive();
RS_Set_Busy(hRS); // set RS busy
RS_Set_RX_Flags(hRS); // initialize flags for receive
hRS->pMessagePtr = RS_msg; // set pointer to message structire for filling it from UARTHandler fucntions
// start receiving
uart_res = HAL_UART_Receive_IT(hRS->huart, hRS->pBufferPtr, RX_FIRST_PART_SIZE); // receive until ByteCnt+1 byte,
// then in Callback restart receive for rest bytes
// if receive isnt started - abort RS
if(uart_res != HAL_OK)
{
RS_RES = RS_Abort(hRS, ABORT_RS);
printf_rs_err("\n%d: Error RS: Failed to start RS receiving...", uwTick);
}
else
{
RS_RES = RS_OK;
printf_rs("\n%d: RS: Start Receiving...", uwTick);
}
hRS->RS_STATUS = RS_RES;
return RS_RES; // returns result of receive init
}
/**
* @brief Start transmit IT.
* @param hRS - указатель на хендлер RS.
* @param RS_msg - указатель на структуру сообщения.
* @return RS_RES - статус о состоянии RS после инициализации передачи.
*/
RS_StatusTypeDef RS_Transmit_IT(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg)
{
RS_StatusTypeDef RS_RES = 0;
HAL_StatusTypeDef uart_res = 0;
//-------------CHECK RS LINE----------------
// check that transmit isnt busy
if( RS_Is_TX_Busy(hRS) ) // if tx busy - return busy status
return RS_BUSY;
// check receive line
//------------COLLECT MESSAGE---------------
RS_RES = RS_Collect_Message(hRS, RS_msg, hRS->pBufferPtr);
if (RS_RES != RS_OK) // if message isnt collect - stop RS and return error in RS_RES
{// need collect message status, so doesnt write abort to RS_RES
RS_Abort(hRS, ABORT_RS);
RS_Handle_Receive_Start(hRS, hRS->pMessagePtr); // restart receive
}
else // if collect successful
{
//----------INITIALIZE TRANSMIT-------------
RS_EnableTransmit();
// for(int i = 0; i < hRS->sRS_Timeout; i++);
RS_Set_Busy(hRS); // set RS busy
RS_Set_TX_Flags(hRS); // initialize flags for transmit IT
hRS->pMessagePtr = RS_msg; // set pointer for filling given structure from UARTHandler fucntion
// if all OK: start transmitting
uart_res = HAL_UART_Transmit_IT(hRS->huart, hRS->pBufferPtr, hRS->RS_Message_Size);
// if transmit isnt started - abort RS
if(uart_res != HAL_OK)
{
RS_RES = RS_Abort(hRS, ABORT_RS);
printf_rs_err("\n%d: Error RS: Failed to start RS transmitting...", uwTick);
}
else
{
RS_RES = RS_OK;
printf_rs("\n%d: RS: Start Transmitting...", uwTick);
}
}
hRS->RS_STATUS = RS_RES;
return RS_RES; // returns result of transmit init
}
/**
* @brief Initialize UART and handle RS stucture.
* @param hRS - указатель на хендлер RS.
* @param suart - указатель на структуру с настройками UART.
* @param stim - указатель на структуру с настройками таймера.
* @param pRS_BufferPtr - указатель на буффер для приема-передачи по UART. Если он NULL, то поставиться библиотечный буфер.
* @return RS_RES - статус о состоянии RS после инициализации.
* @note Инициализация перефирии и структуры для приема-передачи по RS.
*/
RS_StatusTypeDef RS_Init(RS_HandleTypeDef *hRS, UART_HandleTypeDef *huart, TIM_HandleTypeDef *htim, uint8_t *pRS_BufferPtr)
{
// check that hRS is defined
if (hRS == NULL)
return RS_ERR;
// check that huart is defined
if (huart == NULL)
return RS_ERR;
// init uart
// RS_UART_Init();
hRS->huart = huart;
// RS_TIM_Init();
hRS->htim = htim;
if (hRS->sRS_RX_Size_Mode == NULL)
return RS_ERR;
// check that buffer is defined
if (hRS->pBufferPtr == NULL)
{
hRS->pBufferPtr = RS_Buffer; // if no - set default
}
else
hRS->pBufferPtr = pRS_BufferPtr; // if yes - set by user
return RS_OK;
}
/**
* @brief ReInitialize UART and RS receive.
* @param hRS - указатель на хендлер RS.
* @param suart - указатель на структуру с настройками UART.
* @return RS_RES - статус о состоянии RS после инициализации.
* @note Реинициализация UART и приема по RS.
*/
HAL_StatusTypeDef RS_ReInit_UART(RS_HandleTypeDef *hRS, UART_HandleTypeDef *huart)
{
HAL_StatusTypeDef RS_RES;
hRS->f.ReInit_UART = 0;
// // check is settings are valid
// if(Check_UART_Init_Struct(suart) != HAL_OK)
// return HAL_ERROR;
RS_Abort(hRS, ABORT_RS);
RS_UART_DeInit(huart);
RS_UART_Init();
RS_Receive_IT(hRS, hRS->pMessagePtr);
return RS_RES;
}
/**
* @brief Abort RS/UART.
* @param hRS - указатель на хендлер RS.
* @param AbortMode - выбор, что надо отменить.
- ABORT_TX: Отмена передачи по ЮАРТ, с очищением флагов TX,
- ABORT_RX: Отмена приема по ЮАРТ, с очищением флагов RX,
- ABORT_RX_TX: Отмена приема и передачи по ЮАРТ,
- ABORT_RS: Отмена приема-передачи RS, с очищением всей структуры.
* @return RS_RES - статус о состоянии RS после аборта.
* @note Отмена работы UART в целом или отмена приема/передачи RS.
Также очищается хендл hRS.
*/
RS_StatusTypeDef RS_Abort(RS_HandleTypeDef *hRS, RS_AbortTypeDef AbortMode)
{
HAL_StatusTypeDef uart_res = 0;
hRS->htim->Instance->CNT = 0;
__HAL_TIM_CLEAR_IT(hRS->htim, TIM_IT_UPDATE);
if(hRS->sRS_Timeout) // if timeout setted
HAL_TIM_Base_Stop_IT(hRS->htim); // stop timeout
if((AbortMode&ABORT_RS) == 0x00)
{
if((AbortMode&ABORT_RX) == ABORT_RX)
{
uart_res = HAL_UART_AbortReceive(hRS->huart); // abort receive
RS_Reset_RX_Flags(hRS);
}
if((AbortMode&ABORT_TX) == ABORT_TX)
{
uart_res = HAL_UART_AbortTransmit(hRS->huart); // abort transmit
RS_Reset_TX_Flags(hRS);
}
}
else
{
uart_res = HAL_UART_Abort(hRS->huart);
RS_Clear_All(hRS);
}
hRS->RS_STATUS = RS_ABORTED;
return RS_ABORTED;
}
//-------------------------GENERAL FUNCTIONS-------------------------
//-------------------------------------------------------------------
//-------------------------------------------------------------------
//--------------------CALLBACK/HANDLER FUNCTIONS---------------------
/**
* @brief Handle for starting receive.
* @param hRS - указатель на хендлер RS.
* @param RS_msg - указатель на структуру сообщения.
* @return RS_RES - статус о состоянии RS после инициализации приема или окончания общения.
* @note Определяет начинать прием команды/ответа или нет.
*/
RS_StatusTypeDef RS_Handle_Receive_Start(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg)
{
RS_StatusTypeDef RS_RES = 0;
switch(hRS->sRS_Mode)
{
case SLAVE_ALWAYS_WAIT: // in slave mode with permanent waiting
RS_RES = RS_Receive_IT(hRS, RS_msg); break; // start receiving again
case SLAVE_TIMEOUT_WAIT: // in slave mode with timeout waiting (start receiving cmd by request)
RS_Set_Free(hRS); RS_RES = RS_OK; break; // end RS communication (set RS unbusy)
}
if(RS_RES != RS_OK)
{
}
return RS_RES;
}
/**
* @brief Handle for starting transmit.
* @param hRS - указатель на хендлер RS.
* @param RS_msg - указатель на структуру сообщения.
* @return RS_RES - статус о состоянии RS после инициализации передачи.
* @note Определяет отвечать ли на команду или нет.
*/
RS_StatusTypeDef RS_Handle_Transmit_Start(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg)
{
RS_StatusTypeDef RS_RES = 0;
switch(hRS->sRS_Mode)
{
case SLAVE_ALWAYS_WAIT: // in slave mode always response
case SLAVE_TIMEOUT_WAIT: // transmit response
RS_RES = RS_Transmit_IT(hRS, RS_msg); break;
}
if(RS_RES != RS_OK)
{
}
return RS_RES;
}
/**
* @brief UART RX Callback: define behaviour after receiving parts of message.
* @param hRS - указатель на хендлер RS.
* @return RS_RES - статус о состоянии RS после обработки приема.
* @note Контролирует прием сообщения: определяет размер принимаемой посылки и обрабатывает его.
*/
RS_StatusTypeDef RS_UART_RxCpltCallback(RS_HandleTypeDef *hRS)
{
RS_StatusTypeDef RS_RES = 0;
HAL_StatusTypeDef uart_res = 0;
// if we had received bytes before ByteCnt
if((hRS->sRS_RX_Size_Mode == RS_RX_Size_NotConst) && (hRS->f.RX_Half == 0)) // if data size isnt constant and its first half, and
{ // First receive part of message, then define size of rest of message, and start receive it
hRS->f.RX_Half = 1;
//---------------FIND DATA SIZE-----------------
uint32_t NuRS_of_Rest_Bytes = 0xFFFF;
RS_RES = RS_Define_Size_of_RX_Message(hRS, &NuRS_of_Rest_Bytes);
// if we need to skip this message - restart receive
if(RS_RES == RS_SKIP || NuRS_of_Rest_Bytes == 0xFFFF)
{
RS_Abort(hRS, ABORT_RX);
RS_RES = RS_Handle_Receive_Start(hRS, hRS->pMessagePtr);
return RS_RES;
}
// if there is no bytes to receive
if(NuRS_of_Rest_Bytes == 0)
{
hRS->f.RX_Half = 0;
//---------PROCESS DATA & ENDING RECEIVING--------
RS_Set_RX_End(hRS);
if(hRS->sRS_Timeout) // if timeout setted
HAL_TIM_Base_Stop_IT(hRS->htim); // stop timeout
// parse received data
RS_RES = RS_Parse_Message(hRS, hRS->pMessagePtr, hRS->pBufferPtr); // parse message
// RESPONSE
RS_RES = RS_Response(hRS, hRS->pMessagePtr);
return RS_RES;
}
//-------------START UART RECEIVE---------------
uart_res = HAL_UART_Receive_IT(hRS->huart, (hRS->pBufferPtr + RX_FIRST_PART_SIZE), NuRS_of_Rest_Bytes);
if(uart_res != HAL_OK)
{// need uart status, so doesnt write abort to RS_RES
RS_RES = RS_Abort(hRS, ABORT_RS);
}
else
RS_RES = RS_OK;
}
else // if we had received whole message
{
hRS->f.RX_Half = 0;
//---------PROCESS DATA & ENDING RECEIVING--------
RS_Set_RX_End(hRS);
if(hRS->sRS_Timeout) // if timeout setted
HAL_TIM_Base_Stop_IT(hRS->htim); // stop timeout
// parse received data
RS_RES = RS_Parse_Message(hRS, hRS->pMessagePtr, hRS->pBufferPtr); // parse message
// RESPONSE
RS_RES = RS_Response(hRS, hRS->pMessagePtr);
}
return RS_RES;
}
/**
* @brief UART TX Callback: define behaviour after transmiting message.
* @param hRS - указатель на хендлер RS.
* @return RS_RES - статус о состоянии RS после обработки приема.
* @note Определяет поведение RS после передачи сообщения.
*/
RS_StatusTypeDef RS_UART_TxCpltCallback(RS_HandleTypeDef *hRS)
{
RS_StatusTypeDef RS_RES = RS_OK;
HAL_StatusTypeDef uart_res = 0;
//--------------ENDING TRANSMITTING-------------
RS_Set_TX_End(hRS);
RS_EnableReceive();
// for(int i = 0; i < hRS->sRS_Timeout; i++);
//-----------START RECEIVING or END RS----------
RS_RES = RS_Handle_Receive_Start(hRS, hRS->pMessagePtr);
return RS_RES;
}
/**
* @brief Handler for UART.
* @param hRS - указатель на хендлер RS.
* @note Обрабатывает ошибки если есть и вызывает RS Коллбеки.
* Добавить вызов этой функции в UARTx_IRQHandler() после HAL_UART_IRQHandler().
*/
void RS_UART_Handler(RS_HandleTypeDef *hRS)
{
//-------------CALL RS CALLBACKS------------
/* IF NO ERROR OCCURS */
if(hRS->huart->ErrorCode == 0)
{
hRS->htim->Instance->CNT = 0; // reset cnt;
/* Start timeout */
if(hRS->sRS_Timeout) // if timeout setted
if((hRS->huart->RxXferCount+1 == hRS->huart->RxXferSize) && RS_Is_RX_Busy(hRS)) // if first byte is received and receive is active
{
hRS->htim->Instance->ARR = hRS->sRS_Timeout; // reset cnt;
HAL_TIM_Base_Start_IT(hRS->htim);
RS_Set_RX_Active_Flags(hRS);
}
/* RX Callback */
if (( hRS->huart->RxXferCount == 0U) && RS_Is_RX_Busy(hRS) && // if all bytes are received and receive is active
hRS->huart->RxState != HAL_UART_STATE_BUSY_RX) // also check that receive "REALLY" isnt busy
RS_UART_RxCpltCallback(hRS);
/* TX Callback */
if (( hRS->huart->TxXferCount == 0U) && RS_Is_TX_Busy(hRS) && // if all bytes are transmited and transmit is active
hRS->huart->gState != HAL_UART_STATE_BUSY_TX) // also check that receive "REALLY" isnt busy
RS_UART_TxCpltCallback(hRS);
}
//----------------ERRORS HANDLER----------------
else
{
if(hRS->f.RX_Busy)
{
/* de-init uart transfer */
RS_Abort(hRS, ABORT_RS);
RS_Handle_Receive_Start(hRS, hRS->pMessagePtr);
// later, maybe, will be added specific handlers for err
}
}
}
/**
* @brief Handler for TIM.
* @param hRS - указатель на хендлер RS.
* @note Попадание сюда = таймаут и перезапуск RS приема
* Добавить вызов этой функции в TIMx_IRQHandler() после HAL_TIM_IRQHandler().
*/
void RS_TIM_Handler(RS_HandleTypeDef *hRS)
{
HAL_TIM_Base_Stop_IT(hRS->htim);
RS_Abort(hRS, ABORT_RS);
RS_Handle_Receive_Start(hRS, hRS->pMessagePtr);
}
//--------------------CALLBACK/HANDLER FUNCTIONS---------------------
//-------------------------------------------------------------------
//-------------------------------------------------------------------
//--------------WEAK PROTOTYPES FOR PROCESSING MESSAGE---------------
/**
* @brief Respond accord to received message.
* @param hRS - указатель на хендлер RS.
* @param RS_msg - указатель на структуру сообщения.
* @return RS_RES - статус о результате ответа на комманду.
* @note Обработка принятой комманды и ответ на неё.
*/
__weak RS_StatusTypeDef RS_Response(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg)
{
/* Redefine function for user purposes */
return RS_ERR;
}
/**
* @brief Collect message in buffer to transmit it.
* @param hRS - указатель на хендлер RS.
* @param RS_msg - указатель на структуру сообщения.
* @param msg_uart_buff - указатель на буффер UART.
* @return RS_RES - статус о результате заполнения буфера.
* @note Заполнение буффера UART из структуры сообщения.
*/
__weak RS_StatusTypeDef RS_Collect_Message(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg, uint8_t *msg_uart_buff)
{
/* Redefine function for user purposes */
return RS_ERR;
}
/**
* @brief Parse message from buffer to process it.
* @param hRS - указатель на хендлер RS.
* @param RS_msg - указатель на структуру сообщения.
* @param msg_uart_buff - указатель на буффер UART.
* @return RS_RES - статус о результате заполнения структуры.
* @note Заполнение структуры сообщения из буффера UART.
*/
__weak RS_StatusTypeDef RS_Parse_Message(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg, uint8_t *msg_uart_buff)
{
/* Redefine function for user purposes */
return RS_ERR;
}
/**
* @brief Define size of RX Message that need to be received.
* @param hRS - указатель на хендлер RS.
* @param rx_data_size - указатель на переменную для записи кол-ва байт для принятия.
* @return RS_RES - статус о корректности рассчета кол-ва байт для принятия.
* @note Определение сколько байтов надо принять по протоколу.
*/
__weak RS_StatusTypeDef RS_Define_Size_of_RX_Message(RS_HandleTypeDef *hRS, uint32_t *rx_data_size)
{
/* Redefine function for user purposes */
return RS_ERR;
}
//--------------WEAK PROTOTYPES FOR PROCESSING MESSAGE---------------
//-------------------------------------------------------------------

View File

@@ -0,0 +1,257 @@
/**
**************************************************************************
* @file rs_message.h
* @brief Заголовочный файл для модуля реализации протоколов по RS/UART.
**************************************************************************
* @defgroup RS_TOOLS
* @brief Всякое для работы по UART/RS
**************************************************************************
@details
**************************************************************************
Для настройки RS/UART под нужный протокол, необходимо:
- Определить структуру сообщения RS_MsgTypeDef и
дефайны RX_FIRST_PART_SIZE и MSG_SIZE_MAX.
- Подключить этот файл в раздел rs_message.h.
- Определить функции для обработки сообщения: RS_Parse_Message(),
RS_Collect_Message(), RS_Response(), RS_Define_Size_of_RX_Message()
- Добавить UART/TIM Handler в Хендлер используемых UART/TIM.
Так же данный модуль использует счетчики
**************************************************************************
@verbatim
Визуальное описание. Форматирование сохраняется как в коде.
@endverbatim
*************************************************************************/
#ifndef __RS_LIB_H_
#define __RS_LIB_H_
#include "modbus.h"
#include "crc_algs.h"
/////////////////////////////////////////////////////////////////////
////////////////////////////---DEFINES---////////////////////////////
/* Check that all defines required by RS are defined */
#ifndef MSG_SIZE_MAX
#error Define MSG_SIZE_MAX (Maximum size of message). This is necessary to create buffer for UART.
#endif
#ifndef RX_FIRST_PART_SIZE
#error Define RX_FIRST_PART_SIZE (Size of first part of message). This is necessary to receive the first part of the message, from which determine the size of the remaining part of the message.
#endif
/* Clear message-uart buffer */
#define RS_Clear_Buff(_buff_) for(int i=0; i<MSG_SIZE_MAX;i++) _buff_[i] = NULL
/* Set/Reset flags */
#define RS_Set_Free(_hRS_) _hRS_->f.RS_Busy = 0
#define RS_Set_Busy(_hRS_) _hRS_->f.RS_Busy = 1
#define RS_Set_RX_Flags(_hRS_) _hRS_->f.RX_Busy = 1; _hRS_->f.RX_Done = 0; _hRS_->f.RX_Half = 0
#define RS_Set_RX_Active_Flags(_hRS_) _hRS_->f.RX_Ongoing = 1
#define RS_Set_TX_Flags(_hRS_) _hRS_->f.TX_Busy = 1; _hRS_->f.TX_Done = 0
#define RS_Reset_RX_Active_Flags(_hRS_) _hRS_->f.RX_Ongoing = 0
#define RS_Reset_RX_Flags(_hRS_) RS_Reset_RX_Active_Flags(_hRS_); _hRS_->f.RX_Busy = 0; _hRS_->f.RX_Done = 0; _hRS_->f.RX_Half = 0
#define RS_Reset_TX_Flags(_hRS_) _hRS_->f.TX_Busy = 0; _hRS_->f.TX_Done = 0
#define RS_Set_RX_End_Flag(_hRS_) _hRS_->f.RX_Done = 1;
#define RS_Set_TX_End_Flag(_hRS_) _hRS_->f.TX_Done = 1
#define RS_Set_RX_End(_hRS_) RS_Reset_RX_Flags(_hRS_); RS_Set_RX_End_Flag(_hRS_)
#define RS_Set_TX_End(_hRS_) RS_Reset_TX_Flags(_hRS_); RS_Set_TX_End_Flag(_hRS_)
/* Clear all RS stuff */
#define RS_Clear_All(_hRS_) RS_Clear_Buff(_hRS_->pBufferPtr); RS_Reset_RX_Flags(_hRS_); RS_Reset_TX_Flags(_hRS_);
//#define MB_Is_RX_Busy(_hRS_) ((_hRS_->huart->gState&HAL_USART_STATE_BUSY_RX) == HAL_USART_STATE_BUSY_RX)
//#define MB_Is_TX_Busy(_hRS_) ((_hRS_->huart->gState&HAL_USART_STATE_BUSY_RX) == HAL_USART_STATE_BUSY_TX)
#define RS_Is_RX_Busy(_hRS_) (_hRS_->f.RX_Busy == 1)
#define RS_Is_TX_Busy(_hRS_) (_hRS_->f.TX_Busy == 1)
#ifndef RS_EnableReceive
#define RS_EnableReceive()
#endif
#ifndef RS_EnableTransmit
#define RS_EnableTransmit()
#endif
////////////////////////////---DEFINES---////////////////////////////
/////////////////////////////////////////////////////////////////////
///////////////////////---STRUCTURES & ENUMS---//////////////////////
//------------------ENUMERATIONS--------------------
/** @brief Enums for respond CMD about RS status */
typedef enum // RS_StatusTypeDef
{
/* IN-CODE STATUS (start from 0x01, and goes up)*/
/*0x01*/ RS_OK = 0x01,
/*0x02*/ RS_ERR,
/*0x03*/ RS_ABORTED,
/*0x04*/ RS_BUSY,
/*0x05*/ RS_SKIP,
/*0x06*/ RS_COLLECT_MSG_ERR,
/*0x07*/ RS_PARSE_MSG_ERR,
// reserved values
// /*0x00*/ RS_UNKNOWN_ERR = 0x00, ///< reserved for case, if no one error founded (nothing changed response from zero)
}RS_StatusTypeDef;
/** @brief Enums for RS Modes */
typedef enum // RS_ModeTypeDef
{
SLAVE_ALWAYS_WAIT = 0x01, ///< Slave mode with infinity waiting
SLAVE_TIMEOUT_WAIT = 0x02, ///< Slave mode with waiting with timeout
// MASTER = 0x03, ///< Master mode
}RS_ModeTypeDef;
/** @brief Enums for RS UART Modes */
typedef enum // RS_ITModeTypeDef
{
BLCK_MODE = 0x00, ///< Blocking mode
IT_MODE = 0x01, ///< Interrupt mode
}RS_ITModeTypeDef;
/** @brief Enums for Abort modes */
typedef enum // RS_AbortTypeDef
{
ABORT_TX = 0x01, ///< Abort transmit
ABORT_RX = 0x02, ///< Abort receive
ABORT_RX_TX = 0x03, ///< Abort receive and transmit
ABORT_RS = 0x04, ///< Abort uart and reset RS structure
}RS_AbortTypeDef;
/** @brief Enums for RX Size modes */
typedef enum // RS_RXSizeTypeDef
{
RS_RX_Size_Const = 0x01, ///< size of receiving message is constant
RS_RX_Size_NotConst = 0x02, ///< size of receiving message isnt constant
}RS_RXSizeTypeDef;
//-----------STRUCTURE FOR HANDLE RS------------
/** @brief Struct for flags RS */
typedef struct
{
unsigned RX_Half:1; ///< flag: 0 - receiving msg before ByteCnt, 0 - receiving msg after ByteCnt
unsigned RS_Busy:1; ///< flag: 1 - RS is busy, 0 - RS isnt busy
unsigned RX_Ongoing:1; ///< flag: 1 - receiving data right now, 0 - waiting for receiving data
unsigned RX_Busy:1; ///< flag: 1 - receiving is active, 0 - receiving isnt active
unsigned TX_Busy:1; ///< flag: 1 - transmiting is active, 0 - transmiting isnt active
unsigned RX_Done:1; ///< flag: 1 - receiving is done, 0 - receiving isnt done
unsigned TX_Done:1; ///< flag: 1 - transmiting is done, 0 - transmiting isnt done
// setted by user
unsigned MessageHandled:1; ///< flag: 1 - RS command is handled, 0 - RS command isnt handled yet
unsigned EchoResponse:1; ///< flag: 1 - response with received msg, 0 - response with own msg
unsigned DeferredResponse:1; ///< flag: 1 - response not in interrupt, 0 - response in interrupt
unsigned ReInit_UART:1; ///< flag: 1 - need to reinitialize uart, 0 - nothing
}RS_FlagsTypeDef;
/**
* @brief Handle for RS communication.
* @note Prefixes: h - handle, s - settings, f - flag
*/
typedef struct // RS_HandleTypeDef
{
/* MESSAGE */
uint8_t ID; ///< ID of RS "channel"
RS_MsgTypeDef *pMessagePtr; ///< pointer to message struct
uint8_t *pBufferPtr; ///< pointer to message buffer
uint32_t RS_Message_Size; ///< size of whole message, not only data
/* HANDLERS and SETTINGS */
UART_HandleTypeDef *huart; ///< handler for used uart
TIM_HandleTypeDef *htim; ///< handler for used tim
RS_ModeTypeDef sRS_Mode; ///< setting: slave or master @ref RS_ModeTypeDef
RS_ITModeTypeDef sRS_IT_Mode; ///< setting: 1 - IT mode, 0 - Blocking mode
uint16_t sRS_Timeout; ///< setting: timeout in ms
RS_RXSizeTypeDef sRS_RX_Size_Mode; ///< setting: 1 - not const, 0 - const
/* FLAGS */
RS_FlagsTypeDef f; ///< These flags for controling receive/transmit
/* RS STATUS */
RS_StatusTypeDef RS_STATUS; ///< RS status
}RS_HandleTypeDef;
extern RS_HandleTypeDef hmodbus1;
///////////////////////---STRUCTURES & ENUMS---//////////////////////
/////////////////////////////////////////////////////////////////////
///////////////////////////---FUNCTIONS---///////////////////////////
//----------------FUNCTIONS FOR PROCESSING MESSAGE-------------------
/*--------------------Defined by users purposes--------------------*/
/* Respond accord to received message */
RS_StatusTypeDef RS_Response(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg);
/* Collect message in buffer to transmit it */
RS_StatusTypeDef RS_Collect_Message(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg, uint8_t *msg_uart_buff);
/* Parse message from buffer to process it */
RS_StatusTypeDef RS_Parse_Message(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg, uint8_t *msg_uart_buff);
/* Define size of RX Message that need to be received */
RS_StatusTypeDef RS_Define_Size_of_RX_Message(RS_HandleTypeDef *hRS, uint32_t *rx_data_size);
//-------------------------GENERAL FUNCTIONS-------------------------
/*-----------------Should be called from main code-----------------*/
/* Start receive IT */
RS_StatusTypeDef RS_Receive_IT(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg);
/* Start transmit IT */
RS_StatusTypeDef RS_Transmit_IT(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg);
/* Initialize UART and handle RS stucture */
RS_StatusTypeDef RS_Init(RS_HandleTypeDef *hRS, UART_HandleTypeDef *huart, TIM_HandleTypeDef *htim, uint8_t *pRS_BufferPtr);
/* ReInitialize UART and RS receive */
HAL_StatusTypeDef RS_ReInit_UART(RS_HandleTypeDef *hRS, UART_HandleTypeDef *suart);
/* Abort RS/UART */
RS_StatusTypeDef RS_Abort(RS_HandleTypeDef *hRS, RS_AbortTypeDef AbortMode);
//-------------------------GENERAL FUNCTIONS-------------------------
//-------------------------------------------------------------------
//--------------------CALLBACK/HANDLER FUNCTIONS---------------------
/* Handle for starting receive */
RS_StatusTypeDef RS_Handle_Receive_Start(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg);
/* Handle for starting transmit */
RS_StatusTypeDef RS_Handle_Transmit_Start(RS_HandleTypeDef *hRS, RS_MsgTypeDef *RS_msg);
/* UART RX Callback: define behaviour after receiving parts of message */
RS_StatusTypeDef RS_UART_RxCpltCallback(RS_HandleTypeDef *hRS);
/* UART TX Callback: define behaviour after transmiting message */
RS_StatusTypeDef RS_UART_TxCpltCallback(RS_HandleTypeDef *hRS);
/* Handler for UART */
void RS_UART_Handler(RS_HandleTypeDef *hRS);
/* Handler for TIM */
void RS_TIM_Handler(RS_HandleTypeDef *hRS);
//--------------------CALLBACK/HANDLER FUNCTIONS---------------------
///////////////////////////---FUNCTIONS---///////////////////////////
#ifndef printf_rs_err
#define printf_rs_err(...)
#endif
#ifndef printf_rs
#define printf_rs(...)
#endif
#endif // __RS_LIB_H_

View File

@@ -33,53 +33,55 @@ Mcu.IPNb=11
Mcu.Name=STM32F103C(4-6)Tx
Mcu.Package=LQFP48
Mcu.Pin0=PC13-TAMPER-RTC
Mcu.Pin1=PD0-OSC_IN
Mcu.Pin10=PA7
Mcu.Pin11=PB0
Mcu.Pin12=PB1
Mcu.Pin13=PB2
Mcu.Pin14=PB10
Mcu.Pin15=PB11
Mcu.Pin16=PB12
Mcu.Pin17=PB13
Mcu.Pin18=PB14
Mcu.Pin19=PB15
Mcu.Pin2=PD1-OSC_OUT
Mcu.Pin20=PA8
Mcu.Pin21=PA9
Mcu.Pin22=PA10
Mcu.Pin23=PA11
Mcu.Pin24=PA12
Mcu.Pin25=PA13
Mcu.Pin26=PA14
Mcu.Pin27=PA15
Mcu.Pin28=PB3
Mcu.Pin29=PB4
Mcu.Pin3=PA0-WKUP
Mcu.Pin30=PB5
Mcu.Pin31=PB6
Mcu.Pin32=PB7
Mcu.Pin33=PB8
Mcu.Pin34=PB9
Mcu.Pin35=VP_ADC1_TempSens_Input
Mcu.Pin36=VP_ADC1_Vref_Input
Mcu.Pin37=VP_RTC_VS_RTC_Activate
Mcu.Pin38=VP_RTC_VS_RTC_Calendar
Mcu.Pin39=VP_SYS_VS_tim3
Mcu.Pin4=PA1
Mcu.Pin40=VP_TIM1_VS_ClockSourceINT
Mcu.Pin41=VP_TIM2_VS_ClockSourceINT
Mcu.Pin5=PA2
Mcu.Pin6=PA3
Mcu.Pin7=PA4
Mcu.Pin8=PA5
Mcu.Pin9=PA6
Mcu.PinsNb=42
Mcu.Pin1=PC14-OSC32_IN
Mcu.Pin10=PA5
Mcu.Pin11=PA6
Mcu.Pin12=PA7
Mcu.Pin13=PB0
Mcu.Pin14=PB1
Mcu.Pin15=PB2
Mcu.Pin16=PB10
Mcu.Pin17=PB11
Mcu.Pin18=PB12
Mcu.Pin19=PB13
Mcu.Pin2=PC15-OSC32_OUT
Mcu.Pin20=PB14
Mcu.Pin21=PB15
Mcu.Pin22=PA8
Mcu.Pin23=PA9
Mcu.Pin24=PA10
Mcu.Pin25=PA11
Mcu.Pin26=PA12
Mcu.Pin27=PA13
Mcu.Pin28=PA14
Mcu.Pin29=PA15
Mcu.Pin3=PD0-OSC_IN
Mcu.Pin30=PB3
Mcu.Pin31=PB4
Mcu.Pin32=PB5
Mcu.Pin33=PB6
Mcu.Pin34=PB7
Mcu.Pin35=PB8
Mcu.Pin36=PB9
Mcu.Pin37=VP_ADC1_TempSens_Input
Mcu.Pin38=VP_ADC1_Vref_Input
Mcu.Pin39=VP_RTC_VS_RTC_Activate
Mcu.Pin4=PD1-OSC_OUT
Mcu.Pin40=VP_RTC_VS_RTC_Calendar
Mcu.Pin41=VP_SYS_VS_tim3
Mcu.Pin42=VP_TIM1_VS_ClockSourceINT
Mcu.Pin43=VP_TIM2_VS_ClockSourceINT
Mcu.Pin5=PA0-WKUP
Mcu.Pin6=PA1
Mcu.Pin7=PA2
Mcu.Pin8=PA3
Mcu.Pin9=PA4
Mcu.PinsNb=44
Mcu.ThirdPartyNb=0
Mcu.UserConstants=
Mcu.UserName=STM32F103C6Tx
MxCube.Version=6.15.0
MxDb.Version=DB.6.0.150
MxCube.Version=6.12.0
MxDb.Version=DB.6.0.120
NVIC.BusFault_IRQn=true\:0\:0\:false\:false\:true\:false\:false\:false
NVIC.DebugMonitor_IRQn=true\:0\:0\:false\:false\:true\:false\:false\:false
NVIC.ForceEnableDMAVector=true
@@ -169,8 +171,12 @@ PB8.Mode=I2C
PB8.Signal=I2C1_SCL
PB9.Mode=I2C
PB9.Signal=I2C1_SDA
PC13-TAMPER-RTC.Locked=true
PC13-TAMPER-RTC.Signal=GPIO_Output
PC13-TAMPER-RTC.Mode=RTC OUT
PC13-TAMPER-RTC.Signal=RTC_OUT
PC14-OSC32_IN.Mode=LSE-External-Oscillator
PC14-OSC32_IN.Signal=RCC_OSC32_IN
PC15-OSC32_OUT.Mode=LSE-External-Oscillator
PC15-OSC32_OUT.Signal=RCC_OSC32_OUT
PD0-OSC_IN.Mode=HSE-External-Oscillator
PD0-OSC_IN.Signal=RCC_OSC_IN
PD1-OSC_OUT.Mode=HSE-External-Oscillator
@@ -178,7 +184,6 @@ PD1-OSC_OUT.Signal=RCC_OSC_OUT
PinOutPanel.RotationAngle=0
ProjectManager.AskForMigrate=true
ProjectManager.BackupPrevious=false
ProjectManager.CompilerLinker=GCC
ProjectManager.CompilerOptimize=6
ProjectManager.ComputerToolchain=false
ProjectManager.CoupleFile=true

View File

@@ -1,431 +0,0 @@
LabVIEW Measurement
Writer_Version 2
Reader_Version 2
Separator Tab
Decimal_Separator ,
Multi_Headings Yes
X_Columns One
Time_Pref Absolute
Operator z
Date 2025/11/13
Time 15:16:08,040531158447265625
***End_of_Header***
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:08,040531158447265625
X_Dimension Time
X0 0,0000000000000000E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
0,000000 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:08,151824951171875
X_Dimension Time
X0 1,1129379272460937E-1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
0,111294 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:09,1365952491760253906
X_Dimension Time
X0 1,0960640907287598E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
1,096064 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:10,1405615806579589844
X_Dimension Time
X0 2,1000304222106934E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
2,100030 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:11,1472897529602050781
X_Dimension Time
X0 3,1067585945129395E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
3,106759 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:12,765697479248046875
X_Dimension Time
X0 4,7251663208007812E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
4,725166 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:13,140415191650390625
X_Dimension Time
X0 5,0998840332031250E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
5,099884 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:14,1417174339294433594
X_Dimension Time
X0 6,1011862754821777E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
6,101186 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:15,1356105804443359375
X_Dimension Time
X0 7,0950794219970703E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
7,095079 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:16,1398367881774902344
X_Dimension Time
X0 8,0993056297302246E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
8,099306 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:17,1468534469604492187
X_Dimension Time
X0 9,1063222885131836E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
9,106322 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:18,1485104560852050781
X_Dimension Time
X0 1,0107979297637939E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
10,107979 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:19,1396398544311523437
X_Dimension Time
X0 1,1099108695983887E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
11,099109 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:20,14166259765625
X_Dimension Time
X0 1,2101131439208984E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
12,101131 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:21,1363024711608886719
X_Dimension Time
X0 1,3095771312713623E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
13,095771 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:22,1432185173034667969
X_Dimension Time
X0 1,4102687358856201E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
14,102687 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:23,1432042121887207031
X_Dimension Time
X0 1,5102673053741455E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
15,102673 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:24,1468262672424316406
X_Dimension Time
X0 1,6106295108795166E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
16,106295 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:25,1429185867309570312
X_Dimension Time
X0 1,7102387428283691E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
17,102387 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:26,1594376564025878906
X_Dimension Time
X0 1,8118906497955322E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
18,118906 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:27,1411752700805664062
X_Dimension Time
X0 1,9100644111633301E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
19,100644 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:28,1400208473205566406
X_Dimension Time
X0 2,0099489688873291E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
20,099490 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:29,1346111297607421875
X_Dimension Time
X0 2,1094079971313477E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
21,094080 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:30,1374959945678710937
X_Dimension Time
X0 2,2096964836120605E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
22,096965 28,500000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:31,1462650299072265625
X_Dimension Time
X0 2,3105733871459961E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
23,105734 29,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:32,1459894180297851562
X_Dimension Time
X0 2,4105458259582520E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
24,105458 29,500000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:33,1347680091857910156
X_Dimension Time
X0 2,5094236850738525E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
25,094237 30,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:34,1428799629211425781
X_Dimension Time
X0 2,6102348804473877E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
26,102349 30,500000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:35,142475128173828125
X_Dimension Time
X0 2,7101943969726562E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
27,101944 31,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:36,1425271034240722656
X_Dimension Time
X0 2,8101995944976807E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
28,101996 30,500000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:37,1589808464050292969
X_Dimension Time
X0 2,9118449687957764E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
29,118450 30,500000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:38,1375432014465332031
X_Dimension Time
X0 3,0097012042999268E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
30,097012 30,500000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:39,5883951187133789063
X_Dimension Time
X0 3,1547863960266113E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
31,547864 30,500000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:40,1435170173645019531
X_Dimension Time
X0 3,2102985858917236E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
32,102986 30,500000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:41,1350607872009277344
X_Dimension Time
X0 3,3094529628753662E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
33,094530 30,500000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:42,1323223114013671875
X_Dimension Time
X0 3,4091791152954102E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
34,091791 30,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:43,1501688957214355469
X_Dimension Time
X0 3,5109637737274170E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
35,109638 30,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:16:44,1386942863464355469
X_Dimension Time
X0 3,6098163127899170E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
36,098163 30,000000 temp1

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@@ -1,233 +0,0 @@
LabVIEW Measurement
Writer_Version 2
Reader_Version 2
Separator Tab
Decimal_Separator ,
Multi_Headings Yes
X_Columns One
Time_Pref Absolute
Operator z
Date 2025/11/13
Time 15:18:42,2196631431579589844
***End_of_Header***
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:42,2196631431579589844
X_Dimension Time
X0 0,0000000000000000E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
0,000000 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:43,1454310417175292969
X_Dimension Time
X0 9,2576789855957031E-1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
0,925768 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:44,1414446830749511719
X_Dimension Time
X0 1,9217815399169922E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
1,921782 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:45,1437168121337890625
X_Dimension Time
X0 2,9240536689758301E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
2,924054 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:46,1456303596496582031
X_Dimension Time
X0 3,9259672164916992E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
3,925967 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:47,1414666175842285156
X_Dimension Time
X0 4,9218034744262695E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
4,921803 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:48,14643096923828125
X_Dimension Time
X0 5,9267678260803223E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
5,926768 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:49,1424298286437988281
X_Dimension Time
X0 6,9227666854858398E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
6,922767 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:50,1434178352355957031
X_Dimension Time
X0 7,9237546920776367E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
7,923755 28,500000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:51,1381001472473144531
X_Dimension Time
X0 8,9184370040893555E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
8,918437 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:52,1338038444519042969
X_Dimension Time
X0 9,9141407012939453E+0
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
9,914141 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:53,1467270851135253906
X_Dimension Time
X0 1,0927063941955566E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
10,927064 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:54,1358785629272460937
X_Dimension Time
X0 1,1916215419769287E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
11,916215 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:55,14373016357421875
X_Dimension Time
X0 1,2924067020416260E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
12,924067 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:56,1407599449157714844
X_Dimension Time
X0 1,3921096801757812E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
13,921097 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:58,7443718910217285156
X_Dimension Time
X0 1,6524708747863770E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
16,524709 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:58,8754205703735351562
X_Dimension Time
X0 1,6655757427215576E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
16,655757 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:18:59,1390137672424316406
X_Dimension Time
X0 1,6919350624084473E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
16,919351 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:19:00,13970947265625
X_Dimension Time
X0 1,7920046329498291E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
17,920046 28,000000 temp1
Channels 1
Samples 1
Date 2025/11/13
Time 15:19:01,1449561119079589844
X_Dimension Time
X0 1,8925292968750000E+1
Delta_X 1,000000
***End_of_Header***
X_Value Untitled Comment
18,925293 28,000000 temp1

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Submodule labview_john/labview_proj added at fcba827e91