pico-sdk/src/rp2_common/pico_lwip/lwip_freertos.c
Peter Harper 9227cadf84
add pico_status_led (#2501)
Co-authored-by: graham sanderson <graham.sanderson@raspberrypi.com>
2025-07-28 11:56:15 -05:00

63 lines
1.7 KiB
C

/*
* Copyright (c) 2022 Raspberry Pi (Trading) Ltd.
*
* SPDX-License-Identifier: BSD-3-Clause
*/
#include "pico/async_context.h"
#include "pico/time.h"
#include "lwip/tcpip.h"
#include "lwip/timeouts.h"
#include "FreeRTOS.h"
#include "semphr.h"
#if NO_SYS
#error lwip_freertos_async_context_bindings requires NO_SYS=0
#endif
static async_context_t * volatile lwip_context;
// lwIP tcpip_task cannot be shutdown, so we block it when we are de-initialized.
static SemaphoreHandle_t tcpip_task_blocker;
static void tcpip_init_done(void *param) {
xSemaphoreGive((SemaphoreHandle_t)param);
}
bool lwip_freertos_init(async_context_t *context) {
assert(!lwip_context || lwip_context == context);
static bool done_lwip_init;
if (!done_lwip_init) {
lwip_context = context;
done_lwip_init = true;
SemaphoreHandle_t init_sem = xSemaphoreCreateBinary();
tcpip_task_blocker = xSemaphoreCreateBinary();
tcpip_init(tcpip_init_done, init_sem);
xSemaphoreTake(init_sem, portMAX_DELAY);
vSemaphoreDelete(init_sem);
} else {
xSemaphoreGive(tcpip_task_blocker);
}
return true;
}
static uint32_t clear_lwip_context(__unused void *param) {
lwip_context = NULL;
return 0;
}
void lwip_freertos_deinit(__unused async_context_t *context) {
// clear the lwip context under lock as lwIP may still be running in tcpip_task
async_context_execute_sync(context, clear_lwip_context, NULL);
}
void pico_lwip_custom_lock_tcpip_core(void) {
while (!lwip_context) {
xSemaphoreTake(tcpip_task_blocker, portMAX_DELAY);
}
async_context_acquire_lock_blocking(lwip_context);
}
void pico_lwip_custom_unlock_tcpip_core(void) {
async_context_release_lock(lwip_context);
}