ラズパイ+3GPiをufw/hostapd/dnsmasqでモバイルWi-Fiルータにして格安SIMで使う

タイトル通りですが、ラズパイ＋[メカトラックス様](https://mechatrax.com/)の「[3GPi](https://mechatrax.com/products/3gpi/)」を、ufw/hostapd/dnsmasqでモバイルWi-Fiルータ化し、格安SIMで使ってみます。

#何ができるの？
- 固定回線や無線LANが無い環境でも、制御機器やGoogle Homeが使えます。（[HT100LN](http://www.aterm.jp/product/atermstation/product/mobile/ht100ln/)など市販の据置LTEルータと同じです）
- 格安SIMに固定IPアドレスの[イプシム](https://ipsim.net/)を使うと、ラズパイ自身や配下の無線LAN機器をInternet側から制御できます。（[構築事例](https://qiita.com/ipsim_net/items/9305190478d4f2361389)と、[Google Homeと組み合わせた活用例(?)](https://qiita.com/ipsim_net/items/300ff73635d5c44c30b3)）


##参照サイト
- [Using your new Raspberry Pi 3 as a WiFi access point with hostapd](https://frillip.com/using-your-raspberry-pi-3-as-a-wifi-access-point-with-hostapd/) ほぼこの内容通り
- [Raspberry Pi 3 アクセスポイント化 〜hostapd〜](http://www.hattotech.com/entry/2016/05/05/154130) isc-dhcp-server、DNS無し
- [[メモ] Raspberry Pi 3で、Wi-Fi アクセスポイントルータ](https://qiita.com/mt08/items/f2e4f9d3b1ed00849e23) isc-dhcp-server、DNS無し
- [Raspberry Piでローカルアクセスポイントを立てる](http://4009.jp/post/2017-01-05-rpiap/) isc-dhcp-server、DNS無し、hostapdをmake
- [Raspberry Piの無線LANアクセスポイント化](http://hyottokoaloha.hatenablog.com/entry/2015/02/24/000655) isc-dhcp-server、DNS無し、無線⇔有線LANをルーティング
- [Raspberry Pi 3 を WiFi アクセス・ポイント化する](https://azriton.github.io/2017/03/22/Raspberry-Pi-3-%E3%82%92-WiFi-%E3%82%A2%E3%82%AF%E3%82%BB%E3%82%B9%E3%83%BB%E3%83%9D%E3%82%A4%E3%83%B3%E3%83%88%E5%8C%96%E3%81%99%E3%82%8B/) 無線APのみ、DHCP/DNS無し、無線⇔有線LANをブリッジ

※何故かdnsmasqの代わりにisc-dhcp-serverが多いようですが、元記事に従ってdnsmasqを使い、DHCP兼DNSサーバにします。

##ネットワーク構成
`Internet --(3G回線)-- <ppp0>[3GPi+格安SIM]+[RPi]<wlan0> --(無線LAN)-- [制御機器、Google Home等]`

##準備するもの

- Raspberry Pi 3 Model B（またはRPi2とUSB無線LANドングルの組み合わせ＋追加設定）
- [3GPi](https://mechatrax.com/products/3gpi/)＋同梱Raspbian([3gpi2-jessie-20170904](https://github.com/mechatrax/3gpi/tree/master/release))（またはUSBモデム＋追加設定）
- [3GPiで使える格安SIM](https://github.com/mechatrax/3gpi/wiki/%E3%81%9D%E3%81%AE%E4%BB%96#%E5%8B%95%E4%BD%9C%E7%A2%BA%E8%AA%8D%E6%B8%88%E3%81%BF-sim)
- 無線LAN機器（スマートフォン、タブレット、制御機器、Google Home等）


#構築手順

1. ラズパイ＋3GPiをNATルータにします [ufw]
1. ラズパイを無線LANのAP（アクセスポイント）にします [hostapd]
1. ラズパイをDHCPサーバ・DNSサーバにします [dnsmasq]

※今回ラズパイの有線LANは利用しません。（無線LANとブリッジする、別LANで使う、などの応用は可能です）

##ufwでラズパイ+3GPiをNATルータに

1. ufwのインストール、初期設定
    インストール

    ```
sudo apt-get install ufw
```

    IPv6無効

    ```
sudo vi /etc/default/ufw
```

    ```text:/etc/default/ufw
#IPV6=yes
IPV6=no
```

    全ての接続を拒否

    ```
sudo ufw default deny
```

    default denyでもpingには応答してしまうので、ppp0（SIM側）のみ拒否

    ```
sudo vi /etc/ufw/before.rules
```

    ```text:/etc/ufw/before.rules
#「# ok icmp codes」の直前
# ppp0
-A ufw-before-input -p icmp -i ppp0 --icmp-type echo-request -j DROP
```

    ufw有効化、状態確認

    ```
sudo ufw enable
sudo ufw status
```

1. 格安SIMのAPN設定

    ```
sudo nmcli con add type gsm ifname "*" con-name [名称] apn [APN名] user [ID] password [Password]
```

1. IPv4フォワーディングを有効に変更（コメントアウトを外す）

    ```
sudo vi /etc/sysctl.conf
```

    ```text:/etc/sysctl.conf
net.ipv4.ip_forward=1
```

1. ufwのNAPT設定
    IPv4フォワードポリシーを有効に変更

    ```
sudo vi /etc/default/ufw
```

    ```text:/etc/default/ufw
#DEFAULT_FORWARD_POLICY=”DROP”
DEFAULT_FORWARD_POLICY=”ACCEPT"
```

    NAPT(MASQUERADE)を設定

    ```
sudo vi /etc/ufw/before.rules
```

    ```text:/etc/ufw/before.rules
#「# Don't delete these required lines, otherwise there will be errors」の直前に追加
# NAPT
*nat
:POSTROUTING ACCEPT [0:0]
-A POSTROUTING -s 192.168.168.0/24 -o ppp0 -j MASQUERADE
COMMIT
```

##hostapdでラズパイを無線APに

1. wlan0（無線LAN I/F）をDHCPから固定IPアドレスに変更
    wlan0をDHCPクライアントの対象から除外

    ```
sudo vi /etc/dhcpcd.conf
```

    ```text:/etc/dhcpd.conf
#（最終行に追加）
denyinterfaces wlan0
```

    wlan0にIPアドレスを指定（このIPアドレスが無線LAN機器のdefault gwになります）

    ```
sudo vi /etc/network/interfaces
```

	```text:/etc/network/interfaces
	#iface wlan0 inet manual
	#    wpa-conf /etc/wpa_supplicant/wpa_supplicant.conf
	iface wlan0 inet static
	    address 192.168.168.1
	    netmask 255.255.255.0
	    network 192.168.168.0
	    broadcast 192.168.168.255
	```

    DHCPクライアントの再起動、wlan0のdown/up

    ```
sudo service dhcpcd restart
sudo ifdown wlan0; sudo ifup wlan0
```

    wlan0の確認

	```text:ifconfig
	$ ifconfig wlan0
	wlan0     Link encap:Ethernet  HWaddr b8:27:eb:xx:xx:xx
	          inet addr:192.168.168.1  Bcast:192.168.168.255  Mask:255.255.255.0
	          UP BROADCAST MULTICAST  MTU:1500  Metric:1
	          RX packets:0 errors:0 dropped:0 overruns:0 frame:0
	          TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
	          collisions:0 txqueuelen:1000
	          RX bytes:0 (0.0 B)  TX bytes:0 (0.0 B)
	```
1. hostapdのインストール、設定
    インストール

    ```
sudo apt-get install hostapd
```

    設定ファイルを新規作成

    ```
sudo vi /etc/hostapd/hostapd.conf
````

	```text:/etc/hostapd/hostapd.conf
	# This is the name of the WiFi interface we configured above
	interface=wlan0

	# Use the nl80211 driver with the brcmfmac driver
	driver=nl80211

	# This is the name of the network ※SSID名
	ssid=RPi

	# Use the 2.4GHz band
	hw_mode=g

	# Use channel 6 ※チャンネル
	channel=6

	# Enable 802.11n
	ieee80211n=1

	# Enable WMM
	wmm_enabled=1

	# Enable 40MHz channels with 20ns guard interval
	ht_capab=[HT40][SHORT-GI-20][DSSS_CCK-40]

	# Accept all MAC addresses
	macaddr_acl=0

	# Use WPA authentication
	auth_algs=1

	# Require clients to know the network name
	ignore_broadcast_ssid=0

	# Use WPA2
	wpa=2

	# Use a pre-shared key
	wpa_key_mgmt=WPA-PSK

	# The network passphrase ※WPAパスワード
	wpa_passphrase=***

	# Use AES, instead of TKIP
	rsn_pairwise=CCMP
	```
    ブート時の設定ファイルを指定

    ```
sudo vi /etc/default/hostapd
```

    ```text:/etc/default/hostapd
#DAEMON_CONF=""
DAEMON_CONF="/etc/hostapd/hostapd.conf"
```

1. hostapdの動作確認
    hostapdをフロントでテスト起動

    ```
sudo /usr/sbin/hostapd /etc/hostapd/hostapd.conf
```

    無線LAN機器からSSIDが見えること、および無線LAN機器にIPアドレス等を以下の通り手動設定して接続

    >IPアドレス：192.168.168.2
    >ネットマスク：255.255.255.0
    >ゲートウェイ：192.168.168.1

    無線LAN機器上で疎通を確認

    ```text:無線LAN機器で実行
ping 192.168.168.1
ping 8.8.8.8
```

##dnsmasqでラズパイをDHCP/DNSサーバに

1. /etc/hostsにwlan0のIPアドレスとホスト名を追加（dnsmasqのwarning対策）

    ```
sudo vi /etc/hosts
```

    ```text:/etc/hosts
192.168.168.1	rpi3
```

1. dnsmasqのインストール、設定
    インストール

    ```
sudo apt-get install dnsmasq
```

    デフォルト設定ファイルをリネーム、設定ファイルを新規作成

    ```
sudo mv /etc/dnsmasq.conf /etc/dnsmasq.conf.orig  
sudo vi /etc/dnsmasq.conf
```

    ```text:/etc/dnsmasq.conf
interface=wlan0      # Use interface wlan0
listen-address=192.168.168.1 # Explicitly specify the address to listen on
bind-interfaces      # Bind to the interface to make sure we aren't sending things elsewhere
domain-needed        # Don't forward short names
bogus-priv           # Never forward addresses in the non-routed address spaces.
dhcp-range=192.168.168.11, 192.168.168.20, 24h # Assign IP addresses between 192.168.168.11 and 192.168.168.20 with a 24 hour lease time
```

    ※`server=8.8.8.8       # Forward DNS requests to Google DNS`は指定しません。

1. dnsmasqの動作確認
    無線LAN機器を手動設定からDHCPに戻して再接続し、以下のようにIPアドレス等が割り当てられていることを確認

    >IPアドレス：192.168.168.11 ～ 192.168.168.20のいずれか
    >ネットマスク：255.255.255.0
    >ゲートウェイ：192.168.168.1
    >DNSサーバ：192.168.168.1

    Wi-Fiルータとして使えることを確認

    ```text:無線LAN機器で実行
ping 192.168.168.1
ping 8.8.8.8
ping www.google.co.jp
```

1. 【参考】DHCPでしか動作しない機器[^1]に対し、常に同一のIPアドレスを割り当てる設定
    対象機器のMACアドレスを調べる（例：arpコマンド）

    ```
    arp -na
```

    dnsmasq.confに、MACアドレスとIPアドレスを指定する（IPアドレスはdhcp-rangeの範囲外でOK）


    ```text:/etc/dnsmasq.conf
dhcp-host=XX:XX:XX:XX:XX:XX, GoogleHome, 192.168.168.2, infinite
```

[^1]: [Google Home](https://qiita.com/ipsim_net/items/300ff73635d5c44c30b3)とか。

#実際に接続してみて
無線LAN機器がつながってしまえば、ラズパイを意識することはありません。当然ですが、それだけの用途であればHT100LNなどを利用する方が楽です。やはり、無線APがラズパイである、（DDNSやsshトンネルをうまく使ったり、固定IPアドレスSIMと組み合わせるなどして）Internet側からラズパイ自身や配下の無線LAN機器が制御できる、といった利点を活かすことができるかが鍵になると思います。