OpenWRT
Installation von FHEM incl. OpenWRT auf einem Router/Kleinstcomputer z.B. TP-LINK MR3020
Wer nicht unbedingt eine Fritz!Box braucht sondern einfach nur FHEM ohne laufenden PC betreiben will, kann auch OpenWRT auf einem Router nutzen, z.B. dem sehr günstigen (25 Euro März 2012) und stromsparenden (ca. 1 Watt) TP-LINK MR3020.
Bitte beachten: Es kann keine Garantie übernommen werden, dass der Router bei Befolgung dieser Anleitung "kaputt" geht, z.B. dadurch, dass er bei Fehlkonfiguration im Netz nicht mehr erreichbar ist. Der Umbau erfolgt auf eigene Gefahr.
Vorraussetzungen
- Der Router (in diesem Howto ist der TP-LINK MR3020 verwendet worden, OpenWRT wird aber prinzipiell immer gleich aufgesetzt
- Ein USB Stick, da die Flash-Speicher der Router zu klein sind
- optional ein passiver USB-Hub (wenn der Router nur einen USB Port hat und ein CUL Stick betrieben werden soll)
- Ein Linux-PC zum Erstellen des Images. Dies kann auch eine virtuelle Maschine sein. Der Autor hat Ubuntu 10.11 verwendet.
Vorbereiten des USB-Sticks
Auf einem USB Stick müssen zwei Partitionen angelegt werden, eine als Auslagerungsspeicher für den RAM und eine für das Dateisystem auf dem später auch Perl und FHEM installiert werden. Das geht am besten mit dem Tool fdisk
auf dem vorbereiteten Linux-PC. Dazu den Stick anstöpseln und per Aufruf von fdisk -l
die Lister der gefundenen "Festplatten" anzeigen lassen. Eine davon ist der USB-Stick, z.B. an seiner Größe zu erkennen (500Mb reichen locker aus). In der Ausgabe z.B. nach einer Zeile suchen, die sinngemäß so aussieht: Disk /dev/sdc: 484 MB, 484442112 bytes
. In diesem Fall ist der USB-Stick das Gerät "/dev/sdc".
Daraufhin kann fdisk für das Gerät aufgerufen werden. Detaillierte ANleitungen für fdisk finden sich im Internet. Vereinfacht ist folgender Vorgang auszuführen (alle Daten gehen auf dem Stick verloren!).
fdisk /dev/sdc o n p 1 1 +64M n p 2 (drei mal Enter drücken) t 1 82 w
Danach ist der Stick partitioniert. Ein erneuter Aufruf von fdisk -l
sollte ungefähr folgendes ERgebnis liefern:
Disk /dev/sdc: 484 MB, 484442112 bytes 2 heads, 63 sectors/track, 7509 cylinders Units = cylinders of 126 * 512 = 64512 bytes Disk identifier: 0x8c5e341e Device Boot Start End Blocks Id System /dev/sdc1 1 993 62527+ 82 Linux swap / Solaris /dev/sdc2 994 7509 410508 83 Linux
Jetzt müssen die Partitionen noch formatiert werden. Vorsicht: Nur hier heisst der Stick /dev/sdc. Er kann auch anders heissen! Wenn ihr die falschen Namen verwendet, könntet ihr eure Festplatte löschen! /dev/sdc1 ist durch /dev/<euer-sdx>1 zu ersetzen
mkswap /dev/sdc1 mkfs.ext4 /dev/sdc2 sync
Der Stick ist nun fertig vorbereitet und wird im Linux-PC nicht mehr benötigt. Er kann jetzt in den Router
Bauen des OpenWRT-Images
Um OpenWRT zu bauen, müssen die entsprechenden Werkzeuge auf dem Linux-PC installiert sein. Unter Ubuntu geht das so:
sudo apt-get -y install subversion build-essential
OpenWRT kann am besten aus dem Subversion ausgecheckt werden.
svn co svn://svn.openwrt.org/openwrt/trunk openwrt
Das Auschecken dauert eine Weile, aber das ist noch gar nichts, das Bauen dauert noch viel länger. Sobald alles runtergeladen ist, wird in das Verzeichnis gewechselt und die Konfiguration vorgenommen
cd openwrt make menuconfig
Für die Konfiguration muss die Architektur des Routers bekannt sein. Diese kann auf der OpenWRT-Seite nachgeschlagen werden. der TP-LINK MR3020 hat eine ar71xx
-Architektur.
Als erstes also die ARchitektur auswählen (Hier: ar71xxx/ar91xxx
)
Zweitens kann beim Target-Profile zumeinst genau der Router ausgewählt werden (Notfalls auf der OpenWRT-Seite nachlesen)
Optional kann nun unter Image-Configuration
bereits eine Netzwerkkonfiguration eingestellt werden, die der Router dann nach seinem Hochfahren hat. Wenn der Router in ein bestehendes Netz mit bestehenden DHCP-Server und Adressraum eingebunden wird, ist das sinnvoll. Wer das hat, weiss auch, was hier einzustellen ist. Standardmäßig ist die Adresse 192.168.1.1 vorgegeben. Die Konfiguration kann auch später jederzeit geändert werden.
Nun zu den Kernel-Modules. Hier sollte folgendes aktiviert werden (Einiges ist ggf. nicht nötig, aber so geht es). Die Einträge müssen mit "*" und nicht mit "M" selektiert sein, sonst kommen sie nicht ins Image.
- Block-Devices
- kmod-ide-core
- kmod-ide-generic
- kmod-loop (kann man immer mal brauchen)
- kmod-scsi-generic
- kmod-fs-ext4 (davon wollen wir später booten, vom USB-Stick
- kmod-usb-acm (für CUL)
- kmod-usb-hid
- kmod-usb-ohci
- kmod-usb-serial
- kmod-usb-serial-ftdi
- kmod-usb-storage-extras
- kmod-usb-uhci
- kmod-usb2
Unter Utilities noch folgendes aktivieren
- Filesystem
- e2fsprogs
- fdisk (für Analysezwecke sinnvoll)
- swap-utils
Nun kann - in aller Ruhe - alles gebaut werden durch Eingabe von
make
Vorbereiten des Routers
Das ganze kann bis zu mehrere Stunden laufen. Nun ist Zeit, den Router ins Netzwerk einzubinden. Wie genau, hängt von derpersönlichen Konstellation ab. Der TP-Link MR3020 hat standardmäßig die IP-Adresse 192.168.0.254. Viele andere Router haben z.B. 192.168.0.1. Ich empfehle, das Update auf jeden Fall nicht über WLAN sondern ein Netzwerkkabel zu machen. Die meisten Router haben einen aktivierten DHCP-Server. Ein angestöpselter Windows-PC bekommt dann von ihm eine IP-Adresse zugewiesen. Beim MR3020 kann dann die Weboberfläche über http://192.168.0.254 erreicht werden. (User/Passwort: admin/admin)
Installation von OpenWRT auf dem Router
In der Weboberfläche des Routers gibt es irgendwo einen Menüpunkt zum Firmware-Upgrade. Beim MR3020 erreichbar unter System Tools / Firmware Upgrade. Sobald das Bauen von OpenWRT fertig ist, liegt das Image im Unterordner bin/<architektur>/. Es sollte das Image genommen werden, was den Namen des Routers sowie "squashfs" sowie "factory" im Dateinamen enthält. Dieses muss jetzt im Webinterface wie beschrieben ausgewählt werden und hochgeladen werden. Alle Bestätigungsmeldungen und "Wollen-Sie-Das-auch-Wirklich"-Fragen natürlich bestätigen.
Nach einer Weile sollte dann der Router unter 192.168.1.1 anpingbar sein (von Linux aus: ping 192.168.1.1
) bzw. unter der in der Image Configuration eingestellten IP. Wenn das nicht geht, kann man den Router auch ein 2. mal starten, da sollte man dann aber nach dem Flashen mal 10 Minuten Geduld haben (also Stecker raus/rein). Auf keinen Fall zu früh machen, dann könnte es sein, dass er gar nicht mehr hochfährt!
Zunächst muss man sich nun per telnet verbinden.
telnet 192.168.1.1
Nun ist man schon im OpenWRT eingeloggt. Das erste und einzige, was in diesem Login nun gemacht wird, ist, per
passwd
ein Passwort zu setzen. Danach kann man sich mit
exit
ausloggen. Nun kann man per SSH eine Verbindung herstellen, da ja jetzt ein Passwort gesetzt ist
ssh 192.168.1.1
Für den weiteren Verlauf ist es notwendig, dass der Router Internetzugang hat. Dazu muss man ggf. von Hand in der Datei /etc/config/network
die Netzwerkeinstellungen entsprechend anpassen.
vi /etc/config/network
Zur Bedienung von vi z.B. hier
Wichtig ist die IP-Adresse, die Netzmaske, das Gateway und der DNS-Server. Bitte genau auf Tippfehler achten. Bei einer fehlenden Konfiguration ist der Router nicht mehr erreichbar. Nach abspeichern kann die neue Konfiguration aktiviert werden
/etc/init.d/network restart
Falls sich auch die IP-Adresse geändert hat, mit ssh wie oben neu anmelden. Als nächstes soll der USB-Stick eingebunden werden, dazu sind einige Pakete zu installieren. OpenWRT hat einen eingebauten Paketmanager zur Nachinstallation von Software direkt aus dem Netz. Zunächst wird nur das installiert, was in den internen Speicher des Routers muss. Das Root-Dateisystem soll anschließend durch den USB-Stick erweitert werden, um dann dorthin die meiste Software zu installieren. Viele Details hierzu finden sich hier
opkg update opkg install block-mount
Bei einem Aufruf von
fdisk -l
sollte der an dem Router angeschlossene Stick bereits zu sehen sein (analog zu oben). Hiermit lässt sich dann auch rausfinden, wie das Gerät auf dem Router heisst. In den meisten Fällen dürfte dies /dev/sda
sein. In diesem Fall können wir nun das Dateisystem einbinden und dann die Dateien aus dem internen Speicher dorthin kopieren.
mkdir /mnt/sda2 mount /dev/sda2 /mnt/sda2 tar -C /overlay -cvf - . | tar -C /mnt/sda2 -xf -
Nun kann auch schon die Konfiguration so umgestellt werden, dass beim nächsten Neustart der USB-Stick mit ins Root-Filesystem eingebunden wird. Dazu ist die Konfigurationsdatei /etc/config/fstab
zu editieren.
vi /etc/config/fstab
Diese sollte danach ungefähr so aussehen, wobei das von Router zu Router abweichen kann. Der automatische Block für "home" kann bearbeitet werden und der Spap-Block ebenfalls auf (hier) /dev/sda1 angepasst werden
config global automount option from_fstab 1 option anon_mount 1 config global autoswap option from_fstab 1 option anon_swap 1 config mount option target /overlay option device /dev/sda2 option fstype ext4 option options rw,sync option enabled 1 option enabled_fsck 1 config swap option device /dev/sda1 option enabled 1
Nun kann die Konfiguration aktiviert und die Box mit eingestecktem Stick neu gestartet werden
/etc/init.d/fstab enable reboot
Nun sollte überprüft werden, ob der Stick richtig eingebunden ist
df -h
Die Ausgabe sollte sinngemäß folgende Zeilen enthalten
/dev/sda2 397.7M 19.8M 357.9M 5% /overlay overlayfs:/overlay 397.7M 19.8M 357.9M 5% /
Ist dies nicht der Fall, kann auf der OpenWRT Seite nach Troubleshooting-Möglichkeiten gesucht werden und dann hier fortgesetzt werden. Nachdem nun der Stick erfolgreiche eingebunden werden, können die ganzen Pakete installiert werden, die zum Betrieb von FHEM notwendig sind. Da dies eine Vielzahl der perlbase-Pakete ist, sind hier schlichtweg alle verfügbaren perl-Pakete installiert worden. Ebenfalls einige andere nützliche Werkzeuge. Speichermäßig ist das auf dem USB-Stick nicht entscheidend.
opkg update opkg install usbutils luci ntpclient uhttpd perl perl-compress-bzip2 perl-dbi perl-html-parser perl-html-tagset perl-html-tree perl-lockfile-simple \ perl-net-telnet perl-uri perl-www perl-www-curl perl-www-mechanize perlbase-abbrev perlbase-anydbm-file perlbase-archive perlbase-assert perlbase-attribute \ perlbase-attributes perlbase-attrs perlbase-autoloader perlbase-autosplit perlbase-autouse perlbase-b perlbase-base perlbase-benchmark perlbase-bigfloat \ perlbase-bigint perlbase-bignum perlbase-bigrat perlbase-blib perlbase-bytes perlbase-cacheout perlbase-cgi perlbase-charnames perlbase-class \ perlbase-complete perlbase-compress perlbase-config perlbase-cpan perlbase-cpanplus perlbase-ctime perlbase-cwd perlbase-data perlbase-db \ perlbase-db-file perlbase-dbm-filter perlbase-devel perlbase-diagnostics perlbase-digest perlbase-dirhandle perlbase-dotsh perlbase-dumpvalue \ perlbase-dumpvar perlbase-dynaloader perlbase-encode perlbase-encoding perlbase-english perlbase-env perlbase-errno perlbase-essential perlbase-exceptions \ perlbase-extutils perlbase-fastcwd perlbase-fatal perlbase-fcntl perlbase-feature perlbase-fields perlbase-file perlbase-filecache perlbase-filehandle \ perlbase-filetest perlbase-filter perlbase-find perlbase-findbin perlbase-finddepth perlbase-flush perlbase-gdbm-file perlbase-getcwd perlbase-getopt \ perlbase-getoptpl perlbase-hash perlbase-hostname perlbase-i18n perlbase-if perlbase-importenv perlbase-integer perlbase-io perlbase-ipc perlbase-less \ perlbase-list perlbase-locale perlbase-log perlbase-look perlbase-math perlbase-memoize perlbase-mime perlbase-module perlbase-mro perlbase-net \ perlbase-next perlbase-o perlbase-object perlbase-opcode perlbase-open perlbase-ops perlbase-package perlbase-params perlbase-perl5db perlbase-perlio \ perlbase-pod perlbase-posix perlbase-pwd perlbase-re perlbase-safe perlbase-scalar perlbase-sdbm-file perlbase-search perlbase-selectsaver \ perlbase-selfloader perlbase-shell perlbase-shellwords perlbase-sigtrap perlbase-socket perlbase-sort perlbase-stat perlbase-storable perlbase-switch \ perlbase-symbol perlbase-sys perlbase-syslog perlbase-tainted perlbase-term perlbase-termcap perlbase-test perlbase-text perlbase-thread perlbase-threads \ perlbase-tie perlbase-time perlbase-unicode perlbase-unicore perlbase-user perlbase-xsloader
Das Webinterface "Luci" ist mitinstalliert worden und bietet komfortable Einstellmöglichkeiten für den Router allgemein. Nach einem
/etc/init.d/uhttpd enable /etc/init.d/uhttpd start
ist es unter http://192.168.1.1/
bzw. der entsprechenden Router-IP erreichbar. Wichtig ist es ggf. den DHCP-Server zu deaktivieren. Die meisten Router können auch als WLAN-Clients konfiguriert werden, sie brauchen also nicht zwangsweise ein Netzwerkkabel. All dies geht über die Weboberfläche.
Nun kann FHEM auf den Router/Stick kopiert werden. In diesem Beispiel benutzen wir das SVN-Repository
opkg install subversion-client make libelf mkdir /usr/src cd /usr/src svn co https://fhem.svn.sourceforge.net/svnroot/fhem/trunk/fhem cd fhem make install-pgm2
Die Bearbeitung der /etc/fhem.cfg
ist nun so durchzuführen, wie bei jeder anderen FHEM-Installation auch. Wenn ein CUL-Stock am Router verwendet werden soll, dann geht dies über den Umweg ser2net, da das Device::Serial - CPAN Modul für OpenWRT nicht standardmäßig zur Verfügung steht
opkg install ser2net vi /etc/ser2net.conf
In der Datei kann alles gelöscht werden und dann genau diese Zeile eingefügt werden:
27073:raw:300:/dev/ttyACM0:115200 NONE 1STOPBIT 7DATABITS
In der fhem.cfg ist die Definition des CUL-Sticks dann folgendermaßen:
define MyCUL CUL 127.0.0.1:27073 3333
Wenn man CUL doch per Device::Serial ansprechen oder andere FHEM Module verwenden will, die auf Device::Serial angewiesen sind, kann man das entsprechende OpenWRT Paket auch selber erstellen. Hinweise dazu gibt es hier.
Nun muss nur noch der Autostart von ser2net und fhem eingebaut werden und die integrierte, stromsparende FHEM-Kiste ist fertig.
vi /etc/init.d/ser2net
mit folgendem Inhalt
#!/bin/sh /etc/rc.common # Ser2Net Init Script START=10 STOP=15 start() { ser2net } stop(){ killall ser2net }
Danach Ser2Net aktivieren und starten:
chmod +x /etc/init.d/ser2net /etc/init.d/ser2net enable /etc/init.d/ser2net start
Nun noch die Konfiguration für fhem selbst
#!/bin/sh /etc/rc.common # FHEM Init Script START=11 STOP=15 start() { /usr/bin/fhem.pl /etc/fhem.cfg } stop(){ echo "shutdown" | nc localhost 7072 }
Und auch hier aktivieren:
chmod +x /etc/init.d/fhem /etc/init.d/fhem enable /etc/init.d/fhem start
Da das ständige Schreiben 1. langsam und 2. den meisten USB-Sticks nicht gut tut, sollten die Logfiles ins RAM geschrieben werden, also ein Pfad unterhalb von /tmp
. Der Speicher ist allerdings begrenzt. Je nach persönlichen Anforderungen muss dann regelmäßig das Log aus dem Speicher gelöscht oder archiviert werden. Z.b. wöchentlich auf den USB Stick oder auf Netzlaufwerke etc. Dies ist mit dem FileLog von alleine möglich -> [1].