dms/ota_update/main.c

/*******************************************************************************
* # License
* Copyright 2019 Silicon Laboratories Inc. www.silabs.com
*******************************************************************************
*
* The licensor of this software is Silicon Laboratories Inc. Your use of this
* software is governed by the terms of Silicon Labs Master Software License
* Agreement (MSLA) available at
* www.silabs.com/about-us/legal/master-software-license-agreement. This
* software is distributed to you in Source Code format and is governed by the
* sections of the MSLA applicable to Source Code.
*
******************************************************************************/
#include "gos.h"
#include "example_app_util.h"
// The period in seconds that the device checks the DMS for firmare updates
// NOTE: This value is just for demo purposes.
// In production this value should be hours or days
#define FIRMWARE_QUERY_PERIOD 60
// Allow a 'multi-pass' firmware update
#define ALLOW_MULTIPASS_UPDATES true
/*************************************************************************************************/
void gos_app_init(void)
{
GOS_LOG("\r\nDMS OTA DFU example starting ...");
// Get the last DFU status
const gos_dfu_status_t last_dfu_status = gos_dms_get_dfu_status();
// Clear the DFU status
// If the status is non-null
if(last_dfu_status != GOS_DFU_STATUS_NONE)
{
// Then print the status as a log
GOS_LOG("Last DFU status: %d", last_dfu_status);
}
// Bring up the network if it isn't already
// This also pretty prints an error if no network credentials are set
if(example_app_util_network_up(GOS_INTERFACE_WLAN, false, network_event_handler) == GOS_SUCCESS)
{
// If the network is already up
// then invoke the DFU query event handler
gos_event_issue(query_dms_event_handler, NULL, GOS_EVENT_FLAG_NONE);
}
}
/*************************************************************************************************/
static void network_event_handler(bool is_up)
{
if(is_up == true)
{
GOS_LOG("Network up");
// Invoke the DFU query event handler
gos_event_issue(query_dms_event_handler, NULL, GOS_EVENT_FLAG_NONE);
}
else
{
GOS_LOG("Network down");
}
}
/*************************************************************************************************/
static void query_dms_event_handler(void *arg)
{
gos_result_t result;
char response_str[192];
gos_buffer_t response =
{
.data = (uint8_t*)response_str,
.size = sizeof(response_str)-1
};
GOS_LOG("Querying DMS for firmware update ...");
if(GOS_FAILED(result, gos_dms_dfu_query(&status, &response)))
{
GOS_LOG("Failed to query DMS, err:%d", result);
}
else
{
// Null-terminate string
response_str[response.size] = 0;
switch(status)
{
GOS_LOG("Query error, msg: %s", response_str);
break;
GOS_LOG("Firmware up-to-date");
break;
GOS_LOG("Update available: %s", response_str);
break;
default:
GOS_LOG("Unknown status: %d", status);
}
}
// If a firmware update is available
{
GOS_LOG("Invoking firmware update ...");
// Then invoke an OTA firmware update
// NOTE: This does NOT return if successful
if(GOS_FAILED(result, gos_dms_ota_update(NULL, ALLOW_MULTIPASS_UPDATES)))
{
GOS_LOG("Failed to invoke firmware update, err:%d", result);
}
}
// If we get here then something failed or no update is available
// Register this handler to execute again at a later time
GOS_LOG("Querying DMS again in %d seconds", FIRMWARE_QUERY_PERIOD);
gos_event_register_timed(query_dms_event_handler, NULL, FIRMWARE_QUERY_PERIOD*1000, GOS_EVENT_FLAG_NONE);
}