今日こそ頑張ります

危機感を抱きつつ、怠けるエンジニア。日記や備忘録。(以前のブログ:http://harupanda.blog.jp/)

ISP1807でBLEペリフェラルを実装するための準備

前回まででISP1807に対して、nRF52833-DKの
オンボードJ-Linkを使って任意のソフトを書き込む準備ができました。

今回は、ISP1807でSDKのBLEペリフェラルソフトを走らせるところまでやります。
これも先人たちの参考資料ほぼそのままなんですが。

ソフトデバイス

まず、ソフトデバイスってやつをダウンロードします。
こちらの記事の通りです。
qiita.com

ソフトデバイスというのは、Nordic 社が提供するBLEのプロトコルスタックライブラリの名称です。
nRFでBLEを利用するためには必須ってことですね。
Nordicのダウンロードサイトをみると、nRF52840だと、S113もしくはS140が対応するようです。

違いとしては、S113だとペリフェラル機能のみだが、省メモリ。
S140だとセントラル+ペリフェラル機能の両対応で、リッチ。
とりあえず両方ダウンロードして、書き込みはS113にしておくことにします。

nRF Connect for Desktop

ソフトデバイスをnRFに書き込むために、nRF Connect for Desktopをインストールします。
nRF Connect for Desktop - Downloads - nordicsemi.com

nRF Connect for Desktopはいろいろな開発ツールが詰まったランチャーソフトみたいなものです。
その中のProgrammerというソフトを使ってソフトデバイスを書き込みます。

さて、Programmerをインストールして起動し、さらにnRF52833-DKを接続(ISP1807をJ-Link経由で接続したもの)すると
下記のように、左上のデバイス名称欄には、「ISP1807」や「nRF52840」という名称ではなく、
nRF52833-DKという名称が表示されます。

「あれ、J-Link先のデバイスが認識されないのか??」と、初めは戸惑いましたがこれで正しいようです。
接続されているJ-Linkデバイスそのもの、という意味で、nRF52833-DKと表示されているようです。
J-Link先のデバイスとしては、Programmerのウィンドウのところに、ちゃんとNRF52840の名称が出ています。
(ちなみに、J-Linkの配線を外すと、NRF52840の表示はERRORになってしまいます。)

この状態で、File Memory layoutのところにソフトデバイスの.hexファイルをドラッグアンドドロップします。
さらに、Readアイコンをクリック。
すると下記のような表示になります。

右が現在のデバイスの状態。
左が.hexファイルのレイアウト。
この状態で、Erase&writeをクリックするとソフトデバイスが書き込まれます。
書き込み後にReadをクリックして、書き込み後の状態が.hexファイルと同様になっているかを確認します。

とりあえず、BLEビーコンを発射させる

とりあえず、サンプルソフトを書き込んで走らせます。
BLEビーコンを出してみることにします。
下記プロジェクトをDebug&Runします。

nRF5_SDK_17.1.0_ddde560\examples\ble_peripheral\ble_app_beacon\pca10056\s140\ses

と、ここで、コンパイルエラーが発生します。

SEGGER_RTT_Syscalls_SES.c:76:10: fatal error: __vfprintf.h: No such file or directory

今回もDevZoneを調べてみると、下記のような書き込みがありました。
devzone.nordicsemi.com

There has been a change in recent Segger Embedded Studio versions that require you to remove the SEGGER_RTT_Syscalls_SES.c file from the project.

というわけで、深く考えずにBuild対象から除外します。
ProjectツリーのところでSEGGER_RTT_Syscalls_SES.cを右クリックして、
Exclude from Buildをクリックです。

これでDebug & Runすると、ビーコン(アドバタイズパケット)が発射されます。
確認方法としては、スマホでLightBlueというアプリを実行すると、
NordicのManufacturer Specific Dataが載ったパケットが確認できるので、
それでうまく実行できていることがわかります。

次回はGatt通信や、セントラル側も走らせてみたいなぁと思います。

ISP1807でLチカ

前回まででnRF52833-DKのLチカができたので、
今回はISP1807でLチカをさせたいと思います。
先日買っておいた、スイッチサイエンスのISP1807(USB Type-C版)の出番です。

nRF52833-DKをオンボードJ-Linkとして接続

今回の主目的はLチカというよりかは、
nRF52833-DKをオンボードJ-Linkとして使えるようにすることが本題です。
といっても、大したことはありませんでした。

まずは、ISP1807とnRF52833-DKをジャンパーで接続します。
下記の記事を参考にさせていただきました。

lipoyang.hatenablog.com

今回は、ISP1807がブレイクアウトボードに実装されているので
本当にジャンパーで接続するだけです。
(ヘッダーピンのはんだ付け+ブレッドボードへの挿入は必要でしたが)

接続関係は上記の記事通りですが、以下の通り。

nRF52833-DKの接続 ISP1807の接続
GND GND
VDD_nRF VDD_nRF
GND DETECT GND
VTG VDD_nRF
SWD_CLK SWD_CLK
SWD_IO SWD_IO

Projectの設定

必要かどうかはわからないが、
SESのプロジェクトファイルの設定をいじりました。

画面左のプロジェクトツリーのプロジェクト名で右クリックし、Optionを選択。
DebugグループのDebuggerのところで、Target DeviceをnRF52840_xxAAにしました。
(そもそもnRF52833になっていなかったが)

また、Register Definition Fileをnrf52840.svdにしました。

あとの設定はよくわからんので、いさぎよく放置です。

いざLチカ

とりあえず、前回作ったLチカソースコードで、
オンボードの4つのコードに関わるところはすべてコメントアウトし、
P0.23のGPIOのところだけ、生かしておきます。

幸いなことに、P0.23はISP1807でも引き出されているので
そこからブレッドボード上に、前回と同じく3.3kの抵抗とLEDを接続します。

あとはSESで、Build&Runです。
「外部ターゲットに書き込む」みたいな選択がどこかにあるのかと思ったのですが、
見当たらなかったので、とりあえずBuild&RunしてみたらちゃんとISP1807に書き込まれました。

オンボードLEDに関する記載をすべて殺したのに、nRF52833-DKのオンボードLEDは
相変わらずチカチカしていたので、nRF52833-DK側には書き込みに行っておらず、
ISP1807だけに書き込んだのは間違いなさそうです。
外部ターゲットが接続されているのを検知したら、そっちに書き込むのでしょうか。

とりあえず、目的は達成できたのでよしとしましょう。
次回はいよいよ、BLEに取り組み始めます!

nRF52833-DKの任意のGPIOでLチカをする

nRF52833-DK上にはLEDが実装されていて、SDKのサンプルではその中の4つのLEDを点滅させるようになっています。

今回は、それら既存のLEDとは異なるLEDを1つブレッドボード上に用意し、
さらに別のGPIOを操作してブレッドボード上のLEDを点滅させることにします。
(そっちの方が練習になるかと思い。)

GPIOの選択と接続

P0.23のGPIOに、LEDおよび3.3kオームの電流制限抵抗を介して、VDD_nRF(3.3V)に接続しています。
ちなみにnRF52833のGPIOのドライバビリティ(電流駆動能力)はデータシートに載っておらず。
DevZoneで検索してみると15mAという話みたい。結構流せるのね。
今回は3.3kを介して1mAなんで余裕です。

※なお、P1.01~08のGPIOも空いていて、はじめはそちら(P1.03)に接続していましたが、
うまく制御できず。(サンプルプログラムがP1.**を制御することが想定されていないのか??)
きちんと制御アドレスとかを解析すればできそうだけど、今回はそれはパスしてP0番台のGPIOを選択。

ソースコードの編集

nRF5_SDK_17.1.0_ddde560\examples\peripheral\blinky\pca10100e\blank\ses\blinky_pca10100e.emProject
をベースに編集していきます。

main.cのmain関数。

int main(void)
{
    /* Configure board. */
    bsp_board_init(BSP_INIT_LEDS);

    /* Toggle LEDs. */
    while (true)
    {
        for (int i = 0; i < LEDS_NUMBER; i++)
        {
            bsp_board_led_invert(i);
            nrf_delay_ms(500);
        }
    }
}

ここはそのままです。
bsp_board_initでは、GPIOを初期化をしているようです。
while文のループ内のbsp_board_led_invertでLEDを明滅させます。
簡単ですね。

bsp_board_initと、bsp_board_led_invertに
P0.23のGPIOの初期化、およびトグルの記述を追加しましょう。

それぞれ、board.cに記述があります。
まず、bsp_board_initから。

void bsp_board_init(uint32_t init_flags)
{
    #if defined(BOARDS_WITH_USB_DFU_TRIGGER) && defined(BOARD_PCA10059)
    (void) nrf_dfu_trigger_usb_init();
    #endif

    #if LEDS_NUMBER > 0
    if (init_flags & BSP_INIT_LEDS)
    {
        bsp_board_leds_init();
    }
    #endif //LEDS_NUMBER > 0

    #if BUTTONS_NUMBER > 0
    if (init_flags & BSP_INIT_BUTTONS)
    {
        bsp_board_buttons_init();
    }
    #endif //BUTTONS_NUMBER > 0
}

ここもそのままです。
今回、ポイントとなるのはbsp_board_leds_init()で、ここにさらに潜ると、

static void bsp_board_leds_init(void)
{
    #if defined(BOARD_PCA10059)
    // If nRF52 USB Dongle is powered from USB (high voltage mode),
    // GPIO output voltage is set to 1.8 V by default, which is not
    // enough to turn on green and blue LEDs. Therefore, GPIO voltage
    // needs to be increased to 3.0 V by configuring the UICR register.
    if (NRF_POWER->MAINREGSTATUS &
       (POWER_MAINREGSTATUS_MAINREGSTATUS_High << POWER_MAINREGSTATUS_MAINREGSTATUS_Pos))
    {
        gpio_output_voltage_setup();
    }
    #endif

    uint32_t i;
    for (i = 0; i < LEDS_NUMBER; ++i)
    {
        nrf_gpio_cfg_output(m_board_led_list[i]);
    }
    bsp_board_leds_off();

    //test
    uint8_t led_test_pin = LED_TEST;
    nrf_gpio_cfg_output(led_test_pin);
    nrf_gpio_pin_write(led_test_pin,0);
}

ここで、GPIOを出力に初期化し、さらに初期設定として消灯しています。
それぞれ、nrf_gpio_cfg_outputと、bsp_board_leds_offですね。

これを真似して追加します。testコメントから下3行です。
LED_TESTというdefineは、pca10100.hに以下のように追加しています。

#define LED_1          NRF_GPIO_PIN_MAP(0,13)
#define LED_2          NRF_GPIO_PIN_MAP(0,14)
#define LED_3          NRF_GPIO_PIN_MAP(0,15)
#define LED_4          NRF_GPIO_PIN_MAP(0,16)
#define LED_TEST       NRF_GPIO_PIN_MAP(0,23)

同じようなノリで、bsp_board_led_invertにも下記のように追記します。

void bsp_board_led_invert(uint32_t led_idx)
{
    ASSERT(led_idx < LEDS_NUMBER);
    nrf_gpio_pin_toggle(m_board_led_list[led_idx]);

    //test
    uint8_t led_test_pin = LED_TEST;
    nrf_gpio_pin_toggle(led_test_pin);
}

基本的にはこれでいけるはずなんですが、最後に1つ力業が必要です。
nrf_gpio_cfg_outputの先で呼び出されるnrf_gpio_pin_port_decodeの中の
NRF_ASSERTをコメントアウトします。
nrf_gpio_pin_present_checkの先では、エラッタ処理を通したりしているようですが
ここをそのまま通すとエラー処理側に落ちてしまいます。
趣味工作の範疇ではスキップしても問題ないだろ!所詮チェックだし!ということで
潔くコメントアウトしましょう。

__STATIC_INLINE NRF_GPIO_Type * nrf_gpio_pin_port_decode(uint32_t * p_pin)
{
    //test
    //NRFX_ASSERT(nrf_gpio_pin_present_check(*p_pin));

これでLチカの完成です。
次はBLEをいじりたいのですが、nRF52833-DKは技適を通していないので
BLEの電波を飛ばせません。

といわけで、ここらで本番環境であるISP1807をいじり始めたいと思います。
(nRF52833-DKはもともとオンボードJ-linkの目的で買っております)

次回は、ISP1807を利用してLチカさせたいと思います。

SEGGER Embedded Studio for ARM (V6.40)をインストール

続き。

SESのインストール

SEGGER Embedded Studio for ARM などのツールをインストールしました。
参考にさせていただいたページは下記。
shizuk.sakura.ne.jp

SESは以下からダウンロード。
SEGGER - The Embedded Experts - Downloads - Embedded Studio

nRF52のSDKを以下からダウンロード。
nRF5 SDK downloads - nordicsemi.com

J-linkのソフトは以下からダウンロード。
SEGGER - The Embedded Experts - Downloads - J-Link / J-Trace

インストール自体はポチポチ押していくだけですね。
早速SDKのサンプルをビルドし、nRF52833-DK上でRunさせたいと思います。

まずはボードナンバーの確認から。
下記のページを参照します。
Nordic Semiconductor Infocenter

nRF52833-DKのボードは、PCA10110のようです。
Lチカサンプルの下記のプロジェクトを開きます。
nRF5_SDK_17.1.0_ddde560\examples\peripheral\blinky\pca10100e\blank\ses\blinky_pca10100e.emProject

なお、起動時に下記の画面が出て、ライセンスが見つからん、と言われます。

書いてある通り、非商用目的・教育目的であれば、このままAcceptをクリックで使い続けられますが
nRF52に対して使うのであれば、正式ライセンスが発行してもらえるので、せっかくなのでゲットします。
(毎回ライセンス確認画面が出てくるのも鬱陶しいですしね)
下の方にある"Obtain a License"をクリック。

ブラウザが立ち上がるので、下記の画面の"Request your license at..."のURLをクリック。

名前やメールアドレスを登録すると、登録したメアド宛にライセンスキーが届きます。
SES上のライセンスマネージャーにて、そのライセンスキーを登録すれば完了。

Buildエラーが出る。

早速、nRF52833_DK基板とPCをUSB(ちなみにJ2コネクタ側)で接続し、
blinky_pca10100e.emProjectをBuild&Debugしてみましたが、
下記のエラーに遭遇。

".text is larger than specified size" and ".rodata is larger than specified size".

なんでサンプルでエラーが出てくるねん・・・。

しかし何も心配はいりません。nRFを選択したもう一つの理由がここで活きます。
大概のトラブルは先人たちが解決し、Nordic Devzoneに答えを書いてくれているのです。

今回の問題も下記で解決しました。
(ただ、対処方法は書いてあるけど、根本原因の理解はできず・・・ですが)
Build error - Nordic Q&A - Nordic DevZone - Nordic DevZone

上記のページに書いてある通り、
nRF5_SDK_17.1.0_ddde560\examples\peripheral\blinky\pca10100e\blank\ses\flash_placement.xml
の記載をmodifyします。

下記の通り。

You should see:
ProgramSection alignment="4" load="Yes" name=".text" size="0x4" /
and
ProgramSection alignment="4" load="Yes" name=".rodata" size="0x4" /

Remove: size="0x4" from both lines resulting in:
ProgramSection alignment="4" load="Yes" name=".text" /
and
ProgramSection alignment="4" load="Yes" name=".rodata" /

https://devzone.nordicsemi.com/f/nordic-q-a/89236/build-error/374975より転載

これでコンパイルが通るようになりました。

続きは次回。

開発環境とモノの購入から

週末です。
土曜・日曜と家族が妻の実家に帰ってるから、自由な週末です。

さて、ISP1807を使ったBLE実験ですが、まだまだ序盤の環境整備です。
初心者なので、わかりやすそうなWebの情報を必死で探してます。

このブログに作業記録を残していきます。
目的としては、
・備忘録
・アウトプットすることで知識の定着を図る
ということで、あくまで自分のためのもので
世の中の役に立てるつもりは一切ない感じです。
すみません。

開発環境を調べるところからスタート

電源入れてもソフトが無いと動かないのは当たり前なので、
まずはどうやってソフトを焼くんじゃい、ってとこからです。

下記のページによれば、大きく3種類にわかれるようです。

tech.144lab.com

①フル書き換え方式
・先頭から必要なバイナリをすべて書き込む。
・あらゆる領域を上書き可能
・デバッガが必要

ブートローダー方式
フラッシュメモリの後方にブートローダを置く。
・シリアルやUSB-CDCまたはUSB-MSD経由で書き換え可能
(=USBケーブルの接続でアップデートが可能)

ブートローダー+VMランタイム方式
・疑似ファイルシステム領域にスクリプトを書き込む
・USB-MSD経由で書き換え可能

下にいけばいくほど、お手軽だけど、リソースのオーバーヘッドが大きいみたい。
(いずれ実際に実験して確認したいけど、今回は見切り発車)
今回は消費電力や起動時間をカリカリに切り詰めたいので、①(もしくは②)を選択します。

なお環境としては、③だとCircuitPythonが便利そう。いずれ挑戦したいです。
①を選択した今回は準備する環境として、
・SEGGER Embedded Studio
・J-link
がおすすめな様子。(同ページ参照

SEEGER Embedded Studioについては、30万オーバーというとんでもない価格ですが、
nRF51、nRF52シリーズに限り無料で商用利用可能とのことで、これは行くしかないという感じです。

一方J-linkについては、お手頃なところとして非商用版のJ-Link EDUがあったようですが、
残念ながら2022年11月現在は流通していないようです。
www.embitek.shop

本家SEGGER社のネット販売ページもout of stockとなっていて、やはりダメそうです。
とはいえ、趣味用途で10万円する通常のJ-linkは購入はできません。
そんな状況なので、巷ではオンボードJ-linkを使うのが主流のようです。

参考になりそうなページ。
あとで実際に手を動かしながら、さらに調べていきます。

secon.dev

lipoyang.hatenablog.com

オンボードJ-Linkを利用するためには、nRFのDevelopment Kitが必要な様子です。
ここまでで、何を買えばいいかが見えてきました。

購入したもの

・ISP1807ピッチ変換基板 USB Type-C版
ISP1807ピッチ変換基板 USB Type-C版www.switch-science.com
スイッチサイエンスで3500円くらい。
BLE実験をするためのメインデバイスです。
これを選んだ理由は、nRF52840を搭載した基板の中でも最も回路がシンプルだったためです。
本当はセントラル・ペリフェラルで計2つ必要ですが、とりあえず1つ買いました。
うまく作業が進んだら複数個買うつもりです。

・nRF52833-DK
www.mouser.jp
Mouserで7000円くらいです。
オンボードJ-linkを実現するための環境です。
nRF52840ではなくnRF52833にした理由は、違うものも試してみたかったからです。

・ブレッドボード、ジャンパー線、ピンヘッダ等
必要そうなものをamazonで購入しました。

続きは次回。

nRF52833 DK

ちょうどこの秋くらいから、J-link EDUが生産停止?状態ということになっているらしく、nRFを趣味で楽しむ人にとってはつらい状況になってるようだ。
でもそんな人たちにとっては、nRF5* DKのオンボードJ-linkを使うのがおすすめらしく、さっそく買ってみた。
サンプルSDKのLチカまでは確認したのだが、まだまだわからないことだらけ。今日も寝よう。

本当は、J-linkとは何か、とかnRFとは何か、とかからまとめたいんだけど。年末年始かしら・・・。

BLExラズパイ センサタグ(CC2650)と接続

6月も半分が終わったよ。
週末は少しエアコンを付けちゃったよ。蒸し暑い。

そういえば、夏のボーナスは年初の予定通り支給された。
コロナ禍の影響で業績ガタ落ちだから、冬は本当に危ないかもね。

エンジニアとしてのレベルを上げないと、家族を養えなくなってしまう・・・。
といいながら、まだまだ低レベルな自分。
さてそんな中、ラズパイ工作、少しだけ進めたよ。
ついにセンサタグからデータを引っ張るとこまで。
https://github.com/Panda-papa/Raspberry/blob/master/blescan.py

データは本当にとりあえず取得だけ。
取得しているデータの精査とかはこれから。

bluepyにSensorTagというクラスがあって、
それを使えば接続~データ取得までできるみたいなんだけど、
SensorTagクラスに関してはマニュアルが無くて、ソースコード読んでんだけど
全然わけわからん。

下記ページが無ければ、とりあえずの接続すら危うい。うう・・。
qiita.com


自己啓発の意味を込めた活動なので、
こういう不明部分の車輪の再発明がしたくてたまらない。
まぁ発明まで行かなくても、せめて動作原理くらいはつかみたい。

夏休み前後くらいには、グラフ書くところくらいまでは行きたい。