5
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

Raspberry Pi 4BをOTG設定してUSBストレージとして使う

Last updated at Posted at 2023-05-14

この記事について

WindowsPCなどからUSBケーブル接続したラズパイにデータ転送する環境の構築手順の説明です。

  • ラズパイのUSB On-The-Go(OTG)設定
  • USB mass strage設定
  • systemd設定
  • microSDカードのROM化設定

相変わらず平日は時間が取れず週末に手を付けましたが、今回もしっかり嵌りポイントがあったので記録を残しておきたいと思います。

参考文献

こちらの記事を参考にしました御礼申し上げます。

環境

Raspberry Pi: Raspberry Pi 4 Model B Rev 1.2
OS: Raspberry Pi OS Lite 64-bit (Raspbian GNU/Linux 11 (bullseye))
microSDカード: 16GB、32GB各一枚ずつ
USBケーブル: usb-A <-> usb-c オスオス
クライアント機: DesktopPC(Windows11 Pro)

事前準備

こちらの記事等を参考にRaspberry Pi Imagerで起動用microSDカードを作成します。

構築手順

USBストレージ用記憶領域の確保

嵌りポイントその①です。初めに、USBストレージとして割り当てるボリュームを作る為に、microSDカードに空き領域を確保します。

邪道ですが手持ちのサイズ違いmicroSDカードを使って準備しました。

  • Imagerで16GBカードに起動イメージを作る
  • 16GBカードのimageで一度起動してupdateとupgradeする
  • 16GBカードimageを保存して32GBのmicroSDカードに書き込む

記事の手順を使われる際は、普通にラズパイimageの入ったSDカードを圧縮してimage保存する等ご自分のやり易い方法で準備ください。

昨年まではImagerでimage書き込み後にcmdline.txtから"init=/usr/lib/raspi-config/init_resize.sh"を削除することで初回起動時にパーティションの自動拡張を止められたようですが、記事執筆時点(2023.05.14)では出来ませんでした。

ということでmicroSDカードを2枚使い「imageを作って別のマシンで圧縮して保存する」より一手間少なく済ませました。

USB On-The-Go(OTG)設定

USB On-The-Go(OTG)

接続したデバイス(WindowsPC)側からラズパイをUSBストレージとして認識させるには起動時OTG設定が必要になります。以下、WikiPediaより

USB On-The-Go(略してUSB OTG)は、USB機器どうしを直接接続するインタフェース規格である。パソコン等をホストとせずに、動作時にホスト機器を動的に切り替える機能を拡張したもの。 IEEE 1394のように直接接続できるので、いろいろな機器に応用できる。2001年12月18日に発行されたUSB OTG 2.0 Revision 1.0 は High Speed (480Mbps) がオプション扱いとなっていたが[1]、2009年5月8日に発行された USB OTG 2.0 Revision 2.0 では High Speed を含み[2]、2011年7月1日に発行された USB OTG 3.0 では SuperSpeed (5Gbps) を含む。

/boot/config.txt

ラズパイのOTGを有効にする為に、起動設定に以下の一行を追加します。

/boot/config.txtに追加
dtoverlay=dwc2

USB mass strage設定

/boot/cmdline.txt

g_mass_storageを使ってストレージ起動するのに以下を起動設定に追加します。

/boot/cmdline.txtに追加
modules-load=dwc2,g_mass_strage

exfat-fuseインストール

exfatをUSBメモリのフォーマットとして使用するためにexfat-fuseをインストールします。

$ sudo apt install exfat-fuse

パーティション設定

microSDカードの空き領域にUSBストレージとして利用する領域を確保します。
初回起動直後のパーティションの状態は以下のようになっています。
16GBのSDカードのimageがそのまま書き込まれています。

$ sudo parted /dev/mmcblk0
GNU Parted 3.4
Using /dev/mmcblk0
Welcome to GNU Parted! Type 'help' to view a list of commands.
(parted) p
Model: SD EB1QT (sd/mmc)
Disk /dev/mmcblk0: 32.0GB
Sector size (logical/physical): 512B/512B
Partition Table: msdos
Disk Flags:

Number  Start   End     Size    Type     File system  Flags
 1      4194kB  273MB   268MB   primary  fat32        lba
 2      273MB   15.9GB  15.7GB  primary  ext4

15.9GB以降の空き領域にUSBストレージ用のボリュームを作ります。

(parted) mkpart

primary partitionでWindowsファイル用にntfsで作ります。

Partition type?  primary/extended? primary
File system type?  [ext2]? fat32

ボリュームサイズは約1GBにします。

Start? 15.9GB
End? 16.9GB
(parted) p
Model: SD EB1QT (sd/mmc)
Disk /dev/mmcblk0: 32.0GB
Sector size (logical/physical): 512B/512B
Partition Table: msdos
Disk Flags:

Number  Start   End     Size    Type     File system  Flags
 1      4194kB  273MB   268MB   primary  fat32        lba
 2      273MB   15.9GB  15.7GB  primary  ext4
 3      15.9GB  16.0GB  88.1MB  primary  ntfs         lba

partedから抜けます。

(parted) q
Information: You may need to update /etc/fstab.

/etc/fstabを書き換えなさいと優しく怒られますが、fstabではコピーしたファイルのTZが上手く修正出来なかったので今回は別の方法でmountします。

blk03にUSBストレージ用の新しいボリュームができたことを確認します。

$ sudo fdisk -l
Device         Boot    Start      End  Sectors  Size Id Type
/dev/mmcblk0p1          8192   532479   524288  256M  c W95 FAT32 (LBA)
/dev/mmcblk0p2        532480 31116287 30583808 14.6G 83 Linux
/dev/mmcblk0p3      31117312 33007615  1890304  923M  7 HPFS/NTFS/exFAT

ボリュームタイプ変更

古い設備にUSB接続する予定があるのでFAT32に変換しておきます。

$ sudo mkfs.vfat -F 32 /dev/mmcblk0p3

ラズパイ側のmount point設定

Linuxのファイルシステム側のmount pointとして、user直下に/usbを作ってUSBストレージ用ボリュームをmountします。mount pointは意図してtmpfsに設定しますのでデータロスには注意が必要です。

/etc/fstab
tmpfs /home/user/usb   tmpfs   defaults,size=1024m,mode=0755   0 0

mountコマンドはcronの起動時設定に組み込みます。Windowsのtimestampが+09:00になってしまうのでマウント時にオフセット処理します。

crontab
@reboot sudo mount -otime_offset=540 /dev/mmcblk0p3 /home/user/usb

systemd設定

サービス化してmass starageを起動/停止します。

$ sudo nano /lib/systemd/system/usb_storage.service
/lib/systemd/system/usb_storage.service
[Unit]
Description = USB MASS Storage Service
After = local-fs.target

[Service]
ExecStart = /sbin/modprobe g_mass_storage file=/dev/mmcblk0p3 removable=y
ExecStop = /sbin/modprobe -r g_mass_storage
Type = oneshot
RemainAfterExit = true

[Install]
WantedBy = multi-user.target

サービスを起動時有効にします。

$ sudo systemctl enable usb_storage

動作確認

mass strageがUSBストレージとしてWindowsPCから認識できるか確認します。

OTG接続port

結論から言うとPi4BではUSB-c portと相手側の端末をUSBケーブルで接続します。

実は今回のメイン嵌りイベントはここでした。

2023.05.14時点でラズパイのどのUSB portでOTG接続できるかを公式のアナウンスで確認したところZeroに関するドキュメントしか確認することができませんでした。

この部分です。

Specification
802.11 b/g/n wireless LAN
Bluetooth 4.1
Bluetooth Low Energy (BLE)
1GHz, single-core CPU
512MB RAM
Mini HDMI port and micro USB On-The-Go (OTG) port
Micro USB power
HAT-compatible 40-pin header
Composite video and reset headers
CSI camera connector

micro USB On-The-Go (OTG) port Micro USB powerとあるので給電port以外のUSB portでOTGすると捉えましたが、残念ながらPi4BではUSB-c portを使う必要がありました。半日以上溶かしましたがこちらの記事のおかげでクリアすることができました。本当に感謝です。

mass strage起動

ここまでで自動起動設定が完成しているので一度電源を落とします。

$ sudo shutdown now

普段は給電に使うラズパイのUSB-cとWindowsPCのUSB portをケーブルでつなぎ再起動します。

しばらくするとWindows側でUSBデバイス認識の通知が出ててラズパイをUSBストレージ化出来たとこが確認できます。

ファイル転送

Windows上で立ち上がったexplorerでUSBドライブ上にサンプルテキストを作成するとラズパイのmount先でも確認できました。

~/usb $ ls -lah
合計 16K
drwxr-xr-x 3 root     root     4.0K  1月  1  1970  .
drwxr-xr-x 6 user     user     4.0K  5月 14 14:16  ..
drwxr-xr-x 2 root     root     4.0K  5月 14 13:22 'System Volume Information'
-rwxr-xr-x 1 root     root        4  5月 14 13:51  test1.txt

microSDカードのROM化設定

最後に連続使用を想定して、今まで同様microSDカードにROM化設定をします。

ROM化設定/解除/再設定用のscriptを/protectにまとめ、初期設定用のscript(protect_prov.sh)と一緒にuser directoryにコピーして実行します。

sudo chmod +u+x protect_prov.sh
./protect_prov.sh

それぞれのscriptは以下です。

ROM化設定用script

protect_prov.sh
#!/bin/bash

test -d ./root-ro
if [ $? == 0 ]; then
  sudo rm -r ./root-ro
  echo "Elminated old root-ro"
else
  echo "root-ro is not exist" 
fi

sudo cp ~/protect/protect.sh /root
sudo cp ~/protect/protect /bin
sudo cp ~/protect/nonprotect /bin

sudo chmod u+x /root/protect.sh /bin/protect /bin/nonprotect
sudo chown root:root /root/protect.sh /bin/protect /bin/nonprotect

sudo sh /root/protect.sh

sudo rm *prov.sh
sudo rm -r ./protect

sudo reboot
/protect/protect.sh
#!/bin/bash

echo Installing all dependencies
apt-get install git subversion rsync gawk busybox bindfs -y
echo Disabling swap
dphys-swapfile swapoff
dphys-swapfile uninstall
update-rc.d dphys-swapfile disable
systemctl disable dphys-swapfile
echo Cloning repository
git clone https://github.com/josepsanzcamp/root-ro.git
echo Doing the setup
rsync -va root-ro/etc/initramfs-tools/* /etc/initramfs-tools/
mkinitramfs -o /boot/initrd.gz
echo initramfs initrd.gz >> /boot/config.txt
echo Restarting RPI
exit

ROM化解除用script

/protect/nonprotect
#!/bin/sh

if [ -e /mnt/boot-ro/config.txt ]; then
    sudo mount -o remount,rw /dev/mmcblk0p1
    sudo grep -v initramfs /mnt/boot-ro/config.txt >/tmp/config.txt
    sudo cp /tmp/config.txt /mnt/boot-ro/config.txt
    sudo reboot
else
    echo Already write enabled
fi

ROM化再設定用script

/protect/protect
#!/bin/sh

if [ -e /mnt/boot-ro/config.txt ]; then
    echo Already write protected
else
    sudo grep -v initramfs /boot/config.txt >/tmp/config.txt
    sudo echo initramfs initrd.gz >> /tmp/config.txt
    sudo cp /tmp/config.txt /boot/config.txt
    sudo reboot
fi

構築手順の説明は以上となります。

追記

2023.05.14 誤記訂正
2025.05.15 説明欠落箇所(exfat-fuseインストール)を追記

5
5
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
5
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?