Уже давненько была задача реализовать приёмопередатчик на STM32 (вроде удлинителя RS485, опустим подробности). Сама по себе задача простая, принял от хоста посылку, передал в устройство. Ни чего "военного".
С архитектурой STM32 до этого дела не имел, опыт был с 8-ми битными микроконтроллерами SiLabs (кстати очень мне понравились они организационно, т.е. документация и среда разработки удобная для меня, есть примеры работы со всеми устройствами на борту).
Вот так, не ожидая неприятностей, приступил к работе. В протоколе обмена есть такая особенность, иногда выполняется запрос в один байт, на который абонент отвечает очень быстро. То есть, необходимо как можно быстрее, после передачи, переключить приёмопередатчик RS485. Раньше я считал, что прерывание микроконтроллера по завершению передачи происходит в середине стопового бита. (Именно так у SiLabs и Dallas).
Поэтому, нужно выждать паузу, равную половине бита для текущей скорости обмена, после чего выполнять переключение приёмопередатчика. Иначе стоповый бит будет обрезан, что приведёт к ошибке передачи. Запустил устройство, вижу постоянные сбои связи. Ни каких аппаратных средств не было (вроде осциллографа и т.д.). Подробностей уже не помню, экспериментально установил, что увеличение паузы перед переключением приёмопередатчика снижает частоту сбоев связи. В конце-концов, нашёл достаточно большое значение паузы, при котором наблюдал стабильный обмен в течении часа.
Выводы следующие. Либо из-за моего слабого знакомства с STM32, я где то ошибся в программе, либо у STM32 прерывание "плавает" т.е. происходит не точно в середине стопового бита.
(Небольшое отступление от темы. Если бы я не наталкивался раньше на аппаратные ошибки в микросхемах, то однозначно считал бы это своей ошибкой. Так бывает чаще всего. Но у STM32 документ с аппаратными ошибками чуть ли не толще мануала. Ну шучу конечно, просто он объёмный. Вот например АЦП AD7730 обычный в DIP корпусе работает "нормально", а мало потребляющий с буквой L и почему то только в планарном корпусе, в одном из диапазонов работы шумит. Программа одна и та же, переключил диапазон, всё нормально и там и там. Вернулся на другой диапазон, у L-ки шум, у обычной норма.)
Внимание вопрос, когда происходит прерывание по завершению передачи по UART в STM32? Наблюдал ли кто нибудь подобный эффект? (возможно просто партия была с дефектом)
Если кому то "скучно" или просто сильно любопытный, могу выложить весь проект с иcходным кодом. Там ни чего секретного нет.
Из разряда догадок. Возможно причина в раздельном тактировании периферии у STM32. Читал когда то статью, о преобразователях интерфейса различных производителей. Там говорилось (пишу по памяти), что частота дискретизации у разных производителей отличалась. У большинства 8 - 16 дискрет на бит передачи, у SiLabs 128 - 256 дискрет на бит передачи. Возможно в этом причина неточности.
|