Raspberry Pi 4B を自宅サーバにする(CentOS Stream 8)
はじめに
以前の記事 で、Raspberry Pi 4B を自宅サーバ化するために Ubuntu を採用したが、結局 IPv6 ネットワーク周りに関してどうしても解決できない問題が出たため継続利用を断念。本記事では、 Ubuntu でのインストール実績はなかったもの として、CentOS Stream 8 版として焼き直すことにする。
目標と主な構成
主な目標
- 24時間常時稼働
- Micro SD カードではなく SSD 運用とする
- IPv6 対応+IPv6 アプリケーションの動作確認・テスト用
- 自宅リモート接続用の OpenVPN サーバ (IPv4/IPv6)
- 自宅用ファイルサーバ
- Web フレームワーク構築学習用 (Python Django/Flask)
OS
CentOS Stream 8 を選択。
長年慣れた rpm 系ディストリビューションであり、社内でもずっと RHEL/CentOS 一択だった。RPM パッケージをリビルドする必要が出たとしても、大抵はなんとかなる。 ただ、CentOS 8 → CentOS Stream 8 移行問題については悩ましい。CentOS 8 (無印) は 2021年末にサポートが終わってしまうし、CentOS 7 ではライブラリが古すぎる。 Fedora/CentOS Stream/CentOS/RHELの関係性 (赤帽エンジニアブログ, 2020/7/27) を読む限り、「CentOS 以上、Fedora 未満」の熱さ加減らしいので、ここに期待する。
ケース
Argon ONE M.2 Case for Raspberry Pi 4 を選択。
M.2 SATA 型の SSD を内蔵可能、放熱性のよいアルミ筐体、可変コントロールFAN、配線をすべて背面にまとめられる等々がお気に入り。SSDユニットを接続するために特殊な USB-A ブリッジコネクターが付いている。
正面 | 背面 | 背面コネクタ |
---|---|---|
上面(GPIO端子) | 部品一式 | 梱包箱 |
---|---|---|
機器仕様・構成
項目 | 構成 |
---|---|
本体 | Raspberry Pi 4 Type B (RAM 4GB) |
電源 | USB-C 端子 (5V/3A) |
ケース | Argon ONE M.2 Case |
ストレージ | Western Digital: WD BLUE M.2 500GB SSD (WDS500G2B0B) |
出力 | インストール時のみ HDMI モニタに接続し、セットアップ後は外す |
インターフェース | 作業時のみキーボード・マウスを接続し、セットアップ後は外す |
OS | Cent OS Stream 8 (64bit) |
ネットワーク | 内蔵Gigabit Ethernet |
ケースへの SSD の組み込み
(ラズパイ自身の組み込みは省略。)
ケースの底蓋側が SSD ユニットになっているのでこれを外し、M.2 コネクタに SSD を差し込んでから、SSD自体をネジ1本で固定する。 再度底蓋を閉めたら、USB のブリッジコネクタを差し込む。完了まで何度か底蓋を外すことになるので、底蓋側のネジは最後まで締めずにおく。
OS インストール
インストール作業用OSの準備
ラズパイ標準構成以外のデバイスや OS を使おうと思ったら、とにかく標準 Raspberry Pi OS を起動して前準備をする。こちらはセットアップ済みの MicroSD カードの用意が前提。
- MicroSD カードから Raspberry Pi OS (デスクトップ版) を起動し、ログインする
- ターミナル内で、Raspberry Pi OS 自身を更新し、再起動する
sudo apt update
sudo apt upgrade
sudo reboot
- 再度 Raspberry Pi デスクトップにログインして下記を進める。
イメージファイルダウンロード
CentOS コミュニティの Pablo Greco さん がラズパイ用の CentOS イメージファイルを公開しているので、Raspberry Pi OS デスクトップ上でダウンロードしておく。
CentOS-Userland-8-stream-aarch64-RaspberryPI-Minimal-4-sda.raw.xz
SSD に CentOS イメージを入れる
Raspberry Pi OS デスクトップ版にログインし、ここから SSD に書き込む。
- Raspberry Pi OS の MicroSD をラズパイ本体に挿す。
- Argon ONE M.2 に SSD をセットし、USB ブリッジコネクタで接続。(まだ裏蓋ネジは締めないで仮置き)
- 電源を入れ、MicroSD から Raspberry Pi OS を起動し、デスクトップ (X Windows) にログインする。
- 公式の Raspberry Pi Imager をインストールする。
sudo apt install rpi-imager
- Raspberry Pi Imager を起動
- CHOOSE STORAGE で USB 経由の SSD デバイスを指定 (MicroSD を指定すると起動中の OS が壊れるので注意!)
- CHOOSE OS で Use custom を指定
- 先ほどダウンロードしておいた xxx.raw.xz ファイルを指定する。自動展開されるため事前に xz 圧縮を展開しておく必要はない。
- WRITE をクリックして終わるまで待つ
CentOS kernel 起動ファイルを編集
Raspi OS のターミナルから実行
sudo su -
mkdir -p /mnt/sda1
mount /dev/sda1 /mnt/sda1
PARTUUID を確認
blkid | grep "sda"
結果から PARTUUID を拾っておく。例:
/dev/sda1: PARTUUID="68bafdb3-01"
/dev/sda2: PARTUUID="68bafdb3-02"
/dev/sda3: PARTUUID="68bafdb3-03"
kernel 起動引数の設定
vi /mnt/sda1/cmdline.txt
変更部分:
root=/dev/mmcblk0p3
↓
root=PARTUUID=68bafdb3-03
fstab の編集
マウントデバイス名を PARTUUID=xxxx 形式に書き換える。
vi /mnt/sda3/etc/fstab
例)
PARTUUID=68bafdb3-01 /boot vfat defaults,noatime 0 0
PARTUUID=68bafdb3-02 swap swap defaults,noatime 0 0
PARTUUID=68bafdb3-03 / ext4 defaults,noatime 0 0
※PARTUUID の指定はダブルクォートを外すこと
ラズパイ起動オプションの編集
ファイル新規作成
vi /mnt/sda1/config.txt
- SD カードスロット検索の無効化
- BlueTooth無効化 (省電力)
- Wi-Fi 無効化 (省電力)
- 起動時 Splash 画面OFF
- その他 Argon One M.2 Case 用の設定
dtparam=sd_poll_once dtoverlay=disable-bt dtoverlay=disable-wifi disable_splash=1 dtparam=i2c_arm=on enable_uart=1
デバイス起動順序の変更
ラズパイのデフォルトブートデバイスは microSD カードになっているので、USB に変更する。ラズパイには BIOS メニューが存在しないので、OS から変更する。
Raspberry Pi OS のターミナルを起動し raspi-config を実行:
sudo raspi-config
raspi-config 20210212 版の場合、下記の順でメニューを選択。メニュー名やコメントはバージョンによって違うことがある。
- Advanced Options Configure advanced settings
- Boot Order Choose network or USB device boot
- USB Boot Boot from USB if available, otherwise boot from SD Card
USB から起動
- 作業に使った Raspberry Pi OS をシャットダウンする。
- USBブリッジコネクタを含め全てコネクタを外し、(ネジの締めていない) 裏蓋を空ける
- MicroSD カードを抜く
- 再度裏蓋を閉め、USBブリッジコネクタを挿す。
- キーボード、モニタ、自宅ネットワークのLANケーブルを挿し、電源を入れる。
- SSD から CentOS が起動することを確認
CentOS 起動後の調整
コンソールから初回ログインする。 ユーザー: root、パスワードは centos。
パーティションを拡張し再起動する。
rootfs-expand
reboot
起動後、DHCP でネットワークアクセスができるはずなので、下記の順で作業する。
#OS アップデート
dnf -y update
#物理キーボードを日本語に変更
localectl set-keymap jp106
#システムロケール変更
#JP だと HDMI コンソールが文字化けするので en_US にしておく
localectl set-locale LANG=en_US.utf8
#タイムゾーン変更
timedatectl set-timezone Asia/Tokyo
#ホスト名変更 (お好みで)
hostnamectl set-hostname raspiyamk1
#root パスワード変更 (2回入力)
passwd
#再起動
reboot
起動時エラー対応
起動時にコンソールまたは /var/log/messages に下記のエラーが出る場合:
FAT-fs (sda1): Volume was not properly unmounted. Some data may be corrupt. Please run fsck.
FAT32 用のツールをインストール
dnf install dosfstools
下記の手順を実行
# fsck.fat -V /dev/sda1
fsck.fat 4.1 (2017-01-24)
0x25: Dirty bit is set. Fs was not properly unmounted and some data may be corrupt.
1) Remove dirty bit
2) No action
? 1
Starting check/repair pass.
Starting verification pass.
Perform changes ? (y/n) y
/dev/sda1: 238 files, 6907/36587 clusters
Wi-Fi の設定を完全 OFF
利用しないインターフェースを認識させないようにする。
nmcli radio wifi off
CentOS Stream 8 への切り替え
最初から Stream のはずなのになぜかなっていない。
現在のリリースを確認
# cat /etc/centos-release
CentOS Linux release 8.3.2011
Stream に切り替え:
dnf -y install centos-release-stream
dnf -y swap centos-{linux,stream}-repos
dnf -y distro-sync
# 終わったら再起動
reboot
再起動後、リリースを確認
# cat /etc/centos-release
CentOS Stream release 8
その他ツールインストール
#bash 補完パッケージ
dnf install -y bash-completion
#VIM 拡張
dnf install -y vim-enhanced
#ネットワークツール
dnf install -y telnet nc wireshark-cli tcpdump
SELinux 無効化
vi /etc/selinux/config
SELINUX=disabled
reboot
firewall 無効化
systemctl stop firewalld
systemctl disable firewalld
mDNS (Multicast DNS) 有効化
※2021/7/2 パッケージ nss-mdns のインストールと設定を追加
dnf install -y avahi nss-mdns
systemctl enable avahi-daemon
systemctl start avahi-daemon
名前解決順序を修正: /etc/nsswitch.conf
変更前
hosts: files mdns4_minimal [NOTFOUND=return] dns myhostname
変更後
hosts: files mdns_minimal [NOTFOUND=return] dns mdns myhostname
同じネットワーク内の Windows 10 の PowerShell から、“ホスト名.local” で名前解決ができるか確認する。例)
Resolve-DnsName raspiyamk1.local
固定IP設定
Network Manager の設定は nmcli にて行う
コネクション名の変更
日本語ロケールで構築したためか、コネクション名が「有線接続 1」になってしまっているため、コマンドラインで入力しやすい英語名に修正する。
#Connection名の確認
nmcli c
NAME UUID TYPE DEVICE
有線接続 1 a3f45bb3-2970-3e05-bd40-1b8a56a0fd80 ethernet eth0
#connection名変更
nmcli connection modify "有線接続 1" connection.id "wired1"
△ “Wired connection 1”
○ “wired1”
IPv4 アドレスの固定
確認方法
nmcli con show wired1 | grep ipv4
nmcli con modify wired1 ipv4.addresses 192.168.0.16/24
nmcli con modify wired1 ipv4.gateway 192.168.0.1
nmcli con modify wired1 ipv4.dns 192.168.0.1
nmcli con modify wired1 ipv4.method manual
nmcli con reload
nmcli con down wired1 & nmcli con up wired1
IPv6 アドレスの半固定
確認方法
nmcli con show wired1 | grep ipv6
nmcli con modify wired1 ipv6.method auto
nmcli con modify wired1 ipv6.ip6-privacy 0
nmcli con modify wired1 ipv6.addr-gen-mode eui64
nmcli con modify wired1 ipv6.token ::16
nmcli con reload
nmcli con down wired1 & nmcli con up wired1
お片付け
ここまでの設定で、他の端末から SSH ログインできるようになっているはずなので、忘れずに裏蓋をネジ止めしておく。(この記事を書き上げるために何度裏蓋を外し、MicroSD を付け外ししたことか‥‥)
あとは冷暗所に置いて LAN ケーブルと電源アダプタだけを接続し、いつでもリモートログインできる状態なことを確認する。
Raspi の状態表示コマンドの導入
vcgencmd が CentOS にはないので、ソースからビルドする
開発環境のインストール
dnf install cmake gcc gcc-c++ make git
ソース展開とコンパイル
mkdir ~/work
cd ~/work/
git clone https://github.com/raspberrypi/userland.git
cd userland
./buildme --aarch64
以上でインストールまで完了するので、下記フォルダを確認。
ls /opt/vc/bin
実行できるようにもろもろやる。
cat <<'__EOT__' > /etc/ld.so.conf.d/raspberrypi.conf
/opt/vc/lib
__EOT__
ldconfig
cat <<'__EOT__' >> ~/.bashrc
PATH="/opt/vc/bin:$PATH"
export PATH
__EOT__
root で再ログインし直すと、vcgencmd が使えるようになる。 例)
#温度
vcgencmd measure_temp
#CPU周波数を表示
vcgencmd measure_clock arm
#電圧を表示
vcgencmd measure_clock arm
#CPU(arm),GPUのメモリ使用量
vcgencmd get_mem arm