Raspberry Pi Picoのオンボードフラッシュメモリの一部をlittlefsでフォーマットし、Pico内部から読み書きしつつ、USB接続した普通のホストPC(とても重要)にマウントしてファイルを読み出すサンプルというか概念実証をしました。
組み込みデバイスにとってlittlefsは電源切断にも耐性があってカッコよくて良いですよね。ですが、普通のPCではサポートされていないファイルシステムなので、「デバイスをUSBメモリのようにPCにマウントしてしてファイルを読み書きしたい」たぐいのユースケースには色々と難があります。「それ、LinuxとFUSEならできるよ」とか言われても困るし。
マイコン側USBマスストレージクラスドライバ上に、littlefsをFAT12に擬態する中間層を設けることで実現できるなーと思いつきで書き始めて。できました。
サンプルでは、PicoのBOOTSELボタンを押した回数をSENSOR.TXT
に追記しています。
マイコン側ではlfs_file_open(..., LFS_O_RDWR|LFS_O_APPEND|LFS_O_CREAT)
して lfs_file_write()
するだけなので簡単でいいですね。PCに接続するとFAT12を備えたUSBメモリとして認識され、SENSOR.TXT
を読み出すことができます。
マイコン上ではlittlefsファイルシステムを操作しつつ、ホストPC側からはFATファイルシステムのUSBメモリとして読み出せる。そんな構成ができます。この実装と手法には様々な制限がありますが、他のマイクロコントローラでも同様のアプローチで実現できるはずです。くどいようですが、これは概念実証なのでリードオンリーです。 (その後リードライト両方をサポートしました)
擬態のしかた
FAT12は非常にシンプルなファイルシステムなので、簡単に擬態できます。USBホストがリクエストしたブロックデバイスの位置に応じて、マイクロコントローラーが適切なFAT12ブロックを組み立てて返します。
ブロック0
静的なFAT12ブートブロックを返します
ブロック1
擬態したFATテーブルを返します。littlefsのルートディレクトリを検索し、各ファイルのファイルサイズに応じてFATファイルシステム上のストレージ位置の情報を保持するFATテーブルを組み立てて返します。
ブロック2
擬態したルートディレクトリエントリを返します。littlefsのルートディレクトリを検索し、FATのルートディレクトリブロックを組み立てて返します。
ブロック3以降
littlefsの対応するファイルブロックを返します。リクエストされたブロックを保持するファイルをFATルートディレクトリエントリで検索し、littlefs上のファイル名とオフセット位置を取得します。littlefsのファイルを開き、オフセット位置のデータを返します。
今後について
戯れに書いたので特にないです。
これを書いた時点ではRead onlyでしたが、その後ナゾのやる気スイッチが入りWrite accessもサポートしました。littlefsファイルシステム上のファイルを、普通のPCから作成・読み込み・更新・削除できます。