EC2 + Ubuntu +  nvidia CUDA + hardware accelerated FFMPEGのインストール方法

##はじめに

こんにちは streampack チームのメディです。
https://cloudpack.jp/service/option/streampack.html

##Copyrights 
Big Buck Bunny
© copyright 2008, Blender Foundation | www.bigbuckbunny.org


##Objective ・ 目的
Learning how to compile FFMPEG with nvidia hardware acceleration on an Ubuntu EC2 instance.
Ubuntu EC2インスタンス上でnvidiaハードウェアアクセラレーションを使ってFFMPEGをコンパイルする方法を学ぶ。

We will use a **gs3.xlarge** Ec2 instance.
**gs3.xlarge** Ec2インスタンスを使用します。

This kind of EC2 instance is using a **nvidia Tesla M60** card. This graphic card has been released in **2015**.
This card will increase FFMPEG video encoding speed.

この種のEC2インスタンスは、**nvidia Tesla M60**カードを使用しています。 このグラフィックカードは**2015**年に発売されました。
このカードはFFMPEGビデオのエンコード速度を上げます。

<img width="270" alt="Screen Shot 2019-02-21 at 11.12.19.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/eab9a7e1-dc50-ebd4-ab36-4857d8b5f18d.png"><img width="445" alt="Screen Shot 2019-02-21 at 17.26.09.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/344cedf8-dbef-24b3-26dd-9512dccb499f.png">


##Pricing ・ 料金
<img width="651" alt="Screen Shot 2019-02-19 at 17.59.46.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/5d574621-00bb-622c-55be-816aea55fa04.png">
**0.75 USD** by hour.
１時間で**0.75 USD**です。

**Check the latest price・最新の価格を確認**
https://aws.amazon.com/ec2/pricing/on-demand/

## Select the instance type・インスタンスタイプを選択
Machine Linux Image : **Ubuntu Server 18.04 LTS**
Instance type :  **g3s.xlarge**
<img width="1036" alt="typeScreen Shot 2019-02-21 at 10.19.59.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/6f0e4da5-5696-3224-c951-64807698a9ee.png">



 

## Connect to your instance・インスタンスに接続する

```bash 
ssh -i yourKeyFile.pem ubuntu@YourServerIP
```



## Update the OS ・ OSをアップデートする
```bash
sudo apt-get update
sudo apt-get upgrade
sudo apt-get install yasm
```

## Update the sources list ・ ソースリストを更新する

```bash
sudo add-apt-repository ppa:graphics-drivers/ppa
sudo apt update

```
<img width="539" alt="Screen Shot 2019-02-21 at 12.50.50.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/af82e96f-b333-1432-1a63-9a875b137da1.png">


## List drivers  ・ドライバ一覧
```bash
sudo apt install ubuntu-drivers-common
ubuntu-drivers devices
```
<img width="491" alt="Screen Shot 2019-02-20 at 11.31.13a.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/8022bae0-aa51-7969-25d6-d24ef73e79f1.png">


## Install the  nvidia-driver (v 415) for the Tesla M60 

```bash
sudo ubuntu-drivers autoinstall
```

## Reboot  ・ リブート
You need to reboot the Ec2 instance.
Ec2インスタンスを再起動する必要があります。
![roy.png](https://qiita-image-store.s3.amazonaws.com/0/229807/3a4ffbf3-a15a-5034-fa51-48d4dd5f1c21.png)

```bash
sudo shutdown -r now
```


## nvidia driver version ・ nvidiaカードとドライバのバージョンを表示
![moss.jpg](https://qiita-image-store.s3.amazonaws.com/0/229807/11e0a994-51b2-897c-9134-7f241cfd00f0.jpeg)

Did you **really** reboot your instance ?
インスタンスを**本当に**再起動しましたか？

```bash

nvidia-smi
```

<img width="558" alt="Screen Shot 2019-02-20 at 11.06.34.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/4d4fdd56-d0ef-5b16-2e21-0cca05cce3e4.png">



**List CUDA paths ・ CUDAパスをリストする**

```bash
ldconfig -p | grep cuda
```

## nvidia toolkit 

```bash
sudo apt install nvidia-cuda-toolkit
sudo shutdown -r now
```
Don't forget to reboot your instance !
インスタンスを再起動することを忘れないでください。

### Checking nvidia toolkit 

```bash
nvcc -V
```

<img width="335" alt="Screen Shot 2019-02-21 at 15.37.30.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/1e9468bc-f601-16e3-ef79-4eb00087c142.png">


## NVIDIA CODECS ・ NVIDIAコーデック
***Caution・注意***  
*Because the Tesla M60 card is a little bit old, we cannot use the latest version of nvidia codecs.*
*Tesla M60カードは少し古いため、最新バージョンのnvidiaコーデックを使用することはできません。*

*For drivers 415.x and older versions*
*415.xドライバ以前のバージョン用*

```bash
cd
mkdir nvcodec
cd nvcodec 
git init 
git clone https://git.videolan.org/git/ffmpeg/nv-codec-headers.git
cd nv-codec-headers/
git checkout n8.2.15.7
make && sudo make install
```
***Caution***
The `n8.2.15.7` version of the `nv codecs`  works fine with the  `415.xx` version of the nvidia driver.
If you are using a different version of the driver, please refer to the [official nvidia codecs project website](https://github.com/FFmpeg/nv-codec-headers/releases). 

***注意***
`n 8.2.15.7`バージョンの` nv codecs`は、 `415.xx`バージョンのnvidiaドライバとうまく動作します。
別のバージョンのドライバを使用している場合は、[公式のnvidiaコーデックプロジェクトのWebサイト](https://github.com/FFmpeg/nv-codec-headers/releases)を参照してください。

*I found this solution on GitHub but I cannot retrieve the link, sorry.*
*GitHubでこの解決策を見つけましたが、申し訳ありませんが、リンクを取得できません。*

## Compiling FFMPEG with CUDA enabled ・CUDAを有効にしてFFMPEGをコンパイルする


**Before compiling ・ コンパイルする前に**

```bash
sudo apt-get install nasm
sudo apt-get install mingw-w64
```

**Compiling / installing ・ コンパイル / インストール**

```bash
cd 
mkdir ffmpeg 
cd ffmpeg 
git init 
git clone https://github.com/FFmpeg/FFmpeg.git 
cd FFmpeg
./configure --enable-cuda --enable-cuvid --enable-nvenc --enable-nonfree --enable-libnpp --extra-cflags=-I/usr/local/cuda/include --extra-ldflags=-L/usr/local/cuda/lib64
make -j10
sudo make install
```


## List the encoders  ・ エンコーダを一覧表示する
All encoders・全エンコーダ

```bash
ffmpeg -encoders
```

nvidia encoders・nvidia エンコーダ

```bash
ffmpeg -encoders | grep nv
```
<img width="1028" alt="Screen Shot 2019-02-21 at 17.09.25.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/a6bd99da-6886-90d5-daa5-33116218b50c.png">


## Testing ・テスト
###Big Buck Bunny :  4k 2160p 30fps



```bash 
cd
mkdir videos
cd videos
wget http://distribution.bbb3d.renderfarming.net/video/mp4/bbb_sunflower_2160p_30fps_normal.mp4
```


### Hardware accelerated encoding with nvenc_h264 ・ nvenc_h264によるハードウェアアクセラレーションエンコーディング
**4K --> 2K**

```bash
ffmpeg -hwaccel cuvid -c:v h264_cuvid -i ~/videos/bbb_sunflower_2160p_30fps_normal.mp4 -vf scale_npp=1920:1280 -c:v h264_nvenc ~/videos/out_nvenc.mp4
```
Encoding speed is around **3.8** 
<img width="359" alt="Screen Shot 2019-02-21 at 16.38.34.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/01b6a3bc-1d97-d85e-ae1e-84dc81571dbe.png">


**Download the transcoded file ・  トランスコードファイルをダウンロードする**
Open a new terminal window:
新しいターミナルウィンドウを開いてください。

```bash 
scp -i yourKey.pem ubuntu@yourServerIp:/home/ubuntu/videos/out_nvenc.mp4 .
```



### Software encoding with libx264 ・ libx264によるソフトウェアのエンコーディング
We will use a static build of FFMPEG.
FFMPEGの静的ビルドを使用しています。
**4K --> 2K**

```bash
cd
mkdir static_ffmpeg
cd static_ffmpeg
wget https://johnvansickle.com/ffmpeg/releases/ffmpeg-release-amd64-static.tar.xz
tar xf ffmpeg-release-amd64-static.tar.xz
cd ffmpeg-4.1.1-amd64-static 
./ffmpeg -i ~/videos/bbb_sunflower_2160p_30fps_normal.mp4 -vf scale=1920:1280 -c:v libx264 ~/videos/out_soft.mp4
```
Encoding speed is around **0.5x** 
<img width="356" alt="Screen Shot 2019-02-21 at 16.45.40.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/fbc6539f-88fb-b4bc-b869-a490a15b02a8.png">


**Download the transcoded file ・  トランスコードファイルをダウンロードする**
Open a new terminal window :
新しいターミナルウィンドウを開いてください。

```bash
scp -i yourKey.pem ubuntu@yourServerIp:/home/ubuntu/videos/out_soft.mp4 .
```



####Results ・ 結果
To convert a video from 4k to 2k, hardware accelerated encoding  is in average **7 times faster** than software encoding.
ビデオを4kから2kに変換するために、ハードウェアアクセラレーションエンコーディングはソフトウェアエンコーディングよりも平均**７倍高速**です。

<img width="1237" alt="Screen Shot 2019-02-21 at 16.58.10.png" src="https://qiita-image-store.s3.amazonaws.com/0/229807/48a471af-64ac-03d4-ccc0-2221db0811fe.png">



##Information sources ・ 情報源
https://images.nvidia.com/content/tesla/pdf/188417-Tesla-M60-DS-A4-fnl-Web.pdf
https://www.nvidia.com/object/tesla-m60.html
https://developer.nvidia.com/ffmpeg
https://en.wikipedia.org/wiki/Nvidia_Tesla
http://bbb3d.renderfarming.net/download.html
https://qiita.com/clerk67/items/d8897b97b5cd93b2d752
https://powersj.github.io/post/ubuntu-server-nvidia-cuda/
https://gist.github.com/Brainiarc7/4b49f463a08377530df6cecb8171306a
https://linuxconfig.org/how-to-install-the-nvidia-drivers-on-ubuntu-18-04-bionic-beaver-linux