aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/adapt/nstack_dmm_adpt.c250
-rw-r--r--src/adapt/nstack_dmm_adpt.h62
-rw-r--r--src/adapt/nstack_epoll_comm.c1077
-rw-r--r--src/adapt/nstack_rd_mng.c317
-rw-r--r--src/adapt/nstack_rd_mng.h27
-rw-r--r--src/adapt/nstack_share_res.c176
-rw-r--r--src/adapt/nstack_share_res.h66
-rw-r--r--src/framework/CMakeLists.txt61
-rw-r--r--src/framework/common/base/include/common/common_func.h98
-rw-r--r--src/framework/common/base/include/common/common_mem_api.h144
-rw-r--r--src/framework/common/base/include/common/common_mem_base_type.h85
-rw-r--r--src/framework/common/base/include/common/common_mem_buf.h75
-rw-r--r--src/framework/common/base/include/common/common_mem_common.h25
-rw-r--r--src/framework/common/base/include/common/common_mem_malloc.h25
-rw-r--r--src/framework/common/base/include/common/common_mem_mbuf.h40
-rw-r--r--src/framework/common/base/include/common/common_mem_mempool.h25
-rw-r--r--src/framework/common/base/include/common/common_mem_memzone.h25
-rw-r--r--src/framework/common/base/include/common/common_mem_pal.h30
-rw-r--r--src/framework/common/base/include/common/common_mem_pal_memconfig.h26
-rw-r--r--src/framework/common/base/include/common/common_mem_spinlock.h40
-rw-r--r--src/framework/common/base/include/common/common_sys_config.h46
-rw-r--r--src/framework/common/base/include/common/generic/common_mem_rwlock.h25
-rw-r--r--src/framework/common/base/include/common_pal_bitwide_adjust.h222
-rw-r--r--src/framework/common/base/include/nsfw_base_linux_api.h58
-rw-r--r--src/framework/common/base/include/nsfw_getopt.h50
-rw-r--r--src/framework/common/base/liblinuxapi/base_linux_api_declare.h51
-rw-r--r--src/framework/common/base/liblinuxapi/nsfw_base_linux_api.c628
-rw-r--r--src/framework/common/base/liblinuxapi/nsfw_getopt.c455
-rw-r--r--src/framework/common/base/liblinuxapi/nsfw_lock_file.c174
-rw-r--r--src/framework/common/data_struct/eprb_tree.c492
-rw-r--r--src/framework/common/data_struct/list.c163
-rw-r--r--src/framework/common/data_struct/pidinfo.c125
-rw-r--r--src/framework/common/data_struct/sha256.c397
-rw-r--r--src/framework/common/include/compile_config.h30
-rw-r--r--src/framework/common/include/compiling_check.h106
-rw-r--r--src/framework/common/include/ephlist.h199
-rw-r--r--src/framework/common/include/eprb_tree.h84
-rw-r--r--src/framework/common/include/list.h181
-rw-r--r--src/framework/common/include/pidinfo.h48
-rw-r--r--src/framework/common/include/sha256.h94
-rw-r--r--src/framework/common/include/types.h97
-rw-r--r--src/framework/common/mem_mgr/include/nsfw_mem_desc.h172
-rw-r--r--src/framework/common/mem_mgr/include/nsfw_ring_data.h95
-rw-r--r--src/framework/common/mem_mgr/include/nsfw_ring_fun.h110
-rw-r--r--src/framework/common/mem_mgr/nsfw_mem_api.c879
-rw-r--r--src/framework/common/mem_mgr/nsfw_mem_construct.c21
-rw-r--r--src/framework/common/mem_mgr/nsfw_mem_desc.c92
-rw-r--r--src/framework/common/mem_mgr/nsfw_mem_stat.c292
-rw-r--r--src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mdesc.c47
-rw-r--r--src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mdesc.h22
-rw-r--r--src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mng.c544
-rw-r--r--src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mng.h70
-rw-r--r--src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_ring.c436
-rw-r--r--src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_ring.h37
-rw-r--r--src/framework/common/mem_mgr/nsfw_res_mgr.c429
-rw-r--r--src/framework/common/mem_mgr/nsfw_shmem/nsfw_rshmem_mng.c987
-rw-r--r--src/framework/common/mem_mgr/nsfw_shmem/nsfw_rshmem_mng.h51
-rw-r--r--src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mdesc.c47
-rw-r--r--src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mdesc.h22
-rw-r--r--src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mng.c880
-rw-r--r--src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mng.h133
-rw-r--r--src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_ring.c839
-rw-r--r--src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_ring.h60
-rw-r--r--src/framework/hal/hal.c865
-rw-r--r--src/framework/hal/hal.h182
-rw-r--r--src/framework/include/hal_api.h148
-rw-r--r--src/framework/include/nsfw_fd_timer_api.h64
-rw-r--r--src/framework/include/nsfw_init.h148
-rw-r--r--src/framework/include/nsfw_maintain_api.h320
-rw-r--r--src/framework/include/nsfw_mem_api.h546
-rw-r--r--src/framework/include/nsfw_mgr_com_api.h198
-rw-r--r--src/framework/include/nsfw_ps_api.h134
-rw-r--r--src/framework/include/nsfw_ps_mem_api.h36
-rw-r--r--src/framework/include/nsfw_recycle_api.h92
-rw-r--r--src/framework/include/nsfw_snapshot.h144
-rw-r--r--src/framework/include/nsfw_upgrade.h51
-rw-r--r--src/framework/include/nstack_log.h580
-rw-r--r--src/framework/include/nstack_rd_data.h80
-rw-r--r--src/framework/include/nstack_securec.h145
-rw-r--r--src/framework/include/nstack_trace.h76
-rw-r--r--src/framework/init/CMakeLists.txt24
-rw-r--r--src/framework/init/fw_init.c320
-rw-r--r--src/framework/init/fw_module.c331
-rw-r--r--src/framework/init/fw_module.h85
-rw-r--r--src/framework/ipc/mgr_com/mgr_com.c2037
-rw-r--r--src/framework/ipc/mgr_com/mgr_com.h150
-rw-r--r--src/framework/ipc/ps/nsfw_fd_timer.c378
-rw-r--r--src/framework/ipc/ps/nsfw_ps_mem_module.c924
-rw-r--r--src/framework/ipc/ps/nsfw_ps_mem_module.h87
-rw-r--r--src/framework/ipc/ps/nsfw_ps_module.c1725
-rw-r--r--src/framework/ipc/ps/nsfw_ps_module.h99
-rw-r--r--src/framework/ipc/ps/nsfw_recycle_module.c666
-rw-r--r--src/framework/ipc/ps/nsfw_recycle_module.h84
-rw-r--r--src/framework/ipc/ps/nsfw_soft_param.c296
-rw-r--r--src/framework/lib_common_mem/common_api.c325
-rw-r--r--src/framework/lib_common_mem/common_buf.c260
-rw-r--r--src/framework/lib_common_mem/common_func.c205
-rw-r--r--src/framework/log/nsfw_set_log.c228
-rw-r--r--src/framework/log/nstack_log.c825
-rw-r--r--src/framework/snapshot/fw_snapshot.c483
-rw-r--r--src/framework/snapshot/fw_ss_tlv.h47
-rw-r--r--src/framework/tracing/nstack_trace.c52
102 files changed, 26104 insertions, 0 deletions
diff --git a/src/adapt/nstack_dmm_adpt.c b/src/adapt/nstack_dmm_adpt.c
new file mode 100644
index 0000000..eea2bf1
--- /dev/null
+++ b/src/adapt/nstack_dmm_adpt.c
@@ -0,0 +1,250 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#include "nsfw_init.h"
+#include "nsfw_mem_api.h"
+#include "nsfw_recycle_api.h"
+#include "nsfw_mgr_com_api.h"
+#include "nsfw_ps_mem_api.h"
+#include "nsfw_ps_api.h"
+#include "nsfw_recycle_api.h"
+#include "nsfw_fd_timer_api.h"
+#include "nsfw_maintain_api.h"
+#include "nstack_eventpoll.h"
+#include "nstack_dmm_api.h"
+#include "nstack_dmm_adpt.h"
+#include "nstack_rd_mng.h"
+#include "mgr_com.h"
+
+int g_same_process = 1;
+
+extern int nsep_adpt_attach_memory ();
+extern int nstack_init_share_res ();
+extern int nstack_attach_share_res ();
+extern int nsep_adpt_reg_res_mgr ();
+
+/**
+ * This just for linux kernel epoll thread
+ */
+int
+nstack_event_callback (void *pdata, int events)
+{
+ nsep_epollInfo_t *epInfo = (nsep_epollInfo_t *) pdata;
+
+ if (!epInfo)
+ {
+ NSSOC_LOGWAR ("!!!!!!!err pdata=%p,get null epInfo", pdata);
+ return -1;
+ }
+#if 0
+ if (epInfo->rmidx >= 0 && epInfo->rmidx != modInx)
+ {
+ NSSOC_LOGDBG ("This fd should not issue events");
+ return -1;
+ }
+#endif
+
+ NSSOC_LOGDBG ("Got one event]fd=%d,events=%u", epInfo->fd, events);
+
+ sys_arch_lock_with_pid (&epInfo->epiLock);
+ struct list_node *fdEpiHead =
+ (struct list_node *) ADDR_SHTOL (epInfo->epiList.head);
+ struct list_node *node = (struct list_node *) ADDR_SHTOL (fdEpiHead->next);
+ struct epitem *epi = NULL;
+ struct eventpoll *ep = NULL;
+ while (node)
+ {
+
+ epi = (struct epitem *) ep_list_entry (node, struct epitem, fllink);
+
+ node = (struct list_node *) ADDR_SHTOL (node->next);
+ ep = (struct eventpoll *) ADDR_SHTOL (epi->ep);
+ if (!(epi->event.events & events))
+ continue;
+
+ /*event should not notice other process */
+ if ((ep->pid != get_sys_pid ()) && g_same_process)
+ {
+ continue;
+ }
+
+ sys_arch_lock_with_pid (&ep->lock);
+
+ if (unlikely (ep->ovflist != NSEP_EP_UNACTIVE_PTR))
+ {
+ if (epi->next == NSEP_EP_UNACTIVE_PTR)
+ {
+ epi->next = ep->ovflist;
+ ep->ovflist = (struct epitem *) ADDR_LTOSH (epi);
+ }
+ epi->ovf_revents |= events;
+ NSSOC_LOGDBG ("Add to ovflist]protoFD=%d,event=%d", epInfo->fd,
+ events);
+ goto out_unlock;
+ }
+ if (!EP_HLIST_NODE_LINKED (&epi->rdllink))
+ {
+ ep_hlist_add_tail (&ep->rdlist, &epi->rdllink);
+ sem_post (&ep->waitSem);
+ }
+ epi->revents |= events;
+ out_unlock:
+ sys_sem_s_signal (&ep->lock);
+ }
+ sys_sem_s_signal (&epInfo->epiLock);
+ /* [Remove fdInf->event_sem post] */
+ return 0;
+}
+
+int
+nstack_adpt_init (nstack_dmm_para * para)
+{
+ nsfw_mem_para stinfo = { 0 };
+ i32 init_ret = 0;
+
+ if (!para)
+ {
+ return -1;
+ }
+ stinfo.iargsnum = para->argc;
+ stinfo.pargs = para->argv;
+ stinfo.enflag = para->proc_type;
+ if (para->deploy_type >= NSTACK_MODEL_TYPE1)
+ {
+ g_same_process = 0;
+ }
+
+ nsfw_com_attr_set (para->attr.policy, para->attr.pri);
+
+ (void) nstack_framework_setModuleParam (NSFW_MEM_MGR_MODULE, &stinfo);
+ (void) nstack_framework_setModuleParam (NSFW_MGR_COM_MODULE,
+ (void *) ((u64) para->proc_type));
+ (void) nstack_framework_setModuleParam (NSFW_TIMER_MODULE,
+ (void *) ((u64) para->proc_type));
+ (void) nstack_framework_setModuleParam (NSFW_PS_MODULE,
+ (void *) ((u64) para->proc_type));
+ (void) nstack_framework_setModuleParam (NSFW_PS_MEM_MODULE,
+ (void *) ((u64) para->proc_type));
+ (void) nstack_framework_setModuleParam (NSFW_RECYCLE_MODULE,
+ (void *) ((u64) para->proc_type));
+ (void) nstack_framework_setModuleParam (NSFW_RES_MGR_MODULE,
+ (void *) ((u64) para->proc_type));
+ (void) nstack_framework_setModuleParam (NSFW_SOFT_PARAM_MODULE,
+ (void *) ((u64) para->proc_type));
+ (void) nstack_framework_setModuleParam (NSFW_LOG_CFG_MODULE,
+ (void *) ((u64) para->proc_type));
+
+ init_ret = nstack_framework_init ();
+ if (init_ret < 0)
+ {
+ NSFW_LOGERR
+ ("######################init failed!!!!######################");
+ return -1;
+ }
+
+ if ((para->proc_type != NSFW_PROC_APP)
+ && (para->proc_type != NSFW_PROC_MAIN))
+ {
+ return 0;
+ }
+
+ if (para->proc_type == NSFW_PROC_MAIN)
+ {
+ if (nstack_init_share_res () != 0)
+ {
+ NSFW_LOGERR ("nstack_init_share_res failed");
+ return -1;
+ }
+ if (nsep_create_memory () != 0)
+ {
+ NSFW_LOGERR ("nsep_create_memory failed");
+ return -1;
+ }
+
+ if (nstack_rd_mng_int (0) != 0)
+ {
+ NSFW_LOGERR ("nstack_rd_mng_int failed");
+ return -1;
+ }
+ }
+ else
+ {
+ if (nstack_attach_share_res () != 0)
+ {
+ NSFW_LOGERR ("nstack_attach_share_res failed");
+ return -1;
+ }
+
+ /**
+ * the share memory for epoll is created and usedy be app, don't clear
+ * it in fault case.
+ */
+ if (0 != nsep_adpt_attach_memory ())
+ {
+ NSFW_LOGERR ("nsep_adpt_attach_memory failed");
+ return -1;
+ }
+
+ if (nstack_rd_mng_int (1) != 0)
+ {
+ NSFW_LOGERR ("nstack_rd_mng_int failed");
+ return -1;
+ }
+ }
+
+ void *pret =
+ nsfw_recycle_reg_obj (NSFW_REC_PRO_LOWEST, NSFW_REC_NSOCKET_EPOLL,
+ NULL);
+ if (!pret)
+ {
+ NSFW_LOGERR ("regist recycle failed");
+ return -1;
+ }
+ (void) nsep_adpt_reg_res_mgr ();
+
+ return 0;
+}
+
+/*just to used to dependence by other module*/
+int
+nstack_init_module (void *para)
+{
+ return 0;
+}
+
+NSFW_MODULE_NAME (NSTACK_DMM_MODULE)
+NSFW_MODULE_PRIORITY (10)
+NSFW_MODULE_DEPENDS (NSFW_MEM_MGR_MODULE)
+NSFW_MODULE_DEPENDS (NSFW_MGR_COM_MODULE)
+NSFW_MODULE_DEPENDS (NSFW_TIMER_MODULE)
+NSFW_MODULE_DEPENDS (NSFW_PS_MODULE)
+NSFW_MODULE_DEPENDS (NSFW_PS_MEM_MODULE)
+NSFW_MODULE_DEPENDS (NSFW_RECYCLE_MODULE)
+NSFW_MODULE_DEPENDS (NSFW_LOG_CFG_MODULE)
+NSFW_MODULE_DEPENDS (NSFW_RES_MGR_MODULE)
+NSFW_MODULE_DEPENDS (NSFW_SOFT_PARAM_MODULE)
+NSFW_MODULE_INIT (nstack_init_module)
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/adapt/nstack_dmm_adpt.h b/src/adapt/nstack_dmm_adpt.h
new file mode 100644
index 0000000..e71dce3
--- /dev/null
+++ b/src/adapt/nstack_dmm_adpt.h
@@ -0,0 +1,62 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#ifndef __NSTACK_DMM_ADPT_H__
+#define __NSTACK_DMM_ADPT_H__
+
+typedef enum
+{
+ NSTACK_MODEL_TYPE1 = 1, /*nSocket and stack belong to the same process */
+ NSTACK_MODEL_TYPE2 = 2, /*nSocket and stack belong to different processes,
+ *and nStack don't take care the communication between stack and stack adpt
+ */
+ NSTACK_MODEL_TYPE3 = 3, /*nSocket and stack belong to different processes, and sbr was spplied to communicate whit stack */
+ NSTACK_MODEL_INVALID,
+} nstack_model_deploy_type;
+
+#define NSTACK_DMM_MODULE "nstack_dmm_module"
+
+typedef struct nsfw_com_attr
+{
+ int policy;
+ int pri;
+} nsfw_com_attr;
+
+typedef struct __nstack_dmm_para
+{
+ nstack_model_deploy_type deploy_type;
+ int proc_type;
+ nsfw_com_attr attr;
+ int argc;
+ char **argv;
+} nstack_dmm_para;
+
+extern int nstack_adpt_init (nstack_dmm_para * para);
+extern int nstack_event_callback (void *pdata, int events);
+
+#endif
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/adapt/nstack_epoll_comm.c b/src/adapt/nstack_epoll_comm.c
new file mode 100644
index 0000000..1f3fd02
--- /dev/null
+++ b/src/adapt/nstack_epoll_comm.c
@@ -0,0 +1,1077 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "nstack_eventpoll.h"
+#include "nsfw_mem_api.h"
+#include "nstack_log.h"
+#include "nstack_securec.h"
+#include "nsfw_recycle_api.h"
+#include "nsfw_maintain_api.h"
+#include <stdio.h>
+#include <stdlib.h>
+
+nsep_epollManager_t g_epollMng = {
+ .infoSockMap = NULL,
+};
+
+/*
+ * This function will find the epitem of fd in eventpool ep
+ * This is only used in epoll_ctl add
+ */
+struct epitem *
+nsep_find_ep (struct eventpoll *ep, int fd)
+{
+ struct ep_rb_node *rbp;
+ struct epitem *epi, *epir = NULL;
+ u32_t loopCnt = 0;
+ for (rbp = ADDR_SHTOL (ep->rbr.rb_node); rbp;)
+ {
+ ++loopCnt;
+ if (loopCnt > NSTACK_MAX_EPITEM_NUM)
+ break;
+
+ epi = (struct epitem *) ep_rb_entry (rbp, struct epitem, rbn);
+ if (fd > epi->fd)
+ {
+ rbp = (struct ep_rb_node *) ADDR_SHTOL (rbp->rb_right);
+ }
+ else if (fd < epi->fd)
+ {
+ rbp = (struct ep_rb_node *) ADDR_SHTOL (rbp->rb_left);
+ }
+ else
+ {
+ epir = epi;
+ break;
+ }
+ }
+
+ if (loopCnt > NSTACK_MAX_EPITEM_NUM)
+ {
+ NSSOC_LOGERR ("Loop out of range!!!!");
+ }
+
+ return epir;
+}
+
+int
+nstack_ep_unlink (struct eventpoll *ep, struct epitem *epi)
+{
+ int error = ENOENT;
+
+ if (ep_rb_parent (&epi->rbn) ==
+ (struct ep_rb_node *) ADDR_LTOSH_EXT (&epi->rbn))
+ {
+ NSSOC_LOGWAR ("ep_rb_parent == epi->rbn");
+ return error;
+ }
+
+ epi->event.events = 0;
+
+ ep_rb_erase (&epi->rbn, &ep->rbr);
+ ep_rb_set_parent (&epi->rbn, &epi->rbn);
+
+ if (EP_HLIST_NODE_LINKED (&epi->rdllink))
+ {
+ ep_hlist_del (&ep->rdlist, &epi->rdllink);
+ }
+
+ return 0;
+}
+
+/**
+ * @Function nsep_free_epitem
+ * @Description free nstack epitem
+ * @param in data - the epitem to be free
+ * @return 0 on success, -1 on error
+ */
+int
+nsep_free_epitem (struct epitem *data)
+{
+ struct epitem *epiEntry = (struct epitem *) data;
+ struct epitem_pool *pool = &nsep_getManager ()->epitemPool;
+ epiEntry->pid = 0;
+ NSSOC_LOGDBG ("nsep_free_epitem data:%p", data);
+ if (res_free (&epiEntry->res_chk))
+ {
+ NSFW_LOGERR ("epitem refree!]epitem=%p", epiEntry);
+ return 0;
+ }
+
+ if (nsfw_mem_ring_enqueue (pool->ring, (void *) epiEntry) != 1)
+ {
+ NSSOC_LOGERR ("Error to free epitem");
+ }
+ return 0;
+}
+
+NSTACK_STATIC void
+nsep_initEpInfo (nsep_epollInfo_t * info)
+{
+ int iindex = 0;
+ EP_LIST_INIT (&info->epiList);
+ NSTACK_SEM_MALLOC (info->epiLock, 1);
+ NSTACK_SEM_MALLOC (info->freeLock, 1);
+
+ info->rlfd = -1;
+ info->rmidx = -1;
+ info->fd = -1;
+ info->ep = NULL;
+ info->fdtype = 0;
+ info->private_data = NULL;
+ info->epaddflag = 0;
+ for (iindex = 0; iindex < NSEP_SMOD_MAX; iindex++)
+ {
+ info->protoFD[iindex] = -1;
+ }
+ (void) nsep_for_pidinfo_init (&(info->pidinfo));
+}
+
+NSTACK_STATIC void
+nsep_destroy_epinfo (nsep_epollInfo_t * info)
+{
+ // TODO: Here we need to free the semaphore
+ return;
+}
+
+/**
+ * @Function nstack_eventpoll_allocShareInfo
+ * @Description alloc nstack share info
+ * @param out data - the return value alloced
+ * @return 0 on success, -1 on error
+ */
+int
+nsep_alloc_epinfo (nsep_epollInfo_t ** data)
+{
+ nsep_epollInfo_t *head_info = NULL;
+
+ if (NULL == data)
+ return -1;
+ NSSOC_LOGDBG ("epinfo alloc begin");
+
+ nsep_infoPool_t *pool = &nsep_getManager ()->infoPool;
+ if (0 == nsfw_mem_ring_dequeue (pool->ring, (void *) &head_info)
+ || NULL == head_info)
+ {
+ NSSOC_LOGERR ("epinfo ring alloc failed]pool->ring=%p", pool->ring);
+ return -1;
+ }
+
+ res_alloc (&head_info->res_chk);
+
+ nsep_initEpInfo (head_info);
+ if (0 != nsep_add_pid (&head_info->pidinfo, get_sys_pid ()))
+ {
+ NSSOC_LOGERR ("epinfo pid add to headinfo failed]pid=%d,headinfo=%p",
+ get_sys_pid (), head_info);
+ }
+ NSSOC_LOGDBG ("epinfo ring:%p alloc epinfo:%p end", pool->ring, head_info);
+ *data = head_info;
+ return 0;
+}
+
+/**
+ * @Function nstack_eventpoll_freeShareInfo
+ * @Description free nstack share info
+ * @param in info - the info to be free
+ * @return 0 on success, -1 on error
+ */
+int
+nsep_free_epinfo (nsep_epollInfo_t * info)
+{
+
+ if (NULL == info)
+ return -1;
+
+ nsep_infoPool_t *pool = &nsep_getManager ()->infoPool;
+ NSSOC_LOGDBG ("nsep_free_epinfo info:%p, pool->ring:%p", info, pool->ring);
+ nsep_destroy_epinfo (info);
+
+ (void) nsep_for_pidinfo_init (&(info->pidinfo));
+ if (res_free (&info->res_chk))
+ {
+ NSFW_LOGERR ("epinfo refree!]epitem=%p", info);
+ return 0;
+ }
+
+ if (nsfw_mem_ring_enqueue (pool->ring, (void *) info) != 1)
+ {
+ NSSOC_LOGERR ("Errot to free epinfo");
+ }
+
+ return 0;
+}
+
+int
+nsep_force_epinfo_free (void *data)
+{
+ nsep_epollInfo_t *info = data;
+ if (NULL == info)
+ {
+ return FALSE;
+ }
+
+ if (!nsep_is_pid_array_empty (&info->pidinfo))
+ {
+ return FALSE;
+ }
+
+ res_alloc (&info->res_chk);
+ (void) nsep_free_epinfo (info);
+ NSFW_LOGINF ("free epinfo]%p", data);
+ return TRUE;
+}
+
+int
+nsep_force_epitem_free (void *data)
+{
+ struct epitem *item = data;
+ if (NULL == item)
+ {
+ return FALSE;
+ }
+
+ if (0 != item->pid)
+ {
+ return FALSE;
+ }
+
+ res_alloc (&item->res_chk);
+ (void) nsep_free_epitem (item);
+ NSFW_LOGINF ("free epitem]%p", data);
+ return TRUE;
+}
+
+int
+nsep_force_epevent_free (void *data)
+{
+ struct eventpoll *epevent = data;
+ if (NULL == epevent)
+ {
+ return FALSE;
+ }
+
+ if (0 != epevent->pid)
+ {
+ return FALSE;
+ }
+
+ res_alloc (&epevent->res_chk);
+ (void) nsep_free_eventpoll (epevent);
+ NSFW_LOGINF ("free event pool]%p", data);
+ return TRUE;
+}
+
+NSTACK_STATIC int
+nsep_init_eventpoll (struct eventpoll *ep)
+{
+ if (0 != sem_init (&ep->waitSem, 1, 0))
+ {
+ return -1;
+ }
+
+ NSTACK_SEM_MALLOC (ep->lock, 1);
+ NSTACK_SEM_MALLOC (ep->sem, 1);
+
+ EP_HLIST_INIT (&ep->rdlist);
+ ep->ovflist = NSEP_EP_UNACTIVE_PTR;
+ ep->rbr.rb_node = NULL;
+ ep->epfd = -1;
+ return 0;
+}
+
+NSTACK_STATIC void
+nsep_destroy_eventpoll (struct eventpoll *ep)
+{
+ (void) sem_destroy (&ep->waitSem);
+}
+
+/**
+ * @Function nsep_free_eventpoll
+ * @Description free nstack eventpoll
+ * @param in ep - the eventpoll to be free
+ * @return 0 on success, -1 on error
+ */
+int
+nsep_free_eventpoll (struct eventpoll *ep)
+{
+ if (!ep)
+ return -1;
+ struct eventpoll *epEntry = (struct eventpoll *) ep;
+ struct eventpoll_pool *pool = &nsep_getManager ()->epollPool;
+ NSSOC_LOGDBG ("nsep_free_eventpoll ep:%p, epollPool:%p", ep, pool);
+ nsep_destroy_eventpoll (ep);
+ ep->pid = 0;
+ NSSOC_LOGDBG ("Free eventpool");
+ if (res_free (&ep->res_chk))
+ {
+ NSFW_LOGERR ("ep refree!]epitem=%p", epEntry);
+ return 0;
+ }
+
+ if (nsfw_mem_ring_enqueue (pool->ring, epEntry) != 1)
+ {
+ NSSOC_LOGERR ("Errot to free eventpoll");
+ }
+
+ return 0;
+}
+
+/**
+ * @Function nsep_alloc_eventpoll
+ * @Description alloc nstack eventpoll
+ * @param out data - the eventpoll alloced
+ * @return 0 on success, -1 on error
+ */
+int
+nsep_alloc_eventpoll (struct eventpoll **data)
+{
+ struct eventpoll *p_head = NULL;
+ struct eventpoll_pool *pool = &nsep_getManager ()->epollPool;
+
+ NSSOC_LOGDBG ("ring:%p alloc eventpool begin", pool->ring);
+ if (0 == nsfw_mem_ring_dequeue (pool->ring, (void *) &p_head)
+ || NULL == p_head)
+ {
+ NSSOC_LOGERR ("ring alloc eventpool failed]ring=%p", pool->ring);
+ return -1;
+ }
+
+ NSSOC_LOGDBG ("alloc eventpool, pid=%u", get_sys_pid ());
+ res_alloc (&p_head->res_chk);
+ p_head->pid = get_sys_pid ();
+
+ if (0 != nsep_init_eventpoll ((struct eventpoll *) p_head))
+ {
+ NSSOC_LOGERR ("p_head init pid alloc failed]p_head=%p,pid=%d", p_head,
+ get_sys_pid ());
+ (void) nsep_free_eventpoll ((struct eventpoll *) p_head);
+ return -1;
+ }
+
+ NSSOC_LOGDBG ("ring:%p eventpoll:%p alloc eventpool end", pool->ring,
+ p_head);
+ *data = p_head;
+ return 0;
+}
+
+NSTACK_STATIC int
+nsep_init_epitem (struct epitem *epi)
+{
+ int retVal;
+ epi->rbn.rb_parent = (struct ep_rb_node *) ADDR_LTOSH_EXT (&epi->rbn);
+ EP_HLIST_INIT_NODE (&epi->rdllink);
+ EP_HLIST_INIT_NODE (&epi->lkFDllink);
+ epi->nwait = 0;
+ epi->ep = NULL;
+ epi->next = NSEP_EP_UNACTIVE_PTR;
+ retVal =
+ MEMSET_S (&epi->event, sizeof (epi->event), 0, sizeof (epi->event));
+ if (EOK != retVal)
+ {
+ NSSOC_LOGERR ("MEMSET_S failed]ret=%d", retVal);
+ return -1;
+ }
+
+ EP_LIST_INIT_NODE (&epi->fllink);
+ epi->revents = 0;
+ epi->ovf_revents = 0;
+ epi->fd = -1;
+ epi->private_data = NULL;
+
+ return 0;
+}
+
+/**
+ * @Function nsep_alloc_epitem
+ * @Description alloc nstack epitem
+ * @param out data - the epitem alloced
+ * @return 0 on success, -1 on error
+ */
+int
+nsep_alloc_epitem (struct epitem **data)
+{
+ struct epitem *p_head_entry = NULL;
+ struct epitem_pool *pool = &nsep_getManager ()->epitemPool;
+
+ NSSOC_LOGDBG ("epitem alloc begin..");
+
+ if (0 == nsfw_mem_ring_dequeue (pool->ring, (void *) &p_head_entry)
+ || NULL == p_head_entry)
+ {
+ NSSOC_LOGERR ("epitem ring alloc failed]ring=%p", pool->ring);
+ return -1;
+ }
+
+ res_alloc (&p_head_entry->res_chk);
+ p_head_entry->pid = get_sys_pid ();
+
+ if (nsep_init_epitem ((struct epitem *) p_head_entry))
+ {
+ (void) nsep_free_epitem ((struct epitem *) p_head_entry);
+ p_head_entry = NULL;
+ NSSOC_LOGERR ("ring epitem init failed]ring=%p,epitem=%p", pool->ring,
+ p_head_entry);
+ return -1;
+ }
+
+ NSSOC_LOGDBG ("epitem alloc success..ring:%p head:%p", pool->ring,
+ p_head_entry);
+ *data = p_head_entry;
+ return 0;
+}
+
+typedef int (*nsep_shem_initFn_t) (void *, size_t);
+
+NSTACK_STATIC int
+nsep_epPoolInit (void *addr, size_t lenth)
+{
+ u32_t pos;
+ int ret;
+
+ NSSOC_LOGDBG ("Start to init eventpoll pool");
+
+ ret = MEMSET_S (addr, lenth, 0, lenth);
+ if (EOK != ret)
+ {
+ NSSOC_LOGERR ("MEMSET_S failed]ret=%d", ret);
+ return -1;
+ }
+ struct eventpoll *pool = (struct eventpoll *) addr;
+ nsep_epollManager_t *manager = nsep_getManager ();
+ manager->epollPool.pool = pool;
+
+ /* init g_nStackInfo.sockPool->nstack_block_array */
+ for (pos = 0; pos < NSTACK_MAX_EPOLL_INFO_NUM; pos++)
+ {
+ pool[pos].pid = 0;
+ if (-1 == nsfw_mem_ring_enqueue (manager->epollPool.ring, &pool[pos]))
+ {
+ NSSOC_LOGERR ("init fail to enqueue epitem]pos=%u", pos);
+ return -1;
+ }
+ }
+ return 0;
+}
+
+NSTACK_STATIC int
+nsep_epitemPoolInit (void *addr, size_t lenth)
+{
+ u32_t pos;
+ int ret;
+
+ NSSOC_LOGDBG ("Start to init epitem pool");
+
+ ret = MEMSET_S (addr, lenth, 0, lenth);
+ if (EOK != ret)
+ {
+ NSSOC_LOGERR ("MEMSET_S failed]ret=%d", ret);
+ return -1;
+ }
+ struct epitem *pool = (struct epitem *) addr;
+ nsep_epollManager_t *manager = nsep_getManager ();
+ manager->epitemPool.pool = pool;
+
+ /* init g_nStackInfo.sockPool->nstack_block_array */
+ for (pos = 0; pos < NSTACK_MAX_EPITEM_NUM; pos++)
+ {
+ pool[pos].pid = 0;
+ if (-1 == nsfw_mem_ring_enqueue (manager->epitemPool.ring, &pool[pos]))
+ {
+ NSSOC_LOGERR ("init fail to enqueue epitem]pos=%u", pos);
+ return -1;
+ }
+ }
+ return 0;
+}
+
+NSTACK_STATIC int
+nsep_epInfoPoolInit (void *addr, size_t lenth)
+{
+ u32_t pos;
+ int ret;
+
+ NSSOC_LOGDBG ("shmem info init start");
+
+ ret = MEMSET_S (addr, lenth, 0, lenth);
+ if (EOK != ret)
+ {
+ NSSOC_LOGERR ("MEMSET_S failed]ret=%d", ret);
+ return -1;
+ }
+ nsep_epollInfo_t *pool = (nsep_epollInfo_t *) addr;
+ nsep_epollManager_t *manager = nsep_getManager ();
+ manager->infoPool.pool = pool;
+
+ /* init g_nStackInfo.sockPool->nstack_block_array */
+ for (pos = 0; pos < NSTACK_MAX_EPOLL_INFO_NUM; pos++)
+ {
+ if (nsep_for_pidinfo_init (&(pool[pos].pidinfo)))
+ {
+ NSSOC_LOGERR ("pid info init failed]pos=%u", pos);
+ return -1;
+ }
+
+ if (-1 == nsfw_mem_ring_enqueue (manager->infoPool.ring, &pool[pos]))
+ {
+ NSSOC_LOGERR ("init fail to enqueue epInfo]pos=%u", pos);
+ return -1;
+ }
+ }
+
+ NSSOC_LOGDBG ("nstack_shmen_info_init success");
+ return 0;
+}
+
+NSTACK_STATIC int
+nsep_create_shmem (size_t length, char *name, nsep_shem_initFn_t initFn)
+{
+ nsfw_mem_zone pmeminfo;
+ mzone_handle phandle;
+ int ret;
+
+ pmeminfo.ireserv = 0;
+ pmeminfo.isocket_id = NSFW_SOCKET_ANY;
+ pmeminfo.lenth = length;
+ ret =
+ STRCPY_S (pmeminfo.stname.aname, sizeof (pmeminfo.stname.aname), name);
+ if (EOK != ret)
+ {
+ NSSOC_LOGERR ("STRCPY_S failed]name=%s,ret=%d", name, ret);
+ return -1;
+ }
+ pmeminfo.stname.entype = NSFW_SHMEM;
+
+ phandle = nsfw_mem_zone_create (&pmeminfo);
+ if (NULL == phandle)
+ {
+ NSSOC_LOGERR ("create nstack epoll memory failed]name=%s", name);
+ return -1;
+ }
+
+ if (0 != initFn ((void *) phandle, length))
+ {
+ NSSOC_LOGERR ("Fail to init memory]name=%s", name);
+ return -1;
+ }
+
+ return 0;
+}
+
+NSTACK_STATIC int
+nsep_create_epInfoMem ()
+{
+ nsfw_mem_mring pringinfo;
+ pringinfo.enmptype = NSFW_MRING_MPMC;
+ pringinfo.isocket_id = NSFW_SOCKET_ANY;
+ pringinfo.stname.entype = NSFW_SHMEM;
+ pringinfo.usnum = NSTACK_MAX_EPOLL_INFO_NUM;
+
+ if (-1 ==
+ SPRINTF_S (pringinfo.stname.aname, NSFW_MEM_NAME_LENTH, "%s",
+ MP_NSTACK_EPINFO_RING_NAME))
+ {
+ NSSOC_LOGERR ("Error to create ring]name=%s", pringinfo.stname.aname);
+ return -1;
+ }
+
+ mring_handle ring_handle = nsfw_mem_ring_create (&pringinfo);
+
+ if (NULL == ring_handle)
+ {
+ NSSOC_LOGERR ("Error to create ring]name=%s", pringinfo.stname.aname);
+ return -1;
+ }
+
+ nsep_epollManager_t *manager = nsep_getManager ();
+ manager->infoPool.ring = ring_handle;
+
+ return nsep_create_shmem (sizeof (nsep_epollInfo_t) *
+ NSTACK_MAX_EPOLL_INFO_NUM,
+ MP_NSTACK_EPOLL_INFO_NAME, nsep_epInfoPoolInit);
+}
+
+NSTACK_STATIC int
+nsep_adpt_attach_epInfoMem ()
+{
+ nsfw_mem_name name;
+ name.entype = NSFW_SHMEM;
+ name.enowner = NSFW_PROC_MAIN;
+
+ if (-1 ==
+ SPRINTF_S (name.aname, NSFW_MEM_NAME_LENTH, "%s",
+ MP_NSTACK_EPINFO_RING_NAME))
+ {
+ NSSOC_LOGERR ("Error to attach ring]name=%s", name.aname);
+ return -1;
+ }
+ mring_handle ring_handle = nsfw_mem_ring_lookup (&name);
+
+ if (NULL == ring_handle)
+ {
+ NSSOC_LOGERR ("Error to attach ring]name=%s", name.aname);
+ return -1;
+ }
+
+ nsep_epollManager_t *manager = nsep_getManager ();
+ manager->infoPool.ring = ring_handle;
+
+ if (-1 ==
+ SPRINTF_S (name.aname, NSFW_MEM_NAME_LENTH, "%s",
+ MP_NSTACK_EPOLL_INFO_NAME))
+ {
+ NSSOC_LOGERR ("SPRINTF_S failed]");
+ return -1;
+ }
+ manager->infoPool.pool = nsfw_mem_zone_lookup (&name);
+ if (NULL == manager->infoPool.pool)
+ {
+ NSSOC_LOGERR ("Error to attach memzone]name=%s",
+ MP_NSTACK_EPOLL_INFO_NAME);
+ return -1;
+ }
+ return 0;
+}
+
+NSTACK_STATIC int
+nsep_create_epItemMem ()
+{
+ nsfw_mem_mring pringinfo;
+ pringinfo.enmptype = NSFW_MRING_MPMC;
+ pringinfo.isocket_id = NSFW_SOCKET_ANY;
+ pringinfo.stname.entype = NSFW_SHMEM;
+ pringinfo.usnum = NSTACK_MAX_EPITEM_NUM;
+
+ if (-1 ==
+ SPRINTF_S (pringinfo.stname.aname, NSFW_MEM_NAME_LENTH, "%s",
+ MP_NSTACK_EPITEM_RING_NAME))
+ {
+ NSSOC_LOGERR ("Error to create ring]name=%s", pringinfo.stname.aname);
+ return -1;
+ }
+
+ mring_handle ring_handle = nsfw_mem_ring_create (&pringinfo);
+
+ if (NULL == ring_handle)
+ {
+ NSSOC_LOGERR ("Error to create ring]name=%s", pringinfo.stname.aname);
+ return -1;
+ }
+
+ nsep_epollManager_t *manager = nsep_getManager ();
+ manager->epitemPool.ring = ring_handle;
+
+ return nsep_create_shmem (sizeof (struct epitem) * NSTACK_MAX_EPITEM_NUM,
+ MP_NSTACK_EPITEM_POOL, nsep_epitemPoolInit);
+}
+
+NSTACK_STATIC int
+nsep_adpt_attach_epItemMem ()
+{
+ nsfw_mem_name name;
+ name.entype = NSFW_SHMEM;
+ name.enowner = NSFW_PROC_MAIN;
+
+ if (-1 ==
+ SPRINTF_S (name.aname, NSFW_MEM_NAME_LENTH, "%s",
+ MP_NSTACK_EPITEM_RING_NAME))
+ {
+ NSSOC_LOGERR ("Error to attach epItemMem]name=%s", name.aname);
+ return -1;
+ }
+
+ mring_handle ring_handle = nsfw_mem_ring_lookup (&name);
+
+ if (NULL == ring_handle)
+ {
+ NSSOC_LOGERR ("Error to attach ring]name=%s", name.aname);
+ return -1;
+ }
+
+ nsep_epollManager_t *manager = nsep_getManager ();
+ manager->epitemPool.ring = ring_handle;
+
+ if (-1 ==
+ SPRINTF_S (name.aname, NSFW_MEM_NAME_LENTH, "%s",
+ MP_NSTACK_EPITEM_POOL))
+ {
+ NSSOC_LOGERR ("SPRINTF_S failed]");
+ return -1;
+ }
+ manager->epitemPool.pool = nsfw_mem_zone_lookup (&name);
+ if (NULL == manager->epitemPool.pool)
+ {
+ NSSOC_LOGERR ("Error to attach memzone]name=%s", MP_NSTACK_EPITEM_POOL);
+ return -1;
+ }
+ return 0;
+}
+
+NSTACK_STATIC int
+nsep_create_eventpollMem ()
+{
+ nsfw_mem_mring pringinfo;
+ pringinfo.enmptype = NSFW_MRING_MPMC;
+ pringinfo.isocket_id = NSFW_SOCKET_ANY;
+ pringinfo.stname.entype = NSFW_SHMEM;
+ pringinfo.usnum = NSTACK_MAX_EPOLL_NUM;
+
+ if (-1 ==
+ SPRINTF_S (pringinfo.stname.aname, NSFW_MEM_NAME_LENTH, "%s",
+ MP_NSTACK_EVENTPOOL_RING_NAME))
+ {
+ NSSOC_LOGERR ("Error to create ring]name=%s", pringinfo.stname.aname);
+ return -1;
+ }
+
+ mring_handle ring_handle = nsfw_mem_ring_create (&pringinfo);
+
+ if (NULL == ring_handle)
+ {
+ NSSOC_LOGERR ("Error to create ring]name=%s", pringinfo.stname.aname);
+ return -1;
+ }
+
+ nsep_epollManager_t *manager = nsep_getManager ();
+ manager->epollPool.ring = ring_handle;
+
+ return nsep_create_shmem (sizeof (struct eventpoll) * NSTACK_MAX_EPOLL_NUM,
+ MP_NSTACK_EVENTPOLL_POOL, nsep_epPoolInit);
+}
+
+NSTACK_STATIC int
+nsep_adpt_attach_eventpollMem ()
+{
+ nsfw_mem_name name;
+ name.entype = NSFW_SHMEM;
+ name.enowner = NSFW_PROC_MAIN;
+
+ if (-1 ==
+ SPRINTF_S (name.aname, NSFW_MEM_NAME_LENTH, "%s",
+ MP_NSTACK_EVENTPOOL_RING_NAME))
+ {
+ NSSOC_LOGERR ("Error to attach ring]name=%s", name.aname);
+ return -1;
+ }
+
+ mring_handle ring_handle = nsfw_mem_ring_lookup (&name);
+
+ if (NULL == ring_handle)
+ {
+ NSSOC_LOGERR ("Error to create ring]name=%s", name.aname);
+ return -1;
+ }
+
+ nsep_epollManager_t *manager = nsep_getManager ();
+ manager->epollPool.ring = ring_handle;
+
+ int retVal = SPRINTF_S (name.aname, NSFW_MEM_NAME_LENTH, "%s",
+ MP_NSTACK_EVENTPOLL_POOL);
+ if (-1 == retVal)
+ {
+ NSSOC_LOGERR ("SPRINTF_S faild]ret=%d", retVal);
+ return -1;
+ }
+ manager->epollPool.pool = nsfw_mem_zone_lookup (&name);
+ if (NULL == manager->epollPool.pool)
+ {
+ NSSOC_LOGERR ("Error to attach memzone]name=%s",
+ MP_NSTACK_EVENTPOLL_POOL);
+ return -1;
+ }
+
+ return 0;
+}
+
+int
+nsep_create_memory ()
+{
+ typedef int (*nsep_createMemFunc_t) (void);
+ nsep_createMemFunc_t createFuncs[] = { nsep_create_epInfoMem,
+ nsep_create_epItemMem,
+ nsep_create_eventpollMem
+ };
+
+ int i = 0;
+ for (i = 0;
+ i < (int) (sizeof (createFuncs) / sizeof (nsep_createMemFunc_t)); i++)
+ {
+ if (-1 == createFuncs[i] ())
+ return -1;
+ }
+
+ return 0;
+}
+
+int
+nsep_adpt_attach_memory ()
+{
+ typedef int (*nsep_attachMemFunc_t) (void);
+ nsep_attachMemFunc_t attachFuncs[] = { nsep_adpt_attach_epInfoMem,
+ nsep_adpt_attach_epItemMem,
+ nsep_adpt_attach_eventpollMem
+ };
+
+ int i = 0;
+ for (i = 0;
+ i < (int) (sizeof (attachFuncs) / sizeof (nsep_attachMemFunc_t)); i++)
+ {
+ if (-1 == attachFuncs[i] ())
+ {
+ NSSOC_LOGERR ("mem attach fail]idx=%d", i);
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+int
+nsep_adpt_reg_res_mgr ()
+{
+
+ nsep_epollManager_t *manager = nsep_getManager ();
+
+ nsfw_res_scn_cfg scn_cfg_info = { NSFW_RES_SCAN_ARRAY, 90, 3, 16,
+ NSTACK_MAX_EPOLL_INFO_NUM / 128, NSTACK_MAX_EPOLL_INFO_NUM,
+ sizeof (nsep_epollInfo_t),
+ offsetof (nsep_epollInfo_t, res_chk),
+ manager->infoPool.pool,
+ manager->infoPool.ring,
+ nsep_force_epinfo_free
+ };
+
+ nsfw_res_scn_cfg scn_cfg_item = { NSFW_RES_SCAN_ARRAY, 90, 3, 16,
+ NSTACK_MAX_EPITEM_NUM / 128, NSTACK_MAX_EPITEM_NUM,
+ sizeof (struct epitem),
+ offsetof (struct epitem, res_chk),
+ manager->epitemPool.pool,
+ manager->epitemPool.ring,
+ nsep_force_epitem_free
+ };
+
+ nsfw_res_scn_cfg scn_cfg_event = { NSFW_RES_SCAN_ARRAY, 90, 3, 16,
+ NSTACK_MAX_EPOLL_NUM / 128, NSTACK_MAX_EPOLL_NUM,
+ sizeof (struct eventpoll),
+ offsetof (struct eventpoll, res_chk),
+ manager->epollPool.pool,
+ manager->epollPool.ring,
+ nsep_force_epevent_free
+ };
+
+ (void) nsfw_res_mgr_reg (&scn_cfg_info);
+ (void) nsfw_res_mgr_reg (&scn_cfg_item);
+ (void) nsfw_res_mgr_reg (&scn_cfg_event);
+ return 0;
+}
+
+int
+nsep_epitem_remove (nsep_epollInfo_t * pinfo, u32 pid)
+{
+ struct list_node *prenode = NULL;
+ struct list_node *nextnode = NULL;
+ struct epitem *epi = NULL;
+ u32_t i = 0;
+ int icnt = 0;
+ (void) sys_arch_lock_with_pid (&pinfo->epiLock);
+ /*list head must be not null */
+ prenode = (struct list_node *) ADDR_SHTOL (pinfo->epiList.head);
+ nextnode = (struct list_node *) ADDR_SHTOL (prenode->next);
+ while ((nextnode) && (i++ <= NSTACK_MAX_EPOLL_INFO_NUM))
+ {
+ epi = ep_list_entry (nextnode, struct epitem, fllink);
+ if (pid == epi->pid)
+ {
+ /*shmem equal to shmem */
+ prenode->next = nextnode->next;
+ nextnode->next = NULL;
+ (void) nsep_free_epitem (epi);
+ nextnode = ADDR_SHTOL (prenode->next);
+ icnt++;
+ continue;
+ }
+ prenode = nextnode;
+ nextnode = ADDR_SHTOL (nextnode->next);
+ }
+ sys_sem_s_signal (&pinfo->epiLock);
+ if (i >= NSTACK_MAX_EPOLL_INFO_NUM)
+ {
+ NSSOC_LOGERR ("free pinfo:%p pid:%u, error maybe happen", pinfo, pid);
+ }
+ return icnt;
+}
+
+void
+nsep_recycle_epfd (void *epinfo, u32 pid)
+{
+ struct eventpoll *ep = NULL;
+ nsep_epollInfo_t *info = (nsep_epollInfo_t *) epinfo;
+ int ret = 0;
+ int ileftcnt = 0;
+ if (!epinfo)
+ {
+ NSSOC_LOGDBG ("input null, pid:%u", pid);
+ return;
+ }
+ (void) sys_arch_lock_with_pid (&info->freeLock);
+ ileftcnt = nsep_del_last_pid (&info->pidinfo, pid);
+ sys_sem_s_signal (&info->freeLock);
+ /*no pid exist */
+ if (-1 == ileftcnt)
+ {
+ return;
+ }
+ if (NSTACK_EPOL_FD == info->fdtype)
+ {
+ NSSOC_LOGDBG ("recycle epfd:%d epinfo pid:%u begin...", info->fd, pid);
+ if (0 == ileftcnt)
+ {
+ ep = ADDR_SHTOL (info->ep);
+ info->ep = NULL;
+ (void) nsep_free_eventpoll (ep);
+ (void) nsep_free_epinfo (info);
+ }
+ return;
+ }
+
+ NSSOC_LOGDBG ("recycle fd:%d epinfo pid:%u begin...", info->fd, pid);
+
+ ret = nsep_epitem_remove (info, pid);
+ if (0 != ret)
+ {
+ NSSOC_LOGINF ("info:%p, fd:%d pid:%u, %d items was left", info,
+ info->fd, pid, ret);
+ }
+
+ if (0 == ileftcnt)
+ {
+ NSSOC_LOGINF ("info:%p, fd:%d pid:%u was finally freed", info, info->fd,
+ pid);
+ (void) nsep_free_epinfo (info);
+ }
+ return;
+}
+
+int
+nsep_recyle_ep (u32 pid)
+{
+ nsep_epollManager_t *manager = nsep_getManager ();
+ nsep_epollInfo_t *pool = manager->infoPool.pool;
+
+ u32_t pos;
+ for (pos = 0; pos < NSTACK_MAX_EPOLL_INFO_NUM; pos++)
+ {
+ (void) nsep_recycle_epfd (&pool[pos], pid);
+ }
+ return 0;
+}
+
+NSTACK_STATIC int
+nsep_recyle_epItem (u32 pid)
+{
+ nsep_epollManager_t *manager = nsep_getManager ();
+ struct epitem *pool = manager->epitemPool.pool;
+
+ u32_t pos;
+ for (pos = 0; pos < NSTACK_MAX_EPITEM_NUM; pos++)
+ {
+ if (pool[pos].pid != pid)
+ continue;
+
+ if (-1 == nsep_free_epitem (&pool[pos]))
+ return -1;
+ }
+
+ return 0;
+}
+
+NSTACK_STATIC int
+nsep_recyle_eventpoll (u32 pid)
+{
+ nsep_epollManager_t *manager = nsep_getManager ();
+ struct eventpoll *pool = manager->epollPool.pool;
+
+ u32_t pos;
+ for (pos = 0; pos < NSTACK_MAX_EPOLL_INFO_NUM; pos++)
+ {
+ if (pool[pos].pid != pid)
+ continue;
+
+ if (-1 == nsep_free_eventpoll (&pool[pos]))
+ return -1;
+ }
+
+ return 0;
+}
+
+NSTACK_STATIC
+ nsfw_rcc_stat nsep_recycle_resource (u32 exit_pid, void *pdata,
+ u16 rec_type)
+{
+ NSSOC_LOGINF ("pid:%u recycle", exit_pid);
+ (void) nsep_recyle_epItem (exit_pid);
+ (void) nsep_recyle_eventpoll (exit_pid);
+ return NSFW_RCC_CONTINUE;
+}
+
+NSTACK_STATIC
+ nsfw_rcc_stat nsep_recyle_lock (u32 pid, void *pdata, u16 rec_type)
+{
+ nsep_epollManager_t *manager = nsep_getManager ();
+ nsep_epollInfo_t *pool = manager->infoPool.pool;
+ u32_t pos;
+ if (NULL != pool)
+ {
+ for (pos = 0; pos < NSTACK_MAX_EPOLL_INFO_NUM; pos++)
+ {
+ if (pid == pool[pos].epiLock.locked)
+ {
+ pool[pos].epiLock.locked = 0;
+ NSFW_LOGWAR ("epiLock locked]pos=%u,pid=%u", pos, pid);
+ }
+ if (pid == pool[pos].freeLock.locked)
+ {
+ pool[pos].freeLock.locked = 0;
+ NSFW_LOGWAR ("freelock locked]pos=%u,pid=%u", pos, pid);
+ }
+ }
+ }
+
+ struct eventpoll *ev_pool = manager->epollPool.pool;
+ if (NULL != ev_pool)
+ {
+ for (pos = 0; pos < NSTACK_MAX_EPOLL_NUM; pos++)
+ {
+ if (pid == ev_pool[pos].lock.locked)
+ {
+ ev_pool[pos].lock.locked = 0;
+ NSFW_LOGWAR ("event_pollLock locked]pos=%u,pid=%u", pos, pid);
+ }
+
+ if (pid == ev_pool[pos].sem.locked)
+ {
+ ev_pool[pos].sem.locked = 0;
+ NSFW_LOGWAR ("event_pollLock sem]pos=%u,pid=%u", pos, pid);
+ }
+ }
+ }
+
+ return NSFW_RCC_CONTINUE;
+}
+
+REGIST_RECYCLE_OBJ_FUN (NSFW_REC_NSOCKET_EPOLL,
+ nsep_recycle_resource)
+REGIST_RECYCLE_LOCK_REL (nsep_recyle_lock, NULL, NSFW_PROC_NULL)
diff --git a/src/adapt/nstack_rd_mng.c b/src/adapt/nstack_rd_mng.c
new file mode 100644
index 0000000..64c54a8
--- /dev/null
+++ b/src/adapt/nstack_rd_mng.c
@@ -0,0 +1,317 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdlib.h>
+#include "nstack_rd_data.h"
+#include "nsfw_mem_api.h"
+#include "nstack_log.h"
+#include "nstack_securec.h"
+
+#define RD_SHMEM_NAME "rd_table"
+
+#define RD_AGE_MAX_TIME 3
+
+rd_route_table *g_rd_table_handle = NULL;
+
+#define RD_IP_ROUTE_CPY(pnode, name, data) { \
+ if (EOK != STRCPY_S((pnode)->data.stack_name, RD_PLANE_NAMELEN, (name))) \
+ { \
+ NSSOC_LOGERR("STRCPY_S failed]copy_name=%s", name); \
+ } \
+ (pnode)->data.type = RD_DATA_TYPE_IP; \
+ (pnode)->agetime = 0; \
+ (pnode)->data.ipdata.addr = (data)->addr; \
+ (pnode)->data.ipdata.masklen = (data)->masklen; \
+ (pnode)->data.ipdata.resev[0] = 0; \
+ (pnode)->data.ipdata.resev[1] = 0; \
+}
+
+/*****************************************************************************
+* Prototype : nstack_rd_mng_int
+* Description : rd mng moudule init, create a block memory
+* Input : int flag
+* Output : None
+* Return Value : int
+* Calls :
+* Called By : nStackMain
+*****************************************************************************/
+int
+nstack_rd_mng_int (int flag)
+{
+ int ret;
+ nsfw_mem_zone zname = {
+ {NSFW_SHMEM, NSFW_PROC_MAIN, RD_SHMEM_NAME},
+ sizeof (rd_route_table),
+ NSFW_SOCKET_ANY,
+ 0
+ };
+ NSSOC_LOGINF ("nstack rd mng init begin]flag=%d", flag);
+ /*nstack main create, app lookup */
+ if (0 == flag)
+ {
+ g_rd_table_handle = (rd_route_table *) nsfw_mem_zone_create (&zname);
+ if (!g_rd_table_handle)
+ {
+ NSSOC_LOGERR ("mem create fail]mem name=%s", RD_SHMEM_NAME);
+ return -1;
+ }
+ ret =
+ MEMSET_S (&(g_rd_table_handle->node[0]), sizeof (rd_route_node), 0,
+ sizeof (rd_route_node));
+ if (EOK != ret)
+ {
+ NSSOC_LOGERR ("MEMSET_S failed]ret=%d", ret);
+ return -1;
+ }
+ g_rd_table_handle->size = NSTACK_RD_DATA_MAX;
+ g_rd_table_handle->icnt = 0;
+ }
+ else /* static data will not be erased in fault case */
+ {
+ g_rd_table_handle =
+ (rd_route_table *) nsfw_mem_zone_lookup (&(zname.stname));
+ if (!g_rd_table_handle)
+ {
+ NSSOC_LOGERR ("mem lookup fail]mem name=%s", RD_SHMEM_NAME);
+ return -1;
+ }
+ }
+ NSSOC_LOGINF ("nstack rd mng init end flag");
+ return 0;
+}
+
+/*****************************************************************************
+* Prototype : nstack_rd_ip_node_insert
+* Description : insert a rd_ip_data into list
+* Input : char *name
+* rd_ip_data *data
+* Output : None
+* Return Value : int
+* Calls :
+* Called By : nStackMain
+*****************************************************************************/
+int
+nstack_rd_ip_node_insert (char *name, rd_ip_data * data)
+{
+ if (!g_rd_table_handle)
+ {
+ NSSOC_LOGERR ("nstack rd mng not inited");
+ return -1;
+ }
+ int iindex = 0;
+ rd_route_node *pnode = NULL;
+ int agetime = 0;
+ int ageindex = -1;
+ int freeindex = -1;
+ int repeatflag = 0;
+
+ for (iindex = 0; iindex < NSTACK_RD_DATA_MAX; iindex++)
+ {
+ pnode = &(g_rd_table_handle->node[iindex]);
+ /*record the index of first free element */
+ if (RD_NODE_USELESS == pnode->flag)
+ {
+ if (-1 == freeindex)
+ {
+ freeindex = iindex;
+ NSSOC_LOGINF ("nstack rd ip free element index:%d was found",
+ iindex);
+ }
+ continue;
+ }
+
+ /*if is using, and repeat just set flag */
+ if (RD_NODE_USING == pnode->flag)
+ {
+ if (MASK_V (pnode->data.ipdata.addr, pnode->data.ipdata.masklen) ==
+ MASK_V (data->addr, data->masklen))
+ {
+ NSSOC_LOGWAR
+ ("nstack:%s, old_addr:0x%x index:%d new_addr:0x%x, masklen:%u was repeat",
+ name, pnode->data.ipdata.addr, iindex, data->addr,
+ data->masklen);
+ repeatflag = 1;
+ }
+ continue;
+ }
+
+ /*if flag is deleting, just update the age time, if agetime is on, just set flag to free */
+ if (RD_NODE_DELETING == pnode->flag)
+ {
+ pnode->agetime++;
+ if (pnode->agetime >= RD_AGE_MAX_TIME)
+ {
+ pnode->flag = RD_NODE_USELESS;
+ NSSOC_LOGINF
+ ("nstack rd ip element index:%d addr:0x%x, masklen:%u was delete and set to free",
+ iindex, pnode->data.ipdata.addr, pnode->data.ipdata.masklen);
+ }
+ /*record delete time */
+ if (agetime < pnode->agetime)
+ {
+ agetime = pnode->agetime;
+ ageindex = iindex;
+ }
+ continue;
+ }
+ }
+
+ /*if repeat, just return */
+ if (1 == repeatflag)
+ {
+ return 0;
+ }
+ if (-1 == freeindex)
+ {
+ if (-1 != ageindex)
+ {
+ freeindex = ageindex;
+ }
+ else
+ {
+ NSSOC_LOGERR
+ ("the rd table is full,nstack:%s, rd addr:0x%x, masklen:%u can't be inserted",
+ name, data->addr, data->masklen);
+ return -1;
+ }
+ }
+ pnode = &(g_rd_table_handle->node[freeindex]);
+ /*if no free found, just reuse the big agetime */
+ RD_IP_ROUTE_CPY (pnode, name, data);
+ pnode->flag = RD_NODE_USING; /*last set */
+ g_rd_table_handle->icnt++;
+ NSSOC_LOGINF ("nstack:%s, rd addr:0x%x, masklen:%u index was inserted",
+ name, data->addr, data->masklen);
+ return 0;
+}
+
+/*****************************************************************************
+* Prototype : nstack_rd_ip_node_delete
+* Description : rd data delete
+* Input : rd_ip_data *data
+* Output : None
+* Return Value : int
+* Calls :
+* Called By : nStackMain
+* just set delete flag, becuase
+*****************************************************************************/
+int
+nstack_rd_ip_node_delete (rd_ip_data * data)
+{
+ int iindex = 0;
+ rd_route_node *pnode = NULL;
+
+ if (!g_rd_table_handle)
+ {
+ NSSOC_LOGERR ("nstack rd mng not inited");
+ return -1;
+ }
+
+ for (iindex = 0; iindex < NSTACK_RD_DATA_MAX; iindex++)
+ {
+ pnode = &(g_rd_table_handle->node[iindex]);
+ if ((RD_NODE_USING == pnode->flag)
+ && (MASK_V (pnode->data.ipdata.addr, pnode->data.ipdata.masklen) ==
+ MASK_V (data->addr, data->masklen)))
+ {
+ pnode->flag = RD_NODE_DELETING; /*just set deleting state */
+ pnode->agetime = 0;
+ g_rd_table_handle->icnt--;
+ NSSOC_LOGINF
+ ("nstack rd delete:%s, addr:0x%x, masklen:%u index:%d was delete",
+ pnode->data.stack_name, data->addr, data->masklen, iindex);
+ return 0;
+ }
+ }
+ NSSOC_LOGINF ("nstack rd delete, addr:0x%x, masklen:%u index was not found",
+ data->addr, data->masklen);
+ return 0;
+}
+
+/*****************************************************************************
+* Prototype : nstack_rd_ip_get
+* Description : get rd data from rd table
+* Input : char *planename
+* rd_route_data **data
+* int *num
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+* Note : a block memory was alloc and return by data,
+* this need free by caller if return 0, otherwise no need
+*****************************************************************************/
+int
+nstack_rd_ip_get (rd_route_data ** data, int *num)
+{
+ rd_route_data *pdata = NULL;
+ rd_route_node *pnode = NULL;
+ int size = 0;
+ int icnt = 0;
+ int idex = 0;
+ int ret;
+
+ if (!g_rd_table_handle || !data || !num)
+ {
+ NSSOC_LOGERR ("nstack rd mng not inited or input err");
+ return -1;
+ }
+ size = sizeof (rd_route_data) * g_rd_table_handle->size;
+ pdata = (rd_route_data *) malloc (size);
+ if (!pdata)
+ {
+ NSSOC_LOGERR ("rd route data malloc fail");
+ return -1;
+ }
+ ret = MEMSET_S (pdata, size, 0, size);
+ if (EOK != ret)
+ {
+ NSSOC_LOGERR ("MEMSET_S failed]ret=%d", ret);
+ free (pdata);
+ return -1;
+ }
+ for (icnt = 0; icnt < g_rd_table_handle->size; icnt++)
+ {
+ pnode = &(g_rd_table_handle->node[icnt]);
+ if (RD_NODE_USING == pnode->flag)
+ {
+ pdata[idex].type = pnode->data.type;
+ pdata[idex].ipdata.addr = pnode->data.ipdata.addr;
+ pdata[idex].ipdata.masklen = pnode->data.ipdata.masklen;
+ pdata[idex].ipdata.resev[0] = pnode->data.ipdata.resev[0];
+ pdata[idex].ipdata.resev[1] = pnode->data.ipdata.resev[1];
+ ret =
+ STRCPY_S (pdata[idex].stack_name, RD_PLANE_NAMELEN,
+ pnode->data.stack_name);
+ if (EOK != ret)
+ {
+ NSSOC_LOGERR ("STRCPY_S failed]ret=%d", ret);
+ free (pdata);
+ return -1;
+ }
+ idex++;
+ }
+ }
+ /*if no data fetched , just return fail */
+ if (idex == 0)
+ {
+ free (pdata);
+ return -1;
+ }
+ *data = pdata;
+ *num = idex;
+ return 0;
+}
diff --git a/src/adapt/nstack_rd_mng.h b/src/adapt/nstack_rd_mng.h
new file mode 100644
index 0000000..f1fe7a3
--- /dev/null
+++ b/src/adapt/nstack_rd_mng.h
@@ -0,0 +1,27 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef __NSTACK_RD_MNG_H
+#define __NSTACK_RD_MNG_H
+#include <stdlib.h>
+#include "nstack_rd_data.h"
+
+int nstack_rd_mng_int (int flag);
+int nstack_rd_ip_node_insert (char *name, rd_ip_data * data);
+int nstack_rd_ip_node_delete (rd_ip_data * data);
+int nstack_rd_ip_get (rd_route_data ** data, int *num);
+
+#endif
diff --git a/src/adapt/nstack_share_res.c b/src/adapt/nstack_share_res.c
new file mode 100644
index 0000000..421b5ed
--- /dev/null
+++ b/src/adapt/nstack_share_res.c
@@ -0,0 +1,176 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "nstack_share_res.h"
+#include "nsfw_mem_api.h"
+#include "types.h"
+#include "nsfw_recycle_api.h"
+#include "nstack_securec.h"
+#include "nstack_log.h"
+#include "nsfw_maintain_api.h"
+#include "nstack_types.h"
+
+#define NSTACK_SHARE_FORK_LOCK "share_fork_lock"
+
+typedef struct
+{
+ common_mem_spinlock_t *fork_share_lock;
+} nstack_share_res;
+
+NSTACK_STATIC nstack_share_res g_nstack_share_res;
+
+/** global timer tick */
+nstack_tick_info_t g_nstack_timer_tick;
+
+NSTACK_STATIC int
+nstack_create_share_fork_lock ()
+{
+ mzone_handle zone;
+ nsfw_mem_zone param;
+ int ret;
+
+ param.isocket_id = -1;
+ param.lenth = sizeof (common_mem_spinlock_t);
+ param.stname.entype = NSFW_SHMEM;
+
+ ret =
+ STRCPY_S (param.stname.aname, NSFW_MEM_NAME_LENTH,
+ NSTACK_SHARE_FORK_LOCK);
+ if (EOK != ret)
+ {
+ NSSOC_LOGERR ("STRCPY_S failed]name=%s,ret=%d", NSTACK_SHARE_FORK_LOCK,
+ ret);
+ return -1;
+ }
+
+ zone = nsfw_mem_zone_create (&param);
+ if (!zone)
+ {
+ NSSOC_LOGERR ("nsfw_mem_zone_create failed]name=%s",
+ NSTACK_SHARE_FORK_LOCK);
+ return -1;
+ }
+
+ g_nstack_share_res.fork_share_lock = (common_mem_spinlock_t *) zone;
+ common_mem_spinlock_init (g_nstack_share_res.fork_share_lock);
+
+ NSSOC_LOGDBG ("ok");
+ return 0;
+}
+
+NSTACK_STATIC int
+nstack_lookup_share_fork_lock ()
+{
+ mzone_handle zone;
+ nsfw_mem_name param;
+
+ param.entype = NSFW_SHMEM;
+ param.enowner = NSFW_PROC_MAIN;
+ if (STRCPY_S (param.aname, NSFW_MEM_NAME_LENTH, NSTACK_SHARE_FORK_LOCK) !=
+ 0)
+ {
+ NSSOC_LOGERR ("STRCPY_S failed]name=%s", NSTACK_SHARE_FORK_LOCK);
+ return -1;
+ }
+
+ zone = nsfw_mem_zone_lookup (&param);
+ if (!zone)
+ {
+ NSSOC_LOGERR ("nsfw_mem_zone_lookup failed]name=%s",
+ NSTACK_SHARE_FORK_LOCK);
+ return -1;
+ }
+
+ g_nstack_share_res.fork_share_lock = (common_mem_spinlock_t *) zone;
+
+ NSSOC_LOGDBG ("ok");
+
+ return 0;
+}
+
+NSTACK_STATIC int
+nstack_lookup_share_global_tick ()
+{
+ int ret;
+ nsfw_mem_name name = {.entype = NSFW_SHMEM,.enowner = NSFW_PROC_MAIN };
+
+ ret = STRCPY_S (name.aname, NSFW_MEM_NAME_LENTH, NSTACK_GLOBAL_TICK_SHM);
+ if (EOK != ret)
+ {
+ NSSOC_LOGERR ("STRCPY_S failed]name=%s,ret=%d", NSTACK_GLOBAL_TICK_SHM,
+ ret);
+ return -1;
+ }
+
+ g_nstack_timer_tick.tick_ptr = (u64_t *) nsfw_mem_zone_lookup (&name);
+ if (NULL == g_nstack_timer_tick.tick_ptr)
+ {
+ NSPOL_LOGERR ("Failed to lookup global timer tick memory");
+ return -1;
+ }
+
+ NSSOC_LOGDBG ("ok");
+ return 0;
+}
+
+int
+nstack_init_share_res ()
+{
+ if (nstack_create_share_fork_lock () != 0)
+ {
+ return -1;
+ }
+
+ return 0;
+}
+
+int
+nstack_attach_share_res ()
+{
+ if (nstack_lookup_share_fork_lock () != 0)
+ {
+ return -1;
+ }
+
+ if (nstack_lookup_share_global_tick () != 0)
+ {
+ return -1;
+ }
+
+ return 0;
+}
+
+common_mem_spinlock_t *
+nstack_get_fork_share_lock ()
+{
+ return g_nstack_share_res.fork_share_lock;
+}
+
+NSTACK_STATIC nsfw_rcc_stat
+nstack_recycle_fork_share_lock (u32 exit_pid, void *pdata, u16 rec_type)
+{
+ NSSOC_LOGDBG ("recycle]pid=%u", exit_pid);
+
+ if (g_nstack_share_res.fork_share_lock
+ && (g_nstack_share_res.fork_share_lock->locked == exit_pid))
+ {
+ common_mem_spinlock_unlock (g_nstack_share_res.fork_share_lock);
+ }
+
+ return NSFW_RCC_CONTINUE;
+}
+
+REGIST_RECYCLE_LOCK_REL (nstack_recycle_fork_share_lock, NULL, NSFW_PROC_APP)
diff --git a/src/adapt/nstack_share_res.h b/src/adapt/nstack_share_res.h
new file mode 100644
index 0000000..5025482
--- /dev/null
+++ b/src/adapt/nstack_share_res.h
@@ -0,0 +1,66 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef NSTACK_SHARE_RES_H
+#define NSTACK_SHARE_RES_H
+
+#include <stdint.h>
+#include "common_mem_spinlock.h"
+#include "nstack_log.h"
+#include "common_func.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+#define NSTACK_VERSION_SHM "nstack_version"
+#define NSTACK_VERSION_LEN 128
+COMPAT_PROTECT (NSTACK_VERSION_LEN, 128);
+#define MAX_UNMATCH_VER_CNT 32
+COMPAT_PROTECT (MAX_UNMATCH_VER_CNT, 32);
+
+#define NSTACK_GLOBAL_TICK_SHM "nstack_global_tick"
+
+typedef struct unmatch_ver_info
+{
+ int unmatch_count;
+ char lib_version[NSTACK_VERSION_LEN];
+ char first_time_stamp[LOG_TIME_STAMP_LEN];
+} unmatch_ver_info_t;
+
+#define DFX_TMR_INTERVAL 60000 /*60 seconds */
+typedef struct nstack_tick_info
+{
+ uint64_t *tick_ptr; // tick from shared memory
+ uint64_t interval; // tick interval, only used in stack process
+ /* tick refference, updated periodically and read in tcpip_thread only */
+ struct timeval ref_time; // ref tick time
+ uint64_t ref_tick; // ref tick
+} nstack_tick_info_t;
+
+int nstack_init_share_res ();
+int nstack_attach_share_res ();
+common_mem_spinlock_t *nstack_get_fork_share_lock ();
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
+
+#endif
diff --git a/src/framework/CMakeLists.txt b/src/framework/CMakeLists.txt
new file mode 100644
index 0000000..78c5a45
--- /dev/null
+++ b/src/framework/CMakeLists.txt
@@ -0,0 +1,61 @@
+#########################################################################
+#
+# Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at:
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#########################################################################
+
+if(WITH_HAL_LIB)
+else()
+ SET(PAL_H_DIRECTORIES "${DMM_DPDK_INSTALL_DIR}/include/dpdk/")
+ FILE(GLOB_RECURSE LIBCOMM lib_common_mem/*.c)
+endif()
+
+FILE(GLOB_RECURSE COMMON common/*.c)
+FILE(GLOB INIT init/*.c)
+FILE(GLOB_RECURSE IPC ipc/*.c)
+FILE(GLOB LOG log/*.c)
+FILE(GLOB SNAPSHOT snapshot/*.c)
+FILE(GLOB STARTUP startup/*.c)
+FILE(GLOB MAINTAIN maintain/*.c)
+FILE(GLOB TRACEING tracing/*.c)
+FILE(GLOB HAL hal/*.c)
+FILE(GLOB DMM_ADPT ../adapt/*.c)
+
+
+
+ADD_LIBRARY(dmm_api STATIC ${COMMON} ${INIT} ${IPC} ${LOG} ${SNAPSHOT} ${STARTUP} ${MAINTAIN} ${TRACEING} ${HAL} ${DMM_ADPT} ${LIBCOMM})
+if(WITH_SECUREC_LIB)
+ADD_DEPENDENCIES(dmm_api SECUREC JSON GLOG)
+else()
+ADD_DEPENDENCIES(dmm_api JSON GLOG)
+endif()
+INCLUDE_DIRECTORIES(
+ dmm_api
+ PRIVATE
+ ${JSON_C_SRC}
+ ${GLOG_SRC}
+ ${SECUREC_SRC_H}
+ ipc/mgr_com/
+ hal/
+ include/
+ common/base/include/generic
+ common/base/include/
+ ${PAL_H_DIRECTORIES}
+ common/base/liblinuxapi/
+ common/mem_mgr/include
+ common/mem_mgr/nsfw_shmem/
+ common/mem_mgr/nsfw_nshmem/
+ ${CMAKE_CURRENT_LIST_DIR}/../nSocket/nstack/event/
+ ${CMAKE_CURRENT_LIST_DIR}/../nSocket/nstack/event/epoll
+ ${CMAKE_CURRENT_LIST_DIR}/../nSocket/include
+) \ No newline at end of file
diff --git a/src/framework/common/base/include/common/common_func.h b/src/framework/common/base/include/common/common_func.h
new file mode 100644
index 0000000..fdf2802
--- /dev/null
+++ b/src/framework/common/base/include/common/common_func.h
@@ -0,0 +1,98 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _RTE_COMM_FUNC_H_
+#define _RTE_COMM_FUNC_H_
+
+#ifdef HAL_LIB
+
+#else
+
+#define common_mem_rwlock_t rte_rwlock_t
+#define common_mem_spinlock_t rte_spinlock_t
+ //typedef rte_rwlock_t common_mem_rwlock_t;
+
+#define nsfw_write_lock(plock) rte_rwlock_write_lock(plock)
+#define nsfw_write_unlock(plock) rte_rwlock_write_unlock(plock)
+#define nsfw_read_lock(plock) rte_rwlock_read_lock(plock)
+#define nsfw_read_unlock(plock) rte_rwlock_read_unlock(plock)
+
+#define common_mem_align32pow2 rte_align32pow2
+
+#define common_mem_atomic32_cmpset rte_atomic32_cmpset
+#define common_mem_pause rte_pause
+
+#define COMMON_MEM_MAX_MEMZONE RTE_MAX_MEMZONE
+
+#define common_mem_atomic32_t rte_atomic32_t
+
+#define common_mem_memseg rte_memseg
+#define common_mem_mem_config rte_mem_config
+
+#define common_mem_pal_get_configuration rte_eal_get_configuration
+
+ //#define commem_mem_pal_module_info rte_eal_module_info
+ //
+#define common_mem_pal_init rte_eal_init
+
+#define COMMON_MEM_MEMPOOL_NAMESIZE RTE_MEMPOOL_NAMESIZE
+
+#define common_mem_memzone_lookup rte_memzone_lookup
+#define common_mem_memzone rte_memzone
+#define common_mem_atomic32_add_return rte_atomic32_add_return
+
+#define common_mem_spinlock_init rte_spinlock_init
+#define common_mem_spinlock_lock rte_spinlock_lock
+#define common_mem_spinlock_unlock rte_spinlock_unlock
+
+#define common_mem_memzone_free rte_memzone_free
+#define common_mem_pktmbuf_pool_create rte_pktmbuf_pool_create
+
+#define common_mem_pktmbuf_alloc rte_pktmbuf_alloc
+
+#define common_mem_mempool rte_mempool
+
+#define common_mem_pktmbuf_free rte_pktmbuf_free
+#define common_mem_mbuf rte_mbuf
+
+#define common_mem_mempool_lookup rte_mempool_lookup
+
+#define common_mem_ring_get_memsize rte_ring_get_memsize
+#define common_mem_ring rte_ring
+
+#define COMMON_MEM_MAX_MEMSEG RTE_MAX_MEMSEG
+
+#define common_mem_memzone_reserve rte_memzone_reserve
+#define common_mem_rwlock_read_lock rte_rwlock_read_lock
+#define common_mem_rwlock_read_unlock rte_rwlock_read_unlock
+
+#define common_mem_rwlock_write_lock rte_rwlock_write_lock
+#define common_mem_rwlock_write_unlock rte_rwlock_write_unlock
+#define common_mem_spinlock_trylock rte_spinlock_trylock
+
+#define common_mem_socket_id rte_socket_id
+#define common_mem_malloc_socket_stats rte_malloc_socket_stats
+
+#define COMMON_MEM_MIN RTE_MIN
+
+#define common_pal_module_init nscomm_pal_module_init
+#define common_memzone_data_reserve_name nscomm_memzone_data_reserve_name
+#define common_memzone_data_lookup_name nscomm_memzone_data_lookup_name
+
+#define common_dump_stack rte_dump_stack
+#endif
+
+#endif // _RTE_COMM_FUNC_H_
diff --git a/src/framework/common/base/include/common/common_mem_api.h b/src/framework/common/base/include/common/common_mem_api.h
new file mode 100644
index 0000000..9eb4344
--- /dev/null
+++ b/src/framework/common/base/include/common/common_mem_api.h
@@ -0,0 +1,144 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef __COMMON_MEM_API_H__
+#define __COMMON_MEM_API_H__
+
+#ifdef HAL_LIB
+#else
+
+#include "rte_atomic.h"
+#include "common_mem_spinlock.h"
+#include <sys/types.h>
+#include <unistd.h>
+#include <semaphore.h>
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+#ifndef NSTACK_LINT_CODE_DISABLE
+#define NSTACK_LINT_CODE_DISABLE(code) /*lint -e#code */
+#endif
+
+#ifndef NSTACK_LINT_CODE_ENABLE
+#define NSTACK_LINT_CODE_ENABLE(code) /*lint +e#code */
+#endif
+
+#define SYS_MBOX_NULL (sys_mbox_t)0
+
+typedef sem_t *sys_sem_t_v1;
+typedef sem_t sys_sem_st_v1;
+typedef struct queue *sys_mbox_t;
+
+typedef rte_spinlock_t *sys_sem_t_v2;
+typedef rte_spinlock_t sys_sem_st_v2;
+
+#ifndef u32_t
+typedef uint32_t u32_t;
+#endif
+
+#ifndef u8_t
+typedef uint8_t u8_t;
+#endif
+
+#ifndef s8_t
+typedef int8_t s8_t;
+#endif
+
+#ifndef err_t
+typedef s8_t err_t;
+#endif
+
+/** Return code for timeouts from sys_arch_mbox_fetch and sys_arch_sem_wait */
+#define SYS_ARCH_TIMEOUT 0xffffffffUL
+
+/** sys_mbox_tryfetch() returns SYS_MBOX_EMPTY if appropriate.
+ * For now we use the same magic value, but we allow this to change in future.
+ */
+#define SYS_MBOX_EMPTY SYS_ARCH_TIMEOUT
+
+void sys_sem_signal_s_v2 (sys_sem_t_v2 sem);
+void sys_sem_init_v2 (sys_sem_t_v2 sem);
+
+u32_t sys_arch_sem_wait_s_v2 (sys_sem_t_v2 sem);
+
+#define SYS_HOST_INITIAL_PID 1
+extern volatile pid_t g_sys_host_pid;
+pid_t sys_get_hostpid_from_file (pid_t pid);
+static inline pid_t
+get_sys_pid ()
+{
+ if (SYS_HOST_INITIAL_PID == g_sys_host_pid)
+ (void) sys_get_hostpid_from_file (getpid ());
+ return g_sys_host_pid;
+}
+
+pid_t updata_sys_pid ();
+long sys_now (void);
+
+#define sys_sem_t sys_sem_t_v2
+#define sys_sem_st sys_sem_st_v2
+#define sys_sem_new(sem, count) sys_sem_new_v2(sem, count)
+#define sys_sem_free(sem) sys_sem_free_v2(sem)
+#define sys_sem_signal(sem) sys_sem_signal_v2(sem)
+#define sys_arch_sem_wait(sem, timeout) sys_arch_sem_wait_v2(sem)
+#define sys_arch_sem_trywait(sem) sys_arch_sem_trywait_v2(sem)
+
+#define sys_sem_init(sem) sys_sem_init_v2(sem)
+#define sys_sem_s_signal(sem) sys_sem_signal_s_v2(sem)
+#define sys_arch_sem_s_wait(sem, timeout) sys_arch_sem_wait_s_v2(sem)
+#define sys_arch_lock_with_pid(sem) (void)sys_arch_lock_with_pid_v2(sem)
+
+#define BUF_SIZE_FILEPATH 256
+#define STR_PID "pid:"
+#define READ_FILE_BUFLEN 512
+
+extern pid_t sys_get_hostpid_from_file (pid_t pid);
+extern pid_t get_hostpid_from_file (u32_t pid);
+extern void get_exec_name_by_pid (pid_t pid, char *task_name,
+ int task_name_len);
+
+static inline u32_t
+sys_arch_lock_with_pid_v2 (sys_sem_t_v2 sem)
+{
+ if (SYS_HOST_INITIAL_PID == g_sys_host_pid)
+ (void) sys_get_hostpid_from_file (getpid ());
+ dmm_spinlock_lock_with_pid (sem, g_sys_host_pid);
+ return 0;
+}
+
+#define NSTACK_SEM_MALLOC(sys_sem,count) \
+{ \
+ rte_spinlock_init(&(sys_sem)); \
+ /*lint -e506*/\
+ if (!(count)) \
+ /*lint +e506*/\
+ { \
+ rte_spinlock_lock(&(sys_sem)); \
+ } \
+}
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
+#endif
+
+#endif /* __COMMON_MEM_API_H__ */
diff --git a/src/framework/common/base/include/common/common_mem_base_type.h b/src/framework/common/base/include/common/common_mem_base_type.h
new file mode 100644
index 0000000..01707d9
--- /dev/null
+++ b/src/framework/common/base/include/common/common_mem_base_type.h
@@ -0,0 +1,85 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _COMMON_MEM_BASE_TYPE_H_
+#define _COMMON_MEM_BASE_TYPE_H_
+
+#ifdef HAL_LIB
+
+#else
+
+#define ALIGN_TYPE uint64_t
+#define PTR_ALIGN_TYPE uint64_t
+
+/*alignment define*/
+#define ALIGNMENT_DEF(name, type, aligntype) \
+ union { \
+ type name; \
+ aligntype name##_align; \
+ }
+
+#define PTR_ALIGNMENT_DEF(name, type) ALIGNMENT_DEF(name, type, PTR_ALIGN_TYPE)
+
+#define OTHER_ALIGNMENT_DEF(name, type) ALIGNMENT_DEF(name, type, ALIGN_TYPE)
+
+/*
+ * * List definitions.
+ * */
+#define DMM_LIST_HEAD(name, type) \
+struct name { \
+ PTR_ALIGNMENT_DEF(lh_first, struct type *); /* first element */ \
+}
+
+#define DMM_LIST_ENTRY(type) \
+struct { \
+ PTR_ALIGNMENT_DEF(le_next, struct type *); /* next element */\
+ PTR_ALIGNMENT_DEF(le_prev, struct type **); /* address of previous next element */ \
+}
+
+/*
+ * * Tail queue definitions.
+ * */
+#define _DMM_TAILQ_HEAD(name, type, qual) \
+struct name { \
+ PTR_ALIGNMENT_DEF(tqh_first, qual type *); /* first element */ \
+ PTR_ALIGNMENT_DEF(tqh_last, qual type * qual *); /* addr of last next element */ \
+}
+
+#define DMM_TAILQ_HEAD(name, type) _DMM_TAILQ_HEAD(name, struct type,)
+
+#define _DMM_TAILQ_ENTRY(type, qual) \
+struct { \
+ PTR_ALIGNMENT_DEF(tqe_next, qual type *); /* next element */\
+ PTR_ALIGNMENT_DEF(tqe_prev, qual type * qual*); /* address of previous next element */\
+}
+#define DMM_TAILQ_ENTRY(type) _DMM_TAILQ_ENTRY(struct type,)
+
+/*
+ * * Singly-linked Tail queue declarations.
+ * */
+#define DMM_STAILQ_HEAD(name, type) \
+ struct name { \
+ PTR_ALIGNMENT_DEF(stqh_first, struct type *); /* first element */ \
+ PTR_ALIGNMENT_DEF(stqh_last, struct type **); /* addr of last next element */ \
+ }
+
+#define DMM_STAILQ_ENTRY(type) \
+ struct { \
+ PTR_ALIGNMENT_DEF(stqe_next, struct type *); /* next element */ \
+ }
+#endif
+
+#endif
diff --git a/src/framework/common/base/include/common/common_mem_buf.h b/src/framework/common/base/include/common/common_mem_buf.h
new file mode 100644
index 0000000..d0d3588
--- /dev/null
+++ b/src/framework/common/base/include/common/common_mem_buf.h
@@ -0,0 +1,75 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _COMMON_MEM_BUF_H_
+#define _COMMON_MEM_BUF_H_
+
+#ifdef HAL_LIB
+#else
+
+#include "common_mem_base_type.h"
+
+typedef enum __DMM_PROC_TYPE
+{
+ DMM_PROC_T_AUTO = 0, /*auto detect */
+ DMM_PROC_T_PRIMARY = 1, /* set to primary */
+ DMM_PROC_T_SECONDARY = 2, /* set to seconday */
+ DMM_PROC_T_INVALID
+} DMM_PROC_TYPE;
+
+#define DMM_MBUF_RET_OK 0
+#define DMM_MBUF_RET_ERR 1
+
+#define LCORE_MAX 128
+#define LCORE_MASK_PER (sizeof(int) * 8)
+#define LCORE_MASK_MAX (LCORE_MAX/LCORE_MASK_PER)
+
+#define LCORE_MASK_SET(ilcoremask, value) \
+ if (value < LCORE_MAX) \
+ { \
+ ilcoremask[(value/LCORE_MASK_PER)] = (int) ( (ilcoremask[(value/LCORE_MASK_PER)]) | (1< (value%LCORE_MASK_PER))); \
+ } \
+
+#define DMM_HUGTBL_ENABLE 0
+#define DMM_HUGTBL_DISABLE 1
+
+typedef struct __common_pal_module_info
+{
+ int ishare_mem_size; /*shared memory size */
+ int ilcoremask[LCORE_MASK_MAX];
+ /**/ unsigned char uchugeflag;
+ unsigned char ucproctype;
+ unsigned char ucinstance;
+ unsigned char ucresrv2;
+} common_mem_pal_module_info;
+
+/**
+ * rte pal module init.
+ *
+ *
+ * @param name
+ * The name of the buf pool.
+ */
+int nscomm_pal_module_init (common_mem_pal_module_info * pinfo);
+
+void *nscomm_memzone_data_reserve_name (const char *name, size_t len,
+ int socket_id);
+
+void *nscomm_memzone_data_lookup_name (const char *name);
+
+#endif
+
+#endif /* _COMMON_MEM_BUF_H_ */
diff --git a/src/framework/common/base/include/common/common_mem_common.h b/src/framework/common/base/include/common/common_mem_common.h
new file mode 100644
index 0000000..1e4cf56
--- /dev/null
+++ b/src/framework/common/base/include/common/common_mem_common.h
@@ -0,0 +1,25 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _COMMON_MEM_COMMON_H_
+#define _COMMON_MEM_COMMON_H_
+
+#ifdef HAL_LIB
+#else
+#include "rte_common.h"
+#endif
+
+#endif
diff --git a/src/framework/common/base/include/common/common_mem_malloc.h b/src/framework/common/base/include/common/common_mem_malloc.h
new file mode 100644
index 0000000..68721cd
--- /dev/null
+++ b/src/framework/common/base/include/common/common_mem_malloc.h
@@ -0,0 +1,25 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _COMMON_MEM_MALLOC_H_
+#define _COMMON_MEM_MALLOC_H_
+
+#ifdef HAL_LIB
+#else
+#include "rte_malloc.h"
+#endif
+
+#endif /* _COMMON_MEM_MALLOC_H_ */
diff --git a/src/framework/common/base/include/common/common_mem_mbuf.h b/src/framework/common/base/include/common/common_mem_mbuf.h
new file mode 100644
index 0000000..0bb7696
--- /dev/null
+++ b/src/framework/common/base/include/common/common_mem_mbuf.h
@@ -0,0 +1,40 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+/*******************************************************************
+ Copyright 2017 - 2047, Huawei Tech. Co., Ltd.
+ ALL RIGHTS RESERVED
+
+Filename : common_mem_mbuf.h
+Description :
+Version : 1.1
+********************************************************************/
+
+#ifndef _COMMON_MEM_MBUF_H_
+#define _COMMON_MEM_MBUF_H_
+
+#ifdef HAL_LIB
+#else
+#include "rte_mbuf.h"
+#include "common_func.h"
+
+typedef uint32_t (*dmm_mbuf_item_fun) (void *data, void *argv);
+int32_t dmm_pktmbuf_pool_iterator (struct common_mem_mempool *mp,
+ uint32_t start, uint32_t end,
+ dmm_mbuf_item_fun fun, void *argv);
+#endif
+
+#endif /* _COMMON_MEM_MBUF_H_ */
diff --git a/src/framework/common/base/include/common/common_mem_mempool.h b/src/framework/common/base/include/common/common_mem_mempool.h
new file mode 100644
index 0000000..58a8e82
--- /dev/null
+++ b/src/framework/common/base/include/common/common_mem_mempool.h
@@ -0,0 +1,25 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _COMMON_MEM_MEMPOOL_H_
+#define _COMMON_MEM_MEMPOOL_H_
+
+#ifdef HAL_LIB
+#else
+#include "rte_mempool.h"
+#endif
+
+#endif /* _COMMON_MEM_MEMPOOL_H_ */
diff --git a/src/framework/common/base/include/common/common_mem_memzone.h b/src/framework/common/base/include/common/common_mem_memzone.h
new file mode 100644
index 0000000..20e18c2
--- /dev/null
+++ b/src/framework/common/base/include/common/common_mem_memzone.h
@@ -0,0 +1,25 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _COMMON_MEM_MEMZONE_H_
+#define _COMMON_MEM_MEMZONE_H_
+
+#ifdef HAL_LIB
+#else
+#include "rte_memzone.h"
+#endif
+
+#endif /* _COMMON_MEM_MEMZONE_H_ */
diff --git a/src/framework/common/base/include/common/common_mem_pal.h b/src/framework/common/base/include/common/common_mem_pal.h
new file mode 100644
index 0000000..209b8bd
--- /dev/null
+++ b/src/framework/common/base/include/common/common_mem_pal.h
@@ -0,0 +1,30 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _COMMON_MEM_PAL_H_
+#define _COMMON_MEM_PAL_H_
+
+#ifdef HAL_LIB
+#else
+
+#include "nsfw_base_linux_api.h"
+
+/*print the map address*/
+void dmm_addr_print (void);
+
+#endif
+
+#endif /* _COMMON_MEM_PAL_H_ */
diff --git a/src/framework/common/base/include/common/common_mem_pal_memconfig.h b/src/framework/common/base/include/common/common_mem_pal_memconfig.h
new file mode 100644
index 0000000..65b6e04
--- /dev/null
+++ b/src/framework/common/base/include/common/common_mem_pal_memconfig.h
@@ -0,0 +1,26 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _COMMON_MEM_PAL_MEMCONFIG_H_
+#define _COMMON_MEM_PAL_MEMCONFIG_H_
+
+#ifdef HAL_LIB
+#else
+#include "rte_eal_memconfig.h"
+
+#endif
+
+#endif
diff --git a/src/framework/common/base/include/common/common_mem_spinlock.h b/src/framework/common/base/include/common/common_mem_spinlock.h
new file mode 100644
index 0000000..23f6b1e
--- /dev/null
+++ b/src/framework/common/base/include/common/common_mem_spinlock.h
@@ -0,0 +1,40 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _COMMON_MEM_SPINLOCK_X86_64_H_
+#define _COMMON_MEM_SPINLOCK_X86_64_H_
+
+#ifdef HAL_LIB
+#else
+#include "rte_spinlock.h"
+
+static inline void
+dmm_spinlock_lock_with_pid (rte_spinlock_t * sl, int pid)
+{
+ while (!__sync_bool_compare_and_swap (&sl->locked, 0, pid))
+ while (sl->locked)
+ rte_pause ();
+}
+
+static inline int
+dmm_spinlock_try_lock_with_pid (rte_spinlock_t * sl, int pid)
+{
+ return __sync_bool_compare_and_swap (&sl->locked, 0, pid);
+}
+
+#endif
+
+#endif /* _COMMON_MEM_SPINLOCK_X86_64_H_ */
diff --git a/src/framework/common/base/include/common/common_sys_config.h b/src/framework/common/base/include/common/common_sys_config.h
new file mode 100644
index 0000000..552cae3
--- /dev/null
+++ b/src/framework/common/base/include/common/common_sys_config.h
@@ -0,0 +1,46 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef __COMMON_SYS_CONFIG_H_
+#define __COMMON_SYS_CONFIG_H_
+
+/* Below compile macro is used only in UT makefile */
+#if (HAL_LIB)
+#else
+#undef RTE_CACHE_LINE_SIZE
+#define RTE_CACHE_LINE_SIZE 64
+#undef RTE_MAX_LCORE
+#define RTE_MAX_LCORE 128
+#undef RTE_MAX_NUMA_NODES
+#define RTE_MAX_NUMA_NODES 8
+#undef RTE_MAX_MEMSEG
+#define RTE_MAX_MEMSEG 256
+#undef RTE_MAX_MEMZONE
+#define RTE_MAX_MEMZONE 2560
+#undef RTE_MAX_TAILQ
+#define RTE_MAX_TAILQ 32
+#undef RTE_ARCH_X86
+#define RTE_ARCH_X86 1
+#undef RTE_ARCH_64
+#define RTE_ARCH_64 1
+#undef RTE_PKTMBUF_HEADROOM
+#define RTE_PKTMBUF_HEADROOM 128
+#undef RTE_MEMPOOL_CACHE_MAX_SIZE
+#define RTE_MEMPOOL_CACHE_MAX_SIZE 512
+
+#endif
+
+#endif // __COMMON_SYS_CONFIG_H_
diff --git a/src/framework/common/base/include/common/generic/common_mem_rwlock.h b/src/framework/common/base/include/common/generic/common_mem_rwlock.h
new file mode 100644
index 0000000..2eed259
--- /dev/null
+++ b/src/framework/common/base/include/common/generic/common_mem_rwlock.h
@@ -0,0 +1,25 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _COMMON_MEM_RWLOCK_H_
+#define _COMMON_MEM_RWLOCK_H_
+
+#ifdef HAL_LIB
+#else
+#include "rte_rwlock.h"
+#endif
+
+#endif /* _COMMON_MEM_RWLOCK_H_ */
diff --git a/src/framework/common/base/include/common_pal_bitwide_adjust.h b/src/framework/common/base/include/common_pal_bitwide_adjust.h
new file mode 100644
index 0000000..850742b
--- /dev/null
+++ b/src/framework/common/base/include/common_pal_bitwide_adjust.h
@@ -0,0 +1,222 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _COMMON_PAL_BITWIDE_ADJUST_H_
+#define _COMMON_PAL_BITWIDE_ADJUST_H_
+
+#ifdef HAL_LIB
+#include "pal_bitwide_adjust.h"
+#else
+#define MODULE(name) (1)
+
+#include "common_mem_common.h"
+
+#include "common_func.h"
+
+#ifndef _UT_FUN_DISABLE_
+/*define struct for UT restore global variant*/
+struct ut_adjust_global
+{
+ void **ut_PrimAddr2LocalMap;
+ uint64_t *ut_LocalAddr2PrimMap;
+ void *ut_LocalBaseAddr;
+ void *ut_LocalMaxAddr;
+ void *ut_LocalCfgAddrBase;
+ uint64_t ut_PrimBaseAddr;
+ uint64_t ut_PrimMaxAddr;
+ uint64_t ut_PrimCfgAddrBase;
+ int ut_PrimSameFlg;
+ uint64_t ut_LBitMask;
+ int ut_LBitMaskLen;
+ struct common_mem_memseg *ut_PMemSegArry;
+ void **ut_LMegAddrArry;
+};
+#endif
+
+#define ALIGN_SIZET(size) ((uint64_t)(size))
+#define ALIGN_PTR(PTR) ((uint64_t)(PTR))
+
+extern struct common_mem_memseg *g_PMemSegArry;
+extern void **g_LMegAddrArry;
+
+/*get Local Seg addr by segIdx*/
+#define HMEM_SEG_LVADDR(segid) (g_LMegAddrArry[segid])
+/*get SegIDX by PrimSegAddr, just get the arry Idx of g_PMemSegArry*/
+#define HMEM_SEGID(segaddr) ((struct common_mem_memseg*)segaddr - &(g_PMemSegArry[0]))
+
+/*****************************************************************
+Parameters : LMegAddrArry[] Loacol common_mem_memseg addr Arry
+ SegNum common_mem_memseg Num.
+Return :
+Description : init g_PrimAddr2LocalMap g_LocalAddr2PrimMap while the process start
+*****************************************************************/
+void *pal_shddr_to_laddr (uint64_t shaddr);
+uint64_t pal_laddr_to_shddr (void *laddr);
+int dmm_pal_addr_align ();
+
+extern int g_PrimSameFlg;
+
+/* if __NSTACK_MAIN__ is defined, no need do addr trans*/
+#ifndef __NSTACK_MAIN__
+/* g_PrimSameFlg check should be done before calling cast functions */
+
+/*share memory address to local virtual address*/
+#define ADDR_SHTOL(addr) (g_PrimSameFlg ? ((void*) (addr)) : pal_shddr_to_laddr((uint64_t)(addr)))
+
+/*local virtual address to share memory address according to memseg*/
+#define ADDR_LTOSH(addr) (g_PrimSameFlg ? ((uint64_t)(addr)) : pal_laddr_to_shddr((void*)(addr)))
+
+#define PTR_SHTOL(type, addr) ((type)ADDR_SHTOL(addr))
+
+/*local virtual address to share memory address; for compatible, not delete ADDR_LTOSH_EXT*/
+#define ADDR_LTOSH_EXT(addr) ADDR_LTOSH(addr)
+#else
+/*share memory address to local virtual address*/
+#define ADDR_SHTOL(addr) ((void*)(addr))
+
+/*local virtual address to share memory address according to memseg*/
+#define ADDR_LTOSH(addr) ((uint64_t)(addr))
+
+#define PTR_SHTOL(type, addr) ((type)(addr))
+
+/*local virtual address to share memory address; for compatible, not delete ADDR_LTOSH_EXT*/
+#define ADDR_LTOSH_EXT(addr) ADDR_LTOSH(addr)
+#endif
+
+#if MODULE("list")
+#define COMMON_LIST_INSERT_HEAD(lhead, lelm, field) do { \
+ if (((lelm)->field.le_next_align = (lhead)->lh_first_align) != ((typeof((lhead)->lh_first_align))(long)NULL)) \
+ ((typeof((lhead)->lh_first))ADDR_SHTOL((lhead)->lh_first_align))->field.le_prev_align = \
+ ADDR_LTOSH(&(lelm)->field.le_next); \
+ (lhead)->lh_first_align = ADDR_LTOSH(lelm); \
+ (lelm)->field.le_prev_align = ADDR_LTOSH(&(lhead)->lh_first); \
+} while (/*CONSTCOND*/0)
+
+#define COMMON_LIST_REMOVE(lelm, field) do { \
+ if ((lelm)->field.le_next_align != ((typeof((lelm)->field.le_next_align))ALIGN_PTR(NULL))) \
+ ((typeof((lelm)->field.le_next))ADDR_SHTOL((lelm)->field.le_next_align))->field.le_prev_align = \
+ (lelm)->field.le_prev_align; \
+ if (EOK != (MEMCPY_S((typeof((lelm)->field.le_prev))ADDR_SHTOL((lelm)->field.le_prev_align), \
+ sizeof((lelm)->field.le_next_align), \
+ &((lelm)->field.le_next_align), \
+ sizeof((lelm)->field.le_next_align)))) \
+ {\
+ NSCOMM_LOGERR("MEMCPY_S failed.");\
+ return;\
+ }\
+} while (/*CONSTCOND*/0)
+
+#define COMMON_LIST_EMPTY(lhead) ((typeof((lhead)->lh_first))ADDR_SHTOL((lhead)->lh_first_align) == NULL)
+#define COMMON_LIST_FIRST(lhead) ((typeof((lhead)->lh_first))ADDR_SHTOL((lhead)->lh_first_align))
+#define COMMON_LIST_NEXT(lelm, field) ((typeof((lelm)->field.le_next))ADDR_SHTOL((lelm)->field.le_next_align))
+
+#endif
+
+#if MODULE("tailq")
+
+#define COMMON_TAILQ_INSERT_TAIL(lhead, lelm, field) do { \
+ (lelm)->field.tqe_next_align = (typeof((lelm)->field.tqe_next_align))NULL; \
+ (lelm)->field.tqe_prev_align = (lhead)->tqh_last_align; \
+ typeof((lhead)->tqh_last_align) tempelm = ADDR_LTOSH(lelm);\
+ if (EOK != (MEMCPY_S(ADDR_SHTOL((lhead)->tqh_last_align), sizeof(tempelm), &tempelm, sizeof(tempelm)))) \
+ {\
+ NSCOMM_LOGERR("MEMCPY_S failed.");\
+ }\
+ (lhead)->tqh_last_align = ADDR_LTOSH(&(lelm)->field.tqe_next); \
+} while (/*CONSTCOND*/0)
+
+#define COMMON_TAILQ_FOREACH(lvar, lhead, field) \
+ for ((lvar) = (typeof(lvar))ADDR_SHTOL((lhead)->tqh_first_align); \
+ (lvar); \
+ (lvar) = (typeof(lvar))ADDR_SHTOL((lvar)->field.tqe_next_align))
+
+#define COMMON_TAILQ_REMOVE(lhead, lelm, field) do { \
+ if (((lelm)->field.tqe_next_align) != (typeof((lelm)->field.tqe_next_align))NULL) \
+ ((typeof((lelm)->field.tqe_next))ADDR_SHTOL((lelm)->field.tqe_next_align))->field.tqe_prev_align = \
+ (lelm)->field.tqe_prev_align; \
+ else \
+ (lhead)->tqh_last_align = (lelm)->field.tqe_prev_align; \
+ if (EOK != (MEMCPY_S(ADDR_SHTOL((lelm)->field.tqe_prev_align), \
+ sizeof((lelm)->field.tqe_next_align), \
+ &((lelm)->field.tqe_next_align), \
+ sizeof((lelm)->field.tqe_next_align)))) \
+ {\
+ NSCOMM_LOGERR("MEMCPY_S failed.");\
+ }\
+ } while (/*CONSTCOND*/0)
+
+/*
+ * Tail queue functions.
+ */
+#define COMMON_TAILQ_INIT(head) do { \
+ (head)->tqh_first_align = (typeof((head)->tqh_first_align))NULL; \
+ (head)->tqh_last_align = ADDR_LTOSH(&(head)->tqh_first); \
+ } while (/*CONSTCOND*/0)
+
+/*
+ * Tail queue access methods.
+ */
+#define COMMON_TAILQ_EMPTY(head) ((head)->tqh_first_align == (typeof((head)->tqh_first_align))NULL)
+#define COMMON_TAILQ_FIRST(head) ((typeof((head)->tqh_first))ADDR_SHTOL((head)->tqh_first_align))
+#define COMMON_TAILQ_NEXT(elm, field) ((typeof((elm)->field.tqe_next))ADDR_SHTOL((elm)->field.tqe_next_align))
+
+#endif
+
+#if MODULE("stailq")
+/*
+* Singly-linked Tail queue functions.
+*/
+#define COMMON_STAILQ_INIT(head) do { \
+ (head)->stqh_first_align = ALIGN_PTR(NULL); \
+ (head)->stqh_last_align = ADDR_LTOSH(&(head)->stqh_first); \
+} while (/*CONSTCOND*/0)
+
+#define COMMON_STAILQ_INSERT_TAIL(head, elm, field) do { \
+ (elm)->field.stqe_next_align = ALIGN_PTR(NULL); \
+ typeof((head)->stqh_last_align) telm = ADDR_LTOSH(elm);\
+ if (EOK != (MEMCPY_S(ADDR_SHTOL((head)->stqh_last_align), sizeof(telm), &telm, sizeof(telm))))\
+ {\
+ NSCOMM_LOGERR("MEMCPY_S failed.");\
+ }\
+ (head)->stqh_last_align = ADDR_LTOSH(&(elm)->field.stqe_next); \
+} while (/*CONSTCOND*/0)
+
+#define COMMON_STAILQ_REMOVE_HEAD(head, field) do { \
+ if (((head)->stqh_first_align = \
+ ((typeof((head)->stqh_first))ADDR_SHTOL((head)->stqh_first_align))->field.stqe_next_align) == \
+ (PTR_ALIGN_TYPE)NULL) \
+ (head)->stqh_last_align = ADDR_LTOSH(&(head)->stqh_first); \
+} while (/*CONSTCOND*/0)
+
+#define COMMON_STAILQ_FOREACH(var, head, field) \
+ for ((var) = ADDR_SHTOL((head)->stqh_first_align); \
+ (var); \
+ (var) = ADDR_SHTOL((var)->field.stqe_next_align))
+
+/*
+* Singly-linked Tail queue access methods.
+*/
+
+#define COMMON_STAILQ_EMPTY(head) ((head)->stqh_first_align == (PTR_ALIGN_TYPE)NULL)
+
+#define COMMON_STAILQ_FIRST(head) (ADDR_SHTOL((head)->stqh_first_align))
+
+#define COMMON_STAILQ_NEXT(elm, field) (ADDR_SHTOL((elm)->field.stqe_next_align))
+#endif
+
+#endif
+
+#endif
diff --git a/src/framework/common/base/include/nsfw_base_linux_api.h b/src/framework/common/base/include/nsfw_base_linux_api.h
new file mode 100644
index 0000000..83b5a32
--- /dev/null
+++ b/src/framework/common/base/include/nsfw_base_linux_api.h
@@ -0,0 +1,58 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_BASE_LINUX_API_H_
+#define _NSFW_BASE_LINUX_API_H_
+
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <sys/epoll.h>
+#include <unistd.h>
+
+int nsfw_base_socket (int, int, int);
+int nsfw_base_bind (int, const struct sockaddr *, socklen_t);
+int nsfw_base_listen (int, int);
+int nsfw_base_shutdown (int, int);
+int nsfw_base_getsockname (int, struct sockaddr *, socklen_t *);
+int nsfw_base_getpeername (int, struct sockaddr *, socklen_t *);
+int nsfw_base_getsockopt (int, int, int, void *, socklen_t *);
+int nsfw_base_setsockopt (int, int, int, const void *, socklen_t);
+int nsfw_base_accept (int, struct sockaddr *, socklen_t *);
+int nsfw_base_accept4 (int, struct sockaddr *, socklen_t *, int flags);
+int nsfw_base_connect (int, const struct sockaddr *, socklen_t);
+ssize_t nsfw_base_recv (int, void *, size_t, int);
+ssize_t nsfw_base_send (int, const void *, size_t, int);
+ssize_t nsfw_base_read (int, void *, size_t);
+ssize_t nsfw_base_write (int, const void *, size_t);
+ssize_t nsfw_base_writev (int, const struct iovec *, int);
+ssize_t nsfw_base_readv (int, const struct iovec *, int);
+ssize_t nsfw_base_sendto (int, const void *, size_t, int,
+ const struct sockaddr *, socklen_t);
+ssize_t nsfw_base_recvfrom (int, void *, size_t, int, struct sockaddr *,
+ socklen_t *);
+ssize_t nsfw_base_sendmsg (int, const struct msghdr *, int flags);
+ssize_t nsfw_base_recvmsg (int, struct msghdr *, int flags);
+int nsfw_base_close (int);
+int nsfw_base_select (int, fd_set *, fd_set *, fd_set *, struct timeval *);
+int nsfw_base_ioctl (int, unsigned long, unsigned long);
+int nsfw_base_fcntl (int, int, unsigned long);
+int nsfw_base_epoll_create (int);
+int nsfw_base_epoll_create1 (int);
+int nsfw_base_epoll_ctl (int, int, int, struct epoll_event *);
+int nsfw_base_epoll_wait (int, struct epoll_event *, int, int);
+pid_t nsfw_base_fork (void);
+
+#endif
diff --git a/src/framework/common/base/include/nsfw_getopt.h b/src/framework/common/base/include/nsfw_getopt.h
new file mode 100644
index 0000000..f1394cf
--- /dev/null
+++ b/src/framework/common/base/include/nsfw_getopt.h
@@ -0,0 +1,50 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef NSFW_GETOPT_H
+#define NSFW_GETOPT_H 1
+
+#if defined(__cplusplus)
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+#define nsfw_no_argument 0
+#define nsfw_required_argument 1
+#define nsfw_optional_argument 2
+
+struct option
+{
+ const char *name;
+ int has_arg;
+ int *flag;
+ int val;
+};
+
+int nsfw_getopt_long (int argc, char *const argv[], const char *optstring,
+ const struct option *longopts, int *longindex);
+
+extern char *nsfw_optarg;
+extern int nsfw_optind, nsfw_opterr, nsfw_optopt;
+
+#if defined(__cplusplus)
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
+
+#endif
diff --git a/src/framework/common/base/liblinuxapi/base_linux_api_declare.h b/src/framework/common/base/liblinuxapi/base_linux_api_declare.h
new file mode 100644
index 0000000..943ae04
--- /dev/null
+++ b/src/framework/common/base/liblinuxapi/base_linux_api_declare.h
@@ -0,0 +1,51 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+BASE_MK_DECL (int, socket, (int, int, int));
+BASE_MK_DECL (int, bind, (int, const struct sockaddr *, socklen_t));
+BASE_MK_DECL (int, listen, (int, int));
+BASE_MK_DECL (int, shutdown, (int, int));
+BASE_MK_DECL (int, getsockname, (int, struct sockaddr *, socklen_t *));
+BASE_MK_DECL (int, getpeername, (int, struct sockaddr *, socklen_t *));
+BASE_MK_DECL (int, getsockopt, (int, int, int, void *, socklen_t *));
+BASE_MK_DECL (int, setsockopt, (int, int, int, const void *, socklen_t));
+BASE_MK_DECL (int, accept, (int, struct sockaddr *, socklen_t *));
+BASE_MK_DECL (int, accept4, (int, struct sockaddr *, socklen_t *, int flags));
+BASE_MK_DECL (int, connect, (int, const struct sockaddr *, socklen_t));
+BASE_MK_DECL (ssize_t, recv, (int, void *, size_t, int));
+BASE_MK_DECL (ssize_t, send, (int, const void *, size_t, int));
+BASE_MK_DECL (ssize_t, read, (int, void *, size_t));
+BASE_MK_DECL (ssize_t, write, (int, const void *, size_t));
+BASE_MK_DECL (ssize_t, writev, (int, const struct iovec *, int));
+BASE_MK_DECL (ssize_t, readv, (int, const struct iovec *, int));
+BASE_MK_DECL (ssize_t, sendto,
+ (int, const void *, size_t, int, const struct sockaddr *,
+ socklen_t));
+BASE_MK_DECL (ssize_t, recvfrom,
+ (int, void *, size_t, int, struct sockaddr *, socklen_t *));
+BASE_MK_DECL (ssize_t, sendmsg, (int, const struct msghdr *, int flags));
+BASE_MK_DECL (ssize_t, recvmsg, (int, struct msghdr *, int flags));
+BASE_MK_DECL (int, close, (int));
+BASE_MK_DECL (int, select,
+ (int, fd_set *, fd_set *, fd_set *, struct timeval *));
+BASE_MK_DECL (int, ioctl, (int, unsigned long, unsigned long));
+BASE_MK_DECL (int, fcntl, (int, int, unsigned long));
+BASE_MK_DECL (int, epoll_create, (int));
+BASE_MK_DECL (int, epoll_create1, (int));
+BASE_MK_DECL (int, epoll_ctl, (int, int, int, struct epoll_event *));
+BASE_MK_DECL (int, epoll_wait, (int, struct epoll_event *, int, int));
+BASE_MK_DECL (pid_t, fork, (void));
+#undef BASE_MK_DECL
diff --git a/src/framework/common/base/liblinuxapi/nsfw_base_linux_api.c b/src/framework/common/base/liblinuxapi/nsfw_base_linux_api.c
new file mode 100644
index 0000000..de98877
--- /dev/null
+++ b/src/framework/common/base/liblinuxapi/nsfw_base_linux_api.c
@@ -0,0 +1,628 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "nsfw_base_linux_api.h"
+#include "nstack_log.h"
+#include <pthread.h>
+#include <stdio.h>
+#include <errno.h>
+#include <dlfcn.h>
+
+#define NSFW_BASE_OK 0
+#define NSFW_BASE_FAIL (-1)
+
+#define nsfw_call_ret(symbol, para){ \
+ if (NSFW_BASE_OK != nsfw_posix_api_init()) \
+ { \
+ return NSFW_BASE_FAIL; \
+ } \
+ if (g_nsfw_posix_api.pf##symbol) \
+ { \
+ return g_nsfw_posix_api.pf##symbol para;\
+ } \
+ errno = ENOSYS; \
+ return NSFW_BASE_FAIL; \
+}
+
+typedef enum
+{
+ BASE_STATE_INIT,
+ BASE_STATE_SUCCESS,
+ BASE_STATE_FAIL
+} nsfw_base_state;
+
+typedef struct __base_linux_api
+{
+#define BASE_MK_DECL(ret, fn, args) ret (*pf##fn) args;
+#include "base_linux_api_declare.h"
+} base_linux_api;
+
+nsfw_base_state g_nsfw_mudule_state = BASE_STATE_INIT;
+pthread_mutex_t g_nsfw_init_mutex = PTHREAD_MUTEX_INITIALIZER;
+base_linux_api g_nsfw_posix_api = { 0 };
+
+void *g_linux_lib_handle = (void *) 0;
+
+int
+nsfw_posix_symbol_load ()
+{
+ g_linux_lib_handle = dlopen ("libc.so.6", RTLD_NOW | RTLD_GLOBAL);
+ if ((void *) 0 == g_linux_lib_handle)
+ {
+ /* optimize dlopen err print */
+ NSSOC_LOGERR ("cannot dlopen libc.so.6] err_string=%s", dlerror ());
+ return NSFW_BASE_FAIL;
+ }
+#define BASE_MK_DECL(ret, fn, args) \
+ g_nsfw_posix_api.pf##fn = (typeof(g_nsfw_posix_api.pf##fn))dlsym(g_linux_lib_handle, #fn);
+#include <base_linux_api_declare.h>
+
+ return NSFW_BASE_OK;
+}
+
+/*****************************************************************
+Parameters : void
+Return :
+Description : linux posix api init with threadonce
+*****************************************************************/
+static inline int
+nsfw_posix_api_init ()
+{
+ int iret = NSFW_BASE_OK;
+
+ /*if init already, just return success, if init fail before, just return err */
+ if (BASE_STATE_INIT != g_nsfw_mudule_state)
+ {
+ return (BASE_STATE_SUCCESS ==
+ g_nsfw_mudule_state ? NSFW_BASE_OK : NSFW_BASE_FAIL);
+ }
+
+ (void) pthread_mutex_lock (&g_nsfw_init_mutex);
+
+ /*if init already, just return success, if init fail before, just return err */
+ if (BASE_STATE_INIT != g_nsfw_mudule_state)
+ {
+ (void) pthread_mutex_unlock (&g_nsfw_init_mutex);
+ return (BASE_STATE_SUCCESS ==
+ g_nsfw_mudule_state ? NSFW_BASE_OK : NSFW_BASE_FAIL);
+ }
+
+ iret = nsfw_posix_symbol_load ();
+ if (NSFW_BASE_OK == iret)
+ {
+ g_nsfw_mudule_state = BASE_STATE_SUCCESS;
+ }
+ else
+ {
+ g_nsfw_mudule_state = BASE_STATE_FAIL;
+ }
+
+ (void) pthread_mutex_unlock (&g_nsfw_init_mutex);
+ return iret;
+}
+/* *INDENT-OFF* */
+/*****************************************************************************
+* Prototype : nsfw_base_socket
+* Description : linux socket api
+* Input : int a
+* int b
+* int c
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+
+*
+*****************************************************************************/
+int nsfw_base_socket(int a, int b, int c)
+{
+ nsfw_call_ret(socket, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_bind
+* Description : linux fd bind api
+* Input : int a
+* const struct sockaddr* b
+* socklen_t c
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_bind(int a, const struct sockaddr* b, socklen_t c)
+{
+ nsfw_call_ret(bind, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_listen
+* Description : linux fd listen api
+* Input : int a
+* int b
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_listen(int a, int b)
+{
+ nsfw_call_ret(listen, (a, b))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_shutdown
+* Description : linux shutdown api
+* Input : int a
+* int b
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*
+*****************************************************************************/
+int nsfw_base_shutdown(int a, int b)
+{
+ nsfw_call_ret(shutdown, (a, b))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_getsockname
+* Description : linux getsockname api
+* Input : int a
+* struct sockaddr* b
+* socklen_t* c
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_getsockname(int a, struct sockaddr* b, socklen_t* c)
+{
+ nsfw_call_ret(getsockname, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_getpeername
+* Description : linux getpername api
+* Input : int a
+* struct sockaddr* b
+* socklen_t* c
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_getpeername(int a, struct sockaddr* b, socklen_t* c)
+{
+ nsfw_call_ret(getpeername, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_getsockopt
+* Description : linux getsockopt api
+* Input : int a
+* int b
+* int c
+* void* d
+* socklen_t* e
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_getsockopt(int a, int b, int c, void* d, socklen_t* e)
+{
+ nsfw_call_ret(getsockopt, (a, b, c, d, e))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_setsockopt
+* Description : linux setsockopt api
+* Input : int a
+* int b
+* int c
+* const void* d
+* socklen_t e
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int nsfw_base_setsockopt(int a, int b, int c, const void* d, socklen_t e)
+{
+ nsfw_call_ret(setsockopt, (a, b, c, d, e))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_accept
+* Description : linux accept api
+* Input : int a
+* struct sockaddr* b
+* socklen_t* c
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int nsfw_base_accept(int a, struct sockaddr* b, socklen_t* c)
+{
+ nsfw_call_ret(accept, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_accept4
+* Description : linux accept4 api
+* Input : int a
+* struct sockaddr* b
+* socklen_t* c
+* int flags
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int nsfw_base_accept4(int a, struct sockaddr* b, socklen_t* c, int flags)
+{
+ nsfw_call_ret(accept4, (a, b, c, flags))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_connect
+* Description : linux connect api
+* Input : int a
+* const struct sockaddr* b
+* socklen_t c
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_connect(int a, const struct sockaddr* b, socklen_t c)
+{
+ nsfw_call_ret(connect, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_recv
+* Description : linux recv api
+* Input : int a
+* void* b
+* size_t c
+* int d
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+ssize_t nsfw_base_recv(int a, void* b, size_t c, int d)
+{
+ nsfw_call_ret(recv, (a, b, c, d))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_send
+* Description : linux send api
+* Input : int a
+* const void* b
+* size_t c
+* int d
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+ssize_t nsfw_base_send(int a, const void* b, size_t c, int d)
+{
+ nsfw_call_ret(send, (a, b, c, d))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_read
+* Description : linux read api
+* Input : int a
+* void* b
+* size_t c
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+ssize_t nsfw_base_read(int a, void* b, size_t c)
+{
+ nsfw_call_ret(read, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_write
+* Description : linux write api
+* Input : int a
+* const void* b
+* size_t c
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+ssize_t nsfw_base_write(int a, const void* b, size_t c)
+{
+ nsfw_call_ret(write, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_writev
+* Description : linux writev api
+* Input : int a
+* const struct iovec * b
+* int c
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*****************************************************************************/
+ssize_t nsfw_base_writev(int a, const struct iovec * b, int c)
+{
+ nsfw_call_ret(writev, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_readv
+* Description : linux readv api
+* Input : int a
+* const struct iovec * b
+* int c
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+ssize_t nsfw_base_readv(int a, const struct iovec * b, int c)
+{
+ nsfw_call_ret(readv, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_sendto
+* Description : linux sendto api
+* Input : int a
+* const void * b
+* size_t c
+* int d
+* const struct sockaddr *e
+* socklen_t f
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*****************************************************************************/
+ssize_t nsfw_base_sendto(int a, const void * b, size_t c, int d, const struct sockaddr *e, socklen_t f)
+{
+ nsfw_call_ret(sendto, (a, b, c, d, e, f))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_recvfrom
+* Description : linux recvfrom api
+* Input : int a
+* void *b
+* size_t c
+* int d
+* struct sockaddr *e
+* socklen_t *f
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*****************************************************************************/
+ssize_t nsfw_base_recvfrom(int a, void *b, size_t c, int d,struct sockaddr *e, socklen_t *f)
+{
+ nsfw_call_ret(recvfrom, (a, b, c, d, e, f))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_sendmsg
+* Description : linux sendmsg api
+* Input : int a
+* const struct msghdr *b
+* int flags
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+ssize_t nsfw_base_sendmsg(int a, const struct msghdr *b, int flags)
+{
+ nsfw_call_ret(sendmsg, (a, b, flags))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_recvmsg
+* Description : linux recvmsg api
+* Input : int a
+* struct msghdr *b
+* int flags
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+ssize_t nsfw_base_recvmsg(int a, struct msghdr *b, int flags)
+{
+ nsfw_call_ret(recvmsg, (a, b, flags))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_close
+* Description : linux close api
+* Input : int a
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_close(int a)
+{
+ nsfw_call_ret(close, (a))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_select
+* Description : linux select api
+* Input : int a
+* fd_set *b
+* fd_set *c
+* fd_set *d
+* struct timeval *e
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int nsfw_base_select(int a, fd_set *b, fd_set *c, fd_set *d, struct timeval *e)
+{
+ nsfw_call_ret(select, (a, b, c, d, e))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_ioctl
+* Description : linux ioctl api
+* Input : int a
+* unsigned long b
+* unsigned long c
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_ioctl(int a, unsigned long b, unsigned long c)
+{
+ nsfw_call_ret(ioctl, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_fcntl
+* Description : linux fcntl api
+* Input : int a
+* int b
+* unsigned long c
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_fcntl(int a, int b, unsigned long c)
+{
+ nsfw_call_ret(fcntl, (a, b, c))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_epoll_create
+* Description : linux epoll_create api
+* Input : int a
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_epoll_create(int a)
+{
+ nsfw_call_ret(epoll_create, (a))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_epoll_create1
+* Description : linux epoll_create1 api
+* Input : int a
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_epoll_create1(int a)
+{
+ nsfw_call_ret(epoll_create1, (a))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_epoll_ctl
+* Description : linux epoll_ctl api
+* Input : int a
+* int b
+* int c
+* struct epoll_event *d
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_epoll_ctl(int a, int b, int c, struct epoll_event *d)
+{
+ nsfw_call_ret(epoll_ctl, (a, b, c, d))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_epoll_wait
+* Description : linux epoll_wait api
+* Input : int a
+* struct epoll_event *b
+* int c
+* int d
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int nsfw_base_epoll_wait(int a, struct epoll_event *b, int c, int d)
+{
+ nsfw_call_ret(epoll_wait, (a, b, c, d))
+}
+
+/*****************************************************************************
+* Prototype : nsfw_base_fork
+* Description : linux fork api
+* Input : void
+* Output : None
+* Return Value : pid_t
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+pid_t nsfw_base_fork(void)
+{
+ nsfw_call_ret(fork, ())
+}
+/* *INDENT-ON* */
diff --git a/src/framework/common/base/liblinuxapi/nsfw_getopt.c b/src/framework/common/base/liblinuxapi/nsfw_getopt.c
new file mode 100644
index 0000000..ac7d6bf
--- /dev/null
+++ b/src/framework/common/base/liblinuxapi/nsfw_getopt.c
@@ -0,0 +1,455 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdio.h>
+#include <stdarg.h>
+#include <stdlib.h>
+#include <string.h>
+#include "nsfw_getopt.h"
+#include "nstack_log.h"
+
+char *nsfw_optarg = NULL;
+int nsfw_optind = 1;
+int nsfw_opterr = 1;
+int nsfw_optopt = '?';
+NSTACK_STATIC char *nsfw_optnext = NULL;
+NSTACK_STATIC int posixly_correct = -1;
+NSTACK_STATIC int handle_nonopt_argv = 0;
+NSTACK_STATIC int start = 0;
+NSTACK_STATIC int end = 0;
+
+NSTACK_STATIC void check_gnu_extension (const char *optstring);
+NSTACK_STATIC int nsfw_getopt_internal (int argc, char *const argv[],
+ const char *optstring,
+ const struct option *longopts,
+ int *longindex, int long_only);
+NSTACK_STATIC int nsfw_getopt_shortopts (int argc, char *const argv[],
+ const char *optstring,
+ int long_only);
+NSTACK_STATIC int nsfw_getopt_longopts (int argc, char *const argv[],
+ char *arg, const char *optstring,
+ const struct option *longopts,
+ int *longindex, int *long_only_flag);
+NSTACK_STATIC inline int nsfw_getopt_internal_check_opts (const char
+ *optstring);
+NSTACK_STATIC inline int nsfw_getopt_check_optind ();
+NSTACK_STATIC inline int nsfw_getopt_internal_init (char *const argv[]);
+NSTACK_STATIC inline int nsfw_getopt_longopts_check_longonly (int
+ *long_only_flag,
+ const char
+ *optstring,
+ char *const
+ argv[]);
+
+NSTACK_STATIC void
+check_gnu_extension (const char *optstring)
+{
+ if (optstring[0] == '+' || getenv ("POSIXLY_CORRECT") != NULL)
+ {
+ posixly_correct = 1;
+ }
+ else
+ {
+ posixly_correct = 0;
+ }
+ if (optstring[0] == '-')
+ {
+ handle_nonopt_argv = 1;
+ }
+ else
+ {
+ handle_nonopt_argv = 0;
+ }
+}
+
+int
+nsfw_getopt_long (int argc, char *const argv[], const char *optstring,
+ const struct option *longopts, int *longindex)
+{
+ return nsfw_getopt_internal (argc, argv, optstring, longopts, longindex, 0);
+}
+
+NSTACK_STATIC inline int
+nsfw_getopt_internal_check_opts (const char *optstring)
+{
+ if (NULL == optstring)
+ {
+ return -1;
+ }
+
+ if (nsfw_optopt == '?')
+ {
+ nsfw_optopt = 0;
+ }
+
+ if (posixly_correct == -1)
+ {
+ check_gnu_extension (optstring);
+ }
+
+ if (nsfw_optind == 0)
+ {
+ check_gnu_extension (optstring);
+ nsfw_optind = 1;
+ nsfw_optnext = NULL;
+ }
+
+ switch (optstring[0])
+ {
+ case '+':
+ case '-':
+ optstring++;
+ break;
+ default:
+ break;
+ }
+ return 0;
+}
+
+NSTACK_STATIC inline int
+nsfw_getopt_check_optind ()
+{
+ if (nsfw_optind <= 0)
+ nsfw_optind = 1;
+ return 0;
+}
+
+NSTACK_STATIC inline int
+nsfw_getopt_internal_init (char *const argv[])
+{
+ if (nsfw_optnext == NULL && start != 0)
+ {
+ int last_pos = nsfw_optind - 1;
+
+ nsfw_optind -= end - start;
+ (void) nsfw_getopt_check_optind ();
+
+ while (start < end--)
+ {
+ int i;
+ char *arg = argv[end];
+
+ for (i = end; i < last_pos; i++)
+ {
+ int j = i + 1;
+ ((char **) argv)[i] = argv[j];
+ }
+ ((char const **) argv)[i] = arg;
+ last_pos--;
+ }
+ start = 0;
+ }
+ return 0;
+}
+
+NSTACK_STATIC int
+nsfw_getopt_internal (int argc, char *const argv[], const char *optstring,
+ const struct option *longopts, int *longindex,
+ int long_only)
+{
+
+ (void) nsfw_getopt_internal_check_opts (optstring);
+
+ (void) nsfw_getopt_internal_init (argv);
+
+ if (nsfw_optind >= argc)
+ {
+ nsfw_optarg = NULL;
+ return -1;
+ }
+ if (nsfw_optnext == NULL)
+ {
+ const char *arg = argv[nsfw_optind];
+ if (*arg != '-')
+ {
+ if (handle_nonopt_argv)
+ {
+ nsfw_optarg = argv[nsfw_optind++];
+ start = 0;
+ return 1;
+ }
+ else if (posixly_correct)
+ {
+ nsfw_optarg = NULL;
+ return -1;
+ }
+ else
+ {
+ int i;
+
+ start = nsfw_optind;
+ for (i = nsfw_optind + 1; i < argc; i++)
+ {
+ if (argv[i][0] == '-')
+ {
+ end = i;
+ break;
+ }
+ }
+ if (i == argc)
+ {
+ nsfw_optarg = NULL;
+ return -1;
+ }
+ nsfw_optind = i;
+ arg = argv[nsfw_optind];
+ }
+ }
+ if (strcmp (arg, "--") == 0)
+ {
+ nsfw_optind++;
+ return -1;
+ }
+ if (longopts != NULL && arg[1] == '-')
+ {
+ return nsfw_getopt_longopts (argc, argv, argv[nsfw_optind] + 2,
+ optstring, longopts, longindex, NULL);
+ }
+ }
+
+ if (nsfw_optnext == NULL)
+ {
+ nsfw_optnext = argv[nsfw_optind] + 1;
+ }
+ if (long_only)
+ {
+ int long_only_flag = 0;
+ int rv =
+ nsfw_getopt_longopts (argc, argv, nsfw_optnext, optstring, longopts,
+ longindex, &long_only_flag);
+ if (!long_only_flag)
+ {
+ nsfw_optnext = NULL;
+ return rv;
+ }
+ }
+
+ return nsfw_getopt_shortopts (argc, argv, optstring, long_only);
+}
+
+NSTACK_STATIC int
+nsfw_getopt_shortopts (int argc, char *const argv[], const char *optstring,
+ int long_only)
+{
+ int opt = *nsfw_optnext;
+ const char *os;
+ if (optstring != NULL)
+ {
+ os = strchr (optstring, opt);
+ }
+ else
+ {
+ /* here try to keep same with below behavior */
+ return '?';
+ }
+
+ if (os == NULL)
+ {
+ nsfw_optarg = NULL;
+ if (long_only)
+ {
+ if (':' != optstring[0])
+ {
+ NSFW_LOGERR ("unrecognized option] argv_0=%s, netopt=%s",
+ argv[0], nsfw_optnext);
+ }
+ nsfw_optind++;
+ nsfw_optnext = NULL;
+ }
+ else
+ {
+ nsfw_optopt = opt;
+ if (':' != optstring[0])
+ {
+ NSFW_LOGERR ("invalid option] argv_0=%s, opt=%c", argv[0], opt);
+ }
+ if (*(++nsfw_optnext) == 0)
+ {
+ nsfw_optind++;
+ nsfw_optnext = NULL;
+ }
+ }
+ return '?';
+ }
+ if (os[1] == ':')
+ {
+ if (nsfw_optnext[1] == 0)
+ {
+ nsfw_optind++;
+ if (os[2] == ':')
+ {
+ nsfw_optarg = NULL;
+ }
+ else
+ {
+ if (nsfw_optind == argc)
+ {
+ nsfw_optarg = NULL;
+ nsfw_optopt = opt;
+ if (':' != optstring[0])
+ {
+ NSFW_LOGERR
+ ("option requires an argument] argv_0=%s, opt=%c",
+ argv[0], opt);
+ }
+ return optstring[0] == ':' ? ':' : '?';
+ }
+ nsfw_optarg = argv[nsfw_optind];
+ nsfw_optind++;
+ }
+ }
+ else
+ {
+ nsfw_optarg = nsfw_optnext + 1;
+ nsfw_optind++;
+ }
+ nsfw_optnext = NULL;
+ }
+ else
+ {
+ nsfw_optarg = NULL;
+ if (nsfw_optnext[1] == 0)
+ {
+ nsfw_optnext = NULL;
+ nsfw_optind++;
+ }
+ else
+ {
+ nsfw_optnext++;
+ }
+ }
+ return opt;
+}
+
+NSTACK_STATIC inline int
+nsfw_getopt_longopts_check_longonly (int *long_only_flag,
+ const char *optstring,
+ char *const argv[])
+{
+ if (long_only_flag)
+ {
+ *long_only_flag = 1;
+ }
+ else
+ {
+ if (':' != optstring[0])
+ {
+ NSFW_LOGERR ("unrecognized option] argv_0=%s, option=%s", argv[0],
+ argv[nsfw_optind]);
+ }
+ nsfw_optind++;
+ }
+ return 0;
+}
+
+NSTACK_STATIC int
+nsfw_getopt_longopts (int argc, char *const argv[], char *arg,
+ const char *optstring, const struct option *longopts,
+ int *longindex, int *long_only_flag)
+{
+ char *val = NULL;
+ const struct option *opt;
+ size_t namelen;
+ int idx;
+
+ if ((longopts == NULL) || (arg == NULL))
+ {
+ return -1;
+ }
+
+ for (idx = 0; longopts[idx].name != NULL; idx++)
+ {
+ opt = &longopts[idx];
+ namelen = strlen (opt->name);
+
+ if (strncmp (arg, opt->name, namelen) == 0)
+ {
+ switch (arg[namelen])
+ {
+ case '\0':
+ switch (opt->has_arg)
+ {
+ case nsfw_required_argument:
+ nsfw_optind++;
+
+ if (nsfw_optind == argc)
+ {
+ nsfw_optarg = NULL;
+ nsfw_optopt = opt->val;
+ if (':' != optstring[0])
+ {
+ NSFW_LOGERR
+ ("requires an argument] argv_0=%s, opt name=%s",
+ argv[0], opt->name);
+ }
+ return optstring[0] == ':' ? ':' : '?';
+ }
+
+ val = argv[nsfw_optind];
+ break;
+
+ default:
+ break;
+ }
+
+ goto found;
+
+ case '=':
+ if (opt->has_arg == nsfw_no_argument)
+ {
+ const char *hyphens =
+ (argv[nsfw_optind][1] == '-') ? "--" : "-";
+ nsfw_optind++;
+ nsfw_optarg = NULL;
+ nsfw_optopt = opt->val;
+ if (':' != optstring[0])
+ {
+ NSFW_LOGERR
+ ("doesn't allow an argument] argv_0=%s, hyphens=%s, opt name=%s",
+ argv[0], hyphens, opt->name);
+ }
+ return '?';
+ }
+
+ val = arg + namelen + 1;
+ goto found;
+
+ default:
+ break;
+ }
+ }
+ }
+
+ (void) nsfw_getopt_longopts_check_longonly (long_only_flag, optstring,
+ argv);
+ return '?';
+
+found:
+ nsfw_optarg = val;
+ nsfw_optind++;
+
+ if (opt->flag)
+ {
+ *opt->flag = opt->val;
+ }
+
+ if (longindex)
+ {
+ *longindex = idx;
+ }
+
+ return opt->flag ? 0 : opt->val;
+}
diff --git a/src/framework/common/base/liblinuxapi/nsfw_lock_file.c b/src/framework/common/base/liblinuxapi/nsfw_lock_file.c
new file mode 100644
index 0000000..0ec196f
--- /dev/null
+++ b/src/framework/common/base/liblinuxapi/nsfw_lock_file.c
@@ -0,0 +1,174 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <unistd.h>
+
+#include "types.h"
+#include "nstack_securec.h"
+#include "nsfw_init.h"
+#include "common_mem_api.h"
+
+#include "nstack_log.h"
+#include "nsfw_maintain_api.h"
+#include "nsfw_mgr_com_api.h"
+
+#include "nsfw_base_linux_api.h"
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define NSFW_FILE_PATH_LEN 128
+#define LOCK_FOLDER "/ip_module/"
+#define LOCK_SUFFIX ".pid"
+
+#define read_lock(fd, offset, whence, len) nsfw_lock_reg((fd), F_SETLK, F_RDLCK, (offset), (whence), (len))
+#define readw_lock(fd, offset, whence, len) nsfw_lock_reg((fd), F_SETLKW, F_RDLCK, (offset), (whence), (len))
+#define write_lock(fd, offset, whence, len) nsfw_lock_reg((fd), F_SETLK, F_WRLCK, (offset), (whence), (len))
+#define writew_lock(fd, offset, whence, len) nsfw_lock_reg((fd), F_SETLKW, F_WRLCK, (offset), (whence), (len))
+#define un_lock(fd, offset, whence, len) nsfw_lock_reg((fd), F_SETLK, F_UNLCK, (offset), (whence), (len))
+
+i32
+nsfw_lock_reg (i32 fd, i32 cmd, i32 type, off_t offset, i32 whence, off_t len)
+{
+ struct flock lock_file;
+ lock_file.l_type = type;
+ lock_file.l_start = offset;
+ lock_file.l_whence = whence;
+ lock_file.l_len = len;
+ return (fcntl (fd, cmd, &lock_file));
+}
+
+/*****************************************************************************
+* Prototype : nsfw_proc_start_with_lock
+* Description : lock file start
+* Input : u8 proc_type
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_proc_start_with_lock (u8 proc_type)
+{
+ NSFW_LOGINF ("lock_file init]type=%u", proc_type);
+ char *module_name = nsfw_get_proc_name (proc_type);
+ if (NULL == module_name)
+ {
+ NSFW_LOGERR ("proc type error]proc_type=%u", proc_type);
+ return 0;
+ }
+
+ const char *directory = NSFW_DOMAIN_DIR;
+ const char *home_dir = getenv ("HOME");
+
+ if (getuid () != 0 && home_dir != NULL)
+ {
+ directory = home_dir;
+ }
+
+ int ret;
+ char lock_fpath[NSFW_FILE_PATH_LEN] = { 0 };
+ ret = STRCPY_S (lock_fpath, NSFW_FILE_PATH_LEN, directory);
+ if (EOK != ret)
+ {
+ NSFW_LOGERR ("lock init STRCPY_S failed]ret=%d", ret);
+ return -1;
+ }
+
+ ret = STRCAT_S (lock_fpath, NSFW_FILE_PATH_LEN, LOCK_FOLDER);
+ if (EOK != ret)
+ {
+ NSFW_LOGERR ("lock init STRCAT_S failed]ret=%d", ret);
+ return -1;
+ }
+
+ ret = STRCAT_S (lock_fpath, NSFW_FILE_PATH_LEN, module_name);
+ if (EOK != ret)
+ {
+ NSFW_LOGERR ("lock init STRCAT_S failed]ret=%d", ret);
+ return -1;
+ }
+
+ ret = STRCAT_S (lock_fpath, NSFW_FILE_PATH_LEN, LOCK_SUFFIX);
+ if (EOK != ret)
+ {
+ NSFW_LOGERR ("lock init STRCAT_S failed]ret=%d", ret);
+ return -1;
+ }
+
+ i32 fd;
+ if ((fd = open (lock_fpath, O_RDWR | O_CREAT, 0640)) == -1)
+ { /* file permission no large than 0640 */
+ NSFW_LOGERR ("open lock file error!]path=%s,error = %d", lock_fpath,
+ errno);
+ return -1;
+ }
+
+ int rc = nsfw_set_close_on_exec (fd);
+ if (rc == -1)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("set exec err]fd=%d, errno=%d", fd, errno);
+ return -1;
+ }
+
+ if (write_lock (fd, 0, SEEK_SET, 0) < 0)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("get lock file error!]path=%s,error = %d", lock_fpath,
+ errno);
+ return -1;
+ }
+
+ char buf[32] = { 0 };
+ if (ftruncate (fd, 0) < 0)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("ftruncate file error!]path=%s,error = %d", lock_fpath,
+ errno);
+ return -1;
+ }
+
+ ret =
+ SNPRINTF_S (buf, sizeof (buf), sizeof (buf) - 1, "%ld", (long) getpid ());
+ if (-1 == ret)
+ {
+ NSTCP_LOGERR ("SNPRINTF_S failed]ret=%d", ret);
+ (void) nsfw_base_close (fd);
+ return -1;
+ }
+
+ if (write (fd, buf, strlen (buf) + 1) < 0)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("write file error!]path=%s,error = %d", lock_fpath, errno);
+ return -1;
+ }
+
+ return 0;
+}
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/common/data_struct/eprb_tree.c b/src/framework/common/data_struct/eprb_tree.c
new file mode 100644
index 0000000..c8af17c
--- /dev/null
+++ b/src/framework/common/data_struct/eprb_tree.c
@@ -0,0 +1,492 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "eprb_tree.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+/*
+ * This function returns the first node (in sort order) of the tree.
+ */
+struct ep_rb_node *
+ep_rb_first (const struct ep_rb_root *root)
+{
+ if (NULL == root)
+ return NULL;
+
+ struct ep_rb_node *n;
+ n = (struct ep_rb_node *) ADDR_SHTOL (root->rb_node);
+
+ if (!n)
+ {
+ return NULL;
+ }
+
+ while (n->rb_left)
+ {
+ n = (struct ep_rb_node *) ADDR_SHTOL (n->rb_left);
+ }
+
+ return n;
+}
+
+void
+__ep_rb_rotate_left (struct ep_rb_node *X, struct ep_rb_root *root)
+{
+ /**************************
+ * rotate Node X to left *
+ **************************/
+ struct ep_rb_node *Y = (struct ep_rb_node *) ADDR_SHTOL (X->rb_right);
+
+ /* estblish X->Right link */
+ X->rb_right = Y->rb_left;
+
+ if (Y->rb_left != NULL)
+ {
+ ((struct ep_rb_node *) ADDR_SHTOL (Y->rb_left))->rb_parent =
+ (struct ep_rb_node *) ADDR_LTOSH_EXT (X);
+ }
+
+ /* estblish Y->Parent link */
+ Y->rb_parent = X->rb_parent;
+
+ if (X->rb_parent)
+ {
+ struct ep_rb_node *xParent =
+ (struct ep_rb_node *) ADDR_SHTOL (X->rb_parent);
+
+ if (X == ADDR_SHTOL (xParent->rb_left))
+ {
+ xParent->rb_left = (struct ep_rb_node *) ADDR_LTOSH_EXT (Y);
+ }
+ else
+ {
+ xParent->rb_right = (struct ep_rb_node *) ADDR_LTOSH_EXT (Y);
+ }
+ }
+ else
+ {
+ root->rb_node = (struct ep_rb_node *) ADDR_LTOSH_EXT (Y);
+ }
+
+ /* link X and Y */
+ Y->rb_left = (struct ep_rb_node *) ADDR_LTOSH_EXT (X);
+ X->rb_parent = (struct ep_rb_node *) ADDR_LTOSH_EXT (Y);
+
+ return;
+}
+
+void
+__ep_rb_rotate_right (struct ep_rb_node *X, struct ep_rb_root *root)
+{
+ /****************************
+ * rotate Node X to right *
+ ****************************/
+ struct ep_rb_node *Y = (struct ep_rb_node *) ADDR_SHTOL (X->rb_left);
+
+ /* estblish X->Left link */
+ X->rb_left = Y->rb_right;
+
+ if (Y->rb_right != NULL)
+ {
+ ((struct ep_rb_node *) ADDR_SHTOL (Y->rb_right))->rb_parent =
+ (struct ep_rb_node *) ADDR_LTOSH_EXT (X);
+ }
+
+ /* estblish Y->Parent link */
+ Y->rb_parent = X->rb_parent;
+
+ if (X->rb_parent)
+ {
+ struct ep_rb_node *xParent =
+ (struct ep_rb_node *) ADDR_SHTOL (X->rb_parent);
+
+ if (X == (struct ep_rb_node *) ADDR_SHTOL (xParent->rb_right))
+ {
+ xParent->rb_right = (struct ep_rb_node *) ADDR_LTOSH_EXT (Y);
+ }
+ else
+ {
+ xParent->rb_left = (struct ep_rb_node *) ADDR_LTOSH_EXT (Y);
+ }
+ }
+ else
+ {
+ root->rb_node = (struct ep_rb_node *) ADDR_LTOSH_EXT (Y);
+ }
+
+ /* link X and Y */
+ Y->rb_right = (struct ep_rb_node *) ADDR_LTOSH_EXT (X);
+ X->rb_parent = (struct ep_rb_node *) ADDR_LTOSH_EXT (Y);
+
+ return;
+}
+
+#define EP_RBTREE_PARENT(X) ((struct ep_rb_node*) ADDR_SHTOL((X)->rb_parent))
+#define EP_RBTREE_GRANDF(X) EP_RBTREE_PARENT(EP_RBTREE_PARENT(X))
+
+/* X, Y are for application */
+void
+ep_rb_insert_color (struct ep_rb_node *X, struct ep_rb_root *root)
+{
+ /*************************************
+ * maintain red-black tree balance *
+ * after inserting node X *
+ *************************************/
+ /* check red-black properties */
+ while (X != (struct ep_rb_node *) ADDR_SHTOL (root->rb_node)
+ && EP_RBTREE_PARENT (X)->color == EP_RB_RED)
+ {
+ /* we have a violation */
+ if (X->rb_parent == EP_RBTREE_GRANDF (X)->rb_left)
+ {
+ struct ep_rb_node *Y =
+ (struct ep_rb_node *) ADDR_SHTOL (EP_RBTREE_GRANDF (X)->rb_right);
+
+ if (Y && Y->color == EP_RB_RED)
+ {
+
+ /* uncle is red */
+ EP_RBTREE_PARENT (X)->color = EP_RB_BLACK;
+ Y->color = EP_RB_BLACK;
+ EP_RBTREE_GRANDF (X)->color = EP_RB_RED;
+ X = EP_RBTREE_GRANDF (X);
+ }
+ else
+ {
+
+ /* uncle is black */
+ if (X ==
+ (struct ep_rb_node *)
+ ADDR_SHTOL (EP_RBTREE_PARENT (X)->rb_right))
+ {
+ /* make X a left child */
+ X = EP_RBTREE_PARENT (X);
+ __ep_rb_rotate_left (X, root);
+ }
+
+ /* recolor and rotate */
+ EP_RBTREE_PARENT (X)->color = EP_RB_BLACK;
+ EP_RBTREE_GRANDF (X)->color = EP_RB_RED;
+ __ep_rb_rotate_right (EP_RBTREE_GRANDF (X), root);
+ }
+ }
+ else
+ {
+ /* miror image of above code */
+ struct ep_rb_node *Y =
+ (struct ep_rb_node *) ADDR_SHTOL (EP_RBTREE_GRANDF (X)->rb_left);
+
+ if (Y && (Y->color == EP_RB_RED))
+ {
+
+ /* uncle is red */
+ EP_RBTREE_PARENT (X)->color = EP_RB_BLACK;
+ Y->color = EP_RB_BLACK;
+ EP_RBTREE_GRANDF (X)->color = EP_RB_RED;
+ X = EP_RBTREE_GRANDF (X);
+ }
+ else
+ {
+
+ /* uncle is black */
+ if (X ==
+ (struct ep_rb_node *)
+ ADDR_SHTOL (EP_RBTREE_PARENT (X)->rb_left))
+ {
+ X = EP_RBTREE_PARENT (X);
+ __ep_rb_rotate_right (X, root);
+ }
+
+ EP_RBTREE_PARENT (X)->color = EP_RB_BLACK;
+ EP_RBTREE_GRANDF (X)->color = EP_RB_RED;
+ __ep_rb_rotate_left (EP_RBTREE_GRANDF (X), root);
+ }
+ }
+ }
+
+ ((struct ep_rb_node *) ADDR_SHTOL (root->rb_node))->color = EP_RB_BLACK;
+
+ return;
+}
+
+void
+__ep_rb_erase_color (struct ep_rb_node *X, struct ep_rb_node *Parent,
+ struct ep_rb_root *root)
+{
+ /*************************************
+ * maintain red-black tree balance *
+ * after deleting node X *
+ *************************************/
+ while (X != (struct ep_rb_node *) ADDR_SHTOL (root->rb_node)
+ && (!X || X->color == EP_RB_BLACK))
+ {
+
+ if (Parent == NULL)
+ {
+ break;
+ }
+
+ if (X == (struct ep_rb_node *) ADDR_SHTOL (Parent->rb_left))
+ {
+ struct ep_rb_node *W =
+ (struct ep_rb_node *) ADDR_SHTOL (Parent->rb_right);
+
+ if (W->color == EP_RB_RED)
+ {
+ W->color = EP_RB_BLACK;
+ Parent->color = EP_RB_RED; /* Parent != NIL? */
+ __ep_rb_rotate_left (Parent, root);
+ W = (struct ep_rb_node *) ADDR_SHTOL (Parent->rb_right);
+ }
+
+ if ((!W->rb_left
+ || ((struct ep_rb_node *) ADDR_SHTOL (W->rb_left))->color ==
+ EP_RB_BLACK) && (!W->rb_right
+ || ((struct ep_rb_node *)
+ ADDR_SHTOL (W->rb_right))->color ==
+ EP_RB_BLACK))
+ {
+ W->color = EP_RB_RED;
+ X = Parent;
+ Parent = (struct ep_rb_node *) ADDR_SHTOL (X->rb_parent);
+ }
+ else
+ {
+ if (!W->rb_right
+ || ((struct ep_rb_node *) ADDR_SHTOL (W->rb_right))->color
+ == EP_RB_BLACK)
+ {
+ if (W->rb_left != NULL)
+ {
+ ((struct ep_rb_node *) ADDR_SHTOL (W->rb_left))->color
+ = EP_RB_BLACK;
+ }
+
+ W->color = EP_RB_RED;
+ __ep_rb_rotate_right (W, root);
+ W = (struct ep_rb_node *) ADDR_SHTOL (Parent->rb_right);
+ }
+
+ W->color = Parent->color;
+ Parent->color = EP_RB_BLACK;
+
+ if (((struct ep_rb_node *) ADDR_SHTOL (W->rb_right))->color !=
+ EP_RB_BLACK)
+ {
+ ((struct ep_rb_node *) ADDR_SHTOL (W->rb_right))->color =
+ EP_RB_BLACK;
+ }
+
+ __ep_rb_rotate_left (Parent, root);
+ X = (struct ep_rb_node *) ADDR_SHTOL (root->rb_node);
+ break;
+ }
+ }
+ else
+ {
+
+ struct ep_rb_node *W =
+ (struct ep_rb_node *) ADDR_SHTOL (Parent->rb_left);
+
+ if (W->color == EP_RB_RED)
+ {
+ W->color = EP_RB_BLACK;
+ Parent->color = EP_RB_RED; /* Parent != NIL? */
+ __ep_rb_rotate_right (Parent, root);
+ W = (struct ep_rb_node *) ADDR_SHTOL (Parent->rb_left);
+ }
+
+ if ((!W->rb_left
+ || (((struct ep_rb_node *) ADDR_SHTOL (W->rb_left))->color ==
+ EP_RB_BLACK)) && (!W->rb_right
+ ||
+ (((struct ep_rb_node *)
+ ADDR_SHTOL (W->rb_right))->color ==
+ EP_RB_BLACK)))
+ {
+ W->color = EP_RB_RED;
+ X = Parent;
+ Parent = (struct ep_rb_node *) ADDR_SHTOL (X->rb_parent);
+ }
+ else
+ {
+ if (!W->rb_left
+ || ((struct ep_rb_node *) ADDR_SHTOL (W->rb_left))->color
+ == EP_RB_BLACK)
+ {
+ if (W->rb_right != NULL)
+ {
+ ((struct ep_rb_node *)
+ ADDR_SHTOL (W->rb_right))->color = EP_RB_BLACK;
+ }
+
+ W->color = EP_RB_RED;
+ __ep_rb_rotate_left (W, root);
+ W = (struct ep_rb_node *) ADDR_SHTOL (Parent->rb_left);
+ }
+
+ W->color = Parent->color;
+ Parent->color = EP_RB_BLACK;
+
+ if (((struct ep_rb_node *) ADDR_SHTOL (W->rb_left))->color !=
+ EP_RB_BLACK)
+ {
+ ((struct ep_rb_node *) ADDR_SHTOL (W->rb_left))->color =
+ EP_RB_BLACK;
+ }
+
+ __ep_rb_rotate_right (Parent, root);
+ X = (struct ep_rb_node *) ADDR_SHTOL (root->rb_node);
+ break;
+ }
+ }
+ }
+
+ if (X)
+ {
+ X->color = EP_RB_BLACK;
+ }
+
+ return;
+}
+
+void
+ep_rb_erase (struct ep_rb_node *node, struct ep_rb_root *root)
+{
+ struct ep_rb_node *child, *parent;
+ int color;
+
+ if (!node->rb_left)
+ {
+ child = (struct ep_rb_node *) ADDR_SHTOL (node->rb_right);
+ }
+ else if (!node->rb_right)
+ {
+ child = (struct ep_rb_node *) ADDR_SHTOL (node->rb_left);
+ }
+ else
+ {
+ struct ep_rb_node *old = node, *left;
+
+ node = (struct ep_rb_node *) ADDR_SHTOL (node->rb_right);
+
+ while ((left =
+ (struct ep_rb_node *) ADDR_SHTOL (node->rb_left)) != NULL)
+ {
+ node = left;
+ }
+
+ if (old->rb_parent)
+ {
+ struct ep_rb_node *oldParent =
+ (struct ep_rb_node *) ADDR_SHTOL (old->rb_parent);
+
+ if (oldParent->rb_left ==
+ (struct ep_rb_node *) ADDR_LTOSH_EXT (old))
+ {
+ oldParent->rb_left =
+ (struct ep_rb_node *) ADDR_LTOSH_EXT (node);
+ }
+ else
+ {
+ oldParent->rb_right =
+ (struct ep_rb_node *) ADDR_LTOSH_EXT (node);
+ }
+ }
+ else
+ {
+ root->rb_node = (struct ep_rb_node *) ADDR_LTOSH_EXT (node);
+ }
+
+ child = (struct ep_rb_node *) ADDR_SHTOL (node->rb_right);
+ parent = (struct ep_rb_node *) ADDR_SHTOL (node->rb_parent);
+ color = node->color;
+
+ if (parent == old)
+ {
+ parent = node;
+ }
+ else
+ {
+ if (child)
+ {
+ child->rb_parent =
+ (struct ep_rb_node *) ADDR_LTOSH_EXT (parent);
+ }
+
+ parent->rb_left = (struct ep_rb_node *) ADDR_LTOSH_EXT (child);
+
+ node->rb_right = old->rb_right;
+ ((struct ep_rb_node *) ADDR_SHTOL (old->rb_right))->rb_parent =
+ (struct ep_rb_node *) ADDR_LTOSH_EXT (node);
+ }
+
+ node->color = old->color;
+ node->rb_parent = old->rb_parent;
+ node->rb_left = old->rb_left;
+ ((struct ep_rb_node *) ADDR_SHTOL (old->rb_left))->rb_parent =
+ (struct ep_rb_node *) ADDR_LTOSH_EXT (node);
+
+ if (color == EP_RB_BLACK)
+ {
+ __ep_rb_erase_color (child, parent, root);
+ }
+
+ return;
+
+ }
+
+ parent = (struct ep_rb_node *) ADDR_SHTOL (node->rb_parent);
+ color = node->color;
+
+ if (child)
+ {
+ child->rb_parent = (struct ep_rb_node *) ADDR_LTOSH_EXT (parent);
+ }
+
+ if (parent)
+ {
+ if (parent->rb_left == (struct ep_rb_node *) ADDR_LTOSH_EXT (node))
+ {
+ parent->rb_left = (struct ep_rb_node *) ADDR_LTOSH_EXT (child);
+ }
+ else
+ {
+ parent->rb_right = (struct ep_rb_node *) ADDR_LTOSH_EXT (child);
+ }
+ }
+ else
+ {
+ root->rb_node = (struct ep_rb_node *) ADDR_LTOSH_EXT (child);
+ }
+
+ if (color == EP_RB_BLACK)
+ {
+ __ep_rb_erase_color (child, parent, root);
+ }
+ return;
+}
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
diff --git a/src/framework/common/data_struct/list.c b/src/framework/common/data_struct/list.c
new file mode 100644
index 0000000..7645640
--- /dev/null
+++ b/src/framework/common/data_struct/list.c
@@ -0,0 +1,163 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "list.h"
+
+/**
+ * list_empty - tests whether a list is empty
+ * @head: the list to test.
+ */
+inline int
+list_empty (const struct list_head *head)
+{
+ return head->next == head;
+}
+
+inline void
+list_del (struct list_head *entry)
+{
+ if (entry->prev == NULL || entry->next == NULL)
+ {
+ return;
+ }
+ entry->next->prev = entry->prev;
+ entry->prev->next = entry->next;
+ entry->next = NULL;
+ entry->prev = NULL;
+}
+
+/*get the first element of the list, need to check if list empty or not before calling this.*/
+inline struct list_head *
+list_get_first (struct list_head *head)
+{
+ return head->next;
+}
+
+inline void
+list_add (struct list_head *newp, struct list_head *head)
+{
+ head->next->prev = newp;
+ newp->next = head->next;
+ newp->prev = head;
+ head->next = newp;
+}
+
+inline void
+list_link (struct list_head *newhead, struct list_head *head)
+{
+ struct list_head *tmp;
+
+ newhead->prev->next = head;
+ head->prev->next = newhead;
+
+ tmp = newhead->prev;
+ newhead->prev = head->prev;
+ head->prev = tmp;
+}
+
+inline void
+list_add_tail (struct list_head *newp, struct list_head *head)
+{
+ list_add (newp, head->prev);
+}
+
+inline void
+hlist_del_init (struct hlist_node *n)
+{
+ struct hlist_node *next = n->next;
+ struct hlist_node **pprev = n->pprev;
+
+ if (pprev == NULL && next == NULL)
+ {
+ return;
+ }
+
+ if (pprev)
+ {
+ *pprev = next;
+ }
+
+ if (next)
+ {
+ next->pprev = pprev;
+ }
+
+ n->next = NULL;
+ n->pprev = NULL;
+}
+
+/**
+ * next must be != NULL
+ * add n node before next node
+ *
+ * @n: new node
+ * @next: node in the hlist
+ */
+inline void
+hlist_add_before (struct hlist_node *n, struct hlist_node *next)
+{
+ n->pprev = next->pprev;
+ n->next = next;
+ next->pprev = &n->next;
+ *(n->pprev) = n;
+}
+
+/**
+ * next must be != NULL
+ * add n node after next node
+ * actual behavior is add after n
+ * @n: node in the hlist
+ * @next: new node
+ */
+inline void
+hlist_add_after (struct hlist_node *n, struct hlist_node *next)
+{
+ next->next = n->next;
+ n->next = next;
+ next->pprev = &n->next;
+ if (next->next)
+ {
+ next->next->pprev = &next->next;
+ }
+}
+
+/* add after the head */
+inline void
+hlist_add_head (struct hlist_node *n, struct hlist_head *h)
+{
+ struct hlist_node *first = h->first;
+
+ n->next = first;
+ if (first)
+ {
+ first->pprev = &n->next;
+ }
+
+ h->first = n;
+ n->pprev = &h->first;
+}
+
+inline int
+hlist_unhashed (const struct hlist_node *h)
+{
+ return !h->pprev;
+}
+
+inline int
+hlist_empty (const struct hlist_head *h)
+{
+ return !h->first;
+}
diff --git a/src/framework/common/data_struct/pidinfo.c b/src/framework/common/data_struct/pidinfo.c
new file mode 100644
index 0000000..08e551f
--- /dev/null
+++ b/src/framework/common/data_struct/pidinfo.c
@@ -0,0 +1,125 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "pidinfo.h"
+#include "nstack_securec.h"
+
+inline i32
+nsfw_pidinfo_init (nsfw_pidinfo * pidinfo)
+{
+ int retVal =
+ MEMSET_S (pidinfo, sizeof (nsfw_pidinfo), 0, sizeof (nsfw_pidinfo));
+ if (EOK != retVal)
+ {
+ return -1;
+ }
+
+ return 0;
+}
+
+inline int
+nsfw_add_pid (nsfw_pidinfo * pidinfo, u32 pid)
+{
+ u32 i;
+
+ for (i = 0; i < NSFW_MAX_FORK_NUM; i++)
+ {
+ if ((0 == pidinfo->apid[i])
+ && (__sync_bool_compare_and_swap (&pidinfo->apid[i], 0, pid)))
+ {
+ if (pidinfo->used_size < i + 1)
+ {
+ pidinfo->used_size = i + 1;
+ }
+ return 0;
+ }
+ }
+ return -1;
+}
+
+inline int
+nsfw_del_pid (nsfw_pidinfo * pidinfo, u32 pid)
+{
+ u32 i;
+
+ for (i = 0; i < pidinfo->used_size && i < NSFW_MAX_FORK_NUM; i++)
+ {
+ if (pid == pidinfo->apid[i])
+ {
+ pidinfo->apid[i] = 0;
+ return 0;
+ }
+ }
+ return -1;
+}
+
+inline int
+nsfw_del_last_pid (nsfw_pidinfo * pidinfo, u32 pid)
+{
+ u32 i;
+ int count = 0;
+ int deleted = 0;
+ for (i = 0; i < pidinfo->used_size && i < NSFW_MAX_FORK_NUM; i++)
+ {
+ if (pid == pidinfo->apid[i])
+ {
+ pidinfo->apid[i] = 0;
+ deleted = 1;
+ continue;
+ }
+
+ if (pidinfo->apid[i] != 0)
+ {
+ ++count;
+ }
+ }
+
+ if (!deleted)
+ {
+ return -1;
+ }
+
+ return count;
+}
+
+inline int
+nsfw_pid_exist (nsfw_pidinfo * pidinfo, u32 pid)
+{
+ u32 i;
+
+ for (i = 0; i < pidinfo->used_size && i < NSFW_MAX_FORK_NUM; i++)
+ {
+ if (pid == pidinfo->apid[i])
+ {
+ return 1;
+ }
+ }
+ return 0;
+}
+
+inline int
+nsfw_pidinfo_empty (nsfw_pidinfo * pidinfo)
+{
+ u32 i;
+ for (i = 0; i < pidinfo->used_size && i < NSFW_MAX_FORK_NUM; i++)
+ {
+ if (pidinfo->apid[i] != 0)
+ {
+ return 0;
+ }
+ }
+ return 1;
+}
diff --git a/src/framework/common/data_struct/sha256.c b/src/framework/common/data_struct/sha256.c
new file mode 100644
index 0000000..504b365
--- /dev/null
+++ b/src/framework/common/data_struct/sha256.c
@@ -0,0 +1,397 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+/*Possible access of out-of-bounds pointer:
+ The algorithms has been tested on purify. So no
+ out of bounds access possible.*/
+
+/*Possible creation of out-of-bounds pointer
+ No Out of bounds pointers are created.- false positive.*/
+
+#include <string.h> /* for mem copy function etc. */
+#include "sha256.h"
+#include "nstack_securec.h"
+#include "types.h"
+#include "nstack_log.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+#define rotl32(x,n) (((x) << n) | ((x) >> (32 - n)))
+#define rotr32(x,n) (((x) >> n) | ((x) << (32 - n)))
+
+#if !defined(bswap_32)
+#define bswap_32(x) ((rotr32((x), 24) & 0x00ff00ff) | (rotr32((x), 8) & 0xff00ff00))
+#endif
+
+#ifdef LITTLE_ENDIAN
+#define SWAP_BYTES
+#else
+#undef SWAP_BYTES
+#endif
+
+#define ch(x,y,z) ((z) ^ ((x) & ((y) ^ (z))))
+#define maj(x,y,z) (((x) & (y)) | ((z) & ((x) ^ (y))))
+
+ /* round transforms for SHA256 and SHA512 compression functions */
+
+#define vf(n,i) v[(n - i) & 7]
+
+#define hf(i) (p[i & 15] += \
+ g_1(p[(i + 14) & 15]) + p[(i + 9) & 15] + g_0(p[(i + 1) & 15]))
+
+#define v_cycle(i,j) \
+{ \
+ vf(7,i) += (j ? hf(i) : p[i]) + k_0[i+j] \
+ + s_1(vf(4,i)) + ch(vf(4,i),vf(5,i),vf(6,i)); \
+ vf(3,i) += vf(7,i); \
+ vf(7,i) += s_0(vf(0,i))+ maj(vf(0,i),vf(1,i),vf(2,i)); \
+}
+
+#define SHA256_MASK (SHA256_BLOCK_SIZE - 1)
+
+#if defined(SWAP_BYTES)
+#define bsw_32(p,n) \
+{ \
+ u32 _i = (n); \
+ while (_i--) \
+ { \
+ ((u32*)p)[_i] = bswap_32(((u32*)p)[_i]); \
+ } \
+}
+
+#else
+#define bsw_32(p,n)
+#endif
+
+#define s_0(x) (rotr32((x), 2) ^ rotr32((x), 13) ^ rotr32((x), 22))
+#define s_1(x) (rotr32((x), 6) ^ rotr32((x), 11) ^ rotr32((x), 25))
+#define g_0(x) (rotr32((x), 7) ^ rotr32((x), 18) ^ ((x) >> 3))
+#define g_1(x) (rotr32((x), 17) ^ rotr32((x), 19) ^ ((x) >> 10))
+#define k_0 k256
+
+/* rotated SHA256 round definition. Rather than swapping variables as in */
+/* FIPS-180, different variables are 'rotated' on each round, returning */
+/* to their starting positions every eight rounds */
+
+#define q(n) v##n
+
+#define one_cycle(a,b,c,d,e,f,g,h,k,w) \
+ q(h) += s_1(q(e)) + ch(q(e), q(f), q(g)) + k + w; \
+ q(d) += q(h); q(h) += s_0(q(a)) + maj(q(a), q(b), q(c))
+
+/*
+Description: SHA256 mixing data
+Value Range: None
+Access: Used to mix with data to create SHA256 key.
+Remarks:
+*/
+static const u32 k256[64] = {
+ 010242427630, 016115642221, 026560175717, 035155355645,
+ 07125541133, 013174210761, 022217701244, 025307057325,
+ 033001725230, 02240655401, 04414302676, 012503076703,
+ 016257456564, 020067530776, 023367003247, 030146770564,
+ 034446664701, 035757443606, 01760316706, 04403120714,
+ 05572226157, 011235102252, 013454124734, 016676304332,
+ 023017450522, 025014343155, 026000623710, 027726277707,
+ 030670005763, 032551710507, 0662461521, 02412224547,
+ 04755605205, 05606620470, 011513066774, 012316006423,
+ 014502471524, 016632405273, 020160544456, 022234426205,
+ 024257764241, 025006463113, 030222705560, 030733050643,
+ 032144564031, 032646203044, 036403432605, 02032520160,
+ 03151140426, 03615666010, 04722073514, 06454136265,
+ 07107006263, 011666125112, 013347145117, 015013467763,
+ 016443701356, 017051261557, 020462074024, 021461601010,
+ 022057577772, 024424066353, 027676321767, 030634274362,
+};
+
+/* Compile 64 bytes of hash data into SHA256 digest value */
+/* NOTE: this routine assumes that the byte order in the */
+/* ctx->wbuf[] at this point is such that low address bytes */
+/* in the ORIGINAL byte stream will go into the high end of */
+/* words on BOTH big and little endian systems */
+
+#define v_ v
+#define ptr p
+
+/*===========================================================================*\
+ Function :Sha256_compile__
+ Description : This function generates the digest value for SHA256.
+ Compile 64 bytes of hash data into SHA256 digest value
+ Calls : mem copy - Secure mem copy function.
+ Called by :
+ Return : This is a static internal function which doesn't return any value.
+ Parameters :
+ SHA256_CTX ctx[1] -
+ Note : this routine assumes that the byte order in the
+ ctx->wbuf[] at this point is such that low address bytes in
+ the ORIGINAL byte stream will go into the high end of
+ words on BOTH big and little endian systems.
+\*===========================================================================*/
+NSTACK_STATIC void
+Sha256_compile__ (SHA256_CTX ctx[1])
+{
+
+ /* macros defined above to this function i.e. v_ and ptr should not be removed */
+ /* v_cycle - for 0 to 15 */
+ u32 j;
+ u32 *ptr = ctx->wbuf;
+ u32 v_[8];
+
+ int ret = MEMCPY_S (v_, 8 * sizeof (u32), ctx->hash, 8 * sizeof (u32));
+ if (EOK != ret)
+ {
+ NSPOL_LOGERR ("MEMCPY_S failed");
+ return;
+ }
+
+ for (j = 0; j < 64; j += 16)
+ {
+ /*v_cycle operations from 0 to 15 */
+ v_cycle (0, j);
+ v_cycle (1, j);
+ v_cycle (2, j);
+ v_cycle (3, j);
+ v_cycle (4, j);
+ v_cycle (5, j);
+ v_cycle (6, j);
+ v_cycle (7, j);
+ v_cycle (8, j);
+ v_cycle (9, j);
+ v_cycle (10, j);
+ v_cycle (11, j);
+ v_cycle (12, j);
+ v_cycle (13, j);
+ v_cycle (14, j);
+ v_cycle (15, j);
+ }
+
+ /* update the context */
+ ctx->hash[0] += v_[0];
+ ctx->hash[1] += v_[1];
+ ctx->hash[2] += v_[2];
+ ctx->hash[3] += v_[3];
+ ctx->hash[4] += v_[4];
+ ctx->hash[5] += v_[5];
+ ctx->hash[6] += v_[6];
+ ctx->hash[7] += v_[7];
+
+ return;
+}
+
+#undef v_
+#undef ptr
+
+/* SHA256 hash data in an array of bytes into hash buffer */
+/* and call the hash_compile function as required. */
+
+/*===========================================================================*\
+ Function :Sha256_upd
+ Description :
+ Calls :
+ Called by :
+ Return :void -
+ Parameters :
+ SHA256_CTX ctx[1] -
+ const unsigned char data[] -
+ size_t len -
+ Note :
+\*===========================================================================*/
+void
+Sha256_upd (SHA256_CTX ctx[1], const u8 data[], size_t len)
+{
+ u32 pos = (u32) (ctx->count[0] & SHA256_MASK);
+ u32 space = SHA256_BLOCK_SIZE - pos;
+ const u8 *sp = data;
+ int ret;
+
+ if ((ctx->count[0] += (u32) len) < len)
+ {
+ ++(ctx->count[1]);
+ }
+
+ while (len >= space)
+ {
+
+ /* tranfer whole blocks while possible */
+ ret = MEMCPY_S (((u8 *) ctx->wbuf) + pos, space, sp, space);
+ if (EOK != ret)
+ {
+ NSPOL_LOGERR ("MEMCPY_S failed");
+ return;
+ }
+
+ sp += space;
+ len -= space;
+ space = SHA256_BLOCK_SIZE;
+ pos = 0;
+ bsw_32 (ctx->wbuf, SHA256_BLOCK_SIZE >> 2);
+ Sha256_compile__ (ctx);
+ }
+
+ if (len != 0)
+ {
+ ret = MEMCPY_S (((u8 *) ctx->wbuf) + pos, (u32) len, sp, (u32) len);
+ if (EOK != ret)
+ {
+ NSPOL_LOGERR ("MEMCPY_S failed");
+ return;
+ }
+ }
+
+ return;
+}
+
+/* SHA256 Final padding and digest calculation */
+
+/*===========================================================================*\
+ Function :SHA_fin1
+ Description :
+ Calls :
+ Called by :
+ Return :void -
+ Parameters :
+ unsigned char hval[] -
+ SHA256_CTX ctx[1] -
+ const unsigned int hlen -
+ Note :
+\*===========================================================================*/
+NSTACK_STATIC void
+SHA_fin1 (u8 hval[], SHA256_CTX ctx[1], const unsigned int hlen)
+{
+ u32 i = (u32) (ctx->count[0] & SHA256_MASK);
+
+ /* Not unusal shift operation. Checked with purify. */
+
+ /*put bytes in the buffer in an order in which references to */
+ /*32-bit words will put bytes with lower addresses into the */
+ /*top of 32 bit words on BOTH big and little endian machines */
+ bsw_32 (ctx->wbuf, (i + 3) >> 2);
+
+ /*we now need to mask valid bytes and add the padding which is */
+ /*a single 1 bit and as many zero bits as necessary. Note that */
+ /*we can always add the first padding byte here because the */
+ /*buffer always has at least one empty slot */
+ ctx->wbuf[i >> 2] &= (u32) 0xffffff80 << 8 * (~i & 3);
+ ctx->wbuf[i >> 2] |= (u32) 0x00000080 << 8 * (~i & 3);
+
+ /* we need 9 or more empty positions, one for the padding byte */
+ /* (above) and eight for the length count. If there is not */
+ /* enough space pad and empty the buffer */
+ if (i > SHA256_BLOCK_SIZE - 9)
+ {
+ if (i < 60)
+ {
+ ctx->wbuf[15] = 0;
+ }
+
+ Sha256_compile__ (ctx);
+ i = 0;
+ }
+ else
+ {
+ /* compute a word index for the empty buffer positions */
+ i = (i >> 2) + 1;
+ }
+
+ while (i < 14)
+ {
+ /* and zero pad all but last two positions */
+ ctx->wbuf[i++] = 0;
+ }
+
+ /* the following 32-bit length fields are assembled in the */
+ /* wrong byte order on little endian machines but this is */
+ /* corrected later since they are only ever used as 32-bit */
+ /* word values. */
+ ctx->wbuf[14] = (ctx->count[1] << 3) | (ctx->count[0] >> 29);
+ ctx->wbuf[15] = ctx->count[0] << 3;
+ Sha256_compile__ (ctx);
+
+ /* extract the hash value as bytes in case the hash buffer is */
+ /* mislaigned for 32-bit words */
+ for (i = 0; i < hlen; ++i)
+ {
+ hval[i] = (u8) (ctx->hash[i >> 2] >> (8 * (~i & 3)));
+ }
+
+ return;
+}
+
+/*
+Description: Internal data for SHA256 digest calculation
+Value Range: None
+Access: Used to store internal data for SHA256 digest calculation
+Remarks:
+*/
+static const u32 g_i256[] = {
+ 0x6A09E667, 0xBB67AE85, 0x3C6EF372, 0xA54FF53A,
+ 0x510E527F, 0x9B05688C, 0x1F83D9AB, 0x5BE0CD19
+};
+
+/*===========================================================================*\
+ Function :Sha256_set
+ Description :
+ Calls :
+ Called by :
+ Return :void -
+ Parameters :
+ SHA256_CTX ctx[1] -
+ Note :
+\*===========================================================================*/
+void
+Sha256_set (SHA256_CTX ctx[1])
+{
+ int ret;
+ ctx->count[0] = ctx->count[1] = 0;
+
+ ret = MEMCPY_S (ctx->hash, sizeof (ctx->hash), g_i256, sizeof (g_i256));
+ if (EOK != ret)
+ {
+ NSPOL_LOGERR ("MEMCPY_S failed");
+ return;
+ }
+
+ return;
+}
+
+/*===========================================================================*\
+ Function :Sha256_fin
+ Description :
+ Calls :
+ Called by :
+ Return :void -
+ Parameters :
+ SHA256_CTX ctx[1] -
+ unsigned char hval[] -
+ Note :
+\*===========================================================================*/
+void
+Sha256_fin (SHA256_CTX ctx[1], u8 hval[])
+{
+ SHA_fin1 (hval, ctx, SHA256_DIGEST_SIZE);
+
+ return;
+}
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
diff --git a/src/framework/common/include/compile_config.h b/src/framework/common/include/compile_config.h
new file mode 100644
index 0000000..2ec5373
--- /dev/null
+++ b/src/framework/common/include/compile_config.h
@@ -0,0 +1,30 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef COMPILE_CONFIG_H
+#define COMPILE_CONFIG_H
+
+#ifndef NSTACK_STATIC
+#ifndef NSTACK_STATIC_CHECK
+#define NSTACK_STATIC static
+#else
+#define NSTACK_STATIC
+#endif
+#endif
+
+#include "compiling_check.h"
+
+#endif /*compile_config.h */
diff --git a/src/framework/common/include/compiling_check.h b/src/framework/common/include/compiling_check.h
new file mode 100644
index 0000000..e4a7538
--- /dev/null
+++ b/src/framework/common/include/compiling_check.h
@@ -0,0 +1,106 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef COMPILING_CHECK_H
+#define COMPILING_CHECK_H
+
+/* protect the value of macro whose value impacts the version
+ * compatibility, can't be changed!!! */
+#define COMPAT_PROTECT(name, value) \
+static inline char value_of_##name##_equal_to() \
+{ \
+ char __dummy1[(name) - (value)]; \
+ char __dummy2[(value) - (name)]; \
+ return __dummy1[-1] + __dummy2[-1]; \
+}
+
+/* check whether struct size is equal to a special value */
+#define SIZE_OF_TYPE_EQUAL_TO(type, size) \
+static inline char size_of_##type##_equal_to_##size() \
+{ \
+ char __dummy1[sizeof(type) - size]; \
+ char __dummy2[size - sizeof(type)]; \
+ return __dummy1[-1] + __dummy2[-1]; \
+}
+
+/* check whether struct size is not equal to a special value */
+#define SIZE_OF_TYPE_UNEQUAL_TO(type, size) \
+static inline char size_of_##type##_unequal_to_##size() \
+{ \
+ char __dummy1[0==(10/(sizeof(type)-size))]; \
+ return __dummy1[-1]; \
+}
+
+/* check whether struct size is not larger than a special value */
+#define SIZE_OF_TYPE_NOT_LARGER_THAN(type, size) \
+static inline char size_of_##type##_not_larger_than_##size() \
+{ \
+ char __dummy1[size - sizeof(type)]; \
+ return __dummy1[-1]; \
+}
+
+/* check whether struct size + sizeof(void*) is not larger than a special value */
+/* reserve 8 bytes for 64 bits pointers */
+#define SIZE_OF_TYPE_PLUS8_NOT_LARGER_THAN(type, size) \
+static inline char size_of_##type##_not_larger_than_##size() \
+{ \
+ char __dummy1[size - sizeof(type) - sizeof(void*)]; \
+ return __dummy1[-1]; \
+}
+
+/* check whether struct size is not smaller than a special value */
+#define SIZE_OF_TYPE_NOT_SMALLER_THAN(type, size) \
+static inline char size_of_##type##_not_smaller_than_##size() \
+{ \
+ char __dummy1[sizeof(type) - size]; \
+ return __dummy1[-1]; \
+}
+
+/* check whether struct size is smaller than a special value */
+#define SIZE_OF_TYPE_SMALLER_THAN(type, size) \
+ SIZE_OF_TYPE_NOT_LARGER_THAN(type, size) \
+ SIZE_OF_TYPE_UNEQUAL_TO(type, size)
+
+/* check whether struct size is larger than a special value */
+#define SIZE_OF_TYPE_LARGER_THAN(type, size) \
+ SIZE_OF_TYPE_NOT_SMALLER_THAN(type, size) \
+ SIZE_OF_TYPE_UNEQUAL_TO(type, size)
+
+/* check whether struct size is smaller than a special value, version 2 */
+#define SIZE_OF_TYPE_SMALLER_THAN2(type, size) \
+static inline char size_of_##type##_smaller_than2_##size() \
+{ \
+ char __dummy1[size - sizeof(type) - 1]; \
+ return __dummy1[-1]; \
+}
+
+/* check whether struct size is larger than a special value, version 2 */
+#define SIZE_OF_TYPE_LARGER_THAN2(type, size) \
+static inline char size_of_##type##_larger_than2_##size() \
+{ \
+ char __dummy1[sizeof(type) - size - 1]; \
+ return __dummy1[-1]; \
+}
+
+/* check whether struct size is equal to an integer multiple of a special value */
+#define SIZE_OF_TYPE_IS_MULTIPLE_OF(type, size) \
+static inline char size_of_##type##_is_multiple_of_##size() \
+{ \
+ char __dummy1[0 - (sizeof(type) % size)]; \
+ return __dummy1[-1]; \
+}
+
+#endif /*compiling_check.h */
diff --git a/src/framework/common/include/ephlist.h b/src/framework/common/include/ephlist.h
new file mode 100644
index 0000000..90491b0
--- /dev/null
+++ b/src/framework/common/include/ephlist.h
@@ -0,0 +1,199 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _EPHLIST_H_
+#define _EPHLIST_H_
+
+#include <stdio.h>
+#include "types.h"
+#include "common_mem_pal.h"
+#include "common_mem_buf.h"
+#include "common_pal_bitwide_adjust.h"
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+struct ep_hlist_node
+{
+ struct ep_hlist_node *next, **pprev;
+};
+
+struct ep_node_list
+{
+ struct ep_hlist_node *head;
+ struct ep_hlist_node *tail;
+};
+
+struct ep_hlist
+{
+ struct ep_hlist_node node;
+ struct ep_hlist_node *head;
+ struct ep_hlist_node *tail;
+};
+
+#define ep_hlist_entry(ptr, type, member) container_of(ptr, type, member)
+
+#define EP_HLIST_INIT_NODE(node) {\
+ (node)->next = NULL;\
+ (node)->pprev = NULL; \
+ }
+
+#define EP_HLIST_INIT(ptr) {\
+ EP_HLIST_INIT_NODE(&((ptr)->node)); \
+ (ptr)->head = (struct ep_hlist_node*)ADDR_LTOSH_EXT(&((ptr)->node)); \
+ (ptr)->tail = (struct ep_hlist_node*)ADDR_LTOSH_EXT(&((ptr)->node)); \
+ }
+
+#define EP_HLIST_PREV(ptr) ((struct ep_hlist_node*)(ADDR_SHTOL((ptr)->pprev)))
+/* list check may below zero check header, because if app crash before
+ do list->size++, it will lead problem */
+#define EP_HLIST_EMPTY(list) (NULL == ((struct ep_hlist_node*)ADDR_SHTOL((list)->head))->next)
+#define EP_HLIST_NODE_LINKED(node) (!(!(node)->pprev))
+
+static __inline void ep_hlist_del (struct ep_hlist *list,
+ struct ep_hlist_node *n);
+static __inline void ep_hlist_add_tail (struct ep_hlist *list,
+ struct ep_hlist_node *node);
+
+/*
+ * list , n are local pointer, don't need to cast
+ */
+static __inline void
+ep_hlist_del (struct ep_hlist *list, struct ep_hlist_node *n)
+{
+ if (!EP_HLIST_NODE_LINKED (n))
+ return;
+ EP_HLIST_PREV (n)->next = n->next;
+ if (n->next)
+ {
+ ((struct ep_hlist_node *) ADDR_SHTOL (n->next))->pprev = n->pprev;
+ }
+ else
+ {
+ list->tail = (struct ep_hlist_node *) (n->pprev);
+ }
+ EP_HLIST_INIT_NODE (n);
+}
+
+/**
+ * list, node are local pointer , don't need to case
+ */
+static __inline void
+ep_hlist_add_tail (struct ep_hlist *list, struct ep_hlist_node *node)
+{
+ struct ep_hlist_node *tail =
+ (struct ep_hlist_node *) ADDR_SHTOL (list->tail);
+ EP_HLIST_INIT_NODE (node);
+ node->pprev = (struct ep_hlist_node **) ADDR_LTOSH_EXT (&tail->next);
+ tail->next = (struct ep_hlist_node *) ADDR_LTOSH_EXT (node);
+ list->tail = (struct ep_hlist_node *) ADDR_LTOSH_EXT (node);
+}
+
+/*#########################################################*/
+struct list_node
+{
+ struct list_node *next;
+};
+
+struct ep_list
+{
+ struct list_node node;
+ struct list_node *head;
+};
+
+#define ep_list_entry(ptr, type, member) container_of(ptr, type, member)
+
+#define EP_LIST_INIT_NODE(node) {\
+ (node)->next = NULL;\
+ }
+
+#define EP_LIST_INIT(ptr) {\
+ EP_LIST_INIT_NODE(&((ptr)->node)); \
+ (ptr)->head = (struct list_node*)ADDR_LTOSH_EXT(&((ptr)->node)); \
+ }
+
+#define EP_LIST_EMPTY(list) (NULL == ((struct list_node*)ADDR_SHTOL((list)->head))->next)
+
+static __inline void ep_list_del (struct ep_list *list, struct list_node *n);
+static __inline void ep_list_add_tail (struct ep_list *list,
+ struct list_node *node);
+
+/*
+ * list , n are local pointer, don't need to cast
+ */
+static __inline void
+ep_list_del (struct ep_list *list, struct list_node *n)
+{
+ if (NULL == n)
+ {
+ return;
+ }
+
+ struct list_node *p_node;
+ struct list_node *p_prev = NULL;
+ p_node = ((struct list_node *) ADDR_SHTOL (list->head));
+ while (NULL != p_node && p_node != n)
+ {
+ p_prev = p_node;
+ p_node = ((struct list_node *) ADDR_SHTOL (p_node->next));
+ }
+
+ if (p_node != n || p_prev == NULL)
+ {
+ return;
+ }
+
+ p_prev->next = n->next;
+
+ EP_LIST_INIT_NODE (n);
+ return;
+}
+
+/**
+ * list, node are local pointer , don't need to case
+ */
+static __inline void
+ep_list_add_tail (struct ep_list *list, struct list_node *node)
+{
+
+ struct list_node *p_node;
+ struct list_node *p_prev = NULL;
+ p_node = ((struct list_node *) ADDR_SHTOL (list->head));
+ while (NULL != p_node)
+ {
+ p_prev = p_node;
+ p_node = ((struct list_node *) ADDR_SHTOL (p_node->next));
+ }
+
+ if (NULL == p_prev)
+ {
+ return;
+ }
+
+ EP_LIST_INIT_NODE (node);
+ p_prev->next = (struct list_node *) ADDR_LTOSH_EXT (node);
+ return;
+}
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
+
+#endif /* _HLIST_H_ */
diff --git a/src/framework/common/include/eprb_tree.h b/src/framework/common/include/eprb_tree.h
new file mode 100644
index 0000000..558ab2d
--- /dev/null
+++ b/src/framework/common/include/eprb_tree.h
@@ -0,0 +1,84 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _EPRB_TREE_H_
+#define _EPRB_TREE_H_
+
+#include <stdio.h>
+#include <stdlib.h>
+#include "types.h"
+#include "common_mem_pal.h"
+#include "common_mem_buf.h"
+#include "common_pal_bitwide_adjust.h"
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+#define EP_RB_RED 0
+#define EP_RB_BLACK 1
+
+struct ep_rb_node
+{
+ int color;
+
+ struct ep_rb_node *rb_parent;
+ struct ep_rb_node *rb_right;
+ struct ep_rb_node *rb_left;
+};
+
+/* The alignment might seem pointless, but allegedly CRIS needs it */
+
+struct ep_rb_root
+{
+ struct ep_rb_node *rb_node;
+};
+
+#define ep_rb_parent(r) ((struct ep_rb_node *)((r)->rb_parent))
+
+static inline void
+ep_rb_set_parent (struct ep_rb_node *rb, struct ep_rb_node *p)
+{
+ rb->rb_parent = (struct ep_rb_node *) ADDR_LTOSH_EXT (p);
+}
+
+#define ep_rb_entry(ptr, type, member) container_of(ptr, type, member)
+
+extern void ep_rb_insert_color (struct ep_rb_node *, struct ep_rb_root *);
+extern void ep_rb_erase (struct ep_rb_node *, struct ep_rb_root *);
+struct ep_rb_node *ep_rb_first (const struct ep_rb_root *);
+
+static inline void
+ep_rb_link_node (struct ep_rb_node *node,
+ struct ep_rb_node *parent, struct ep_rb_node **rb_link)
+{
+
+ node->rb_parent = (struct ep_rb_node *) ADDR_LTOSH_EXT (parent);
+ node->rb_left = node->rb_right = NULL;
+
+ *rb_link = (struct ep_rb_node *) ADDR_LTOSH_EXT (node);
+ node->color = EP_RB_RED;
+
+}
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
+
+#endif
diff --git a/src/framework/common/include/list.h b/src/framework/common/include/list.h
new file mode 100644
index 0000000..01860bc
--- /dev/null
+++ b/src/framework/common/include/list.h
@@ -0,0 +1,181 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef LIST_H_
+#define LIST_H_
+
+#include <signal.h>
+#include <stdio.h>
+#include <pthread.h>
+#include <unistd.h>
+
+#include "types.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+struct list_head
+{
+ union
+ {
+ struct list_head *next;
+ };
+
+ union
+ {
+ struct list_head *prev;
+ };
+};
+
+struct hlist_node
+{
+ /**
+ * @pprev: point the previous node's next pointer
+ */
+ union
+ {
+ struct hlist_node *next;
+ };
+
+ union
+ {
+ struct hlist_node **pprev;
+ };
+};
+
+struct hlist_head
+{
+ struct hlist_node *first;
+};
+
+#define list_entry(ptr, type, member) \
+ container_of(ptr, type, member)
+
+#define list_for_each_entry_type(tpos, typeof_tpos,pos, head, member) \
+ for (pos = ((head)->next); \
+ pos && pos != (head) && ({tpos = list_entry(pos, typeof_tpos, member); 1;}); \
+ pos = ((pos)->next))
+
+#define LINT_LIST()
+
+#define list_for_each_entry(tpos, pos, head, member) \
+ for (pos = ((head)->next); \
+ pos && pos != (head) && ({tpos = list_entry(pos, typeof(*tpos), member); 1;}); \
+ pos = ((pos)->next))
+
+#define list_for_each_entry_list_head(tpos, pos, head, member) \
+ for (pos = (struct list_head *)((head)->next); \
+ pos && pos != (struct list_head *)(head) && ({tpos = list_entry(pos, typeof(*tpos), member); 1;}); \
+ pos = (pos)->next)
+#define list_for_each_safe_entry(tpos, pos, n, head, member) \
+ for (pos = (head)->next,n = pos->next; \
+ pos && pos != (head) && ({tpos = list_entry(pos, typeof(*tpos), member); 1;}); \
+ pos = n,n = (pos)->next)
+
+#define INIT_LIST_HEAD(list) {(list)->next = (list); (list)->prev = (list);}
+
+/*
+ * @head: the list to test.
+ */
+inline void list_add (struct list_head *newp, struct list_head *head);
+inline void list_link (struct list_head *newhead, struct list_head *head);
+inline void list_add_tail (struct list_head *newp, struct list_head *head);
+inline int list_empty (const struct list_head *head);
+inline void list_del (struct list_head *entry);
+inline struct list_head *list_get_first (struct list_head *head);
+inline void hlist_del_init (struct hlist_node *n);
+
+struct hlist_tail
+{
+ struct hlist_node *end;
+};
+
+struct hlist_ctl
+{
+ struct hlist_head head;
+ struct hlist_tail tail;
+};
+#define INIT_HLIST_CTRL(ptr) {(ptr)->head.first = NULL; (ptr)->tail.end = NULL;}
+
+inline int hlist_empty (const struct hlist_head *h);
+inline void hlist_add_head (struct hlist_node *n, struct hlist_head *h);
+
+#define INIT_HLIST_HEAD(ptr) ((ptr)->first = NULL)
+#define INIT_HLIST_NODE(ptr) {(ptr)->next = NULL; (ptr)->pprev = NULL;}
+#define hlist_entry(ptr, type, member) \
+ container_of(ptr, type, member)
+
+/***
+ * hlist_for_each_entry - iterate over list of given type
+ * @member: the name of the hlist_node within the struct.
+ * @head: the head for your list.
+ * @pos: the &struct hlist_node to use as a loop cursor.
+ * @tpos: the type * to use as a loop cursor.
+ */
+#define hlist_for_each_entry(tpos, pos, head, member) \
+ for (pos = (head)->first; \
+ pos && ({tpos = hlist_entry(pos, typeof(*tpos), member); 1;}); \
+ pos = pos->next)
+
+/**
+ * hlist_for_each_entry_type - iterate over list of given type
+ * @member: the name of the hlist_node within the struct.
+ * @head: the head for your list.
+ * @pos: the &struct hlist_node to use as a loop cursor.
+ * @tpos: the type * to use as a loop cursor.
+ */
+#define hlist_for_each_entry_type(tpos, typeof_tpos,pos, head, member) \
+ for (pos = (head)->first; \
+ pos && ({tpos = hlist_entry(pos, typeof_tpos, member); 1;}); \
+ pos = pos->next)
+
+inline void hlist_del_init (struct hlist_node *n);
+
+/**
+ * next must be != NULL
+ * add n node before next node
+ *
+ * @n: new node
+ * @next: node in the hlist
+ */
+inline void hlist_add_before (struct hlist_node *n, struct hlist_node *next);
+
+/**
+ * next must be != NULL
+ * add n node after next node
+ * actual behavior is add after n
+ * @n: node in the hlist
+ * @next: new node
+ */
+inline void hlist_add_after (struct hlist_node *n, struct hlist_node *next);
+
+/* add after the head */
+inline void hlist_add_head (struct hlist_node *n, struct hlist_head *h);
+
+inline int hlist_unhashed (const struct hlist_node *h);
+
+inline int hlist_empty (const struct hlist_head *h);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+};
+/* *INDENT-ON* */
+#endif
+
+#endif /* HASH_H_ */
diff --git a/src/framework/common/include/pidinfo.h b/src/framework/common/include/pidinfo.h
new file mode 100644
index 0000000..7438756
--- /dev/null
+++ b/src/framework/common/include/pidinfo.h
@@ -0,0 +1,48 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _PIDINFO_H_
+#define _PIDINFO_H_
+
+#include "types.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+#define NSFW_MAX_FORK_NUM 32
+typedef struct
+{
+ u32 used_size;
+ u32 apid[NSFW_MAX_FORK_NUM];
+} nsfw_pidinfo;
+
+inline i32 nsfw_pidinfo_init (nsfw_pidinfo * pidinfo);
+inline int nsfw_add_pid (nsfw_pidinfo * pidinfo, u32 pid);
+inline int nsfw_del_pid (nsfw_pidinfo * pidinfo, u32 pid);
+inline int nsfw_del_last_pid (nsfw_pidinfo * pidinfo, u32 pid);
+inline int nsfw_pid_exist (nsfw_pidinfo * pidinfo, u32 pid);
+inline int nsfw_pidinfo_empty (nsfw_pidinfo * pidinfo);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+};
+/* *INDENT-ON* */
+#endif
+
+#endif /* _PIDINFO_H_ */
diff --git a/src/framework/common/include/sha256.h b/src/framework/common/include/sha256.h
new file mode 100644
index 0000000..b1c7f3c
--- /dev/null
+++ b/src/framework/common/include/sha256.h
@@ -0,0 +1,94 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _SHA256_H_
+#define _SHA256_H_
+#include "types.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+/* Note that the following function prototypes are the same */
+/* for both the bit and byte oriented implementations. But */
+/* the length fields are in bytes or bits as is appropriate */
+/* for the version used. Bit sequences are arrays of bytes */
+/* in which bit sequence indexes increase from the most to */
+/* the least significant end of each byte */
+
+#define SHA256_DIGEST_SIZE 32 /* in bytes */
+#define SHA256_BLOCK_SIZE 64 /* in bytes */
+
+typedef struct
+{
+ u32 count[2];
+ u32 hash[8];
+ u32 wbuf[16];
+} SHA256_CTX;
+
+/* SHA256 hash data in an array of bytes into hash buffer */
+/* and call the hash_compile function as required. */
+
+/*===========================================================================*\
+ Function :Sha256_upd
+ Description :
+ Calls :
+ Called by :
+ Return :void -
+ Parameters :
+ SHA256_CTX ctx[1] -
+ const unsigned char data[] -
+ size_t len -
+ Note :
+\*===========================================================================*/
+void Sha256_upd (SHA256_CTX ctx[1], const u8 data[], size_t len);
+
+/* SHA256 Final padding and digest calculation */
+
+/*===========================================================================*\
+ Function :Sha256_set
+ Description :
+ Calls :
+ Called by :
+ Return :void -
+ Parameters :
+ SHA256_CTX ctx[1] -
+ Note :
+\*===========================================================================*/
+void Sha256_set (SHA256_CTX ctx[1]);
+
+/*===========================================================================*\
+ Function :Sha256_fin
+ Description :
+ Calls :
+ Called by :
+ Return :void -
+ Parameters :
+ SHA256_CTX ctx[1] -
+ unsigned char hval[] -
+ Note :
+\*===========================================================================*/
+void Sha256_fin (SHA256_CTX ctx[1], u8 hval[]);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
+
+#endif /* _SHA256_H_ */
diff --git a/src/framework/common/include/types.h b/src/framework/common/include/types.h
new file mode 100644
index 0000000..c7d013c
--- /dev/null
+++ b/src/framework/common/include/types.h
@@ -0,0 +1,97 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef clib_types_h
+#define clib_types_h
+#include <stddef.h>
+
+/* Standard CLIB types. */
+
+/* Define signed and unsigned 8, 16, 32, and 64 bit types
+ and machine signed/unsigned word for all architectures. */
+typedef char i8;
+typedef short i16;
+
+typedef unsigned char u8;
+typedef unsigned short u16;
+
+typedef int i32;
+typedef long long i64;
+
+typedef unsigned int u32;
+typedef unsigned long long u64;
+
+#ifndef bool
+#define bool int
+#endif
+
+#ifndef TRUE
+#define TRUE 1
+#endif
+
+#ifndef true
+#define true 1
+#endif
+
+#ifndef FALSE
+#define FALSE 0
+#endif
+
+#ifndef false
+#define false 0
+#endif
+
+#ifndef NULL
+#define NULL ((void *)0)
+#endif
+
+#define container_of(ptr, type, member) ( \
+ (type *)((char *)(ptr) - offsetof(type,member)) \
+ )
+
+#define PRIMARY_ADDR
+
+typedef struct _nsfw_res
+{
+ u8 alloc_flag;
+ u8 u8Reserve;
+ u16 chk_count;
+ u32 data;
+} nsfw_res;
+
+static inline void
+res_alloc (nsfw_res * res)
+{
+ res->alloc_flag = TRUE;
+ res->chk_count = 0;
+ res->u8Reserve = 0;
+}
+
+static inline int
+res_free (nsfw_res * res)
+{
+ if (TRUE != res->alloc_flag)
+ {
+ return -1;
+ }
+ res->chk_count = 0;
+ res->alloc_flag = FALSE;
+ return 0;
+}
+
+#define NSFW_THREAD __thread
+
+#endif /*clib_types_h */
diff --git a/src/framework/common/mem_mgr/include/nsfw_mem_desc.h b/src/framework/common/mem_mgr/include/nsfw_mem_desc.h
new file mode 100644
index 0000000..1e959d9
--- /dev/null
+++ b/src/framework/common/mem_mgr/include/nsfw_mem_desc.h
@@ -0,0 +1,172 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_MEM_DESC_H
+#define _NSFW_MEM_DESC_H
+#include <sys/types.h>
+#include <unistd.h>
+#include <string.h>
+#include "nsfw_mem_api.h"
+#include "nsfw_mgr_com_api.h"
+#include "nsfw_ring_data.h"
+
+#define NSFW_MEM_NOT_INIT (0)
+#define NSFW_MEM_INIT_ERR (1)
+#define NSFW_MEM_INIT_OK (2)
+
+#define NSFW_NAME_LENCHECK_RET(name, desc) \
+ { \
+ i32 inamelen = strlen(name); \
+ if (inamelen >= NSFW_MEM_APPNAME_LENTH) \
+ { \
+ NSCOMM_LOGERR("name length check fail] desc=%s, name len=%d, expected max=%d", \
+ #desc, inamelen, NSFW_MEM_APPNAME_LENTH); \
+ return NSFW_MEM_ERR; \
+ } \
+ }
+
+#define NSFW_NAME_LENCHECK_RET_NULL(name, desc) \
+ { \
+ i32 inamelen = strlen(name); \
+ if (inamelen >= NSFW_MEM_APPNAME_LENTH) \
+ { \
+ NSCOMM_LOGERR("name length check fail] desc=%s, name len=%d, expected max=%d", \
+ #desc, inamelen, NSFW_MEM_APPNAME_LENTH); \
+ return NULL; \
+ } \
+ }
+
+#define NSFW_MEM_PARA_CHECK_RET(handle, pdata, desc, num) {\
+ if ((NULL == (handle)) || (NULL == (pdata)) || (num <= 0)\
+ || (((struct nsfw_mem_ring*)(handle))->memtype >= NSFW_MEM_TYPEMAX)) \
+ { \
+ NSCOMM_LOGERR("input para error] desc=%s,mhandle=%p, pdata=%p, inum=%d", desc, (handle), (pdata), num); \
+ return 0; \
+ } \
+ }
+
+#define NSFW_MEM_ENQ_PARA_CHECK_RET(handle, desc) {\
+ if ((NULL == (handle)) \
+ || (((struct nsfw_mem_ring*)(handle))->memtype >= NSFW_MEM_TYPEMAX)) \
+ { \
+ NSCOMM_LOGERR("input para error] desc=%s,mhandle=%p", desc, (handle)); \
+ return 0; \
+ } \
+ }
+
+#define NSFW_MEM_NAME_CHECK_RET_ERR(pname, desc) {\
+ if ((NULL == (pname)) || ((pname)->entype >= NSFW_MEM_TYPEMAX)) \
+ { \
+ NSCOMM_LOGERR("input para error] desc=%s, pname=%p, mtype=%d", desc, pname, (pname) ? (pname)->entype:-1); \
+ return NSFW_MEM_ERR; \
+ } \
+ }
+
+#define NSFW_MEM_NAME_CHECK_RET_NULL(pname, desc) {\
+ if ((NULL == (pname)) || ((pname)->entype >= NSFW_MEM_TYPEMAX)) \
+ { \
+ NSCOMM_LOGERR("input para error] desc=%s, pname=%p, mtype=%d", desc, pname, (pname) ? (pname)->entype:-1); \
+ return NULL; \
+ } \
+ }
+
+#define NSFW_MEM_RING_CHECK_RET(pringinfo, pringhandle_array, iringnum) {\
+ if ((NULL == pringinfo) || (NULL == pringhandle_array) || (pringinfo[0].stname.entype >= NSFW_MEM_TYPEMAX)) \
+ { \
+ NSCOMM_LOGERR("input para error] pringinfo=%p, iringnum=%d, pringhandle_array=%p, mtype=%d", \
+ pringinfo, iringnum, pringhandle_array, pringinfo ? pringinfo[0].stname.entype : (-1)); \
+ return NSFW_MEM_ERR; \
+ } \
+ }
+
+#define NSFW_MEM_RINGV_CHECK_RET(pmpinfo, inum, pringhandle_array, iarray_num) { \
+ if ((NULL == pmpinfo) || (NULL == pringhandle_array) \
+ || (inum != iarray_num) || (inum <= 0) || (pmpinfo[0].stname.entype >= NSFW_MEM_TYPEMAX)) \
+ { \
+ NSCOMM_LOGERR("input para error] pmpinfo=%p, inum=%d, pringhandle_array=%p, iarray_num=%d", \
+ pmpinfo, inum, pringhandle_array, iarray_num, pmpinfo ? pmpinfo[0].stname.entype : (-1)); \
+ return NSFW_MEM_ERR; \
+ } \
+ }
+
+#define NSFW_MEM_MBUF_CHECK_RET_ERR(mhandle, entype, desc) {\
+ if ((NULL == mhandle) || (entype >= NSFW_MEM_TYPEMAX)) \
+ { \
+ NSCOMM_LOGERR("input para error] desc=%s, mhandle=%p, mtype=%d", desc, mhandle, entype); \
+ return NSFW_MEM_ERR; \
+ } \
+ }
+
+#define NSFW_MEM_MBUF_CHECK_RET_NULL(mhandle, entype, desc) {\
+ if ((NULL == mhandle) || (entype >= NSFW_MEM_TYPEMAX)) \
+ { \
+ NSCOMM_LOGERR("input para error] desc=%s, mhandle=%p, mtype=%d", desc, mhandle, entype); \
+ return NULL; \
+ } \
+ }
+
+/*memory access inferface define*/
+typedef struct
+{
+ i32 (*mem_ops_init) (nsfw_mem_para * para);
+ void (*mem_ops_destroy) (void);
+ mzone_handle (*mem_ops_zone_creae) (nsfw_mem_zone * pinfo);
+ i32 (*mem_ops_zone_createv) (nsfw_mem_zone * pmeminfo, i32 inum,
+ mzone_handle * paddr_array, i32 iarray_num);
+ mzone_handle (*mem_ops_zone_lookup) (nsfw_mem_name * pname);
+ i32 (*mem_ops_mzone_release) (nsfw_mem_name * pname);
+ mpool_handle (*mem_ops_mbfmp_create) (nsfw_mem_mbfpool * pbufinfo);
+ i32 (*mem_ops_mbfmp_createv) (nsfw_mem_mbfpool * pmbfname, i32 inum,
+ mpool_handle * phandle_array,
+ i32 iarray_num);
+ mbuf_handle (*mem_ops_mbf_alloc) (mpool_handle mhandle);
+ i32 (*mem_ops_mbf_free) (mbuf_handle mhandle);
+ mpool_handle (*mem_ops_mbfmp_lookup) (nsfw_mem_name * pmbfname);
+ i32 (*mem_ops_mbfmp_release) (nsfw_mem_name * pname);
+ mring_handle (*mem_ops_sp_create) (nsfw_mem_sppool * pmpinfo);
+ i32 (*mem_ops_sp_createv) (nsfw_mem_sppool * pmpinfo, i32 inum,
+ mring_handle * pringhandle_array,
+ i32 iarray_num);
+ i32 (*mem_ops_spring_create) (nsfw_mem_mring * prpoolinfo,
+ mring_handle * pringhandle_array,
+ i32 iringnum);
+ i32 (*mem_ops_sp_release) (nsfw_mem_name * pname);
+ mring_handle (*mem_ops_sp_lookup) (nsfw_mem_name * pname);
+ mring_handle (*mem_ops_ring_create) (nsfw_mem_mring * pringinfo);
+ mring_handle (*mem_ops_ring_lookup) (nsfw_mem_name * pname);
+ i32 (*mem_ops_ring_release) (nsfw_mem_name * pname);
+ ssize_t (*mem_ops_mem_statics) (void *handle, nsfw_mem_struct_type type);
+ i32 (*mem_ops_mbuf_recycle) (mpool_handle handle);
+ i32 (*mem_ops_sp_iterator) (mpool_handle handle, u32 start, u32 end,
+ nsfw_mem_item_fun fun, void *argv);
+ i32 (*mem_ops_mbuf_iterator) (mpool_handle handle, u32 start, u32 end,
+ nsfw_mem_item_fun fun, void *argv);
+} nsfw_mem_ops;
+
+typedef struct
+{
+ nsfw_mem_type entype;
+ nsfw_mem_ops *stmemop;
+} nsfw_mem_attr;
+
+typedef struct
+{
+ fw_poc_type enflag; /*app, nStackMain, Master */
+} nsfw_mem_localdata;
+
+extern nsfw_mem_attr g_nsfw_mem_ops[];
+extern i32 g_mem_type_num;
+#endif
diff --git a/src/framework/common/mem_mgr/include/nsfw_ring_data.h b/src/framework/common/mem_mgr/include/nsfw_ring_data.h
new file mode 100644
index 0000000..99ec0ed
--- /dev/null
+++ b/src/framework/common/mem_mgr/include/nsfw_ring_data.h
@@ -0,0 +1,95 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_RING_DATA_H_
+#define _NSFW_RING_DATA_H_
+
+#include <stdint.h>
+#include "types.h"
+#include "common_mem_api.h"
+
+#define VALUE_LEN 40
+
+/*
+Ring Data has two part; Ver&Data
+val is a pointer offset base on rte_perf_ring::Addrbase, this struct support 1TB, it's enough now;
+future __int128 maybe used, this type can perfectly solve the version & address rang problem.
+*/
+union RingData_U
+{
+ struct RingData_S
+ {
+ /*
+ value of data, indeed it's a pointer offset base on rte_perf_ring::Addrbase;40bit is enough for user space addr
+ ver must using 24bit, so val using 40bit; a CAS now just support 64bit; in future, we may using __int128,now __int128 not support well.
+ */
+ volatile unsigned long long val:VALUE_LEN;
+ /*
+ version of data, using 16b store version flg is more suitable for Address save, but using 16b version is too short, it's value range is [0-65535];
+ between two cpu schedule time (TM-SPACE) of one process/thread, other processes/threads do N times queue oper. if N > 65535, still have a chance of ABA.
+ if using a 24bit save version flg, if ABA happened, 16777216 times queue oper need done in one TM-SPACE, it's impossible for today cpu.
+ */
+ volatile unsigned long long ver:(64 - VALUE_LEN);
+ } data_s;
+ u64 data_l;
+};
+
+/*
+ this high perf Ring rely on the init value of Ring Slot;
+ Ring Must init using PerfRingInit, Pool Must init using PerfPoolInit
+
+ the addrbase is base addr for all element; now we support 1024G offset;
+ for nstack the Ring element is from hugepage, and the addr is in stack space.
+
+ 1. not support a ring who's element space range bigger than 1024GB
+ [if one element from heep, one from stack, range will bigger than 1024GB, we not support]
+ 2. one more thing addr from mmap is in stack
+ 3. rte_perf_ring must create by rte_perf_ring_create/rte_perf_pool_create
+*/
+struct nsfw_mem_ring
+{
+ u8 memtype; //shared, no shared
+ u8 ringflag; //scmp, scsp, mcsp,mcmp
+ u16 reserv; //reserv data
+ u32 size; //size of the Ring, must 2^n
+ u32 eltsize; //for sppool, it is the size of per buf, if is ring, eltsize is zero.
+ u32 mask; //mask of the Ring, used mask mod Head/Tail to get real pos, must 2^n-1
+ void *Addrbase; /*Cause the Addr we support just 40b(1024G), we using a basAddr+offset to get the real addr; ring[x].data_s.val just store offset;
+ * not used when no shared mode
+ */
+ volatile u32_t prodhflag; //for nshmem fork recover
+ volatile u32_t prodtflag; //for nshmem fork recover
+ volatile u32_t conshflag; //for nshmem fork recover
+ volatile u32_t constflag; //for nshmem fork recover
+ nsfw_res res_chk;
+
+ struct
+ {
+ volatile u32 head; //Head of the Ring, used to indicat pos where to pull a val
+ volatile u32 tail; //for nshmem, shmem not used.
+ } prod;
+ struct
+ {
+ volatile u32 head; //for nshmem, shmem not used.
+ volatile u32 tail; //Tail of the Ring, used to indicat pos where to push a val
+ } cons;
+ u32 uireserv[4]; //reserved for update
+ union RingData_U ring[0]; //Value of Ring
+};
+
+#define PERFRING_ADDR_RANGE (0xFFFFFFFFFFL)
+
+#endif /*_NSFW_RING_DATA_H_*/
diff --git a/src/framework/common/mem_mgr/include/nsfw_ring_fun.h b/src/framework/common/mem_mgr/include/nsfw_ring_fun.h
new file mode 100644
index 0000000..57a7bf3
--- /dev/null
+++ b/src/framework/common/mem_mgr/include/nsfw_ring_fun.h
@@ -0,0 +1,110 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_RING_FUN_H_
+#define _NSFW_RING_FUN_H_
+
+#include <stdint.h>
+#include "common_pal_bitwide_adjust.h"
+#include "nsfw_mem_api.h"
+#include "nsfw_ring_data.h"
+
+/*
+ for nstack I advise addrbase set to lowest of mmaped hugepage Addr.
+ to simple:
+ 1. ring element is from mmaped mem, set Addrbase to 0x7fffffffffff - 0xffffffffff is OK;
+ 1. ring element is from heap, set Addrbase to NULL is ok;
+*/
+static inline void
+nsfw_mem_ring_init (struct nsfw_mem_ring *ring, unsigned int size,
+ void *addrbase, unsigned char memtype, unsigned char flag)
+{
+ unsigned int loop = 0;
+
+ if (!ring)
+ {
+ return;
+ }
+
+ ring->prod.head = 0;
+ ring->prod.tail = 0;
+ ring->cons.head = 0;
+ ring->cons.tail = 0;
+ ring->size = size;
+ ring->eltsize = 0;
+ ring->mask = size - 1;
+ ring->memtype = memtype;
+ ring->ringflag = flag;
+ ring->prodtflag = ring->prodhflag = get_sys_pid ();
+ ring->conshflag = ring->constflag = get_sys_pid ();
+ /*if shmem, addrbase already changed to primary memory address */
+ ring->Addrbase = addrbase;
+ ring->uireserv[0] = 0;
+ ring->uireserv[1] = 0;
+ ring->uireserv[2] = 0;
+ ring->uireserv[3] = 0;
+
+ /*init Ring */
+ for (loop = 0; loop < size; loop++)
+ {
+ /*
+ for a empty ring, version is the mapping head val - size
+ so the empty ring's ver is loop-size;
+ */
+ ring->ring[loop].data_s.ver = (loop - size);
+ ring->ring[loop].data_s.val = 0;
+ }
+}
+
+/*
+another way to init Pool while no continuous space
+1. init a empt rte_perf_ring
+2. add element to PerRing.
+*/
+static inline void
+nsfw_mem_pool_head_init (struct nsfw_mem_ring *ring, unsigned int size,
+ unsigned int eltsize, void *addrbase,
+ nsfw_mem_type memtype, nsfw_mpool_type flag)
+{
+ ring->prod.head = size;
+ ring->prod.tail = size;
+ ring->cons.head = 0;
+ ring->cons.tail = 0;
+ ring->size = size;
+ ring->eltsize = eltsize;
+ ring->mask = size - 1;
+ ring->memtype = memtype;
+ ring->ringflag = flag;
+ ring->prodtflag = ring->prodhflag = get_sys_pid ();
+ ring->conshflag = ring->constflag = get_sys_pid ();
+ /*if shmem, addrbase already changed to primary memory address */
+ ring->Addrbase = addrbase;
+ ring->uireserv[0] = 0;
+ ring->uireserv[1] = 0;
+ ring->uireserv[2] = 0;
+ ring->uireserv[3] = 0;
+ return;
+}
+
+#define NSFW_RING_FLAG_CHECK_RET(handle, desc) {\
+ if (((struct nsfw_mem_ring*)mhandle)->ringflag >= NSFW_MPOOL_TYPEMAX) \
+ { \
+ NSCOMM_LOGERR("invalid ring] desc=%s, ringflag=%d", desc, ((struct nsfw_mem_ring*)mhandle)->ringflag); \
+ return 0; \
+ } \
+ }
+
+#endif /*_NSFW_RING_FUN_H_*/
diff --git a/src/framework/common/mem_mgr/nsfw_mem_api.c b/src/framework/common/mem_mgr/nsfw_mem_api.c
new file mode 100644
index 0000000..b795921
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_mem_api.c
@@ -0,0 +1,879 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <sys/types.h>
+#include <unistd.h>
+#include "nsfw_mem_desc.h"
+#include "nstack_securec.h"
+
+#ifdef SYS_MEM_RES_STAT
+#include "common_mem_ring.h"
+#include "common_mem_mempool.h"
+#endif
+
+#define MEM_OP_CALL_OK_RET(mtype, fun, para) { \
+ if (g_nsfw_mem_ops[mtype].stmemop->fun) \
+ { \
+ return g_nsfw_mem_ops[mtype].stmemop->fun para; \
+ } \
+ }
+
+/*****************************************************************************
+* Prototype : nsfw_mem_init
+* Description : memory mgr module init
+* Input : point to nstak_fwmem_para
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_mem_init (void *para)
+{
+ nsfw_mem_para *ptempara = NULL;
+ i32 iret = NSFW_MEM_OK;
+ i32 icount = 0;
+ i32 iindex = 0;
+
+ if (NULL == para)
+ {
+ NSCOMM_LOGERR ("ns mem init input error");
+ return NSFW_MEM_ERR;
+ }
+
+ ptempara = (nsfw_mem_para *) para;
+
+ if (ptempara->enflag >= NSFW_PROC_MAX)
+ {
+ NSCOMM_LOGERR ("ns mem init input enflag invalid] enflag=%d",
+ ptempara->enflag);
+ return NSFW_MEM_ERR;
+ }
+
+ NSCOMM_LOGINF ("ns mem init begin] enflag=%d, iargsnum=%d",
+ ptempara->enflag, ptempara->iargsnum);
+
+ for (iindex = 0; iindex < ptempara->iargsnum; iindex++)
+ {
+ NSCOMM_LOGINF ("%s", ptempara->pargs[iindex]);
+ }
+
+ for (icount = 0; icount < g_mem_type_num; icount++)
+ {
+ if ((NULL != g_nsfw_mem_ops[icount].stmemop)
+ && (NULL != g_nsfw_mem_ops[icount].stmemop->mem_ops_init))
+ {
+ iret = g_nsfw_mem_ops[icount].stmemop->mem_ops_init (ptempara);
+
+ if (NSFW_MEM_OK != iret)
+ {
+ NSCOMM_LOGERR ("mem init failed]index=%d, memtype=%d", icount,
+ g_nsfw_mem_ops[icount].entype);
+ break;
+ }
+ }
+ }
+
+ /*if some module init fail, destory the moudles that success */
+ if (icount < g_mem_type_num)
+ {
+ for (iindex = 0; iindex < icount; iindex++)
+ {
+ if (g_nsfw_mem_ops[icount].stmemop->mem_ops_destroy)
+ {
+ g_nsfw_mem_ops[icount].stmemop->mem_ops_destroy ();
+ }
+ }
+
+ return NSFW_MEM_ERR;
+ }
+
+ NSCOMM_LOGINF ("ns mem init end");
+ return NSFW_MEM_OK;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_zone_create
+* Description : create a block memory with name
+* nsfw_mem_zone::stname
+* nsfw_mem_zone::isize
+* note : 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* Input : nsfw_mem_zone* pinfo
+* Output : None
+* Return Value : mzone_handle
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+mzone_handle
+nsfw_mem_zone_create (nsfw_mem_zone * pinfo)
+{
+
+ if ((NULL == pinfo) || (pinfo->stname.entype >= NSFW_MEM_TYPEMAX))
+ {
+ NSCOMM_LOGERR ("zone create input para error] pinfo=%p, mtype=%d",
+ pinfo, pinfo ? pinfo->stname.entype : (-1));
+ return NULL;
+ }
+
+ MEM_OP_CALL_OK_RET (pinfo->stname.entype, mem_ops_zone_creae, (pinfo));
+ NSCOMM_LOGINF ("mem create fail] memtype=%d, name=%s, size=%zu",
+ pinfo->stname.entype, pinfo->stname.aname, pinfo->lenth);
+ return NULL;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_zone_createv
+* Description : create some memory blocks
+* note : 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* Input : nsfw_mem_zone* pmeminfo
+* i32 inum
+* mzone_handle* paddr_array
+* i32 iarray_num
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_mem_zone_createv (nsfw_mem_zone * pmeminfo, i32 inum,
+ mzone_handle * paddr_array, i32 iarray_num)
+{
+ if ((NULL == pmeminfo) || (NULL == paddr_array)
+ || (inum != iarray_num) || (inum <= 0)
+ || (pmeminfo[0].stname.entype >= NSFW_MEM_TYPEMAX))
+ {
+ NSCOMM_LOGERR
+ ("input para error] pmeminfo=%p, inum=%d, paddr_array=%p, iarray_num=%d, mtype=%d",
+ pmeminfo, inum, paddr_array, iarray_num,
+ pmeminfo ? pmeminfo[0].stname.entype : (-1));
+ return NSFW_MEM_ERR;
+ }
+
+ MEM_OP_CALL_OK_RET (pmeminfo[0].stname.entype, mem_ops_zone_createv,
+ (pmeminfo, inum, paddr_array, iarray_num));
+ NSCOMM_LOGINF ("mem create fail] memtype=%d", pmeminfo[0].stname.entype);
+ return NSFW_MEM_ERR;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_zone_lookup
+* Description : look up a memory
+* 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* 2. if the memory is shared, pname->enowner indicate that who create this memory.
+* note : 1. when calling any shared memory create inferface, the name of memory end with _0 created by nStackMain,
+* end with none created by nStackMaster, and end with _<pid> created by other.
+* 2. pname->enowner is available only when call look up shared memory.
+* 3. if the roles of process is NSFW_PROC_MASTER but the memory was created by others, or pname->enowner is NSFW_PROC_NULL,
+* the name must be full name.
+* for examles if the memory was created by nStackMain and pname->enowner is NSFW_PROC_NULL,
+* must add '_0' at the end of name, if the memory was created by app and the role of process is NSFW_PROC_MASTER, must add
+* _(pid) at the end of name, nstack_123.
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : mzone_handle
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+mzone_handle
+nsfw_mem_zone_lookup (nsfw_mem_name * pname)
+{
+ NSFW_MEM_NAME_CHECK_RET_NULL (pname, "mem zone look up");
+ MEM_OP_CALL_OK_RET (pname->entype, mem_ops_zone_lookup, (pname));
+ NSCOMM_LOGERR ("mem lookup fail] memtype=%d, name=%s ", pname->entype,
+ pname->aname);
+ return NULL;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_zone_release
+* Description : release a memory
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_mem_zone_release (nsfw_mem_name * pname)
+{
+ NSFW_MEM_NAME_CHECK_RET_ERR (pname, "mem zone release");
+ MEM_OP_CALL_OK_RET (pname->entype, mem_ops_mzone_release, (pname));
+ NSCOMM_LOGERR ("mem release fail] memtype=%d, name=%s", pname->entype,
+ pname->aname);
+ return NSFW_MEM_ERR;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_mbfmp_create
+* Description : create a mbuf pool
+* Input : nsfw_mem_mbfpool* pbufinfo
+* Output : None
+* Return Value : mpool_handle
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+mpool_handle
+nsfw_mem_mbfmp_create (nsfw_mem_mbfpool * pbufinfo)
+{
+ if ((NULL == pbufinfo) || (pbufinfo->stname.entype >= NSFW_MEM_TYPEMAX))
+ {
+ NSCOMM_LOGERR ("input para error] pbufinfo=%p, mtype=%d", pbufinfo,
+ pbufinfo ? pbufinfo->stname.entype : (-1));
+ return NULL;
+ }
+
+ MEM_OP_CALL_OK_RET (pbufinfo->stname.entype, mem_ops_mbfmp_create,
+ (pbufinfo));
+ NSCOMM_LOGERR ("mbufmp create fail] memtype=%d, name=%s ",
+ pbufinfo->stname.entype, pbufinfo->stname.aname);
+ return NULL;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_mbfmp_createv
+* Description : create some mbuf pools
+* 1. the name of lenth must be less than NSFW_MEM_APPNAME_LENTH.
+* Input : nsfw_mem_mbfpool* pmbfname
+* i32 inum
+* mpool_handle* phandle_array
+* i32 iarray_num
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_mem_mbfmp_createv (nsfw_mem_mbfpool * pmbfname, i32 inum,
+ mpool_handle * phandle_array, i32 iarray_num)
+{
+ if ((NULL == pmbfname) || (NULL == phandle_array)
+ || (inum != iarray_num) || (inum <= 0)
+ || (pmbfname[0].stname.entype >= NSFW_MEM_TYPEMAX))
+ {
+ NSCOMM_LOGERR
+ ("input para error] pmbfname=%p, inum=%d, phandle_array=%p, iarray_num=%d",
+ pmbfname, inum, phandle_array, iarray_num,
+ pmbfname ? pmbfname[0].stname.entype : (-1));
+ return NSFW_MEM_ERR;
+ }
+
+ MEM_OP_CALL_OK_RET (pmbfname[0].stname.entype, mem_ops_mbfmp_createv,
+ (pmbfname, inum, phandle_array, iarray_num));
+ NSCOMM_LOGERR ("mbufmp createv fail] memtype=%d",
+ pmbfname[0].stname.entype);
+ return NSFW_MEM_ERR;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_mbf_alloc
+* Description : alloc a mbuf from mbuf pool
+* Input : mpool_handle mhandle
+* nsfw_mem_type entype
+* Output : None
+* Return Value : mbuf_handle
+* Calls :
+* Called By :
+*****************************************************************************/
+mbuf_handle
+nsfw_mem_mbf_alloc (mpool_handle mhandle, nsfw_mem_type entype)
+{
+ NSFW_MEM_MBUF_CHECK_RET_NULL (mhandle, entype, "mbf alloc");
+ MEM_OP_CALL_OK_RET (entype, mem_ops_mbf_alloc, (mhandle));
+ NSCOMM_LOGERR ("mbf alloc fail] handle=%p, type=%d", mhandle, entype);
+ return NULL;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_mbf_free
+* Description : put a mbuf backintp mbuf pool
+* Input : mbuf_handle mhandle
+* nsfw_mem_type entype
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_mem_mbf_free (mbuf_handle mhandle, nsfw_mem_type entype)
+{
+ NSFW_MEM_MBUF_CHECK_RET_ERR (mhandle, entype, "mbuf free");
+ MEM_OP_CALL_OK_RET (entype, mem_ops_mbf_free, (mhandle));
+ NSCOMM_LOGERR ("mbf free fail] handle=%p, type=%d", mhandle, entype);
+ return NSFW_MEM_ERR;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_mbfmp_lookup
+* Description : look up mbuf mpool
+* 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* 2. if the memory is shared, pname->enowner indicate that who create this memory.
+* note : 1. when calling any shared memory create inferface, the name of memory end with _0 created by nStackMain,
+* end with none created by nStackMaster, and end with _<pid> created by other.
+* 2. pname->enowner is available only when call look up shared memory.
+* 3. if the roles of process is NSFW_PROC_MASTER but the memory was created by others, or pname->enowner is NSFW_PROC_NULL,
+* the name must be full name.
+* for examles if the memory was created by nStackMain and pname->enowner is NSFW_PROC_NULL,
+* must add '_0' at the end of name, if the memory was created by app and the role of process is NSFW_PROC_MASTER, must add
+* _(pid) at the end of name, nstack_123.
+* Input : nsfw_mem_name* pmbfname
+* Output : None
+* Return Value : mpool_handle
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+mpool_handle
+nsfw_mem_mbfmp_lookup (nsfw_mem_name * pmbfname)
+{
+ NSFW_MEM_NAME_CHECK_RET_NULL (pmbfname, "mbuf pool look up");
+ MEM_OP_CALL_OK_RET (pmbfname->entype, mem_ops_mbfmp_lookup, (pmbfname));
+ NSCOMM_LOGERR ("mbufmp lookup fail] memtype=%d, name=%s ", pmbfname->entype,
+ pmbfname->aname);
+ return NULL;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_mbfmp_release
+* Description : release mbuf pool
+* note : 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_mem_mbfmp_release (nsfw_mem_name * pname)
+{
+ NSFW_MEM_NAME_CHECK_RET_ERR (pname, "mbuf mp release");
+ MEM_OP_CALL_OK_RET (pname->entype, mem_ops_mbfmp_release, (pname));
+ NSCOMM_LOGERR ("mbfmp release fail] memtype=%d, name=%s", pname->entype,
+ pname->aname);
+ return NSFW_MEM_ERR;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_sp_create
+* Description : create a simple pool
+* note : 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* Input : nsfw_mem_sppool* pmpinfo
+* Output : None
+* Return Value : mring_handle
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+mring_handle
+nsfw_mem_sp_create (nsfw_mem_sppool * pmpinfo)
+{
+ if ((NULL == pmpinfo) || (pmpinfo->stname.entype >= NSFW_MEM_TYPEMAX))
+ {
+ NSCOMM_LOGERR ("input para error] pmpinfo=%p, mtype=%d", pmpinfo,
+ pmpinfo ? pmpinfo->stname.entype : (-1));
+ return NULL;
+ }
+
+ MEM_OP_CALL_OK_RET (pmpinfo->stname.entype, mem_ops_sp_create, (pmpinfo));
+ NSCOMM_LOGERR ("sp create fail] memtype=%d, name=%s ",
+ pmpinfo->stname.entype, pmpinfo->stname.aname);
+ return NULL;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_sp_createv
+* Description : create some simple pools one time
+* note : 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* Input : nsfw_mem_sppool* pmpinfo
+* i32 inum
+* mring_handle* pringhandle_array
+* i32 iarray_num
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_mem_sp_createv (nsfw_mem_sppool * pmpinfo, i32 inum,
+ mring_handle * pringhandle_array, i32 iarray_num)
+{
+ NSFW_MEM_RINGV_CHECK_RET (pmpinfo, inum, pringhandle_array, iarray_num);
+ MEM_OP_CALL_OK_RET (pmpinfo[0].stname.entype, mem_ops_sp_createv,
+ (pmpinfo, inum, pringhandle_array, iarray_num));
+ NSCOMM_LOGERR ("sp createv fail] memtype=%d", pmpinfo[0].stname.entype);
+ return NSFW_MEM_ERR;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_sp_ring_create
+* Description : create a simple pool with many rings
+* note : 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* Input : nsfw_mem_mring* pringinfo
+* mring_handle* pringhandle_array
+* i32 iringnum
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_mem_sp_ring_create (nsfw_mem_mring * pringinfo,
+ mring_handle * pringhandle_array, i32 iringnum)
+{
+ NSFW_MEM_RING_CHECK_RET (pringinfo, pringhandle_array, iringnum);
+ MEM_OP_CALL_OK_RET (pringinfo[0].stname.entype, mem_ops_spring_create,
+ (pringinfo, pringhandle_array, iringnum));
+ NSCOMM_LOGERR ("mppool spring creat fail] memtype=%d",
+ pringinfo[0].stname.entype);
+ return NSFW_MEM_ERR;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_sp_release
+* Description : release a simple mempool
+* note : 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_mem_sp_release (nsfw_mem_name * pname)
+{
+ NSFW_MEM_NAME_CHECK_RET_ERR (pname, "sp release");
+ MEM_OP_CALL_OK_RET (pname->entype, mem_ops_sp_release, (pname));
+ NSCOMM_LOGERR ("sp release fail] memtype=%d, name=%s ", pname->entype,
+ pname->aname);
+ return NSFW_MEM_ERR;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_sp_lookup
+* Description : look up a simpile ring
+* 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* 2. if the memory is shared, pname->enowner indicate that who create this memory.
+* note : 1. when calling any shared memory create inferface, the name of memory end with _0 created by nStackMain,
+* end with none created by nStackMaster, and end with _<pid> created by other.
+* 2. pname->enowner is available only when call look up shared memory.
+* 3. if the roles of process is NSFW_PROC_MASTER but the memory was created by others, or pname->enowner is NSFW_PROC_NULL,
+* the name must be full name.
+* for examles if the memory was created by nStackMain and pname->enowner is NSFW_PROC_NULL,
+* must add '_0' at the end of name, if the memory was created by app and the role of process is NSFW_PROC_MASTER, must add
+* _(pid) at the end of name, nstack_123.
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : mring_handle
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+mring_handle
+nsfw_mem_sp_lookup (nsfw_mem_name * pname)
+{
+ NSFW_MEM_NAME_CHECK_RET_NULL (pname, "sp look up");
+ MEM_OP_CALL_OK_RET (pname->entype, mem_ops_sp_lookup, (pname));
+ NSCOMM_LOGERR ("sp lookup fail] memtype=%d, name=%s", pname->entype,
+ pname->aname);
+ return NULL;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_ring_create
+* Description : create a ring
+* note : 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* 2. shared memory ring (NSFW_SHMEM) just can put a pointor into the queue, the queue also point to a shared block memory.
+* no shared memory ring(NSFW_NSHMEM) is other wise.
+* Input : nsfw_mem_mring* pringinfo
+* Output : None
+* Return Value : mring_handle
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+mring_handle
+nsfw_mem_ring_create (nsfw_mem_mring * pringinfo)
+{
+ if ((NULL == pringinfo) || (pringinfo->stname.entype >= NSFW_MEM_TYPEMAX))
+ {
+ NSCOMM_LOGERR ("input para error] pmpinfo=%p, mtype=%d", pringinfo,
+ pringinfo ? pringinfo->stname.entype : (-1));
+ return NULL;
+ }
+
+ MEM_OP_CALL_OK_RET (pringinfo->stname.entype, mem_ops_ring_create,
+ (pringinfo));
+ NSCOMM_LOGERR ("ring create fail] memtype=%d, name=%s ",
+ pringinfo->stname.entype, pringinfo->stname.aname);
+ return NULL;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_ring_lookup
+* Description : look up a ring by name
+* 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+* 2. if the memory is shared, pname->enowner indicate that who create this memory.
+* note:
+* 1. when calling any shared memory create inferface, the name of memory end with _0 created by nStackMain,
+* end with none created by nStackMaster, and end with _<pid> created by other.
+* 2. pname->enowner is available only when call look up shared memory.
+* 3. if the roles of process is NSFW_PROC_MASTER but the memory was created by others, or pname->enowner is NSFW_PROC_NULL,
+* the name must be full name.
+* for examles if the memory was created by nStackMain and pname->enowner is NSFW_PROC_NULL,
+* must add '_0' at the end of name, if the memory was created by app and the role of process is NSFW_PROC_MASTER, must add
+* _(pid) at the end of name, nstack_123.
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : mring_handle
+* Calls :
+* Called By :
+*
+*
+*****************************************************************************/
+mring_handle
+nsfw_mem_ring_lookup (nsfw_mem_name * pname)
+{
+ NSFW_MEM_NAME_CHECK_RET_NULL (pname, "ring lookup");
+ MEM_OP_CALL_OK_RET (pname->entype, mem_ops_ring_lookup, (pname));
+ NSCOMM_LOGERR ("ring lookup fail] memtype=%d, name=%s", pname->entype,
+ pname->aname);
+ return NULL;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_ring_reset
+* Description : reset the number of producer and consumer, also, the
+* state of ring reset to empty
+* notes : must be called before doing any operations base on the ring
+* Input : mring_handle mhandle
+* nsfw_mpool_type entype
+* Output : None
+* Return Value : void
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+void
+nsfw_mem_ring_reset (mring_handle mhandle, nsfw_mpool_type entype)
+{
+ u32 loop = 0;
+ struct nsfw_mem_ring *ring = (struct nsfw_mem_ring *) mhandle;
+
+ if (!ring)
+ {
+ return;
+ }
+
+ ring->prod.head = 0;
+ ring->cons.tail = 0;
+ ring->ringflag = (u8) entype;
+
+ /*init Ring */
+ for (loop = 0; loop < ring->size; loop++)
+ {
+ /*
+ for a empty ring, version is the mapping head val - size
+ so the empty ring's ver is loop-size;
+ */
+ ring->ring[loop].data_s.ver = (loop - ring->size);
+ ring->ring[loop].data_s.val = 0;
+ }
+
+ return;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_ring_free_count
+* Description : get the free number of ring
+* Input : mring_handle mhandle
+* Output : None
+* Return Value : u32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+u32
+nsfw_mem_ring_free_count (mring_handle mhandle)
+{
+ struct nsfw_mem_ring *temp = NULL;
+ u32 thead = 0;
+ u32 ttail = 0;
+ if (NULL == mhandle)
+ {
+ NSCOMM_LOGERR ("input para error] mhandle=%p", mhandle);
+ return 0;
+ }
+
+ temp = (struct nsfw_mem_ring *) mhandle;
+ thead = temp->prod.head;
+ ttail = temp->cons.tail;
+ return ttail + temp->size - thead;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_ring_using_count
+* Description : get the in using number of ring
+* Input : mring_handle mhandle
+* Output : None
+* Return Value : u32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+u32
+nsfw_mem_ring_using_count (mring_handle mhandle)
+{
+ struct nsfw_mem_ring *temp = NULL;
+ u32 thead = 0;
+ u32 ttail = 0;
+ if (NULL == mhandle)
+ {
+ NSCOMM_LOGERR ("input para error] mhandle=%p", mhandle);
+ return 0;
+ }
+
+ temp = (struct nsfw_mem_ring *) mhandle;
+ thead = temp->prod.head;
+ ttail = temp->cons.tail;
+ return thead - ttail;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_ring_size
+* Description : get size of ring
+* Input : mring_handle mhandle
+* Output : None
+* Return Value : u32
+* Calls :
+* Called By :
+*****************************************************************************/
+u32
+nsfw_mem_ring_size (mring_handle mhandle)
+{
+ struct nsfw_mem_ring *temp = NULL;
+
+ if (NULL == mhandle)
+ {
+ NSCOMM_LOGERR ("input para error] mhandle=%p", mhandle);
+ return 0;
+ }
+
+ temp = (struct nsfw_mem_ring *) mhandle;
+
+ return temp->size;
+}
+
+#ifdef SYS_MEM_RES_STAT
+/*****************************************************************************
+* Prototype : nsfw_mem_mbfpool_free_count
+* Description : get the free mbuf count of a mbuf pool
+* Input : mpool_handle mhandle
+* Output : None
+* Return Value : u32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+u32
+nsfw_mem_mbfpool_free_count (mpool_handle mhandle)
+{
+ if (!mhandle)
+ {
+ NSCOMM_LOGERR ("input para error] mhandle=%p", mhandle);
+ return 0;
+ }
+ struct common_mem_mempool *mp = (struct common_mem_mempool *) mhandle;
+ struct common_mem_ring *mp_ring =
+ (struct common_mem_ring *) (mp->ring_align);
+ if (!mp_ring)
+ {
+ NSCOMM_LOGERR ("ring is null");
+ return 0;
+ }
+ u32 p_head = mp_ring->prod.head;
+ u32 c_tail = mp_ring->cons.tail;
+
+ return p_head - c_tail;
+}
+#endif /* SYS_MEM_RES_STAT */
+
+/*****************************************************************************
+* Prototype : nsfw_mem_ring_release
+* Description : release a ring memory
+* notes : the lenth of name must be less than NSFW_MEM_APPNAME_LENTH
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_mem_ring_release (nsfw_mem_name * pname)
+{
+ NSFW_MEM_NAME_CHECK_RET_ERR (pname, "ring release");
+ MEM_OP_CALL_OK_RET (pname->entype, mem_ops_ring_release, (pname));
+ NSCOMM_LOGERR ("ring release fail] name=%s, type=%d", pname->aname,
+ pname->entype);
+ return NSFW_MEM_ERR;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_get_len
+* Description : statics mbufpool, sppool, ring mem size.
+* return: <=0, err happen, >0 mem size
+* NSFW_MEM_MZONE: not surport because you already know the lenth when create
+* Input : void * handle
+* nsfw_mem_struct_type type
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*****************************************************************************/
+ssize_t
+nsfw_mem_get_len (void *handle, nsfw_mem_struct_type type)
+{
+ if (NULL == handle)
+ {
+ NSCOMM_LOGERR ("input para error] handle=%p", handle);
+ return -1;
+ }
+ if ((NSFW_MEM_SPOOL == type) || (NSFW_MEM_RING == type))
+ {
+ struct nsfw_mem_ring *ring = (struct nsfw_mem_ring *) handle;
+ if (ring->memtype >= NSFW_MEM_TYPEMAX)
+ {
+ NSCOMM_LOGERR ("invalid ring] ring type=%u ,handle=%p",
+ ring->memtype, handle);
+ return -1;
+ }
+ MEM_OP_CALL_OK_RET (ring->memtype, mem_ops_mem_statics, (handle, type));
+ }
+ else
+ {
+ MEM_OP_CALL_OK_RET (NSFW_SHMEM, mem_ops_mem_statics, (handle, type));
+ }
+ return -1;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_mbuf_pool_recycle
+* Description : recycle mbuf
+* Input : mpool_handle handle
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_mem_mbuf_pool_recycle (mpool_handle handle)
+{
+ MEM_OP_CALL_OK_RET (NSFW_SHMEM, mem_ops_mbuf_recycle, (handle));
+ return -1;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_sp_iterator
+* Description : spool iterator
+* Input : mpool_handle handle
+* u32 start
+* u32 end
+* nsfw_mem_item_fun fun
+* void *argv
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_mem_sp_iterator (mpool_handle handle, u32 start, u32 end,
+ nsfw_mem_item_fun fun, void *argv)
+{
+ MEM_OP_CALL_OK_RET (NSFW_SHMEM, mem_ops_sp_iterator,
+ (handle, start, end, fun, argv));
+ return -1;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_mbuf_iterator
+* Description : mbuf iterator
+* Input : mpool_handle handle
+* u32 start
+* u32 end
+* nsfw_mem_item_fun fun
+* void *argv
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_mem_mbuf_iterator (mpool_handle handle, u32 start, u32 end,
+ nsfw_mem_item_fun fun, void *argv)
+{
+ MEM_OP_CALL_OK_RET (NSFW_SHMEM, mem_ops_mbuf_iterator,
+ (handle, start, end, fun, argv));
+ return -1;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_dfx_ring_print
+* Description : print ring info
+* Input : mring_handle mhandle
+* Output : None
+* Return Value : if no err happen, return the lenth of string print, 0 or -1 maybe err happen
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_mem_dfx_ring_print (mring_handle mhandle, char *pbuf, int lenth)
+{
+ struct nsfw_mem_ring *temp = (struct nsfw_mem_ring *) mhandle;
+ u32 head = 0;
+ u32 tail = 0;
+ int ret = 0;
+ if ((!temp) || (!pbuf) || (lenth <= 0))
+ {
+ return 0;
+ }
+ head = temp->prod.head;
+ tail = temp->cons.tail;
+ ret =
+ SPRINTF_S (pbuf, lenth,
+ "[.Head=%u,\n .Tail=%u,\n .(|Tail-Head|)=%u,\n .size=%u,\n .mask=%u]\n",
+ head, tail, (tail >= head) ? (tail - head) : (head - tail),
+ temp->size, temp->mask);
+ return ret;
+}
diff --git a/src/framework/common/mem_mgr/nsfw_mem_construct.c b/src/framework/common/mem_mgr/nsfw_mem_construct.c
new file mode 100644
index 0000000..ed6fe27
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_mem_construct.c
@@ -0,0 +1,21 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "nsfw_init.h"
+#include "nsfw_mem_api.h"
+
+NSFW_MODULE_NAME (NSFW_MEM_MGR_MODULE)
+NSFW_MODULE_PRIORITY (10) NSFW_MODULE_INIT (nsfw_mem_init)
diff --git a/src/framework/common/mem_mgr/nsfw_mem_desc.c b/src/framework/common/mem_mgr/nsfw_mem_desc.c
new file mode 100644
index 0000000..d0fbfd3
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_mem_desc.c
@@ -0,0 +1,92 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <sys/types.h>
+#include <unistd.h>
+#include "nsfw_mem_desc.h"
+#include "nsfw_shmem_mdesc.h"
+#include "nsfw_nshmem_mdesc.h"
+#include "nsfw_shmem_ring.h"
+#include "nsfw_nshmem_ring.h"
+
+/* *INDENT-OFF* */
+/*the order you add must be NSFW_SHMEM, NSFW_NSHMEM*/
+nsfw_mem_attr g_nsfw_mem_ops[] =
+{
+ {NSFW_SHMEM, &g_shmem_ops},
+ {NSFW_NSHMEM, &g_nshmem_ops},
+};
+
+i32 g_mem_type_num = sizeof(g_nsfw_mem_ops) / sizeof(nsfw_mem_attr);
+
+
+nsfw_ring_ops g_ring_ops_arry[NSFW_MEM_TYPEMAX][NSFW_MPOOL_TYPEMAX] = {
+ {
+ {
+ (nsfw_mem_ring_enqueue_fun)nsfw_shmem_ring_sp_enqueue, \
+ (nsfw_mem_ring_dequeue_fun)nsfw_shmem_ring_sc_dequeue, \
+ (nsfw_mem_ring_dequeuev_fun)nsfw_shmem_ring_sc_dequeuev
+ },
+ {
+ (nsfw_mem_ring_enqueue_fun)nsfw_shmem_ring_mp_enqueue, \
+ (nsfw_mem_ring_dequeue_fun)nsfw_shmem_ring_sc_dequeue, \
+ (nsfw_mem_ring_dequeuev_fun)nsfw_shmem_ring_sc_dequeuev
+ },
+ {
+ (nsfw_mem_ring_enqueue_fun)nsfw_shmem_ring_sp_enqueue, \
+ (nsfw_mem_ring_dequeue_fun)nsfw_shmem_ring_mc_dequeue, \
+ (nsfw_mem_ring_dequeuev_fun)nsfw_shmem_ring_mc_dequeuev
+ },
+ {
+ (nsfw_mem_ring_enqueue_fun)nsfw_shmem_ring_mp_enqueue, \
+ (nsfw_mem_ring_dequeue_fun)nsfw_shmem_ring_mc_dequeue, \
+ (nsfw_mem_ring_dequeuev_fun)nsfw_shmem_ring_mc_dequeuev
+ },
+ {
+ (nsfw_mem_ring_enqueue_fun)nsfw_shmem_ring_singlethread_enqueue, \
+ (nsfw_mem_ring_dequeue_fun)nsfw_shmem_ring_singlethread_dequeue, \
+ (nsfw_mem_ring_dequeuev_fun)nsfw_shmem_ring_singlethread_dequeuev
+ }
+ },
+ {
+ {
+ (nsfw_mem_ring_enqueue_fun)nsfw_nshmem_ring_sp_enqueue, \
+ (nsfw_mem_ring_dequeue_fun)nsfw_nshmem_ring_sc_dequeue, \
+ (nsfw_mem_ring_dequeuev_fun)nsfw_nshmem_ring_sc_dequeuev
+ },
+ {
+ (nsfw_mem_ring_enqueue_fun)nsfw_nshmem_ring_mp_enqueue, \
+ (nsfw_mem_ring_dequeue_fun)nsfw_nshmem_ring_sc_dequeue, \
+ (nsfw_mem_ring_dequeuev_fun)nsfw_nshmem_ring_sc_dequeuev
+ },
+ {
+ (nsfw_mem_ring_enqueue_fun)nsfw_nshmem_ring_sp_enqueue, \
+ (nsfw_mem_ring_dequeue_fun)nsfw_nshmem_ring_mc_dequeue, \
+ (nsfw_mem_ring_dequeuev_fun)nsfw_nshmem_ring_mc_dequeuev
+ },
+ {
+ (nsfw_mem_ring_enqueue_fun)nsfw_nshmem_ring_mp_enqueue, \
+ (nsfw_mem_ring_dequeue_fun)nsfw_nshmem_ring_mc_dequeue, \
+ (nsfw_mem_ring_dequeuev_fun)nsfw_nshmem_ring_mc_dequeuev
+ },
+ {
+ (nsfw_mem_ring_enqueue_fun)nsfw_nshmem_ring_singlethread_enqueue, \
+ (nsfw_mem_ring_dequeue_fun)nsfw_nshmem_ring_singlethread_dequeue, \
+ (nsfw_mem_ring_dequeuev_fun)nsfw_nshmem_ring_singlethread_dequeuev
+ }
+ }
+};
+/* *INDENT-ON* */
diff --git a/src/framework/common/mem_mgr/nsfw_mem_stat.c b/src/framework/common/mem_mgr/nsfw_mem_stat.c
new file mode 100644
index 0000000..f7a1f41
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_mem_stat.c
@@ -0,0 +1,292 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdlib.h>
+#include "types.h"
+#include "nstack_securec.h"
+#include "nsfw_init.h"
+
+#include "nstack_log.h"
+#include "nsfw_maintain_api.h"
+#include "nsfw_mem_api.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define NSFW_MEM_STAT_NUM 512
+
+#define NSFW_MEM_STAT_MODULE "nsfw_mem_stat_module"
+
+typedef struct _nsfw_mem_stat
+{
+ u8 mem_type;
+ u8 alloc_flag;
+ char module[NSFW_MEM_MODULE_LEN];
+ char mem_name[NSFW_MEM_NAME_LEN];
+ u32 mem_size;
+} nsfw_mem_stat_t;
+
+nsfw_mem_stat_t g_mem_stat[NSFW_MEM_STAT_NUM];
+
+#ifdef SYS_MEM_RES_STAT
+#define MAX_STAT_ITEM_NUM 20
+typedef struct _mem_stat_item_t
+{
+ char name[32];
+ u64 size;
+} mem_stat_item_t;
+
+typedef struct _mem_stat_mgr_t
+{
+ u32 item_num;
+ mem_stat_item_t item[MAX_STAT_ITEM_NUM];
+} mem_stat_mgr;
+
+mem_stat_mgr g_max_mem_list;
+#endif
+
+/*****************************************************************************
+* Prototype : nsfw_mem_stat
+* Description : add memory stat
+* Input : char *module
+* char *mem_name
+* u8 mem_type
+* u32 mem_size
+* Output : None
+* Return Value : void
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+void
+nsfw_mem_stat (char *module, char *mem_name, u8 mem_type, u32 mem_size)
+{
+ if (NULL == module || NULL == mem_name)
+ {
+ NSFW_LOGERR ("argv err]module=%p,mem_name=%p", module, mem_name);
+ return;
+ }
+
+ int i;
+ nsfw_mem_stat_t *mem_stat_item = NULL;
+ for (i = 0; i < NSFW_MEM_STAT_NUM; i++)
+ {
+ if (FALSE == g_mem_stat[i].alloc_flag)
+ {
+ g_mem_stat[i].alloc_flag = TRUE;
+ mem_stat_item = &g_mem_stat[i];
+ break;
+ }
+ }
+
+ if (NULL == mem_stat_item)
+ {
+ NSFW_LOGERR ("mem stat full]module=%s,type=%u,name=%s,size=%u",
+ module, mem_type, mem_name, mem_size);
+ return;
+ }
+
+ mem_stat_item->mem_type = mem_type;
+ mem_stat_item->mem_size = mem_size;
+
+ if (EOK != STRCPY_S (mem_stat_item->module, NSFW_MEM_MODULE_LEN, module))
+ {
+ NSFW_LOGERR ("STRNCPY_S failed");
+ return;
+ }
+ if (EOK != STRCPY_S (mem_stat_item->mem_name, NSFW_MEM_NAME_LEN, mem_name))
+ {
+ NSFW_LOGERR ("STRNCPY_S failed");
+ return;
+ }
+
+ return;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_stat_print
+* Description : print all memory info
+* Input : None
+* Output : None
+* Return Value : void
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+void
+nsfw_mem_stat_print ()
+{
+ int i;
+ for (i = 0; i < NSFW_MEM_STAT_NUM; i++)
+ {
+ if (TRUE == g_mem_stat[i].alloc_flag)
+ {
+ NSFW_LOGINF ("mem_module=%s,name=%s,type=%u,size=%u",
+ g_mem_stat[i].module, g_mem_stat[i].mem_name,
+ g_mem_stat[i].mem_type, g_mem_stat[i].mem_size);
+ }
+ }
+
+}
+
+#ifdef SYS_MEM_RES_STAT
+void
+clear_mem_stat_item ()
+{
+ if (EOK != MEMSET_S ((char *) &g_max_mem_list, sizeof (mem_stat_mgr),
+ 0, sizeof (mem_stat_mgr)))
+ {
+ NSFW_LOGERR ("MEMSET_S failed");
+ }
+}
+
+void
+insert_mem_stat_item (char *name, u64 len)
+{
+ int j, temp;
+
+ if (g_max_mem_list.item_num == 0)
+ {
+ if (EOK !=
+ STRCPY_S (g_max_mem_list.item[0].name,
+ sizeof (g_max_mem_list.item[0].name), name))
+ {
+ NSFW_LOGERR ("STRCPY_S failed");
+ }
+ g_max_mem_list.item[0].size = len;
+ g_max_mem_list.item_num++;
+ return;
+ }
+ else if (g_max_mem_list.item_num < MAX_STAT_ITEM_NUM)
+ {
+ if (len <= g_max_mem_list.item[g_max_mem_list.item_num - 1].size)
+ {
+ if (EOK !=
+ STRCPY_S (g_max_mem_list.item[g_max_mem_list.item_num].name,
+ sizeof (g_max_mem_list.item
+ [g_max_mem_list.item_num].name), name))
+ {
+ NSFW_LOGERR ("STRCPY_S failed");
+ }
+ g_max_mem_list.item[g_max_mem_list.item_num].size = len;
+ g_max_mem_list.item_num++;
+ return;
+ }
+ j = 0;
+ temp = g_max_mem_list.item_num;
+ while (j < temp)
+ {
+ if (len >= g_max_mem_list.item[j].size)
+ {
+ goto insert_it;
+ }
+ j++;
+ }
+ if (j == temp)
+ {
+ if (EOK !=
+ STRCPY_S (g_max_mem_list.item[j].name,
+ sizeof (g_max_mem_list.item[j].name), name))
+ {
+ NSFW_LOGERR ("STRCPY_S failed");
+ }
+ g_max_mem_list.item[j].size = len;
+ g_max_mem_list.item_num++;
+ return;
+ }
+ }
+ else
+ {
+ j = 0;
+ temp = MAX_STAT_ITEM_NUM - 1;
+ while (j < MAX_STAT_ITEM_NUM)
+ {
+ if (len >= g_max_mem_list.item[j].size)
+ {
+ goto insert_it;
+ }
+ j++;
+ }
+ }
+
+ return;
+
+insert_it:
+ while (temp - 1 >= j)
+ {
+ if (EOK !=
+ STRCPY_S (g_max_mem_list.item[temp].name,
+ sizeof (g_max_mem_list.item[temp].name),
+ g_max_mem_list.item[temp - 1].name))
+ {
+ NSFW_LOGERR ("STRCPY_S failed");
+ }
+ g_max_mem_list.item[temp].size = g_max_mem_list.item[temp - 1].size;
+ temp--;
+ }
+ if (EOK !=
+ STRCPY_S (g_max_mem_list.item[j].name,
+ sizeof (g_max_mem_list.item[j].name), name))
+ {
+ NSFW_LOGERR ("STRCPY_S failed");
+ }
+ g_max_mem_list.item[j].size = len;
+ g_max_mem_list.item_num++;
+ return;
+}
+
+int
+get_mem_stat_item (int idx, char **name, u64 * len)
+{
+ if (idx < 0 || idx >= MAX_STAT_ITEM_NUM)
+ {
+ return -1;
+ }
+
+ *name = g_max_mem_list.item[idx].name;
+ *len = g_max_mem_list.item[idx].size;
+
+ return 0;
+}
+#endif
+
+static int nsfw_mem_stat_init (void *param);
+static int
+nsfw_mem_stat_init (void *param)
+{
+ MEM_STAT (NSFW_MEM_STAT_MODULE, "g_mem_stat", NSFW_NSHMEM,
+ sizeof (g_mem_stat));
+ nsfw_mem_stat_print ();
+#ifdef SYS_MEM_RES_STAT
+ clear_mem_stat_item ();
+#endif
+ return 0;
+}
+
+/* *INDENT-OFF* */
+NSFW_MODULE_NAME (NSFW_MEM_STAT_MODULE)
+NSFW_MODULE_PRIORITY (99)
+NSFW_MODULE_INIT (nsfw_mem_stat_init)
+/* *INDENT-ON* */
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mdesc.c b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mdesc.c
new file mode 100644
index 0000000..c78c27e
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mdesc.c
@@ -0,0 +1,47 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "nsfw_mem_desc.h"
+#include "nsfw_nshmem_mng.h"
+#include "nsfw_nshmem_mdesc.h"
+
+/*no share memory access inferface*/
+nsfw_mem_ops g_nshmem_ops = {
+ nsfw_nshmem_init,
+ nsfw_nshmem_destory,
+ nsfw_nshmem_create,
+ NULL,
+ nsfw_nshmem_lookup,
+ nsfw_nshmem_release,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ nsfw_nshmem_spcreate,
+ NULL,
+ NULL,
+ nsfw_nshmem_sprelease,
+ nsfw_nshmem_sp_lookup,
+ nsfw_nshmem_ringcreate,
+ NULL,
+ nsfw_nshmem_ringrelease,
+ nsfw_nshmem_stactic,
+ NULL,
+ NULL, /*mem_ops_sp_iterator */
+ NULL, /*mem_ops_mbuf_iterator */
+};
diff --git a/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mdesc.h b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mdesc.h
new file mode 100644
index 0000000..1b63520
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mdesc.h
@@ -0,0 +1,22 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_NSHMEM_MDESC_H
+#define _NSFW_NSHMEM_MDESC_H
+
+extern nsfw_mem_ops g_nshmem_ops;
+
+#endif
diff --git a/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mng.c b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mng.c
new file mode 100644
index 0000000..d5661fd
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mng.c
@@ -0,0 +1,544 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdlib.h>
+#include "nstack_log.h"
+#include "nstack_securec.h"
+#include "nsfw_mem_desc.h"
+#include "nsfw_ring_fun.h"
+#include "nsfw_nshmem_ring.h"
+#include "nsfw_nshmem_mng.h"
+
+#include "common_func.h"
+
+#define nsfw_get_glb_lock() (&g_nshmem_internal_cfg->mlock)
+
+#define NSFW_NSHMEM_INIT_CHK_RET_NULL() \
+ if ((!g_nshmem_internal_cfg) || (!g_nshmem_localdata)) \
+ { \
+ NSCOMM_LOGDBG("Error] g_nshmem_internal_cfg=%p, g_nshmem_localdata=%p", g_nshmem_internal_cfg, g_nshmem_localdata); \
+ return NULL; \
+ }
+
+#define NSFW_NSHMEM_INIT_CHK_RET() \
+ if ((!g_nshmem_internal_cfg) || (!g_nshmem_localdata)) \
+ { \
+ NSCOMM_LOGDBG("Error] g_nshmem_internal_cfg=%p, g_nshmem_localdata=%p", g_nshmem_internal_cfg, g_nshmem_localdata); \
+ return NSFW_MEM_ERR; \
+ }
+
+nsfw_mem_localdata *g_nshmem_localdata = NULL;
+nsfw_nshmem_cfg *g_nshmem_internal_cfg = NULL;
+
+/*look up a mem zone*/
+NSTACK_STATIC inline nsfw_nshmem_mzone *
+nsfw_nshmem_get_free_zone (void)
+{
+ int icnt = 0;
+
+ /*g_nshmem_internal_cfg must not be null if come here */
+ for (icnt = 0; icnt < COMMON_MEM_MAX_MEMZONE; icnt++)
+ {
+ if (g_nshmem_internal_cfg->amemzone[icnt].addr == NULL)
+ {
+ return &g_nshmem_internal_cfg->amemzone[icnt];
+ }
+ }
+
+ return NULL;
+}
+
+NSTACK_STATIC inline void
+nsfw_nshmem_free_zone (nsfw_nshmem_mzone * pzone)
+{
+ nsfw_nshmem_mzone *pzonebase = &g_nshmem_internal_cfg->amemzone[0];
+ nsfw_nshmem_mzone *pzoneend =
+ &g_nshmem_internal_cfg->amemzone[NSFW_NSHMEM_ZONE_MAX - 1];
+
+ if ((((int) ((char *) pzone - (char *) pzonebase) < 0)
+ || ((int) ((char *) pzone - (char *) pzoneend) > 0))
+ && ((unsigned int) ((char *) pzone - (char *) pzonebase) %
+ sizeof (nsfw_nshmem_mzone) != 0))
+ {
+ NSCOMM_LOGERR ("nshmem free fail] mem=%p", pzone);
+ return;
+ }
+ if (pzone->addr)
+ {
+ free (pzone->addr);
+ }
+ pzone->addr = NULL;
+
+ int ret = MEMSET_S ((void *) pzone, sizeof (nsfw_nshmem_mzone), 0,
+ sizeof (nsfw_nshmem_mzone));
+ if (EOK != ret)
+ {
+ NSCOMM_LOGERR ("MEMSET_S failed] mem=%p, ret=%d", pzone, ret);
+ }
+ return;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_init
+* Description : nsh module init
+* Input : nsfw_mem_para* para
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_nshmem_init (nsfw_mem_para * para)
+{
+ i32 iret = NSFW_MEM_OK;
+ NSCOMM_LOGINF ("nsfw nshmem init begin");
+ g_nshmem_localdata =
+ (nsfw_mem_localdata *) malloc (sizeof (nsfw_mem_localdata));
+
+ if (NULL == g_nshmem_localdata)
+ {
+ NSCOMM_LOGERR ("nshmem init g_nshmem_localdata malloc fail");
+ return NSFW_MEM_ERR;
+ }
+
+ iret =
+ MEMSET_S (g_nshmem_localdata, sizeof (nsfw_mem_localdata), 0,
+ sizeof (nsfw_mem_localdata));
+
+ if (EOK != iret)
+ {
+ NSCOMM_LOGERR ("nshmem init g_nshmem_localdata MEMSET_S fail");
+ goto ERROR;
+ }
+
+ g_nshmem_internal_cfg =
+ (nsfw_nshmem_cfg *) malloc (sizeof (nsfw_nshmem_cfg));
+
+ if (NULL == g_nshmem_internal_cfg)
+ {
+ NSCOMM_LOGERR ("nshmem init g_nshmem_internal_cfg malloc fail");
+ goto ERROR;
+ }
+
+ iret =
+ MEMSET_S (g_nshmem_internal_cfg, sizeof (nsfw_nshmem_cfg), 0,
+ sizeof (nsfw_nshmem_cfg));
+
+ if (EOK != iret)
+ {
+ NSCOMM_LOGERR ("nshmem init g_nshmem_internal_cfg MEMSET_S fail");
+ goto ERROR;
+ }
+
+ g_nshmem_localdata->enflag = para->enflag;
+ NSCOMM_LOGINF ("nsfw nshmem init end");
+ goto OK;
+
+ERROR:
+ iret = NSFW_MEM_ERR;
+ nsfw_nshmem_destory ();
+ return iret;
+OK:
+ iret = NSFW_MEM_OK;
+ return iret;
+}
+
+/*
+ * memory destory
+ */
+void
+nsfw_nshmem_destory (void)
+{
+ if (g_nshmem_localdata)
+ {
+ free (g_nshmem_localdata);
+ g_nshmem_localdata = NULL;
+ }
+
+ if (g_nshmem_internal_cfg)
+ {
+ free (g_nshmem_internal_cfg);
+ g_nshmem_internal_cfg = NULL;
+ }
+
+ return;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_reserv_safe
+* Description : malloc a memory and save to memzone
+* Input : const char* name
+* size_t lenth
+* Output : None
+* Return Value : mzone_handle
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+mzone_handle
+nsfw_nshmem_reserv_safe (const char *name, size_t lenth)
+{
+ void *addr = NULL;
+ i32 iret = NSFW_MEM_OK;
+ nsfw_nshmem_mzone *pmemzone = NULL;
+
+ if (lenth <= 0)
+ {
+ return NULL;
+ }
+
+ nsfw_write_lock (nsfw_get_glb_lock ());
+
+ addr = malloc (lenth);
+ if (!addr)
+ {
+ NSCOMM_LOGERR ("nshmem malloc addr fail] addr=%p", addr);
+ nsfw_write_unlock (nsfw_get_glb_lock ());
+ return NULL;
+ }
+
+ iret = MEMSET_S (addr, lenth, 0, lenth);
+ if (EOK != iret)
+ {
+ NSCOMM_LOGERR ("nshmem malloc addr MEMSET_S fail] addr=%p", addr);
+ free (addr);
+ nsfw_write_unlock (nsfw_get_glb_lock ());
+ return NULL;
+ }
+
+ pmemzone = nsfw_nshmem_get_free_zone ();
+
+ if (!pmemzone)
+ {
+ NSCOMM_LOGERR ("nshmem get free zone fail");
+ free (addr);
+ nsfw_write_unlock (nsfw_get_glb_lock ());
+ return NULL;
+ }
+
+ pmemzone->addr = addr;
+ pmemzone->lenth = lenth;
+ /*name must be less than NSFW_MEM_APPNAME_LENTH */
+ if (EOK !=
+ STRCPY_S ((char *) pmemzone->aname, sizeof (pmemzone->aname), name))
+ {
+ NSCOMM_LOGERR ("STRCPY_S failed]name=%s", name);
+ free (addr);
+ nsfw_write_unlock (nsfw_get_glb_lock ());
+ return NULL;
+ }
+
+ nsfw_write_unlock (nsfw_get_glb_lock ());
+ return addr;
+}
+
+/*
+ * create no shared memory
+ * nsfw_mem_zone::stname no shared memory name
+ * nsfw_mem_zone::isize memory size
+ */
+mzone_handle
+nsfw_nshmem_create (nsfw_mem_zone * pinfo)
+{
+
+ NSFW_NAME_LENCHECK_RET_NULL (pinfo->stname.aname, "nshmem create");
+ NSFW_NSHMEM_INIT_CHK_RET_NULL ();
+ return nsfw_nshmem_reserv_safe (pinfo->stname.aname, pinfo->lenth);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_lookup
+* Description : find a block memory by name
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : mzone_handle
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+mzone_handle
+nsfw_nshmem_lookup (nsfw_mem_name * pname)
+{
+ int icnt = 0;
+ nsfw_nshmem_mzone *mz = NULL;
+
+ NSFW_NAME_LENCHECK_RET_NULL (pname->aname, "nshmem lookup");
+ NSFW_NSHMEM_INIT_CHK_RET_NULL ();
+ nsfw_read_lock (nsfw_get_glb_lock ());
+
+ for (icnt = 0; icnt < NSFW_NSHMEM_ZONE_MAX; icnt++)
+ {
+ mz = &g_nshmem_internal_cfg->amemzone[icnt];
+
+ if (mz->addr != NULL
+ && !strncmp (pname->aname, mz->aname, NSFW_MEM_NAME_LENTH))
+ {
+ nsfw_read_unlock (nsfw_get_glb_lock ());
+ return mz->addr;
+ }
+ }
+
+ nsfw_read_unlock (nsfw_get_glb_lock ());
+ return NULL;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_release
+* Description : free a block memory
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_nshmem_release (nsfw_mem_name * pname)
+{
+ int icnt = 0;
+ nsfw_nshmem_mzone *mz = NULL;
+
+ NSFW_NAME_LENCHECK_RET (pname->aname, "nshmem release");
+ NSFW_NSHMEM_INIT_CHK_RET ();
+ nsfw_read_lock (nsfw_get_glb_lock ());
+
+ for (icnt = 0; icnt < NSFW_NSHMEM_ZONE_MAX; icnt++)
+ {
+ mz = &g_nshmem_internal_cfg->amemzone[icnt];
+
+ if (mz->addr != NULL
+ && !strncmp (pname->aname, mz->aname, NSFW_MEM_NAME_LENTH))
+ {
+ nsfw_nshmem_free_zone (mz);
+ nsfw_read_unlock (nsfw_get_glb_lock ());
+ return NSFW_MEM_OK;
+ }
+ }
+
+ nsfw_read_unlock (nsfw_get_glb_lock ());
+ return NSFW_MEM_OK;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_spcreate
+* Description : create a memory pool by ring
+* Input : nsfw_mem_sppool* pmpinfo
+* Output : None
+* Return Value : mring_handle
+* Calls :
+* Called By :
+*****************************************************************************/
+mring_handle
+nsfw_nshmem_spcreate (nsfw_mem_sppool * pmpinfo)
+{
+ size_t len = 0;
+ unsigned int usnum = common_mem_align32pow2 (pmpinfo->usnum + 1);
+ unsigned int uselt_size = pmpinfo->useltsize;
+ struct nsfw_mem_ring *pringhead = NULL;
+ unsigned int uscnt = 0;
+ char *pmz = NULL;
+ NSFW_NAME_LENCHECK_RET_NULL (pmpinfo->stname.aname, "nshmem sp create");
+ NSFW_NSHMEM_INIT_CHK_RET_NULL ();
+
+ len =
+ sizeof (struct nsfw_mem_ring) +
+ (size_t) usnum *sizeof (union RingData_U) + (size_t) usnum *uselt_size;
+ pringhead =
+ (struct nsfw_mem_ring *) nsfw_nshmem_reserv_safe (pmpinfo->stname.aname,
+ len);
+
+ if (!pringhead)
+ {
+ NSCOMM_LOGERR ("nshmem sp create mzone reserv fail");
+ return NULL;
+ }
+
+ nsfw_mem_ring_init (pringhead, usnum, pringhead, NSFW_NSHMEM,
+ pmpinfo->enmptype);
+ pmz =
+ ((char *) pringhead + sizeof (struct nsfw_mem_ring) +
+ usnum * sizeof (union RingData_U));
+
+ for (uscnt = 0; uscnt < usnum; uscnt++)
+ {
+ if (0 ==
+ g_ring_ops_arry[pringhead->memtype][pringhead->
+ ringflag].ring_ops_enqueue
+ (pringhead, (void *) pmz))
+ {
+ NSCOMM_LOGERR ("nsfw_nshmem_ringenqueue enque fail] uscnt=%u",
+ uscnt);
+ }
+
+ pmz = pmz + uselt_size;
+ }
+
+ return pringhead;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_sp_lookup
+* Description : look up a sppool memory
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : mring_handle
+* Calls :
+* Called By :
+*****************************************************************************/
+mring_handle
+nsfw_nshmem_sp_lookup (nsfw_mem_name * pname)
+{
+ return nsfw_nshmem_lookup (pname);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_sprelease
+* Description : release a sp pool
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_nshmem_sprelease (nsfw_mem_name * pname)
+{
+ NSFW_NAME_LENCHECK_RET (pname->aname, "nshmem sp mempool release");
+ NSFW_NSHMEM_INIT_CHK_RET ();
+ return nsfw_nshmem_release (pname);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_ringcreate
+* Description : create a ring
+* Input : nsfw_mem_mring* pringinfo
+* Output : None
+* Return Value : mring_handle
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+mring_handle
+nsfw_nshmem_ringcreate (nsfw_mem_mring * pringinfo)
+{
+ size_t len = 0;
+ unsigned int usnum = common_mem_align32pow2 (pringinfo->usnum + 1);
+ struct nsfw_mem_ring *pringhead = NULL;
+ NSFW_NAME_LENCHECK_RET_NULL (pringinfo->stname.aname, "nshmem ring create");
+ NSFW_NSHMEM_INIT_CHK_RET_NULL ();
+
+ len = sizeof (struct nsfw_mem_ring) + usnum * sizeof (union RingData_U);
+ pringhead =
+ (struct nsfw_mem_ring *) nsfw_nshmem_reserv_safe (pringinfo->stname.aname,
+ len);
+
+ if (!pringhead)
+ {
+ NSCOMM_LOGERR ("nshmem ring create mzone reserv fail");
+ return NULL;
+ }
+
+ nsfw_mem_ring_init (pringhead, usnum, (void *) pringhead, NSFW_NSHMEM,
+ pringinfo->enmptype);
+ return pringhead;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_ringrelease
+* Description : release a nsh ring memory
+* Input : nsfw_mem_name* pname
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32
+nsfw_nshmem_ringrelease (nsfw_mem_name * pname)
+{
+ NSFW_NAME_LENCHECK_RET (pname->aname, "nshmem ring mempool release");
+ NSFW_NSHMEM_INIT_CHK_RET ();
+ return nsfw_nshmem_release (pname);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_sppool_statics
+* Description : static the memory size of sppool
+* Input : mring_handle sppool
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+ssize_t
+nsfw_nshmem_sppool_statics (mring_handle sppool)
+{
+ struct nsfw_mem_ring *phead = (struct nsfw_mem_ring *) sppool;
+
+ return sizeof (struct nsfw_mem_ring) +
+ (ssize_t) phead->size * sizeof (union RingData_U) +
+ (ssize_t) phead->size * phead->eltsize;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_ring_statics
+* Description : static the memory size of ring
+* Input : mring_handle handle
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+ssize_t
+nsfw_nshmem_ring_statics (mring_handle handle)
+{
+ struct nsfw_mem_ring *ring = (struct nsfw_mem_ring *) handle;
+ return ring->size * sizeof (union RingData_U) +
+ sizeof (struct nsfw_mem_ring);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_nshmem_stactic
+* Description : static the memory size according to mem type
+* Input : void* handle
+* nsfw_mem_struct_type type
+* Output : None
+* Return Value : ssize_t
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+ssize_t
+nsfw_nshmem_stactic (void *handle, nsfw_mem_struct_type type)
+{
+ switch (type)
+ {
+ case NSFW_MEM_MBUF:
+ return -1;
+ case NSFW_MEM_SPOOL:
+ return nsfw_nshmem_sppool_statics (handle);
+ case NSFW_MEM_RING:
+ return nsfw_nshmem_ring_statics (handle);
+ default:
+ break;
+ }
+ return -1;
+}
diff --git a/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mng.h b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mng.h
new file mode 100644
index 0000000..3f5b1b9
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_mng.h
@@ -0,0 +1,70 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_NSHMEM_MNG_H_
+#define _NSFW_NSHMEM_MNG_H_
+
+#include "generic/common_mem_rwlock.h"
+
+#include "common_func.h"
+
+#define NSFW_NSHMEM_ZONE_MAX 2560
+
+typedef struct
+{
+ i8 aname[NSFW_MEM_NAME_LENTH];
+ void *addr;
+ int lenth;
+} nsfw_nshmem_mzone;
+
+typedef struct
+{
+ nsfw_nshmem_mzone amemzone[NSFW_NSHMEM_ZONE_MAX];
+ common_mem_rwlock_t mlock;
+} nsfw_nshmem_cfg;
+
+/*
+ * no share memory module init
+ */
+i32 nsfw_nshmem_init (nsfw_mem_para * para);
+
+/*
+ * no share memory moudle destory
+ */
+void nsfw_nshmem_destory (void);
+
+/*
+ * create a no shared memory
+ */
+mzone_handle nsfw_nshmem_create (nsfw_mem_zone * pinfo);
+
+mzone_handle nsfw_nshmem_lookup (nsfw_mem_name * pname);
+
+i32 nsfw_nshmem_release (nsfw_mem_name * pname);
+
+mring_handle nsfw_nshmem_spcreate (nsfw_mem_sppool * pmpinfo);
+
+i32 nsfw_nshmem_sprelease (nsfw_mem_name * pname);
+
+mring_handle nsfw_nshmem_sp_lookup (nsfw_mem_name * pname);
+
+mring_handle nsfw_nshmem_ringcreate (nsfw_mem_mring * pringinfo);
+
+i32 nsfw_nshmem_ringrelease (nsfw_mem_name * pname);
+
+ssize_t nsfw_nshmem_stactic (void *handle, nsfw_mem_struct_type type);
+
+#endif
diff --git a/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_ring.c b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_ring.c
new file mode 100644
index 0000000..64e7d57
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_ring.c
@@ -0,0 +1,436 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <string.h>
+#include <sched.h>
+#include "nstack_securec.h"
+
+#include "nsfw_mem_desc.h"
+#include "nsfw_nshmem_ring.h"
+#include "nsfw_ring_fun.h"
+#include "common_func.h"
+
+/*copy the data to obj*/
+NSTACK_STATIC inline void
+nsfw_nshmem_ring_obj_copy (struct nsfw_mem_ring *r, uint32_t cons_head,
+ void **obj_table, unsigned n)
+{
+ uint32_t idx = cons_head & r->mask;
+ unsigned i = 0;
+ const uint32_t size = r->size;
+
+ if (likely (idx + n < size))
+ {
+ for (i = 0; i < (n & (~(unsigned) 0x3)); i += 4, idx += 4)
+ {
+ obj_table[i] = (void *) r->ring[idx].data_l;
+ obj_table[i + 1] = (void *) r->ring[idx + 1].data_l;
+ obj_table[i + 2] = (void *) r->ring[idx + 2].data_l;
+ obj_table[i + 3] = (void *) r->ring[idx + 3].data_l;
+ }
+ switch (n & 0x3)
+ {
+ case 3:
+ obj_table[i++] = (void *) r->ring[idx++].data_l;
+
+ case 2:
+ obj_table[i++] = (void *) r->ring[idx++].data_l;
+
+ case 1:
+ obj_table[i++] = (void *) r->ring[idx++].data_l;
+ }
+ }
+ else
+ {
+ for (i = 0; idx < size; i++, idx++)
+ {
+ obj_table[i] = (void *) r->ring[idx].data_l;
+ }
+
+ for (idx = 0; i < n; i++, idx++)
+ {
+ obj_table[i] = (void *) r->ring[idx].data_l;
+ }
+ }
+}
+
+/*fork recover*/
+NSTACK_STATIC inline void
+nsfw_nshmem_enqueue_fork_recov (struct nsfw_mem_ring *r)
+{
+ u32_t pidflag = 0;
+ u32_t curpid = get_sys_pid ();
+ int success = 0;
+ /*if pid is not the same, maybe mult thread fork happen */
+ pidflag = r->prodhflag;
+
+ if (unlikely (pidflag != curpid))
+ {
+ success = common_mem_atomic32_cmpset (&r->prodhflag, pidflag, curpid);
+
+ if (unlikely (success != 0))
+ {
+ /*recover it */
+ if (r->prod.tail != r->prod.head)
+ {
+ r->prod.head = r->prod.tail;
+ }
+
+ r->prodtflag = curpid;
+ }
+ }
+
+ return;
+}
+
+NSTACK_STATIC inline void
+nsfw_nshmem_dequeue_fork_recov (struct nsfw_mem_ring *r)
+{
+ u32_t pidflag = 0;
+ u32_t curpid = get_sys_pid ();
+ int success = 0;
+ /*if pid is not the same, maybe mult thread fork happen */
+ pidflag = r->conshflag;
+
+ if (unlikely (pidflag != curpid))
+ {
+ success = common_mem_atomic32_cmpset (&r->conshflag, pidflag, curpid);
+
+ if (unlikely (success != 0))
+ {
+ /*recover it */
+ if (r->cons.tail != r->cons.head)
+ {
+ r->cons.head = r->cons.tail;
+ }
+
+ r->constflag = curpid;
+ }
+ }
+
+ return;
+}
+
+/*
+this is a multi thread/process enqueue function, please pay attention to the bellow point
+1. while Enqueue corrupt, we may lose one element; because no one to add the Head
+*/
+int
+nsfw_nshmem_ring_mp_enqueue (struct nsfw_mem_ring *mem_ring, void *obj_table)
+{
+ uint32_t prod_head, prod_next;
+ uint32_t cons_tail, free_entries;
+ int success;
+ unsigned rep = 0;
+ uint32_t mask = mem_ring->mask;
+ uint32_t size = mem_ring->size;
+ uint32_t n = 1;
+
+ /* move prod.head atomically */
+ do
+ {
+
+ prod_head = mem_ring->prod.head;
+ cons_tail = mem_ring->cons.tail;
+ /* The subtraction is done between two unsigned 32bits value
+ * (the result is always modulo 32 bits even if we have
+ * prod_head > cons_tail). So 'free_entries' is always between 0
+ * and size(ring)-1. */
+ free_entries = (size + cons_tail - prod_head);
+
+ /* check that we have enough room in ring */
+ if (unlikely (n > free_entries))
+ {
+ return 0;
+ /* Below code is commented currenlty as its a dead code. */
+ }
+
+ /*if pid is not the same, maybe mult thread fork happen */
+ nsfw_nshmem_enqueue_fork_recov (mem_ring);
+
+ while (unlikely
+ ((mem_ring->prod.tail != mem_ring->prod.head)
+ || (mem_ring->prodtflag != mem_ring->prodhflag)))
+ {
+ common_mem_pause ();
+ }
+
+ prod_next = prod_head + n;
+ success =
+ common_mem_atomic32_cmpset (&mem_ring->prod.head, prod_head,
+ prod_next);
+ }
+ while (unlikely (success == 0));
+
+ mem_ring->ring[prod_head & mask].data_l = (u64) obj_table;
+
+ /*
+ * If there are other enqueues in progress that preceded us,
+ * we need to wait for them to complete
+ */
+ while (unlikely (mem_ring->prod.tail != prod_head))
+ {
+ common_mem_pause ();
+
+ /* Set COMMON_RING_PAUSE_REP_COUNT to avoid spin too long waiting
+ * for other thread finish. It gives pre-empted thread a chance
+ * to proceed and finish with ring dequeue operation. */
+ /* check the queue can be operate */
+ if (++rep == 5)
+ {
+ rep = 0;
+ (void) sched_yield ();
+ }
+ }
+
+ mem_ring->prod.tail = prod_next;
+ return (int) n;
+}
+
+/*
+ this is a single thread/process enqueue function
+ */
+int
+nsfw_nshmem_ring_sp_enqueue (struct nsfw_mem_ring *r, void *obj_table)
+{
+ uint32_t prod_head, cons_tail;
+ uint32_t prod_next, free_entries;
+ uint32_t mask = r->mask;
+ uint32_t n = 1;
+ uint32_t size = r->size;
+
+ prod_head = r->prod.head;
+ cons_tail = r->cons.tail;
+ /* The subtraction is done between two unsigned 32bits value
+ * (the result is always modulo 32 bits even if we have
+ * prod_head > cons_tail). So 'free_entries' is always between 0
+ * and size(ring)-1. */
+ free_entries = size + cons_tail - prod_head;
+
+ /* check that we have enough room in ring */
+ if (unlikely (n > free_entries))
+ {
+ return 0;
+ }
+
+ nsfw_nshmem_enqueue_fork_recov (r);
+
+ prod_next = prod_head + n;
+ r->prod.head = prod_next;
+
+ r->ring[prod_head & mask].data_l = (u64) obj_table;
+
+ r->prod.tail = prod_next;
+ return (int) n;
+}
+
+/*
+ this is enhanced mc_ring_dequeue, support dequeue multi element one time.
+*/
+int
+nsfw_nshmem_ring_mc_dequeuev (struct nsfw_mem_ring *r, void **obj_table,
+ unsigned int n)
+{
+ uint32_t cons_head, prod_tail;
+ uint32_t cons_next, entries;
+ int success;
+ unsigned rep = 0;
+ uint32_t num = n;
+
+ /* Avoid the unnecessary cmpset operation below, which is also
+ * potentially harmful when n equals 0. */
+ if (unlikely (num == 0))
+ {
+ return 0;
+ }
+
+ nsfw_nshmem_dequeue_fork_recov (r);
+
+ /* move cons.head atomically */
+ do
+ {
+ num = n;
+ cons_head = r->cons.head;
+ prod_tail = r->prod.tail;
+ /* The subtraction is done between two unsigned 32bits value
+ * (the result is always modulo 32 bits even if we have
+ * cons_head > prod_tail). So 'entries' is always between 0
+ * and size(ring)-1. */
+ entries = (prod_tail - cons_head);
+
+ /* Set the actual entries for dequeue */
+ if (unlikely (num > entries))
+ {
+ if (likely (entries > 0))
+ {
+ num = entries;
+ }
+ else
+ {
+ return 0;
+ }
+ }
+
+ /* check the queue can be operate */
+ while (unlikely
+ ((r->cons.tail != r->cons.head)
+ || (r->conshflag != r->constflag)))
+ {
+ common_mem_pause ();
+ }
+
+ cons_next = cons_head + num;
+
+ success =
+ common_mem_atomic32_cmpset (&r->cons.head, cons_head, cons_next);
+ }
+ while (unlikely (success == 0));
+
+ nsfw_nshmem_ring_obj_copy (r, cons_head, obj_table, num);
+
+ /*
+ * If there are other dequeues in progress that preceded us,
+ * we need to wait for them to complete
+ */
+ while (unlikely (r->cons.tail != cons_head))
+ {
+ common_mem_pause ();
+
+ /* Set COMMON_RING_PAUSE_REP_COUNT to avoid spin too long waiting
+ * for other thread finish. It gives pre-empted thread a chance
+ * to proceed and finish with ring dequeue operation. */
+ /* check the queue can be operate */
+ if (++rep == 5)
+ {
+ rep = 0;
+ (void) sched_yield ();
+ }
+ }
+
+ r->cons.tail = cons_next;
+
+ return (int) num;
+}
+
+/*this is a multi thread/process dequeue function, please pay attention to the bellow point
+1. while dequeue corrupt, the tail no one added, may multy the try times.
+*/
+int
+nsfw_nshmem_ring_mc_dequeue (struct nsfw_mem_ring *ring, void **box)
+{
+ return nsfw_nshmem_ring_mc_dequeuev (ring, box, 1);
+}
+
+/*
+ this is a single thread/process dequeue function
+*/
+int
+nsfw_nshmem_ring_sc_dequeuev (struct nsfw_mem_ring *r, void **obj_table,
+ unsigned int n)
+{
+ uint32_t cons_head, prod_tail;
+ uint32_t cons_next, entries;
+ uint32_t inum = n;
+ cons_head = r->cons.head;
+ prod_tail = r->prod.tail;
+ /* The subtraction is done between two unsigned 32bits value
+ * (the result is always modulo 32 bits even if we have
+ * cons_head > prod_tail). So 'entries' is always between 0
+ * and size(ring)-1. */
+ entries = prod_tail - cons_head;
+
+ if (unlikely (inum > entries))
+ {
+ if (likely (entries > 0))
+ {
+ inum = entries;
+ }
+ else
+ {
+ return 0;
+ }
+ }
+
+ nsfw_nshmem_dequeue_fork_recov (r);
+
+ cons_next = cons_head + inum;
+ r->cons.head = cons_next;
+
+ nsfw_nshmem_ring_obj_copy (r, cons_head, obj_table, inum);
+
+ r->cons.tail = cons_next;
+ return (int) inum;
+}
+
+/*
+ this is enhanced mc_ring_dequeue, support dequeue multi element one time.
+*/
+int
+nsfw_nshmem_ring_sc_dequeue (struct nsfw_mem_ring *ring, void **box)
+{
+ return nsfw_nshmem_ring_sc_dequeuev (ring, box, 1);
+}
+
+/*stack just using one thread, for performance using que not support multi thread*/
+int
+nsfw_nshmem_ring_singlethread_enqueue (struct nsfw_mem_ring *ring, void *box)
+{
+ u32 head = 0;
+
+ /*if queue is full, just return 0 */
+ if (unlikely (ring->prod.head >= (ring->size + ring->cons.tail)))
+ {
+ return 0;
+ }
+
+ head = ring->prod.head;
+ ring->ring[head & ring->mask].data_l = (u64) box;
+ ring->prod.head++;
+ return 1;
+}
+
+/*stack just using one thread, for performance using que not support multi thread*/
+int
+nsfw_nshmem_ring_singlethread_dequeue (struct nsfw_mem_ring *ring, void **box)
+{
+ return nsfw_nshmem_ring_singlethread_dequeuev (ring, box, 1);
+}
+
+/*stack just using one thread, for performance using que not support multi thread*/
+int
+nsfw_nshmem_ring_singlethread_dequeuev (struct nsfw_mem_ring *ring,
+ void **box, unsigned int n)
+{
+ u32 tail = 0;
+ u32 num = 0;
+
+ while (num < n)
+ {
+ tail = ring->cons.tail;
+
+ /* if all entries are dequed return 0 */
+ if (unlikely (ring->prod.head == ring->cons.tail))
+ {
+ return num;
+ }
+
+ box[num] = (void *) ring->ring[tail & ring->mask].data_l;
+ ring->cons.tail++;
+ num++;
+ }
+
+ return num;
+}
diff --git a/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_ring.h b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_ring.h
new file mode 100644
index 0000000..93a4d4a
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_nshmem/nsfw_nshmem_ring.h
@@ -0,0 +1,37 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_NSHMEM_RING_H_
+#define _NSFW_NSHMEM_RING_H_
+
+#include <stdint.h>
+
+int nsfw_nshmem_ring_mp_enqueue (struct nsfw_mem_ring *ring, void *box);
+int nsfw_nshmem_ring_sp_enqueue (struct nsfw_mem_ring *ring, void *box);
+int nsfw_nshmem_ring_mc_dequeue (struct nsfw_mem_ring *ring, void **box);
+int nsfw_nshmem_ring_mc_dequeuev (struct nsfw_mem_ring *ring, void **box,
+ unsigned int n);
+int nsfw_nshmem_ring_sc_dequeue (struct nsfw_mem_ring *ring, void **box);
+int nsfw_nshmem_ring_sc_dequeuev (struct nsfw_mem_ring *ring, void **box,
+ unsigned int n);
+int nsfw_nshmem_ring_singlethread_enqueue (struct nsfw_mem_ring *ring,
+ void *box);
+int nsfw_nshmem_ring_singlethread_dequeue (struct nsfw_mem_ring *ring,
+ void **box);
+int nsfw_nshmem_ring_singlethread_dequeuev (struct nsfw_mem_ring *ring,
+ void **box, unsigned int n);
+
+#endif /*_NSFW_NSHMEM_RING_H_*/
diff --git a/src/framework/common/mem_mgr/nsfw_res_mgr.c b/src/framework/common/mem_mgr/nsfw_res_mgr.c
new file mode 100644
index 0000000..2f676c9
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_res_mgr.c
@@ -0,0 +1,429 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+/*==============================================*
+ * include header files *
+ *----------------------------------------------*/
+
+/*==============================================*
+ * constants or macros define *
+ *----------------------------------------------*/
+
+/*==============================================*
+ * project-wide global variables *
+ *----------------------------------------------*/
+
+/*==============================================*
+ * routines' or functions' implementations *
+ *----------------------------------------------*/
+
+#include <stdlib.h>
+#include "types.h"
+#include "nstack_securec.h"
+#include "nsfw_init.h"
+#include "common_mem_mbuf.h"
+
+#include "nstack_log.h"
+#include "nsfw_maintain_api.h"
+
+#include "nsfw_mem_api.h"
+#include "nsfw_fd_timer_api.h"
+#include "nsfw_ring_data.h"
+
+#include "common_func.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+nsfw_res_mgr_item_cfg g_all_res_can[NSFW_MAX_RES_SCAN_COUNT];
+
+#define NSFW_RES_SCAN_TVLAUE_DEF 60
+#define NSFW_RES_SCAN_TVLAUE (g_scan_cfg.scan_tvalue)
+
+typedef struct _nsfw_res_scan_init_cfg
+{
+ nsfw_timer_info *scan_timer;
+ u16 scan_tvalue;
+} nsfw_res_scan_init_cfg;
+nsfw_res_scan_init_cfg g_scan_cfg;
+
+u8
+nsfw_res_mgr_reg (nsfw_res_scn_cfg * cfg)
+{
+ if (NULL == cfg)
+ {
+ NSFW_LOGERR ("argv err!");
+ return FALSE;
+ }
+
+ u32 i;
+ for (i = 0; i < NSFW_MAX_RES_SCAN_COUNT; i++)
+ {
+ if ((NULL == g_all_res_can[i].scn_cfg.free_fun)
+ &&
+ (__sync_bool_compare_and_swap
+ (&g_all_res_can[i].scn_cfg.free_fun, 0, cfg->free_fun)))
+ {
+ g_all_res_can[i].scn_cfg = *cfg;
+ NSFW_LOGINF ("reg res_mgr fun suc]fun=%p,data=%p", cfg->free_fun,
+ cfg->data);
+ return TRUE;
+ }
+ }
+
+ NSFW_LOGERR
+ ("reg]type=%u,per=%u,chk=%u,cyc=%u,total=%u,size=%u,offset=%u,fun=%p,data=%p",
+ cfg->type, cfg->force_free_percent, cfg->force_free_chk_num,
+ cfg->num_per_cyc, cfg->total_num, cfg->elm_size, cfg->res_mem_offset,
+ cfg->res_mem_offset, cfg->free_fun, cfg->data);
+ return FALSE;
+}
+
+static inline u32
+nsfw_get_alloc_count (u32 head, u32 tail)
+{
+ if (head >= tail)
+ {
+ return head - tail;
+ }
+
+ return head + (0xFFFFFFFF - tail);
+}
+
+int
+nsfw_res_sp_item_chk (void *data, void *argv)
+{
+ nsfw_res_mgr_item_cfg *res_scn_item = (nsfw_res_mgr_item_cfg *) argv;
+ nsfw_res_scn_cfg *scn_cfg = &res_scn_item->scn_cfg;
+ char *elm = (char *) data;
+
+ if (NULL == scn_cfg || NULL == elm)
+ {
+ return FALSE;
+ }
+
+ nsfw_res *res_item = NULL;
+ res_item = (nsfw_res *) (elm + scn_cfg->res_mem_offset);
+ if (0 == res_item->chk_count)
+ {
+ res_item->data = res_scn_item->cons_head;
+ }
+ res_item->chk_count++;
+
+ if (res_item->chk_count < scn_cfg->force_free_chk_num)
+ {
+ return FALSE;
+ }
+
+ if (res_scn_item->free_percent > scn_cfg->force_free_percent)
+ {
+ return FALSE;
+ }
+
+ if (scn_cfg->total_num * scn_cfg->alloc_speed_factor >
+ nsfw_get_alloc_count (res_scn_item->cons_head, res_item->data))
+ {
+ return FALSE;
+ }
+
+ if (NULL == scn_cfg->free_fun)
+ {
+ return FALSE;
+ }
+
+ if (TRUE == scn_cfg->free_fun ((void *) elm))
+ {
+ res_scn_item->force_count++;
+ }
+
+ res_item->chk_count = 0;
+ return TRUE;
+}
+
+int
+nsfw_res_flash_data (nsfw_res_mgr_item_cfg * res_scn_item)
+{
+ nsfw_res_scn_cfg *scn_cfg = &res_scn_item->scn_cfg;
+
+ u32 cur_head = 0;
+ u32 cur_tail = 0;
+ u32 elm_num = 0;
+ u32 free_count = 0;
+
+ switch (scn_cfg->type)
+ {
+ case NSFW_RES_SCAN_MBUF:
+ {
+ struct common_mem_ring *ring =
+ (struct common_mem_ring *) scn_cfg->mgr_ring;
+ struct common_mem_mempool *mp =
+ (struct common_mem_mempool *) scn_cfg->data;
+ if (NULL == ring)
+ {
+ ring = mp->ring;
+ if (NULL == ring)
+ return FALSE;
+ }
+ cur_head = ring->prod.head;
+ cur_tail = ring->cons.head;
+ elm_num = mp->size;
+ }
+ break;
+ case NSFW_RES_SCAN_SPOOL:
+ {
+ struct nsfw_mem_ring *mem_ring =
+ (struct nsfw_mem_ring *) scn_cfg->mgr_ring;
+ if (NULL == mem_ring)
+ {
+ mem_ring = (struct nsfw_mem_ring *) scn_cfg->data;
+ if (NULL == mem_ring)
+ return FALSE;
+ }
+
+ cur_head = mem_ring->prod.head;
+ cur_tail = mem_ring->cons.tail;
+ elm_num = mem_ring->size;
+ }
+ break;
+ case NSFW_RES_SCAN_ARRAY:
+ {
+ struct nsfw_mem_ring *mem_ring =
+ (struct nsfw_mem_ring *) scn_cfg->mgr_ring;
+ if (NULL == mem_ring)
+ {
+ return FALSE;
+ }
+
+ cur_head = mem_ring->prod.head;
+ cur_tail = mem_ring->cons.tail;
+ elm_num = scn_cfg->total_num;
+ }
+ break;
+ default:
+ return FALSE;
+ }
+
+ free_count = nsfw_get_alloc_count (cur_head, cur_tail);
+
+ res_scn_item->cons_head = cur_head;
+ res_scn_item->prod_head = cur_tail;
+ if (0 != elm_num)
+ {
+ res_scn_item->free_percent = free_count * 100 / elm_num;
+ }
+ else
+ {
+ res_scn_item->free_percent = 100;
+ }
+
+ scn_cfg->total_num = elm_num;
+ return TRUE;
+}
+
+void
+nsfw_res_scan_mem (nsfw_res_mgr_item_cfg * res_scn_item)
+{
+ if (NULL == res_scn_item)
+ {
+ return;
+ }
+
+ nsfw_res_scn_cfg *scn_cfg = &res_scn_item->scn_cfg;
+ if (NULL == scn_cfg->data)
+ {
+ return;
+ }
+
+ u32 start = res_scn_item->last_scn_idx;
+ u32 end = start + scn_cfg->num_per_cyc;
+ int res_chk_number = 0;
+ if (NSFW_RES_SCAN_SPOOL == scn_cfg->type)
+ {
+ res_chk_number =
+ nsfw_mem_sp_iterator (scn_cfg->data, start, end,
+ nsfw_res_sp_item_chk, (void *) res_scn_item);
+ }
+ else
+ {
+ res_chk_number =
+ nsfw_mem_mbuf_iterator (scn_cfg->data, start, end,
+ nsfw_res_sp_item_chk, (void *) res_scn_item);
+ }
+
+ if (0 == res_chk_number)
+ {
+ res_scn_item->last_scn_idx = 0;
+ start = res_scn_item->last_scn_idx;
+ end = start + scn_cfg->num_per_cyc;
+ if (NSFW_RES_SCAN_SPOOL == scn_cfg->type)
+ {
+ res_chk_number =
+ nsfw_mem_sp_iterator (scn_cfg->data, start, end,
+ nsfw_res_sp_item_chk,
+ (void *) res_scn_item);
+ }
+ else
+ {
+ res_chk_number =
+ nsfw_mem_mbuf_iterator (scn_cfg->data, start, end,
+ nsfw_res_sp_item_chk,
+ (void *) res_scn_item);
+ }
+ }
+
+ if (res_chk_number + start < end)
+ {
+ res_scn_item->last_scn_idx = 0;
+ }
+ else
+ {
+ res_scn_item->last_scn_idx += res_chk_number;
+ }
+
+ return;
+}
+
+void
+nsfw_res_scan_array (nsfw_res_mgr_item_cfg * res_scn_item)
+{
+ if (NULL == res_scn_item)
+ {
+ return;
+ }
+
+ nsfw_res_scn_cfg *scn_cfg = &res_scn_item->scn_cfg;
+ if (NULL == scn_cfg->data)
+ {
+ return;
+ }
+
+ u32 i;
+ char *elm =
+ (char *) scn_cfg->data + (res_scn_item->last_scn_idx * scn_cfg->elm_size);
+ for (i = res_scn_item->last_scn_idx; i < scn_cfg->total_num; i++)
+ {
+ if (i >= res_scn_item->last_scn_idx + scn_cfg->num_per_cyc)
+ {
+ break;
+ }
+
+ if (TRUE == nsfw_res_sp_item_chk (elm, (void *) res_scn_item))
+ {
+ NSFW_LOGINF ("force free item]data=%p,cfg=%p", elm, res_scn_item);
+ }
+
+ elm += scn_cfg->elm_size;
+ }
+
+ if (i >= scn_cfg->total_num)
+ {
+ res_scn_item->last_scn_idx = 0;
+ }
+ else
+ {
+ res_scn_item->last_scn_idx = i;
+ }
+
+ return;
+}
+
+void
+nsfw_res_scan_proc (nsfw_res_mgr_item_cfg * res_scn_item)
+{
+ (void) nsfw_res_flash_data (res_scn_item);
+ switch (res_scn_item->scn_cfg.type)
+ {
+ case NSFW_RES_SCAN_ARRAY:
+ nsfw_res_scan_array (res_scn_item);
+ break;
+ case NSFW_RES_SCAN_SPOOL:
+ case NSFW_RES_SCAN_MBUF:
+ nsfw_res_scan_mem (res_scn_item);
+ break;
+ default:
+ break;
+ }
+}
+
+int
+nsfw_res_scan_all (u32 timer_type, void *data)
+{
+ NSFW_LOGDBG ("scan start!");
+ struct timespec time_left = { NSFW_RES_SCAN_TVLAUE, 0 };
+ g_scan_cfg.scan_timer =
+ nsfw_timer_reg_timer (0, NULL, nsfw_res_scan_all, time_left);
+
+ if (g_hbt_switch)
+ {
+ return TRUE;
+ }
+
+ int i;
+ for (i = 0; i < NSFW_MAX_RES_SCAN_COUNT; i++)
+ {
+ /*last fun */
+ if (NULL == g_all_res_can[i].scn_cfg.data)
+ {
+ break;
+ }
+
+ nsfw_res_scan_proc (&g_all_res_can[i]);
+ }
+
+ return TRUE;
+}
+
+static int nsfw_resmgr_module_init (void *param);
+static int
+nsfw_resmgr_module_init (void *param)
+{
+ u8 proc_type = (u8) ((long long) param);
+ NSFW_LOGINF ("res mgr module init]type=%u", proc_type);
+ g_scan_cfg.scan_tvalue = NSFW_RES_SCAN_TVLAUE_DEF;
+ switch (proc_type)
+ {
+ case NSFW_PROC_MAIN:
+ {
+ struct timespec time_left = { NSFW_RES_SCAN_TVLAUE, 0 };
+ g_scan_cfg.scan_timer =
+ nsfw_timer_reg_timer (0, NULL, nsfw_res_scan_all, time_left);
+ return 0;
+ }
+ default:
+ if (proc_type < NSFW_PROC_MAX)
+ {
+ break;
+ }
+ return -1;
+ }
+
+ return 0;
+}
+
+/* *INDENT-OFF* */
+NSFW_MODULE_NAME(NSFW_RES_MGR_MODULE)
+NSFW_MODULE_PRIORITY(99)
+NSFW_MODULE_INIT(nsfw_resmgr_module_init)
+/* *INDENT-ON* */
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/common/mem_mgr/nsfw_shmem/nsfw_rshmem_mng.c b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_rshmem_mng.c
new file mode 100644
index 0000000..dc3400d
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_rshmem_mng.c
@@ -0,0 +1,987 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdint.h>
+#include "nstack_securec.h"
+#include "nstack_log.h"
+#include "nsfw_ring_fun.h"
+#include "nsfw_shmem_ring.h"
+#include "nsfw_shmem_mng.h"
+#include "common_mem_buf.h"
+#include "common_mem_common.h"
+
+#include "common_func.h"
+
+/*get the base address of msg data */
+#define NSFW_SHMEM_GET_DATA(pmsg, type) (type *)&((pmsg)->aidata[0])
+
+/*if input point is nun, just return null*/
+#define NSFW_POINT_CHK_RET_NULL(p, desc) \
+ if (NULL == (p)) \
+ { \
+ NSCOMM_LOGERR("point check fail] desc_para=%s", desc); \
+ return NULL; \
+ }
+
+/*if input point is nun, just return err num*/
+#define NSFW_POINT_CHK_RET_ERR(p, desc) \
+ if (NULL == (p)) \
+ { \
+ NSCOMM_LOGDBG("point check fail] desc_para=%s", desc); \
+ return NSFW_MEM_ERR; \
+ }
+
+/*if input point is nun, goto flag*/
+#define NSFW_POINT_CHK_RET_GOTO(p, gotoflag, desc) \
+ if (NULL == (p)) \
+ { \
+ NSCOMM_LOGERR("point check fail] desc_para=%s", desc); \
+ goto gotoflag; \
+ }
+
+/*init the msg head*/
+#define NSFW_SHMEM_MSG_HEAD_INIT(pmsg, type, lenth) { \
+ (pmsg)->usmsg_type = (type); \
+ (pmsg)->uslenth = (lenth); \
+ }
+
+/*rsp msg head check, and if err goto*/
+#define NSFW_SHMEM_MSGHEAD_CHK_GOTO(pmsg, type, lenth, gotoflag) { \
+ if (((type) != pmsg->usmsg_type) && ((lenth) != pmsg->uslenth)) \
+ { \
+ NSCOMM_LOGERR("check fail] msgtype=%d, type_para=%d, len=%d", (pmsg->usmsg_type), (type), (lenth)); \
+ goto gotoflag; \
+ } \
+ }
+
+/*rsp check the state*/
+#define NSFW_SHMEM_ACKSTATE_CHK_GOTO(expret, ret, expseg, seg, gotoflag) { \
+ if (((ret) != (expret)) || ((expseg) != (seg))) \
+ { \
+ NSCOMM_LOGERR("ackstate check fail]msgack exp=%d, real=%d,eseg=%d, rseg=%d", (expret), (ret), (expseg), (seg)); \
+ goto gotoflag; \
+ } \
+ }
+
+/*mzone msg init*/
+#define NSFW_SHMEM_MZONE_DATA_INIT(pdata, slenth, seg, socketid) { \
+ (pdata)->isocket_id = (socketid); \
+ (pdata)->lenth = (slenth); \
+ (pdata)->usseq = (seg); \
+ (pdata)->ireserv = 0; \
+ }
+
+/*mbuf msg init*/
+#define NSFW_SHMEM_MBUF_DATA_INIT(pdata, seg, num, cashsize, priv_size, data_room, flag, socketid) { \
+ (pdata)->usseq = (seg); \
+ (pdata)->usnum = (num); \
+ (pdata)->uscash_size = (cashsize); \
+ (pdata)->uspriv_size = (priv_size); \
+ (pdata)->usdata_room = (data_room); \
+ (pdata)->enmptype = (flag); \
+ (pdata)->isocket_id = (socketid); \
+ (pdata)->ireserv = 0; \
+ }
+
+/*mpool msg init*/
+#define NSFW_SHMEM_MPOOL_DATA_INIT(pdata, seg, num, eltsize, flag, socketid) { \
+ (pdata)->usseq = (seg); \
+ (pdata)->usnum = (num); \
+ (pdata)->useltsize = (eltsize); \
+ (pdata)->enmptype = (flag); \
+ (pdata)->isocket_id = (socketid); \
+ (pdata)->ireserv = 0; \
+ }
+
+/*mring msg init*/
+#define NSFW_SHMEM_MRING_DATA_INIT(pdata, seg, num, flag, socketid) { \
+ (pdata)->usseq = (seg); \
+ (pdata)->usnum = (num); \
+ (pdata)->enmptype = (flag); \
+ (pdata)->isocket_id = (socketid); \
+ (pdata)->ireserv = 0; \
+ }
+
+#define NSFW_SHMEM_MSG_FREE(pmsg, prsp_msg) {\
+ if (pmsg) \
+ { \
+ nsfw_mgr_msg_free(pmsg); \
+ } \
+ if (prsp_msg) \
+ { \
+ nsfw_mgr_msg_free(prsp_msg); \
+ } \
+}
+
+/*
+ * create a block memory by send a msg
+ *
+ */
+mzone_handle
+nsfw_memzone_remote_reserv (const i8 * name, size_t mlen, i32 socket_id)
+{
+ /*msg point define */
+ nsfw_mgr_msg *pmsg = NULL;
+ nsfw_mgr_msg *prsp_msg = NULL;
+
+ /*msg head point define */
+ nsfw_shmem_msg_head *pdata_head = NULL;
+
+ /*msg data point define */
+ nsfw_shmem_reserv_req *pdata = NULL;
+ nsfw_shmem_msg_head *pack_head = NULL;
+
+ /*ack msg define */
+ nsfw_shmem_ack *pack_data = NULL;
+
+ mzone_handle hhandle = NULL;
+ u8 ucret = TRUE;
+ i32 iretval = NSFW_MEM_OK;
+
+ //pmsg = nsfw_mgr_msg_alloc(MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MASTER);
+ pmsg = nsfw_mgr_msg_alloc (MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MAIN);
+ NSFW_POINT_CHK_RET_NULL (pmsg, "remote reserv pmsg alloc");
+
+ prsp_msg = nsfw_mgr_null_rspmsg_alloc ();
+ NSFW_POINT_CHK_RET_GOTO (prsp_msg, release, "remote reserv rspmsg alloc");
+
+ /*msg head init */
+ pdata_head = GET_USER_MSG (nsfw_shmem_msg_head, pmsg);
+ NSFW_SHMEM_MSG_HEAD_INIT (pdata_head, NSFW_RESERV_REQ_MSG,
+ sizeof (nsfw_shmem_reserv_req));
+
+ /*msg data init */
+ pdata = NSFW_SHMEM_GET_DATA (pdata_head, nsfw_shmem_reserv_req);
+ iretval = STRCPY_S (pdata->aname, sizeof (pdata->aname), name);
+ if (EOK != iretval)
+ {
+ NSCOMM_LOGERR ("reserv mem copy name fail] ret=%d", iretval);
+ goto release;
+ }
+
+ /*fill msg data */
+ NSFW_SHMEM_MZONE_DATA_INIT (pdata, mlen, (u16) 0, socket_id);
+
+ ucret = nsfw_mgr_send_req_wait_rsp (pmsg, prsp_msg);
+
+ if (FALSE == ucret)
+ {
+ NSCOMM_LOGERR ("reserv mem req rsp fail] ret=%u", ucret);
+ goto release;
+ }
+
+ /*interrupt msg head */
+ pack_head = GET_USER_MSG (nsfw_shmem_msg_head, prsp_msg);
+ NSFW_SHMEM_MSGHEAD_CHK_GOTO (pack_head, NSFW_RESERV_ACK_MSG,
+ sizeof (nsfw_shmem_ack), release);
+
+ pack_data = NSFW_SHMEM_GET_DATA (pack_head, nsfw_shmem_ack);
+ NSFW_SHMEM_ACKSTATE_CHK_GOTO (NSFW_MEM_ALLOC_SUCC, pack_data->cstate, 0,
+ pack_data->usseq, release);
+
+ hhandle = (mzone_handle) ADDR_SHTOL (pack_data->pbase_addr);
+ NSCOMM_LOGDBG ("mem reserve] name=%s, handle=%p, seg=%u", name, hhandle,
+ pack_data->usseq);
+release:
+ NSFW_SHMEM_MSG_FREE (pmsg, prsp_msg);
+ return hhandle;
+}
+
+/*
+ *create some memorys by send a msg
+ */
+i32
+nsfw_memzone_remote_reserv_v (nsfw_mem_zone * pmeminfo,
+ mzone_handle * paddr_array, i32 inum, pid_t pid)
+{
+ /*msg point define */
+ nsfw_mgr_msg *pmsg = NULL;
+ nsfw_mgr_msg *prsp_msg = NULL;
+ nsfw_shmem_msg_head *pdata_head = NULL;
+ nsfw_shmem_reserv_req *pdata = NULL;
+ nsfw_shmem_reserv_req *ptempdata = NULL;
+ nsfw_shmem_msg_head *pack_head = NULL;
+
+ nsfw_shmem_ack *pack_data = NULL;
+ u8 ucret = TRUE;
+ i32 iretval = NSFW_MEM_OK;
+ i32 icount = 0;
+ i32 itindex = 0;
+ i32 iindex = 0;
+ u16 ussegbase = 0;
+ u16 ustempv = 0;
+ i32 ieltnum = 0;
+ i32 ieltnum_max =
+ (NSFW_MGR_MSG_BODY_LEN -
+ sizeof (nsfw_shmem_msg_head)) / sizeof (nsfw_shmem_reserv_req);
+
+ //pmsg = nsfw_mgr_msg_alloc(MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MASTER);
+ pmsg = nsfw_mgr_msg_alloc (MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MAIN);
+ NSFW_POINT_CHK_RET_GOTO (pmsg, err, "remote reserv_v msg alloc");
+
+ prsp_msg = nsfw_mgr_null_rspmsg_alloc ();
+ NSFW_POINT_CHK_RET_GOTO (prsp_msg, err, "remote reserv_v rspmsg alloc");
+
+ pdata_head = GET_USER_MSG (nsfw_shmem_msg_head, pmsg);
+
+ ptempdata = pdata = NSFW_SHMEM_GET_DATA (pdata_head, nsfw_shmem_reserv_req);
+
+ do
+ {
+ icount++;
+ ieltnum++;
+
+ if (((icount % ieltnum_max) == 0) || (icount >= inum))
+ {
+ NSFW_SHMEM_MSG_HEAD_INIT (pdata_head, NSFW_RESERV_REQ_MSG,
+ ieltnum * sizeof (nsfw_shmem_reserv_req));
+
+ itindex = icount - 1;
+ int retVal =
+ SPRINTF_S (ptempdata->aname, sizeof (ptempdata->aname), "%s_%x",
+ pmeminfo[itindex].stname.aname, pid);
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]ret=%d", retVal);
+ }
+ NSFW_SHMEM_MZONE_DATA_INIT (ptempdata, pmeminfo[itindex].lenth,
+ (u16) itindex,
+ pmeminfo[itindex].isocket_id);
+
+ ucret = nsfw_mgr_send_req_wait_rsp (pmsg, prsp_msg);
+
+ if (FALSE == ucret)
+ {
+ NSCOMM_LOGERR ("reserv v mem req rsp fail] ret=%u", ucret);
+ goto err;
+ }
+
+ pack_head = GET_USER_MSG (nsfw_shmem_msg_head, prsp_msg);
+ NSFW_SHMEM_MSGHEAD_CHK_GOTO (pack_head, NSFW_RESERV_ACK_MSG,
+ ieltnum * sizeof (nsfw_shmem_ack),
+ err);
+
+ pack_data = NSFW_SHMEM_GET_DATA (pack_head, nsfw_shmem_ack);
+
+ for (iindex = 0; iindex < ieltnum; iindex++)
+ {
+ ustempv = ussegbase + iindex;
+
+ NSFW_SHMEM_ACKSTATE_CHK_GOTO (NSFW_MEM_ALLOC_SUCC,
+ pack_data->cstate, ustempv,
+ (u16) pack_data->usseq, err);
+
+ paddr_array[ustempv] = ADDR_SHTOL (pack_data->pbase_addr);
+ NSCOMM_LOGDBG ("remote reserve]index=%u, seg=%u, handle=%p",
+ ustempv, pack_data->usseq, paddr_array[ustempv]);
+ pack_data++;
+ }
+
+ ussegbase = icount;
+ ieltnum = 0;
+ ptempdata = pdata;
+ }
+ else
+ {
+ itindex = icount - 1;
+ int retVal =
+ SPRINTF_S (ptempdata->aname, sizeof (ptempdata->aname), "%s_%x",
+ pmeminfo[itindex].stname.aname, pid);
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]ret=%d", retVal);
+ }
+ NSFW_SHMEM_MZONE_DATA_INIT (ptempdata, pmeminfo[itindex].lenth,
+ (u16) itindex,
+ pmeminfo[itindex].isocket_id);
+ ptempdata++;
+ }
+ }
+ while (icount < inum);
+
+ iretval = NSFW_MEM_OK;
+ goto free;
+
+err:
+ iretval = NSFW_MEM_ERR;
+free:
+ NSFW_SHMEM_MSG_FREE (pmsg, prsp_msg);
+ return iretval;
+}
+
+/*
+ *release a block memory with name by send msg
+ */
+i32
+nsfw_remote_free (const i8 * name, nsfw_mem_struct_type entype)
+{
+ /*msg point define */
+ nsfw_mgr_msg *pmsg = NULL;
+ nsfw_mgr_msg *prsp_msg = NULL;
+
+ nsfw_shmem_msg_head *pdata_head = NULL;
+
+ nsfw_shmem_free_req *pdata = NULL;
+
+ nsfw_shmem_msg_head *pack_head = NULL;
+ nsfw_shmem_ack *pack_data = NULL;
+ u8 ucret = TRUE;
+ i32 iretval = NSFW_MEM_OK;
+
+ pmsg = nsfw_mgr_msg_alloc (MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MAIN);
+ NSFW_POINT_CHK_RET_ERR (pmsg, "remote free msg alloc");
+
+ prsp_msg = nsfw_mgr_null_rspmsg_alloc ();
+ NSFW_POINT_CHK_RET_GOTO (prsp_msg, terr, "remote free rspmsg alloc");
+
+ pdata_head = GET_USER_MSG (nsfw_shmem_msg_head, pmsg);
+ NSFW_SHMEM_MSG_HEAD_INIT (pdata_head, NSFW_RELEASE_REQ_MSG,
+ sizeof (nsfw_shmem_free_req));
+
+ pdata = NSFW_SHMEM_GET_DATA (pdata_head, nsfw_shmem_free_req);
+ if (EOK != STRCPY_S (pdata->aname, sizeof (pdata->aname), name))
+ {
+ NSCOMM_LOGERR ("STRCPY_S failed]name=%s", name);
+ }
+ pdata->usseq = 0;
+ pdata->ustype = entype;
+ pdata->ireserv = 0;
+
+ ucret = nsfw_mgr_send_req_wait_rsp (pmsg, prsp_msg);
+
+ if (FALSE == ucret)
+ {
+ NSCOMM_LOGERR ("free mem req rsp fail] ret=%u", ucret);
+ goto release;
+ }
+
+ pack_head = GET_USER_MSG (nsfw_shmem_msg_head, prsp_msg);
+ NSFW_SHMEM_MSGHEAD_CHK_GOTO (pack_head, NSFW_RELEASE_ACK_MSG,
+ sizeof (nsfw_shmem_ack), terr);
+
+ pack_data = NSFW_SHMEM_GET_DATA (pack_head, nsfw_shmem_ack);
+ NSFW_SHMEM_ACKSTATE_CHK_GOTO (NSFW_MEM_ALLOC_SUCC, pack_data->cstate, 0,
+ pack_data->usseq, terr);
+
+ iretval = NSFW_MEM_OK;
+ goto release;
+terr:
+ iretval = NSFW_MEM_ERR;
+release:
+ NSFW_SHMEM_MSG_FREE (pmsg, prsp_msg);
+ return iretval;
+}
+
+/*
+ *create a mbuf pool by send a msg
+ */
+mpool_handle
+nsfw_remote_shmem_mbf_create (const i8 * name, unsigned n,
+ unsigned cache_size, unsigned priv_size,
+ unsigned data_room_size, i32 socket_id,
+ nsfw_mpool_type entype)
+{
+ /*msg point define */
+ nsfw_mgr_msg *pmsg = NULL;
+ nsfw_mgr_msg *prsp_msg = NULL;
+ nsfw_shmem_msg_head *pdata_head = NULL;
+ nsfw_shmem_mbuf_req *pdata = NULL;
+ nsfw_shmem_msg_head *tpack_head = NULL;
+ nsfw_shmem_ack *tpack_data = NULL;
+ mpool_handle hhandle = NULL;
+ u8 ucret = TRUE;
+ i32 iretval = NSFW_MEM_OK;
+
+ pmsg = nsfw_mgr_msg_alloc (MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MAIN);
+ NSFW_POINT_CHK_RET_NULL (pmsg, "remote mbf create pmsg alloc");
+
+ prsp_msg = nsfw_mgr_null_rspmsg_alloc ();
+ NSFW_POINT_CHK_RET_GOTO (prsp_msg, release, "remote mbf create msg alloc");
+
+ pdata_head = GET_USER_MSG (nsfw_shmem_msg_head, pmsg);
+ NSFW_SHMEM_MSG_HEAD_INIT (pdata_head, NSFW_MBUF_REQ_MSG,
+ sizeof (nsfw_shmem_mbuf_req));
+
+ pdata = NSFW_SHMEM_GET_DATA (pdata_head, nsfw_shmem_mbuf_req);
+ iretval = STRCPY_S (pdata->aname, sizeof (pdata->aname), name);
+ if (EOK != iretval)
+ {
+ NSCOMM_LOGERR ("mbf create name cpy fail] ret=%d", iretval);
+ goto release;
+ }
+
+ NSFW_SHMEM_MBUF_DATA_INIT (pdata, 0, n, cache_size, priv_size,
+ data_room_size, (u16) entype, socket_id);
+
+ ucret = nsfw_mgr_send_req_wait_rsp (pmsg, prsp_msg);
+
+ if (FALSE == ucret)
+ {
+ NSCOMM_LOGERR ("mbf create mem req rsp fail] ret=%u", ucret);
+ goto release;
+ }
+
+ tpack_head = GET_USER_MSG (nsfw_shmem_msg_head, prsp_msg);
+ NSFW_SHMEM_MSGHEAD_CHK_GOTO (tpack_head, NSFW_MBUF_ACK_MSG,
+ sizeof (nsfw_shmem_ack), release);
+
+ tpack_data = NSFW_SHMEM_GET_DATA (tpack_head, nsfw_shmem_ack);
+ NSFW_SHMEM_ACKSTATE_CHK_GOTO (NSFW_MEM_ALLOC_SUCC, tpack_data->cstate, 0,
+ tpack_data->usseq, release);
+
+ hhandle = ADDR_SHTOL (tpack_data->pbase_addr);
+ NSCOMM_LOGDBG ("mbf create] name=%s, handle=%p, seg=%u", name, hhandle,
+ tpack_data->usseq);
+release:
+ NSFW_SHMEM_MSG_FREE (pmsg, prsp_msg);
+ return hhandle;
+}
+
+/*
+ *create some mbuf pools
+ */
+i32
+nsfw_remote_shmem_mbf_createv (nsfw_mem_mbfpool * pmbfname,
+ mpool_handle * phandle_array, i32 inum,
+ pid_t pid)
+{
+ /*msg point define */
+ nsfw_mgr_msg *mbpmsg = NULL;
+ nsfw_mgr_msg *prsp_msg = NULL;
+ nsfw_shmem_msg_head *pdata_head = NULL;
+
+ nsfw_shmem_mbuf_req *pdata = NULL;
+ nsfw_shmem_mbuf_req *ptempdata = NULL;
+
+ nsfw_shmem_msg_head *pack_head = NULL;
+
+ nsfw_shmem_ack *pack_data = NULL;
+ mpool_handle hhandle = NULL;
+ u8 ucret = TRUE;
+ i32 iretval = NSFW_MEM_OK;
+ i32 icount = 0;
+ i32 itindex = 0;
+ i32 iindex = 0;
+ i32 isegbase = 0;
+ i32 ieltnum = 0;
+ i32 ieltnum_max =
+ (NSFW_MGR_MSG_BODY_LEN -
+ sizeof (nsfw_shmem_msg_head)) / sizeof (nsfw_shmem_mbuf_req);
+
+ mbpmsg = nsfw_mgr_msg_alloc (MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MAIN);
+ NSFW_POINT_CHK_RET_GOTO (mbpmsg, lerr, "remote mbf createv msg alloc");
+
+ prsp_msg = nsfw_mgr_null_rspmsg_alloc ();
+ NSFW_POINT_CHK_RET_GOTO (prsp_msg, lerr, "remote mbf createv rspmsg alloc");
+
+ pdata_head = GET_USER_MSG (nsfw_shmem_msg_head, mbpmsg);
+
+ ptempdata = pdata = NSFW_SHMEM_GET_DATA (pdata_head, nsfw_shmem_mbuf_req);
+
+ do
+ {
+ icount++;
+ ieltnum++;
+
+ if (((icount % ieltnum_max) == 0) || (icount >= inum))
+ {
+ NSFW_SHMEM_MSG_HEAD_INIT (pdata_head, NSFW_MBUF_REQ_MSG,
+ ieltnum * sizeof (nsfw_shmem_mbuf_req));
+
+ /*fill msg data */
+ itindex = icount - 1;
+ if (-1 ==
+ SPRINTF_S (ptempdata->aname, sizeof (ptempdata->aname), "%s_%x",
+ pmbfname[itindex].stname.aname, pid))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]");
+ goto lerr;
+ }
+ NSFW_SHMEM_MBUF_DATA_INIT (ptempdata, (u16) itindex,
+ pmbfname[itindex].usnum,
+ pmbfname[itindex].uscash_size,
+ pmbfname[itindex].uspriv_size,
+ pmbfname[itindex].usdata_room,
+ pmbfname[itindex].enmptype,
+ pmbfname[itindex].isocket_id);
+
+ ucret = nsfw_mgr_send_req_wait_rsp (mbpmsg, prsp_msg);
+
+ if (FALSE == ucret)
+ {
+ NSCOMM_LOGERR ("mbf createv mem req rsp fail] ret=%d", ucret);
+ goto lerr;
+ }
+
+ /*interrup msg head */
+ pack_head = GET_USER_MSG (nsfw_shmem_msg_head, prsp_msg);
+ NSFW_SHMEM_MSGHEAD_CHK_GOTO (pack_head, NSFW_MBUF_ACK_MSG,
+ ieltnum * sizeof (nsfw_shmem_ack),
+ lerr);
+
+ pack_data = NSFW_SHMEM_GET_DATA (pack_head, nsfw_shmem_ack);
+
+ for (iindex = 0; iindex < ieltnum; iindex++)
+ {
+ NSFW_SHMEM_ACKSTATE_CHK_GOTO (NSFW_MEM_ALLOC_SUCC,
+ pack_data->cstate,
+ (isegbase + iindex),
+ (u16) pack_data->usseq, lerr);
+ phandle_array[isegbase + iindex] =
+ ADDR_SHTOL (pack_data->pbase_addr);
+ NSCOMM_LOGDBG ("mbf createv] seg=%d, handle=%p",
+ pack_data->usseq, hhandle);
+ pack_data++;
+ }
+
+ isegbase = icount;
+ ieltnum = 0;
+ ptempdata = pdata;
+ }
+ else
+ {
+ itindex = icount - 1;
+ if (-1 ==
+ SPRINTF_S (ptempdata->aname, sizeof (ptempdata->aname), "%s_%x",
+ pmbfname[itindex].stname.aname, pid))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]");
+ goto lerr;
+ }
+ NSFW_SHMEM_MBUF_DATA_INIT (ptempdata, (u16) itindex,
+ pmbfname[itindex].usnum,
+ pmbfname[itindex].uscash_size,
+ pmbfname[itindex].uspriv_size,
+ pmbfname[itindex].usdata_room,
+ pmbfname[itindex].enmptype,
+ pmbfname[itindex].isocket_id);
+ ptempdata++;
+ }
+ }
+ while (icount < inum);
+
+ /*release memory */
+ iretval = NSFW_MEM_OK;
+ goto release;
+
+lerr:
+ iretval = NSFW_MEM_ERR;
+release:
+ NSFW_SHMEM_MSG_FREE (mbpmsg, prsp_msg);
+ return iretval;
+}
+
+/*
+ *create a simpile pool
+ */
+mring_handle
+nsfw_remote_shmem_mpcreate (const char *name, unsigned int n,
+ unsigned int elt_size, i32 socket_id,
+ nsfw_mpool_type entype)
+{
+ /*msg point define */
+ nsfw_mgr_msg *pmsg = NULL;
+ nsfw_mgr_msg *prsp_msg = NULL;
+ nsfw_shmem_msg_head *pdata_head = NULL;
+ nsfw_shmem_sppool_req *pdata = NULL;
+ nsfw_shmem_msg_head *mppack_head = NULL;
+ nsfw_shmem_ack *mppack_data = NULL;
+ mring_handle hhandle = NULL;
+ u8 ucret = TRUE;
+ i32 iretval = NSFW_MEM_OK;
+
+ pmsg = nsfw_mgr_msg_alloc (MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MAIN);
+ NSFW_POINT_CHK_RET_NULL (pmsg, "remote mbf mpcreate pmsg alloc");
+
+ prsp_msg = nsfw_mgr_null_rspmsg_alloc ();
+ NSFW_POINT_CHK_RET_GOTO (prsp_msg, release, "remote mpcreate rspmsg alloc");
+
+ /*init msg head */
+ pdata_head = GET_USER_MSG (nsfw_shmem_msg_head, pmsg);
+ NSFW_SHMEM_MSG_HEAD_INIT (pdata_head, NSFW_SPPOOL_REQ_MSG,
+ sizeof (nsfw_shmem_sppool_req));
+
+ /*fill msg data */
+ pdata = NSFW_SHMEM_GET_DATA (pdata_head, nsfw_shmem_sppool_req);
+ iretval = STRCPY_S (pdata->aname, sizeof (pdata->aname), name);
+ if (EOK != iretval)
+ {
+ NSCOMM_LOGERR ("mp create copy name fail] ret=%d", iretval);
+ goto release;
+ }
+
+ /*fill msg data */
+ NSFW_SHMEM_MPOOL_DATA_INIT (pdata, 0, n, elt_size, entype, socket_id);
+
+ ucret = nsfw_mgr_send_req_wait_rsp (pmsg, prsp_msg);
+
+ if (FALSE == ucret)
+ {
+ NSCOMM_LOGERR ("mp create rsp fail] ret=%d", ucret);
+ goto release;
+ }
+
+ /*get msg head */
+ mppack_head = GET_USER_MSG (nsfw_shmem_msg_head, prsp_msg);
+ NSFW_SHMEM_MSGHEAD_CHK_GOTO (mppack_head, NSFW_SPPOOL_ACK_MSG,
+ sizeof (nsfw_shmem_ack), release);
+
+ mppack_data = NSFW_SHMEM_GET_DATA (mppack_head, nsfw_shmem_ack);
+ NSFW_SHMEM_ACKSTATE_CHK_GOTO (NSFW_MEM_ALLOC_SUCC, mppack_data->cstate, 0,
+ mppack_data->usseq, release);
+
+ hhandle = ADDR_SHTOL (mppack_data->pbase_addr);
+ NSCOMM_LOGDBG ("mpcreate] name=%s, handle=%p, seg=%d", name, hhandle,
+ mppack_data->usseq);
+release:
+ NSFW_SHMEM_MSG_FREE (pmsg, prsp_msg);
+ return hhandle;
+}
+
+/*
+ *create some simpile pools by send a msg
+ */
+i32
+nsfw_remote_shmem_mpcreatev (nsfw_mem_sppool * pmpinfo,
+ mring_handle * pringhandle_array, i32 inum,
+ pid_t pid)
+{
+ /*msg point define */
+ nsfw_mgr_msg *pmsg = NULL;
+ nsfw_mgr_msg *prsp_msg = NULL;
+
+ /*msg head define */
+ nsfw_shmem_msg_head *pdata_head = NULL;
+
+ /*msg data define */
+ nsfw_shmem_sppool_req *pdata = NULL;
+ nsfw_shmem_sppool_req *ptempdata = NULL;
+
+ /*ack msg define */
+ nsfw_shmem_msg_head *pack_head = NULL;
+
+ nsfw_shmem_ack *pack_data = NULL;
+ mring_handle hhandle = NULL;
+ u8 ucret = TRUE;
+ i32 iretval = NSFW_MEM_OK;
+ i32 icount = 0;
+ i32 itindex = 0;
+ i32 iindex = 0;
+ i32 isegbase = 0;
+ i32 ieltnum = 0;
+ /*the max members that a msg can take */
+ i32 ieltnum_max =
+ (NSFW_MGR_MSG_BODY_LEN -
+ sizeof (nsfw_shmem_msg_head)) / sizeof (nsfw_shmem_sppool_req);
+
+ /*alloc a msg */
+ //pmsg = nsfw_mgr_msg_alloc(MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MASTER);
+ pmsg = nsfw_mgr_msg_alloc (MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MAIN);
+ NSFW_POINT_CHK_RET_GOTO (pmsg, mperr, "remote mpcreatev pmsg alloc");
+
+ /*alloc rsp msg */
+ prsp_msg = nsfw_mgr_null_rspmsg_alloc ();
+ NSFW_POINT_CHK_RET_GOTO (prsp_msg, mperr, "remote mpcreatev rspmsg alloc");
+
+ pdata_head = GET_USER_MSG (nsfw_shmem_msg_head, pmsg);
+
+ ptempdata = pdata = NSFW_SHMEM_GET_DATA (pdata_head, nsfw_shmem_sppool_req);
+
+ do
+ {
+ icount++;
+ ieltnum++;
+
+ /*if the element num reach the bigest, or already send all, just deal */
+ if (((icount % ieltnum_max) == 0) || (icount >= inum))
+ {
+ /*init msg header */
+ NSFW_SHMEM_MSG_HEAD_INIT (pdata_head, NSFW_SPPOOL_REQ_MSG,
+ ieltnum * sizeof (nsfw_shmem_sppool_req));
+
+ /*fill the msg data */
+ itindex = icount - 1;
+
+ int retVal =
+ SPRINTF_S (ptempdata->aname, sizeof (ptempdata->aname), "%s_%x",
+ pmpinfo[itindex].stname.aname, pid);
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S fail]ret=%d", retVal);
+ goto mperr;
+ }
+ NSFW_SHMEM_MPOOL_DATA_INIT (ptempdata, itindex,
+ pmpinfo[itindex].usnum,
+ pmpinfo[itindex].useltsize,
+ pmpinfo[itindex].enmptype,
+ pmpinfo[itindex].isocket_id);
+
+ ucret = nsfw_mgr_send_req_wait_rsp (pmsg, prsp_msg);
+
+ if (FALSE == ucret)
+ {
+ NSCOMM_LOGERR ("mpcreatev create fail] ret=%u", ucret);
+ goto mperr;
+ }
+
+ /*interrup mgs head */
+ pack_head = GET_USER_MSG (nsfw_shmem_msg_head, prsp_msg);
+ NSFW_SHMEM_MSGHEAD_CHK_GOTO (pack_head, NSFW_SPPOOL_ACK_MSG,
+ ieltnum * sizeof (nsfw_shmem_ack),
+ mperr);
+
+ pack_data = NSFW_SHMEM_GET_DATA (pack_head, nsfw_shmem_ack);
+
+ for (iindex = 0; iindex < ieltnum; iindex++)
+ {
+ NSFW_SHMEM_ACKSTATE_CHK_GOTO (NSFW_MEM_ALLOC_SUCC,
+ pack_data->cstate,
+ (isegbase + iindex),
+ (u16) pack_data->usseq, mperr);
+ pringhandle_array[isegbase + iindex] =
+ ADDR_SHTOL (pack_data->pbase_addr);
+ NSCOMM_LOGDBG ("mpcreatev] seg=%u, handle=%p", pack_data->usseq,
+ hhandle);
+ pack_data++;
+ }
+
+ isegbase = icount;
+ ieltnum = 0;
+ ptempdata = pdata;
+ }
+ else
+ {
+ itindex = icount - 1;
+ int retVal =
+ SPRINTF_S (ptempdata->aname, sizeof (ptempdata->aname), "%s_%x",
+ pmpinfo[itindex].stname.aname, pid);
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S fail]ret=%d", retVal);
+ goto mperr;
+ }
+ NSFW_SHMEM_MPOOL_DATA_INIT (ptempdata, itindex,
+ pmpinfo[itindex].usnum,
+ pmpinfo[itindex].useltsize,
+ pmpinfo[itindex].enmptype,
+ pmpinfo[itindex].isocket_id);
+
+ ptempdata++;
+ }
+ }
+ while (icount < inum);
+
+ /*release the memory */
+ iretval = NSFW_MEM_OK;
+ goto release;
+
+mperr:
+ iretval = NSFW_MEM_ERR;
+release:
+ NSFW_SHMEM_MSG_FREE (pmsg, prsp_msg);
+ return iretval;
+}
+
+/*
+ *create a ring
+ */
+mring_handle
+nsfw_remote_shmem_ringcreate (const char *name, unsigned int n, i32 socket_id,
+ nsfw_mpool_type entype)
+{
+ /*msg point define */
+ nsfw_mgr_msg *pmsg = NULL;
+ nsfw_mgr_msg *prsp_msg = NULL;
+
+ /*msg head define */
+ nsfw_shmem_msg_head *pdata_head = NULL;
+
+ /*msg data define */
+ nsfw_shmem_ring_req *pdata = NULL;
+ /*ack msg define */
+ nsfw_shmem_msg_head *pack_head = NULL;
+ nsfw_shmem_ack *ppack_data = NULL;
+ mring_handle hhandle = NULL;
+ u8 ucret = TRUE;
+ i32 iretval = NSFW_MEM_OK;
+
+ //pmsg = nsfw_mgr_msg_alloc(MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MASTER);
+ pmsg = nsfw_mgr_msg_alloc (MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MAIN);
+ NSFW_POINT_CHK_RET_NULL (pmsg, "remote ringcreate pmsg alloc");
+
+ prsp_msg = nsfw_mgr_null_rspmsg_alloc ();
+ NSFW_POINT_CHK_RET_GOTO (prsp_msg, release,
+ "remote ringcreate rspmsg alloc");
+
+ /*fill msg head */
+ pdata_head = GET_USER_MSG (nsfw_shmem_msg_head, pmsg);
+ NSFW_SHMEM_MSG_HEAD_INIT (pdata_head, NSFW_RING_REQ_MSG,
+ sizeof (nsfw_shmem_ring_req));
+
+ /*fill msg data */
+ pdata = NSFW_SHMEM_GET_DATA (pdata_head, nsfw_shmem_ring_req);
+ iretval = STRCPY_S (pdata->aname, sizeof (pdata->aname), name);
+ if (EOK != iretval)
+ {
+ NSCOMM_LOGERR ("ring create cpy name fail] ret=%d", iretval);
+ goto release;
+ }
+
+ /*fill msg data */
+ NSFW_SHMEM_MRING_DATA_INIT (pdata, 0, n, entype, socket_id);
+
+ ucret = nsfw_mgr_send_req_wait_rsp (pmsg, prsp_msg);
+
+ if (FALSE == ucret)
+ {
+ NSCOMM_LOGERR ("ring create rsp fail] ret=%d", ucret);
+ goto release;
+ }
+
+ /*interrup mgs head */
+ pack_head = GET_USER_MSG (nsfw_shmem_msg_head, prsp_msg);
+ NSFW_SHMEM_MSGHEAD_CHK_GOTO (pack_head, NSFW_RING_ACK_MSG,
+ sizeof (nsfw_shmem_ack), release);
+
+ ppack_data = NSFW_SHMEM_GET_DATA (pack_head, nsfw_shmem_ack);
+ NSFW_SHMEM_ACKSTATE_CHK_GOTO (NSFW_MEM_ALLOC_SUCC, ppack_data->cstate, 0,
+ ppack_data->usseq, release);
+
+ hhandle = ADDR_SHTOL (ppack_data->pbase_addr);
+ NSCOMM_LOGDBG ("ring create] name=%s, handle=%p, seg=%u", name, hhandle,
+ ppack_data->usseq);
+release:
+ NSFW_SHMEM_MSG_FREE (pmsg, prsp_msg);
+ return hhandle;
+}
+
+/*
+ *create a mem pool that the members are rings by send a msg
+ *ieltnum:the num of ring member
+ *iringnum:the num of ring in simple mem pook
+ *entype:the defualt the of ring
+ */
+i32
+nsfw_remote_shmem_ringcreatev (const char *name, i32 ieltnum,
+ mring_handle * pringhandle_array, i32 iringnum,
+ i32 socket_id, nsfw_mpool_type entype)
+{
+ unsigned int useltsize = 0;
+ mring_handle nhandle = NULL;
+ i32 icount = 0;
+ i32 n = 0;
+ uint64_t baseaddr = 0;
+ uint64_t endaddr = 0;
+ /*the num of ring member must be power of 2 */
+ unsigned int usnum = common_mem_align32pow2 (ieltnum + 1);
+
+ useltsize =
+ sizeof (struct nsfw_mem_ring) + usnum * sizeof (union RingData_U);
+ nhandle =
+ nsfw_remote_shmem_mpcreate (name, iringnum, useltsize, socket_id,
+ NSFW_MRING_SPSC);
+ NSFW_POINT_CHK_RET_ERR (nhandle, "remote ringcreatev msg alloc");
+
+ n =
+ nsfw_shmem_ring_sc_dequeuev (nhandle, (void **) pringhandle_array,
+ iringnum);
+
+ if (n != iringnum)
+ {
+ NSCOMM_LOGERR ("ring dequeue fail] ringnum=%d, retnum=%d", iringnum, n);
+ return NSFW_MEM_ERR;
+ }
+
+ nsfw_shmem_ring_baseaddr_query (&baseaddr, &endaddr);
+
+ for (icount = 0; icount < iringnum; icount++)
+ {
+ nsfw_mem_ring_init (pringhandle_array[icount], usnum, (void *) baseaddr,
+ NSFW_SHMEM, entype);
+ }
+
+ return NSFW_MEM_OK;
+}
+
+/*
+ *look up a msg by send a msg
+ */
+void *
+nsfw_remote_shmem_lookup (const i8 * name, nsfw_mem_struct_type entype)
+{
+ /*msg point define */
+ nsfw_mgr_msg *pmsg = NULL;
+ nsfw_mgr_msg *prsp_msg = NULL;
+ void *addr = NULL;
+ /*msg head data define */
+ nsfw_shmem_msg_head *pdata_head = NULL;
+
+ /*msg data define */
+ nsfw_shmem_lookup_req *pdata = NULL;
+
+ /*ack msg define */
+ nsfw_shmem_msg_head *pack_head = NULL;
+ nsfw_shmem_ack *lpack_data = NULL;
+ u8 ucret = TRUE;
+
+ pmsg = nsfw_mgr_msg_alloc (MGR_MSG_MEM_ALLOC_REQ, NSFW_PROC_MAIN);
+ NSFW_POINT_CHK_RET_NULL (pmsg, "remote lookup pmsg alloc");
+
+ prsp_msg = nsfw_mgr_null_rspmsg_alloc ();
+ NSFW_POINT_CHK_RET_GOTO (prsp_msg, perr, "remote lookup rspmsg alloc");
+
+ /*msg head init */
+ pdata_head = GET_USER_MSG (nsfw_shmem_msg_head, pmsg);
+ NSFW_SHMEM_MSG_HEAD_INIT (pdata_head, NSFW_MEM_LOOKUP_REQ_MSG,
+ sizeof (nsfw_shmem_lookup_req));
+
+ pdata = NSFW_SHMEM_GET_DATA (pdata_head, nsfw_shmem_lookup_req);
+ if (EOK != STRCPY_S (pdata->aname, sizeof (pdata->aname), name))
+ {
+ NSCOMM_LOGERR ("STRCPY_S faild]name=%s", name);
+ }
+ pdata->usseq = 0;
+ pdata->ustype = entype;
+ pdata->ireserv = 0;
+
+ ucret = nsfw_mgr_send_req_wait_rsp (pmsg, prsp_msg);
+
+ if (FALSE == ucret)
+ {
+ NSCOMM_LOGERR ("mem lookup fail] ret=%u", ucret);
+ goto release;
+ }
+
+ /*interrup mgs head */
+ pack_head = GET_USER_MSG (nsfw_shmem_msg_head, prsp_msg);
+ NSFW_SHMEM_MSGHEAD_CHK_GOTO (pack_head, NSFW_MEM_LOOKUP_ACK_MSG,
+ sizeof (nsfw_shmem_ack), perr);
+
+ lpack_data = NSFW_SHMEM_GET_DATA (pack_head, nsfw_shmem_ack);
+ NSFW_SHMEM_ACKSTATE_CHK_GOTO (NSFW_MEM_ALLOC_SUCC, lpack_data->cstate, 0,
+ lpack_data->usseq, perr);
+
+ addr = ADDR_SHTOL (lpack_data->pbase_addr);
+ NSCOMM_LOGDBG ("shmem lookup] name=%s, handle=%p, seg=%u", name, addr,
+ lpack_data->usseq);
+ goto release;
+perr:
+ addr = NULL;
+
+release:
+ NSFW_SHMEM_MSG_FREE (pmsg, prsp_msg);
+ return addr;
+}
diff --git a/src/framework/common/mem_mgr/nsfw_shmem/nsfw_rshmem_mng.h b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_rshmem_mng.h
new file mode 100644
index 0000000..60c4115
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_rshmem_mng.h
@@ -0,0 +1,51 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_RSHMEM_MNG_H
+#define _NSFW_RSHMEM_MNG_H
+
+mzone_handle nsfw_memzone_remote_reserv (const i8 * name, size_t mlen,
+ i32 socket_id);
+i32 nsfw_memzone_remote_reserv_v (nsfw_mem_zone * pmeminfo,
+ mzone_handle * paddr_array, i32 inum,
+ pid_t pid);
+i32 nsfw_remote_free (const i8 * name, nsfw_mem_struct_type entype);
+mpool_handle nsfw_remote_shmem_mbf_create (const i8 * name, unsigned int n,
+ unsigned cache_size,
+ unsigned priv_size,
+ unsigned data_room_size,
+ i32 socket_id,
+ nsfw_mpool_type entype);
+i32 nsfw_remote_shmem_mbf_createv (nsfw_mem_mbfpool * pmbfname,
+ mpool_handle * phandle_array, i32 inum,
+ pid_t pid);
+mring_handle nsfw_remote_shmem_mpcreate (const char *name, unsigned int n,
+ unsigned int elt_size, i32 socket_id,
+ nsfw_mpool_type entype);
+i32 nsfw_remote_shmem_mpcreatev (nsfw_mem_sppool * pmpinfo,
+ mring_handle * pringhandle_array, i32 inum,
+ pid_t pid);
+mring_handle nsfw_remote_shmem_ringcreate (const char *name, unsigned int n,
+ i32 socket_id,
+ nsfw_mpool_type entype);
+i32 nsfw_remote_shmem_ringcreatev (const char *name, i32 ieltnum,
+ mring_handle * pringhandle_array,
+ i32 iringnum, i32 socket_id,
+ nsfw_mpool_type entype);
+
+void *nsfw_remote_shmem_lookup (const i8 * name, nsfw_mem_struct_type entype);
+
+#endif
diff --git a/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mdesc.c b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mdesc.c
new file mode 100644
index 0000000..e7a11ad
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mdesc.c
@@ -0,0 +1,47 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "nsfw_mem_desc.h"
+#include "nsfw_shmem_mng.h"
+#include "nsfw_shmem_mdesc.h"
+
+/*the inferaces accessing memory*/
+nsfw_mem_ops g_shmem_ops = {
+ nsfw_shmem_init,
+ nsfw_shmem_destroy,
+ nsfw_shmem_create,
+ nsfw_shmem_createv,
+ nsfw_shmem_lookup,
+ nsfw_shmem_release,
+ nsfw_shmem_mbfmpcreate,
+ nsfw_shmem_mbfmpcreatev,
+ nsfw_shmem_mbfalloc,
+ nsfw_shmem_mbffree,
+ nsfw_shmem_mbfmplookup,
+ nsfw_shmem_mbfmprelease,
+ nsfw_shmem_spcreate,
+ nsfw_shmem_spcreatev,
+ nswf_shmem_sp_ringcreate,
+ nsfw_shmem_sprelease,
+ nsfw_shmem_sp_lookup,
+ nsfw_shmem_ringcreate,
+ nsfw_shmem_ring_lookup,
+ nsfw_shmem_ringrelease,
+ nsfw_shmem_stactic,
+ nsfw_shmem_mbuf_recycle,
+ nsfw_shmem_sp_iterator,
+ nsfw_shmem_mbuf_iterator
+};
diff --git a/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mdesc.h b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mdesc.h
new file mode 100644
index 0000000..afd9e29
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mdesc.h
@@ -0,0 +1,22 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_SHMEM_MDESC_H_
+#define _NSFW_SHMEM_MDESC_H_
+
+extern nsfw_mem_ops g_shmem_ops;
+
+#endif
diff --git a/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mng.c b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mng.c
new file mode 100644
index 0000000..f85e70d
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mng.c
@@ -0,0 +1,880 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "nstack_securec.h"
+#include "nstack_log.h"
+#include "nsfw_mem_desc.h"
+#include "nsfw_ring_fun.h"
+#include "nsfw_shmem_ring.h"
+#include "nsfw_shmem_mng.h"
+#include "common_mem_mempool.h"
+#include "common_mem_memzone.h"
+#include "common_mem_buf.h"
+#include "common_mem_mbuf.h"
+#include "nsfw_rshmem_mng.h"
+#include "common_mem_api.h"
+#include "common_sys_config.h"
+#include "nsfw_maintain_api.h"
+#include "common_pal_bitwide_adjust.h"
+
+#include "common_mem_pal.h"
+
+#include "common_func.h"
+
+#define NSFW_SHMEM_PID (get_sys_pid())
+#define NSFW_SHMEM_FLAG (g_shmem_localdata->enflag)
+
+nsfw_mem_localdata *g_shmem_localdata = NULL;
+
+/*check g_mem_localdata*/
+#define NSFW_INIT_CHK_RET() \
+ if (!g_shmem_localdata) \
+ { \
+ return NSFW_MEM_ERR; \
+ }
+
+#define NSFW_INIT_CHK_RET_NULL() \
+ if (!g_shmem_localdata) \
+ { \
+ return NULL; \
+ }
+
+/*
+ *share memory mng module init
+ *
+ */
+i32
+nsfw_shmem_init (nsfw_mem_para * para)
+{
+ common_mem_pal_module_info rteinfo = { 0 };
+ i32 iret = NSFW_MEM_ERR;
+ int flag = 0;
+ if (!para)
+ {
+ return NSFW_MEM_ERR;
+ }
+
+ NSCOMM_LOGINF ("nsfw shmem init begin");
+
+ if (NSFW_PROC_MASTER == para->enflag)
+ {
+ iret = common_mem_pal_init (para->iargsnum, para->pargs);
+ }
+ else if (NSFW_PROC_MAIN == para->enflag)
+ {
+ iret = common_pal_module_init (NULL);
+ }
+ else
+ {
+ LCORE_MASK_SET (rteinfo.ilcoremask, 1);
+ rteinfo.ucproctype = DMM_PROC_T_SECONDARY;
+ iret = common_pal_module_init (&rteinfo);
+ }
+
+ if (NSFW_MEM_OK != iret)
+ {
+ NSCOMM_LOGERR ("rte init fail] ret=0x%x", iret);
+ return NSFW_MEM_ERR;
+ }
+
+ flag = dmm_pal_addr_align ();
+ if ((0 == flag) && (NSFW_PROC_MAIN == para->enflag))
+ {
+ dmm_addr_print ();
+ NSCOMM_LOGERR
+ ("rte init addr is not the same with primary] nstackmain flag=%d",
+ flag);
+ return NSFW_MEM_ERR;
+ }
+
+ g_shmem_localdata =
+ (nsfw_mem_localdata *) malloc (sizeof (nsfw_mem_localdata));
+
+ if (NULL == g_shmem_localdata)
+ {
+ NSCOMM_LOGERR ("g_shmem_localdata malloc fail");
+ return NSFW_MEM_ERR;
+ }
+
+ iret =
+ MEMSET_S (g_shmem_localdata, sizeof (nsfw_mem_localdata), 0,
+ sizeof (nsfw_mem_localdata));
+ if (EOK != iret)
+ {
+ NSCOMM_LOGERR ("memset fail] g_shmem_localdata=%p ", g_shmem_localdata);
+ free (g_shmem_localdata);
+ g_shmem_localdata = NULL;
+ return NSFW_MEM_ERR;
+ }
+
+ g_shmem_localdata->enflag = para->enflag;
+
+ NSCOMM_LOGINF ("nsfw shmem init end] enflag=%d", para->enflag);
+ return NSFW_MEM_OK;
+
+}
+
+/*
+ *module destroy
+ */
+void
+nsfw_shmem_destroy (void)
+{
+ if (g_shmem_localdata)
+ {
+ free (g_shmem_localdata);
+ g_shmem_localdata = NULL;
+ }
+
+ return;
+}
+
+/*
+ * create a shared memory
+ * nsfw_mem_zone::stname memory name
+ * nsfw_mem_zone::isize
+ */
+mzone_handle
+nsfw_shmem_create (nsfw_mem_zone * pinfo)
+{
+ i8 aname[COMMON_MEM_MEMPOOL_NAMESIZE] = { 0 };
+
+ NSFW_INIT_CHK_RET_NULL ()if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ return common_memzone_data_reserve_name (pinfo->stname.aname,
+ pinfo->lenth,
+ pinfo->isocket_id);
+ }
+ else
+ {
+ /*app must less than NSFW_MEM_APPNAME_LENTH */
+ NSFW_NAME_LENCHECK_RET_NULL (pinfo->stname.aname, "shmem create")
+ if (-1 ==
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s_%x",
+ pinfo->stname.aname, NSFW_SHMEM_PID))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]");
+ return NULL;
+ }
+ }
+
+ return nsfw_memzone_remote_reserv ((char *) &aname[0], pinfo->lenth,
+ SOCKET_ID_ANY);
+}
+
+/*
+ *create some memory
+ *inum must be equal iarray_num
+ */
+i32
+nsfw_shmem_createv (nsfw_mem_zone * pmeminfo, i32 inum,
+ mzone_handle * paddr_array, i32 iarray_num)
+{
+ NSFW_INIT_CHK_RET ();
+
+ if (NSFW_PROC_MASTER == NSFW_SHMEM_FLAG)
+ {
+ return NSFW_MEM_ERR;
+ }
+ else if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ return nsfw_memzone_remote_reserv_v (pmeminfo, paddr_array, iarray_num,
+ 0);
+ }
+ else
+ {
+ return nsfw_memzone_remote_reserv_v (pmeminfo, paddr_array, iarray_num,
+ NSFW_SHMEM_PID);
+ }
+ return NSFW_MEM_ERR;
+}
+
+mzone_handle
+nsfw_shmem_lookup (nsfw_mem_name * pname)
+{
+ i8 aname[COMMON_MEM_MEMPOOL_NAMESIZE] = { 0 };
+ NSFW_INIT_CHK_RET_NULL ();
+
+ if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ return common_memzone_data_lookup_name (pname->aname);
+ }
+
+ if ((NSFW_PROC_NULL == pname->enowner)
+ || (NSFW_PROC_MAIN == pname->enowner))
+ {
+ int retVal =
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s", pname->aname);
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild");
+ return NULL;
+ }
+ }
+ else
+ {
+ /*app must less than NSFW_MEM_APPNAME_LENTH */
+ NSFW_NAME_LENCHECK_RET_NULL (pname->aname, "shmem lookup")
+ int retVal =
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s_%x", pname->aname,
+ NSFW_SHMEM_PID);
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild");
+ return NULL;
+ }
+ }
+
+ return nsfw_remote_shmem_lookup (aname, NSFW_MEM_MZONE);
+}
+
+i32
+nsfw_shmem_release (nsfw_mem_name * pname)
+{
+ i8 aname[COMMON_MEM_MEMPOOL_NAMESIZE] = { 0 };
+ const struct common_mem_memzone *pmzone = NULL;
+ NSFW_INIT_CHK_RET ();
+
+ if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ pmzone = common_mem_memzone_lookup (pname->aname);
+
+ if (pmzone)
+ {
+ common_mem_memzone_free (pmzone);
+ }
+ return NSFW_MEM_OK;
+ }
+ else
+ {
+ NSFW_NAME_LENCHECK_RET (pname->aname, "shmem free")
+ if (-1 ==
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s_%x",
+ pname->aname, NSFW_SHMEM_PID))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild");
+ return NSFW_MEM_ERR;
+ }
+ }
+
+ return nsfw_remote_free (aname, NSFW_MEM_MZONE);
+}
+
+mpool_handle
+nsfw_shmem_mbfmpcreate (nsfw_mem_mbfpool * pbufinfo)
+{
+ i8 aname[COMMON_MEM_MEMPOOL_NAMESIZE] = { 0 };
+
+ NSFW_INIT_CHK_RET_NULL ();
+
+ if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ return common_mem_pktmbuf_pool_create (pbufinfo->stname.aname,
+ pbufinfo->usnum,
+ pbufinfo->uscash_size,
+ pbufinfo->uspriv_size,
+ pbufinfo->usdata_room,
+ pbufinfo->isocket_id);
+ }
+ else
+ {
+ /*app must less than NSFW_MEM_APPNAME_LENTH */
+ NSFW_NAME_LENCHECK_RET_NULL (pbufinfo->stname.aname, "mbufpool create")
+ if (-1 ==
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s_%x",
+ pbufinfo->stname.aname, NSFW_SHMEM_PID))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]");
+ }
+ }
+
+ return nsfw_remote_shmem_mbf_create (aname, pbufinfo->usnum,
+ pbufinfo->uscash_size,
+ pbufinfo->uspriv_size,
+ pbufinfo->usdata_room, SOCKET_ID_ANY,
+ pbufinfo->enmptype);
+}
+
+/*
+ *create some mbuf pools
+ */
+i32
+nsfw_shmem_mbfmpcreatev (nsfw_mem_mbfpool * pmbfname, i32 inum,
+ mpool_handle * phandle_array, i32 iarray_num)
+{
+ NSFW_INIT_CHK_RET ();
+
+ if (NSFW_PROC_MASTER == NSFW_SHMEM_FLAG)
+ {
+ return NSFW_MEM_ERR;
+ }
+ else if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ return nsfw_remote_shmem_mbf_createv (pmbfname, phandle_array,
+ iarray_num, 0);
+ }
+ else
+ {
+ return nsfw_remote_shmem_mbf_createv (pmbfname, phandle_array,
+ iarray_num, NSFW_SHMEM_PID);
+ }
+
+ return NSFW_MEM_ERR;
+}
+
+mbuf_handle
+nsfw_shmem_mbfalloc (mpool_handle mhandle)
+{
+ return (mbuf_handle) common_mem_pktmbuf_alloc ((struct common_mem_mempool *)
+ mhandle);
+}
+
+i32
+nsfw_shmem_mbffree (mbuf_handle mhandle)
+{
+ common_mem_pktmbuf_free ((struct common_mem_mbuf *) mhandle);
+ return NSFW_MEM_OK;
+}
+
+i32
+nsfw_shmem_mbfmprelease (nsfw_mem_name * pname)
+{
+ return NSFW_MEM_OK;
+}
+
+mpool_handle
+nsfw_shmem_mbfmplookup (nsfw_mem_name * pmbfname)
+{
+ i8 aname[COMMON_MEM_MEMPOOL_NAMESIZE] = { 0 };
+
+ NSFW_INIT_CHK_RET_NULL ();
+
+ if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ return common_mem_mempool_lookup (pmbfname->aname);
+ }
+
+ if ((NSFW_PROC_NULL == pmbfname->enowner)
+ || (NSFW_PROC_MAIN == pmbfname->enowner))
+ {
+ if (-1 ==
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s",
+ pmbfname->aname))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]");
+ }
+ }
+ else
+ {
+ /*app must less than NSFW_MEM_APPNAME_LENTH */
+ NSFW_NAME_LENCHECK_RET_NULL (pmbfname->aname, "shmem lookup")
+ if (-1 ==
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s_%x",
+ pmbfname->aname, NSFW_SHMEM_PID))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]");
+ }
+ }
+
+ return nsfw_remote_shmem_lookup (aname, NSFW_MEM_MBUF);
+}
+
+mring_handle
+nsfw_shmem_spcreate (nsfw_mem_sppool * pmpinfo)
+{
+ i8 aname[COMMON_MEM_MEMPOOL_NAMESIZE] = { 0 };
+
+ NSFW_INIT_CHK_RET_NULL ();
+
+ if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ return nsfw_shmem_pool_create (pmpinfo->stname.aname, pmpinfo->usnum,
+ pmpinfo->useltsize, pmpinfo->isocket_id,
+ pmpinfo->enmptype);
+ }
+ else
+ {
+ NSFW_NAME_LENCHECK_RET_NULL (pmpinfo->stname.aname, "mpool create")
+ if (-1 ==
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s_%x",
+ pmpinfo->stname.aname, NSFW_SHMEM_PID))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]");
+ }
+ }
+
+ return nsfw_remote_shmem_mpcreate (aname, pmpinfo->usnum,
+ pmpinfo->useltsize, SOCKET_ID_ANY,
+ pmpinfo->enmptype);
+}
+
+i32
+nsfw_shmem_spcreatev (nsfw_mem_sppool * pmpinfo, i32 inum,
+ mring_handle * pringhandle_array, i32 iarray_num)
+{
+ NSFW_INIT_CHK_RET ();
+
+ if (NSFW_PROC_MASTER == NSFW_SHMEM_FLAG)
+ {
+ return NSFW_MEM_ERR;
+ }
+ else if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ return nsfw_remote_shmem_mpcreatev (pmpinfo, pringhandle_array, inum,
+ 0);
+ }
+ else
+ {
+ return nsfw_remote_shmem_mpcreatev (pmpinfo, pringhandle_array, inum,
+ NSFW_SHMEM_PID);
+ }
+ return NSFW_MEM_ERR;
+}
+
+i32
+nsfw_lshmem_ringcreatev (const char *name, i32 ieltnum,
+ mring_handle * pringhandle_array, i32 iringnum,
+ i32 socket_id, nsfw_mpool_type entype)
+{
+ i32 useltsize = 0;
+ mring_handle nhandle = NULL;
+ i32 icount = 0;
+ i32 n = 0;
+ uint64_t baseaddr = 0;
+ uint64_t endaddr = 0;
+ i32 usnum = common_mem_align32pow2 (ieltnum + 1);
+
+ useltsize =
+ sizeof (struct nsfw_mem_ring) + usnum * sizeof (union RingData_U);
+ nhandle =
+ nsfw_shmem_pool_create (name, iringnum, useltsize, socket_id,
+ NSFW_MRING_SPSC);
+ if (NULL == (nhandle))
+ {
+ return NSFW_MEM_ERR;
+ }
+
+ n =
+ nsfw_shmem_ring_sc_dequeuev (nhandle, (void **) pringhandle_array,
+ iringnum);
+
+ if (n != iringnum)
+ {
+ NSCOMM_LOGERR
+ ("ring dequeuev failed] ring=%p, dequeue num=%d, expect num=%d",
+ nhandle, n, iringnum);
+ return NSFW_MEM_ERR;
+ }
+
+ nsfw_shmem_ring_baseaddr_query (&baseaddr, &endaddr);
+
+ for (icount = 0; icount < iringnum; icount++)
+ {
+ nsfw_mem_ring_init (pringhandle_array[icount], usnum, (void *) baseaddr,
+ NSFW_SHMEM, entype);
+ }
+
+ return NSFW_MEM_OK;
+}
+
+i32
+nswf_shmem_sp_ringcreate (nsfw_mem_mring * prpoolinfo,
+ mring_handle * pringhandle_array, i32 iringnum)
+{
+ i8 aname[COMMON_MEM_MEMPOOL_NAMESIZE] = { 0 };
+
+ NSFW_INIT_CHK_RET ();
+
+ if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ return nsfw_lshmem_ringcreatev (prpoolinfo->stname.aname,
+ prpoolinfo->usnum, pringhandle_array,
+ iringnum, SOCKET_ID_ANY,
+ prpoolinfo->enmptype);
+ }
+ else
+ {
+ NSFW_NAME_LENCHECK_RET (prpoolinfo->stname.aname, "ring pool")
+ int retVal = SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s_%x",
+ prpoolinfo->stname.aname, NSFW_SHMEM_PID);
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]");
+ }
+ }
+
+ return nsfw_remote_shmem_ringcreatev (aname, prpoolinfo->usnum,
+ pringhandle_array, iringnum,
+ SOCKET_ID_ANY, prpoolinfo->enmptype);
+}
+
+i32
+nsfw_shmem_sprelease (nsfw_mem_name * pname)
+{
+ i8 aname[COMMON_MEM_MEMPOOL_NAMESIZE] = { 0 };
+ void *mz_mem = NULL;
+ struct nsfw_mem_ring *ring_ptr = NULL;
+ NSFW_INIT_CHK_RET ();
+
+ if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ mz_mem = common_memzone_data_lookup_name (pname->aname);
+
+ if (mz_mem)
+ {
+ ring_ptr =
+ (struct nsfw_mem_ring *) ((char *) mz_mem +
+ sizeof (struct nsfw_shmem_ring_head));
+ nsfw_shmem_pool_free (ring_ptr);
+ }
+ return NSFW_MEM_OK;
+ }
+ else
+ {
+ NSFW_NAME_LENCHECK_RET (pname->aname, "shmem free")
+ if (-1 ==
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s_%x",
+ pname->aname, NSFW_SHMEM_PID))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]");
+ }
+ }
+
+ return nsfw_remote_free (aname, NSFW_MEM_SPOOL);
+}
+
+mring_handle
+nsfw_shmem_sp_lookup (nsfw_mem_name * pname)
+{
+ i8 aname[COMMON_MEM_MEMPOOL_NAMESIZE] = { 0 };
+ void *mz_mem = NULL;
+ struct nsfw_mem_ring *ring_ptr = NULL;
+ NSFW_INIT_CHK_RET_NULL ();
+
+ if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ mz_mem = common_memzone_data_lookup_name (pname->aname);
+
+ if (mz_mem)
+ {
+ ring_ptr =
+ (struct nsfw_mem_ring *) ((char *) mz_mem +
+ sizeof (struct nsfw_shmem_ring_head));
+ return ring_ptr;
+ }
+ return mz_mem;
+ }
+
+ if ((NSFW_PROC_NULL == pname->enowner)
+ || (NSFW_PROC_MAIN == pname->enowner))
+ {
+ if (-1 ==
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s", pname->aname))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]");
+ }
+ }
+ else
+ {
+ /*app's name can not over NSFW_MEM_APPNAME_LENTH */
+ NSFW_NAME_LENCHECK_RET_NULL (pname->aname, "shmem lookup")
+ if (-1 ==
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s_%x",
+ pname->aname, NSFW_SHMEM_PID))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]");
+ }
+ }
+
+ return nsfw_remote_shmem_lookup (aname, NSFW_MEM_SPOOL);
+}
+
+mring_handle
+nsfw_shmem_ringcreate (nsfw_mem_mring * pringinfo)
+{
+ i8 aname[COMMON_MEM_MEMPOOL_NAMESIZE] = { 0 };
+
+ NSFW_INIT_CHK_RET_NULL ();
+
+ if (NSFW_PROC_MAIN == NSFW_SHMEM_FLAG)
+ {
+ return nsfw_shmem_ring_create (pringinfo->stname.aname,
+ pringinfo->usnum, pringinfo->isocket_id,
+ pringinfo->enmptype);
+ }
+ else
+ {
+ NSFW_NAME_LENCHECK_RET_NULL (pringinfo->stname.aname, "ring create")
+ if (-1 ==
+ SPRINTF_S (aname, COMMON_MEM_MEMPOOL_NAMESIZE, "%s_%x",
+ pringinfo->stname.aname, NSFW_SHMEM_PID))
+ {
+ NSCOMM_LOGERR ("SPRINTF_S faild]");
+ }
+ }
+
+ return nsfw_remote_shmem_ringcreate (aname, pringinfo->usnum, SOCKET_ID_ANY,
+ pringinfo->enmptype);
+}
+
+mring_handle
+nsfw_shmem_ring_lookup (nsfw_mem_name * pname)
+{
+ return nsfw_shmem_lookup (pname);
+}
+
+i32
+nsfw_shmem_ringrelease (nsfw_mem_name * pname)
+{
+ return nsfw_shmem_release (pname);
+}
+
+size_t
+nsfw_shmem_mbufpool_statics (mpool_handle mbufpool)
+{
+ struct common_mem_mempool *mp = (struct common_mem_mempool *) mbufpool;
+ return (size_t) mp->size * (mp->header_size + mp->elt_size +
+ mp->trailer_size) +
+ (size_t) mp->private_data_size +
+ (size_t)
+ common_mem_ring_get_memsize (common_mem_align32pow2 (mp->size + 1));
+}
+
+size_t
+nsfw_shmem_sppool_statics (mring_handle sppool)
+{
+ struct nsfw_shmem_ring_head *temp = NULL;
+ size_t lent = 0;
+ temp =
+ (struct nsfw_shmem_ring_head *) ((char *) sppool -
+ sizeof (struct nsfw_shmem_ring_head));
+
+ while (temp)
+ {
+ lent += temp->mem_zone->len;
+ temp = temp->next;
+ }
+
+ return lent;
+}
+
+size_t
+nsfw_shmem_ring_statics (mring_handle handle)
+{
+ struct nsfw_mem_ring *ring = (struct nsfw_mem_ring *) handle;
+ return ring->size * sizeof (union RingData_U) +
+ sizeof (struct nsfw_mem_ring);
+}
+
+ssize_t
+nsfw_shmem_stactic (void *handle, nsfw_mem_struct_type type)
+{
+ switch (type)
+ {
+ case NSFW_MEM_MBUF:
+ return nsfw_shmem_mbufpool_statics (handle);
+ case NSFW_MEM_SPOOL:
+ return nsfw_shmem_sppool_statics (handle);
+ case NSFW_MEM_RING:
+ return nsfw_shmem_ring_statics (handle);
+ default:
+ break;
+ }
+ return -1;
+}
+
+i32
+nsfw_shmem_mbuf_recycle (mpool_handle handle)
+{
+#if 0
+ const struct common_mem_mempool *mp = (struct common_mem_mempool *) handle;
+ struct common_mem_ring *rteRing = NULL;
+ struct common_mem_mbuf *m_buf = NULL;
+ uint32_t item;
+ u32_t *recycle_flg;
+ uint32_t size = mp->size;
+ uint32_t threadsize = (size >> 2) * 3;
+ rteRing = (struct common_mem_ring *) ADDR_SHTOL (mp->ring);
+
+ if (rteRing->prod.tail - rteRing->cons.head < threadsize)
+ {
+ for (item = 0; item < size - 1; item++)
+ {
+ m_buf = (struct common_mem_mbuf *) ADDR_SHTOL (mp->elt_va_start + item * (mp->header_size + mp->elt_size + mp->trailer_size) + mp->header_size); /*lint !e647 */
+ recycle_flg =
+ (uint32_t *) ((char *) (ADDR_SHTOL (m_buf->buf_addr_align)) +
+ RTE_PKTMBUF_HEADROOM - sizeof (uint32_t));
+
+ if (m_buf->refcnt > 0 && *recycle_flg == MBUF_HLD_BY_APP)
+ {
+ NSCOMM_LOGINF ("free mbuf hold by app]ring=%p, mbuf=%p", handle,
+ m_buf);
+ *recycle_flg = MBUF_UNUSED;
+ common_mem_pktmbuf_free (m_buf);
+ }
+ }
+ }
+
+ NSCOMM_LOGINF ("To recycle app_tx_pool now]ring=%p,prod.head=%u,"
+ "prod.tail=%u,cons.head=%u,cons.tail=%u.", handle,
+ rteRing->prod.head, rteRing->prod.tail,
+ rteRing->cons.head, rteRing->cons.tail);
+
+ /*we Must check and recorrect the Queue if Queue is not correct
+ 1.if proc.head != proc.tail set proc.head to proc.tail [may lost some buf,but the queue still can use]
+ App May not putIn Data , just done head++, we can't set proc.tail to proc.head.
+ 2.if cons.head != cons.tail set cons.tail to cons.head [may lost some buf,but the queue still can use]
+ App May alread finish deque,just not tail++, we can't set cons.head to cons.tail.
+ */
+ if ((rteRing->prod.head != rteRing->prod.tail)
+ || (rteRing->cons.head != rteRing->cons.tail))
+ {
+ rteRing->prod.head = rteRing->prod.tail;
+ rteRing->cons.tail = rteRing->cons.head;
+ }
+#endif
+ return NSFW_MEM_OK;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_shmem_sp_iterator
+* Description : sp pool iterator
+* Input : mpool_handle handle
+* u32 start
+* u32 end
+* nsfw_mem_item_fun fun
+* void *argv
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_shmem_sp_iterator (mpool_handle handle, u32 start, u32 end,
+ nsfw_mem_item_fun fun, void *argv)
+{
+ struct nsfw_mem_ring *perfring_ptr = (struct nsfw_mem_ring *) handle;
+ if (NULL == perfring_ptr || NULL == fun)
+ {
+ return 0;
+ }
+
+ if (0 == perfring_ptr->eltsize)
+ {
+ return 0;
+ }
+
+ int num = perfring_ptr->size;
+ if (start >= (u32) num || end <= start)
+ {
+ return 0;
+ }
+
+ struct nsfw_shmem_ring_head *ring_head =
+ (struct nsfw_shmem_ring_head *) ((char *) handle -
+ sizeof (struct nsfw_shmem_ring_head));
+ void *mz =
+ (void *) ((char *) perfring_ptr + sizeof (struct nsfw_mem_ring) +
+ num * sizeof (union RingData_U));
+
+ if (ring_head->mem_zone->len <
+ sizeof (struct nsfw_shmem_ring_head) + sizeof (struct nsfw_mem_ring) +
+ num * sizeof (union RingData_U))
+ {
+ return 0;
+ }
+
+ u32 mz_len =
+ ring_head->mem_zone->len - sizeof (struct nsfw_shmem_ring_head) -
+ sizeof (struct nsfw_mem_ring) - num * sizeof (union RingData_U);
+
+ u32 start_idx = 0;
+ u32 elm_num = 0;
+ elm_num = mz_len / perfring_ptr->eltsize;
+ while (start > start_idx + elm_num)
+ {
+ if (NULL == ring_head->next || NULL == ring_head->next->mem_zone
+ || 0 == elm_num)
+ {
+ return 0;
+ }
+
+ ring_head =
+ (struct nsfw_shmem_ring_head *) ring_head->next->mem_zone->addr_64;
+ mz_len =
+ ring_head->mem_zone->len - sizeof (struct nsfw_shmem_ring_head);
+
+ elm_num = mz_len / perfring_ptr->eltsize;
+ mz =
+ (void *) ((char *) ring_head + sizeof (struct nsfw_shmem_ring_head));
+ start_idx += elm_num;
+ }
+
+ u32 cur_idx = start - start_idx;
+ char *cur_elm = NULL;
+ int proc_count = 0;
+ while (cur_idx + start_idx < end && cur_idx + start_idx < (u32) num)
+ {
+ if (cur_idx >= elm_num)
+ {
+ if (NULL == ring_head->next || NULL == ring_head->next->mem_zone
+ || 0 == elm_num)
+ {
+ break;
+ }
+
+ ring_head =
+ (struct nsfw_shmem_ring_head *) ring_head->next->
+ mem_zone->addr_64;
+ mz_len =
+ ring_head->mem_zone->len - sizeof (struct nsfw_shmem_ring_head);
+
+ elm_num = mz_len / perfring_ptr->eltsize;
+ mz =
+ (void *) ((char *) ring_head +
+ sizeof (struct nsfw_shmem_ring_head));
+ start_idx += elm_num;
+
+ cur_idx = 0;
+ cur_elm = NULL;
+ continue;
+ }
+
+ if (NULL == cur_elm)
+ {
+ cur_elm = ((char *) mz + cur_idx * perfring_ptr->eltsize);
+ }
+ else
+ {
+ cur_elm += perfring_ptr->eltsize;
+ }
+
+ cur_idx++;
+ proc_count++;
+ (void) fun (cur_elm, argv);
+ }
+
+ return proc_count;
+}
+
+i32
+nsfw_shmem_mbuf_iterator (mpool_handle handle, u32 start, u32 end,
+ nsfw_mem_item_fun fun, void *argv)
+{
+ return dmm_pktmbuf_pool_iterator ((struct common_mem_mempool *) handle,
+ start, end, (dmm_mbuf_item_fun) fun,
+ argv);
+}
diff --git a/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mng.h b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mng.h
new file mode 100644
index 0000000..f81b34a
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_mng.h
@@ -0,0 +1,133 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_SHMEM_MNG_H
+#define _NSFW_SHMEM_MNG_H
+
+/*
+ * mem mgr module init
+ * para:point to nstak_fwmem_para
+ */
+i32 nsfw_shmem_init (nsfw_mem_para * para);
+
+/*
+ * mem mgr module destory
+ *
+ */
+void nsfw_shmem_destroy (void);
+
+/*
+ * create a block memory with name
+ * fw_mem_zone::stname name of memory
+ * fw_mem_zone::isize memory size
+ */
+mzone_handle nsfw_shmem_create (nsfw_mem_zone * pinfo);
+
+/*
+ *create some blocks memeory
+ */
+i32 nsfw_shmem_createv (nsfw_mem_zone * pmeminfo, i32 inum,
+ mzone_handle * paddr_array, i32 iarray_num);
+
+/*
+ *lookup a memory
+ */
+mzone_handle nsfw_shmem_lookup (nsfw_mem_name * pname);
+
+/*release the memory*/
+i32 nsfw_shmem_release (nsfw_mem_name * pname);
+
+/*
+ *create mbuf pool
+ */
+mpool_handle nsfw_shmem_mbfmpcreate (nsfw_mem_mbfpool * pbufinfo);
+
+/*
+ *create some mbuf pool
+ */
+i32 nsfw_shmem_mbfmpcreatev (nsfw_mem_mbfpool * pmbfname, i32 inum,
+ mpool_handle * phandle_array, i32 iarray_num);
+
+/*
+ *alloc a mbuf from mbuf pool
+ */
+mbuf_handle nsfw_shmem_mbfalloc (mpool_handle mhandle);
+
+/*
+ *release a mbuf pool
+ */
+i32 nsfw_shmem_mbffree (mbuf_handle mhandle);
+
+/*
+ *put mbuf backto mbuf pool
+ */
+i32 nsfw_shmem_mbfmprelease (nsfw_mem_name * pname);
+
+/*look up mbuf mpool*/
+mpool_handle nsfw_shmem_mbfmplookup (nsfw_mem_name * pmbfname);
+
+/*
+ *create simple pool
+ */
+mring_handle nsfw_shmem_spcreate (nsfw_mem_sppool * pmpinfo);
+
+/*
+ *create some simple pools
+ */
+i32 nsfw_shmem_spcreatev (nsfw_mem_sppool * pmpinfo, i32 inum,
+ mring_handle * pringhandle_array, i32 iarray_num);
+
+/*
+ *create a simple pool that members are rings
+ */
+i32 nswf_shmem_sp_ringcreate (nsfw_mem_mring * prpoolinfo,
+ mring_handle * pringhandle_array, i32 iringnum);
+
+/*
+ *release a simple pool
+ */
+i32 nsfw_shmem_sprelease (nsfw_mem_name * pname);
+
+/*
+ *look up a simple pool
+ */
+mring_handle nsfw_shmem_sp_lookup (nsfw_mem_name * pname);
+
+/*
+ *create a ring with name
+ */
+mring_handle nsfw_shmem_ringcreate (nsfw_mem_mring * pringinfo);
+
+/*
+ *look up a ring with name
+ */
+mring_handle nsfw_shmem_ring_lookup (nsfw_mem_name * pname);
+
+/*
+ *release ring
+ */
+i32 nsfw_shmem_ringrelease (nsfw_mem_name * pname);
+
+ssize_t nsfw_shmem_stactic (void *handle, nsfw_mem_struct_type type);
+
+i32 nsfw_shmem_mbuf_recycle (mpool_handle handle);
+
+i32 nsfw_shmem_sp_iterator (mpool_handle handle, u32 start, u32 end,
+ nsfw_mem_item_fun fun, void *argv);
+i32 nsfw_shmem_mbuf_iterator (mpool_handle handle, u32 start, u32 end,
+ nsfw_mem_item_fun fun, void *argv);
+
+#endif
diff --git a/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_ring.c b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_ring.c
new file mode 100644
index 0000000..af46e18
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_ring.c
@@ -0,0 +1,839 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <string.h>
+#include <common_sys_config.h>
+
+#include "common_mem_pal.h"
+#include "common_mem_pal_memconfig.h"
+#include "nstack_securec.h"
+#include "nsfw_shmem_ring.h"
+#include "nsfw_ring_fun.h"
+#include "common_mem_buf.h"
+#include "common_func.h"
+
+void
+nsfw_shmem_ring_baseaddr_query (uint64_t * rte_lowest_addr,
+ uint64_t * rte_highest_addr)
+{
+ struct common_mem_mem_config *pMemCfg =
+ common_mem_pal_get_configuration ()->mem_config;
+ struct common_mem_memseg *PMemSegArry = pMemCfg->memseg;
+
+ *rte_lowest_addr = PMemSegArry[0].addr_64;
+ *rte_highest_addr = PMemSegArry[0].addr_64 + PMemSegArry[0].len;
+
+ int s = 1;
+
+ while (s < COMMON_MEM_MAX_MEMSEG && PMemSegArry[s].len > 0)
+ {
+ if (*rte_lowest_addr > PMemSegArry[s].addr_64)
+ {
+ *rte_lowest_addr = PMemSegArry[s].addr_64;
+ }
+
+ if (*rte_highest_addr < PMemSegArry[s].addr_64 + PMemSegArry[s].len)
+ {
+ *rte_highest_addr = PMemSegArry[s].addr_64 + PMemSegArry[s].len;
+ }
+
+ s++;
+ }
+
+}
+
+static unsigned
+nsfw_shmem_pool_node_alloc (struct nsfw_mem_ring *perfring_ptr,
+ unsigned alloc_index, unsigned max_index,
+ void *mz, size_t mz_len, unsigned elt_size)
+{
+ size_t alloc_size = 0;
+ unsigned offset_idx = 0;
+ NSTCP_LOGINF ("mz(%p), mz_len = 0x%x", mz, mz_len);
+
+ while (alloc_size + elt_size <= mz_len)
+ {
+ perfring_ptr->ring[alloc_index + offset_idx].data_s.ver =
+ alloc_index + offset_idx;
+ perfring_ptr->ring[alloc_index + offset_idx].data_s.val =
+ ADDR_LTOSH_EXT (mz) - ((uint64_t) perfring_ptr->Addrbase);
+ mz = (char *) mz + elt_size;
+ alloc_size += elt_size;
+ offset_idx++;
+
+ if (alloc_index + offset_idx == max_index)
+ {
+ break;
+ }
+ }
+
+ return offset_idx;
+}
+
+void
+nsfw_shmem_pool_free (struct nsfw_mem_ring *perfring_ptr)
+{
+ struct nsfw_shmem_ring_head *ptemp;
+
+ if (NULL == perfring_ptr)
+ {
+ return;
+ }
+
+ struct nsfw_shmem_ring_head *pnode =
+ (struct nsfw_shmem_ring_head *) ((char *) perfring_ptr -
+ sizeof (struct nsfw_shmem_ring_head));
+
+ while (pnode)
+ {
+ // phead is involved in phead->mem_zone
+ ptemp = pnode->next;
+ common_mem_memzone_free (pnode->mem_zone);
+ pnode = ptemp;
+ }
+}
+
+struct nsfw_mem_ring *
+nsfw_shmem_pool_create (const char *name, unsigned int n,
+ unsigned int elt_size, int socket_id,
+ unsigned char flag)
+{
+ struct nsfw_mem_ring *perfring_ptr = NULL;
+ struct common_mem_memzone *mz_mem;
+ void *mz = NULL;
+
+ /*get pool size, pool size must pow of 2 */
+ unsigned int num = common_mem_align32pow2 (n + 1);
+
+ struct nsfw_shmem_ring_head *pcur = NULL;
+ /*calculat the empty rte_perf_ring Size */
+ size_t len =
+ sizeof (struct nsfw_shmem_ring_head) + sizeof (struct nsfw_mem_ring) +
+ (size_t) num * sizeof (union RingData_U) + (size_t) num * elt_size;
+ size_t alloc_len = len;
+ unsigned int alloc_num = 0;
+ unsigned int alloc_index = 0;
+
+ size_t mz_len = 0;
+
+ unsigned int mz_index = 1;
+ char mz_name[128] = { 0 };
+ int retVal;
+ /*we'd better use `strlen(src)` or `sizeof(dst)` to explain copying length of src string.
+ it's meaningless using `sizeof(dst) - 1` to reserve 1 byte for '\0'.
+ if copying length equals to or bigger than dst length, just let STRNCPY_S() returns failure. */
+ retVal = STRNCPY_S (mz_name, sizeof (mz_name), name, sizeof (mz_name));
+
+ if (EOK != retVal)
+ {
+ NSTCP_LOGERR ("STRNCPY_S failed]ret=%d", retVal);
+ return NULL;
+ }
+
+ mz_mem = common_memzone_data_lookup_name (name);
+ NSTCP_LOGINF ("memzone data look up] n=%u,num=%u,len=%zu", n, num, len);
+
+ if (mz_mem)
+ {
+ perfring_ptr =
+ (struct nsfw_mem_ring *) ((char *) mz_mem +
+ sizeof (struct nsfw_shmem_ring_head));
+ return perfring_ptr;
+ }
+
+ while (alloc_len > 0)
+ {
+ if (NULL != perfring_ptr)
+ {
+ retVal =
+ SPRINTF_S (mz_name, sizeof (mz_name), "%s_%03d", name, mz_index);
+
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]ret=%d", retVal);
+ nsfw_shmem_pool_free (perfring_ptr);
+ return NULL;
+ }
+ }
+
+ mz_mem =
+ (struct common_mem_memzone *) common_mem_memzone_reserve (mz_name,
+ alloc_len,
+ socket_id,
+ 0);
+
+ if (mz_mem == NULL)
+ {
+ mz_mem =
+ (struct common_mem_memzone *) common_mem_memzone_reserve (mz_name,
+ 0,
+ socket_id,
+ 0);
+ }
+
+ if (mz_mem == NULL)
+ {
+ nsfw_shmem_pool_free (perfring_ptr);
+ return NULL;
+ }
+
+ if (NULL == perfring_ptr
+ && (mz_mem->len <
+ sizeof (struct nsfw_shmem_ring_head) +
+ sizeof (struct nsfw_mem_ring) +
+ num * sizeof (union RingData_U)))
+ {
+ common_mem_memzone_free (mz_mem);
+ return NULL;
+ }
+
+ if (NULL == perfring_ptr)
+ {
+ pcur = (struct nsfw_shmem_ring_head *) ADDR_SHTOL (mz_mem->addr_64);
+ pcur->mem_zone = mz_mem;
+ pcur->next = NULL;
+
+ perfring_ptr =
+ (struct nsfw_mem_ring *) ((char *) pcur +
+ sizeof (struct nsfw_shmem_ring_head));
+
+ mz =
+ (void *) ((char *) perfring_ptr + sizeof (struct nsfw_mem_ring) +
+ num * sizeof (union RingData_U));
+ mz_len =
+ mz_mem->len - sizeof (struct nsfw_shmem_ring_head) -
+ sizeof (struct nsfw_mem_ring) - num * sizeof (union RingData_U);
+
+ uint64_t rte_base_addr;
+ uint64_t rte_highest_addr;
+ nsfw_shmem_ring_baseaddr_query (&rte_base_addr, &rte_highest_addr);
+ nsfw_mem_pool_head_init (perfring_ptr, num, elt_size,
+ (void *) rte_base_addr, NSFW_SHMEM,
+ (nsfw_mpool_type) flag);
+ }
+ else
+ {
+ if (pcur)
+ {
+ pcur->next =
+ (struct nsfw_shmem_ring_head *) ADDR_SHTOL (mz_mem->addr_64);
+ pcur = pcur->next;
+ pcur->mem_zone = mz_mem;
+ pcur->next = NULL;
+
+ if (mz_mem->len < sizeof (struct nsfw_shmem_ring_head))
+ {
+ NSCOMM_LOGERR ("mz_len error %d", mz_mem->len);
+ nsfw_shmem_pool_free (perfring_ptr);
+ return NULL;
+ }
+
+ mz =
+ (void *) ((char *) pcur +
+ sizeof (struct nsfw_shmem_ring_head));
+ mz_len = mz_mem->len - sizeof (struct nsfw_shmem_ring_head);
+ }
+ }
+
+ alloc_num =
+ nsfw_shmem_pool_node_alloc (perfring_ptr, alloc_index, num, mz,
+ mz_len, elt_size);
+ alloc_index += alloc_num;
+
+ if (alloc_index >= num)
+ {
+ break;
+ }
+
+ // second time allocate should not containd all ring head
+ alloc_len =
+ (size_t) (num - alloc_index) * elt_size +
+ sizeof (struct nsfw_shmem_ring_head);
+ mz_index++;
+ }
+
+ return perfring_ptr;
+}
+
+/*ring create*/
+struct nsfw_mem_ring *
+nsfw_shmem_ring_create (const char *name, unsigned int n, int socket_id,
+ unsigned char flag)
+{
+ struct nsfw_mem_ring *perfring_ptr;
+ struct common_mem_memzone *mz;
+ uint64_t rte_base_addr;
+ uint64_t rte_highest_addr;
+
+ unsigned int num = common_mem_align32pow2 (n);
+
+ mz =
+ (struct common_mem_memzone *) common_mem_memzone_reserve (name,
+ sizeof (struct
+ nsfw_mem_ring)
+ +
+ num *
+ sizeof (union
+ RingData_U),
+ socket_id, 0);
+
+ if (mz == NULL)
+ {
+ return NULL;
+ }
+
+ perfring_ptr = mz->addr;
+
+ nsfw_shmem_ring_baseaddr_query (&rte_base_addr, &rte_highest_addr);
+ nsfw_mem_ring_init (perfring_ptr, num, (void *) rte_base_addr, NSFW_SHMEM,
+ flag);
+
+ return perfring_ptr;
+}
+
+/*
+this is a multi thread/process enqueue function, please pay attention to the bellow point
+1. while Enqueue corrupt, we may lose one element; because no one to add the Head
+*/
+int
+nsfw_shmem_ring_mp_enqueue (struct nsfw_mem_ring *ring, void *box)
+{
+ union RingData_U expectPostVal;
+ union RingData_U curVal;
+ unsigned int tmpHead;
+ unsigned int tmpTail;
+ unsigned int CurHead = ring->prod.head;
+ unsigned int mask = ring->mask;
+ unsigned int size = ring->size;
+ void *prmBox = NULL;
+
+ prmBox = (void *) ADDR_LTOSH_EXT (box);
+
+ /*do box range check */
+ if ((char *) prmBox <= (char *) ring->Addrbase
+ || (char *) prmBox > (char *) ring->Addrbase + PERFRING_ADDR_RANGE)
+ {
+ /*invalid addr of box, can't put in rte_perf_ring, maybe should set a errno here */
+ return -1;
+ }
+
+ do
+ {
+ /*
+ if the ring is Full return directly; this not a exact check, cause we made tail++ after dequeue success.
+ the thing we could make sure is ring[ring->Tail&mask] already dequeue
+ */
+ tmpTail = ring->cons.tail;
+
+ if (tmpTail + size - CurHead == 0)
+ {
+ /*
+ here we give enque a chance to recorrect the Tail, if tail not has Data let tail++
+ */
+ if (ring->ring[tmpTail & mask].data_s.val == 0)
+ {
+ (void) __sync_bool_compare_and_swap (&ring->cons.tail, tmpTail,
+ tmpTail + 1);
+ }
+ else
+ {
+ return 0;
+ }
+ }
+
+ /*
+ the old version of ring->ring[CurHead&mask] must CurHead - size, which enqueue set to this pos lasttime
+ & the val must already dequeue. otherwise this pos can't enqueue;
+ */
+ expectPostVal.data_l =
+ (((unsigned long long) (CurHead - size)) << VALUE_LEN);
+
+ /*
+ the new version of ring->ring[CurHead&mask] must CurHead, which enqueue set to this pos this time.
+ */
+ curVal.data_l =
+ ((((unsigned long long) CurHead) << VALUE_LEN) |
+ ((char *) prmBox - (char *) ring->Addrbase));
+ if (ring->ring[CurHead & mask].data_s.ver == expectPostVal.data_s.ver
+ && __sync_bool_compare_and_swap (&ring->ring[CurHead & mask].data_l,
+ expectPostVal.data_l,
+ curVal.data_l))
+ {
+ /*
+ enqueue success, add Head Value now
+ here we using CAS set instead __sync_fetch_and_add(&ring->Head, 1) to assume that, if one process enque sucess && been killed before
+ add Head, other process can recorrect the Head Value;
+ one more thing the direction of Tail must been add-direction, so we using the condition (ring->Head - CurHead >0x80000000);
+ while many thread do enque at same time, Head may not correct,exp:
+ thread A get old head 10, thread A want set head to 11
+ thread B get old head 10, thread B want set head to 12
+ thread A do CAS && thread B do CAS at same time, thread A do CAS success;
+ the result of head is 11, but the correct Value should be 12;
+
+ then thread C get old head 11, thread C will set head to 13[cause pos 12 already has value, thread C will skill 12],
+ the head will be recorrect by thread C.
+ if no thread C, thread A& B are the last enque thread; the head must recorrect by the deque function.
+ */
+ tmpHead = ring->prod.head;
+
+ if (0 == (CurHead & 0x03) && tmpHead - CurHead > 0x80000000)
+ {
+ (void) __sync_bool_compare_and_swap (&ring->prod.head, tmpHead,
+ CurHead + 1);
+ }
+
+ break;
+ }
+
+ /*
+ CurHead++ here;
+ may be cpu slice is end here; while re-sched CurHead < ring->Tail < ring->Head; to avoid multi try
+ we using a cmp & CurHead++ instead CurHead++ directly.
+ if using CurHead++ will amplify the probability of ABA problem
+ */
+ /*CurHead++; */
+ tmpHead = ring->prod.head;
+ CurHead = CurHead - tmpHead < mask - 1 ? CurHead + 1 : tmpHead;
+ }
+ while (1);
+
+ return 1;
+}
+
+/*
+ this is a single thread/process enqueue function
+ */
+int
+nsfw_shmem_ring_sp_enqueue (struct nsfw_mem_ring *ring, void *box)
+{
+ union RingData_U texpectPostVal;
+ union RingData_U curVal;
+ unsigned int tmpTail;
+ unsigned int CurHead = ring->prod.head;
+ unsigned int mask = ring->mask;
+ unsigned int uisize = ring->size;
+ void *prmBox = NULL;
+
+ prmBox = (void *) ADDR_LTOSH_EXT (box);
+
+ if ((char *) prmBox <= (char *) ring->Addrbase
+ || (char *) prmBox > (char *) ring->Addrbase + PERFRING_ADDR_RANGE)
+ {
+ return -1;
+ }
+
+ do
+ {
+ tmpTail = ring->cons.tail;
+ if (tmpTail + uisize - CurHead == 0)
+ {
+ /*
+ *here we give enque a chance to recorrect the Tail, if tail not has Data let tail++
+ */
+ if (ring->ring[tmpTail & mask].data_s.val == 0)
+ {
+ (void) __sync_bool_compare_and_swap (&ring->cons.tail, tmpTail,
+ tmpTail + 1);
+ }
+ else
+ {
+ return 0;
+ }
+ }
+ texpectPostVal.data_l =
+ (((unsigned long long) (CurHead - uisize)) << VALUE_LEN);
+
+ curVal.data_l =
+ ((((unsigned long long) CurHead) << VALUE_LEN) |
+ ((char *) prmBox - (char *) ring->Addrbase));
+
+ if (ring->ring[CurHead & mask].data_l == texpectPostVal.data_l)
+ {
+ ring->ring[CurHead & mask].data_l = curVal.data_l;
+ ring->prod.head = CurHead + 1;
+ break;
+ }
+
+ CurHead++;
+ }
+ while (1);
+ return 1;
+}
+
+/*this is a multi thread/process dequeue function, please pay attention to the bellow point
+*/
+int
+nsfw_shmem_ring_mc_dequeue (struct nsfw_mem_ring *ring, void **box)
+{
+ unsigned int CurTail;
+ unsigned int tmpTail;
+ unsigned int tmpHead;
+ unsigned int mask = ring->mask;
+ union RingData_U curNullVal;
+ union RingData_U ExcpRingVal;
+
+ CurTail = ring->cons.tail;
+ do
+ {
+ /*if ring is empty return directly */
+ tmpHead = ring->prod.head;
+
+ if (CurTail == tmpHead)
+ {
+ /*
+ here we give deque a chance to recorrect the Head, if head has Data let Head++
+ */
+ if (ring->ring[tmpHead & mask].data_s.val != 0)
+ {
+ (void) __sync_bool_compare_and_swap (&ring->prod.head, tmpHead,
+ tmpHead + 1);
+ }
+ else
+ {
+ return 0;
+ }
+ }
+ curNullVal.data_l = (((unsigned long long) CurTail) << VALUE_LEN);
+ ExcpRingVal = ring->ring[CurTail & mask];
+ /*
+ *the version of ring->ring[CurTail&mask] must CurTail&0xFFFFFF
+ */
+ if ((curNullVal.data_s.ver == ExcpRingVal.data_s.ver)
+ && (ExcpRingVal.data_s.val)
+ && __sync_bool_compare_and_swap (&ring->ring[CurTail & mask].data_l,
+ ExcpRingVal.data_l,
+ curNullVal.data_l))
+ {
+
+ *box =
+ ADDR_SHTOL (((char *) ring->Addrbase + ExcpRingVal.data_s.val));
+
+ /*
+ enqueue success, add Tail Value now
+ here we using CAS set instead __sync_fetch_and_add(&ring->Tail, 1) to assume that, if one process dequeue sucess && been killed before
+ add Tail, other process can recorrect the Tail Value;
+ one more thing the direction of Tail must been add-direction, so we using the condition (rlTail - CurTail >0x80000000);
+ while multi CAS done the result value of CurTail may not correct, but we don't care, it will be recorrect while next deque done.
+
+ avg CAS cost 200-300 Cycles, so we using cache loop to instead some CAS;[head&tail not exact guide, so no need Do CAS evertime]
+ here we using 0 == (CurTail&0x11) means we only do CAS while head/tail low bit is 0x11; four times do one CAS.
+ */
+ tmpTail = ring->cons.tail;
+
+ if (0 == (CurTail & 0x03) && tmpTail - CurTail > 0x80000000)
+ {
+ (void) __sync_bool_compare_and_swap (&ring->cons.tail, tmpTail,
+ CurTail + 1);
+ }
+ break;
+ }
+
+ /*
+ CurTail++ here;
+ may be cpu slice is end here; while re-sched CurTail < ring->Tail < ring->Head; to avoid multi try
+ we using a cmp & CurTail++ instead CurTail++ directly.
+ if using CurTail++ will amplify the probability of ABA problem
+ */
+ /*CurTail++; */
+ tmpTail = ring->cons.tail;
+ CurTail = CurTail - tmpTail < mask - 1 ? CurTail + 1 : tmpTail;
+ }
+ while (1);
+
+ return 1;
+}
+
+/*
+ this is enhanced mc_ring_dequeue, support dequeue multi element one time.
+*/
+int
+nsfw_shmem_ring_mc_dequeuev (struct nsfw_mem_ring *ring, void **box,
+ unsigned int n)
+{
+ unsigned int uiCurTail;
+ unsigned int tmpTail;
+ unsigned int tmpHead;
+ unsigned int uimask = ring->mask;
+ union RingData_U curNullVal;
+ union RingData_U ExcpRingVal;
+ unsigned int deqNum = 0;
+ uiCurTail = ring->cons.tail;
+ do
+ {
+ /*if ring is empty return directly */
+ tmpHead = ring->prod.head;
+ if (uiCurTail == tmpHead)
+ {
+ /*
+ here we give deque a chance to recorrect the Head, if head has Data let Head++;
+ here must done to avoid some msg can't deque.
+ */
+ if (deqNum == 0 && ring->ring[tmpHead & uimask].data_s.val != 0)
+ {
+ (void) __sync_bool_compare_and_swap (&ring->prod.head, tmpHead,
+ tmpHead + 1);
+ }
+ else
+ {
+ return deqNum;
+ }
+ }
+
+ curNullVal.data_l = (((unsigned long long) uiCurTail) << VALUE_LEN);
+ ExcpRingVal = ring->ring[uiCurTail & uimask];
+
+ /*
+ *the version of ring->ring[CurTail&mask] must CurTail&0xFFFFFF
+ */
+ if ((curNullVal.data_s.ver == ExcpRingVal.data_s.ver)
+ && (ExcpRingVal.data_s.val)
+ && __sync_bool_compare_and_swap (&ring->
+ ring[uiCurTail & uimask].data_l,
+ ExcpRingVal.data_l,
+ curNullVal.data_l))
+ {
+
+ box[deqNum] =
+ ADDR_SHTOL (((char *) ring->Addrbase + ExcpRingVal.data_s.val));
+
+ /*
+ enqueue success, add Tail Value now
+ here we using CAS set instead __sync_fetch_and_add(&ring->Tail, 1) to assume that, if one process dequeue sucess && been killed before
+ add Tail, other process can recorrect the Tail Value;
+ one more thing the direction of Tail must been add-direction, so we using the condition (rlTail - CurTail >0x80000000);
+
+ avg CAS cost 200-300 Cycles, so we using cache loop to instead some CAS;[head&tail not exact guide, so no need Do CAS evertime]
+ here we using 0 == (CurTail&0x11) means we only do CAS while head/tail low bit is 0x11; four times do one CAS.
+ */
+ tmpTail = ring->cons.tail;
+
+ if (0 == (uiCurTail & 0x03) && tmpTail - uiCurTail > 0x80000000)
+ {
+ (void) __sync_bool_compare_and_swap (&ring->cons.tail, tmpTail,
+ uiCurTail + 1);
+ }
+
+ deqNum++;
+ }
+
+ /*
+ CurTail++ here;
+ may be cpu slice is end here; while re-sched CurTail < ring->Tail < ring->Head; to avoid multi try
+ we using a cmp & CurTail++ instead CurTail++ directly.
+ if using CurTail++ will amplify the probability of ABA problem
+ */
+ /*CurTail++; */
+ tmpTail = ring->cons.tail;
+ uiCurTail = uiCurTail - tmpTail < uimask - 1 ? uiCurTail + 1 : tmpTail;
+
+ }
+ while (n > deqNum);
+
+ return deqNum;
+}
+
+/*
+ this is enhanced mc_ring_dequeue, support dequeue multi element one time.
+*/
+int
+nsfw_shmem_ring_sc_dequeue (struct nsfw_mem_ring *ring, void **box)
+{
+ unsigned int CurTail;
+ unsigned int mask = ring->mask;
+ union RingData_U curNullVal;
+ union RingData_U ExcpRingVal;
+ unsigned int uitmpHead;
+
+ CurTail = ring->cons.tail;
+
+ do
+ {
+ /*if ring is empty return directly */
+ uitmpHead = ring->prod.head;
+ if (CurTail == uitmpHead)
+ {
+ /*
+ here we give deque a chance to recorrect the Head, if head has Data let Head++
+ */
+ if (ring->ring[uitmpHead & mask].data_s.val != 0)
+ {
+ (void) __sync_bool_compare_and_swap (&ring->prod.head,
+ uitmpHead, uitmpHead + 1);
+ }
+ else
+ {
+ return 0;
+ }
+ }
+ curNullVal.data_l = (((unsigned long long) CurTail) << VALUE_LEN);
+ ExcpRingVal = ring->ring[CurTail & mask];
+
+ if ((curNullVal.data_s.ver == ExcpRingVal.data_s.ver)
+ && (ExcpRingVal.data_s.val))
+ {
+ ring->ring[CurTail & mask].data_l = curNullVal.data_l;
+
+ *box =
+ ADDR_SHTOL (((char *) ring->Addrbase + ExcpRingVal.data_s.val));
+
+ ring->cons.tail = CurTail + 1;
+ break;
+ }
+
+ CurTail++;
+ }
+ while (1);
+
+ return 1;
+}
+
+/*
+ this is a single thread/process dequeue function
+*/
+int
+nsfw_shmem_ring_sc_dequeuev (struct nsfw_mem_ring *ring, void **box,
+ unsigned int n)
+{
+ unsigned int CurTail;
+ unsigned int tmpHead;
+ unsigned int mask = ring->mask;
+ union RingData_U curNullVal;
+ union RingData_U ExcpRingVal;
+ unsigned int usdeqNum = 0;
+
+ CurTail = ring->cons.tail;
+
+ do
+ {
+ /*if ring is empty return directly */
+ tmpHead = ring->prod.head;
+ if (CurTail == tmpHead)
+ {
+ /*
+ here we give deque a chance to recorrect the Head, if head has Data let Head++;
+ here must done to avoid some msg can't deque.
+ */
+ if (usdeqNum == 0 && ring->ring[tmpHead & mask].data_s.val != 0)
+ {
+ (void) __sync_bool_compare_and_swap (&ring->prod.head, tmpHead,
+ tmpHead + 1);
+ }
+ else
+ {
+ return usdeqNum;
+ }
+ }
+ curNullVal.data_l = (((unsigned long long) CurTail) << VALUE_LEN);
+ ExcpRingVal = ring->ring[CurTail & mask];
+
+ /*
+ the version of ring->ring[CurTail&mask] must CurTail&0xFFFFFF
+ */
+ if ((curNullVal.data_s.ver == ExcpRingVal.data_s.ver)
+ && (ExcpRingVal.data_s.val))
+ {
+ ring->ring[CurTail & mask].data_l = curNullVal.data_l;
+
+ box[usdeqNum] =
+ ADDR_SHTOL (((char *) ring->Addrbase + ExcpRingVal.data_s.val));
+
+ ring->cons.tail = CurTail + 1;
+ usdeqNum++;
+ }
+
+ CurTail++;
+ }
+ while (n > usdeqNum);
+
+ return usdeqNum;
+}
+
+/* nstack just using one thread, for performance using que not support multi thread*/
+int
+nsfw_shmem_ring_singlethread_enqueue (struct nsfw_mem_ring *ring, void *box)
+{
+ u32 head = 0;
+ void *prmBox = NULL;
+
+ /*if queue is full, just return 0 */
+ if (ring->prod.head >= (ring->size + ring->cons.tail))
+ {
+ return 0;
+ }
+
+ prmBox = (void *) ADDR_LTOSH_EXT (box);
+
+ head = ring->prod.head;
+ ring->prod.head = head + 1;
+ ring->ring[head & ring->mask].data_s.ver = head;
+ ring->ring[head & ring->mask].data_s.val =
+ (char *) prmBox - (char *) ring->Addrbase;
+ return 1;
+}
+
+/* nstack just using one thread, for performance using que not support multi thread*/
+int
+nsfw_shmem_ring_singlethread_dequeue (struct nsfw_mem_ring *ring, void **box)
+{
+ u32 tail = 0;
+
+ /* if all entries are dequed return 0 */
+ if (unlikely (ring->prod.head == ring->cons.tail))
+ {
+ return 0;
+ }
+
+ tail = ring->cons.tail;
+ *box =
+ ADDR_SHTOL ((char *) ring->Addrbase +
+ ring->ring[tail & ring->mask].data_s.val);
+ ring->ring[tail & ring->mask].data_s.val = 0;
+ ring->ring[tail & ring->mask].data_s.ver = tail;
+ ring->cons.tail++;
+ return 1;
+}
+
+/* nstack just using one thread, for performance using que not support multi thread*/
+int
+nsfw_shmem_ring_singlethread_dequeuev (struct nsfw_mem_ring *ring, void **box,
+ unsigned int n)
+{
+ u32 tail = 0;
+ u32 num = 0;
+
+ while (num < n)
+ {
+ tail = ring->cons.tail;
+
+ /* if all entries are dequed return 0 */
+ if (unlikely (ring->prod.head == ring->cons.tail))
+ {
+ return num;
+ }
+
+ ring->cons.tail = tail + 1;
+
+ box[num] =
+ ADDR_SHTOL ((char *) ring->Addrbase +
+ ring->ring[tail & ring->mask].data_s.val);
+
+ ring->ring[tail & ring->mask].data_s.val = 0;
+ ring->ring[tail & ring->mask].data_s.ver = tail;
+ num++;
+ }
+
+ return num;
+}
diff --git a/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_ring.h b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_ring.h
new file mode 100644
index 0000000..15cd1dd
--- /dev/null
+++ b/src/framework/common/mem_mgr/nsfw_shmem/nsfw_shmem_ring.h
@@ -0,0 +1,60 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_SHMEM_RING_H_
+#define _NSFW_SHMEM_RING_H_
+
+#include <stdint.h>
+
+#include "common_func.h"
+
+struct nsfw_shmem_ring_head
+{
+ struct common_mem_memzone *mem_zone;
+ struct nsfw_shmem_ring_head *next;
+ unsigned int uireserv[4];
+};
+
+void nsfw_shmem_ring_baseaddr_query (uint64_t * rte_lowest_addr,
+ uint64_t * rte_highest_addr);
+struct nsfw_mem_ring *nsfw_shmem_pool_create (const char *name,
+ unsigned int n,
+ unsigned int elt_size,
+ int socket_id,
+ unsigned char flag);
+struct nsfw_mem_ring *nsfw_shmem_ring_create (const char *name,
+ unsigned int n, int socket_id,
+ unsigned char flag);
+
+void nsfw_shmem_pool_free (struct nsfw_mem_ring *perfring_ptr);
+
+void nsfw_shmem_ring_reset (struct nsfw_mem_ring *ring, unsigned char flag);
+int nsfw_shmem_ring_mp_enqueue (struct nsfw_mem_ring *ring, void *box);
+int nsfw_shmem_ring_sp_enqueue (struct nsfw_mem_ring *ring, void *box);
+int nsfw_shmem_ring_mc_dequeue (struct nsfw_mem_ring *ring, void **box);
+int nsfw_shmem_ring_mc_dequeuev (struct nsfw_mem_ring *ring, void **box,
+ unsigned int n);
+int nsfw_shmem_ring_sc_dequeue (struct nsfw_mem_ring *ring, void **box);
+int nsfw_shmem_ring_sc_dequeuev (struct nsfw_mem_ring *ring, void **box,
+ unsigned int n);
+int nsfw_shmem_ring_singlethread_enqueue (struct nsfw_mem_ring *ring,
+ void *box);
+int nsfw_shmem_ring_singlethread_dequeue (struct nsfw_mem_ring *ring,
+ void **box);
+int nsfw_shmem_ring_singlethread_dequeuev (struct nsfw_mem_ring *ring,
+ void **box, unsigned int n);
+
+#endif /*_NSFW_SHMEM_RING_H_*/
diff --git a/src/framework/hal/hal.c b/src/framework/hal/hal.c
new file mode 100644
index 0000000..1adf274
--- /dev/null
+++ b/src/framework/hal/hal.c
@@ -0,0 +1,865 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "common_sys_config.h"
+#include "common_mem_mbuf.h"
+#include "nstack_log.h"
+#include "nstack_securec.h"
+#include "hal.h"
+#include "hal_api.h"
+
+#define HAL_ARRAY_SIZE(x) (sizeof(x)/sizeof(x[0]))
+/* *INDENT-OFF* */
+static char hal_invalid_char_script[] = {'|', ';', '&', '$', '>', '<', '`', '\\', '\"', '\'',
+ '(', ')', '[', ']', '~', '?', '*'
+ };
+
+static char* hal_invalid_str_script[] = {"&&", "||", ">>", "${", ";;", "/./", "/../"};
+
+static char* hal_invalid_str_script_begin[] = {"./", "../"};
+
+extern const netif_ops_t dpdk_netif_ops;
+
+static hal_hdl_t hal_invaldi_hdl = {.id = -1};
+
+static const netif_ops_t* netif_ops_table[HAL_DRV_MAX];
+static int netif_ops_init_flag = 0;
+
+netif_inst_t netif_tbl[HAL_MAX_NIC_NUM];
+/* *INDENT-ON* */
+
+void
+hal_io_adpt_register (const netif_ops_t * ops)
+{
+ int icnt = 0;
+ if (netif_ops_init_flag == 0)
+ {
+ (void) MEMSET_S (&netif_ops_table[0], sizeof (netif_ops_table), 0,
+ sizeof (netif_ops_table));
+ netif_ops_init_flag = 1;
+ }
+
+ for (icnt = 0; icnt < HAL_DRV_MAX; icnt++)
+ {
+ if (netif_ops_table[icnt] == 0)
+ {
+ netif_ops_table[icnt] = ops;
+ break;
+ }
+ }
+ return;
+}
+
+/*****************************************************************************
+ Prototype : hal_snprintf
+ Description : create shell script
+ Input : char* buffer
+ size_t buflen
+ const char* format
+ ...
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+int
+hal_snprintf (char *buffer, size_t buflen, const char *format, ...)
+{
+ int len;
+ va_list ap;
+
+ /* check buffer validity */
+ if (NULL == buffer || 0 == buflen)
+ {
+ goto einval_error;
+ }
+
+ if (format == NULL)
+ {
+ buffer[0] = '\0';
+
+ goto einval_error;
+ }
+
+ (void) va_start (ap, format);
+ len = VSNPRINTF_S (buffer, buflen, buflen - 1, format, ap);
+
+ if (-1 == len)
+ {
+ va_end (ap);
+ goto einval_error;
+ }
+
+ va_end (ap);
+
+ buffer[buflen - 1] = '\0';
+
+ return len;
+
+einval_error:
+ errno = EINVAL;
+ return -1;
+}
+
+/*****************************************************************************
+ Prototype : hal_is_script_valid
+ Description : Check External Injection of Shell script Validation
+ Input : const char* cmd
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+int
+hal_is_script_valid (const char *cmd)
+{
+ unsigned int i;
+
+ if (cmd)
+ {
+ char *cmd_str = (char *) cmd;
+
+ /* skip space */
+ while (*cmd_str == ' ' || *cmd_str == '\t')
+ {
+ cmd_str++;
+ }
+
+ /* cmd can not start with ./ and ../ */
+ for (i = 0; i < HAL_ARRAY_SIZE (hal_invalid_str_script_begin); i++)
+ {
+ if (strstr (cmd_str, hal_invalid_str_script_begin[i]) == cmd_str)
+ {
+ return 0;
+ }
+ }
+
+ /* cmd can not include | ; $ and so on */
+ for (i = 0; i < HAL_ARRAY_SIZE (hal_invalid_char_script); i++)
+ {
+ if (strchr (cmd, hal_invalid_char_script[i]))
+ {
+ return 0;
+ }
+ }
+
+ /* cmd can not include && || >> and so on */
+ for (i = 0; i < HAL_ARRAY_SIZE (hal_invalid_str_script); i++)
+ {
+ if (strstr (cmd, hal_invalid_str_script[i]))
+ {
+ return 0;
+ }
+ }
+
+ return 1;
+ }
+
+ return 0;
+}
+
+/*****************************************************************************
+ Prototype : hal_run_script
+ Description : run shell script
+ Input : const char* cmd
+ char* result_buf
+ size_t max_result_len
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+int
+hal_run_script (const char *cmd, char *result_buf, size_t max_result_len)
+{
+ size_t n;
+ if (!cmd || !result_buf || max_result_len <= 1)
+ {
+ return -1;
+ }
+
+ FILE *fd = popen (cmd, "r");
+
+ if (fd != NULL)
+ {
+ n = fread (result_buf, sizeof (char), max_result_len - 1, fd);
+
+ if (n == 0)
+ {
+ result_buf[0] = '\0';
+ }
+ else if ('\n' == result_buf[n - 1])
+ {
+ result_buf[n - 1] = '\0';
+ }
+ /* make it null terminated */
+ else
+ {
+ result_buf[n] = '\0';
+ }
+
+ (void) pclose (fd);
+ return n;
+ }
+
+ return -1;
+}
+
+/*****************************************************************************
+ Prototype : hal_init_global
+ Description : init hal when proccess start
+ Input : int argc
+ char** argv
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+int
+hal_init_global (int argc, char **argv)
+{
+ int ret;
+ int netif_type;
+
+ ret =
+ MEMSET_S (netif_tbl, HAL_MAX_NIC_NUM * sizeof (netif_inst_t), 0,
+ HAL_MAX_NIC_NUM * sizeof (netif_inst_t));
+ if (EOK != ret)
+ {
+ NSHAL_LOGERR ("MEMSET_S failed");
+ return -1;
+ }
+
+ for (netif_type = 0; netif_ops_table[netif_type]; ++netif_type)
+ {
+ if (netif_ops_table[netif_type]->init_global)
+ {
+ if (netif_ops_table[netif_type]->init_global (argc, argv))
+ {
+ NSHAL_LOGERR ("failed to init global]netif type=%d",
+ netif_type);
+ return -1;
+ }
+ }
+ }
+
+ return 0;
+}
+
+/*****************************************************************************
+ Prototype : hal_init_local
+ Description : init hal when process or thread start
+ Input : None
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+int
+hal_init_local ()
+{
+ int netif_type;
+
+ for (netif_type = 0; netif_ops_table[netif_type]; ++netif_type)
+ {
+ if (netif_ops_table[netif_type]->init_local)
+ {
+ if (netif_ops_table[netif_type]->init_local ())
+ {
+ NSHAL_LOGERR ("failed to init local]netif type=%d", netif_type);
+ return -1;
+ }
+ }
+ }
+
+ return 0;
+}
+
+/*****************************************************************************
+ Prototype : hal_get_invalid_hdl
+ Description : get the invalid object
+ Input : None
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+hal_hdl_t
+hal_get_invalid_hdl ()
+{
+ return hal_invaldi_hdl;
+}
+
+/*****************************************************************************
+ Prototype : hal_create
+ Description : create hal object
+ Input : const char* name
+ hal_netif_config_t* conf
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+hal_hdl_t
+hal_create (const char *name, hal_netif_config_t * conf)
+{
+ int ret = -1;
+ uint32_t netif_type;
+ netif_inst_t *inst;
+
+ if ((NULL == name) || (NULL == conf))
+ {
+ NSHAL_LOGERR ("invalid para]name=%p,conf=%p", name, conf);
+ return hal_get_invalid_hdl ();
+ }
+
+ inst = alloc_netif_inst ();
+
+ if (NULL == inst)
+ {
+ NSHAL_LOGERR ("failed to alloc netif inst]netif name=%s", name);
+
+ return hal_get_invalid_hdl ();
+ }
+
+ /*open */
+ for (netif_type = 0; NULL != netif_ops_table[netif_type]; ++netif_type)
+ {
+ ret = netif_ops_table[netif_type]->open (inst, name);
+
+ if (0 == ret)
+ {
+ inst->ops = netif_ops_table[netif_type];
+
+ NSHAL_LOGINF ("netif ops]netif type=%u, netif name=%s", netif_type,
+ inst->ops->name);
+
+ break;
+ }
+ }
+
+ if (ret != 0)
+ {
+ inst->state = NETIF_STATE_FREE;
+
+ inst->ops = NULL;
+
+ NSHAL_LOGERR ("open fail]netif name=%s", name);
+
+ return hal_get_invalid_hdl ();
+ }
+
+ /*config */
+ ret = inst->ops->config (inst, conf);
+
+ if (ret != 0)
+ {
+ inst->state = NETIF_STATE_FREE;
+
+ NSHAL_LOGERR ("config fail]netif name=%s", name);
+
+ return hal_get_invalid_hdl ();
+ }
+
+ /*start */
+ ret = inst->ops->start (inst);
+
+ if (ret != 0)
+ {
+ inst->state = NETIF_STATE_FREE;
+
+ NSHAL_LOGERR ("start fail]netif name=%s", name);
+
+ return hal_get_invalid_hdl ();
+ }
+
+ return inst->hdl;
+}
+
+/*****************************************************************************
+ Prototype : hal_bond
+ Description : create hal object for bond mode
+ Input : const char* bond_name
+ uint8_t slave_num
+ hal_hdl_t slave_hdl[]
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+hal_hdl_t
+hal_bond (const char *bond_name, uint8_t slave_num, hal_hdl_t slave_hdl[])
+{
+ int i, ret;
+ netif_inst_t *inst;
+ netif_inst_t *slave_inst[HAL_MAX_SLAVES_PER_BOND];
+
+ if ((0 == slave_num) || (HAL_MAX_SLAVES_PER_BOND < slave_num)
+ || (NULL == bond_name) || (NULL == slave_hdl))
+ {
+ NSHAL_LOGERR ("invalid para]bond_name=%p,slave_num=%u,slave_hdl=%p,",
+ bond_name, slave_num, slave_hdl);
+
+ return hal_get_invalid_hdl ();
+ }
+
+ for (i = 0; i < slave_num; i++)
+ {
+ slave_inst[i] = get_netif_inst (slave_hdl[i]);
+
+ if (NULL == slave_inst[i])
+ {
+ NSHAL_LOGERR ("invalid para slave_hdl]index=%d, slave_inst=%d", i,
+ slave_hdl[i].id);
+ return hal_get_invalid_hdl ();
+ }
+ }
+
+ inst = alloc_netif_inst ();
+
+ if (NULL == inst)
+ {
+ NSHAL_LOGERR ("failed to alloc nic inst]bond_name=%s", bond_name);
+ return hal_get_invalid_hdl ();
+ }
+
+ inst->ops = slave_inst[0]->ops;
+
+ ret = inst->ops->bond (inst, bond_name, slave_num, slave_inst);
+
+ if (0 != ret)
+ {
+ inst->state = NETIF_STATE_FREE;
+
+ inst->ops = NULL;
+
+ NSHAL_LOGERR ("bond netif fail]bond_name=%s", bond_name);
+
+ return hal_get_invalid_hdl ();
+ }
+
+ return inst->hdl;
+}
+
+/*****************************************************************************
+ Prototype : hal_close
+ Description : destroy hal object
+ Input : hal_hdl_t hdl
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+int
+hal_close (hal_hdl_t hdl)
+{
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return -1;
+ }
+
+ inst->state = NETIF_STATE_FREE;
+
+ return inst->ops->close (inst);
+}
+
+/*****************************************************************************
+ Prototype : hal_stop
+ Description : stop recv packet
+ Input : hal_hdl_t hdl
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+int
+hal_stop (hal_hdl_t hdl)
+{
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return -1;
+ }
+
+ return inst->ops->stop (inst);
+}
+
+/*****************************************************************************
+ Prototype : hal_get_mtu
+ Description : get the mtu from nic
+ Input : hal_hdl_t hdl
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+uint32_t
+hal_get_mtu (hal_hdl_t hdl)
+{
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return 0;
+ }
+
+ return inst->ops->mtu (inst);
+}
+
+/*****************************************************************************
+ Prototype : hal_get_macaddr
+ Description : in normal mode, get the mac addr from nic
+ in bond mode1, get the mac addr from primary nic
+ Input : hal_hdl_t hdl
+ void* mac_addr
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+void
+hal_get_macaddr (hal_hdl_t hdl, void *mac_addr)
+{
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return;
+ }
+
+ (void) inst->ops->macaddr (inst, mac_addr);
+}
+
+/*****************************************************************************
+ Prototype : hal_get_capability
+ Description : get offload capability from nic
+ Input : hal_hdl_t hdl
+ hal_netif_capa_t* info
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+void
+hal_get_capability (hal_hdl_t hdl, hal_netif_capa_t * info)
+{
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return;
+ }
+
+ (void) inst->ops->capability (inst, info);
+}
+
+/*****************************************************************************
+ Prototype : hal_recv_packet
+ Description : recv packet from nic
+ Input : hal_hdl_t hdl
+ uint16_t queue_id
+ struct common_mem_mbuf** rx_pkts
+ uint16_t nb_pkts
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+uint16_t
+hal_recv_packet (hal_hdl_t hdl, uint16_t queue_id,
+ struct common_mem_mbuf **rx_pkts, uint16_t nb_pkts)
+{
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return 0;
+ }
+
+ return inst->ops->recv (inst, queue_id, rx_pkts, nb_pkts);
+}
+
+/*****************************************************************************
+ Prototype : hal_send_packet
+ Description : send packet to nic
+ Input : hal_hdl_t hdl
+ uint16_t queue_id
+ struct common_mem_mbuf** tx_pkts
+ uint16_t nb_pkts
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+uint16_t
+hal_send_packet (hal_hdl_t hdl, uint16_t queue_id,
+ struct common_mem_mbuf ** tx_pkts, uint16_t nb_pkts)
+{
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return 0;
+ }
+
+ return inst->ops->send (inst, queue_id, tx_pkts, nb_pkts);
+}
+
+/*****************************************************************************
+ Prototype : hal_link_status
+ Description : get link status form nic
+ Input : hal_hdl_t hdl
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+uint32_t
+hal_link_status (hal_hdl_t hdl)
+{
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return 0;
+ }
+
+ return inst->ops->link_status (inst);
+}
+
+/*****************************************************************************
+ Prototype : hal_stats
+ Description : get link statistics form nic
+ Input : hal_hdl_t hdl
+ hal_netif_stats_t* stats
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+int
+hal_stats (hal_hdl_t hdl, hal_netif_stats_t * stats)
+{
+ netif_inst_t *inst;
+
+ if (NULL == stats)
+ {
+ NSHAL_LOGERR ("invalid para");
+ return -1;
+ }
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return -1;
+ }
+
+ return inst->ops->stats (inst, stats);
+}
+
+/*****************************************************************************
+ Prototype : hal_stats_reset
+ Description : reset link statistics to nic
+ Input : hal_hdl_t hdl
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+void
+hal_stats_reset (hal_hdl_t hdl)
+{
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return;
+ }
+
+ (void) inst->ops->stats_reset (inst);
+}
+
+/*****************************************************************************
+ Prototype : hal_add_mcastaddr
+ Description : set multicast addrs to nic
+ Input : hal_hdl_t hdl
+ void* mc_addr_set
+ void* mc_addr
+ uint32_t nb_mc_addr
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+int
+hal_add_mcastaddr (hal_hdl_t hdl, void *mc_addr_set,
+ void *mc_addr, uint32_t nb_mc_addr)
+{
+ int ret;
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return -1;
+ }
+
+ ret = inst->ops->mcastaddr (inst, mc_addr_set, mc_addr, nb_mc_addr);
+ /* if set mcast addr failed, we have to manually add the mac addr to nic. */
+ if (ret < 0)
+ {
+ ret = inst->ops->add_mac (inst, mc_addr);
+ }
+ return ret;
+}
+
+/*****************************************************************************
+ Prototype : hal_del_mcastaddr
+ Description : delete multicast addrs to nic
+ Input : hal_hdl_t hdl
+ void* mc_addr_set
+ void* mc_addr
+ uint32_t nb_mc_addr
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+int
+hal_del_mcastaddr (hal_hdl_t hdl, void *mc_addr_set,
+ void *mc_addr, uint32_t nb_mc_addr)
+{
+ int ret;
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return -1;
+ }
+
+ ret = inst->ops->mcastaddr (inst, mc_addr_set, mc_addr, nb_mc_addr);
+ /* if set mcast addr failed, we have to manually delete the mac addr from nic. */
+ if (ret < 0)
+ {
+ ret = inst->ops->rmv_mac (inst, mc_addr);
+ }
+ return ret;
+}
+
+/*****************************************************************************
+ Prototype : hal_set_allmulti_mode
+ Description : set all multicast mode
+ Input : hal_hdl_t hdl
+ uint8_t enable
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+void
+hal_set_allmulti_mode (hal_hdl_t hdl, uint8_t enable)
+{
+ netif_inst_t *inst;
+
+ inst = get_netif_inst (hdl);
+
+ if (inst == NULL)
+ {
+ NSHAL_LOGERR ("netif does not exist]inst=%i", HAL_HDL_TO_ID (hdl));
+ return;
+ }
+
+ (void) inst->ops->allmcast (inst, enable);
+}
+
+/*****************************************************************************
+ Prototype : hal_is_nic_exist
+ Description : check nic is exist
+ Input : const char *name
+ Output : None
+ Return Value :
+ Calls :
+ Called By :
+*****************************************************************************/
+uint32_t
+hal_is_nic_exist (const char *name)
+{
+ char script_cmmd[HAL_SCRIPT_LENGTH];
+ char result_buf[HAL_SCRIPT_LENGTH];
+ int len_out;
+ int retval;
+
+ if (!hal_is_script_valid (name))
+ {
+ NSHAL_LOGERR ("nic name is not valid");
+ return 0;
+ }
+
+ retval =
+ hal_snprintf (script_cmmd, sizeof (script_cmmd),
+ "sudo ifconfig -a | grep -w \"%s[ :]\"", name);
+ if (-1 == retval)
+ {
+ NSHAL_LOGERR ("rte_snprintf failed]retval=%d", retval);
+ return 0;
+ }
+
+ len_out = hal_run_script (script_cmmd, result_buf, sizeof (result_buf) - 1);
+ /* buffer not initialized, should take length as decision */
+ if (0 != len_out)
+ {
+ return 1;
+ }
+
+ return 0;
+}
diff --git a/src/framework/hal/hal.h b/src/framework/hal/hal.h
new file mode 100644
index 0000000..2f66914
--- /dev/null
+++ b/src/framework/hal/hal.h
@@ -0,0 +1,182 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _HAL_H_
+#define _HAL_H_
+
+#include <stdint.h>
+#include "hal_api.h"
+#include "nstack_log.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+#define HAL_DRV_MAX 32
+
+#define HAL_IO_REGISTER(name, ops) \
+ static __attribute__((__constructor__)) void __hal_register##name(void) \
+ {\
+ hal_io_adpt_register(ops); \
+ } \
+
+
+#define HAL_MAX_PCI_ADDR_LEN 16
+
+#define HAL_MAX_DRIVER_NAME_LEN 128
+
+#define HAL_MAX_PATH_LEN 4096 //max path length on linux is 4096
+
+#define HAL_SCRIPT_LENGTH 256
+
+#define HAL_HDL_TO_ID(hdl) (hdl.id)
+
+/* IO using DPDK interface */
+typedef struct dpdk_if
+{
+ uint8_t port_id; /**< DPDK port identifier */
+ uint8_t slave_num;
+ uint8_t slave_port[HAL_MAX_SLAVES_PER_BOND];
+
+ uint32_t hw_vlan_filter:1;
+ uint32_t hw_vlan_strip:1;
+ uint32_t rsv30:30;
+
+ uint32_t rx_queue_num;
+ uint32_t rx_ring_size[HAL_ETH_MAX_QUEUE_NUM];
+ struct rte_mempool *rx_pool[HAL_ETH_MAX_QUEUE_NUM];
+
+ uint32_t tx_queue_num;
+ uint32_t tx_ring_size[HAL_ETH_MAX_QUEUE_NUM];
+
+ char pci_addr[HAL_MAX_PCI_ADDR_LEN];
+ char nic_name[HAL_MAX_NIC_NAME_LEN];
+ char driver_name[HAL_MAX_DRIVER_NAME_LEN];
+} dpdk_if_t;
+
+typedef struct netif_inst
+{
+ enum
+ {
+ NETIF_STATE_FREE = 0,
+ NETIF_STATE_ACTIVE
+ } state;
+
+ hal_hdl_t hdl;
+
+ const struct netif_ops *ops; /**< Implementation specific methods */
+
+ union
+ {
+ dpdk_if_t dpdk_if; /**< using DPDK for IO */
+ } data;
+
+} netif_inst_t;
+
+typedef struct netif_ops
+{
+ const char *name;
+ int (*init_global) (int argc, char **argv);
+ int (*init_local) (void);
+ int (*open) (netif_inst_t * inst, const char *name);
+ int (*close) (netif_inst_t * inst);
+ int (*start) (netif_inst_t * inst);
+ int (*stop) (netif_inst_t * inst);
+ int (*bond) (netif_inst_t * inst, const char *bond_name,
+ uint8_t slave_num, netif_inst_t * slave[]);
+ uint32_t (*mtu) (netif_inst_t * inst);
+ int (*macaddr) (netif_inst_t * inst, void *mac_addr);
+ int (*capability) (netif_inst_t * inst, hal_netif_capa_t * info);
+ uint16_t (*recv) (netif_inst_t * inst, uint16_t queue_id,
+ struct common_mem_mbuf ** rx_pkts, uint16_t nb_pkts);
+ uint16_t (*send) (netif_inst_t * inst, uint16_t queue_id,
+ struct common_mem_mbuf ** tx_pkts, uint16_t nb_pkts);
+ uint32_t (*link_status) (netif_inst_t * inst);
+ int (*stats) (netif_inst_t * inst, hal_netif_stats_t * stats);
+ int (*stats_reset) (netif_inst_t * inst);
+ int (*config) (netif_inst_t * inst, hal_netif_config_t * conf);
+ int (*mcastaddr) (netif_inst_t * inst, void *mc_addr_set,
+ void *mc_addr, uint32_t nb_mc_addr);
+ int (*add_mac) (netif_inst_t * inst, void *mc_addr);
+ int (*rmv_mac) (netif_inst_t * inst, void *mc_addr);
+ int (*allmcast) (netif_inst_t * inst, uint8_t enable);
+} netif_ops_t;
+
+extern netif_inst_t netif_tbl[HAL_MAX_NIC_NUM];
+
+static inline netif_inst_t *
+alloc_netif_inst ()
+{
+ int i;
+ netif_inst_t *inst;
+
+ for (i = 0; i < HAL_MAX_NIC_NUM; ++i)
+ {
+ inst = &netif_tbl[i];
+
+ if (NETIF_STATE_FREE == inst->state)
+ {
+ inst->state = NETIF_STATE_ACTIVE;
+
+ inst->hdl.id = i;
+
+ return inst;
+ }
+ }
+
+ return NULL;
+
+}
+
+static inline netif_inst_t *
+get_netif_inst (hal_hdl_t hdl)
+{
+ netif_inst_t *inst;
+
+ if (unlikely (!hal_is_valid (hdl)))
+ {
+ NSHAL_LOGERR ("inst id is not valid]inst=%i, HAL_MAX_NIC_NUM=%d",
+ HAL_HDL_TO_ID (hdl), HAL_MAX_NIC_NUM);
+
+ return NULL;
+ }
+
+ inst = &netif_tbl[HAL_HDL_TO_ID (hdl)];
+
+ if (unlikely ((NETIF_STATE_ACTIVE != inst->state) || (NULL == inst->ops)))
+ {
+ NSHAL_LOGERR ("netif is not active]inst=%i", HAL_HDL_TO_ID (hdl));
+
+ return NULL;
+ }
+
+ return inst;
+}
+
+int hal_snprintf (char *buffer, size_t buflen, const char *format, ...);
+int hal_is_script_valid (const char *cmd);
+int hal_run_script (const char *cmd, char *result_buf, size_t max_result_len);
+void hal_io_adpt_register (const netif_ops_t * ops);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
+
+#endif
diff --git a/src/framework/include/hal_api.h b/src/framework/include/hal_api.h
new file mode 100644
index 0000000..24ed779
--- /dev/null
+++ b/src/framework/include/hal_api.h
@@ -0,0 +1,148 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _HAL_API_H_
+#define _HAL_API_H_
+
+#include "common_mem_mbuf.h"
+#include "common_mem_mempool.h"
+#include "common_func.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+#define HAL_ETH_MAX_QUEUE_NUM 4
+
+#define HAL_ETH_QUEUE_STAT_CNTRS 16
+
+#define HAL_MAX_NIC_NUM 4096
+COMPAT_PROTECT (HAL_MAX_NIC_NUM, 4096);
+
+#define HAL_MAX_SLAVES_PER_BOND 2
+
+#define HAL_MAX_NIC_NAME_LEN 256
+
+/**
+ * TX offload capabilities of a device.
+ */
+#define HAL_ETH_TX_OFFLOAD_IPV4_CKSUM 0x00000002
+#define HAL_ETH_TX_OFFLOAD_UDP_CKSUM 0x00000004
+#define HAL_ETH_TX_OFFLOAD_TCP_CKSUM 0x00000008
+
+/**
+ * Hal Instance Handler
+ */
+typedef struct hal_hdl
+{
+ int id;
+} hal_hdl_t;
+
+/**
+ * Ethernet device capability
+ */
+typedef struct hal_netif_capa
+{
+ uint32_t tx_offload_capa; /**< Device TX offload capabilities. */
+} hal_netif_capa_t;
+
+/**
+ * A structure used to retrieve statistics for an Ethernet port.
+ */
+typedef struct hal_netif_stats
+{
+ uint64_t ipackets; /**< Total no.of packets that are successfully received . */
+ uint64_t opackets; /**< Total no.of packets that are successfully transmitted .*/
+ uint64_t ibytes; /**< Total no.of bytes that are successfully received . */
+ uint64_t obytes; /**< Total no.of bytes that are successfully transmitted . */
+ uint64_t imissed; /**< Total no.of RX packets that are dropped by the HW. */
+ uint64_t ierrors; /**< Total no.of packets that are received as erroneous. */
+ uint64_t oerrors; /**< Total no.of failed transmitted packets. */
+ uint64_t rx_nombuf; /**< Total no.of RX mbuf allocation failures. */
+
+ uint64_t q_ipackets[HAL_ETH_QUEUE_STAT_CNTRS]; /**< Total no.of queue RX packets. */
+ uint64_t q_opackets[HAL_ETH_QUEUE_STAT_CNTRS]; /**< Total no.of queue TX packets. */
+ uint64_t q_ibytes[HAL_ETH_QUEUE_STAT_CNTRS]; /**< Total no.of successfully received queue bytes. */
+ uint64_t q_obytes[HAL_ETH_QUEUE_STAT_CNTRS]; /**< Total no.of successfully transmitted queue bytes. */
+ uint64_t q_errors[HAL_ETH_QUEUE_STAT_CNTRS]; /**< Total no.of queue packets received that are dropped. */
+} hal_netif_stats_t;
+
+/**
+ * Ethernet device config
+ */
+typedef struct hal_netif_config
+{
+ struct
+ {
+ uint32_t hw_vlan_filter:1;
+ uint32_t hw_vlan_strip:1;
+ uint32_t rsv30:30;
+ } bit;
+
+ struct
+ {
+ uint32_t queue_num;
+ uint32_t ring_size[HAL_ETH_MAX_QUEUE_NUM];
+ struct common_mem_mempool *ring_pool[HAL_ETH_MAX_QUEUE_NUM];
+ } rx;
+
+ struct
+ {
+ uint32_t queue_num;
+ uint32_t ring_size[HAL_ETH_MAX_QUEUE_NUM];
+ } tx;
+
+} hal_netif_config_t;
+
+int hal_init_global (int argc, char **argv);
+int hal_init_local ();
+hal_hdl_t hal_create (const char *name, hal_netif_config_t * conf);
+hal_hdl_t hal_bond (const char *bond_name, uint8_t slave_num,
+ hal_hdl_t slave_hdl[]);
+
+#define hal_is_valid(hdl) ((hdl.id >= 0) && (hdl.id < HAL_MAX_NIC_NUM))
+
+#define hal_is_equal(hdl_left, hdl_right) (hdl_left.id == hdl_right.id)
+
+int hal_close (hal_hdl_t hdl);
+int hal_stop (hal_hdl_t hdl);
+uint32_t hal_get_mtu (hal_hdl_t hdl);
+void hal_get_macaddr (hal_hdl_t hdl, void *mac_addr);
+void hal_get_capability (hal_hdl_t hdl, hal_netif_capa_t * info);
+uint16_t hal_recv_packet (hal_hdl_t hdl, uint16_t queue_id,
+ struct common_mem_mbuf **rx_pkts, uint16_t nb_pkts);
+uint16_t hal_send_packet (hal_hdl_t hdl, uint16_t queue_id,
+ struct common_mem_mbuf **tx_pkts, uint16_t nb_pkts);
+uint32_t hal_link_status (hal_hdl_t hdl);
+int hal_stats (hal_hdl_t hdl, hal_netif_stats_t * stats);
+void hal_stats_reset (hal_hdl_t hdl);
+int hal_add_mcastaddr (hal_hdl_t hdl, void *mc_addr_set,
+ void *mc_addr, uint32_t nb_mc_addr);
+int hal_del_mcastaddr (hal_hdl_t hdl, void *mc_addr_set,
+ void *mc_addr, uint32_t nb_mc_addr);
+void hal_set_allmulti_mode (hal_hdl_t hdl, uint8_t enable);
+uint32_t hal_is_nic_exist (const char *name);
+hal_hdl_t hal_get_invalid_hdl ();
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
+
+#endif
diff --git a/src/framework/include/nsfw_fd_timer_api.h b/src/framework/include/nsfw_fd_timer_api.h
new file mode 100644
index 0000000..0b42fe0
--- /dev/null
+++ b/src/framework/include/nsfw_fd_timer_api.h
@@ -0,0 +1,64 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_FD_TIMER_API_H
+#define _NSFW_FD_TIMER_API_H
+
+#include "list.h"
+#include <time.h>
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define NSFW_TIMER_MODULE "nsfw_timer"
+
+typedef struct _nsfw_timer_init_cfg
+{
+ u32 timer_info_size;
+ void *timer_info_pool;
+ struct list_head timer_head;
+ struct list_head exp_timer_head;
+} nsfw_timer_init_cfg;
+
+typedef int (*nsfw_timer_proc_fun) (u32 timer_type, void *argv);
+typedef struct _nsfw_timer_info
+{
+ struct list_head node;
+ nsfw_timer_proc_fun fun;
+ void *argv;
+ struct timespec time_left;
+ u32 timer_type;
+ u8 alloc_flag;
+} nsfw_timer_info;
+
+extern nsfw_timer_info *nsfw_timer_reg_timer (u32 timer_type, void *data,
+ nsfw_timer_proc_fun fun,
+ struct timespec time_left);
+extern void nsfw_timer_rmv_timer (nsfw_timer_info * tm_info);
+
+extern u8 g_hbt_switch;
+extern int nsfw_timer_module_init (void *param);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _NSFW_FD_TIMER_API_H */
diff --git a/src/framework/include/nsfw_init.h b/src/framework/include/nsfw_init.h
new file mode 100644
index 0000000..def97b2
--- /dev/null
+++ b/src/framework/include/nsfw_init.h
@@ -0,0 +1,148 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _FW_INIT_H
+#define _FW_INIT_H
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define NSFW_INIT_PRIORITY_ROOT 101
+#define NSFW_INIT_PRIORITY_BASE 102
+#define NSFW_INIT_PRIORITY_INITFN 103
+
+#define NSFW_INIT_MODULE_PRIORITY_BASE 1
+#define NSFW_INIT_MODULE_PRIORITY(x) (NSFW_INIT_MODULE_PRIORITY_BASE + x)
+
+#define NSFW_SET_INSTANCE_VALUE(_attr, _inst, _value) \
+ nsfw_module_set_instance_##_attr(_inst, _value)
+
+#define NSFW_INIT_CRAETE_LOCAL_INSTANCE() \
+ if (!nsfwLocalInitInst) {\
+ nsfwLocalInitInst = nsfw_module_create_instance(); \
+ nsfw_module_add_instance(nsfwLocalInitInst);\
+ }
+
+#define _NSFW_MODULE_ATTRIBUTE_DEFINE_SURFIX(_attr, _value, _priority, _surfix) \
+ static __attribute__((__constructor__(_priority))) void nsfw_module_attribute_##_attr##_surfix(void){\
+ NSFW_INIT_CRAETE_LOCAL_INSTANCE(); \
+ NSFW_SET_INSTANCE_VALUE(_attr, nsfwLocalInitInst, _value);\
+ } \
+
+#define NSFW_MODULE_ATTRIBUTE_DEFINE_SURFIX(_attr, _value, _priority, _surfix) \
+ _NSFW_MODULE_ATTRIBUTE_DEFINE_SURFIX(_attr, _value, _priority, _surfix)
+
+#define NSFW_MODULE_ATTRIBUTE_DEFINE_UNIQUE(_attr, _value, _priority) \
+ NSFW_MODULE_ATTRIBUTE_DEFINE_SURFIX(_attr, _value, _priority, __LINE__)
+
+#define NSFW_MODULE_ATTRIBUTE_DEFINE(_attr, _value, _priority) \
+ NSFW_MODULE_ATTRIBUTE_DEFINE_UNIQUE(_attr, _value, _priority)
+
+#define NSFW_MODULE_NAME(_name) \
+ NSFW_MODULE_ATTRIBUTE_DEFINE(name, _name, NSFW_INIT_PRIORITY_BASE)
+
+#define NSFW_MODULE_FATHER(_father) \
+ NSFW_MODULE_ATTRIBUTE_DEFINE(father, _father, NSFW_INIT_PRIORITY_BASE)
+
+#define NSFW_MODULE_PRIORITY(_priority) \
+ NSFW_MODULE_ATTRIBUTE_DEFINE(priority, _priority, NSFW_INIT_PRIORITY_BASE)
+
+#define NSFW_MODULE_DEPENDS(_depends) \
+ NSFW_MODULE_ATTRIBUTE_DEFINE(depends, _depends, NSFW_INIT_PRIORITY_BASE)
+
+#define NSFW_MODULE_INIT(_initfn) \
+ NSFW_MODULE_ATTRIBUTE_DEFINE(initfn, _initfn, NSFW_INIT_PRIORITY_INITFN)
+
+#define NSFW_MAX_STRING_LENGTH 128
+
+#define NSFW_DEPENDS_SIZE 8
+typedef struct _nsfw_module_depends
+{
+ char name[NSFW_MAX_STRING_LENGTH];
+ int isReady;
+ struct _nsfw_module_depends *next; /* It is a list, not just only one */
+} nsfw_module_depends_t;
+
+typedef enum
+{
+ NSFW_INST_STAT_CHECKING, /* Not check yet */
+ NSFW_INST_STAT_DEPENDING, /* Blocked, waiting for other module instances */
+ NSFW_INST_STAT_DONE, /* Check done */
+ NSFW_INST_STAT_FAIL /* Check Fail */
+} nsfw_module_instance_stat_t;
+
+typedef int (*nsfw_module_init_fn) (void *);
+
+typedef struct _nsfw_module_instance
+{
+ nsfw_module_init_fn fnInit;
+ char name[NSFW_MAX_STRING_LENGTH];
+ char fatherName[NSFW_MAX_STRING_LENGTH];
+ int priority;
+ nsfw_module_depends_t *depends;
+ nsfw_module_instance_stat_t stat;
+ void *param;
+ struct _nsfw_module_instance *next;
+ struct _nsfw_module_instance *child;
+ struct _nsfw_module_instance *father;
+} nsfw_module_instance_t;
+
+static nsfw_module_instance_t *nsfwLocalInitInst __attribute__ ((unused)) =
+ (void *) 0;
+
+extern nsfw_module_instance_t *nsfw_module_create_instance ();
+extern nsfw_module_instance_t *nsfw_module_getModuleByName (char *);
+extern void nsfw_module_add_instance (nsfw_module_instance_t * inst);
+extern void nsfw_module_del_instance (nsfw_module_instance_t * inst);
+extern void nsfw_module_set_instance_name (nsfw_module_instance_t * inst,
+ char *name);
+extern void nsfw_module_set_instance_father (nsfw_module_instance_t * inst,
+ char *father);
+extern void nsfw_module_set_instance_priority (nsfw_module_instance_t *
+ inst, int priority);
+extern void nsfw_module_set_instance_initfn (nsfw_module_instance_t * inst,
+ nsfw_module_init_fn fn);
+extern void nsfw_module_set_instance_depends (nsfw_module_instance_t * inst,
+ char *name);
+
+/**
+ * @Function nstack_framework_init
+ * @Description This function will do framework initial work, it will involk all initial functions
+ * registed using macro NSFW_MODULE_INIT before
+ * @param none
+ * @return 0 on success, -1 on error
+ */
+extern int nstack_framework_init (void);
+
+/**
+ * @Function nstack_framework_setModuleParam
+ * @Description This function set parameter of module initial function parameter
+ * @param module - name of module
+ * @param param - parameter to set
+ * @return 0 on success, -1 on error
+ */
+extern int nstack_framework_setModuleParam (char *module, void *param);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _FW_INIT_H */
diff --git a/src/framework/include/nsfw_maintain_api.h b/src/framework/include/nsfw_maintain_api.h
new file mode 100644
index 0000000..74cedf6
--- /dev/null
+++ b/src/framework/include/nsfw_maintain_api.h
@@ -0,0 +1,320 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_MEM_STAT_API_H
+#define _NSFW_MEM_STAT_API_H
+
+#include "types.h"
+#include "nsfw_mgr_com_api.h"
+#include "compiling_check.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+/*################MEM_STAT######################*/
+#define NSFW_MEM_MODULE_LEN 32
+#define NSFW_MEM_NAME_LEN 64
+
+#define OMC_PROC_MM "omc_proc_maintain"
+
+#define MEM_STAT(module, mem_name, mem_type, mem_size)\
+ nsfw_mem_stat(module, mem_name, mem_type, mem_size)
+
+extern void nsfw_mem_stat (char *module, char *mem_name, u8 mem_type,
+ u32 mem_size);
+extern void nsfw_mem_stat_print ();
+/*##############################################*/
+
+/*################SRV_CTRL######################*/
+typedef enum _nsfw_srv_ctrl_state
+{
+ NSFW_SRV_CTRL_RESUME = 1,
+ NSFW_SRV_CTRL_SUSPEND = 2
+} nsfw_srv_ctrl_state;
+
+typedef struct _nsfw_srv_ctrl_msg
+{
+ nsfw_srv_ctrl_state srv_state;
+ u16 rsp_code;
+} nsfw_srv_ctrl_msg;
+extern u8 nsfw_srv_ctrl_send (nsfw_srv_ctrl_state state, u8 rsp_flag);
+/*#############################################*/
+
+/*#################RES_MGR######################*/
+#define NSFW_RES_MGR_MODULE "nsfw_res_mgr"
+
+typedef enum _nsfw_res_scan_type
+{
+ NSFW_RES_SCAN_ARRAY = 0,
+ NSFW_RES_SCAN_SPOOL,
+ NSFW_RES_SCAN_MBUF,
+ NSFW_RES_SCAN_MAX
+} nsfw_res_scan_type;
+
+typedef int (*nsfw_res_free_fun) (void *pdata);
+
+typedef struct _nsfw_res_scn_cfg
+{
+ u8 type; /*nsfw_res_scan_type */
+ u8 force_free_percent; /*if the resource free percent below this vlaue, begin to force free the element */
+ u16 force_free_chk_num; /*if the check count beyone this vlaue, call free fun release this element */
+ u16 alloc_speed_factor; /*alloc fast with higher value */
+
+ u32 num_per_cyc; /*define the element number in one scan cycle process and increase chk_count of every element */
+ u32 total_num; /*total number of elements */
+ u32 elm_size; /*element size */
+ u32 res_mem_offset; /*the nsfw_res offset from the element start */
+
+ void *data; /*the array addr or spool addr */
+ void *mgr_ring;
+
+ nsfw_res_free_fun free_fun;
+} nsfw_res_scn_cfg;
+
+typedef struct _nsfw_res_mgr_item_cfg
+{
+ nsfw_res_scn_cfg scn_cfg;
+ u32 cons_head;
+ u32 prod_head;
+ u32 free_percent;
+ u32 last_scn_idx;
+ u64 force_count;
+} nsfw_res_mgr_item_cfg;
+
+#define NSFW_MAX_RES_SCAN_COUNT 256
+
+extern u8 nsfw_res_mgr_reg (nsfw_res_scn_cfg * cfg);
+extern i32 nsfw_proc_start_with_lock (u8 proc_type);
+/*#############################################*/
+
+typedef enum _nsfw_exit_code
+{
+ NSFW_EXIT_SUCCESS = 0,
+ NSFW_EXIT_FAILED = 1,
+ NSFW_EXIT_DST_ERROR = 2,
+ NSFW_EXIT_TIME_OUT = 3,
+
+ NSFW_EXIT_MAX_COM_ERR = 31,
+} nsfw_exit_code;
+
+/*#############################################*/
+
+/*#################SOFT_PARAM##################*/
+#define NSFW_SOFT_PARAM_MODULE "nsfw_soft_param"
+
+typedef struct _nsfw_soft_param_msg
+{
+ u32 param_name;
+ u32 rsp_code;
+ u8 param_value[NSFW_MGR_MSG_BODY_LEN - sizeof (u32) - sizeof (u32)];
+}
+nsfw_soft_param_msg;
+
+typedef enum _nsfw_soft_param
+{
+ NSFW_DBG_MODE_PARAM = 1,
+ NSFW_HBT_TIMER = 2,
+ NSFW_HBT_COUNT_PARAM = 3,
+ NSFW_APP_EXIT_TIMER = 4,
+ NSFW_SRV_RESTORE_TIMER = 5,
+ NSFW_APP_RESEND_TIMER = 6,
+ NSFW_APP_SEND_PER_TIME = 7,
+
+ NSFW_MAX_SOFT_PARAM = 1024
+} nsfw_soft_param;
+
+typedef int (*nsfw_set_soft_fun) (u32 param, char *buf, u32 buf_len);
+extern u8 nsfw_soft_param_reg_fun (u32 param_name, nsfw_set_soft_fun fun);
+extern u8 nsfw_soft_param_reg_int (u32 param_name, u32 size, u32 min,
+ u32 max, u64 * data);
+
+extern void nsfw_set_soft_para (fw_poc_type proc_type, u32 para_name,
+ void *value, u32 size);
+
+extern int nsfw_isdigitstr (const char *str);
+#define NSFW_REG_SOFT_INT(_param,_data,_min, _max) nsfw_soft_param_reg_int(_param,sizeof(_data),_min,_max,(u64*)&_data)
+/*#############################################*/
+
+/*#################LOG_CONFIG##################*/
+#define NSFW_LOG_CFG_MODULE "nsfw_log_cfg"
+
+#define NSFW_MODULE_NAME_LEN 20
+#define NSFW_LOG_LEVEL_LEN 10
+#define NSFW_LOG_VALUE_LEN 256
+
+typedef struct _nsfw_set_log_msg
+{
+ u16 rsp_code;
+ char module[NSFW_MODULE_NAME_LEN];
+ char log_level[NSFW_LOG_VALUE_LEN];
+} nsfw_set_log_msg;
+/*#############################################*/
+
+/*################## DFX ######################*/
+#define MAX_DFX_QRY_RES_LEN 28
+
+#define SPL_DFX_RES_ALL "all"
+#define SPL_DFX_RES_QUEUE "queue"
+#define SPL_DFX_RES_CONN "conn"
+#define SPL_DFX_RES_L2TO4 "l2to4"
+#define SPL_DFX_RES_UNMATCH "version"
+#define SPL_DFX_RES_SOCKT_CB "socketcb"
+#define SPL_DFX_RES_COMM_MEMPOOL "mbufpool"
+#define SPL_DFX_RES_PCBLIST "pcblist"
+#define SPL_DFX_RES_ARPLIST "arplist"
+
+typedef enum
+{
+ DFX_ACTION_SNAPSHOT,
+ DFX_ACTION_RST_STATS,
+ DFX_ACTION_SWITCH,
+ DFX_ACTION_MAX
+} dfx_module_action;
+
+typedef struct _nsfw_dfx_qry_msg
+{
+ dfx_module_action action;
+ char resource[MAX_DFX_QRY_RES_LEN];
+ char flag; //for snapshot print "all"
+} nsfw_dfx_qry_msg;
+
+typedef enum
+{
+ QUERY_ACTION_GET,
+ QUERY_ACTION_MAX
+} query_action;
+
+typedef struct _nsfw_qry_msg
+{
+ query_action action;
+ char resource[MAX_DFX_QRY_RES_LEN];
+} nsfw_get_qry_msg;
+
+/*##################DFX#########################*/
+
+/*#################for tcpdump#####################*/
+
+#ifndef nstack_min
+#define nstack_min(a, b) (a) < (b) ? (a) : (b)
+#endif
+
+#define GET_CUR_TIME(ptime) \
+ (void)clock_gettime(CLOCK_MONOTONIC, ptime);
+
+#define TCPDUMP_MODULE "tcpdump_tool"
+
+#define DUMP_MSG_NUM (64 * 1024)
+COMPAT_PROTECT (DUMP_MSG_NUM, 64 * 1024);
+#define DUMP_MSG_SIZE 128 // can not be less than 14
+COMPAT_PROTECT (DUMP_MSG_SIZE, 128);
+
+#define DEFAULT_DUMP_TIME 600
+#define MAX_DUMP_TIME 86400
+#define MIN_DUMP_TIME 1
+
+#define MAX_DUMP_TASK 16
+#define DUMP_HBT_INTERVAL 2
+#define DUMP_HBT_CHK_INTERVAL 4
+#define DUMP_TASK_HBT_TIME_OUT 30
+
+#define DUMP_SHMEM_RIGN_NAME "tcpdump_ring"
+#define DUMP_SHMEM_POOL_NAME "tcpdump_pool"
+
+enum L2_PROTOCOL
+{
+ PROTOCOL_IP = 0x0800,
+ PROTOCOL_ARP = 0x0806,
+ PROTOCOL_RARP = 0x8035,
+ PROTOCOL_OAM_LACP = 0x8809,
+ INVALID_L2_PROTOCOL = 0xFFFF
+};
+
+enum L3_PROTOCOL
+{
+ PROTOCOL_ICMP = 1,
+ PROTOCOL_TCP = 6,
+ PROTOCOL_UDP = 17,
+ INVALID_L3_PROTOCOL = 0xFF
+};
+
+enum DUMP_MSG_DIRECTION
+{
+ DUMP_SEND = 1,
+ DUMP_RECV = 2,
+ DUMP_SEND_RECV = 3
+};
+
+enum DUMP_MSG_TYPE
+{
+ START_DUMP_REQ,
+ STOP_DUMP_REQ,
+ TOOL_COM_HBT_REQ,
+
+ DUMP_MSG_TYPE_RSP = 0x00010000,
+
+ START_DUMP_RSP = START_DUMP_REQ + DUMP_MSG_TYPE_RSP,
+ STOP_DUMP_RSP = STOP_DUMP_REQ + DUMP_MSG_TYPE_RSP,
+
+ DUMP_MSG_TYPE_INVALID
+};
+
+typedef struct _nsfw_tool_hbt
+{
+ u32 seq;
+ i16 task_id;
+} nsfw_tool_hbt;
+
+typedef struct _nsfw_tool_dump_msg
+{
+ u16 op_type;
+ i16 task_id;
+ u32 task_keep_time;
+} nsfw_tool_dump_msg;
+
+typedef struct _dump_msg_info
+{
+ u32 len;
+ u16 direction; // 1:SEND, 2:RECV
+ u32 dump_sec;
+ u32 dump_usec;
+ nsfw_res res_chk;
+ char buf[1];
+} dump_msg_info;
+
+typedef struct _dump_timer_info
+{
+ u32 seq;
+ i16 task_id;
+ void *interval;
+ void *ptimer;
+} dump_timer_info;
+
+extern void ntcpdump_loop (void *buf, u32 buf_len, u16 direction,
+ void *eth_addr);
+extern void ntcpdump (void *buf, u32 buf_len, u16 direction);
+
+/*##############for tcpdump######################*/
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _NSFW_MEM_STAT_API_H */
diff --git a/src/framework/include/nsfw_mem_api.h b/src/framework/include/nsfw_mem_api.h
new file mode 100644
index 0000000..ec78692
--- /dev/null
+++ b/src/framework/include/nsfw_mem_api.h
@@ -0,0 +1,546 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_MEM_API_H
+#define _NSFW_MEM_API_H
+#include <stdint.h>
+#include <sys/types.h>
+
+#include "types.h"
+#include "nsfw_mgr_com_api.h"
+#include "nstack_log.h"
+
+#define NSFW_MEM_MGR_MODULE "nsfw_mem_mgr"
+
+/*
+ *the max len of memory name is 32bytes, but app just can use max 22bytes, left 10bytes to memory manager module
+ */
+#define NSFW_MEM_NAME_LENTH (32)
+#define NSFW_MEM_APPNAME_LENTH (22)
+
+#define NSFW_SOCKET_ANY (-1)
+#define NSFW_MEM_OK (0)
+#define NSFW_MEM_ERR (-1)
+
+/*
+ *type of memory:
+ *NSFW_SHMEM:shared memory
+ *NSFW_NSHMEM:allocated by calling malloc
+ */
+typedef enum
+{
+ NSFW_SHMEM,
+ NSFW_NSHMEM,
+ NSFW_MEM_TYPEMAX,
+} nsfw_mem_type;
+
+/*type of ring operation*/
+typedef enum
+{
+ NSFW_MRING_SPSC, /*sigle producer sigle consumer ring */
+ NSFW_MRING_MPSC, /*multi producer sigle consumer ring */
+ NSFW_MRING_SPMC, /*sigle producer multi consumer ring */
+ NSFW_MRING_MPMC, /*multi producer multi consumer ring */
+ NSFW_MRING_SPSC_ST, /*single producer single consumer and belong to one thread ring */
+ NSFW_MPOOL_TYPEMAX,
+} nsfw_mpool_type;
+
+typedef void *mpool_handle;
+typedef void *mzone_handle;
+typedef void *mbuf_handle;
+typedef void *mring_handle;
+
+/*initial of param*/
+typedef struct
+{
+ i32 iargsnum;
+ i8 **pargs;
+ fw_poc_type enflag; /*app, nStackMain, Master */
+} nsfw_mem_para;
+
+typedef struct
+{
+ nsfw_mem_type entype;
+ fw_poc_type enowner; /*notes: 1. when calling any shared memory create inferface, the name of memory end with _0 created by nStackMain,
+ * end with null created by nStackMaster, and end with _<pid> created by other.
+ * 2. pname->enowner is available only when call look up shared memory.
+ * 3. if the roles of process is NSFW_PROC_MASTER but the memory was created by others, or pname->enowner is NSFW_PROC_NULL,
+ * the name must be full name.
+ * for examles if the memory was created by nStackMain and pname->enowner is NSFW_PROC_NULL,
+ * must add '_0' at the end of name, if the memory was created by app and the role of process is NSFW_PROC_MASTER, must add
+ * _(pid) at the end of name, nstack_123.
+ */
+ i8 aname[NSFW_MEM_NAME_LENTH]; /*the lenth of name must be less than NSFW_MEM_APPNAME_LENTH. */
+} nsfw_mem_name;
+
+typedef struct
+{
+ nsfw_mem_name stname;
+ size_t lenth;
+ i32 isocket_id;
+ i32 ireserv;
+} nsfw_mem_zone;
+
+typedef struct
+{
+ nsfw_mem_name stname;
+ unsigned usnum; /*the really created mbfpool num is (num+1) power of 2 */
+ unsigned uscash_size;
+ unsigned uspriv_size;
+ unsigned usdata_room;
+ i32 isocket_id;
+ nsfw_mpool_type enmptype;
+} nsfw_mem_mbfpool;
+
+typedef struct
+{
+ nsfw_mem_name stname;
+ u32 usnum; /*the really created sppool num is (num+1) power of 2 */
+ u32 useltsize;
+ i32 isocket_id;
+ nsfw_mpool_type enmptype;
+} nsfw_mem_sppool;
+
+typedef struct
+{
+ nsfw_mem_name stname;
+ u32 usnum; /*the really created ring num is (num+1) power of 2 */
+ i32 isocket_id;
+ nsfw_mpool_type enmptype;
+} nsfw_mem_mring;
+
+typedef enum
+{
+ NSFW_MEM_ALLOC_SUCC = 1,
+ NSFW_MEM_ALLOC_FAIL = 2,
+} nsfw_mem_alloc_state;
+
+typedef enum
+{
+ NSFW_MEM_MZONE,
+ NSFW_MEM_MBUF,
+ NSFW_MEM_SPOOL,
+ NSFW_MEM_RING
+} nsfw_mem_struct_type;
+
+typedef enum
+{
+ NSFW_RESERV_REQ_MSG,
+ NSFW_RESERV_ACK_MSG,
+ NSFW_MBUF_REQ_MSG,
+ NSFW_MBUF_ACK_MSG,
+ NSFW_SPPOOL_REQ_MSG,
+ NSFW_SPPOOL_ACK_MSG,
+ NSFW_RING_REQ_MSG,
+ NSFW_RING_ACK_MSG,
+ NSFW_RELEASE_REQ_MSG,
+ NSFW_RELEASE_ACK_MSG,
+ NSFW_MEM_LOOKUP_REQ_MSG,
+ NSFW_MEM_LOOKUP_ACK_MSG,
+ NSFW_MEM_MAX_MSG
+} nsfw_remote_msg;
+
+typedef struct __nsfw_shmem_msg_head
+{
+ unsigned usmsg_type;
+ unsigned uslenth;
+ i32 aidata[0];
+} nsfw_shmem_msg_head;
+
+typedef struct __nsfw_shmem_ack
+{
+ void *pbase_addr;
+ u16 usseq;
+ i8 cstate;
+ i8 creserv;
+ i32 ireserv;
+} nsfw_shmem_ack;
+
+typedef struct __nsfw_shmem_reserv_req
+{
+ i8 aname[NSFW_MEM_NAME_LENTH];
+ u16 usseq;
+ u16 usreserv;
+ i32 isocket_id;
+ size_t lenth;
+ i32 ireserv;
+} nsfw_shmem_reserv_req;
+
+typedef struct __nsfw_shmem_mbuf_req
+{
+ i8 aname[NSFW_MEM_NAME_LENTH];
+ u16 usseq;
+ u16 enmptype;
+ unsigned usnum;
+ unsigned uscash_size;
+ unsigned uspriv_size;
+ unsigned usdata_room;
+ i32 isocket_id;
+ i32 ireserv;
+} nsfw_shmem_mbuf_req;
+
+typedef struct __nsfw_shmem_sppool_req
+{
+ i8 aname[NSFW_MEM_NAME_LENTH];
+ u16 usseq;
+ u16 enmptype;
+ u32 usnum;
+ u32 useltsize;
+ i32 isocket_id;
+ i32 ireserv;
+} nsfw_shmem_sppool_req;
+
+typedef struct __nsfw_shmem_ring_req
+{
+ i8 aname[NSFW_MEM_NAME_LENTH];
+ u16 usseq;
+ u16 enmptype;
+ u32 usnum;
+ i32 isocket_id;
+ i32 ireserv;
+} nsfw_shmem_ring_req;
+
+typedef struct __nsfw_shmem_free_req
+{
+ i8 aname[NSFW_MEM_NAME_LENTH];
+ u16 usseq;
+ u16 ustype; /*structure of memory(memzone,mbuf,mpool,ring) */
+ i32 ireserv;
+} nsfw_shmem_free_req;
+
+typedef struct __nsfw_shmem_lookup_req
+{
+ i8 aname[NSFW_MEM_NAME_LENTH];
+ u16 usseq;
+ u16 ustype; /*structure of memory(memzone,mbuf,mpool,ring) */
+ i32 ireserv;
+} nsfw_shmem_lookup_req;
+
+typedef int (*nsfw_mem_ring_enqueue_fun) (mring_handle ring, void *box);
+typedef int (*nsfw_mem_ring_dequeue_fun) (mring_handle ring, void **box);
+typedef int (*nsfw_mem_ring_dequeuev_fun) (mring_handle ring, void **box,
+ unsigned int n);
+
+typedef struct
+{
+ nsfw_mem_ring_enqueue_fun ring_ops_enqueue;
+ nsfw_mem_ring_dequeue_fun ring_ops_dequeue;
+ nsfw_mem_ring_dequeuev_fun ring_ops_dequeuev;
+} nsfw_ring_ops;
+
+/*
+ * memory module init
+ * para:point to nstak_fwmem_para
+ */
+i32 nsfw_mem_init (void *para);
+
+/*
+ * create a block memory with name
+ * nsfw_mem_zone::stname
+ * nsfw_mem_zone::isize
+ * note: 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ */
+mzone_handle nsfw_mem_zone_create (nsfw_mem_zone * pinfo);
+
+/*
+ *create some memory blocks
+ * note: 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ */
+i32 nsfw_mem_zone_createv (nsfw_mem_zone * pmeminfo, i32 inum,
+ mzone_handle * paddr_array, i32 iarray_num);
+
+/*
+ *look up a memory
+ * note: 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ * 2. if the memory is shared, pname->enowner indicate that who create this memory,
+ * note:
+ * 1. when calling any shared memory create inferface, the name of memory end with _0 created by nStackMain,
+ * end with none created by nStackMaster, and end with _<pid> created by other.
+ * 2. pname->enowner is available only when call look up shared memory.
+ * 3. if the roles of process is NSFW_PROC_MASTER but the memory was created by others, or pname->enowner is NSFW_PROC_NULL,
+ * the name must be full name.
+ * for examles if the memory was created by nStackMain and pname->enowner is NSFW_PROC_NULL,
+ * must add '_0' at the end of name, if the memory was created by app and the role of process is NSFW_PROC_MASTER, must add
+ * _(pid) at the end of name, nstack_123.
+ */
+mzone_handle nsfw_mem_zone_lookup (nsfw_mem_name * pname);
+
+/*release a memory*/
+i32 nsfw_mem_zone_release (nsfw_mem_name * pname);
+
+/*
+ *create a mbuf pool
+ */
+mpool_handle nsfw_mem_mbfmp_create (nsfw_mem_mbfpool * pbufinfo);
+
+/*
+ *create some mbuf pools
+ * note: 1. the name of lenth must be less than NSFW_MEM_APPNAME_LENTH.
+ */
+i32 nsfw_mem_mbfmp_createv (nsfw_mem_mbfpool * pmbfname, i32 inum,
+ mpool_handle * phandle_array, i32 iarray_num);
+
+/*
+ *alloc a mbuf from mbuf pool
+ */
+mbuf_handle nsfw_mem_mbf_alloc (mpool_handle mhandle, nsfw_mem_type entype);
+
+/*
+ *put a mbuf backintp mbuf pool
+ */
+i32 nsfw_mem_mbf_free (mbuf_handle mhandle, nsfw_mem_type entype);
+
+/*
+ *look up mbuf mpool
+ * note: 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ * 2. if the memory is shared, pname->enowner indicate that who create this memory.
+ * note:
+ * 1. when calling any shared memory create inferface, the name of memory end with _0 created by nStackMain,
+ * end with none created by nStackMaster, and end with _<pid> created by other.
+ * 2. pname->enowner is available only when call look up shared memory.
+ * 3. if the roles of process is NSFW_PROC_MASTER but the memory was created by others, or pname->enowner is NSFW_PROC_NULL,
+ * the name must be full name.
+ * for examles if the memory was created by nStackMain and pname->enowner is NSFW_PROC_NULL,
+ * must add '_0' at the end of name, if the memory was created by app and the role of process is NSFW_PROC_MASTER, must add
+ * _(pid) at the end of name, nstack_123.
+ */
+mpool_handle nsfw_mem_mbfmp_lookup (nsfw_mem_name * pmbfname);
+
+/*
+ *release mbuf pool
+ * note: 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ */
+i32 nsfw_mem_mbfmp_release (nsfw_mem_name * pname);
+
+/*
+ *create a simple pool
+ *note: 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ */
+mring_handle nsfw_mem_sp_create (nsfw_mem_sppool * pmpinfo);
+
+/*
+ *create some simple pools one time
+ *note: 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ */
+i32 nsfw_mem_sp_createv (nsfw_mem_sppool * pmpinfo, i32 inum,
+ mring_handle * pringhandle_array, i32 iarray_num);
+
+/*
+ *create a simple pool with many rings
+ *note: 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ */
+i32 nsfw_mem_sp_ring_create (nsfw_mem_mring * prpoolinfo,
+ mring_handle * pringhandle_array, i32 iringnum);
+
+/*
+ *release a simple mempool
+ *note: 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ */
+i32 nsfw_mem_sp_release (nsfw_mem_name * pname);
+
+/*
+ *look up a simpile ring
+ * note: 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ * 2. if the memory is shared, pname->enowner indicate that who create this memory,
+ * note:
+ * 1. when calling any shared memory create inferface, the name of memory end with _0 created by nStackMain,
+ * end with none created by nStackMaster, and end with _<pid> created by other.
+ * 2. pname->enowner is available only when call look up shared memory.
+ * 3. if the roles of process is NSFW_PROC_MASTER but the memory was created by others, or pname->enowner is NSFW_PROC_NULL,
+ * the name must be full name.
+ * for examles if the memory was created by nStackMain and pname->enowner is NSFW_PROC_NULL,
+ * must add '_0' at the end of name, if the memory was created by app and the role of process is NSFW_PROC_MASTER, must add
+ * _(pid) at the end of name, nstack_123.
+ */
+mring_handle nsfw_mem_sp_lookup (nsfw_mem_name * pname);
+
+/*
+ *create a ring
+ *note: 1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ * 2. shared memory ring (NSFW_SHMEM) just can put a pointor into the queue, the queue also point to a shared block memory.
+ * no shared memory ring(NSFW_NSHMEM) is other wise.
+ */
+mring_handle nsfw_mem_ring_create (nsfw_mem_mring * pringinfo);
+
+/*
+ *look up a ring by name
+ * note:1. the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ * 2. if the memory is shared, pname->enowner indicate that who create this memory,
+ * note:
+ * 1. when calling any shared memory create inferface, the name of memory end with _0 created by nStackMain,
+ * end with none created by nStackMaster, and end with _<pid> created by other.
+ * 2. pname->enowner is available only when call look up shared memory.
+ * 3. if the roles of process is NSFW_PROC_MASTER but the memory was created by others, or pname->enowner is NSFW_PROC_NULL,
+ * the name must be full name.
+ * for examles if the memory was created by nStackMain and pname->enowner is NSFW_PROC_NULL,
+ * must add '_0' at the end of name, if the memory was created by app and the role of process is NSFW_PROC_MASTER, must add
+ * _(pid) at the end of name, nstack_123.
+ */
+mring_handle nsfw_mem_ring_lookup (nsfw_mem_name * pname);
+
+/*
+ * reset the number of producer and consumer, also, the state of ring reset to empty
+ * notes: must be called before doing any operations base on the ring
+ */
+void nsfw_mem_ring_reset (mring_handle mhandle, nsfw_mpool_type entype);
+
+extern nsfw_ring_ops g_ring_ops_arry[NSFW_MEM_TYPEMAX][NSFW_MPOOL_TYPEMAX];
+
+/*****************************************************************************
+* Prototype : nsfw_mem_ring_dequeue
+* Description : get a member from a ring
+* note : if NSFW_SHMEM ring, pdata returned alread a local address
+* Input : mring_handle mhandle
+* void** pdata
+* Output : None
+* Return Value : the num of elment get from the queue, =0: get null, <0: err happen, >0: return num.
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+static inline i32
+nsfw_mem_ring_dequeue (mring_handle mhandle, void **pdata)
+{
+ if (NULL == mhandle || *((u8 *) mhandle) >= NSFW_MEM_TYPEMAX
+ || *((u8 *) mhandle + 1) >= NSFW_MPOOL_TYPEMAX)
+ {
+ NSCOMM_LOGERR ("input para error] mhandle=%p", mhandle);
+ return -1;
+ }
+
+ return
+ g_ring_ops_arry[*((u8 *) mhandle)][*((u8 *) mhandle + 1)].ring_ops_dequeue
+ (mhandle, pdata);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_ring_dequeuev
+* Description : get some members from a ring
+* note : if NSFW_SHMEM ring, pdata returned alread a local address
+* Input : mring_handle mhandle
+* void** pdata
+* unsigned inum
+* Output : None
+* Return Value : the num of elment get from the queue, =0: get null, <0: err happen, >0: return num.
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+static inline i32
+nsfw_mem_ring_dequeuev (mring_handle mhandle, void **pdata, unsigned int inum)
+{
+ if (NULL == mhandle || *((u8 *) mhandle) >= NSFW_MEM_TYPEMAX
+ || *((u8 *) mhandle + 1) >= NSFW_MPOOL_TYPEMAX)
+ {
+ NSCOMM_LOGERR ("input para error] mhandle=%p", mhandle);
+ return -1;
+ }
+
+ return
+ g_ring_ops_arry[*((u8 *) mhandle)][*
+ ((u8 *) mhandle +
+ 1)].ring_ops_dequeuev (mhandle, pdata,
+ inum);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_ring_enqueue
+* Description : put a member back into a ring
+* note : pdata must point to a shared block memory when put into the NSFW_SHMEM type memory ring, and the
+* value of pdata must be local address
+* Input : mring_handle mhandle
+* void* pdata
+* Output : None
+* Return Value : the num of elment put into the queue, =0: put null, <0: err happen, >0: return num.
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+static inline i32
+nsfw_mem_ring_enqueue (mring_handle mhandle, void *pdata)
+{
+ if (NULL == mhandle || *((u8 *) mhandle) >= NSFW_MEM_TYPEMAX
+ || *((u8 *) mhandle + 1) >= NSFW_MPOOL_TYPEMAX)
+ {
+ NSCOMM_LOGERR ("input para error] mhandle=%p", mhandle);
+ return -1;
+ }
+
+ return
+ g_ring_ops_arry[*((u8 *) mhandle)][*((u8 *) mhandle + 1)].ring_ops_enqueue
+ (mhandle, pdata);
+}
+
+/*
+ *get the free number of ring
+ */
+u32 nsfw_mem_ring_free_count (mring_handle mhandle);
+
+/*
+ *get the in using number of ring
+ */
+u32 nsfw_mem_ring_using_count (mring_handle mhandle);
+
+/*
+ *get size of ring
+ */
+u32 nsfw_mem_ring_size (mring_handle mhandle);
+
+/*
+ *release a ring memory
+ *note: the lenth of name must be less than NSFW_MEM_APPNAME_LENTH.
+ */
+i32 nsfw_mem_ring_release (nsfw_mem_name * pname);
+
+/*
+ *statics mbufpool, sppool, ring mem size
+ *return: <=0, err happen, >0 mem size
+ * NSFW_MEM_MZONE: not surport because you already know the lenth when create
+ */
+ssize_t nsfw_mem_get_len (void *handle, nsfw_mem_struct_type type);
+
+/*
+ *recycle mbuf
+ *
+ */
+i32 nsfw_mem_mbuf_pool_recycle (mpool_handle handle);
+
+typedef int (*nsfw_mem_item_fun) (void *data, void *argv);
+
+i32 nsfw_mem_sp_iterator (mpool_handle handle, u32 start, u32 end,
+ nsfw_mem_item_fun fun, void *argv);
+i32 nsfw_mem_mbuf_iterator (mpool_handle handle, u32 start, u32 end,
+ nsfw_mem_item_fun fun, void *argv);
+
+/*****************************************************************************
+* Prototype : nsfw_mem_dfx_ring_print
+* Description : print ring info
+* Input : mring_handle mhandle
+* char *pbuf
+* int lenth
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+i32 nsfw_mem_dfx_ring_print (mring_handle mhandle, char *pbuf, int lenth);
+
+#ifdef SYS_MEM_RES_STAT
+u32 nsfw_mem_mbfpool_free_count (mpool_handle mhandle);
+#endif
+
+#endif
diff --git a/src/framework/include/nsfw_mgr_com_api.h b/src/framework/include/nsfw_mgr_com_api.h
new file mode 100644
index 0000000..2499fee
--- /dev/null
+++ b/src/framework/include/nsfw_mgr_com_api.h
@@ -0,0 +1,198 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+/*==============================================*
+ * include header files *
+ *----------------------------------------------*/
+#ifndef _NSFW_MGRCOM_API_H
+#define _NSFW_MGRCOM_API_H
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define NSFW_MGR_COM_MODULE "nsfw_mgr_com"
+
+#define MRG_RSP(_req_msg) (_req_msg + MGR_MSG_RSP_BASE)
+
+typedef enum _mgr_msg_type
+{
+ MGR_MSG_NULL = 0,
+ /*#############common msg type################# */
+ MGR_MSG_CHK_INIT_REQ = 1,
+ MGR_MSG_INIT_NTY_REQ,
+ MGR_MSG_CHK_HBT_REQ,
+ MGR_MSG_APP_EXIT_REQ,
+ MGR_MSG_SRV_CTL_REQ,
+ MGR_MSG_VER_MGR_REQ,
+ MGR_MSG_SOF_PAR_REQ,
+
+ /*############################################# */
+ MGR_MSG_MEM_ALLOC_REQ = 64, /* memory msg type */
+
+ /*############################################# */
+ MGR_MSG_DFX_QRY_REQ = 96, /* nStackCtrl maitain msg */
+ MGR_MSG_SET_LOG_REQ,
+
+ /*############################################# */
+ MGR_MSG_RCC_END_REQ = 128, /* service msg type */
+
+ /*############################################# */
+ MGR_MSG_TOOL_TCPDUMP_REQ = 256, /* for tools */
+ MGR_MSG_TOOL_HEART_BEAT,
+
+ /*###query message with large rsp message begin## */
+ MGR_MSG_LARGE_QRY_REQ_BEGIN = 384,
+ MGR_MSG_LARGE_STA_QRY_REQ = MGR_MSG_LARGE_QRY_REQ_BEGIN,
+ MGR_MSG_LARGE_MT_QRY_REQ, /* nStackCtrl maitain msg */
+
+ /*############################################# */
+ MGR_MSG_LARGE_ALARM_REQ = 500, /* alarm msg type */
+
+ MGR_MSG_RSP_BASE = 512,
+ /*#############common msg type################# */
+ MGR_MSG_CHK_INIT_RSP = MRG_RSP (MGR_MSG_CHK_INIT_REQ),
+ MGR_MSG_INIT_NTY_RSP = MRG_RSP (MGR_MSG_INIT_NTY_REQ),
+ MGR_MSG_CHK_HBT_RSP = MRG_RSP (MGR_MSG_CHK_HBT_REQ),
+ MGR_MSG_APP_EXIT_RSP = MRG_RSP (MGR_MSG_APP_EXIT_REQ),
+ MGR_MSG_SRV_CTL_RSP = MRG_RSP (MGR_MSG_SRV_CTL_REQ),
+ MGR_MSG_VER_MGR_RSP = MRG_RSP (MGR_MSG_VER_MGR_REQ),
+ MGR_MSG_SOF_PAR_RSP = MRG_RSP (MGR_MSG_SOF_PAR_REQ),
+ /*############################################# */
+
+ MGR_MSG_MEM_ALLOC_RSP = MRG_RSP (MGR_MSG_MEM_ALLOC_REQ),
+
+ MGR_MSG_DFX_QRY_RSP = MRG_RSP (MGR_MSG_DFX_QRY_REQ),
+
+ MGR_MSG_SET_LOG_RSP = MRG_RSP (MGR_MSG_SET_LOG_REQ),
+
+ MGR_MSG_RCC_END_RSP = MRG_RSP (MGR_MSG_RCC_END_REQ),
+
+ /*############################################# */
+ MGR_MSG_TOOL_TCPDUMP_RSP = MRG_RSP (MGR_MSG_TOOL_TCPDUMP_REQ),
+ MGR_MSG_TOOL_HEART_BEAT_RSP = MRG_RSP (MGR_MSG_TOOL_HEART_BEAT),
+
+ /*##############LARGE RSP MESSAGE################## */
+ MGR_MSG_LAG_QRY_RSP_BEGIN = MRG_RSP (MGR_MSG_LARGE_QRY_REQ_BEGIN),
+ MGR_MSG_LAG_STA_QRY_RSP = MRG_RSP (MGR_MSG_LARGE_STA_QRY_REQ),
+ MGR_MSG_LAG_MT_QRY_RSP = MRG_RSP (MGR_MSG_LARGE_MT_QRY_REQ),
+ MGR_MSG_LARGE_ALARM_RSP = MRG_RSP (MGR_MSG_LARGE_ALARM_REQ),
+ MGR_MSG_MAX = 1024
+} mgr_msg_type;
+
+typedef enum _fw_poc_type
+{
+ NSFW_PROC_NULL = 0,
+ NSFW_PROC_MAIN,
+ NSFW_PROC_MASTER,
+ NSFW_PROC_APP,
+ NSFW_PROC_CTRL,
+ NSFW_PROC_TOOLS,
+ NSFW_PROC_ALARM,
+ NSFW_PROC_MAX = 16
+} fw_poc_type;
+
+#define NSFW_DOMAIN_DIR "/var/run"
+#define NSTACK_MAX_PROC_NAME_LEN 20
+
+typedef enum _nsfw_mgr_msg_rsp_code
+{
+ NSFW_MGR_SUCESS,
+ NSFW_MGR_MSG_TYPE_ERROR,
+} mgr_msg_rsp_code;
+
+extern char *nsfw_get_proc_name (u8 proc_type);
+
+#define GET_USER_MSG(_stu, _msg) ((_stu *)(&(_msg)->msg_body[0]))
+
+/*for log print*/
+#define MSGINFO "msg=%p,len=%d,t=%d,sq=%d,st=%d,sp=%d,dt=%d,dp=%d"
+#define PRTMSG(msg) (msg), (msg)->msg_len,(msg)->msg_type,(msg)->seq, (msg)->src_proc_type,(msg)->src_pid,(msg)->dst_proc_type,(msg)->dst_pid
+
+#define NSFW_MGR_MSG_LEN 512
+#define NSFW_MGR_MSG_HDR_LEN 32
+#define NSFW_MGR_MSG_BODY_LEN (NSFW_MGR_MSG_LEN - NSFW_MGR_MSG_HDR_LEN)
+
+#define NSFW_MGR_LARGE_MSG_LEN (256*1024)
+#define NSFW_MGR_LARGE_MSG_BODY_LEN (NSFW_MGR_LARGE_MSG_LEN - NSFW_MGR_MSG_HDR_LEN)
+
+typedef struct _nsfw_mgr_msg
+{
+ u16 msg_type; /* mgr_msg_type */
+ u16 u16Reserve;
+ u32 msg_len;
+
+ u8 alloc_flag:1;
+ u8 fw_flag:1;
+ u8 from_mem:1;
+ u8 more_msg_flag:1;
+ u8 reserve_flag:4;
+ u8 resp_code;
+ u8 src_proc_type; /* fw_poc_type */
+ u8 dst_proc_type;
+ i32 seq;
+
+ u32 src_pid;
+ u32 dst_pid;
+
+ u64 traceid;
+
+ u8 msg_body[NSFW_MGR_MSG_BODY_LEN];
+} nsfw_mgr_msg;
+
+extern nsfw_mgr_msg *nsfw_mgr_msg_alloc (u16 msg_type, u8 dst_proc_type);
+extern void nsfw_mgr_msg_free (nsfw_mgr_msg * msg);
+
+/* for rsp msg alloc*/
+extern nsfw_mgr_msg *nsfw_mgr_null_rspmsg_alloc ();
+extern nsfw_mgr_msg *nsfw_mgr_rsp_msg_alloc (nsfw_mgr_msg * req_msg);
+
+/* for msg proc fun reg*/
+typedef int (*nsfw_mgr_msg_fun) (nsfw_mgr_msg * msg);
+extern u8 nsfw_mgr_reg_msg_fun (u16 msg_type, nsfw_mgr_msg_fun fun);
+
+extern u8 nsfw_mgr_send_msg (nsfw_mgr_msg * msg);
+extern u8 nsfw_mgr_send_req_wait_rsp (nsfw_mgr_msg * req_msg,
+ nsfw_mgr_msg * rsp_msg);
+
+/* for fork clear parent resource*/
+extern void nsfw_mgr_close_dst_proc (u8 proc_type, u32 dst_pid);
+extern u8 nsfw_mgr_clr_fd_lock ();
+
+/* for epoll thread reg other sock proc fun*/
+typedef int (*nsfw_mgr_sock_fun) (i32 epfd, i32 socket, u32 events);
+extern u8 nsfw_mgr_reg_sock_fun (i32 socket, nsfw_mgr_sock_fun fun);
+extern void nsfw_mgr_unreg_sock_fun (i32 socket);
+extern int nsfw_mgr_com_socket_error (i32 fd, nsfw_mgr_sock_fun fun,
+ i32 timer);
+extern u8 nsfw_mgr_ep_start ();
+extern int nsfw_mgr_com_module_init (void *param);
+extern int nsfw_mgr_run_script (const char *cmd, char *result,
+ int result_buf_len);
+
+extern int nsfw_mgr_com_chk_hbt (int v_add);
+extern i32 nsfw_set_close_on_exec (i32 sock);
+extern int nsfw_mgr_comm_fd_init (u32 proc_type);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _NSFW_MGRCOM_API_H */
diff --git a/src/framework/include/nsfw_ps_api.h b/src/framework/include/nsfw_ps_api.h
new file mode 100644
index 0000000..69fa992
--- /dev/null
+++ b/src/framework/include/nsfw_ps_api.h
@@ -0,0 +1,134 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_PS_API_H
+#define _NSFW_PS_API_H
+
+#include "list.h"
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define NSFW_PS_MODULE "nsfw_ps"
+
+#define NSFW_PS_MAX_CALLBACK 16
+
+#define NSFW_MAX_HBT_CHK_COUNT_DEF 60
+
+typedef enum _nsfw_ps_state
+{
+ NSFW_PS_NULL = 0,
+ NSFW_PS_START,
+ NSFW_PS_RUNNING,
+ NSFW_PS_PARENT_FORK,
+ NSFW_PS_CHILD_FORK,
+ NSFW_PS_HBT_FAILED,
+ NSFW_PS_EXITING,
+ NSFW_PS_EXIT,
+ NSFW_PS_MAX
+} nsfw_ps_state;
+
+/* for state change call back proc*/
+typedef int (*nsfw_ps_proc_fun) (void *pps_info, void *argv);
+typedef struct _nsfw_ps_callback
+{
+ u8 state;
+ nsfw_ps_proc_fun fun;
+ void *argv;
+} nsfw_ps_callback;
+
+/* for value in ps_info get/set*/
+typedef enum _nsfw_ps_user_value
+{
+ NSFW_REC_IDX = 1,
+ NSFW_REC_TIMER = 2,
+ NSFW_PS_UV_MAX = 16
+} nsfw_ps_user_value;
+#define nsfw_ps_set_uv(_pps_info, _type, _value) (_pps_info)->value[(_type)] = (_value)
+#define nsfw_ps_get_uv(_pps_info, _type) ((_pps_info)->value[(_type)])
+
+typedef struct _nsfw_ps_info
+{
+ struct list_head node;
+ u8 alloc_flag;
+ u8 state; /*nsfw_ps_state */
+ u8 proc_type; /*fw_poc_type */
+ u8 rechk_flg;
+ u32 host_pid;
+ u32 parent_pid; /* only use for fork */
+ u32 cur_child_pid; /* only use for fork */
+ void *exit_timer_ptr;
+ void *resend_timer_ptr;
+ void *hbt_timer_ptr;
+ u32 hbt_failed_count;
+ nsfw_ps_callback callback[NSFW_PS_MAX_CALLBACK];
+ void *value[NSFW_PS_UV_MAX];
+} nsfw_ps_info;
+
+typedef struct _nsfw_thread_dogs
+{
+ u8 alloc_flag;
+ i32 count;
+ u32 thread_id;
+} nsfw_thread_dogs;
+
+extern nsfw_ps_info *nsfw_ps_info_alloc (u32 pid, u8 proc_type);
+extern nsfw_ps_info *nsfw_ps_info_get (u32 pid);
+extern void nsfw_ps_info_free (nsfw_ps_info * ps_info);
+
+extern u8 nsfw_ps_reg_fun (nsfw_ps_info * pps_info, u8 ps_state,
+ nsfw_ps_proc_fun fun, void *argv);
+
+/* will auto reg after ps_info alloc*/
+extern u8 nsfw_ps_reg_global_fun (u8 proc_type, u8 ps_state,
+ nsfw_ps_proc_fun fun, void *argv);
+
+typedef struct _nsfw_ps_info_msg
+{
+ u32 host_pid;
+ u32 parent_pid;
+ u64 reserve;
+} nsfw_ps_info_msg;
+extern u8 nsfw_ps_exit_end_notify (u32 pid);
+
+/*for heartbeat check*/
+extern u8 nsfw_ps_check_dst_init (u8 dst_proc_type);
+extern u8 nsfw_thread_chk ();
+extern nsfw_thread_dogs *nsfw_thread_getDog ();
+extern u8 nsfw_thread_chk_unreg ();
+extern u8 nsfw_ps_hbt_start (nsfw_ps_info * ps_info);
+extern u8 nsfw_ps_hbt_stop (nsfw_ps_info * ps_info);
+
+extern u32 nsfw_ps_iterator (nsfw_ps_proc_fun fun, void *argv);
+
+#define MAX_THREAD 16
+extern pthread_t g_all_thread[];
+extern u8 nsfw_reg_trace_thread (pthread_t tid);
+
+typedef int (*nsfw_ps_pid_fun) (u32 pid, u8 proc_type, void *argv);
+extern int nsfw_ps_rechk_pid_exit (nsfw_ps_pid_fun fun, void *argv);
+extern nsfw_ps_info *nsfw_share_ps_info_get (u32 pid);
+extern void nsfw_ps_cfg_set_chk_count (u16 count);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _NSFW_PS_API_H */
diff --git a/src/framework/include/nsfw_ps_mem_api.h b/src/framework/include/nsfw_ps_mem_api.h
new file mode 100644
index 0000000..01f9cd3
--- /dev/null
+++ b/src/framework/include/nsfw_ps_mem_api.h
@@ -0,0 +1,36 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_PS_MEM_API_H
+#define _NSFW_PS_MEM_API_H
+
+#include "nsfw_mem_api.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define NSFW_PS_MEM_MODULE "nsfw_ps_mem"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _NSFW_PS_MEM_API_H */
diff --git a/src/framework/include/nsfw_recycle_api.h b/src/framework/include/nsfw_recycle_api.h
new file mode 100644
index 0000000..fd2bd8f
--- /dev/null
+++ b/src/framework/include/nsfw_recycle_api.h
@@ -0,0 +1,92 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_RECYCLE_API_H
+#define _NSFW_RECYCLE_API_H
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define NSFW_RECYCLE_MODULE "nsfw_recycle"
+
+typedef enum _nsfw_recycle_item_type
+{
+ NSFW_REC_TYPE_NULL = 0,
+ NSFW_REC_SBR_START = 1,
+ NSFW_REC_SBR_SOCKET,
+ NSFW_REC_SBR_END = NSFW_REC_SBR_START + 63,
+ NSFW_REC_NSOCKET_START,
+ NSFW_REC_NSOCKET_EPOLL,
+ NSFW_REC_NSOCKET_END = NSFW_REC_NSOCKET_START + 63,
+ NSFW_REC_TYPE_MAX = 512
+} nsfw_recycle_item_type;
+
+typedef enum _nsfw_recycle_priority
+{
+ NSFW_REC_PRO_HIGHTEST = 0,
+ NSFW_REC_PRO_NORMAL = 1,
+ NSFW_REC_PRO_DEFALUT = 2,
+ NSFW_REC_PRO_LOWEST = 3,
+ NSFW_REC_PRO_MAX = 4
+} nsfw_recycle_priority;
+
+typedef enum _nsfw_rcc_stat
+{
+ NSFW_RCC_CONTINUE = 0,
+ NSFW_RCC_SUSPEND = 1,
+ NSFW_RCC_FAILED = 2,
+} nsfw_rcc_stat;
+
+/*work on nStackMain*/
+typedef nsfw_rcc_stat (*nsfw_recycle_fun) (u32 exit_pid, void *pdata,
+ u16 rec_type);
+extern u8 nsfw_recycle_reg_fun (u16 obj_type, nsfw_recycle_fun fun);
+extern u8 nsfw_recycle_obj_end (u32 pid);
+extern u8 nsfw_recycle_lock_rel_fun (nsfw_recycle_fun fun, void *data,
+ u8 proc_type);
+extern int nsfw_recycle_exit_pid_lock (u32 pid, u8 proc_type, void *argv);
+
+#define REGIST_RECYCLE_OBJ_FUN(_obj_type, _fun) \
+ NSTACK_STATIC void regist_ ## _obj_type ## _fun (void) \
+ __attribute__((__constructor__)); \
+ NSTACK_STATIC void regist_ ## _obj_type ## _fun (void) \
+ { \
+ (void)nsfw_recycle_reg_fun(_obj_type, _fun); \
+ }
+
+#define REGIST_RECYCLE_LOCK_REL(_fun, _data, _proc) \
+ NSTACK_STATIC void regist_lock ## _fun (void) \
+ __attribute__((__constructor__)); \
+ NSTACK_STATIC void regist_lock ## _fun (void) \
+ { \
+ (void)nsfw_recycle_lock_rel_fun(_fun, _data,_proc); \
+ }
+
+/*work on nStackApp*/
+extern void *nsfw_recycle_reg_obj (u8 priority, u16 rec_type, void *data);
+extern u8 nsfw_recycle_fork_init ();
+extern int nsfw_recycle_rechk_lock ();
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _NSFW_RECYCLE_API_H */
diff --git a/src/framework/include/nsfw_snapshot.h b/src/framework/include/nsfw_snapshot.h
new file mode 100644
index 0000000..8958c64
--- /dev/null
+++ b/src/framework/include/nsfw_snapshot.h
@@ -0,0 +1,144 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _FW_SNAPSHOT_H
+#define _FW_SNAPSHOT_H
+
+#include <stdlib.h>
+#include "types.h"
+#include "../snapshot/fw_ss_tlv.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+// object type(7 bits) | member type (7 bits) | is object(1 bit) | is array(1 bit)
+// member type is the type in object structure , it only effects the own object
+/**
+ * type - object , type object of array, type base item
+ */
+
+#define NSFW_SS_TYPE_OBJ(_objType) (0xfe00 & ((_objType) << 9))
+#define NSFW_SS_TYPE_GETOBJ(_objType) ((0xfe00 & (_objType)) >> 9)
+
+#define NSFW_SS_TYPE_MEMBER(_memType) (0x01fc & ((_memType) << 2))
+#define NSFW_SS_TYPE_GET_MEMBER(_memType) ((0x01fc & (_memType)) >> 2)
+
+#define NSFW_SS_TYPE_SET_MEMBER_ITEM(_memType) (NSFW_SS_TYPE_MEMBER((_memType)))
+#define NSFW_SS_TYPE_SET_MEMBER_OBJ(_objType, _memType) \
+ (NSFW_SS_TYPE_OBJ((_objType)) | NSFW_SS_TYPE_SET_MEMBER_ITEM((_memType)) | 0x02)
+#define NSFW_SS_TYPE_SET_MEMBER_OBJ_ARRAY(_objType, _memType) \
+ (NSFW_SS_TYPE_SET_MEMBER_OBJ((_objType), (_memType)) | 0x01)
+
+#define NSFW_SS_TYPE_IS_MEMBER_OBJ(_memType) ((_memType) & 0x02)
+#define NSFW_SS_TYPE_IS_MEMBER_ARRAY(_memType) ((_memType) & 0x01)
+
+/*
+ * This structure tells how to describe one object and its members
+ */
+typedef struct _nsfw_ss_objMemDesc
+{
+ u16 type; // object type(7 bits) | member type (7 bits) | is object(1 bit) | is array(1 bit)
+ u32 length;
+ u8 offset;
+} nsfw_ss_objMemDesc_t;
+
+typedef struct _nsfw_ss_objDesc
+{
+ u16 objType; /* Type number of object */
+ u8 memNum; /* Nubmer of object members */
+ u32 objSize;
+ nsfw_ss_objMemDesc_t *memDesc; /* Member descripe */
+} nsfw_ss_objDesc_t;
+
+#define NSFW_SS_MAX_OBJDESC_NUM 256
+
+/* Traversal, you can save the current value to start the search, do not need to start from the beginning of the search, because the value is generally a sequential */
+
+typedef struct _nsfw_ss_objDescManager
+{
+ nsfw_ss_objDesc_t *g_nsfw_ss_objDescs[NSFW_SS_MAX_OBJDESC_NUM];
+ int g_nsfw_ss_objDesNum;
+} nsfw_ss_objDescManager_t;
+
+extern nsfw_ss_objDescManager_t g_nsfw_ss_objDescManager;
+
+#define nsfw_ss_getObjDescManagerInst() (&g_nsfw_ss_objDescManager)
+
+/**
+ * @Function nsfw_ss_registe_ObjDesc
+ * @Description Registe object description to snapshot
+ * @param objDesc - description of object
+ * @return void
+ */
+extern void nsfw_ss_register_ObjDesc (nsfw_ss_objDesc_t * objDesc);
+
+/**
+ * @Function nsfw_ss_store
+ * @Description store object to memory
+ * @param (in) objType - type of object
+ * @param (in) obj - adderss of object memory
+ * @param (in) storeMem - address of memory to store object data
+ * @param (in) storeMemLen - maximal length of storage memory
+ * @return positive integer means length of memory cost on success. return -1 if error
+ */
+extern int nsfw_ss_store (u16 objType, void *obj, void *storeMem,
+ u32 storeMemLen);
+
+/**
+ * @Function nsfw_ss_restore
+ * @Description restore object from memory
+ * @param (in) objMem - memory of object
+ * @param (in) mem - memory of storage
+ * @param (in) storeMemLen - maximal length of storage memory
+ * @return positive integer stands on object type, -1 on error
+ */
+extern int nsfw_ss_restore (void *objMem, void *mem, u32 storeMemLen);
+
+/**
+ * @Function nsfw_ss_getObjStoreMemLen
+ * @Description Get the maximal memory it needs
+ * @param (in) objType - type of object
+ * @return length of memory needs, -1 if error
+ */
+extern int nsfw_ss_getObjStoreMemLen (int objType);
+
+#define _NSFW_SNAPSHOT_OBJDESC_REGISTER_SURFIX(_value, _surfix) \
+ static __attribute__((__constructor__(121))) void nsfw_snapshot_objdesc_register_constructor##_surfix(void){\
+ nsfw_ss_register_ObjDesc((_value));\
+ }
+
+#define NSFW_SNAPSHOT_OBJDESC_REGISTER_SURFIX(_value, _surfix) \
+ _NSFW_SNAPSHOT_OBJDESC_REGISTER_SURFIX(_value, _surfix)
+
+#define NSFW_SNAPSHOT_OBJDESC_REGISTER_UNIQUE(_value) \
+ NSFW_SNAPSHOT_OBJDESC_REGISTER_SURFIX(_value, __LINE__)
+
+/**
+ * Using this marcro to register object description
+ */
+#define NSFW_SS_REGSITER_OBJDESC(_value) \
+ NSFW_SNAPSHOT_OBJDESC_REGISTER_UNIQUE(_value)
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _FW_SNAPSHOT_H */
diff --git a/src/framework/include/nsfw_upgrade.h b/src/framework/include/nsfw_upgrade.h
new file mode 100644
index 0000000..a4e809c
--- /dev/null
+++ b/src/framework/include/nsfw_upgrade.h
@@ -0,0 +1,51 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef NSFW_UPGRADE_H
+#define NSFW_UPGRADE_H
+#include "types.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+#endif
+
+#define ENUM_STRUCT(struct) enum enum_upgrade_ ## struct
+
+#define ENUM_MEM(struct, mem) struct ## _ ## mem
+
+#define GET_MEM_BIT(mem_bit, struct, mem) (mem_bit & ((i64)1 << struct ## _ ## mem))
+
+#define USE_MEM_BIT(mem_bit, struct, mem) (mem_bit |= ((i64)1 << struct ## _ ## mem))
+
+#define UPGRADE_MEM_VAL(mem_bit, struct, mem, obj, defalut) { \
+ if (!GET_MEM_BIT(mem_bit, struct, mem)){ \
+ obj->mem = defalut; \
+ } \
+ }
+
+#define CONSTRUCT_UPGRADE_FUN(struct, obj) void upgrade_ ## struct (struct* obj)
+
+#define CALL_UPGRADE_FUN(struct, obj) upgrade_ ## struct (obj)
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
+
+#endif
diff --git a/src/framework/include/nstack_log.h b/src/framework/include/nstack_log.h
new file mode 100644
index 0000000..bb90ec8
--- /dev/null
+++ b/src/framework/include/nstack_log.h
@@ -0,0 +1,580 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSTACK_LOG_H_
+#define _NSTACK_LOG_H_
+/*==============================================*
+ * include header files *
+ *----------------------------------------------*/
+#pragma GCC diagnostic ignored "-Wcpp"
+#include <stdio.h>
+#include <string.h>
+#include <stdint.h>
+#include <stdarg.h>
+#include <stdlib.h>
+#include <sys/time.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <unistd.h>
+#include <sys/syscall.h>
+#include <sys/types.h>
+#include <signal.h>
+#include "types.h"
+#include "nstack_trace.h"
+
+#include "glog/nstack_glog.ph"
+#include "glog/nstack_glog_in.h"
+
+#define NSTACK_GETVER_MODULE "nStack"
+#define NSTACK_GETVER_VERSION "VPP2.0 V100R002C10B053"
+#define NSTACK_GETVER_BUILDTIME "[" __DATE__ "]" "[" __TIME__ "]"
+#define NSTACK_VERSION NSTACK_GETVER_VERSION " (" NSTACK_GETVER_MODULE ") " NSTACK_GETVER_BUILDTIME
+
+#define LOG_TIME_STAMP_LEN 17 // "YYYYMMDDHHMMSS";
+
+/*==============================================*
+ * constants or macros define *
+ *----------------------------------------------*/
+typedef enum _LOG_MODULE
+{
+ NSOCKET = 1,
+ STACKX,
+ OPERATION,
+ MASTER,
+ LOGTCP,
+ LOGUDP,
+ LOGIP,
+ LOGCMP,
+ LOGARP,
+ LOGRTE,
+ LOGHAL,
+ LOGDFX,
+ LOGFW,
+ LOGSBR,
+ MAX_LOG_MODULE
+} LOG_MODULE;
+
+enum _LOG_TYPE
+{
+ LOG_TYPE_NSTACK = 0,
+ LOG_TYPE_OPERATION,
+ LOG_TYPE_MASTER,
+ LOG_TYPE_APP,
+ MAX_LOG_TYPE
+};
+
+enum _LOG_PROCESS
+{
+ LOG_PRO_NSTACK = 0,
+ LOG_PRO_MASTER,
+ LOG_PRO_APP,
+ LOG_PRO_OMC_CTRL,
+ LOG_PRO_INVALID
+};
+
+#define LOG_INVALID_VALUE 0xFFFF
+
+#define NSLOG_DBG 0x10
+#define NSLOG_INF 0x08
+#define NSLOG_WAR 0x04
+#define NSLOG_ERR 0x02
+#define NSLOG_EMG 0x01
+#define NSLOG_OFF 0x00
+
+#define LOG_LEVEL_EMG "emg"
+#define LOG_LEVEL_ERR "err"
+#define LOG_LEVEL_WAR "war"
+#define LOG_LEVEL_DBG "dbg"
+#define LOG_LEVEL_INF "inf"
+
+#define GET_FILE_NAME(name_have_path) strrchr(name_have_path,'/')?strrchr(name_have_path,'/')+1:name_have_path
+
+#define NSTACK_LOG_NAME "/product/gpaas/log/nStack"
+
+#define STACKX_LOG_NAME "running.log"
+
+#define OPERATION_LOG_NAME "operation.log"
+
+#define MASTER_LOG_NAME "master.log"
+
+#define OMC_CTRL_LOG_NAME "omc_ctrl.log"
+
+#define FAILURE_LOG_NAME "fail_dump.log"
+
+#define FLUSH_TIME 30
+
+#define APP_LOG_SIZE 30
+#define APP_LOG_COUNT 10
+#define APP_LOG_PATH "/var/log"
+#define APP_LOG_NAME "nStack_nSocket.log"
+
+#define NS_LOG_STACKX_ON 0x80U
+#define NS_LOG_STACKX_TRACE 0x40U
+#define NS_LOG_STACKX_STATE 0x20U
+#define NS_LOG_STACKX_FRESH 0x10U
+#define NS_LOG_STACKX_HALT 0x08U
+#define NS_LOG_STACKX_OFF 0x00U
+
+#define NULL_STRING ""
+#define MODULE_INIT_FORMAT_STRING "module %s]name=[%s]%s"
+#define MODULE_INIT_START "init"
+#define MODULE_INIT_FAIL "start failed"
+#define MODULE_INIT_SUCCESS "start success"
+
+#define PRE_INIT_LOG_LENGTH 128
+
+struct nstack_logs
+{
+ uint32_t level; /**< Log level. */
+ int pad64;
+ int inited;
+ int file_type;
+};
+
+struct log_init_para
+{
+ uint32_t run_log_size;
+ uint32_t run_log_count;
+ char *run_log_path;
+ uint32_t mon_log_size; //master and ctrl both use the parameter to reduce the redundancy
+ uint32_t mon_log_count; //master and ctrl both use the parameter to reduce the redundancy
+ char *mon_log_path; //master and ctrl both use the parameter to reduce the redundancy
+};
+
+enum LOG_CTRL_ID
+{
+ // for socket api
+ LOG_CTRL_SEND = 0,
+ LOG_CTRL_RECV,
+ LOG_CTRL_SENDMSG,
+ LOG_CTRL_RECVMSG,
+ LOG_CTRL_READ,
+ LOG_CTRL_WRITE,
+ LOG_CTRL_READV,
+ LOG_CTRL_WRITEV,
+ LOG_CTRL_GETSOCKNAME,
+ LOG_CTRL_GETPEERNAME,
+ LOG_CTRL_GETSOCKOPT,
+
+ // for nstack service
+ LOG_CTRL_RECV_QUEUE_FULL,
+ LOG_CTRL_L4_RECV_QUEUE_FULL,
+ LOG_CTRL_HUGEPAGE_ALLOC_FAIL,
+ LOG_CTRL_TCP_MEM_NOT_ENOUGH,
+ LOG_CTRL_IPREASS_OVERFLOW,
+ LOG_CTRL_ID_MAX
+};
+
+struct log_ctrl_info
+{
+ u32 expire_time;
+ u32 unprint_count;
+ struct timespec last_log_time;
+};
+
+struct pre_init_info
+{
+ uint32_t level; /**< Log level. */
+ char log_buffer[PRE_INIT_LOG_LENGTH];
+};
+
+#define NS_LOG_STACKX(dbug,_module,_prestr,_level,fmt, ...) \
+{\
+ if ((dbug) & NS_LOG_STACKX_ON)\
+ {\
+ NS_LOGPID(_module,_prestr,_level,fmt,##__VA_ARGS__);\
+ }\
+}\
+
+
+/*****************************************************************************
+* Prototype : nstack_get_log_level
+* Description : get log level
+* Input : int module
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+extern struct nstack_logs g_nstack_logs[MAX_LOG_MODULE];
+static inline int
+nstack_get_log_level (int module)
+{
+ /* validity check for path */
+ if ((MAX_LOG_MODULE <= module) || (module < 0))
+ {
+ return -1;
+ }
+
+ return g_nstack_logs[module].level;
+}
+
+/*****************************************************************************
+* Prototype : level_stoa
+* Description : convert stack log level to app log level
+* Input : unsigned int nstack_level
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+static inline unsigned int
+level_stoa (unsigned int level)
+{
+ unsigned int golg_level;
+ switch (level)
+ {
+ case NSLOG_DBG:
+ golg_level = GLOG_LEVEL_DEBUG;
+ break;
+ case NSLOG_INF:
+ golg_level = GLOG_LEVEL_INFO;
+ break;
+ case NSLOG_WAR:
+ golg_level = GLOG_LEVEL_WARNING;
+ break;
+ case NSLOG_ERR:
+ golg_level = GLOG_LEVEL_ERROR;
+ break;
+ case NSLOG_EMG:
+ golg_level = GLOG_LEVEL_FATAL;
+ break;
+ default:
+ golg_level = GLOG_LEVEL_BUTT;
+ break;
+ }
+ return golg_level;
+}
+
+/* use the glog function to replace old nstack log module */
+
+/* segregate the dump info */
+#define LOG_TYPE(_module, _level) \
+ (((STACKX == _module) && (NSLOG_EMG == _level)) ? GLOG_LEVEL_ERROR : ((OPERATION == _module) ? GLOG_LEVEL_WARNING : GLOG_LEVEL_INFO))
+
+#define log_shooting(_module,_level) \
+ ((NULL == g_log_hook_tag.log_hook) ? (nstack_get_log_level(_module) >= _level) : (level_stoa(_level) >= g_log_hook_tag.level))
+
+/* add the non reentry protection */
+extern __thread unsigned int nstack_log_nonreentry;
+
+/* hanging up version check log need restrain */
+extern int ctrl_log_switch;
+
+#if defined MPTCP_UT
+#define NS_LOGPID(_module,_prestr,_level,fmt, ...)
+#elif !defined FOR_NSTACK_UT
+#define NS_LOGPID(_module,_prestr,_level,fmt, ...) \
+{\
+ if (log_shooting(_module, _level) && (0 == nstack_log_nonreentry) && (0 == ctrl_log_switch))\
+ {\
+ nstack_log_nonreentry = 1;\
+ NSTACK_TRACING(_level, _prestr, fmt,##__VA_ARGS__);\
+ if(nstack_log_info_check(_module, _level))\
+ glog_print(LOG_TYPE(_module,_level),_prestr,level_stoa(_level),-1,GET_FILE_NAME(__FILE__),\
+ __LINE__,__func__,fmt, ##__VA_ARGS__);\
+ nstack_log_nonreentry = 0;\
+ }\
+}
+#else
+static inline void
+ut_log_info (const char *file_name, int line_no, const char *func_name,
+ int _module, const char *_prestr, unsigned int _level, char *fmt,
+ ...)
+{
+ va_list ap;
+
+ if (log_shooting (_module, _level) && (0 == nstack_log_nonreentry)
+ && (0 == ctrl_log_switch))
+ {
+
+ nstack_log_nonreentry = 1;
+ if (nstack_log_info_check (_module, _level))
+ {
+ char pMsgBuf[MAX_LOG_TRANSITIONAL_LEN] = "\0";
+ va_start (ap, fmt);
+ VSNPRINTF_S (pMsgBuf,
+ MAX_LOG_TRANSITIONAL_LEN,
+ MAX_LOG_TRANSITIONAL_LEN - 1, fmt, ap);
+ glog_print (LOG_TYPE (_module, _level), _prestr,
+ level_stoa (_level), -1, GET_FILE_NAME (file_name),
+ line_no, func_name, "%s", pMsgBuf);
+ va_end (ap);
+ }
+ nstack_log_nonreentry = 0;
+
+ }
+}
+
+#define NS_LOGPID(_module,_prestr,_level,fmt, ...) \
+{\
+ ut_log_info(__FILE__,__LINE__, __func__, _module,_prestr,_level,fmt, ##__VA_ARGS__); \
+}
+
+#endif
+
+#ifndef FOR_NSTACK_UT
+#define NS_LOG_CTRL(_id, _module, _prestr, _level, fmt, ...) \
+{\
+ if (log_shooting(_module, _level) && (0 == nstack_log_nonreentry) && check_log_prt_time(_id))\
+ {\
+ nstack_log_nonreentry = 1;\
+ NSTACK_TRACING(_level, _prestr, fmt,##__VA_ARGS__);\
+ if(nstack_log_info_check(_module, _level))\
+ glog_print(LOG_TYPE(_module,_level),_prestr,level_stoa(_level),get_unprt_log_count(_id),\
+ GET_FILE_NAME(__FILE__),__LINE__,__func__,fmt, ##__VA_ARGS__);\
+ clr_unprt_log_count(_id);\
+ nstack_log_nonreentry = 0;\
+ }\
+}
+
+#else
+static inline void
+ut_ctrl_log_info (char *file_name, int line_no, char *func_name, int _id,
+ int _module, char *_prestr, unsigned int _level, char *fmt,
+ ...)
+{
+ va_list ap;
+ if (log_shooting (_module, _level) && (0 == nstack_log_nonreentry)
+ && check_log_prt_time (_id))
+ {
+ nstack_log_nonreentry = 1;
+ if (nstack_log_info_check (_module, _level))
+ {
+ char pMsgBuf[MAX_LOG_TRANSITIONAL_LEN] = "\0";
+ va_start (ap, fmt);
+ VSNPRINTF_S (pMsgBuf,
+ MAX_LOG_TRANSITIONAL_LEN,
+ MAX_LOG_TRANSITIONAL_LEN - 1, fmt, ap);
+ glog_print (LOG_TYPE (_module, _level), _prestr,
+ level_stoa (_level), get_unprt_log_count (_id),
+ GET_FILE_NAME (file_name), line_no, func_name, "%s",
+ pMsgBuf);
+ va_end (ap);
+ }
+ clr_unprt_log_count (_id);
+ nstack_log_nonreentry = 0;
+
+ }
+}
+
+#define NS_LOG_CTRL(_id, _module, _prestr, _level, fmt, ...) \
+{\
+ ut_ctrl_log_info(__FILE__,__LINE__, __func__, _id, _module,_prestr,_level,fmt, ##__VA_ARGS__); \
+}
+
+#endif
+
+#define NS_LOG_CTRL_STACKX(_id, dbug,_module,_prestr,_level,fmt, ...) \
+{\
+ if ((dbug) & NS_LOG_STACKX_ON)\
+ {\
+ NS_LOG_CTRL(_id, _module,_prestr,_level,fmt,##__VA_ARGS__);\
+ }\
+}\
+
+
+/*for every log modules should def marcos below use a sort module name, just like MON means Monitor*/
+#define NSMON_LOGINF(fmt, ...) NS_LOGPID(MASTER,"NSMON",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSMON_LOGDBG(fmt, ...) NS_LOGPID(MASTER,"NSMON",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSMON_LOGWAR(fmt, ...) NS_LOGPID(MASTER,"NSMON",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSMON_LOGERR(fmt, ...) NS_LOGPID(MASTER,"NSMON",NSLOG_ERR,fmt,##__VA_ARGS__)
+
+#define NSPOL_LOGINF(debug,fmt, ...)NS_LOG_STACKX(debug,STACKX,"NSPOL",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSPOL_LOGDBG(debug,fmt, ...) NS_LOG_STACKX(debug,STACKX,"NSPOL",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSPOL_LOGWAR(debug,fmt, ...) NS_LOG_STACKX(debug,STACKX,"NSPOL",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSPOL_LOGERR(fmt, ...) NS_LOGPID(STACKX,"NSPOL",NSLOG_ERR,fmt,##__VA_ARGS__)
+#define NSPOL_LOGEMG(fmt, ...) NS_LOGPID(STACKX,"NSPOL",NSLOG_EMG,fmt,##__VA_ARGS__)
+
+#define NSOPR_LOGINF(fmt, ...) NS_LOGPID(OPERATION,"NSOPR",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSOPR_LOGDBG(fmt, ...) NS_LOGPID(OPERATION,"NSOPR",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSOPR_LOGWAR(fmt, ...) NS_LOGPID(OPERATION,"NSOPR",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSOPR_LOGERR(fmt, ...) NS_LOGPID(OPERATION,"orchestration",NSLOG_ERR,fmt,##__VA_ARGS__)
+
+#define NSSOC_LOGINF(fmt, ...) NS_LOGPID(NSOCKET,"NSSOC",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSSOC_LOGDBG(fmt, ...) NS_LOGPID(NSOCKET,"NSSOC",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSSOC_LOGWAR(fmt, ...) NS_LOGPID(NSOCKET,"NSSOC",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSSOC_LOGERR(fmt, ...) NS_LOGPID(NSOCKET,"NSSOC",NSLOG_ERR,fmt,##__VA_ARGS__)
+
+#define NSSBR_LOGINF(fmt, ...) NS_LOGPID(LOGSBR,"NSSBR",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSSBR_LOGDBG(fmt, ...) NS_LOGPID(LOGSBR,"NSSBR",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSSBR_LOGWAR(fmt, ...) NS_LOGPID(LOGSBR,"NSSBR",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSSBR_LOGERR(fmt, ...) NS_LOGPID(LOGSBR,"NSSBR",NSLOG_ERR,fmt,##__VA_ARGS__)
+
+#define NSCOMM_LOGINF(fmt, ...) NS_LOGPID(LOGRTE, "NSRTE",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSCOMM_LOGDBG(fmt, ...) NS_LOGPID(LOGRTE, "NSRTE",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSCOMM_LOGWAR(fmt, ...) NS_LOGPID(LOGRTE, "NSRTE",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSCOMM_LOGERR(fmt, ...) NS_LOGPID(LOGRTE, "NSRTE",NSLOG_ERR,fmt,##__VA_ARGS__)
+
+#define NSTCP_LOGINF(fmt, ...) NS_LOGPID(LOGTCP,"NSTCP",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSTCP_LOGDBG(fmt, ...) NS_LOGPID(LOGTCP,"NSTCP",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSTCP_LOGWAR(fmt, ...) NS_LOGPID(LOGTCP,"NSTCP",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSTCP_LOGERR(fmt, ...) NS_LOGPID(LOGTCP,"NSTCP",NSLOG_ERR,fmt,##__VA_ARGS__)
+
+#define NSIP_LOGINF(fmt, ...) NS_LOGPID(LOGIP,"NSIP",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSIP_LOGDBG(fmt, ...) NS_LOGPID(LOGIP,"NSIP",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSIP_LOGWAR(fmt, ...) NS_LOGPID(LOGIP,"NSIP",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSIP_LOGERR(fmt, ...) NS_LOGPID(LOGIP,"NSIP",NSLOG_ERR,fmt,##__VA_ARGS__)
+
+#define NSUDP_LOGINF(fmt, ...) NS_LOGPID(LOGUDP,"NSUDP",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSUDP_LOGDBG(fmt, ...) NS_LOGPID(LOGUDP,"NSUDP",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSUDP_LOGWAR(fmt, ...) NS_LOGPID(LOGUDP,"NSUDP",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSUDP_LOGERR(fmt, ...) NS_LOGPID(LOGUDP,"NSUDP",NSLOG_ERR,fmt,##__VA_ARGS__)
+
+#define NSHAL_LOGINF(fmt, ...) NS_LOGPID(LOGHAL,"NSHAL",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSHAL_LOGDBG(fmt, ...) NS_LOGPID(LOGHAL,"NSHAL",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSHAL_LOGWAR(fmt, ...) NS_LOGPID(LOGHAL,"NSHAL",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSHAL_LOGERR(fmt, ...) NS_LOGPID(LOGHAL,"NSHAL",NSLOG_ERR,fmt,##__VA_ARGS__)
+
+#define NSARP_LOGINF(fmt, ...) NS_LOGPID(LOGARP,"NSARP",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSARP_LOGDBG(fmt, ...) NS_LOGPID(LOGARP,"NSARP",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSARP_LOGWAR(fmt, ...) NS_LOGPID(LOGARP,"NSARP",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSARP_LOGERR(fmt, ...) NS_LOGPID(LOGARP,"NSARP",NSLOG_ERR,fmt,##__VA_ARGS__)
+
+#define NSDFX_LOGINF(fmt, ...) NS_LOGPID(LOGDFX,"NSDFX",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSDFX_LOGDBG(fmt, ...) NS_LOGPID(LOGDFX,"NSDFX",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSDFX_LOGWAR(fmt, ...) NS_LOGPID(LOGDFX,"NSDFX",NSLOG_WAR,fmt,##__VA_ARGS__)
+#define NSDFX_LOGERR(fmt, ...) NS_LOGPID(LOGDFX,"NSDFX",NSLOG_ERR,fmt,##__VA_ARGS__)
+
+#define NSFW_LOGINF(fmt, ...) NS_LOGPID(LOGFW,"NSFW",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSFW_LOGDBG(fmt, ...) NS_LOGPID(LOGFW,"NSFW",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSFW_LOGERR(fmt, ...) NS_LOGPID(LOGFW,"NSFW",NSLOG_ERR,fmt,##__VA_ARGS__)
+#define NSFW_LOGWAR(fmt, ...) NS_LOGPID(LOGFW,"NSFW",NSLOG_WAR,fmt,##__VA_ARGS__)
+
+#define NSAM_LOGINF(fmt, ...) NS_LOGPID(LOGFW,"NSAM",NSLOG_INF,fmt,##__VA_ARGS__)
+#define NSAM_LOGDBG(fmt, ...) NS_LOGPID(LOGFW,"NSAM",NSLOG_DBG,fmt,##__VA_ARGS__)
+#define NSAM_LOGERR(fmt, ...) NS_LOGPID(LOGFW,"NSAM",NSLOG_ERR,fmt,##__VA_ARGS__)
+#define NSAM_LOGWAR(fmt, ...) NS_LOGPID(LOGFW,"NSAM",NSLOG_WAR,fmt,##__VA_ARGS__)
+
+#define INIT_LOG_ASSEM(log_module,_prestr,_level, init_module , function, errString, errValue, status) \
+ if ((LOG_INVALID_VALUE <= errValue) && (1 == sizeof(errString))) \
+ { \
+ NS_LOGPID(log_module,_prestr, _level,MODULE_INIT_FORMAT_STRING, (char*)status, init_module, function ); \
+ } \
+ else if (LOG_INVALID_VALUE <= errValue)\
+ { \
+ NS_LOGPID(log_module,_prestr, _level,MODULE_INIT_FORMAT_STRING",err_string=%s", (char*)status, init_module, function, errString ); \
+ } \
+ else if (1 == sizeof(errString))\
+ { \
+ NS_LOGPID(log_module,_prestr, _level,MODULE_INIT_FORMAT_STRING",err_value=%d", (char*)status, init_module, function, errValue ); \
+ } \
+ else \
+ { \
+ NS_LOGPID(log_module,_prestr, _level,MODULE_INIT_FORMAT_STRING",err_string=%s,err_value=%d", (char*)status, init_module, function, errString, errValue ); \
+ } \
+
+#define INITPOL_LOGINF(init_module_name, function, err_string, err_value, status) \
+ INIT_LOG_ASSEM(STACKX,"NSPOL",NSLOG_INF,init_module_name , function, err_string, err_value, status)\
+
+#define INITPOL_LOGERR(init_module_name, function, err_string, err_value, status) \
+ INIT_LOG_ASSEM(STACKX,"NSPOL",NSLOG_ERR,init_module_name , function, err_string, err_value, status)\
+
+#define INITTCP_LOGINF(init_module_name , function, err_string, err_value, status) \
+ INIT_LOG_ASSEM(LOGTCP,"NSTCP",NSLOG_INF,init_module_name , function, err_string, err_value, status)\
+
+#define INITTCP_LOGERR(init_module_name , function, err_string, err_value, status) \
+ INIT_LOG_ASSEM(LOGTCP,"NSTCP",NSLOG_ERR,init_module_name , function, err_string, err_value, status)\
+
+#define INITMON_LOGERR(init_module_name , function, err_string, err_value, status) \
+ INIT_LOG_ASSEM(MASTER,"NSMON",NSLOG_ERR,init_module_name , function, err_string, err_value, status)\
+
+#define INITSOC_LOGERR(init_module_name , function, err_string, err_value, status) \
+ INIT_LOG_ASSEM(NSOCKET,"NSSOC",NSLOG_ERR,init_module_name , function, err_string, err_value, status)
+
+#define NSPOL_DUMP_LOGINF(fmt, ...) NSPOL_LOGINF(0x80, fmt, ##__VA_ARGS__)
+#define NSPOL_DUMP_LOGDBG(fmt, ...) NSPOL_LOGDBG(0x80, fmt, ##__VA_ARGS__)
+#define NSPOL_DUMP_LOGERR(fmt, ...) NSPOL_LOGERR(fmt, ##__VA_ARGS__)
+#define NSPOL_DUMP_LOGWAR(fmt, ...) NSPOL_LOGWAR(0x80, fmt, ##__VA_ARGS__)
+
+/*==============================================*
+ * routines' or functions' implementations *
+ *----------------------------------------------*/
+
+void save_pre_init_log (uint32_t level, char *fmt, ...);
+void write_pre_init_log ();
+
+void set_log_init_para (struct log_init_para *para);
+
+void nstack_setlog_level (int module, uint32_t level);
+bool nstack_log_info_check (uint32_t module, uint32_t level);
+int nstack_log_init ();
+void nstack_log_init_app ();
+int get_app_env_log_path (char *app_file_path, unsigned int app_file_size);
+void set_log_proc_type (int log_proc_type);
+
+int setlog_level_value (const char *param, const char *value);
+int get_str_value (const char *arg);
+int check_log_dir_valid (const char *path);
+void nstack_segment_error (int s);
+void init_log_ctrl_info ();
+void set_log_ctrl_time (int id, int ctrl_time);
+
+int cmp_log_path (const char *path);
+
+#ifndef sys_sleep_ns
+#define sys_sleep_ns(_s, _ns)\
+ {\
+ if ((_s) >= 0 && (_ns) >= 0){\
+ struct timespec delay, remain;\
+ delay.tv_sec=(_s);\
+ delay.tv_nsec=(_ns);\
+ while (nanosleep (&delay, &remain) < 0)\
+ {\
+ delay = remain;\
+ }\
+ }\
+ }
+#endif /* sys_sleep_ns */
+
+int check_log_prt_time (int id);
+int get_unprt_log_count (int id);
+void clr_unprt_log_count (int id);
+
+void get_current_time (char *buf, const int len);
+
+#ifdef CPU_CYCLES
+static __inline__ unsigned long long
+nstack_rdtsc (void)
+{
+ unsigned hi, lo;
+ __asm__ __volatile__ ("rdtsc":"=a" (lo), "=d" (hi));
+ return ((unsigned long long) lo) | (((unsigned long long) hi) << 32);
+}
+
+#define CPUB(name) \
+unsigned long long start##name = 0;\
+unsigned long long stop##name = 0;\
+static unsigned long long total##name = 0;\
+static unsigned long long total_cout##name = 0;\
+start##name = nstack_rdtsc();
+
+#define CPUE(name) \
+stop##name = nstack_rdtsc();\
+total##name += (stop##name - start##name);\
+if(++total_cout##name == 1000000)\
+{\
+ NSSOC_LOGINF(#name" cpu %llu-------\n", total##name / total_cout##name);\
+ total##name = 0;\
+ total_cout##name = 0;\
+}
+#else
+#define CPUB(name)
+#define CPUE(name)
+#endif
+
+#endif
diff --git a/src/framework/include/nstack_rd_data.h b/src/framework/include/nstack_rd_data.h
new file mode 100644
index 0000000..3924680
--- /dev/null
+++ b/src/framework/include/nstack_rd_data.h
@@ -0,0 +1,80 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef __NSTACK_RD_DATA_H
+#define __NSTACK_RD_DATA_H
+
+/*choose router base on ip seg*/
+#define STACK_NAME_MAX 32
+#define RD_PLANE_NAMELEN (32)
+#define NSTACK_IP_BIT_MAX (32)
+#define NSTACK_RD_DATA_MAX (2048)
+#define RD_IP_STR_MAX_LEN (32)
+
+typedef enum __rd_data_type
+{
+ RD_DATA_TYPE_IP,
+ RD_DATA_TYPE_PROTO,
+ RD_DATA_TYPE_MAX,
+} rd_data_type;
+
+typedef enum __rd_node_state
+{
+ RD_NODE_USELESS,
+ RD_NODE_USING,
+ RD_NODE_DELETING,
+ RD_NODE_MAX,
+} rd_node_state;
+
+/*route info base on ip*/
+typedef struct __rd_route_ip_data
+{
+ unsigned int addr;
+ unsigned int masklen;
+ unsigned int resev[2];
+} rd_ip_data;
+
+/*route data*/
+typedef struct __rd_route_data
+{
+ /*route info type , for example base on ip */
+ rd_data_type type;
+ char stack_name[RD_PLANE_NAMELEN];
+ union
+ {
+ rd_ip_data ipdata;
+ unsigned int proto_type;
+ /*:::other type to be add */
+ };
+} rd_route_data;
+
+typedef struct __rd_route_node
+{
+ rd_node_state flag;
+ int agetime;
+ rd_route_data data;
+} rd_route_node;
+
+typedef struct __rd_route_table
+{
+ int size;
+ int icnt;
+ rd_route_node node[NSTACK_RD_DATA_MAX];
+} rd_route_table;
+
+#define MASK_V(ipaddr, masklen) ((ipaddr) & (~0 << (NSTACK_IP_BIT_MAX - (masklen))))
+
+#endif
diff --git a/src/framework/include/nstack_securec.h b/src/framework/include/nstack_securec.h
new file mode 100644
index 0000000..c9efb4f
--- /dev/null
+++ b/src/framework/include/nstack_securec.h
@@ -0,0 +1,145 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef __NSTACK_SECUREC_H__
+#define __NSTACK_SECUREC_H__
+
+/*if you need export the function of this library in Win32 dll, use __declspec(dllexport) */
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C" {
+/* *INDENT-ON* */
+
+#endif /* */
+#ifndef SECUREC_LIB
+#include <stdio.h>
+#include <stdarg.h>
+#include <wchar.h>
+#include <string.h>
+
+#ifndef NULL
+#define NULL ((void *)0)
+#endif /*
+ */
+
+/*define error code*/
+#ifndef errno_t
+typedef int errno_t;
+
+#endif /*
+ */
+
+/* success */
+#define EOK (0)
+
+/* invalid parameter */
+#ifndef EINVAL
+#define EINVAL (22)
+#endif /*
+ */
+
+#define EINVAL_AND_RESET (22 | 0X80)
+#define ERANGE_AND_RESET (34 | 0X80)
+
+#define SCANF_S scanf
+#define WSCANF_S wscanf
+#define VSCANF_S vscanf
+#define VWSCANF_S vwscanf
+#define FSCANF_S fscanf
+#define FWSCANF_S fwscanf
+#define VFSCANF_S vfscanf
+#define VFWSCANF_S vfwscanf
+#define SSCANF_S sscanf
+#define SWSCANF_S swscanf
+#define VSSCANF_S vsscanf
+#define VSWSCANF_S vswscanf
+
+#define SPRINTF_S(a, b, ...) sprintf(a, ##__VA_ARGS__)
+#define SWPRINTF_S(a, b, c, ...) swprintf(a, b, c, ##__VA_ARGS__)
+#define VSPRINTF_S(a, b, c, d) vsprintf(a, c, d)
+#define VSWPRINTF_S(a, b, c, d) vswprintf(a, b, c, d)
+#define VSNPRINTF_S(a, b, c, d, e) vsnprintf(a, c, d, e)
+#define SNPRINTF_S(a, b, c, d, ...) snprintf(a, c, d, ##__VA_ARGS__)
+
+#define WMEMCPY_S(a, b, c, d) ((NULL == wmemcpy(a, c, d)) ? EINVAL : EOK)
+#define MEMMOVE_S(a, b, c, d) ((NULL == memmove(a, c, d)) ? EINVAL : EOK)
+#define WMEMMOVE_S(a, b, c, d) ((NULL == wmemmove(a, c, d)) ? EINVAL : EOK)
+#define WCSCPY_S(a, b, c) ((NULL == wcscpy(a, c)) ? EINVAL : EOK)
+#define WCSNCPY_S(a, b, c, d) ((NULL == wcsncpy(a, c, d)) ? EINVAL : EOK)
+#define WCSCAT_S(a, b, c) ((NULL == wcscat(a, c)) ? EINVAL : EOK)
+#define WCSNCAT_S(a, b, c, d) ((NULL == wcsncat(a, c, d)) ? EINVAL : EOK)
+
+#define MEMSET_S(a, b, c, d) ((NULL == memset(a, c, d)) ? EINVAL : EOK)
+#define MEMCPY_S(a, b, c, d) ((NULL == memcpy(a, c, d)) ? EINVAL : EOK)
+#define STRCPY_S(a, b, c) ((NULL == strcpy(a, c )) ? EINVAL : EOK)
+#define STRNCPY_S(a, b, c, d) ((NULL == strncpy(a, c, d)) ? EINVAL : EOK)
+#define STRCAT_S(a, b, c) ((NULL == strcat(a, c)) ? EINVAL : EOK)
+#define STRNCAT_S(a, b, c, d) ((NULL == strncat(a, c, d)) ? EINVAL : EOK)
+
+#define STRTOK_S(a, b, c) strtok(a, b)
+#define WCSTOK_S(a, b, c) wcstok(a, b)
+#define GETS_S(a, b) gets(a)
+
+#else /* */
+#include "securec.h"
+
+#define SCANF_S scanf_s
+#define WSCANF_S wscanf_s
+#define VSCANF_S vscanf_s
+#define VWSCANF_S vwscanf_s
+#define FSCANF_S fscanf_s
+#define FWSCANF_S fwscanf_s
+#define VFSCANF_S vfscanf_s
+#define VFWSCANF_S vfwscanf_s
+#define SSCANF_S sscanf_s
+#define SWSCANF_S swscanf_s
+#define VSSCANF_S vsscanf_s
+#define VSWSCANF_S vswscanf_s
+
+#define SPRINTF_S(a, b, ...) sprintf_s (a, b, ##__VA_ARGS__)
+#define SWPRINTF_S(a, b, c, ...) swprintf_s(a, b, c, ##__VA_ARGS__)
+#define VSPRINTF_S(a, b, c, d) vsprintf_s(a, b, c, d)
+#define VSWPRINTF_S(a, b, c, d) vswprintf_s(a, b, c, d)
+#define VSNPRINTF_S(a, b, c, d, e) vsnprintf_s(a, b, c, d, e)
+#define SNPRINTF_S(a, b, c, d, ...) snprintf_s(a, b, c, d, ##__VA_ARGS__)
+
+#define WMEMCPY_S(a, b, c, d) wmemcpy_s(a, b, c, d)
+#define MEMMOVE_S(a, b, c, d) memmove_s(a, b, c, d)
+#define WMEMMOVE_S(a, b, c, d) wmemmove_s(a, b, c, d)
+#define WCSCPY_S(a, b, c) wcscpy_s(a, b, c)
+#define WCSNCPY_S(a, b, c, d) wcsncpy_s(a, b, c, d)
+#define WCSCAT_S(a, b, c) wcscat_s(a, b, c)
+#define WCSNCAT_S(a, b, c, d) wcsncat_s(a, b, c, d)
+
+#define MEMSET_S(a, b, c, d) memset_s(a, b, c, d)
+#define MEMCPY_S(a, b, c, d) memcpy_s(a, b, c, d)
+#define STRCPY_S(a, b, c) strcpy_s(a, b, c)
+#define STRNCPY_S(a, b, c, d) strncpy_s(a, b, c, d)
+#define STRCAT_S(a, b, c) strcat_s(a, b, c)
+#define STRNCAT_S(a, b, c, d) strncat_s(a, b, c, d)
+
+#define STRTOK_S(a, b, c) strtok_s(a, b, c)
+#define WCSTOK_S(a, b, c) wcstok_s(a, b, c)
+#define GETS_S(a, b) gets_s(a, b)
+#endif /* */
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* __NSTACK_SECUREC_H__ */
diff --git a/src/framework/include/nstack_trace.h b/src/framework/include/nstack_trace.h
new file mode 100644
index 0000000..0f4f640
--- /dev/null
+++ b/src/framework/include/nstack_trace.h
@@ -0,0 +1,76 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef __NSTACK_TRACE_H__
+#define __NSTACK_TRACE_H__
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif
+
+/*==============================================*
+ * include header files *
+ *----------------------------------------------*/
+#include "types.h"
+#include "nstack_log.h"
+#include <time.h>
+#define SPAN_NAME_MAX 64
+#define TRACE_NULL 0
+#define NSTACK_TRACE_ON 0
+#define NSTACK_TRACE_OFF 1
+
+typedef struct nst_trace_header
+{
+ u64 trace_id;
+ u64 span_pid;
+ u64 span_id; /*now us */
+ int fd;
+ int thread_id;
+} trace_hread_t;
+
+typedef struct nst_trace_fun
+{
+ u64 (*current_traceid) ();
+ void (*span_raw) (char *msg);
+ void (*tracing_enable) (int enable);
+ void (*tracing_simpling) (int frequency);
+ void (*tracing_cleanup) ();
+ void (*tracing_setup) (u32 process);
+ u64 (*tracing_string_to_traceid) (const char *input, size_t length);
+} trace_fun_t;
+
+extern __thread struct nst_trace_header strace_header;
+
+#define get_trace_header() (&strace_header)
+
+//For Tracing define own tracing feature.
+#define nstack_trace_init( a )
+#define nstack_set_tracing_contex( a,b,c)
+#define nstack_get_tracing_contex(traceid,spanid,spanpid,fd)
+#define nstack_clear_tracing_contex( )
+#define NSTACK_TRACING(level, module_name,famt,...)
+#define nstack_tracing_enalbe()
+#define nstack_get_traceid() (NULL)
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif
+
+#endif
diff --git a/src/framework/init/CMakeLists.txt b/src/framework/init/CMakeLists.txt
new file mode 100644
index 0000000..ff8d4d2
--- /dev/null
+++ b/src/framework/init/CMakeLists.txt
@@ -0,0 +1,24 @@
+#########################################################################
+#
+# Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at:
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#########################################################################
+
+SET(LIBSBR_SRC fw_init.c fw_module.c)
+
+SET(COMM_CONFIG ${PROJECT_SOURCE_DIR}/src/framework/common/base/include/common_sys_config.h)
+ADD_DEFINITIONS(-fPIC -mssse3)
+ADD_DEFINITIONS(-include ${COMM_CONFIG})
+
+ADD_LIBRARY(nStackfwinit static ${LIBSBR_SRC})
+
diff --git a/src/framework/init/fw_init.c b/src/framework/init/fw_init.c
new file mode 100644
index 0000000..6337b67
--- /dev/null
+++ b/src/framework/init/fw_init.c
@@ -0,0 +1,320 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include "nstack_securec.h"
+#include "fw_module.h"
+#include "nstack_log.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+NSTACK_STATIC int
+nsfw_module_instance_isIndepend (nsfw_module_instance_t * inst)
+{
+ nsfw_module_depends_t *dep = inst->depends;
+ while (dep)
+ {
+ if (!dep->isReady)
+ return 1;
+ dep = dep->next;
+ }
+
+ return 0;
+}
+
+NSTACK_STATIC void
+nsfw_module_instance_depend_check (nsfw_module_instance_t * inst)
+{
+ nsfw_module_instance_t *curInst = nsfw_module_getManager ()->inst;
+ while (curInst)
+ {
+ if (curInst == inst)
+ goto nextLoop;
+ if (NSFW_INST_STAT_CHECKING == curInst->stat
+ || NSFW_INST_STAT_DEPENDING == curInst->stat)
+ {
+ nsfw_module_depends_t *dep = curInst->depends;
+ while (dep)
+ {
+ if (0 == dep->isReady && 0 == strcmp (dep->name, inst->name))
+ {
+ dep->isReady = 1; /* Don't break for case that duplicate name exist, though I think it should
+ not happen */
+ }
+ dep = dep->next;
+ }
+ }
+ nextLoop:
+ curInst = curInst->next;
+ }
+
+}
+
+/**
+ * @Function nstack_framework_init
+ * @Description Init child modules
+ * @param father instance , NULL means root
+ * @return 0 on success, -1 on error
+ */
+NSTACK_STATIC int
+nstack_framework_initChild_unsafe (nsfw_module_instance_t * father)
+{
+ NSFW_LOGDBG ("init framework module] name=%s",
+ father ? father->name : "NULL");
+
+ nsfw_module_instance_t *inst = nsfw_module_getManager ()->inst;
+
+ while (inst)
+ {
+ NSFW_LOGDBG
+ ("init child] inst=%s, inst->father=%s, inst->depends=%s, inst->state=%d",
+ inst->name, inst->father ? inst->father->name : "NULL",
+ inst->depends ? inst->depends->name : "NULL", inst->stat);
+
+ if (father != inst->father)
+ {
+ NSFW_LOGDBG ("inst->father not match] inst=%s, ", inst->name);
+
+ inst = inst->next;
+ continue;
+ }
+
+ switch (inst->stat)
+ {
+ case NSFW_INST_STAT_CHECKING:
+ /* First, check if any depends, then check if other instance depends on it */
+ if (nsfw_module_instance_isIndepend (inst))
+ {
+ inst->stat = NSFW_INST_STAT_DEPENDING;
+ NSFW_LOGDBG ("inst is still depending] name=%s", inst->name);
+ inst = inst->next;
+ break;
+ }
+
+ NSFW_LOGINF ("Going to init module] name=%s, init fun=%p",
+ inst->name, inst->fnInit);
+ if (NULL != inst->fnInit && 0 != inst->fnInit (inst->param))
+ {
+ NSFW_LOGERR ("initial fail!!!] inst=%s", inst->name);
+ inst->stat = NSFW_INST_STAT_FAIL;
+ return -1;
+ }
+
+ inst->stat = NSFW_INST_STAT_DONE;
+ nsfw_module_instance_depend_check (inst);
+
+ if (-1 == nsfw_module_addDoneNode (inst))
+ {
+ NSFW_LOGERR ("add done node fail");
+ }
+
+ inst = nsfw_module_getManager ()->inst; /* check from begining */
+ break;
+ case NSFW_INST_STAT_DEPENDING:
+ /* check if depending stat is still there */
+ if (!nsfw_module_instance_isIndepend (inst))
+ {
+ inst->stat = NSFW_INST_STAT_CHECKING;
+ break;
+ }
+ case NSFW_INST_STAT_FAIL:
+ case NSFW_INST_STAT_DONE:
+ default:
+ inst = inst->next;
+ break;
+ }
+ }
+
+ return 0;
+}
+
+NSTACK_STATIC void
+nstack_framework_printInstanceInfo (nsfw_module_instance_t * inst)
+{
+
+ if (NULL == inst)
+ {
+ NSFW_LOGERR ("param error,inst==NULL");
+ return;
+ }
+
+ char info[1024] = "";
+ int plen = 0;
+
+ int ret = SPRINTF_S (info, sizeof (info), "Inst:%s,father:%s,depends:",
+ inst->name,
+ inst->father ? inst->father->name : "NULL");
+
+ if (ret <= 0)
+ {
+ NSFW_LOGERR ("Sprintf Error] module=%s,state=%d, ret=%d", inst->name,
+ inst->stat, ret);
+ return;
+ }
+ else
+ {
+ plen += ret;
+ }
+
+ if (NULL == inst->depends)
+ {
+ ret = SPRINTF_S (info + plen, sizeof (info) - plen, "NULL");
+ if (ret <= 0)
+ {
+ NSFW_LOGERR ("Sprintf Error] module=%s,state=%d, ret=%d",
+ inst->name, inst->stat, ret);
+ return;
+ }
+ NSFW_LOGINF ("] inst info=%s", info);
+ return;
+ }
+
+ nsfw_module_depends_t *dep = inst->depends;
+ while (dep)
+ {
+ ret = SPRINTF_S (info + plen, sizeof (info) - plen, "%s ", dep->name);
+ if (ret <= 0)
+ {
+ NSFW_LOGERR ("Sprintf Error] module=%s,state=%d, ret=%d",
+ inst->name, inst->stat, ret);
+ return;
+ }
+ plen += ret;
+ dep = dep->next;
+ }
+
+ NSFW_LOGINF ("] inst info=%s", info);
+}
+
+NSTACK_STATIC void
+nstack_framework_printInitialResult ()
+{
+ nsfw_module_manager_t *manager = nsfw_module_getManager ();
+
+ if (manager->doneHead)
+ {
+ NSFW_LOGINF ("Here is the initial done modules: ");
+
+ nsfw_module_doneNode_t *curNode = manager->doneHead;
+ while (curNode)
+ {
+ nstack_framework_printInstanceInfo (curNode->inst);
+ curNode = curNode->next;
+ }
+ }
+ else
+ {
+ NSFW_LOGERR ("No initial done modules");
+ }
+
+ nsfw_module_instance_t *curInst = manager->inst;
+ int unDoneNum = 0;
+ while (curInst)
+ {
+ if (curInst->stat != NSFW_INST_STAT_DONE)
+ {
+ if (0 == unDoneNum)
+ {
+ NSFW_LOGINF ("Here is the unInited modules:");
+ }
+ unDoneNum++;
+ nstack_framework_printInstanceInfo (curInst);
+ }
+ curInst = curInst->next;
+ }
+ if (0 == unDoneNum)
+ NSFW_LOGINF ("All modules are inited");
+}
+
+/**
+ * @Function nstack_framework_init
+ * @Description This function will do framework initial work, it will involk all initial functions
+ * registed using macro NSFW_MODULE_INIT before
+ * @param none
+ * @return 0 on success, -1 on error
+ */
+int
+nstack_framework_init (void)
+{
+ int ret = -1;
+ if (nsfw_module_getManager ()->done)
+ {
+ goto init_finished;
+ }
+
+ if (pthread_mutex_lock (&nsfw_module_getManager ()->initMutex))
+ {
+ return -1;
+ }
+
+ if (nsfw_module_getManager ()->done)
+ {
+ goto done;
+ }
+
+ ret = nstack_framework_initChild_unsafe (NULL);
+
+ if (0 == ret)
+ {
+ nsfw_module_getManager ()->done = 1;
+ }
+ else
+ {
+ nsfw_module_getManager ()->done = -1;
+ }
+
+ // Going to print done modules and undone modules
+ nstack_framework_printInitialResult ();
+
+done:
+ if (pthread_mutex_unlock (&nsfw_module_getManager ()->initMutex))
+ {
+ return -1;
+ }
+init_finished:
+ ret = nsfw_module_getManager ()->done == 1 ? 0 : -1;
+ return ret;
+}
+
+/**
+ * @Function nstack_framework_setModuleParam
+ * @Description This function set parameter of module initial function parameter
+ * @param module - name of module
+ * @param param - parameter to set
+ * @return 0 on success, -1 on error
+ */
+int
+nstack_framework_setModuleParam (char *module, void *param)
+{
+ nsfw_module_instance_t *inst = nsfw_module_getModuleByName (module);
+ if (!inst)
+ return -1;
+
+ inst->param = param;
+ return 0;
+}
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/init/fw_module.c b/src/framework/init/fw_module.c
new file mode 100644
index 0000000..65bbb0a
--- /dev/null
+++ b/src/framework/init/fw_module.c
@@ -0,0 +1,331 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <memory.h>
+#include <string.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include "nstack_securec.h"
+#include "fw_module.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+COMPAT_PROTECT (NSFW_MOUDLE_INSTANCE_POOL_SIZE, 64);
+COMPAT_PROTECT (NSFW_MOUDLE_DEPENDS_POOL_SIZE, 128);
+
+nsfw_module_instance_pool_t g_nsfw_module_inst_pool;
+nsfw_module_depends_pool_t g_nsfw_module_deps_pool;
+
+/*
+* WARNING!!!:
+* This function is only used in constructor progress. Multi-thread concurrent is not supported!
+*/
+NSTACK_STATIC nsfw_module_instance_t *
+nsfw_module_malloc_instance ()
+{
+ if (g_nsfw_module_inst_pool.last_idx >= NSFW_MOUDLE_INSTANCE_POOL_SIZE)
+ {
+ return NULL;
+ }
+ return
+ &g_nsfw_module_inst_pool.module_instance_pool[g_nsfw_module_inst_pool.
+ last_idx++];
+}
+
+/*
+* WARNING!!!:
+* This function is only used in constructor progress. Multi-thread concurrent is not supported!
+*/
+NSTACK_STATIC nsfw_module_depends_t *
+nsfw_module_malloc_depends ()
+{
+ if (g_nsfw_module_deps_pool.last_idx >= NSFW_MOUDLE_DEPENDS_POOL_SIZE)
+ {
+ return NULL;
+ }
+ return
+ &g_nsfw_module_deps_pool.module_depends_pool[g_nsfw_module_deps_pool.
+ last_idx++];
+}
+
+NSTACK_STATIC void
+nsfw_module_setChildInstance (nsfw_module_instance_t *
+ father, nsfw_module_instance_t * child)
+{
+ if (NULL == father || NULL == child)
+ return;
+ child->father = father;
+}
+
+nsfw_module_depends_t *
+nsfw_module_create_depends (char *name)
+{
+ if (NULL == name)
+ return NULL;
+
+ /*Change module malloc to pool array */
+ nsfw_module_depends_t *dep = nsfw_module_malloc_depends ();
+
+ if (NULL == dep)
+ return NULL;
+
+ if (EOK !=
+ MEMSET_S (dep, sizeof (nsfw_module_depends_t), 0,
+ sizeof (nsfw_module_depends_t)))
+ {
+ goto fail;
+ }
+
+ /*change destMax from nameSize - 1 to sizeof(dep->name) */
+ if (EOK != STRCPY_S (dep->name, sizeof (dep->name), name))
+ {
+ goto fail;
+ }
+ dep->isReady = 0;
+
+ return dep;
+
+fail:
+ // NOTE: if dep is not null, we do not free it and just leave it there.
+ return NULL;
+}
+
+nsfw_module_instance_t *
+nsfw_module_create_instance (void)
+{
+ /*Change module malloc to pool array */
+ nsfw_module_instance_t *inst = nsfw_module_malloc_instance ();
+ if (NULL == inst)
+ return NULL;
+
+ if (EOK !=
+ MEMSET_S (inst, sizeof (nsfw_module_instance_t), 0,
+ sizeof (nsfw_module_instance_t)))
+ {
+ // NOTE: if inst is not null, we do not free it and just leave it there.
+ return NULL;
+ }
+
+ inst->stat = NSFW_INST_STAT_CHECKING;
+ return inst;
+}
+
+void
+nsfw_module_set_instance_name (nsfw_module_instance_t * inst, char *name)
+{
+ if (NULL == inst || NULL == name || inst->name[0] != '\0')
+ {
+ return;
+ }
+
+ /*change destMax from nameSize - 1 to sizeof(inst->name) */
+ if (EOK != STRCPY_S (inst->name, sizeof (inst->name), name))
+ {
+ return;
+ }
+
+ // Now we need to search if it's any instance's father
+ nsfw_module_instance_t *curInst = nsfw_module_getManager ()->inst;
+ while (curInst)
+ {
+ if (curInst == inst)
+ goto next_loop;
+
+ if (0 == strcmp (curInst->fatherName, inst->name)
+ && NULL == curInst->father)
+ {
+ nsfw_module_setChildInstance (inst, curInst);
+ }
+ next_loop:
+ curInst = curInst->next;
+ }
+ return;
+}
+
+void
+nsfw_module_set_instance_father (nsfw_module_instance_t * inst,
+ char *fatherName)
+{
+ if (NULL == inst || NULL == fatherName)
+ {
+ return;
+ }
+
+ if (EOK !=
+ STRCPY_S (inst->fatherName, sizeof (inst->fatherName), fatherName))
+ {
+ return;
+ }
+
+ nsfw_module_instance_t *fatherInst =
+ nsfw_module_getModuleByName (fatherName);
+ if (fatherInst)
+ {
+ nsfw_module_setChildInstance (fatherInst, inst);
+ }
+ return;
+}
+
+void
+nsfw_module_set_instance_priority (nsfw_module_instance_t * inst,
+ int priority)
+{
+ if (NULL == inst)
+ return;
+ inst->priority = priority;
+
+ nsfw_module_del_instance (inst);
+ nsfw_module_add_instance (inst);
+ return;
+}
+
+void
+nsfw_module_set_instance_initfn (nsfw_module_instance_t * inst,
+ nsfw_module_init_fn fn)
+{
+ if (NULL == inst)
+ return;
+ inst->fnInit = fn;
+ return;
+}
+
+void
+nsfw_module_set_instance_depends (nsfw_module_instance_t * inst, char *name)
+{
+ if (NULL == inst || name == NULL)
+ return;
+
+ // Check if depends already set
+ nsfw_module_depends_t *dep = inst->depends;
+ while (dep)
+ {
+ if (0 == strcmp (dep->name, name))
+ return;
+ dep = dep->next;
+ }
+
+ dep = nsfw_module_create_depends (name);
+ if (NULL == dep)
+ return;
+
+ if (NULL == inst->depends)
+ inst->depends = dep;
+ else
+ inst->depends->next = dep;
+}
+
+/* *INDENT-OFF* */
+nsfw_module_manager_t g_nsfw_module_manager = {.inst = NULL, .initMutex =
+ PTHREAD_MUTEX_INITIALIZER, .done = 0};
+/* *INDENT-ON* */
+
+void
+nsfw_module_add_instance (nsfw_module_instance_t * inst)
+{
+ nsfw_module_instance_t *curInst = nsfw_module_getManager ()->inst;
+
+ if (NULL == curInst || curInst->priority > inst->priority)
+ {
+ inst->next = curInst;
+ nsfw_module_getManager ()->inst = inst;
+ }
+ else
+ {
+ while (curInst->next && curInst->next->priority <= inst->priority)
+ {
+ curInst = curInst->next;
+ }
+ inst->next = curInst->next;
+ curInst->next = inst;
+ }
+}
+
+void
+nsfw_module_del_instance (nsfw_module_instance_t * inst)
+{
+ if (nsfw_module_getManager ()->inst == inst)
+ {
+ nsfw_module_getManager ()->inst = inst->next;
+ return;
+ }
+
+ nsfw_module_instance_t *curInst = nsfw_module_getManager ()->inst;
+
+ while (curInst->next && curInst->next != inst)
+ curInst = curInst->next;
+
+ if (!curInst->next)
+ return;
+ curInst->next = inst->next;
+}
+
+nsfw_module_instance_t *
+nsfw_module_getModuleByName (char *name)
+{
+ if (NULL == name)
+ return NULL;
+
+ nsfw_module_instance_t *curInst = nsfw_module_getManager ()->inst;
+ while (curInst)
+ {
+ if (0 == strcmp (curInst->name, name))
+ {
+ return curInst;
+ }
+ curInst = curInst->next;
+ }
+
+ return NULL;
+}
+
+int
+nsfw_module_addDoneNode (nsfw_module_instance_t * inst)
+{
+ nsfw_module_doneNode_t *node =
+ (nsfw_module_doneNode_t *) malloc (sizeof (nsfw_module_doneNode_t));
+ if (NULL == node)
+ return -1;
+ node->inst = inst;
+ node->next = NULL;
+
+ nsfw_module_manager_t *manager = nsfw_module_getManager ();
+ if (NULL == manager->doneHead)
+ {
+ manager->doneHead = node;
+ }
+ else
+ {
+ nsfw_module_doneNode_t *tail = manager->doneHead;
+ while (tail->next)
+ {
+ tail = tail->next;
+ }
+
+ tail->next = node;
+ }
+
+ return 0;
+}
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/init/fw_module.h b/src/framework/init/fw_module.h
new file mode 100644
index 0000000..1cfc95f
--- /dev/null
+++ b/src/framework/init/fw_module.h
@@ -0,0 +1,85 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _FW_MODULE
+#define _FW_MODULE
+#include <pthread.h>
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* _cplusplus */
+
+#include "nsfw_init.h"
+
+/* Unique name declare */
+#define NSFW__STRINGIFY(x) #x
+#define NSFW_STRINGIFY(x) NSFW__STRINGIFY(x)
+
+#define NSFW__PASTE(a,b) a##b
+#define NSFW_PASTE(a,b) NSFW__PASTE(a,b)
+
+#define NSFW_UNIQUE_ID(prefix) NSFW_PASTE(NSFW_PASTE(__LINE__, prefix), __COUNTER__)
+
+#define NSFW_MODULE_INITFN(_fn) \
+ static int _fn(void* param)
+extern nsfw_module_depends_t *nsfw_module_create_depends (char *name);
+
+#define NSFW_MODULE_SET_STATE(inst, state) ((inst)->stat = (state))
+
+typedef struct _nsfw_module_doneNode
+{
+ nsfw_module_instance_t *inst;
+ struct _nsfw_module_doneNode *next;
+} nsfw_module_doneNode_t;
+
+typedef struct _nsfw_module_manager
+{
+ pthread_mutex_t initMutex;
+ int done; // 0 - not finished, 1 - finished, -1 - error
+ nsfw_module_instance_t *inst;
+ nsfw_module_doneNode_t *doneHead;
+} nsfw_module_manager_t;
+
+extern int nsfw_module_addDoneNode (nsfw_module_instance_t * inst);
+
+extern nsfw_module_manager_t g_nsfw_module_manager;
+#define nsfw_module_getManager() (&g_nsfw_module_manager)
+
+#define NSFW_MOUDLE_INSTANCE_POOL_SIZE 64
+#define NSFW_MOUDLE_DEPENDS_POOL_SIZE 128
+
+typedef struct _nsfw_module_instance_pool
+{
+ int last_idx;
+ nsfw_module_instance_t
+ module_instance_pool[NSFW_MOUDLE_INSTANCE_POOL_SIZE];
+} nsfw_module_instance_pool_t;
+
+typedef struct _nsfw_module_depends_pool
+{
+ int last_idx;
+ nsfw_module_depends_t module_depends_pool[NSFW_MOUDLE_DEPENDS_POOL_SIZE];
+} nsfw_module_depends_pool_t;
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* _cplusplus */
+
+#endif /* _FW_MODULE */
diff --git a/src/framework/ipc/mgr_com/mgr_com.c b/src/framework/ipc/mgr_com/mgr_com.c
new file mode 100644
index 0000000..4a57d6a
--- /dev/null
+++ b/src/framework/ipc/mgr_com/mgr_com.c
@@ -0,0 +1,2037 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+/*==============================================*
+ * include header files *
+ *----------------------------------------------*/
+
+#include "types.h"
+#include "nstack_securec.h"
+#include "nsfw_init.h"
+#include "common_mem_api.h"
+
+#include "nsfw_mgr_com_api.h"
+#include "mgr_com.h"
+#include "nstack_log.h"
+#include "nsfw_base_linux_api.h"
+
+#include <sys/un.h>
+#include <stddef.h>
+#include <sys/epoll.h>
+#include <fcntl.h>
+
+#include "nsfw_maintain_api.h"
+#include "nsfw_ps_api.h"
+#include "nsfw_fd_timer_api.h"
+
+#include "common_func.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+/* *INDENT-OFF* */
+
+/* *INDENT-OFF* */
+nsfw_mgr_msg_fun g_mgr_fun[MGR_MSG_MAX][NSFW_MGRCOM_MAX_PROC_FUN];
+nsfw_mgr_init_cfg g_mgr_com_cfg;
+nsfw_mgr_sock_map g_mgr_sockt_map = {{0}, NULL};
+nsfw_mgrcom_stat g_mgr_stat;
+nsfw_mgrcom_proc g_ep_proc = { 0 };
+/* *INDENT-ON* */
+
+u32 g_mgr_sockfdmax = NSFW_MGRCOM_MAX_SOCKET;
+
+char g_proc_info[NSFW_PROC_MAX][NSTACK_MAX_PROC_NAME_LEN] = {
+ "", "nStackMain", "nStackMaster", "nStackLib", "nStackTools", "nStackCtrl",
+ "", "", "", "", "", "", "", "", "", ""
+};
+
+/* *INDENT-ON* */
+
+int g_thread_policy = 0;
+int g_thread_pri = 0;
+
+void
+nsfw_com_attr_set (int policy, int pri)
+{
+ g_thread_policy = policy;
+ g_thread_pri = pri;
+}
+
+char *
+nsfw_get_proc_name (u8 proc_type)
+{
+ if (proc_type >= NSFW_PROC_MAX || NSFW_PROC_NULL == proc_type)
+ {
+ return NULL;
+ }
+
+ return g_proc_info[proc_type];
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_reg_msg_fun
+* Description : reg the callback funciton when receive new message
+* Input : u16 msg_type
+* nsfw_mgr_msg_fun fun
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_mgr_reg_msg_fun (u16 msg_type, nsfw_mgr_msg_fun fun)
+{
+ u32 i;
+ if (MGR_MSG_MAX <= msg_type)
+ {
+ NSFW_LOGERR ("reg mgr_msg]msg_type=%u,fun=%p", msg_type, fun);
+ return FALSE;
+ }
+
+ for (i = 0; i < NSFW_MGRCOM_MAX_PROC_FUN; i++)
+ {
+ if (NULL == g_mgr_fun[msg_type][i])
+ {
+ /*TODO should use cas */
+ g_mgr_fun[msg_type][i] = fun;
+ NSFW_LOGINF ("reg mgr_msg fun suc]msg_type=%u,fun=%p", msg_type,
+ fun);
+ return TRUE;
+ }
+ }
+
+ NSFW_LOGERR ("reg mgr_msg type full]msg_type=%u,fun=%p", msg_type, fun);
+ return FALSE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_null_rspmsg_alloc
+* Description : alloc null response msg for receive message buffer
+* Input : None
+* Output : None
+* Return Value : nsfw_mgr_msg*
+* Calls :
+* Called By :
+*****************************************************************************/
+nsfw_mgr_msg *
+nsfw_mgr_null_rspmsg_alloc ()
+{
+ return nsfw_mgr_msg_alloc (MGR_MSG_NULL, NSFW_PROC_NULL);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_msg_alloc
+* Description : alloc new request message to send
+* Input : u16 msg_type
+* u8 dst_proc_type
+* Output : None
+* Return Value : nsfw_mgr_msg*
+* Calls :
+* Called By :
+*****************************************************************************/
+nsfw_mgr_msg *
+nsfw_mgr_msg_alloc (u16 msg_type, u8 dst_proc_type)
+{
+ nsfw_mgr_msg *p_msg = NULL;
+ u8 from_mem_flag = FALSE;
+ u32 alloc_len = sizeof (nsfw_mgr_msg);
+
+ if (MGR_MSG_LAG_QRY_RSP_BEGIN <= msg_type)
+ {
+ from_mem_flag = TRUE;
+ alloc_len = NSFW_MGR_LARGE_MSG_LEN;
+ }
+
+ if ((NULL == g_mgr_com_cfg.msg_pool)
+ && (MGR_MSG_INIT_NTY_REQ == msg_type
+ || MGR_MSG_INIT_NTY_RSP == msg_type))
+ {
+ from_mem_flag = TRUE;
+ }
+
+ if (FALSE == from_mem_flag)
+ {
+ if (0 ==
+ nsfw_mem_ring_dequeue (g_mgr_com_cfg.msg_pool, (void *) &p_msg))
+ {
+ NSFW_LOGERR ("alloc msg full]type=%u,dst=%u", msg_type,
+ dst_proc_type);
+ return NULL;
+ }
+ alloc_len = sizeof (nsfw_mgr_msg);
+ }
+ else
+ {
+ p_msg = (nsfw_mgr_msg *) malloc (alloc_len);
+ }
+
+ if (NULL == p_msg)
+ {
+ NSFW_LOGERR ("alloc msg nul]type=%u,dst=%u", msg_type, dst_proc_type);
+ return NULL;
+ }
+
+ if (EOK != MEMSET_S (p_msg, alloc_len, 0, alloc_len))
+ {
+ p_msg->from_mem = from_mem_flag;
+ nsfw_mgr_msg_free (p_msg);
+ NSFW_LOGERR ("alloc msg MEMSET_S failed]type=%u,dst=%u", msg_type,
+ dst_proc_type);
+ return NULL;
+ }
+ p_msg->from_mem = from_mem_flag;
+
+ if (msg_type < MGR_MSG_RSP_BASE && msg_type > 0)
+ {
+ p_msg->seq = common_mem_atomic32_add_return (&g_mgr_com_cfg.cur_idx, 1);
+ }
+
+ p_msg->from_mem = from_mem_flag;
+ p_msg->msg_type = msg_type;
+ p_msg->src_pid = get_sys_pid ();
+ p_msg->src_proc_type = g_mgr_com_cfg.proc_type;
+ p_msg->msg_len = alloc_len;
+ p_msg->dst_proc_type = dst_proc_type;
+ p_msg->alloc_flag = TRUE;
+ p_msg->more_msg_flag = 0;
+
+ g_mgr_stat.msg_alloc++;
+ return p_msg;
+}
+
+static inline void
+lint_lock_1 ()
+{
+ return;
+}
+
+static inline void
+lint_unlock_1 ()
+{
+ return;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_rsp_msg_alloc
+* Description : alloc response message from request message
+* Input : nsfw_mgr_msg* req_msg
+* Output : None
+* Return Value : nsfw_mgr_msg*
+* Calls :
+* Called By :
+*****************************************************************************/
+nsfw_mgr_msg *
+nsfw_mgr_rsp_msg_alloc (nsfw_mgr_msg * req_msg)
+{
+ nsfw_mgr_msg *p_msg = NULL;
+ if (NULL == req_msg)
+ {
+ NSFW_LOGERR ("req msg nul!");
+ return NULL;
+ }
+
+ p_msg =
+ nsfw_mgr_msg_alloc (req_msg->msg_type + MGR_MSG_RSP_BASE,
+ req_msg->src_proc_type);
+ if (NULL == p_msg)
+ {
+ return NULL;
+ }
+
+ p_msg->dst_pid = req_msg->src_pid;
+ p_msg->seq = req_msg->seq;
+ return p_msg;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_msg_free
+* Description : message free
+* Input : nsfw_mgr_msg *msg
+* Output : None
+* Return Value : void
+* Calls :
+* Called By :
+*****************************************************************************/
+void
+nsfw_mgr_msg_free (nsfw_mgr_msg * msg)
+{
+ if (NULL == msg)
+ {
+ return;
+ }
+
+ if (FALSE == msg->alloc_flag)
+ {
+ NSFW_LOGERR ("msg refree]msg=%p, type=%u", msg, msg->msg_type);
+ return;
+ }
+
+ msg->alloc_flag = FALSE;
+
+ if (TRUE == msg->from_mem)
+ {
+ if ((MGR_MSG_INIT_NTY_REQ == msg->msg_type
+ || MGR_MSG_INIT_NTY_RSP == msg->msg_type)
+ || (MGR_MSG_LAG_QRY_RSP_BEGIN <= msg->msg_type))
+ {
+ free (msg);
+ g_mgr_stat.msg_free++;
+ return;
+ }
+ NSFW_LOGERR ("msg err free]type=%u", msg->msg_type);
+ }
+
+ if (0 == nsfw_mem_ring_enqueue (g_mgr_com_cfg.msg_pool, msg))
+ {
+ NSFW_LOGERR ("msg free failed pool full]msg=%p, type=%u", msg,
+ msg->msg_type);
+ return;
+ }
+
+ g_mgr_stat.msg_free++;
+ return;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_get_listen_socket
+* Description : get domain socket listen fd
+* Input : None
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_mgr_get_listen_socket ()
+{
+ i32 fd, len;
+ struct sockaddr_un un;
+
+ if ((fd = nsfw_base_socket (AF_UNIX, SOCK_STREAM, 0)) < 0)
+ {
+ NSFW_LOGERR ("create sock failed!");
+ return -1;
+ }
+
+ if (-1 == unlink ((char *) g_mgr_com_cfg.domain_path))
+ {
+ NSFW_LOGWAR ("unlink failed]error=%d", errno);
+ }
+ if (EOK != MEMSET_S (&un, sizeof (un), 0, sizeof (un)))
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("create sock MEMSET_S failed!] error=%d", errno);
+ return -1;
+ }
+
+ un.sun_family = AF_UNIX;
+ int retVal = STRCPY_S ((char *) un.sun_path, sizeof (un.sun_path),
+ (char *) g_mgr_com_cfg.domain_path);
+ if (EOK != retVal)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("create sock STRCPY_S failed!] error=%d", errno);
+ return -1;
+ }
+
+ int rc = nsfw_set_close_on_exec (fd);
+ if (rc == -1)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("set exec err]fd=%d, errno=%d", fd, errno);
+ return -1;
+ }
+
+ len =
+ offsetof (struct sockaddr_un,
+ sun_path) +strlen ((char *) g_mgr_com_cfg.domain_path);
+
+ if (nsfw_base_bind (fd, (struct sockaddr *) &un, len) < 0)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("bind failed!]mgr_fd=%d,error=%d", fd, errno);
+ return -1;
+ }
+
+ if (nsfw_base_listen (fd, 10) < 0)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("listen failed!]mgr_fd=%d,error=%d", fd, errno);
+ return -1;
+ }
+
+ NSFW_LOGINF ("mgr com start with]mgr_fd=%d", fd);
+ return fd;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_get_connect_socket
+* Description : get new connect fd to destination procedure
+* Input : u8 proc_type
+* u32 host_pid
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_mgr_get_connect_socket (u8 proc_type, u32 host_pid)
+{
+ i32 fd, len;
+ char *name;
+ struct sockaddr_un un;
+ const char *directory = NSFW_DOMAIN_DIR;
+ const char *home_dir = getenv ("HOME");
+
+ if (getuid () != 0 && home_dir != NULL)
+ directory = home_dir;
+
+ switch (proc_type)
+ {
+ case NSFW_PROC_MAIN:
+ name = NSFW_MAIN_FILE;
+ break;
+ case NSFW_PROC_MASTER:
+ name = NSFW_MASTER_FILE;
+ break;
+ case NSFW_PROC_ALARM:
+ directory = "/tmp";
+ name = NSFW_ALARM_FILE;
+ break;
+ default:
+ NSFW_LOGERR ("get dst socket err]type=%u,pid=%u", proc_type, host_pid);
+ return -1;
+ }
+
+ if ((fd = nsfw_base_socket (AF_UNIX, SOCK_STREAM, 0)) < 0)
+ {
+ NSFW_LOGERR ("create socket err]type=%u,pid=%u,errno=%d", proc_type,
+ host_pid, errno);
+ return -1;
+ }
+
+ if (EOK != MEMSET_S (&un, sizeof (un), 0, sizeof (un)))
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("get dst socket err]mgr_fd=%d,type=%u,pid=%u", fd,
+ proc_type, host_pid);
+ return -1;
+ }
+
+ struct timeval tv;
+ tv.tv_sec = MGR_COM_RECV_TIMEOUT;
+ tv.tv_usec = 0;
+ if (nsfw_base_setsockopt
+ (fd, SOL_SOCKET, SO_RCVTIMEO, (char *) &tv, sizeof tv))
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("setsockopt socket err]mgr_fd=%d,type=%u,pid=%u", fd,
+ proc_type, host_pid);
+ return -1;
+ }
+
+ int rc = nsfw_set_close_on_exec (fd);
+ if (rc == -1)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("set exec err]fd=%d, errno=%d", fd, errno);
+ return -1;
+ }
+
+ int size, size_len;
+ size = MAX_RECV_BUF_DEF;
+ size_len = sizeof (size);
+ if (0 >
+ nsfw_base_setsockopt (fd, SOL_SOCKET, SO_RCVBUF, (void *) &size,
+ (socklen_t) size_len))
+ {
+ NSFW_LOGERR ("set socket opt err!]error=%d", errno);
+ }
+
+ if (0 >
+ nsfw_base_setsockopt (fd, SOL_SOCKET, SO_SNDBUF, (void *) &size,
+ (socklen_t) size_len))
+ {
+ NSFW_LOGERR ("set socket opt err!]error=%d", errno);
+ }
+
+ un.sun_family = AF_UNIX;;
+ int retVal = STRCPY_S ((char *) un.sun_path, sizeof (un.sun_path),
+ (char *) directory);
+ if (EOK != retVal)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("create sock STRCPY_S failed!] error=%d", errno);
+ return -1;
+ }
+
+ retVal = STRCAT_S (un.sun_path, sizeof (un.sun_path), name);
+ if (EOK != retVal)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR ("create sock STRCAT_S failed!] error=%d", errno);
+ return -1;
+ }
+
+ len = offsetof (struct sockaddr_un, sun_path) +strlen (un.sun_path);
+ if (nsfw_base_connect (fd, (struct sockaddr *) &un, len) < 0)
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGERR
+ ("create socket err]mgr_fd=%d,type=%u,pid=%u,errno=%d,path=%s", fd,
+ proc_type, host_pid, errno, un.sun_path);
+ return -1;
+ }
+
+ NSFW_LOGINF ("get dst socket]mgr_fd=%d,type=%u,pid=%u", fd, proc_type,
+ host_pid);
+ return (fd);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_new_socket
+* Description : management the new fd to cache
+* Input : u32 fd
+* u8 proc_type
+* u32 host_pid
+* Output : None
+* Return Value : static inline u8
+* Calls :
+* Called By :
+*****************************************************************************/
+NSTACK_STATIC inline u8
+nsfw_mgr_new_socket (i32 fd, u8 proc_type, u32 host_pid)
+{
+ nsfw_mgr_sock_info *sock_info = NULL;
+ if (((i32) NSFW_MGR_FD_MAX <= fd) || (fd < 0) || (!g_mgr_sockt_map.sock))
+ {
+ NSFW_LOGERR ("fd err]mgr_fd=%d, sock=%p", fd, g_mgr_sockt_map.sock);
+ return FALSE;
+ }
+
+ sock_info = &g_mgr_sockt_map.sock[fd];
+ if (host_pid != sock_info->host_pid)
+ {
+ NSFW_LOGDBG
+ ("update sock info]mgr_fd=%d,old_pid=%u,new_pid=%u,type=%u", fd,
+ sock_info->host_pid, host_pid, proc_type);
+ }
+
+ sock_info->host_pid = host_pid;
+ sock_info->proc_type = proc_type;
+
+ if (proc_type < NSFW_PROC_MAX)
+ {
+ g_mgr_sockt_map.proc_cache[proc_type] = fd;
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_del_socket
+* Description : delete the fd from cache when fd close
+* Input : u32 fd
+* Output : None
+* Return Value : static inline u8
+* Calls :
+* Called By :
+*****************************************************************************/
+NSTACK_STATIC inline u8
+nsfw_mgr_del_socket (u32 fd)
+{
+ nsfw_mgr_sock_info *sock_info = NULL;
+ if ((NSFW_MGR_FD_MAX <= fd) || (!g_mgr_sockt_map.sock))
+ {
+ NSFW_LOGERR ("fd err]mgr_fd=%u, sock=%p", fd, g_mgr_sockt_map.sock);
+ return FALSE;
+ }
+
+ sock_info = &g_mgr_sockt_map.sock[fd];
+
+ if (sock_info->proc_type < NSFW_PROC_MAX
+ && fd == g_mgr_sockt_map.proc_cache[sock_info->proc_type])
+ {
+ g_mgr_sockt_map.proc_cache[sock_info->proc_type] = 0;
+ }
+
+ NSFW_LOGDBG ("del sock]mgr_fd=%u,type=%u,pid=%u", fd,
+ sock_info->proc_type, sock_info->host_pid);
+ sock_info->host_pid = 0;
+ sock_info->proc_type = 0;
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_get_dst_socket
+* Description : get the fd to send message to destination procedure
+* Input : u8 proc_type
+* u32 dst_pid
+* Output : None
+* Return Value : static inline i32
+* Calls :
+* Called By :
+*****************************************************************************/
+NSTACK_STATIC inline i32
+nsfw_mgr_get_dst_socket (u8 proc_type, u32 dst_pid)
+{
+ i32 fd = -1;
+
+ nsfw_mgr_sock_info *sock_info = NULL;
+
+ if (proc_type < NSFW_PROC_MAX)
+ {
+ fd = g_mgr_sockt_map.proc_cache[proc_type];
+ }
+
+ if (!g_mgr_sockt_map.sock)
+ {
+ return -1;
+ }
+
+ if (fd > 0 && fd < (i32) NSFW_MGR_FD_MAX)
+ {
+ sock_info = &g_mgr_sockt_map.sock[fd];
+ if (sock_info->host_pid != 0)
+ {
+ if (0 == dst_pid || dst_pid == sock_info->host_pid)
+ {
+ return fd;
+ }
+ }
+ else if (proc_type == sock_info->proc_type)
+ {
+ return fd;
+ }
+ }
+
+ i32 i;
+ for (i = 0; i < (i32) NSFW_MGR_FD_MAX; i++)
+ {
+ sock_info = &g_mgr_sockt_map.sock[i];
+ if (sock_info->host_pid != 0 && proc_type == sock_info->proc_type)
+ {
+ if (0 == dst_pid || dst_pid == sock_info->host_pid)
+ {
+ return i;
+ }
+ }
+ }
+
+ return -1;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_get_new_socket
+* Description : get new connect
+* Input : u8 proc_type
+* u32 dst_pid
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_mgr_get_new_socket (u8 proc_type, u32 dst_pid)
+{
+ i32 fd = 0;
+ fd = nsfw_mgr_get_connect_socket (proc_type, dst_pid);
+ if (fd > 0)
+ {
+ (void) nsfw_mgr_new_socket (fd, proc_type, dst_pid);
+ (void) nsfw_mgr_reg_sock_fun (fd, nsfw_mgr_new_msg);
+ }
+ return fd;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_clr_fd_lock
+* Description : clear the fd lock when fork in child proc
+* Input : None
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_mgr_clr_fd_lock ()
+{
+ i32 i;
+ if (!g_mgr_sockt_map.sock)
+ {
+ NSFW_LOGERR ("clr fd lock fail, sock is null");
+ return FALSE;
+ }
+ for (i = 0; i < (i32) NSFW_MGR_FD_MAX; i++)
+ {
+ common_mem_spinlock_init (&(g_mgr_sockt_map.sock[i].opr_lock));
+ }
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_close_dst_proc
+* Description : close the remote connect
+* Input : u8 proc_type
+* u32 dst_pid
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+void
+nsfw_mgr_close_dst_proc (u8 proc_type, u32 dst_pid)
+{
+ i32 fd = nsfw_mgr_get_dst_socket (proc_type, dst_pid);
+ if (fd > 0)
+ {
+ (void) nsfw_mgr_del_socket (fd);
+ (void) nsfw_mgr_unreg_sock_fun (fd);
+ (void) nsfw_base_close (fd);
+ }
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_send_msg_socket
+* Description : send message to dst fd
+* Input : u32 fd
+* nsfw_mgr_msg* msg
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_mgr_send_msg_socket (u32 fd, nsfw_mgr_msg * msg)
+{
+ i32 send_len = 0;
+ i32 off_set = 0;
+
+ if (NULL == msg)
+ {
+ NSFW_LOGERR ("msg nul]mgr_fd=%u", fd);
+ return FALSE;
+ }
+
+ if (msg->msg_len < sizeof (nsfw_mgr_msg))
+ {
+ msg->msg_len = sizeof (nsfw_mgr_msg);
+ }
+
+ if (msg->msg_type == MGR_MSG_LARGE_ALARM_RSP)
+ {
+ off_set = NSFW_MGR_MSG_HDR_LEN;
+ }
+
+ /*TODO if closed by peer, may send failed, should close this fd */
+ do
+ {
+ off_set += send_len;
+ send_len =
+ nsfw_base_send (fd, (char *) msg + off_set, msg->msg_len - off_set,
+ MSG_NOSIGNAL);
+ if (send_len <= 0)
+ {
+ NSFW_LOGERR
+ ("send error]mgr_fd=%u,send_len=%d,off_set=%d,errno=%d" MSGINFO,
+ fd, send_len, off_set, errno, PRTMSG (msg));
+ return FALSE;
+ }
+ }
+ while ((send_len + off_set) < (i32) msg->msg_len);
+ NSFW_LOGDBG ("send mgr_msg suc]mgr_fd=%u," MSGINFO, fd, PRTMSG (msg));
+ g_mgr_stat.msg_send[msg->msg_type]++;
+ return TRUE;
+}
+
+#define MAX_RECV_COUNT 100
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_recv_msg_socket
+* Description : receive new message from fd
+* Input : u32 fd
+* nsfw_mgr_msg* msg
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_mgr_recv_msg_socket (u32 fd, nsfw_mgr_msg * msg,
+ nsfw_mgr_msg ** large_msg)
+{
+ i32 recv_len = 0;
+ i32 off_set = 0;
+ u32 msg_len = 0;
+ i32 max_count = 0;
+ if (NULL == msg)
+ {
+ return FALSE;
+ }
+
+ u8 from_flag = msg->from_mem;
+ msg_len = msg->msg_len;
+ do
+ {
+ off_set += recv_len;
+ recv_len =
+ nsfw_base_recv (fd, (char *) msg + off_set, msg_len - off_set, 0);
+ if (recv_len <= 0)
+ {
+ if ((EINTR == errno || EAGAIN == errno)
+ && (max_count < MAX_RECV_COUNT))
+ {
+ recv_len = 0;
+ max_count++;
+ continue;
+ }
+
+ NSFW_LOGERR
+ ("recv error]mgr_fd=%u,recv_len=%d,off_set=%d,errno=%d,"
+ MSGINFO, fd, recv_len, off_set, errno, PRTMSG (msg));
+ msg->from_mem = from_flag;
+ return FALSE;
+ }
+ }
+ while (recv_len + off_set < (i32) msg_len);
+
+ msg->from_mem = from_flag;
+
+ g_mgr_stat.msg_recv[msg->msg_type]++;
+
+ if (msg->msg_len <= msg_len)
+ {
+ NSFW_LOGDBG ("recv mgr_msg suc]mgr_fd=%u," MSGINFO, fd, PRTMSG (msg));
+ return TRUE;
+ }
+
+ if (large_msg == NULL)
+ {
+ return TRUE;
+ }
+
+ nsfw_mgr_msg *l_msg =
+ nsfw_mgr_msg_alloc (msg->msg_type, msg->dst_proc_type);
+ if (NULL == l_msg)
+ {
+ return TRUE;
+ }
+
+ if (l_msg->msg_len <= msg_len)
+ {
+ NSFW_LOGWAR ("alloc new msg error!]len=%u,org_len=%u,type=%u",
+ l_msg->msg_len, msg->msg_len, msg->msg_type);
+ nsfw_mgr_msg_free (l_msg);
+ return TRUE;
+ }
+
+ max_count = 0;
+ (void) nsfw_set_sock_block (fd, FALSE);
+ from_flag = l_msg->from_mem;
+ u32 l_msg_len = l_msg->msg_len;
+ do
+ {
+ off_set += recv_len;
+ recv_len =
+ nsfw_base_recv (fd, (char *) l_msg + off_set, l_msg_len - off_set, 0);
+ if (recv_len <= 0)
+ {
+ if ((EINTR == errno || EAGAIN == errno)
+ && (max_count < MAX_RECV_COUNT))
+ {
+ recv_len = 0;
+ max_count++;
+ continue;
+ }
+
+ NSFW_LOGERR
+ ("recv error]mgr_fd=%u,recv_len=%d,off_set=%d,errno=%d,"
+ MSGINFO, fd, recv_len, off_set, errno, PRTMSG (msg));
+ l_msg->from_mem = from_flag;
+ nsfw_mgr_msg_free (l_msg);
+ return FALSE;
+ }
+ }
+ while (recv_len + off_set < (i32) l_msg_len);
+ (void) nsfw_set_sock_block (fd, TRUE);
+ int retVal = MEMCPY_S (l_msg, msg_len, msg, msg_len);
+ if (EOK != retVal)
+ {
+ NSFW_LOGERR ("MEMCPY_S failed] ret=%d", retVal);
+ l_msg->from_mem = from_flag;
+ nsfw_mgr_msg_free (l_msg);
+ return TRUE;
+ }
+ l_msg->from_mem = from_flag;
+ l_msg->msg_len = l_msg_len;
+
+ *large_msg = l_msg;
+ NSFW_LOGDBG ("recv large mgr_msg suc]mgr_fd=%u," MSGINFO, fd,
+ PRTMSG (l_msg));
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_send_req_wait_rsp
+* Description : send request message and block waiting for it's response
+ within MGR_COM_RECV_TIMEOUT
+* Input : nsfw_mgr_msg* req_msg
+* nsfw_mgr_msg* rsp_msg
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_mgr_send_req_wait_rsp (nsfw_mgr_msg * req_msg, nsfw_mgr_msg * rsp_msg)
+{
+ if (NULL == req_msg)
+ {
+ NSFW_LOGERR ("req msg nul!");
+ return FALSE;
+ }
+
+ i32 dst_socket =
+ nsfw_mgr_get_dst_socket (req_msg->dst_proc_type, req_msg->dst_pid);
+ if (dst_socket <= 0)
+ {
+ dst_socket =
+ nsfw_mgr_get_new_socket (req_msg->dst_proc_type, req_msg->dst_pid);
+ if (dst_socket <= 0)
+ {
+ NSFW_LOGERR ("send msg get dst_socket_error]" MSGINFO,
+ PRTMSG (req_msg));
+ return FALSE;
+ }
+ }
+
+ if ((NULL == rsp_msg) && (req_msg->msg_len == sizeof (nsfw_mgr_msg)))
+ {
+ LOCK_MGR_FD (dst_socket)
+ if (FALSE == nsfw_mgr_send_msg_socket (dst_socket, req_msg))
+ {
+ NSFW_LOGERR ("send msg error]" MSGINFO, PRTMSG (req_msg));
+ g_mgr_stat.msg_send_failed++;
+ UNLOCK_MGR_FD (dst_socket) return FALSE;
+ }
+ UNLOCK_MGR_FD (dst_socket) return TRUE;
+ }
+
+ LOCK_MGR_FD (dst_socket);
+ (void) nsfw_mgr_unreg_sock_fun (dst_socket);
+ if (FALSE == nsfw_mgr_send_msg_socket (dst_socket, req_msg))
+ {
+ NSFW_LOGERR ("send msg error]" MSGINFO, PRTMSG (req_msg));
+ g_mgr_stat.msg_send_failed++;
+ (void) nsfw_mgr_reg_sock_fun (dst_socket, nsfw_mgr_new_msg);
+ UNLOCK_MGR_FD (dst_socket);
+ return FALSE;
+ }
+
+ if (NULL == rsp_msg)
+ {
+ (void) nsfw_mgr_reg_sock_fun (dst_socket, nsfw_mgr_new_msg);
+ UNLOCK_MGR_FD (dst_socket) return TRUE;
+ }
+
+ u16 i;
+ for (i = 0; i < MGR_COM_MAX_DROP_MSG; i++)
+ {
+ if (FALSE == nsfw_mgr_recv_msg_socket (dst_socket, rsp_msg, NULL))
+ {
+ NSFW_LOGERR ("recv msg error]" MSGINFO, PRTMSG (req_msg));
+ (void) nsfw_mgr_reg_sock_fun (dst_socket, nsfw_mgr_new_msg);
+ UNLOCK_MGR_FD (dst_socket) return FALSE;
+ }
+
+ if ((rsp_msg->seq == req_msg->seq)
+ && (rsp_msg->msg_type == req_msg->msg_type + MGR_MSG_RSP_BASE))
+ {
+ break;
+ }
+
+ NSFW_LOGINF ("recv msg forward]" MSGINFO, PRTMSG (rsp_msg));
+ rsp_msg->fw_flag = TRUE;
+ (void) nsfw_mgr_send_msg (rsp_msg);
+ }
+
+ (void) nsfw_mgr_reg_sock_fun (dst_socket, nsfw_mgr_new_msg);
+ if (0 == req_msg->dst_pid)
+ {
+ (void) nsfw_mgr_new_socket (dst_socket, rsp_msg->src_proc_type,
+ rsp_msg->src_pid);
+ }
+ UNLOCK_MGR_FD (dst_socket) return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_send_msg
+* Description : send message to peer
+* Input : nsfw_mgr_msg* msg
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_mgr_send_msg (nsfw_mgr_msg * msg)
+{
+ return nsfw_mgr_send_req_wait_rsp (msg, NULL);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_msg_in
+* Description : when new domain socket mgr message receive, this function will be call
+* Input : i32 fd
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_mgr_msg_in (i32 fd)
+{
+ u32 i = 0;
+ u8 ret = FALSE;
+ u8 msg_match = FALSE;
+ nsfw_mgr_msg *msg = nsfw_mgr_null_rspmsg_alloc ();
+ nsfw_mgr_msg *large_msg = NULL;
+
+ LOCK_MGR_FD (fd) ret = nsfw_mgr_recv_msg_socket (fd, msg, &large_msg);
+ UNLOCK_MGR_FD (fd) if (large_msg != NULL)
+ {
+ nsfw_mgr_msg_free (msg);
+ msg = large_msg;
+ }
+
+ if (FALSE == ret)
+ {
+ nsfw_mgr_msg_free (msg);
+ return FALSE;
+ }
+ nstack_get_tracing_contex (msg->traceid, 0, 0, -1);
+ if (msg->fw_flag != TRUE)
+ {
+ (void) nsfw_mgr_new_socket (fd, msg->src_proc_type, msg->src_pid);
+ }
+
+ if (msg->msg_type < MGR_MSG_MAX)
+ {
+ for (i = 0; i < NSFW_MGRCOM_MAX_PROC_FUN; i++)
+ {
+ if (NULL == g_mgr_fun[msg->msg_type][i])
+ {
+ break;
+ }
+
+ (void) g_mgr_fun[msg->msg_type][i] (msg);
+ msg_match = TRUE;
+ }
+ }
+
+ if (FALSE != msg_match)
+ {
+ nsfw_mgr_msg_free (msg);
+ nstack_clear_tracing_contex ();
+ return TRUE;
+ }
+
+ if (msg->msg_type < MGR_MSG_RSP_BASE)
+ {
+ NSFW_LOGERR ("msg match failed! auto rsp]" MSGINFO, PRTMSG (msg));
+ nsfw_mgr_msg *rsp_msg = nsfw_mgr_rsp_msg_alloc (msg);
+ if (NULL != rsp_msg)
+ {
+ rsp_msg->resp_code = NSFW_MGR_MSG_TYPE_ERROR;
+ (void) nsfw_mgr_send_msg (rsp_msg);
+ nsfw_mgr_msg_free (rsp_msg);
+ }
+ }
+
+ NSFW_LOGERR ("drop msg]" MSGINFO, PRTMSG (msg));
+ /* fix "Out-of-bounds write" type codedex issue */
+ if (msg->msg_type < MGR_MSG_MAX)
+ {
+ g_mgr_stat.recv_drop[msg->msg_type]++;
+ }
+ nsfw_mgr_msg_free (msg);
+ nstack_clear_tracing_contex ();
+ return FALSE;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_new_msg
+* Description : when new mgr message recive from socket, this funciton
+ will call back
+* Input : i32 epfd
+* i32 fd
+* u32 events
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_mgr_new_msg (i32 epfd, i32 fd, u32 events)
+{
+ lint_lock_1 ();
+ if ((events & EPOLLERR) || (events & EPOLLHUP) || (!(events & EPOLLIN)))
+ {
+ (void) nsfw_mgr_del_socket (fd);
+ (void) nsfw_mgr_unreg_sock_fun (fd);
+ (void) nsfw_base_close (fd);
+ lint_unlock_1 ();
+ return TRUE;
+ }
+
+ (void) nsfw_mgr_msg_in (fd);
+ lint_unlock_1 ();
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_com_rereg_fun
+* Description : rereg the error socket
+* Input : u32 timer_type
+* void* data
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_mgr_com_rereg_fun (u32 timer_type, void *data)
+{
+ (void) nsfw_mgr_reg_sock_fun (timer_type, (nsfw_mgr_sock_fun) data);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_com_socket_error
+* Description : remove the error fd from ep
+* Input : i32 fd
+* nsfw_mgr_sock_fun fun
+* i32 timer
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_mgr_com_socket_error (i32 fd, nsfw_mgr_sock_fun fun, i32 timer)
+{
+ struct timespec time_left = { timer, 0 };
+ nsfw_mgr_unreg_sock_fun (fd);
+ nsfw_timer_reg_timer (fd, (void *) fun, nsfw_mgr_com_rereg_fun, time_left);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_new_connection
+* Description : when new mgr connection in, this funciton will call back
+* Input : i32 epfd
+* i32 fd
+* u32 events
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_mgr_new_connection (i32 epfd, i32 fd, u32 events)
+{
+ if ((events & EPOLLERR) || (events & EPOLLHUP) || (!(events & EPOLLIN)))
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGWAR ("listen disconnect!]epfd=%d,listen=%d,event=0x%x", epfd,
+ fd, events);
+ (void) nsfw_mgr_unreg_sock_fun (fd);
+ i32 listen_fd = nsfw_mgr_get_listen_socket ();
+ if (listen_fd < 0)
+ {
+ NSFW_LOGERR
+ ("get listen_fd faied!]epfd=%d,listen_fd=%d,event=0x%x", epfd,
+ fd, events);
+ return FALSE;
+ }
+
+ (void) nsfw_mgr_reg_sock_fun (listen_fd, nsfw_mgr_new_connection);
+ return TRUE;
+ }
+
+ struct sockaddr in_addr;
+ socklen_t in_len;
+ int infd;
+ in_len = sizeof in_addr;
+
+ int size, size_len;
+ u8 accept_flag = FALSE;
+ while (1)
+ {
+ infd = nsfw_base_accept (fd, &in_addr, &in_len);
+ if (infd == -1)
+ {
+ if (FALSE == accept_flag)
+ {
+ nsfw_mgr_com_socket_error (fd, nsfw_mgr_new_connection, 1);
+ }
+ break;
+ }
+
+ if (-1 == nsfw_set_close_on_exec (infd))
+ {
+ (void) nsfw_base_close (infd);
+ NSFW_LOGERR ("set exec err]fd=%d, errno=%d", infd, errno);
+ break;
+ }
+
+ size = MAX_RECV_BUF_DEF;
+ size_len = sizeof (size);
+ if (0 >
+ nsfw_base_setsockopt (infd, SOL_SOCKET, SO_RCVBUF, (void *) &size,
+ (socklen_t) size_len))
+ {
+ NSFW_LOGERR ("set socket opt err!]error=%d", errno);
+ }
+
+ if (0 >
+ nsfw_base_setsockopt (infd, SOL_SOCKET, SO_SNDBUF, (void *) &size,
+ (socklen_t) size_len))
+ {
+ NSFW_LOGERR ("set socket opt err!]error=%d", errno);
+ }
+
+ (void) nsfw_mgr_reg_sock_fun (infd, nsfw_mgr_new_msg);
+ NSFW_LOGDBG ("accept_flag new fd]new_mgr_fd=%d", infd);
+ accept_flag = TRUE;
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_set_sock_block
+* Description : set fd blok or not for epoll thread
+* Input : i32 sock
+* u8 flag
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_set_sock_block (i32 sock, u8 flag)
+{
+ i32 flags;
+ flags = nsfw_base_fcntl (sock, F_GETFL, 0);
+ if (flags < 0)
+ {
+ NSFW_LOGERR ("fcntl err]new_mgr_fd=%d,errno=%d", sock, errno);
+ return -1;
+ }
+
+ if (TRUE == flag)
+ {
+ flags = flags | O_NONBLOCK;
+ }
+ else
+ {
+ flags = flags & (~O_NONBLOCK);
+ struct timeval tv;
+ tv.tv_sec = MGR_COM_RECV_TIMEOUT;
+ tv.tv_usec = 0;
+ if (nsfw_base_setsockopt
+ (sock, SOL_SOCKET, SO_RCVTIMEO, (char *) &tv, sizeof tv))
+ {
+ NSFW_LOGERR ("setsockopt socket err]mgr_fd=%d", sock);
+ return -1;
+ }
+ }
+
+ if (nsfw_base_fcntl (sock, F_SETFL, flags) < 0)
+ {
+ NSFW_LOGERR ("fcntl err]new_mgr_fd=%d,errno=%d,flags=%d", sock, errno,
+ flags);
+ return -1;
+ }
+
+ return 0;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_set_close_on_exec
+* Description : close on exec set
+* Input : i32 sock
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_set_close_on_exec (i32 sock)
+{
+ i32 flags;
+ flags = nsfw_base_fcntl (sock, F_GETFD, 0);
+ if (flags < 0)
+ {
+ NSFW_LOGERR ("fcntl err]fd=%d,errno=%d", sock, errno);
+ return -1;
+ }
+
+ flags |= FD_CLOEXEC;
+
+ if (nsfw_base_fcntl (sock, F_SETFD, flags) < 0)
+ {
+ NSFW_LOGERR ("fcntl err]fd=%d,errno=%d,flags=%d", sock, errno, flags);
+ return -1;
+ }
+
+ return 0;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_add_sock_to_ep
+* Description : add fd to epoll wait thread
+* Input : i32 fd
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_add_sock_to_ep (i32 fd)
+{
+ struct epoll_event event;
+ event.data.fd = fd;
+ event.events = EPOLLIN;
+ if (g_ep_proc.epfd == 0)
+ {
+ return TRUE;
+ }
+
+ (void) nsfw_set_sock_block (fd, TRUE);
+
+ if (0 > nsfw_base_epoll_ctl (g_ep_proc.epfd, EPOLL_CTL_ADD, fd, &event))
+ {
+ NSFW_LOGINF
+ ("add sock to ep thread failed]mgr_fd=%d,errno=%d,epfd=%d", fd,
+ errno, g_ep_proc.epfd);
+ return FALSE;
+ }
+
+ NSFW_LOGDBG ("add sock to ep thread]mgr_fd=%d,epfd=%d", fd,
+ g_ep_proc.epfd) return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_rmv_sock_from_ep
+* Description : remove fd from epoll thread
+* Input : i32 fd
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_rmv_sock_from_ep (i32 fd)
+{
+ struct epoll_event event;
+ event.data.fd = fd;
+ event.events = EPOLLIN;
+ if (g_ep_proc.epfd == 0)
+ {
+ return TRUE;
+ }
+
+ (void) nsfw_set_sock_block (fd, FALSE);
+
+ if (0 > nsfw_base_epoll_ctl (g_ep_proc.epfd, EPOLL_CTL_DEL, fd, &event))
+ {
+ NSFW_LOGINF
+ ("rmv sock to ep thread failed] mgr_fd=%d,errno=%d,epfd=%d", fd,
+ errno, g_ep_proc.epfd);
+ return FALSE;
+ }
+
+ NSFW_LOGDBG ("rmv sock to ep thread] mgr_fd=%d,epfd=%d", fd,
+ g_ep_proc.epfd) return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_reg_sock_fun
+* Description : reg fd process function to call back when epoll thread
+ recvice new event of the reg fd
+* Input : i32 fd
+* nsfw_mgr_sock_fun fun
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_mgr_reg_sock_fun (i32 fd, nsfw_mgr_sock_fun fun)
+{
+ lint_lock_1 ();
+ if ((fd >= (i32) NSFW_MGR_FD_MAX) || (fd < 0) || NULL == fun)
+ {
+ NSFW_LOGINF ("reg sock fun error!] mgr_fd=%d,fun=%p", fd, fun);
+ lint_unlock_1 ();
+ return FALSE;
+ }
+
+ if ((g_ep_proc.ep_fun) && (NULL == g_ep_proc.ep_fun[fd]))
+ {
+ g_ep_proc.ep_fun[fd] = fun;
+ if (FALSE == nsfw_add_sock_to_ep (fd))
+ {
+ g_ep_proc.ep_fun[fd] = NULL;
+ lint_unlock_1 ();
+ return FALSE;
+ }
+
+ NSFW_LOGDBG ("reg sock fun] mgr_fd=%d,fun=%p", fd, fun);
+ lint_unlock_1 ();
+ return TRUE;
+ }
+ lint_unlock_1 ();
+ return FALSE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_unreg_sock_fun
+* Description : unreg the fd event function
+* Input : i32 fd
+* Output : None
+* Return Value : void
+* Calls :
+* Called By :
+*****************************************************************************/
+void
+nsfw_mgr_unreg_sock_fun (i32 fd)
+{
+ lint_lock_1 ();
+ if (fd >= (i32) NSFW_MGR_FD_MAX)
+ {
+ NSFW_LOGINF ("unreg sock fun failed!] mgr_fd=%d", fd);
+ lint_unlock_1 ();
+ return;
+ }
+
+ if ((g_ep_proc.ep_fun) && (NULL != g_ep_proc.ep_fun[fd]))
+ {
+ g_ep_proc.ep_fun[fd] = NULL;
+ (void) nsfw_rmv_sock_from_ep (fd);
+ NSFW_LOGDBG ("unreg sock fun] mgr_fd=%d", fd);
+ lint_unlock_1 ();
+ return;
+ }
+
+ lint_unlock_1 ();
+ return;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_sock_fun_callback
+* Description : call back the event process function
+* Input : i32 epfd
+* i32 fd
+* u32 events
+* Output : None
+* Return Value : static inline u8
+* Calls :
+* Called By :
+*****************************************************************************/
+NSTACK_STATIC inline u8
+nsfw_sock_fun_callback (i32 epfd, i32 fd, u32 events)
+{
+ if ((fd < (i32) NSFW_MGR_FD_MAX)
+ && (g_ep_proc.ep_fun) && (NULL != g_ep_proc.ep_fun[fd]))
+ {
+ (void) g_ep_proc.ep_fun[fd] (epfd, fd, events);
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_sock_add_to_ep
+* Description : add all event process function has ben reg to the epoll
+ thread when thread start
+* Input : i32 epfd
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_sock_add_to_ep (i32 epfd)
+{
+ u32 i;
+
+ for (i = 0; i < NSFW_MGR_FD_MAX; i++)
+ {
+ if ((g_ep_proc.ep_fun) && (NULL == g_ep_proc.ep_fun[i]))
+ {
+ continue;
+ }
+ (void) nsfw_add_sock_to_ep (i);
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_com_start
+* Description : start mgr com module
+* Input : None
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_mgr_com_start ()
+{
+ i32 listern_fd = nsfw_mgr_get_listen_socket ();
+ if (listern_fd < 0)
+ {
+ NSFW_LOGERR ("get listern_fd failed!");
+ return FALSE;
+ }
+
+ NSFW_LOGINF ("start mgr_com module!] listern_fd=%d", listern_fd);
+ (void) nsfw_mgr_reg_sock_fun (listern_fd, nsfw_mgr_new_connection);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_com_start_local
+* Description : start_local_msg_com
+* Input : None
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_mgr_com_start_local (u8 proc_type)
+{
+ int fd[2];
+ if ((socketpair (AF_UNIX, SOCK_STREAM, 0, fd)) < 0)
+ {
+ NSFW_LOGERR ("create socket err] type=%u,errno=%d", proc_type, errno);
+ return FALSE;
+ }
+
+ (void) nsfw_mgr_new_socket (fd[0], proc_type, get_sys_pid ());
+ (void) nsfw_mgr_new_socket (fd[1], proc_type, get_sys_pid ());
+ (void) nsfw_mgr_reg_sock_fun (fd[0], nsfw_mgr_new_msg);
+ (void) nsfw_mgr_reg_sock_fun (fd[1], nsfw_mgr_new_msg);
+ NSFW_LOGINF ("create local socket] fd0=%d,fd1=%d", fd[0], fd[1]);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_listen_thread
+* Description : epoll thread function
+* Input : void* arg
+* Output : None
+* Return Value : void *
+* Calls :
+* Called By :
+*****************************************************************************/
+void *
+nsfw_mgr_listen_thread (void *arg)
+{
+ i32 epfd = 0;
+ //i32 listen_socket = 0;
+
+ lint_lock_1 ();
+#define MAXEVENTS 10
+ epfd = nsfw_base_epoll_create (10);
+
+ struct epoll_event events[MAXEVENTS];
+ if (EOK != MEMSET_S (events, sizeof (events), 0, sizeof (events)))
+ {
+ NSFW_LOGERR ("MEMSET_S failed!]epfd=%d", epfd);
+ lint_unlock_1 ();
+ return NULL;
+ }
+
+ g_ep_proc.epfd = epfd;
+ g_ep_proc.hbt_count = 0;
+ (void) nsfw_sock_add_to_ep (epfd);
+ lint_unlock_1 ();
+ while (1)
+ {
+ lint_lock_1 ();
+ int n, i;
+ n = nsfw_base_epoll_wait (epfd, events, MAXEVENTS, -1);
+ for (i = 0; i < n; i++)
+ {
+ if (TRUE ==
+ nsfw_sock_fun_callback (epfd, events[i].data.fd,
+ events[i].events))
+ {
+ g_ep_proc.hbt_count = 0;
+ continue;
+ }
+
+ NSFW_LOGERR ("error event recv] fd=%d,event=%d",
+ events[i].data.fd, events[i].events);
+ }
+ lint_unlock_1 ();
+ }
+
+}
+
+NSTACK_STATIC inline void
+get_thread_policy (pthread_attr_t * attr)
+{
+ int policy;
+ int rs = pthread_attr_getschedpolicy (attr, &policy);
+ if (rs != 0)
+ {
+ NSFW_LOGERR ("pthread_attr_getschedpolicy failed");
+ return;
+ }
+ switch (policy)
+ {
+ case SCHED_FIFO:
+ NSFW_LOGINF ("policy= SCHED_FIFO");
+ break;
+ case SCHED_RR:
+ NSFW_LOGINF ("policy= SCHED_RR");
+ break;
+ case SCHED_OTHER:
+ NSFW_LOGINF ("policy=SCHED_OTHER");
+ break;
+ default:
+ NSFW_LOGINF ("policy=UNKNOWN");
+ break;
+ }
+
+ return;
+}
+
+NSTACK_STATIC inline void
+get_thread_priority (pthread_attr_t * attr)
+{
+ struct sched_param param;
+ int rs = pthread_attr_getschedparam (attr, &param);
+ if (rs != 0)
+ {
+ NSFW_LOGERR ("pthread_attr_getschedparam failed");
+ return;
+ }
+
+ NSFW_LOGINF ("get thread priority] pri=%d", param.sched_priority);
+}
+
+/* support thread priority configuration */
+void
+set_thread_attr (pthread_attr_t * pattr, int stacksize, int pri, int policy)
+{
+ struct sched_param param;
+ (void) pthread_attr_init (pattr);
+
+ if (stacksize > 0)
+ {
+ (void) pthread_attr_setstacksize (pattr, stacksize);
+ }
+
+ param.sched_priority = pri;
+ if (SCHED_OTHER != policy)
+ {
+ (void) pthread_attr_setschedpolicy (pattr, policy);
+ (void) pthread_attr_setschedparam (pattr, &param);
+ (void) pthread_attr_setinheritsched (pattr, PTHREAD_EXPLICIT_SCHED);
+ }
+ get_thread_policy (pattr);
+ get_thread_priority (pattr);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_ep_start
+* Description : start epoll thread
+* Input : None
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_mgr_ep_start ()
+{
+ /* heart beat thread should have the same priority with the tcpip thread */
+ pthread_attr_t attr;
+ pthread_attr_t *pattr = NULL;
+
+ if (g_thread_policy != SCHED_OTHER)
+ {
+ set_thread_attr (&attr, 0, g_thread_pri, g_thread_policy);
+ pattr = &attr;
+ }
+
+ if (pthread_create
+ (&g_ep_proc.ep_thread, pattr, nsfw_mgr_listen_thread, NULL))
+ {
+ return FALSE;
+ }
+
+ NSFW_LOGINF ("start thread] id=%d", g_ep_proc.ep_thread);
+
+ if (pthread_setname_np (g_ep_proc.ep_thread, NSFW_MGRCOM_THREAD))
+ {
+ return TRUE;
+ }
+ (void) nsfw_reg_trace_thread (g_ep_proc.ep_thread);
+ return TRUE;
+}
+
+int
+nsfw_mgr_com_chk_hbt (int v_add)
+{
+ int ret = g_ep_proc.hbt_count;
+ g_ep_proc.hbt_count += v_add;
+ return ret;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_comm_fd_destroy
+* Description : free the memeory
+* Input :
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+void
+nsfw_mgr_comm_fd_destroy ()
+{
+ if (g_ep_proc.ep_fun)
+ {
+ free (g_ep_proc.ep_fun);
+ g_ep_proc.ep_fun = NULL;
+ }
+ if (g_mgr_sockt_map.sock)
+ {
+ free (g_mgr_sockt_map.sock);
+ g_mgr_sockt_map.sock = NULL;
+ }
+ return;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_comm_fd_init
+* Description : fd map and socket info init
+* Input : u32 proc_type
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_mgr_comm_fd_init (u32 proc_type)
+{
+ /*only app need to do this */
+ if ((g_mgr_sockt_map.sock) && (g_ep_proc.ep_fun))
+ {
+ return 0;
+ }
+ if (NSFW_PROC_APP == proc_type)
+ {
+ long sysfdmax = 0;
+ sysfdmax = sysconf (_SC_OPEN_MAX);
+ NSFW_LOGINF ("] sys max open files=%d", sysfdmax);
+ if (sysfdmax > 0)
+ {
+ NSFW_MGR_FD_MAX =
+ (int) ((sysfdmax <=
+ NSFW_MGRCOM_MAX_SOCKET *
+ 60) ? sysfdmax : NSFW_MGRCOM_MAX_SOCKET * 60);
+ }
+ else
+ {
+ NSFW_LOGERR ("get sys max open file fail");
+ NSFW_MGR_FD_MAX = NSFW_MGRCOM_MAX_SOCKET;
+ }
+ }
+ NSFW_LOGINF ("] final max fd=%d", NSFW_MGR_FD_MAX);
+ if (!g_mgr_sockt_map.sock)
+ {
+ g_mgr_sockt_map.sock =
+ (nsfw_mgr_sock_info *) malloc (sizeof (nsfw_mgr_sock_info) *
+ NSFW_MGR_FD_MAX);
+ if (NULL == g_mgr_sockt_map.sock)
+ {
+ NSFW_LOGERR ("malloc fail] length=%d",
+ sizeof (nsfw_mgr_sock_info) * NSFW_MGR_FD_MAX);
+ return -1;
+ }
+ (void) MEMSET_S (g_mgr_sockt_map.sock,
+ sizeof (nsfw_mgr_sock_info) * NSFW_MGR_FD_MAX, 0,
+ sizeof (nsfw_mgr_sock_info) * NSFW_MGR_FD_MAX);
+ }
+ if (!g_ep_proc.ep_fun)
+ {
+ g_ep_proc.ep_fun =
+ (nsfw_mgr_sock_fun *) malloc (sizeof (nsfw_mgr_sock_fun) *
+ NSFW_MGR_FD_MAX);
+ if (NULL == g_ep_proc.ep_fun)
+ {
+ NSFW_LOGERR ("malloc fail] length=%d ",
+ sizeof (nsfw_mgr_sock_fun) * NSFW_MGR_FD_MAX);
+ return -1;
+ }
+ (void) MEMSET_S (g_ep_proc.ep_fun,
+ sizeof (nsfw_mgr_sock_fun) * NSFW_MGR_FD_MAX, 0,
+ sizeof (nsfw_mgr_sock_fun) * NSFW_MGR_FD_MAX);
+ }
+ return 0;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_com_module_init
+* Description : module init
+* Input : void* param
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int nsfw_mgr_com_module_init (void *param);
+int
+nsfw_mgr_com_module_init (void *param)
+{
+ lint_lock_1 ();
+ u32 proc_type = (u32) ((long long) param);
+ nsfw_mgr_init_cfg *mgr_cfg = &g_mgr_com_cfg;
+ const char *directory = NSFW_DOMAIN_DIR;
+ const char *home_dir = getenv ("HOME");
+
+ NSFW_LOGINF ("module mgr init] type=%u", proc_type);
+
+ if (getuid () != 0 && home_dir != NULL)
+ directory = home_dir;
+
+ if (0 != nsfw_mgr_comm_fd_init (proc_type))
+ {
+ NSFW_LOGERR ("fd init fail] proc_type=%u", proc_type);
+ lint_unlock_1 ();
+ return -1;
+ }
+
+ switch (proc_type)
+ {
+ case NSFW_PROC_MAIN:
+ /* modify destMax, remove "-1" */
+ if (EOK !=
+ STRCPY_S (mgr_cfg->domain_path, NSFW_MGRCOM_PATH_LEN, directory))
+ {
+ NSFW_LOGERR ("module mgr init STRCPY_S failed!");
+ lint_unlock_1 ();
+ return -1;
+ }
+
+ /* modify destMax, remove "-1" */
+ if (EOK !=
+ STRCAT_S (mgr_cfg->domain_path, NSFW_MGRCOM_PATH_LEN,
+ NSFW_MAIN_FILE))
+ {
+ NSFW_LOGERR ("module mgr init STRCAT_S failed!");
+ lint_unlock_1 ();
+ return -1;
+ }
+
+ NSFW_LOGINF ("module mgr init]NSFW_PROC_MAIN domain_path=%s",
+ mgr_cfg->domain_path);
+
+ if (TRUE != nsfw_mgr_com_start ())
+ {
+ NSFW_LOGERR ("module mgr nsfw_mgr_com_start failed!");
+ lint_unlock_1 ();
+ return -1;
+ }
+
+ break;
+ case NSFW_PROC_MASTER:
+ /* modify destMax, remove "-1" */
+ if (EOK !=
+ STRCPY_S (mgr_cfg->domain_path, NSFW_MGRCOM_PATH_LEN, directory))
+ {
+ NSFW_LOGERR ("module mgr init STRCPY_S failed!");
+ lint_unlock_1 ();
+ return -1;
+ }
+
+ /* modify destMax, remove "-1" */
+ if (EOK !=
+ STRCAT_S (mgr_cfg->domain_path, NSFW_MGRCOM_PATH_LEN,
+ NSFW_MASTER_FILE))
+ {
+ NSFW_LOGERR ("module mgr init STRCAT_S failed!");
+ lint_unlock_1 ();
+ return -1;
+ }
+
+ NSFW_LOGINF ("module mgr init]NSFW_PROC_MASTER domain_path=%s",
+ mgr_cfg->domain_path);
+
+ if (TRUE != nsfw_mgr_com_start ())
+ {
+ NSFW_LOGERR ("module mgr nsfw_mgr_com_start failed!");
+ lint_unlock_1 ();
+ return -1;
+ }
+
+ break;
+ case NSFW_PROC_TOOLS:
+ break;
+ case NSFW_PROC_CTRL:
+ if (TRUE != nsfw_mgr_com_start_local (proc_type))
+ {
+ NSFW_LOGERR ("module mgr nsfw_mgr_com_start_local failed!");
+ lint_unlock_1 ();
+ return -1;
+ }
+ break;
+ default:
+ if (proc_type < NSFW_PROC_MAX)
+ {
+ break;
+ }
+ lint_unlock_1 ();
+ return -1;
+ }
+
+ mgr_cfg->msg_size = MGR_COM_MSG_COUNT_DEF;
+ mgr_cfg->max_recv_timeout = MGR_COM_RECV_TIMEOUT_DEF;
+ mgr_cfg->max_recv_drop_msg = MGR_COM_MAX_DROP_MSG_DEF;
+
+ mgr_cfg->proc_type = proc_type;
+
+ nsfw_mem_sppool pmpinfo;
+ if (EOK != MEMSET_S (&pmpinfo, sizeof (pmpinfo), 0, sizeof (pmpinfo)))
+ {
+ NSFW_LOGERR ("Error to memset!!!");
+ nsfw_mgr_comm_fd_destroy ();
+ lint_unlock_1 ();
+ return -1;
+ }
+
+ pmpinfo.enmptype = NSFW_MRING_MPMC;
+ pmpinfo.usnum = mgr_cfg->msg_size;
+ pmpinfo.useltsize = sizeof (nsfw_mgr_msg);
+ pmpinfo.isocket_id = NSFW_SOCKET_ANY;
+ pmpinfo.stname.entype = NSFW_NSHMEM;
+ if (-1 ==
+ SPRINTF_S (pmpinfo.stname.aname, sizeof (pmpinfo.stname.aname), "%s",
+ "MS_MGR_MSGPOOL"))
+ {
+ NSFW_LOGERR ("Error to SPRINTF_S!!!");
+ nsfw_mgr_comm_fd_destroy ();
+ lint_unlock_1 ();
+ return -1;
+ }
+
+ mgr_cfg->msg_pool = nsfw_mem_sp_create (&pmpinfo);
+
+ if (!mgr_cfg->msg_pool)
+ {
+ NSFW_LOGERR ("module mgr init msg_pool alloc failed!");
+ nsfw_mgr_comm_fd_destroy ();
+ lint_unlock_1 ();
+ return -1;
+ }
+
+ (void) MEM_STAT (NSFW_MGR_COM_MODULE, pmpinfo.stname.aname, NSFW_NSHMEM,
+ nsfw_mem_get_len (mgr_cfg->msg_pool, NSFW_MEM_SPOOL));
+
+ if ((NSFW_PROC_TOOLS == proc_type)
+ || (NSFW_PROC_CTRL == proc_type) || (NSFW_PROC_MAIN == proc_type))
+ {
+ if (TRUE != nsfw_mgr_ep_start ())
+ {
+ NSFW_LOGERR ("module mgr nsfw_mgr_ep_start failed!");
+ nsfw_mgr_comm_fd_destroy ();
+ lint_unlock_1 ();
+ return -1;
+ }
+ }
+ lint_unlock_1 ();
+ return 0;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mgr_run_script
+* Description : run a linux shell script
+* Input : const char *cmd, char *result, int result_buf_len
+* Output : result length
+* Return Value : int
+* Calls :
+* Called By :
+ *****************************************************************************/
+int
+nsfw_mgr_run_script (const char *cmd, char *result, int result_buf_len)
+{
+ if (!cmd || !result || result_buf_len <= 1)
+ {
+ return -1;
+ }
+
+ FILE *fp = popen (cmd, "r");
+ if (fp != NULL)
+ {
+ size_t n = fread (result, sizeof (char), result_buf_len - 1, fp);
+ if (n == 0)
+ {
+ result[0] = '\0';
+ }
+ else if ('\n' == result[n - 1])
+ {
+ result[n - 1] = '\0';
+ }
+ else
+ {
+ result[n] = '\0';
+ }
+
+ pclose (fp);
+ return n;
+ }
+
+ return -1;
+}
+
+/* *INDENT-OFF* */
+NSFW_MODULE_NAME(NSFW_MGR_COM_MODULE)
+NSFW_MODULE_PRIORITY(10)
+NSFW_MODULE_DEPENDS(NSFW_MEM_MGR_MODULE)
+NSFW_MODULE_INIT(nsfw_mgr_com_module_init)
+/* *INDENT-ON* */
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/ipc/mgr_com/mgr_com.h b/src/framework/ipc/mgr_com/mgr_com.h
new file mode 100644
index 0000000..c4333a1
--- /dev/null
+++ b/src/framework/ipc/mgr_com/mgr_com.h
@@ -0,0 +1,150 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+/*****************************************************************************
+* Prototype : ifndef _NSFW_MGRCOM_MODULE_H
+* Description : mgr com module definition
+* Input : None
+* Output : None
+* Return Value : #
+* Calls :
+* Called By :
+ *****************************************************************************/
+#ifndef _NSFW_MGRCOM_MODULE_H
+#define _NSFW_MGRCOM_MODULE_H
+
+#include "pthread.h"
+#include "nsfw_mem_api.h"
+#include "common_mem_api.h"
+
+#include "common_func.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define NSFW_MGRCOM_PATH_LEN 128
+#define NSFW_MGRCOM_MAX_SOCKET 1024
+#define NSFW_MGRCOM_MAX_PROC_FUN 8
+
+#define MAX_RECV_BUF_DEF 0x34000*2
+
+#define MGR_COM_MSG_COUNT_DEF 1023 /*g_mgr_com_cfg */
+#define MGR_COM_RECV_TIMEOUT_DEF 5
+#define MGR_COM_MAX_DROP_MSG_DEF 1024
+
+#define MGR_COM_MSG_COUNT (g_mgr_com_cfg.msg_size)
+#define MGR_COM_RECV_TIMEOUT (g_mgr_com_cfg.max_recv_timeout)
+#define MGR_COM_MAX_DROP_MSG (g_mgr_com_cfg.max_recv_drop_msg)
+
+#define NSFW_MAIN_FILE "/ip_module/nStackMainMgr"
+#define NSFW_MASTER_FILE "/ip_module/nStackMasterMgr"
+#define NSFW_ALARM_FILE "/HuskyAlarm.domain"
+
+#define NSFW_MGRCOM_THREAD "nStackMgrCom"
+
+typedef struct _nsfw_mgr_init_cfg
+{
+ u8 proc_type; /*fw_poc_type */
+ u8 max_recv_timeout;
+ u16 max_recv_drop_msg;
+ u32 msg_size;
+ common_mem_atomic32_t cur_idx;
+ u64 u64reserve;
+ mring_handle msg_pool;
+ char domain_path[NSFW_MGRCOM_PATH_LEN];
+} nsfw_mgr_init_cfg;
+
+typedef struct _nsfw_mgrcom_stat
+{
+ u64 msg_send[MGR_MSG_MAX];
+ u64 msg_recv[MGR_MSG_MAX];
+ u64 recv_drop[MGR_MSG_MAX];
+ u64 msg_alloc;
+ u64 msg_free;
+ u64 msg_send_failed;
+ u64 reconnect_count;
+} nsfw_mgrcom_stat;
+
+typedef struct _nsfw_mgr_sock_info
+{
+ u8 proc_type; /*_ns_poc_type*/
+ u32 host_pid;
+ common_mem_spinlock_t opr_lock;
+} nsfw_mgr_sock_info;
+
+typedef struct _nsfw_mgr_sock_map
+{
+ i32 proc_cache[NSFW_PROC_MAX];
+ nsfw_mgr_sock_info *sock;
+} nsfw_mgr_sock_map;
+
+#define NSFW_SOCK_MAX_PROC_FUN 4
+
+typedef struct _nsfw_mgrcom_proc_fun
+{
+ i32 fd;
+ nsfw_mgr_sock_fun fun;
+} nsfw_mgrcom_proc_fun;
+
+typedef struct _nsfw_mgrcom_proc
+{
+ i32 epfd;
+ u32 hbt_count;
+ pthread_t ep_thread;
+ nsfw_mgr_sock_fun *ep_fun;
+} nsfw_mgrcom_proc;
+
+i32 nsfw_set_sock_block (i32 sock, u8 flag);
+
+u8 nsfw_rmv_sock_from_ep (i32 fd);
+u8 nsfw_add_sock_to_ep (i32 fd);
+
+int nsfw_mgr_new_msg (i32 epfd, i32 socket, u32 events);
+
+u8 nsfw_mgr_ep_start ();
+u8 nsfw_mgr_stop ();
+
+#define LOCK_MGR_FD(_fd){\
+ if ((i32)NSFW_MGR_FD_MAX > _fd)\
+ {\
+ common_mem_spinlock_lock(&g_mgr_sockt_map.sock[_fd].opr_lock);\
+ }\
+}
+
+#define UNLOCK_MGR_FD(_fd){\
+ if ((i32)NSFW_MGR_FD_MAX > _fd)\
+ {\
+ common_mem_spinlock_unlock(&g_mgr_sockt_map.sock[_fd].opr_lock);\
+ }\
+}
+
+#define NSFW_MGR_FD_MAX g_mgr_sockfdmax
+
+extern void set_thread_attr (pthread_attr_t * pattr, int stacksize, int pri,
+ int policy);
+
+extern void nsfw_com_attr_set (int policy, int pri);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _NSFW_MGRCOM_MODULE_H */
diff --git a/src/framework/ipc/ps/nsfw_fd_timer.c b/src/framework/ipc/ps/nsfw_fd_timer.c
new file mode 100644
index 0000000..57535a3
--- /dev/null
+++ b/src/framework/ipc/ps/nsfw_fd_timer.c
@@ -0,0 +1,378 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdlib.h>
+#include <errno.h>
+#include <stdio.h>
+#include <sys/timerfd.h>
+
+#include "types.h"
+#include "list.h"
+
+#include "nstack_securec.h"
+#include "nsfw_init.h"
+#include "nsfw_mgr_com_api.h"
+#include "nsfw_mem_api.h"
+#include "nstack_log.h"
+#include "nsfw_base_linux_api.h"
+#include "nsfw_fd_timer_api.h"
+#include "nsfw_maintain_api.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define NSFW_TIMER_CYCLE 1
+#define NSFW_TIMER_INFO_MAX_COUNT_DEF 8191
+#define NSFW_TIMER_INFO_MAX_COUNT (g_timer_cfg.timer_info_size)
+/* *INDENT-OFF* */
+nsfw_timer_init_cfg g_timer_cfg;
+
+u8 g_hbt_switch = FALSE;
+/* *INDENT-ON* */
+
+/*****************************************************************************
+* Prototype : nsfw_timer_reg_timer
+* Description : reg timer with callback function when timeout
+* Input : u32 timer_type
+* void* data
+* nsfw_timer_proc_fun fun
+* struct timespec time_left
+* Output : None
+* Return Value : nsfw_timer_info*
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+nsfw_timer_info *
+nsfw_timer_reg_timer (u32 timer_type, void *data,
+ nsfw_timer_proc_fun fun, struct timespec time_left)
+{
+ nsfw_timer_info *tm_info = NULL;
+ if (0 ==
+ nsfw_mem_ring_dequeue (g_timer_cfg.timer_info_pool, (void *) &tm_info))
+ {
+ NSFW_LOGERR ("dequeue error]data=%p,fun=%p", data, fun);
+ return NULL;
+ }
+
+ if (EOK != MEMSET_S (tm_info, sizeof (*tm_info), 0, sizeof (*tm_info)))
+ {
+ if (0 == nsfw_mem_ring_enqueue (g_timer_cfg.timer_info_pool, tm_info))
+ {
+ NSFW_LOGERR ("enqueue error]data=%p,fun=%p", data, fun);
+ }
+ NSFW_LOGERR ("mem set error]data=%p,fun=%p", data, fun);
+ return NULL;
+ }
+
+ tm_info->fun = fun;
+ tm_info->argv = data;
+ tm_info->time_left = time_left;
+ //tm_info->time_left.tv_sec += NSFW_TIMER_CYCLE;
+ tm_info->timer_type = timer_type;
+ list_add_tail (&tm_info->node, &g_timer_cfg.timer_head);
+ tm_info->alloc_flag = TRUE;
+ return tm_info;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_timer_rmv_timer
+* Description : stop timer
+* Input : nsfw_timer_info* tm_info
+* Output : None
+* Return Value : void
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+void
+nsfw_timer_rmv_timer (nsfw_timer_info * tm_info)
+{
+ if (NULL == tm_info)
+ {
+ NSFW_LOGWAR ("tm_info nul");
+ return;
+ }
+
+ if (FALSE == tm_info->alloc_flag)
+ {
+ NSFW_LOGERR ("tm_info refree]tm_info=%p,argv=%p,fun=%p", tm_info,
+ tm_info->argv, tm_info->fun);
+ return;
+ }
+
+ tm_info->alloc_flag = FALSE;
+ list_del (&tm_info->node);
+ if (0 == nsfw_mem_ring_enqueue (g_timer_cfg.timer_info_pool, tm_info))
+ {
+ NSFW_LOGERR ("tm_info free failed]tm_info=%p,argv=%p,fun=%p", tm_info,
+ tm_info->argv, tm_info->fun);
+ }
+ return;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_timer_exp
+* Description : timer expire
+* Input : u64 count
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+void
+nsfw_timer_exp (u64 count)
+{
+ nsfw_timer_info *tm_info = NULL;
+ struct list_head *tNode;
+ struct list_head *tPretNode;
+
+ LINT_LIST ()list_for_each_entry (tm_info, tNode, (&g_timer_cfg.timer_head),
+ node)
+ {
+ tPretNode = tm_info->node.prev;
+ if (tm_info->time_left.tv_sec > (long) count * NSFW_TIMER_CYCLE)
+ {
+ tm_info->time_left.tv_sec -= count * NSFW_TIMER_CYCLE;
+ continue;
+ }
+
+ list_del (&tm_info->node);
+ list_add_tail (&tm_info->node, &g_timer_cfg.exp_timer_head);
+ tNode = tPretNode;
+ }
+
+ u32 i = 0;
+ while (!list_empty (&g_timer_cfg.exp_timer_head)
+ && i++ < NSFW_TIMER_INFO_MAX_COUNT)
+ {
+ tm_info =
+ (nsfw_timer_info *) list_get_first (&g_timer_cfg.exp_timer_head);
+ if (NULL != tm_info->fun)
+ {
+ (void) tm_info->fun (tm_info->timer_type, tm_info->argv);
+ }
+ nsfw_timer_rmv_timer (tm_info);
+ }
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_get_timer_socket
+* Description : get timer socket from kernel
+* Input : None
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_get_timer_socket ()
+{
+ i32 tfd = timerfd_create (CLOCK_MONOTONIC, TFD_NONBLOCK);
+ if (tfd == -1)
+ {
+ NSFW_LOGERR ("timerfd_create failed!]errno=%d\n", errno);
+ return -1;
+ }
+
+ /* close on exe */
+ if (-1 == nsfw_set_close_on_exec (tfd))
+ {
+ (void) nsfw_base_close (tfd);
+ NSFW_LOGERR ("set exec err]fd=%d, errno=%d", tfd, errno);
+ return -1;
+ }
+
+ struct itimerspec ts;
+ ts.it_interval.tv_sec = NSFW_TIMER_CYCLE;
+ ts.it_interval.tv_nsec = 0;
+ ts.it_value.tv_sec = 0;
+ ts.it_value.tv_nsec = NSFW_TIMER_CYCLE;
+
+ if (timerfd_settime (tfd, 0, &ts, NULL) < 0)
+ {
+ NSFW_LOGERR ("timerfd_settime failed] errno=%d", errno);
+ close (tfd);
+ return -1;
+ }
+
+ return tfd;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_timer_notify_fun
+* Description : receive timer event from kernel
+* Input : i32 epfd
+* i32 fd
+* u32 events
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_timer_notify_fun (i32 epfd, i32 fd, u32 events)
+{
+ i32 rc;
+
+ if ((events & EPOLLERR) || (events & EPOLLHUP) || (!(events & EPOLLIN)))
+ {
+ (void) nsfw_base_close (fd);
+ NSFW_LOGWAR ("timer disconnect!]epfd=%d,timer=%d,event=0x%x", epfd,
+ fd, events);
+
+ (void) nsfw_mgr_unreg_sock_fun (fd);
+ i32 timer_fd = nsfw_get_timer_socket ();
+ if (timer_fd < 0)
+ {
+ NSFW_LOGERR ("get timer_fd faied!]epfd=%d,timer_fd=%d,event=0x%x",
+ epfd, fd, events);
+ return FALSE;
+ }
+
+ (void) nsfw_mgr_reg_sock_fun (timer_fd, nsfw_timer_notify_fun);
+ return TRUE;
+ }
+
+ u64 data;
+ while (1)
+ {
+ rc = nsfw_base_read (fd, &data, sizeof (data));
+ if (rc == 0)
+ {
+ NSFW_LOGERR ("timer_fd recv 0]timer_fd=%d,errno=%d", fd, errno);
+ break;
+ }
+ else if (rc == -1)
+ {
+ if (errno == EINTR || errno == EAGAIN)
+ {
+ break;
+ }
+ NSMON_LOGERR ("timer_fd recv]timer_fd=%d,errno=%d", fd, errno);
+ break;
+ }
+
+ nsfw_timer_exp (data);
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_timer_start
+* Description : reg the timer module to epoll thread
+* Input : None
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+u8
+nsfw_timer_start ()
+{
+ i32 timer_fd = nsfw_get_timer_socket ();
+ if (timer_fd < 0)
+ {
+ NSFW_LOGERR ("get timer_fd failed!");
+ return FALSE;
+ }
+
+ NSFW_LOGINF ("start timer_fd module!]timer_fd=%d", timer_fd);
+ (void) nsfw_mgr_reg_sock_fun (timer_fd, nsfw_timer_notify_fun);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_timer_module_init
+* Description : module init
+* Input : void* param
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+int
+nsfw_timer_module_init (void *param)
+{
+ u32 proc_type = (u32) ((long long) param);
+ nsfw_timer_init_cfg *timer_cfg = &g_timer_cfg;
+ NSFW_LOGINF ("ps module init]type=%u", proc_type);
+ switch (proc_type)
+ {
+ case NSFW_PROC_MASTER:
+ case NSFW_PROC_MAIN:
+ (void) NSFW_REG_SOFT_INT (NSFW_DBG_MODE_PARAM, g_hbt_switch, 0, 1);
+ break;
+ case NSFW_PROC_TOOLS:
+ case NSFW_PROC_CTRL:
+ break;
+ default:
+ return 0;
+ }
+
+ timer_cfg->timer_info_size = NSFW_TIMER_INFO_MAX_COUNT_DEF;
+
+ nsfw_mem_sppool pmpinfo;
+ pmpinfo.enmptype = NSFW_MRING_MPMC;
+ pmpinfo.usnum = timer_cfg->timer_info_size;
+ pmpinfo.useltsize = sizeof (nsfw_timer_info);
+ pmpinfo.isocket_id = NSFW_SOCKET_ANY;
+ pmpinfo.stname.entype = NSFW_NSHMEM;
+ if (-1 ==
+ SPRINTF_S (pmpinfo.stname.aname, NSFW_MEM_NAME_LENTH, "%s",
+ "MS_TM_INFOPOOL"))
+ {
+ NSFW_LOGERR ("SPRINTF_S failed");
+ return -1;
+ }
+ timer_cfg->timer_info_pool = nsfw_mem_sp_create (&pmpinfo);
+
+ if (!timer_cfg->timer_info_pool)
+ {
+ NSFW_LOGERR ("alloc timer info pool_err");
+ return -1;
+ }
+
+ MEM_STAT (NSFW_TIMER_MODULE, pmpinfo.stname.aname, NSFW_NSHMEM,
+ nsfw_mem_get_len (timer_cfg->timer_info_pool, NSFW_MEM_SPOOL));
+
+ INIT_LIST_HEAD (&(timer_cfg->timer_head));
+ INIT_LIST_HEAD (&(timer_cfg->exp_timer_head));
+
+ (void) nsfw_timer_start ();
+ return 0;
+}
+
+/* *INDENT-OFF* */
+NSFW_MODULE_NAME (NSFW_TIMER_MODULE)
+NSFW_MODULE_PRIORITY (10)
+NSFW_MODULE_DEPENDS (NSFW_MGR_COM_MODULE)
+NSFW_MODULE_INIT (nsfw_timer_module_init)
+/* *INDENT-ON* */
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/ipc/ps/nsfw_ps_mem_module.c b/src/framework/ipc/ps/nsfw_ps_mem_module.c
new file mode 100644
index 0000000..9cda6b3
--- /dev/null
+++ b/src/framework/ipc/ps/nsfw_ps_mem_module.c
@@ -0,0 +1,924 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdlib.h>
+#include "types.h"
+#include "nstack_securec.h"
+#include "nsfw_init.h"
+
+#include "nsfw_ps_module.h"
+#include "nsfw_mgr_com_api.h"
+#include "nsfw_ps_mem_api.h"
+#include "nsfw_ps_mem_module.h"
+#include "nsfw_ps_api.h"
+#include "nsfw_maintain_api.h"
+#include "nsfw_fd_timer_api.h"
+
+#include "nstack_log.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+ns_mem_mng_init_cfg g_mem_cfg;
+
+int mem_ps_exiting (void *pps_info, void *argv);
+
+int
+nsfw_mem_ps_exit_resend_timeout (u32 timer_type, void *data)
+{
+ nsfw_ps_info *ps_info = data;
+ if (NULL == ps_info)
+ {
+ NSFW_LOGERR ("ps_info nul!");
+ return FALSE;
+ }
+
+ if (NSFW_PROC_APP != ps_info->proc_type)
+ {
+ return FALSE;
+ }
+
+ if (NSFW_PS_EXITING != ps_info->state)
+ {
+ return FALSE;
+ }
+
+ ps_info->resend_timer_ptr = NULL;
+ (void) mem_ps_exiting (ps_info, NULL);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : mem_ps_exiting
+* Description : send exiting message when ps_info exiting
+* Input : void *pps_info
+* void* argv
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+mem_ps_exiting (void *pps_info, void *argv)
+{
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("ps_info nul!");
+ return FALSE;
+ }
+
+ if (TRUE == NSFW_SRV_STATE_SUSPEND)
+ {
+ NSFW_LOGERR ("main suspend]ps_info=%d,pid=%u", pps_info,
+ ((nsfw_ps_info *) pps_info)->host_pid);
+ return FALSE;
+ }
+
+ nsfw_mgr_msg *msg =
+ nsfw_mgr_msg_alloc (MGR_MSG_APP_EXIT_REQ, NSFW_PROC_MAIN);
+ if (NULL == msg)
+ {
+ NSFW_LOGERR ("ps_exit alloc msg failed]ps_info=%p,pid=%u", pps_info,
+ ((nsfw_ps_info *) pps_info)->host_pid);
+ return FALSE;
+ }
+
+ nsfw_ps_info_msg *ps_msg = GET_USER_MSG (nsfw_ps_info_msg, msg);
+ ps_msg->host_pid = ((nsfw_ps_info *) pps_info)->host_pid;
+
+ (void) nsfw_mgr_send_msg (msg);
+ NSFW_LOGINF ("ps_exiting send msg]ps_info=%p,pid=%u", pps_info,
+ ps_msg->host_pid);
+ nsfw_mgr_msg_free (msg);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : mem_alloc_ps_info
+* Description : alloc ps_info
+* Input : u32 pid
+* u8 proc_type
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+mem_alloc_ps_info (u32 pid, u8 proc_type)
+{
+ nsfw_ps_info *pps_info = NULL;
+ pps_info = nsfw_ps_info_get (pid);
+ if (NULL != pps_info)
+ {
+ return TRUE;
+ }
+
+ pps_info = nsfw_ps_info_alloc (pid, proc_type);
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("alloc ps_info falied!]pid=%u,proc_type=%u", pid,
+ proc_type);
+ return FALSE;
+ }
+
+ NSFW_LOGINF ("alloc new ps_info]pps_info=%p,pid=%u", pps_info, pid);
+ return TRUE;
+}
+
+/*mem alloc by msg begin*/
+void *
+mem_item_zone_create (void *mem_info)
+{
+ return (void *) nsfw_mem_zone_create ((nsfw_mem_zone *) mem_info);
+}
+
+void *
+mem_item_mbfmp_create (void *mem_info)
+{
+ return (void *) nsfw_mem_mbfmp_create ((nsfw_mem_mbfpool *) mem_info);
+}
+
+void *
+mem_item_sp_create (void *mem_info)
+{
+ return (void *) nsfw_mem_sp_create ((nsfw_mem_sppool *) mem_info);
+}
+
+void *
+mem_item_ring_create (void *mem_info)
+{
+ return (void *) nsfw_mem_ring_create ((nsfw_mem_mring *) mem_info);
+}
+
+nsfw_ps_mem_item_cfg g_ps_mem_map[] = {
+ {
+ NSFW_RESERV_REQ_MSG,
+ sizeof (nsfw_shmem_reserv_req),
+ NSFW_MEM_MZONE,
+ mem_item_zone_create,
+ mem_item_get_callargv}
+ ,
+
+ {
+ NSFW_MBUF_REQ_MSG,
+ sizeof (nsfw_shmem_mbuf_req),
+ NSFW_MEM_MBUF,
+ mem_item_mbfmp_create,
+ mem_item_get_callargv}
+ ,
+ {
+ NSFW_SPPOOL_REQ_MSG,
+ sizeof (nsfw_shmem_sppool_req),
+ NSFW_MEM_SPOOL,
+ mem_item_sp_create,
+ mem_item_get_callargv}
+ ,
+ {
+ NSFW_RING_REQ_MSG,
+ sizeof (nsfw_shmem_ring_req),
+ NSFW_MEM_RING,
+ mem_item_ring_create,
+ mem_item_get_callargv}
+ ,
+ {
+ NSFW_RELEASE_REQ_MSG,
+ sizeof (nsfw_shmem_free_req),
+ 0xFFFF,
+ mem_item_free,
+ mem_item_get_callargv,
+ }
+ ,
+ {
+ NSFW_MEM_LOOKUP_REQ_MSG,
+ sizeof (nsfw_shmem_lookup_req),
+ 0xFFFF,
+ mem_item_lookup,
+ mem_item_get_callargv,
+ }
+};
+
+/*****************************************************************************
+* Prototype : mem_item_get_cfg_from_msg
+* Description : get memory config
+* Input : u16 msg_type
+* Output : None
+* Return Value : nsfw_ps_mem_item_cfg *
+* Calls :
+* Called By :
+*****************************************************************************/
+nsfw_ps_mem_item_cfg *
+mem_item_get_cfg_from_msg (u16 msg_type)
+{
+ int idx;
+ int map_count = sizeof (g_ps_mem_map) / sizeof (nsfw_ps_mem_item_cfg);
+ for (idx = 0; idx < map_count; idx++)
+ {
+ if (g_ps_mem_map[idx].usmsg_type == msg_type)
+ {
+ return &g_ps_mem_map[idx];
+ }
+ }
+
+ return NULL;
+}
+
+/*****************************************************************************
+* Prototype : mem_item_get_callargv
+* Description : change the message value to structur value
+* Input : u16 msg_type
+* char* msg_body
+* char *memstr_buf
+* i32 buf_len
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+mem_item_get_callargv (u16 msg_type, char *msg_body, char *memstr_buf,
+ i32 buf_len)
+{
+ switch (msg_type)
+ {
+ case NSFW_RESERV_REQ_MSG:
+ MEM_GET_CALLARGV (lenth, lenth, nsfw_mem_zone, nsfw_shmem_reserv_req,
+ memstr_buf, msg_body);
+ MEM_GET_CALLARGV (isocket_id, isocket_id, nsfw_mem_zone,
+ nsfw_shmem_reserv_req, memstr_buf, msg_body);
+ break;
+ case NSFW_MBUF_REQ_MSG:
+ MEM_GET_CALLARGV (usnum, usnum, nsfw_mem_mbfpool, nsfw_shmem_mbuf_req,
+ memstr_buf, msg_body);
+ MEM_GET_CALLARGV (uscash_size, uscash_size, nsfw_mem_mbfpool,
+ nsfw_shmem_mbuf_req, memstr_buf, msg_body);
+ MEM_GET_CALLARGV (uspriv_size, uspriv_size, nsfw_mem_mbfpool,
+ nsfw_shmem_mbuf_req, memstr_buf, msg_body);
+ MEM_GET_CALLARGV (usdata_room, usdata_room, nsfw_mem_mbfpool,
+ nsfw_shmem_mbuf_req, memstr_buf, msg_body);
+ MEM_GET_CALLARGV (enmptype, enmptype, nsfw_mem_mbfpool,
+ nsfw_shmem_mbuf_req, memstr_buf, msg_body);
+ MEM_GET_CALLARGV (isocket_id, isocket_id, nsfw_mem_mbfpool,
+ nsfw_shmem_mbuf_req, memstr_buf, msg_body);
+ break;
+ case NSFW_SPPOOL_REQ_MSG:
+ MEM_GET_CALLARGV (usnum, usnum, nsfw_mem_sppool,
+ nsfw_shmem_sppool_req, memstr_buf, msg_body);
+ MEM_GET_CALLARGV (useltsize, useltsize, nsfw_mem_sppool,
+ nsfw_shmem_sppool_req, memstr_buf, msg_body);
+ MEM_GET_CALLARGV (enmptype, enmptype, nsfw_mem_sppool,
+ nsfw_shmem_sppool_req, memstr_buf, msg_body);
+ MEM_GET_CALLARGV (isocket_id, isocket_id, nsfw_mem_sppool,
+ nsfw_shmem_sppool_req, memstr_buf, msg_body);
+ break;
+ case NSFW_RING_REQ_MSG:
+ MEM_GET_CALLARGV (usnum, usnum, nsfw_mem_mring, nsfw_shmem_ring_req,
+ memstr_buf, msg_body);
+ MEM_GET_CALLARGV (enmptype, enmptype, nsfw_mem_mring,
+ nsfw_shmem_ring_req, memstr_buf, msg_body);
+ MEM_GET_CALLARGV (isocket_id, isocket_id, nsfw_mem_mring,
+ nsfw_shmem_ring_req, memstr_buf, msg_body);
+ break;
+ case NSFW_RELEASE_REQ_MSG:
+ MEM_GET_CALLARGV (ustype, ustype, nsfw_mem_type_info,
+ nsfw_shmem_free_req, memstr_buf, msg_body);
+ break;
+ case NSFW_MEM_LOOKUP_REQ_MSG:
+ MEM_GET_CALLARGV (ustype, ustype, nsfw_mem_type_info,
+ nsfw_shmem_lookup_req, memstr_buf, msg_body);
+ break;
+ default:
+ NSFW_LOGERR ("error msg]type=%u", msg_type);
+ return FALSE;
+ }
+ if (EOK !=
+ STRCPY_S (((nsfw_mem_zone *) memstr_buf)->stname.aname,
+ NSFW_MEM_NAME_LENTH,
+ ((nsfw_shmem_reserv_req *) msg_body)->aname))
+ {
+ NSFW_LOGERR ("STRCPY_S failed]msg_type=%u", msg_type);
+ return FALSE;
+ }
+
+ ((nsfw_mem_zone *) memstr_buf)->stname.entype = NSFW_SHMEM;
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : mem_item_free
+* Description : free memory item
+* Input : void *pdata
+* Output : None
+* Return Value : void*
+* Calls :
+* Called By :
+*****************************************************************************/
+void *
+mem_item_free (void *pdata)
+{
+ nsfw_mem_type_info *mem_free = (nsfw_mem_type_info *) pdata;
+ i32 ret;
+ NSFW_LOGINF ("free mem]type=%u,name=%s", mem_free->ustype,
+ mem_free->stname.aname);
+ switch (mem_free->ustype)
+ {
+ case NSFW_MEM_MZONE:
+ ret = nsfw_mem_zone_release (&mem_free->stname);
+ break;
+ case NSFW_MEM_MBUF:
+ ret = nsfw_mem_mbfmp_release (&mem_free->stname);
+ break;
+ case NSFW_MEM_SPOOL:
+ ret = nsfw_mem_sp_release (&mem_free->stname);
+ break;
+ case NSFW_MEM_RING:
+ ret = nsfw_mem_ring_release (&mem_free->stname);
+ break;
+ default:
+ NSFW_LOGERR ("free mem err type]type=%u", mem_free->ustype);
+ return NULL;
+ }
+
+ if (NSFW_MEM_OK != ret)
+ {
+ NSFW_LOGERR ("mem free failed!]ret=%d", ret);
+ return NULL;
+ }
+
+ return pdata;
+}
+
+/*****************************************************************************
+* Prototype : mem_item_lookup
+* Description : lookup memory item
+* Input : void *pdata
+* Output : None
+* Return Value : void*
+* Calls :
+* Called By :
+*****************************************************************************/
+void *
+mem_item_lookup (void *pdata)
+{
+ nsfw_mem_type_info *mem_lookup = (nsfw_mem_type_info *) pdata;
+ void *ret;
+ NSFW_LOGDBG ("lookup mem]type=%u,name=%s", mem_lookup->ustype,
+ mem_lookup->stname.aname);
+ switch (mem_lookup->ustype)
+ {
+ case NSFW_MEM_MZONE:
+ ret = nsfw_mem_zone_lookup (&mem_lookup->stname);
+ break;
+ case NSFW_MEM_MBUF:
+ ret = nsfw_mem_mbfmp_lookup (&mem_lookup->stname);
+ break;
+ case NSFW_MEM_SPOOL:
+ ret = nsfw_mem_sp_lookup (&mem_lookup->stname);
+ break;
+ case NSFW_MEM_RING:
+ ret = nsfw_mem_ring_lookup (&mem_lookup->stname);
+ break;
+ default:
+ NSFW_LOGERR ("lookup mem err type]type=%d", mem_lookup->ustype);
+ return NULL;
+ }
+
+ if (NULL == ret)
+ {
+ NSFW_LOGERR ("mem lookup failed!]ret=%p,name=%s", ret,
+ mem_lookup->stname.aname);
+ return NULL;
+ }
+
+ return ret;
+}
+
+/*****************************************************************************
+* Prototype : mem_item_proc_by_msg
+* Description : call memory item process function
+* Input : void *pdata
+* nsfw_ps_mem_item_cfg* item_cfg
+* Output : None
+* Return Value : void*
+* Calls :
+* Called By :
+*****************************************************************************/
+void *
+mem_item_proc_by_msg (void *pdata, nsfw_ps_mem_item_cfg * item_cfg)
+{
+ char argv_buf[NSFW_MEM_CALL_ARG_BUF] = { 0 };
+
+ if ((NULL == item_cfg->change_fun) || (NULL == item_cfg->create_fun))
+ {
+ NSFW_LOGERR ("item error]change_fun=%p,create_fun=%p",
+ item_cfg->change_fun, item_cfg->create_fun);
+ return NULL;
+ }
+
+ if (FALSE ==
+ item_cfg->change_fun (item_cfg->usmsg_type, pdata, argv_buf,
+ NSFW_MEM_CALL_ARG_BUF))
+ {
+ NSFW_LOGERR ("call change_fun failed!]type=%u", item_cfg->usmsg_type);
+ return NULL;
+ }
+
+ void *pdataret = NULL;
+ pdataret = (item_cfg->create_fun) ((void *) argv_buf);
+ return pdataret;
+}
+
+/*****************************************************************************
+* Prototype : mem_init_rsp_msg
+* Description : init the rsp message
+* Input : nsfw_shmem_msg_head* msg
+* nsfw_shmem_msg_head *rsp
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+u8
+mem_init_rsp_msg (nsfw_shmem_msg_head * msg, nsfw_shmem_msg_head * rsp)
+{
+ nsfw_ps_mem_item_cfg *item_cfg =
+ mem_item_get_cfg_from_msg (msg->usmsg_type);
+ if (NULL == item_cfg)
+ {
+ NSFW_LOGERR ("get item cfg failed!]msg_type=%u", msg->usmsg_type);
+ return FALSE;
+ }
+
+ int idx;
+ int mem_count = msg->uslenth / item_cfg->item_size;
+
+ rsp->usmsg_type = msg->usmsg_type + 1;
+ rsp->uslenth = mem_count * sizeof (nsfw_shmem_ack);
+ nsfw_shmem_ack *pack = (nsfw_shmem_ack *) & (rsp->aidata[0]);
+ char *pdata = NULL;
+ for (idx = 0; idx < mem_count; idx++)
+ {
+ pdata = (char *) msg->aidata + idx * item_cfg->item_size;
+ pack->pbase_addr = NULL;
+ pack->usseq = ((nsfw_shmem_reserv_req *) pdata)->usseq;
+ pack->cstate = NSFW_MEM_ALLOC_FAIL;
+ pack++;
+ }
+
+ NSFW_LOGDBG ("init all rsp ack]mem_count=%d,msg_type=%u", mem_count,
+ msg->usmsg_type);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : mem_rel_mem_by_msg
+* Description : release memory by message
+* Input : nsfw_shmem_msg_head* req_msg
+* nsfw_shmem_msg_head *rsp
+* u32 pid
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+mem_rel_mem_by_msg (nsfw_shmem_msg_head * req_msg,
+ nsfw_shmem_msg_head * rsp, u32 pid)
+{
+ u32 i;
+ nsfw_ps_mem_item_cfg *item_cfg =
+ mem_item_get_cfg_from_msg (req_msg->usmsg_type);
+ if (NULL == item_cfg)
+ {
+ NSFW_LOGERR ("get item cfg failed!]msg_type=%u", req_msg->usmsg_type);
+ return FALSE;
+ }
+
+ unsigned int mem_count = req_msg->uslenth / item_cfg->item_size;
+ char *pdata = NULL;
+ nsfw_shmem_ack *pack = (nsfw_shmem_ack *) & (rsp->aidata[0]);
+ for (i = 0; i < mem_count; i++)
+ {
+ pdata = (char *) req_msg->aidata + i * item_cfg->item_size;
+ if (NULL != mem_item_proc_by_msg ((void *) pdata, item_cfg))
+ {
+ pack->cstate = NSFW_MEM_ALLOC_SUCC;
+ pack->pbase_addr = NULL;
+ }
+ pack++;
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : mem_lookup_mem_by_msg
+* Description : lookup memory by message
+* Input : nsfw_shmem_msg_head* mgr_msg
+* nsfw_shmem_msg_head *rsp
+* u32 pid
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+mem_lookup_mem_by_msg (nsfw_shmem_msg_head * mgr_msg,
+ nsfw_shmem_msg_head * rsp, u32 pid)
+{
+ i32 idx;
+ nsfw_ps_mem_item_cfg *item_cfg =
+ mem_item_get_cfg_from_msg (mgr_msg->usmsg_type);
+ if (NULL == item_cfg)
+ {
+ NSFW_LOGERR ("get item cfg failed!]msg_type=%u", mgr_msg->usmsg_type);
+ return FALSE;
+ }
+
+ int mem_count = mgr_msg->uslenth / item_cfg->item_size;
+ char *pdata = NULL;
+ void *paddr = NULL;
+ nsfw_shmem_ack *pack = (nsfw_shmem_ack *) & (rsp->aidata[0]);
+
+ for (idx = 0; idx < mem_count; idx++)
+ {
+ pdata = (char *) mgr_msg->aidata + idx * item_cfg->item_size;
+ paddr = mem_item_proc_by_msg ((void *) pdata, item_cfg);
+ if (NULL != paddr)
+ {
+ pack->cstate = NSFW_MEM_ALLOC_SUCC;
+ pack->pbase_addr = paddr;
+ }
+ pack++;
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : mem_alloc_mem_by_msg
+* Description : alloc memory by message
+* Input : nsfw_shmem_msg_head* mem_msg
+* nsfw_shmem_msg_head *rsp
+* Output : None
+* Return Value : ns_mem_info*
+* Calls :
+* Called By :
+*****************************************************************************/
+void *
+mem_alloc_mem_by_msg (nsfw_shmem_msg_head * mem_msg,
+ nsfw_shmem_msg_head * rsp)
+{
+ nsfw_ps_mem_item_cfg *item_cfg =
+ mem_item_get_cfg_from_msg (mem_msg->usmsg_type);
+ if (NULL == item_cfg)
+ {
+ NSFW_LOGERR ("get item cfg failed!]msg_type=%u", mem_msg->usmsg_type);
+ return NULL;
+ }
+
+ int i;
+ int j;
+ nsfw_mem_type_info mem_free;
+ char *pdata = NULL;
+ void *p_addr = NULL;
+
+ int mem_count = mem_msg->uslenth / item_cfg->item_size;
+ nsfw_shmem_ack *pack = (nsfw_shmem_ack *) & (rsp->aidata[0]);
+ for (i = 0; i < mem_count; i++)
+ {
+ pdata = (char *) mem_msg->aidata + i * item_cfg->item_size;
+ p_addr = mem_item_proc_by_msg ((void *) pdata, item_cfg);
+ if (NULL == p_addr)
+ {
+ NSFW_LOGERR
+ ("alloc mem failed!]type=%u,mem_count=%d,item=%d,name=%s",
+ mem_msg->usmsg_type, mem_count, i,
+ ((nsfw_shmem_reserv_req *) pdata)->aname);
+ goto fail_free_mem;
+ }
+
+ pack->cstate = NSFW_MEM_ALLOC_SUCC;
+ pack->pbase_addr = p_addr;
+ NSFW_LOGINF
+ ("alloc mem suc!]addr=%p,type=%u,mem_count=%d,item=%d,name=%s",
+ p_addr, mem_msg->usmsg_type, mem_count, i,
+ ((nsfw_shmem_reserv_req *) pdata)->aname);
+ pack++;
+ }
+ return p_addr;
+
+fail_free_mem:
+ for (j = 0; j < i; j++)
+ {
+ pdata = (char *) mem_msg->aidata + j * item_cfg->item_size;
+ if (EOK !=
+ STRCPY_S (mem_free.stname.aname, NSFW_MEM_NAME_LENTH,
+ ((nsfw_shmem_reserv_req *) pdata)->aname))
+ {
+ NSFW_LOGERR ("STRCPY_S failed]j=%d", j);
+ continue;
+ }
+
+ mem_free.ustype = item_cfg->mem_type;
+ mem_free.stname.entype = NSFW_SHMEM;
+ (void) mem_item_free (&mem_free);
+ NSFW_LOGINF ("free mem]addr=%p,type=%u,mem_count=%d,item=%d,name=%s",
+ p_addr, mem_msg->usmsg_type, mem_count, j,
+ ((nsfw_shmem_reserv_req *) pdata)->aname);
+ pack++;
+ }
+
+ return NULL;
+
+}
+
+/*****************************************************************************
+* Prototype : mem_alloc_req_proc
+* Description : memory message
+* Input : nsfw_mgr_msg* msg
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+mem_alloc_req_proc (nsfw_mgr_msg * msg)
+{
+ void *mem_addr = NULL;
+
+ if (NULL == msg)
+ {
+ NSFW_LOGERR ("msg nul");
+ return FALSE;
+ }
+
+ nsfw_shmem_msg_head *mem_msg = GET_USER_MSG (nsfw_shmem_msg_head, msg);
+ nsfw_mgr_msg *rsp_msg = nsfw_mgr_rsp_msg_alloc (msg);
+ if (NULL == rsp_msg)
+ {
+ NSFW_LOGERR ("alloc rsp msg failed]msg_type=%u", mem_msg->usmsg_type);
+ return FALSE;
+ }
+
+ nsfw_shmem_msg_head *mem_rsp_msg =
+ GET_USER_MSG (nsfw_shmem_msg_head, rsp_msg);
+
+ if (!mem_init_rsp_msg (mem_msg, mem_rsp_msg))
+ {
+ NSFW_LOGERR ("init rsp msg failed]msg_type=%u", mem_msg->usmsg_type);
+ nsfw_mgr_msg_free (rsp_msg);
+ return FALSE;
+ }
+
+ switch (mem_msg->usmsg_type)
+ {
+ case NSFW_MEM_LOOKUP_REQ_MSG:
+ if (!mem_lookup_mem_by_msg (mem_msg, mem_rsp_msg, msg->src_pid))
+ {
+ NSFW_LOGERR ("lookup mem msg failed]msg_type=%u",
+ mem_msg->usmsg_type);
+ goto sendrspmsg;
+ }
+ (void) mem_alloc_ps_info (msg->src_pid, msg->src_proc_type);
+ break;
+ case NSFW_RESERV_REQ_MSG:
+ case NSFW_MBUF_REQ_MSG:
+ case NSFW_SPPOOL_REQ_MSG:
+ case NSFW_RING_REQ_MSG:
+ mem_addr = mem_alloc_mem_by_msg (mem_msg, mem_rsp_msg);
+ if (NULL == mem_addr)
+ {
+ NSFW_LOGERR ("alloc mem msg failed]msg_type=%u",
+ mem_msg->usmsg_type);
+ (void) mem_init_rsp_msg (mem_msg, mem_rsp_msg);
+ goto sendrspmsg;
+ }
+ (void) mem_alloc_ps_info (msg->src_pid, msg->src_proc_type);
+ break;
+ case NSFW_RELEASE_REQ_MSG:
+ if (!mem_rel_mem_by_msg (mem_msg, mem_rsp_msg, msg->src_pid))
+ {
+ NSFW_LOGERR ("rel mem msg failed]msg_type=%u", mem_msg->usmsg_type);
+ goto sendrspmsg;
+ }
+ break;
+ default:
+ break;
+ }
+
+sendrspmsg:
+ (void) nsfw_mgr_send_msg (rsp_msg);
+ nsfw_mgr_msg_free (rsp_msg);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : mem_ps_exiting_resend
+* Description : send the exiting message again
+* Input : void *pps_info
+* void* argv
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+mem_ps_exiting_resend (void *pps_info, void *argv)
+{
+ u32 *count = argv;
+ nsfw_ps_info *ps_info = pps_info;
+ if (NULL == ps_info)
+ {
+ NSFW_LOGERR ("ps_info nul!");
+ return FALSE;
+ }
+
+ if (NSFW_PROC_APP != ps_info->proc_type)
+ {
+ return FALSE;
+ }
+
+ if (NSFW_PS_EXITING != ps_info->state)
+ {
+ return FALSE;
+ }
+
+ if (NULL != count)
+ {
+ NSFW_LOGINF ("send count]count=%u,pid=%u", *count, ps_info->host_pid);
+ if (NSFW_PS_SEND_PER_TIME < (*count)++)
+ {
+ struct timespec time_left =
+ { NSFW_PS_MEM_RESEND_TVLAUE +
+((*count) / NSFW_PS_SEND_PER_TIME), 0
+ };
+ ps_info->resend_timer_ptr =
+ (void *) nsfw_timer_reg_timer (NSFW_PS_MEM_RESEND_TIMER,
+ pps_info,
+ nsfw_mem_ps_exit_resend_timeout,
+ time_left);
+ return TRUE;
+ }
+ }
+
+ (void) mem_ps_exiting (ps_info, NULL);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_mem_srv_restore_timeout
+* Description : service waiting resume timeout
+* Input : u32 timer_type
+* void* data
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_mem_srv_restore_timeout (u32 timer_type, void *data)
+{
+ u32 max_count = 0;
+
+ g_mem_cfg.p_restore_timer = NULL;
+ if (TRUE == NSFW_SRV_STATE_SUSPEND)
+ {
+ NSFW_SRV_STATE_SUSPEND = FALSE;
+ (void) nsfw_ps_iterator (mem_ps_exiting_resend, &max_count);
+ }
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : mem_srv_ctrl_proc
+* Description : service control message process
+* Input : nsfw_mgr_msg* msg
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+mem_srv_ctrl_proc (nsfw_mgr_msg * msg)
+{
+ if (NULL == msg)
+ {
+ NSFW_LOGERR ("msg nul");
+ return FALSE;
+ }
+
+ nsfw_srv_ctrl_msg *ctrl_msg = GET_USER_MSG (nsfw_srv_ctrl_msg, msg);
+ nsfw_mgr_msg *rsp_msg = nsfw_mgr_rsp_msg_alloc (msg);
+ if (NULL == rsp_msg)
+ {
+ NSFW_LOGERR ("alloc rsp msg failed]msg=%p", msg);
+ return FALSE;
+ }
+ nsfw_srv_ctrl_msg *ctrl_rsp_msg = GET_USER_MSG (nsfw_srv_ctrl_msg, rsp_msg);
+ NSFW_LOGINF ("get srv ctrl state] state=%d", ctrl_msg->srv_state);
+
+ ctrl_rsp_msg->rsp_code = NSFW_MGR_SUCESS;
+
+ (void) nsfw_mgr_send_msg (rsp_msg);
+ nsfw_mgr_msg_free (rsp_msg);
+
+ if (NSFW_SRV_CTRL_RESUME == ctrl_msg->srv_state)
+ {
+ if (TRUE == NSFW_SRV_STATE_SUSPEND)
+ {
+ NSFW_SRV_STATE_SUSPEND = FALSE;
+ }
+ u32 max_count = 0;
+ (void) nsfw_ps_iterator (mem_ps_exiting_resend, &max_count);
+ if (NULL != g_mem_cfg.p_restore_timer)
+ {
+ nsfw_timer_rmv_timer ((nsfw_timer_info *)
+ g_mem_cfg.p_restore_timer);
+ g_mem_cfg.p_restore_timer = NULL;
+ }
+ }
+ else
+ {
+ NSFW_SRV_STATE_SUSPEND = TRUE;
+ struct timespec time_left = { NSFW_SRV_RESTORE_TVALUE, 0 };
+ g_mem_cfg.p_restore_timer =
+ (void *) nsfw_timer_reg_timer (0, NULL,
+ nsfw_mem_srv_restore_timeout,
+ time_left);
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_mem_module_init
+* Description : module init
+* Input : void* param
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_ps_mem_module_init (void *param)
+{
+ u32 proc_type = (u32) ((long long) param);
+ NSFW_LOGINF ("ps_mem module init]type=%u", proc_type);
+ switch (proc_type)
+ {
+ case NSFW_PROC_MAIN:
+ (void) nsfw_ps_reg_global_fun (NSFW_PROC_APP, NSFW_PS_EXITING,
+ mem_ps_exiting, NULL);
+ (void) nsfw_mgr_reg_msg_fun (MGR_MSG_MEM_ALLOC_REQ, mem_alloc_req_proc);
+ (void) NSFW_REG_SOFT_INT (NSFW_SRV_RESTORE_TIMER,
+ NSFW_SRV_RESTORE_TVALUE, 1, 0xFFFF);
+ (void) NSFW_REG_SOFT_INT (NSFW_APP_RESEND_TIMER,
+ NSFW_PS_MEM_RESEND_TVLAUE, 1, 0xFFFF);
+ (void) NSFW_REG_SOFT_INT (NSFW_APP_SEND_PER_TIME,
+ NSFW_PS_SEND_PER_TIME, 1, 0xFFFF);
+ break;
+ default:
+ if (proc_type < NSFW_PROC_MAX)
+ {
+ return 0;
+ }
+ return -1;
+ }
+
+ g_mem_cfg.srv_restore_tvalue = NSFW_SRV_RESTORE_TVALUE_DEF;
+ g_mem_cfg.ps_exit_resend_tvalue = NSFW_PS_MEM_RESEND_TVLAUE_DEF;
+ g_mem_cfg.ps_send_per_time = NSFW_PS_SEND_PER_TIME_DEF;
+
+ return 0;
+}
+
+/* *INDENT-OFF* */
+NSFW_MODULE_NAME (NSFW_PS_MEM_MODULE)
+NSFW_MODULE_PRIORITY (10)
+NSFW_MODULE_DEPENDS (NSFW_PS_MODULE)
+NSFW_MODULE_INIT (nsfw_ps_mem_module_init)
+/* *INDENT-ON* */
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/ipc/ps/nsfw_ps_mem_module.h b/src/framework/ipc/ps/nsfw_ps_mem_module.h
new file mode 100644
index 0000000..6b2b3c9
--- /dev/null
+++ b/src/framework/ipc/ps/nsfw_ps_mem_module.h
@@ -0,0 +1,87 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_PS_MEM_MODULE_H
+#define _NSFW_PS_MEM_MODULE_H
+
+#include "list.h"
+#include "pidinfo.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define MEMZONE_MAX_NAME 32
+#define NS_MAX_FORK_NUM 32
+#define NSFW_PS_MEM_MAX_FILTER 4
+
+#define NSFW_SRV_RESTORE_TVALUE_DEF 120
+#define NSFW_SRV_RESTORE_TVALUE g_mem_cfg.srv_restore_tvalue
+#define NSFW_SRV_STATE_SUSPEND g_mem_cfg.srv_suspend
+
+#define NSFW_PS_MEM_RESEND_TIMER 1
+#define NSFW_PS_MEM_RESEND_TVLAUE_DEF 2
+#define NSFW_PS_SEND_PER_TIME_DEF 150
+#define NSFW_PS_SEND_PER_TIME (g_mem_cfg.ps_send_per_time)
+#define NSFW_PS_MEM_RESEND_TVLAUE (g_mem_cfg.ps_exit_resend_tvalue)
+
+typedef struct _ns_mem_mng_init_cfg
+{
+ u16 srv_restore_tvalue;
+ u16 ps_exit_resend_tvalue;
+ u16 ps_send_per_time;
+ u16 srv_suspend;
+ void *p_restore_timer;
+} ns_mem_mng_init_cfg;
+
+/*mem alloc by msg begin*/
+typedef struct
+{
+ nsfw_mem_name stname;
+ u16 ustype;
+} nsfw_mem_type_info;
+
+#define NSFW_MEM_CALL_ARG_BUF 256
+#define MEM_GET_CALLARGV(_dst_member,_src_member, _dst_type,_srctype,_dst_buf, _src_buf) \
+ ((_dst_type*)(void*)_dst_buf)->_dst_member = ((_srctype*)(void*)_src_buf)->_src_member
+
+typedef void *(*nsfw_ps_mem_create_fun) (void *memstr);
+typedef u8 (*nsfw_ps_mem_msg_to_memstr) (u16 msg_type, char *msg_body,
+ char *memstr_buf, i32 buf_len);
+
+typedef struct __nsfw_ps_mem_item_cfg
+{
+ u16 usmsg_type;
+ u16 item_size;
+ u16 mem_type;
+ nsfw_ps_mem_create_fun create_fun;
+ nsfw_ps_mem_msg_to_memstr change_fun;
+} nsfw_ps_mem_item_cfg;
+
+void *mem_item_free (void *pdata);
+void *mem_item_lookup (void *pdata);
+u8 mem_item_get_callargv (u16 msg_type, char *msg_body, char *memstr_buf,
+ i32 buf_len);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _NSFW_PS_MEM_MODULE_H */
diff --git a/src/framework/ipc/ps/nsfw_ps_module.c b/src/framework/ipc/ps/nsfw_ps_module.c
new file mode 100644
index 0000000..e532c31
--- /dev/null
+++ b/src/framework/ipc/ps/nsfw_ps_module.c
@@ -0,0 +1,1725 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdlib.h>
+#include "types.h"
+#include "nstack_securec.h"
+#include "nsfw_init.h"
+
+#include "nsfw_mgr_com_api.h"
+#include "nsfw_ps_api.h"
+#include "nsfw_ps_module.h"
+#include "nsfw_mem_api.h"
+#include "nstack_log.h"
+#include "nsfw_base_linux_api.h"
+#include "nsfw_fd_timer_api.h"
+#include "nsfw_maintain_api.h"
+
+#include <errno.h>
+#include <sys/un.h>
+#include <stddef.h>
+#include <sys/epoll.h>
+#include <fcntl.h>
+
+#include <linux/cn_proc.h>
+#include <linux/connector.h>
+#include <linux/netlink.h>
+#include <dirent.h>
+#include <fnmatch.h>
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+nsfw_ps_init_cfg g_ps_cfg;
+
+nsfw_pid_item *g_ps_info = NULL;
+
+nsfw_pid_item *g_master_ps_info = NULL;
+
+struct list_head g_ps_runing_list;
+nsfw_ps_callback g_ps_init_callback[NSFW_PROC_MAX][NSFW_PS_MAX_CALLBACK];
+nsfw_ps_info g_main_ps_info;
+
+void *g_ps_chk_timer = NULL;
+
+/*****************************************************************************
+* Prototype : nsfw_ps_reg_fun
+* Description : reg the callback fun when process state change
+* Input : nsfw_ps_info *pps_info
+* u8 ps_state
+* nsfw_ps_proc_fun fun
+* void* argv
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_ps_reg_fun (nsfw_ps_info * pps_info, u8 ps_state,
+ nsfw_ps_proc_fun fun, void *argv)
+{
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("reg pps_info nul]state=%d,fun=%p", ps_state, fun);
+ return FALSE;
+ }
+
+ u32 i;
+ for (i = 0; i < NSFW_PS_MAX_CALLBACK; i++)
+ {
+ if (NULL == pps_info->callback[i].fun)
+ {
+ pps_info->callback[i].fun = fun;
+ pps_info->callback[i].argv = argv;
+ pps_info->callback[i].state = ps_state;
+ NSFW_LOGDBG
+ ("reg fun suc]ps_info=%p,state=%d,fun=%p,argv=%p,i=%d",
+ pps_info, ps_state, fun, argv, i);
+ return TRUE;
+ }
+ }
+
+ NSFW_LOGERR ("reg fun failed]ps_info=%p,state=%d,fun=%p,argv=%p,i=%d",
+ pps_info, ps_state, fun, argv, i);
+ return FALSE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_reg_global_fun
+* Description : reg the callback function of the specify proc_type state
+ change
+* Input : u8 proc_type
+* u8 ps_state
+* nsfw_ps_proc_fun fun
+* void* argv
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_ps_reg_global_fun (u8 proc_type, u8 ps_state, nsfw_ps_proc_fun fun,
+ void *argv)
+{
+ if (NSFW_PROC_MAX <= proc_type)
+ {
+ NSFW_LOGERR ("proc_type err]state=%u,fun=%p,type=%u", ps_state, fun,
+ proc_type);
+ return FALSE;
+ }
+
+ nsfw_ps_callback *cb_fun = g_ps_init_callback[proc_type];
+ u32 i;
+ for (i = 0; i < NSFW_PS_MAX_CALLBACK; i++)
+ {
+ if (NULL == cb_fun[i].fun)
+ {
+ cb_fun[i].fun = fun;
+ cb_fun[i].argv = argv;
+ cb_fun[i].state = ps_state;
+ NSFW_LOGINF ("reg fun suc]type=%u,state=%u,fun=%p,argv=%p,i=%u",
+ proc_type, ps_state, fun, argv, i);
+ return TRUE;
+ }
+ }
+
+ NSFW_LOGERR ("reg fun ful failed]type=%u,state=%u,fun=%p,argv=%p,i=%u",
+ proc_type, ps_state, fun, argv, i);
+ return FALSE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_exit
+* Description : when recvive the process exit finish message ,change
+ to exit state
+* Input : nsfw_mgr_msg* msg
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_ps_exit (nsfw_mgr_msg * msg)
+{
+ nsfw_ps_info *pps_info;
+ if (NULL == msg)
+ {
+ NSFW_LOGERR ("msg nul!");
+ return FALSE;
+ }
+
+ nsfw_ps_info_msg *ps_msg = GET_USER_MSG (nsfw_ps_info_msg, msg);
+ pps_info = nsfw_ps_info_get (ps_msg->host_pid);
+ NSFW_LOGINF ("recv ps exit]host_pid=%d,ps_info=%p", ps_msg->host_pid,
+ pps_info);
+
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("error msg pps_info nul]host_pid=%d", ps_msg->host_pid);
+ return true;
+ }
+ (void) nsfw_sw_ps_state (pps_info, NSFW_PS_EXIT);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_info_fork_alloc
+* Description : alloc fork ps_info
+* Input : u32 parent_pid
+* u32 child_pid
+* Output : None
+* Return Value : nsfw_ps_info*
+* Calls :
+* Called By :
+*****************************************************************************/
+nsfw_ps_info *
+nsfw_ps_info_fork_alloc (u32 parent_pid, u32 child_pid)
+{
+ nsfw_ps_info *pps_info = NULL;
+ nsfw_ps_info *pps_info_parent = NULL;
+ pps_info_parent = nsfw_ps_info_get (parent_pid);
+ if (NULL == pps_info_parent)
+ {
+ NSFW_LOGERR ("pps_info_parent nul");
+ return NULL;
+ }
+
+ pps_info = nsfw_ps_info_get (child_pid);
+ if (NULL == pps_info)
+ {
+ pps_info = nsfw_ps_info_alloc (child_pid, pps_info_parent->proc_type);
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR
+ ("alloc ps_info failed!]ps_info=%p,host_pid=%u,child_pid=%u",
+ pps_info_parent, pps_info_parent->host_pid, child_pid);
+ return NULL;
+ }
+ }
+ else
+ {
+ NSFW_LOGWAR
+ ("fork alloc mem before!]ps_info=%p,host_pid=%u,child_pid=%u",
+ pps_info_parent, pps_info_parent->host_pid, child_pid);
+ }
+
+ NSFW_LOGWAR ("ps_info fork]ps_info=%p,host_pid=%u,child_pid=%u",
+ pps_info_parent, pps_info_parent->host_pid, child_pid);
+ pps_info->parent_pid = parent_pid;
+ if (EOK !=
+ MEMCPY_S (pps_info->callback, sizeof (pps_info->callback),
+ pps_info_parent->callback,
+ sizeof (pps_info_parent->callback)))
+ {
+ nsfw_ps_info_free (pps_info);
+ NSFW_LOGERR ("ps_info set_failed");
+ return NULL;
+ }
+
+ if (EOK !=
+ MEMCPY_S (pps_info->value, sizeof (pps_info->value),
+ pps_info_parent->value, sizeof (pps_info_parent->value)))
+ {
+ nsfw_ps_info_free (pps_info);
+ NSFW_LOGERR ("ps_info cpy_failed");
+ return NULL;
+ }
+
+ return pps_info;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_info_alloc
+* Description : alloc ps_info
+* Input : u32 pid
+* u8 proc_type
+* Output : None
+* Return Value : nsfw_ps_info*
+* Calls :
+* Called By :
+*****************************************************************************/
+nsfw_ps_info *
+nsfw_ps_info_alloc (u32 pid, u8 proc_type)
+{
+ nsfw_ps_info *pps_info = NULL;
+ if (0 == nsfw_mem_ring_dequeue (g_ps_cfg.ps_info_pool, (void *) &pps_info))
+ {
+ NSFW_LOGERR ("alloc ps_info falied]pid=%u,type=%u", pid, proc_type);
+ return NULL;
+ }
+
+ if (NULL == pps_info)
+ {
+ if (NSFW_PROC_MAIN != proc_type || TRUE == g_main_ps_info.alloc_flag)
+ {
+ NSFW_LOGERR ("alloc ps_info nul]pid=%u,type=%u", pid, proc_type);
+ return NULL;
+ }
+ pps_info = &g_main_ps_info;
+ }
+
+ if (EOK !=
+ MEMSET_S (pps_info, sizeof (nsfw_ps_info), 0, sizeof (nsfw_ps_info)))
+ {
+ nsfw_ps_info_free (pps_info);
+ NSFW_LOGERR ("set failed");
+ return NULL;
+ }
+
+ pps_info->proc_type = proc_type;
+ pps_info->host_pid = pid;
+
+ if (proc_type < NSFW_PROC_MAX)
+ {
+ int retval;
+ retval =
+ MEMCPY_S (pps_info->callback, sizeof (pps_info->callback),
+ g_ps_init_callback[proc_type], sizeof (pps_info->callback));
+ if (EOK != retval)
+ {
+ NSFW_LOGERR ("Failed to MEMCPY_S]retval=%d", retval);
+ nsfw_ps_info_free (pps_info);
+ return NULL;
+ }
+ }
+ list_add_tail (&pps_info->node, &g_ps_runing_list);
+ pps_info->alloc_flag = TRUE;
+
+ (void) nsfw_sw_ps_state (pps_info, NSFW_PS_RUNNING);
+ if (pid < NSFW_MAX_PID)
+ {
+ g_ps_info[pid].ps_info = pps_info;
+ g_ps_info[pid].proc_type = proc_type;
+ }
+
+ NSFW_LOGINF ("ps_info alloc]ps_info=%p,pid=%u,type=%u", pps_info, pid,
+ proc_type);
+ return pps_info;
+
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_info_get
+* Description : get ps_info by pid
+* Input : u32 pid
+* Output : None
+* Return Value : inline nsfw_ps_info*
+* Calls :
+* Called By :
+*****************************************************************************/
+inline nsfw_ps_info *
+nsfw_ps_info_get (u32 pid)
+{
+ if (pid < NSFW_MAX_PID)
+ {
+ return g_ps_info[pid].ps_info;
+ }
+
+ return NULL;
+}
+
+nsfw_ps_info *
+nsfw_share_ps_info_get (u32 pid)
+{
+ if (pid < NSFW_MAX_PID)
+ {
+ return g_master_ps_info[pid].ps_info;
+ }
+
+ return NULL;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_info_free
+* Description : free ps_info
+* Input : nsfw_ps_info *ps_info
+* Output : None
+* Return Value : void
+* Calls :
+* Called By :
+*****************************************************************************/
+void
+nsfw_ps_info_free (nsfw_ps_info * ps_info)
+{
+ if (NULL == ps_info)
+ {
+ NSFW_LOGERR ("ps_info nul");
+ return;
+ }
+
+ if (FALSE == ps_info->alloc_flag)
+ {
+ NSFW_LOGERR ("ps_info refree]ps_info=%p,pid=%u,state=%u", ps_info,
+ ps_info->host_pid, ps_info->state);
+ return;
+ }
+
+ if (NULL != ps_info->exit_timer_ptr)
+ {
+ nsfw_timer_rmv_timer ((nsfw_timer_info *) ps_info->exit_timer_ptr);
+ ps_info->exit_timer_ptr = NULL;
+ }
+
+ if (NULL != ps_info->resend_timer_ptr)
+ {
+ nsfw_timer_rmv_timer ((nsfw_timer_info *) ps_info->resend_timer_ptr);
+ ps_info->resend_timer_ptr = NULL;
+ }
+
+ if (NULL != ps_info->hbt_timer_ptr)
+ {
+ nsfw_timer_rmv_timer ((nsfw_timer_info *) ps_info->hbt_timer_ptr);
+ ps_info->hbt_timer_ptr = NULL;
+ }
+
+ list_del (&ps_info->node);
+
+ ps_info->alloc_flag = FALSE;
+
+ NSFW_LOGINF ("ps_info free]ps_info=%p,pid=%u,state=%u", ps_info,
+ ps_info->host_pid, ps_info->state);
+ if (ps_info != &g_main_ps_info)
+ {
+ if (0 == nsfw_mem_ring_enqueue (g_ps_cfg.ps_info_pool, ps_info))
+ {
+ NSFW_LOGERR ("ps_info free failed]ps_info=%p,pid=%u,state=%u",
+ ps_info, ps_info->host_pid, ps_info->state);
+ return;
+ }
+ }
+
+ if (ps_info->host_pid < NSFW_MAX_PID)
+ {
+ g_ps_info[ps_info->host_pid].proc_type = 0;
+ g_ps_info[ps_info->host_pid].ps_info = NULL;
+ }
+
+ return;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_exiting_timeout
+* Description : waiting for remove ps_info timeout
+* Input : u32 timer_type
+* void* data
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_ps_exiting_timeout (u32 timer_type, void *data)
+{
+ nsfw_ps_info *pps_info = (nsfw_ps_info *) data;
+ NSFW_LOGINF ("ps_info timerout]pps_info=%p,pid=%u", pps_info,
+ pps_info->host_pid);
+ if (NULL == pps_info)
+ {
+ return TRUE;
+ }
+
+ pps_info->exit_timer_ptr = NULL;
+
+ if (TRUE == g_hbt_switch)
+ {
+ NSFW_LOGINF ("hbt off");
+ struct timespec time_left = { NSFW_PS_WEXIT_TVLAUE, 0 };
+ pps_info->exit_timer_ptr =
+ (void *) nsfw_timer_reg_timer (NSFW_PS_WEXIT_TIMER, pps_info,
+ nsfw_ps_exiting_timeout, time_left);
+ return TRUE;
+ }
+
+ if (NSFW_PS_EXITING == pps_info->state)
+ {
+ (void) nsfw_sw_ps_state (pps_info, NSFW_PS_EXIT);
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_exit_end_notify
+* Description : send exitting state process finished
+* Input : u32 pid
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_ps_exit_end_notify (u32 pid)
+{
+ nsfw_mgr_msg *rsp_msg =
+ nsfw_mgr_msg_alloc (MGR_MSG_APP_EXIT_RSP, NSFW_PROC_MASTER);
+ if (NULL == rsp_msg)
+ {
+ NSFW_LOGERR ("alloc rsp msg failed]pid=%u", pid);
+ return FALSE;
+ }
+
+ nsfw_ps_info_msg *ps_msg = GET_USER_MSG (nsfw_ps_info_msg, rsp_msg);
+ ps_msg->host_pid = pid;
+ (void) nsfw_mgr_send_msg (rsp_msg);
+ nsfw_mgr_msg_free (rsp_msg);
+ NSFW_LOGINF ("send exit rsp msg]pid=%u", pid);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_sw_ps_state
+* Description : switch ps_info state
+* Input : nsfw_ps_info* pps_info
+* u8 new_state
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_sw_ps_state (nsfw_ps_info * pps_info, u8 new_state)
+{
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("pps_info nul!");
+ return FALSE;
+ }
+
+ NSFW_LOGINF ("sw]ps_info=%p,pid=%u,type=%u,old_state=%u,newstate=%u",
+ pps_info, pps_info->host_pid, pps_info->proc_type,
+ pps_info->state, new_state);
+
+ i32 i, ret;
+ for (i = 0; i < NSFW_PS_MAX_CALLBACK; i++)
+ {
+ if (NULL == pps_info->callback[i].fun)
+ {
+ /* NULL should be the last fun */
+ break;
+ }
+
+ if (new_state == pps_info->callback[i].state)
+ {
+ ret =
+ pps_info->callback[i].fun (pps_info, pps_info->callback[i].argv);
+ NSFW_LOGINF ("callback fun]ps_info=%p,i=%d,fun=%p,argv=%p,ret=%d",
+ pps_info, i, pps_info->callback[i].fun,
+ pps_info->callback[i].argv, ret);
+ }
+ }
+
+ if (NSFW_PS_HBT_FAILED != new_state)
+ {
+ pps_info->state = new_state;
+ }
+
+ if (NSFW_PS_EXIT == new_state)
+ {
+ nsfw_ps_info_free (pps_info);
+ }
+
+ if (NSFW_PS_EXITING == new_state)
+ {
+ struct timespec time_left = { NSFW_PS_WEXIT_TVLAUE, 0 };
+ pps_info->exit_timer_ptr =
+ (void *) nsfw_timer_reg_timer (NSFW_PS_WEXIT_TIMER, pps_info,
+ nsfw_ps_exiting_timeout, time_left);
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_get_netlink_socket
+* Description : get netlink socket to kernel
+* Input : None
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_ps_get_netlink_socket ()
+{
+ int rc;
+ int nl_sock;
+ int size, size_len;
+ struct sockaddr_nl sa_nl;
+
+ nl_sock = nsfw_base_socket (PF_NETLINK, SOCK_DGRAM, NETLINK_CONNECTOR);
+ if (nl_sock == -1)
+ {
+ NSFW_LOGERR ("get netlink socket err]errno=%d", errno);
+ return -1;
+ }
+
+ rc = nsfw_set_close_on_exec (nl_sock);
+ if (rc == -1)
+ {
+ (void) nsfw_base_close (nl_sock);
+ NSFW_LOGERR ("set exec err]fd=%d, errno=%d", nl_sock, errno);
+ return -1;
+ }
+
+ sa_nl.nl_family = AF_NETLINK;
+ sa_nl.nl_groups = CN_IDX_PROC;
+ sa_nl.nl_pid = getpid ();
+
+ rc = nsfw_base_bind (nl_sock, (struct sockaddr *) &sa_nl, sizeof (sa_nl));
+ if (rc == -1)
+ {
+ (void) nsfw_base_close (nl_sock);
+ NSFW_LOGERR ("netlink bind err]netlink_fd=%d, errno=%d", nl_sock,
+ errno);
+ return -1;
+ }
+
+ struct __attribute__ ((aligned (NLMSG_ALIGNTO)))
+ {
+ struct nlmsghdr nl_hdr;
+ struct __attribute__ ((__packed__))
+ {
+ struct cn_msg cn_msg;
+ enum proc_cn_mcast_op cn_mcast;
+ };
+ } nlcn_msg;
+ if (EOK != MEMSET_S (&nlcn_msg, sizeof (nlcn_msg), 0, sizeof (nlcn_msg)))
+ {
+ (void) nsfw_base_close (nl_sock);
+ NSFW_LOGERR ("netlink set failed]netlink_fd=%d", nl_sock);
+ return -1;
+ }
+ nlcn_msg.nl_hdr.nlmsg_len = sizeof (nlcn_msg);
+ nlcn_msg.nl_hdr.nlmsg_pid = getpid ();
+ nlcn_msg.nl_hdr.nlmsg_type = NLMSG_DONE;
+
+ nlcn_msg.cn_msg.id.idx = CN_IDX_PROC;
+ nlcn_msg.cn_msg.id.val = CN_VAL_PROC;
+ nlcn_msg.cn_msg.len = sizeof (enum proc_cn_mcast_op);
+
+ nlcn_msg.cn_mcast = PROC_CN_MCAST_LISTEN;
+ rc = nsfw_base_send (nl_sock, &nlcn_msg, sizeof (nlcn_msg), 0);
+ if (rc == -1)
+ {
+ (void) nsfw_base_close (nl_sock);
+ NSFW_LOGERR ("netlink send err]netlink_fd=%d, errno=%d", nl_sock,
+ errno);
+ return -1;
+ }
+
+ NSFW_LOGINF ("netlink connect]netlink_fd=%d", nl_sock);
+ int val, len;
+ len = sizeof (val);
+ if (0 >
+ nsfw_base_getsockopt (nl_sock, SOL_SOCKET, SO_RCVBUF, &val,
+ (socklen_t *) & len))
+ {
+ NSFW_LOGERR ("get socket opt err!]error=%d", errno);
+ }
+ else
+ {
+ NSFW_LOGINF ("] SO_RCVBUF=0x%x", val);
+ }
+
+ size = MAX_NET_LINK_BUF;
+ size_len = sizeof (size);
+ if (0 >
+ nsfw_base_setsockopt (nl_sock, SOL_SOCKET, SO_RCVBUFFORCE,
+ (void *) &size, (socklen_t) size_len))
+ {
+ NSFW_LOGERR ("set socket opt err!]error=%d", errno);
+ }
+
+ size_len = sizeof (size);
+ if (0 >
+ nsfw_base_getsockopt (nl_sock, SOL_SOCKET, SO_RCVBUF, (void *) &size,
+ (socklen_t *) & size_len))
+ {
+ NSFW_LOGERR ("get socket opt err!]error=%d", errno);
+ }
+
+ NSFW_LOGINF ("] SO_RCVBUF=0x%x", size);
+ return nl_sock;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_change_fun
+* Description : proc change when receive event from kernel
+* Input : i32 epfd
+* i32 fd
+* u32 events
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_ps_change_fun (i32 epfd, i32 fd, u32 events)
+{
+ i32 rc;
+ u32 host_pid;
+ nsfw_ps_info *pps_info = NULL;
+
+ struct __attribute__ ((aligned (NLMSG_ALIGNTO)))
+ {
+ struct nlmsghdr nl_hdr;
+ struct __attribute__ ((__packed__))
+ {
+ struct cn_msg cn_msg;
+ struct proc_event proc_ev;
+ };
+ } nlcn_msg;
+
+ if (!(events & EPOLLIN))
+ {
+ return TRUE;
+ }
+
+ while (1)
+ {
+ rc = nsfw_base_recv (fd, &nlcn_msg, sizeof (nlcn_msg), 0);
+ if (rc == 0)
+ {
+ NSFW_LOGWAR ("netlink recv 0]netlink_fd=%d,errno=%d", fd, errno);
+ break;
+ }
+ else if (rc == -1)
+ {
+ if (errno == EINTR || errno == EAGAIN)
+ {
+ break;
+ }
+ NSMON_LOGERR ("netlink recv]netlink_fd=%d,errno=%d", fd, errno);
+ if (errno == ENOBUFS)
+ {
+ struct timespec time_left = { NSFW_PS_FIRST_CHK_TVLAUE, 0 };
+ g_ps_chk_timer =
+ (void *) nsfw_timer_reg_timer (NSFW_PS_CHK_TIMER,
+ (void *) FALSE,
+ nsfw_ps_chk_timeout,
+ time_left);
+ }
+ break;
+ }
+
+ switch (nlcn_msg.proc_ev.what)
+ {
+ case PROC_EVENT_EXIT:
+ host_pid = nlcn_msg.proc_ev.event_data.exit.process_pid;
+ pps_info = nsfw_ps_info_get (host_pid);
+ if (NULL == pps_info)
+ {
+ NSFW_LOGDBG ("pps info is null]host pid=%d", host_pid);
+ break;
+ }
+
+ if (NSFW_PS_EXITING == pps_info->state)
+ {
+ NSFW_LOGERR ("double pid info]ps_info=%p,pid=%d", pps_info,
+ host_pid);
+ break;
+ }
+
+ (void) nsfw_sw_ps_state (pps_info, NSFW_PS_EXITING);
+ break;
+ default:
+ break;
+ }
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_start_netlink
+* Description : reg ps_module to epoll thread
+* Input : None
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*
+*****************************************************************************/
+u8
+nsfw_ps_start_netlink ()
+{
+ i32 netlink_fd = nsfw_ps_get_netlink_socket ();
+ if (netlink_fd < 0)
+ {
+ NSFW_LOGERR ("get netlink failed!");
+ return FALSE;
+ }
+
+ NSFW_LOGINF ("start ps_info module!]netlink_fd=%d", netlink_fd);
+ (void) nsfw_mgr_reg_sock_fun (netlink_fd, nsfw_ps_change_fun);
+ (void) nsfw_mgr_reg_msg_fun (MGR_MSG_APP_EXIT_RSP, nsfw_ps_exit);
+ return TRUE;
+}
+
+/* for heartbeat check*/
+
+NSTACK_STATIC __thread i32 t_val_idx = 0;
+nsfw_thread_dogs g_thread_dogs[NSFW_MAX_THREAD_DOGS_COUNT];
+/*****************************************************************************
+* Prototype : nsfw_all_thread_chk
+* Description : get all thread check state
+* Input : None
+* Output : None
+* Return Value : i32
+* Calls :
+* Called By :
+*****************************************************************************/
+i32
+nsfw_all_thread_chk ()
+{
+ i32 count = -1;
+ u32 i;
+ for (i = 0; i < NSFW_MAX_THREAD_DOGS_COUNT; i++)
+ {
+ if (FALSE == g_thread_dogs[i].alloc_flag)
+ {
+ continue;
+ }
+
+ if (count < g_thread_dogs[i].count)
+ {
+ count = g_thread_dogs[i].count;
+ }
+
+ g_thread_dogs[i].count++;
+ }
+ return count;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_thread_chk_unreg
+* Description : cancel the thread check
+* Input : None
+* Output : None
+* Return Value : inline u8
+* Calls :
+* Called By :
+*****************************************************************************/
+inline u8
+nsfw_thread_chk_unreg ()
+{
+ if (t_val_idx > 0 && t_val_idx < NSFW_MAX_THREAD_DOGS_COUNT)
+ {
+ g_thread_dogs[t_val_idx].alloc_flag = FALSE;
+ g_thread_dogs[t_val_idx].count = 0;
+ g_thread_dogs[t_val_idx].thread_id = 0;
+ t_val_idx = 0;
+ }
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_thread_chk
+* Description : add the thread to check, and should be call in every
+ process cycle
+* Input : None
+* Output : None
+* Return Value : inline u8
+* Calls :
+* Called By :
+*****************************************************************************/
+inline u8
+nsfw_thread_chk ()
+{
+ u32 i;
+ if (t_val_idx > 0 && t_val_idx < NSFW_MAX_THREAD_DOGS_COUNT)
+ {
+ g_thread_dogs[t_val_idx].count = 0;
+ return TRUE;
+ }
+
+ for (i = 1; i < NSFW_MAX_THREAD_DOGS_COUNT; i++)
+ {
+ if ((FALSE == g_thread_dogs[i].alloc_flag)
+ && __sync_bool_compare_and_swap (&g_thread_dogs[i].alloc_flag,
+ FALSE, TRUE))
+ {
+ t_val_idx = i;
+ break;
+ }
+ }
+
+ if (t_val_idx > 0 && t_val_idx < NSFW_MAX_THREAD_DOGS_COUNT)
+ {
+ g_thread_dogs[t_val_idx].count = 0;
+ g_thread_dogs[t_val_idx].thread_id = syscall (SYS_gettid);
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************
+Parameters : None
+Return :
+Description :
+*****************************************************************/
+nsfw_thread_dogs *
+nsfw_thread_getDog ()
+{
+ u32 i;
+ nsfw_thread_dogs *retPtr = NULL;
+ if (t_val_idx > 0 && t_val_idx < NSFW_MAX_THREAD_DOGS_COUNT)
+ {
+ return &g_thread_dogs[t_val_idx];
+ }
+
+ for (i = 1; i < NSFW_MAX_THREAD_DOGS_COUNT; i++)
+ {
+ if ((FALSE == g_thread_dogs[i].alloc_flag)
+ && __sync_bool_compare_and_swap (&g_thread_dogs[i].alloc_flag,
+ FALSE, TRUE))
+ {
+ t_val_idx = i;
+ break;
+ }
+ }
+
+ if (t_val_idx > 0 && t_val_idx < NSFW_MAX_THREAD_DOGS_COUNT)
+ {
+ g_thread_dogs[t_val_idx].count = 0;
+ g_thread_dogs[t_val_idx].thread_id = syscall (SYS_gettid);
+ retPtr = &g_thread_dogs[t_val_idx];
+ }
+ return retPtr;
+}
+
+pthread_t g_all_thread[MAX_THREAD] = { 0 };
+
+u8
+nsfw_reg_trace_thread (pthread_t tid)
+{
+ int i;
+ for (i = 0; i < MAX_THREAD; i++)
+ {
+ if ((0 == g_all_thread[i])
+ && __sync_bool_compare_and_swap (&g_all_thread[i], 0, tid))
+ {
+ return TRUE;
+ }
+ }
+ return FALSE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_check_dst_init
+* Description : send check msg check the dst process is listening
+* Input : u8 dst_proc_type
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_ps_check_dst_init (u8 dst_proc_type)
+{
+ u8 ps_state = FALSE;
+ nsfw_mgr_msg *msg =
+ nsfw_mgr_msg_alloc (MGR_MSG_CHK_INIT_REQ, dst_proc_type);
+ if (NULL == msg)
+ {
+ NSFW_LOGERR ("alloc msg failed]dst_typ=%d", dst_proc_type);
+ return FALSE;
+ }
+
+ nsfw_ps_chk_msg *ps_msg = GET_USER_MSG (nsfw_ps_chk_msg, msg);
+ ps_msg->ps_state = TRUE;
+
+ nsfw_mgr_msg *rsp_msg = nsfw_mgr_null_rspmsg_alloc ();
+ if (NULL == rsp_msg)
+ {
+ nsfw_mgr_msg_free (msg);
+ NSFW_LOGERR ("alloc rsp msg failed]dst_typ=%d", dst_proc_type);
+ return FALSE;
+ }
+
+ (void) nsfw_mgr_send_req_wait_rsp (msg, rsp_msg);
+
+ ps_msg = GET_USER_MSG (nsfw_ps_chk_msg, rsp_msg);
+ ps_state = ps_msg->ps_state;
+
+ nsfw_mgr_msg_free (msg);
+ nsfw_mgr_msg_free (rsp_msg);
+ NSFW_LOGINF ("get peer state]dst_type=%d,state=%d", dst_proc_type,
+ ps_state);
+ return ps_state;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_send_hbt
+* Description : seng heart beat message to peer
+* Input : nsfw_ps_info* pps_info
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_ps_send_hbt (nsfw_ps_info * pps_info)
+{
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("null ps_info!");
+ return FALSE;
+ }
+
+ nsfw_mgr_msg *req_msg =
+ nsfw_mgr_msg_alloc (MGR_MSG_CHK_HBT_REQ, pps_info->proc_type);
+ if (NULL == req_msg)
+ {
+ NSFW_LOGERR ("alloc req msg failed]pps_info=%p", pps_info);
+ return FALSE;
+ }
+
+ req_msg->dst_pid = pps_info->host_pid;
+ nsfw_ps_chk_msg *ps_msg = GET_USER_MSG (nsfw_ps_chk_msg, req_msg);
+ ps_msg->ps_state = TRUE;
+ u8 ret = nsfw_mgr_send_msg (req_msg);
+ nsfw_mgr_msg_free (req_msg);
+ NSFW_LOGDBG ("send hbt msg]ret=%d,pps_info=%p,pid=%d,type=%d", ret,
+ pps_info, pps_info->host_pid, pps_info->proc_type);
+ return ret;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_recv_hbt
+* Description : recv heart beat message process
+* Input : nsfw_mgr_msg* msg
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_ps_recv_hbt (nsfw_mgr_msg * msg)
+{
+ if (NULL == msg)
+ {
+ NSFW_LOGERR ("error msg nul!");
+ return FALSE;
+ }
+
+ nsfw_mgr_msg *rsp_msg = nsfw_mgr_rsp_msg_alloc (msg);
+ if (NULL == rsp_msg)
+ {
+ NSFW_LOGERR ("alloc rsp failed,drop msg!" MSGINFO, PRTMSG (msg));
+ return FALSE;
+ }
+
+ nsfw_ps_chk_msg *ps_msg = GET_USER_MSG (nsfw_ps_chk_msg, rsp_msg);
+ ps_msg->ps_state = TRUE;
+ ps_msg->thread_chk_count = nsfw_all_thread_chk ();
+ (void) nsfw_mgr_send_msg (rsp_msg);
+ nsfw_mgr_msg_free (rsp_msg);
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_recv_hbt_rsp
+* Description : recv heart beat response message process
+* Input : nsfw_mgr_msg* msg
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_ps_recv_hbt_rsp (nsfw_mgr_msg * msg)
+{
+ if (NULL == msg)
+ {
+ NSFW_LOGERR ("error msg nul!");
+ return FALSE;
+ }
+
+ nsfw_ps_chk_msg *ps_msg = GET_USER_MSG (nsfw_ps_chk_msg, msg);
+ if (TRUE != ps_msg->ps_state)
+ {
+ NSFW_LOGERR ("Heartbeat failed]pid=%u,type=%u", msg->src_pid,
+ msg->src_proc_type);
+ return FALSE;
+ }
+
+ nsfw_ps_info *pps_info = nsfw_ps_info_get (msg->src_pid);
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("get ps_info failed]pid=%u,type=%u,count=%d",
+ msg->src_pid, msg->src_proc_type,
+ ps_msg->thread_chk_count);
+ return FALSE;
+ }
+
+ if (0 == ps_msg->thread_chk_count)
+ {
+ pps_info->hbt_failed_count = 0;
+ return TRUE;
+ }
+
+ if (pps_info->hbt_failed_count > (u32) ps_msg->thread_chk_count)
+ {
+ pps_info->hbt_failed_count = (u32) ps_msg->thread_chk_count;
+ }
+
+ NSFW_LOGERR ("Heartbeat failed]pid=%u,type=%u,count=%d,ps_count=%u",
+ msg->src_pid, msg->src_proc_type, ps_msg->thread_chk_count,
+ pps_info->hbt_failed_count);
+ return FALSE;
+}
+
+int
+nsfw_ps_reset_hbt (void *pps_info, void *argv)
+{
+ nsfw_ps_info *ps_info = pps_info;
+ if (NULL == ps_info)
+ {
+ NSFW_LOGERR ("ps_info nul!");
+ return FALSE;
+ }
+
+ if (NSFW_PROC_MAIN != ps_info->proc_type)
+ {
+ return FALSE;
+ }
+
+ ps_info->hbt_failed_count = *(u32 *) argv;
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_hbt_timeout
+* Description : heart beat time out
+* Input : u32 timer_type
+* void* data
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_ps_hbt_timeout (u32 timer_type, void *data)
+{
+ nsfw_ps_info *pps_info = (nsfw_ps_info *) data;
+
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("null ps_info!");
+ return FALSE;
+ }
+
+ if (NULL == pps_info->hbt_timer_ptr)
+ {
+ NSFW_LOGERR ("hbt has stop]pps_info=%p", pps_info);
+ pps_info->hbt_failed_count = 0;
+ return TRUE;
+ }
+
+ if (TRUE == g_hbt_switch)
+ {
+ struct timespec time_left = { NSFW_CHK_HBT_TVLAUE, 0 };
+ pps_info->hbt_timer_ptr =
+ (void *) nsfw_timer_reg_timer (NSFW_CHK_HBT_TIMER, data,
+ nsfw_ps_hbt_timeout, time_left);
+ return TRUE;
+ }
+
+ /* nic init may cost a few seconds, master will restart main if heartbeat timeout */
+ if (NSFW_SOFT_HBT_CHK_COUNT != NSFW_MAX_HBT_CHK_COUNT)
+ {
+ if (NSFW_SOFT_HBT_CHK_COUNT < NSFW_MAX_HBT_CHK_COUNT)
+ {
+ u32 new_hbt_count = 0;
+ (void) nsfw_ps_iterator (nsfw_ps_reset_hbt, &new_hbt_count);
+ }
+
+ NSFW_MAX_HBT_CHK_COUNT = NSFW_SOFT_HBT_CHK_COUNT;
+ }
+
+ if (NSFW_MAX_HBT_CHK_COUNT <= pps_info->hbt_failed_count)
+ {
+ (void) nsfw_sw_ps_state (pps_info, NSFW_PS_HBT_FAILED);
+ /*reset counter */
+ pps_info->hbt_failed_count = 0;
+ }
+
+ if (TRUE != nsfw_ps_send_hbt (pps_info))
+ {
+ }
+
+ if (pps_info->hbt_failed_count > 0)
+ {
+ NSFW_LOGWAR ("Heartbeat failed]pid=%u,ps_count=%u, max_count=%d",
+ pps_info->host_pid, pps_info->hbt_failed_count,
+ NSFW_MAX_HBT_CHK_COUNT);
+ }
+
+ pps_info->hbt_failed_count++;
+ struct timespec time_left = { NSFW_CHK_HBT_TVLAUE, 0 };
+ pps_info->hbt_timer_ptr =
+ (void *) nsfw_timer_reg_timer (NSFW_CHK_HBT_TIMER, data,
+ nsfw_ps_hbt_timeout, time_left);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_hbt_start
+* Description : start ps_info heart beat
+* Input : nsfw_ps_info* pps_info
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_ps_hbt_start (nsfw_ps_info * pps_info)
+{
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("null ps_info!");
+ return FALSE;
+ }
+
+ if (NULL != pps_info->hbt_timer_ptr)
+ {
+ NSFW_LOGERR ("hbt start before!]ps_info=%p,pid=%u,type=%u", pps_info,
+ pps_info->host_pid, pps_info->proc_type);
+ return FALSE;
+ }
+
+ struct timespec time_left = { NSFW_CHK_HBT_TVLAUE, 0 };
+ pps_info->hbt_timer_ptr =
+ (void *) nsfw_timer_reg_timer (NSFW_CHK_HBT_TIMER, (void *) pps_info,
+ nsfw_ps_hbt_timeout, time_left);
+ NSFW_LOGINF ("hbt start!]ps_info=%p,pid=%u,type=%u", pps_info,
+ pps_info->host_pid, pps_info->proc_type);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_hbt_stop
+* Description : stop ps_info heart beat
+* Input : nsfw_ps_info* pps_info
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_ps_hbt_stop (nsfw_ps_info * pps_info)
+{
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("null ps_info!");
+ return FALSE;
+ }
+
+ if (NULL != pps_info->hbt_timer_ptr)
+ {
+ nsfw_timer_rmv_timer ((nsfw_timer_info *) pps_info->hbt_timer_ptr);
+ pps_info->hbt_timer_ptr = NULL;
+ }
+
+ NSFW_LOGINF ("hbt stop!]ps_info=%p,pid=%d,type=%d", pps_info,
+ pps_info->host_pid, pps_info->proc_type);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_iterator
+* Description : get all ps_info process by fun
+* Input : nsfw_ps_proc_fun fun
+* void* argv
+* Output : None
+* Return Value : u32
+* Calls :
+* Called By :
+*****************************************************************************/
+u32
+nsfw_ps_iterator (nsfw_ps_proc_fun fun, void *argv)
+{
+ u32 count = 0;
+ nsfw_ps_info *pps_info = NULL;
+ struct list_head *tNode;
+
+ if (NULL == fun)
+ {
+ NSFW_LOGERR ("fun null!");
+ return count;
+ }
+
+ LINT_LIST ()list_for_each_entry (pps_info, tNode, (&g_ps_runing_list), node)
+ {
+ (void) fun (pps_info, argv);
+ count++;
+ }
+
+ NSFW_LOGINF ("proc pid]count=%u", count);
+ return count;
+}
+
+int
+filter (const struct dirent *dir)
+{
+ return !fnmatch ("[1-9]*", dir->d_name, 0);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_realloc_pid
+* Description : realloc pid
+* Input : u32 pid
+* Output : None
+* Return Value : inline nsfw_ps_info*
+* Calls :
+* Called By :
+*****************************************************************************/
+inline nsfw_ps_info *
+nsfw_ps_realloc_pid (u32 pid, u8 realloc_flg)
+{
+ nsfw_ps_info *pps_info = NULL;
+ if (pid >= NSFW_MAX_PID)
+ {
+ return NULL;
+ }
+
+ if (g_ps_info[pid].ps_info == NULL)
+ {
+ return NULL;
+ }
+
+ if (TRUE == realloc_flg)
+ {
+ pps_info = nsfw_ps_info_alloc (pid, g_ps_info[pid].proc_type);
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("alloc ps_info failed!]pid=%u,type=%u", pid,
+ g_ps_info[pid].proc_type);
+ return NULL;
+ }
+ }
+ else
+ {
+ pps_info = g_ps_info[pid].ps_info;
+ }
+
+ pps_info->rechk_flg = TRUE;
+ return pps_info;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_reload_pid
+* Description : reload pid
+* Input : None
+* Output : None
+* Return Value : void
+* Calls :
+* Called By :
+*****************************************************************************/
+void
+nsfw_ps_reload_pid ()
+{
+ struct dirent **namelist;
+ i32 n;
+ u32 host_pid;
+ nsfw_ps_info *pps_info = NULL;
+
+ n = scandir ("/proc", &namelist, filter, 0);
+ if (n < 0)
+ {
+ NSFW_LOGERR ("buf null");
+ }
+ else
+ {
+ while (n--)
+ {
+ host_pid = strtol (namelist[n]->d_name, NULL, 10);
+ pps_info = nsfw_ps_info_get (host_pid);
+ if (NULL != pps_info)
+ {
+ pps_info->rechk_flg = FALSE;
+ }
+ free (namelist[n]);
+ }
+ free (namelist);
+ }
+ return;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_realloc_all_pid
+* Description : realloc all pid
+* Input : u32 *main_pid
+* Output : None
+* Return Value : void
+* Calls :
+* Called By :
+*****************************************************************************/
+void
+nsfw_ps_realloc_all_pid (u32 * main_pid, u8 realloc_flg)
+{
+ u32 i;
+ nsfw_ps_info *pps_info = NULL;
+ for (i = 0; i < NSFW_MAX_PID; i++)
+ {
+ pps_info = nsfw_ps_realloc_pid (i, realloc_flg);
+ if (NULL != main_pid)
+ {
+ if (NULL != pps_info && NSFW_PROC_MAIN == pps_info->proc_type)
+ {
+ (*main_pid) = i;
+ }
+ }
+ }
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_chk_exit_timeout
+* Description : chk ps info
+* Input : u32 timer_type
+* void* data
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_ps_chk_exit_timeout (u32 timer_type, void *data)
+{
+ u32 i;
+ nsfw_ps_info *pps_info = NULL;
+ u32 pid = (u64) data;
+
+ /*main pid exit first */
+ if (NULL != data)
+ {
+ pps_info = nsfw_ps_info_get (pid);
+ if (NULL != pps_info && TRUE == pps_info->rechk_flg)
+ {
+ if (NSFW_PS_EXITING != pps_info->state)
+ {
+ NSFW_LOGWAR ("rechk pid exit]ps_info=%p,pid=%u", pps_info,
+ pps_info->host_pid);
+ (void) nsfw_sw_ps_state (pps_info, NSFW_PS_EXITING);
+ pps_info->rechk_flg = FALSE;
+ }
+ }
+ }
+
+ for (i = 0; i < NSFW_MAX_PID; i++)
+ {
+ pps_info = nsfw_ps_info_get (i);
+ if (NULL != pps_info && TRUE == pps_info->rechk_flg)
+ {
+ if (NSFW_PS_EXITING == pps_info->state)
+ {
+ NSFW_LOGWAR ("double pid info]ps_info=%p,pid=%u", pps_info,
+ pps_info->host_pid);
+ continue;
+ }
+
+ NSFW_LOGWAR ("rechk pid exit]ps_info=%p,pid=%u", pps_info,
+ pps_info->host_pid);
+ (void) nsfw_sw_ps_state (pps_info, NSFW_PS_EXITING);
+ pps_info->rechk_flg = FALSE;
+ }
+ }
+
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_chk_timeout
+* Description : load all running pid
+* Input : u32 timer_type
+* void* data
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+****************************************************************************/
+int
+nsfw_ps_chk_timeout (u32 timer_type, void *data)
+{
+ u32 main_pid = 0;
+ u8 realloc_flg = (u8) (u64) data;
+
+ nsfw_ps_realloc_all_pid (&main_pid, realloc_flg);
+ nsfw_ps_reload_pid ();
+
+ struct timespec time_left = { NSFW_PS_CHK_EXIT_TVLAUE, 0 };
+ g_ps_chk_timer =
+ (void *) nsfw_timer_reg_timer (NSFW_PS_CHK_EXIT_TVLAUE,
+ (void *) (u64) main_pid,
+ nsfw_ps_chk_exit_timeout, time_left);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_rechk_pid_exit
+* Description : rechck pid exit
+* Input : nsfw_ps_proc_fun fun
+* void* argv
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_ps_rechk_pid_exit (nsfw_ps_pid_fun fun, void *argv)
+{
+ u32 ulI = 0;
+ if (NULL == fun)
+ {
+ NSFW_LOGERR ("input err! fun null");
+ return -1;
+ }
+
+ u8 *ps_pid = malloc (NSFW_MAX_PID);
+ if (NULL == ps_pid)
+ {
+ NSFW_LOGERR ("malloc failed");
+ return -1;
+ }
+
+ int retval = MEMSET_S (ps_pid, NSFW_MAX_PID, 0, NSFW_MAX_PID);
+ if (EOK != retval)
+ {
+ NSFW_LOGERR ("MEMSET_S failed]retval=%d", retval);
+ free (ps_pid);
+ return -1;
+ }
+
+ struct dirent **namelist;
+ i32 n;
+ u32 host_pid;
+ n = scandir ("/proc", &namelist, filter, 0);
+ if (n < 0)
+ {
+ NSFW_LOGERR ("buf null");
+ free (ps_pid);
+ return -1;
+ }
+
+ while (n--)
+ {
+ host_pid = strtol (namelist[n]->d_name, NULL, 10);
+ if (host_pid < NSFW_MAX_PID)
+ {
+ ps_pid[ulI] = TRUE;
+ }
+ free (namelist[n]);
+ }
+ free (namelist);
+
+ int count = 0;
+ for (ulI = 0; ulI < NSFW_MAX_PID; ulI++)
+ {
+ if ((NULL != g_master_ps_info[ulI].ps_info) && (FALSE == ps_pid[ulI]))
+ {
+ (void) fun (ulI, g_master_ps_info[ulI].proc_type, argv);
+ NSFW_LOGWAR ("rechk pid exit]pid=%d,type=%d", ulI,
+ g_master_ps_info[ulI].proc_type);
+ count++;
+ continue;
+ }
+ }
+
+ free (ps_pid);
+ return count;
+}
+
+void
+nsfw_ps_cfg_set_chk_count (u16 count)
+{
+ g_ps_cfg.ps_chk_hbt_count = count;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_ps_module_init
+* Description : ps_module init
+* Input : void* param
+* Output : None
+* Return Value : static int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_ps_module_init (void *param)
+{
+ u32 proc_type = (u32) ((long long) param);
+ nsfw_ps_init_cfg *ps_cfg = &g_ps_cfg;
+ int retval;
+ nsfw_pid_item *pid_info = NULL;
+ NSFW_LOGINF ("ps module init]type=%u", proc_type);
+
+ ps_cfg->ps_chk_hbt_count = NSFW_MAX_HBT_CHK_COUNT_DEF;
+ ps_cfg->ps_chk_hbt_tvalue = NSFW_CHK_HBT_TVLAUE_DEF;
+ ps_cfg->ps_chk_hbt_soft_count = ps_cfg->ps_chk_hbt_count;
+
+ nsfw_mem_zone pzoneinfo;
+ pzoneinfo.isocket_id = NSFW_SOCKET_ANY;
+ pzoneinfo.stname.entype = NSFW_SHMEM;
+ pzoneinfo.lenth = sizeof (nsfw_pid_item) * NSFW_MAX_PID;
+ if (-1 ==
+ SPRINTF_S (pzoneinfo.stname.aname, NSFW_MEM_NAME_LENTH, "%s",
+ "MAS_PS_INFO"))
+ {
+ NSFW_LOGERR ("SPRINTF_S failed]");
+ return -1;
+ }
+
+ switch (proc_type)
+ {
+ case NSFW_PROC_MASTER:
+ {
+ (void) nsfw_mgr_reg_msg_fun (MGR_MSG_CHK_HBT_RSP,
+ nsfw_ps_recv_hbt_rsp);
+ (void) NSFW_REG_SOFT_INT (NSFW_HBT_TIMER, NSFW_CHK_HBT_TVLAUE, 1,
+ 0xFFFF);
+ (void) NSFW_REG_SOFT_INT (NSFW_HBT_COUNT_PARAM,
+ NSFW_SOFT_HBT_CHK_COUNT, 1, 0xFFFF);
+ (void) NSFW_REG_SOFT_INT (NSFW_APP_EXIT_TIMER, NSFW_PS_WEXIT_TVLAUE,
+ 1, 0xFFFF);
+
+ pid_info = nsfw_mem_zone_lookup (&pzoneinfo.stname);
+ if (NULL == pid_info)
+ {
+ pid_info = nsfw_mem_zone_create (&pzoneinfo);
+ if (NULL == pid_info)
+ {
+ NSFW_LOGERR ("alloc rec nul!");
+ return -1;
+ }
+
+ retval =
+ MEMSET_S (pid_info, (sizeof (nsfw_pid_item) * NSFW_MAX_PID),
+ 0, (sizeof (nsfw_pid_item) * NSFW_MAX_PID));
+ if (EOK != retval)
+ {
+ NSFW_LOGERR ("MEMSET_S failed]retval=%d.\n", retval);
+ return -1;
+ }
+ }
+
+ MEM_STAT (NSFW_PS_MODULE, pzoneinfo.stname.aname, NSFW_SHMEM,
+ pzoneinfo.lenth);
+ g_ps_info = pid_info;
+ break;
+ }
+ case NSFW_PROC_MAIN:
+ {
+ pid_info = malloc (sizeof (nsfw_pid_item) * NSFW_MAX_PID);
+ if (NULL == pid_info)
+ {
+ NSFW_LOGERR ("malloc mem failed!");
+ return -1;
+ }
+
+ retval =
+ MEMSET_S (pid_info, (sizeof (nsfw_pid_item) * NSFW_MAX_PID), 0,
+ (sizeof (nsfw_pid_item) * NSFW_MAX_PID));
+ if (EOK != retval)
+ {
+ NSFW_LOGERR ("MEMSET_S failed]retval=%d.\n", retval);
+ free (pid_info);
+ return -1;
+ }
+
+ g_ps_info = pid_info;
+
+ pzoneinfo.stname.enowner = NSFW_PROC_MAIN;
+ pid_info = nsfw_mem_zone_create (&pzoneinfo);
+ if (NULL == pid_info)
+ {
+ NSFW_LOGERR ("create pid_info failed!");
+ return -1;
+ }
+
+ g_master_ps_info = pid_info;
+ break;
+ }
+ default:
+ return 0;
+ }
+
+ ps_cfg->ps_info_size = NSFW_PS_INFO_MAX_COUNT;
+ ps_cfg->ps_waite_exit_tvalue = NSFW_PS_WEXIT_TVLAUE_DEF;
+ ps_cfg->net_link_buf = MAX_NET_LINK_BUF_DEF;
+
+ INIT_LIST_HEAD (&(g_ps_runing_list));
+
+ nsfw_mem_sppool pmpinfo;
+ pmpinfo.enmptype = NSFW_MRING_MPMC;
+ pmpinfo.usnum = ps_cfg->ps_info_size;
+ pmpinfo.useltsize = sizeof (nsfw_ps_info);
+ pmpinfo.isocket_id = NSFW_SOCKET_ANY;
+ pmpinfo.stname.entype = NSFW_NSHMEM;
+ if (-1 ==
+ SPRINTF_S (pmpinfo.stname.aname, NSFW_MEM_NAME_LENTH, "%s",
+ "MAS_PS_INFOPOOL"))
+ {
+ NSFW_LOGERR ("SPRINTF_S failed]");
+ return -1;
+ }
+
+ ps_cfg->ps_info_pool = nsfw_mem_sp_create (&pmpinfo);
+
+ if (!ps_cfg->ps_info_pool)
+ {
+ NSFW_LOGERR ("alloc ps info pool_err");
+ return -1;
+ }
+
+ MEM_STAT (NSFW_PS_MODULE, pmpinfo.stname.aname, NSFW_NSHMEM,
+ nsfw_mem_get_len (ps_cfg->ps_info_pool, NSFW_MEM_SPOOL));
+
+ if (NSFW_PROC_MASTER != proc_type)
+ {
+ return 0;
+ }
+
+ struct timespec time_left = { NSFW_PS_FIRST_CHK_TVLAUE, 0 };
+ g_ps_chk_timer =
+ (void *) nsfw_timer_reg_timer (NSFW_PS_CHK_TIMER, (void *) TRUE,
+ nsfw_ps_chk_timeout, time_left);
+
+ if (TRUE != nsfw_ps_start_netlink ())
+ {
+ return -1;
+ }
+
+ return 0;
+}
+
+/* *INDENT-OFF* */
+NSFW_MODULE_NAME (NSFW_PS_MODULE)
+NSFW_MODULE_PRIORITY (10)
+NSFW_MODULE_DEPENDS (NSFW_MGR_COM_MODULE)
+NSFW_MODULE_DEPENDS (NSFW_TIMER_MODULE)
+NSFW_MODULE_INIT (nsfw_ps_module_init)
+/* *INDENT-ON* */
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/ipc/ps/nsfw_ps_module.h b/src/framework/ipc/ps/nsfw_ps_module.h
new file mode 100644
index 0000000..b754cea
--- /dev/null
+++ b/src/framework/ipc/ps/nsfw_ps_module.h
@@ -0,0 +1,99 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_PS_MODULE_H
+#define _NSFW_PS_MODULE_H
+
+#include "nsfw_ps_api.h"
+#include "nsfw_mem_api.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+/*==============================================*
+ * constants or macros define *
+ *----------------------------------------------*/
+
+#define NSFW_MAX_PID 65535
+COMPAT_PROTECT (NSFW_MAX_PID, 65535);
+
+#define NSFW_PS_INFO_MAX_COUNT 4095
+#define MAX_NET_LINK_BUF_DEF 0x34000*32
+
+#define NSFW_PS_WEXIT_TIMER 1
+#define NSFW_PS_WEXIT_TVLAUE_DEF 180
+
+#define NSFW_PS_WEXIT_TVLAUE (g_ps_cfg.ps_waite_exit_tvalue)
+#define MAX_NET_LINK_BUF (g_ps_cfg.net_link_buf)
+
+typedef struct _nsfw_ps_init_cfg
+{
+ u32 ps_info_size;
+ u32 net_link_buf;
+
+ u16 ps_waite_exit_tvalue;
+ u16 ps_chk_hbt_count;
+ u16 ps_chk_hbt_soft_count;
+ u16 ps_chk_hbt_tvalue;
+
+ mring_handle ps_info_pool;
+} nsfw_ps_init_cfg;
+
+#define NSFW_PS_CHK_TIMER 1
+#define NSFW_PS_FIRST_CHK_TVLAUE 1
+#define NSFW_PS_CHK_EXIT_TVLAUE 1
+
+typedef struct _nsfw_pid_item
+{
+ u8 proc_type;
+ u8 u8_reserve;
+ u16 u16_reserve;
+ u32 u32_reserve;
+ nsfw_ps_info *ps_info;
+} nsfw_pid_item;
+
+int nsfw_ps_change_fun (i32 epfd, i32 socket, u32 events);
+u8 nsfw_sw_ps_state (nsfw_ps_info * pps_info, u8 new_state);
+
+/* for heartbeat checking*/
+#define NSFW_MAX_THREAD_DOGS_COUNT 8
+#define NSFW_CHK_HBT_TIMER 1
+#define NSFW_MAX_HBT_PROC_FUN 4
+
+#define NSFW_CHK_HBT_TVLAUE_DEF 1
+
+#define NSFW_MAX_HBT_CHK_COUNT (g_ps_cfg.ps_chk_hbt_count)
+#define NSFW_SOFT_HBT_CHK_COUNT (g_ps_cfg.ps_chk_hbt_soft_count)
+#define NSFW_CHK_HBT_TVLAUE (g_ps_cfg.ps_chk_hbt_tvalue)
+
+typedef struct _nsfw_ps_chk_msg
+{
+ u32 ps_state;
+ i32 thread_chk_count;
+} nsfw_ps_chk_msg;
+
+int nsfw_ps_chk_timeout (u32 timer_type, void *data);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _NSFW_PS_MODULE_H */
diff --git a/src/framework/ipc/ps/nsfw_recycle_module.c b/src/framework/ipc/ps/nsfw_recycle_module.c
new file mode 100644
index 0000000..bb3844f
--- /dev/null
+++ b/src/framework/ipc/ps/nsfw_recycle_module.c
@@ -0,0 +1,666 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdlib.h>
+#include "types.h"
+#include "nstack_securec.h"
+#include "nsfw_init.h"
+
+#include "nsfw_mgr_com_api.h"
+#include "nsfw_mem_api.h"
+#include "nsfw_ps_api.h"
+#include "nsfw_ps_mem_api.h"
+#include "nsfw_fd_timer_api.h"
+#include "nsfw_recycle_module.h"
+#include "nsfw_maintain_api.h"
+#include "nstack_log.h"
+#include "common_mem_api.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+/* only work on nStackMain*/
+nsfw_recycle_cfg g_rec_cfg;
+
+nsfw_recycle_fun g_rec_fun[NSFW_REC_TYPE_MAX] = { 0 };
+
+nsfw_rec_fun_info g_rec_lock_fun[NSFW_REC_LOCK_REL_MAX_FUN];
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_reg_fun
+* Description : reg one recycle type recycle funciton
+* Input : u16 rec_type
+* nsfw_recycle_fun fun
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_recycle_reg_fun (u16 rec_type, nsfw_recycle_fun fun)
+{
+ if (NULL == fun || rec_type >= NSFW_REC_TYPE_MAX)
+ {
+ NSFW_LOGERR ("argv err]fun=%p,type=%u", fun, rec_type);
+ return FALSE;
+ }
+
+ g_rec_fun[rec_type] = fun;
+ NSFW_LOGINF ("reg]fun=%d,type=%u", fun, rec_type);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_lock_rel_fun
+* Description : reg lock release when app exit run
+* Input : nsfw_recycle_fun fun
+* void* data
+* u8 proc_type: NULL as all
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_recycle_lock_rel_fun (nsfw_recycle_fun fun, void *data, u8 proc_type)
+{
+ if (NULL == fun)
+ {
+ NSFW_LOGERR ("argv err]fun=%p,data=%p", fun, data);
+ return FALSE;
+ }
+
+ u32 i;
+
+ for (i = 0; i < NSFW_REC_LOCK_REL_MAX_FUN; i++)
+ {
+ if (NULL == g_rec_lock_fun[i].rec_fun)
+ {
+ g_rec_lock_fun[i].rec_fun = fun;
+ g_rec_lock_fun[i].data = data;
+ g_rec_lock_fun[i].proc_type = proc_type;
+ NSFW_LOGINF ("reg mgr_msg fun suc]fun=%p,data=%p", fun, data);
+ return TRUE;
+ }
+ }
+
+ NSFW_LOGINF ("reg]fun=%p,data=%p", fun, data);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_exit_pid_lock
+* Description : release all lock fun
+* Input : u32 pid
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_recycle_exit_pid_lock (u32 pid, u8 proc_type, void *argv)
+{
+ u32 i;
+ NSFW_LOGINF ("release lock]pid=%d,type=%d", pid, proc_type);
+ for (i = 0; i < NSFW_REC_LOCK_REL_MAX_FUN; i++)
+ {
+ if (NULL == g_rec_lock_fun[i].rec_fun)
+ {
+ break;
+ }
+
+ if ((NSFW_PROC_NULL == g_rec_lock_fun[i].proc_type)
+ || (proc_type == g_rec_lock_fun[i].proc_type))
+ {
+ (void) g_rec_lock_fun[i].rec_fun (pid, g_rec_lock_fun[i].data, 0);
+ }
+ }
+
+ return 0;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_obj_end
+* Description : one recycle object process finished notify
+* Input : u32 pid
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_recycle_obj_end (u32 pid)
+{
+ nsfw_mgr_msg *rsp_msg =
+ nsfw_mgr_msg_alloc (MGR_MSG_RCC_END_REQ, NSFW_PROC_MAIN);
+ if (NULL == rsp_msg)
+ {
+ NSFW_LOGERR ("alloc rsp msg failed]pid=%u", pid);
+ return FALSE;
+ }
+
+ nsfw_ps_info_msg *ps_msg = GET_USER_MSG (nsfw_ps_info_msg, rsp_msg);
+ ps_msg->host_pid = pid;
+ (void) nsfw_mgr_send_msg (rsp_msg);
+ nsfw_mgr_msg_free (rsp_msg);
+ NSFW_LOGINF ("send obj end msg]pid=%d", pid);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_callback_all_obj
+* Description : process all recycle object
+* Input : u32 pid
+* nsfw_recycle_pool *rec_pool
+* Output : None
+* Return Value : nsfw_rcc_stat
+* Calls :
+* Called By :
+*****************************************************************************/
+nsfw_rcc_stat
+nsfw_recycle_callback_all_obj (u32 pid, nsfw_recycle_pool * rec_pool)
+{
+ u32 match = 0;
+ nsfw_recycle_obj *obj = NULL;
+ if (NULL == rec_pool)
+ {
+ return NSFW_RCC_CONTINUE;
+ }
+
+ nsfw_recycle_obj *p_start = rec_pool->obj;
+ u32 i;
+ u32 size = rec_pool->pool_size;
+
+ nsfw_ps_info *pps_info;
+ pps_info = nsfw_ps_info_get (pid);
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("get ps_info falied!]pid=%d", pid);
+ return NSFW_RCC_CONTINUE;
+ }
+
+ i32 cur_idx = (i32) (u64) nsfw_ps_get_uv (pps_info, NSFW_REC_IDX);
+
+ if (-1 == cur_idx)
+ {
+ cur_idx = 0;
+ nsfw_ps_set_uv (pps_info, NSFW_REC_IDX, (void *) (u64) cur_idx);
+ (void) nsfw_recycle_exit_pid_lock (pid, NSFW_PROC_APP, NULL);
+ }
+ else
+ {
+ cur_idx++;
+ nsfw_ps_set_uv (pps_info, NSFW_REC_IDX, (void *) (u64) cur_idx);
+ }
+
+ for (i = cur_idx; i < size; i++)
+ {
+ obj = &p_start[i];
+ cur_idx = i;
+ nsfw_ps_set_uv (pps_info, NSFW_REC_IDX, (void *) (u64) cur_idx);
+ if (FALSE == obj->alloc_flag)
+ {
+ continue;
+ }
+
+ if ((obj->rec_type < NSFW_REC_TYPE_MAX)
+ && (NULL != g_rec_fun[obj->rec_type]))
+ {
+ match++;
+ if (NSFW_RCC_SUSPEND ==
+ g_rec_fun[obj->rec_type] (pid, obj->data, obj->rec_type))
+ {
+ NSFW_LOGINF
+ ("call suspend]type=%d,obj_pid=%d,pid=%d,count=%d",
+ obj->rec_type, obj->host_pid, pid, match);
+ return NSFW_RCC_SUSPEND;
+ }
+ }
+ else
+ {
+ NSFW_LOGERR ("obj_error!drop]type=%d,obj_pid=%d,pid=%d",
+ obj->rec_type, obj->host_pid, pid);
+ }
+ }
+
+ NSFW_LOGWAR ("rec obj]pid=%d,count=%d,cur_idx=%d", pid, match, cur_idx);
+ return NSFW_RCC_CONTINUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_pid_obj
+* Description : recycle object with pid
+* Input : u32 pid
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_recycle_pid_obj (u32 pid)
+{
+ nsfw_ps_info *pps_info;
+ pps_info = nsfw_ps_info_get (pid);
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("get ps_info falied!]pid=%d", pid);
+ return FALSE;
+ }
+
+ nsfw_recycle_pool *rec_pool = g_rec_cfg.mem_rec_obj_pool;
+ void *timer_ptr = nsfw_ps_get_uv (pps_info, NSFW_REC_TIMER);
+ if (NSFW_RCC_SUSPEND == nsfw_recycle_callback_all_obj (pid, rec_pool))
+ {
+ if (NULL != timer_ptr)
+ {
+ nsfw_timer_rmv_timer (timer_ptr);
+ timer_ptr = NULL;
+ }
+
+ struct timespec time_left = { NSFW_REC_WEND_TVLAUE, 0 };
+ timer_ptr =
+ (void *) nsfw_timer_reg_timer (NSFW_REC_WEND_TIMER,
+ (void *) (u64) pid,
+ nsfw_recycle_obj_timeout, time_left);
+ nsfw_ps_set_uv (pps_info, NSFW_REC_TIMER, timer_ptr);
+ return TRUE;
+ }
+
+ if (NULL != timer_ptr)
+ {
+ nsfw_timer_rmv_timer (timer_ptr);
+ nsfw_ps_set_uv (pps_info, NSFW_REC_TIMER, NULL);
+ }
+
+ (void) nsfw_ps_exit_end_notify (pid);
+ nsfw_ps_info_free (pps_info);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_all_obj
+* Description :
+* Input : u32 pid
+* nsfw_mem_addr_msg *addr_msg
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_recycle_all_obj (u32 pid)
+{
+ nsfw_ps_info *pps_info;
+ pps_info = nsfw_ps_info_get (pid);
+ if (NULL == pps_info)
+ {
+ pps_info = nsfw_ps_info_alloc (pid, NSFW_PROC_APP);
+ if (NULL == pps_info)
+ {
+ NSFW_LOGERR ("alloc ps_info falied!]pid=%u", pid);
+ return FALSE;
+ }
+ }
+
+ nsfw_ps_set_uv (pps_info, NSFW_REC_IDX, (void *) (-1));
+ nsfw_ps_set_uv (pps_info, NSFW_REC_TIMER, NULL);
+ return nsfw_recycle_pid_obj (pid);
+}
+
+/*****************************************************************************
+* Prototype : mem_app_exit_proc
+* Description : exiting message process
+* Input : nsfw_mgr_msg* msg
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+mem_app_exit_proc (nsfw_mgr_msg * msg)
+{
+ if (NULL == msg)
+ {
+ NSFW_LOGERR ("msg nul");
+ return FALSE;
+ }
+
+ nsfw_ps_info_msg *ps_info_msg = GET_USER_MSG (nsfw_ps_info_msg, msg);
+
+ /* look up the app rec memzone and release all resource */
+ /* no need to send rsp for it will be send after stack process over */
+ if (TRUE == nsfw_recycle_all_obj (ps_info_msg->host_pid))
+ {
+ NSFW_LOGINF ("obj found!]pid=%d", ps_info_msg->host_pid);
+ return TRUE;
+ }
+
+ (void) nsfw_ps_exit_end_notify (ps_info_msg->host_pid);
+ return FALSE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_obj_end_proc
+* Description : obj recycle finished notify process
+* Input : nsfw_mgr_msg* msg
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_recycle_obj_end_proc (nsfw_mgr_msg * msg)
+{
+ if (NULL == msg)
+ {
+ NSFW_LOGERR ("msg nul");
+ return FALSE;
+ }
+
+ nsfw_ps_info_msg *ps_info_msg = GET_USER_MSG (nsfw_ps_info_msg, msg);
+
+ return nsfw_recycle_pid_obj (ps_info_msg->host_pid);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_obj_timeout
+* Description : recycle object timeout process
+* Input : u32 timer_type
+* void* data
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_recycle_obj_timeout (u32 timer_type, void *data)
+{
+ u32 pid = (u64) data;
+ void *timer_ptr = NULL;
+ NSFW_LOGINF ("ps_info timerout]pid=%u", pid);
+
+ nsfw_ps_info *pps_info;
+ pps_info = nsfw_ps_info_get (pid);
+ if (NULL != pps_info)
+ {
+ nsfw_recycle_pool *rec_pool = g_rec_cfg.mem_rec_obj_pool;
+ if (NULL != rec_pool)
+ {
+ if (TRUE == g_hbt_switch)
+ {
+ struct timespec time_left = { NSFW_REC_WEND_TVLAUE, 0 };
+ timer_ptr =
+ (void *) nsfw_timer_reg_timer (timer_type, data,
+ nsfw_recycle_obj_timeout,
+ time_left);
+ nsfw_ps_set_uv (pps_info, NSFW_REC_TIMER, timer_ptr);
+ return TRUE;
+ }
+ }
+ nsfw_ps_set_uv (pps_info, NSFW_REC_TIMER, timer_ptr);
+ }
+
+ (void) nsfw_recycle_pid_obj (pid);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : mem_rec_zone_init
+* Description : init recycle zone in app, only work on App
+* Input : None
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+mem_rec_zone_init ()
+{
+ nsfw_mem_mring pringinfo;
+ pringinfo.enmptype = NSFW_MRING_MPMC;
+ pringinfo.isocket_id = NSFW_SOCKET_ANY;
+ pringinfo.stname.entype = NSFW_NSHMEM;
+ pringinfo.usnum = MEM_RECYCLE_PER_PRO_QUE;
+ u32 i;
+ for (i = 0; i < NSFW_REC_PRO_MAX; i++)
+ {
+ if (-1 ==
+ SPRINTF_S (pringinfo.stname.aname, NSFW_MEM_NAME_LENTH, "%s%d",
+ MEM_REC_QUEUE_NAME, i))
+ {
+ NSFW_LOGERR ("SPRINTF_S failed]");
+ return FALSE;
+ }
+ g_rec_cfg.mem_rec_pro[i] = nsfw_mem_ring_create (&pringinfo);
+ if (NULL == g_rec_cfg.mem_rec_pro[i])
+ {
+ NSFW_LOGERR ("alloc rec ring nul!");
+ return FALSE;
+ }
+ }
+
+ MEM_STAT (NSFW_RECYCLE_MODULE, MEM_REC_QUEUE_NAME, NSFW_NSHMEM,
+ NSFW_REC_PRO_MAX * nsfw_mem_get_len (g_rec_cfg.mem_rec_pro[0],
+ NSFW_MEM_RING));
+
+ nsfw_mem_zone pzoneinfo;
+ pzoneinfo.isocket_id = NSFW_SOCKET_ANY;
+ pzoneinfo.stname.entype = NSFW_NSHMEM;
+ pzoneinfo.lenth =
+ MEM_RECYCLE_OBJ_MAX_NUM * sizeof (nsfw_recycle_obj) +
+ sizeof (nsfw_recycle_pool);
+ if (-1 ==
+ SPRINTF_S (pzoneinfo.stname.aname, NSFW_MEM_NAME_LENTH, "%s",
+ MEM_REC_POOL_NAME))
+ {
+ NSFW_LOGERR ("SPRINTF_S failed]");
+ return FALSE;
+ }
+
+ g_rec_cfg.mem_rec_obj_pool = nsfw_mem_zone_create (&pzoneinfo);
+ if (NULL == g_rec_cfg.mem_rec_obj_pool)
+ {
+ NSFW_LOGERR ("alloc rec pool nul!");
+ return FALSE;
+ }
+
+ MEM_STAT (NSFW_RECYCLE_MODULE, MEM_REC_POOL_NAME, NSFW_NSHMEM,
+ pzoneinfo.lenth);
+
+ int retval;
+ retval =
+ MEMSET_S (g_rec_cfg.mem_rec_obj_pool, pzoneinfo.lenth, 0,
+ pzoneinfo.lenth);
+ if (EOK != retval)
+ {
+ NSFW_LOGERR ("mem set init failed!");
+ return FALSE;
+ }
+
+ i32 j;
+ nsfw_recycle_pool *rec_pool =
+ (nsfw_recycle_pool *) g_rec_cfg.mem_rec_obj_pool;
+ rec_pool->pool_size = MEM_RECYCLE_OBJ_MAX_NUM;
+
+ nsfw_recycle_obj *p_start = rec_pool->obj;
+ for (i = 0; i < NSFW_REC_PRO_MAX; i++)
+ {
+ for (j = 0; j < MEM_RECYCLE_PER_PRO_QUE; j++)
+ {
+ if (FALSE == p_start[j].alloc_flag)
+ {
+ if (0 ==
+ nsfw_mem_ring_enqueue (g_rec_cfg.mem_rec_pro[i],
+ &p_start[j]))
+ {
+ NSFW_LOGERR ("enqueue failed");
+ break;
+ }
+ }
+ }
+ p_start = p_start + MEM_RECYCLE_PER_PRO_QUE;
+ }
+
+ NSFW_LOGINF ("init rec pool and ring suc!");
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_reg_obj
+* Description : reg one recycle object
+* Input : u8 priority
+* u16 rec_type
+* void* data
+* Output : None
+* Return Value : void *
+* Calls :
+* Called By :
+*****************************************************************************/
+void *
+nsfw_recycle_reg_obj (u8 priority, u16 rec_type, void *data)
+{
+ if (NSFW_REC_PRO_MAX <= priority)
+ {
+ NSFW_LOGERR ("pro error]priority=%d,rec_type=%d,data=%p", priority,
+ rec_type, data);
+ return NULL;
+ }
+
+ nsfw_recycle_obj *obj = NULL;
+ if (0 ==
+ nsfw_mem_ring_dequeue (g_rec_cfg.mem_rec_pro[priority], (void *) &obj))
+ {
+ NSFW_LOGERR ("dequeue error]priority=%d,rec_type=%d,data=%p",
+ priority, rec_type, data);
+ return NULL;
+ }
+
+ if (EOK != MEMSET_S (obj, sizeof (*obj), 0, sizeof (*obj)))
+ {
+ if (0 == nsfw_mem_ring_enqueue (g_rec_cfg.mem_rec_pro[priority], obj))
+ {
+ NSFW_LOGERR ("enqueue error]priority=%d,rec_type=%d,data=%p",
+ priority, rec_type, data);
+ }
+
+ NSFW_LOGERR ("mem set error]priority=%d,rec_type=%d,data=%p",
+ priority, rec_type, data);
+ return NULL;
+ }
+
+ obj->alloc_flag = TRUE;
+ obj->rec_type = rec_type;
+ obj->data = data;
+ obj->host_pid = get_sys_pid ();
+ obj->alloc_flag = TRUE;
+ NSFW_LOGINF ("en queue obj]priority=%d,rec_type=%d,data=%p", priority,
+ rec_type, data);
+ return obj;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_rechk_lock
+* Description : add for rechk lock
+* Input : None
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_recycle_rechk_lock ()
+{
+ return nsfw_ps_rechk_pid_exit (nsfw_recycle_exit_pid_lock, NULL);
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_module_init
+* Description : module init
+* Input : void* param
+* Output : None
+* Return Value : static int
+* Calls :
+* Called By :
+*****************************************************************************/
+NSTACK_STATIC int nsfw_recycle_module_init (void *param);
+NSTACK_STATIC int
+nsfw_recycle_module_init (void *param)
+{
+ u32 proc_type = (u32) ((long long) param);
+ NSFW_LOGINF ("recycle module init]type=%d", proc_type);
+ g_rec_cfg.rec_waite_end_tvalue = NSFW_REC_WEND_TVLAUE_DEF;
+ switch (proc_type)
+ {
+ case NSFW_PROC_MASTER:
+ return 0;
+ case NSFW_PROC_MAIN:
+ (void) nsfw_mgr_reg_msg_fun (MGR_MSG_APP_EXIT_REQ, mem_app_exit_proc);
+ (void) nsfw_mgr_reg_msg_fun (MGR_MSG_RCC_END_REQ,
+ nsfw_recycle_obj_end_proc);
+ if (TRUE == mem_rec_zone_init ())
+ {
+ return 0;
+ }
+
+ return 0;
+ default:
+ if (proc_type < NSFW_PROC_MAX)
+ {
+ break;
+ }
+ return -1;
+ }
+
+ return 0;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_recycle_fork_init
+* Description : fork init
+* Input : None
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_recycle_fork_init ()
+{
+ /* reconnect to master after fork in child proc */
+ nsfw_mgr_close_dst_proc (NSFW_PROC_MAIN, 0);
+ nsfw_mgr_close_dst_proc (NSFW_PROC_MASTER, 0);
+ if (0 == nsfw_recycle_module_init ((void *) ((long long) NSFW_PROC_APP)))
+ {
+ return TRUE;
+ }
+ return FALSE;
+}
+
+/* *INDENT-OFF* */
+NSFW_MODULE_NAME (NSFW_RECYCLE_MODULE)
+NSFW_MODULE_PRIORITY (10)
+NSFW_MODULE_DEPENDS (NSFW_PS_MEM_MODULE)
+NSFW_MODULE_INIT (nsfw_recycle_module_init)
+/* *INDENT-ON* */
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/ipc/ps/nsfw_recycle_module.h b/src/framework/ipc/ps/nsfw_recycle_module.h
new file mode 100644
index 0000000..694c1d2
--- /dev/null
+++ b/src/framework/ipc/ps/nsfw_recycle_module.h
@@ -0,0 +1,84 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _NSFW_RECYCLE_MODULE_H
+#define _NSFW_RECYCLE_MODULE_H
+
+#include "nsfw_recycle_api.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#define MEM_RECYCLE_PER_PRO_QUE 128
+#define MEM_RECYCLE_OBJ_MAX_NUM (MEM_RECYCLE_PER_PRO_QUE*NSFW_REC_PRO_MAX)
+
+#define MEM_REC_POOL_NAME "APP_REC_POOL"
+#define MEM_REC_QUEUE_NAME "APP_REC_RINGQ"
+
+#define REC_POOL_MAGIC_FLAG 0xDBFC01A600000000
+
+#define NSFW_REC_WEND_TIMER 1
+#define NSFW_REC_WEND_TVLAUE_DEF 60
+
+#define NSFW_REC_WEND_TVLAUE (g_rec_cfg.rec_waite_end_tvalue)
+
+typedef struct _nsfw_recycle_obj
+{
+ u8 alloc_flag;
+ u8 u8reserve;
+ u16 rec_type;
+ u32 host_pid;
+ void *data;
+ u64 u64reserve;
+} nsfw_recycle_obj;
+
+#define NSFW_REC_LOCK_REL_MAX_FUN 32
+
+typedef struct _nsfw_rec_fun_info
+{
+ nsfw_recycle_fun rec_fun;
+ void *data;
+ u8 proc_type;
+} nsfw_rec_fun_info;
+
+typedef struct _nsfw_recycle_pool
+{
+ u32 pool_size;
+ nsfw_recycle_obj obj[0];
+} nsfw_recycle_pool;
+
+typedef struct _nsfw_recycle_cfg
+{
+ u16 rec_waite_end_tvalue;
+ mring_handle mem_rec_obj_pool;
+ mzone_handle mem_rec_pro[NSFW_REC_PRO_MAX];
+} nsfw_recycle_cfg;
+
+extern nsfw_rcc_stat nsfw_recycle_callback_all_obj (u32 pid,
+ nsfw_recycle_pool *
+ rec_pool);
+extern int nsfw_recycle_obj_timeout (u32 timer_type, void *data);
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _NSFW_RECYCLE_MODULE_H */
diff --git a/src/framework/ipc/ps/nsfw_soft_param.c b/src/framework/ipc/ps/nsfw_soft_param.c
new file mode 100644
index 0000000..d458040
--- /dev/null
+++ b/src/framework/ipc/ps/nsfw_soft_param.c
@@ -0,0 +1,296 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+/*==============================================*
+ * include header files *
+ *----------------------------------------------*/
+
+#include <stdlib.h>
+#include "types.h"
+#include "nstack_securec.h"
+#include "nsfw_init.h"
+
+#include "nstack_log.h"
+#include "nsfw_maintain_api.h"
+
+#include "nsfw_mem_api.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+typedef struct _nsfw_set_soft_item
+{
+ void *data;
+ u32 size;
+ u64 max;
+ u64 min;
+} nsfw_set_soft_item;
+
+/* *INDENT-OFF* */
+nsfw_set_soft_fun g_soft_fun[NSFW_MAX_SOFT_PARAM] = { 0 };
+nsfw_set_soft_item g_soft_int_cfg[NSFW_MAX_SOFT_PARAM];
+/* *INDENT-ON* */
+
+int
+nsfw_isdigitstr (const char *str)
+{
+ if (NULL == str || '\0' == str[0])
+ return 0;
+
+ while (*str)
+ {
+ if (*str < '0' || *str > '9')
+ return 0;
+ str++;
+ }
+ return 1;
+}
+
+u8
+nsfw_soft_param_reg_fun (u32 param_name, nsfw_set_soft_fun fun)
+{
+ if (NULL == fun || param_name >= NSFW_MAX_SOFT_PARAM)
+ {
+ NSFW_LOGERR ("argv err]fun=%p,type=%u", fun, param_name);
+ return FALSE;
+ }
+
+ g_soft_fun[param_name] = fun;
+ NSFW_LOGINF ("reg]fun=%d,type=%u", fun, param_name);
+ return TRUE;
+}
+
+int
+nsfw_soft_set_int (u32 param, char *buf, u32 buf_len)
+{
+ u64 buf_value = 0;
+ if (NULL == buf || param >= NSFW_MAX_SOFT_PARAM)
+ {
+ NSFW_LOGERR ("argv err]buf=%p,param=%u", buf, param);
+ return FALSE;
+ }
+
+ if (!nsfw_isdigitstr (buf))
+ {
+ NSFW_LOGERR ("argv err]buf=%s,param=%u", buf, param);
+ return FALSE;
+ }
+
+ char *parsing_end;
+ buf_value = (u64) strtol (buf, &parsing_end, 10);
+ nsfw_set_soft_item *int_item = &g_soft_int_cfg[param];
+ if (NULL == int_item->data)
+ {
+ NSFW_LOGERR ("data err]buf=%s,param=%u,min=%llu,max=%llu", buf, param, int_item->min, int_item->max); //[DTS2017112402499][2017-11-24][z00316269] Issue #40, fix type dismatch
+ return FALSE;
+ }
+
+ if (buf_value < int_item->min || buf_value > int_item->max)
+ {
+ NSFW_LOGERR ("argv err]buf=%s,param=%u,min=%llu,max=%llu", buf, param, int_item->min, int_item->max); //[DTS2017112402499][2017-11-24][z00316269] Issue #40, fix type dismatch
+ return FALSE;
+ }
+
+ u32 size = int_item->size;
+ if (size >= sizeof (u64))
+ {
+ size = sizeof (u64);
+ }
+
+ if (EOK != MEMCPY_S (int_item->data, size, &buf_value, size))
+ {
+ NSFW_LOGERR ("MEMCPY_S failed");
+ return FALSE;
+ }
+
+ NSFW_LOGINF ("set soft param ok]param=%u,value=%llu,size=%u", param,
+ buf_value, size);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_soft_param_reg_int
+* Description : reg int param set
+* Input : u32 param_name
+* u32 size
+* u32 min
+* u32 max
+* u64 *data
+* Output : None
+* Return Value : u8
+* Calls :
+* Called By :
+*****************************************************************************/
+u8
+nsfw_soft_param_reg_int (u32 param_name, u32 size, u32 min, u32 max,
+ u64 * data)
+{
+ if (NULL == data || param_name >= NSFW_MAX_SOFT_PARAM)
+ {
+ NSFW_LOGERR ("argv err]data=%p,type=%u", data, param_name);
+ return FALSE;
+ }
+
+ g_soft_int_cfg[param_name].data = data;
+ g_soft_int_cfg[param_name].size = size;
+ g_soft_int_cfg[param_name].max = max;
+ g_soft_int_cfg[param_name].min = min;
+ return nsfw_soft_param_reg_fun (param_name, nsfw_soft_set_int);
+}
+
+void
+nsfw_set_soft_para (fw_poc_type proc_type, u32 para_name, void *value,
+ u32 size)
+{
+ nsfw_mgr_msg *msg =
+ (nsfw_mgr_msg *) nsfw_mgr_msg_alloc (MGR_MSG_SOF_PAR_REQ, proc_type);
+ if (NULL == msg)
+ {
+ NSFW_LOGERR
+ ("nsfw_mgr_msg_alloc failed] msg type=%d, proc type=%d, para_name=%u",
+ MGR_MSG_SOF_PAR_REQ, proc_type, para_name);
+ return;
+ }
+
+ nsfw_soft_param_msg *soft_msg = GET_USER_MSG (nsfw_soft_param_msg, msg);
+
+ soft_msg->param_name = para_name;
+ soft_msg->rsp_code = 0;
+
+ if (EOK !=
+ MEMCPY_S (soft_msg->param_value, sizeof (soft_msg->param_value),
+ value, size))
+ {
+ NSFW_LOGERR
+ ("MEMCPY_S failed] msg type=%d, proc type=%d, para_name=%u",
+ MGR_MSG_SOF_PAR_REQ, proc_type, para_name);
+ nsfw_mgr_msg_free (msg);
+ return;
+ }
+
+ nsfw_mgr_msg *rsp = nsfw_mgr_null_rspmsg_alloc ();
+ if (NULL == rsp)
+ {
+ NSFW_LOGERR
+ ("nsfw_mgr_null_rspmsg_alloc failed] msg type=%d, proc type=%d, para_name=%u",
+ MGR_MSG_SOF_PAR_REQ, proc_type, para_name);
+ nsfw_mgr_msg_free (msg);
+ return;
+ }
+
+ if (!nsfw_mgr_send_req_wait_rsp (msg, rsp))
+ {
+ NSFW_LOGERR
+ ("can not get response] msg type=%d, proc type=%d, para_name=%u",
+ MGR_MSG_SOF_PAR_REQ, proc_type, para_name);
+ nsfw_mgr_msg_free (msg);
+ nsfw_mgr_msg_free (rsp);
+ return;
+ }
+
+ nsfw_soft_param_msg *soft_rsp_msg = GET_USER_MSG (nsfw_soft_param_msg, rsp);
+ if (soft_rsp_msg->rsp_code != NSFW_EXIT_SUCCESS)
+ {
+ NSFW_LOGERR
+ ("set soft param failed] msg type=%d, proc type=%d, para_name=%u, rsp code=%u",
+ MGR_MSG_SOF_PAR_REQ, proc_type, para_name, soft_rsp_msg->rsp_code);
+ nsfw_mgr_msg_free (msg);
+ nsfw_mgr_msg_free (rsp);
+ return;
+ }
+
+ NSFW_LOGINF
+ ("set soft param success] msg type=%d, proc type=%d, para_name=%u",
+ MGR_MSG_SOF_PAR_REQ, proc_type, para_name);
+
+ nsfw_mgr_msg_free (msg);
+ nsfw_mgr_msg_free (rsp);
+ return;
+}
+
+int
+nsfw_softparam_msg_proc (nsfw_mgr_msg * msg)
+{
+ nsfw_mgr_msg *rsp_msg = nsfw_mgr_rsp_msg_alloc (msg);
+ if (NULL == rsp_msg)
+ {
+ NSFW_LOGERR ("alloc rsp failed,drop msg!" MSGINFO, PRTMSG (msg));
+ return FALSE;
+ }
+
+ nsfw_soft_param_msg *soft_msg = GET_USER_MSG (nsfw_soft_param_msg, msg);
+ nsfw_soft_param_msg *soft_rsp_msg =
+ GET_USER_MSG (nsfw_soft_param_msg, rsp_msg);
+ if ((soft_msg->param_name < NSFW_MAX_SOFT_PARAM)
+ && (NULL != g_soft_fun[soft_msg->param_name]))
+ {
+ soft_msg->param_value[sizeof (soft_msg->param_value) - 1] = 0;
+ (void) g_soft_fun[soft_msg->param_name] (soft_msg->param_name,
+ (char *)
+ soft_msg->param_value,
+ sizeof
+ (soft_msg->param_value));
+ soft_rsp_msg->rsp_code = NSFW_EXIT_SUCCESS;
+ }
+ else
+ {
+ NSFW_LOGERR ("set soft failed!]soft=%u", soft_msg->param_name);
+ soft_rsp_msg->rsp_code = NSFW_EXIT_FAILED;
+ }
+
+ (void) nsfw_mgr_send_msg (rsp_msg);
+ nsfw_mgr_msg_free (rsp_msg);
+ return TRUE;
+}
+
+int nsfw_softparam_module_init (void *param);
+int
+nsfw_softparam_module_init (void *param)
+{
+ u8 proc_type = (u8) ((long long) param);
+ NSFW_LOGINF ("softparam module init]type=%u", proc_type);
+ switch (proc_type)
+ {
+ case NSFW_PROC_MAIN:
+ case NSFW_PROC_MASTER:
+ (void) nsfw_mgr_reg_msg_fun (MGR_MSG_SOF_PAR_REQ,
+ nsfw_softparam_msg_proc);
+ return 0;
+ default:
+ if (proc_type < NSFW_PROC_MAX)
+ {
+ break;
+ }
+ return -1;
+ }
+
+ return 0;
+}
+
+/* *INDENT-OFF* */
+NSFW_MODULE_NAME (NSFW_SOFT_PARAM_MODULE)
+NSFW_MODULE_PRIORITY (99)
+NSFW_MODULE_INIT (nsfw_softparam_module_init)
+/* *INDENT-ON* */
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/lib_common_mem/common_api.c b/src/framework/lib_common_mem/common_api.c
new file mode 100644
index 0000000..b535ee6
--- /dev/null
+++ b/src/framework/lib_common_mem/common_api.c
@@ -0,0 +1,325 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <string.h>
+#include "common_mem_api.h"
+#include "common_mem_pal.h"
+#include "nstack_log.h"
+#include "nstack_securec.h"
+#include "common_func.h"
+
+void
+sys_sem_init_v2 (sys_sem_t_v2 sem)
+{
+ sem->locked = 1;
+}
+
+/** Returns the current time in milliseconds,
+ * may be the same as sys_jiffies or at least based on it. */
+long
+sys_now (void)
+{
+ struct timespec now;
+
+ if (unlikely (0 != clock_gettime (CLOCK_MONOTONIC, &now)))
+ {
+ NSCOMM_LOGERR ("Failed to get time, errno = %d", errno);
+ }
+
+ return 1000 * now.tv_sec + now.tv_nsec / 1000000;
+}
+
+long
+sys_jiffies (void)
+{
+ return sys_now ();
+}
+
+err_t
+sys_sem_new_v2 (sys_sem_t_v2 * sem, u8_t isUnLockd)
+{
+ int retVal;
+ if (!sem)
+ {
+ return -1;
+ }
+ *sem = malloc (sizeof (common_mem_spinlock_t));
+
+ if (NULL == *sem)
+ {
+ return -1;
+ }
+ else
+ {
+ retVal =
+ MEMSET_S (*sem, sizeof (common_mem_spinlock_t), 0,
+ sizeof (common_mem_spinlock_t));
+ if (EOK != retVal)
+ {
+ NSCOMM_LOGERR ("MEMSET_S failed]ret=%d", retVal);
+ free (*sem);
+ *sem = NULL;
+ return -1;
+ }
+ common_mem_spinlock_init (*sem);
+ }
+
+ if (!isUnLockd)
+ {
+ common_mem_spinlock_lock (*sem);
+ }
+
+ return 0;
+}
+
+void
+sys_sem_free_v2 (sys_sem_t_v2 * sem)
+{
+ if ((sem != NULL) && (*sem != NULL))
+ {
+ free (*sem);
+ *sem = NULL;
+ }
+ else
+ {
+ }
+}
+
+void
+sys_sem_signal_v2 (sys_sem_t_v2 * sem)
+{
+ common_mem_spinlock_unlock (*sem);
+}
+
+void
+sys_sem_signal_s_v2 (sys_sem_t_v2 sem)
+{
+ common_mem_spinlock_unlock (sem);
+}
+
+u32_t
+sys_arch_sem_trywait_v2 (sys_sem_t_v2 * sem)
+{
+ return (u32_t) common_mem_spinlock_trylock (*sem);
+}
+
+u32_t
+sys_arch_sem_wait_v2 (sys_sem_t_v2 * pstsem)
+{
+ common_mem_spinlock_lock (*pstsem);
+ return 0;
+}
+
+u32_t
+sys_arch_sem_wait_s_v2 (sys_sem_t_v2 sem)
+{
+ common_mem_spinlock_lock (sem);
+ return 0;
+}
+
+volatile pid_t g_sys_host_pid = SYS_HOST_INITIAL_PID;
+
+/*****************************************************************************
+* Prototype : get_exec_name_by_pid
+* Description : get exec name by pid
+* Input : pid_t pid
+* char *task_name
+* Output : None
+* Return Value : void
+* Calls :
+* Called By :
+*****************************************************************************/
+void
+get_exec_name_by_pid (pid_t pid, char *task_name, int task_name_len)
+{
+ int retVal;
+ char path[READ_FILE_BUFLEN] = { 0 };
+ char buf[READ_FILE_BUFLEN] = { 0 };
+
+ retVal = SPRINTF_S (path, sizeof (path), "/proc/%d/status", pid);
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]ret=%d", retVal);
+ return;
+ }
+
+ FILE *fp = fopen (path, "r");
+ if (NULL != fp)
+ {
+ if (fgets (buf, READ_FILE_BUFLEN - 1, fp) == NULL)
+ {
+ fclose (fp);
+ return;
+ }
+ fclose (fp);
+
+#ifdef SECUREC_LIB
+ retVal = SSCANF_S (buf, "%*s %s", task_name, task_name_len);
+#else
+ retVal = SSCANF_S (buf, "%*s %s", task_name);
+#endif
+
+ if (1 != retVal)
+ {
+ NSSOC_LOGERR ("SSCANF_S failed]ret=%d", retVal);
+ return;
+ }
+ }
+}
+
+pid_t
+get_hostpid_from_file_one_time (u32_t pid)
+{
+ int retVal;
+ char path[READ_FILE_BUFLEN] = { 0 };
+ char buf[READ_FILE_BUFLEN] = { 0 };
+ char fmt[READ_FILE_BUFLEN] = { 0 };
+ char out[READ_FILE_BUFLEN] = { 0 };
+ char task_name[BUF_SIZE_FILEPATH] = { 0 };
+ pid_t hostpid = SYS_HOST_INITIAL_PID;
+ get_exec_name_by_pid (pid, task_name, BUF_SIZE_FILEPATH);
+
+ retVal = SPRINTF_S (fmt, sizeof (fmt), "%s%s", task_name, " (%s");
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]ret=%d", retVal);
+ return hostpid;
+ }
+ retVal = SPRINTF_S (path, sizeof (path), "/proc/%d/sched", pid);
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]ret=%d", retVal);
+ return hostpid;
+ }
+ FILE *fp = fopen (path, "r");
+ if (NULL != fp)
+ {
+ if (fgets (buf, READ_FILE_BUFLEN - 1, fp) == NULL)
+ {
+ fclose (fp);
+ return hostpid;
+ }
+ fclose (fp);
+ /* Compiler needs "fmt" to be like "%s%s" to
+ understand. But we have "fmt" already prepared and used here. It can
+ be suppressed, not an issue
+ */
+#pragma GCC diagnostic ignored "-Wformat-nonliteral"
+ retVal = SSCANF_S (buf, fmt, out, READ_FILE_BUFLEN);
+ if (-1 == retVal)
+ {
+ NSPOL_LOGERR ("SSCANF_S failed]ret=%d", retVal);
+ return hostpid;
+ }
+ }
+
+ hostpid = (pid_t) strtol (out, NULL, 0);
+ if (hostpid == 0)
+ {
+ hostpid = 1;
+ }
+
+ return hostpid;
+}
+
+#define MAX_GET_PID_TIME 10
+pid_t
+get_hostpid_from_file (u32_t pid)
+{
+ pid_t ret_pid = SYS_HOST_INITIAL_PID;
+ int i = 0;
+ ret_pid = get_hostpid_from_file_one_time (pid);
+ while (0 == ret_pid || ret_pid == SYS_HOST_INITIAL_PID)
+ {
+ i++;
+ if (i > MAX_GET_PID_TIME)
+ {
+ NSFW_LOGERR ("get pid failed]pid=%u,hostpid=%d", pid, ret_pid);
+ break;
+ }
+ sys_sleep_ns (0, 5000000);
+ ret_pid = get_hostpid_from_file_one_time (pid);
+ }
+
+ return ret_pid;
+}
+
+/*****************************************************************************
+* Prototype : get_hostpid_from_file
+* Description : get host pid by sub namespace pid in docker
+* Input : uint32_t pid
+* Output : None
+* Return Value : uint32_t
+* Calls :
+* Called By :
+*****************************************************************************/
+pid_t
+sys_get_hostpid_from_file (pid_t pid)
+{
+ g_sys_host_pid = get_hostpid_from_file (pid);
+ NSCOMM_LOGDBG ("ok]cur pid=%d, input pid=%d", g_sys_host_pid, pid);
+ return g_sys_host_pid;
+}
+
+pid_t
+updata_sys_pid ()
+{
+ g_sys_host_pid = SYS_HOST_INITIAL_PID;
+ return get_sys_pid ();
+}
+
+/*****************************************************************************
+* Prototype : get_pid_namespace
+* Description : Get namespace of pid
+* Input : uint32_t pid
+* Output : None
+* Return Value : uint64_t
+* Calls :
+* Called By :
+*****************************************************************************/
+uint64_t
+get_pid_namespace (pid_t pid)
+{
+ char buf[BUF_SIZE_FILEPATH] = { 0 };
+ char path[BUF_SIZE_FILEPATH] = { 0 };
+ const char *pstart;
+ int ret = 0;
+ if (!pid)
+ {
+ NSSOC_LOGERR ("Pid is zero!");
+ return 0;
+ }
+
+ ret =
+ SNPRINTF_S (path, sizeof (path), sizeof (path) - 1, "/proc/%d/ns/pid",
+ pid);
+ if (-1 == ret)
+ {
+ NSSOC_LOGERR ("SNPRINTF_S failed]ret=%d", ret);
+ return 0;
+ }
+
+ ret = readlink (path, buf, sizeof (buf) - 1);
+ if (ret <= (int) sizeof (STR_PID))
+ {
+ NSSOC_LOGERR ("readlink pid ns file error]ret=%d", ret);
+ return 0;
+ }
+
+ buf[ret - 1] = 0;
+ pstart = &(buf[sizeof (STR_PID)]);
+ return strtoull (pstart, NULL, 10);
+}
diff --git a/src/framework/lib_common_mem/common_buf.c b/src/framework/lib_common_mem/common_buf.c
new file mode 100644
index 0000000..523ce54
--- /dev/null
+++ b/src/framework/lib_common_mem/common_buf.c
@@ -0,0 +1,260 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <string.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <stdint.h>
+#include <stdarg.h>
+#include <inttypes.h>
+#include <errno.h>
+#include <ctype.h>
+#include <sys/queue.h>
+
+#include "common_mem_base_type.h"
+
+#include "common_mem_common.h"
+
+#include "common_mem_memzone.h"
+
+#include "common_mem_pal.h"
+
+#include "common_mem_mempool.h"
+#include "common_mem_buf.h"
+
+#include "nstack_log.h"
+#include "nstack_securec.h"
+
+#include "common_func.h"
+#include "common_pal_bitwide_adjust.h"
+
+#define LOG_ERR 0
+#define LOG_WARN 1
+#define LOG_INFO 2
+#define LOG_DEBUG 3
+#define LOG_MAX 4
+
+#define COMMON_LOG_PRINT(leve, fmt, args...) \
+ if (leve <= log_levl) NSCOMM_LOGERR("===>[COMMON]"fmt, ##args); \
+
+#define COMMON_PANIC(fmt) \
+ NSCOMM_LOGERR("==>[COMMON_PANIC]"fmt); \
+ common_dump_stack(); \
+
+#define PARA1_SET(argv, tempargv, Index, para1) do {\
+ retVal = STRCPY_S(tempargv[Index], PATA_STRLENT, para1);\
+ if (retVal != EOK)\
+ {\
+ NSCOMM_LOGERR("STRCPY_S failed]ret=%d", retVal);\
+ return DMM_MBUF_RET_ERR;\
+ }\
+ argv[Index] = tempargv[Index]; \
+ Index ++; } while (0)
+
+#define PARA2_SET(argv, tempargv, Index, para1, para2) do {\
+ retVal = STRCPY_S(tempargv[Index], PATA_STRLENT, para1); \
+ if (retVal != EOK)\
+ {\
+ NSCOMM_LOGERR("STRCPY_S failed]ret=%d", retVal);\
+ return DMM_MBUF_RET_ERR;\
+ }\
+ argv[Index] = tempargv[Index]; \
+ Index++; \
+ retVal = STRCPY_S(tempargv[Index], PATA_STRLENT, para2); \
+ if (retVal != EOK)\
+ {\
+ NSCOMM_LOGERR("STRCPY_S failed]ret=%d", retVal);\
+ return DMM_MBUF_RET_ERR;\
+ }\
+ argv[Index] = tempargv[Index]; \
+ Index ++; } while (0)
+
+#define PATA_STRLENT 64
+#define PATA_NUM_MAX 12
+
+int log_levl = LOG_INFO;
+
+int
+nscomm_pal_module_init (common_mem_pal_module_info * pinfo)
+{
+ char tempargv[PATA_NUM_MAX][PATA_STRLENT];
+ char *argv[PATA_NUM_MAX];
+ char tempbuf[PATA_STRLENT];
+ unsigned int Index = 0;
+ int ioffset = 0;
+ int agindex = 0;
+ int intmask = 0;
+ int retVal;
+ retVal = MEMSET_S (tempargv, sizeof (tempargv), '\0', sizeof (tempargv));
+ if (EOK != retVal)
+ {
+ NSCOMM_LOGERR ("MEMSET_S failed]ret=%d", retVal);
+ return DMM_MBUF_RET_ERR;
+ }
+ retVal = MEMSET_S (argv, sizeof (argv), 0, sizeof (argv));
+ if (EOK != retVal)
+ {
+ NSCOMM_LOGERR ("MEMSET_S failed]ret=%d", retVal);
+ return DMM_MBUF_RET_ERR;
+ }
+ if (NULL == pinfo)
+ {
+ PARA1_SET (argv, tempargv, agindex, "nStackMain");
+ PARA2_SET (argv, tempargv, agindex, "-c", "0x1");
+ PARA2_SET (argv, tempargv, agindex, "-n", "4");
+ PARA2_SET (argv, tempargv, agindex, "-m", "2048");
+ PARA1_SET (argv, tempargv, agindex, "--huge-dir=/mnt/nstackhuge");
+ PARA1_SET (argv, tempargv, agindex, "--proc-type=primary");
+ }
+ else
+ {
+ PARA1_SET (argv, tempargv, agindex, "nStackMain");
+
+ /*[DTS2017032711606 ][2017-04-08][z00353090] There are some unsafe function ,need to be replace with safe function */
+ retVal = SPRINTF_S (tempbuf, PATA_STRLENT, "0x");
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]ret=%d", ioffset);
+ return DMM_MBUF_RET_ERR;
+ }
+ ioffset = retVal;
+ for (Index = 0; Index < LCORE_MASK_MAX; Index++)
+ {
+ if (ioffset >= PATA_STRLENT)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S tempbuf overflow]ioffset=%d",
+ ioffset);
+ return DMM_MBUF_RET_ERR;
+ }
+ retVal =
+ SPRINTF_S (&(tempbuf[ioffset]), PATA_STRLENT - ioffset, "%8u",
+ pinfo->ilcoremask[Index]);
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]ret=%d", ioffset);
+ return DMM_MBUF_RET_ERR;
+ }
+ ioffset = ioffset + retVal;
+ intmask |= pinfo->ilcoremask[Index];
+ }
+ if (0 == intmask)
+ {
+ PARA2_SET (argv, tempargv, agindex, "-c", "0x1");
+ }
+ else
+ {
+ PARA2_SET (argv, tempargv, agindex, "-c", tempbuf);
+ }
+ if (pinfo->ishare_mem_size > 0)
+ {
+ retVal = MEMSET_S (tempbuf, PATA_STRLENT, 0, PATA_NUM_MAX);
+ if (EOK != retVal)
+ {
+ NSCOMM_LOGERR ("MEMSET_S failed]ret=%d", retVal);
+ return DMM_MBUF_RET_ERR;
+ }
+ retVal =
+ SPRINTF_S (tempbuf, PATA_STRLENT, "%d", pinfo->ishare_mem_size);
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]ret=%d", retVal);
+ return DMM_MBUF_RET_ERR;
+ }
+ PARA2_SET (argv, tempargv, agindex, "-m", tempbuf);
+ }
+
+ retVal = MEMSET_S (tempbuf, PATA_STRLENT, 0, PATA_NUM_MAX);
+ if (EOK != retVal)
+ {
+ NSCOMM_LOGERR ("MEMSET_S failed]ret=%d", retVal);
+ return DMM_MBUF_RET_ERR;
+ }
+
+ switch (pinfo->ucproctype)
+ {
+ case DMM_PROC_T_PRIMARY:
+ retVal = SPRINTF_S (tempbuf, PATA_STRLENT, "--proc-type=primary");
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]ret=%d", retVal);
+ return DMM_MBUF_RET_ERR;
+ }
+ break;
+ case DMM_PROC_T_SECONDARY:
+ retVal = SPRINTF_S (tempbuf, PATA_STRLENT, "--proc-type=secondary");
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]ret=%d", retVal);
+ return DMM_MBUF_RET_ERR;
+ }
+ break;
+ case DMM_PROC_T_AUTO:
+ default:
+ retVal = SPRINTF_S (tempbuf, PATA_STRLENT, "--proc-type=auto");
+ if (-1 == retVal)
+ {
+ NSCOMM_LOGERR ("SPRINTF_S failed]ret=%d", retVal);
+ return DMM_MBUF_RET_ERR;
+ }
+ break;
+ }
+ PARA1_SET (argv, tempargv, agindex, tempbuf);
+
+ if (DMM_HUGTBL_DISABLE == pinfo->uchugeflag)
+ {
+ PARA1_SET (argv, tempargv, agindex, "--no-huge");
+ }
+ }
+ if (common_mem_pal_init (agindex, argv) < 0)
+ {
+ COMMON_LOG_PRINT (LOG_ERR, "Cannot init pal\r\n");
+ return DMM_MBUF_RET_ERR;
+ }
+ return DMM_MBUF_RET_OK;
+}
+
+void *
+nscomm_memzone_data_reserve_name (const char *name, size_t len, int socket_id)
+{
+ const struct common_mem_memzone *mz = NULL;
+ /*
+ rte_memzone_reserve must Call first, cause rte_memzone_reserve has a globe lock.
+ while proc race happen, who(calls A) got lock first will create memzone success.
+ others create same memzone proc will got lock after A, and rte_memzone_reserve return NULL;
+ so while rte_memzone_reserve return NULL we need do rte_memzone_lookup;
+ */
+ mz = common_mem_memzone_reserve (name, len, socket_id, 0);
+ if (mz == NULL)
+ {
+ mz = common_mem_memzone_lookup (name);
+ }
+
+ return mz ? (void *) ADDR_SHTOL (mz->addr_64) : NULL;
+}
+
+void *
+nscomm_memzone_data_lookup_name (const char *name)
+{
+ void *addr = NULL;
+ const struct common_mem_memzone *mz = NULL;
+ mz = common_mem_memzone_lookup (name);
+ if (mz == NULL)
+ {
+ return NULL;
+ }
+ addr = (void *) ADDR_SHTOL (mz->addr_64);
+ return addr;
+}
diff --git a/src/framework/lib_common_mem/common_func.c b/src/framework/lib_common_mem/common_func.c
new file mode 100644
index 0000000..f68380f
--- /dev/null
+++ b/src/framework/lib_common_mem/common_func.c
@@ -0,0 +1,205 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "common_mem_pal_memconfig.h"
+#include "common_mem_mbuf.h"
+#include "common_mem_common.h"
+#include "nstack_log.h"
+#include "common_pal_bitwide_adjust.h"
+
+#include "common_func.h"
+
+#include "nstack_securec.h"
+
+#define COMMON_PROCESS_MAPS "/proc/self/maps"
+
+int g_PrimSameFlg = 1;
+
+NSTACK_STATIC void **g_PrimAddr2LocalMap = NULL;
+NSTACK_STATIC void *g_LocalBaseAddr = NULL;
+NSTACK_STATIC void *g_LocalMaxAddr = NULL;
+NSTACK_STATIC void *g_LocalCfgAddrBase = NULL;
+
+NSTACK_STATIC uint64_t *g_LocalAddr2PrimMap = NULL;
+NSTACK_STATIC uint64_t g_PrimBaseAddr = 0;
+NSTACK_STATIC uint64_t g_PrimMaxAddr = 0;
+NSTACK_STATIC uint64_t g_PrimCfgAddrBase = 0;
+
+NSTACK_STATIC uint64_t g_LBitMask = 0;
+NSTACK_STATIC int g_LBitMaskLen = 0;
+
+uint64_t
+pal_laddr_to_shddr (void *LAddr)
+{
+ size_t l2pIdx;
+
+ if (g_PrimSameFlg || LAddr == NULL)
+ {
+ return (uint64_t) LAddr;
+ }
+
+ /*calculate the IDX */
+ l2pIdx = (ALIGN_PTR (LAddr) - ALIGN_PTR (g_LocalBaseAddr)) >> g_LBitMaskLen;
+
+ /*check the Hugepage Addr Rang */
+ if (LAddr <= g_LocalMaxAddr && LAddr >= g_LocalBaseAddr
+ && g_LocalAddr2PrimMap[l2pIdx])
+ {
+ return g_LocalAddr2PrimMap[l2pIdx] + (ALIGN_PTR (LAddr) & g_LBitMask);
+ }
+
+ /*check the Cfg Mapping Addr Rang */
+ if (LAddr >= g_LocalCfgAddrBase
+ && LAddr <=
+ (void *) ((char *) g_LocalCfgAddrBase +
+ sizeof (struct common_mem_mem_config)))
+ {
+ return g_PrimCfgAddrBase + ((char *) LAddr -
+ (char *) g_LocalCfgAddrBase);
+ }
+
+ NSCOMM_LOGWAR
+ ("WARNING!!! Input invalid LAddr]LAddr=%p, g_LocalBaseAddr=%p, g_LocalMaxAddr=%p, g_LocalCfgAddrBase=%p, g_LocalCfgAddrMax=%p.",
+ LAddr, g_LocalBaseAddr, g_LocalMaxAddr, g_LocalCfgAddrBase,
+ (char *) g_LocalCfgAddrBase + sizeof (struct common_mem_mem_config));
+
+ return (uint64_t) LAddr;
+}
+
+void *
+pal_shddr_to_laddr (uint64_t PAddr)
+{
+ size_t p2lIdx;
+
+ if (g_PrimSameFlg || PAddr == ALIGN_PTR (NULL))
+ {
+ return (void *) PAddr;
+ }
+
+ p2lIdx = (PAddr - g_PrimBaseAddr) >> g_LBitMaskLen;
+ /*check the Hugepage Addr Rang */
+ if (PAddr <= g_PrimMaxAddr && PAddr >= g_PrimBaseAddr
+ && g_PrimAddr2LocalMap[p2lIdx])
+ {
+ return (void *) ((uint64_t) g_PrimAddr2LocalMap[p2lIdx] +
+ (PAddr & g_LBitMask));
+ }
+
+ /*check the Cfg Mapping Addr Rang */
+ if (PAddr >= g_PrimCfgAddrBase
+ && PAddr <= g_PrimCfgAddrBase + sizeof (struct common_mem_mem_config))
+ {
+ return (void *) ((uint64_t) g_LocalCfgAddrBase + PAddr -
+ g_PrimCfgAddrBase);
+ }
+
+ NSCOMM_LOGWAR
+ ("WARNING!!! Input invalid PAddr]PAddr=%lx, g_PrimBaseAddr=%lx, g_PrimMaxAddr=%lx, g_PrimCfgAddrBase=%lx, g_PrimCfgAddrMax=%lx.",
+ PAddr, g_PrimBaseAddr, g_PrimMaxAddr, g_PrimCfgAddrBase,
+ g_PrimCfgAddrBase + sizeof (struct common_mem_mem_config));
+
+ return (void *) PAddr;
+}
+
+/*lint +e539 */
+
+int
+dmm_pal_addr_align ()
+{
+ return g_PrimSameFlg;
+}
+
+int32_t
+dmm_pktmbuf_pool_iterator (struct common_mem_mempool * mp, uint32_t start,
+ uint32_t end, dmm_mbuf_item_fun fun, void *argv)
+{
+ if (NULL == mp || fun == NULL)
+ {
+ return 0;
+ }
+
+ if (start >= mp->size || end <= start)
+ {
+ return 0;
+ }
+
+ int32_t elm_size = mp->elt_size + mp->header_size + mp->trailer_size;
+ struct common_mem_mbuf *elm_mbuf = (struct common_mem_mbuf *) (mp->elt_va_start + start * elm_size + mp->header_size); /*lint !e647 */
+
+ uint32_t i;
+ uint32_t mbuf_end = COMMON_MEM_MIN (end, mp->size) - start;
+ for (i = 0; i < mbuf_end; i++)
+ {
+ (void) fun (elm_mbuf, argv);
+ elm_mbuf = (struct common_mem_mbuf *) ((char *) elm_mbuf + elm_size);
+ }
+
+ return mbuf_end;
+}
+
+void
+dmm_addr_print (void)
+{
+ const struct common_mem_mem_config *mcfg =
+ common_mem_pal_get_configuration ()->mem_config;
+ int s;
+ FILE *fd;
+ char *ptembuf = NULL;
+ if (!mcfg)
+ {
+ NSCOMM_LOGERR ("mcfg is null");
+ return;
+ }
+ /*printf base address */
+ NSCOMM_LOGINF ("********master baseaddr begin***************");
+ for (s = 0; s < COMMON_MEM_MAX_MEMSEG; ++s)
+ {
+ if ((mcfg->memseg[s].len > 0) && (mcfg->memseg[s].addr != 0))
+ {
+ NSCOMM_LOGINF ("addr:%p, len:%u", mcfg->memseg[s].addr,
+ mcfg->memseg[s].len);
+ }
+ }
+ NSCOMM_LOGINF ("********master baseaddr end***************");
+
+ fd = fopen (COMMON_PROCESS_MAPS, "r");
+ if (!fd)
+ {
+ NSCOMM_LOGERR ("/proc/self/maps open fail, erro:%d", errno);
+ return;
+ }
+
+ ptembuf = (char *) malloc (BUFSIZ);
+ if (!ptembuf)
+ {
+ NSCOMM_LOGERR ("malloc buff failed]buff_len=%d", BUFSIZ);
+ fclose (fd);
+ return;
+ }
+ if (EOK != MEMSET_S (ptembuf, BUFSIZ, 0, BUFSIZ))
+ {
+ NSCOMM_LOGERR ("MEMSET_S failed] buff=%p", ptembuf);
+ }
+ NSCOMM_LOGINF ("********self process addr space begin***************");
+ while (fgets (ptembuf, BUFSIZ, fd) != NULL)
+ {
+ NSCOMM_LOGERR ("%s", ptembuf);
+ }
+ NSCOMM_LOGINF ("********self process addr space end*****************");
+ fclose (fd);
+ free (ptembuf);
+ return;
+}
diff --git a/src/framework/log/nsfw_set_log.c b/src/framework/log/nsfw_set_log.c
new file mode 100644
index 0000000..a4b3b92
--- /dev/null
+++ b/src/framework/log/nsfw_set_log.c
@@ -0,0 +1,228 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdlib.h>
+#include "types.h"
+#include "nstack_securec.h"
+#include "nsfw_init.h"
+
+#include "nstack_log.h"
+#include "nsfw_maintain_api.h"
+#include "nsfw_mem_api.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+typedef struct _nsfw_log_cfg
+{
+ u8 proc_type;
+ char master_log_path[NSFW_LOG_VALUE_LEN];
+ char runing_log_path[NSFW_LOG_VALUE_LEN];
+ char opr_log_path[NSFW_LOG_VALUE_LEN];
+} nsfw_log_cfg;
+
+nsfw_log_cfg g_log_cfg;
+
+const char nsfw_mas_log[NSFW_LOG_VALUE_LEN] = "maspath";
+const char nsfw_flush_name[NSFW_LOG_VALUE_LEN] = "flush";
+
+enum _set_log_type
+{
+ SET_LOG_LEVEL = 0,
+ SET_LOG_FLUSH,
+ SET_LOG_MASTER,
+ SET_LOG_MAIN,
+
+ SET_LOG_INVALID
+};
+
+/*****************************************************************************
+* Prototype : nsfw_set_log_path
+* Description : set log path
+* Input : const char *param
+* const char *value
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_set_log_path (const char *param, const char *value)
+{
+ if (NULL == param || NULL == value)
+ {
+ NSFW_LOGERR ("log param error!]param=%p,value=%p", param, value);
+ return FALSE;
+ }
+
+ if (cmp_log_path (value))
+ {
+ if (check_log_dir_valid (value) < 0)
+ {
+ NSFW_LOGERR ("path is invalid]value=%s", value);
+ return FALSE;
+ }
+ if (EOK !=
+ STRCPY_S (g_log_cfg.master_log_path, NSFW_LOG_VALUE_LEN, value))
+ {
+ NSFW_LOGERR ("strcpy error!");
+ return FALSE;
+ }
+
+ NSFW_LOGINF ("renew log path]%s", g_log_cfg.master_log_path);
+ nstack_modify_log_dir (g_log_cfg.master_log_path);
+ NSFW_LOGINF ("set log sucess]newpath=%s!", g_log_cfg.master_log_path);
+ return TRUE;
+ }
+ return FALSE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_flush_log_info
+* Description : flush the log info
+* Input : const char *param
+* u8 proc_type
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_flush_log_info (const char *param, u8 proc_type)
+{
+ if (NULL == param)
+ {
+ NSFW_LOGERR ("log param error!]param=%p", param);
+ return FALSE;
+ }
+ glogFlushLogFiles (GLOG_LEVEL_DEBUG);
+ NSFW_LOGINF ("flush log sucess]proc_type=%u", proc_type);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_set_log_msg_proc
+* Description : set log message process
+* Input : nsfw_mgr_msg* msg
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+nsfw_set_log_msg_proc (nsfw_mgr_msg * msg)
+{
+ int ret = -1;
+ int status = -1;
+ if (NULL == msg)
+ {
+ NSFW_LOGERR ("msg nul");
+ return FALSE;
+ }
+
+ nsfw_set_log_msg *set_log_msg = GET_USER_MSG (nsfw_set_log_msg, msg);
+
+ if (0 == strcmp (set_log_msg->module, nsfw_mas_log))
+ {
+ status = SET_LOG_MASTER;
+ }
+ else if (0 == strcmp (set_log_msg->module, nsfw_flush_name))
+ {
+ status = SET_LOG_FLUSH;
+ }
+ else if (nsfw_isdigitstr (set_log_msg->module))
+ {
+ status = SET_LOG_LEVEL;
+ }
+
+ switch (status)
+ {
+ case SET_LOG_LEVEL:
+ ret = setlog_level_value (set_log_msg->module, set_log_msg->log_level);
+ break;
+ case SET_LOG_FLUSH:
+ ret = nsfw_flush_log_info (set_log_msg->module, msg->dst_proc_type);
+ break;
+ case SET_LOG_MASTER:
+ ret = nsfw_set_log_path (set_log_msg->module, set_log_msg->log_level);
+ break;
+ default:
+ NSFW_LOGERR ("default error]status=%d,set_log_msg->module=%s", status,
+ set_log_msg->module);
+ return FALSE;
+ }
+
+ nsfw_mgr_msg *rsp_msg = nsfw_mgr_rsp_msg_alloc (msg);
+ if (NULL == rsp_msg)
+ {
+ NSFW_LOGERR ("alloc rsp failed,drop msg!" MSGINFO, PRTMSG (msg));
+ return FALSE;
+ }
+ nsfw_set_log_msg *log_rsp_msg = GET_USER_MSG (nsfw_set_log_msg, rsp_msg);
+ log_rsp_msg->rsp_code = ret;
+ (void) nsfw_mgr_send_msg (rsp_msg);
+ nsfw_mgr_msg_free (rsp_msg);
+ return TRUE;
+}
+
+/*****************************************************************************
+* Prototype : nsfw_cfg_module_init
+* Description : module init
+* Input : void* param
+* Output : None
+* Return Value : static int
+* Calls :
+* Called By :
+*****************************************************************************/
+static int nsfw_cfg_module_init (void *param);
+static int
+nsfw_cfg_module_init (void *param)
+{
+ u8 proc_type = (u8) ((long long) param);
+ NSFW_LOGINF ("log cfg module init]type=%u", proc_type);
+ switch (proc_type)
+ {
+ case NSFW_PROC_MAIN:
+ case NSFW_PROC_MASTER:
+ (void) nsfw_mgr_reg_msg_fun (MGR_MSG_SET_LOG_REQ,
+ nsfw_set_log_msg_proc);
+ g_log_cfg.proc_type = proc_type;
+ return 0;
+ default:
+ if (proc_type < NSFW_PROC_MAX)
+ {
+ break;
+ }
+ return -1;
+ }
+
+ return 0;
+}
+
+/* *INDENT-OFF* */
+NSFW_MODULE_NAME (NSFW_LOG_CFG_MODULE)
+NSFW_MODULE_PRIORITY (99)
+NSFW_MODULE_INIT (nsfw_cfg_module_init)
+/* *INDENT-ON* */
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/log/nstack_log.c b/src/framework/log/nstack_log.c
new file mode 100644
index 0000000..5e8ffd4
--- /dev/null
+++ b/src/framework/log/nstack_log.c
@@ -0,0 +1,825 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+/*==============================================*
+ * include header files *
+ *----------------------------------------------*/
+
+#include "nstack_log.h"
+#include <sys/stat.h>
+#include <dirent.h>
+#include <time.h>
+#include <errno.h>
+#include <execinfo.h>
+#include <fcntl.h>
+#include "nstack_securec.h"
+#include <pthread.h>
+
+/*==============================================*
+ * constants or macros define *
+ *----------------------------------------------*/
+
+#define FILE_NAME_LEN 256
+#define MAX_PRE_INIT_LOG_COUNT 256
+#define MAX_LOCK_RETRY_COUNT 50000 /* changed MAX_LOCK_RETRY_COUNT to 50000 to avoid function being blocked for too long */
+/* *INDENT-OFF* */
+int g_l4_dump_enable = 0;
+static int pre_init_log_count = 0;
+static struct pre_init_info pre_init_log[MAX_PRE_INIT_LOG_COUNT] = {{0, ""}};
+/* *INDENT-ON* */
+__thread unsigned int nstack_log_nonreentry = 0;
+int ctrl_log_switch = 0;
+
+/*==============================================*
+ * project-wide global variables *
+ *----------------------------------------------*/
+struct nstack_logs g_nstack_logs[MAX_LOG_MODULE] = { {0, 0, 0, 0}, {0xFFFF, 0, 0, 0} }; /* Clear compile warning */
+struct log_init_para g_log_init_para =
+ { 50, 10, NSTACK_LOG_NAME, 10, 10, NSTACK_LOG_NAME };
+static int g_my_pro_type = LOG_PRO_INVALID;
+
+#define DEFAULT_LOG_CTR_TIME 5
+static struct log_ctrl_info g_log_ctrl_info[LOG_CTRL_ID_MAX];
+
+/*==============================================*
+ * routines' or functions' implementations *
+ *----------------------------------------------*/
+
+/* change the print level, not only has err, Begin.*/
+void
+save_pre_init_log (uint32_t level, char *fmt, ...)
+{
+ va_list ap;
+ int ret = 0;
+ /* add pre_init_log_count rang check */
+ if (level > NSLOG_DBG || pre_init_log_count >= MAX_PRE_INIT_LOG_COUNT
+ || pre_init_log_count < 0)
+
+ {
+ return;
+ }
+ pre_init_log[pre_init_log_count].log_buffer[PRE_INIT_LOG_LENGTH - 1] = '\0';
+ (void) va_start (ap, fmt);
+ ret =
+ VSNPRINTF_S (pre_init_log[pre_init_log_count].log_buffer,
+ PRE_INIT_LOG_LENGTH, PRE_INIT_LOG_LENGTH - 1, fmt, ap);
+ if (-1 == ret)
+ {
+ va_end (ap);
+ return;
+ }
+ va_end (ap);
+ pre_init_log[pre_init_log_count].level = level;
+ pre_init_log_count++;
+}
+
+void
+write_pre_init_log ()
+{
+ int i = 0;
+ for (; i < pre_init_log_count; i++)
+ {
+ if (NSLOG_ERR == pre_init_log[i].level)
+ {
+ NSPOL_LOGERR ("pre init log: %s", pre_init_log[i].log_buffer);
+ }
+ else if (NSLOG_WAR == pre_init_log[i].level)
+ {
+ NSPOL_LOGWAR (NS_LOG_STACKX_ON, "pre init log: %s",
+ pre_init_log[i].log_buffer);
+ }
+ else if (NSLOG_INF == pre_init_log[i].level)
+ {
+ NSPOL_LOGINF (NS_LOG_STACKX_ON, "pre init log: %s",
+ pre_init_log[i].log_buffer);
+ }
+ }
+}
+
+int
+cmp_log_path (const char *path)
+{
+ if (NULL == path)
+ {
+ return 1;
+ }
+
+ /* remove struct log_info g_nstack_log_info */
+ if (NULL != g_log_init_para.mon_log_path)
+ {
+ if (strcmp (g_log_init_para.mon_log_path, path) == 0)
+ {
+ return 0;
+ }
+ }
+ return 1;
+}
+
+void
+get_current_time (char *buf, const int len)
+{
+ int retVal;
+ time_t cur_tick;
+ struct tm cur_time;
+ (void) time (&cur_tick);
+ /* add return value check, */
+ if (NULL == localtime_r (&cur_tick, &cur_time))
+ {
+ return;
+ }
+
+ // from man page of localtime_r:
+ // tm_year The number of years since 1900.
+ // tm_mon The number of months since January, in the range 0 to 11.
+ retVal =
+ SNPRINTF_S (buf, len, len - 1, "%04d%02d%02d%02d%02d%02d",
+ cur_time.tm_year + 1900, cur_time.tm_mon + 1,
+ cur_time.tm_mday, cur_time.tm_hour, cur_time.tm_min,
+ cur_time.tm_sec);
+ if (-1 == retVal)
+ {
+ return;
+ }
+ buf[len - 1] = 0;
+}
+
+/*****************************************************************************
+* Prototype : nstack_setlog_level
+* Description : Set global log level
+* Input : int module
+* uint32_t level
+* Output : None
+* Return Value : void
+* Calls :
+* Called By :
+*****************************************************************************/
+void
+nstack_setlog_level (int module, uint32_t level)
+{
+ if (MAX_LOG_MODULE <= module || module < 0)
+ {
+ return;
+ }
+ g_nstack_logs[module].level = level;
+}
+
+/*****************************************************************************
+* Prototype : nstack_log_info_check
+* Description : log info check
+* Input : uint32_t module
+* uint32_t level
+* ...
+* Output : None
+* Return Value : bool
+* Calls :
+* Called By :
+*****************************************************************************/
+bool
+nstack_log_info_check (uint32_t module, uint32_t level)
+{
+ if (MAX_LOG_MODULE <= module)
+ {
+ return false;
+ }
+
+ /* no need compare module ,which is done ahead */
+ if (LOG_PRO_INVALID == g_my_pro_type)
+ {
+ return false;
+ }
+ return true;
+}
+
+/* *INDENT-OFF* */
+NSTACK_STATIC inline void init_operation_log_para()
+{
+ g_nstack_logs[OPERATION].file_type = LOG_TYPE_OPERATION;
+}
+
+NSTACK_STATIC inline void init_nstack_log_para()
+{
+ int i = 0;
+
+ (void)glogLevelSet(GLOG_LEVEL_DEBUG);
+ glogBufLevelSet(GLOG_LEVEL_WARNING);
+ for(; i<GLOG_LEVEL_BUTT; i++)
+ glogSetLogSymlink(i,"");
+ glogDir(g_log_init_para.run_log_path);
+ nstack_log_count_set(g_log_init_para.run_log_count);
+ glogMaxLogSizeSet(g_log_init_para.run_log_size);
+ glogSetLogFilenameExtension(STACKX_LOG_NAME);
+ glogFlushLogSecsSet(FLUSH_TIME);
+
+ for (i = 0; i < MAX_LOG_MODULE ; i++ )
+ {
+ if (i == OPERATION)
+ {
+ continue;
+ }
+ g_nstack_logs[i].file_type = LOG_TYPE_NSTACK;
+ }
+ init_operation_log_para();
+}
+
+NSTACK_STATIC inline void init_ctrl_log_para()
+{
+ int i = 0;
+
+ (void)glogLevelSet(GLOG_LEVEL_DEBUG);
+ glogBufLevelSet(GLOG_LEVEL_WARNING);
+ for(; i<GLOG_LEVEL_BUTT; i++)
+ glogSetLogSymlink(i,"");
+ glogDir(g_log_init_para.mon_log_path);
+ nstack_log_count_set(g_log_init_para.mon_log_count);
+ glogMaxLogSizeSet(g_log_init_para.mon_log_size);
+ glogSetLogFilenameExtension(OMC_CTRL_LOG_NAME);
+ glogFlushLogSecsSet(FLUSH_TIME);
+}
+
+NSTACK_STATIC inline void init_master_log_para()
+{
+ int i = 0;
+
+ (void)glogLevelSet(GLOG_LEVEL_DEBUG);
+ glogBufLevelSet(GLOG_LEVEL_WARNING);
+ for(; i<GLOG_LEVEL_BUTT; i++)
+ glogSetLogSymlink(i,"");
+ glogDir(g_log_init_para.mon_log_path);
+ nstack_log_count_set(g_log_init_para.mon_log_count);
+ glogMaxLogSizeSet(g_log_init_para.mon_log_size);
+ glogSetLogFilenameExtension(MASTER_LOG_NAME);
+ glogFlushLogSecsSet(FLUSH_TIME);
+ for (i = 0; i < MAX_LOG_MODULE ; i++ )
+ {
+ g_nstack_logs[i].file_type = LOG_TYPE_MASTER;
+ }
+}
+/* *INDENT-OFF* */
+
+/*****************************************************************************
+* Prototype : nstack_log_init
+* Description : called by environment-specific log init function
+* Input : None
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int nstack_log_init()
+{
+ char *pst_temp = NULL;
+ int log_level = NSLOG_INF;
+ pst_temp = getenv("NSTACK_LOG_ON");
+ if (pst_temp)
+ {
+ if (strcmp (pst_temp, "INF") == 0)
+ {
+ log_level = NSLOG_INF;
+ }
+ else if (strcmp (pst_temp, "DBG") == 0)
+ {
+ log_level = NSLOG_DBG;
+ }
+ else if (strcmp (pst_temp, "WAR") == 0)
+ {
+ log_level = NSLOG_WAR;
+ }
+ else if (strcmp (pst_temp, "ERR") == 0)
+ {
+ log_level = NSLOG_ERR;
+ }
+ else if (strcmp (pst_temp, "EMG") == 0)
+ {
+ log_level = NSLOG_EMG;
+ }
+ else
+ {
+ log_level = NSLOG_ERR;
+ }
+ }
+ else
+ {
+ log_level = NSLOG_INF;
+ }
+ int i = 0;
+ for (i = 0; i < MAX_LOG_MODULE; i++)
+ {
+ nstack_setlog_level (i, log_level);
+ }
+ if (log_level <= NSLOG_WAR)
+ {
+ /*MONITR log level must set to larger than warning */
+ nstack_setlog_level (MASTER, NSLOG_WAR);
+ }
+
+ /* monitr and nstack write the same file, it will cause synchronize problem */
+ switch (g_my_pro_type)
+ {
+ case LOG_PRO_NSTACK:
+ glogInit ("NSTACK");
+ init_nstack_log_para ();
+ break;
+ case LOG_PRO_OMC_CTRL:
+ glogInit ("CTRL");
+ init_ctrl_log_para ();
+ break;
+ case LOG_PRO_MASTER:
+ glogInit ("MASTER");
+ init_master_log_para ();
+ break;
+ default:
+ return 0;
+ }
+
+ init_log_ctrl_info();
+
+ // this is for monitr to check whether log has beed inited
+ g_nstack_logs[NSOCKET].inited = 1;
+ NSPOL_LOGERR ("nStackMain_version=%s", NSTACK_VERSION);
+ write_pre_init_log();
+ return 0;
+}
+
+/*****************************************************************************
+* Prototype : get_str_value
+* Description : get int value
+* Input : const char *arg
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+get_str_value (const char *arg)
+{
+ char *parsing_end;
+ int iValue = 0;
+ int oldErrno = errno;
+ if (arg == NULL)
+ {
+ return -1;
+ }
+ errno = 0;
+ iValue = (int) strtol (arg, &parsing_end, 0);
+ if (errno || (!parsing_end) || parsing_end[0] != 0)
+ {
+ iValue = -1;
+ }
+ errno = oldErrno;
+ return iValue;
+}
+
+
+/*****************************************************************************
+* Prototype : setlog_level_value
+* Description : proc log level config
+* Input : const char *param
+* const char *value
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+setlog_level_value (const char *param, const char *value)
+{
+ int i = 0;
+ int module = 0;
+ int logLevel = 0;
+ module = get_str_value (param);
+ if ((module < 0) || (MAX_LOG_MODULE <= module))
+ {
+ NSOPR_LOGERR ("input module error]param=%s,module=%d", param, module);
+ return 1;
+ }
+
+ if (strcmp (value, LOG_LEVEL_ERR) == 0)
+ {
+ logLevel = NSLOG_ERR;
+ }
+ else if (strcmp (value, LOG_LEVEL_WAR) == 0)
+ {
+ logLevel = NSLOG_WAR;
+ }
+ else if (strcmp (value, LOG_LEVEL_DBG) == 0)
+ {
+ logLevel = NSLOG_DBG;
+ }
+ else if (strcmp (value, LOG_LEVEL_INF) == 0)
+ {
+ logLevel = NSLOG_INF;
+ }
+ else if (strcmp (value, LOG_LEVEL_EMG) == 0)
+ {
+ logLevel = NSLOG_EMG;
+ }
+ else
+ {
+ NSOPR_LOGERR ("input log level error!");
+ return 1;
+ }
+ NSOPR_LOGINF ("set module log with level]module=%d,logLevel=0x%x",
+ module, logLevel);
+ if (module > 0)
+ {
+ nstack_setlog_level (module, logLevel);
+ return 0;
+ }
+ if (0 == module)
+ {
+ for ( i = 0; i < MAX_LOG_MODULE ; i++ )
+ {
+ nstack_setlog_level(i,logLevel);
+ }
+ }
+ return 0;
+}
+
+
+/*****************************************************************************
+* Prototype : check_log_dir_valid
+* Description : check the log dir valid or not
+* Input : const char *arg
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+check_log_dir_valid (const char *path)
+{
+ size_t length;
+ struct stat statbuf;
+ if (NULL == path)
+ {
+ return -1;
+ }
+ length = strlen (path) + 1;
+ if ((length <= 1) || (length > FILE_NAME_LEN))
+ {
+ return -1;
+ }
+
+ /* only write permission is allowed */
+ if ((0 != access (path, W_OK)))
+ {
+ /* if path can access, use env path */
+ return -1;
+ }
+
+ if ((0 == lstat (path, &statbuf)) && S_ISDIR (statbuf.st_mode))
+ {
+ return 0;
+ }
+ else
+ {
+ return -1;
+ }
+}
+
+
+/*****************************************************************************
+* Prototype : get_app_env_log_path
+* Description : called by environment-specific log init function
+* Input : app_file_path, a char pointer to store the log path
+* Input : app_file_size, the app_file_path size
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+int
+get_app_env_log_path (char *app_file_path, unsigned int app_file_size)
+{
+ char *pst_app_log_path_flag = NULL;
+ char *pst_app_log_path_string = NULL;
+ int log_to_file = 0;
+ int ret = -1;
+ char *app_dir = NULL;
+
+ if ((NULL == app_file_path) || (0 == app_file_size))
+ {
+ return 0;
+ }
+ pst_app_log_path_flag = getenv ("NSTACK_LOG_FILE_FLAG");
+ if (pst_app_log_path_flag && strcmp (pst_app_log_path_flag, "1") == 0)
+ {
+ /* if set enviroment variable to 1,then output to file*/
+ log_to_file = 1;
+ }
+ else
+ {
+ /* if enviroment variable is not equal 1 or
+ don't set this enviroment variable ,output to STDOUT */
+ return 0;
+ }
+
+ /* add the realpath and dir check */
+ /* APP LOG can be set by user */
+ pst_app_log_path_string = getenv("NSTACK_APP_LOG_PATH");
+
+ if ((NULL == pst_app_log_path_string)
+ ||(strlen (pst_app_log_path_string) > FILE_NAME_LEN - 1))
+ {
+ goto app_default;
+ }
+
+ app_dir = realpath (pst_app_log_path_string, NULL);
+ if (check_log_dir_valid (pst_app_log_path_string) < 0)
+ {
+ goto app_default;
+ }
+ ret = STRCPY_S (app_file_path, app_file_size, app_dir);
+ if(EOK != ret)
+ {
+ log_to_file = 0;
+ }
+
+ free(app_dir);
+ return log_to_file;
+
+app_default:
+
+ if ((0 == access (APP_LOG_PATH, W_OK)))
+ {
+ ret = STRCPY_S (app_file_path, app_file_size, APP_LOG_PATH);
+ if (EOK != ret)
+ {
+ log_to_file = 0;
+ }
+ }
+ else
+ {
+ log_to_file = 0;
+ }
+
+ if (NULL != app_dir)
+ {
+ free (app_dir);
+ }
+
+ return log_to_file;
+
+}
+
+/*****************************************************************************
+* Prototype : nstack_log_init_app
+* Description : called by environment-specific log init function
+* Input : None
+* Output : None
+* Return Value : int
+* Calls :
+* Called By :
+*****************************************************************************/
+void
+nstack_log_init_app ()
+{
+ char *pc_temp = NULL;
+ int log_level = NSLOG_ERR;
+ int i = 0;
+ int file_flag = 0;
+ char app_log_path[FILE_NAME_LEN] = { 0 };
+
+ /* log alread initialized, just return */
+ if (LOG_PRO_INVALID != g_my_pro_type)
+ {
+ return;
+ }
+ /* Add app log hook module init */
+ nstack_log_hook_init ();
+
+ if (0 != g_nstack_logs[NSOCKET].inited)
+ {
+ return;
+ }
+ glogInit ("APP");
+
+ pc_temp = getenv ("NSTACK_LOG_ON");
+ if (pc_temp)
+ {
+ if (strcmp (pc_temp, "INF") == 0)
+ {
+ log_level = NSLOG_INF;
+ }
+ else if (strcmp (pc_temp, "DBG") == 0)
+ {
+ log_level = NSLOG_DBG;
+ }
+ else if (strcmp (pc_temp, "WAR") == 0)
+ {
+ log_level = NSLOG_WAR;
+ }
+ else if (strcmp (pc_temp, "ERR") == 0)
+ {
+ log_level = NSLOG_ERR;
+ }
+ else if (strcmp (pc_temp, "EMG") == 0)
+ {
+ log_level = NSLOG_EMG;
+ }
+ else
+ {
+ log_level = NSLOG_ERR;
+ }
+
+ }
+ else
+ {
+ log_level = NSLOG_ERR;
+ }
+
+ /* socket interface APP called include both stack-x and nstack module! */
+ nstack_setlog_level (STACKX, log_level);
+ nstack_setlog_level (NSOCKET, log_level);
+ nstack_setlog_level (LOGRTE, log_level);
+ nstack_setlog_level (LOGDFX, log_level);
+ nstack_setlog_level (LOGFW, log_level);
+ nstack_setlog_level (LOGHAL, log_level);
+ nstack_setlog_level (LOGSBR, log_level);
+
+ /* package the app env handle function, Begin */
+ file_flag = get_app_env_log_path (app_log_path, FILE_NAME_LEN);
+ if ((1 == file_flag) && (strlen (app_log_path) > 0))
+ {
+ glogDir (app_log_path);
+ glogBufLevelSet (GLOG_LEVEL_WARNING);
+ (void) glogLevelSet (GLOG_LEVEL_DEBUG);
+ for (i = 0; i < GLOG_LEVEL_BUTT; i++)
+ glogSetLogSymlink (i, "");
+ nstack_log_count_set (APP_LOG_COUNT);
+ glogMaxLogSizeSet (APP_LOG_SIZE);
+ glogSetLogFilenameExtension (APP_LOG_NAME);
+ glogFlushLogSecsSet (FLUSH_TIME);
+ }
+ else
+ {
+ glogToStderrSet (1);
+ }
+
+ for (i = 0; i < MAX_LOG_MODULE; i++)
+ {
+ g_nstack_logs[i].file_type = LOG_TYPE_APP;
+ }
+ init_log_ctrl_info ();
+ g_my_pro_type = LOG_PRO_APP;
+#ifdef FOR_NSTACK_UT
+
+#else
+ SetGlogCtrlOpt (TRUE);
+#endif
+ NSPOL_LOGERR ("app_nStack_version=%s", NSTACK_VERSION);
+ return;
+}
+
+void
+nstack_segment_error (int s)
+{
+
+#define BACKTRACE_SIZ 20
+ void *array[BACKTRACE_SIZ];
+ int size;
+ int i;
+ char **strings = NULL;
+
+ /*if set, flush the log immediately */
+ glogFlushLogFiles (GLOG_LEVEL_DEBUG);
+
+ size = backtrace (array, BACKTRACE_SIZ);
+ NSPOL_LOGEMG
+ ("------------------DUMP_BACKTRACE[%d]--------------------------------\n",
+ size);
+
+ /* easy to view signal in separate log file */
+ NSPOL_LOGEMG ("Received signal s=%d", s);
+
+ for (i = 0; i < size; i++)
+ {
+ NSPOL_LOGEMG ("[%d]:%p\n", i, array[i]);
+ }
+ strings = backtrace_symbols (array, size);
+ if (NULL == strings)
+ {
+ return;
+ }
+ for (i = 0; i < size; i++)
+ {
+ NSPOL_LOGEMG ("[%d]:%s\n", i, strings[i]);
+ }
+ NSPOL_LOGEMG
+ ("-------------------------------------------------------------------\n");
+ free (strings);
+}
+
+void
+set_log_init_para (struct log_init_para *para)
+{
+ if (NULL == para)
+
+ {
+ return;
+ }
+ if (EOK !=
+ MEMCPY_S (&g_log_init_para, sizeof (struct log_init_para), para,
+ sizeof (struct log_init_para)))
+
+ {
+ return;
+ }
+}
+
+/* control log printed counts */
+static inline void
+update_log_prt_time (struct timespec *cur_time, struct timespec *log_prt_time)
+{
+ log_prt_time->tv_sec = cur_time->tv_sec;
+ log_prt_time->tv_nsec = cur_time->tv_nsec;
+}
+
+int
+check_log_prt_time (int id)
+{
+ struct timespec cur_time;
+ struct timespec *log_prt_time = NULL;
+ if (id >= LOG_CTRL_ID_MAX || id < 0)
+
+ {
+ return 0;
+ }
+ (void) clock_gettime (CLOCK_MONOTONIC, &cur_time);
+ log_prt_time = &g_log_ctrl_info[id].last_log_time;
+ if (cur_time.tv_sec - log_prt_time->tv_sec >=
+ g_log_ctrl_info[id].expire_time)
+ {
+ /* first log need print */
+ set_log_ctrl_time (id, DEFAULT_LOG_CTR_TIME);
+ update_log_prt_time (&cur_time, log_prt_time);
+ return 1;
+ }
+ g_log_ctrl_info[id].unprint_count++;
+ return 0;
+}
+
+int
+get_unprt_log_count (int id)
+{
+ return g_log_ctrl_info[id].unprint_count;
+}
+
+void
+clr_unprt_log_count (int id)
+{
+ g_log_ctrl_info[id].unprint_count = 0;
+}
+
+void
+set_log_ctrl_time (int id, int ctrl_time)
+{
+ if (id >= LOG_CTRL_ID_MAX || id < 0)
+ {
+ return;
+ }
+
+ if (ctrl_time <= 0)
+ {
+ return;
+ }
+
+ g_log_ctrl_info[id].expire_time = ctrl_time;
+}
+
+void
+init_log_ctrl_info ()
+{
+ int i = 0;
+ for (; i < LOG_CTRL_ID_MAX; i++)
+ {
+ /* first log need print */
+ g_log_ctrl_info[i].expire_time = 0;
+ g_log_ctrl_info[i].unprint_count = 0;
+ g_log_ctrl_info[i].last_log_time.tv_sec = 0;
+ g_log_ctrl_info[i].last_log_time.tv_nsec = 0;
+ }
+
+ // for every socket api, need different log id
+
+ // for nstack inner
+}
+
+void
+set_log_proc_type (int log_proc_type)
+{
+ g_my_pro_type = log_proc_type;
+}
diff --git a/src/framework/snapshot/fw_snapshot.c b/src/framework/snapshot/fw_snapshot.c
new file mode 100644
index 0000000..790ecbf
--- /dev/null
+++ b/src/framework/snapshot/fw_snapshot.c
@@ -0,0 +1,483 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include "nstack_securec.h"
+#include "nsfw_snapshot.h"
+#include "nstack_log.h"
+#include "fw_ss_tlv.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+/* *INDENT-OFF* */
+nsfw_ss_objDescManager_t g_nsfw_ss_objDescManager =
+{
+.g_nsfw_ss_objDesNum = 0};
+
+/* *INDENT-ON* */
+
+void
+nsfw_ss_register_ObjDesc (nsfw_ss_objDesc_t * objDesc)
+{
+ if (objDesc == NULL)
+ return;
+ nsfw_ss_objDescManager_t *manager = nsfw_ss_getObjDescManagerInst ();
+ if (manager->g_nsfw_ss_objDesNum >= NSFW_SS_MAX_OBJDESC_NUM)
+ return;
+ manager->g_nsfw_ss_objDescs[manager->g_nsfw_ss_objDesNum++] = objDesc;
+}
+
+static nsfw_ss_objDesc_t *
+nsfw_ss_getObjDescFromType (u16 objType)
+{
+ nsfw_ss_objDescManager_t *manager = nsfw_ss_getObjDescManagerInst ();
+ int i;
+ for (i = 0; i < manager->g_nsfw_ss_objDesNum && i < NSFW_SS_MAX_OBJDESC_NUM;
+ i++)
+ {
+ if (manager->g_nsfw_ss_objDescs[i]->objType == objType)
+ return manager->g_nsfw_ss_objDescs[i];
+ }
+ return NULL;
+}
+
+static nsfw_ss_objMemDesc_t *
+nsfw_ss_getMemDescFromType (u16 objType, nsfw_ss_objDesc_t * objDesc)
+{
+ int i;
+ for (i = 0; i < objDesc->memNum; i++)
+ {
+ if (objDesc->memDesc[i].type == objType)
+ {
+ return &objDesc->memDesc[i];
+ }
+ }
+ return NULL;
+}
+
+/**
+ * @Function nsfw_ss_store
+ * @Description store object to memory
+ * @param (in) objType - type of object with member description
+ * @param (in) obj - adderss of object memory
+ * @param (in) storeMem - address of memory to store object data
+ * @param (in) storeMemLen - maximal length of storage memory
+ * @return positive integer means length of memory cost on success. return -1 if error
+ */
+int
+nsfw_ss_storeObjMem (u16 objMemType, void *obj, void *storeMem,
+ u32 storeMemLen)
+{
+ if (NULL == obj || NULL == storeMem)
+ return -1;
+
+ // example of object
+ /* struct A{ */
+ /* int a1; */
+ /* struct A2 a2; --> struct A2 {int a2} */
+ /* struct A3 a3[2]; --> struct A3 [{int a3}, {int a3}] */
+ /* } */
+
+ /* -------------------------------------------- */
+ /* | type(object) | length | */
+ /* | -------------------------------------- | */// --
+ /* | | type(item) | length | | */// member a1
+ /* | | item value (object->member) | | */// --
+ /* | -------------------------------------- | */// object a2
+ /* | | type(object) | length | | */// --
+ /* | | ------------------------------- | | */// member a2
+ /* | | | type(item) | length | | | */// --
+ /* | | | item value (object->member) | | | */// --
+ /* | | ------------------------------- | | *///
+ /* | -------------------------------------- | *///
+ /* | | type(object array) | length | | */// array member a3
+ /* | | ------------------------------- | | */// --
+ /* | | | type(object) | length | | | */// object a3_1
+ /* | | | ----------------------------| | | */// --
+ /* | | | type(item) | length | | | */// member a3_1_1
+ /* | | | item value (object->member) | | | */
+ /* | | | ----------------------------| | | */
+ /* | | ------------------------------- | | */
+ /* | | | type(object) | length | | | */
+ /* | | | ----------------------------| | | */
+ /* | | | type(item) | length | | | */
+ /* | | | item value (object->member) | | | */
+ /* | | | ----------------------------| | | */
+ /* | | ------------------------------- | | */
+ /* | |------------------------------------| | */
+ /* -------------------------------------------- */
+ nsfw_ss_objDesc_t *objDesc =
+ nsfw_ss_getObjDescFromType (NSFW_SS_TYPE_GETOBJ (objMemType));
+ if (NULL == objDesc)
+ return -1;
+
+ /* Get object header tlv */
+ if (storeMemLen < tlv_header_length ())
+ return -1;
+ nsfw_ss_tlv_t *tlv = (nsfw_ss_tlv_t *) storeMem;
+ tlv->type = objMemType;
+ tlv->length = 0;
+ tlv_header (storeMem);
+ storeMemLen -= tlv_header_length ();
+
+ /* Search every object member */
+
+ /* For base item(including array of base item), it should start with a tlv header */
+ /* For object array, it should start with one tlv header including array information */
+ /* For object, it should call nsfw_ss_store recursively */
+ int i;
+ for (i = 0; i < objDesc->memNum; i++)
+ {
+ nsfw_ss_objMemDesc_t *memDesc = &objDesc->memDesc[i];
+ if (NSFW_SS_TYPE_IS_MEMBER_OBJ (memDesc->type))
+ {
+
+ if (NSFW_SS_TYPE_IS_MEMBER_ARRAY (memDesc->type))
+ {
+ /* array object should includes one array tlv header, shows the array informations */
+ if (storeMemLen < tlv_header_length ())
+ return -1;
+ nsfw_ss_tlv_t *arrayTlv = (nsfw_ss_tlv_t *) storeMem;
+ arrayTlv->type = memDesc->type;
+ arrayTlv->length = 0;
+ tlv_header (storeMem);
+ storeMemLen -= tlv_header_length ();
+ nsfw_ss_objDesc_t *memObjDesc =
+ nsfw_ss_getObjDescFromType (NSFW_SS_TYPE_GETOBJ
+ (memDesc->type));
+ if (NULL == memObjDesc)
+ return -1;
+ u32 arraySize = memDesc->length / memObjDesc->objSize;
+ u32 j;
+ for (j = 0; j < arraySize; j++)
+ {
+ int ret =
+ nsfw_ss_storeObjMem (NSFW_SS_TYPE_SET_MEMBER_OBJ
+ (NSFW_SS_TYPE_GETOBJ (memDesc->type),
+ 0),
+ (char *) obj +
+ (u64) (memDesc->offset) +
+ (u64) j * memObjDesc->objSize,
+ storeMem, storeMemLen);
+ if ((-1 == ret) || (storeMemLen < (u32) ret))
+ return -1;
+ tlv_mem_forward (storeMem, ret);
+ storeMemLen -= (u32) ret;
+ arrayTlv->length += (u32) ret;
+ }
+ tlv->length += (arrayTlv->length + (u32) tlv_header_length ());
+ }
+ else
+ {
+ int ret = nsfw_ss_storeObjMem (memDesc->type,
+ ((char *) obj + memDesc->offset),
+ storeMem, storeMemLen);
+ if (ret < 0 || (storeMemLen < (u32) ret))
+ return -1;
+ storeMemLen -= (u32) ret;
+ tlv_mem_forward (storeMem, ret);
+ tlv->length += (u32) ret;
+ }
+ }
+ else
+ {
+ // Base Item
+ if (storeMemLen < tlv_header_length ())
+ {
+ return -1;
+ }
+ nsfw_ss_tlv_t *curtlv = (nsfw_ss_tlv_t *) storeMem; // curTlv means next tlv elem
+ curtlv->type = memDesc->type;
+ curtlv->length = memDesc->length;
+ tlv_header (storeMem);
+ storeMemLen -= tlv_header_length ();
+ if (storeMemLen < curtlv->length)
+ return -1;
+ if (EOK !=
+ MEMCPY_S (storeMem, (size_t) storeMemLen,
+ ((char *) obj + memDesc->offset),
+ (size_t) memDesc->length))
+ {
+ return -1;
+ }
+ tlv_mem_forward (storeMem, memDesc->length);
+ storeMemLen -= memDesc->length;
+ tlv->length += (curtlv->length + (u32) tlv_header_length ());
+ }
+ }
+ return (int) (tlv->length + tlv_header_length ());
+}
+
+/**
+ * @Function nsfw_ss_store
+ * @Description store object to memory
+ * @param (in) objType - type of object
+ * @param (in) obj - adderss of object memory
+ * @param (in) storeMem - address of memory to store object data
+ * @param (in) storeMemLen - maximal length of storage memory
+ * @return positive integer means length of memory cost on success. return -1 if error
+ */
+int
+nsfw_ss_store (u16 objType, void *obj, void *storeMem, u32 storeMemLen)
+{
+ return nsfw_ss_storeObjMem (NSFW_SS_TYPE_SET_MEMBER_OBJ (objType, 0),
+ obj, storeMem, storeMemLen);
+}
+
+/**
+ * @Function nsfw_ss_restoreObjArray
+ * @Description restore array of objects
+ * @param (in) objType - type of object
+ * @param (in) objMem - object memory to restore
+ * @param (in) mem - memory of storage
+ * @param (in) storeMemLength - maximal length of storage memroy
+ * @return 0 on succss , -1 on error
+ */
+NSTACK_STATIC int
+nsfw_ss_restoreObjArray (int objType, void *objMem, void *mem,
+ u32 storeMemLength)
+{
+ if (storeMemLength < tlv_header_length ())
+ return -1;
+ nsfw_ss_tlv_t *arrayTlv = (nsfw_ss_tlv_t *) mem;
+ storeMemLength -= tlv_header_length ();
+ tlv_header (mem);
+ if (0 == arrayTlv->length || storeMemLength < arrayTlv->length)
+ return -1;
+ storeMemLength = arrayTlv->length; // Only cares tlv->value
+ nsfw_ss_objDesc_t *objDesc = nsfw_ss_getObjDescFromType ((u16) objType);
+ if (NULL == objDesc)
+ return -1;
+
+ /* Now we are going to iterate every object */
+ u32 objCnt = 0;
+ while (storeMemLength)
+ {
+ if (storeMemLength < tlv_header_length ())
+ return -1; // Format error
+ nsfw_ss_tlv_t *objTlv = (nsfw_ss_tlv_t *) mem;
+ if ((int) NSFW_SS_TYPE_GETOBJ (objTlv->type) != objType)
+ {
+ return -1;
+ }
+ int ret =
+ nsfw_ss_restore ((char *) objMem + (u64) objDesc->objSize * objCnt,
+ mem, storeMemLength);
+ if (-1 == ret)
+ return -1;
+ objCnt++;
+ tlv_mem_forward (mem, (objTlv->length + tlv_header_length ()));
+ storeMemLength -= (objTlv->length + tlv_header_length ());
+ }
+ return 0;
+}
+
+/**
+ * @Function nsfw_ss_restore
+ * @Description restore object from memory
+ * @param (in) objMem - memory of object
+ * @param (in) mem - memory of storage
+ * @param (in) storeMemLen - maximal length of storage memory
+ * @return positive integer stands on object type, -1 on error
+ */
+int
+nsfw_ss_restore (void *objMem, void *mem, u32 storeMemLen)
+{
+ if (NULL == objMem || NULL == mem || 0 == storeMemLen)
+ return -1;
+
+ // example of object
+ /* struct A{ */
+ /* int a1; */
+ /* struct A2 a2; --> struct A2 {int a2} */
+ /* struct A3 a3[2]; --> struct A3 [{int a3}, {int a3}] */
+ /* } */
+
+ /* -------------------------------------------- */// --
+ /* | type(object) | length | */// type length
+ /* | -------------------------------------- | */// --
+ /* | | type(item) | length | | */// member a1
+ /* | | item value (object->member) | | */// --
+ /* | -------------------------------------- | */// object a2
+ /* | | type(object) | length | | */// --
+ /* | | ------------------------------- | | */// member a2
+ /* | | | type(item) | length | | | */// --
+ /* | | | item value (object->member) | | | */// --
+ /* | | ------------------------------- | | *///
+ /* | -------------------------------------- | *///
+ /* | | type(object array) | length | | */// array member a3
+ /* | | ------------------------------- | | */// --
+ /* | | | type(object) | length | | | */// object a3_1
+ /* | | | ----------------------------| | | */// --
+ /* | | | type(item) | length | | | */// member a3_1_1
+ /* | | | item value (object->member) | | | */
+ /* | | | ----------------------------| | | */
+ /* | | ------------------------------- | | */
+ /* | | | type(object) | length | | | */
+ /* | | | ----------------------------| | | */
+ /* | | | type(item) | length | | | */
+ /* | | | item value (object->member) | | | */
+ /* | | | ----------------------------| | | */
+ /* | | ------------------------------- | | */
+ /* | |------------------------------------| | */
+ /* -------------------------------------------- */
+ if (storeMemLen < tlv_header_length ())
+ return -1;
+ nsfw_ss_tlv_t *tlv = (nsfw_ss_tlv_t *) mem;
+ storeMemLen -= tlv_header_length ();
+ tlv_header (mem);
+ nsfw_ss_objDesc_t *objDesc =
+ nsfw_ss_getObjDescFromType (NSFW_SS_TYPE_GETOBJ (tlv->type));
+ if (NULL == objDesc)
+ {
+ return -1;
+ }
+ if (!NSFW_SS_TYPE_IS_MEMBER_OBJ (tlv->type))
+ return -1;
+ if (0 == tlv->length || storeMemLen < tlv->length)
+ return -1;
+
+ /* Now we go to inner of object */
+ storeMemLen = tlv->length; /* Only care about tlv values */
+ while (storeMemLen)
+ {
+ if (storeMemLen < tlv_header_length ())
+ return -1; // Format error
+ nsfw_ss_tlv_t *curtlv = (nsfw_ss_tlv_t *) mem;
+ nsfw_ss_objMemDesc_t *memDesc =
+ nsfw_ss_getMemDescFromType (curtlv->type, objDesc);
+ if (NULL == memDesc)
+ { // This type not support
+ storeMemLen -= tlv_header_length ();
+ tlv_header (mem);
+ if (storeMemLen < curtlv->length)
+ return -1;
+ tlv_mem_forward (mem, curtlv->length);
+ storeMemLen -= curtlv->length;
+ continue;
+ }
+ if (NSFW_SS_TYPE_IS_MEMBER_OBJ (curtlv->type))
+ {
+ if (NSFW_SS_TYPE_IS_MEMBER_ARRAY (curtlv->type))
+ {
+ int ret =
+ nsfw_ss_restoreObjArray ((int)
+ NSFW_SS_TYPE_GETOBJ (curtlv->type),
+ (void *) ((char *) objMem +
+ memDesc->offset), mem,
+ storeMemLen);
+ if (-1 == ret)
+ return -1;
+ }
+ else
+ {
+ int ret =
+ nsfw_ss_restore ((void *) ((char *) objMem +
+ memDesc->offset), mem,
+ storeMemLen);
+ if (-1 == ret)
+ return -1;
+ }
+ tlv_mem_forward (mem, (curtlv->length + tlv_header_length ()));
+ storeMemLen -= (curtlv->length + tlv_header_length ());
+ }
+ else
+ {
+ tlv_header (mem);
+ storeMemLen -= tlv_header_length ();
+ NSFW_LOGDBG
+ ("curtlv->type(%u), curtlv->length(%u), memDesc->offset(%u), memDesc->length(%u), mem(%u)",
+ curtlv->type, curtlv->length, memDesc->offset, memDesc->length,
+ *(u32 *) mem);
+ if (storeMemLen < curtlv->length)
+ return -1;
+ if (EOK !=
+ MEMCPY_S ((void *) ((char *) objMem + memDesc->offset),
+ (size_t) memDesc->length, mem,
+ (size_t) curtlv->length))
+ {
+ return -1;
+ }
+ tlv_mem_forward (mem, curtlv->length);
+ storeMemLen -= curtlv->length;
+ }
+ }
+ return (int) tlv->type;
+}
+
+/**
+ * @Function nsfw_ss_getObjStoreMemLen
+ * @Description Get the maximal memory it needs
+ * @param (in) objType - type of object
+ * @return length of memory needs, -1 if error
+ */
+int
+nsfw_ss_getObjStoreMemLen (int objType)
+{
+ u32 maxlength = tlv_header_length ();
+ u32 i;
+ nsfw_ss_objDesc_t *objDesc = nsfw_ss_getObjDescFromType ((u16) objType);
+ if (!objDesc)
+ return -1;
+ for (i = 0; i < objDesc->memNum; i++)
+ {
+ nsfw_ss_objMemDesc_t *memDesc = &objDesc->memDesc[i];
+ int temp_len;
+ if (NSFW_SS_TYPE_IS_MEMBER_OBJ (memDesc->type))
+ {
+ nsfw_ss_objDesc_t *curObjDesc =
+ nsfw_ss_getObjDescFromType (NSFW_SS_TYPE_GETOBJ (memDesc->type));
+ if (NULL == curObjDesc)
+ return -1;
+ if (NSFW_SS_TYPE_IS_MEMBER_ARRAY (memDesc->type))
+ {
+ maxlength += tlv_header_length (); // array length
+ u32 arrSize = memDesc->length / curObjDesc->objSize;
+ u32 j;
+ for (j = 0; j < arrSize; j++)
+ {
+ temp_len =
+ nsfw_ss_getObjStoreMemLen ((int) curObjDesc->objType);
+ if (temp_len < 0)
+ return -1;
+ maxlength += (u32) temp_len;
+ }
+ }
+ else
+ {
+ temp_len =
+ nsfw_ss_getObjStoreMemLen ((int) curObjDesc->objType);
+ if (temp_len < 0)
+ return -1;
+ maxlength += (u32) temp_len;
+ }
+ }
+ else
+ {
+ maxlength += ((u32) tlv_header_length () + memDesc->length);
+ }
+ }
+ return (int) maxlength;
+}
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
diff --git a/src/framework/snapshot/fw_ss_tlv.h b/src/framework/snapshot/fw_ss_tlv.h
new file mode 100644
index 0000000..0bfbd91
--- /dev/null
+++ b/src/framework/snapshot/fw_ss_tlv.h
@@ -0,0 +1,47 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#ifndef _FW_SS_TLV_H
+#define _FW_SS_TLV_H
+
+#include <stdlib.h>
+#include "types.h"
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+typedef struct _nsfw_ss_tlv
+{
+ u16 type;
+ u32 length;
+ void *value;
+} nsfw_ss_tlv_t;
+
+#define tlv_header_length() ((size_t)(&((nsfw_ss_tlv_t*)0)->value))
+
+#define tlv_mem_forward(mem, step) ((mem) = (void*) ((char*)(mem) + (step)))
+#define tlv_header(mem) tlv_mem_forward((mem), tlv_header_length()) // move header
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif /* __cplusplus */
+
+#endif /* _FW_SS_TLV_H */
diff --git a/src/framework/tracing/nstack_trace.c b/src/framework/tracing/nstack_trace.c
new file mode 100644
index 0000000..88c8ffb
--- /dev/null
+++ b/src/framework/tracing/nstack_trace.c
@@ -0,0 +1,52 @@
+/*
+*
+* Copyright (c) 2018 Huawei Technologies Co.,Ltd.
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at:
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+/*==============================================*
+ * include header files *
+ *----------------------------------------------*/
+#include "nstack_trace.h"
+#include "nstack_securec.h"
+#include <stdarg.h>
+#include <dlfcn.h>
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+extern "C"{
+/* *INDENT-ON* */
+#endif
+
+/*==============================================*
+ * constants or macros define *
+ *----------------------------------------------*/
+#define EVENT_MAX 5
+#define NSTACK_TRACE_SWICH "NSTACK_TRACE_ON"
+/*==============================================*
+ * project-wide global variables *
+ *----------------------------------------------*/
+trace_fun_t nstack_trace_fun;
+__thread trace_hread_t strace_header = {
+ .thread_id = -1,
+ .trace_id = TRACE_NULL,
+};
+
+int tracing_inited = 0;
+__thread char *cad_traceID_string = NULL;
+
+#ifdef __cplusplus
+/* *INDENT-OFF* */
+}
+/* *INDENT-ON* */
+#endif