Over The Air (OTA) Update Library

group index

This library provides support for OTA updating using Wi-Fi of the application code running on a PSoC® 6 MCU with CYW4343W or CYW43012 connectivity device. For simplification, this document will refer to an MQTT Broker or an HTTP Server as “server”.

The library provides a number of combinations on how to get the OTA image. One or two steps can be used to get the OTA image. The two steps are “get job” and “get data”. The caller can skip the “get job” step and get the OTA image directly.

Step 1 - Get Job:

  • The OTA Agent downloads a JSON “Job” document (default name “ota_update.json”).

  • The Job document has information about an update that is available, including its location.

Step 2: - Get Data:

  • The OTA Agent will download the OTA image to the secondary slot (Slot 1).

    On the next reboot, MCUboot will copy the new version of the application from the secondary slot (Slot 1) to the Primary slot (Slot 0) and run the application.

You can skip Step 1 by setting the use_get_job_flow field in cy_ota_network_params_t to CY_OTA_DIRECT_FLOW when calling cy_ota_agent_start().

The ModusToolbox OTA code examples import this library automatically.

Features and Functionality

This library utilizes MQTT or HTTPS and TLS to securely connect to and download an update for the users application.

Other features:

  • Configuration to adjust multiple timing values to customize how often to check for updates, and other parameters for the MQTT Broker connection.

  • Runs in a separate background thread, only connecting to the server based on the parameters passed to cy_ota_agent_start().

  • Server info, credentials, and other parameters are passed into cy_ota_agent_start().

  • Provides a callback mechanism to report stages of connect, download percentage, and errors.

Once the application starts the OTA Agent, the OTA Agent will contact the server at the defined intervals to see if there is an update available.

Integration Notes

A pre-defined configuration file has been bundled with this library.

The user is expected to:

  • Copy the cy_ota_config.h file from the libs/anycloud-ota/configs

    directory to the top-level code example directory.

  • Add the following to COMPONENTS in the code example project’s Makefile

    • FREERTOS, PSOC6HAL, LWIP, MBEDTLS and either 4343W or 43012 depending on the platform.

      For example, if CY8CKIT-062S2-43012 is chosen, the Makefile entry would be:

      COMPONENTS=FREERTOS PSOC6HAL LWIP MBEDTLS 43012
      

General Concept

The OTA Agent stores the update to the secondary slot and uses MCUboot to validate and copy the update from the secondary slot to the primary slot.

  • MCUboot runs the current application in the primary slot.

  • The OTA Agent downloads the update and stores it in the secondary slot.

  • The secondary slot is marked so that MCUboot will copy it over to the primary slot.

  • If validate_after_reboot == 0, the secondary slot will be tagged as “perm”

  • If validate_after_reboot == 1, the secondary slot will be tagged as “test”

  • If reboot_upon_completion == 1, the system will reboot automatically.

  • On the next system reboot, MCUboot sees that there is an update in the secondary slot and copies the update to the srimary slot.

  • MCUboot runs the current application (now the update) in the primary slot.

  • If validate_after_reboot == 1, the updated application must validate itself and call cy_ota_validated() to inform MCUboot that it is now “perm” to complete the process.

API Overview

Start the OTA Agent

cy_ota_start_agent() is a non-blocking call, which returns a context pointer that is used in subsequent calls.

The OTA Agent uses callbacks to signal the application when events occur.

cy_rslt_t

cy_ota_agent_start(cy_ota_network_params_t *network_params, cy_ota_agent_params_t *agent_params, cy_ota_context_ptr *ota_ptr);

These defines determine when the checks happen. Between checks, the OTA Agent is not conencted to a server, and not checking for updates.

  • CY_OTA_INITIAL_CHECK_SECS

  • CY_OTA_NEXT_CHECK_INTERVAL_SECS

  • CY_OTA_RETRY_INTERVAL_SECS

  • CY_OTA_CHECK_TIME_SECS

Stop the OTA Agent

When you want to stop the OTA Agent from checking for updates.

cy_rslt_t

cy_ota_agent_stop(cy_ota_context_ptr *ota_ptr);

Trigger a check right now.

Use this when you want to trigger a check for an OTA update earlier than

is currently scheduled. The OTA Agent must have been started already.

cy_rslt_t

cy_ota_get_update_now(cy_ota_context_ptr ota_ptr);

Override Default Settings

Copy the cy_ota_config.h file from the libs/anycloud-ota/configs

directory to the top-level code example directory in the project.

Change these values to your preferred settings.


#define CY_OTA_INITIAL_CHECK_SECS           (10)            /* 10 seconds */

#define CY_OTA_NEXT_CHECK_INTERVAL_SECS     (24 * 60 * 60)  /* 1 day between checks */

#define CY_OTA_RETRY_INTERVAL_SECS          (5)             /* 5 seconds between retries after an error */

#define CY_OTA_CHECK_TIME_SECS              (10 * 60)       /* 10 minutes */

#define CY_OTA_PACKET_INTERVAL_SECS         (0)             /* default disabled */

#define CY_OTA_JOB_CHECK_TIME_SECS           (30)               /* 30 seconds */

#define CY_OTA_DATA_CHECK_TIME_SECS          (20 * 60)           /* 20 minutes */

#define CY_OTA_RETRIES                      (3)             /* retry entire process 3 times */

#define CY_OTA_CONNECT_RETRIES              (3)             /* 3 server connect retries  */

#define CY_OTA_MAX_DOWNLOAD_TRIES           (3)             /* 3 download OTA Image retries */

/**********************************************************************
 * Message Defines
 **********************************************************************/

#define PUBLISHER_LISTEN_TOPIC              "publish_notify"

#define COMPANY_TOPIC_PREPEND               "anycloud"

#define PUBLISHER_DIRECT_TOPIC               "OTAImage"

#define CY_OTA_RESULT_SUCCESS               "Success"

#define CY_OTA_RESULT_FAILURE               "Failure"


#define CY_OTA_HTTP_JOB_FILE               "/ota_update.json"

#define CY_OTA_HTTP_DATA_FILE              "/anycloud-ota.bin"

#define CY_OTA_SUBSCRIBE_UPDATES_AVAIL \
"{\
\"Message\":\"Update Availability\", \
\"Manufacturer\": \"Express Widgits Corporation\", \
\"ManufacturerID\": \"EWCO\", \
\"ProductID\": \"Easy Widgit\", \
\"SerialNumber\": \"ABC213450001\", \
\"BoardName\": \"CY8CPROTO_062_4343W\", \
\"Version\": \"%d.%d.%d\", \
\"UniqueTopicName\": \"%s\"\
}"

#define CY_OTA_DOWNLOAD_REQUEST \
"{\
\"Message\":\"Request Update\", \
\"Manufacturer\": \"Express Widgits Corporation\", \
\"ManufacturerID\": \"EWCO\", \
\"ProductID\": \"Easy Widgit\", \
\"SerialNumber\": \"ABC213450001\", \
\"BoardName\": \"CY8CPROTO_062_4343W\", \
\"Version\": \"%d.%d.%d\", \
\"UniqueTopicName\": \"%s\" \
}"

#define CY_OTA_DOWNLOAD_CHUNK_REQUEST \
"{\
\"Message\":\"Request Data Chunk\", \
\"Manufacturer\": \"Express Widgits Corporation\", \
\"ManufacturerID\": \"EWCO\", \
\"ProductID\": \"Easy Widgit\", \
\"SerialNumber\": \"ABC213450001\", \
\"BoardName\": \"CY8CPROTO_062_4343W\", \
\"Version\": \"%d.%d.%d\", \
\"UniqueTopicName\": \"%s\", \
\"Filename\": \"%s\", \
\"Offset\": \"%ld\", \
\"Size\": \"%ld\"\
}"

#define CY_OTA_DOWNLOAD_DIRECT_REQUEST \
"{\
\"Message\":\"Send Direct Update\", \
\"Manufacturer\": \"Express Widgits Corporation\", \
\"ManufacturerID\": \"EWCO\", \
\"ProductID\": \"Easy Widgit\", \
\"SerialNumber\": \"ABC213450001\", \
\"BoardName\": \"CY8CPROTO_062_4343W\", \
\"Version\": \"%d.%d.%d\" \
}"

#define CY_OTA_MQTT_RESULT_JSON \
"{\
\"Message\":\"%s\", \
\"UniqueTopicName\": \"%s\"\
}"

#define CY_OTA_HTTP_RESULT_JSON \
"{\
\"Message\":\"%s\", \
\"File\":\"%s\" \
}"

#ifndef CY_OTA_HTTP_GET_TEMPLATE
#define CY_OTA_HTTP_GET_TEMPLATE \
    "GET %s HTTP/1.1\r\n" \
    "Host: %s:%d \r\n" \
    "\r\n"
#endif

#ifndef CY_OTA_HTTP_GET_RANGE_TEMPLATE
#define CY_OTA_HTTP_GET_RANGE_TEMPLATE \
    "GET %s HTTP/1.1\r\n" \
    "Host: %s:%d \r\n" \
    "Range: bytes=%ld-%ld \r\n" \
    "\r\n"
#endif

#ifndef CY_OTA_HTTP_POST_TEMPLATE
#define CY_OTA_HTTP_POST_TEMPLATE \
    "POST %s HTTP/1.1\r\n" \
    "Content-Length:%ld \r\n" \
    "\r\n%s"
#endif

/**********************************************************************
 * MQTT Defines
 **********************************************************************/

#define CY_OTA_MQTT_KEEP_ALIVE_SECONDS          (60)                /* 60 second keepalive. */

#define CY_OTA_MQTT_MAX_TOPICS                  (2)

#define CY_OTA_MQTT_TOPIC_PREFIX                "cy_ota_device"

#define CY_OTA_MQTT_CLIENT_ID_PREFIX            "cy_device"

Code Snippets

The following code snippet demonstrates an example for initializing the

cy_ota_network_params_t and ota_agent_params structures required to start the OTA Agent.
/* Macro to enable/disable TLS. */
#define ENABLE_TLS          (false)

#define HTTP_SERVER         "my.httpserver.com"
#define HTTP_SERVER_PORT    (80)                /* 443 for TLS. */

/* Number of MQTT topic filters. */
#define MQTT_TOPIC_FILTER_NUM   (1)

#define MQTT_BROKER         "mqtt.broker.com"

#define MQTT_BROKER_PORT    (1883)              /* (8883) for TLS support. */
/* MQTT topics. */
const char * mqtt_topics[ MQTT_TOPIC_FILTER_NUM ] =
{
        "anycloud/test/ota/image"
};

/* Root CA Certificate.
   Must include the PEM header and footer:

        "-----BEGIN CERTIFICATE-----\n" \
        ".........base64 data.......\n" \
        "-----END CERTIFICATE-------\n"
*/
#define ROOT_CA_CERTIFICATE     ""

/* Client Certificate.
   Must include the PEM header and footer:

        "-----BEGIN CERTIFICATE-----\n" \
        ".........base64 data.......\n" \
        "-----END CERTIFICATE-------\n"
*/
#define CLIENT_CERTIFICATE      ""


/* Private Key.
   Must include the PEM header and footer:

        "-----BEGIN RSA PRIVATE KEY-----\n" \
        "...........base64 data.........\n" \
        "-----END RSA PRIVATE KEY-------\n"
*/
#define CLIENT_KEY              ""

/* OTA context. */
static cy_ota_context_ptr ota_context;

/* OTA callback function define. */
cy_ota_callback_results_t ota_callback(cy_ota_cb_struct_t *cb_data);

 /* MQTT Credentials for OTA. */
cy_awsport_ssl_credentials_t    mqtt_credentials;

/* HTTP Credentials for OTA. */
cy_awsport_ssl_credentials_t    http_credentials;

/* network parameters for OTA. */
cy_ota_network_params_t     network_params = { CY_OTA_CONNECTION_UNKNOWN };

/* Parameters for the OTA Agent. */
cy_ota_agent_params_t ota_agent_params =
{
    .cb_func = ota_callback,                /* Set the value to NULL if the callback function is not used. */
    .cb_arg = &ota_context,                 /* Set the value to NULL if the callback function is not used. */
    .reboot_upon_completion = 1             /* Reboot after completing OTA with success. */
};

The example function demonstrates the usage of the OTA callback function to print the status of every OTA event. The callback feature is optional but be aware that the OTA middleware will not print the status of the OTA Agent on its own.

Note: You must initialize retarget-io to use the debug UART port.

/*******************************************************************************
 * Function Name: ota_callback()
 *******************************************************************************
 * Summary:
 *  Got a callback from OTA.
 *
 *  @param[in][out] cb_data - Structure holding the information for the application.
 *
 * Return:
 *  CY_OTA_CB_RSLT_OTA_CONTINUE - OTA Agent to continue with the function, using the modified data from the application.
 *  CY_OTA_CB_RSLT_OTA_STOP     - OTA Agent to end the current update session (do not quit).
 *  CY_OTA_CB_RSLT_APP_SUCCESS  - Application completed task; OTA Agent use success.
 *  CY_OTA_CB_RSLT_APP_FAILED   - Application completed task; OTA Agent use failure.
 *
 *******************************************************************************/
static cy_ota_callback_results_t ota_callback(cy_ota_cb_struct_t *cb_data)
{
    cy_ota_callback_results_t   cb_result = CY_OTA_CB_RSLT_OTA_CONTINUE;    /* OTA Agent to continue as normal. */
    const char                  *state_string;
    const char                  *error_string;
    cy_ota_context_ptr          ctx = NULL;

    if (cb_data == NULL)
    {
        return CY_OTA_CB_RSLT_OTA_STOP;
    }
    ctx = *((cy_ota_context_ptr *)cb_data->cb_arg);
    if (ctx == NULL)
    {
        return CY_OTA_CB_RSLT_OTA_STOP;
    }

    state_string = cy_ota_get_state_string(cb_data->state);
    error_string = cy_ota_get_error_string(cy_ota_get_last_error());
    reason_string = cy_ota_get_callback_reason_string(cb_data->reason);

    switch (cb_data->reason)
    {

    case CY_OTA_LAST_REASON:                /* To keep linker happy. */
        break;

    case CY_OTA_REASON_SUCCESS:
        printf("APP CB OTA SUCCESS state:%d %s last_error:%s\n", cb_data->state, state_string, error_string);
        break;
    case CY_OTA_REASON_FAILURE:
        printf("APP CB OTA FAILURE state:%d %s last_error:%s\n", cb_data->state, state_string, error_string);
        break;
    case CY_OTA_REASON_STATE_CHANGE:

        switch (cb_data->state)
        {
            /* Informational. */
        case CY_OTA_STATE_NOT_INITIALIZED:
        case CY_OTA_STATE_EXITING:
        case CY_OTA_STATE_INITIALIZING:
        case CY_OTA_STATE_AGENT_STARTED:
        case CY_OTA_STATE_AGENT_WAITING:
            printf("APP CB OTA STATE CHANGE state:%d %s last_error:%s\n", cb_data->state, state_string, error_string);
            break;

        case CY_OTA_STATE_START_UPDATE:
            printf("APP CB OTA STATE CHANGE CY_OTA_STATE_START_UPDATE\n");
            break;

        case CY_OTA_STATE_STORAGE_OPEN:
            printf("APP CB OTA STORAGE OPEN\n");
            break;
        case CY_OTA_STATE_STORAGE_WRITE:
            printf("APP CB OTA STORAGE WRITE %ld%% (%ld of %ld)\n", cb_data->percentage, cb_data->bytes_written, cb_data->total_size);
            break;
        case CY_OTA_STATE_STORAGE_CLOSE:
            printf("APP CB OTA STORAGE CLOSE\n");
            break;


        case CY_OTA_STATE_JOB_CONNECT:
            printf("APP CB OTA CONNECT FOR JOB using ");
            /* NOTE:
             *  MQTT - json_doc holds the MQTT JSON request document.
             *  HTTP - json_doc holds the HTTP "GET" request.
             */
            if (cb_data->connection_type == CY_OTA_CONNECTION_MQTT)
            {
                printf("MQTT: server:%s port: %d\n", cb_data->broker_server.pHostName, cb_data->broker_server.port);
            }
            else
            {
                printf("HTTP: server:%s port: %d\n", cb_data->broker_server.pHostName, cb_data->broker_server.port);
            }
            break;
        case CY_OTA_STATE_JOB_DOWNLOAD:
            printf("APP CB OTA JOB DOWNLOAD using ");
            /* NOTE:
             *  MQTT - json_doc holds the MQTT JSON request document.
             *  HTTP - json_doc holds the HTTP "GET" request.
             */
            if (cb_data->connection_type == CY_OTA_CONNECTION_MQTT)
            {
                printf("MQTT: '%s'", cb_data->json_doc);
                printf("                 topic: '%s' \n", cb_data->unique_topic);
            }
            else
            {
                printf("HTTP: '%s'", cb_data->file);
            }
            break;
        case CY_OTA_STATE_JOB_DISCONNECT:
            printf("APP CB OTA JOB DISCONNECT\n");
            break;

        case CY_OTA_STATE_JOB_PARSE:
            printf("APP CB OTA PARSE JOB: '%.*s' \n", strlen(cb_data->json_doc), cb_data->json_doc);
            break;
        case CY_OTA_STATE_JOB_REDIRECT:
            printf("APP CB OTA JOB REDIRECT\n");
            break;

        case CY_OTA_STATE_DATA_CONNECT:
            printf("APP CB OTA CONNECT FOR DATA using ");
            if (cb_data->connection_type == CY_OTA_CONNECTION_MQTT)
            {
                printf("MQTT: %s:%d \n", cb_data->broker_server.pHostName, cb_data->broker_server.port);
            }
            else
            {
                printf("HTTP: %s:%d \n", cb_data->broker_server.pHostName, cb_data->broker_server.port);
            }
            break;
        case CY_OTA_STATE_DATA_DOWNLOAD:
            printf("APP CB OTA DATA DOWNLOAD using ");
            /* NOTE:
             *  MQTT - json_doc holds the MQTT JSON request document.
             *  HTTP - json_doc holds the HTTP "GET" request.
             */
            if (cb_data->connection_type == CY_OTA_CONNECTION_MQTT)
            {
                printf("MQTT: '%s' \n", cb_data->json_doc);
                printf("                       topic: '%s' \n", cb_data->unique_topic);
            }
            else
            {
                printf("HTTP: '%s' \n", cb_data->json_doc);
                printf("                        file: '%s' \n", cb_data->file);
            }
            break;
        case CY_OTA_STATE_DATA_DISCONNECT:
            printf("APP CB OTA DATA DISCONNECT\n");
            break;

        case CY_OTA_STATE_VERIFY:
            printf("APP CB OTA VERIFY\n");
            break;

        case CY_OTA_STATE_RESULT_REDIRECT:
            printf("APP CB OTA RESULT REDIRECT\n");
            break;

        case CY_OTA_STATE_RESULT_CONNECT:
            printf("APP CB OTA SEND RESULT CONNECT using ");
            /* NOTE:
             *  MQTT - json_doc holds the MQTT JSON request document.
             *  HTTP - json_doc holds the HTTP "GET" request.
             */
            if (cb_data->connection_type == CY_OTA_CONNECTION_MQTT)
            {
                printf("MQTT: Broker:%s port: %d\n", cb_data->broker_server.pHostName, cb_data->broker_server.port);
                printf("                                      topic: '%s' \n", cb_data->unique_topic);
            }
            else
            {
                printf("HTTP: Server:%s port: %d\n", cb_data->broker_server.pHostName, cb_data->broker_server.port);
            }
            break;
        case CY_OTA_STATE_RESULT_SEND:
            printf("APP CB OTA SENDING RESULT using ");
            /* NOTE:
             *  MQTT - json_doc holds the MQTT JSON request document.
             *  HTTP - json_doc holds the HTTP "PUT".
             */
            if (cb_data->connection_type == CY_OTA_CONNECTION_MQTT)
            {
                printf("MQTT: '%s' \n", cb_data->json_doc);
            }
            else
            {
                printf("HTTP: '%s' \n", cb_data->json_doc);
            }
            break;
        case CY_OTA_STATE_RESULT_RESPONSE:
            printf("APP CB OTA Got Result response\n");
            break;

        case CY_OTA_STATE_RESULT_DISCONNECT:
            printf("APP CB OTA Result Disconnect\n");
            break;

        case CY_OTA_STATE_OTA_COMPLETE:
            printf("APP CB OTA Session Complete\n");
            break;

        case CY_OTA_NUM_STATES: /* To keep compiler happy. */
            break;

        }   /* Switch state. */
        break;


    }

    return cb_result;
}

The following code snippet demonstrates the initialization of the OTA Agent.

/* Initialize and start the OTA Agent.
 *
 * The main application must:
 * - Turn off the Watchdog Timer (if being used)
 *          cyhal_wdt_t wdt_obj;
 *          cyhal_wdt_init(&wdt_obj, cyhal_wdt_get_max_timeout_ms());
 *          cyhal_wdt_free(&wdt_obj);
 * - Validate the application (if the update just happened)
 *          cy_ota_storage_validated();
 * - Initialize Wi-Fi.
 * - Connect to the Wi-Fi AP.
 * -
 * */

cy_rslt_t ota_setup(void)
{
    cy_rslt_t   result;

    /*****************************************************************************
    < Add code snippet here to initialize and connect to a Wi-Fi AP >
    ******************************************************************************/

    /* Initialize the underlying support code that is needed for OTA and MQTT. */
    if (cy_awsport_network_init() != CY_RSLT_SUCCESS)
    {
        printf("cy_awsport_network_init Failed.\n");
        while(1)
        {
            cy_rtos_delay_milliseconds(10);
        }
    }

    /* Initialize the MQTT subsystem. */
     if (cy_mqtt_init() != CY_RSLT_SUCCESS )
    {
        printf("cy_mqtt_init() Failed.\n");
        while(1)
        {
            cy_rtos_delay_milliseconds(10);
        }
    }

     /* Set up parameters for starting the OTA Agent. */
     memset(&network_params, 0, sizeof(network_params));
     memset(&agent_params,   0, sizeof(agent_params));

     /* Common network parameters. */
     /* Server parameters. */
     network_params.initial_connection = ota->connection_type;

     /* Set all network parameters for both MQTT & HTTP in case of switching
      * from Job Broker/server to data Broker/server.
      */
     /* MQTT Connection values. */
     network_params.mqtt.broker.host_name = MQTT_BROKER;
     network_params.mqtt.broker.port = MQTT_BROKER_PORT;

     network_params.use_get_job_flow     = true;                    /* False for Direct flow. */
     network_params.mqtt.numTopicFilters = MQTT_TOPIC_FILTER_NUM;
     network_params.mqtt.pTopicFilters   = mqtt_topics;
     network_params.mqtt.pIdentifier     = "MQTTClientUniqueIdentifier";    /* Create a unique identifier. */
     network_params.mqtt.session_type    = CY_OTA_MQTT_SESSION_CLEAN;

     /* HTTP connection values. */
     network_params.http.server.host_name = HTTP_SERVER;      /* Must not be a local variable. */
     network_params.http.server.port = HTTP_SERVER_PORT;

     /* For HTTP, change the file with the GET when using a Job flow. */
     network_params.use_get_job_flow = ota->update_flow;
     if (network_params.use_get_job_flow == CY_OTA_JOB_FLOW)
     {
         /* For HTTP server to get the "Job" file. */
         network_params.http.file = OTA_HTTP_JOB_FILE;
     }
     else
     {
         /* For HTTP server to get the "data" file directly. */
         network_params.http.file = OTA_HTTP_DATA_FILE;
     }

     /* Set up MQTT credentials - only used if start_TLS is set. */
     memset(&network_params.mqtt.credentials, 0x00, sizeof(network_params.mqtt.credentials ));

     if (service is AMAZON, for testing we need to set the username )
     {
         /* Only set this for Amazon testing. */
         mqtt_credentials.username      = "Test";
         mqtt_credentials.username_size = strlen(mqtt_credentials.username);
         mqtt_credentials.password      = "";
         mqtt_credentials.password_size = strlen(mqtt_credentials.password);
     }
     mqtt_credentials.alpnprotos         = NULL;
     mqtt_credentials.alpnprotoslen      = 0;
     mqtt_credentials.sni_host_name      = NULL;
     mqtt_credentials.sni_host_name_size = 0;
     mqtt_credentials.root_ca            = mqtt_root_ca_certificate_table[ota->mqtt_certificates];
     mqtt_credentials.root_ca_size       = strlen(mqtt_root_ca_certificate_table[ota->mqtt_certificates]) + 1;
     mqtt_credentials.client_cert        = mqtt_client_cert_table[ota->mqtt_certificates];
     mqtt_credentials.client_cert_size   = strlen(mqtt_client_cert_table[ota->mqtt_certificates]) + 1;
     mqtt_credentials.private_key        = mqtt_client_key_table[ota->mqtt_certificates];
     mqtt_credentials.private_key_size   = strlen(mqtt_client_key_table[ota->mqtt_certificates]) + 1;
     if (ota->start_TLS)
     {
         network_params.mqtt.credentials = mqtt_credentials;
     }

     memset(&network_params.http.credentials, 0x00, sizeof(network_params.http.credentials ));

     /* Set up HTTP credentials - only used if start_TLS is set. */

     /* Only if the HTTP server needs this: */
 //    http_credentials.password         = "";
 //    http_credentials.username_size      = strlen(http_credentials.password);
 //    http_credentials.password         = "";
 //    http_credentials.password_size      = strlen(http_credentials.password);
     http_credentials.alpnprotos         = NULL;
     http_credentials.alpnprotoslen      = 0;
     http_credentials.sni_host_name      = NULL;
     http_credentials.sni_host_name_size = 0;
     http_credentials.root_ca            = (const char *)root_ca_certificate_https;
     http_credentials.root_ca_size       = strlen(root_ca_certificate_https) + 1;
     http_credentials.client_cert        = (const char *)client_cert_https;
     http_credentials.client_cert_size   = strlen(client_cert_https) + 1;
     http_credentials.private_key        = (const char *)client_key_https;
     http_credentials.private_key_size   = strlen(client_key_https) + 1;
     if (ota->start_TLS)
     {
         network_params.http.credentials = http_credentials;
     }

     /* OTA Agent parameters. */
     agent_params.validate_after_reboot  = 0;        /* Validate after download so that you don't have to call
                                                      *          cy_ota_validated() on reboot.               */
     agent_params.reboot_upon_completion = 1;        /* 1 = Reboot when download is finished.                */
     agent_params.do_not_send_result     = 0;        /* 1 = Do not send the result info to the Broker/server.        */
     agent_params.cb_func                = ota_callback;
     agent_params.cb_arg                 = ota;

    /* Initialize and start the OTA Agent. */
    result = cy_ota_agent_start(&network_params, &agent_params, &ota_context);

    return cy_rslt_t;
}

Code Example

For AnyCloud OTA v1.2.0 code example, see this example:https://github.com/cypresssemiconductorco/mtb-example-anycloud-ota-mqtt