Menu
Элементы умного дома на OpenWRT роутере

Элементы умного дома на OpenWRT роутере

В наличии имеется китайский GL.inet роутер, USB хаб, камера и GSM модем.

Задача: на удаленном объекте с плохой связью настроить видеонаблюдение и элементы управления и мониторинга.

Для прочих свистелок имеем дома или где-то (есть бесплатные хостинги) настроенный  WWW(для просмотра снэпшотов),FTP(удаленно складывать снэпшоты),openvpn(не обязательно, рулить удаленно).

Как настроить на роутере SSH и зайти, в текущей статье рассматриваться не будет, так как путей сделать это много. В данном роутере первоначальную настройку я делал в Luci, зайдя по адресу http://192.168.8.15/cgi-bin/luci/

Добрый совет: при настройке SSH, расшарьте его наружу, если требуется удаленное управление, и смените его порт на некий другой, чтобы не соблазнять интересующихся. (С 22 на 2222 например)

Подключаемся к LAN порту роутера по SSH:
(я использую ubuntu, если у вы любитель windows - ваш путь - putty +)

ssh -p2222 -lroot 192.168.8.1
root@192.168.8.1's password:
root@openwrt:~#
root@openwrt:~# uname -a
Linux openwrt 3.18.23 #6 Mon Jan 4 11:55:23 HKT 2016 mips GNU/Linux

 

 MOTION

Motion выбран по причине его гибкости настроек, хотя под такую задачу можно было выбрать что-то по проще, типа mjpeg-streamer. Motion будет сохранять снэпшоты по движению и раз в 5 минут, так как канал плохой и процессор не силен.

 Обновляем список пакетов:

opkg update

 Устанавливаем поддержку USB модема:

 opkg install kmod-usb-serial kmod-usb-serial-wwan kmod-usb-serial-cp210x kmod-usb-serial-option

 При удачной установке должны появиться /dev/ttyUSB0 и тд.

Устанавливаем поддержку USB камеры (всяких, для верности) (список - https://wiki.openwrt.org/doc/howto/usb.video):

 opkg install kmod-video-core kmod-video-gspca-core kmod-video-uvc kmod-video-gspca-zc3xx kmod-video-gspca-sonixj kmod-video-gspca-sonixb 

При удачном определении камеры должно появиться устройство /dev/video

Устанавливаем motion (нужно удалить или остановить предустановленные видео-сервисы, если есть):

opkg install motion wput

Конфигурируем /etc/motion.conf:
(желательно, чтобы логи, pid'ы, jpg'и он складывал в /tmp, чтобы продлить жизнь флэш-памяти)

Примерный конфиг моего /etc/motion.conf. Не забудьте исправить логины и пароли.

создаем скрипт отсылки снэпшотов:

find /tmp/motion/ -name 'video_????????????????????.jpg' > /tmp/dvrdir.lst
cd /tmp/motion/
ls -t | grep -v \/ | head -n 1 | while read var; do echo "$var"; cp $var /tmp/lastsnap.jpg; done
wput -R -i /tmp/dvrdir.lst ftp://ftpuser:ftppassword@server_addr/ddvr/jpgs/

создаем расписание в /etc/crontabs/root для отсылки снэпшотов

*/5 * * * * /etc/motion/wput_dvr.sh

Таким образом получилась схема отправки снэпшотов на удаленный сервер. Можно остановиться на этом, а можно дописать визуализация и формирование видео.

 

GPIO

В GL.Inet6416 их всего 5 (GPIO18-GPIO22). Не так много, как в raspberry, зато дешевле. С помощью них можно управлять внешними устройствами, контролировать замыкание контактов и снимать данные с некоторых сенсоров. Есть другие модели бюджетных роутеров, у которых разведены GPIO, отдельно, на кнопки и светодиодную индикацию. 

GL.Inet GPIOСхема разводки выходов GPIO и др на GL.Inet

GPIO (General Purpose Input Output) - низкоуровневый интерфейс ввода-вывода прямого управления.

GPIO базовое включениеБазовая схема подключения к GPIO. VCC - 3.3.V.

GPIO relay
Схема включения реле.

В моей реализации мониторинг и управление осуществляется связкой Bash-скрипта (демон бэкэнд) и PHP-скрипта (фронтэнд). Два порта будут заведены на сухой контакт (герконы), два - на реле, один - на 1-wire.

Основной принцип работы с GPIO:

Установка ввода - in, или вывода - out порта:

echo in > /sys/class/gpio/18/direction

Чтение состояния порта:

cat /sys/class/gpio/18/value

Запись состояния:

echo 1 > /sys/class/gpio/18/value

Вывод информации о GPIO:

cat /sys/kernel/debug/gpio

В некоторых моделях есть управление питанием USB: (keenetic kn-1211,

echo 0 > /sys/class/gpio/usbpower/value

Устанавлваем lighttpd, php,bash и тд:

opkg install lighttpd lighttpd-mod-auth lighttpd-mod-cgi lighttpd-mod-expire lighttpd-mod-fastcgi php5 php5-cgi php5-mod-curl 

Конфигурируя всё это нужно постараться оставить рабочим Luci, если оно вообще было и нужно.

Примерный конфиг /etc/lighttpd/lighttpd.conf:

# version=3.0
server.modules = (
"mod_cgi",
"mod_auth",
)

server.network-backend = "write"
server.error-handler-404="/welcome.html"
server.document-root = "/www/"
server.pid-file = "/tmp/run/lighttpd.pid"
server.errorlog = "/tmp/log/lighttpd/error.log"

index-file.names = ( "welcome.html","login.html","index.php","index.php" )

$HTTP["url"] =~ "\.html" {
expire.url = ( "" => "access plus 1 seconds" )
}


##
# which extensions should not be handle via static-file transfer
#
# .php, .pl, .fcgi are most often handled by mod_fastcgi or mod_cgi
#static-file.exclude-extensions = ( ".php", ".pl", ".fcgi" )

######### Options that are good to be but not neccesary to be changed #######

## bind to port (default: 80)
server.port = 80

server.upload-dirs = ( "/tmp" )

fastcgi.server = (
"/cgi-bin/download_file" => (
"download_file.handler" => (
"socket" => "download_file.socket",
"check-local" => "disable",
"bin-path" => "/www/cgi-bin/download_file",
"max-procs" => 1,
"allow-x-send-file" => "enable"
)
)
)
#### CGI module
$HTTP["url"] =~ "^/cgi-bin/" {
cgi.assign = ( "" => "" )
}

include "/etc/lighttpd/mime.conf"
include_shell "cat /etc/lighttpd/conf.d/*.conf"

# Access control

#auth.backend = "htpasswd"
#auth.backend.htpasswd.userfile="/etc/lighttpd/lighttpd-htpasswd.user"
#auth.require = ( "/files" =>
# (
# "method" => "basic",
# "realm" => "files",
# "require" => "user"
# )

/etc/lighttpd/conf.d/10-cgi.conf

server.modules += ( "mod_cgi" )
cgi.assign = ( ".pl" => "/usr/bin/perl",
".cgi" => "/usr/bin/perl",
".rb" => "/usr/bin/ruby",
".erb" => "/usr/bin/eruby",
".py" => "/usr/bin/python",
".php" => "/usr/bin/php-cgi" )

Также в php.ini нужно указать корневую директорию, временную - в /tmp и желательно подкрутить timezone.

 В конечном итоге должно получиться следующее:

gpio php controller

 Скрипты и картинки для управления и мониторинга GPIO

Основная логика состоит в создании флагов в /tmp. Фронтэнд создает флаг состояния реле, а бэкэнд реализует его. И наоборот, бэкэнд выставляет флаг срабатывания датчика, а фронтэнд выводит его. Вся конфигурация GPIO происходит в скрипте бэкэнда, и интуитивно понятна. В коде бэкэнда заремирована возможность отправки СМС через gnokii или отправки e-mail через msmtp, предварительно установив их и сконфигурировав.

 

1-wire

1-wire -  двунаправленная шина связи для устройств с низкоскоростной передачей данных. То есть в идеале, имеется жила питания/данных и жила земли. В одной сети могут находится некоторое, в зависимости от удаленности и потребления, количество ведомых (slave) устройств и одно ведущее (master) устройство. В моем случае мастером будет выступать GPIO с драйвером 1w из ядра. Покупка USB мастеров достаточно накладна, но сильно уменьшает количество проблем со slave устройствами, сложнее термодатчиков, но это не наш путь. Устанавливаем поддержку 1-wire на GPIO:

opkg install kmod-w1 kmod-w1-gpio-custom kmod-w1-master-gpio kmod-w1-slave-therm

В данном случае буду использовать GPIO18, поэтому:

echo "w1-gpio-custom bus0=0,18,0" > /etc/modules.d/59-w1-gpio-custom
reboot && exit

ls /sys/bus/w1/drivers/w1_slave_driver/
28-000000483037 29-000000174f7c bind uevent unbind

, где  28-000000483037 - DS18B20 (цифровой датчик температуры), 29-000000174f7c - DS2408 (8-портовая микросхема ввода/вывода)

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

OpenWRT GPIO DS18B20

Схема включения DS18B20

 Считываем значение датчика:

 cat /sys/bus/w1/drivers/w1_slave_driver/*/w1_slave
a0 00 4b 46 7f ff 10 10 53 : crc=53 YES
a0 00 4b 46 7f ff 10 10 53 t=10000

Температура это значение t=10000, то есть 10.00 гр.С. Делим температуру на 1000:

awk -F= '/t=/ {printf "%.02f\n", $2/1000}' /sys/bus/w1/drivers/w1_slave_driver/*/w1_slave
(Для нескольких датчиков обращаемся конкретно по их ID.)

Есть возможность просматривать историю температуры в виде графика изменения.
Требуется установка curl и bash:

opkg install curl bash

Создаем св /etc/ bash cкрипт themp.update следующего содержания

#!/bin/bash
themp=$(awk -F= '/t=/ {printf "%.00f\n", $2/1000}' /sys/bus/w1/drivers/w1_slave_driver/*/w1_slave)
#testing only
#themp=$(( ( RANDOM % 35 ) - 15 ))
echo $themp
curl -k "http://1.1.1.1/themp-graph.php?p=12345&themp1=$themp"

,где 1.1.1.1 - IP или адрес домашнего сервера. Прописываем его запуск раз в 2 часа в /etc/crontabs/root:

3 0,2,4,6,8,10,12,14,16,18,20,22 * * * /etc/themp.update

На домашнем сервере требуется настроенный PHP с GD. Создаем PHP скрипт учета и построения графика

DS18B20 graph

 

DS2408


На текущем этапе мне, к сожалению, не удалось завести DS2408. Буду ждать обновлений. Но по идее должно работать так:

ls /sys/devices/w1_bus_master1/29-000000174f7c/

Считывание:
dd if=./rw bs=1 count=1 | hexdump

Запись:
echo -e '\x00' |dd of=rw bs=1 count=1
echo -e '\xff' |dd of=rw bs=1 count=1

 DS2408 рассматривалась как експандер портов ввода/вывода, однако для этой цели могут подойти аналоги MCP23017, но уже с использованием шины I2C.

В перспективе думается связать роутер по I2C с AVR и управлять, например светом, как с роутера по беспроводной связи или удаленно, так и с кнопок, установленных вмести выключателей. Таким образом должна будет осуществлена некая защита управления от выхода из строя роутера со всей обвязкой, и лавный контроль управления ложится на AVR. Но об этом позднее...

Возможные проблемы при настройке OpenWRT

 * Из webLUCI при настроенной системе нельзя сменить внутренний IP интерфейса и DHCP:

Сделать это можно в консоли:

uci set network.lan.ipaddr='192.168.2.1'
uci commit
/etc/init.d/network restart

Далее исправить правила фаервола и статических адресов


Ilya L. / 2016