2024年10月20日日曜日

nRF52833で測距(1)

nRF52833で測距できるらしい、、、まずは理屈はそっちのけでやってみる

 
nRF52833のexampleをだらだら見てたら、Bluetooth: nRF Distance Measurement with Bluetooth LE discoveryってのを見つけたのでやってみる。
どういう原理で測距しているか、下の方からこちら(https://docs.nordicsemi.com/bundle/ncs-latest/page/nrfxlib/nrf_dm/README.html)に飛べば多少説明があるっぽいけど、まずは見ないことにする。で、exampleのページの下のほうにTestingって項があって、この通りにやるわけだけど、
1. ターミナルをつないだ状態のKitにこのsampleのソフトを書き込む
2. kitをリセットする
3. もう1個のkitに同じsampleソフトを書き込んでリセットする
4. kitたちが勝手に同期するのを待つ
5. ターミナルの出力を見る
ってことらしい。簡単やん。
まずは、普通に進めていく。
nRF Connectのアイコンをつつく
Create a new application
Copy a sample
nrf_dmって入力して出てくるDistance measurement sampleをつつく
ォルダを決めて(通常はそのまんまおすすめされた通りでもいい)、エンター
当然、Open
これ↓は無視
で、ここで欲が出てくるわけよ。printkをUSBに出したいって。ははーん。
が、どうやるのが正解なのかさっぱりわからない。MDBT50Q-DB-33(nRF52833)でUSBにprintkでできたもので反映しといたほうがよさそうなものを全部やってみる。たぶんこの後のAdd build configurationで必要なものを自動的に集めてくれるはずなので、このタイミングでやっとかんといかんと思う。

app.overlay
  1. /*
  2.  * Copyright (c) 2023 Nordic Semiconductor ASA
  3.  *
  4.  * SPDX-License-Identifier: LicenseRef-Nordic-5-Clause
  5.  */
  6. / {
  7.     /* The timer instance to use. */
  8.     chosen {
  9.         ncs,dm-timer = &timer2;
  10.         zephyr,console = &cdc_acm_uart0;/*2024.10.20 Sunday Engineer */
  11.     };
  12.     /* The selected pins will be used by Distance Measurement module for debug purposes. */
  13.     dm_gpio {
  14.         compatible = "gpio-leds";
  15.         dm_ranging: dm-ranging {
  16.             gpios = <&gpio0 27 GPIO_ACTIVE_LOW>;
  17.             label = "DM Ranging Pin";
  18.         };
  19.         dm_add_request: dm-add-request {
  20.             gpios = <&gpio0 26 GPIO_ACTIVE_LOW>;
  21.             label = "DM Add request Pin";
  22.         };
  23.     };
  24. };
  25. /*2024.10.20 Sunday Engineer from here*/
  26. &zephyr_udc0 {
  27.     cdc_acm_uart0: cdc_acm_uart0 {
  28.         compatible = "zephyr,cdc-acm-uart";
  29.     };
  30. };
  31. /*2024.10.20 Sunday Engineer to here*/

CMakeLists.txt
  1. #
  2. # Copyright (c) 2021 Nordic Semiconductor
  3. #
  4. # SPDX-License-Identifier: LicenseRef-Nordic-5-Clause
  5. #
  6. cmake_minimum_required(VERSION 3.20)
  7. find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE})
  8. project(nrf_dm)
  9. # NORDIC SDK APP START
  10. target_sources(app PRIVATE
  11.   src/main.c
  12.   src/pwm_led.c
  13.   src/peer.c
  14.   src/service.c
  15.   )
  16. # NORDIC SDK APP END
  17. zephyr_library_include_directories(${CMAKE_CURRENT_SOURCE_DIR})
  18. #2024.10.20 Sunday Engineer from here
  19. include(${ZEPHYR_BASE}/samples/subsys/usb/common/common.cmake)
  20. FILE(GLOB app_sources src/*.c)
  21. #2024.10.20 Sunday Engineer to here

prj.conf
  1. #
  2. # Copyright (c) 2021 Nordic Semiconductor ASA
  3. #
  4. # SPDX-License-Identifier: LicenseRef-Nordic-5-Clause
  5. #
  6. # BT
  7. CONFIG_BT=y
  8. CONFIG_BT_CENTRAL=y
  9. CONFIG_BT_PERIPHERAL=y
  10. CONFIG_BT_SCAN=y
  11. CONFIG_BT_SCAN_FILTER_ENABLE=y
  12. CONFIG_BT_SCAN_NAME_CNT=1
  13. CONFIG_BT_SCAN_MANUFACTURER_DATA_CNT=1
  14. CONFIG_BT_SCAN_WITH_IDENTITY=y
  15. CONFIG_BT_ID_MAX=1
  16. CONFIG_BT_EXT_ADV=y
  17. CONFIG_BT_DEVICE_NAME="nRF_DM"
  18. CONFIG_BT_DDFS=y
  19. # Distance Measurement
  20. CONFIG_DM_MODULE=y
  21. CONFIG_MPSL=y
  22. CONFIG_MPSL_TIMESLOT_SESSION_COUNT=1
  23. CONFIG_DM_MODULE_LOG_LEVEL_DBG=n
  24. CONFIG_DM_GPIO_DEBUG=y
  25. CONFIG_PWM=y
  26. CONFIG_NCS_SAMPLES_DEFAULTS=y
  27. CONFIG_DK_LIBRARY=y
  28. CONFIG_DM_HIGH_PRECISION_CALC=y
  29. #2024.10.20 Sunday Engineer from here
  30. CONFIG_USB_DEVICE_STACK=y
  31. CONFIG_USB_DEVICE_PRODUCT="Zephyr USB console sample"
  32. CONFIG_USB_DEVICE_PID=0x0004
  33. CONFIG_USB_DEVICE_INITIALIZE_AT_BOOT=n
  34. CONFIG_SERIAL=y
  35. CONFIG_CONSOLE=y
  36. CONFIG_UART_CONSOLE=y
  37. CONFIG_UART_LINE_CTRL=y
  38. #2024.10.20 Sunday Engineer to here

sample.yaml
  1. sample:
  2.   description: nRF Distance Measurement sample
  3.   name: Distance measurement sample
  4. tests:
  5.   sample.bluetooth.nrf_dm.timeslot:
  6.     sysbuild: true
  7.     build_only: true
  8.     extra_configs:
  9.       - CONFIG_DM_HIGH_PRECISION_CALC=n
  10.     integration_platforms:
  11.       - nrf52dk/nrf52832
  12.       - nrf52833dk/nrf52833
  13.       - nrf52840dk/nrf52840
  14.       - nrf5340dk/nrf5340/cpuapp
  15.     platform_allow: >
  16.       nrf52dk/nrf52832 nrf52833dk/nrf52833 nrf52840dk/nrf52840 nrf5340dk/nrf5340/cpuapp
  17.     tags: bluetooth ci_build sysbuild
  18.   sample.bluetooth.nrf_dm.timeslot.high_precision:
  19.     sysbuild: true
  20.     build_only: true
  21.     extra_configs:
  22.       - CONFIG_DM_HIGH_PRECISION_CALC=y
  23.     integration_platforms:
  24.       - nrf52833dk/nrf52833
  25.       - nrf52840dk/nrf52840
  26.       - nrf5340dk/nrf5340/cpuapp
  27.     platform_allow: nrf52833dk/nrf52833 nrf52840dk/nrf52840 nrf5340dk/nrf5340/cpuapp
  28.     tags: bluetooth ci_build sysbuild
  29. #2024.10.20 Sunday Engineer from here
  30.   sample.usb.console:
  31.     depends_on:
  32.       - usb_device
  33.       - usb_cdc
  34.     tags: usb
  35.     harness: console
  36.     harness_config:
  37.       fixture: fixture_usb_cdc
  38. #2024.10.20 Sunday Engineer to here

main.c
  1. /*
  2.  * Copyright (c) 2021 Nordic Semiconductor ASA
  3.  *
  4.  * SPDX-License-Identifier: LicenseRef-Nordic-5-Clause
  5.  */
  6. /** @file
  7.  * @brief Nordic Distance Measurement sample
  8.  */
  9. #include <stdint.h>
  10. #include <zephyr/kernel.h>
  11. #include <zephyr/sys/printk.h>
  12. #include <zephyr/sys/byteorder.h>
  13. #include <zephyr/bluetooth/bluetooth.h>
  14. #include <bluetooth/scan.h>
  15. #include <bluetooth/services/ddfs.h>
  16. #include <dk_buttons_and_leds.h>
  17. /*2024.10.20 Sunday Engineer from here*/
  18. #include <zephyr/kernel.h>
  19. #include <zephyr/sys/printk.h>
  20. #include <zephyr/usb/usb_device.h>
  21. #include <zephyr/usb/usbd.h>
  22. #include <zephyr/drivers/uart.h>
  23. /*2024.10.20 Sunday Engineer to here*/
  24. #include <dm.h>
  25. #include "peer.h"
  26. #include "service.h"
  27. #define DEVICE_NAME CONFIG_BT_DEVICE_NAME
  28. #define DEVICE_NAME_LEN (sizeof(DEVICE_NAME) - 1)
  29. #define RUN_STATUS_LED DK_LED2
  30. #define CON_STATUS_LED DK_LED3
  31. #define RUN_LED_BLINK_INTERVAL 1000
  32. #define SUPPORT_DM_CODE 0xFF55AA5A
  33. struct adv_mfg_data {
  34.     uint16_t company_code;     /* Company Identifier Code. */
  35.     uint32_t support_dm_code; /* To identify the device that supports distance measurement. */
  36.     uint32_t rng_seed; /* Random seed used for generating hopping patterns. */
  37. } __packed;
  38. static struct adv_mfg_data mfg_data;
  39. struct bt_le_adv_param adv_param_conn =
  40.     BT_LE_ADV_PARAM_INIT(BT_LE_ADV_OPT_CONNECTABLE |
  41.              BT_LE_ADV_OPT_NOTIFY_SCAN_REQ,
  42.              BT_GAP_ADV_FAST_INT_MIN_2,
  43.              BT_GAP_ADV_FAST_INT_MAX_2,
  44.              NULL);
  45. struct bt_le_adv_param adv_param_noconn =
  46.     BT_LE_ADV_PARAM_INIT(BT_LE_ADV_OPT_USE_IDENTITY |
  47.              BT_LE_ADV_OPT_SCANNABLE |
  48.              BT_LE_ADV_OPT_NOTIFY_SCAN_REQ,
  49.              BT_GAP_ADV_FAST_INT_MIN_2,
  50.              BT_GAP_ADV_FAST_INT_MAX_2,
  51.              NULL);
  52. struct bt_le_adv_param *adv_param = &adv_param_conn;
  53. static const struct bt_data ad[] = {
  54.     BT_DATA_BYTES(BT_DATA_FLAGS, (BT_LE_AD_GENERAL | BT_LE_AD_NO_BREDR)),
  55.     BT_DATA(BT_DATA_NAME_COMPLETE, DEVICE_NAME, DEVICE_NAME_LEN),
  56. };
  57. static const struct bt_data sd[] = {
  58.     BT_DATA(BT_DATA_MANUFACTURER_DATA, (unsigned char *)&mfg_data, sizeof(mfg_data)),
  59.     BT_DATA_BYTES(BT_DATA_UUID128_ALL, BT_UUID_DDFS_VAL),
  60. };
  61. static struct bt_le_scan_param scan_param = {
  62.     .type = BT_LE_SCAN_TYPE_ACTIVE,
  63.     .interval = BT_GAP_SCAN_FAST_INTERVAL,
  64.     .window = BT_GAP_SCAN_FAST_WINDOW,
  65.     .options = BT_LE_SCAN_OPT_NONE,
  66.     .timeout = 0,
  67. };
  68. static struct bt_scan_init_param scan_init = {
  69.     .connect_if_match = 0,
  70.     .scan_param = &scan_param,
  71.     .conn_param = NULL
  72. };
  73. static uint32_t scanner_random_share;
  74. static struct bt_le_ext_adv *adv;
  75. static void adv_work_handle(struct k_work *item);
  76. static K_WORK_DEFINE(adv_work, adv_work_handle);
  77. static void adv_update_data(void);
  78. static uint32_t scanner_addr_to_random_share(const bt_addr_t *p_scanner_addr);
  79. static uint32_t get_id_addr_random_share(void);
  80. static struct bt_scan_manufacturer_data scan_mfg_data = {
  81.     .data = (unsigned char *)&mfg_data,
  82.     .data_len = sizeof(mfg_data.company_code) + sizeof(mfg_data.support_dm_code),
  83. };
  84. static bool data_cb(struct bt_data *data, void *user_data)
  85. {
  86.     struct adv_mfg_data *recv_mfg_data;
  87.     struct dm_request req;
  88.     switch (data->type) {
  89.     case BT_DATA_MANUFACTURER_DATA:
  90.         if (sizeof(struct adv_mfg_data) == data->data_len) {
  91.             recv_mfg_data = (struct adv_mfg_data *)data->data;
  92.             bt_addr_le_copy(&req.bt_addr, user_data);
  93.             req.role = DM_ROLE_INITIATOR;
  94.             req.ranging_mode = peer_ranging_mode_get();
  95.             /* We need to make sure that we only initiate a ranging to a single peer.
  96.              * A scan response that is received by this device can be received by
  97.              * multiple other devices which can all start a ranging at the same time
  98.              * as a consequence. To prevent this, we need to make sure that we set a
  99.              * per-peer random as the random seed. This helps the ranging library to
  100.              * avoid interference from other devices trying to range at the same time.
  101.              *
  102.              * This means that the initiator and the reflector need to set the same
  103.              * value for the random seed.
  104.              */
  105.             req.rng_seed =
  106.                 sys_le32_to_cpu(recv_mfg_data->rng_seed) + scanner_random_share;
  107.             req.start_delay_us = 0;
  108.             req.extra_window_time_us = 0;
  109.             dm_request_add(&req);
  110.         }
  111.         return false;
  112.     default:
  113.         return true;
  114.     }
  115. }
  116. static uint32_t get_id_addr_random_share(void)
  117. {
  118.     bt_addr_le_t addrs[CONFIG_BT_ID_MAX];
  119.     size_t count = CONFIG_BT_ID_MAX;
  120.     bt_id_get(addrs, &count);
  121.     __ASSERT(count == 1, "The sample assumes a single ID addr");
  122.     return scanner_addr_to_random_share(&addrs[0].a);
  123. }
  124. static uint32_t scanner_addr_to_random_share(const bt_addr_t *p_scanner_addr)
  125. {
  126.     return (p_scanner_addr->val[0] | p_scanner_addr->val[1] << 8 |
  127.         p_scanner_addr->val[2] << 16 | p_scanner_addr->val[3] << 24) +
  128.      (p_scanner_addr->val[4] | p_scanner_addr->val[5] << 8);
  129. }
  130. static void scan_filter_match(struct bt_scan_device_info *device_info,
  131.              struct bt_scan_filter_match *filter_match,
  132.              bool connectable)
  133. {
  134.     bt_addr_le_t addr;
  135.     bt_addr_le_copy(&addr, device_info->recv_info->addr);
  136.     peer_supported_add(device_info->recv_info->addr);
  137.     bt_data_parse(device_info->adv_data, data_cb, &addr);
  138. }
  139. BT_SCAN_CB_INIT(scan_cb, scan_filter_match, NULL, NULL, NULL);
  140. static void adv_scanned_cb(struct bt_le_ext_adv *adv,
  141.             struct bt_le_ext_adv_scanned_info *info)
  142. {
  143.     struct dm_request req;
  144.     if (peer_supported_test(info->addr)) {
  145.         bt_addr_le_copy(&req.bt_addr, info->addr);
  146.         req.role = DM_ROLE_REFLECTOR;
  147.         req.ranging_mode = peer_ranging_mode_get();
  148.         /* We need to make sure that we only initiate a ranging to a single peer.
  149.          * A scan response from this device can be received by multiple peers which can
  150.          * all start a ranging at the same time as a consequence. To prevent this,
  151.          * we need to make sure that we set a per-peer random as the random seed.
  152.          * This helps the ranging library to avoid interference from other devices
  153.          * trying to range at the same time.
  154.          *
  155.          * This means that the initiator and the reflector need to set the same value
  156.          * for the random seed.
  157.          */
  158.         req.rng_seed = peer_rng_seed_get() + scanner_addr_to_random_share(&info->addr->a);
  159.         req.start_delay_us = 0;
  160.         req.extra_window_time_us = 0;
  161.         dm_request_add(&req);
  162.         adv_update_data();
  163.     }
  164. }
  165. const static struct bt_le_ext_adv_cb adv_cb = {
  166.     .scanned = adv_scanned_cb,
  167. };
  168. static void adv_update_data(void)
  169. {
  170.     int err;
  171.     if (!adv) {
  172.         return;
  173.     }
  174.     mfg_data.rng_seed = peer_rng_seed_prepare();
  175.     err = bt_le_ext_adv_set_data(adv, ad, ARRAY_SIZE(ad), sd, ARRAY_SIZE(sd));
  176.     if (err) {
  177.         printk("Failed setting adv data (err %d)\n", err);
  178.     }
  179. }
  180. static int adv_start(void)
  181. {
  182.     int err;
  183.     struct bt_le_ext_adv_start_param ext_adv_start_param = {0};
  184.     if (adv) {
  185.         err = bt_le_ext_adv_stop(adv);
  186.         if (err) {
  187.             printk("Failed to stop extended advertising (err %d)\n", err);
  188.             return err;
  189.         }
  190.             err = bt_le_ext_adv_delete(adv);
  191.         if (err) {
  192.             printk("Failed to delete advertising set (err %d)\n", err);
  193.             return err;
  194.         }
  195.     }
  196.     err = bt_le_ext_adv_create(adv_param, &adv_cb, &adv);
  197.     if (err) {
  198.         printk("Failed to create advertising set (err %d)\n", err);
  199.         return err;
  200.     }
  201.     err = bt_le_ext_adv_set_data(adv, ad, ARRAY_SIZE(ad), sd, ARRAY_SIZE(sd));
  202.     if (err) {
  203.         printk("Failed setting adv data (err %d)\n", err);
  204.         return err;
  205.     }
  206.     err = bt_le_ext_adv_start(adv, &ext_adv_start_param);
  207.     if (err) {
  208.         printk("Failed to start extended advertising (err %d)\n", err);
  209.         return err;
  210.     }
  211.     return err;
  212. }
  213. static int scan_start(void)
  214. {
  215.     int err;
  216.     bt_scan_init(&scan_init);
  217.     bt_scan_cb_register(&scan_cb);
  218.     err = bt_scan_filter_add(BT_SCAN_FILTER_TYPE_MANUFACTURER_DATA, &scan_mfg_data);
  219.     if (err) {
  220.         printk("Scanning filters cannot be set (err %d)\n", err);
  221.         return err;
  222.     }
  223.     err = bt_scan_filter_enable(BT_SCAN_MANUFACTURER_DATA_FILTER, false);
  224.     if (err) {
  225.         printk("Filters cannot be turned on (err %d)\n", err);
  226.         return err;
  227.     }
  228.     scanner_random_share = get_id_addr_random_share();
  229.     err = bt_scan_start(BT_SCAN_TYPE_SCAN_ACTIVE);
  230.     if (err) {
  231.         printk("Scanning failed to start (err %d)\n", err);
  232.         return err;
  233.     }
  234.     return err;
  235. }
  236. static void adv_work_handle(struct k_work *item)
  237. {
  238.     adv_start();
  239. }
  240. static void connected(struct bt_conn *conn, uint8_t conn_err)
  241. {
  242.     adv_param = &adv_param_noconn;
  243.     k_work_submit(&adv_work);
  244.     dk_set_led_on(CON_STATUS_LED);
  245. }
  246. static void disconnected(struct bt_conn *conn, uint8_t reason)
  247. {
  248.     adv_param = &adv_param_conn;
  249.     k_work_submit(&adv_work);
  250.     dk_set_led_off(CON_STATUS_LED);
  251. }
  252. BT_CONN_CB_DEFINE(conn_callbacks) = {
  253.     .connected = connected,
  254.     .disconnected = disconnected,
  255. };
  256. static int bt_sync_init(void)
  257. {
  258.     /* Synchronisation is based on advertising and scanning modes.
  259.      * It occurs when SCAN_REQ and SCAN_RESP packets are exchanged.
  260.      */
  261.     int err;
  262.     printk("DM Bluetooth LE Synchronization initialization\n");
  263.     mfg_data.company_code = sys_cpu_to_le16(CONFIG_BT_COMPANY_ID_NORDIC);
  264.     mfg_data.support_dm_code = sys_cpu_to_le32(SUPPORT_DM_CODE);
  265.     mfg_data.rng_seed = sys_cpu_to_le32(peer_rng_seed_prepare());
  266.     err = adv_start();
  267.     if (err) {
  268.         printk("Failed to start advertising (err %d)\n", err);
  269.         return err;
  270.     }
  271.     err = scan_start();
  272.     if (err) {
  273.         printk("Failed to start scanning (err %d)\n", err);
  274.     }
  275.     return err;
  276. }
  277. static void data_ready(struct dm_result *result)
  278. {
  279.     if (result->status) {
  280.         peer_update(result);
  281.     }
  282. }
  283. static struct dm_cb dm_cb = {
  284.     .data_ready = data_ready,
  285. };
  286. /*2024.10.20 Sunday Engineer from here*/
  287. BUILD_ASSERT(DT_NODE_HAS_COMPAT(DT_CHOSEN(zephyr_console), zephyr_cdc_acm_uart),
  288.      "Console device is not ACM CDC UART device");
  289. #if defined(CONFIG_USB_DEVICE_STACK_NEXT)
  290. static struct usbd_context *sample_usbd;
  291. static int enable_usb_device_next(void)
  292. {
  293.     int err;
  294.     sample_usbd = sample_usbd_init_device(NULL);
  295.     if (sample_usbd == NULL) {
  296.         return -ENODEV;
  297.     }
  298.     err = usbd_enable(sample_usbd);
  299.     if (err) {
  300.         return err;
  301.     }
  302.     return 0;
  303. }
  304. #endif /* IS_ENABLED(CONFIG_USB_DEVICE_STACK_NEXT) */
  305. /*2024.10.20 Sunday Engineer to here*/
  306. int main(void)
  307. {
  308. /*2024.10.20 Sunday Engineer from here*/
  309.     const struct device *const dev = DEVICE_DT_GET(DT_CHOSEN(zephyr_console));
  310.     uint32_t dtr = 0;
  311. #if defined(CONFIG_USB_DEVICE_STACK_NEXT)
  312.     if (enable_usb_device_next()) {
  313.         return 0;
  314.     }
  315. #else
  316.     if (usb_enable(NULL)) {
  317.         return 0;
  318.     }
  319. #endif
  320.     /* Poll if the DTR flag was set */
  321.     while (!dtr) {
  322.         uart_line_ctrl_get(dev, UART_LINE_CTRL_DTR, &dtr);
  323.         /* Give CPU resources to low priority threads. */
  324.         k_sleep(K_MSEC(100));
  325.     }
  326.     //while (1) {
  327.         printk("Hello World! %s\n", CONFIG_ARCH);
  328.         k_sleep(K_SECONDS(1));
  329.     //}
  330. /*2024.10.20 Sunday Engineer to here*/
  331.     int err;
  332.     uint32_t blink_status = 0;
  333.     struct dm_init_param init_param;
  334.     printk("Starting Distance Measurement example\n");
  335.     err = dk_leds_init();
  336.     if (err) {
  337.         printk("LEDs init failed (err %d)\n", err);
  338.         return 0;
  339.     }
  340.     err = peer_init();
  341.     if (err) {
  342.         printk("Peer init failed (err %d)\n", err);
  343.         return 0;
  344.     }
  345.     init_param.cb = &dm_cb;
  346.     err = dm_init(&init_param);
  347.     if (err) {
  348.         printk("Distance measurement init failed (err %d)\n", err);
  349.         return 0;
  350.     }
  351.     err = service_ddfs_init();
  352.     if (err) {
  353.         printk("DDF Service init failed (err %d)\n", err);
  354.         return 0;
  355.     }
  356.     err = bt_enable(NULL);
  357.     if (err) {
  358.         printk("Bluetooth init failed (err %d)\n", err);
  359.         return 0;
  360.     }
  361.     err = bt_sync_init();
  362.     if (err) {
  363.         printk("Synchronisation init failed (err %d)\n", err);
  364.         return 0;
  365.     }
  366.     for (;;) {
  367.         dk_set_led(RUN_STATUS_LED, (++blink_status) % 2);
  368.         k_sleep(K_MSEC(RUN_LED_BLINK_INTERVAL));
  369.         service_azimuth_elevation_simulation();
  370.     }
  371. }

↑の変更を適用した後、Add build configuration
Board targetのドロップダウンリストに52833と入力して、nrf52833dkを選ぶ
下のほうまでスクロールしてBuild Configuration
なんじゃかんじゃやっている
おわったっぽい、、、警告が13個もあるが、いったん、掘らない
実行とデバッグアイコンを押す
launch.jsonファイルを作成します。を押す
ここでの選択は全く意味ないけどCortex Debugを押す
エディタにlanuch.jsonが開くので、これを入力(てかコピペ)
今回もCMSIS-DAPと化したSeeeduinoXIAOを使う
  1. {
  2.     "version": "0.2.0",
  3.     "configurations": [
  4.         {
  5.             "name": "Cortex Debug",
  6.             "type": "cortex-debug",
  7.             "request": "launch",
  8.             "servertype": "openocd",
  9.             "cwd": "${workspaceRoot}",
  10.             "executable": "${workspaceFolder}/build/zephyr/zephyr.elf",
  11.             "configFiles": [
  12.                 "interface/cmsis-dap.cfg",
  13.                 "target/nrf52.cfg"
  14.             ],
  15.             "runToEntryPoint": "main",
  16.             "postRestartCommands": [
  17.                 "break main",
  18.                 "continue"
  19.             ],
  20.             "serverpath": "/usr/bin/openocd", // OpenOCDのインストールパス
  21.             "gdbPath": "/home/hoge/ncs/toolchains/e9dba88316/opt/zephyr-sdk/arm-zephyr-eabi/bin/arm-zephyr-eabi-gdb", // GDBのパス
  22.             "armToolchainPath": "/home/hoge/ncs/toolchains/e9dba88316/opt/zephyr-sdk/arm-zephyr-eabi/bin/" // ARMツールチェーンのパス
  23.         }
  24.     ]
  25. }
main.cのBLE Distance Measurementの最初の部分にブレークポイントを置く
デバッグを開始する
mainの直後でいったん止まる
再生ボタンを押す、、、とDTRフラグ待ち(USB接続待ちってことになるのかな?)になる
VSCodeのシリアルモニターで、ポートの再読み込みやらポートの選択やらして、監視の開始を押すとちゃんと動いていることがわかる
さらに再生ボタンを押す
ちゃんと動いているっぽい。で、一旦PCから取っ払って、もう1つのボードをつないで、デバッグを開始する部分からおんなじことをやる。
まぁ、こういう状態
で、さっきぶっこぬいたボードを、、、まぁうちの場合、WindowsPCのほうにつないでTeraTermでポートを開く(1つのPCでも問題ないはずなんやけど、紛らわしさを避けるために)と、
こんな感じで、両方のボードからコンソールに出力される、、、いくつかの方法で推定しているっぽい。まぁこの値、正しくはなさそうだけど、距離を変えたときにそれに伴って値が動くかどうかってのが重要。で、今日はしんどいので、ここまでにする。とりあえず、動くところまでいったところがえらいぞ、じぶん!いや、役に立つのかどうかわからんのに、時間やお金を自分に投資しているのがえらいぞ、じぶん!

2024年10月19日土曜日

MDBT50Q-DB-33(nRF52833)でUSBにprintk

MDBT50Q-DB-33(nRF52833)でUSBにprintkで文字列を出力する

 
nRF52833にCMSIS-DAPデバッガをつないでVSCodeでデバッグの最後のほうで、nRF52833評価ボード(MDBT50Q-DB-33)でprintk出力する際にFTDIのUSBシリアル変換ICのボードを使ったわけだけど、nRF52833にはUSBポートあるので、そこから出力できないものかって思う。
ところで、MDBT50Q-DB-33は台湾のRaytocってところが作っていて本家はこちら(https://www.raytac.com/product/ins.php?index_id=97)。スイッチサイエンスや共立エレショップで4000円程度で購入できる。Nordic製のnRF52833 DKはDigikeyで8000円程度で購入できる。本家のほうがドキュメントとかexampleとかが充実しているので安心なんだけど、安いのを使いこなすってスキルも必要かなっと(単なるお財布事情を高尚に語る)。
では、、、とはいえ、実は、それらしいexampleがあるので、これがMDBT50Q-DB-33で動けばオkなわけで、しかもnRF52833 DKのボードコンフィグで動くのではないかと、HP見るとUSBのD+/D-が単につながっているだけだし、動く確信をもって、それを確認するだけ。
VSCodeを起動して、Nordicのアイコンを押す。
Create a new application
Copy a sample
Consoleって入力して、Console over USBを選択
フォルダを決めて(通常はそのまんまおすすめされた通りでもいい)、エンター
当然、Open
これ↓は無視
Nordicアイコンを再び押す
  Add build configuration
  Board targetのドロップダウンリストに52833と入力して、nrf52833dkを選ぶ(MDBT50Q-DB-33も選択できるんだけど、あえて)
 下のほうまでスクロールしてBuild Configuration
ターミナルを見ると、なんじゃかんじゃやっていることがわかる
で、おわった的なことがわかる
デバッグボタンを押す
launch.jsonファイルを作成します。を押す
ここでの選択は全く意味ないけどCortex Debugを押す
エディタにlanuch.jsonが開くので、これを入力(てかコピペ)
今回もCMSIS-DAPと化したSeeeduinoXIAOを使う
  1. {
  2.     "version": "0.2.0",
  3.     "configurations": [
  4.         {
  5.             "name": "Cortex Debug",
  6.             "type": "cortex-debug",
  7.             "request": "launch",
  8.             "servertype": "openocd",
  9.             "cwd": "${workspaceRoot}",
  10.             "executable": "${workspaceFolder}/build/zephyr/zephyr.elf",
  11.             "configFiles": [
  12.                 "interface/cmsis-dap.cfg",
  13.                 "target/nrf52.cfg"
  14.             ],
  15.             "runToEntryPoint": "main",
  16.             "postRestartCommands": [
  17.                 "break main",
  18.                 "continue"
  19.             ],
  20.             "serverpath": "/usr/bin/openocd", // OpenOCDのインストールパス
  21.             "gdbPath": "/home/hoge/ncs/toolchains/e9dba88316/opt/zephyr-sdk/arm-zephyr-eabi/bin/arm-zephyr-eabi-gdb", // GDBのパス
  22.             "armToolchainPath": "/home/hoge/ncs/toolchains/e9dba88316/opt/zephyr-sdk/arm-zephyr-eabi/bin/" // ARMツールチェーンのパス
  23.         }
  24.     ]
  25. }
で、ブツを接続
再生ボタンを押す
mainの最初の命令で自動的に止まる
この段階ではそれらしいUSBデバイスは接続されていないかんじになてる
再生ボタンを押す
それらしいのが現れた
VSCodeのシリアルモニターを開いてそれらしいポートを設定して監視の開始を押す(VSCode内じゃなくてもお好みのターミナルソフトでも当然ok)
こんな感じでちゃんと出力されてますイイネ
 
ところで、わたくしは、Nordicの回し者ではない。たまたまそろそろBLEに取り組もうかなと思って最初に入手したのがSeeeduino XIAO BLE nRF52840だったからその流れで。BLEのチップってあちこちのICメーカがあるよね、、、大手だとNordicとか???とか??とか。???は仕様がほとんど開示されていなくて、ホビーユーザーには敷居が高い。??はアレだし。ホビーユーザーは自然とNordic一択かも。