DFU for nrf52840

We are trying to implement DFU for a nrf52840. Step one is creating a binary that Notehub can retrieve the version information from.

Following the esp32 example, I added a version.c file:

#include "main.h"
#include <string.h>

// Edit options, Common
// Build
// Set 'Always Rebuild' to yes

// C Helpers to convert a number to a string
#define STRINGIFY(x) STRINGIFY_(x)
#define STRINGIFY_(x) #x

// Definitions used by firmware update
#define PRODUCT_ORG_NAME      ""
#define PRODUCT_DISPLAY_NAME  "Notecard Example"
#define PRODUCT_FIRMWARE_ID   "notecard-example-v1"
#define PRODUCT_DESC          ""
#define PRODUCT_MAJOR         1
#define PRODUCT_MINOR         0
#define PRODUCT_PATCH         0
#define PRODUCT_BUILD         0
#define PRODUCT_BUILT         __DATE__ " " __TIME__
#define PRODUCT_BUILDER       ""
#define PRODUCT_VERSION       STRINGIFY(PRODUCT_MAJOR) "." STRINGIFY(PRODUCT_MINOR) "." STRINGIFY(PRODUCT_PATCH)

// This is a product configuration JSON structure that enables the Notehub to recognize this
// firmware when it's uploaded, to help keep track of versions and so we only ever download
// firmware builds that are appropriate for this device.
#define QUOTE(x) "\"" x "\""
#define FIRMWARE_VERSION_HEADER "firmware::info:"
#define FIRMWARE_VERSION FIRMWARE_VERSION_HEADER         \
    "{" QUOTE("org") ":" QUOTE(PRODUCT_ORG_NAME)         \
    "," QUOTE("product") ":" QUOTE(PRODUCT_DISPLAY_NAME) \
    "," QUOTE("description") ":" QUOTE(PRODUCT_DESC)     \
    "," QUOTE("firmware") ":" QUOTE(PRODUCT_FIRMWARE_ID) \
    "," QUOTE("version") ":" QUOTE(PRODUCT_VERSION)      \
    "," QUOTE("built") ":" QUOTE(PRODUCT_BUILT)          \
    "," QUOTE("ver_major") ":" STRINGIFY(PRODUCT_MAJOR)  \
    "," QUOTE("ver_minor") ":" STRINGIFY(PRODUCT_MINOR)  \
    "," QUOTE("ver_patch") ":" STRINGIFY(PRODUCT_PATCH)  \
    "," QUOTE("ver_build") ":" STRINGIFY(PRODUCT_BUILD)  \
    "," QUOTE("builder") ":" QUOTE(PRODUCT_BUILDER)      \
    "}"

const char *productVersion() {
    return ("Ver " PRODUCT_VERSION " " PRODUCT_BUILT);
}

// Return the firmware's version, which is both stored within the image and which is verified by DFU
const char *firmwareVersion() {
    return &FIRMWARE_VERSION[strlen(FIRMWARE_VERSION_HEADER)];
}

I confirmed that the binary file contains the json formatted string with the “firmware::info” header. It’s near the end of the file, with all the other string constants.

But when I upload it to Notehub, the version is not recognized. The version, metadata, organization, description, product, built, and builder fields are empty.

Is Notehub looking for the “firmware::info” string in a particular location?

Is there a way to remove a file from Notehub once I’ve uploaded it?

Thanks

Here’s the section of the binary file that contains the json encoded version information:

Hi @mdf thanks for the question, and welcome to the community! From the image you shared, it looks like the firmware::info string is appearing twice in the binary, first as a null string and then with the correct value. Can you change your firmwareVersion function above to the following and let me know if that helps?

const char *firmwareVersion()
{
    return &FIRMWARE_VERSION[sizeof(FIRMWARE_VERSION_HEADER)-1];
}

Thanks!

Thanks, that worked.

Now how do I get rid of the earlier ‘bad’ uploads to Notehub?

1 Like

Hi @mdf deleting firmware is not currently supported in Notehub.io, but it is on our backlog.

I’m making progress…
I successfully uploaded a firmware binary to Notehub.
I successfully downloaded it to the Notecard.
I successfully retrieved it from the Notecard (without actually flashing it).
The md5 hashes matched.

Now I’m ready to actually write the data to flash.

I can’t do it a second time though, I uploaded a new binary with a different version number, but it doesn’t seem to download to the Notecard.

The dfu status is:

{"req":"dfu.status"}
{"status":"successful firmware update","mode":"completed","on":true}
dfu: no image is ready for firmware update

The environment vars on the Notecard show yesterday’s download (06/01/21)

{"req":"env.get"}
{"body":{"sensor_threshold":"7400000","measure_interval_sec":"6","name":"Sensor","send_interval_sec":"24","_fw":"MyFirmware$20210601192009.bin","_fw_retry":"1622650392"}}
 code here

The Notehub Device page has:
DFU Version: 1.0.0
DFU Status: Completed
Requested Version: 1.0.1

On the Events page I see:

device_vars {"_fw":"MyFirmware$20210603142236.bin","_fw_retry":"1622731322"}

Which is the one I am trying to download.

I also tried changing an environment variable, and it shows up in _env.dbs, but not on the “env.get” response from the Notecard.

Events are coming from the Notecard just fine.

Thanks for your help.

Never mind. It just took a while.

1 Like