Связь между микроконтроллерами - I2C, SPI, UART?

По сути, у меня есть два микроконтроллера, которые мне нужны для связи друг с другом.

Оба контроллера отправляют и получают данные.

Основная идея, которая у меня есть:

  1. I2C, SPI - то, что я думаю, что мы не можем использовать эти протоколы в этом случае. Потому что оба являются протоколами на основе master-slave. Таким образом, если один контроллер настроен как ведущий, а другой как подчиненный, то в этом случае, если подчиненный UC хочет передать данные, он не может инициировать передачу, а также не может генерировать часы.

  2. UART - я думаю, это должно работать, поскольку оно асинхронно. Так что никто не обязан быть рабом или господином.

Мой вопрос в том, верны ли сделанные выше предположения? Если нет , то поправьте меня.

Какой микроконтроллер вы используете, и что вы используете для его программирования? Если он основан на Arduino, вы можете использовать библиотеку SoftwareSerial, чтобы использовать любой из «цифровых» контактов в качестве поддельного UART, если у вас есть обычные аппаратные UART, выполняющие другие задачи.

Ответы (3)

Ваши предположения верны, да. SPI и I2C обычно являются ведущими/ведомыми протоколами, хотя есть способы «согнуть» их, чтобы они могли работать в любом случае.

Но для простоты да, UART наверное самый простой и толковый.

UART для победы! Однако в его микроконтроллере может не быть много/ни одного запасного UART, иногда бывает непросто иметь столько из них, сколько вы хотите.
Таким образом, вы выбираете микроконтроллеры, которые соответствуют дизайну, а не дизайну вокруг Arduino ;) Вот почему мне нравится концепция Cypress PSoC, где вы сами решаете, сколько UART (например) у вас есть в вашем чипе. Жаль, что у него нет программной поддержки ни для чего, кроме Windows :(
Я изучил материал Cypress PSOC, его программа дизайна действительно крутая. Есть новые Atmel Cortex M0, серия D20, которые теперь имеют реконфигурируемые интерфейсные блоки, которые могут действовать как любое из основных периферийных устройств связи. Значит, у вас есть все UART, которые вы хотите!

Если это для вашей собственной настройки, то единственное, что имеет значение, это согласованность. Вы контролируете все, так что это зависит от вас. Вы можете использовать стандартный протокол, создать свой собственный или изменить его в соответствии с вашими потребностями . Если у вас уже есть такая шина, как I2C или SPI, вы можете продолжать ее использовать.

Тем не менее, хотя I2C и SPI являются протоколами master-slave, это можно легко обойти с помощью вывода прерывания/сигнала. Если ведомое устройство хочет поговорить с ведущим, оно переключает вывод прерывания, и ведущее устройство инициирует сеанс I2C/SPI. Или опрос.

Что касается генерации часов, если у вас нет особой потребности в том, чтобы оба микроконтроллера делали это, зачем беспокоиться? Вам нужно запустить один на другой скорости? Заранее выберите тактовую частоту и придерживайтесь ее в своей реализации.

Также для SPI и т. Д. Вы можете иметь оба устройства в обычном режиме в режиме ведомого, а затем, когда одно из них хочет поговорить с другим, оно переключается в режим ведущего на время передачи. Действительно хорошо работает только на прямой ссылке 1: 1, а не на общей шине.
Это очень хороший подход, я никогда не думал об этом. Однако таким образом только один контроллер сможет отправлять данные одновременно, если другой контроллер захочет отправить данные, он должен стать ведущим. Это правильно?
@virendrakumar «отправка» данных субъективна. И spi, и i2c являются двунаправленными шинами. Отправка данных от ведомого к ведущему просто означает, что ведущее устройство запрашивает данные, а ведомое отвечает. С несколькими устройствами у вас может быть несколько выводов прерывания или одно общее прерывание с открытым стоком, а затем мастер опрашивает каждое устройство, чтобы узнать, какое из них готово к отправке данных. Или, если у вас их много, расширитель портов gpio, выступающий в качестве посредника, тоже подойдет.
Кроме того, в i2c есть настройки с несколькими мастерами, где любое устройство может стать мастером, если это необходимо. Или smbus, «расширенный i2c», который также имеет многоадресную глобальную адресацию, где он сигнализирует всем устройствам, чтобы они ответили, если у них есть предупреждение и т. д. и т. д. Много способов сделать это.

Устройства на шине I²C не имеют предопределенных ролей ведущего и ведомого: устройство является ведущим, если оно в настоящее время контролирует транзакцию с ведомым или активно пытается это сделать. Устройство является ведомым, если оно имеет адрес ведомого и либо обменивается данными с ведущим устройством, либо прослушивает ведущие устройства. Другие устройства на шине просто неактивны.

I²C поддерживает несколько ведущих и несколько ведомых устройств. Если у вас есть несколько устройств, которые должны иметь возможность отправлять или получать данные по желанию, вы назначаете подчиненный адрес каждому из них и программируете их на роль ведущего, когда им нужно передавать или запрашивать данные.

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

Короче говоря, то, что вы хотите, определенно возможно с I²C. Тем не менее, реализация I²C немного утомительна и, вероятно, излишняя для всего двух микроконтроллеров, пытающихся общаться друг с другом. Я бы выбрал UART в вашем случае, благодаря его простоте и гибкости.