Какую скорость передачи я могу получить (без ошибок)?


40

Стандарт составляет 9600 бод. Это просто стандарт . Используя Arduino Uno SMD R2, какова максимальная практическая скорость передачи, которую я могу достичь?

Бонусные очки для смелых: Как бы вы пошли о создании механизма проверки ошибок, а затем о смешном увеличении скорости передачи, чтобы получить высокие скорости передачи?


2
Стоит отметить, что платы Arduino, использующие микросхемы FTDI USB-serial, могут работать ОЧЕНЬ быстро. Обычный FT232 может без проблем работать со скоростью 3 мегабода (это 3 000 000 бод). Использование ATmega16U2 является ограничивающим фактором.
Коннор Вольф

1
Мой клон Arduino Nano, который я получил от eBay, превысил 1099999. Шутки в сторону. Это сделал. Как только он достиг 1 100 000, результат был искажен. laqq`na`fca`fga`fga`bcngaah````iin`ha`a`a`bga`fga`bcqpahhqfq```fh`oopa`bca`fca, Для связи через USB используется чип CH340.
PNDA,

Ответы:


59

Здесь есть несколько факторов:

  • Какую скорость передачи данных может получить микроконтроллер ATmega328P?
  • Какую скорость передачи данных может обеспечить интерфейс USB-Serial?
  • Какова частота генератора на ATmega328P?
  • Какова частота генератора на последовательном USB-интерфейсе (если он есть)?
  • Насколько устойчив USB-последовательный интерфейс к несоответствию скорости передачи?

Все эти факторы имеют отношение к определению максимально достижимой скорости передачи. ATmega328P использует аппаратный делитель от своей тактовой частоты для генерации базовой частоты для последовательного интерфейса. Если нет целочисленного отношения от основного тактового генератора к битовому времени желаемой скорости передачи, MCU не сможет точно произвести желаемую скорость. Это может привести к потенциальным проблемам, поскольку некоторые устройства гораздо более чувствительны к несоответствию скорости передачи, чем другие.

Интерфейсы на основе FTDI вполне терпимы к несоответствию скорости передачи данных до нескольких процентов ошибок. Однако я работал со специализированными встроенными модулями GPS, которые не могли справиться даже с ошибкой скорости передачи 0,5%.

Обычные последовательные интерфейсы допускают ошибку скорости передачи ~ 5%. Однако, так как каждый конец может быть выключен, более распространенная спецификация составляет + -2,5%. Таким образом, если один конец работает на 2,5% быстрее, а другой - на 2,5% медленнее, ваша общая ошибка по-прежнему составляет всего 5%.


В любом случае. Uno использует ATmega328P в качестве основного MCU и ATmega16U2 в качестве последовательного USB-интерфейса. Нам также повезло, что в обоих этих микроконтроллерах используются аналогичные аппаратные средства USART, а также тактовые частоты 16 МГц.

Поскольку оба MCU имеют одинаковое аппаратное обеспечение и тактовую частоту, они оба будут иметь одинаковую ошибку скорости передачи в одном и том же направлении, поэтому мы можем функционально игнорировать проблему ошибки передачи.

В любом случае, «правильный» ответ на этот вопрос будет включать в себя поиск источника для ATmega16U2 и определение возможных скоростей передачи оттуда, но, поскольку я ленив, я полагаю, простое эмпирическое тестирование подойдет.

Быстрый взгляд на таблицу данных ATmega328P приводит к следующей таблице:
введите описание изображения здесь

Поэтому, учитывая максимальную скорость передачи данных 2 Мбит / с, я написал программу быстрого тестирования:

void setup(){};

void loop()
{

  delay(1000);
  Serial.begin(57600);
  Serial.println("\r\rBaud-rate = 57600");
  delay(1000);
  Serial.begin(76800);
  Serial.println("\r\rBaud-rate = 76800");
  delay(1000);
  Serial.begin(115200);
  Serial.println("\r\rBaud-rate = 115200");
  delay(1000);
  Serial.begin(230400);
  Serial.println("\r\rBaud-rate = 230400");
  delay(1000);
  Serial.begin(250000);
  Serial.println("\r\rBaud-rate = 250000");
  delay(1000);
  Serial.begin(500000);
  Serial.println("\r\rBaud-rate = 500000");
  delay(1000);
  Serial.begin(1000000);
  Serial.println("\r\rBaud-rate = 1000000");
  delay(1000);
  Serial.begin(2000000);
  Serial.println("\r\rBaud-rate = 2000000");
};

И затем, глядя на соответствующий последовательный порт с последовательным терминалом:

введите описание изображения здесь

Похоже, аппаратное обеспечение может без проблем работать на скорости 2 000 000 бод.

Обратите внимание, что эта скорость передачи только дает MCU 64 80 тактов на байт, поэтому было бы очень сложно поддерживать последовательный интерфейс занятым. В то время как отдельные байты могут передаваться очень быстро, вероятно, будет много времени, когда интерфейс просто простаивает.


Изменить: фактическое тестирование!

2 Мбит / с реальны:
введите описание изображения здесь
каждый бит равен 500 нс, что в точности соответствует ожидаемому.

Проблемы с производительностью! Общая длина пакета:
500 Кбод: введите описание изображения здесь

1 МБод: введите описание изображения здесь

2 Мбод: введите описание изображения здесь
Примечание. Заметное превышение вызвано плохой практикой заземления зонда и, вероятно, не соответствует действительности. Я использую вывод заземления, который является частью моего зондового прицела, и индуктивность вывода, вероятно, является причиной большинства перерегулирований.

Как видите, общая длина передачи одинакова для 0,5, 1 и 2 МБод. Это потому, что код, который помещает байты в последовательный буфер, плохо оптимизирован. Таким образом, вы никогда не достигнете ничего лучше, чем эффективные 500 кбод, если вы не напишите свои собственные последовательные библиотеки. Библиотеки Arduino очень плохо оптимизированы, поэтому, вероятно, не составит большого труда получить надлежащие 2 Мбод, по крайней мере для пакетной передачи, если вы потратите на это немного времени.


4
Хорошая иллюстрация ограничения пропускной способности!
Джиппи

1
@AnnonomusPerson - если вы переключаетесь на тактовую частоту 20 МГц, вы можете использовать скорость 2,5 Мбит / с.
Коннор Вольф

1
@AnnonomusPerson - вам нужно поменять местами оба или использовать USB-последовательный интерфейс FTDI с 20 МГц генератором ATmega328P. ATmega328P не может работать со скоростью 2,5 Мбит / с без 20 МГц кристалла / резонатора. То же самое верно для любых интерфейсов ATmega16U2.
Коннор Вольф

1
Отличный ответ! Только одно небольшое исправление: при 2 Мбит / с каждая передача байта занимает 80 циклов ЦП, а не 64. Это связано с тем, что по времени каждый байт стоит 10 бит (1 старт, 8 данных, 1 остановка).
Эдгар Бонет

1
@ linhartr22 - Провода действительно вступают в игру только в том случае, если они длинные , как в 12 "+. Я думаю, что, вероятно, маловероятно, что слишком много людей используют слишком длинные кабели длиной 100 футов. Кроме того, вопрос заключался в том, насколько высоко arduino / ATmega Скорость передачи данных может увеличиваться, а не то, насколько высока может быть произвольная сборка кабеля
Коннор Вольф

7

Окно Arduino Serial Monitor ограничивает вас 115200, но это не самая высокая скорость передачи данных. Вы можете прочитать таблицы данных Atmel и FT232 (или что вы используете), чтобы узнать максимум, но я могу успешно использовать 230400 (в два раза быстрее, чем самый большой, который поддерживает последовательный монитор Arduino) без проблем.

Если вы хотите увидеть результаты на своем компьютере, вам потребуется еще один последовательный монитор, который поддерживает другие параметры скорости передачи. Мне нравятся CoolTerm и Termite .

Обратите внимание, что это также сильно зависит от вашей тактовой частоты.

Вот калькулятор, чтобы помочь вам с расчетом, что возможно.


Когда вы начинаете работать все быстрее и быстрее, ограничение становится последовательной библиотекой - ее реализация не очень эффективна.
Cybergibbons

сайт ссылки не работает
Codebeat

3

Вероятно, это один из немногих аспектов, в которых доски el-Cheapo отличаются от оригинальных плат. Максимальная скорость последовательной передачи данных в значительной степени ограничена качеством платы и ее расположением. Как только последовательные данные поступают в интерфейсную микросхему AVR или USB, данные будут обрабатываться иначе, чем последовательный протокол UART.

Имейте в виду, однако, что микроконтроллер имеет некоторое базовое аппаратное обеспечение для сдвига входных / выходных последовательных данных на / с выводов ввода-вывода, но абсолютная максимальная частота ограничена тактовой частотой 16 МГц (для AVR). Как только байт перемещается в последовательный буфер, аппаратное обеспечение UART вступает во владение и самостоятельно выдвигает / вытягивает биты. В лучшем случае AVR достигает 16M инструкций в секунду, а прерывания, используемые для заполнения последовательного буфера, имеют некоторые издержки (по меньшей мере 8 тактов для обработки прерываний + инструкции для сохранения текущего состояния + несколько инструкций для фактического заполнения буфера). При заданной скорости передачи данных протокол будет работать с колоссальными n битами в секунду, но вашему контроллеру требуется больше времени для заполнения последовательного буфера, чем для фактического вывода данных, что приводит к более низкой средней пропускной способности, чем вы ожидаете, и UART на холостом ходу. относительно долгое время.

Еще один эффект, который следует помнить, заключается в том, что все накладные расходы, необходимые для выталкивания данных в UART (или извлечения их), не могут быть потрачены в вашей реальной программе, что опять-таки влияет на среднюю практическую пропускную способность. Вы можете использовать каждый цикл инструкций только один раз, либо для заполнения буфера, либо для вычисления основного цикла.

Таким образом, максимальная пропускная способность зависит от используемого вами приложения (насколько быстро данные генерируются / вычисляются / готовы к перемещению в / из последовательного буфера), а фактический «физический» битрейт является лишь малой частью проектного решения.


1
Я действительно, ДЕЙСТВИТЕЛЬНО сомневаюсь, что у любой из плат есть проблемы с компоновкой, достаточно серьезные, чтобы помешать нормальной работе сигнала 2 МГц. 2 МГц не совсем высокая частота.
Коннор Вольф

@FakeName По крайней мере одна доска на моем столе увеличила BER, когда я увеличиваю скорость последовательной передачи. Я обычно использую 9600, что более чем достаточно для большинства приложений и является надежным.
Джиппи

Без шуток! Да. Интересно, как плохо должно быть расположение, чтобы это произошло? Я подозреваю, что это не макет, а плохо терпимые резонаторы / кристаллы, хотя.
Коннор Вольф

1
Высокие скорости передачи данных, особенно U2Xn = 1в USART, имеют тенденцию быть довольно расстроенным из-за несоответствия.
Коннор Вольф

@FakeName Я динозавр, мне нравится "9600 8N1" по всем неправильным причинам, о которых вы можете подумать; o)
Джиппи

2

Проверка ошибок на самом деле очень проста, и есть библиотека AVR, которая делает это в один слой.

Читайте дальше, util/crc16.hи вы должны быть хороши в кратчайшие сроки с включенными примерами.

CRC достаточно надежен и быстр для простых приложений.

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.