Но ведь это несложно и проверить на деле.
Нет, не выставляется, ведь ничего не было принято, поскольку старт-бит и стоп-бит не были обнаружены, и запуска сдвигового регистра приема не было.
Во время приема флаг RXNE выставляется в конце приема байта, а флаг IDLE будет выставлен после того, как линия RX будет оставаться свободной в течение времени, равного длительности кадра (обычно 10 бит).
Флаг ORE (overrun) будет выставляться тогда, когда был принят новый байт, а предыдущий не был прочитан.
Код: Выделить всё
oid USART2_IRQHandler(void)
{
/* Линия свободна (idle frame) */
if((USART2->ISR & USART_ISR_IDLE)&&(USART2->CR1 & USART_CR1_IDLEIE))
{
Start_RTOTimer();
USART2->ICR = USART_ICR_IDLECF;
}
/* Предыдущий принятый символ не был прочитан */
if(USART2->ISR & USART_ISR_ORE)
{
ToRXBuff(USART2->RDR);
USART2->ICR = USART_ICR_ORECF;
}
/* Символ был принят */
if((USART2->ISR & USART_ISR_RXNE)&&(USART2->CR1 & USART_CR1_RXNEIE))
{
Stop_RTOTimer();
ToRXBuff(USART2->RDR);
}
/* Готов к передаче символа */
if((USART2->ISR & USART_ISR_TXE)&&(USART2->CR1 & USART_CR1_TXEIE))
{
uint8_t ch;
if(FromTXBuff(&ch))
USART2->TDR = ch;
else
USART2->CR1 &= ~USART_CR1_TXEIE;
}
/* Передача символа была завершена и передающий буфер пуст */
if((USART2->ISR & USART_ISR_TC)&&(USART2->CR1 & USART_CR1_TCIE))
{
}
/* Ошибка кадра в приемнике */
if(USART2->ISR & USART_ISR_FE)
{
USART2->ICR = USART_ICR_FECF;
}
}
причем, запуск RTO-таймера можно делать или в IDLE, или в RXNE. В последнем случае таймер не останавливается, а перезапускается с начала.
Так же, я настоятельно рекомендую использовать проверку не только флага источника прерывания, но и бита разрешения этого источника. Особенно это необходимо при передаче по TXE-флагу. Этот флаг устанавливается независимо от того, включен передатчик (TE) или выключен. И попадая в прерывание по другому источнику, будет лишняя загрузка передающего регистра. Именно с помощью запрета прерывания TXEIE прекращается передача (в варианте передачи по прерываниям).
Флаг TC устанавливается по завершению передачи символа, если в передающем буфере нет загруженных байтов (TXE = 1).
Ну и не надо писать if((USART1->SR & USART_SR_RXNE) >> USART_SR_RXNE_Pos) == 1), поскольку это излишние действия. Нужно отталкиваться от того, что по правилам языка Си, выражение в
if() будет истинно при любом ненулевом значении. А запись
USART1->SR & USART_SR_RXNE представляет собой логическую побитовую операцию AND с содержимым регистра и значением битовой маски. То есть, например 0
110 AND 0
100 = 0
100, это есть ненулевое значение и условие
if будет истинно и выполнится. Если же 0
010 AND 0
100 = 0
000, то условие
if будет ложно и не выполнится.
& - означает побитовую операцию AND двух чисел.
&& - означает логическое AND выражений: "если (ВЫРАЖЕНИЕ_1 = истина)
И (ВЫРАЖЕНИЕ_2 = истина)"