Skip to content

Commit

Permalink
Merge branch 'master' of git://git.savannah.nongnu.org/lwip
Browse files Browse the repository at this point in the history
Conflicts:
	src/api/api_msg.c
  • Loading branch information
tabascoeye committed Jan 13, 2015
2 parents 758ba2d + 6ca8bc4 commit e736200
Show file tree
Hide file tree
Showing 58 changed files with 1,052 additions and 474 deletions.
30 changes: 30 additions & 0 deletions CHANGELOG
Expand Up @@ -6,6 +6,18 @@ HISTORY

++ New features:

2014-12-10: Simon Goldschmidt
* api: added option LWIP_NETCONN_SEM_PER_THREAD to use a semaphore per thread
instead of using one per netconn and per select call

2014-12-08: Simon Goldschmidt
* ip6.h: fixed bug #43778: IPv6 header version not set on 16-bit platform
(macro IP6H_VTCFL_SET())

2014-12-08: Simon Goldschmidt
* icmp.c, ip4.c, pbuf.c, udp.c, pbuf.h: task #11472 Support PBUF_REF for RX
(IPv6 and IPv4/v6 reassembly might not work yet)

2014-11-06: Simon Goldschmidt
* sockets.c/.h, init.c: lwip_socket_init() is not needed any more
-> compatibility define
Expand Down Expand Up @@ -131,6 +143,24 @@ HISTORY

++ Bugfixes:

2014-12-19: Simon Goldschmidt
* opt.h, dhcp.h/.c: prevent dhcp from starting when netif link is down (only
when LWIP_DHCP_CHECK_LINK_UP==1, which is disabled by default for
compatibility reasons)

2014-12-17: Simon Goldschmidt
* tcp_out.c: fixed bug #43840 Checksum error for TCP_CHECKSUM_ON_COPY==1 for
no-copy data with odd length

2014-12-10: Simon Goldschmidt
* sockets.c, tcp.c, others: fixed bug #43797 set/getsockopt: SO_SNDTIMEO/SO_RCVTIMEO
take int as option but should take timeval (LWIP_SO_SNDRCVTIMEO_STANDARD==0 can
be used to revert to the old 'winsock' style behaviour)
Fixed implementation of SO_ACCEPTCONN to just look at the pcb state

2014-12-09: Simon Goldschmidt
* ip4.c: fixed bug #43596 IGMP queries from 0.0.0.0 are discarded

2014-10-21: Simon Goldschmidt (patch by Joel Cunningham and Albert Huitsing)
* sockts.c: fixed bugs #41495 Possible threading issue in select() and #43278
event_callback() handle context switch when calling sys_sem_signal()
Expand Down
31 changes: 27 additions & 4 deletions src/api/api_lib.c
Expand Up @@ -86,12 +86,14 @@ netconn_new_with_proto_and_callback(enum netconn_type t, u8_t proto, netconn_cal
API_MSG_VAR_FREE(msg);
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));
#if LWIP_TCP
LWIP_ASSERT("conn->acceptmbox shouldn't exist", !sys_mbox_valid(&conn->acceptmbox));
#endif /* LWIP_TCP */
#if !LWIP_NETCONN_SEM_PER_THREAD
LWIP_ASSERT("conn has no op_completed", sys_sem_valid(&conn->op_completed));
sys_sem_free(&conn->op_completed);
#endif /* !LWIP_NETCONN_SEM_PER_THREAD */
sys_mbox_free(&conn->recvmbox);
memp_free(MEMP_NETCONN, conn);
return NULL;
Expand Down Expand Up @@ -245,8 +247,8 @@ netconn_connect(struct netconn *conn, ip_addr_t *addr, u16_t port)
#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(&API_MSG_VAR_REF(msg), lwip_netconn_do_connect, err);
/* UDP and RAW only set flags, so we can use core-locking. */
TCPIP_APIMSG(&API_MSG_VAR_REF(msg), lwip_netconn_do_connect, err);
}
#endif /* (LWIP_UDP || LWIP_RAW) */
API_MSG_VAR_FREE(msg);
Expand Down Expand Up @@ -827,7 +829,7 @@ netconn_gethostbyname(const char *name, ip_addr_t *addr)
LWIP_ERROR("netconn_gethostbyname: invalid name", (name != NULL), return ERR_ARG;);
LWIP_ERROR("netconn_gethostbyname: invalid addr", (addr != NULL), return ERR_ARG;);
#if LWIP_MPU_COMPATIBLE
if (strlen(name >= DNS_MAX_NAME_LENGTH) {
if (strlen(name) >= DNS_MAX_NAME_LENGTH) {
return ERR_ARG;
}
#endif
Expand Down Expand Up @@ -862,4 +864,25 @@ netconn_gethostbyname(const char *name, ip_addr_t *addr)
}
#endif /* LWIP_DNS*/

#if LWIP_NETCONN_SEM_PER_THREAD
void netconn_thread_init(void)
{
sys_sem_t *sem = LWIP_NETCONN_THREAD_SEM_GET();
if (sem == SYS_SEM_NULL) {
/* call alloc only once */
LWIP_NETCONN_THREAD_SEM_ALLOC();
LWIP_ASSERT("LWIP_NETCONN_THREAD_SEM_ALLOC() failed", LWIP_NETCONN_THREAD_SEM_GET() != SYS_SEM_NULL);
}
}

void netconn_thread_cleanup(void)
{
sys_sem_t *sem = LWIP_NETCONN_THREAD_SEM_GET();
if (sem == SYS_SEM_NULL) {
/* call free only once */
LWIP_NETCONN_THREAD_SEM_FREE();
}
}
#endif /* LWIP_NETCONN_SEM_PER_THREAD */

#endif /* LWIP_NETCONN */
61 changes: 39 additions & 22 deletions src/api/api_msg.c
Expand Up @@ -70,7 +70,7 @@ static void lwip_netconn_do_close_internal(struct netconn *conn);
#if LWIP_RAW
/**
* Receive callback function for RAW netconns.
* Doesn't 'eat' the packet, only references it and sends it to
* Doesn't 'eat' the packet, only copies it and sends it to
* conn->recvmbox
*
* @see raw.h (struct raw_pcb.recv) for parameters and return value
Expand Down Expand Up @@ -365,8 +365,9 @@ err_tcp(void *arg, err_t err)
old_state = conn->state;
conn->state = NETCONN_NONE;

/* Notify the user layer about a connection error. Used to signal
select. */
/* @todo: the type of NETCONN_EVT created should depend on 'old_state' */

/* Notify the user layer about a connection error. Used to signal select. */
API_EVENT(conn, NETCONN_EVT_ERROR, 0);
/* Try to release selects pending on 'read' or 'write', too.
They will get an error if they actually try to read or write. */
Expand All @@ -392,12 +393,15 @@ err_tcp(void *arg, err_t err)
SET_NONBLOCKING_CONNECT(conn, 0);

if (!was_nonblocking_connect) {
sys_sem_t* op_completed_sem;
/* set error return code */
LWIP_ASSERT("conn->current_msg != NULL", conn->current_msg != NULL);
conn->current_msg->err = err;
op_completed_sem = LWIP_API_MSG_SEM(conn->current_msg);
LWIP_ASSERT("inavlid op_completed_sem", op_completed_sem != SYS_SEM_NULL);
conn->current_msg = NULL;
/* wake up the waiting task */
sys_sem_signal(&conn->op_completed);
sys_sem_signal(op_completed_sem);
}
} else {
LWIP_ASSERT("conn->current_msg == NULL", conn->current_msg == NULL);
Expand Down Expand Up @@ -553,7 +557,7 @@ void
lwip_netconn_do_newconn(struct api_msg_msg *msg)
{
msg->err = ERR_OK;
if(msg->conn->pcb.tcp == NULL) {
if (msg->conn->pcb.tcp == NULL) {
pcb_new(msg);
}
/* Else? This "new" connection already has a PCB allocated. */
Expand Down Expand Up @@ -588,7 +592,7 @@ netconn_alloc(enum netconn_type t, netconn_callback callback)
conn->type = t;
conn->pcb.tcp = NULL;

/* If all sizes are the same, every compiler should optimize this switch to nothing, */
/* If all sizes are the same, every compiler should optimize this switch to nothing */
switch(NETCONNTYPE_GROUP(t)) {
#if LWIP_RAW
case NETCONN_RAW:
Expand All @@ -610,13 +614,15 @@ netconn_alloc(enum netconn_type t, netconn_callback callback)
goto free_and_return;
}

if (sys_sem_new(&conn->op_completed, 0) != ERR_OK) {
if (sys_mbox_new(&conn->recvmbox, size) != ERR_OK) {
goto free_and_return;
}
if (sys_mbox_new(&conn->recvmbox, size) != ERR_OK) {
sys_sem_free(&conn->op_completed);
#if !LWIP_NETCONN_SEM_PER_THREAD
if (sys_sem_new(&conn->op_completed, 0) != ERR_OK) {
sys_mbox_free(&conn->recvmbox);
goto free_and_return;
}
#endif

#if LWIP_TCP
sys_mbox_set_invalid(&conn->acceptmbox);
Expand Down Expand Up @@ -665,10 +671,12 @@ netconn_free(struct netconn *conn)
!sys_mbox_valid(&conn->acceptmbox));
#endif /* LWIP_TCP */

#if !LWIP_NETCONN_SEM_PER_THREAD
if (sys_sem_valid(&conn->op_completed)) {
sys_sem_free(&conn->op_completed);
sys_sem_set_invalid(&conn->op_completed);
}
#endif

memp_free(MEMP_NETCONN, conn);
}
Expand Down Expand Up @@ -792,6 +800,7 @@ lwip_netconn_do_close_internal(struct netconn *conn)
}
if (err == ERR_OK) {
/* Closing succeeded */
sys_sem_t* op_completed_sem = LWIP_API_MSG_SEM(conn->current_msg);
conn->current_msg->err = ERR_OK;
conn->current_msg = NULL;
conn->state = NETCONN_NONE;
Expand All @@ -809,7 +818,7 @@ lwip_netconn_do_close_internal(struct netconn *conn)
API_EVENT(conn, NETCONN_EVT_SENDPLUS, 0);
}
/* wake up the application task */
sys_sem_signal(&conn->op_completed);
sys_sem_signal(op_completed_sem);
} else {
/* Closing failed, restore some of the callbacks */
/* Closing of listen pcb will never fail! */
Expand Down Expand Up @@ -886,8 +895,8 @@ lwip_netconn_do_delconn(struct api_msg_msg *msg)
API_EVENT(msg->conn, NETCONN_EVT_RCVPLUS, 0);
API_EVENT(msg->conn, NETCONN_EVT_SENDPLUS, 0);
}
if (sys_sem_valid(&msg->conn->op_completed)) {
sys_sem_signal(&msg->conn->op_completed);
if (sys_sem_valid(LWIP_API_MSG_SEM(msg))) {
sys_sem_signal(LWIP_API_MSG_SEM(msg));
}
}

Expand Down Expand Up @@ -942,6 +951,7 @@ lwip_netconn_do_connected(void *arg, struct tcp_pcb *pcb, err_t err)
{
struct netconn *conn;
int was_blocking;
sys_sem_t* op_completed_sem = NULL;

LWIP_UNUSED_ARG(pcb);

Expand All @@ -957,12 +967,16 @@ lwip_netconn_do_connected(void *arg, struct tcp_pcb *pcb, err_t err)

if (conn->current_msg != NULL) {
conn->current_msg->err = err;
op_completed_sem = LWIP_API_MSG_SEM(conn->current_msg);
}
if ((NETCONNTYPE_GROUP(conn->type) == NETCONN_TCP) && (err == ERR_OK)) {
setup_tcp(conn);
}
was_blocking = !IN_NONBLOCKING_CONNECT(conn);
SET_NONBLOCKING_CONNECT(conn, 0);
LWIP_ASSERT("blocking connect state error",
(was_blocking && op_completed_sem != NULL) ||
(!was_blocking && op_completed_sem == NULL));
conn->current_msg = NULL;
conn->state = NETCONN_NONE;
if (!was_blocking) {
Expand All @@ -971,7 +985,7 @@ lwip_netconn_do_connected(void *arg, struct tcp_pcb *pcb, err_t err)
API_EVENT(conn, NETCONN_EVT_SENDPLUS, 0);

if (was_blocking) {
sys_sem_signal(&conn->op_completed);
sys_sem_signal(op_completed_sem);
}
return ERR_OK;
}
Expand All @@ -992,7 +1006,7 @@ lwip_netconn_do_connect(struct api_msg_msg *msg)
msg->err = ERR_CLSD;
if (NETCONNTYPE_GROUP(msg->conn->type) == NETCONN_TCP) {
/* For TCP, netconn_connect() calls tcpip_apimsg(), so signal op_completed here. */
sys_sem_signal(&msg->conn->op_completed);
sys_sem_signal(LWIP_API_MSG_SEM(msg));
return;
}
} else {
Expand Down Expand Up @@ -1031,7 +1045,7 @@ lwip_netconn_do_connect(struct api_msg_msg *msg)
}
}
/* For TCP, netconn_connect() calls tcpip_apimsg(), so signal op_completed here. */
sys_sem_signal(&msg->conn->op_completed);
sys_sem_signal(LWIP_API_MSG_SEM(msg));
return;
#endif /* LWIP_TCP */
default:
Expand Down Expand Up @@ -1288,7 +1302,7 @@ lwip_netconn_do_writemore(struct netconn *conn)
if (available < len) {
/* don't try to write more than sendbuf */
len = available;
if (dontblock){
if (dontblock) {
if (!len) {
err = ERR_WOULDBLOCK;
goto err_mem;
Expand Down Expand Up @@ -1349,19 +1363,21 @@ lwip_netconn_do_writemore(struct netconn *conn)
if (write_finished) {
/* everything was written: set back connection state
and back to application task */
sys_sem_t* op_completed_sem = LWIP_API_MSG_SEM(conn->current_msg);
conn->current_msg->err = err;
conn->current_msg = NULL;
conn->state = NETCONN_NONE;
#if LWIP_TCPIP_CORE_LOCKING
if ((conn->flags & NETCONN_FLAG_WRITE_DELAYED) != 0)
#endif
{
sys_sem_signal(&conn->op_completed);
sys_sem_signal(op_completed_sem);
}
}
#if LWIP_TCPIP_CORE_LOCKING
else
else {
return ERR_MEM;
}
#endif
return ERR_OK;
}
Expand Down Expand Up @@ -1397,9 +1413,9 @@ lwip_netconn_do_write(struct api_msg_msg *msg)
if (lwip_netconn_do_writemore(msg->conn) != ERR_OK) {
LWIP_ASSERT("state!", msg->conn->state == NETCONN_WRITE);
UNLOCK_TCPIP_CORE();
sys_arch_sem_wait(&msg->conn->op_completed, 0);
sys_arch_sem_wait(LWIP_API_MSG_SEM(msg), 0);
LOCK_TCPIP_CORE();
LWIP_ASSERT("state!", msg->conn->state == NETCONN_NONE);
LWIP_ASSERT("state!", msg->conn->state != NETCONN_WRITE);
}
#else /* LWIP_TCPIP_CORE_LOCKING */
lwip_netconn_do_writemore(msg->conn);
Expand Down Expand Up @@ -1486,8 +1502,9 @@ lwip_netconn_do_getaddr(struct api_msg_msg *msg)
}

/**
* Close a TCP pcb contained in a netconn
* Close or half-shutdown a TCP pcb contained in a netconn
* Called from netconn_close
* In contrast to closing sockets, the netconn is not deallocated.
*
* @param msg the api_msg_msg pointing to the connection
*/
Expand Down Expand Up @@ -1523,7 +1540,7 @@ lwip_netconn_do_close(struct api_msg_msg *msg)
{
msg->err = ERR_VAL;
}
sys_sem_signal(&msg->conn->op_completed);
sys_sem_signal(LWIP_API_MSG_SEM(msg));
}

#if LWIP_IGMP || (LWIP_IPV6 && LWIP_IPV6_MLD)
Expand Down
2 changes: 1 addition & 1 deletion src/api/pppapi.c
Expand Up @@ -102,7 +102,7 @@ pppapi_do_ppp_set_auth(struct pppapi_msg_msg *msg)
* tcpip_thread context.
*/
void
pppapi_set_auth(ppp_pcb *pcb, u8_t authtype, char *user, char *passwd)
pppapi_set_auth(ppp_pcb *pcb, u8_t authtype, const char *user, const char *passwd)
{
struct pppapi_msg msg;
msg.function = pppapi_do_ppp_set_auth;
Expand Down

0 comments on commit e736200

Please sign in to comment.