Aslo create wrapper of sendto() to retry if errno is ENOMEM/ENOBUFFS/EINTR.
And return for other errors, do not assert() cause coredump.
---
 src/mds/mds_dt_tipc.c            | 47 +++++++++++++++++++----
 src/mds/mds_dt_tipc.h            |  3 ++
 src/mds/mds_tipc_fctrl_portid.cc | 65 +++++++++++++++-----------------
 3 files changed, 74 insertions(+), 41 deletions(-)

diff --git a/src/mds/mds_dt_tipc.c b/src/mds/mds_dt_tipc.c
index fdf0da7fb..b0f38ee49 100644
--- a/src/mds/mds_dt_tipc.c
+++ b/src/mds/mds_dt_tipc.c
@@ -51,6 +51,7 @@
 #include "mds_tipc_recvq_stats.h"
 #include "base/osaf_utility.h"
 #include "base/osaf_poll.h"
+#include "base/osaf_time.h"
 
 #ifndef SOCK_CLOEXEC
 enum { SOCK_CLOEXEC = 0x80000 };
@@ -523,9 +524,7 @@ uint32_t mdtm_tipc_destroy(void)
        MDTM_REASSEMBLY_QUEUE *reassem_queue = NULL;
        MDTM_REASSEMBLY_KEY reassembly_key;
 
-       /* close sockets first */
-       close(tipc_cb.BSRsock);
-       close(tipc_cb.Dsock);
+       mds_tipc_fctrl_shutdown();
 
        /* Destroy receiving task */
        if (mdtm_destroy_rcv_task() != NCSCC_RC_SUCCESS) {
@@ -537,7 +536,6 @@ uint32_t mdtm_tipc_destroy(void)
                         NULL);
        m_NCS_IPC_RELEASE(&tipc_cb.tmr_mbx,
                          (NCS_IPC_CB)mdtm_mailbox_mbx_cleanup);
-       mds_tipc_fctrl_shutdown();
        /* Clear reference hdl list */
        while (mdtm_ref_hdl_list_hdr != NULL) {
                /* Store temporary the pointer of entry to be deleted */
@@ -587,6 +585,9 @@ uint32_t mdtm_tipc_destroy(void)
        handle = 0;
        mdtm_global_frag_num = 0;
 
+       close(tipc_cb.BSRsock);
+       close(tipc_cb.Dsock);
+
        return NCSCC_RC_SUCCESS;
 }
 
@@ -3135,6 +3136,37 @@ uint32_t mdtm_add_frag_hdr(uint8_t *buf_ptr, uint16_t 
len, uint32_t seq_num,
        return NCSCC_RC_SUCCESS;
 }
 
+/*********************************************************
+
+  Function NAME: mds_retry_sendto
+
+  DESCRIPTION: wrapper of sendto() for retry purpose
+
+  ARGUMENTS: same as sendto()
+
+  RETURNS: same as sendto()
+
+*********************************************************/
+ssize_t mds_retry_sendto(int sockfd, const void *buf, size_t len, int flags,
+               const struct sockaddr *dest_addr, socklen_t addrlen)
+{
+       int retry = 5;
+       ssize_t send_len = 0;
+       while (retry >= 0) {
+               send_len = sendto(sockfd, buf, len, flags, dest_addr, addrlen);
+               if (send_len == len) {
+                       return send_len;
+               } else if (retry-- > 0) {
+                       if (errno != ENOMEM &&
+                               errno != ENOBUFS &&
+                               errno != EINTR)
+                               break;
+                       osaf_nanosleep(&kTenMilliseconds);
+               }
+       }
+       return send_len;
+}
+
 /*********************************************************
 
   Function NAME: mdtm_sendto
@@ -3176,7 +3208,8 @@ static uint32_t mdtm_sendto(uint8_t *buffer, uint16_t 
buff_len,
        }
 #endif
        if (mds_tipc_fctrl_trysend(buffer, buff_len, id) == NCSCC_RC_SUCCESS) {
-               send_len = sendto(tipc_cb.BSRsock, buffer, buff_len, 0,
+               send_len = mds_retry_sendto(
+                                       tipc_cb.BSRsock, buffer, buff_len, 0,
                                        (struct sockaddr *)&server_addr, 
sizeof(server_addr));
                if (send_len == buff_len) {
                        m_MDS_LOG_INFO("MDTM: Successfully sent message");
@@ -3222,8 +3255,8 @@ static uint32_t mdtm_mcast_sendto(void *buffer, size_t 
size,
        server_addr.addr.nameseq.lower = HTONL(MDS_MDTM_LOWER_INSTANCE);
        /*This can be scope-down to dest_svc_id  server_inst TBD*/
        server_addr.addr.nameseq.upper = HTONL(MDS_MDTM_UPPER_INSTANCE);
-       int send_len =
-           sendto(tipc_cb.BSRsock, buffer, size, 0,
+       ssize_t send_len =
+           mds_retry_sendto(tipc_cb.BSRsock, buffer, size, 0,
                   (struct sockaddr *)&server_addr, sizeof(server_addr));
 
        if (send_len == size) {
diff --git a/src/mds/mds_dt_tipc.h b/src/mds/mds_dt_tipc.h
index e73a11b09..65175839e 100644
--- a/src/mds/mds_dt_tipc.h
+++ b/src/mds/mds_dt_tipc.h
@@ -107,4 +107,7 @@ extern uint32_t mds_mdtm_node_subscribe_tipc(MDS_SVC_HDL 
svc_hdl,
                                              MDS_SUBTN_REF_VAL *subtn_ref_val);
 extern uint32_t mds_mdtm_node_unsubscribe_tipc(MDS_SUBTN_REF_VAL 
subtn_ref_val);
 
+ssize_t mds_retry_sendto(int sockfd, const void *buf, size_t len, int flags,
+               const struct sockaddr *dest_addr, socklen_t addrlen);
+
 #endif  // MDS_MDS_DT_TIPC_H_
diff --git a/src/mds/mds_tipc_fctrl_portid.cc b/src/mds/mds_tipc_fctrl_portid.cc
index dab2b8c69..6b033b0e5 100644
--- a/src/mds/mds_tipc_fctrl_portid.cc
+++ b/src/mds/mds_tipc_fctrl_portid.cc
@@ -17,11 +17,14 @@
 
 #include "mds/mds_tipc_fctrl_portid.h"
 #include "base/ncssysf_def.h"
-#include "base/osaf_time.h"
 
 #include "mds/mds_dt.h"
 #include "mds/mds_log.h"
 
+extern "C" {
+#include "mds/mds_dt_tipc.h"
+}
+
 namespace mds {
 
 int max_retry_send = 100;
@@ -156,18 +159,10 @@ uint32_t TipcPortId::Send(uint8_t* data, uint16_t length) 
{
   server_addr.family = AF_TIPC;
   server_addr.addrtype = TIPC_ADDR_ID;
   server_addr.addr.id = id_;
-  int retry = 5;
-  while (retry >= 0) {
-    ssize_t send_len = sendto(bsrsock_, data, length, 0,
-          (struct sockaddr *)&server_addr, sizeof(server_addr));
-
-    if (send_len == length) {
-      return NCSCC_RC_SUCCESS;
-    } else if (retry-- > 0) {
-      assert(errno == ENOMEM || errno == ENOBUFS);
-      osaf_nanosleep(&kTenMilliseconds);
-    }
-  }
+  ssize_t send_len = mds_retry_sendto(bsrsock_, data, length, 0,
+        (struct sockaddr *)&server_addr, sizeof(server_addr));
+  if (send_len == length)
+    return NCSCC_RC_SUCCESS;
   m_MDS_LOG_ERR("FCTRL: sendto() failed, Error[%s]", strerror(errno));
   return NCSCC_RC_FAILURE;
 }
@@ -291,13 +286,15 @@ uint32_t TipcPortId::ReceiveData(uint32_t mseq, uint16_t 
mfrag,
     if (mfrag == 0) {
       // this is not fragment, the snd_type field is always present in message
       rcving_mbcast_ = false;
-      if (snd_type == MDS_SENDTYPE_BCAST || snd_type == MDS_SENDTYPE_RBCAST) {
+      if (snd_type == MDS_SENDTYPE_BCAST ||
+          snd_type == MDS_SENDTYPE_RBCAST) {
         rcving_mbcast_ = true;
       }
     } else {
       // this is fragment, the snd_type is only present in the first fragment
       if ((mfrag & 0x7fff) == 1 &&
-          (snd_type == MDS_SENDTYPE_BCAST || snd_type == MDS_SENDTYPE_RBCAST)) 
{
+          (snd_type == MDS_SENDTYPE_BCAST ||
+           snd_type == MDS_SENDTYPE_RBCAST)) {
         rcving_mbcast_ = true;
       }
     }
@@ -451,25 +448,25 @@ void TipcPortId::ReceiveChunkAck(uint16_t fseq, uint16_t 
chksize) {
       if (msg == nullptr) {
         break;
       } else {
-          if (Send(msg->msg_data_, msg->header_.msg_len_) == NCSCC_RC_SUCCESS) 
{
-            retry = 0;
-            send_msg_cnt++;
-            msg->is_sent_ = true;
-            m_MDS_LOG_NOTIFY("FCTRL: [me] --> [node:%x, ref:%u], "
-                "SndQData[fseq:%u, len:%u], "
-                "sndwnd[acked:%u, send:%u, nacked:%" PRIu64 "]",
-                id_.node, id_.ref,
-                msg->header_.fseq_, msg->header_.msg_len_,
-                sndwnd_.acked_.v(), sndwnd_.send_.v(), sndwnd_.nacked_space_);
-          } else if (send_msg_cnt == 0) {
-            // If not retry, all messages are kept in queue
-            // and no more trigger to send messages
-            retry++;
-            assert(retry < max_retry_send);
-            continue;
-          } else {
-            break;
-          }
+        if (Send(msg->msg_data_, msg->header_.msg_len_) == NCSCC_RC_SUCCESS) {
+          retry = 0;
+          send_msg_cnt++;
+          msg->is_sent_ = true;
+          m_MDS_LOG_NOTIFY("FCTRL: [me] --> [node:%x, ref:%u], "
+              "SndQData[fseq:%u, len:%u], "
+              "sndwnd[acked:%u, send:%u, nacked:%" PRIu64 "]",
+              id_.node, id_.ref,
+              msg->header_.fseq_, msg->header_.msg_len_,
+              sndwnd_.acked_.v(), sndwnd_.send_.v(), sndwnd_.nacked_space_);
+        } else if (send_msg_cnt == 0) {
+          // If not retry, all messages are kept in queue
+          // and no more trigger to send messages
+          retry++;
+          assert(retry < max_retry_send);
+          continue;
+        } else {
+          break;
+        }
       }
     }
     // no more unsent message, back to kEnabled
-- 
2.17.1



_______________________________________________
Opensaf-devel mailing list
Opensaf-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/opensaf-devel

Reply via email to