diff --git a/net/arp/arp_format.c b/net/arp/arp_format.c index 6cca53a7f9..2b5db120bb 100644 --- a/net/arp/arp_format.c +++ b/net/arp/arp_format.c @@ -75,8 +75,18 @@ void arp_format(FAR struct net_driver_s *dev, in_addr_t ipaddr) { - FAR struct arp_hdr_s *arp = ARPBUF; - FAR struct eth_hdr_s *eth = ETHBUF; + FAR struct arp_hdr_s *arp; + FAR struct eth_hdr_s *eth; + + /* Prepare device buffer before format arp */ + + if (netdev_iob_prepare(dev, false, 0) != OK) + { + return; + } + + arp = ARPBUF; + eth = ETHBUF; /* Construct the ARP packet. Creating both the Ethernet and ARP headers */ diff --git a/net/can/can_poll.c b/net/can/can_poll.c index 1c7b95019d..2def213a5d 100644 --- a/net/can/can_poll.c +++ b/net/can/can_poll.c @@ -66,9 +66,8 @@ void can_poll(FAR struct net_driver_s *dev, FAR struct can_conn_s *conn) /* Setup for the application callback */ - dev->d_appdata = IPBUF(0); - dev->d_len = 0; - dev->d_sndlen = 0; + dev->d_len = 0; + dev->d_sndlen = 0; /* Perform the application callback */ diff --git a/net/devif/devif_poll.c b/net/devif/devif_poll.c index 4b77fbe218..2fdf462acb 100644 --- a/net/devif/devif_poll.c +++ b/net/devif/devif_poll.c @@ -821,13 +821,6 @@ static int devif_iob_poll(FAR struct net_driver_s *dev, { int bstop; - /* Device polling, prepare iob buffer */ - - if (netdev_iob_prepare(dev, false, 0) != OK) - { - return true; - } - /* Perform all connections poll */ bstop = devif_poll_connections(dev, callback); @@ -920,15 +913,6 @@ int devif_poll(FAR struct net_driver_s *dev, devif_poll_callback_t callback) do { - /* Device polling, prepare iob buffer */ - - if (netdev_iob_prepare(dev, false, 0) != OK) - { - nwarn("WARNING: IOB Prepare failed for dev %s!\n", dev->d_ifname); - bstop = true; - break; - } - /* Perform all connections poll */ bstop = devif_poll_connections(dev, devif_poll_callback); diff --git a/net/devif/devif_send.c b/net/devif/devif_send.c index 5e076d0ff8..ea2d5cad41 100644 --- a/net/devif/devif_send.c +++ b/net/devif/devif_send.c @@ -78,12 +78,19 @@ void devif_send(FAR struct net_driver_s *dev, FAR const void *buf, return; } - iob_update_pktlen(dev->d_iob, offset); - /* Copy in iob to target device buffer */ if (len <= iob_navail(false) * CONFIG_IOB_BUFSIZE) { + /* Prepare device buffer before poll callback */ + + if (netdev_iob_prepare(dev, false, 0) != OK) + { + return; + } + + iob_update_pktlen(dev->d_iob, offset); + dev->d_sndlen = iob_trycopyin(dev->d_iob, buf, len, offset, false); } else diff --git a/net/icmp/icmp_poll.c b/net/icmp/icmp_poll.c index 290c129cd4..09d80d570f 100644 --- a/net/icmp/icmp_poll.c +++ b/net/icmp/icmp_poll.c @@ -66,9 +66,8 @@ void icmp_poll(FAR struct net_driver_s *dev, FAR struct icmp_conn_s *conn) /* Setup for the application callback */ - dev->d_appdata = IPBUF(IPICMP_HDRLEN); - dev->d_len = 0; - dev->d_sndlen = 0; + dev->d_len = 0; + dev->d_sndlen = 0; /* Perform the application callback */ diff --git a/net/icmpv6/icmpv6_autoconfig.c b/net/icmpv6/icmpv6_autoconfig.c index 0d899ad4e1..a8021bd224 100644 --- a/net/icmpv6/icmpv6_autoconfig.c +++ b/net/icmpv6/icmpv6_autoconfig.c @@ -125,6 +125,13 @@ static uint16_t icmpv6_router_eventhandler(FAR struct net_driver_s *dev, return flags; } + /* Prepare device buffer */ + + if (netdev_iob_prepare(dev, false, 0) != OK) + { + return flags; + } + /* It looks like we are good to send the data. * * Copy the packet data into the device packet buffer and send it. diff --git a/net/icmpv6/icmpv6_neighbor.c b/net/icmpv6/icmpv6_neighbor.c index 9b2e4f18b4..1612865bad 100644 --- a/net/icmpv6/icmpv6_neighbor.c +++ b/net/icmpv6/icmpv6_neighbor.c @@ -109,6 +109,13 @@ static uint16_t icmpv6_neighbor_eventhandler(FAR struct net_driver_s *dev, return flags; } + /* Prepare device buffer */ + + if (netdev_iob_prepare(dev, false, 0) != OK) + { + return flags; + } + /* It looks like we are good to send the data. * * Copy the packet data into the device packet buffer and send it. diff --git a/net/icmpv6/icmpv6_poll.c b/net/icmpv6/icmpv6_poll.c index 7da0cd005e..278c3f48b7 100644 --- a/net/icmpv6/icmpv6_poll.c +++ b/net/icmpv6/icmpv6_poll.c @@ -67,9 +67,8 @@ void icmpv6_poll(FAR struct net_driver_s *dev, /* Setup for the application callback */ - dev->d_appdata = IPBUF(IPICMPv6_HDRLEN); - dev->d_len = 0; - dev->d_sndlen = 0; + dev->d_len = 0; + dev->d_sndlen = 0; /* Perform the application callback */ diff --git a/net/igmp/igmp_poll.c b/net/igmp/igmp_poll.c index 47ef3d34d6..b7f71f2fbe 100644 --- a/net/igmp/igmp_poll.c +++ b/net/igmp/igmp_poll.c @@ -151,15 +151,11 @@ static inline void igmp_sched_send(FAR struct net_driver_s *dev, void igmp_poll(FAR struct net_driver_s *dev) { FAR struct igmp_group_s *group; - uint16_t iphdrlen; /* Setup the poll operation */ - iphdrlen = IPv4_HDRLEN + RASIZE; - - dev->d_appdata = IPBUF(iphdrlen + IGMP_HDRLEN); - dev->d_len = 0; - dev->d_sndlen = 0; + dev->d_len = 0; + dev->d_sndlen = 0; /* Check each member of the group */ diff --git a/net/igmp/igmp_send.c b/net/igmp/igmp_send.c index c15a695f77..d60a49a21f 100644 --- a/net/igmp/igmp_send.c +++ b/net/igmp/igmp_send.c @@ -109,6 +109,13 @@ void igmp_send(FAR struct net_driver_s *dev, FAR struct igmp_group_s *group, ninfo("msgid: %02x destipaddr: %08x\n", msgid, (int)*destipaddr); + /* Prepare device buffer */ + + if (netdev_iob_prepare(dev, false, 0) != OK) + { + return; + } + /* The IGMP header immediately follows the IP header */ iphdrlen = IPv4_HDRLEN + RASIZE; diff --git a/net/ipforward/ipfwd_forward.c b/net/ipforward/ipfwd_forward.c index 00d7034030..94a933c38a 100644 --- a/net/ipforward/ipfwd_forward.c +++ b/net/ipforward/ipfwd_forward.c @@ -161,6 +161,11 @@ static uint16_t ipfwd_eventhandler(FAR struct net_driver_s *dev, else { + /* Copy the user data into d_appdata and send it. */ + + devif_forward(fwd); + flags &= ~DEVPOLL_MASK; + #if defined(CONFIG_NET_IPv4) && defined(CONFIG_NET_IPv6) /* If both IPv4 and IPv6 support are enabled, then we will need to * select which one to use when generating the outgoing packet. @@ -170,10 +175,6 @@ static uint16_t ipfwd_eventhandler(FAR struct net_driver_s *dev, forward_ipselect(fwd); #endif - /* Copy the user data into d_appdata and send it. */ - - devif_forward(fwd); - flags &= ~DEVPOLL_MASK; } /* Free the allocated callback structure */ diff --git a/net/mld/mld_poll.c b/net/mld/mld_poll.c index d0cd926419..d706ffb29a 100644 --- a/net/mld/mld_poll.c +++ b/net/mld/mld_poll.c @@ -60,9 +60,8 @@ void mld_poll(FAR struct net_driver_s *dev) /* Setup the poll operation */ - dev->d_appdata = IPBUF(IPv6_HDRLEN); - dev->d_len = 0; - dev->d_sndlen = 0; + dev->d_len = 0; + dev->d_sndlen = 0; /* Check if a general query is pending */ diff --git a/net/mld/mld_send.c b/net/mld/mld_send.c index f3fab001d8..8364808f7c 100644 --- a/net/mld/mld_send.c +++ b/net/mld/mld_send.c @@ -96,6 +96,13 @@ void mld_send(FAR struct net_driver_s *dev, FAR struct mld_group_s *group, DEBUGASSERT(dev != NULL); DEBUGASSERT(msgtype == MLD_SEND_GENQUERY || group != NULL); + /* Prepare device buffer */ + + if (netdev_iob_prepare(dev, false, 0) != OK) + { + return; + } + /* Select IPv6 */ IFF_SET_IPv6(dev->d_flags); diff --git a/net/netdev/netdev_iob.c b/net/netdev/netdev_iob.c index d6ebbd87de..f6159c4f54 100644 --- a/net/netdev/netdev_iob.c +++ b/net/netdev/netdev_iob.c @@ -69,6 +69,7 @@ int netdev_iob_prepare(FAR struct net_driver_s *dev, bool throttled, if (dev->d_iob == NULL) { + nwarn("WARNING: IOB Prepare failed for dev %s!\n", dev->d_ifname); return -ENOMEM; } diff --git a/net/pkt/pkt_poll.c b/net/pkt/pkt_poll.c index 7d6978fe84..6901ee324b 100644 --- a/net/pkt/pkt_poll.c +++ b/net/pkt/pkt_poll.c @@ -65,9 +65,8 @@ void pkt_poll(FAR struct net_driver_s *dev, FAR struct pkt_conn_s *conn) { /* Setup for the application callback */ - dev->d_appdata = IPBUF(0); - dev->d_len = 0; - dev->d_sndlen = 0; + dev->d_len = 0; + dev->d_sndlen = 0; /* Perform the application callback */ diff --git a/net/tcp/tcp_devpoll.c b/net/tcp/tcp_devpoll.c index 51e022aa30..3d7206c9b4 100644 --- a/net/tcp/tcp_devpoll.c +++ b/net/tcp/tcp_devpoll.c @@ -87,6 +87,13 @@ void tcp_poll(FAR struct net_driver_s *dev, FAR struct tcp_conn_s *conn) DEBUGASSERT(dev != NULL && conn != NULL && dev == conn->dev); + /* Prepare device buffer */ + + if (netdev_iob_prepare(dev, false, 0) != OK) + { + return; + } + /* Discard any currently buffered data */ if (conn->timeout) diff --git a/net/udp/udp_devpoll.c b/net/udp/udp_devpoll.c index 7796f8f5e1..d317147f9e 100644 --- a/net/udp/udp_devpoll.c +++ b/net/udp/udp_devpoll.c @@ -93,19 +93,8 @@ void udp_poll(FAR struct net_driver_s *dev, FAR struct udp_conn_s *conn) if (conn->lport != 0) { - /* Set up for the callback. We can't know in advance if the - * application is going to send a IPv4 or an IPv6 packet, so this setup - * may not actually be used. - */ - -#if defined(CONFIG_NET_IPv4) - udp_ipv4_select(dev); -#else /* if defined(CONFIG_NET_IPv6) */ - udp_ipv6_select(dev); -#endif - - dev->d_len = 0; - dev->d_sndlen = 0; + dev->d_len = 0; + dev->d_sndlen = 0; /* Perform the application callback */ diff --git a/net/udp/udp_sendto_buffered.c b/net/udp/udp_sendto_buffered.c index e5c36898fc..7263edb1c0 100644 --- a/net/udp/udp_sendto_buffered.c +++ b/net/udp/udp_sendto_buffered.c @@ -406,7 +406,6 @@ static uint16_t sendto_eventhandler(FAR struct net_driver_s *dev, { uint16_t udpiplen = udpip_hdrsize(conn); FAR struct udp_wrbuffer_s *wrb; - size_t sndlen; /* Peek at the head of the write queue (but don't remove anything * from the write queue yet). We know from the above test that @@ -424,14 +423,20 @@ static uint16_t sendto_eventhandler(FAR struct net_driver_s *dev, udp_connect(conn, (FAR const struct sockaddr *)&wrb->wb_dest); + /* Then set-up to send that amount of data with the offset + * corresponding to the size of the IP-dependent address structure. + */ + + netdev_iob_replace(dev, wrb->wb_iob); + /* Get the amount of data that we can send in the next packet. * We will send either the remaining data in the buffer I/O * buffer chain, or as much as will fit given the MSS and current * window size. */ - sndlen = wrb->wb_iob->io_pktlen - udpiplen; - ninfo("wrb=%p sndlen=%zu\n", wrb, sndlen); + dev->d_sndlen = wrb->wb_iob->io_pktlen - udpiplen; + ninfo("wrb=%p sndlen=%d\n", wrb, dev->d_sndlen); #ifdef NEED_IPDOMAIN_SUPPORT /* If both IPv4 and IPv6 support are enabled, then we will need to @@ -443,16 +448,6 @@ static uint16_t sendto_eventhandler(FAR struct net_driver_s *dev, sendto_ipselect(dev, conn); #endif - /* Release current device buffer and bypass the iob to l2 driver */ - - netdev_iob_release(dev); - - /* Then set-up to send that amount of data with the offset - * corresponding to the size of the IP-dependent address structure. - */ - - devif_iob_send(dev, wrb->wb_iob, sndlen, 0, udpiplen); - /* Free the write buffer at the head of the queue and attempt to * setup the next transfer. */ diff --git a/net/udp/udp_sendto_unbuffered.c b/net/udp/udp_sendto_unbuffered.c index ae629bc91d..db1d6ad030 100644 --- a/net/udp/udp_sendto_unbuffered.c +++ b/net/udp/udp_sendto_unbuffered.c @@ -192,6 +192,15 @@ static uint16_t sendto_eventhandler(FAR struct net_driver_s *dev, else { + /* Copy the user data into d_appdata and send it */ + + devif_send(dev, pstate->st_buffer, + pstate->st_buflen, udpip_hdrsize(pstate->st_conn)); + if (dev->d_sndlen == 0) + { + return flags; + } + #ifdef NEED_IPDOMAIN_SUPPORT /* If both IPv4 and IPv6 support are enabled, then we will need to * select which one to use when generating the outgoing packet. @@ -202,23 +211,14 @@ static uint16_t sendto_eventhandler(FAR struct net_driver_s *dev, sendto_ipselect(dev, pstate); #endif - /* Copy the user data into d_appdata and send it */ - - devif_send(dev, pstate->st_buffer, - pstate->st_buflen, udpip_hdrsize(pstate->st_conn)); - if (dev->d_sndlen == 0) - { - return flags; - } - pstate->st_sndlen = pstate->st_buflen; } /* Don't allow any further call backs. */ - pstate->st_cb->flags = 0; - pstate->st_cb->priv = NULL; - pstate->st_cb->event = NULL; + pstate->st_cb->flags = 0; + pstate->st_cb->priv = NULL; + pstate->st_cb->event = NULL; /* Wake up the waiting thread */