summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorgoldsimon <goldsimon@gmx.de>2012-02-28 12:45:59 +0100
committergoldsimon <goldsimon@gmx.de>2012-02-28 12:45:59 +0100
commit4fca628d36c44f927e9326e43e2408f4d886f258 (patch)
tree9380792993c560a37b91620bd8a3cbb41a2e761e
parent7f81c62bf06c99187e25c01ea88452d3228ac0e9 (diff)
downloadlwip-4fca628d36c44f927e9326e43e2408f4d886f258.tar.gz
Speed up LWIP_TCPIP_CORE_LOCKING by directly calling functions in api_msg.c instead of calling via function pointer.
-rw-r--r--src/api/api_lib.c59
-rw-r--r--src/api/tcpip.c24
-rw-r--r--src/include/lwip/tcpip.h18
3 files changed, 47 insertions, 54 deletions
diff --git a/src/api/api_lib.c b/src/api/api_lib.c
index cbae221..b2670d0 100644
--- a/src/api/api_lib.c
+++ b/src/api/api_lib.c
@@ -72,10 +72,11 @@ netconn_new_with_proto_and_callback(enum netconn_type t, u8_t proto, netconn_cal
conn = netconn_alloc(t, callback);
if (conn != NULL) {
- msg.function = do_newconn;
+ err_t err;
msg.msg.msg.n.proto = proto;
msg.msg.conn = conn;
- if (TCPIP_APIMSG(&msg) != ERR_OK) {
+ TCPIP_APIMSG((&msg), do_newconn, err);
+ if (err != ERR_OK) {
LWIP_ASSERT("freeing conn without freeing pcb", conn->pcb.tcp == NULL);
LWIP_ASSERT("conn has no op_completed", sys_sem_valid(&conn->op_completed));
LWIP_ASSERT("conn has no recvmbox", sys_mbox_valid(&conn->recvmbox));
@@ -141,12 +142,11 @@ netconn_getaddr(struct netconn *conn, ip_addr_t *addr, u16_t *port, u8_t local)
LWIP_ERROR("netconn_getaddr: invalid addr", (addr != NULL), return ERR_ARG;);
LWIP_ERROR("netconn_getaddr: invalid port", (port != NULL), return ERR_ARG;);
- msg.function = do_getaddr;
msg.msg.conn = conn;
msg.msg.msg.ad.ipaddr = ip_2_ipX(addr);
msg.msg.msg.ad.port = port;
msg.msg.msg.ad.local = local;
- err = TCPIP_APIMSG(&msg);
+ TCPIP_APIMSG(&msg, do_getaddr, err);
NETCONN_SET_SAFE_ERR(conn, err);
return err;
@@ -170,11 +170,10 @@ netconn_bind(struct netconn *conn, ip_addr_t *addr, u16_t port)
LWIP_ERROR("netconn_bind: invalid conn", (conn != NULL), return ERR_ARG;);
- msg.function = do_bind;
msg.msg.conn = conn;
msg.msg.msg.bc.ipaddr = addr;
msg.msg.msg.bc.port = port;
- err = TCPIP_APIMSG(&msg);
+ TCPIP_APIMSG(&msg, do_bind, err);
NETCONN_SET_SAFE_ERR(conn, err);
return err;
@@ -196,12 +195,29 @@ netconn_connect(struct netconn *conn, ip_addr_t *addr, u16_t port)
LWIP_ERROR("netconn_connect: invalid conn", (conn != NULL), return ERR_ARG;);
- msg.function = do_connect;
msg.msg.conn = conn;
msg.msg.msg.bc.ipaddr = addr;
msg.msg.msg.bc.port = port;
- /* This is the only function which need to not block tcpip_thread */
- err = tcpip_apimsg(&msg);
+#if LWIP_TCP
+#if (LWIP_UDP || LWIP_RAW)
+ if (NETCONNTYPE_GROUP(conn->type) == NETCONN_TCP)
+#endif /* (LWIP_UDP || LWIP_RAW) */
+ {
+ /* The TCP version waits for the connect to succeed,
+ so always needs to use message passing. */
+ msg.function = do_connect;
+ err = tcpip_apimsg(&msg);
+ }
+#endif /* LWIP_TCP */
+#if (LWIP_UDP || LWIP_RAW) && LWIP_TCP
+ else
+#endif /* (LWIP_UDP || LWIP_RAW) && LWIP_TCP */
+#if (LWIP_UDP || LWIP_RAW)
+ {
+ /* UDP and RAW only set flags, so we can use core-locking. */
+ TCPIP_APIMSG(&msg, do_connect, err);
+ }
+#endif /* (LWIP_UDP || LWIP_RAW) */
NETCONN_SET_SAFE_ERR(conn, err);
return err;
@@ -221,9 +237,8 @@ netconn_disconnect(struct netconn *conn)
LWIP_ERROR("netconn_disconnect: invalid conn", (conn != NULL), return ERR_ARG;);
- msg.function = do_disconnect;
msg.msg.conn = conn;
- err = TCPIP_APIMSG(&msg);
+ TCPIP_APIMSG(&msg, do_disconnect, err);
NETCONN_SET_SAFE_ERR(conn, err);
return err;
@@ -249,12 +264,11 @@ netconn_listen_with_backlog(struct netconn *conn, u8_t backlog)
LWIP_ERROR("netconn_listen: invalid conn", (conn != NULL), return ERR_ARG;);
- msg.function = do_listen;
msg.msg.conn = conn;
#if TCP_LISTEN_BACKLOG
msg.msg.msg.lb.backlog = backlog;
#endif /* TCP_LISTEN_BACKLOG */
- err = TCPIP_APIMSG(&msg);
+ TCPIP_APIMSG(&msg, do_listen, err);
NETCONN_SET_SAFE_ERR(conn, err);
return err;
@@ -313,10 +327,9 @@ netconn_accept(struct netconn *conn, struct netconn **new_conn)
}
#if TCP_LISTEN_BACKLOG
/* Let the stack know that we have accepted the connection. */
- msg.function = do_recv;
msg.msg.conn = conn;
/* don't care for the return value of do_recv */
- TCPIP_APIMSG(&msg);
+ TCPIP_APIMSG(&msg, do_recv, err);
#endif /* TCP_LISTEN_BACKLOG */
*new_conn = newconn;
@@ -380,7 +393,6 @@ netconn_recv_data(struct netconn *conn, void **new_buf)
/* Let the stack know that we have taken the data. */
/* TODO: Speedup: Don't block and wait for the answer here
(to prevent multiple thread-switches). */
- msg.function = do_recv;
msg.msg.conn = conn;
if (buf != NULL) {
msg.msg.msg.r.len = ((struct pbuf *)buf)->tot_len;
@@ -388,7 +400,7 @@ netconn_recv_data(struct netconn *conn, void **new_buf)
msg.msg.msg.r.len = 1;
}
/* don't care for the return value of do_recv */
- TCPIP_APIMSG(&msg);
+ TCPIP_APIMSG(&msg, do_recv, err);
}
/* If we are closed, we indicate that we no longer wish to use the socket */
@@ -520,14 +532,14 @@ netconn_recved(struct netconn *conn, u32_t length)
if ((conn != NULL) && (NETCONNTYPE_GROUP(conn->type) == NETCONN_TCP) &&
(netconn_get_noautorecved(conn))) {
struct api_msg msg;
+ err_t err;
/* Let the stack know that we have taken the data. */
/* TODO: Speedup: Don't block and wait for the answer here
(to prevent multiple thread-switches). */
- msg.function = do_recv;
msg.msg.conn = conn;
msg.msg.msg.r.len = length;
/* don't care for the return value of do_recv */
- TCPIP_APIMSG(&msg);
+ TCPIP_APIMSG(&msg, do_recv, err);
}
#else /* LWIP_TCP */
LWIP_UNUSED_ARG(conn);
@@ -572,10 +584,9 @@ netconn_send(struct netconn *conn, struct netbuf *buf)
LWIP_ERROR("netconn_send: invalid conn", (conn != NULL), return ERR_ARG;);
LWIP_DEBUGF(API_LIB_DEBUG, ("netconn_send: sending %"U16_F" bytes\n", buf->p->tot_len));
- msg.function = do_send;
msg.msg.conn = conn;
msg.msg.msg.b = buf;
- err = TCPIP_APIMSG(&msg);
+ TCPIP_APIMSG(&msg, do_send, err);
NETCONN_SET_SAFE_ERR(conn, err);
return err;
@@ -615,7 +626,6 @@ netconn_write_partly(struct netconn *conn, const void *dataptr, size_t size,
}
/* non-blocking write sends as much */
- msg.function = do_write;
msg.msg.conn = conn;
msg.msg.msg.w.dataptr = dataptr;
msg.msg.msg.w.apiflags = apiflags;
@@ -633,7 +643,7 @@ netconn_write_partly(struct netconn *conn, const void *dataptr, size_t size,
/* For locking the core: this _can_ be delayed on low memory/low send buffer,
but if it is, this is done inside api_msg.c:do_write(), so we can use the
non-blocking version here. */
- err = TCPIP_APIMSG(&msg);
+ TCPIP_APIMSG(&msg, do_write, err);
if ((err == ERR_OK) && (bytes_written != NULL)) {
if (dontblock
#if LWIP_SO_SNDTIMEO
@@ -726,12 +736,11 @@ netconn_join_leave_group(struct netconn *conn,
LWIP_ERROR("netconn_join_leave_group: invalid conn", (conn != NULL), return ERR_ARG;);
- msg.function = do_join_leave_group;
msg.msg.conn = conn;
msg.msg.msg.jl.multiaddr = ip_2_ipX(multiaddr);
msg.msg.msg.jl.netif_addr = ip_2_ipX(netif_addr);
msg.msg.msg.jl.join_or_leave = join_or_leave;
- err = TCPIP_APIMSG(&msg);
+ TCPIP_APIMSG(&msg, do_join_leave_group, err);
NETCONN_SET_SAFE_ERR(conn, err);
return err;
diff --git a/src/api/tcpip.c b/src/api/tcpip.c
index ef6fed5..7c1c9ca 100644
--- a/src/api/tcpip.c
+++ b/src/api/tcpip.c
@@ -326,30 +326,6 @@ tcpip_apimsg(struct api_msg *apimsg)
return ERR_VAL;
}
-#if LWIP_TCPIP_CORE_LOCKING
-/**
- * Call the lower part of a netconn_* function
- * This function has exclusive access to lwIP core code by locking it
- * before the function is called.
- *
- * @param apimsg a struct containing the function to call and its parameters
- * @return ERR_OK (only for compatibility fo tcpip_apimsg())
- */
-err_t
-tcpip_apimsg_lock(struct api_msg *apimsg)
-{
-#ifdef LWIP_DEBUG
- /* catch functions that don't set err */
- apimsg->msg.err = ERR_VAL;
-#endif
-
- LOCK_TCPIP_CORE();
- apimsg->function(&(apimsg->msg));
- UNLOCK_TCPIP_CORE();
- return apimsg->msg.err;
-
-}
-#endif /* LWIP_TCPIP_CORE_LOCKING */
#endif /* LWIP_NETCONN */
#if LWIP_NETIF_API
diff --git a/src/include/lwip/tcpip.h b/src/include/lwip/tcpip.h
index 637476e..d0509f5 100644
--- a/src/include/lwip/tcpip.h
+++ b/src/include/lwip/tcpip.h
@@ -59,14 +59,25 @@ extern "C" {
extern sys_mutex_t lock_tcpip_core;
#define LOCK_TCPIP_CORE() sys_mutex_lock(&lock_tcpip_core)
#define UNLOCK_TCPIP_CORE() sys_mutex_unlock(&lock_tcpip_core)
-#define TCPIP_APIMSG(m) tcpip_apimsg_lock(m)
+#ifdef LWIP_DEBUG
+#define TCIP_APIMSG_SET_ERR(m, e) (m)->msg.err = e /* catch functions that don't set err */
+#else
+#define TCIP_APIMSG_SET_ERR(m, e)
+#endif
+#define TCPIP_APIMSG(m,f,e) do { \
+ TCIP_APIMSG_SET_ERR(m, ERR_VAL); \
+ LOCK_TCPIP_CORE(); \
+ f(&((m)->msg)); \
+ UNLOCK_TCPIP_CORE(); \
+ (e) = (m)->msg.err; \
+} while(0)
#define TCPIP_APIMSG_ACK(m)
#define TCPIP_NETIFAPI(m) tcpip_netifapi_lock(m)
#define TCPIP_NETIFAPI_ACK(m)
#else /* LWIP_TCPIP_CORE_LOCKING */
#define LOCK_TCPIP_CORE()
#define UNLOCK_TCPIP_CORE()
-#define TCPIP_APIMSG(m) tcpip_apimsg(m)
+#define TCPIP_APIMSG(m,f,e) do { (m)->function = f; (e) = tcpip_apimsg(m); } while(0)
#define TCPIP_APIMSG_ACK(m) sys_sem_signal(&m->conn->op_completed)
#define TCPIP_NETIFAPI(m) tcpip_netifapi(m)
#define TCPIP_NETIFAPI_ACK(m) sys_sem_signal(&m->sem)
@@ -84,9 +95,6 @@ void tcpip_init(tcpip_init_done_fn tcpip_init_done, void *arg);
#if LWIP_NETCONN
err_t tcpip_apimsg(struct api_msg *apimsg);
-#if LWIP_TCPIP_CORE_LOCKING
-err_t tcpip_apimsg_lock(struct api_msg *apimsg);
-#endif /* LWIP_TCPIP_CORE_LOCKING */
#endif /* LWIP_NETCONN */
err_t tcpip_input(struct pbuf *p, struct netif *inp);