-
Notifications
You must be signed in to change notification settings - Fork 23
samples: siwx917_ota: http/s OTAF application #111
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Conversation
466273e
to
6a581ad
Compare
cmake_minimum_required(VERSION 3.20.0) | ||
|
||
find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE}) | ||
project(siwx917_tcp_client) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OTA already mean Over The Air, so we don't need to specify https. I suggest to rename this sample in siwx91x_ota
.
Align the name of the sample with the name of the project.
zephyr_code_relocate(FILES ${WISECONNECT_DIR}/components/device/silabs/si91x/wireless/ahb_interface/inc/sli_siwx917_soc.h LOCATION RAM) | ||
zephyr_code_relocate(FILES ${WISECONNECT_DIR}/components/sli_si91x_wifi_event_handler/src/sli_si91x_wifi_event_handler.c LOCATION RAM) | ||
zephyr_code_relocate(FILES ${WISECONNECT_DIR}/components/sli_wifi_command_engine/src/sli_wifi_command_engine.c LOCATION RAM) | ||
zephyr_code_relocate(FILES ${SERVICE_DIR}/sleeptimer/src/sl_sleeptimer.c LOCATION RAM) No newline at end of file |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Wow, this is very unexpected. Can you explain why it's required? I assume the iea is to relocate in memory all the code reached by the ISR? In this case, these relocations are not sufficient.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Keeping this frequently used files in RAM to improve the performance. We can keep this in flash, but the performance will be low
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What performance degradation do you get? If this kind of hack is required to get sane performance, we have raise the issue and address it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
When we relocated the code to RAM for TCP transmit throughput analysis, we observed an improvement of approximately 0.5 Mbps in throughput.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I assume we can consider it is still sane.
Overview | ||
******** | ||
|
||
Application demonstrates how to perform HTTP/HTTPS OTA firmware updates on the SiWx917 platform using Zephyr RTOS. It connects to a Wi-Fi network, establishes a secure HTTPS connection using a CA certificate, and downloads firmware updates from a remote server. The application showcases secure connectivity and OTA update mechanisms for IoT devices. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Warp you line at 80 columns.
************ | ||
|
||
* SiWx917 development board with Wi-Fi support. | ||
* Windows PC to run HTTP server python script. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Which python script? It does not work with standard file sharing?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This application is verified with HTTP server python script
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is not clear. Can this application run with another http server? If no, why? If yes, why do we require a specific server?
* For non-secure updates (SECURED_IMAGE_UPDATE=0), the possible values to set HTTP_URL are: | ||
* M4_RPS_FILE - M4 image file | ||
* TA_RPS_FILE - TA image file | ||
* COMBINED_RPS_FILE - Combined image file |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think you can replace app_config.h
by Kconfig.
int ret; | ||
|
||
ret = setup_socket(family, server, port, sock, addr, addr_len); | ||
if (ret < 0 || *sock < 0) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You will simplify your code if you adopt a more Posix way to design setup_socket()
. I suggest to return the socket file descriptor (>= 0) on success and -errno
on error.
Ditto for http_connect_socket()
.
BTW, does it make sense to have setup_socket()
and http_connect_socket()
. Shouldn't we merge them?
printf("\r\nWLAN_SCAN_STATE\r\n"); | ||
struct wifi_scan_params params = { 0 }; | ||
params.dwell_time_active = 99; | ||
if (net_mgmt(NET_REQUEST_WIFI_SCAN, iface, ¶ms, sizeof(params))) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Avoid large blocks of code inside switch .. case
.
}break; | ||
} | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I have no clue of what you are doing in this function. I believe the way to manage the state machine is wrong. I believe you can get rid of the states and make the nominal case clearer:
void app_try_ota()
{
ret = wait_for_network();
if (ret)
return;
http_connect_socket();
ret = wait_for_server();
if (ret)
return;
while (end < ota_image_size - 1) {
ret = handle_http_packet(msg_c.buffer, msg_c.length);
if (ret)
return;
}
sl_si91x_soc_nvic_reset();
}
int main()
{
...
while (1) {
// app_try_ota() does not return in case of success
app_try_ota();
}
}
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Using a state machine approach can be effective for managing error conditions. If an error occurs in a particular state, we can handle by transitioning back to the appropriate state.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For now this code is unmaintainable. Unless you know what you are doing, I suggest to change this design.
However, of course, if you are able to present this code properly, I am fine to approve it.
} break; | ||
} | ||
return status; | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same comment here. Rewrite this function.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Using a state machine approach can be effective for managing error conditions. If an error occurs in a particular state, we can handle by transitioning back to the appropriate state.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ditto
#endif | ||
uint32_t status = 0; | ||
uint8_t otaf_header_size = 0; | ||
switch(otaf_state) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Add a blank line between variable declarations and the first statement.
zephyr_code_relocate(FILES ${WISECONNECT_DIR}/components/device/silabs/si91x/wireless/ahb_interface/inc/sli_siwx917_soc.h LOCATION RAM) | ||
zephyr_code_relocate(FILES ${WISECONNECT_DIR}/components/sli_si91x_wifi_event_handler/src/sli_si91x_wifi_event_handler.c LOCATION RAM) | ||
zephyr_code_relocate(FILES ${WISECONNECT_DIR}/components/sli_wifi_command_engine/src/sli_wifi_command_engine.c LOCATION RAM) | ||
zephyr_code_relocate(FILES ${SERVICE_DIR}/sleeptimer/src/sl_sleeptimer.c LOCATION RAM) No newline at end of file |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What performance degradation do you get? If this kind of hack is required to get sane performance, we have raise the issue and address it.
************ | ||
|
||
* SiWx917 development board with Wi-Fi support. | ||
* Windows PC to run HTTP server python script. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is not clear. Can this application run with another http server? If no, why? If yes, why do we require a specific server?
samples/siwx917_https_otaf/prj.conf
Outdated
# Memory and Threading | ||
CONFIG_MAIN_STACK_SIZE=2048 | ||
CONFIG_INIT_STACKS=y | ||
CONFIG_HEAP_MEM_POOL_SIZE=16384 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Where this allocation happens? If want to increase the space available for malloc()
, this is not the correct option (this option in fact make the memory unavailable for malloc()
). This mem pool is normally used for kernel object allocation. Unless you have specific reason, you should have to change it.
samples/siwx917_https_otaf/prj.conf
Outdated
|
||
# WiFi Configuration | ||
CONFIG_WIFI=y | ||
CONFIG_WIFI_SILABS_SIWX91X_NET_STACK_NATIVE=y |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I believe this the default and you don't need to specify this option.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I believe this option is to differentiate between native or offload stack. The files siwx91x_wifi.c, siwx91x_wifi_ap.c, and siwx91x_wifi_sta.c contain code that conditionally executes based on the CONFIG_WIFI_SILABS_SIWX91X_NET_STACK_NATIVE macro
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Indeed, but CONFIG_WIFI_SILABS_SIWX91X_NET_STACK_NATIVE
set by default if you enable Wifi. You don't need to specify it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ok
dhcpv6_params.request_addr = true; | ||
dhcpv6_params.request_prefix = false; | ||
printf("\r\ndhcpv6 start\r\n"); | ||
net_dhcpv6_start(iface, &dhcpv6_params); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think Zephyr support SLAAC for configuration. Then, I don't think you need DHCPv6.
CONFIG_MBEDTLS_ENABLE_HEAP=y | ||
CONFIG_MBEDTLS_HEAP_SIZE=60000 | ||
CONFIG_TLS_CREDENTIALS=y | ||
CONFIG_NET_SOCKETS_SOCKOPT_TLS=y |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I may miss things, but the following config should be very close of what you need ():
CONFIG_NETWORKING=y
CONFIG_WIFI=y
CONFIG_NET_IPV6=y
CONFIG_NET_IPV4=y
CONFIG_NET_DHCPV4=y
CONFIG_NET_TCP=y
CONFIG_NET_SOCKETS=y
CONFIG_NET_SOCKETS_SOCKOPT_TLS=y
CONFIG_HTTP_CLIENT=y
CONFIG_MAIN_STACK_SIZE=2048
You may improve compatibility with TLS servers by adding the snippet below, but I think this is not strictly required.
CONFIG_MBEDTLS_CIPHER_ALL_ENABLED=y
CONFIG_MBEDTLS_POLY1305=y
Also note I suggest to use the zsock_*()
function so you won't depends on CONFIG_POSIX_API
.
#else | ||
#define SSID "<AP-SSID>" | ||
#define PSK "<AP-PASSPHRASE>" | ||
#define HTTP_SERVER_ADDR "<SERVER-ADDR>" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
hmm... indeed, I see your workaround with TLS_HOSTNAME = NULL
. Probably we want to keep that. I suggest to add note explaining this does not for production and how to properly check the FQDN.
Anyway, FQDN will be usual case and we have to accept an hostname instead of an an IP (zsock_getaddrinfo()
also accept raw IP address anyway).
#include "sl_si91x_hal_soc_soft_reset.h" | ||
|
||
/* Event masks */ | ||
#define L4_EVENT_MASK (NET_EVENT_L4_IPV6_CONNECTED) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You can just use:
net_mgmt_init_event_callback(&l4_cb, l4_event_handler, NET_EVENT_L4_IPV6_CONNECTED);
L4_EVENT_MASK
just make the code more difficult to understand.
int end = (CHUNK_SIZE - 1); | ||
int otaf_state = START_IMAGE; | ||
uint16_t http_sts_code = 0; | ||
osMessageQueueId_t http_data_q; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
osMessageQueueId_t
is not a Zephyr native structure. It provided by the CMSIS-RTOS interface to simplify portability of existing applications.
char link_local[NET_IPV6_ADDR_LEN] = {0}; | ||
char ipv6_address[NET_IPV6_ADDR_LEN] = {0}; | ||
static struct net_mgmt_event_callback l4_cb; | ||
#endif |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Avoid global variables.
569c7b4
to
dd7f3de
Compare
Please rebase this on the latest |
Nevermind. Rerunning the workflow was sufficient, since it does a rebase itself. The check is passing now. |
samples/siwx91x_ota/src/app_config.h
Outdated
OTA_STATE_SERVER_CONNECT, /**< Connect to OTA server */ | ||
OTA_STATE_DOWNLOAD, /**< Download firmware image */ | ||
OTA_STATE_PROCESS, /**< Process downloaded firmware */ | ||
}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This symbol doesn't need to be exported. You can move it to main.c
(then app_config.h
will be useless)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ok
samples/siwx91x_ota/src/main.c
Outdated
char resolved_addr_str[(CONFIG_OTA_IP_PROTOCOL_SELECTION == 0) ? INET_ADDRSTRLEN | ||
: INET6_ADDRSTRLEN]; | ||
static bool ipv6_addr_config_done; | ||
volatile enum ota_state state = OTA_STATE_INIT; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Avoid global variables. You can probably move them to struct app_ctx
(or even better, change them in local variables).
samples/siwx91x_ota/src/main.c
Outdated
static struct net_mgmt_event_callback l4_cb; | ||
struct app_ctx app_ctx = {.wlan_sem = Z_SEM_INITIALIZER(app_ctx.wlan_sem, 0, 1), | ||
.ota_sem = Z_SEM_INITIALIZER(app_ctx.ota_sem, 0, 1), | ||
.dhcp_sem = Z_SEM_INITIALIZER(app_ctx.dhcp_sem, 0, 1)}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Add new lines after opening brace and before closing braces:
struct app_ctx app_ctx = {
.wlan_sem = Z_SEM_INITIALIZER(app_ctx.wlan_sem, 0, 1),
.ota_sem = Z_SEM_INITIALIZER(app_ctx.ota_sem, 0, 1),
.dhcp_sem = Z_SEM_INITIALIZER(app_ctx.dhcp_sem, 0, 1)
};
samples/siwx91x_ota/src/main.c
Outdated
|
||
iface = net_if_get_first_wifi(); | ||
net_mgmt_init_event_callback(&app_ctx.wlan_mgmt_cb, wifi_mgmt_event_handler, | ||
(WIFI_SHELL_MGMT_EVENTS_COMMON)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Parentheses around WIFI_SHELL_MGMT_EVENTS_COMMON
are probably useless.
samples/siwx91x_ota/src/main.c
Outdated
|
||
case OTA_STATE_IP_CONFIG: | ||
ret = configure_ip(app_ctx_st); | ||
state = (ret == 0) ? OTA_STATE_SERVER_CONNECT : OTA_STATE_IP_CONFIG; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ditto.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am not updating the next state in the dhcp callback.
samples/siwx91x_ota/src/main.c
Outdated
int firmware_status = 0; | ||
char *ssid = CONFIG_OTA_WIFI_SSID; | ||
char *pwd = CONFIG_OTA_WIFI_PSK; | ||
sl_wifi_firmware_version_t version = {0}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
sl_wifi_firmware_version_t version = { };
is sufficient.
samples/siwx91x_ota/src/main.c
Outdated
} else { | ||
printf("Failed to get firmware version: 0x%x\n", ret); | ||
} | ||
state = OTA_STATE_SCAN; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This state is only used one. You can simplify your FSM by placing this code outside of the loop. (BTW, since version
is only used for this part, I suggest to create a function for that task).
break; | ||
case NET_EVENT_WIFI_DISCONNECT_RESULT: | ||
handle_wifi_disconnect_result(cb); | ||
break; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If I understand right, the purpose of these callbacks are only to provide info to the user. In this case, why do they need semaphore? Globally, since the call back only change the state, I am not sure any the semaphore are useful (we only have to ensure state
is accessed atomically).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Timeout for receiving the response is implemented using semaphore. If we didn't receive the callback within timeout, status setting as error and retrying.
samples/siwx91x_ota/src/main.c
Outdated
} | ||
/* Purge any remaining messages */ | ||
k_msgq_purge(&http_data_q); | ||
return; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Give an opportunity to the FSM to be useful. Catch the error and repair it. (ditto for wifi disconnection)
32f6693
to
053214b
Compare
samples/siwx91x_ota/src/main.c
Outdated
char *full_url = CONFIG_OTA_UPDATE_URL; | ||
size_t data_len; | ||
|
||
memset(&parser, 0, sizeof(parser)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Redundant with http_parser_url_init()
.
samples/siwx91x_ota/src/main.c
Outdated
int ret = http_parser_parse_url(full_url, strlen(full_url), 0, &parser); | ||
if (ret) { | ||
printf("Failed to parse URL: %s\n", full_url); | ||
return -EINVAL; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Considering:
- this is a fatal error you can't recover
- this is sample (pedagogic) code
You can use __ASSERT()
. Same comment in case host, path or schema is not specified.
BTW, you need to retrieve the schema to know if TLS is enabled or not.
You also need to set a default value for the port if it is not specified.
samples/siwx91x_ota/src/main.c
Outdated
return -errno; | ||
} | ||
|
||
if (IS_ENABLED(CONFIG_OTA_HTTPS_SUPPORT)) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
CONFIG_OTA_HTTPS_SUPPORT
is not required, you can look at the schema of the URL. You may __ASSERT(IS_ENABLED(CONFIG_NET_SOCKETS_SOCKOPT_TLS), "Application was built without support for TLS");
.
samples/siwx91x_ota/src/main.c
Outdated
addr_ptr = &((struct sockaddr_in6 *)res->ai_addr)->sin6_addr; | ||
} | ||
zsock_inet_ntop(res->ai_family, addr_ptr, addr_str, sizeof(addr_str)); | ||
printf("Connected to %s:%s\n", addr_str, http_parse_data_st.port); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just print http_parse_data_st.host
. So you won't have to do the conversion above.
samples/siwx91x_ota/src/main.c
Outdated
struct dns_resolve_context *dnsctx; | ||
|
||
dnsctx = dns_resolve_get_default(); | ||
ret = dns_resolve_reconfigure(dnsctx, dns_servers, NULL, DNS_SOURCE_MANUAL); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In Ipv6 DNS is provided by RDNS field of the Router Advertisements. You don't have to manage manually.
You have to add the symbol CONFIG_NET_IPV6_RA_RDNSS
in prj.conf
.
The user may enable CONFIG_DNS_SERVER_IP_ADDRESSES=y
if his network does not support RDNS.
samples/siwx91x_ota/src/main.c
Outdated
void *addr_ptr; | ||
struct zsock_addrinfo hints = { | ||
.ai_family = (CONFIG_OTA_IP_PROTOCOL_SELECTION == 0) ? AF_INET : AF_INET6, | ||
.ai_socktype = SOCK_STREAM}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hints is not really required. Zephyr will already automatically selects the right IP version.
samples/siwx91x_ota/src/main.c
Outdated
printf("Failed to set TLS_HOSTNAME option (%d)\n", -errno); | ||
zsock_close(*sock_ptr); | ||
zsock_freeaddrinfo(res); | ||
return -errno; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I suggest to manage the errors of this function using a label and goto
.
BTW, "Connection failed
is definitely something we want to report. But, the others (Failed to create TLS socket
, Failed to set TLS secure option
, etc...) should really not happen. Since it is a pedagogic code, I am not sure it make sense to clutter the code with such debug traces.
.protocol = "HTTP/1.1", | ||
.response = ota_http_response_cb, | ||
.recv_buf = app_ctx_st->http_recv_buf, | ||
.recv_buf_len = sizeof(app_ctx_st->http_recv_buf)}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Prefer this format:
struct http_request req = {
.method = HTTP_GET,
.url = app_ctx_st->http_parse_data_st.path,
.header_fields = headers,
.host = app_ctx_st->http_parse_data_st.host,
.protocol = "HTTP/1.1",
.response = ota_http_response_cb,
.recv_buf = app_ctx_st->http_recv_buf,
.recv_buf_len = sizeof(app_ctx_st->http_recv_buf)
};
{ | ||
int ret = 0; | ||
char range_header[64]; | ||
const char *headers[2] = {range_header, NULL}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Add space after {
and before }
.
0x31, 0xee, 0x2a, 0x3b, 0x7b, 0xf0, 0x2c, 0x9e, 0x6f, 0xe9, 0xc4, 0x07, 0x81, 0x24, 0xda, | ||
0x05, 0x70, 0x4d, 0xdd, 0x09, 0xae, 0x9e, 0x72, 0xb8, 0x21, 0x0e, 0x8c, 0xb2, 0xab, 0xaa, | ||
0x4c, 0x49, 0x10, 0xf7, 0x76, 0xf9, 0xb5, 0x0d, 0x6c, 0x20, 0xd3, 0xdf, 0x7a, 0x06, 0x32, | ||
0x8d, 0x29, 0x1f, 0x28, 0x1d, 0x8d, 0x26, 0x33}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The original code with the conversion was fine. Why did you change it?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
With .pem format, the client is closing the connection after the TCP handshake. I was unable to connect with server. I checked by enabling the CONFIG_MBEDTLS_PEM_CERTIFICATE_FORMAT, but it didn't work
if (final_data && staging_len > 0) { | ||
msg_p.length = staging_len; | ||
memcpy(msg_p.buffer, staging_buf, staging_len); | ||
if (k_msgq_put(&app_ctx_st->http_data_q, &msg_p, K_NO_WAIT)) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am not sure you need this callback. This is only required to process the data on the fly. But in your case, you can wait the request terminate. I believe you just have to process req->recv_buf
/ req->data_len
after the call to http_client_req()
.
BTW, I believe http_data_q
is also useless since we store only one buffer at time and we don't do any new request while the previous one is not finished.
BTW, can you place this function close to download_firmware_chunk()
, so the code is easier to read.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We can't use the http_client_req API without passing callback. If we pass callback as NULL, it gives invalid argument error while executing
b8b78eb
to
9a126e8
Compare
This application demonstrates the support for OTA firmware upgrade. Signed-off-by: Devika Raju <[email protected]>
6025ad2
to
8cc35e9
Compare
Updating the SiWx917 device's firmware including NWP, M4, and the combined M4 + TA images using an HTTP or HTTPS server. It supports both secure and non-secure firmware updates for all three types: NWP, M4, and the combined image.