RaspberryPi Pico の開発環境を Ubuntu と RaspberryPi 4 で構築する

　最近 Raspberry Pi Pico W を購入したので、RaspberryPi Pico の開発環境を構築することにしました。
　RaspberryPi Pico の開発環境というとほとんどが Windows OS 向けの解説がほとんどですが、今回紹介するのは Ubuntu OS での構築方法です。

　ほとんどのサイトまたは書籍で紹介するのはWindows のリモートディスクトップ接続 (ラズパイ４側はVNC有効)を前提としたものが多いですが、**VSCode を使うと ラズパイ４では GUIなし (ランレベル3)の状態でビルドとインストール作業をローカルPCから実行することができます。**
※ソースのコーディングに vi エディタまたは Emacs でできる上級者の方は VSCodeのインストールすら不要です。**SSH接続でコマンドラインから全ての作業が可能です。**

![Raspi4_usb_connect_to_pico_w.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/6c4aa7b6-54c0-74f7-244d-dc803ba9629a.jpeg)

### 開発・ビルド環境

+ ターゲット: Raspberry Pi Pico W
+ ローカルPC: Ubuntu 22.04
    + RaspberryPi 4 とはSSHで接続
    + VSCode for Linux
        + ソースコード作成 (VSCodeのリモート機能)
        + ビルド、Pico用バイナリインストール (VSCide リモート実行)
+ Pico用バイナリービルド: RaspberryPi 4 Model B
    + OS: Raspberry Pi OS (Legacy, 64-bit) with desktop 
    + 起動ターゲット: ランレベル3 (multi-user.target) ※VNC無効
    + SSHサーバーが稼働しローカルPCからSSH接続できること

```bash
# OS 情報
pi@raspi-4-dev:~ $ lsb_release -a
No LSB modules are available.
Distributor ID:	Debian
Description:	Debian GNU/Linux 11 (bullseye)
Release:	11
Codename:	bullseye

# RUN LEVEL
pi@raspi-4-dev:~ $ who -r
run-level 3  2024-02-23 19:17
# Target
pi@raspi-4-dev:~ $ systemctl get-default
multi-user.target

# SSH server
pi@raspi-4-dev:~ $ systemctl show -p WantedBy sshd.service
WantedBy=multi-user.target
```

以降 Raspberry Pi 4 はラズパイ４、Raspberry Pi Pico は ラズパイ Pico として説明します。

ラズパイ4は GUIなしで起動しているため、**USBケーブルでラズパイPicoに接続しても /mediaにマウントされることはありません。**

```bash
pi@raspi-4-dev:~ $ ls -l /media/
合計 0
```

ローカルPCはGUIでログインしているので、**USBケーブルでラズパイPicoに接続すると /media にマウントされます。**

<img width="600" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/1dad65bf-2b7d-4818-f001-5dd3fbf4f95b.png">


### 参考にした書籍

　Windows、Linux、MacOS 向けに満遍なく解説されています。現時点で一番詳しく、電子工作をラズパイPicoを使ってプログラムする人には１冊持っていて損はないと思います。

+ ハード周りが詳しく説明図もわかりやすい
+ C/C++ がメインで中級者向け者以上の内容
※ **けっして初心者向けではないです**
+ 公式の Pico SDKが Linux でしか提供されていないため、Linux の知識が必要

![Book_CQPub_pico_strategy.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/249f7667-c8c3-dea4-d94d-4e3d103b0608.jpeg)

+ ラズベリー・パイ Pico/Pico W 攻略本 [CQ出版株式会社]
ISBN978-4-7898-4477-2 (2023 年 6 月 1日 第2版発行)
    + 第３章 Pico の Wi-Fi版「Pico W」
    + 第１部 開発のための基礎知識
        + 第１章 開発環境1 …ラズベリー・パイ4を使った公式推薦のプログラミング
 
### 公式ドキュメント

今回はこのドキュメントに従って構築します。

[Raspberry Pi Datasheets: Getting started with pico [PDF] ](https://datasheets.raspberrypi.com/pico/getting-started-with-pico.pdf)


## Pico用SDK構築

### 1. セットアップ

PDF の [**Chapter 1. Quick Pico Setup**] 参照

#### 1-0. ラズパイ4にSSHログイン

ローカルPCからラズパイ４にSSHでログインします
```bash
yukio@Dell-T7500:~$ ssh pi@raspi-4-dev
```

#### 1-1. セットアップスクリプトのダウンロード

```bash
pi@raspi-4-dev:~ $ wget https://raw.githubusercontent.com/raspberrypi/pico-setup/master/pico_setup.sh
```

#### 1-3. セットアップスクリプトの実行

ダウンロードしたスクリプトの実行権限を付与してスクリプトを実行
※標準出力にログを出力しつつファイルにも保存します。何かエラーがあった時に確認が容易になります。

```bash
pi@raspi-4-dev:~ $ mkdir -p work/logs
pi@raspi-4-dev:~ $ chmod +x pico_setup.sh 
pi@raspi-4-dev:~ $ ./pico_setup.sh | tee ~/work/logs/build_pico_setup.log
Running on a Raspberry Pi
Installing Dependencies
# ...ログ出力は省略...
Disabling Linux serial console (UART) so we can use it for pico
You must run sudo reboot to finish UART setup
```

#### 1-4. リブート

```bash
pi@raspi-4-dev:~ $ sudo reboot
```

## Pico W 用サンプルのビルド

**オンボードLEDの点滅サンプル**をビルドします

PDF [**3.1.2. Build "Blink" for the Pico W**] を参照


### 1. コマンドライン実行

ローカルPCからラズパイ４にSSHでログインして実行

#### 1-1. プリプロセス (cmake)

```~/pico/pico-examples/build``` ディレクトリで実行します

+ **PICO_BOARDビルドオプション**に **pico_w** を指定
+ CMAKE_BUILD_TYPEビルドオプション に Relese を指定

CMakeのリリースビルド方法について参考にしたサイト
[Raspberry Pico and CMake - Release and Debug builds, new C standards](https://community.element14.com/products/raspberry-pi/b/blog/posts/raspberry-pico-and-cmake---release-and-debug-builds-new-c-standards)

```bash
pi@raspi-4-dev:~/pico/pico-examples/build $ cmake .. -DPICO_BOARD=pico_w -DCMAKE_BUILD_TYPE=Release
PICO_SDK_PATH is /home/pi/pico/pico-sdk
PICO platform is rp2040.
Build type is Release
PICO target board is pico_w.
Using CMake board configuration from /home/pi/pico/pico-sdk/src/boards/pico_w.cmake
Using board configuration from /home/pi/pico/pico-sdk/src/boards/include/boards/pico_w.h
TinyUSB available at /home/pi/pico/pico-sdk/lib/tinyusb/src/portable/raspberrypi/rp2040; enabling build support for USB.
BTstack available at /home/pi/pico/pico-sdk/lib/btstack
cyw43-driver available at /home/pi/pico/pico-sdk/lib/cyw43-driver
Pico W Bluetooth build support available.
lwIP available at /home/pi/pico/pico-sdk/lib/lwip
Pico W Wi-Fi build support available.
mbedtls available at /home/pi/pico/pico-sdk/lib/mbedtls
Skipping some Pico W examples as WIFI_SSID is not defined
Adding 20 BTstack examples of type 'background'
Skipping TinyUSB dual examples, as TinyUSB hw/mcu/raspberry_pi/Pico-PIO-USB submodule unavailable
-- Configuring done
-- Generating done
-- Build files have been written to: /home/pi/pico/pico-examples/build
```

#### 1-2. オンボードLEDの点滅サンプルのビルド

(1) Pico w 用のLED点滅サンプルに移動
```bash
pi@raspi-4-dev:~/pico/pico-examples/build $ cd pico_w/wifi/blink/
pi@raspi-4-dev:~/pico/pico-examples/build/pico_w/wifi/blink $ ls -l
合計 132
drwxr-xr-x 3 pi pi   4096  2月 24 20:15 CMakeFiles
-rw-r--r-- 1 pi pi 124398  2月 24 20:05 Makefile
-rw-r--r-- 1 pi pi   1140  2月 24 20:05 cmake_install.cmake
```

(2) コンパイル実行

```bash
pi@raspi-4-dev:~/pico/pico-examples/build/pico_w/wifi/blink $ make -j4
Scanning dependencies of target bs2_default
Scanning dependencies of target PioasmBuild
[  0%] Performing build step for 'ELF2UF2Build'
[  0%] Creating directories for 'PioasmBuild'
# ... 一部省略 ...
[100%] Linking CXX executable picow_blink.elf
[100%] Built target picow_blink
```

(3) 出力内容確認

```bash
pi@raspi-4-dev:~/pico/pico-examples/build/pico_w/wifi/blink $ ls -lrt
合計 2908
-rw-r--r-- 1 pi pi   1140  2月 24 20:05 cmake_install.cmake
-rw-r--r-- 1 pi pi 124398  2月 24 20:05 Makefile
drwxr-xr-x 3 pi pi   4096  2月 24 20:15 CMakeFiles
-rw-r--r-- 1 pi pi 259828  2月 24 20:17 picow_blink.elf.map
-rwxr-xr-x 1 pi pi 323056  2月 24 20:17 picow_blink.elf
-rw-r--r-- 1 pi pi 745573  2月 24 20:17 picow_blink.hex
-rwxr-xr-x 1 pi pi 265048  2月 24 20:17 picow_blink.bin
-rw-r--r-- 1 pi pi 704839  2月 24 20:17 picow_blink.dis
-rw-r--r-- 1 pi pi 530432  2月 24 20:17 picow_blink.uf2
```

#### 1-3. コマンドラインから実行

PDF [**3.2.1. Using the command line**] 参照

以下が コマンドラインで実行する場合の説明の抜粋で、この内容通りに実行します。

![GettingStarted_3_2_1_UsingCommand.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/0dd86f1d-9948-583c-472f-fc50f9b20264.png)

**以降のコマンドの実行にはroot権限が必要です**

##### 1-3-1. ラズパイPicoデバイスの確認
+ ラズパイ４とラズパイPico を USBケーブルで接続する
※**初回は自動でマウントされないので[BOOTSEL]ボタンを押す必要はありません。**
+ ラズパイPico デバイス: **sda1** 

```bash
pi@raspi-4-dev:~ $ dmesg | tail
[ 5473.827172] scsi host0: usb-storage 1-1.3:1.0
[ 5474.853050] scsi 0:0:0:0: Direct-Access     RPI      RP2              3    PQ: 0 ANSI: 2
[ 5474.853573] sd 0:0:0:0: Attached scsi generic sg0 type 0
[ 5474.853848] sd 0:0:0:0: [sda] 262144 512-byte logical blocks: (134 MB/128 MiB)
[ 5474.855159] sd 0:0:0:0: [sda] Write Protect is off
[ 5474.855174] sd 0:0:0:0: [sda] Mode Sense: 03 00 00 00
[ 5474.857827] sd 0:0:0:0: [sda] No Caching mode page found
[ 5474.857842] sd 0:0:0:0: [sda] Assuming drive cache: write through
[ 5474.871213]  sda: sda1
[ 5474.871905] sd 0:0:0:0: [sda] Attached SCSI removable disk
```

##### 1-3-2. ラズパイPico を手動でマウント
+ **初回のみマウントディレクトリを作成**: /mnt/pico
+ **ラズパイPicoデバイス(/dev/sda1) をラズパイ４の /mnt/pico にマウントする**

```bash
pi@raspi-4-dev:~ $ sudo mkdir -p /mnt/pico
pi@raspi-4-dev:~ $ sudo mount /dev/sda1 /mnt/pico
pi@raspi-4-dev:~ $ ls -l /mnt/pico/
合計 8
-r-xr-xr-x 1 root root 241  9月  6  2008 INDEX.HTM
-r-xr-xr-x 1 root root  62  9月  6  2008 INFO_UF2.TXT
```

##### 1-3-3. ラズパイPico にバイナリをコピーし実行
+ picow_blink.uf2　をマウントディレクトリにコピーする
+ sync コマンドを実行する

```bash
pi@raspi-4-dev:~/pico/pico-examples/pico_w/wifi/blink $ sudo cp picow_blink.uf2 /mnt/pico
pi@raspi-4-dev:~/pico/pico-examples/pico_w/wifi/blink $ sudo sync
```

おお〜 ここでビルトインLEDが点滅しました！

![pico_w_blink_led_1_up.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/82bb4c4c-a0e9-1ecb-8ba0-1e2072b98261.jpeg)

##### 1-3-4. マウント解除

以下はPDFの記載箇所をGoogle翻訳したものです ※syncコマンド実行後
>RP2040 は、USB 大容量ストレージ デバイスとして自動的に切断され、コードを実行しますが、安全のため、手動でもアンマウントします。

```bash
pi@raspi-4-dev:~/pico/pico-examples/pico_w/wifi/blink $ sudo umount /mnt/pico
```

##### 1-3-5. ２回目以降の操作

　２回目以降に USBケーブルで接続すると電源として接続され前回投入したバイナリが実行されます。※Picoはストレージとしてマウントされない

別なバイナリを実行させる場合は

+ **[BOOTSEL] を押しながら USBケーブルを接続**
+ Pico デバイス(/dev/sda1) を ラズパイ４にマウント (/mnt/pico ※残っている)
+ 別なバイナリをコピーし sync コマンドを実行
+ マウント解除


### 2. VSCodeからサンプルをビルド

　ここでラズパイ４のSDカードを外し、SDカードに更新済みのOSイメージを書き込みしてから再実行します。

#### 2-0. セットアップをコマンドライン実行

Picoセットアップの実行は、ローカルPCからSSHログインして実行します。
※1 **Picoセットアッブ実行中にVSCodeがインストールされます。**
※2 Picoセットアップ完了後にリブート

#### 2-1. Remote-SSH呼び出し

[F1] キーを押下し、SSHと入力して Remote-SSHを選択します

<img width="600" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/d11ef8cb-958e-a1f3-d308-1ffb1de38311.png">


#### 2-2. ラズパイ4のアドレスを入力

<img width="600" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/420af145-57f4-396f-9a94-4dff55cda48b.png">

#### 2-3. ラズパイ4に接続

　背面がローカルPCのVSCode、前面がラズパイ４側にリモート接続したVSCode画面です。

![vscode_ssh_remote_00_opened.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/18122b16-2778-b942-e75f-d6d6d647446a.png)

#### 2-4. サンプルのソースフォルダを開く

画面 左上の [フォルダを開く] ボタンを押下し、サンプルのフォルダを開きます
※今回はビルトインLEDの点滅サンプル (~/pico/pico-examples/pico_w/wifi/blink)


![vscode_ssh_remote_03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/2dfbf9ea-f626-cda6-4392-7131546bc6bc.png)

フォルダ内のファイルの作成者を信頼する

<img width="550" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/947abca1-4d3d-59c9-6e9f-322563f73179.png">

こちらがフォルダを開いたときの画面　

![vscode_ssh_remote_05_blink_src_opened.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/5eecaacf-f47b-c74f-ee84-aae4b27d556a.png)

#### 2-5. VSCodeのターミナルからプリプロセス実行

1-1. プリプロセス (cmake) と同じ

```$ cmake .. -DPICO_BOARD=pico_w -DCMAKE_BUILD_TYPE=Release```

![vscode_ssh_remote_00_opened_01_cmake_pico_w_release.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/bd28db25-4129-7156-6f79-0fb356a7437a.png)


#### 2-6. ビルトインLED点滅サンプルのコンパイル

(1) ```build/pico_w/wifi/blink/``` サブディレクトリに移動してコンパイル 

![vscode_ssh_remote_00_opened_02_make_pico_w_blink.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/9aa100ee-fcfe-c0a7-1773-25974f00e0ca.png)

(2) コンパイル完了

![vscode_ssh_remote_00_opened_03_make_pico_w_blink_complete.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/78d44029-198d-c3fa-5fb2-c996cc89e590.png)

(3) Picoデバイスを手動でマウントしてバイナリをデバイスにコピー

![vscode_ssh_remote_00_opened_04_cp_blink_to_pico_w.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/e4af712d-f73d-40ce-5178-4305d3f3ecee.png)

(4) ラズパイ４とラズパイPicoをUSBで接続してサンプルを実行

![pico_w_blink_led_0.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/5152340a-a8ad-27bb-b1c1-e78748c8fe79.jpeg)

#### 2-7. ビルトインLED点滅サンプルの改造

+ 点滅間隔を200ミリ秒から 2000ミリ秒に修正し、再コンパイル
+ 実行方法は「1-3-4. ２回目以降の操作」と同じです


![vscode_ssh_remote_00_opened_05_edit_src_rebuild.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3583120/20766a0c-ee8c-9b82-5e5a-60841a166c97.png)

### 結論

　ラズパイ４でVNCサーバーを稼働させなくともコマンドライン、またはVSCodeを通じてサンプルをビルドし実行することかできます。特にラズパイ４側のメモリリソースが少ない場合はこの方法がベストではないでしょうか?

　Windows PCからリモートデスクトップ経由で実行するにしても、Linuxの知識がないとラズパイPico向けセットアップ実行とビルドの実行は難しいと感じました。
 ※私は25年以上のLinux経験があります。Ubuntuでの開発は15年近くになります。

　参考書籍ではセットアップ時に以下の操作が記載されており、最初は書籍通りにコマンドラインからセットアッブしました。
 + **セットアップ実行前にシステムライブラリ libusb (dev)をインストールする**
 + **VSCodeをインストールせず、OPENOCDをビルドしない**

　２回目は公式ドキュメント(PDF)のデフォルトでコマンドラインからセットアップを実行、３回目はVSCodeでの操作の画面をとるため途中からVSCodeのターミナルから実行。３回とも正常にセットアップが完了しサンプルの実行もできました。