nRF52のファームウェアをGitHub Actions上でビルドする


# 概要
nRF52のファームウェア(FW)をGitHub Actions上でビルドする方法を紹介します。

GitHub Actions上に公開されたアクションの中にnRF52用がなかったので、ビルド用のDockerイメージを作成しGitHub Actions上から利用する方法を使っています。

# 1. MacのコマンドラインでnRF52のFWをビルドする
まず、手元のMacでFWをビルドできることを確認します。
nRF52の開発環境であるSegger Embedded Studioの `emBuild` というコマンドを使います。

```bash
$ emBuild -config "Release" nrf52_fw_app.emProject
```

コマンドでビルドできれば、あとはこれをDocker上に持っていくだけなので楽勝です(と思っていたのですが、ここからが長かったです :sweat: )

参考：[Building with a SEGGER Embedded Studio project file](https://studio.segger.com/index.htm?https://studio.segger.com/emBuild_building_with_a_project_file.htm)

# 2. Dockerfileを書いてFWビルド用のDockerイメージを作る

DockerfileにFWのビルドに必要なコマンドを展開する手順を書きます。

### FWのビルドに必要なもの

* Python3
* nRF Util
* Nordic Command Line tools
* GCC
* Segger Embedded Studio
* nRF5 SDK

### Dockerfile
``` Dockerfile
FROM ubuntu:latest

ARG GCC_ARM_VER=gcc-arm-none-eabi-8-2019-q3-update
RUN apt-get update && \
	apt-get install -y libx11-6 libfreetype6 libxrender1 libfontconfig1 libxext6 xvfb curl bzip2 unzip python python3-pip git zip

# nRF Util
RUN pip3 install nrfutil

# Nordic Command Line tools
RUN curl https://nsscprodmedia.blob.core.windows.net/prod/software-and-other-downloads/desktop-software/nrf-command-line-tools/sw/versions-10-x-x/10-15-1/nrf-command-line-tools-10.15.1_linux-amd64.zip -o nrf-command-line-tools.zip && \
	unzip nrf-command-line-tools.zip && \
	tar -zxvf nrf-command-line-tools-10.15.1_Linux-amd64.tar.gz && \
	rm nrf-command-line-tools.zip

# GCC
RUN curl -L https://developer.arm.com/-/media/Files/downloads/gnu-rm/8-2019q3/RC1.1/${GCC_ARM_VER}-linux.tar.bz2?revision=c34d758a-be0c-476e-a2de-af8c6e16a8a2?product=GNU%20Arm%20Embedded%20Toolchain,64-bit,,Linux,8-2019-q3-update -o ${GCC_ARM_VER}.tar.bz2 && \
	tar -xvjf ${GCC_ARM_VER}.tar.bz2 && rm ${GCC_ARM_VER}.tar.bz2 
ENV PATH="/${GCC_ARM_VER}/bin:/nrf-command-line-tools/bin:$PATH"

# Segger Embedded Studio
RUN curl -L https://www.segger.com/downloads/embedded-studio/Setup_EmbeddedStudio_ARM_v568_linux_x64.tar.gz -o ses.tar.gz && \
	tar -zxvf ses.tar.gz && \
	$(find arm_segger_* -name "install_segger*") --copy-files-to /ses  --accept-license && \
	rm ses.tar.gz && \
	rm -rf arm_segger_embedded_studio_*
ENV PATH=$PATH:/ses/bin

# nRF5 SDK
RUN curl https://www.nordicsemi.com/-/media/Software-and-other-downloads/SDKs/nRF5/Binaries/nRF5SDK1702d674dde.zip -o nRF5_SDK_17.0.2.zip && unzip -d nRF5_SDK_17.0.2 nRF5_SDK_17.0.2.zip && rm nRF5_SDK_17.0.2.zip
RUN printf "GNU_INSTALL_ROOT ?= /${GCC_ARM_VER}/bin/\nGNU_VERSION ?= 8.3.1\nGNU_PREFIX ?= arm-none-eabi\n" > /nRF5_SDK_17.0.2/nRF5_SDK_17.0.2_d674dde/components/toolchain/gcc/Makefile.posix
```

### Docker build
Dockerのイメージを作成します。環境にもよりますがイメージの作成には時間がかかります。
私の環境では20~30分程度かかりました。

```
$ docker build ./ -t nrf52
```

# 3. Dockerコンテナ上で動作確認
ビルドしたDockerイメージを起動して中に入ることができます。
コンテナに入って意図した通りにDockerイメージが作成されているか確認します。

```shell
# Dockerコンテナを起動して中に入ってみる
$ docker run -it nrf52 bin/bash

# Dockerコンテナ上にemBuildコマンドが入っていることを確認
$ which emBuild
/ses/bin/emBuild

# ビルドコマンドが使えることを確認
$ emBuild 
SEGGER Embedded Studio for ARM emBuild - Release 5.68
Copyright (c) 2014-2021 SEGGER Microcontroller GmbH
Copyright (c) 1997-2021 Rowley Associates Ltd.
```

# 4. DockerイメージをDocker Hubにプッシュする
GitHub Actions上からDockerイメージを使えるようにするためDocker Hubにイメージをプッシュします。

```shell
# Dockerにログインする
$ docker login

# Docker Hubにイメージをプッシュする
$ docker push acctoun_name/repository_name:latest
```
※Docker HubはDockerイメージをホストするためのサービスです。
※事前にDocker Hubにアカウントを作成し、リポジトリを登録しておく必要があります。

# 5. GitHub ActionsのYAMLを書く
やっとGitHub Actionsです。プルリクにソースがプッシュされた時に自動的にビルドが実行されるようにします。ポイントは、Docker Hubにプッシュしたコンテナを使用する箇所です。

```yaml
name: emBuild

on:
  pull_request:
    types: [opened, synchronize]

jobs:
  build:
    runs-on: ubuntu-latest
    timeout-minutes: 10
    # Docker Hubにプッシュしたコンテナを使用する
    container:
      image: account_name/nrf52:latest
    steps:
      # ビルド対象のソースコードをチェックアウトする
      - uses: actions/checkout@v2
      
      # FWのビルドを実行
      - name: emBuild
        run: emBuild -config "Release" nrf52_app.emProject
        working-directory: ./nrf52_app/ble_peripheral/project/pca10040/s132/ses

      # ビルドの成果物（HEX)をアップロードする
      - name: Upload HEX file
        uses: actions/upload-artifact@v2
        with:
          name: nrf52_app.hex
          path: nrf52_app/ble_peripheral/project/pca10040/s132/ses/Output/Release/Exe/nrf52_app.hex
          retention-days: 90
```

#### 実行結果
GitHub Actions上でFWがビルドされました :sparkles: 
![スクリーンショット 2022-01-02 11.21.12.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/102273/71c9c001-a716-a38d-d56f-2b228730af93.png)

# 環境
- Macbook pro Big Sur 11.5.2
- Nordic Semiconductor nRF52シリーズ
- nRF5 SDK ver 17.0.2
- Segger Embedded Studio V5.68
- Docker Desktop for Mac 4.3.2
- Docker Hub
- GitHub Actions