概要
Nervesを使ってネットワークの設定をしようとすると設定方法が分かりづらかったり不安定だったりと多少なりとも不満がありました。やはり同じようなことを思っている人たちがいたようでNervesのネットワークまわりを再設計するぜ〜って気持ちで作ったのがvintage_net
だと思ってます。…きっと。
SSHログインまでならvintage_net
だけでもいいんですが次の特徴を持ったnerves_pack
というパッケージがあったのでこちらを使って設定してみました
-
nerves_pack
はnerves_init_gadget
のかわりになるため同時に利用はできません - プロジェクト作成時のデフォルトは
nerves_init_gadget
になるので、プロジェクト作成時にnerves_pack
を使うように明示的に引数を設定します(後述) - ネットワークの設定
-
vintage_net
を利用 - mDNSの設定
-
MdnsLite
を利用 - SSH拡張
- disableできる
- 待受ポート番号を変更できる
- upload.shはこれまでどおり利用可
これからしばらくnerves_pack
シリーズになると思います
環境
ハードウェアとネットワークはこのような構成です。
今回はホスト名flamboise03を置き換えることにします。
ハードウェア
- Mac OSX
- NervesをRaspberryPi 3で稼働
ネットワーク
-
Mac OSX
- 有線LAN→メンテナンス用、固定IPアドレス(192.168.5.100/24)
-
RaspberryPi 3(flamboise03)
プロジェクト作成
以下のコマンドを入力してNervesプロジェクトを作成します。今回はvintagenet003
というプロジェクト名にしました。
--nerves-pack
の引数を忘れると作り直しなので注意してください!
~> mix nerves.new vintagenet003 --nerves-pack
~> cd vintagenet003
~> mix deps.get
~> mix firmware
mix firmware
時のエラー
mix firmware
した際、エラーが発生する場合があります。エラーメッセージをよく読むと入力したらいいコマンドを書いてくれているので実行します。@nishiuchikazuma の場合はbrewで以下の2つのコマンドを入力するとmix firmware
できるようになりました。
~> brew install homebrew/core/make
~> brew install gnu-sed
ネットワーク設定
config/target.exs
にネットワークの設定を記述します。
- SSHの設定はこれまでどおりでOK
- デフォルトの
config/target.exs
に手を加えた箇所は2点 - SSH鍵の設定
config: :nerves_firmware_ssh
- ネットワークの設定
config: :vintaget_net
の"eth0"と"wlan0"
import Config
config :shoehorn,
init: [:nerves_runtime, :nerves_pack],
app: Mix.Project.config()[:app]
config :nerves_runtime, :kernel, use_system_registry: false
config :nerves_firmware_ssh,
authorized_keys: [
"公開鍵A",
"公開鍵B"
]
config :vintage_net,
regulatory_domain: "JP",
config: [
{"usb0", %{type: VintageNetDirect}},
{"eth0",
%{
type: VintageNetEthernet,
ipv4: %{
method: :static,
address: "192.168.5.57",
prefix_length: 24,
}
}
},
{"wlan0", %{type: VintageNetWiFi,
vintage_net_wifi: %{
networks: [%{key_mgmt: :wpa_psk, ssid: "SSIDをここに書く", psk: "共通鍵をここに書く"}]
},
ipv4: %{method: :dhcp}
}
}
]
config :mdns_lite,
host: [:hostname, "nerves"],
ttl: 120,
services: [
%{
name: "SSH Remote Login Protocol",
protocol: "ssh",
transport: "tcp",
port: 22
},
%{
name: "Secure File Transfer Protocol over SSH",
protocol: "sftp-ssh",
transport: "tcp",
port: 22
},
%{
name: "Erlang Port Mapper Daemon",
protocol: "epmd",
transport: "tcp",
port: 4369
}
]
確認
mix firmware.burn
を実行してSDカードにイメージを焼いてSSHログインできるかどうか確認します。
~> mix firmware.burn
~> ping 192.168.5.57
~> ssh 192.168.5.57
VintageNet.info()
とifconfig
ネットワーク設定の確認にはこのようなコマンドがあります。
ifconfig
IPアドレス、ネットマスク、MACアドレスを確認するコマンド。DHCPで割り当てられたIPアドレスをサクッと確認するのに便利。
iex> ifconfig
lo: flags=[:up, :loopback, :running]
inet 127.0.0.1 netmask 255.0.0.0
inet ::1 netmask ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff
hwaddr 00:00:00:00:00:00
eth0: flags=[:up, :broadcast, :running, :multicast]
inet 192.168.5.57 netmask 255.255.255.0 broadcast 192.168.5.57
inet fe80::ba27:ebff:fef1:6bfc netmask ffff:ffff:ffff:ffff::
hwaddr b8:27:eb:f1:6b:fc
wlan0: flags=[:up, :broadcast, :running, :multicast]
inet 192.168.46.28 netmask 255.255.255.0 broadcast 192.168.46.255
inet 2001:a5b5:3fff:3e7:ba27:ebff:fea4:3ea9 netmask ffff:ffff:ffff:ffff::
inet fe80::ba27:ebff:fea4:3ea9 netmask ffff:ffff:ffff:ffff::
hwaddr b8:27:eb:a4:3e:a9
VintageNet.info/0
各インタフェースの状態を取得するコマンド。
iex> VintageNet.info
VintageNet 0.7.5
All interfaces: ["eth0", "lo", "wlan0"]
Available interfaces: ["wlan0"]
Interface eth0
Type: VintageNetEthernet
Present: true
State: :configured
Connection: :lan
Configuration:
%{
ipv4: %{address: {192, 168, 5, 57}, method: :static, prefix_length: 24},
type: VintageNetEthernet
}
Interface usb0
Type: VintageNetDirect
Present: nil
State: :retrying
Connection: :disconnected
Configuration:
%{type: VintageNetDirect, vintage_net_direct: %{}}
Interface wlan0
Type: VintageNetWiFi
Present: true
State: :configured
Connection: :internet
Configuration:
%{
ipv4: %{method: :dhcp},
type: VintageNetWiFi,
vintage_net_wifi: %{
networks: [
%{
key_mgmt: :wpa_psk,
mode: :infrastructure,
psk: "....",
ssid: "SSIDがここに表示される"
}
]
}
}
:ok
VintageNet.IP.subnet_mask_to_prefix_length/1
おまけ
サブネットマスクを計算する関数。
iex> VintageNet.IP.subnet_mask_to_prefix_length({255, 255, 255, 248})
{:ok, 29}
VintageNet.get_by_prefix/1
おまけ
ネットワーク関係の情報を表示する関数。
- ルーティングテーブルは表示しない
- inet6って文字が見えるのでIPv6対応がすすんでそう
- インタフェースのIPアドレスを取得したい時に利用できる
iex> VintageNet.get_by_prefix([])
[
{["available_interfaces"], ["wlan0"]},
{["connection"], :internet},
{["interface", "eth0", "addresses"],
[
%{
address: {192, 168, 5, 55},
family: :inet,
netmask: {255, 255, 255, 0},
prefix_length: 24,
scope: :universe
}
]},
{["interface", "eth0", "connection"], :lan},
{["interface", "eth0", "lower_up"], true},
{["interface", "eth0", "mac_address"], "b8:27:eb:f3:62:d3"},
{["interface", "eth0", "present"], true},
{["interface", "eth0", "state"], :configured},
{["interface", "eth0", "type"], VintageNetEthernet},
{["interface", "lo", "addresses"],
[
%{
address: {0, 0, 0, 0, 0, 0, 0, 1},
family: :inet6,
netmask: {65535, 65535, 65535, 65535, 65535, 65535, 65535, 65535},
prefix_length: 128,
scope: :host
},
%{
address: {127, 0, 0, 1},
family: :inet,
netmask: {255, 0, 0, 0},
prefix_length: 8,
scope: :host
}
]},
{["interface", "lo", "lower_up"], true},
{["interface", "lo", "mac_address"], "00:00:00:00:00:00"},
{["interface", "lo", "present"], true},
{["interface", "usb0", "connection"], :disconnected},
{["interface", "usb0", "state"], :retrying},
{["interface", "usb0", "type"], VintageNetDirect},
{["interface", "wlan0", "addresses"],
[
%{
address: {192, 168, 0, 8},
family: :inet,
netmask: {255, 255, 255, 0},
prefix_length: 24,
scope: :universe
}
]},
{["interface", "wlan0", "connection"], :internet},
{["interface", "wlan0", "lower_up"], true},
{["interface", "wlan0", "mac_address"], "b8:27:eb:a6:37:86"},
{["interface", "wlan0", "present"], true},
{["interface", "wlan0", "state"], :configured},
{["interface", "wlan0", "type"], VintageNetWiFi},
{["interface", "wlan0", "wifi", "access_points"],
[
%VintageNetWiFi.AccessPoint{
band: :wifi_2_4_ghz,
bssid: "************",
channel: 1,
flags: [:wpa2_psk_ccmp, :wps, :ess],
frequency: 2412,
signal_dbm: -62,
signal_percent: 63,
ssid: "************"
},
%VintageNetWiFi.AccessPoint{
band: :wifi_2_4_ghz,
bssid: "************",
channel: 3,
flags: [:wpa2_psk_ccmp, :wps, :ess],
frequency: 2422,
signal_dbm: -63,
signal_percent: 61,
ssid: "************"
},
%VintageNetWiFi.AccessPoint{
band: :wifi_5_ghz,
bssid: "************",
channel: 44,
flags: [:wpa2_psk_ccmp, :wps, :ess],
frequency: 5220,
signal_dbm: -86,
signal_percent: 31,
ssid: "************"
}
………野良APをたくさん表示………
]},
{["interface", "wlan0", "wifi", "clients"], []},
{["interface", "wlan0", "wifi", "current_ap"],
%VintageNetWiFi.AccessPoint{
band: :wifi_2_4_ghz,
bssid: "00:3a:9d:d0:09:02",
channel: 1,
flags: [:wpa2_psk_ccmp, :wps, :ess],
frequency: 2412,
signal_dbm: -62,
signal_percent: 63,
ssid: <<0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0>>
}}
]
まとめ
vintaget_net
を含んだnerves_pack
を使ってSSHログインまでできるようになりました!