mackerel-agentをLinux/MIPS32環境で動かしてみた

「[GoのMIPS32 soft-float対応が来たぞー（1.9に入るとは言っていない） - Qiita](http://qiita.com/hnw/items/1cf89069b0d3e4118831)」で紹介した通り、Goで書かれたコードがFPUなしのMIPS32環境で動くようになりました。

そこで、ブロードバンドルータ上で[mackerel-agent](https://github.com/mackerelio/mackerel-agent)を動かしてみます。ブロードバンドルータのCPU(SoC)は32bit ARMか32bit MIPSのどちらかが使われていることが多いのですが、今回のターゲットマシンではMIPSが採用されています。また、この環境ではブロードバンドルータ向けのLinuxディストリビューションである[LEDE](https://lede-project.org/)([OpenWrt](https://openwrt.org/)のfork)が動いています。

以下、参考画像

![2017-05-08 11.44.01.jpg](https://qiita-image-store.s3.amazonaws.com/0/46856/d425b9b1-5311-4ed1-537b-636d42536d78.jpeg)

## ビルド

単に`make build`としてもうまくいかなかったので、`Makefile`を眺めつつ下記の手順でビルドしました。ここで使うgoバイナリはMIPS32向けsoftfloatパッチが当たったものです。また、バイナリサイズ削減のため`Makefile`を書き換えて`BUILD_LDFLAGS`に`-s -w`を追加しています。

```
$ git clone https://github.com/mackerelio/mackerel-agent.git
$ cd mackerel-agent
$ make generate
$ GOOS=linux GOARCH=mips GOMIPS=softfloat make build
```

~~ただし、`shirou/gopsutil`のビルドで怒られるので、`host/host_linux_mips.go`を適当に作っています。~~`shirou/gopsutil`にPull Requestを取り込んでもらったので、現在は特にトラブルなくビルドができると思います。

ビルドが成功すると、`build/`以下にバイナリができます。

```
$ ls -la build/mackerel-agent
-rwxr-xr-x 1 hnw staff 4502656  8 21 08:07 build/mackerel-agent
```

バイナリサイズは4.5MB。ブロードバンドルータのストレージ（容量の小さいNOR型フラッシュメモリが多い）に置くには大きめですね。

実行バイナリを実行可能なまま圧縮するツール[UPX](https://upx.github.io/)がlinux/mipsにも対応しているので、これを適用してサイズ圧縮を試みてみましょう。

```
$ upx build/mackerel-agent
                       Ultimate Packer for eXecutables
                          Copyright (C) 1996 - 2017
UPX 3.94        Markus Oberhumer, Laszlo Molnar & John Reiser   May 12th 2017

        File size         Ratio      Format      Name
   --------------------   ------   -----------   -----------
   4502656 ->   1607704   35.71%   linux/mips    mackerel-agent

Packed 1 file.
```

1.6MBまで圧縮できました。これならOpenWrt/LEDE環境でもギリギリ許容範囲かもしれません。

| UPXのオプション | バイナリサイズ | 起動時間 |
|:-----------|------------:|------------:|
| （元のバイナリ） | 4.3MB | 0.05s |
| `upx -7` (default) | 1.6MB | 0.25s |
| `upx --best` | 1.5MB | 0.25s |
| `upx --brute` | 1.1MB | 0.75s |

同じバイナリについてUPXのコマンドラインを変えながら色々試してみましたが、`--best`がバイナリサイズと展開時間のバランスが一番良い印象です。

# 実際に動かしてみる

LEDEが動いているブロードバンドルータに上記バイナリをコピーして動かしてみました。設定ファイル
`/etc/mackerel-agent/mackerel-agent.conf`の変更点は下記になります。

```
root = "/etc/mackerel-agent/status"
apikey = "[organizationに対応するAPIKEY]"

[filesystems]
ignore = "/dev/root"
```

`root`の設定を変更しているのは、デフォルトのままだと再起動のたびに毎回ホストIDが変わってしまう問題への対処です。OpenWrt/LEDEでは`/var`がtmpfsで実現されているので、この直下にファイルを置くと再起動時に必ず消されてしまうのです。

https://mackerel.io を見ると問題なく動いていることがわかります。

<img width="622" alt="mackerel1.png" src="https://qiita-image-store.s3.amazonaws.com/0/46856/1eb9d527-7c14-7d54-f07f-59ed6365cabb.png">

<img width="836" alt="mackerel3.png" src="https://qiita-image-store.s3.amazonaws.com/0/46856/6c7928a3-7e3a-5ae4-137b-e65c1fc9fa14.png">

agent自体のCPU負荷は無視できる程度に小さい印象です。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/46856/1be03aaa-3f20-ae4a-4a1b-e41113d2666d.png)

ネットワーク通信が増えるとsoftirqが跳ねる、など学びがありますね（自力でLinuxルータ立てたことがない人の意見）。また、LuCI（OpenWrt/LEDEのWeb管理画面）だけでCPUを40%程度まで食うこともわかります[^1]。

[^1]: グラフで9:45より前はWeb管理画面に接続していました。ブラウザを閉じた途端にルータのCPU消費が減っているのがわかります。

<img width="341" alt="mackerel2.png" src="https://qiita-image-store.s3.amazonaws.com/0/46856/9ac9f5c6-738c-d9e7-c8f0-20de00d432dd.png">

ストレージが小さすぎて0.0GB表示になってしまうのはご愛敬でしょう（実際のストレージサイズは28.3MBと2.3MBです）。