New function tcpip_callback_wait() * Call a function inside the tcpip thread and block the calling thread until the callback finishes.

Signed-off-by: Simon Goldschmidt <goldsimon@gmx.de>
This commit is contained in:
Joan Lledó 2019-05-19 11:08:45 +02:00 committed by Simon Goldschmidt
parent 3546a0a4a0
commit 9dca4a0211
3 changed files with 56 additions and 1 deletions

View File

@ -166,6 +166,11 @@ tcpip_thread_handle_msg(struct tcpip_msg *msg)
msg->msg.api_call.arg->err = msg->msg.api_call.function(msg->msg.api_call.arg);
sys_sem_signal(msg->msg.api_call.sem);
break;
case TCPIP_MSG_CALLBACK_STATIC_WAIT:
LWIP_DEBUGF(TCPIP_DEBUG, ("tcpip_thread: CALLBACK WAIT message %p\n", (void *)msg));
msg->msg.cb_wait.function(msg->msg.cb_wait.ctx);
sys_sem_signal(msg->msg.cb_wait.sem);
break;
#endif /* !LWIP_TCPIP_CORE_LOCKING */
#if !LWIP_TCPIP_CORE_LOCKING_INPUT
@ -589,6 +594,49 @@ tcpip_callbackmsg_trycallback_fromisr(struct tcpip_callback_msg *msg)
return sys_mbox_trypost_fromisr(&tcpip_mbox, msg);
}
/**
* Sends a message to TCPIP thread to call a function. Caller thread blocks
* until the function returns.
* It is recommended to use LWIP_TCPIP_CORE_LOCKING (preferred) or
* LWIP_NETCONN_SEM_PER_THREAD.
* If not, a semaphore is created and destroyed on every call which is usually
* an expensive/slow operation.
*
* @param function the function to call
* @param ctx parameter passed to f
* @return ERR_OK if the function was called, another err_t if not
*/
err_t
tcpip_callback_wait(tcpip_callback_fn function, void *ctx)
{
#if LWIP_TCPIP_CORE_LOCKING
LOCK_TCPIP_CORE();
function(ctx);
UNLOCK_TCPIP_CORE();
return ERR_OK;
#else /* LWIP_TCPIP_CORE_LOCKING */
err_t err;
sys_sem_t sem;
struct tcpip_msg msg;
LWIP_ASSERT("Invalid mbox", sys_mbox_valid_val(tcpip_mbox));
err = sys_sem_new(&sem, 0);
if (err != ERR_OK) {
return err;
}
msg.type = TCPIP_MSG_CALLBACK_STATIC_WAIT;
msg.msg.cb_wait.function = function;
msg.msg.cb_wait.ctx = ctx;
msg.msg.cb_wait.sem = &sem;
sys_mbox_post(&tcpip_mbox, &msg);
sys_arch_sem_wait(&sem, 0);
sys_sem_free(&sem);
return ERR_OK;
#endif /* LWIP_TCPIP_CORE_LOCKING */
}
/**
* @ingroup lwip_os
* Initialize this module:

View File

@ -123,7 +123,8 @@ enum tcpip_msg_type {
TCPIP_MSG_UNTIMEOUT,
#endif /* LWIP_TCPIP_TIMEOUT && LWIP_TIMERS */
TCPIP_MSG_CALLBACK,
TCPIP_MSG_CALLBACK_STATIC
TCPIP_MSG_CALLBACK_STATIC,
TCPIP_MSG_CALLBACK_STATIC_WAIT
};
struct tcpip_msg {
@ -139,6 +140,11 @@ struct tcpip_msg {
struct tcpip_api_call_data *arg;
sys_sem_t *sem;
} api_call;
struct {
tcpip_callback_fn function;
void *ctx;
sys_sem_t *sem;
} cb_wait;
#endif /* LWIP_TCPIP_CORE_LOCKING */
#if !LWIP_TCPIP_CORE_LOCKING_INPUT
struct {

View File

@ -81,6 +81,7 @@ err_t tcpip_input(struct pbuf *p, struct netif *inp);
err_t tcpip_try_callback(tcpip_callback_fn function, void *ctx);
err_t tcpip_callback(tcpip_callback_fn function, void *ctx);
err_t tcpip_callback_wait(tcpip_callback_fn function, void *ctx);
/** @ingroup lwip_os
* @deprecated use tcpip_try_callback() or tcpip_callback() instead
*/