From 0c7ae05f7c4d214e55a4b42f3b6604be21e2cdbe Mon Sep 17 00:00:00 2001 From: Tony Le Date: Mon, 7 Aug 2023 11:22:38 -0700 Subject: [PATCH] samples: cellular: nrf_cloud_rest_device_message: use CAF Updated the sample to use CAF instead of DK library for led and button events. Added a device-tree overlay for LEDs to work with CAF LEDs module. Added header files for buttons and LEDs definition which are required by CAF. Also, added error message for when the sample fails to send alerts to nRF Cloud. Signed-off-by: Tony Le --- .../releases/release-notes-changelog.rst | 12 +++ .../CMakeLists.txt | 3 + .../boards/nrf9160dk_nrf9160_ns.overlay | 52 ++++++++++++ .../include/buttons_def.h | 25 ++++++ .../include/leds_def.h | 28 +++++++ .../nrf_cloud_rest_device_message/prj.conf | 17 +++- .../nrf_cloud_rest_device_message/src/main.c | 83 ++++++++++++++----- 7 files changed, 197 insertions(+), 23 deletions(-) create mode 100644 samples/cellular/nrf_cloud_rest_device_message/boards/nrf9160dk_nrf9160_ns.overlay create mode 100644 samples/cellular/nrf_cloud_rest_device_message/include/buttons_def.h create mode 100644 samples/cellular/nrf_cloud_rest_device_message/include/leds_def.h diff --git a/doc/nrf/releases_and_maturity/releases/release-notes-changelog.rst b/doc/nrf/releases_and_maturity/releases/release-notes-changelog.rst index a2e9cc28554..bb178f212bd 100644 --- a/doc/nrf/releases_and_maturity/releases/release-notes-changelog.rst +++ b/doc/nrf/releases_and_maturity/releases/release-notes-changelog.rst @@ -407,6 +407,18 @@ Cellular samples (renamed from nRF9160 samples) * Added reporting of device and connection info to the device shadow. +* :ref:`nrf_cloud_rest_device_message` sample: + + * Added: + + * A DTS overlay file for LEDs on the nRF9160 DK to be compatible with the :ref:`caf_leds` module. + * Header files for buttons and LEDs definition required by the :ref:`lib_caf` library. + + * Updated: + + * The sample to use the :ref:`lib_caf` library instead of the :ref:`dk_buttons_and_leds_readme` library. + * Displaying an error message when the sample fails to send an alert to nRF Cloud. + Trusted Firmware-M (TF-M) samples --------------------------------- diff --git a/samples/cellular/nrf_cloud_rest_device_message/CMakeLists.txt b/samples/cellular/nrf_cloud_rest_device_message/CMakeLists.txt index e1271347f25..d49138ecd9f 100644 --- a/samples/cellular/nrf_cloud_rest_device_message/CMakeLists.txt +++ b/samples/cellular/nrf_cloud_rest_device_message/CMakeLists.txt @@ -8,8 +8,11 @@ cmake_minimum_required(VERSION 3.20.0) find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE}) project(nRF_Cloud_REST_Device_Message_Sample) + zephyr_compile_definitions(PROJECT_NAME=${PROJECT_NAME}) +zephyr_include_directories(include/) # NORDIC SDK APP START +target_include_directories(app PRIVATE include/) target_sources(app PRIVATE src/main.c) # NORDIC SDK APP END diff --git a/samples/cellular/nrf_cloud_rest_device_message/boards/nrf9160dk_nrf9160_ns.overlay b/samples/cellular/nrf_cloud_rest_device_message/boards/nrf9160dk_nrf9160_ns.overlay new file mode 100644 index 00000000000..a3cc56db99f --- /dev/null +++ b/samples/cellular/nrf_cloud_rest_device_message/boards/nrf9160dk_nrf9160_ns.overlay @@ -0,0 +1,52 @@ +/* Copyright (c) 2023 Nordic Semiconductor ASA + * + * SPDX-License-Identifier: LicenseRef-Nordic-5-Clause + */ + +/ { + /* Define 4 monochromatic LEDs connected directly + * to the GPIO to be used with CAF LEDs module + */ + led0 { + compatible = "gpio-leds"; + status = "okay"; + + led0_0: led_0 { + gpios = <&gpio0 2 0>; + }; + }; + + led1 { + compatible = "gpio-leds"; + status = "okay"; + + led1_0: led_0 { + gpios = <&gpio0 3 0>; + }; + }; + + led2 { + compatible = "gpio-leds"; + status = "okay"; + + led2_0: led_0 { + gpios = <&gpio0 4 0>; + }; + }; + + led3 { + compatible = "gpio-leds"; + status = "okay"; + + led3_0: led_0 { + gpios = <&gpio0 5 0>; + }; + }; + + /* Disable the original leds node from device-tree + * since it is incompatible with the CAF LEDs module + */ + leds { + status = "disabled"; + }; +}; diff --git a/samples/cellular/nrf_cloud_rest_device_message/include/buttons_def.h b/samples/cellular/nrf_cloud_rest_device_message/include/buttons_def.h new file mode 100644 index 00000000000..d7df194d564 --- /dev/null +++ b/samples/cellular/nrf_cloud_rest_device_message/include/buttons_def.h @@ -0,0 +1,25 @@ +/* + * Copyright (c) 2023 Nordic Semiconductor ASA + * + * SPDX-License-Identifier: LicenseRef-Nordic-5-Clause + */ + +#include + +/* This file is included by the common application framework (CAF) library */ + +/* This configuration file is included only once from buttons module and holds + * information about pins forming the keyboard matrix. + */ + +/* This structure enforces the header file to be included only once in the build. + * Violating this requirement triggers a multiple definition error at link time. + */ +const struct {} buttons_def_include_once; + +static const struct gpio_pin col[] = {}; + +static const struct gpio_pin row[] = { + { .port = 0, .pin = DT_GPIO_PIN(DT_NODELABEL(button0), gpios) }, + { .port = 0, .pin = DT_GPIO_PIN(DT_NODELABEL(button1), gpios) }, +}; diff --git a/samples/cellular/nrf_cloud_rest_device_message/include/leds_def.h b/samples/cellular/nrf_cloud_rest_device_message/include/leds_def.h new file mode 100644 index 00000000000..5b11485293b --- /dev/null +++ b/samples/cellular/nrf_cloud_rest_device_message/include/leds_def.h @@ -0,0 +1,28 @@ +/* + * Copyright (c) 2023 Nordic Semiconductor ASA + * + * SPDX-License-Identifier: LicenseRef-Nordic-5-Clause + */ + +#include + +/* This configuration file is included only once from the main module and holds + * information about LED on and off effects. + */ + +/* This structure enforces the header file to be included only once in the build. + * Violating this requirement triggers a multiple definition error at link time. + */ +const struct {} leds_def_include_once; + +enum led_id { + LED_ID_0, + LED_ID_1, + LED_ID_2, + LED_ID_3, + + LED_ID_COUNT +}; + +static const struct led_effect led_effect_on = LED_EFFECT_LED_ON(LED_COLOR(255, 255, 255)); +static const struct led_effect led_effect_off = LED_EFFECT_LED_OFF(); diff --git a/samples/cellular/nrf_cloud_rest_device_message/prj.conf b/samples/cellular/nrf_cloud_rest_device_message/prj.conf index 59aaa7cd00b..6159589c497 100644 --- a/samples/cellular/nrf_cloud_rest_device_message/prj.conf +++ b/samples/cellular/nrf_cloud_rest_device_message/prj.conf @@ -14,8 +14,21 @@ CONFIG_NET_SOCKETS=y CONFIG_NET_SOCKETS_POSIX_NAMES=y CONFIG_NET_NATIVE=n -# Button/LED support -CONFIG_DK_LIBRARY=y +# Common Application Framework (CAF) +CONFIG_CAF=y +CONFIG_APP_EVENT_MANAGER=y +CONFIG_APP_EVENT_MANAGER_LOG_LEVEL_ERR=y + +# CAF button module with GPIOs +CONFIG_GPIO=y +CONFIG_CAF_BUTTONS=y +CONFIG_CAF_BUTTONS_POLARITY_INVERSED=y + +# CAF LEDs module with GPIOs +CONFIG_LED=y +CONFIG_CAF_LEDS=y +CONFIG_LED_GPIO=y +CONFIG_CAF_LEDS_GPIO=y # Modem/LTE Link CONFIG_NRF_MODEM_LIB=y diff --git a/samples/cellular/nrf_cloud_rest_device_message/src/main.c b/samples/cellular/nrf_cloud_rest_device_message/src/main.c index d2584be2ef1..3df507ef305 100644 --- a/samples/cellular/nrf_cloud_rest_device_message/src/main.c +++ b/samples/cellular/nrf_cloud_rest_device_message/src/main.c @@ -14,10 +14,17 @@ #include #include #include -#include #include #include +#include +#include +#include +#define MODULE main +#include + +#include "leds_def.h" + LOG_MODULE_REGISTER(nrf_cloud_rest_device_message, CONFIG_NRF_CLOUD_REST_DEVICE_MESSAGE_SAMPLE_LOG_LEVEL); @@ -58,9 +65,30 @@ static struct nrf_cloud_rest_context rest_ctx = { /* Flag to indicate if the user requested JITP to be performed */ static bool jitp_requested; +/* Register a listener for application events, specifically a button event */ +static bool app_event_handler(const struct app_event_header *aeh); +APP_EVENT_LISTENER(MODULE, app_event_handler); +APP_EVENT_SUBSCRIBE(MODULE, button_event); + +static int send_led_event(enum led_id led_idx, const int state) +{ + if (led_idx >= LED_ID_COUNT) { + LOG_ERR("Invalid LED ID: %d", led_idx); + return -EINVAL; + } + + struct led_event *event = new_led_event(); + + event->led_id = led_idx; + event->led_effect = state != 0 ? &led_effect_on : &led_effect_off; + APP_EVENT_SUBMIT(event); + + return 0; +} + static int set_led(const int led, const int state) { - int err = dk_set_led(led, state); + int err = send_led_event(led, state); if (err) { LOG_ERR("Failed to set LED %d, error: %d", led, err); @@ -69,16 +97,10 @@ static int set_led(const int led, const int state) return 0; } -static int init_leds(void) +static int set_leds_off(void) { - int err = dk_leds_init(); + int err = set_led(LTE_LED_NUM, 0); - if (err) { - LOG_ERR("LED init failed, error: %d", err); - return err; - } - - err = set_led(LTE_LED_NUM, 0); if (err) { return err; } @@ -88,15 +110,25 @@ static int init_leds(void) return err; } - return err; + return 0; } -static void button_handler(uint32_t button_states, uint32_t has_changed) +static bool app_event_handler(const struct app_event_header *aeh) { - if (has_changed & button_states & BIT(BTN_NUM - 1)) { - LOG_DBG("Button %d pressed", BTN_NUM); + struct button_event *event = is_button_event(aeh) ? cast_button_event(aeh) : NULL; + + if (!event) { + return false; + } else if (!event->pressed) { + return true; + } + + LOG_DBG("Button %d pressed", BTN_NUM); + if (event->key_id == (uint16_t)(BTN_NUM - 1)) { k_sem_give(&button_press_sem); } + + return true; } static int send_message(const char *const msg) @@ -303,10 +335,12 @@ static int init(void) { int err; - /* Init the LEDs */ - err = init_leds(); + /* Application event manager is used for button press and LED + * events from the common application framework (CAF) library + */ + err = app_event_manager_init(); if (err) { - LOG_ERR("LED initialization failed"); + LOG_ERR("Application Event Manager could not be initialized, error: %d", err); return err; } @@ -317,10 +351,13 @@ static int init(void) return -EFAULT; } - /* Init the button */ - err = dk_buttons_init(button_handler); + /* Inform the app event manager that this module is ready to receive events */ + module_set_state(MODULE_STATE_READY); + + /* Set the LEDs off after all modules are ready */ + err = set_leds_off(); if (err) { - LOG_ERR("Failed to initialize button: error: %d", err); + LOG_ERR("Failed to set LEDs off"); return err; } @@ -397,9 +434,13 @@ int main(void) } rest_ctx.keep_alive = true; - (void)nrf_cloud_rest_alert_send(&rest_ctx, device_id, + err = nrf_cloud_rest_alert_send(&rest_ctx, device_id, ALERT_TYPE_DEVICE_NOW_ONLINE, 0, NULL); + if (err) { + LOG_ERR("Error sending alert to cloud: %d", err); + } + err = nrf_cloud_rest_log_send(&rest_ctx, device_id, LOG_LEVEL_INF, SAMPLE_SIGNON_FMT, CONFIG_REST_DEVICE_MESSAGE_SAMPLE_VERSION);