Вс янв 30, 2022 06:47:57
Вс янв 30, 2022 09:34:59
Вс янв 30, 2022 12:05:27
Вс янв 30, 2022 14:43:49
Вс янв 30, 2022 14:49:55
Вс янв 30, 2022 18:14:04
Вс янв 30, 2022 18:35:33
Вс янв 30, 2022 18:46:33
void USART1_IRQHandler(void) {
if (USART1->SR & USART_SR_IDLE) {
(void)USART1->DR; // Очистка флага IDLE. Мне лично кажется такой подход странным, но так сказано в RM на кристалл. Окей.
// Взводим флаг, что данные были приняты
BOX_CON_RX_DONE = 1;
// Проверяем, что значение счётчика DMA_Stream->NDTR изменилось
if ((sizeof(BoxCon_RX_BUF) - DMA2_Stream5->NDTR) != DMA_BUF_START_LAST) {
// Запоминаем позиции в другие масивы. В итоге получаем ссылки на адреса в кольцевом буфере, без, собственно, ссылок.
DMA_BUF_START[DMA_CURR_WR_BUF] = DMA_BUF_START_LAST;
DMA_BUF_START_LAST = (sizeof(BoxCon_RX_BUF) - DMA2_Stream5->NDTR);
DMA_BUF_END[DMA_CURR_WR_BUF] = DMA_BUF_START_LAST;
// Выбираем следующий указатель (там не указатель, но суть похожа)
DMA_CURR_WR_BUF++;
// Проверяем, и если он последний - возвращаемся в начало.
if (DMA_CURR_WR_BUF >= (MAX_DMA_BUFFERS_COUNT)) { DMA_CURR_WR_BUF = 0; };
};
};
};
Вс янв 30, 2022 19:10:45
Используется прерывание USART:IDLE,
Вс янв 30, 2022 21:14:55
Вс янв 30, 2022 21:23:51
Вс янв 30, 2022 23:18:13
Вс янв 30, 2022 23:22:12
Вс янв 30, 2022 23:31:12
Вот же, всё есть :ivan dimir писал(а):Но не прерывании по USART IDLE
Вы покажите пример который работает и который не работает. И Вам подскажут, что делаете не так.ivan dimir писал(а):Я включал ADC+DMA.Я выключаю прерывание по ADC.Иначе работать не будет.
Пн янв 31, 2022 00:24:33
Прием с использованием DMA
Режим DMA можно включить для приема, установив бит DMAR в регистре USART_CR3.
Данные загружаются из регистра USART_DR в область SRAM, сконфигурированную с помощью DMA.
периферийное устройство (см. спецификацию DMA) всякий раз, когда принимается байт данных. Чтобы отобразить прямой доступ к памяти
канала для приема USART используйте следующую процедуру:
1. Запишите адрес регистра USART_DR в регистр управления DMA, чтобы сконфигурировать его как
источник перевода. Данные будут перемещены с этого адреса в память после
каждое событие RXNE.
2. Запишите адрес памяти в управляющий регистр прямого доступа к памяти, чтобы настроить его как место назначения.
передачи. Данные будут загружаться из USART_DR в эту область памяти после каждого
RXNE-событие.
3. Настройте общее количество байтов для передачи в регистре управления DMA.
4. Настройте приоритет канала в регистре управления DMA.
5. Настройте генерацию прерывания после половинной/полной передачи в соответствии с требованиями приложения.
6. Активируйте канал в регистре управления DMA.
Когда количество передач данных, запрограммированное в контроллере DMA, достигнуто, DMA
контроллер генерирует прерывание по вектору прерывания канала DMA. Бит DMAR должен
быть очищенным программным обеспечением в регистре USART_CR3 во время подпрограммы прерывания
Пометка ошибок и генерация прерываний в многобуферной связи
В случае многобуферной связи, если во время транзакции возникает какая-либо ошибка, флаг ошибки
будет утвержден после текущего байта. Прерывание будет сгенерировано, если разрешение прерывания
установлен флаг. Для ошибки кадрирования, ошибки переполнения и флага шума, которые устанавливаются с помощью RXNE в
В случае приема одного байта будет отдельный бит разрешения прерывания флага ошибки (бит EIE в
регистр USART_CR3), который, если он установлен, вызовет прерывание после текущего байта с
любая из этих ошибок.
Пн янв 31, 2022 00:32:04
Пн янв 31, 2022 00:46:53
Пн янв 31, 2022 01:02:37
Пн янв 31, 2022 07:40:36
Опять тот же вопрос, для чего?Аlex писал(а):Передача - это элементарно.
И опять тот же самый вопрос, для чего?Аlex писал(а):А с приёмом, если размер неизвестен,
void TIM2_IRQHandler(void) {
if (TIM2 - > SR & TIM_SR_UIF) {
TIM2 - > SR &= ~TIM_SR_UIF;
//IWDG->KR = 0xAAAA;
pauza++;
if (pauza > 40) {
//IWDG->KR = 0xAAAA;
GPIOC - > BSRR |= GPIO_BSRR_BS13;
}
if (pauza > 80) {
GPIOC - > BSRR |= GPIO_BSRR_BR13;
pauza = 0;
}
}
}
void TIM3_IRQHandler(void) {
if (TIM3 - > SR & TIM_SR_UIF) {
TIM3 - > SR &= ~TIM_SR_UIF;
pauza1++;
}
}
void timer_2_init(void) {
RCC - > APB1ENR |= RCC_APB1ENR_TIM2EN;
TIM2 - > PSC = 3500 - 1; // ??????????? ???????? ??? ?????? ????? 1000 ??? ? ???????
TIM2 - > ARR = 100 - 1; //65535
TIM2 - > EGR |= TIM_EGR_UG;
TIM2 - > DIER |= TIM_DIER_UIE;
TIM2 - > CR1 |= TIM_CR1_CEN;
NVIC_EnableIRQ(TIM2_IRQn);
}
void timer_3_init(void) {
RCC - > APB1ENR |= RCC_APB1ENR_TIM3EN;
TIM3 - > PSC = 3500 - 1; // ??????????? ???????? ??? ?????? ????? 1000 ??? ? ???????
TIM3 - > ARR = 100 - 1; //65535
TIM3 - > EGR |= TIM_EGR_UG;
TIM3 - > DIER |= TIM_DIER_UIE;
TIM3 - > CR1 |= TIM_CR1_CEN;
NVIC_EnableIRQ(TIM3_IRQn);
}
Пн янв 31, 2022 09:11:45
void Send_USART1_DMA(uint8_t *adr, uint32_t cnt)
{
constexpr uint32_t dma_cfg = _VAL2FLD(DMA_CCR_MSIZE,0) | _VAL2FLD(DMA_CCR_PSIZE,0) | DMA_CCR_DIR | DMA_CCR_MINC;
DMA1_Channel1->CCR = dma_cfg;
DMA1_Channel1->CMAR = (uint32_t) adr; // Чаще всего не надо
DMA1_Channel1->CNDTR = cnt;
DMA1_Channel1->CCR = dma_cfg | DMA_CCR_EN;
}
//void Send_USART1_DMA(uint8_t *adr, uint32_t cnt)
//{
// constexpr uint32_t dma_cfg = _VAL2FLD(DMA_CCR_MSIZE, 0) | _VAL2FLD(DMA_CCR_PSIZE, 0) | DMA_CCR_DIR | DMA_CCR_MINC;
// DMA1_Channel1->CCR = dma_cfg;
_Z15Send_USART1_DMAPhj:
LDR R2,??DataTable3_6
MOVS R3,#+144
STR R3,[R2, #+0]
// DMA1_Channel1->CMAR = (uint32_t) adr; // Чаще всего не надо
STR R0,[R2, #+12]
// DMA1_Channel1->CNDTR = cnt;
STR R1,[R2, #+4]
// DMA1_Channel1->CCR = dma_cfg | DMA_CCR_EN;
MOVS R0,#+145
STR R0,[R2, #+0]
//}
BX LR