From 1b06aff4070ea87fde4539230cb72eb45ecd1da2 Mon Sep 17 00:00:00 2001
From: khemendra kumar <khemendra.kumar13@gmail.com>
Date: Fri, 5 Oct 2018 18:48:40 +0530
Subject: Feat: DMM LWIP support UDP

Change-Id: I7bf108e946ce5543a31ca0e2b79709c52b4d2498
Signed-off-by: khemendra kumar <khemendra.kumar13@gmail.com>
---
 stacks/lwip_stack/lwip_src/api/spl_api_msg.c       | 96 +++++++++++++++++-----
 stacks/lwip_stack/lwip_src/core/spl_pbuf.c         | 14 ++++
 .../lwip_stack/lwip_src/include/stackx/spl_pbuf.h  |  3 +
 3 files changed, 94 insertions(+), 19 deletions(-)

(limited to 'stacks/lwip_stack/lwip_src')

diff --git a/stacks/lwip_stack/lwip_src/api/spl_api_msg.c b/stacks/lwip_stack/lwip_src/api/spl_api_msg.c
index 0986ed4..1c9bf92 100644
--- a/stacks/lwip_stack/lwip_src/api/spl_api_msg.c
+++ b/stacks/lwip_stack/lwip_src/api/spl_api_msg.c
@@ -414,7 +414,7 @@ spl_recv_udp (void *arg, struct udp_pcb *pcb, struct pbuf *p,
 {
   struct spl_netbuf *buf;
   spl_netconn_t *conn = (spl_netconn_t *) arg;
-  struct spl_pbuf *spb = NULL;  //??
+  struct spl_pbuf *spl_pb = NULL;       //??
 
   if (NULL == pcb)
     {
@@ -432,12 +432,28 @@ spl_recv_udp (void *arg, struct udp_pcb *pcb, struct pbuf *p,
   /* //@TODO: malloc and Copy splbuf */
   struct common_pcb *cpcb = (struct common_pcb *) (conn->comm_pcb_data);
 
-  buf = (struct spl_netbuf *) ((char *) p + sizeof (struct spl_pbuf));
-  buf->p = spb;
+  u16_t proc_id = spl_get_lcore_id ();
+
+  spl_pb = spl_pbuf_alloc_hugepage (SPL_PBUF_TRANSPORT,
+                                    p->tot_len +
+                                    g_offSetArry[SPL_PBUF_TRANSPORT],
+                                    SPL_PBUF_HUGE, proc_id, conn);
+
+  if (!spl_pb)
+    {
+      NSPOL_LOGINF (TCP_DEBUG, "spl_pbuf_alloc_hugepage Failed!!!");
+      return;
+    }
+
+  pbuf_to_splpbuf_copy (spl_pb, p);
+  pbuf_free (p);
+
+  buf = (struct spl_netbuf *) ((char *) spl_pb + sizeof (struct spl_pbuf));
+  buf->p = spl_pb;
   spl_ip_addr_set (&buf->addr, ipaddr);
   buf->port = port;
 
-  err_t ret = sp_enqueue (cpcb, (void *) p);
+  err_t ret = sp_enqueue (cpcb, (void *) spl_pb);
   if (ret != ERR_OK)
     {
       NSPOL_LOGDBG (UDP_DEBUG, "mbox post failed");
@@ -1807,6 +1823,56 @@ do_listen (struct common_pcb *cpcb, msg_listen * lmsg)
 
 }
 
+/**
+ * Send some data on UDP pcb contained in a netconn
+ * Called from do_send
+ *
+ * @param msg the api_msg_msg pointing to the connection
+ */
+void
+spl_udp_send (struct common_pcb *cpcb, msg_send_buf * smsg)
+{
+  struct spl_pbuf *p_from = smsg->p;
+  spl_netconn_t *conn = cpcb->conn;
+  struct udp_pcb *upcb = (struct udp_pcb *) (cpcb->conn->private_data);
+  data_com_msg *m = MSG_ENTRY (smsg, data_com_msg, buffer);
+  struct pbuf *p_to = NULL;
+  err_t err = ERR_OK;
+
+  //allocate pbuf and copy spl_pbuf, send , free pbuf and spl_pbuf
+  do
+    {
+      p_to = pbuf_alloc (PBUF_TRANSPORT, p_from->len, PBUF_RAM);
+      if (NULL == p_to)
+        {
+          NSPOL_LOGERR ("pbuf is NULL]conn=%p,pcb=%p", conn, upcb);
+          return;
+        }
+
+      err = splpbuf_to_pbuf_transport_copy (p_to, p_from);
+      if (err != ERR_OK)
+        {
+          SET_MSG_ERR (m, conn->last_err);
+          return;
+        }
+
+      if (ip_addr_isany (&smsg->addr))
+        {
+          SET_MSG_ERR (m, udp_send (upcb, p_to));
+        }
+      else
+        {
+          SET_MSG_ERR (m,
+                       udp_sendto (upcb, p_to, (ip_addr_t *) & smsg->addr,
+                                   smsg->port));
+        }
+
+      p_from = (struct spl_pbuf *) ADDR_SHTOL (p_from->next_a);
+    }
+  while (p_from != NULL);
+
+}
+
 /**
  * Send some data on a RAW or UDP pcb contained in a netconn
  * Called from netconn_send
@@ -1825,8 +1891,8 @@ do_send (struct common_pcb *cpcb, msg_send_buf * smsg)
   if (SPL_ERR_IS_FATAL (conn->last_err))
     {
       SET_MSG_ERR (m, conn->last_err);
-      spl_pbuf_free (p);
-      return;
+      NSPOL_LOGERR ("Invalid param]msg->conn=%p", conn);
+      goto err_return;
     }
 
   switch (SPL_NETCONNTYPE_GROUP (cpcb->type))
@@ -1840,20 +1906,8 @@ do_send (struct common_pcb *cpcb, msg_send_buf * smsg)
             ss_set_local_ip (conn, smsg->local_ip.addr);
           }
 
-        //spl_ip_addr_t *destIP = &smsg->addr;
+        spl_udp_send (cpcb, smsg);
 
-        //@TODO udp send need to update like TCP. copy pbuf here. Once testing done for TCP we'll update it here.
-        if (ip_addr_isany (&smsg->addr))
-          {
-            //SET_MSG_ERR(m, udp_send(upcb, p));
-            /* destIP.addr == IPADDR_ANY means it is from stackx_send
-               and the destination is stored in remote_ip and remote port */
-            //destIP = &upcb->remote_ip;
-          }
-        else
-          {
-            //SET_MSG_ERR(m, udp_sendto(upcb, p, &smsg->addr, smsg->port));
-          }
         break;
       }
 
@@ -1862,6 +1916,10 @@ do_send (struct common_pcb *cpcb, msg_send_buf * smsg)
       break;
     }
 
+err_return:
+  pbuf_free_safe (smsg->p);
+  ASYNC_MSG_FREE (m);
+
   return;
 }
 
diff --git a/stacks/lwip_stack/lwip_src/core/spl_pbuf.c b/stacks/lwip_stack/lwip_src/core/spl_pbuf.c
index 03e30ed..54589e8 100644
--- a/stacks/lwip_stack/lwip_src/core/spl_pbuf.c
+++ b/stacks/lwip_stack/lwip_src/core/spl_pbuf.c
@@ -368,6 +368,20 @@ spl_pbuf_copy (struct spl_pbuf * p_to, struct spl_pbuf * p_from)
   return ERR_OK;
 }
 
+err_t
+splpbuf_to_pbuf_transport_copy (struct pbuf * p_to, struct spl_pbuf * p_from)
+{
+  if (EOK != MEMMOVE_S ((u8_t *) p_to->payload,
+                        p_to->len, (u8_t *) ADDR_SHTOL (p_from->payload_a),
+                        p_from->len))
+    {
+      NSPOL_LOGERR ("MEMMOVE_S failed");
+      return ERR_MEM;
+    }
+
+  return ERR_OK;
+}
+
 err_t
 splpbuf_to_pbuf_copy (struct pbuf * p_to, struct spl_pbuf * p_from)
 {
diff --git a/stacks/lwip_stack/lwip_src/include/stackx/spl_pbuf.h b/stacks/lwip_stack/lwip_src/include/stackx/spl_pbuf.h
index 01fe242..79deace 100644
--- a/stacks/lwip_stack/lwip_src/include/stackx/spl_pbuf.h
+++ b/stacks/lwip_stack/lwip_src/include/stackx/spl_pbuf.h
@@ -48,6 +48,9 @@ struct spl_pbuf *spl_pbuf_alloc_hugepage (spl_pbuf_layer l, u16_t length,
                                           spl_pbuf_type type,
                                           u16_t thread_index, void *net_conn);
 struct pbuf *spl_convert_spl_pbuf_to_pbuf (struct spl_pbuf *p_from);
+err_t
+splpbuf_to_pbuf_transport_copy (struct pbuf *p_to, struct spl_pbuf *p_from);
+
 err_t pbuf_to_splpbuf_copy (struct spl_pbuf *p_to, struct pbuf *p_from);
 err_t splpbuf_to_pbuf_copy (struct pbuf *p_to, struct spl_pbuf *p_from);
 spl_pbuf_layer get_pbuf_layer_from_pbuf_payload (struct pbuf *buf);
-- 
cgit