Arduino Yun cheat sheet

Arduino Yún / Arduino Yun

はじめに

Arduino Uno である程度なれたし、プロトタイプつくったので、そろそろ TCP/IP 喋る段階になって、技適もとれた Arduino Yun に挑戦してみた。

インターネットに接続して AWS 上にある time series database に計測データをストア。(いわゆる IoT ですかね 火暴)
AWS IoT なるものも触ってみたかったし。

簡単に Yun に移行できるかと思っていたら、なかなか結構大変(現在も学習中)なのでいろいろメモメモ。

で、どっち?

SRL:

http://www.arduino.org/
Arduino | Labs | Arduino Yún
https://github.com/arduino-org

LLC:

https://www.arduino.cc/
Arduino - ArduinoYun
https://github.com/arduino

私がスイッチサイエンス社から購入した Yun は製造は SRL 、Atheros AR9331 に組み込まれていたのが Linino ではなく OpenWrt-Yun なので LLC 。

ということは、ソフトウェアは LLC を見た方が良いという判断か。

実際 github 上の動きをみても LLC のほうが好ましい。

IDE も LLC 版は Java8 に上がっている。
ウェブサイトも LLC は https だし。

ソフトウェアは LLC を信頼したほうが良いと思われる。

以下の記述も LLC 版で書きます。

導入

電源

Uno では(ACアダプターからの)DC入力ジャック(5.5mm/2.1mm Center Plus | 7~12V) があったが Yun には無い。

micro-USB から 5V 供給するのが推奨。(びみょうに斜めに付く) PoE モジュールをつければ Ethernet RJ45ジャックから給電も可。VIN pin に定電圧レギュレータの5Vをいれるのも可。

USB Serial

Yun は Arduino Leonardo(ATmega32U4)ベースに作られている。Uno のように USB 通信用のペリフェラル(ATmega16U2がUSBを受け持つ)をもっていない。そのかわりに ATmega32U4 は USB 制御器を内蔵している(Uno の ATmega328P にはその回路はない)。そこで大きな使い勝手の差がある。

micro-USB ケーブルには充電専用というのが紛れ込んでいるので要注意。ハマります...

紐をほどくために Arduino Leonardo ガイドの日本語訳

Guide/ArduinoLeonardo – スイッチサイエンス

WiFi 設定

工場出荷状態なら、WiFi AP モードで Yun が起動するので、そのアクセスポイントに接続してごにょごにょ。SSID が WiFiの MACアドレスになっているので、もしフィルタリングをしてる場合はこれを使う。

ご参考 : 高木浩光@自宅の日記 - 無線LANのMACアドレス制限の無意味さがあまり理解されていない

初心者向け記事:

Arduino YÚNのネットワーク機能を試してみる | ニフティIoTデザインセンターブログ
Arduino Yúnを使ってみよう (1) Yúnを設定する | スイッチサイエンス マガジン
Arduino Yúnを使ってみよう (2) YúnをPCから操作する | スイッチサイエンス マガジン
AWS IoTがリリースされました(Yúnを繋ぎました) | スイッチサイエンス マガジン
AWS IoTをArduino Yúnで使う(少し詳しく書いてみた) | スイッチサイエンス マガジン
LambdaからIoT経由でArduino Yúnへ(前編) | スイッチサイエンス マガジン
LambdaからIoT経由でArduino Yúnへ(後編) | スイッチサイエンス マガジン
Arduino YUNを使ってみる(1) - フィジカル・コンピューティング
Arduino YUNを使ってみる(2) - フィジカル・コンピューティング
Arduino YUNを使ってみる(3) - フィジカル・コンピューティング
Arduino YUNを使ってみる(4) - フィジカル・コンピューティング
Arduino YUNを使ってみる(5) - フィジカル・コンピューティング

注意:Windows の場合は Apple から Bonjour のドライバーをとってきてインストールしておく。

注意:WiFi ルーターが「アイソレーション」「ネットワーク分離機能」「プライバシーセパレータ」等の名前の端末間通信を拒否する設定になっていると同一ネットワークに有る機器は Yun に接続てきません。WiFi ルーターの該当を機能を解除してください。

ネットワーク設定に失敗したら

YunSerialTerminal
ファイル -> スケッチの例 -> Bridge -> YunSerialTerminal

このスケッチをコンパイルしてアップロードする。

Arduino IDE の シリアルモニターでは使い勝手がわるいので、picocom 等で シリアルポートにつなげる。

/etc/config/arduino
/etc/config/wireless
/etc/config/network

を確認して修正する。平文で WiFi のパスワードが書かれているのでこのファイルの扱いは要注意。

もちろん uci でも WiFi パスワードは平文。

OpenWrt-yun のアップデート

導入後最初にやったほうがよさそう。(私が購入した Yun はそのままでは opkg の整合性が合わなかった)

http://crossbar.io/iotcookbook/Arduino-Yun-Basic-Setup/
http://crossbar.io/iotcookbook/Arduino-Yun-Expanding-Disk-Space/
http://crossbar.io/iotcookbook/Arduino-Yun-System-Update/
http://crossbar.io/iotcookbook/Arduino-Yun-Prepare-Image/
step1.sh
crossbar.io ここがマニアックでいいかんじ。
opkg update
opkg install unzip
### ファイルのバージョンは確認のこと
### https://www.arduino.cc/en/Main/Software
cd /tmp
wget http://downloads.arduino.cc/openwrtyun/1/YunSysupgradeImage_v1.5.3.zip
unzip YunSysupgradeImage_v1.5.3.zip
sysupgrade -v -n openwrt-ar71xx-generic-yun-16M-squashfs-sysupgrade.bin

注意 アップデート後、もういちどWiFiの設定を最初からやり直す事。

ディスクの容量を増やす

必要なソフトウェアを導入したらすぐにディスクフルになるので、micro SD をつかってディスク容量を増やす。

http://crossbar.io/iotcookbook/Arduino-Yun-Expanding-Disk-Space/
を参考に

Yun は 32GB までは対応している。できたら class 10 の micro SD カードを準備して挿入する。

opkg update
opkg upgrade temboo
opkg install e2fsprogs mkdosfs fdisk rsync
umount /dev/sda1
### パーティション情報を壊す
dd if=/dev/zero of=/dev/sda bs=4096 count=1000
### FAT32 に 15G、ext4 に残り
(echo o; echo n; echo p; echo 1; echo; echo +15G; echo n; echo p; echo 2; echo; echo; echo t; echo 1; echo c; echo w) | fdisk /dev/sda
mkfs.vfat /dev/sda1
mkfs.ext4 /dev/sda2
mkdir -p /mnt/sda2
mount /dev/sda2 /mnt/sda2
rsync -a --exclude=/mnt/ --exclude=/www/sd /overlay/ /mnt/sda2/
umount /dev/sda2
rm -rf /mnt/sda2
### uci というのは OpenWrt の汎用設定インターフェースシステム
### https://wiki.openwrt.org/doc/uci
uci add fstab mount
uci set fstab.@mount[0].target=/overlay
uci set fstab.@mount[0].device=/dev/sda2
uci set fstab.@mount[0].fstype=ext4
uci set fstab.@mount[0].enabled=1
uci set fstab.@mount[0].enabled_fsck=0
uci set fstab.@mount[0].options=rw,sync,noatime,nodiratime
uci commit
reboot

ブートしたら、

df -h

で増えた事を確認する。

root@Arduino:~# df -h
Filesystem                Size      Used Available Use% Mounted on
rootfs                   14.7G    380.6M     13.6G   3% /
/dev/root                 7.5M      7.5M         0 100% /rom
tmpfs                    29.8M    392.0K     29.5M   1% /tmp
tmpfs                   512.0K         0    512.0K   0% /dev
/dev/sda2                14.7G    380.6M     13.6G   3% /overlay
overlayfs:/overlay       14.7G    380.6M     13.6G   3% /
/dev/sda1                15.0G     18.6M     15.0G   0% /mnt/sda1

RESET

Resetting the processors (AR9331, WiFi, and 32U4)
  1. OpenWrt が稼働する AR9331 をリスタートするには、いっぱい LED がある側の、アナログピンの横の "YÚN RST" を押す。
  2. AVR マイコン ATmega32U4 をリスタートするには、イーサネットポートの横にある、"32U4 RST" を押す。
    1回だけなら通常のリセットになる。2回速く押す事で bootloader mode に入り LED 13 が赤く点灯し 8 秒待機した後、起動する。
    Reset to Bootloader
  3. WiFi ボードをリセットするには、USB-A ポートの横にある "WLAN RST" を押す。
  4. WiFi 設定を初期化するには、"WLAN RST" を 5 秒以上かつ 30 秒以下押し続ける。AR9331 がリスタートして 初期のWiFi設定モードになる。
  5. OpenWrt-Yun を工場出荷の状態に戻すには、"WLAN RST"を 30 秒以上押し続ける。この場合すべての設定が初期化される。
  6. OpenWrt-Yun の root ログインパスワードを忘れた場合は、YunSerialTerminal をロードしてシリアルコンソールから変更する。

Yun 特有な開発

avrdude

USBシリアル経由でプログラムをアップロードするのにいろいろはまった。

Leonardo 側が割り込み禁止になっていれば USB シリアルは使えない。

また SLEEP のモードによっても USB シリアルは使えない。

データシートによると SLEEP_MODE_IDLE と SLEEP_MODE_ADC であれば USB 割り込みから復帰可能であり、割り込み可能の場合は IDE で USBシリアルがつかえる。
ATmega32U4 は USB の回路を内蔵していて Yun の micro-USB 端子に D+ D- VBUS (USB)GND が繋がっている。

スピードは極端におそいが、TCP/IP ネットワーク経由にしておくのが無難だとわかった。

Arduino-Makefile

avrdude のところでおかしくなる。調査する。

例の 1200bps でリセットするところでおかしい...

私の作業環境が Windows の Cygwin なので、新しく接続された USB デバイスを Cygwin 側からは認識しないという事情によるものだった。
あとは 上記と同様な理由で、割り込み禁止にしているか、SLEEP_MODE_PWR_DOWN 等では USB シリアルは使えない。TCP/IP ネットワーク経由で使う方法/パッチ探すことにする...
おそらく ssh で hex を送って、それから OpenWrt 側の avrdude 経由で書き込むようにハックすればいけると思われるので調査する。

memo:

scp sketch.hex root@arduino.local:/tmp/
ssh root@arduino.local 'kill-bridge'
### ssh root@arduino.local '/usr/bin/merge-sketch-with-bootloader.lua /tmp/sketch.hex'
ssh root@arduino.local '/usr/bin/run-avrdude /tmp/sketch.hex'
送った後、なぜかSerial1のLEDがつきっぱなし。要調査。
下手にやると文鎮になりそうなので要注意。もっと遊んでからこの実験をすることにしたので放置。

2つのマイコン

How to improve reboot/reset stability

Arduino Yun は AVR ATmega32U4 と MIPS 24K 系の Atheros AR9331 の2つのマイコンを搭載している。

Uno も2つのマイコンを搭載しているが ATmega16U2 は USB通信をつかさどっている。(ATmega16U2 専用の ICSP 端子があるのでプログラミンは可能)

Yun の AR9331 は U-boot と呼ばれる汎用ブートローダを持ち、LLC 版では GNU/Linux の組み込み系ディストリビューションである OpenWrt-yun が起動する。Yun でのプログラムは Arduino 環境で開発するプログラム(スケッチ)、つまり Arduino Leonardo のプログラムと OpenWrt プログラムとの連携がポイントになる。連携は Bridge ライブラリを利用する。

2つのマイコンは以下の3つの状態を取りうる。

  1. Leonardo と OpenWrt が同時に起動する(電源投入時)場合。Leonardo が瞬時に立ち上がり、OpenWrt は init rc 等上がりきるまで20数秒かかる。
  2. Leonardo がリセットされた時(スケッチがアップロードされた・ボードの Leonardo リセットボタンを押した・OpenWrt から reset-mcu を実行した)、この場合は OpenWrt が稼働し続けている。
  3. OpenWrt がリブートされた時(reboot コマンドを実行した・OpenWrt リセットボタンを押した・OpenWrt をアップグレードした)、この場合は Leonardo は稼働し続けている。

Leonardo と OpenWrt の連携をする場合はこの3つの状態を意識してプログラムをしなければならない。

OpenWrt の boot 完了を待つ処理

Bridge は OpenWrt の起動直後(Serial1活性確認つまり OpenWrt のシリアルコンソール活性後・ブートシーケンスの最初の頃)、Leonardo 側からシリアルコンソールで OpenWrt にログインして run-bridge スクリプトを起動する。つまり、

  Bridge.begin();

は OpenWrt の起動確認後、run-bridge スクリプトを起動する。

Bridge.cpp:

  // Wait for U-boot to finish startup
  do {
    dropAll();
    delay(1000);
  } while (stream.available() > 0);
void BridgeClass::dropAll() {
  while (stream.available() > 0) {
    stream.read();
  }
}
    // Bridge startup:
    // - If the bridge is not running starts it safely
    stream.print(CTRL_C);
    delay(250);
    stream.print(F("\n"));
    delay(250);
    stream.print(F("\n"));
    delay(500);
    // Wait for OpenWRT message
    // "Press enter to activate console"
    stream.print(F("run-bridge\n"));
    delay(500);
    dropAll();

/usr/bin/run-bridge:

python -u bridge.py

このスクリプトの処理を設定後、次の処理にわたす。

Bridge について詳しい記事:

Arduino YunのBridgeメモ

Bridge は破棄することができなさそう。もし Leonardo が稼働中に、OpenWrt が再起動したばあい、bridge.py は起動しておらず、その条件下で再度 Leonardo で Bridge.begin() を呼んでも、private のフラグがセットされていて、bridge.py を呼び出すことはない。

Bridge.cpp:

void BridgeClass::begin() {
  if (started)
    return;
  started = true;
Bridge が動いていないことを検知したら、美しくはないが Leonardo を自らリセットするのがいまのところよさそう。
  asm volatile ("jmp 0");

OpenWrt 起動直後は、ネットワークの設定処理が終わっていないことや、NTP で時刻同期がまだできていない状態で、Leonardo 側の処理が動く場合がある。

ちなみに OpenWrt 側のマイコンには RTC がなく、ブート直後は、時刻が大幅に違っている。(前回 poweroff コマンド実行時の時刻)
/* Check OpenWrt wlan led ON */
boolean CheckOpenWrtWlanLed(void) {
  Process yun_proc;
  String yun_str;
  char c;
  boolean ret = false;

  /* WLAN LED ON ? */
  yun_proc.begin("/bin/cat");
  yun_proc.addParameter("/sys/class/leds/ds:green:wlan/brightness");
  yun_proc.run();
  while(yun_proc.available() > 0) {
    c = yun_proc.read();
    if(c != '\n') {
      yun_str+= c;
    }
  }
  if (yun_str == "255") {
    ret = true;
  }
  return ret;
}
WLANのLEDが点灯している場合は大丈夫という判断はワークアラウンドとしてはつかえる。
WLANが起動して、NTP (sysntpd) が時刻を拾うまで数十秒待つ。(25秒ほど待てば十分)
もちろん OpenWrt が起動済みで Leonardo のみが再起動した場合は待つ必要はない。

Leonardo AVR マイコン

I/O

D0/INT2, D1/INT3 は AR9331 との Serial1 用に接続されている。Yun で外部割り込みで使えるのは D2/INT1 と D3/INI0 とのこと。D7/INT4 は AR9331 の ハンドシェイク用(予定)なので使わない。

I2C(TWI)の SDA/SCL が Uno は A4/A5。Yun は D2/D3 。

はい!終わった!INT1/INT0 の外部割り込みが使えない...
I2C使わないように、SPI に回路変えるか...
SPI で気象データセンサーなら
Adafruit BME280 I2C or SPI Temperature Humidity Pressure Sensor ID: 2652
5V対応
SparkFun Atmospheric Sensor Breakout - BME280 - SEN-13676
3.3Vのみ。5Vマシンならロジックレベルシフターが必要。
SPI でRTC なら
SparkFun DeadOn RTC Breakout - DS3234 - BOB-10160
ハードウェアSPI も UNO と異なる。UNO はICSP 端子と PIN 10, 11, 12 だが YUN は ICSP 端子のみだ。
Yun で ハードウェア SPI のために ICSP 端子に接続する場合は問題がある。network 経由の avrdude でエラーがでる。
Pin により割り込みを他の Pin で可能にする方法がある。
Leonardo - using I2C and external interrupts
Pin Change Interrupt library for the Arduino

Pin Change Interrupt

PinChangeInt の更新版である EnableInterrupt があった。

https://github.com/GreyGnome/EnableInterrupt

これによると Yun と同じ Leonardo の割り込みの拡張・変更は、

外部割り込み  : D0, D1, D2, D4, D7
Pin Change 割り込み : D8, D9, D10, D11, SCK, MOSI, MISO

ポートB の変更になる。

実際に Yun で試したみたところ、割り込みは検知できた。

enableInterrupt() で RISING を設定したが、たしかに 割り込みハンドラは RISING(LOW->HIGH) でのみ起動はした。
しかし AVR の SLEEP が RISING(LOW->HIGH) だけでなく FALLING(HIGH->LOW)でも解除された。
おそらく AVR ポートB の仕様によるものというか、Pin Change Interrupt という文字通りの挙動で、enableInterrupt ライブラリが割り込みハンドルを横取りしてソフト的に RISING, FALLING, CHANGE の制御をおこなっているのであろう。

EnableInterrupt に記述されている Leonardo の割り込みの種類

Pin     Interrupt Port 

 3      INT0      PD0      // External Interrupt (I2C SCL)
 2      INT1      PD1      // External Interrupt (I2C SDA)
 0      INT2      PD2      // External Interrupt (Serial1 RX)
 1      INT3      PD3      // External Interrupt (Serial1 TX)
 7      INT6      PE6      // External Interrupt (AR9331 handshake)
 8      PCINT4    PB4      // Pin Change Interrupt
 9      PCINT5    PB5      // Pin Change Interrupt
10      PCINT6    PB6      // Pin Change Interrupt
11      PCINT7    PB7      // Pin Change Interrupt
SCK/15  PCINT1    PB1      // Pin Change Interrupt
MOSI/16 PCINT2    PB2      // Pin Change Interrupt
MISO/14 PCINT3    PB3      // Pin Change Interrupt
ATmega32U4 DATA SHEET
ATmega32U4 データシート 日本語訳
Arduino のスリープと、Pin Change 割込 | FIRMLOGICS
(Arduino のスリープと、Pin Change 割込 - 私の二次記憶) : はてな版

PINOUT DIAGRAM

これはありがたい。

THE UNOFFICIAL ARDUINO PINOUT DIAGRAM 本家

SLEEP

Leonardo では sleep_bod_disable が未定義になる。

USB(micro-USB)つかうなら sleep mode は SLEEP_MODE_IDLE か SLEEP_MODE_ADC で。(USB制御回路の割り込みでスリープから復帰する)

Timer 2

Timer 2 がない。Uno にはない Timer 3, Timer 4がある

Console

ssh root@arduino.local 'telnet localhost 6571'
たぶん Uno で Serial ってかいてるところをすべて Console ってかいてやれば最初のハードルは越えられそう...

OpenWrt 側からの Console 接続待ち

  while(!Console);
OpenWrt 側から ポート 6571 に接続するまで待つための Leonardo 側プログラム処理。

Process

なんと Leonardo 側から OpenWrt のコマンドを実行できる。

Arduino - Process
邪悪だ...;)
Arduino yunで放射線センサのデータをxivelyとM2Xにアップロードする - XX-Prime's blog
IFTTTを用いてArduinoからツイートする - Qiita
https://github.com/itman83/ArduinoYun

SPI と ICSP と avrdude

Yun で ハードウェアSPI の構成をとる場合、ICSP 端子を使うのだが、ICSP 端子からデバイスを接続している場合、ネットワーク経由での avrdude でエラーがでる。

/usr/bin/run-avrdude /tmp/sketch.hex
avrdude: AVR device not responding
avrdude: initialization failed, rc=-1
         Double check connections and try again, or use -F to override
         this check.

/usr/bin/run-avrdude: line 5: can't open /tmp/efuse: no such file

avrdude: AVR device not responding
avrdude: initialization failed, rc=-1
         Double check connections and try again, or use -F to override
         this check.


avrdude done.  Thank you.

ICSP 端子からデバイスの接続を抜くと avrdude は成功する。プログラムを送信後、再度デバイスを ICSP 端子に接続して reset-mcu する。

私はマイコンのプログラムは通常 HALT/SLEEP で、処理は割り込み駆動で書くべきだとおもっているので YUN の場合 USB での avrdude は使わない・使えない。
https://www.arduino.cc/en/Main/ArduinoBoardYun

の Documentation -> Input and Output -> SPI によると、

SPI: on the ICSP header. These pins support SPI communication using the SPI library. Note that the SPI pins are not connected to any of the digital I/O pins as they are on the Uno, They are only available on the ICSP connector. This means that if you have a shield that uses SPI, but does NOT have a 6-pin ICSP connector that connects to the Yún's 6-pin ICSP header, the shield will not work. The SPI pins are also connected to the AR9331 gpio pins, where it has been implemented in software the SPI interface. This means that the ATMega32u4 and the AR9331 can also communicate using the SPI protocol.

AR9331 の GPIO と共有しているらしい。そりゃ avrdude 動かないわ。

ひょっとしたら AR9331 側の avrdude を呼ぶラッパーが ICSP 端子への書き込みを判定する処理をしているのならハックできるかも。要調査。

DS3234 の SQW と Alarm

Alarm ので割り込みのあとは Alarm flag clear しないと次の割り込みが来ない。

RTClib 改 DS3224 版を fork して clearAlarmFlag という関数つくった。

https://github.com/nxhack/rtclib

あと DS1307 と異なり DS3234 の SQW は負論理である点に注意。

OpenWrt

Arduino - YunSysupgrade
https://github.com/arduino/openwrt-yun
Arduino Yún(OpenWRTYun)の設定情報書き出しには注意 - XX-Prime's blog
Documenting the Yun - Code Snippets

ふつうの PC UNIX とはいろいろ異なる。特に軽量化重視でいろんな設計がされている。

init rc

/etc/rc.d/:

K50dropbear
K90network
K95luci_fixtime
K98boot
K99umount
K99usd
S05defconfig
S05luci_fixtime
S09handle_wifi_reset
S10boot
S11sysctl
S11ubus
S18rename-wifi-if-access-point
S19firewall
S20fstab
S20network
S39usb
S48rngd
S49delete_uhttpd_cert
S49generate_new_gpg_key
S50cron
S50dropbear
S50uhttpd
S59luci_dhcp_migrate
S60dbus
S60dnsmasq
S61avahi-daemon
S93triggerhappy
S95done
S96led
S97watchdog
S98sysntpd
S99rngd-turn-off
S99usd

ボードのLED

/sys/class/leds:

ath9k-phy0
ds:green:usb
ds:green:wlan
brightness
device
max_brightness
subsystem
trigger
uevent

消灯:

echo 0 > /sys/class/leds/ds\:green\:wlan/brightness
echo 0 > /sys/class/leds/ds\:green\:usb/brightness

U-boot

http://www.denx.de/wiki/U-Boot

汎用ブートローダ。GPL。

BusyBox

http://busybox.net/downloads/BusyBox.html

GNU Coreutils 等を1つのプログラムファイルに固めたもの。コードの重複等のさまざまな無駄をはぶいてファイルサイズを少なくし、メモリー使用も少なく、起動を速くしたもの。組み込み系には嬉しい。

Dropbear SSH

https://matt.ucc.asn.au/dropbear/dropbear.html

SSH の軽量実装。OpenSSL を使っていない。zlib を省くことも可能。主な SSH の機能は装備されている。

openssh の ssh-keygen で作ったキーを使おうとしたら

dbclient: Exited: String too long

dropbear 用に変換する必要がある

opkg install dropbearconvert
dropbearconvert openssh dropbear id_dsa id_dsa.db

OpenWrt 版には SSHKeepAlive 対応のパッチがあたっているらしい

Dropbear Configuration

が、OpenWrt-yun のはまだかも...要確認

UCI

https://wiki.openwrt.org/doc/uci

UCI を調査...

uci show

OpenWrt 側から Leonardo のリセット

reset-mcu

yun scripts

openwrt-packages-yun/arduino/yun-scripts/files/usr/bin/
おもしろいのがいっぱい。
reset-to-factory-anyway
豪快
upgrade-all
これいいね

opkg

最初にこれだけは

opkg update
opkg list-upgradable
### なになあればそれを upgrade
### opkg upgrade temboo
opkg install unzip
opkg install screen
opkg install logrotate
mkdir -p -m 0755 /mnt/sda1/var/lib/logrotate
crontab -e
### logrotal の記述かく
### 25 6 * * * /usr/sbin/logrotate -s /mnt/sda1/var/lib/logrotate/status /etc/logrotate.conf > /dev/null 2>&1
### もしくは crontab ファイル
/etc/init.d/cron restart
Homepage V. 5.1 - Rotating lighhtpd logs on OpenWRT

注意:FAT32 で作ったファイルを ext4 に持って行くと x 属性がついてしまっている。logrotate.d 配下に置くファイルはこれが問題になった。

ps aux や w のたびに悲しい思いするのを避けるために

opkg update
opkg install procps --force-overwrite
root@Arduino:~# opkg install procps
Installing procps (3.2.8-1) to root...
Downloading http://downloads.arduino.cc/openwrtyun/1/packages/procps_3.2.8-1_ar71xx.ipk.
Collected errors:
 * check_data_file_clashes: Package procps wants to install file /usr/bin/free
        But that file is already provided by package  * busybox
 * check_data_file_clashes: Package procps wants to install file /usr/bin/pgrep
        But that file is already provided by package  * busybox
 * check_data_file_clashes: Package procps wants to install file /usr/bin/top
        But that file is already provided by package  * busybox
 * opkg_install_cmd: Cannot install package procps.

競合するらしいが、手癖のリズムを優先したいのでリスクを負って --force-overwrite した。

cd /bin
ln -s busybox free
ln -s busybox pgrep
ln -s busybox top

念のため競合したプログラムを復活しておく。

/root/.profile:

alias ps=/usr/bin/ps
alias top='TERM=xterm; export TERM;/usr/bin/top'

PATHを変えるのは影響がでかそうなので alias しておく。

emacs もどき...

opkg install coreutils-ls
opkg install mg

/root/.profile:

alias ls='/usr/bin/ls -F --color=auto'
alias ll='ls -alF --color=auto'
alias emacs="TERM=xterm; export TERM;PATH='/usr/bin:/usr/sbin:/bin:/sbin'; /usr/bin/mg"
(setq-default truncate-lines nil) の挙動がないので、長い行を改行しないことを意識すること。

syslog

syslogd が -C16 というオプション付きで起動されている。

/sbin/syslogd -C16

これは ログメッセージを RAM 上のリングバッファにストアするオプション。

logread

これで表示。もちろんリングバッファということで古いものは消えていく。

logread -f

で tail 表示

python beaver

logstash に計測データを送るために、軽量 shipper beaver を導入。

本当は filebeat が良いのだが、Golang が MIPS に対応してない。

導入する前に micro-SD でディスク容量を増やしておく事。

opkg update
opkg install distribute
opkg install python-openssl
opkg install python-bzip2
easy_install pip
opkg install python-sqlite3
pip install beaver==34.1.0

SSH Tunneling したいので OpenWrt-Yun の 軽量 ssh である Dropbear SSH のための key 変換ツール。これで Dropbear 用に変換する。

opkg install dropbearconvert
/usr/bin/beaver -D -c /mnt/sda1/beaver/beaver.conf -P /mnt/sda1/beaver/beaver.pid

とりあえず動いたっぽい。

opkg install python-expat
pip install supervisor
Supervisor/initscripts
python supervisor startup script for OpenWrt-yun
OpenWrt 用作った。

いろいろ設定して意外とさっくり supervisord 配下で beaver が動いた。

ついでに ssh tunnel も稼働中...

init script で ssh を起動する場合、 HOME が設定されていないので、ssh 関連のファイルの操作ができない。

HOME=/root
export HOME
init script に HOME を設定しておく事。

なんかいろいろやろうとすると supervisor も daemontools とおなじカホリを感じたな...

AR9331 メモリー

AR9331 の主メモリーは 64MB ということで、busybox や dropbear などを使って工夫している。 python supervisor と beaver を稼働させるともちろんメモリーは圧迫されるので無駄をなくす事が重要。 本当は OpenSSH client インストールして ssh tunnel のいろんなオプションつけたいのだけど我慢。ntpd も同様。

最終的に OpenSSH-client は入れた。
root@Arduino:~# free
             total       used       free     shared    buffers     cached
Mem:         61116      56088       5028          0       5572      15992
-/+ buffers/cache:      34524      26592
Swap:            0          0          0

python supervisor と beaver を稼働させた状態。

メンテ用トンネル

おなじみのサーバサイドの sshd_config をホゲる

TCPKeepAlive no
ClientAliveInterval 15
ClientAliveCountMax 3

ssh tunnel サービス は python supervisord 配下で稼働させた。

dropbear の client dbclient のオプションを調査したが、 -o は無視するようだ。

やっぱり -o ExitOnForwardFailure=yes をつかわないとマズイ状態になる。なので

opkg install openssh-client --force-overwrite

OpenSSH いれてテストしてみる。

init script

Init Scripts
#!/bin/sh /etc/rc.common
/etc/init.d/hoge enable

要調査...

ssh-agent やっとけ

OpenWrt側に入ってテストすることがおおいので接続元で

eval `ssh-agent -s`
ssh-add ./.ssh/id_rsa
とかやっとく

OpenWrt 側は Dropbear SSH なので、

~/.ssh/authorized_keys

ではなく

/etc/dropbear/authorized_keys

自分の公開キーを書いておく。

link

Golang on OpenWrt · Akagi201