[nRF 52840学習者]blinky SDKを使用してGPIOを制御


緒論
開発ブログを書こうと決心したが、velogを開いて最初の文章がimbeddyになった.
私はEmbeddyのE字さえ知らないので...たまに開発が必要な場合もありますが、開発不足を埋めるために開発に取り組んでいるので、研究内容を記録したいと思います.
幸いなことに、複雑な機能を実装する必要はなく、基礎の例を修正するだけでよいが、組み込みの知識が不足しているため、少し難しい.
私が勉強する環境は以下の通りです.
  • Arduino Nano 33 Ble(nRF52840)
  • J-Link debugger
  • Segger Embedded Studio
  • Seggerが提供するnRF 5のSDKを利用して、まず最も簡単な「blinky」の例を行ごとに見て、GPIO制御の基礎(?)を築きます報告します.
    基本的には制御ボード上のLEDのコードですが、少し修正するだけでGPIOピンを制御できると思います.
    本題
    #include <stdbool.h>
    #include <stdint.h>
    #include "nrf_delay.h"
    #include "boards.h"
    
    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);
            }
        }
    }
    上記のコードはblinky例のmain.cです.
    幸い(?)あまり長くありません.bsp_board_init(BSP_INIT_LEDS);から始まります.bsp_board_initが宣言されたboards.cを参照すると、追加されたパラメータに基づいてLEDを初期化するか、初期化ボタンを初期化するかが決定される.
    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_INIT_LEDSが渡されているので、bsp_board_leds_init()を使用してLEDを初期化します.
    LEDの数とピン番号が予めマッピングされており、各LEDはnrf_gpio_cfg_output()を使用して初期化されている.これは、設定したpinを出力に設定する関数です.LEDのピン番号が13の場合、nrf_gpio_cfg_output(13)に設定できます.
    その後はbsp_board_leds_off()と呼ばれ、最終的にはnrf_gpio_pin_write(m_board_led_list[led_idx], LEDS_ACTIVE_STATE ? 0 : 1)が実行されます.m_board_led_list[led_idx]はLEDのピン番号(e.g.13)だけで、後の条件は何ですか?
    公式文書は下図の通りです.
    valueに0があればpinをクリアし、1以上の値があればpinを設定...リンベディドがどういう意味か分かりませんが・・・
    しかし、自分でやったところset日の場合gpio pinは電圧が発生し、clearは発生しないことが分かった.正確な内容はわかりませんが、設定時にledを開くことができ、clear時にledを閉じることができることがわかりました.LEDS_ACTIVE_STATE ? 0 : 1は3つの演算子であるため、LED_ACTIVE_STATEはTrue面0、False面1を返します.すなわち,LED_ACTIVE_STATEが0の場合は1,1の場合は0を返す.
    もう一度言います(…)LEDはオンにするとオフになり、オフにするとオンになる役割を果たします.
    今はホワイトゲートの中に入りましょう
    for文は、予め設定されたLED数に従って同じ操作を行うために返されるだけである.bsp_board_led_invert(i);は、パラメータがpin数であるnrf_gpio_pin_toggle()と呼ばれる関数である.nrf_gpio_pin_toggle()を下図に示します.
    __STATIC_INLINE void nrf_gpio_pin_toggle(uint32_t pin_number)
    {
        NRF_GPIO_Type * reg        = nrf_gpio_pin_port_decode(&pin_number);
        uint32_t        pins_state = reg->OUT;
    
        reg->OUTSET = (~pins_state & (1UL << pin_number));
        reg->OUTCLR = (pins_state & (1UL << pin_number));
    }
    切り替え機能も簡単で、LEDが点灯しているとクリアにオフになり、オフになっているとオンに設定されます.
    切り替え機能に加えて、好きなように電源を入れたり、電源を切ったりするコマンドをくれればどうすればいいか考えていましたが、切り替えを説明する正式なドキュメントの近くにnrf_gpio_pin_setを説明する関数があり、調べてみるとnrf_gpio_pin_clearがありました.
    pin番号をパラメータとして入れるだけでよく働くと予想していたかもしれません.(e.g. nrf_gpio_pin_set(21); )

    (無意味なアクティビティ写真/赤いLED)
    P.S.
    以上のように、Arduino Nano 33 Bleを使用しましたが、驚くべきことに、nRF 5 SDKで定義されているARDUINO_13_PINなどが実際のアドゥーエノ品番とどのような関係があるのかということです.(もちろん、アドゥーエノにはモデルがたくさんいるからそうなんだけど…)コードエラーだと思って苦労しましたが、schematicsをダウンロードすれば問題を解決できます.

    Pの後ろにはx.yという形で数字が表示され、xが0ならyをパラメータとして入れるだけです.(e.g.D 7ピンを挿入した場合、コードは23)
    1ページの質疑応答.から見ると、ルールは以下の通りです.
    P0.0 = 0, P0.1 = 1 .... P0.31 = 31 P1.0 = 32, P1.1 = 33. pca10056.hファイルを見ていると、NRF_GPIO_PIN_MAP(1, 11)はこのように書かれていると思いますが、どのように使いますか?
    こうして初めての勉強が終わりました!