[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[lwip-devel] [bug #25051] lwip_recvfrom problem with udp: fromaddr and p
From: |
Tamas Somogyi |
Subject: |
[lwip-devel] [bug #25051] lwip_recvfrom problem with udp: fromaddr and port uses deleted netbuf |
Date: |
Tue, 09 Dec 2008 14:13:48 +0000 |
User-agent: |
Mozilla/5.0 (Windows; U; Windows NT 5.1; en-GB; rv:1.9.0.4) Gecko/2008102920 Firefox/3.0.4 |
URL:
<http://savannah.nongnu.org/bugs/?25051>
Summary: lwip_recvfrom problem with udp: fromaddr and port
uses deleted netbuf
Project: lwIP - A Lightweight TCP/IP stack
Submitted by: tsomogyi
Submitted on: Tue 09 Dec 2008 14:13:47 GMT
Category: sockets
Severity: 3 - Normal
Item Group: Faulty Behaviour
Status: None
Privacy: Public
Assigned to: None
Open/Closed: Open
Discussion Lock: Any
Planned Release:
lwIP version: CVS Head
_______________________________________________________
Details:
At the end of lwip_recvfrom, input address/port is extracted by "addr =
netbuf_fromaddr(buf)" for UDP sockets. But "buf" can already be disposed by
"netbuf_delete(buf);" in the do-while loop.
So if other threads (re-)use that buffer before the address has been copied
to "sin", then it will contain inapropriate data. This is often the case in my
application: I'm getting invalid address/port data 3-6 times/hour.
I fixed the problem by saving the address/port info before deleting netbuf:
lwip_recvfrom(...
//INSERTION-->
struct ip_addr saved_addr = { 0 };
u16_t saved_port = 0;
//<--INSERTION
...
if ((sock->conn->type == NETCONN_TCP) && (buflen - copylen > 0)) {
sock->lastdata = buf;
sock->lastoffset += copylen;
LWIP_DEBUGF(SOCKETS_DEBUG, ("lwip_recvfrom: lastdata now
netbuf=%p\n", (void*)buf));
} else {
//INSERTION-->
/* save addr before deleting buf */
if (from && fromlen) {
addr = netbuf_fromaddr(buf);
if (addr) {
saved_addr = *addr;
}
saved_port = netbuf_fromport(buf);
}
/* delete buf */
//<--INSERTION
sock->lastdata = NULL;
sock->lastoffset = 0;
LWIP_DEBUGF(SOCKETS_DEBUG, ("lwip_recvfrom: deleting netbuf=%p\n",
(void*)buf));
netbuf_delete(buf);
//INSERTION-->
buf = NULL;
//<--INSERTION
}
...
/* Check to see from where the data was.*/
if (from && fromlen) {
struct sockaddr_in sin;
if (netconn_type(sock->conn) == NETCONN_TCP) {
addr = (struct ip_addr*)&(sin.sin_addr.s_addr);
netconn_getaddr(sock->conn, addr, &port, 0);
} else {
//CHANGE-->
if (buf) {
addr = netbuf_fromaddr(buf);
port = netbuf_fromport(buf);
} else {
addr = &saved_addr;
port = saved_port;
}
//<--CHANGE
}
...
and the same change in #if SOCKETS_DEBUG section
...
}
This is just a quick fix also proving that the root of the problem is here.
However it might be possible to give more sophisticated fix (e.g. if I knew
that buf would _always_ be disposed in the loop or when to set "done" to 1 or
using "mem" instead of "buf", etc.).
_______________________________________________________
Reply to this item at:
<http://savannah.nongnu.org/bugs/?25051>
_______________________________________________
Message sent via/by Savannah
http://savannah.nongnu.org/
- [lwip-devel] [bug #25051] lwip_recvfrom problem with udp: fromaddr and port uses deleted netbuf,
Tamas Somogyi <=