Skip to content

Commit 29d8fbe

Browse files
committed
Merge branch 'feat/add_openthread_start_stop_api' into 'master'
feat(openthread): add openthread start stop APIs See merge request espressif/esp-idf!40349
2 parents f514bd5 + 4876f12 commit 29d8fbe

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

54 files changed

+813
-818
lines changed

components/openthread/Kconfig

Lines changed: 31 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,28 @@ menu "OpenThread"
66
help
77
Select this option to enable OpenThread and show the submenu with OpenThread configuration choices.
88

9+
menu "Thread Task Parameters"
10+
depends on OPENTHREAD_ENABLED
11+
12+
config OPENTHREAD_TASK_NAME
13+
string "OpenThread task name"
14+
default "ot_main"
15+
help
16+
The OpenThread task name.
17+
18+
config OPENTHREAD_TASK_SIZE
19+
int "Size of OpenThread task"
20+
default 8192
21+
help
22+
The size in bytes of OpenThread task.
23+
24+
config OPENTHREAD_TASK_PRIORITY
25+
int "Priority of OpenThread task"
26+
default 5
27+
help
28+
The priority of OpenThread task.
29+
endmenu
30+
931
menu "Thread Version Message"
1032
depends on OPENTHREAD_ENABLED
1133

@@ -23,10 +45,18 @@ menu "OpenThread"
2345
endmenu
2446

2547
menu "Thread Console"
26-
depends on OPENTHREAD_ENABLED
48+
config OPENTHREAD_CONSOLE_ENABLE
49+
bool "Enable OpenThread console"
50+
depends on OPENTHREAD_ENABLED
51+
default y
52+
help
53+
Enable the OpenThread-specific console provided by the SDK. This only controls whether
54+
the SDK sets up a dedicated console for OpenThread. Even if disabled, the default
55+
ESP-IDF console (if initialized elsewhere) can still be used independently.
2756

2857
choice OPENTHREAD_CONSOLE_TYPE
2958
prompt "OpenThread console type"
59+
depends on OPENTHREAD_CONSOLE_ENABLE
3060
default OPENTHREAD_CONSOLE_TYPE_UART
3161
help
3262
Select OpenThread console type

components/openthread/include/esp_openthread.h

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
#pragma once
88

99
#include "esp_err.h"
10+
#include "esp_netif.h"
1011
#include "esp_openthread_types.h"
1112
#include "openthread/dataset.h"
1213
#include "openthread/error.h"
@@ -89,6 +90,29 @@ otInstance *esp_openthread_get_instance(void);
8990
*/
9091
esp_err_t esp_openthread_mainloop_exit(void);
9192

93+
/**
94+
* @brief Starts the full OpenThread stack and create a handle task.
95+
*
96+
* @note The OpenThread instance will also be initialized in this function.
97+
*
98+
* @param[in] config The OpenThread platform configuration.
99+
*
100+
* @return
101+
* - ESP_OK on success
102+
* - ESP_ERR_INVALID_STATE if already initialized
103+
*
104+
*/
105+
esp_err_t esp_openthread_start(esp_openthread_platform_config_t *config);
106+
107+
/**
108+
* @brief This function performs OpenThread stack and platform driver deinitialization and delete the handle task.
109+
* @return
110+
* - ESP_OK on success
111+
* - ESP_ERR_INVALID_STATE if Thread is already active
112+
*
113+
*/
114+
esp_err_t esp_openthread_stop(void);
115+
92116
#ifdef __cplusplus
93117
} // end of extern "C"
94118
#endif

components/openthread/private_include/esp_openthread_ncp.h

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,11 @@
11
/*
2-
* SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD
2+
* SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD
33
*
44
* SPDX-License-Identifier: Apache-2.0
55
*/
66

77
#include <spinel.h>
8+
#include <esp_openthread.h>
89

910
#if CONFIG_OPENTHREAD_NCP_VENDOR_HOOK
1011

@@ -15,3 +16,13 @@
1516
#define SPINEL_PROP_VENDOR_ESP_COEX_EVENT (SPINEL_PROP_VENDOR_ESP__BEGIN + 3)
1617

1718
#endif
19+
20+
#ifdef __cplusplus
21+
extern "C" {
22+
#endif
23+
24+
void otAppNcpInit(otInstance *aInstance);
25+
26+
#ifdef __cplusplus
27+
}
28+
#endif

components/openthread/private_include/esp_openthread_platform.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* SPDX-FileCopyrightText: 2021-2024 Espressif Systems (Shanghai) CO LTD
2+
* SPDX-FileCopyrightText: 2021-2025 Espressif Systems (Shanghai) CO LTD
33
*
44
* SPDX-License-Identifier: Apache-2.0
55
*/

components/openthread/src/esp_openthread.cpp

Lines changed: 87 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,12 +4,17 @@
44
* SPDX-License-Identifier: Apache-2.0
55
*/
66

7+
#include "sdkconfig.h"
78
#include "esp_openthread.h"
89
#include "esp_check.h"
10+
#include "esp_heap_caps.h"
911
#include "esp_openthread_border_router.h"
1012
#include "esp_openthread_common_macro.h"
13+
#include "esp_openthread_cli.h"
1114
#include "esp_openthread_dns64.h"
1215
#include "esp_openthread_lock.h"
16+
#include "esp_openthread_ncp.h"
17+
#include "esp_openthread_netif_glue.h"
1318
#include "esp_openthread_platform.h"
1419
#include "esp_openthread_sleep.h"
1520
#include "esp_openthread_state.h"
@@ -18,15 +23,19 @@
1823
#include "freertos/FreeRTOS.h"
1924
#include "lwip/dns.h"
2025
#include "openthread/instance.h"
26+
#include "openthread/logging.h"
2127
#include "openthread/netdata.h"
2228
#include "openthread/tasklet.h"
2329
#include "openthread/thread.h"
30+
#include <cstddef>
2431

2532
#if CONFIG_OPENTHREAD_FTD
2633
#include "openthread/dataset_ftd.h"
2734
#endif
2835

2936
static bool s_ot_mainloop_running = false;
37+
static SemaphoreHandle_t s_ot_syn_semaphore = NULL;
38+
static TaskHandle_t s_ot_task_handle = NULL;
3039

3140
static int hex_digit_to_int(char hex)
3241
{
@@ -223,3 +232,81 @@ esp_err_t esp_openthread_deinit(void)
223232
otInstanceFinalize(esp_openthread_get_instance());
224233
return esp_openthread_platform_deinit();
225234
}
235+
236+
static void ot_task_worker(void *aContext)
237+
{
238+
esp_openthread_platform_config_t* config = (esp_openthread_platform_config_t *)aContext;
239+
// Initialize the OpenThread stack
240+
ESP_ERROR_CHECK(esp_openthread_init(config));
241+
242+
#if CONFIG_OPENTHREAD_FTD || CONFIG_OPENTHREAD_MTD
243+
esp_netif_config_t cfg = ESP_NETIF_DEFAULT_OPENTHREAD();
244+
esp_netif_t *openthread_netif = esp_netif_new(&cfg);
245+
assert(openthread_netif != NULL);
246+
ESP_ERROR_CHECK(esp_netif_attach(openthread_netif, esp_openthread_netif_glue_init(config)));
247+
#endif
248+
249+
#if CONFIG_OPENTHREAD_LOG_LEVEL_DYNAMIC
250+
// The OpenThread log level directly matches ESP log level
251+
(void)otLoggingSetLevel(CONFIG_LOG_DEFAULT_LEVEL);
252+
#endif // CONFIG_OPENTHREAD_LOG_LEVEL_DYNAMIC
253+
254+
#if CONFIG_OPENTHREAD_CLI
255+
esp_openthread_cli_init();
256+
esp_openthread_cli_console_command_register();
257+
#endif // CONFIG_OPENTHREAD_CLI
258+
259+
xSemaphoreGive(s_ot_syn_semaphore);
260+
#if CONFIG_OPENTHREAD_RADIO
261+
otAppNcpInit(esp_openthread_get_instance());
262+
#endif
263+
264+
// Run the main loop
265+
esp_openthread_launch_mainloop();
266+
267+
#if CONFIG_OPENTHREAD_RADIO
268+
ESP_LOGE(OT_PLAT_LOG_TAG, "RCP deinitialization is not supported for now");
269+
assert(false);
270+
#endif
271+
#if CONFIG_OPENTHREAD_CLI
272+
esp_openthread_cli_console_command_unregister();
273+
#endif // CONFIG_OPENTHREAD_CLI
274+
275+
#if CONFIG_OPENTHREAD_FTD || CONFIG_OPENTHREAD_MTD
276+
// Clean up
277+
esp_openthread_netif_glue_deinit();
278+
esp_netif_destroy(openthread_netif);
279+
#endif
280+
281+
ESP_ERROR_CHECK(esp_openthread_deinit());
282+
283+
xSemaphoreGive(s_ot_syn_semaphore);
284+
vTaskDelay(portMAX_DELAY);
285+
}
286+
287+
esp_err_t esp_openthread_start(esp_openthread_platform_config_t *config)
288+
{
289+
ESP_RETURN_ON_FALSE(s_ot_syn_semaphore == NULL, ESP_ERR_INVALID_STATE, OT_PLAT_LOG_TAG, "OpenThread has been initialized");
290+
s_ot_syn_semaphore = xSemaphoreCreateBinary();
291+
ESP_RETURN_ON_FALSE(s_ot_syn_semaphore != NULL, ESP_ERR_INVALID_STATE, OT_PLAT_LOG_TAG, "Failed to create s_ot_syn_semaphore");
292+
assert(xTaskCreate(ot_task_worker, CONFIG_OPENTHREAD_TASK_NAME, CONFIG_OPENTHREAD_TASK_SIZE, config, CONFIG_OPENTHREAD_TASK_PRIORITY, &s_ot_task_handle) == pdPASS);
293+
xSemaphoreTake(s_ot_syn_semaphore, portMAX_DELAY);
294+
return ESP_OK;
295+
}
296+
297+
esp_err_t esp_openthread_stop(void)
298+
{
299+
ESP_RETURN_ON_FALSE(s_ot_syn_semaphore != NULL, ESP_ERR_INVALID_STATE, OT_PLAT_LOG_TAG, "OpenThread is not initialized");
300+
esp_openthread_lock_acquire(portMAX_DELAY);
301+
otInstance *instance = esp_openthread_get_instance();
302+
bool is_thread_not_active = (otThreadGetDeviceRole(instance) == OT_DEVICE_ROLE_DISABLED && otIp6IsEnabled(instance) == false);
303+
esp_openthread_lock_release();
304+
ESP_RETURN_ON_FALSE(is_thread_not_active, ESP_ERR_INVALID_STATE, OT_PLAT_LOG_TAG, "Thread interface is still active");
305+
esp_openthread_mainloop_exit();
306+
xSemaphoreTake(s_ot_syn_semaphore, portMAX_DELAY);
307+
vTaskDelete(s_ot_task_handle);
308+
vSemaphoreDelete(s_ot_syn_semaphore);
309+
s_ot_task_handle = NULL;
310+
s_ot_syn_semaphore = NULL;
311+
return ESP_OK;
312+
}

examples/openthread/ot_br/README.md

Lines changed: 17 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -56,11 +56,11 @@ In order to run the example on single SoC which supports both Wi-Fi and Thread,
5656
Two ways are provided to setup the Thread Border Router in this example:
5757

5858
- Auto Start
59-
Enable `OPENTHREAD_BR_AUTO_START`, configure the `CONFIG_EXAMPLE_WIFI_SSID` and `CONFIG_EXAMPLE_WIFI_PASSWORD` with your access point's ssid and psk.
59+
Enable `OPENTHREAD_NETWORK_AUTO_START`, configure the `CONFIG_EXAMPLE_WIFI_SSID` and `CONFIG_EXAMPLE_WIFI_PASSWORD` with your access point's ssid and psk.
6060
The device will connect to Wi-Fi and form a Thread network automatically after boot up.
6161

6262
- Manual mode
63-
Disable `OPENTHREAD_BR_AUTO_START` and enable `OPENTHREAD_CLI_ESP_EXTENSION`. `wifi` command will be added for connecting the device to the Wi-Fi network.
63+
Disable `OPENTHREAD_NETWORK_AUTO_START` and enable `OPENTHREAD_CLI_ESP_EXTENSION`. `wifi` command will be added for connecting the device to the Wi-Fi network.
6464

6565
If the `CONFIG_EXAMPLE_CONNECT_ETHERNET` option is enabled, the device will connect to `Ethernet`, form a Thread network and act as a Ethernet based Thread Border Router.
6666

@@ -71,14 +71,14 @@ Build the project and flash it to the board, then run monitor tool to view seria
7171
```
7272
idf.py -p PORT build flash monitor
7373
```
74-
If the `OPENTHREAD_BR_AUTO_START` option is enabled, The device will be connected to the configured Wi-Fi and Thread network automatically then act as the border router.
74+
If the `OPENTHREAD_NETWORK_AUTO_START` option is enabled, The device will be connected to the configured Wi-Fi and Thread network automatically then act as the border router.
7575

7676
Otherwise, you need to manually configure the networks with CLI commands.
7777

7878
`wifi` command can be used to configure the Wi-Fi network.
7979

8080
```bash
81-
> wifi
81+
esp32s3> ot wifi
8282
--wifi parameter---
8383
connect
8484
-s : wifi ssid
@@ -96,7 +96,7 @@ Done
9696
To join a Wi-Fi network, please use the `wifi connect` command:
9797

9898
```bash
99-
> wifi connect -s threadcertAP -p threadcertAP
99+
esp32s3> ot wifi connect -s threadcertAP -p threadcertAP
100100
ssid: threadcertAP
101101
psk: threadcertAP
102102
I (11331) wifi:wifi driver task: 3ffd06e4, prio:23, stack:6656, core=0
@@ -117,7 +117,7 @@ Done
117117
To get the state of the Wi-Fi network:
118118

119119
```bash
120-
> wifi state
120+
esp32s3> ot wifi state
121121
connected
122122
Done
123123
```
@@ -165,7 +165,7 @@ For mobile devices, the route table rules will be automatically configured after
165165
Now in the Thread end device, check the IP addresses:
166166

167167
```
168-
> ipaddr
168+
esp32h2> ot ipaddr
169169
fde6:75ff:def4:3bc3:9e9e:3ef:4245:28b5
170170
fdde:ad00:beef:0:0:ff:fe00:c402
171171
fdde:ad00:beef:0:ad4a:9a9a:3cd6:e423
@@ -192,13 +192,13 @@ The newly introduced service registration protocol([SRP](https://datatracker.iet
192192
Now we'll publish the service `my-service._test._udp` with hostname `test0` and port 12345
193193

194194
```
195-
> srp client host name test0
195+
esp32h2> ot srp client host name test0
196196
Done
197-
> srp client host address fde6:75ff:def4:3bc3:9e9e:3ef:4245:28b5
197+
esp32h2> ot srp client host address fde6:75ff:def4:3bc3:9e9e:3ef:4245:28b5
198198
Done
199-
> srp client service add my-service _test._udp 12345
199+
esp32h2> ot srp client service add my-service _test._udp 12345
200200
Done
201-
> srp client autostart enable
201+
esp32h2> ot srp client autostart enable
202202
Done
203203
```
204204

@@ -233,7 +233,7 @@ Then get the border router's OMR prefix global unicast address(or ML-EID), and c
233233

234234
On the border router:
235235
```
236-
> ipaddr
236+
esp32s3> ot ipaddr
237237
fdde:ad00:beef:0:0:ff:fe00:fc10
238238
fd9b:347f:93f7:1:1003:8f00:bcc1:3038
239239
fdde:ad00:beef:0:0:ff:fe00:fc00
@@ -245,19 +245,19 @@ Done
245245

246246
On the Thread end device:
247247
```
248-
> dns config fd9b:347f:93f7:1:1003:8f00:bcc1:3038
248+
esp32h2> ot dns config fd9b:347f:93f7:1:1003:8f00:bcc1:3038
249249
(or
250-
> dns config fdde:ad00:beef:0:f891:287:866:776)
250+
esp32h2> ot dns config fdde:ad00:beef:0:f891:287:866:776)
251251
Done
252252
```
253253

254254
Now the service published on the Host can be discovered on the Thread end device.
255255
```
256-
> dns resolve FA001208.default.service.arpa.
256+
esp32h2> ot dns resolve FA001208.default.service.arpa.
257257
DNS response for FA001208.default.service.arpa. - fdde:ad00:beef:cafe:b939:26be:7516:b87e TTL:120
258258
Done
259259
260-
> dns browse _test._udp.default.service.arpa.
260+
esp32h2> ot dns browse _test._udp.default.service.arpa.
261261
DNS browse response for _test._udp.default.service.arpa.
262262
testhost
263263
Port:5683, Priority:0, Weight:0, TTL:120
@@ -266,7 +266,7 @@ testhost
266266
TXT:[test=31, dn=616162626262] TTL:120
267267
Done
268268
269-
> dns service testhost _test._udp.default.service.arpa.
269+
esp32h2> ot dns service testhost _test._udp.default.service.arpa.
270270
DNS service resolution response for testhost for service _test._udp.default.service.arpa.
271271
Port:5683, Priority:0, Weight:0, TTL:120
272272
Host:FA001208.default.service.arpa.

0 commit comments

Comments
 (0)