RP2040をMicroPython化する際に使用する.uf2ファイルは、単なるMicroPythonの実行可能バイナリを格納したものではなく、RP2040のブートローダーと連携して書き込みを行うための特殊なフォーマットです。RP2040内部で行われる処理を詳細に解説します。
1. BOOTSELモードへの移行:
- RP2040をMicroPython化する最初のステップは、RP2040をBOOTSELモードにすることです。これは通常、以下のいずれかの方法で行います。
- 専用ボタン: RP2040ボードにBOOTSELボタンが搭載されている場合、そのボタンを押しながらUSBケーブルでPC(この場合はRaspberry Pi)に接続します。
- 電源投入シーケンス: 特定のGPIOピンの状態を保持したまま電源を投入することで、BOOTSELモードに入るように設計されているボードもあります。
- BOOTSELモードに入ると、RP2040の内蔵ROMに格納されたファーストステージブートローダーが起動します。このブートローダーは非常に小さく、基本的なUSB通信機能のみを持っています。
2. USBマスストレージデバイス (MSC) としてのエミュレーション:
- ファーストステージブートローダーは、RP2040をUSBマスストレージデバイス(USBメモリ)としてPCに認識させる処理を行います。この時、Raspberry Piのファイルマネージャーには「RPI-RP2」などの名前のボリュームとして表示されます。
3. .uf2 ファイルの認識:
- Raspberry Piから.uf2ファイルがRPI-RP2ボリュームにコピーされると、RP2040のブートローダーはこれを特別なファイルとして認識します。
4. .uf2 ファイルの構造:
- .uf2ファイルは、Microsoftが開発したUSB Flashing Formatというフォーマットに従っています。
- ファイルは512バイトの固定長ブロックで構成されています。
- 各ブロックには、以下の情報を含む32バイトのヘッダーが含まれています。
- マジックナンバー (0x0A324655, "UF2\n"): ファイルの開始とUF2フォーマットであることを示す識別子です。
- セカンドマジックナンバー (0x9E5D5157): ヘッダーの正当性を示すためのものです。
- フラグ: さまざまなオプションフラグ。
- 書き込みアドレス: このブロックのデータがRP2040のフラッシュメモリのどの位置に書き込まれるべきかを示すアドレスです。
- データ長: このブロックに含まれる実際のデータのバイト数(通常は256バイト)。
- ブロックシーケンス番号: ファイル内のブロックの順番を示す番号(0から始まります)。
- 全ブロック数: .uf2ファイル全体のブロック数。
- ファイルサイズ/ボードファミリーID/ゼロ: ファイルサイズやボードの種類を示す情報が含まれることがあります。
- ヘッダーの後には、実際にRP2040のフラッシュメモリに書き込むべきデータ (最大476バイト) が続きます。
- 各ブロックの最後には、ファイナルマジックナンバー (0x0AB16F30) が含まれています。
5. ブートローダーによる書き込み処理:
- ブートローダーは、コピーされた.uf2ファイルをブロックごとに読み込み、ヘッダー情報を解析します。
- ヘッダーに含まれる書き込みアドレスに基づいて、ブロック内のデータをRP2040の外部フラッシュメモリの対応するアドレスに書き込みます。
- ブートローダーは、.uf2ファイル内のすべてのブロックを順番に処理し、フラッシュメモリにMicroPythonファームウェアのバイナリデータを書き込んでいきます。
- 書き込み処理中、ブートローダーはエラーチェックサムなどの検証を行うこともあります。
6. 書き込み完了と再起動:
- .uf2ファイル内のすべてのブロックの書き込みが完了すると、ブートローダーはRP2040をリセット(再起動)します。
7. MicroPythonファームウェアの起動:
- リセット後、RP2040は通常のブートシーケンスを開始します。
- 今度はBOOTSELモードではなく、外部フラッシュメモリの先頭に書き込まれたMicroPythonファームウェアを読み込み、実行を開始します。
まとめ:
.uf2ファイルを用いたMicroPython化の際、RP2040内部では以下の処理が行われています。
- BOOTSELモード: 特殊な起動モードに入り、内蔵ROMのファーストステージブートローダーが起動します。
- MSCエミュレーション: RP2040がUSBマスストレージデバイスとしてPCに認識されます。
- .uf2ファイル認識: ブートローダーがコピーされた.uf2ファイルを特別なファイルとして認識します。
- ヘッダー解析: ブートローダーが.uf2ファイルの各ブロックのヘッダー情報を読み取ります。
- フラッシュ書き込み: ヘッダーの書き込みアドレスに従って、ブロック内のデータが外部フラッシュメモリに書き込まれます。
- 再起動: すべてのブロックの書き込みが完了すると、RP2040がリセットされます。
- MicroPython起動: リセット後、外部フラッシュメモリに書き込まれたMicroPythonファームウェアが起動します。
このように、.uf2ファイルは、RP2040の内蔵ブートローダーと連携することで、簡単かつ安全にMicroPythonファームウェアをフラッシュメモリに書き込むための仕組みを提供しています。