Merge "[l2l3 stack] implements new nd state machine & nd buffering"
authorDeepak S <deepak.s@linux.intel.com>
Thu, 20 Jul 2017 11:22:33 +0000 (11:22 +0000)
committerGerrit Code Review <gerrit@opnfv.org>
Thu, 20 Jul 2017 11:22:33 +0000 (11:22 +0000)
1  2 
VNFs/vACL/pipeline/pipeline_acl_be.c
VNFs/vCGNAPT/pipeline/pipeline_cgnapt_be.c
VNFs/vFW/pipeline/pipeline_vfw_be.c

@@@ -166,30 -166,6 +166,6 @@@ uint32_t local_get_nh_ipv4(uint32_t ip
        return 0;
  }
  
- static void do_local_nh_ipv4_cache(uint32_t dest_if, struct pipeline_acl *p_acl)
- {
-       /* Search for the entry and do local copy */
-       int i;
-       for (i = 0; i < MAX_ARP_RT_ENTRY; i++) {
-               if (lib_arp_route_table[i].port == dest_if) {
-                       struct lib_arp_route_table_entry *lentry =
-                               &p_acl->local_lib_arp_route_table
-                               [p_acl->local_lib_arp_route_ent_cnt];
-                       lentry->ip = lib_arp_route_table[i].ip;
-                       lentry->mask = lib_arp_route_table[i].mask;
-                       lentry->port = lib_arp_route_table[i].port;
-                       lentry->nh = lib_arp_route_table[i].nh;
-                       p_acl->local_lib_arp_route_ent_cnt++;
-                       break;
-               }
-       }
- }
  static uint32_t local_get_nh_ipv6(uint8_t *ip,
                                  uint32_t *port,
                                  uint8_t nhip[], struct pipeline_acl *p_acl)
          }
          return 0;
  }
- void do_local_nh_ipv6_cache(uint32_t dest_if, struct pipeline_acl *p_acl)
- {
-       /* Search for the entry and do local copy */
-       int i, l;
-       for (i = 0; i < MAX_ND_RT_ENTRY; i++) {
-               if (lib_nd_route_table[i].port == dest_if) {
-                       struct lib_nd_route_table_entry *lentry =
-                           &p_acl->local_lib_nd_route_table
-                           [p_acl->local_lib_nd_route_ent_cnt];
-                       for (l = 0; l < 16; l++) {
-                               lentry->ipv6[l] = lib_nd_route_table[i].ipv6[l];
-                               lentry->nhipv6[l] =
-                                   lib_nd_route_table[i].nhipv6[l];
-                       }
-                       lentry->depth = lib_nd_route_table[i].depth;
-                       lentry->port = lib_nd_route_table[i].port;
-                       p_acl->local_lib_nd_route_ent_cnt++;
-                       break;
-               }               /* if */
-       }                       /* for */
- }
  
  static uint8_t check_arp_icmp(struct rte_mbuf *pkt,
                              uint64_t pkt_mask, struct pipeline_acl *p_acl)
@@@ -925,9 -875,9 +875,9 @@@ pkt_work_acl_key(struct rte_pipeline *p
                            (dest_address, &dest_if, (struct ether_addr *) eth_dest);
                        *port_out_id = p_acl->port_out_id[dest_if];
                        if (arp_cache_dest_mac_present(dest_if)) {
-                               ether_addr_copy(get_link_hw_addr(dest_if), (struct ether_addr *)eth_src);
-                               arp_data_ptr[dest_if]->n_last_update = time(NULL);
+                               ether_addr_copy(get_link_hw_addr(dest_if),
+                                        (struct ether_addr *)eth_src);
+                               update_nhip_access(dest_if);
                                if (unlikely(ret_arp_data && ret_arp_data->num_pkts)) {
                                        printf("sending buffered packets\n");
                                        arp_send_buffered_pkts(ret_arp_data,
                                }
                        } else {
                                if (unlikely(ret_arp_data == NULL)) {
+                                       if (ACL_DEBUG)
                                        printf("%s: NHIP Not Found, "
                                        "outport_id: %d\n", __func__,
                                        *port_out_id);
                                                continue;
                                        } else {
                                                arp_pkts_mask |= pkt_mask;
-                                               arp_queue_unresolved_packet(ret_arp_data, pkt);
+                                               arp_queue_unresolved_packet(ret_arp_data,
+                                                                        pkt);
                                                continue;
                                        }
                                }
                        }
                        memcpy(dest_address, *dst_addr, sizeof(dest_address));
                        memset(nhip, 0, sizeof(nhip));
-                       ret = local_get_nh_ipv6(&dest_address[0], &dest_if,
-                                               &nhip[0], p_acl);
-                       if (is_phy_port_privte(phy_port)) {
-                               if (!ret) {
-                                       dest_if = get_prv_to_pub_port((
-                                                                      uint32_t
-                                                                      *)
-                                             &dest_address[0], IP_VERSION_6);
-                                       do_local_nh_ipv6_cache(dest_if, p_acl);
-                                       *port_out_id =
-                                           p_acl->port_out_id[dest_if];
-                               }
-                               //              port = ACL_PUB_PORT_ID;
  
+                       struct nd_entry_data *ret_nd_data = NULL;
+                       ret_nd_data = get_dest_mac_address_ipv6_port
+                           (dest_address, &dest_if, &hw_addr, &nhip[0]);
+                       *port_out_id = p_acl->port_out_id[dest_if];
+                       if (nd_cache_dest_mac_present(dest_if)) {
+                               ether_addr_copy(get_link_hw_addr(dest_if),
+                                       (struct ether_addr *)eth_src);
+                               update_nhip_access(dest_if);
+                               if (unlikely(ret_nd_data && ret_nd_data->num_pkts)) {
+                                       printf("sending buffered packets\n");
+                                       p_acl->counters->tpkts_processed +=
+                                                ret_nd_data->num_pkts;
+                                       nd_send_buffered_pkts(ret_nd_data,
+                                       (struct ether_addr *)eth_dest, *port_out_id);
+                               }
                        } else {
-                               if (!ret) {
-                                       dest_if = get_pub_to_prv_port((
-                                                                      uint32_t
-                                                                      *)
-                                             &dest_address[0], IP_VERSION_6);
-                                       do_local_nh_ipv6_cache(dest_if, p_acl);
-                                       *port_out_id =
-                                           p_acl->port_out_id[dest_if];
+                               if (unlikely(ret_nd_data == NULL)) {
+                                       if (ACL_DEBUG)
+                                               printf("ACL before drop pkt_mask  "
+                                               "%lu, pkt_num %d\n", pkts_mask, pos);
+                                       pkts_mask &= ~(1LLU << pos);
+                                       if (ACL_DEBUG)
+                                               printf("ACL after drop pkt_mask  "
+                                               "%lu, pkt_num %d\n", pkts_mask, pos);
+                                       p_acl->counters->pkts_drop++;
+                                       continue;
                                }
- //               port = ACL_PRV_PORT_ID;
-                       }
  
-                       if (get_dest_mac_address_ipv6_port
-                           (dest_address, &dest_if, &hw_addr, &nhip[0])) {
-                               if (ACL_DEBUG) {
-                                       printf("MAC found for  port %d - "
-                                       " %02x:%02x:%02x:%02x:%02x:%02x\n",
-                                            phy_port, hw_addr.addr_bytes[0],
-                                            hw_addr.addr_bytes[1],
-                                            hw_addr.addr_bytes[2],
-                                            hw_addr.addr_bytes[3],
-                                            hw_addr.addr_bytes[4],
-                                            hw_addr.addr_bytes[5]);
-                                       printf("Dest MAC before -  "
-                                       "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                                            eth_dest[0], eth_dest[1],
-                                            eth_dest[2], eth_dest[3],
-                                            eth_dest[4], eth_dest[5]);
-                               }
-                               memcpy(eth_dest, &hw_addr,
-                                      sizeof(struct ether_addr));
-                               if (ACL_DEBUG) {
-                                       printf("PktP %p, dest_macP %p\n", pkt,
-                                              eth_dest);
-                                       printf("Dest MAC after -  "
-                               "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                                            eth_dest[0], eth_dest[1],
-                                            eth_dest[2], eth_dest[3],
-                                            eth_dest[4], eth_dest[5]);
+                               if (ret_nd_data->status == INCOMPLETE ||
+                                       ret_nd_data->status == PROBE) {
+                                       if (ret_nd_data->num_pkts >= NUM_DESC) {
+                                               /* Drop the pkt */
+                                               if (ACL_DEBUG)
+                                                       printf("ACL before drop pkt_mask  "
+                                                       "%lu, pkt_num %d\n", pkts_mask, pos);
+                                               pkts_mask &= ~(1LLU << pos);
+                                               if (ACL_DEBUG)
+                                                       printf("ACL after drop pkt_mask  "
+                                                       "%lu, pkt_num %d\n", pkts_mask, pos);
+                                               p_acl->counters->pkts_drop++;
+                                               continue;
+                                       } else {
+                                               arp_pkts_mask |= pkt_mask;
+                                               nd_queue_unresolved_packet(ret_nd_data,
+                                                                                pkt);
+                                               continue;
+                                       }
                                }
-                               if (is_phy_port_privte(phy_port))
-                                       memcpy(eth_src,
-                                              get_link_hw_addr(dest_if),
-                                              sizeof(struct ether_addr));
-                               else
-                                       memcpy(eth_src,
-                                              get_link_hw_addr(dest_if),
-                                              sizeof(struct ether_addr));
  
- /* memcpy(eth_src, get_link_hw_addr(p_acl->links_map[phy_port]), */
- /*               sizeof(struct ether_addr)); */
-                               p_acl->counters->tpkts_processed++;
-                               p_acl->counters->bytes_processed +=
-                                   packet_length;
                        }
  
-                       else {
- #if 0
-                       /* Request next neighbor for Ipv6 is yet to be done. */
-                               if (*nhip != 0) {
-                                       if (ACL_DEBUG)
-                                               printf
-                                   ("ACL requesting ARP for ip %x, port %d\n",
-                                                    dest_address, phy_port);
-                       /* request_arp(p_acl->links_map[phy_port], *nhip); */
-                               }
- #endif
-                               /* Drop packet by changing the mask */
-                               if (ACL_DEBUG)
-                                       printf("ACL before drop pkt_mask  "
-                                                       "%lu, pkt_num %d\n",
-                                            pkts_mask, pos);
-                               pkts_mask &= ~(1LLU << pos);
-                               if (ACL_DEBUG)
-                                       printf("ACL after drop pkt_mask  "
-                                                       "%lu, pkt_num %d\n",
-                                            pkts_mask, pos);
-                               p_acl->counters->pkts_drop++;
-                       }
-               }
+               } /* if (hdr_chk == IPv6_HDR_VERSION) */
  
        }
  
@@@ -1645,44 -1551,16 +1551,16 @@@ pkt_work_acl_ipv4_key(struct rte_pipeli
                                                                       nhip));
                        uint32_t packet_length = rte_pktmbuf_pkt_len(pkt);
                        *nhip = 0;
-                       if (is_phy_port_privte(phy_port)) {
-                               dest_address = rte_bswap32(*dst_addr);
-                               ret =
-                                   local_get_nh_ipv4(dest_address, &dest_if,
-                                                     nhip, p_acl);
-                               if (!ret) {
-                                       dest_if =
-                                           get_prv_to_pub_port(&dest_address,
-                                                               IP_VERSION_4);
-                                       do_local_nh_ipv4_cache(dest_if, p_acl);
-                               }
-                               *port_out_id = p_acl->port_out_id[dest_if];
-                       }
-                       /* port = ACL_PUB_PORT_ID; */
-                       else {
-                               dest_address = rte_bswap32(*dst_addr);
-                               ret = local_get_nh_ipv4(dest_address, &dest_if,
-                                                       nhip, p_acl);
-                               if (!ret) {
-                                       dest_if =
-                                           get_pub_to_prv_port(&dest_address,
-                                                               IP_VERSION_4);
-                                       do_local_nh_ipv4_cache(dest_if, p_acl);
-                               };
-                               *port_out_id = p_acl->port_out_id[dest_if];
-                       }
-                       /* port = ACL_PRV_PORT_ID; */
+                       dest_address = rte_bswap32(*dst_addr);
                        struct arp_entry_data *ret_arp_data = NULL;
                        ret_arp_data = get_dest_mac_addr_port
                            (dest_address, &dest_if, (struct ether_addr *)eth_dest);
                        *port_out_id = p_acl->port_out_id[dest_if];
  
                        if (arp_cache_dest_mac_present(dest_if)) {
-                               ether_addr_copy(get_link_hw_addr(dest_if), (struct ether_addr *)eth_src);
-                               arp_data_ptr[dest_if]->n_last_update = time(NULL);
+                               ether_addr_copy(get_link_hw_addr(dest_if),
+                                        (struct ether_addr *)eth_src);
+                               update_nhip_access(dest_if);
                                if (unlikely(ret_arp_data && ret_arp_data->num_pkts)) {
                                        printf("sending buffered packets\n");
                                        arp_send_buffered_pkts(ret_arp_data,
                        } else {
                                if (unlikely(ret_arp_data == NULL)) {
  
+                                       if (ACL_DEBUG)
                                        printf("%s: NHIP Not Found, "
                                        "outport_id: %d\n", __func__,
                                        *port_out_id);
  
                        else {
  
- #if 0
-                       /* Request next neighbor for Ipv6 is yet to be done. */
-                               if (*nhip != 0) {
-                                       if (ACL_DEBUG)
-                                               printf
-                                   ("ACL requesting ARP for ip %x, port %d\n",
-                                                    dest_address, phy_port);
-                       /* request_arp(p_acl->links_map[phy_port], *nhip); */
-                               }
- #endif
                                /* Drop packet by changing the mask */
                                if (ACL_DEBUG)
                                        printf("ACL before drop pkt_mask "
@@@ -2331,151 -2199,6 +2199,6 @@@ pkt_work_acl_ipv6_key(struct rte_pipeli
                uint8_t hdr_chk =
                    RTE_MBUF_METADATA_UINT8(pkt, MBUF_HDR_ROOM + ETH_HDR_SIZE);
                hdr_chk = hdr_chk >> IP_VERSION_CHECK;
- #if 0
-               if (hdr_chk == IPv4_HDR_VERSION) {
-                       struct acl_table_entry *entry =
-                           (struct acl_table_entry *)
-                           p_acl->acl_entries_ipv4[pos];
-                       uint16_t phy_port = entry->head.port_id;
-                       uint32_t *port_out_id =
-                           RTE_MBUF_METADATA_UINT32_PTR(pkt,
-                                                        META_DATA_OFFSET +
-                                                        offsetof(struct
-                                                         mbuf_acl_meta_data,
-                                                                 output_port));
-                       /*  *port_out_id = p_acl->links_map[phy_port]; */
-                       if (is_phy_port_privte(phy_port))
-                               *port_out_id = ACL_PUB_PORT_ID;
-                       else
-                               *port_out_id = ACL_PRV_PORT_ID;
-                       if (ACL_DEBUG)
-                               printf
-                                   ("phy_port = %i,links_map[phy_port] = %i\n",
-                                    phy_port, p_acl->links_map[phy_port]);
-       /* header room + eth hdr size + dst_adr offset in ip header */
-                       uint32_t dst_addr_offset =
-                           MBUF_HDR_ROOM + ETH_HDR_SIZE + IP_HDR_DST_ADR_OFST;
-                       uint32_t *dst_addr =
-                           RTE_MBUF_METADATA_UINT32_PTR(pkt, dst_addr_offset);
-                       uint8_t *eth_dest =
-                           RTE_MBUF_METADATA_UINT8_PTR(pkt, MBUF_HDR_ROOM);
-                       uint8_t *eth_src =
-                           RTE_MBUF_METADATA_UINT8_PTR(pkt, MBUF_HDR_ROOM + 6);
-                       struct ether_addr hw_addr;
-                       uint32_t dest_address = rte_bswap32(*dst_addr);
-                       uint32_t *nhip = RTE_MBUF_METADATA_UINT32_PTR(pkt,
-                                                             META_DATA_OFFSET
-                                                                     +
-                                                                     offsetof
-                                                                     (struct
-                                                      mbuf_acl_meta_data,
-                                                                      nhip));
-                       uint32_t packet_length = rte_pktmbuf_pkt_len(pkt);
-                       *nhip = 0;
-                       if (is_phy_port_privte(phy_port)) {
-                               dest_address = rte_bswap32(*dst_addr);
-                               ret =
-                                   local_get_nh_ipv4(dest_address, &dest_if,
-                                                     nhip, p_acl);
-                               if (!ret) {
-                                       dest_if =
-                                           get_prv_to_pub_port(&dest_address,
-                                                               IP_VERSION_4);
-                                       do_local_nh_ipv4_cache(dest_if, p_acl);
-                               }
-                               *port_out_id = p_acl->port_out_id[dest_if];
-                       }
-                       /* port = ACL_PUB_PORT_ID; */
-                       else {
-                               dest_address = rte_bswap32(*dst_addr);
-                               ret = local_get_nh_ipv4(dest_address, &dest_if,
-                                                       nhip, p_acl);
-                               if (!ret) {
-                                       dest_if =
-                                           get_pub_to_prv_port(&dest_address,
-                                                               IP_VERSION_4);
-                                       do_local_nh_ipv4_cache(dest_if, p_acl);
-                               };
-                               *port_out_id = p_acl->port_out_id[dest_if];
-                       }
-                       /* port = ACL_PRV_PORT_ID; */
-                       if (get_dest_mac_addr_port
-                           (dest_address, &dest_if, &hw_addr)) {
-                               if (ACL_DEBUG) {
-                                       printf("MAC found for ip 0x%x, port "
-                                       " %d - %02x:%02x:%02x:%02x:%02x:%02x\n",
-                                            dest_address, phy_port,
-                                            hw_addr.addr_bytes[0],
-                                            hw_addr.addr_bytes[1],
-                                            hw_addr.addr_bytes[2],
-                                            hw_addr.addr_bytes[3],
-                                            hw_addr.addr_bytes[4],
-                                            hw_addr.addr_bytes[5]);
-                                       printf("Dest MAC before -  "
-                                       "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                                            eth_dest[0], eth_dest[1],
-                                            eth_dest[2], eth_dest[3],
-                                            eth_dest[4], eth_dest[5]);
-                               }
-                               memcpy(eth_dest, &hw_addr,
-                                      sizeof(struct ether_addr));
-                               if (ACL_DEBUG) {
-                                       printf("PktP %p, dest_macP %p\n", pkt,
-                                              eth_dest);
-                                       printf("Dest MAC after -  "
-                                       "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                                            eth_dest[0], eth_dest[1],
-                                            eth_dest[2], eth_dest[3],
-                                            eth_dest[4], eth_dest[5]);
-                               }
-                               if (is_phy_port_privte(phy_port))
-                                       memcpy(eth_src,
-                                              get_link_hw_addr(dest_if),
-                                              sizeof(struct ether_addr));
-                               else
-                                       memcpy(eth_src,
-                                              get_link_hw_addr(dest_if),
-                                              sizeof(struct ether_addr));
-                               p_acl->counters->tpkts_processed++;
-                               p_acl->counters->bytes_processed +=
-                                   packet_length;
-                       }
-                       else {
-                               if (*nhip != 0) {
-                                       if (ACL_DEBUG)
-                                               printf("ACL requesting ARP for "
-                                                       " ip %x, port %d\n",
-                                                    dest_address, phy_port);
-                                       if (is_phy_port_privte(phy_port))
-                                               request_arp(dest_if, *nhip);
-                                       else
-                                               request_arp(dest_if, *nhip);
-                       /*  request_arp(p_acl->links_map[phy_port], *nhip); */
-                               }
-                               /* Drop packet by changing the mask */
-                               if (ACL_DEBUG)
-                                       printf("ACL before drop pkt_mask  "
-                                               "%lu, pkt_num %d\n",
-                                            pkts_mask, pos);
-                               pkts_mask &= ~(1LLU << pos);
-                               if (ACL_DEBUG)
-                                       printf("ACL after drop pkt_mask  "
-                                               "%lu, pkt_num %d\n",
-                                            pkts_mask, pos);
-                               p_acl->counters->pkts_drop++;
-                       }
-               }
- #endif
  
                if (hdr_chk == IPv6_HDR_VERSION) {
  
                        }
                        memcpy(dest_address, *dst_addr, sizeof(dest_address));
                        memset(nhip, 0, sizeof(nhip));
-                       ret = local_get_nh_ipv6(&dest_address[0], &dest_if,
-                                               &nhip[0], p_acl);
-                       if (is_phy_port_privte(phy_port)) {
-                               if (!ret) {
-                                       dest_if = get_prv_to_pub_port((
-                                                                      uint32_t
-                                                                      *)
-                                             &dest_address[0], IP_VERSION_6);
-                                       do_local_nh_ipv6_cache(dest_if, p_acl);
-                               }
-                               //          port = ACL_PUB_PORT_ID;
-                                       *port_out_id =
-                                           p_acl->port_out_id[dest_if];
+                       struct nd_entry_data *ret_nd_data = NULL;
+                       ret_nd_data = get_dest_mac_address_ipv6_port
+                           (dest_address, &dest_if, &hw_addr, &nhip[0]);
+                       *port_out_id = p_acl->port_out_id[dest_if];
  
+                       if (nd_cache_dest_mac_present(dest_if)) {
+                               ether_addr_copy(get_link_hw_addr(dest_if),
+                                       (struct ether_addr *)eth_src);
+                               update_nhip_access(dest_if);
+                               if (unlikely(ret_nd_data && ret_nd_data->num_pkts)) {
+                                       printf("sending buffered packets\n");
+                                       p_acl->counters->tpkts_processed +=
+                                                ret_nd_data->num_pkts;
+                                       nd_send_buffered_pkts(ret_nd_data,
+                                       (struct ether_addr *)eth_dest, *port_out_id);
+                               }
                        } else {
-                               if (!ret) {
-                                       dest_if = get_pub_to_prv_port((
-                                                                      uint32_t
-                                                                      *)
-                                             &dest_address[0], IP_VERSION_6);
-                                       do_local_nh_ipv6_cache(dest_if, p_acl);
+                               if (unlikely(ret_nd_data == NULL)) {
+                                       if (ACL_DEBUG)
+                                               printf("ACL before drop pkt_mask  "
+                                               "%lu, pkt_num %d\n", pkts_mask, pos);
+                                       pkts_mask &= ~(1LLU << pos);
+                                       if (ACL_DEBUG)
+                                               printf("ACL after drop pkt_mask  "
+                                               "%lu, pkt_num %d\n", pkts_mask, pos);
+                                       p_acl->counters->pkts_drop++;
+                                       continue;
                                }
-                               //           port = ACL_PRV_PORT_ID;
-                                       *port_out_id =
-                                           p_acl->port_out_id[dest_if];
-                       }
  
-                       if (get_dest_mac_address_ipv6_port
-                           (dest_address, &dest_if, &hw_addr, &nhip[0])) {
-                               if (ACL_DEBUG) {
-                                       printf("MAC found for  port %d  "
-                                       "- %02x:%02x:%02x:%02x:%02x:%02x\n",
-                                            phy_port, hw_addr.addr_bytes[0],
-                                            hw_addr.addr_bytes[1],
-                                            hw_addr.addr_bytes[2],
-                                            hw_addr.addr_bytes[3],
-                                            hw_addr.addr_bytes[4],
-                                            hw_addr.addr_bytes[5]);
-                                       printf("Dest MAC before - "
-                                       " %02x:%02x:%02x:%02x:%02x:%02x\n",
-                                            eth_dest[0], eth_dest[1],
-                                            eth_dest[2], eth_dest[3],
-                                            eth_dest[4], eth_dest[5]);
-                               }
-                               memcpy(eth_dest, &hw_addr,
-                                      sizeof(struct ether_addr));
-                               if (ACL_DEBUG) {
-                                       printf("PktP %p, dest_macP %p\n", pkt,
-                                              eth_dest);
-                                       printf("Dest MAC after - "
-                                       " %02x:%02x:%02x:%02x:%02x:%02x\n",
-                                            eth_dest[0], eth_dest[1],
-                                            eth_dest[2], eth_dest[3],
-                                            eth_dest[4], eth_dest[5]);
+                               if (ret_nd_data->status == INCOMPLETE ||
+                                       ret_nd_data->status == PROBE) {
+                                       if (ret_nd_data->num_pkts >= NUM_DESC) {
+                                               /* Drop the pkt */
+                                               if (ACL_DEBUG)
+                                                       printf("ACL before drop pkt_mask  "
+                                                       "%lu, pkt_num %d\n", pkts_mask, pos);
+                                               pkts_mask &= ~(1LLU << pos);
+                                               if (ACL_DEBUG)
+                                                       printf("ACL after drop pkt_mask  "
+                                                       "%lu, pkt_num %d\n", pkts_mask, pos);
+                                               p_acl->counters->pkts_drop++;
+                                               continue;
+                                       } else {
+                                               arp_pkts_mask |= pkt_mask;
+                                               nd_queue_unresolved_packet(ret_nd_data,
+                                                                                pkt);
+                                               continue;
+                                       }
                                }
-                               if (is_phy_port_privte(phy_port))
-                                       memcpy(eth_src,
-                                              get_link_hw_addr(dest_if),
-                                              sizeof(struct ether_addr));
-                               else
-                                       memcpy(eth_src,
-                                              get_link_hw_addr(dest_if),
-                                              sizeof(struct ether_addr));
  
-               /*
-                * memcpy(eth_src, get_link_hw_addr(p_acl->links_map[phy_port]),
-                * sizeof(struct ether_addr));
-                */
-                               p_acl->counters->tpkts_processed++;
-                               p_acl->counters->bytes_processed +=
-                                   packet_length;
                        }
  
-                       else {
- #if 0
-                       /* Request next neighbor for Ipv6 is yet to be done. */
-                       if (*nhip != 0) {
-                       if (ACL_DEBUG)
-                               printf
-                                   ("ACL requesting ARP for ip %x, port %d\n",
-                                                    dest_address, phy_port);
-                       /* request_arp(p_acl->links_map[phy_port], *nhip); */
-                               }
- #endif
-                               /* Drop packet by changing the mask */
-                               if (ACL_DEBUG)
-                                       printf("ACL before drop pkt_mask "
-                                               " %lu, pkt_num %d\n",
-                                            pkts_mask, pos);
-                               pkts_mask &= ~(1LLU << pos);
-                               if (ACL_DEBUG)
-                                       printf("ACL after drop pkt_mask "
-                                               " %lu, pkt_num %d\n",
-                                            pkts_mask, pos);
-                               p_acl->counters->pkts_drop++;
-                       }
                }
  
-       }
+       } /* end of for loop */
  
        pkts_drop_mask = keep_mask & ~pkts_mask;
        rte_pipeline_ah_packet_drop(p, pkts_drop_mask);
@@@ -3130,7 -2806,7 +2806,7 @@@ static void *pipeline_acl_init(struct p
         *  p_acl->links_map[0] = 0xff;
         *  p_acl->links_map[1] = 0xff;]
         */
 -      p_acl->traffic_type = MIX;
 +      p_acl->traffic_type = IPv4_HDR_VERSION;
        for (i = 0; i < PIPELINE_MAX_PORT_IN; i++) {
                p_acl->links_map[i] = 0xff;
                p_acl->port_out_id[i] = 0xff;
@@@ -83,7 -83,7 +83,7 @@@ uint8_t n_cgnapt_pipeline
  struct pipeline_cgnapt *global_pnat;
  
  uint64_t arp_pkts_mask;
- extern struct arp_entry_data *arp_data_ptr[16];
  /* To know egress or ingress port */
  static uint8_t cgnapt_in_port_egress_prv[PIPELINE_MAX_PORT_IN];
  static uint8_t cgnapt_prv_que_port_index[PIPELINE_MAX_PORT_IN];
@@@ -192,10 -192,6 +192,6 @@@ static uint32_t local_get_nh_ipv6
        uint8_t nhip[],
        struct pipeline_cgnapt *p_nat);
  
- static void do_local_nh_ipv6_cache(
-       uint32_t dest_if,
-       struct pipeline_cgnapt *p_nat);
  static uint8_t check_arp_icmp(
        struct rte_mbuf *pkt,
        uint64_t pkt_mask,
@@@ -228,36 -224,6 +224,6 @@@ void remove_local_cache(uint8_t port
        link_hw_laddr_valid[port] = 0;
  }
  
- /**
-  * Function to get MAC addr of local link
-  *
-  * @params out_port
-  *  Physical port number
-  *
-  * @return
-  *  Outport Link MAC addr
-  */
- //struct ether_addr *get_local_link_hw_addr(uint8_t out_port)
- //{
- //    return &link_hw_laddr[out_port];
- //}
- /**
-  * Function to get MAC addr from array instead of hash table
-  *
-  * @params out_port
-  *  Physical port number
-  *
-  * @return
-  *  Outport Link MAC addr
-  */
- uint8_t local_dest_mac_present(uint8_t out_port)
- {
-       return link_hw_laddr_valid[out_port];
- }
  /**
   * Function to get IPv4-IP NH from thread local array
   *
@@@ -308,26 -274,7 +274,7 @@@ static void do_local_nh_ipv4_cache
        uint32_t dest_if,
        struct pipeline_cgnapt *p_nat)
  {
-       /* Search for the entry and do local copy */
-       int i;
-       for (i = 0; i < MAX_ARP_RT_ENTRY; i++) {
-               if (lib_arp_route_table[i].port == dest_if) {
-                       struct lib_arp_route_table_entry *lentry =
-                               &p_nat->local_lib_arp_route_table
-                                       [p_nat->local_lib_arp_route_ent_cnt];
-                       lentry->ip   = lib_arp_route_table[i].ip;
-                       lentry->mask = lib_arp_route_table[i].mask;
-                       lentry->port = lib_arp_route_table[i].port;
-                       lentry->nh   = lib_arp_route_table[i].nh;
-                       p_nat->local_lib_arp_route_ent_cnt++;
-                                               break;
-               }
-       }
+       return;
  }
  
  
@@@ -389,45 -336,6 +336,6 @@@ static uint32_t local_get_nh_ipv6
  }
  
  
- /**
-  * Function to make local copy for NH of type IPv6
-  *
-  * @params dest_if
-  *  Physical port number
-  * @params p_nat
-  *  CGNAPT pipeline ptr
-  *
-  */
- static void do_local_nh_ipv6_cache(
-       uint32_t dest_if,
-       struct pipeline_cgnapt *p_nat)
- {
-               /* Search for the entry and do local copy */
-       int i, l;
-       for (i = 0; i < MAX_ND_RT_ENTRY; i++) {
-               if (lib_nd_route_table[i].port == dest_if) {
-                       struct lib_nd_route_table_entry *lentry =
-                               &p_nat->local_lib_nd_route_table
-                                       [p_nat->local_lib_nd_route_ent_cnt];
-                       for (l = 0; l < 16; l++) {
-                               lentry->ipv6[l]   =
-                                       lib_nd_route_table[i].ipv6[l];
-                               lentry->nhipv6[l] =
-                                       lib_nd_route_table[i].nhipv6[l];
-                       }
-                       lentry->depth = lib_nd_route_table[i].depth;
-                       lentry->port  = lib_nd_route_table[i].port;
-                       p_nat->local_lib_nd_route_ent_cnt++;
-                       break;
-                       } //if
-               } //for
- }
  #ifdef SIP_ALG
  /* Commented code may be required for future usage, Please keep it*/
  #if 0
@@@ -918,7 -826,7 +826,7 @@@ void sw_checksum(struct rte_mbuf *pkt, 
        }
  }
  
- void print_pkt_info(uint8_t *eth_dest, struct ether_addr *hw_addr, 
+ void print_pkt_info(uint8_t *eth_dest, struct ether_addr *hw_addr,
                uint32_t dest_address, uint32_t port_id, struct rte_mbuf *pkt)
  {
  
@@@ -1713,7 -1621,6 +1621,6 @@@ void print_common_table(void
   * @return
   *  int that is not checked by caller
   */
  static int cgnapt_in_port_ah_mix(struct rte_pipeline *rte_p,
                                 struct rte_mbuf **pkts,
                                 uint32_t n_pkts, void *arg)
                        *outport_id = p_nat->outport_id[dest_if];
                        struct arp_entry_data *ret_arp_data;
                        ret_arp_data = get_dest_mac_addr_port(dest_address,
-                               &dest_if, (struct ether_addr *)&hw_addr);
+                               &dest_if, (struct ether_addr *)eth_dest);
  
                        if (unlikely(ret_arp_data == NULL)) {
  
+                               #ifdef CGNAPT_DEBUGGING
                                printf("%s: NHIP Not Found, nhip: %x, "
                                "outport_id: %d\n", __func__, nhip,
                                *outport_id);
+                               #endif
                                /* Drop the pkt */
                                p_nat->invalid_packets |= pkt_mask;
                                p_nat->naptDroppedPktCount++;
                        }
  
                        if (ret_arp_data->status == COMPLETE) {
-                               
                                if (ret_arp_data->num_pkts) {
                                        p_nat->naptedPktCount += ret_arp_data->num_pkts;
                                        arp_send_buffered_pkts(ret_arp_data,
                                        print_pkt(pkts[pkt_index]);
                                #endif
  
-                       } else if (ret_arp_data->status == INCOMPLETE || 
+                       } else if (ret_arp_data->status == INCOMPLETE ||
                                ret_arp_data->status == PROBE) {
                                if (ret_arp_data->num_pkts >= NUM_DESC) {
                                        /* Drop the pkt */
                        memcpy((uint8_t *) &dst_addr[0],
                                         &entry->data.u.prv_ipv6[0], 16);
                        memset(nh_ipv6, 0, 16);
+                       struct nd_entry_data *ret_nd_data = NULL;
+                       ret_nd_data = get_dest_mac_address_ipv6_port((uint8_t *)
+                                 &dst_addr[0], &dest_if,
+                                 &hw_addr, &nh_ipv6[0]);
+                       *outport_id = p_nat->outport_id[dest_if];
  
-                       ret = local_get_nh_ipv6((uint8_t *)&dst_addr[0],
-                               &dest_if, &nh_ipv6[0], p_nat);
+                       if (nd_cache_dest_mac_present(dest_if)) {
+                               ether_addr_copy(get_link_hw_addr(dest_if),
+                                       (struct ether_addr *)eth_src);
+                               update_nhip_access(dest_if);
  
-                       if (!ret) {
-                               dest_if = get_prv_to_pub_port(
-                                               &dst_addr[0],
-                                               IP_VERSION_6);
-                               if (dest_if == INVALID_DESTIF) {
-                                       p_nat->invalid_packets |=
-                                               1LLU << pkt_index;
+                               if (unlikely(ret_nd_data && ret_nd_data->num_pkts)) {
+                                       p_nat->naptedPktCount += ret_nd_data->num_pkts;
+                                       nd_send_buffered_pkts(ret_nd_data,
+                                                (struct ether_addr *)eth_dest,
+                                                *outport_id);
+                               }
+                       } else {
+                               if (unlikely(ret_nd_data == NULL)) {
+                                       #ifdef CGNAPT_DEBUGGING
+                                       printf("%s: NHIP Not Found, "
+                                       "outport_id: %d\n", __func__,
+                                       *outport_id);
+                                       #endif
+                                       /* Drop the pkt */
+                                       p_nat->invalid_packets |= pkt_mask;
                                        p_nat->naptDroppedPktCount++;
                                        #ifdef CGNAPT_DEBUGGING
-                                       p_nat->naptDroppedPktCount6++;
+                                       p_nat->naptDroppedPktCount4++;
                                        #endif
                                        continue;
                                }
-                               do_local_nh_ipv6_cache(dest_if, p_nat);
-                       }
-                       *outport_id = p_nat->outport_id[dest_if];
-                       if (get_dest_mac_address_ipv6_port((uint8_t *)
-                               &dst_addr[0], &dest_if,
-                               &hw_addr, &nh_ipv6[0])){
-                               #ifdef CGNAPT_DBG_PRNT
-                               if (CGNAPT_DEBUG > 2) {
-                               printf("MAC found for ip 0x%x, port %d - "
-                               "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                               dest_address, *outport_id,
-                               hw_addr.addr_bytes[0],
-                               hw_addr.addr_bytes[1], hw_addr.addr_bytes[2],
-                               hw_addr.addr_bytes[3], hw_addr.addr_bytes[4],
-                               hw_addr.addr_bytes[5]);
  
-                               printf("Dest MAC before - "
-                               "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                               eth_dest[0], eth_dest[1], eth_dest[2],
-                               eth_dest[3], eth_dest[4], eth_dest[5]);
+                               if (ret_nd_data->status == INCOMPLETE ||
+                                       ret_nd_data->status == PROBE) {
+                                       if (ret_nd_data->num_pkts >= NUM_DESC) {
+                                               /* Drop the pkt */
+                                               p_nat->invalid_packets |= pkt_mask;
+                                               p_nat->naptDroppedPktCount++;
+                                               #ifdef CGNAPT_DEBUGGING
+                                               p_nat->naptDroppedPktCount4++;
+                                               #endif
+                                               continue;
+                                       } else {
+                                               arp_pkts_mask |= pkt_mask;
+                                               nd_queue_unresolved_packet(ret_nd_data,
+                                                        pkts[pkt_index]);
+                                               continue;
+                                       }
                                }
-                               #endif
-                                       memcpy(eth_dest, &hw_addr,
-                                               sizeof(struct ether_addr));
-                                       memcpy(eth_src, get_link_hw_addr(
-                                               dest_if),
-                                               sizeof(struct ether_addr));
-                       #ifdef CGNAPT_DBG_PRNT
-                       if (CGNAPT_DEBUG > 2) {
-                               printf("Dest MAC after - "
-                               "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                               eth_dest[0], eth_dest[1], eth_dest[2],
-                               eth_dest[3], eth_dest[4], eth_dest[5]);
-                       }
-                       #endif
  
-                       #ifdef CGNAPT_DBG_PRNT
-                       if (CGNAPT_DEBUG > 4)
-                               print_pkt(pkts[pkt_index]);
-                       #endif
-                       } else {
-                               p_nat->invalid_packets |= pkt_mask;
-                               p_nat->naptDroppedPktCount++;
-                               #ifdef CGNAPT_DEBUGGING
-                               p_nat->naptDroppedPktCount4++;
-                               #endif
-                               continue;
                        }
  
                        #ifdef NAT_ONLY_CONFIG_REQ
                                *outport_id = p_nat->outport_id[dest_if];
                                struct arp_entry_data *ret_arp_data;
                                ret_arp_data = get_dest_mac_addr_port(dest_address,
-                                       &dest_if, (struct ether_addr *)&hw_addr);
+                                       &dest_if, (struct ether_addr *)eth_dest);
  
                                if (unlikely(ret_arp_data == NULL)) {
  
+                                       #ifdef CGNAPT_DEBUGGING
                                        printf("%s: NHIP Not Found, nhip: %x, "
                                        "outport_id: %d\n", __func__, nhip,
                                        *outport_id);
+                                       #endif
  
                                        /* Drop the pkt */
                                        p_nat->invalid_packets |= pkt_mask;
                                        printf("MAC found for ip 0x%x, port %d - "
                                        "%02x:%02x:%02x:%02x:%02x:%02x\n",
                                        dest_address, *outport_id,
-                                       hw_addr.addr_bytes[0], hw_addr.addr_bytes[1],
-                                       hw_addr.addr_bytes[2], hw_addr.addr_bytes[3],
-                                       hw_addr.addr_bytes[4], hw_addr.addr_bytes[5]);
+                                       hw_addr.addr_bytes[0], hw_addr.addr_bytes[1],
+                                       hw_addr.addr_bytes[2], hw_addr.addr_bytes[3],
+                                       hw_addr.addr_bytes[4], hw_addr.addr_bytes[5]);
  
                                        printf("Dest MAC before - "
                                        "%02x:%02x:%02x:%02x:%02x:%02x\n",
                                                print_pkt(pkts[pkt_index]);
                                        #endif
  
-                               } else if (ret_arp_data->status == INCOMPLETE || 
+                               } else if (ret_arp_data->status == INCOMPLETE ||
                                        ret_arp_data->status == PROBE) {
                                        arp_queue_unresolved_packet(ret_arp_data,
                                                pkts[pkt_index]);
@@@ -2673,9 -2570,6 +2570,6 @@@ static int cgnapt_in_port_ah_ipv4_prv(s
                                                [p_nat->lkup_indx[j]]);
        }
  
-       //prefetch();
        for (i = 0; i < (n_pkts & (~0x3LLU)); i += 4)
                pkt4_work_cgnapt_ipv4_prv(pkts, i, arg, p_nat);
  
@@@ -3941,15 -3835,14 +3835,14 @@@ pkt_work_cgnapt_ipv4_prv
        dest_address = rte_bswap32(*dst_addr);
        uint32_t nhip = 0;
        struct arp_entry_data *ret_arp_data = NULL;
-       ret_arp_data = get_dest_mac_addr_port(dest_address, &dest_if, (struct ether_addr *)eth_dest);
+       ret_arp_data = get_dest_mac_addr_port(dest_address,
+                &dest_if, (struct ether_addr *)eth_dest);
        *outport_id = p_nat->outport_id[dest_if];
  
        if (arp_cache_dest_mac_present(dest_if)) {
                ether_addr_copy(get_link_hw_addr(dest_if),(struct ether_addr *)eth_src);
-               arp_data_ptr[dest_if]->n_last_update = time(NULL);
+               update_nhip_access(dest_if);
                if (unlikely(ret_arp_data && ret_arp_data->num_pkts)) {
-                       printf("sending buffered packets\n");
                        p_nat->naptedPktCount += ret_arp_data->num_pkts;
                        arp_send_buffered_pkts(ret_arp_data,
                                 (struct ether_addr *)eth_dest, *outport_id);
  
                if (unlikely(ret_arp_data == NULL)) {
  
+                       #ifdef CGNAPT_DEBUGGING
                        printf("%s: NHIP Not Found, nhip:%x , "
                        "outport_id: %d\n", __func__, nhip,
                        *outport_id);
+                       #endif
  
                        /* Drop the pkt */
                        p_nat->invalid_packets |= pkt_mask;
                        return;
                }
  
-               if (ret_arp_data->status == INCOMPLETE || 
+               if (ret_arp_data->status == INCOMPLETE ||
                           ret_arp_data->status == PROBE) {
                                if (ret_arp_data->num_pkts >= NUM_DESC) {
                                        /* Drop the pkt */
@@@ -4288,15 -4183,15 +4183,15 @@@ pkt_work_cgnapt_ipv4_pub
  
        dest_address = entry->data.u.prv_ip;
        struct arp_entry_data *ret_arp_data = NULL;
-       ret_arp_data = get_dest_mac_addr_port(dest_address, &dest_if, (struct ether_addr *)eth_dest);
+       ret_arp_data = get_dest_mac_addr_port(dest_address,
+                &dest_if, (struct ether_addr *)eth_dest);
        *outport_id = p_nat->outport_id[dest_if];
  
        if (arp_cache_dest_mac_present(dest_if)) {
                ether_addr_copy(get_link_hw_addr(dest_if), (struct ether_addr *)eth_src);
-               arp_data_ptr[dest_if]->n_last_update = time(NULL);
+               update_nhip_access(dest_if);
  
                if (ret_arp_data && ret_arp_data->num_pkts) {
-                       printf("sending buffered packets\n");
                        p_nat->naptedPktCount += ret_arp_data->num_pkts;
                        arp_send_buffered_pkts(ret_arp_data,
                                 (struct ether_addr *)eth_dest, *outport_id);
  
                        /* Commented code may be required for debug
                         * and future use, Please keep it */
+                       #ifdef CGNAPT_DEBUGGING
                        printf("%s: NHIP Not Found, nhip: %x, "
                        "outport_id: %d\n", __func__, nhip,
                        *outport_id);
+                       #endif
  
                        /* Drop the pkt */
                        p_nat->invalid_packets |= pkt_mask;
  
                }
  
-               if (ret_arp_data->status == INCOMPLETE || 
+               if (ret_arp_data->status == INCOMPLETE ||
                        ret_arp_data->status == PROBE) {
                        if (ret_arp_data->num_pkts >= NUM_DESC) {
                                /* Drop the pkt */
@@@ -4723,14 -4621,15 +4621,15 @@@ pkt4_work_cgnapt_ipv4_prv
                dest_address = rte_bswap32(*dst_addr);
                struct arp_entry_data *ret_arp_data = NULL;
                uint64_t start, end;
-               ret_arp_data = get_dest_mac_addr_port(dest_address, &dest_if, (struct ether_addr *)eth_dest);
+               ret_arp_data = get_dest_mac_addr_port(dest_address,
+                        &dest_if, (struct ether_addr *)eth_dest);
                *outport_id = p_nat->outport_id[dest_if];
                if (arp_cache_dest_mac_present(dest_if)) {
-                       ether_addr_copy(get_link_hw_addr(dest_if), (struct ether_addr *)eth_src);
-                       arp_data_ptr[dest_if]->n_last_update = time(NULL);
-               
+                       ether_addr_copy(get_link_hw_addr(dest_if),
+                                (struct ether_addr *)eth_src);
+                       update_nhip_access(dest_if);
                        if (ret_arp_data && ret_arp_data->num_pkts) {
-                               printf("sending buffered packets\n");
                                p_nat->naptedPktCount += ret_arp_data->num_pkts;
                                arp_send_buffered_pkts(ret_arp_data,
                                         (struct ether_addr *)eth_dest, *outport_id);
  
                        if (unlikely(ret_arp_data == NULL)) {
  
+                               #ifdef CGNAPT_DEBUGGING
                                printf("%s: ARP Not Found, nhip: %x, "
                                "outport_id: %d\n", __func__, nhip,
                                *outport_id);
+                               #endif
  
                                /* Drop the pkt */
                                p_nat->invalid_packets |= pkt_mask;
  
                        }
  
-                       if (ret_arp_data->status == INCOMPLETE || 
+                       if (ret_arp_data->status == INCOMPLETE ||
                                ret_arp_data->status == PROBE) {
                                if (ret_arp_data->num_pkts >= NUM_DESC) {
                                        /* Drop the pkt */
@@@ -5086,15 -4987,15 +4987,15 @@@ pkt4_work_cgnapt_ipv4_pub
                }
                dest_address = entry->data.u.prv_ip;
                struct arp_entry_data *ret_arp_data = NULL;
-               ret_arp_data = get_dest_mac_addr_port(dest_address, &dest_if, (struct ether_addr *)eth_dest);
+               ret_arp_data = get_dest_mac_addr_port(dest_address,
+                        &dest_if, (struct ether_addr *)eth_dest);
                *outport_id = p_nat->outport_id[dest_if];
  
        if (arp_cache_dest_mac_present(dest_if)) {
                ether_addr_copy(get_link_hw_addr(dest_if), (struct ether_addr *)eth_src);
-               arp_data_ptr[dest_if]->n_last_update = time(NULL);
-               
+               update_nhip_access(dest_if);
                if (ret_arp_data && ret_arp_data->num_pkts) {
-                       printf("sending buffered packets\n");
                        p_nat->naptedPktCount += ret_arp_data->num_pkts;
                        arp_send_buffered_pkts(ret_arp_data,
                                 (struct ether_addr *)eth_dest, *outport_id);
  
                if (unlikely(ret_arp_data == NULL)) {
  
+                       #ifdef CGNAPT_DEBUGGING
                        printf("%s: NHIP Not Found, nhip: %x, "
                        "outport_id: %d\n", __func__, nhip,
                        *outport_id);
+                       #endif
  
                        /* Drop the pkt */
                        p_nat->invalid_packets |= pkt_mask;
                        continue;
                }
  
-               if (ret_arp_data->status == INCOMPLETE || 
+               if (ret_arp_data->status == INCOMPLETE ||
                        ret_arp_data->status == PROBE) {
                        if (ret_arp_data->num_pkts >= NUM_DESC) {
                                /* Drop the pkt */
@@@ -6234,23 -6137,6 +6137,6 @@@ pkt_work_cgnapt_ipv6_prv
                dest_address = rte_bswap32(*dst_addr);
                /*Multiport Changes */
        uint32_t nhip = 0;
-       uint32_t ret;
-       ret = local_get_nh_ipv4(dest_address, &dest_if, &nhip, p_nat);
-       if (!ret) {
-               dest_if = get_prv_to_pub_port(&dest_address, IP_VERSION_4);
-               if (dest_if == INVALID_DESTIF) {
-                       p_nat->invalid_packets |= pkt_mask;
-                       p_nat->naptDroppedPktCount++;
-                       #ifdef CGNAPT_DEBUGGING
-                       p_nat->naptDroppedPktCount6++;
-                       #endif
-                       return;
-               }
-               do_local_nh_ipv4_cache(dest_if, p_nat);
-       }
-               *outport_id = p_nat->outport_id[dest_if];
  
                #ifdef CGNAPT_DBG_PRNT
                if (CGNAPT_DEBUG > 2)
        }
        #endif
  
-       if (local_dest_mac_present(dest_if)) {
-               memcpy(eth_src, get_link_hw_addr(dest_if),
-                               sizeof(struct ether_addr));
+       struct arp_entry_data *ret_arp_data;
+       ret_arp_data = get_dest_mac_addr_port(dest_address,
+                &dest_if, (struct ether_addr *)eth_dest);
+       *outport_id = p_nat->outport_id[dest_if];
+       if (arp_cache_dest_mac_present(dest_if)) {
+               ether_addr_copy(get_link_hw_addr(dest_if),
+                       (struct ether_addr *)eth_src);
+               update_nhip_access(dest_if);
+               if (unlikely(ret_arp_data && ret_arp_data->num_pkts)) {
+                       p_nat->naptedPktCount += ret_arp_data->num_pkts;
+                       arp_send_buffered_pkts(ret_arp_data,
+                                (struct ether_addr *)eth_dest, *outport_id);
+               }
        } else {
-               struct arp_entry_data *ret_arp_data;
-               ret_arp_data = get_dest_mac_addr_port(dest_address, &dest_if, (struct ether_addr *)&hw_addr);
  
                if (unlikely(ret_arp_data == NULL)) {
  
-                       printf("%s: NHIP Not Found, nhip: %x, "
+                       #ifdef CGNAPT_DEBUGGING
+                       printf("%s: NHIP Not Found, nhip:%x , "
                        "outport_id: %d\n", __func__, nhip,
                        *outport_id);
+                       #endif
  
                        /* Drop the pkt */
                        p_nat->invalid_packets |= pkt_mask;
                        return;
                }
  
-               if (ret_arp_data->status == COMPLETE) {
-                       #ifdef CGNAPT_DBG_PRNT
-                       if (CGNAPT_DEBUG > 2) {
-                       printf("MAC found for ip 0x%x, port %d - %02x:%02x: "
-                       "%02x:%02x:%02x:%02x\n", dest_address,
-                       *outport_id,
-                       hw_addr.addr_bytes[0], hw_addr.addr_bytes[1],
-                       hw_addr.addr_bytes[2], hw_addr.addr_bytes[3],
-                       hw_addr.addr_bytes[4], hw_addr.addr_bytes[5]);
-                       printf("Dest MAC before - %02x:%02x:%02x:%02x: "
-                       "%02x:%02x\n", eth_dest[0], eth_dest[1],
-                       eth_dest[2], eth_dest[3],
-                       eth_dest[4], eth_dest[5]);
-                       }
-                       #endif
-                       //memcpy(eth_dest, &hw_addr, sizeof(struct ether_addr));
+               if (ret_arp_data->status == INCOMPLETE ||
+                          ret_arp_data->status == PROBE) {
+                       if (ret_arp_data->num_pkts >= NUM_DESC) {
+                               /* Drop the pkt */
+                               p_nat->invalid_packets |= pkt_mask;
+                               p_nat->naptDroppedPktCount++;
  
-                       #ifdef CGNAPT_DBG_PRNT
-                       if (CGNAPT_DEBUG > 2) {
-                               printf("Dest MAC after - "
-                               "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                               eth_dest[0], eth_dest[1], eth_dest[2], eth_dest[3],
-                               eth_dest[4], eth_dest[5]);
+                               #ifdef CGNAPT_DEBUGGING
+                               p_nat->naptDroppedPktCount4++;
+                               #endif
+                               return;
+                       } else {
+                               arp_pkts_mask |= pkt_mask;
+                               arp_queue_unresolved_packet(ret_arp_data, pkt);
+                               return;
                        }
-                       #endif
-                       memcpy(eth_src, get_link_hw_addr(dest_if),
-                                sizeof(struct ether_addr));
-               } else if (ret_arp_data->status == INCOMPLETE || 
-                       ret_arp_data->status == PROBE) {
-                       arp_queue_unresolved_packet(ret_arp_data,
-                               pkt);
-                       return;
                }
        }
  
@@@ -6454,91 -6332,70 +6332,70 @@@ pkt_work_cgnapt_ipv6_pub
                        #endif
                        return;
                }
-               memcpy(&dest_addr_ipv6[0], &entry->data.u.prv_ipv6[0], 16);
-               uint8_t nhipv6[16];
-               int ret;
-               ret = local_get_nh_ipv6(&dest_addr_ipv6[0], &dest_if,
-                               &nhipv6[0], p_nat);
-               if (!ret) {
-                       dest_if = get_prv_to_pub_port((uint32_t *)
-                                       &dest_addr_ipv6[0],
-                                       IP_VERSION_6);
-               if (dest_if == INVALID_DESTIF) {
-                       p_nat->invalid_packets |= pkt_mask;
-                       p_nat->naptDroppedPktCount++;
-                       #ifdef CGNAPT_DEBUGGING
-                       p_nat->naptDroppedPktCount6++;
-                       #endif
-                       return;
-               }
-                       do_local_nh_ipv6_cache(dest_if, p_nat);
-               }
-               *outport_id = p_nat->outport_id[dest_if];
        }
+       memcpy(&dest_addr_ipv6[0], &entry->data.u.prv_ipv6[0], 16);
+       uint8_t nhipv6[16];
  
-       #ifdef CGNAPT_DEBUGGING
-       static int static_count;
+       memset(nh_ipv6, 0, 16);
+       struct nd_entry_data *ret_nd_data = NULL;
+       ret_nd_data = get_dest_mac_address_ipv6_port(
+                 &dest_addr_ipv6[0],
+                 &dest_if,
+                 (struct ether_addr *)eth_dest,
+                 &nh_ipv6[0]);
  
-       if (static_count++ < 10) {
-               print_pkt(pkt);
-               my_print_entry(entry);
-               printf("dest-offset:%d\n", DST_ADR_OFST_IP4);
-               printf("dest_add:%x\n", entry->data.u.prv_ip);
-               printf("DST_ADR_OFST_IP6:%d\n", DST_ADR_OFST_IP6);
-       }
-       #endif
+       *outport_id = p_nat->outport_id[dest_if];
  
-       memset(nh_ipv6, 0, 16);
-       if (get_dest_mac_address_ipv6_port(
-               &dest_addr_ipv6[0],
-               &dest_if,
-               &hw_addr,
-               &nh_ipv6[0])) {
+       if (nd_cache_dest_mac_present(dest_if)) {
+               ether_addr_copy(get_link_hw_addr(dest_if),
+                       (struct ether_addr *)eth_src);
+               update_nhip_access(dest_if);
+               if (unlikely(ret_nd_data && ret_nd_data->num_pkts)) {
+                       p_nat->naptedPktCount += ret_nd_data->num_pkts;
+                       nd_send_buffered_pkts(ret_nd_data,
+                                (struct ether_addr *)eth_dest, *outport_id);
  
-               #ifdef CGNAPT_DBG_PRNT
-               if (CGNAPT_DEBUG > 2) {
-                       printf("MAC found for ip 0x%x, port %d - "
-                       "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                       *((uint32_t *)dest_addr_ipv6 + 12),
-                       *outport_id,
-                       hw_addr.addr_bytes[0],
-                       hw_addr.addr_bytes[1], hw_addr.addr_bytes[2],
-                       hw_addr.addr_bytes[3], hw_addr.addr_bytes[4],
-                       hw_addr.addr_bytes[5]);
-                       printf("Dest MAC before - "
-                       "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                       eth_dest[0], eth_dest[1], eth_dest[2],
-                       eth_dest[3], eth_dest[4], eth_dest[5]);
                }
-               #endif
+       } else {
+               if (unlikely(ret_nd_data == NULL)) {
  
-               memcpy(eth_dest, &hw_addr, sizeof(struct ether_addr));
+                       #ifdef CGNAPT_DEBUGGING
+                       printf("%s: NHIP Not Found, "
+                       "outport_id: %d\n", __func__,
+                       *outport_id);
+                       #endif
  
-               #ifdef CGNAPT_DBG_PRNT
-               if (CGNAPT_DEBUG > 2) {
-                       printf("Dest MAC after - "
-                       "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                       eth_dest[0], eth_dest[1], eth_dest[2], eth_dest[3],
-                       eth_dest[4], eth_dest[5]);
+                       /* Drop the pkt */
+                       p_nat->invalid_packets |= pkt_mask;
+                       p_nat->naptDroppedPktCount++;
+                       #ifdef CGNAPT_DEBUGGING
+                       p_nat->naptDroppedPktCount4++;
+                       #endif
+                       return;
                }
-               #endif
  
-               memcpy(eth_src, get_link_hw_addr(dest_if),
-                                sizeof(struct ether_addr));
-       } else {
-               p_nat->invalid_packets |= pkt_mask;
-               p_nat->naptDroppedPktCount++;
+               if (ret_nd_data->status == INCOMPLETE ||
+                          ret_nd_data->status == PROBE) {
+                       if (ret_nd_data->num_pkts >= NUM_DESC) {
+                               /* Drop the pkt */
+                               p_nat->invalid_packets |= pkt_mask;
+                               p_nat->naptDroppedPktCount++;
  
-               #ifdef CGNAPT_DEBUGGING
-               p_nat->naptDroppedPktCount4++;
-               #endif
+                               #ifdef CGNAPT_DEBUGGING
+                               p_nat->naptDroppedPktCount4++;
+                               #endif
+                               return;
+                       } else {
+                               arp_pkts_mask |= pkt_mask;
+                               nd_queue_unresolved_packet(ret_nd_data, pkt);
+                               return;
+                       }
+               }
  
-               return;
        }
        /* Ingress */
        {
  
@@@ -6759,23 -6616,6 +6616,6 @@@ pkt4_work_cgnapt_ipv6_prv
                        dest_address = rte_bswap32(*dst_addr);
        uint32_t nhip;
        uint32_t ret;
-       ret = local_get_nh_ipv4(dest_address, &dest_if, &nhip, p_nat);
-       if (!ret) {
-               dest_if = get_prv_to_pub_port(&dest_address, IP_VERSION_4);
-               if (dest_if == INVALID_DESTIF) {
-                       p_nat->invalid_packets |= pkt_mask;
-                       p_nat->naptDroppedPktCount++;
-                       #ifdef CGNAPT_DEBUGGING
-                       p_nat->naptDroppedPktCount6++;
-                       #endif
-                       continue;
-               }
-               do_local_nh_ipv4_cache(dest_if, p_nat);
-       }
-               *outport_id = p_nat->outport_id[dest_if];
                #ifdef CGNAPT_DBG_PRNT
                        if (CGNAPT_DEBUG > 2)
                                printf("Egress: \tphy_port:%d\t"
  
        {
                struct arp_entry_data *ret_arp_data;
-               ret_arp_data = get_dest_mac_addr_port(dest_address, &dest_if, (struct ether_addr *)&hw_addr);
+               ret_arp_data = get_dest_mac_addr_port(dest_address,
+                        &dest_if, (struct ether_addr *)eth_dest);
+               *outport_id = p_nat->outport_id[dest_if];
  
-               if (unlikely(ret_arp_data == NULL)) {
+               if (arp_cache_dest_mac_present(dest_if)) {
+                       ether_addr_copy(get_link_hw_addr(dest_if),
+                               (struct ether_addr *)eth_src);
+                       update_nhip_access(dest_if);
  
-                       printf("%s: NHIP Not Found, nhip: %x, "
-                       "outport_id: %d\n", __func__, nhip,
-                       *outport_id);
+                       if (unlikely(ret_arp_data && ret_arp_data->num_pkts)) {
+                               p_nat->naptedPktCount += ret_arp_data->num_pkts;
+                               arp_send_buffered_pkts(ret_arp_data,
+                                        (struct ether_addr *)eth_dest, *outport_id);
  
-                       /* Drop the pkt */
-                       p_nat->invalid_packets |= pkt_mask;
-                       p_nat->naptDroppedPktCount++;
+                       }
+               } else {
  
-                       #ifdef CGNAPT_DEBUGGING
-                       p_nat->naptDroppedPktCount4++;
-                       #endif
-                       continue;
-               }
+                       if (unlikely(ret_arp_data == NULL)) {
  
-               if (ret_arp_data->status == COMPLETE) {
+                               #ifdef CGNAPT_DEBUGGING
+                               printf("%s: NHIP Not Found, nhip:%x , "
+                               "outport_id: %d\n", __func__, nhip,
+                               *outport_id);
+                               #endif
  
-                       #ifdef CGNAPT_DBG_PRNT
-                       if (CGNAPT_DEBUG > 2) {
-                               printf("MAC found for ip 0x%x, port %d - "
-                               "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                               dest_address, *outport_id,
-                                        hw_addr.addr_bytes[0],
-                                        hw_addr.addr_bytes[1],
-                                        hw_addr.addr_bytes[2],
-                                        hw_addr.addr_bytes[3],
-                                        hw_addr.addr_bytes[4],
-                                        hw_addr.addr_bytes[5]
-                                       );
+                               /* Drop the pkt */
+                               p_nat->invalid_packets |= pkt_mask;
+                               p_nat->naptDroppedPktCount++;
  
-                               printf("Dest MAC before - "
-                               "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                               eth_dest[0], eth_dest[1], eth_dest[2],
-                               eth_dest[3], eth_dest[4], eth_dest[5]);
+                               #ifdef CGNAPT_DEBUGGING
+                               p_nat->naptDroppedPktCount4++;
+                               #endif
+                               return;
                        }
-                       #endif
  
-                       //memcpy(eth_dest, &hw_addr, sizeof(struct ether_addr));
+                       if (ret_arp_data->status == INCOMPLETE ||
+                          ret_arp_data->status == PROBE) {
+                               if (ret_arp_data->num_pkts >= NUM_DESC) {
+                                       /* Drop the pkt */
+                                       p_nat->invalid_packets |= pkt_mask;
+                                       p_nat->naptDroppedPktCount++;
  
-                       #ifdef CGNAPT_DBG_PRNT
-                       if (CGNAPT_DEBUG > 2) {
-                               printf("Dest MAC after - "
-                               "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                               eth_dest[0], eth_dest[1], eth_dest[2],
-                               eth_dest[3], eth_dest[4], eth_dest[5]);
+                                       #ifdef CGNAPT_DEBUGGING
+                                       p_nat->naptDroppedPktCount4++;
+                                       #endif
+                                       return;
+                               } else {
+                                       arp_pkts_mask |= pkt_mask;
+                                       arp_queue_unresolved_packet(ret_arp_data, pkt);
+                                       return;
+                               }
                        }
-                       #endif
  
-                       memcpy(eth_src, get_link_hw_addr(dest_if),
-                                        sizeof(struct ether_addr));
-               } else if (ret_arp_data->status == INCOMPLETE || 
-                       ret_arp_data->status == PROBE) {
-                       arp_queue_unresolved_packet(ret_arp_data,
-                               pkt);
-                       continue;
                }
        }
  
@@@ -6991,26 -6826,6 +6826,6 @@@ pkt4_work_cgnapt_ipv6_pub
                        memcpy(&dest_addr_ipv6[0], &entry->data.u.prv_ipv6[0],
                                         16);
                        uint8_t nhipv6[16];
-                       int ret;
-                       ret = local_get_nh_ipv6(&dest_addr_ipv6[0], &dest_if,
-                               &nhipv6[0], p_nat);
-                       if (!ret) {
-                               dest_if = get_prv_to_pub_port((uint32_t *)
-                                       &dest_addr_ipv6[0], IP_VERSION_6);
-                               if (dest_if == INVALID_DESTIF) {
-                                       p_nat->invalid_packets |= pkt_mask;
-                                       p_nat->naptDroppedPktCount++;
-                                       #ifdef CGNAPT_DEBUGGING
-                                       p_nat->naptDroppedPktCount6++;
-                                       #endif
-                                       return;
-                               }
-                               do_local_nh_ipv6_cache(dest_if, p_nat);
-                       }
-                       *outport_id = p_nat->outport_id[dest_if];
                }/* end of ingress */
  
                #ifdef CGNAPT_DEBUGGING
                #endif
  
                memset(nh_ipv6, 0, 16);
-               if (get_dest_mac_address_ipv6
-                       (&dest_addr_ipv6[0], &dest_if,
-                        &hw_addr, &nh_ipv6[0])) {
-                       #ifdef CGNAPT_DBG_PRNT
-                       if (CGNAPT_DEBUG > 2) {
-                               printf("MAC found for ip 0x%x, port %d - "
-                               "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                               *((uint32_t *)dest_addr_ipv6 + 12),
-                               *outport_id,
-                               hw_addr.addr_bytes[0], hw_addr.addr_bytes[1],
-                               hw_addr.addr_bytes[2], hw_addr.addr_bytes[3],
-                               hw_addr.addr_bytes[4], hw_addr.addr_bytes[5]);
+               struct nd_entry_data *ret_nd_data = NULL;
+               ret_nd_data = get_dest_mac_address_ipv6_port
+                               (&dest_addr_ipv6[0], &dest_if,
+                               (struct ether_addr *)eth_dest, &nh_ipv6[0]);
  
-                               printf("Dest MAC before - "
-                               "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                               eth_dest[0], eth_dest[1], eth_dest[2],
-                               eth_dest[3], eth_dest[4], eth_dest[5]);
+               *outport_id = p_nat->outport_id[dest_if];
+               if (nd_cache_dest_mac_present(dest_if)) {
+                       ether_addr_copy(get_link_hw_addr(dest_if),
+                               (struct ether_addr *)eth_src);
+                       update_nhip_access(dest_if);
+                       if (unlikely(ret_nd_data && ret_nd_data->num_pkts)) {
+                               p_nat->naptedPktCount += ret_nd_data->num_pkts;
+                               nd_send_buffered_pkts(ret_nd_data,
+                                (struct ether_addr *)eth_dest, *outport_id);
                        }
-                       #endif
+               } else {
+                       if (unlikely(ret_nd_data == NULL)) {
+                               #ifdef CGNAPT_DEBUGGING
+                               printf("%s: NHIP Not Found "
+                               "outport_id: %d\n", __func__,
+                               *outport_id);
+                               #endif
  
-                       memcpy(eth_dest, &hw_addr, sizeof(struct ether_addr));
+                               /* Drop the pkt */
+                               p_nat->invalid_packets |= pkt_mask;
+                               p_nat->naptDroppedPktCount++;
  
-                       #ifdef CGNAPT_DBG_PRNT
-                       if (CGNAPT_DEBUG > 2) {
-                               printf("Dest MAC after - "
-                               "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                               eth_dest[0], eth_dest[1], eth_dest[2],
-                               eth_dest[3], eth_dest[4], eth_dest[5]);
+                               #ifdef CGNAPT_DEBUGGING
+                               p_nat->naptDroppedPktCount4++;
+                               #endif
+                               continue;
                        }
-                       #endif
  
-                       memcpy(eth_src,
-                                        get_link_hw_addr(dest_if),
-                                        sizeof(struct ether_addr));
-               } else {
-                       p_nat->invalid_packets |= pkt_mask;
-                       p_nat->naptDroppedPktCount++;
+                       if (ret_nd_data->status == INCOMPLETE ||
+                                  ret_nd_data->status == PROBE) {
  
-                       #ifdef CGNAPT_DEBUGGING
-                       p_nat->naptDroppedPktCount4++;
-                       #endif
+                               if (ret_nd_data->num_pkts >= NUM_DESC) {
+                                       /* Drop the pkt */
+                                       p_nat->invalid_packets |= pkt_mask;
+                                       p_nat->naptDroppedPktCount++;
+                                       #ifdef CGNAPT_DEBUGGING
+                                       p_nat->naptDroppedPktCount4++;
+                                       #endif
+                                       continue;
+                               } else {
+                                       arp_pkts_mask |= pkt_mask;
+                                       nd_queue_unresolved_packet(ret_nd_data, pkt);
+                                       continue;
+                               }
+                       }
  
-                       continue;
                }
  
                {
@@@ -7142,6 -6969,7 +6969,7 @@@ static int cgnapt_in_port_ah_ipv6_prv(s
        p_nat->pkt_burst_cnt = 0;       /* for dynamic napt */
        p_nat->valid_packets = rte_p->pkts_mask;        /*n_pkts; */
        p_nat->invalid_packets = 0;
+       arp_pkts_mask = 0;
  
        #ifdef CGNAPT_DBG_PRNT
        if (CGNAPT_DEBUG > 1)
  
        p_nat->valid_packets &= ~(p_nat->invalid_packets);
  
+       if (arp_pkts_mask) {
+               p_nat->valid_packets &= ~(arp_pkts_mask);
+               rte_pipeline_ah_packet_hijack(rte_p, arp_pkts_mask);
+       }
        if (unlikely(p_nat->valid_packets == 0)) {
                /* no suitable packet for lookup */
                rte_pipeline_ah_packet_drop(rte_p, p_nat->invalid_packets);
@@@ -7255,6 -7088,7 +7088,7 @@@ static int cgnapt_in_port_ah_ipv6_pub(s
        p_nat->pkt_burst_cnt = 0;       /* for dynamic napt */
        p_nat->valid_packets = rte_p->pkts_mask;        /*n_pkts; */
        p_nat->invalid_packets = 0;
+       arp_pkts_mask = 0;
  
        #ifdef CGNAPT_DBG_PRNT
        if (CGNAPT_DEBUG > 1)
  
        p_nat->valid_packets &= ~(p_nat->invalid_packets);
  
+       if (arp_pkts_mask) {
+               p_nat->valid_packets &= ~(arp_pkts_mask);
+               rte_pipeline_ah_packet_hijack(rte_p, arp_pkts_mask);
+       }
        if (unlikely(p_nat->valid_packets == 0)) {
                /* no suitable packet for lookup */
                rte_pipeline_ah_packet_drop(rte_p, p_nat->invalid_packets);
@@@ -8374,7 -8213,7 +8213,7 @@@ static void *pipeline_cgnapt_init(struc
        p_nat->hw_checksum_reqd = 0;
        p_nat->pub_ip_port_set = NULL;
        p_nat->pub_ip_count = 0;
 -      p_nat->traffic_type = TRAFFIC_TYPE_MIX;
 +      p_nat->traffic_type = TRAFFIC_TYPE_IPV4;
        p_nat->vnf_set = 0xff;
  
        /* For every init it should be reset */
@@@ -9184,11 -9023,6 +9023,6 @@@ pipeline_cgnapt_msg_req_entry_addm_pair
        }
        #endif
  
-       //if (CGNAPT_DEBUG > 2)
-               //printf("key.ip %x, key.port %d", key.ip, key.port);
-               //printf("key.pid %d, in_type %d,", key.pid, type);
-               //printf("entry_type %d\n", entry.data.type);
        int32_t position = rte_hash_add_key(napt_common_table, &key);
  
        if (position < 0) {
@@@ -68,7 -68,7 +68,7 @@@
  uint32_t timer_lcore;
  
  uint8_t firewall_flag = 1;
- uint8_t VFW_DEBUG;
+ uint8_t VFW_DEBUG = 0;
  uint8_t cnxn_tracking_is_active = 1;
  /**
   * A structure defining the VFW pipeline input port per thread data.
@@@ -142,7 -142,7 +142,7 @@@ struct mbuf_tcp_meta_data 
  
  #define IP_VERSION_4 4
  #define IP_VERSION_6 6
 -#define MIX 10
 +
  /* IPv6 */
  #define IP_HDR_SIZE_IPV6  40
  #define IP_HDR_DSCP_OFST_IPV6 0
@@@ -176,32 -176,6 +176,6 @@@ __rte_cache_aligned
    * TODO: look into "stub" table and see if that can be used
    * to avoid useless table lookup
    */
- /***** ARP local cache *****/
- #if 0
- uint8_t link_hw_laddr_valid[MAX_NUM_LOCAL_MAC_ADDRESS] = {
-        0, 0, 0, 0, 0, 0, 0, 0,
-        0, 0, 0, 0, 0, 0, 0, 0
- };
- static struct ether_addr link_hw_laddr[MAX_NUM_LOCAL_MAC_ADDRESS] = {
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} },
-        {.addr_bytes = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00} }
- };
- #endif
  uint64_t arp_pkts_mask;
  
  /* Start TSC measurement */
@@@ -231,142 -205,6 +205,6 @@@ static inline void end_tsc_measure
         }
  }
  
- //static struct ether_addr *get_local_link_hw_addr(uint8_t out_port)
- //{
- //       return &link_hw_laddr[out_port];
- //}
- #if 0
- static uint8_t local_dest_mac_present(uint8_t out_port)
- {
-        return link_hw_laddr_valid[out_port];
- }
- static uint32_t local_get_nh_ipv4(
-        uint32_t ip,
-        uint32_t *port,
-        uint32_t *nhip,
-        struct pipeline_vfw *vfw_pipe)
- {
-        int i;
-        for (i = 0; i < vfw_pipe->local_lib_arp_route_ent_cnt; i++) {
-               if (((vfw_pipe->local_lib_arp_route_table[i].ip &
-               vfw_pipe->local_lib_arp_route_table[i].mask) ==
-               (ip & vfw_pipe->local_lib_arp_route_table[i].mask))) {
-                      *port = vfw_pipe->local_lib_arp_route_table[i].port;
-                      *nhip = vfw_pipe->local_lib_arp_route_table[i].nh;
-                      return 1;
-               }
-        }
-        return 0;
- }
- static void do_local_nh_ipv4_cache(uint32_t dest_if,
-               struct pipeline_vfw *vfw_pipe)
- {
-        /* Search for the entry and do local copy */
-        int i;
-        for (i = 0; i < MAX_ARP_RT_ENTRY; i++) {
-               if (lib_arp_route_table[i].port == dest_if) {
-                      struct lib_arp_route_table_entry *lentry =
-                             &vfw_pipe->
-                             local_lib_arp_route_table[vfw_pipe->
-                             local_lib_arp_route_ent_cnt];
-                      lentry->ip   = lib_arp_route_table[i].ip;
-                      lentry->mask = lib_arp_route_table[i].mask;
-                      lentry->port = lib_arp_route_table[i].port;
-                      lentry->nh   = lib_arp_route_table[i].nh;
-                      vfw_pipe->local_lib_arp_route_ent_cnt++;
-                      break;
-               }
-        }
- }
- #endif
- static uint32_t local_get_nh_ipv6(
-        uint8_t *ip,
-        uint32_t *port,
-        uint8_t nhip[],
-         struct pipeline_vfw *vfw_pipe)
- {
-        uint8_t netmask_ipv6[IPV6_ADD_SIZE], netip_nd[IPV6_ADD_SIZE],
-               netip_in[IPV6_ADD_SIZE];
-        uint8_t i = 0, j = 0, k = 0, l = 0, depthflags = 0, depthflags1 = 0;
-        memset(netmask_ipv6, 0, sizeof(netmask_ipv6));
-        memset(netip_nd, 0, sizeof(netip_nd));
-        memset(netip_in, 0, sizeof(netip_in));
-        for (i = 0; i < vfw_pipe->local_lib_nd_route_ent_cnt; i++) {
-               convert_prefixlen_to_netmask_ipv6(
-                      vfw_pipe->local_lib_nd_route_table[i].depth,
-                      netmask_ipv6);
-               for (k = 0; k < IPV6_ADD_SIZE; k++)
-                      if (vfw_pipe->local_lib_nd_route_table[i].ipv6[k] &
-                                    netmask_ipv6[k]) {
-                             depthflags++;
-                             netip_nd[k] = vfw_pipe->
-                                    local_lib_nd_route_table[i].ipv6[k];
-                      }
-               for (l = 0; l < IPV6_ADD_SIZE; l++)
-                      if (ip[l] & netmask_ipv6[l]) {
-                             depthflags1++;
-                             netip_in[l] = ip[l];
-                      }
-               if ((depthflags == depthflags1) && (memcmp(netip_nd, netip_in,
-                                           sizeof(netip_nd)) == 0)) {
-                      *port = vfw_pipe->local_lib_nd_route_table[i].port;
-                      for (j = 0; j < IPV6_ADD_SIZE; j++)
-                             nhip[j] = vfw_pipe->
-                                    local_lib_nd_route_table[i].nhipv6[j];
-                      return 1;
-               }
-               depthflags = 0;
-               depthflags1 = 0;
-                      }
-                      return 0;
- }
- static void do_local_nh_ipv6_cache(uint32_t dest_if,
-               struct pipeline_vfw *vfw_pipe)
- {
-               /* Search for the entry and do local copy */
-        int i, l;
-        for (i = 0; i < MAX_ND_RT_ENTRY; i++) {
-               if (lib_nd_route_table[i].port == dest_if) {
-                      struct lib_nd_route_table_entry *lentry = &vfw_pipe->
-                             local_lib_nd_route_table[vfw_pipe->
-                             local_lib_nd_route_ent_cnt];
-                      for (l = 0; l < IPV6_ADD_SIZE; l++) {
-                             lentry->ipv6[l]   =
-                                    lib_nd_route_table[i].ipv6[l];
-                             lentry->nhipv6[l] =
-                                    lib_nd_route_table[i].nhipv6[l];
-                      }
-                      lentry->depth = lib_nd_route_table[i].depth;
-                      lentry->port  = lib_nd_route_table[i].port;
-                      vfw_pipe->local_lib_nd_route_ent_cnt++;
-                      break;
-                      } /* if */
-               } /* for */
- }
  /**
   * Print packet for debugging.
   *
@@@ -929,85 -767,16 +767,16 @@@ pkt4_work_vfw_arp_ipv4_packets(struct r
                uint32_t dest_address = rte_bswap32(ihdr->dst_addr);
                if (must_reverse)
                       rte_sp_exchange_mac_addresses(ehdr);
- #if 0
-               ret = local_get_nh_ipv4(dest_address, &dest_if,
-                             &nhip, vfw_pipe);
-               if (must_reverse) {
-                      rte_sp_exchange_mac_addresses(ehdr);
-                      if (is_phy_port_privte(phy_port)) {
-                             if (!ret) {
-                                    dest_if = get_pub_to_prv_port(
-                                                  &dest_address,
-                                                  IP_VERSION_4);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           *pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv4_cache(
-                                                  dest_if, vfw_pipe);
-                             }
-                      } else {
-                             if (!ret) {
-                                    dest_if = get_prv_to_pub_port(
-                                                  &dest_address,
-                                                  IP_VERSION_4);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           *pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv4_cache(dest_if,
-                                                  vfw_pipe);
-                             }
-                      }
-               } else if (is_phy_port_privte(phy_port)) {
-                      if (!ret) {
-                             dest_if = get_prv_to_pub_port(&dest_address,
-                                           IP_VERSION_4);
-                             if (dest_if == INVALID_DESTIF) {
-                                    *pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv4_cache(dest_if, vfw_pipe);
-                      }
-               } else {
-                      if (!ret) {
-                             dest_if = get_pub_to_prv_port(&dest_address,
-                                           IP_VERSION_4);
-                             if (dest_if == INVALID_DESTIF) {
-                                    *pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv4_cache(dest_if, vfw_pipe);
-                      }
  
-               }
-               meta_data_addr->output_port =  vfw_pipe->outport_id[dest_if];
-               if (local_dest_mac_present(dest_if)) {
-                      ether_addr_copy(get_local_link_hw_addr(dest_if),
-                                    &ehdr->d_addr);
-                      ether_addr_copy(get_link_hw_addr(dest_if),
-                                    &ehdr->s_addr);
-               } else {
- #endif
        struct arp_entry_data *ret_arp_data = NULL;
          ret_arp_data = get_dest_mac_addr_port(dest_address,
                         &dest_if, &ehdr->d_addr);
          meta_data_addr->output_port =  vfw_pipe->outport_id[dest_if];
  
          if (arp_cache_dest_mac_present(dest_if)) {
                  ether_addr_copy(get_link_hw_addr(dest_if), &ehdr->s_addr);
-                 arp_data_ptr[dest_if]->n_last_update = time(NULL);
+               update_nhip_access(dest_if);
                  if (unlikely(ret_arp_data && ret_arp_data->num_pkts)) {
-                         printf("sending buffered packets\n");
                          arp_send_buffered_pkts(ret_arp_data,
                                   &ehdr->d_addr, vfw_pipe->outport_id[dest_if]);
  
  
                       } else {
                  if (unlikely(ret_arp_data == NULL)) {
+                       if (VFW_DEBUG)
                          printf("%s: NHIP Not Found, nhip:%x , "
                          "outport_id: %d\n", __func__, nhip,
                          vfw_pipe->outport_id[dest_if]);
                if (ret_arp_data->status == INCOMPLETE ||
                             ret_arp_data->status == PROBE) {
                                  if (ret_arp_data->num_pkts >= NUM_DESC) {
-                             /* ICMP req sent, drop packet by
-                              * changing the mask */
-                               vfw_pipe->counters->
-                                        pkts_drop_without_arp_entry++;
+                                       /* ICMP req sent, drop packet by
+                                               * changing the mask */
+                                       vfw_pipe->counters->pkts_drop_without_arp_entry++;
                                          continue;
                                  } else {
                                          arp_pkts_mask |= pkt_mask;
@@@ -1096,92 -864,24 +864,24 @@@ pkt_work_vfw_arp_ipv4_packets(struct rt
                if (must_reverse)
                       rte_sp_exchange_mac_addresses(ehdr);
  
- #if 0
-               ret = local_get_nh_ipv4(dest_address, &dest_if,
-                             &nhip, vfw_pipe);
-               if (must_reverse) {
-                      rte_sp_exchange_mac_addresses(ehdr);
-                      if (is_phy_port_privte(phy_port)) {
-                             if (!ret) {
-                                    dest_if = get_pub_to_prv_port(
-                                                  &dest_address,
-                                                  IP_VERSION_4);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           *pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv4_cache(
-                                                  dest_if, vfw_pipe);
-                             }
-                      } else {
-                             if (!ret) {
-                                    dest_if = get_prv_to_pub_port(
-                                                  &dest_address,
-                                                  IP_VERSION_4);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           *pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv4_cache(dest_if,
-                                                  vfw_pipe);
-                             }
-                      }
-               } else if (is_phy_port_privte(phy_port)) {
-                      if (!ret) {
-                             dest_if = get_prv_to_pub_port(&dest_address,
-                                           IP_VERSION_4);
-                             if (dest_if == INVALID_DESTIF) {
-                                    *pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv4_cache(dest_if, vfw_pipe);
-                      }
-               } else {
-                      if (!ret) {
-                             dest_if = get_pub_to_prv_port(&dest_address,
-                                           IP_VERSION_4);
-                             if (dest_if == INVALID_DESTIF) {
-                                    *pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv4_cache(dest_if, vfw_pipe);
-                      }
-               }
-               meta_data_addr->output_port =  vfw_pipe->outport_id[dest_if];
-               if (local_dest_mac_present(dest_if)) {
-                      ether_addr_copy(get_local_link_hw_addr(dest_if),
-                                    &ehdr->d_addr);
-                      ether_addr_copy(get_link_hw_addr(dest_if),
-                                    &ehdr->s_addr);
-               } else {
- #endif
        struct arp_entry_data *ret_arp_data = NULL;
                       ret_arp_data = get_dest_mac_addr_port(dest_address,
                                     &dest_if, &ehdr->d_addr);
-                               meta_data_addr->output_port =  vfw_pipe->outport_id[dest_if];
+                       meta_data_addr->output_port =  vfw_pipe->outport_id[dest_if];
          if (arp_cache_dest_mac_present(dest_if)) {
  
                  ether_addr_copy(get_link_hw_addr(dest_if), &ehdr->s_addr);
-                 arp_data_ptr[dest_if]->n_last_update = time(NULL);
+               update_nhip_access(dest_if);
                  if (unlikely(ret_arp_data && ret_arp_data->num_pkts)) {
-                         printf("sending buffered packets\n");
                          arp_send_buffered_pkts(ret_arp_data,
                                   &ehdr->d_addr, vfw_pipe->outport_id[dest_if]);
  
                              }
                       } else {
                  if (unlikely(ret_arp_data == NULL)) {
  
+                       if (VFW_DEBUG)
                          printf("%s: NHIP Not Found, nhip:%x , "
                          "outport_id: %d\n", __func__, nhip,
                          vfw_pipe->outport_id[dest_if]);
                if (ret_arp_data->status == INCOMPLETE ||
                             ret_arp_data->status == PROBE) {
                                  if (ret_arp_data->num_pkts >= NUM_DESC) {
-                             /* ICMP req sent, drop packet by
-                              * changing the mask */
-                                       vfw_pipe->counters->
-                                               pkts_drop_without_arp_entry++;
+                                       /* ICMP req sent, drop packet by
+                                               * changing the mask */
+                                       vfw_pipe->counters->pkts_drop_without_arp_entry++;
                                          return;
                                  } else {
                                          arp_pkts_mask |= pkt_mask;
@@@ -1237,12 -936,10 +936,10 @@@ pkt4_work_vfw_arp_ipv6_packets(struct r
                struct pipeline_vfw *vfw_pipe)
  {
         uint8_t nh_ipv6[IPV6_ADD_SIZE];
-        uint32_t ret;
         struct ether_addr hw_addr;
         struct mbuf_tcp_meta_data *meta_data_addr;
         struct ether_hdr *ehdr;
         struct rte_mbuf *pkt;
-        uint16_t phy_port;
         uint8_t i;
  
         for (i = 0; i < 4; i++) {
                       continue;
                int must_reverse = ((synproxy_reply_mask & pkt_mask) != 0);
  
-               phy_port = pkt->port;
                meta_data_addr = (struct mbuf_tcp_meta_data *)
                       RTE_MBUF_METADATA_UINT32_PTR(pkt, META_DATA_OFFSET);
                ehdr = rte_vfw_get_ether_addr(pkt);
                uint8_t dest_address[IPV6_ADD_SIZE];
  
                memset(nhip, 0, IPV6_ADD_SIZE);
-               rte_mov16(dest_address, ihdr->dst_addr);
-               ret = local_get_nh_ipv6(&dest_address[0], &dest_if,
-                             &nhip[0], vfw_pipe);
-               if (must_reverse) {
+               if (must_reverse)
                       rte_sp_exchange_mac_addresses(ehdr);
-                      if (is_phy_port_privte(phy_port)) {
-                             if (!ret) {
-                                    dest_if = get_pub_to_prv_port(
-                                                  (uint32_t *)
-                                                  &dest_address[0],
-                                                  IP_VERSION_6);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           *pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv6_cache(dest_if,
-                                                  vfw_pipe);
-                             }
-                      } else {
-                             if (!ret) {
-                                    dest_if = get_prv_to_pub_port(
-                                                  (uint32_t *)
-                                                  &dest_address[0],
-                                                  IP_VERSION_6);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           *pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv6_cache(dest_if,
-                                                  vfw_pipe);
-                             }
-                      }
-               } else if (is_phy_port_privte(phy_port)) {
-                      if (!ret) {
-                             dest_if = get_prv_to_pub_port((uint32_t *)
-                                           &dest_address[0], IP_VERSION_6);
-                             if (dest_if == INVALID_DESTIF) {
-                                    *pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv6_cache(dest_if, vfw_pipe);
-                      }
-               } else {
-                      if (!ret) {
-                             dest_if = get_pub_to_prv_port((uint32_t *)
-                                           &dest_address[0], IP_VERSION_6);
-                             if (dest_if == INVALID_DESTIF) {
-                                    *pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv6_cache(dest_if, vfw_pipe);
-                      }
-               }
-               meta_data_addr->output_port = vfw_pipe->outport_id[dest_if];
  
+               rte_mov16(dest_address, ihdr->dst_addr);
                memset(nh_ipv6, 0, IPV6_ADD_SIZE);
-               if (get_dest_mac_address_ipv6_port(
+               struct nd_entry_data *ret_nd_data = NULL;
+               ret_nd_data = get_dest_mac_address_ipv6_port(
                                     &dest_address[0],
                                     &dest_if,
                                     &hw_addr,
-                                    &nh_ipv6[0])) {
-                      ether_addr_copy(&hw_addr, &ehdr->d_addr);
-                      ether_addr_copy(get_link_hw_addr(dest_if),
-                                    &ehdr->s_addr);
+                                    &nh_ipv6[0]);
  
-                      if (vfw_debug >= DEBUG_LEVEL_4) {
-                             char buf[HW_ADDR_SIZE];
-                             ether_format_addr(buf, sizeof(buf),
-                                           &hw_addr);
-                             printf("MAC found for  dest_if %d: %s, ",
-                                           dest_if, buf);
-                             ether_format_addr(buf, sizeof(buf),
-                                           &ehdr->s_addr);
-                             printf("new eth hdr src: %s, ", buf);
-                             ether_format_addr(buf, sizeof(buf),
-                                           &ehdr->d_addr);
-                             printf("new eth hdr dst: %s\n", buf);
-                      }
+               meta_data_addr->output_port = vfw_pipe->
+                                     outport_id[dest_if];
+               if (nd_cache_dest_mac_present(dest_if)) {
+                     ether_addr_copy(get_link_hw_addr(dest_if),
+                                    &ehdr->s_addr);
+                   update_nhip_access(dest_if);
  
+                     if (unlikely(ret_nd_data && ret_nd_data->num_pkts)) {
+                         nd_send_buffered_pkts(ret_nd_data,
+                               &ehdr->d_addr, meta_data_addr->output_port);
+                     }
                } else {
-                      printf("deleting ipv6\n");
-                      *pkts_mask &= ~pkt_mask;
-                      /*Next Neighbor is not yet implemented
-                       * for ipv6.*/
-                      vfw_pipe->counters->
-                             pkts_drop_without_arp_entry++;
+                     if (unlikely(ret_nd_data == NULL)) {
+                          *pkts_mask &= ~pkt_mask;
+                         vfw_pipe->counters->
+                               pkts_drop_without_arp_entry++;
+                           continue;
+                     }
+                   if (ret_nd_data->status == INCOMPLETE ||
+                         ret_nd_data->status == PROBE) {
+                         if (ret_nd_data->num_pkts >= NUM_DESC) {
+                                 /* Drop the pkt */
+                                 *pkts_mask &= ~pkt_mask;
+                               vfw_pipe->counters->pkts_drop_without_arp_entry++;
+                               continue;
+                           } else {
+                                 arp_pkts_mask |= pkt_mask;
+                                 nd_queue_unresolved_packet(ret_nd_data, pkt);
+                                 continue;
+                           }
+                     }
                }
  
         }
@@@ -1399,12 -1040,10 +1040,10 @@@ pkt_work_vfw_arp_ipv6_packets(struct rt
                struct pipeline_vfw *vfw_pipe)
  {
         uint8_t nh_ipv6[IPV6_ADD_SIZE];
-        uint32_t ret;
         struct ether_addr hw_addr;
         struct mbuf_tcp_meta_data *meta_data_addr;
         struct ether_hdr *ehdr;
         struct rte_mbuf *pkt;
-        uint16_t phy_port;
  
         uint32_t dest_if = INVALID_DESTIF;
         /* bitmask representing only this packet */
  
                int must_reverse = ((synproxy_reply_mask & pkt_mask) != 0);
  
-               phy_port = pkt->port;
                meta_data_addr = (struct mbuf_tcp_meta_data *)
                       RTE_MBUF_METADATA_UINT32_PTR(pkt, META_DATA_OFFSET);
                ehdr = rte_vfw_get_ether_addr(pkt);
                uint8_t dest_address[IPV6_ADD_SIZE];
  
                memset(nhip, 0, IPV6_ADD_SIZE);
-               rte_mov16(dest_address, ihdr->dst_addr);
-               ret = local_get_nh_ipv6(&dest_address[0], &dest_if,
-                             &nhip[0], vfw_pipe);
-               if (must_reverse) {
+               if (must_reverse)
                       rte_sp_exchange_mac_addresses(ehdr);
-                      if (is_phy_port_privte(phy_port)) {
-                             if (!ret) {
-                                    dest_if = get_pub_to_prv_port(
-                                                  (uint32_t *)
-                                                  &dest_address[0],
-                                                  IP_VERSION_6);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           *pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv6_cache(dest_if,
-                                                  vfw_pipe);
-                             }
-                      } else {
-                             if (!ret) {
-                                    dest_if = get_prv_to_pub_port(
-                                                  (uint32_t *)
-                                                  &dest_address[0],
-                                                  IP_VERSION_6);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           *pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv6_cache(dest_if,
-                                                  vfw_pipe);
-                             }
-                      }
-               } else if (is_phy_port_privte(phy_port)) {
-                      if (!ret) {
-                             dest_if = get_prv_to_pub_port((uint32_t *)
-                                           &dest_address[0], IP_VERSION_6);
-                             if (dest_if == INVALID_DESTIF) {
-                                    *pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv6_cache(dest_if, vfw_pipe);
-                      }
-               } else {
-                      if (!ret) {
-                             dest_if = get_pub_to_prv_port((uint32_t *)
-                                           &dest_address[0], IP_VERSION_6);
-                             if (dest_if == INVALID_DESTIF) {
-                                    *pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv6_cache(dest_if, vfw_pipe);
-                      }
-               }
-               meta_data_addr->output_port = vfw_pipe->outport_id[dest_if];
+               rte_mov16(dest_address, ihdr->dst_addr);
                memset(nh_ipv6, 0, IPV6_ADD_SIZE);
-               if (get_dest_mac_address_ipv6_port(
+               struct nd_entry_data *ret_nd_data = NULL;
+               ret_nd_data = get_dest_mac_address_ipv6_port(
                                     &dest_address[0],
                                     &dest_if,
                                     &hw_addr,
-                                    &nh_ipv6[0])) {
-                      ether_addr_copy(&hw_addr, &ehdr->d_addr);
+                                    &nh_ipv6[0]);
+             meta_data_addr->output_port = vfw_pipe->
+                                     outport_id[dest_if];
+               if (nd_cache_dest_mac_present(dest_if)) {
                       ether_addr_copy(get_link_hw_addr(dest_if),
                                     &ehdr->s_addr);
+                   update_nhip_access(dest_if);
  
-                      if (vfw_debug >= DEBUG_LEVEL_4) {
-                             char buf[HW_ADDR_SIZE];
-                             ether_format_addr(buf, sizeof(buf),
-                                           &hw_addr);
-                             printf("MAC found for  dest_if %d: %s, ",
-                                           dest_if, buf);
-                             ether_format_addr(buf, sizeof(buf),
-                                           &ehdr->s_addr);
-                             printf("new eth hdr src: %s, ", buf);
-                             ether_format_addr(buf, sizeof(buf),
-                                           &ehdr->d_addr);
-                             printf("new eth hdr dst: %s\n", buf);
+                     if (unlikely(ret_nd_data && ret_nd_data->num_pkts)) {
+                         nd_send_buffered_pkts(ret_nd_data,
+                               &ehdr->d_addr, meta_data_addr->output_port);
                       }
                } else {
-                      printf("deleting ipv6\n");
-                      *pkts_mask &= ~pkt_mask;
-                      /*Next Neighbor is not yet implemented
-                       * for ipv6.*/
-                      vfw_pipe->counters->
-                             pkts_drop_without_arp_entry++;
+                     if (unlikely(ret_nd_data == NULL)) {
+                         *pkts_mask &= ~pkt_mask;
+                       vfw_pipe->counters->
+                               pkts_drop_without_arp_entry++;
+                         return;
+                     }
+                   if (ret_nd_data->status == INCOMPLETE ||
+                           ret_nd_data->status == PROBE) {
+                           if (ret_nd_data->num_pkts >= NUM_DESC) {
+                                 /* Drop the pkt */
+                                 *pkts_mask &= ~pkt_mask;
+                               vfw_pipe->counters->pkts_drop_without_arp_entry++;
+                                 return;
+                           } else {
+                                 arp_pkts_mask |= pkt_mask;
+                                 nd_queue_unresolved_packet(ret_nd_data, pkt);
+                                 return;
+                           }
+                     }
                }
  
         }
@@@ -1588,85 -1169,16 +1169,16 @@@ rte_vfw_arp_ipv4_packets(struct rte_mbu
                uint32_t dest_address = rte_bswap32(ihdr->dst_addr);
                if (must_reverse)
                       rte_sp_exchange_mac_addresses(ehdr);
- #if 0
-               ret = local_get_nh_ipv4(dest_address, &dest_if,
-                             &nhip, vfw_pipe);
-               if (must_reverse) {
-                      rte_sp_exchange_mac_addresses(ehdr);
-                      if (is_phy_port_privte(phy_port)) {
-                             if (!ret) {
-                                    dest_if = get_pub_to_prv_port(
-                                                  &dest_address,
-                                                  IP_VERSION_4);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv4_cache(
-                                                  dest_if, vfw_pipe);
-                             }
-                      } else {
-                             if (!ret) {
-                                    dest_if = get_prv_to_pub_port(
-                                                  &dest_address,
-                                                  IP_VERSION_4);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv4_cache(dest_if,
-                                                  vfw_pipe);
-                             }
-                      }
-               } else if (is_phy_port_privte(phy_port)) {
-                      if (!ret) {
-                             dest_if = get_prv_to_pub_port(&dest_address,
-                                           IP_VERSION_4);
-                             if (dest_if == INVALID_DESTIF) {
-                                    pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv4_cache(dest_if, vfw_pipe);
-                      }
-               } else {
-                      if (!ret) {
-                             dest_if = get_pub_to_prv_port(&dest_address,
-                                           IP_VERSION_4);
-                             if (dest_if == INVALID_DESTIF) {
-                                    pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv4_cache(dest_if, vfw_pipe);
-                      }
-               }
-               meta_data_addr->output_port =  vfw_pipe->outport_id[dest_if];
-               if (local_dest_mac_present(dest_if)) {
-                      ether_addr_copy(get_local_link_hw_addr(dest_if),
-                                    &ehdr->d_addr);
-                      ether_addr_copy(get_link_hw_addr(dest_if),
-                                    &ehdr->s_addr);
-               } else {
- #endif
                struct arp_entry_data *ret_arp_data = NULL;
                       ret_arp_data = get_dest_mac_addr_port(dest_address,
                                     &dest_if, &ehdr->d_addr);
-                       meta_data_addr->output_port =  vfw_pipe->outport_id[dest_if];
+               meta_data_addr->output_port =  vfw_pipe->outport_id[dest_if];
          if (arp_cache_dest_mac_present(dest_if)) {
  
                  ether_addr_copy(get_link_hw_addr(dest_if), &ehdr->s_addr);
-                 arp_data_ptr[dest_if]->n_last_update = time(NULL);
+               update_nhip_access(dest_if);
                  if (unlikely(ret_arp_data && ret_arp_data->num_pkts)) {
  
-                         printf("sending buffered packets\n");
-                         p_nat->naptedPktCount += ret_arp_data->num_pkts;
                          arp_send_buffered_pkts(ret_arp_data,
                                   &ehdr->d_addr, vfw_pipe->outport_id[dest_if]);
  
                       } else {
                  if (unlikely(ret_arp_data == NULL)) {
  
+                       if (VFW_DEBUG)
                          printf("%s: NHIP Not Found, nhip:%x , "
                          "outport_id: %d\n", __func__, nhip,
                          vfw_pipe->outport_id[dest_if]);
                if (ret_arp_data->status == INCOMPLETE ||
                             ret_arp_data->status == PROBE) {
                                  if (ret_arp_data->num_pkts >= NUM_DESC) {
-                      /* ICMP req sent, drop packet by
-                       * changing the mask */
-                                       vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
+                                       /* ICMP req sent, drop packet by
+                                               * changing the mask */
+                                       vfw_pipe->counters->pkts_drop_without_arp_entry++;
                                          continue;
                                  } else {
                                          arp_pkts_mask |= pkt_mask;
@@@ -1759,106 -1271,52 +1271,52 @@@ rte_vfw_arp_ipv6_packets(struct rte_mbu
                uint8_t dest_address[IPV6_ADD_SIZE];
  
                memset(nhip, 0, IPV6_ADD_SIZE);
-               rte_mov16(dest_address, ihdr->dst_addr);
-               ret = local_get_nh_ipv6(&dest_address[0], &dest_if,
-                             &nhip[0], vfw_pipe);
-               if (must_reverse) {
+               if (must_reverse)
                       rte_sp_exchange_mac_addresses(ehdr);
-                      if (is_phy_port_privte(phy_port)) {
-                             if (!ret) {
-                                    dest_if = get_pub_to_prv_port(
-                                                  (uint32_t *)
-                                                  &dest_address[0],
-                                                  IP_VERSION_6);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv6_cache(dest_if,
-                                                  vfw_pipe);
-                             }
-                      } else {
-                             if (!ret) {
-                                    dest_if = get_prv_to_pub_port(
-                                                  (uint32_t *)
-                                                  &dest_address[0],
-                                                  IP_VERSION_6);
-                                    if (dest_if == INVALID_DESTIF) {
-                                           pkts_mask &= ~pkt_mask;
-                                           vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                                    }
-                                    do_local_nh_ipv6_cache(dest_if,
-                                                  vfw_pipe);
-                             }
-                      }
-               } else if (is_phy_port_privte(phy_port)) {
-                      if (!ret) {
-                             dest_if = get_prv_to_pub_port((uint32_t *)
-                                           &dest_address[0], IP_VERSION_6);
-                             if (dest_if == INVALID_DESTIF) {
-                                    pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv6_cache(dest_if, vfw_pipe);
-                      }
-               } else {
-                      if (!ret) {
-                             dest_if = get_pub_to_prv_port((uint32_t *)
-                                           &dest_address[0], IP_VERSION_6);
-                             if (dest_if == INVALID_DESTIF) {
-                                    pkts_mask &= ~pkt_mask;
-                                    vfw_pipe->counters->
-                                           pkts_drop_without_arp_entry++;
-                             }
-                             do_local_nh_ipv6_cache(dest_if, vfw_pipe);
-                      }
-               }
-               meta_data_addr->output_port = vfw_pipe->outport_id[dest_if];
  
+               rte_mov16(dest_address, ihdr->dst_addr);
                memset(nh_ipv6, 0, IPV6_ADD_SIZE);
-               if (get_dest_mac_address_ipv6_port(
+               struct nd_entry_data *ret_nd_data = NULL;
+               ret_nd_data = get_dest_mac_address_ipv6_port(
                                     &dest_address[0],
                                     &dest_if,
                                     &hw_addr,
-                                    &nh_ipv6[0])) {
-                      ether_addr_copy(&hw_addr, &ehdr->d_addr);
+                                    &nh_ipv6[0]);
+             meta_data_addr->output_port = vfw_pipe->
+                                     outport_id[dest_if];
+               if (nd_cache_dest_mac_present(dest_if)) {
                       ether_addr_copy(get_link_hw_addr(dest_if),
                                     &ehdr->s_addr);
+                   update_nhip_access(dest_if);
  
-                      if (vfw_debug >= DEBUG_LEVEL_4) {
-                             char buf[HW_ADDR_SIZE];
-                             ether_format_addr(buf, sizeof(buf),
-                                           &hw_addr);
-                             printf("MAC found for  dest_if %d: %s, ",
-                                           dest_if, buf);
-                             ether_format_addr(buf, sizeof(buf),
-                                           &ehdr->s_addr);
-                             printf("new eth hdr src: %s, ", buf);
-                             ether_format_addr(buf, sizeof(buf),
-                                           &ehdr->d_addr);
-                             printf("new eth hdr dst: %s\n", buf);
+                     if (unlikely(ret_nd_data && ret_nd_data->num_pkts)) {
+                         nd_send_buffered_pkts(ret_nd_data,
+                                &ehdr->d_addr, meta_data_addr->output_port);
                       }
  
                } else {
-                      printf("deleting ipv6\n");
+                     if (unlikely(ret_nd_data == NULL)) {
                       pkts_mask &= ~pkt_mask;
-                      /*Next Neighbor is not yet implemented
-                       * for ipv6.*/
-                      vfw_pipe->counters->
-                             pkts_drop_without_arp_entry++;
-               }
+                         vfw_pipe->counters->
+                               pkts_drop_without_arp_entry++;
+                           continue;
+                     }
+                   if (ret_nd_data->status == INCOMPLETE ||
+                           ret_nd_data->status == PROBE) {
+                           if (ret_nd_data->num_pkts >= NUM_DESC) {
+                                 /* Drop the pkt */
+                               pkts_mask &= ~pkt_mask;
+                                 vfw_pipe->counters->
+                                     pkts_drop_without_arp_entry++;
+                                 continue;
+                           } else {
+                                 arp_pkts_mask |= pkt_mask;
+                                 nd_queue_unresolved_packet(ret_nd_data, pkt);
+                                 continue;
+                           }
+                     }
+             }
  
         }
  
@@@ -2548,7 -2006,7 +2006,7 @@@ static voi
         strncpy(pipe->name, params->name, sizeof(pipe->name));
         pipe->log_level = params->log_level;
         pipe_vfw->n_flows = 4096;       /* small default value */
 -       pipe_vfw->traffic_type = MIX;
 +       pipe_vfw->traffic_type = IP_VERSION_4;
         pipe_vfw->pipeline_num = 0xff;
         for (i = 0; i < PIPELINE_MAX_PORT_IN; i++) {
                pipe_vfw->links_map[i] = 0xff;