Issue initializing UART after enabling mcumgr serial transport

Hello,

We have recently decided to transition from nRF5 SDK to nRF Connect SDK to develop a simple application that is able to respond with its FW version when requested via UART, and to receive upgrades via serial communication. We use a device based on nRF52840 and we based the application on NUS Central UART example as a starting point. We added the functionality to handle custom requests for the FW version over UART.

After we successfully tested this functionality, we decided to use this guide posted by Simon to add serial DFU functionality to the application. In the guide Simon suggests to add this configuration CONFIG_MCUMGR_SMP_UART to prj.conf and enable it by setting its value to 'y' in order to enable the serial mcumgr transport. It seems like enabling this prevents the UART module from being initialized anymore at start up, and the call to uart_callback_set(uart, uart_cb, NULL) returns an error. We tracked the issue further and noticed that inside that routine the callback check done on line 1240 returns NULL. This only occurs when we enable CONFIG_MCUMGR_SMP_UART. Below is the code snippet where the error was discovered.

if (api->callback_set == NULL) {

        return -ENOSYS;
    }
I am including the rest of the settings from prj.conf.
#
# Copyright (c) 2018 Nordic Semiconductor
#
# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause
#

# Enable mcumgr
CONFIG_MCUMGR=y

# Enable most core commands.
CONFIG_MCUMGR_CMD_IMG_MGMT=y
CONFIG_MCUMGR_CMD_OS_MGMT=y

# Enable the UART driver
CONFIG_UART_ASYNC_API=y
CONFIG_NRFX_UARTE0=y

# Enable the BLE stack with GATT Client configuration
CONFIG_BT=y
CONFIG_BT_CENTRAL=y
CONFIG_BT_SMP=y
CONFIG_BT_GATT_CLIENT=y

# Enable the BLE modules from NCS
CONFIG_BT_NUS_CLIENT=y
CONFIG_BT_SCAN=y
CONFIG_BT_SCAN_FILTER_ENABLE=y
CONFIG_BT_SCAN_UUID_CNT=1
CONFIG_BT_GATT_DM=y
CONFIG_HEAP_MEM_POOL_SIZE=2048

# This example requires more workqueue stack
# CONFIG_SYSTEM_WORKQUEUE_STACK_SIZE=2048

# Enable bonding
CONFIG_BT_SETTINGS=y
CONFIG_FLASH=y
CONFIG_FLASH_PAGE_LAYOUT=y
CONFIG_FLASH_MAP=y
CONFIG_NVS=y
CONFIG_SETTINGS=y

# Config logger
CONFIG_LOG=y
CONFIG_LOG_BACKEND_RTT=y
CONFIG_ASSERT=y

# #Enable immutable bootloader
# CONFIG_SECURE_BOOT=y
# #Enable upgradable bootloader
# CONFIG_BOOTLOADER_MCUBOOT=y
# #Use minimum partition
# CONFIG_B0_MIN_PARTITION_SIZE=y
# #Automatically generate pre-signed variants
# CONFIG_BUILD_S1_VARIANT=y
# #Enable signing the firmware image with the private key located at the project relative location
# CONFIG_SB_SIGNING_KEY_FILE="../../../keys/priv.pem"

#Enable the serial mcumgr transport.
CONFIG_MCUMGR_SMP_UART=y
#Disable UART Console and enable the RTT console
CONFIG_UART_CONSOLE=n
CONFIG_RTT_CONSOLE=y
CONFIG_USE_SEGGER_RTT=y

#Some command handlers require a large stack.
CONFIG_SYSTEM_WORKQUEUE_STACK_SIZE=4096
We are wondering what is the reason that we are unable to enable DFU over serial inside of an application that uses the UART? Furthermore, if this approach is not feasible, can you provide some guidance to help us remedy the issue we are seeing?
Thank you!
Parents Reply Children
  • Hello Øivind, 

    Thanks again for the help! In reply to your question...

    So it doesn't boot the next app automatically when you reset after upload?

    Yes, it does boot the new image after reset. We were able to put the nRF52840 DK in serial recovery mode using the default sequence: press and hold BUTTON1 - P0.11 and reset the board, and it does update.

    We did run into an issue when we tried to re-assign the DFU detect pin from P0.11 to P0.25. Let me provide some explanation why we need to do that. Since we cannot perform a DFU within the application, we decided to use the same GPIO to reset the application and also to allow us to enter DFU mode. On our custom board that pin is P0.25. We are able to confirm that the application resets when BUTTON4 is pressed and held, but it does not enter DFU mode.

    We thought that re-mapping the pin would be pretty straight forward... but apparently we must be making it more difficult than it should be. We tried to gain a little more understanding of how mcuboot works in order to make sure it is possible. We looked at it under bootloader\mcuboot\boot\zephyr\main.c.

    It seems that mcuboot uses mcuboot-button0 alias which has P0.11 assigned as DFU detect pin. Again, in our case, we need to re-assign that functionality to BUTTON4 - P0.25. We tried to do this by updating mcuboot.conf under <project_directory>\child_image. We enabled mcuboot indication LED to help us confirm when we do enter DFU mode. It seems that we are entering DFU mode only when pressing BUTTON1 and not BUTTON4. 

    We also tried to create an overlay file to reassign mcuboot-button0 and created mcuboot.overlay under <project_directory>\child_image. Below are the contents of this file.

    Here are the contents of our application's CMAKE file

    We would welcome any advice with this challenge.

    Thank you!

Related