Jetson nanoでPX-S1UD/PX-Q1UDを使う

#はじめに
Raspberry Piで録画サーバー構築の記事がたくさんあったのでJetsonでも構築できるだろと思って色々つまづきまくったことのまとめとなっております。
Jetson nanoで構築しようと思ったきっかけは、仕様を眺めているとエンコード性能が、`4K @ 30 | 4x 1080p @ 30 | 9x 720p @ 30 (H.264/H.265) `とされているので、必要性は置いておいて4chリアルタイムエンコードができるのでは？？？と思って構築を始めました。
あくまでJetsonでチューナーを使用できる状態にするまでを焦点に当てているので、録画のセットアップ等は他の記事をあたってください。


## 必要な物
- Jetson Nano
- PX-Q1UD or PX-S1UD

## 前提環境
Jetson nanoにOSインストールを行い、SSH等でターミナル操作ができること

## OS環境
Jetson Nano Developer Kit SD Card Image JP 4.4
Kernel 4.9.140

## 手順
### はじめに
上記の環境ではPX-Q1UDを刺すと、

```bash:terminal
$ dmesg
[ 1942.289567] usb 1-2.1.1: new high-speed USB device number 11 using tegra-xusb
[ 1942.310251] usb 1-2.1.1: New USB device found, idVendor=3275, idProduct=0080
[ 1942.310257] usb 1-2.1.1: New USB device strings: Mfr=1, Product=2, SerialNumber=0
[ 1942.310261] usb 1-2.1.1: Product: PX-S1UD Digital TV Tuner
[ 1942.310265] usb 1-2.1.1: Manufacturer: PLEX Digital TV Tuner
```
このようなカーネルメッセージが表示されるのみで、DVBドライバが適用されません。
Jetson標準のカーネルではDVBドライバが省略されているためです。
**第一のつまづき:sob:**
### カーネルのビルド
非常にわかりやすい参考記事があります。コマンドの意味等はこちらを参照してください。
https://qiita.com/yamamo-to/items/6fc622df7b5cce3eccfb

#### カーネルのconfig


カーネルのダウンロードからConfigの設定画面を出すまでのコマンド

```bash:terminal
$ sudo jetson_clocks
$ sudo apt install -y libncurses5-dev
$ cd && mkdir kernel && cd kernel
$ wget https://developer.nvidia.com/embedded/L4T/r32_Release_v4.3/Sources/T210/public_sources.tbz2
$ tar xvf public_sources.tbz2
$ cd Linux-for-Tegra/source/public
$ tar xvf kernel_src.tbz2
$ cd kernel/kernel-4.9
$ zcat /proc/config.gz  > .config
$ make menuconfig
```
[最新のソースのDL先](https://developer.nvidia.com/embedded/linux-tegra)
`L4T Driver Package (BSP) Sources`がURLとなっています

この画面まで進むと、多少の時間の後、

![スクリーンショット 2020-05-11 19.02.08.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/262314/16360023-ea7f-5c29-056e-718093344064.png)
menuconfigの画面が表示されるので、
Device Drivers -> Multimedia supportの順に進みます。
![スクリーンショット 2020-05-11 19.02.17.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/262314/54db54e7-469c-b9e1-a72a-1b8e6f7bb0b6.png)
![スクリーンショット 2020-05-11 19.02.35.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/262314/c2895295-2e64-5ffc-a137-c20bca3a3262.png)

Multimedia support内で

- [y]Digital TV Support
- [M]Media USB Adapters -> Siano SMS1xxx based MDTV receiver

を変更します

変更したらSaveで保存しEsc連打で抜けましょう

#### カーネルパッチ
これでBuildして使用できたらいいのですが、Sianoのドライバにarm64で使用する際にバグがあるらしくチューナーを挿すと一定時間後にハングアップします。
**第二のつまづき:sob:**

dmesgを確認すると
`smsusb:smsusb_onresponse: error, urb status -71, 0 bytes`
`smmu_dump_pagetable なんたら`
`mc-err なんたらかんたら`
こんな感じのエラーが流れます。

問題を解決するためのパッチが公開されているのでそれを当てていきます。

非常にありがたい参考記事
https://blog.ayushio.com/2018/12/27/rock64-record/

```bash:terminal
$ cd ~/kernel/Linux_for_Tegra/source/public/kernel
$ wget -O siano.patch https://patchwork.kernel.org/patch/10256121/raw/
$ cd kernel-4.9
$ patch -p1 < ../siano.patch
```

####　ビルド
```bash:terminal
$ make oldconfig
$ make prepare
$ make modules_prepare
$ make -j4 Image && make -j4 modules
```
1時間程度かかります。しっかり冷却してあげましょう。

#### インストール
```bash:terminal
$ sudo make modules_install
$ sudo cp -p /boot/Image /boot/Image.org
$ sudo cp arch/arm64/boot/Image /boot/Image
```
ここまで終わると再起動（少し時間かかります）

### fimware fileの設置
`isdbt_rio.ino`というファイルを`/lib/firmware`以下に設置する必要があります。

```bash
curl -O http://plex-net.co.jp/plex/px-s1ud/PX-S1UD_driver_Ver.1.0.1.zip
unzip PX-S1UD_driver_Ver.1.0.1.zip
sudo cp PX-S1UD_driver_Ver.1.0.1/x64/amd64/isdbt_rio.inp /lib/firmware/
```


## 確認
PX-Q1UD / PX-S1UDをUSBポートに刺した後、
`dmesg`を実行してみると、

```bash:terminal
[ 2402.115532] usb 1-2.1.1: new high-speed USB device number 10 using tegra-xusb
[ 2402.136510] usb 1-2.1.1: New USB device found, idVendor=3275, idProduct=0080
[ 2402.136515] usb 1-2.1.1: New USB device strings: Mfr=1, Product=2, SerialNumber=0
[ 2402.136519] usb 1-2.1.1: Product: PX-S1UD Digital TV Tuner
[ 2402.136522] usb 1-2.1.1: Manufacturer: PLEX Digital TV Tuner
[ 2402.137321] smsusb:smsusb_probe: board id=18, interface number 0
[ 2402.189130] DVB: registering new adapter (Siano Rio Digital Receiver)
[ 2402.189613] usb 1-2.1.1: DVB: registering adapter 0 frontend 0 (Siano Mobile Digital MDTV Receiver)...
[ 2402.189718] smsdvb:smsdvb_hotplug: DVB interface registered.
[ 2402.189721] smsmdtv:smscore_init_ir: IR port has not been detected
[ 2402.189724] smsusb:smsusb_probe: Device initialized with return code 0
```
このようなログが流れ、/dev/dvb/以下にデバイスが存在していたら成功です。

ちなみに、PX-Q1UDにおいて外部電源を入れた状態で接続するとエラーが表示されることがあったので、その際は外して試してみてください。



## 最後に
意外と日本語記事が多くてびっくり。
英語に比べて吸収が早いのでめっちゃ助かります。
記事として共有してくださった方に感謝。