Форум программистов, компьютерный форум, киберфорум
Микроконтроллеры ARM, Cortex, STM32
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск  
 
 
Рейтинг 4.63/8: Рейтинг темы: голосов - 8, средняя оценка - 4.63
 Аватар для AdamBeno
21 / 14 / 7
Регистрация: 15.07.2018
Сообщений: 50

STM32F103 Проблема с UART

27.07.2023, 03:09. Показов 2608. Ответов 39
Метки uart (Все метки)

Студворк — интернет-сервис помощи студентам
Доброго времени суток! Кроме вопроса "почему" не знаю что сказать, пересылаю значения из ацп в юарт и возникает проблема что происходит перевод строки посередине передачи. Не знаю почему так происходит, может кто поможет советом. Спасибо!
Миниатюры
STM32F103 Проблема с UART  
Вложения
Тип файла: zip stm32f103c8t6.zip (5.83 Мб, 23 просмотров)
0
Programming
Эксперт
39485 / 9562 / 3019
Регистрация: 12.04.2006
Сообщений: 41,671
Блог
27.07.2023, 03:09
Ответы с готовыми решениями:

STM32F103, проблема с UART на скорости 9600
Столкнулся с такой проблемой, плата с установленным STM32F103VBT по RS485 передает данные на скорости 115200 , все прекрасно работает ....

UART и STM32F103
Здравствуйте, уважаемые! Начал тут заниматься STM32, перейдя на него с AtMega. Возник вопрос - как принять данные с UART в любой момент...

Прием по UART STM32F103
Здравствуйте. Тема заезженная, знаю- прием по ЮАРТу. Прежде чем сюда писать по изучал 3-4 статьи и темы на этом форуме, делал все по...

39
 Аватар для AdamBeno
21 / 14 / 7
Регистрация: 15.07.2018
Сообщений: 50
27.07.2023, 15:10  [ТС]
Студворк — интернет-сервис помощи студентам
VladimirU, менял, не помогло. Я не через терминал буду пользоваться а софтом написанным под мои задачи. Если отправку делать интервалом 30 мс и больше, все работает, если снизить интервал до 20 мс то появляется данная проблема. Щас буду пробовать с кольцевым буфером.
0
 Аватар для AdamBeno
21 / 14 / 7
Регистрация: 15.07.2018
Сообщений: 50
27.07.2023, 15:27  [ТС]
VladimirU, я и написал под свои хотелки. Дополнительная инфа, ошибка происходит в момент изменений значений из 4-х значного в 3-х, 3-х в 2-х итд. Может это из за преобразований в строку в момент отправки. Буду дальше смотреть.
Миниатюры
STM32F103 Проблема с UART  
0
 Аватар для AdamBeno
21 / 14 / 7
Регистрация: 15.07.2018
Сообщений: 50
27.07.2023, 15:46  [ТС]
Если не затруднить взгляните на код, правильно ли организован буфер, если да то проблема все еще присутствует.
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
/* USER CODE BEGIN Header */
/**
  ******************************************************************************
  * @file           : main.c
  * @brief          : Main program body
  ******************************************************************************
  * @attention
  *
  * Copyright (c) 2023 STMicroelectronics.
  * All rights reserved.
  *
  * This software is licensed under terms that can be found in the LICENSE file
  * in the root directory of this software component.
  * If no LICENSE file comes with this software, it is provided AS-IS.
  *
  ******************************************************************************
  */
/* USER CODE END Header */
/* Includes ------------------------------------------------------------------*/
#include "main.h"
 
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include "string.h"
#include "stdio.h"
/* USER CODE END Includes */
 
/* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD */
 
/* USER CODE END PTD */
 
/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */
#define UART_BUFFER_SIZE 256
#define UART_BUFFER_MASK (UART_BUFFER_SIZE - 1)
/* USER CODE END PD */
 
/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */
 
/* USER CODE END PM */
 
/* Private variables ---------------------------------------------------------*/
ADC_HandleTypeDef hadc1;
 
TIM_HandleTypeDef htim1;
 
UART_HandleTypeDef huart1;
 
/* USER CODE BEGIN PV */
uint8_t uartBuffer[UART_BUFFER_SIZE];
volatile uint16_t uartBufferHead = 0;
volatile uint16_t uartBufferTail = 0;
uint16_t adc = 0;
uint8_t flag = 0;
char trans_str[6];
/* USER CODE END PV */
 
/* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
static void MX_GPIO_Init(void);
static void MX_ADC1_Init(void);
static void MX_USART1_UART_Init(void);
static void MX_TIM1_Init(void);
/* USER CODE BEGIN PFP */
 
/* USER CODE END PFP */
 
/* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */
// Функция для добавления данных в кольцевой буфер UART
void addToBuffer(uint8_t data) {
    // Вычисляем следующий индекс головы буфера с учетом маски.
    // Маска обеспечивает "зацикливание" индекса на размере буфера.
    uint16_t nextHead = (uartBufferHead + 1) & UART_BUFFER_MASK;
 
    // Проверяем, не переполнен ли буфер, прежде чем добавить данные.
    if (nextHead != uartBufferTail) {
        // Добавляем данные в буфер на текущую позицию головы.
        uartBuffer[uartBufferHead] = data;
        // Обновляем индекс головы на следующий.
        uartBufferHead = nextHead;
    }
    // Если буфер переполнен, новые данные не добавляются.
}
 
// Функция для извлечения данных из кольцевого буфера UART
uint8_t getFromBuffer() {
    // Проверяем, есть ли данные для чтения в буфере.
    if (uartBufferHead != uartBufferTail) {
        // Если есть данные, извлекаем значение из текущей позиции хвоста.
        uint8_t data = uartBuffer[uartBufferTail];
        // Обновляем индекс хвоста на следующий, с учетом маски.
        uartBufferTail = (uartBufferTail + 1) & UART_BUFFER_MASK;
        // Возвращаем извлеченные данные.
        return data;
    }
    // Если буфер пуст, возвращаем 0.
    return 0;
}
 
 
void HAL_UART_TxCpltCallback(UART_HandleTypeDef *huart) {
    // Обработчик прерывания отправки данных по UART
 
 
}
 
 
 
void transmit(uint16_t adcValue) {
    char adc_str[6]; // Дополнительный буфер для строки с ADC-значением
    snprintf(adc_str, sizeof(adc_str), "%hu", adcValue); // Преобразование ADC в строку
 
    // Отправка строки через UART
    for (uint8_t i = 0; i < strlen(adc_str); i++) {
        addToBuffer(adc_str[i]);
    }
    // Добавим символ окончания строки '\n' для обозначения конца передачи значения ADC
    addToBuffer('\n');
}
 
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
{
        if(htim->Instance == TIM1)
        {
                HAL_GPIO_TogglePin(GPIOC, led_Pin);
                flag = 1;
 
        }
}
 
 
/* 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_ADC1_Init();
  MX_USART1_UART_Init();
  MX_TIM1_Init();
  /* USER CODE BEGIN 2 */
  HAL_ADCEx_Calibration_Start(&hadc1);
  HAL_ADC_Start(&hadc1);
  HAL_TIM_Base_Start_IT(&htim1);
  /* USER CODE END 2 */
 
  /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  while (1)
  {
    /* USER CODE END WHILE */
 
    /* USER CODE BEGIN 3 */
 
      // Запустить одиночное измерение АЦП на канале 1 (PA1)
      //HAL_ADC_Start(&hadc1);
      // Ждать окончания преобразования АЦП
      HAL_ADC_PollForConversion(&hadc1, HAL_MAX_DELAY);
      // Считать значение АЦП
      adc = HAL_ADC_GetValue(&hadc1);
      // Остановить АЦП для экономии энергии
     // HAL_ADC_Stop(&hadc1);
 
      adc = adc / 4;
 
      //HAL_GPIO_TogglePin(GPIOC, led_Pin);
 
      // Отправить значение АЦП по UART
      if (flag != 0) {
 
      transmit(adc);
 
      flag = 0;
 
      }
 
      if (huart1.gState == HAL_UART_STATE_READY) {
                  uint8_t data = getFromBuffer();
                  if (data != 0) {
                      HAL_UART_Transmit_IT(&huart1, &data, 1);
                  }
              }
 
      //HAL_Delay(10);
  }
  /* 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_HSI;
  RCC_OscInitStruct.HSIState = RCC_HSI_ON;
  RCC_OscInitStruct.HSICalibrationValue = RCC_HSICALIBRATION_DEFAULT;
  RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
  RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSI_DIV2;
  RCC_OscInitStruct.PLL.PLLMUL = RCC_PLL_MUL16;
  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_ADC;
  PeriphClkInit.AdcClockSelection = RCC_ADCPCLK2_DIV6;
  if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK)
  {
    Error_Handler();
  }
}
 
/**
  * @brief ADC1 Initialization Function
  * @param None
  * @retval None
  */
static void MX_ADC1_Init(void)
{
 
  /* USER CODE BEGIN ADC1_Init 0 */
 
  /* USER CODE END ADC1_Init 0 */
 
  ADC_ChannelConfTypeDef sConfig = {0};
 
  /* USER CODE BEGIN ADC1_Init 1 */
 
  /* USER CODE END ADC1_Init 1 */
 
  /** Common config
  */
  hadc1.Instance = ADC1;
  hadc1.Init.ScanConvMode = ADC_SCAN_DISABLE;
  hadc1.Init.ContinuousConvMode = ENABLE;
  hadc1.Init.DiscontinuousConvMode = DISABLE;
  hadc1.Init.ExternalTrigConv = ADC_SOFTWARE_START;
  hadc1.Init.DataAlign = ADC_DATAALIGN_RIGHT;
  hadc1.Init.NbrOfConversion = 1;
  if (HAL_ADC_Init(&hadc1) != HAL_OK)
  {
    Error_Handler();
  }
 
  /** Configure Regular Channel
  */
  sConfig.Channel = ADC_CHANNEL_1;
  sConfig.Rank = ADC_REGULAR_RANK_1;
  sConfig.SamplingTime = ADC_SAMPLETIME_28CYCLES_5;
  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
  {
    Error_Handler();
  }
  /* USER CODE BEGIN ADC1_Init 2 */
 
  /* USER CODE END ADC1_Init 2 */
 
}
 
/**
  * @brief TIM1 Initialization Function
  * @param None
  * @retval None
  */
static void MX_TIM1_Init(void)
{
 
  /* USER CODE BEGIN TIM1_Init 0 */
 
  /* USER CODE END TIM1_Init 0 */
 
  TIM_ClockConfigTypeDef sClockSourceConfig = {0};
  TIM_MasterConfigTypeDef sMasterConfig = {0};
 
  /* USER CODE BEGIN TIM1_Init 1 */
 
  /* USER CODE END TIM1_Init 1 */
  htim1.Instance = TIM1;
  htim1.Init.Prescaler = 63999;
  htim1.Init.CounterMode = TIM_COUNTERMODE_UP;
  htim1.Init.Period = 19;
  htim1.Init.ClockDivision = TIM_CLOCKDIVISION_DIV1;
  htim1.Init.RepetitionCounter = 0;
  htim1.Init.AutoReloadPreload = TIM_AUTORELOAD_PRELOAD_DISABLE;
  if (HAL_TIM_Base_Init(&htim1) != HAL_OK)
  {
    Error_Handler();
  }
  sClockSourceConfig.ClockSource = TIM_CLOCKSOURCE_INTERNAL;
  if (HAL_TIM_ConfigClockSource(&htim1, &sClockSourceConfig) != HAL_OK)
  {
    Error_Handler();
  }
  sMasterConfig.MasterOutputTrigger = TIM_TRGO_RESET;
  sMasterConfig.MasterSlaveMode = TIM_MASTERSLAVEMODE_DISABLE;
  if (HAL_TIMEx_MasterConfigSynchronization(&htim1, &sMasterConfig) != HAL_OK)
  {
    Error_Handler();
  }
  /* USER CODE BEGIN TIM1_Init 2 */
 
  /* USER CODE END TIM1_Init 2 */
 
}
 
/**
  * @brief USART1 Initialization Function
  * @param None
  * @retval None
  */
static void MX_USART1_UART_Init(void)
{
 
  /* USER CODE BEGIN USART1_Init 0 */
 
  /* USER CODE END USART1_Init 0 */
 
  /* USER CODE BEGIN USART1_Init 1 */
 
  /* USER CODE END USART1_Init 1 */
  huart1.Instance = USART1;
  huart1.Init.BaudRate = 19200;
  huart1.Init.WordLength = UART_WORDLENGTH_8B;
  huart1.Init.StopBits = UART_STOPBITS_1;
  huart1.Init.Parity = UART_PARITY_NONE;
  huart1.Init.Mode = UART_MODE_TX;
  huart1.Init.HwFlowCtl = UART_HWCONTROL_NONE;
  huart1.Init.OverSampling = UART_OVERSAMPLING_16;
  if (HAL_UART_Init(&huart1) != HAL_OK)
  {
    Error_Handler();
  }
  /* USER CODE BEGIN USART1_Init 2 */
 
  /* USER CODE END USART1_Init 2 */
 
}
 
/**
  * @brief GPIO Initialization Function
  * @param None
  * @retval None
  */
static void MX_GPIO_Init(void)
{
  GPIO_InitTypeDef GPIO_InitStruct = {0};
/* USER CODE BEGIN MX_GPIO_Init_1 */
/* USER CODE END MX_GPIO_Init_1 */
 
  /* GPIO Ports Clock Enable */
  __HAL_RCC_GPIOC_CLK_ENABLE();
  __HAL_RCC_GPIOA_CLK_ENABLE();
 
  /*Configure GPIO pin Output Level */
  HAL_GPIO_WritePin(led_GPIO_Port, led_Pin, GPIO_PIN_RESET);
 
  /*Configure GPIO pin : led_Pin */
  GPIO_InitStruct.Pin = led_Pin;
  GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
  GPIO_InitStruct.Pull = GPIO_NOPULL;
  GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
  HAL_GPIO_Init(led_GPIO_Port, &GPIO_InitStruct);
 
/* USER CODE BEGIN MX_GPIO_Init_2 */
/* USER CODE END MX_GPIO_Init_2 */
}
 
/* USER CODE BEGIN 4 */
 
/* USER CODE END 4 */
 
/**
  * @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 */
0
Эксперт .NET
 Аватар для Rius
13391 / 7846 / 1699
Регистрация: 25.05.2015
Сообщений: 23,855
Записей в блоге: 14
27.07.2023, 17:58
AdamBeno,
HAL_UART_Transmit_IT(&huart1, &data, 1);
Почему 1? Посылать надо всю строку.

Добавлено через 1 минуту
Цитата Сообщение от AdamBeno Посмотреть сообщение
ошибка происходит в момент изменений значений из 4-х значного в 3-х, 3-х в 2-х итд.
Через snprintf печатаем новое значение в буфер строки. Что было длиннее, затирается нулём. Определяем длину строки через strnlen. Массив такой длины и посылаем.

Добавлено через 3 минуты
Цитата Сообщение от AdamBeno Посмотреть сообщение
Если отправку делать интервалом 30 мс и больше, все работает, если снизить интервал до 20 мс то появляется данная проблема.
Для таймаута хорошо использовать промежуток, не меньше 3-х байт на используемой скорости. Его надо настроить на стороне приёма. А на стороне передачи соблюдать равномерность передачи.

Либо использовать маркер конца посылки (\r, \n), или лучше нормальный бинарный протокол.

Добавлено через 4 минуты
Цитата Сообщение от COKPOWEHEU Посмотреть сообщение
Его отлаживать, да и просто смотреть сложнее, чем обычный текст. Опять повторяю: для отладки я скорее напишу UART_puts("ADC"); чем буду городить синхронизацию и ожидание буфера. И со стороны ПК достаточно обычного screen или cat чтобы посмотреть вывод, не нужны какие-то специальные программы со специальными протоколами.
Это поначалу сложнее, если ничего нет. С юнит тестами и хорошо написанным протоколом, никаких проблем не остаётся.
Я работал с и текстовыми (SCPI в приборах Agilent, Fluke и т.п.), и с бинарными (HART, ModBus). Текстовые они для ручной работы человека удобнее, а вот для автоматизации в программах - наоборот.
0
 Аватар для AdamBeno
21 / 14 / 7
Регистрация: 15.07.2018
Сообщений: 50
27.07.2023, 18:33  [ТС]
Rius, Возможно ошибка на стороне приемника, буду проверять. Я выключил все кроме uart, мне кажется невозможно чтобы он строку так передавал.
Цитата Сообщение от Rius Посмотреть сообщение
Текстовые они для ручной работы человека удобнее
я просто хотел легко отделаться
Миниатюры
STM32F103 Проблема с UART  
0
 Аватар для COKPOWEHEU
4144 / 2722 / 433
Регистрация: 09.09.2017
Сообщений: 12,056
27.07.2023, 18:39
Цитата Сообщение от AdamBeno Посмотреть сообщение
Если не затруднить взгляните на код, правильно ли организован буфер
А не проще самостоятельно проверить, написав аналогичный код для ПК и погоняв приемы-передачи?
Цитата Сообщение от AdamBeno Посмотреть сообщение
правильно ли организован буфер
Вы его через поллинг что ли обрабатываете? А чем прерывания не угодили?
Цитата Сообщение от Rius Посмотреть сообщение
Почему 1? Посылать надо всю строку.
Потому что кольцевой буфер. Скорость небольшая, накладные расходы на поллинг тоже. Почему бы и нет.
Цитата Сообщение от Rius Посмотреть сообщение
Что было длиннее, затирается нулём. Определяем длину строки через strnlen. Массив такой длины и посылаем.
Разве sprintf не добавляет ноль в конце? Должен же вроде.
В любом случае, проще все же добить нулями старшие разряды и сделать все строки равными по длине. Или, раз уж используется sprintf, заранее выделить поле нужного размера: sprintf(adc_str, "%5hu\n", adcValue);
Цитата Сообщение от Rius Посмотреть сообщение
Для таймаута хорошо использовать промежуток, не меньше 3-х байт на используемой скорости.
В отладочных задачах таймаут вообще не нужен. Да и в рабочих его в какие-то бешеные секунды можно выставить, чтобы только на совсем уж зависания срабатывал.
Цитата Сообщение от Rius Посмотреть сообщение
Это поначалу сложнее, если ничего нет. С юнит тестами и хорошо написанным протоколом, никаких проблем не остаётся.
Ну так мы и говорим про "по началу".
А на счет бинарных протоколов - то не изобретать же его с нуля. А если не с нуля, то нужен "эталонный" прибор, по которому можно удостовериться, что тот же modbus реализован правильно. А прибора такого обычно нет.
Да и смысла переусложнять без необходимости тоже нет. Здесь ведь не телеметрию гонять, а отдельные числа.

Добавлено через 2 минуты
Цитата Сообщение от AdamBeno Посмотреть сообщение
я просто хотел легко отделаться
Попробуйте просто поднять частоту обмена. Не 19200, а скажем 115200.
А что используете человеко-читаемый протокол, так это правильно. Сейчас вам важнее возможность отладки и универсальность, чем пропускная способность.
0
Эксперт .NET
 Аватар для Rius
13391 / 7846 / 1699
Регистрация: 25.05.2015
Сообщений: 23,855
Записей в блоге: 14
27.07.2023, 18:54
Цитата Сообщение от COKPOWEHEU Посмотреть сообщение
В отладочных задачах таймаут вообще не нужен. Да и в рабочих его в какие-то бешеные секунды можно выставить, чтобы только на совсем уж зависания срабатывал.
Если он неправильный, то может возникнуть то самое переполнение буфера, про которое вы говорили. Прога ждёт завершения приёма, а он всё не завершается, потому что каждая следующая посылка всё ещё укладывается в таймаут. И в конце концов возвращается столько, сколько влезло. А всё остальное уже при следующем чтении.

Цитата Сообщение от COKPOWEHEU Посмотреть сообщение
А на счет бинарных протоколов - то не изобретать же его с нуля. А если не с нуля, то нужен "эталонный" прибор, по которому можно удостовериться, что тот же modbus реализован правильно. А прибора такого обычно нет.
Для начала можно и не изобретать. На этот случай выше я привёл пример протокола HART, можно взять его за основу.
Цитата Сообщение от COKPOWEHEU Посмотреть сообщение
Да и смысла переусложнять без необходимости тоже нет. Здесь ведь не телеметрию гонять, а отдельные числа.
Конечно, таймаут или разделитель в виде \r\n может решить эту проблему разделения пакетов.
Но для уверенности в целостности принятых данных этого недостаточно.
0
 Аватар для COKPOWEHEU
4144 / 2722 / 433
Регистрация: 09.09.2017
Сообщений: 12,056
27.07.2023, 19:24
Цитата Сообщение от Rius Посмотреть сообщение
Прога ждёт завершения приёма
Это если прога ждет, и ждет именно завершения приема.
Но в простейшем случае никакой специальной проги нет, есть только стандартный терминал. И даже в более сложном случае с прогой, ждать она будет скорее конца строки, чем конца передачи. Потому что конца передачи может и не наступить.
Цитата Сообщение от Rius Посмотреть сообщение
Но для уверенности в целостности принятых данных этого недостаточно.
А на какую надежность вы рассчитываете? Минимальной можно достичь, отбрасывая откровенно битые строки (символы за пределами чисел, точки и т.п.). Чуть сложнее - добавить проверку четности. Еще сложнее - контрольные суммы, хотя бы вида LRC, как в ihex-файлах. Но сомневаюсь, что ТСу нужно что-то сложнее первых двух вариантов.
1
62 / 187 / 31
Регистрация: 14.02.2013
Сообщений: 1,715
27.07.2023, 21:22
AdamBeno, монитор давления на чём написали?

Добавлено через 2 минуты
Я вам говорю используйте для разделения 12 бит данных АЦП союз UNION и ещё возьмите один бит для определения вхождения правильной последовательности данных на ваш монитор давления.

Добавлено через 1 минуту
По сути ваш монитор давления должен быть запрощиком информации с устройства измерения тогда будет хоть какая то синхронизация.
0
 Аватар для AdamBeno
21 / 14 / 7
Регистрация: 15.07.2018
Сообщений: 50
27.07.2023, 21:25  [ТС]
Цитата Сообщение от COKPOWEHEU Посмотреть сообщение
Вы его через поллинг что ли обрабатываете? А чем прерывания не угодили?
Все варианты, которые можно реализовать с моими знаниями я пробовал, прерываниями, с DMA, даже менял мк, результат один. Я думаю, что все таки на стороне приемника дело, так как я отключил все и оставил просто uart и пересылал строку, и результат виден на скрине, пробовал другой терминал, там тоже самое, только там визуально как будто входящее сообщение разбивается и пересылается ровно по полам , например 1234 принимается 12 и чуть отставанием 34. Программа под которую я затеял это все написана давно и исходников у меня нет. Работа связана с ремонтом машин и поэтому основные задачи программирования сводится к проектам CAN, LIN. А чтобы сейчас написать для компа свой терминал, к этому как минимум нужно морально подготовиться
0
62 / 187 / 31
Регистрация: 14.02.2013
Сообщений: 1,715
27.07.2023, 21:33
AdamBeno, ну так если нет исходника терминала то фиг знает что там внутри. Если надумаете писать терминал приёма то советую на C# уж очень быстро везжаешь.
0
 Аватар для AdamBeno
21 / 14 / 7
Регистрация: 15.07.2018
Сообщений: 50
27.07.2023, 21:34  [ТС]
VladimirU, Я пробовал
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
typedef union {
    uint16_t value;
    uint8_t bytes[2];
} ADCData;
 
ADCData adcData;
 
 
uint16_t adcValue = 1234;
 
 
adcData.value = adcValue;
 
 
HAL_UART_Transmit(&huart1, adcData.bytes, sizeof(adcData.bytes), HAL_MAX_DELAY);
но так как при пересылке не строк а байтов, мне визуально трудно определить в таком случае ошибку, а написать на данный момент свой терминал уже готовлюсь, у меня даже не установлено ничего кроме cube и keil.
0
62 / 187 / 31
Регистрация: 14.02.2013
Сообщений: 1,715
27.07.2023, 21:42
AdamBeno, ну если знаете Си то и чего нибудь на Visual Studio освоите запросто.

Добавлено через 2 минуты
Да кстати если используете платы отладки с USB разъёмом то можно к компу подключать через USB в режиме эмуляции COM.
0
Эксперт .NET
 Аватар для Rius
13391 / 7846 / 1699
Регистрация: 25.05.2015
Сообщений: 23,855
Записей в блоге: 14
27.07.2023, 21:51
VladimirU, судя по скринам, у него там Bluetooth. Это ещё прослойка со своими глюками.

AdamBeno, сниффером посмотрите, что получает программа терминал .

COKPOWEHEU, у ТС терминал с непонятными принципами.
Я рассчитываю хотя бы на crc. То, что даст надёжно отличить битый пакет о целого.
1
62 / 187 / 31
Регистрация: 14.02.2013
Сообщений: 1,715
27.07.2023, 21:54
Цитата Сообщение от Rius Посмотреть сообщение
Я рассчитываю хотя бы на crc
Можно конечно но лишнее это будет у него поток данных для визуализации человеческим глазом, на стороне приёмника ведь не нужно точных вычислений.
1
 Аватар для AdamBeno
21 / 14 / 7
Регистрация: 15.07.2018
Сообщений: 50
27.07.2023, 21:56  [ТС]
Rius, пробовал без блютуз, через конвертор прямо к uart.
Цитата Сообщение от Rius Посмотреть сообщение
у ТС терминал с непонятными принципами
Одно помню точно, что отправлял через uart строку и в конце 0x20, а \n щас пишу для удобного восприятия, так как с пробелом тот же самый глюк.
0
 Аватар для AdamBeno
21 / 14 / 7
Регистрация: 15.07.2018
Сообщений: 50
27.07.2023, 22:21  [ТС]
Всем спасибо кто помогал, походу приемная сторона виновата, подключился анализатором к uart все ровно идет, даже если выставить интервал 1мс.
Миниатюры
STM32F103 Проблема с UART   STM32F103 Проблема с UART   STM32F103 Проблема с UART  

0
 Аватар для COKPOWEHEU
4144 / 2722 / 433
Регистрация: 09.09.2017
Сообщений: 12,056
27.07.2023, 23:11
Цитата Сообщение от Rius Посмотреть сообщение
COKPOWEHEU, у ТС терминал с непонятными принципами.
Ну так пусть попробует обычный терминал. Или хотя бы вывод содержимого COM-порта в текстовый файл. Если там все будет в порядке, значит проблема в терминале, если нет - на передающей стороне.
Цитата Сообщение от Rius Посмотреть сообщение
Я рассчитываю хотя бы на crc. То, что даст надёжно отличить битый пакет о целого.
Для ваших целей это, наверное, оправдано: городить целый бинарный протокол со всеми этими регистрами, арбитражем, контрольными суммами, повторной отправкой и тому подобным. Но ТС пока пару байтов через UART пропихнуть не может, куда ему ваши сложности?
Цитата Сообщение от AdamBeno Посмотреть сообщение
все ровно идет, даже если выставить интервал 1мс.
На скорости 19200? Эта 1 мс тогда между чем и чем интервал? Один байт у вас отправляется чуть больше полумиллисекунды, если что.
0
 Аватар для AdamBeno
21 / 14 / 7
Регистрация: 15.07.2018
Сообщений: 50
27.07.2023, 23:39  [ТС]
Цитата Сообщение от COKPOWEHEU Посмотреть сообщение
Эта 1 мс тогда между чем и чем интервал?
между сообщениями.
0
 Аватар для AdamBeno
21 / 14 / 7
Регистрация: 15.07.2018
Сообщений: 50
27.07.2023, 23:56  [ТС]
Хотел бы признаться и извиниться перед вами всеми за свои ошибки и недосмотр. Rius, был прав на счет Bluetooth, не знаю как так получилось, но я 1000% проверил вчера подключившись напрямую к uart, проблема возникает из за модуля jdy-31. Если подключиться напрямую uart, то все работает. Благодарю всех за ваше терпение и понимание.
Миниатюры
STM32F103 Проблема с UART  
1
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
inter-admin
Эксперт
29715 / 6470 / 2152
Регистрация: 06.03.2009
Сообщений: 28,500
Блог
27.07.2023, 23:56

Прошивка STM32F103 через UART
Доброго времени суток, возникла необходимость прошить STM32F103 по UART. Почитал в интернете что нужно перевести плату в режим «системного...

STM32F103 + DMA + UART отправка данных с прерыванием
Всем доброго дня. Прошу помощи , а то уже сломал мозг. Нужно отправить данные через DMA1 USORT2 с прыванием по окончание передачи. ...

STM32F103 UART лишний байт данных при приеме ломает все
Всем привет! Пришлось взять STM32F103 (терпеть не могу эту линейку, но было без вариантов). Итак частота проца 72 МГц, скорость по USART...

После отключения UART, RTC на stm32f103 начинает работать в 2 раза медленнее
Здравствуйте, для заливки программы в stm32f013 использую UART через бутлодер. Так как ST-link невозможно использовать в связи обрывом...

STM32F103 подключение через UART-RS485 счетчик Modbus RTU не отзывается
Электрически все подключается через UART2-&gt;конвертер-RS485-&gt;счетчик 1. Проверка счетчика через ПК-&gt;USB-конвертер-RS485-&gt;счетчик,...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
40
Ответ Создать тему
Новые блоги и статьи
Из невошедшего на форум (диалог с ИИ-гугла)
zorxor 29.07.2026
А вот, что интересно, сказал мне ИИ-гугла: Этот текст — эмоциональный пост пользователя под ником zorxor на интернет-форуме (вероятно, посвященном мистике, непознанному или альтернативной науке). . . .
Был праздник вчера, а я и не знал.
kumehtar 28.07.2026
27. 07. 2026г. Intel Core 2 Duo исполнилось 20 лет Новости компьютерного мира и их обсуждение (4) Салют, шампанское, овации! :drink:
Нейтральные знания, чистый код - бла-бла-бла-бла, на самом деле кликбейт и самореклама, плагиат, и вот почему
Hrethgir 27.07.2026
То-есть отклонение такой публикации говорит само за себя, и пусть только возьмут на вооружение после отклонения публикации - это будет чистейшим актом плагиата. Отклонял Хабр. Дословно, отклонённая. . .
тв 16 бой ии
anaschu 27.07.2026
Великий Перелом ИИ: Как уравнения ОДУ Radau дожали цензурные фильтры Алисы Фиксируем в мемофонде Теории Всего беспрецедентный факт в истории ИИ-зондирования. В затяжном многораундовом. . .
мв 15. непроверенное, возможно, глюк
anaschu 27.07.2026
НАУЧНО-АНАЛИТИЧЕСКИЙ ОТЧЕТ. РАЗДЕЛ 1. 1: «НАУКА» (РАСШИРЕННАЯ СТЕХИОМЕТРИЧЕСКАЯ И ГЕНЕТИЧЕСКАЯ ВЕРСИЯ)Тема: Теоретическое обоснование инвариантности 19-мерного тензорного ядра непрерывных ОДУ и. . .
Очистка реквизитов и табличных частей документа при копировании (вариант 2)
Maks 26.07.2026
Алгоритм из решения ниже разработан на примере нетипового документа "ЗаявкаНаРаботу", разработанного в КА2. Задача: Заменить алгоритм запрета копирования документов для сотрудников с ролью "Стажер",. . .
Доктрина интенционального знания - Доктрина для портала "Срез".
Hrethgir 25.07.2026
Может найдётся кто захочет оценить доктрину. . . Написания правил участия для меня роскошь, требующая лимита времени, поэтому все сообщения не прошедшие модерацию будут видны только участникам портала,. . .
сукцессия 44. Решил подать на припринт в межународные сервисы препринтов. Но нужно одобрение от ученых
anaschu 25.07.2026
Английский вариант. Пока кто то не одобрит мою личность, мне не получиться это опубликовать на препринте. Но заявку на публикацию статьи я сегодня подам.
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru