Gsm модуль подключение к микроконтроллеру. Проекты. Что мы имеем после прошивки

Итак, после продолжительного времени раскуривания тонкостей работы с GSM модулем SIM900D анонсируем первый рабочий проект, совмещающий в себе охранную систему с возможностью удаленного контроля. Если кратко, то устройство способно отправлять информирующие SMS в случае срабатывания датчика проникновения, делать дозвон для возможности аудиоконтроля помещения, следить за температурой и отправлять ее смс-кой по запросу, а также управлять какой-нибудь нагрузкой по команде отправленной по смс.

Кто следил за данной темой, тот в курсе, что у меня GSM модуль и модуль управления им - две разные платы, соединенные бутербродом (см. плата с SIM900D и плата управления ). На управляющей плате помимо микроконтроллера ATmega32a стоит модуль питания, выполненный на преобразователе LM2596 , он запитывает схему постоянным напряжением 3,5 вольт. В принципе подойдет любой другой источник питания, главное чтобы он был способен кратковременно вытянуть до 2 ампер (именно такое потребление GSM-модуля в момент регистрации).

Удобства ради, к плате управления подключен дисплей от телефона Nokia3310, методы работы с котором уже ни раз описывались на этом сайте. Благодаря дисплею можно быстро определить состояние устройства и значение датчиков.

В итоге получившаяся схема подключения вышла такая (кликабельно):

Нумерация выводов микроконтроллера на схеме приведена для DIP корпуса, поэтому если повторяете схему с использованием мк в корпусе TQFP будьте внимательны, нумерация выводов у него отличается. Тактируется микроконтроллер от внешнего кварца на 16 МГц.

Линия Control идущая от коллектора транзистора Q2 к выводу PortD.4 микроконтроллера добавлена для перестраховки и нужна за тем чтобы следить включен ли модуль. Так как порог выключения у SIM900 составляет 3,2 вольта то даже при незначительной просадке напряжения модуль автоматически выключится, тогда как микроконтроллер продолжит работать и выполнять программу (порог сброса у ATmega32a 2,7 вольта). В рабочем состоянии на этой линии находится низкий уровень. Если микроконтроллер обнаружит что на этой линии высокий уровень, выполнится функция повторного запуска GSM модуля.

А вот так это выглядит в работе на данный момент.

После окончательной обгонки программы, все это будет засунуто в корпус, а разъемные соединения для надежности будут запаяны.

На дисплей выводится основная информация о состоянии устройства: название оператора, качество сигнала связи, значение температуры с датчика 18b20, состояние выхода нагрузки и датчика проникновения, а так же время и дата.

Видео включения модуля

Время и дата берутся от встроенных в GSM-модуль часов. Для их работы обязательно наличие 3-х вольтовой батарейки подключенной к выводу 15 (VRTC). Диод D1 рекомендуется ставить с низким падением напряжения, например Шоттки. Настройка часов и даты делается в ручную, команды были описаны ранее

Дата выводится на дисплей в том формате как получается с модуля, тоесть сначала год, затем месяц и дата. Здесь пока ничего менять не стал.

За измерение температуры отвечает датчик DS18B20, он подключается к выводу PortD.3 микроконтроллера.

К PortD.6 можно подключить какую-нибудь нагрузку и управлять ей посредством команд смс. У меня сейчас висит светодиод - D4 на схеме. Но ничего не мешает повесить сюда релюху или симистор и управлять чем-нибудь посерьезней.

В охранных целях планируется применение датчика движения HC-SR501 , купленного на E-bay. В случае срабатывания на выходе датчика появляется логическая единица. Поймав ее, микроконтроллер даст команду на отправку SMS сообщения по телефонному номеру, заданному в программе.

Выход датчика подключается к выводу PortD.7 микроконтроллера, на схеме, датчик условно заменен на кнопку.

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

Для того чтобы предотвратить многократное отсылание предупреждающих смс в случае срабатывания датчика, в программу введено ограничение: после первого отправленного смс ставится запрет на последующую отправку. Чтобы заново разрешить отправку уведомляющих сообщений при срабатывании датчика, необходимо отослать на модуль смс с определенной командой. Когда посылка смс запрещена на дисплей возле состояния датчика, выведется восклицательный знак.

Список команд

А вот и список команд в смс которые обрабатывает модуль. Для удобства и простоты комады цифровые, возможно в следующих версиях прошивки будут более осмысленные имена команд:)

0 - Отключение нагрузки (на выводе PortD.6 выставляется логический 0)

1 - Включение нагрузки (на выводе PortD.6 выставляется логическая 1)

2 - Приняв эту команду, модуль перезвонит на указанный в программе телефонный номер

3 - Запрос баланса и отправление его смс-кой обратно на указанный номер. Здесь есть один важный нюанс - ответы на USSD запросы обязательно должны приходить в латинице. Иначе заместо осмысленного текста в ответ придет сообщение в шестнадцатеричной кодировке. Как перевести USSD в латиницу нужно уточнить у своего оператора. К примеру, на используемой мной симке от Смартса, нужно ввести *102*1# (в мегафоне *105*0#)

4 - Запрос температуры. Значение температуры будет отправлено нам в смс.

5 - Разрешенить отсылать сообщения в случае срабатывания датчика проникновения.

6 - Запрет на отправление уведомляющих смс от датчика проникновения.

? - По этой команде модуль пришлет нам смс, в котором находится общая информация об устройстве, такие как значение с датчика температуры, включена ли нагрузка, состояние на входе от датчика проникновения и разрешена ли отправка уведомляющих смс от него. К примеру, вот как может выглядеть такое сообщение: температура +24, нагрузка выключена, на выходе датчика движения 0, отправка смс в случае срабатывания запрещена.

Теперь как настроить чтобы модуль отправлял sms именно на ваш номер. В архиве с программой находим основной файл программы, она так и называется "программа" :) и находим в ней константу:

Const Phonenumber = "+7908390хххх"

подставляем сюда свой номер телефона, компилируем программу и получаем hex файл прошивки.

Программа как и всегда написана в Bascom-AVR, поэтому разобраться с алгоритмом работы с GSM модулем достаточно просто. Удачи!

Ну и напоследок демонстрация того как модуль обрабатывает команды.

Отдельное спасибо за участие и помощь в разработке, давнему товарищу сайта Сергею RD3AVJ!

UPD: от 31.10.12

Немного доработал прошивку, теперь для того чтобы задать номер на который будут слаться уведомляющие SMS не нужно перекомпилировать программу. Достаточно послать на модуль смску с сообщением "Firstnumber" (без ковычек) и номер, с которого была отправлена эта команда, записывается в энергонезависимую память микроконтроллера.

Vassilis Serasidis

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

Основные характеристики устройства:

  • управление 4 реле (вкл./выкл.);
  • возможность отслеживания состояния реле и 8 цифровых входов для дальнейшей отправки SMS пользователю с целью информирования о текущем состоянии;
  • простая схема, небольшое количество используемых компонентов;
  • управление с помощью SMS. Команды управления защищены паролем (может быть изменен пользователем) с целью предотвращения ложного срабатывания.

Принципиальная схема устройства изображена на рис. 1.

Основой устройства является микроконтроллер ATtiny2313 корпорации и GSM модуль производства фирмы .

Микроконтроллер IC2 работает на частоте 4 МГц, которая задается внешним кварцевым резонатором X1.



Рис.2 Внешний вид GSM модуля GM-47

Для работы GSM модуля необходима SIM карта, которая подключается непосредственно к модулю с помощью специального держателя. Питание микроконтроллера и GSM модуля осуществляется от регулятора IC1 LM1117T 3.3 с выходным напряжением 3.3 В. Вообще, микроконтроллер сохраняет работоспособность в пределах 2.7 В - 5.5 В (при рабочей частоте до 10 МГц), поэтому для обеспечения согласования логических уровней GSM модуля и микроконтроллера мы можем запитать его от регулятора IC1.

Коммуникация с GSM модулем осуществляется на скорости 9600 бит/с с помощью AT команд. Стоит заметить, что уровни напряжения при данной коммуникации составляют 3.3 В со стороны микроконтроллера AVR и 2.75 В со стороны GSM модуля. Поэтому для адаптации уровней был применен транзистор T5 BC547 .

Модуль подключается с помощью коннектора на печатной плате.



Рис.3 Печатная плата с установленным коннектором под модуль GM-47

Подключение SIM карты осуществляется с помощью слота K15, который имеет встроенный концевой переключатель SW для обнаружения присутствия карты в держателе.

Управление реле осуществляется посредством ключей выполненных на транзисторах BC547


Рис.4 Внешний вид печатной платы с установленным модулем

Светодиод D6 предназначен для индикации статуса подключения к сети, и если он мигает, то это означает удачное подключение к сотовой GSM сети, которую поддерживает SIM карта. Если светодиод постоянно светится - это означает, что модуль не может подключиться к сотовой сети.

GSM модуль имеет цифровые и аналоговые входы/выходы, но в этом проекте автор их не использовал, чтобы исключить опасность повреждения модуля.

Какие задачи выполняет микроконтроллер AVR

После подачи питания на плату микроконтроллер ожидает пока пройдет инициализация GSM модуля, т.е. модуль должен считать SIM карту и подключиться к GSM сети, которую она поддерживает.

После удачной инициализации микроконтроллер посылает AT команду, что означает выбор памяти модуля в качестве хранилища SMS. Должен быть ответ модуля на эту команду, в противном случае команда посылается еще раз.

После выбора памяти микроконтроллер посылает следующую команду. Данная команда указывает модулю, что сообщения будут считываться в текстовом формате (а не формате PDU, который также поддерживается модулем).

Затем следует команда, благодаря которой из текста SMS сообщения будет удаляться некоторая информация, например номер SMS сервера, дата и время. Это сделано с целью уменьшения SMS и упрощения работы микроконтроллера с ними.

Следующая команда предназначена для чтения SMS, сохраненного по первому адресу в памяти модуля.

При наличии текста SMS микроконтроллер считывает его и проверяет наличие корректного пароля. По умолчанию пароль - 1234, который затем может быть изменен пользователем. После проверки пароля проверяется наличие символа «*», который означает смену пароля на следующие после символа «*» 4 цифры (буквы).

После этого SMS обрабатывается далее с целью обнаружения зарезервированной команды где X - означает номер реле (1-4), Y - команда вкл./выкл. реле, может принимать значения 1 (вкл.) или 0 (выкл.). Например, команда Relay2=1 означает включить реле №2.

После этого микроконтроллер обрабатывает SMS далее на предмет наличия команды Status , и при ее наличии считывает состояние восьми цифровых линий и состояния всех реле и отсылает SMS с текстовым сообщением о состоянии контроллируемых линий на номер, с которого пришла SMS-команда. При этом не забудьте, что на SIM карте для отправки SMS должны быть средства.

После всех этих операций микроконтроллер удаляет SMS сообщение находящееся по первому адресу в памяти модуля и переходит к ожиданию получения следующего SMS-сообщения.

Посылка команд с помощью SMS с мобильного телефона осуществляется с соблюдением определенного синтаксиса. Рассмотрим его на примере команд:

  1. Команда: 1234*5678 Relay1=1 Relay2=0 Relay3=1 Relay4=1 Status
    Здесь мы имеем самую насыщенную команду. Сначала мы посылаем пароль (1234) и указываем, что он будет сменен (*) на 5678. Затем мы включаем реле №1, 3, 4 и выключаем реле №2. Кроме того, затем посылая команду мы запрашиваем информацию о состоянии 8 датчиков и всех реле.
  2. Команда: 1234 Relay1=1 Relay2=0 Relay3=1 Relay4=1 Status
    В этой SMS-команде мы включаем реле №1, 3, 4, выключаем реле №2 и запрашиваем информацию о состоянии датчиков и реле.
  3. Команда: 1234 1=1 2=0 3=1 4=1 Status
    Данная команда аналогична рассмотренной команде 2), здесь мы опустили слова.
  4. Команда: 1234 Status
    При помощи мы только запрашиваем информацию о состоянии датчиков и реле.
  5. Команда: 1234 Relay2=0
    В этой команде, как видно, мы только отключаем реле №2

Принципиальная схема, рисунок печатной платы, исходный код (AVR ассемблер) - .

Для комментирования материалов с сайта и получения полного доступа к нашему форуму Вам необходимо зарегистрироваться .

  • а возможно ли использовать вместо SM модуля GM-47 мобильник,по моему мобильник легче достать и дешевле
  • Таких модулей и нет в продаже. А так интересное устройство. Вообще здесь много интересных вещей печатают, если бы ещё и всё это доступно было бы нам...
  • Управление посредством SMS возможно с использованием GSM модема или телефона, используемого в качестве модема, подключенного к компьютеру. Вас интересуют детали реализации? Или этот вариант с применением компьютера для Вас слишком громоздок!? Можно использовать микро PC или контроллер совместимого типа с GSM модулем, этот вариант компактнее. Так что упоминаемые выше специализированные устройства, это и есть по сути GSM модем + компьютер, можно реализовать и самостоятельно из более широко доступных компонентов.
  • Можно, я так думаю, использовать совместимые модули, у которых система команд совпадает...
  • В GSM модулях и мобильных телефонах для управления и контроля используется специализированные АТ команды, набор которых, в основном, для различных фирм изготовителей и различных подобного рода устройств один и тот же, и в зависимости от специализации устройства и особенностей набор команд включаются дополнительные спец команды. Это устройство можно переделать практически под любой GSM модуль или мобильный телефон. Делаем на плате разъем управления, которое осуществляется по 2-х проводному интерфейсу UART, вместо 20 – 40 ног для модема, и немного правим исходный код АSM, который нам доступен (что может даже и не понадобится!) ну и само собой под новый проект новая разводка платы. И получаем универсальное устройство управления и контроля.
  • Вот вариант реализации удалённого управления на доступном GSM модуле SIM300D - http://electromost.com/index/mnogofu...kontrolja/0-35 При использовании SMS есть один момент - доставка SMS оператором по времени не нормируется. Поэтому управлять ответственными устройствами таким способом не рекомендуется. Кроме того, в обязательном порядке нужно отслеживать подтверждение выполненной команды - иначе "пульнули" SMS и неизвестно - выполнена команда или нет:). Поэтому при использовании сотовой связи управлять нагрузками нужно в "режиме реального времени" с подтверждением выполненых команд. Например, использовать GPRS. Или хотя бы DTMF - как в устройстве, ссылку на которое давал выше.
  • Господа, всем доброго времени суток! Кто-нибудь пробовал собирать сей девайс? Мои попытки с использованием модуля Neoway M590 не увенчались успехом. После чтения принятого СМС микроконтроллер делает паузу на пару секунд, затем удаляет его из памяти и продолжает посылку в модуль АТ-команды по циклу. При этом не происходит ни изменений состояния реле, ни отправки сообщения по команде "Status". У кого-нибудь есть мысли по этому поводу?
  • Пошивка устройства нерабочая. Я тоже собирал такой девайс на плате с оригинальной разводкой, и с GR-47. Реакция такая же как и у Вас. Также читал на одном западном форуме о подобной проблеме этого девайса. Чтобы не ковырять листинг на асме, переписал на CodeVision AVR, при этом ввел оптимизацию: не постоянно гонять цикл опроса, а в начале работы с модемом отправить команду на выдачу в терминал сообщения о приходе смс, и дальше парсить смс после прихода сообщения о получении.
  • Вот и я перерыл практически весь интернет в поисках правды, и даже писал автору Serasidis Vasilis с просьбой помочь разобраться (на английском, естественно), однако так ничего и не добился. Как мне кажется, засада тут кроется в различии телефонных номеров наших и забугорных. Из листинга программы видно, что у них этот номер на одну цифру больше, соответственно, необходимо везде корректировать параметр регистра "No_Of_ignore_bytes" (R25). Хотя, могу и ошибаться. На одном из профильных сайтов поднималась эта проблема в точности как и у нас, и похоже, ее там благополучно решили, но каким именно образом, к сожалению, умалчивается. Зарегистрироваться на этом сайте, чтобы пообщаться с участниками темы тоже не получается - отфутболивают без разъяснений, сразу на этапе регистрации. Вот ссылка: http://www.edaboard.com/thread290544.html Уважаемый max7780, если у Вас устройство заработало, не поделитесь программой? Был бы очень Вам признателен, поскольку мои познания в программировании не позволяют мне написать такую сложную программу с нуля ни на асме, ни на СИ, а ковырять имеющуюся я уже просто мозг сломал за два месяца.
  • Устройство собирал 5 лет назад, если найду, то возможно завтра выложу исходник. Но там реализованы не все функции, например не делал команду status, которая читает состояния входов, и нет гарантии что программа заработает с Вашим модемом, возможно есть какие - то отличия в ответах на команды или в самих командах. Также в оригинальном исходнике отсутствует анализ ответа модуля, модем может сообщить об ошибке, а программа продолжит выдачу команд, либо модем может банально зависнуть, а микроконтроллер просто не сможет его перезагрузить, так как на оригинальной плате отсутствует управление PowerPin-ом модуля. Я проанализирую Datasheet на Ваш модуль и помогу, чем смогу. Также хотелось бы сказать что 590-й - редкостная дрянь, три модуля купил, только один нормально заработал без глюков. При переделке софта не стояла задача обеспечить безотказную работу устройства гарантировано в течении длительного времени, а просто запустить железку, также много неоптимального кода, лучше я перешлю Вам эту программу на электронную почту.
  • У меня из двух приобретенных модемов 590-х тоже заработал нормально лишь один, второй шлет в эфир всякий мусор, который видно на терминале. Пробовал подбирать скорость - бесполезно. А второй работает четко на скорости 9600, но с микроконтроллером дружить не хочет почему-то, хотя, тут мы уже выяснили, что дело скорее всего в самой программе. Однако, для меня все равно остается загадкой почему у одних она работает, а у других нет. Вроде у GM47 и NEOWAY полностью совпадают протоколы АТ-команд, единственное отличие - у Neoway нет порта под микрофон, соответственно - невозможно реализовать голосовой вызов. А схема и контроллер у Вас остались прежними, или изменились? Да я буду рад любому, даже "сырому" решению, ведь потом его уже можно доработать как положено. Главное - это основа. Так что буду безмерно благодарен, если отправите прогу на адрес [email protected], тогда уже можно будет двигаться дальше в этом направлении, потому как сейчас я просто зашел в тупик...

Итак, после продолжительного времени раскуривания тонкостей работы с GSM модулем SIM900D анонсируем первый рабочий проект, совмещающий в себе охранную систему с возможностью удаленного контроля. Если кратко, то устройство способно отправлять информирующие SMS в случае срабатывания датчика проникновения, делать дозвон для возможности аудиоконтроля помещения, следить за температурой и отправлять ее смс-кой по запросу, а также управлять какой-нибудь нагрузкой по команде отправленной по смс.

Кто следил за данной темой, тот в курсе, что у меня GSM модуль и модуль управления им – две разные платы, соединенные бутербродом (см. плата с SIM900D и плата управления). На управляющей плате помимо микроконтроллера ATmega32a стоит модуль питания, выполненный на преобразователе LM2596 , он запитывает схему постоянным напряжением 3,5 вольт. В принципе подойдет любой другой источник питания, главное чтобы он был способен кратковременно вытянуть до 2 ампер (именно такое потребление GSM-модуля в момент регистрации).

Удобства ради, к плате управления подключен дисплей от телефона Nokia3310, методы работы с котором уже ни раз описывались на этом сайте. Благодаря дисплею можно быстро определить состояние устройства и значение датчиков.

В итоге получившаяся схема подключения вышла такая (кликабельно):

Нумерация выводов микроконтроллера на схеме приведена для DIP корпуса, поэтому если повторяете схему с использованием мк в корпусе TQFP будьте внимательны, нумерация выводов у него отличается. Тактируется микроконтроллер от внешнего кварца на 16 МГц.

Линия Control идущая от коллектора транзистора Q2 к выводу PortD.4 микроконтроллера добавлена для перестраховки и нужна за тем чтобы следить включен ли модуль. Так как порог выключения у SIM900 составляет 3,2 вольта то даже при незначительной просадке напряжения модуль автоматически выключится, тогда как микроконтроллер продолжит работать и выполнять программу (порог сброса у ATmega32a 2,7 вольта). В рабочем состоянии на этой линии находится низкий уровень. Если микроконтроллер обнаружит что на этой линии высокий уровень, выполнится функция повторного запуска GSM модуля.

А вот так это выглядит в работе на данный момент.

После окончательной обгонки программы, все это будет засунуто в корпус, а разъемные соединения для надежности будут запаяны.

На дисплей выводится основная информация о состоянии устройства: название оператора, качество сигнала связи, значение температуры с датчика 18b20, состояние выхода нагрузки и датчика проникновения, а так же время и дата.

Видео включения модуля

Время и дата берутся от встроенных в GSM-модуль часов. Для их работы обязательно наличие 3-х вольтовой батарейки подключенной к выводу 15 (VRTC). Диод D1 рекомендуется ставить с низким падением напряжения, например Шоттки. Настройка часов и даты делается в ручную, команды были описаны ранее

Дата выводится на дисплей в том формате как получается с модуля, тоесть сначала год, затем месяц и дата. Здесь пока ничего менять не стал.

За измерение температуры отвечает датчик DS18B20, он подключается к выводу PortD.3 микроконтроллера.

К PortD.6 можно подключить какую-нибудь нагрузку и управлять ей посредством команд смс. У меня сейчас висит светодиод – D4 на схеме. Но ничего не мешает повесить сюда релюху или симистор и управлять чем-нибудь посерьезней.

В охранных целях планируется применение датчика движения HC-SR501 , купленного на E-bay. В случае срабатывания на выходе датчика появляется логическая единица. Поймав ее, микроконтроллер даст команду на отправку SMS сообщения по телефонному номеру, заданному в программе.

Выход датчика подключается к выводу PortD.7 микроконтроллера, на схеме, датчик условно заменен на кнопку.

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

Для того чтобы предотвратить многократное отсылание предупреждающих смс в случае срабатывания датчика, в программу введено ограничение: после первого отправленного смс ставится запрет на последующую отправку. Чтобы заново разрешить отправку уведомляющих сообщений при срабатывании датчика, необходимо отослать на модуль смс с определенной командой. Когда посылка смс запрещена на дисплей возле состояния датчика, выведется восклицательный знак.

Список команд

А вот и список команд в смс которые обрабатывает модуль. Для удобства и простоты комады цифровые, возможно в следующих версиях прошивки будут более осмысленные имена команд 🙂

0 – Отключение нагрузки (на выводе PortD.6 выставляется логический 0)

1 – Включение нагрузки (на выводе PortD.6 выставляется логическая 1)

2 – Приняв эту команду, модуль перезвонит на указанный в программе телефонный номер

3 – Запрос баланса и отправление его смс-кой обратно на указанный номер. Здесь есть один важный нюанс – ответы на USSD запросы обязательно должны приходить в латинице. Иначе заместо осмысленного текста в ответ придет сообщение в шестнадцатеричной кодировке. Как перевести USSD в латиницу нужно уточнить у своего оператора. К примеру, на используемой мной симке от Смартса, нужно ввести *102*1# (в мегафоне *105*0#)

4 – Запрос температуры. Значение температуры будет отправлено нам в смс.

5 – Разрешенить отсылать сообщения в случае срабатывания датчика проникновения.

6 – Запрет на отправление уведомляющих смс от датчика проникновения.

? – По этой команде модуль пришлет нам смс, в котором находится общая информация об устройстве, такие как значение с датчика температуры, включена ли нагрузка, состояние на входе от датчика проникновения и разрешена ли отправка уведомляющих смс от него. К примеру, вот как может выглядеть такое сообщение: температура +24, нагрузка выключена, на выходе датчика движения 0, отправка смс в случае срабатывания запрещена.

Теперь как настроить чтобы модуль отправлял sms именно на ваш номер. В архиве с программой находим основной файл программы, она так и называется “программа” 🙂 и находим в ней константу:

Const Phonenumber = “+7908390хххх”

подставляем сюда свой номер телефона, компилируем программу и получаем hex файл прошивки.

Программа как и всегда написана в Bascom-AVR, поэтому разобраться с алгоритмом работы с GSM модулем достаточно просто. Удачи!

Ну и напоследок демонстрация того как модуль обрабатывает команды.

Отдельное спасибо за участие и помощь в разработке, давнему товарищу сайта Сергею RD3AVJ!

UPD: от 31.10.12

Немного доработал прошивку, теперь для того чтобы задать номер на который будут слаться уведомляющие SMS не нужно перекомпилировать программу. Достаточно послать на модуль смску с сообщением “Firstnumber” (без ковычек) и номер, с которого была отправлена эта команда, записывается в энергонезависимую память микроконтроллера.

Идея проекта: спроектировать устройство на базе микроконтроллера AVR для управления готовым GSM модулем (я выбрал модуль TC35 от SIEMENS, но можно использовать любой другой, если используется связь через последовательный порт RS232). Устройство должно быть компактным, минимально простым и надёжным.

Отправка заранее записанного в память сообщения на указанный номер должна выполняться после нажатия кнопки. Всего нужно было 6 кнопок для отправки на 6 различных номеров. Для индикации процессов были выбраны 3 светодиода (Ready, Send, Error), но в последствии был добавлен алфавитно цифровой LCD 16x2 (скорее, для отладки устройства, чем для обычного использования).

Проектировалось всё дело на плате Pinboard II (Rev 2) со стандартным процессорным модулем на ATmega16. На готовом устройстве схема была немного другой (и микроконтроллер использовался ATmega8). Программа писалась в AVR Studio 4.19. В проекте были использованы различные заголовочные файлы (#include) для переключения между Pinboard и готовым устройством.

Общая схема системы:


Для контроллера была выпилена такая платка:

Времени было много, поэтому в последствии я заказал платы у китайцев:

А когда с железом было закончено, следом пошёл процесс программирования. Всё написано на Си под AVR Studio 4.19. Полный проект выкладываю в конце статьи, если кому интересен полный код. Но пока поговорим об общении с GSM модулем.

Полный перечень AT команд есть на каждый модуль в его документации. Но отправка сообщения происходит несколькими командами.

//команда: AT+CMGF=1 //ответ модуля: OK
Переводит модуль в текстовый режим. Цифровой режим я пока не освоил (пока не было необходимости). Ответ модуля на начальных стадиях проекта никак не использовался. Но потом (когда был написан дешифратор команд) служил условием продолжения отправки или сообщения об ошибке протокола. Идём дальше:

Команда: AT+CMGS=(номер телефона) ответ модуля: > отправляем сообщение: Hello, GSM module! ответ модуля: +CMGS: 62 OK
После набора сообщения, нужно отправить не Enter (0x0D) а CTRL-Z (0x1A). Ответ модуля после отправки содержит порядковый номер отправляемого сообщения.

Для отправки команд в модуль в модуль и получения ответов я использовал два кольцевых буфера со входящими и исходящими индексами.

Для большей понятности кода приведу заголовки:

#define BUF_SIZE 128 #define BUF_MASK (BUF_SIZE-1) #define IN_BUF_SIZE 64 #define IN_BUF_MASK (IN_BUF_SIZE-1) volatile char buffer=""; volatile char inbuf="$"; //inner buffer of USART volatile uint8_t ind_in=0, ind_out=0, rxind_out=0, rxind_in=0, mess = 0;
Запись строк или отдельных символов в буфер производилась обычными функциями:

//sending RS232 with interupt void SendByte(char byte) { buffer = byte; ind_in &= BUF_MASK; } void SendStr(char *string) { while (*string!="\n") //check if End { SendByte(*string); string++; } }
А отправка производится через обработчик прерывания:

//Sending data from buffer ISR (USART_UDRE_vect) { UDR = buffer; //запись из буфера ind_out &= BUF_MASK; //проверка маски кольцевого буфера if (ind_in == ind_out) //если буфер уже пуст { UCSRB &= ~(1< Теперь для отправки нужно записать нужную команду в буфер (включая конечный символ \n), а затем включить прерывания опустошения регистра отправки (UDR):

SendStr("AT+CMGF=1\n"); SendByte(CR); //отправляем (0x0D) UCSRB &= ~(1< Пока идёт отправка, можно отправить надпись на LCD или просто подождать (delay).
Писать в это время в буфер нельзя. Опытным путём обнаружил, что модуль не успевает обработать сплошной потом команд. А остановка происходит, когда буфер пуст (входящий и исходящие индексы равны).

И таким образом мы отправляем сообщение. В зависимости от нажатой кнопки (в главном цикле я сканирую порт) происходит отправка сообщения:

While (1) { tmp = PINC; switch (tmp) { case 1: send_sms(0,NUM1); break; case 2: send_sms(0,NUM2); break; case 3: send_sms(0,NUM3); break; //и так далее... default: break; } Ready_Snd (); //перевод обратно в режим готовности }
В функцию отправки я посылаю номер выбранного сообщения (их у меня 2 типа) и номер телефона.
Можно даже отправить команду на звонок теми же AT командами. Всё зависит от необходимой функции.

Теперь о получении команд с модуля.

Модуль отправляет множество команд. Например, OK, RING, ERROR…
Иногда нужно, чтобы при получении команды контроллер смог опознать её и выполнить какое-то действие. Например, получен входящий звонок. Модуль при этом отправляет в контроллер:

RING RING RING
В зависимости от настроек модуля, может отправлять ещё и номер того, кто звонит. Пока нет никакой программы, контроллер ничего с этим сделать не сможет (в лучшем случае) или (в худшем) сделает что не то, а то и вовсе зависнет (не сможет выйти из прерывания).

Требования к коду обработки:
1. Минимальное количество времени на сохранение полученных команд. Никаких задержек в программе прерывания быть не должно. Потом уже с полученным массивом будем делать что угодно.

2. Сохранение всех полученных команд в одном буфере. Для разделения отдельных будем использовать символ $.

3. Распознавание распространенных команд в числовые коды. Например, OK будет 1, ERROR - 4, RING - 2.

Приведу заголовки из предыдущей статьи с поправками:

#define BUF_SIZE 128 //Исходящий буфер #define BUF_MASK (BUF_SIZE-1) #define IN_BUF_SIZE 64 //Входящий буфер #define IN_BUF_MASK (IN_BUF_SIZE-1) volatile char buffer=""; volatile char inbuf="$"; //inner buffer of USART volatile uint8_t ind_in=0, ind_out=0, rxind_out=0, rxind_in=0, mess = 0; volatile uint8_t com_detect=0; //сюда будет записана обнаруженная команда #define TIMEOUT 100 //на случай если команда так и не принята
Пишем обработчик прерывания приёма данных:

//recieving Data from RS232 ISR (USART_RXC_vect) { uint8_t tmp; tmp = UDR; if (tmp == 0x0D) //получен конец команды - { mess++; //one more message inbuf = "$"; //вставляем разделитель в буфер rxind_in &= IN_BUF_MASK; } else { if (tmp != 0x0A) //очистка непонятного символа с модуля { inbuf = tmp; //записываем в буфер rxind_in &= IN_BUF_MASK; } } sei (); }
Теперь у нас все команды записаны в буфере. Можно в свободное время проверить переменную mess и если она не равна нулю - запустить обработчик команды. В самом проекте были добавлены команды для LCD экрана. Здесь я их пропущу за ненадобностью.

Void rx_check_in (void) { uint8_t count=0; com_detect = 0; //обнуление команды (чтобы не мешал предыдущий мусор) while (1) { if (inbuf != "$") //обнаружен конец команды (разделитель) { com_detect ^= inbuf; //делаем XOR полученным символам rxind_out &= IN_BUF_MASK; count++; //считаем, сколько символов в команде } else { rxind_out++; rxind_out &= IN_BUF_MASK; code_com (count); //!! важная часть - раскодировать команду break; } } }
Полученные символы мы пропускаем через мясорубку. Делаем XOR операцию. Получаем таким образом уникальный код (не уверен на счёт уникальности, но пока не подводило). R^I^N^G нам даст 0x12. O^K даст 0x04. Этот код и количество символов (в команде) сохранены в переменных com_detect (глобальная) и count. Теперь запустим обработчик:

Void code_com (uint8_t count) { switch (com_detect) { case (0x12): if (count == 4) com_detect = 2; break; //R^I^N^G case (0x58): if (count == 5) com_detect = 3; break; //ERROR case (0x04): if (count == 2) com_detect = 1; break; //OK case (0x5C): if (count == 3) com_detect = 4; break; //ATI default: com_detect = 0; } }
Распознали команду. Количество символов я ввёл для надёжности на случай если в длинной команде XOR код совпадёт. Распознаваемые команды можно добавлять. Нужно только подсчитать (или макросом) XOR код желаемой команды и присвоить ей цифру.

Теперь в com_detect у нас полученная команда. Теперь устройство может отреагировать SMS сообщением на полученный звонок:

While (1) { if (mess != 0) //if we have mess in buffer { // code mess--; //minus one rx_check_in (); //распознаём отдельную команду if (com_detect == 2) //если была команда RING (код 2) { //Посылаем сообщение // и принимаем входящие команды (OK) if (!send_sms (1,NUM0)) ErrMes (); //если после отправки не было команды OK } //тогда выдать сообщение о ошибке протокола com_detect = 0; //обнуляем команду }
Так можно обрабатывать разные полученные команды.

Итог: устройство умеет отправлять сообщение на телефон и умеет реагировать на различные команды от GSM модуля.

Спасибо за внимание.