diff --git a/src/vnet/srv6/sr_localsid.c b/src/vnet/srv6/sr_localsid.c
new file mode 100755
index 0000000..bdc6638
--- /dev/null
+++ b/src/vnet/srv6/sr_localsid.c
@@ -0,0 +1,1492 @@
+/*
+ * sr_localsid.c: ipv6 segment routing Endpoint behaviors
+ *
+ * Copyright (c) 2016 Cisco and/or its affiliates.
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * @file
+ * @brief Processing of packets with a SRH
+ *
+ * CLI to define new Segment Routing End processing functions.
+ * Graph node to support such functions.
+ *
+ * Each function associates an SRv6 segment (IPv6 address) with an specific
+ * Segment Routing function.
+ *
+ */
+
+#include <vlib/vlib.h>
+#include <vnet/vnet.h>
+#include <vnet/srv6/sr.h>
+#include <vnet/ip/ip.h>
+#include <vnet/srv6/sr_packet.h>
+#include <vnet/ip/ip6_packet.h>
+#include <vnet/fib/ip6_fib.h>
+#include <vnet/dpo/dpo.h>
+#include <vnet/adj/adj.h>
+
+#include <vppinfra/error.h>
+#include <vppinfra/elog.h>
+
+/**
+ * @brief Dynamically added SR localsid DPO type
+ */
+static dpo_type_t sr_localsid_dpo_type;
+static dpo_type_t sr_localsid_d_dpo_type;
+
+/**
+ * @brief SR localsid add/del
+ *
+ * Function to add or delete SR LocalSIDs.
+ *
+ * @param is_del Boolean of whether its a delete instruction
+ * @param localsid_addr IPv6 address of the localsid
+ * @param is_decap Boolean of whether decapsulation is allowed in this function
+ * @param behavior Type of behavior (function) for this localsid
+ * @param sw_if_index Only for L2/L3 xconnect. OIF. In VRF variant the fib_table.
+ * @param vlan_index Only for L2 xconnect. Outgoing VLAN tag.
+ * @param fib_table  FIB table in which we should install the localsid entry
+ * @param nh_addr Next Hop IPv4/IPv6 address. Only for L2/L3 xconnect.
+ *
+ * @return 0 on success, error otherwise.
+ */
+int
+sr_cli_localsid (char is_del, ip6_address_t * localsid_addr,
+		 char end_psp, u8 behavior, u32 sw_if_index, u32 vlan_index,
+		 u32 fib_table, ip46_address_t * nh_addr, void *ls_plugin_mem)
+{
+  ip6_sr_main_t *sm = &sr_main;
+  uword *p;
+  int rv;
+
+  ip6_sr_localsid_t *ls = 0;
+
+  dpo_id_t dpo = DPO_INVALID;
+
+  /* Search for the item */
+  p = mhash_get (&sm->sr_localsids_index_hash, localsid_addr);
+
+  if (p)
+    {
+      if (is_del)
+	{
+	  /* Retrieve localsid */
+	  ls = pool_elt_at_index (sm->localsids, p[0]);
+	  /* Delete FIB entry */
+	  fib_prefix_t pfx = {
+	    .fp_proto = FIB_PROTOCOL_IP6,
+	    .fp_len = 128,
+	    .fp_addr = {
+			.ip6 = *localsid_addr,
+			}
+	  };
+
+	  fib_table_entry_delete (fib_table_find (FIB_PROTOCOL_IP6,
+						  fib_table),
+				  &pfx, FIB_SOURCE_SR);
+
+	  /* In case it is a Xconnect iface remove the (OIF, NHOP) adj */
+	  if (ls->behavior == SR_BEHAVIOR_X || ls->behavior == SR_BEHAVIOR_DX6
+	      || ls->behavior == SR_BEHAVIOR_DX4)
+	    adj_unlock (ls->nh_adj);
+
+	  if (ls->behavior >= SR_BEHAVIOR_LAST)
+	    {
+	      sr_localsid_fn_registration_t *plugin = 0;
+	      plugin = pool_elt_at_index (sm->plugin_functions,
+					  ls->behavior - SR_BEHAVIOR_LAST);
+
+	      /* Callback plugin removal function */
+	      rv = plugin->removal (ls);
+	    }
+
+	  /* Delete localsid registry */
+	  pool_put (sm->localsids, ls);
+	  mhash_unset (&sm->sr_localsids_index_hash, localsid_addr, NULL);
+	  return 1;
+	}
+      else			/* create with function already existing; complain */
+	return -1;
+    }
+  else
+    /* delete; localsid does not exist; complain */
+  if (is_del)
+    return -2;
+
+  /* Check whether there exists a FIB entry with such address */
+  fib_prefix_t pfx = {
+    .fp_proto = FIB_PROTOCOL_IP6,
+    .fp_len = 128,
+  };
+
+  pfx.fp_addr.as_u64[0] = localsid_addr->as_u64[0];
+  pfx.fp_addr.as_u64[1] = localsid_addr->as_u64[1];
+
+  /* Lookup the FIB index associated to the table id provided */
+  u32 fib_index = fib_table_find (FIB_PROTOCOL_IP6, fib_table);
+  if (fib_index == ~0)
+    return -3;
+
+  /* Lookup the localsid in such FIB table */
+  fib_node_index_t fei = fib_table_lookup_exact_match (fib_index, &pfx);
+  if (FIB_NODE_INDEX_INVALID != fei)
+    return -4;			//There is an entry for such address (the localsid addr)
+
+  /* Create a new localsid registry */
+  pool_get (sm->localsids, ls);
+  memset (ls, 0, sizeof (*ls));
+
+  clib_memcpy (&ls->localsid, localsid_addr, sizeof (ip6_address_t));
+  ls->end_psp = end_psp;
+  ls->behavior = behavior;
+  ls->nh_adj = (u32) ~ 0;
+  ls->fib_table = fib_table;
+  switch (behavior)
+    {
+    case SR_BEHAVIOR_END:
+      break;
+    case SR_BEHAVIOR_X:
+      ls->sw_if_index = sw_if_index;
+      clib_memcpy (&ls->next_hop.ip6, &nh_addr->ip6, sizeof (ip6_address_t));
+      break;
+    case SR_BEHAVIOR_DX4:
+      ls->sw_if_index = sw_if_index;
+      clib_memcpy (&ls->next_hop.ip4, &nh_addr->ip4, sizeof (ip4_address_t));
+      break;
+    case SR_BEHAVIOR_DX6:
+      ls->sw_if_index = sw_if_index;
+      clib_memcpy (&ls->next_hop.ip6, &nh_addr->ip6, sizeof (ip6_address_t));
+      break;
+    case SR_BEHAVIOR_DT6:
+      ls->vrf_index = sw_if_index;
+      break;
+    case SR_BEHAVIOR_DX2:
+      ls->sw_if_index = sw_if_index;
+      ls->vlan_index = vlan_index;
+      break;
+    }
+
+  /* Figure out the adjacency magic for Xconnect variants */
+  if (ls->behavior == SR_BEHAVIOR_X || ls->behavior == SR_BEHAVIOR_DX4
+      || ls->behavior == SR_BEHAVIOR_DX6)
+    {
+      adj_index_t nh_adj_index = ADJ_INDEX_INVALID;
+
+      /* Retrieve the adjacency corresponding to the (OIF, next_hop) */
+      if (ls->behavior == SR_BEHAVIOR_DX6 || ls->behavior == SR_BEHAVIOR_X)
+	nh_adj_index = adj_nbr_add_or_lock (FIB_PROTOCOL_IP6, VNET_LINK_IP6,
+					    nh_addr, sw_if_index);
+
+      else if (ls->behavior == SR_BEHAVIOR_DX4)
+	nh_adj_index = adj_nbr_add_or_lock (FIB_PROTOCOL_IP4, VNET_LINK_IP4,
+					    nh_addr, sw_if_index);
+
+      /* Check for ADJ creation error. If so panic */
+      if (nh_adj_index == ADJ_INDEX_INVALID)
+	{
+	  pool_put (sm->localsids, ls);
+	  return -5;
+	}
+
+      ls->nh_adj = nh_adj_index;
+    }
+
+  /* Set DPO */
+  if (ls->behavior == SR_BEHAVIOR_END || ls->behavior == SR_BEHAVIOR_X)
+    dpo_set (&dpo, sr_localsid_dpo_type, DPO_PROTO_IP6, ls - sm->localsids);
+  else if (ls->behavior > SR_BEHAVIOR_D_FIRST
+	   && ls->behavior < SR_BEHAVIOR_LAST)
+    dpo_set (&dpo, sr_localsid_d_dpo_type, DPO_PROTO_IP6, ls - sm->localsids);
+  else if (ls->behavior >= SR_BEHAVIOR_LAST)
+    {
+      sr_localsid_fn_registration_t *plugin = 0;
+      plugin = pool_elt_at_index (sm->plugin_functions,
+				  ls->behavior - SR_BEHAVIOR_LAST);
+      /* Copy the unformat memory result */
+      ls->plugin_mem = ls_plugin_mem;
+      /* Callback plugin creation function */
+      rv = plugin->creation (ls);
+      if (rv)
+	{
+	  pool_put (sm->localsids, ls);
+	  return -6;
+	}
+      dpo_set (&dpo, plugin->dpo, DPO_PROTO_IP6, ls - sm->localsids);
+    }
+
+  /* Set hash key for searching localsid by address */
+  mhash_set (&sm->sr_localsids_index_hash, localsid_addr, ls - sm->localsids,
+	     NULL);
+
+  fib_table_entry_special_dpo_add (fib_index, &pfx, FIB_SOURCE_SR,
+				   FIB_ENTRY_FLAG_EXCLUSIVE, &dpo);
+  dpo_reset (&dpo);
+
+  /* Set counter to zero */
+  vlib_validate_combined_counter (&(sm->sr_ls_valid_counters),
+				  ls - sm->localsids);
+  vlib_validate_combined_counter (&(sm->sr_ls_invalid_counters),
+				  ls - sm->localsids);
+
+  vlib_zero_combined_counter (&(sm->sr_ls_valid_counters),
+			      ls - sm->localsids);
+  vlib_zero_combined_counter (&(sm->sr_ls_invalid_counters),
+			      ls - sm->localsids);
+
+  return 0;
+}
+
+/**
+ * @brief SR LocalSID CLI function.
+ *
+ * @see sr_cli_localsid
+ */
+static clib_error_t *
+sr_cli_localsid_command_fn (vlib_main_t * vm, unformat_input_t * input,
+			    vlib_cli_command_t * cmd)
+{
+  vnet_main_t *vnm = vnet_get_main ();
+  ip6_sr_main_t *sm = &sr_main;
+  u32 sw_if_index = (u32) ~ 0, vlan_index = (u32) ~ 0, fib_index = 0;
+  int is_del = 0;
+  int end_psp = 0;
+  ip6_address_t resulting_address;
+  ip46_address_t next_hop;
+  char address_set = 0;
+  char behavior = 0;
+  void *ls_plugin_mem = 0;
+
+  int rv;
+
+  memset (&resulting_address, 0, sizeof (ip6_address_t));
+  ip46_address_reset (&next_hop);
+
+  while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
+    {
+      if (unformat (input, "del"))
+	is_del = 1;
+      else if (!address_set
+	       && unformat (input, "address %U", unformat_ip6_address,
+			    &resulting_address))
+	address_set = 1;
+      else if (!address_set
+	       && unformat (input, "addr %U", unformat_ip6_address,
+			    &resulting_address))
+	address_set = 1;
+      else if (unformat (input, "fib-table %u", &fib_index));
+      else if (vlan_index == (u32) ~ 0
+	       && unformat (input, "vlan %u", &vlan_index));
+      else if (!behavior && unformat (input, "behavior"))
+	{
+	  if (unformat (input, "end.x %U %U",
+			unformat_vnet_sw_interface, vnm, &sw_if_index,
+			unformat_ip6_address, &next_hop.ip6))
+	    behavior = SR_BEHAVIOR_X;
+	  else if (unformat (input, "end.dx6 %U %U",
+			     unformat_vnet_sw_interface, vnm, &sw_if_index,
+			     unformat_ip6_address, &next_hop.ip6))
+	    behavior = SR_BEHAVIOR_DX6;
+	  else if (unformat (input, "end.dx4 %U %U",
+			     unformat_vnet_sw_interface, vnm, &sw_if_index,
+			     unformat_ip4_address, &next_hop.ip4))
+	    behavior = SR_BEHAVIOR_DX4;
+	  else if (unformat (input, "end.dx2 %U",
+			     unformat_vnet_sw_interface, vnm, &sw_if_index))
+	    behavior = SR_BEHAVIOR_DX2;
+	  else if (unformat (input, "end.dt6 %u", &sw_if_index))
+	    behavior = SR_BEHAVIOR_DT6;
+	  else if (unformat (input, "end.dt4 %u", &sw_if_index))
+	    behavior = SR_BEHAVIOR_DT4;
+	  else
+	    {
+	      /* Loop over all the plugin behavior format functions */
+	      sr_localsid_fn_registration_t *plugin = 0, **vec_plugins = 0;
+	      sr_localsid_fn_registration_t **plugin_it = 0;
+
+	      /* Create a vector out of the plugin pool as recommended */
+        /* *INDENT-OFF* */
+        pool_foreach (plugin, sm->plugin_functions,
+        {
+          vec_add1 (vec_plugins, plugin);
+        });
+        /* *INDENT-ON* */
+
+	      vec_foreach (plugin_it, vec_plugins)
+	      {
+		if (unformat
+		    (input, "%U", (*plugin_it)->ls_unformat, &ls_plugin_mem))
+		  {
+		    behavior = (*plugin_it)->sr_localsid_function_number;
+		    break;
+		  }
+	      }
+	    }
+
+	  if (!behavior)
+	    {
+	      if (unformat (input, "end"))
+		behavior = SR_BEHAVIOR_END;
+	      else
+		break;
+	    }
+	}
+      else if (!end_psp && unformat (input, "psp"))
+	end_psp = 1;
+      else
+	break;
+    }
+
+  if (!behavior && end_psp)
+    behavior = SR_BEHAVIOR_END;
+
+  if (!address_set)
+    return clib_error_return (0,
+			      "Error: SRv6 LocalSID address is mandatory.");
+  if (!is_del && !behavior)
+    return clib_error_return (0,
+			      "Error: SRv6 LocalSID behavior is mandatory.");
+  if (vlan_index != (u32) ~ 0)
+    return clib_error_return (0,
+			      "Error: SRv6 End.DX2 with rewrite VLAN tag not supported by now.");
+  if (end_psp && !(behavior == SR_BEHAVIOR_END || behavior == SR_BEHAVIOR_X))
+    return clib_error_return (0,
+			      "Error: SRv6 PSP only compatible with End and End.X");
+
+  rv = sr_cli_localsid (is_del, &resulting_address, end_psp, behavior,
+			sw_if_index, vlan_index, fib_index, &next_hop,
+			ls_plugin_mem);
+
+  switch (rv)
+    {
+    case 0:
+      break;
+    case 1:
+      return 0;
+    case -1:
+      return clib_error_return (0,
+				"Identical localsid already exists. Requested localsid not created.");
+    case -2:
+      return clib_error_return (0,
+				"The requested localsid could not be deleted. SR localsid not found");
+    case -3:
+      return clib_error_return (0, "FIB table %u does not exist", fib_index);
+    case -4:
+      return clib_error_return (0, "There is already one FIB entry for the"
+				"requested localsid non segment routing related");
+    case -5:
+      return clib_error_return (0,
+				"Could not create ARP/ND entry for such next_hop. Internal error.");
+    case -6:
+      return clib_error_return (0,
+				"Error on the plugin based localsid creation.");
+    default:
+      return clib_error_return (0, "BUG: sr localsid returns %d", rv);
+    }
+  return 0;
+}
+
+/* *INDENT-OFF* */
+VLIB_CLI_COMMAND (sr_localsid_command, static) = {
+  .path = "sr localsid",
+  .short_help = "sr localsid (del) address XX:XX::YY:YY"
+      "(fib-table 8) behavior STRING",
+  .long_help =
+    "Create SR LocalSID and binds it to a particular behavior\n"
+    "Arguments:\n"
+    "\tlocalSID IPv6_addr(128b)   LocalSID IPv6 address\n"
+    "\t(fib-table X)              Optional. VRF where to install SRv6 localsid\n"
+    "\tbehavior STRING            Specifies the behavior\n"
+    "\n\tBehaviors:\n"
+    "\tEnd\t-> Endpoint.\n"
+    "\tEnd.X\t-> Endpoint with decapsulation and Layer-3 cross-connect.\n"
+    "\t\tParameters: '<iface> <ip6_next_hop>'\n"
+    "\tEnd.DX2\t-> Endpoint with decapsulation and Layer-2 cross-connect.\n"
+    "\t\tParameters: '<iface>'\n"
+    "\tEnd.DX6\t-> Endpoint with decapsulation and IPv6 cross-connect.\n"
+    "\t\tParameters: '<iface> <ip6_next_hop>'\n"
+    "\tEnd.DX4\t-> Endpoint with decapsulation and IPv4 cross-connect.\n"
+    "\t\tParameters: '<iface> <ip4_next_hop>'\n"
+    "\tEnd.DT6\t-> Endpoint with decapsulation and specific IPv6 table lookup.\n"
+    "\t\tParameters: '<ip6_fib_table>'\n"
+    "\tEnd.DT4\t-> Endpoint with decapsulation and specific IPv4 table lookup.\n"
+    "\t\tParameters: '<ip4_fib_table>'\n",
+  .function = sr_cli_localsid_command_fn,
+};
+/* *INDENT-ON* */
+
+/**
+ * @brief CLI function to 'show' all SR LocalSIDs on console.
+ */
+static clib_error_t *
+show_sr_localsid_command_fn (vlib_main_t * vm, unformat_input_t * input,
+			     vlib_cli_command_t * cmd)
+{
+  vnet_main_t *vnm = vnet_get_main ();
+  ip6_sr_main_t *sm = &sr_main;
+  ip6_sr_localsid_t **localsid_list = 0;
+  ip6_sr_localsid_t *ls;
+  int i;
+
+  vlib_cli_output (vm, "SRv6 - My LocalSID Table:");
+  vlib_cli_output (vm, "=========================");
+  /* *INDENT-OFF* */
+  pool_foreach (ls, sm->localsids, ({ vec_add1 (localsid_list, ls); }));
+  /* *INDENT-ON* */
+  for (i = 0; i < vec_len (localsid_list); i++)
+    {
+      ls = localsid_list[i];
+      switch (ls->behavior)
+	{
+	case SR_BEHAVIOR_END:
+	  vlib_cli_output (vm, "\tAddress: \t%U\n\tBehavior: \tEnd",
+			   format_ip6_address, &ls->localsid);
+	  break;
+	case SR_BEHAVIOR_X:
+	  vlib_cli_output (vm,
+			   "\tAddress: \t%U\n\tBehavior: \tX (Endpoint with Layer-3 cross-connect)"
+			   "\n\tIface:  \t%U\n\tNext hop: \t%U",
+			   format_ip6_address, &ls->localsid,
+			   format_vnet_sw_if_index_name, vnm, ls->sw_if_index,
+			   format_ip6_address, &ls->next_hop.ip6);
+	  break;
+	case SR_BEHAVIOR_DX4:
+	  vlib_cli_output (vm,
+			   "\tAddress: \t%U\n\tBehavior: \tDX4 (Endpoint with decapsulation and IPv4 cross-connect)"
+			   "\n\tIface:  \t%U\n\tNext hop: \t%U",
+			   format_ip6_address, &ls->localsid,
+			   format_vnet_sw_if_index_name, vnm, ls->sw_if_index,
+			   format_ip4_address, &ls->next_hop.ip4);
+	  break;
+	case SR_BEHAVIOR_DX6:
+	  vlib_cli_output (vm,
+			   "\tAddress: \t%U\n\tBehavior: \tDX6 (Endpoint with decapsulation and IPv6 cross-connect)"
+			   "\n\tIface:  \t%U\n\tNext hop: \t%U",
+			   format_ip6_address, &ls->localsid,
+			   format_vnet_sw_if_index_name, vnm, ls->sw_if_index,
+			   format_ip6_address, &ls->next_hop.ip6);
+	  break;
+	case SR_BEHAVIOR_DX2:
+	  if (ls->vlan_index == (u32) ~ 0)
+	    vlib_cli_output (vm,
+			     "\tAddress: \t%U\n\tBehavior: \tDX2 (Endpoint with decapulation and Layer-2 cross-connect)"
+			     "\n\tIface:  \t%U", format_ip6_address,
+			     &ls->localsid, format_vnet_sw_if_index_name, vnm,
+			     ls->sw_if_index);
+	  else
+	    vlib_cli_output (vm,
+			     "Unsupported yet. (DX2 with egress VLAN rewrite)");
+	  break;
+	case SR_BEHAVIOR_DT6:
+	  vlib_cli_output (vm,
+			   "\tAddress: \t%U\n\tBehavior: \tDT6 (Endpoint with decapsulation and specific IPv6 table lookup)"
+			   "\n\tTable: %u", format_ip6_address, &ls->localsid,
+			   ls->fib_table);
+	  break;
+	case SR_BEHAVIOR_DT4:
+	  vlib_cli_output (vm,
+			   "\tAddress: \t%U\n\tBehavior: \tDT4 (Endpoint with decapsulation and specific IPv4 table lookup)"
+			   "\n\tTable: \t%u", format_ip6_address,
+			   &ls->localsid, ls->fib_table);
+	  break;
+	default:
+	  if (ls->behavior >= SR_BEHAVIOR_LAST)
+	    {
+	      sr_localsid_fn_registration_t *plugin =
+		pool_elt_at_index (sm->plugin_functions,
+				   ls->behavior - SR_BEHAVIOR_LAST);
+
+	      vlib_cli_output (vm, "\tAddress: \t%U\n"
+			       "\tBehavior: \t%s (%s)\n\t%U",
+			       format_ip6_address, &ls->localsid,
+			       plugin->keyword_str, plugin->def_str,
+			       plugin->ls_format, ls->plugin_mem);
+	    }
+	  else
+	    //Should never get here...
+	    vlib_cli_output (vm, "Internal error");
+	  break;
+	}
+      if (ls->end_psp)
+	vlib_cli_output (vm, "\tPSP: \tTrue\n");
+
+      /* Print counters */
+      vlib_counter_t valid, invalid;
+      vlib_get_combined_counter (&(sm->sr_ls_valid_counters), i, &valid);
+      vlib_get_combined_counter (&(sm->sr_ls_invalid_counters), i, &invalid);
+      vlib_cli_output (vm, "\tGood traffic: \t[%Ld packets : %Ld bytes]\n",
+		       valid.packets, valid.bytes);
+      vlib_cli_output (vm, "\tBad traffic:  \t[%Ld packets : %Ld bytes]\n",
+		       invalid.packets, invalid.bytes);
+      vlib_cli_output (vm, "--------------------");
+    }
+  return 0;
+}
+
+/* *INDENT-OFF* */
+VLIB_CLI_COMMAND (show_sr_localsid_command, static) = {
+  .path = "show sr localsids",
+  .short_help = "show sr localsids",
+  .function = show_sr_localsid_command_fn,
+};
+/* *INDENT-ON* */
+
+/**
+ * @brief Function to 'clear' ALL SR localsid counters
+ */
+static clib_error_t *
+clear_sr_localsid_counters_command_fn (vlib_main_t * vm,
+				       unformat_input_t * input,
+				       vlib_cli_command_t * cmd)
+{
+  ip6_sr_main_t *sm = &sr_main;
+
+  vlib_clear_combined_counters (&(sm->sr_ls_valid_counters));
+  vlib_clear_combined_counters (&(sm->sr_ls_invalid_counters));
+
+  return 0;
+}
+
+/* *INDENT-OFF* */
+VLIB_CLI_COMMAND (clear_sr_localsid_counters_command, static) = {
+  .path = "clear sr localsid counters",
+  .short_help = "clear sr localsid counters",
+  .function = clear_sr_localsid_counters_command_fn,
+};
+/* *INDENT-ON* */
+
+/************************ SR LocalSID graphs node ****************************/
+/**
+ * @brief SR localsid node trace
+ */
+typedef struct
+{
+  u32 localsid_index;
+  ip6_address_t src, out_dst;
+  u8 sr[256];
+  u8 num_segments;
+  u8 segments_left;
+  //With SRv6 header update include flags here.
+} sr_localsid_trace_t;
+
+#define foreach_sr_localsid_error                                   \
+_(NO_INNER_HEADER, "(SR-Error) No inner IP header")                 \
+_(NO_MORE_SEGMENTS, "(SR-Error) No more segments")                  \
+_(NO_SRH, "(SR-Error) No SR header")                                \
+_(NO_PSP, "(SR-Error) PSP Not available (segments left > 0)")       \
+_(NOT_LS, "(SR-Error) Decaps not available (segments left > 0)")    \
+_(L2, "(SR-Error) SRv6 decapsulated a L2 frame without dest")
+
+typedef enum
+{
+#define _(sym,str) SR_LOCALSID_ERROR_##sym,
+  foreach_sr_localsid_error
+#undef _
+    SR_LOCALSID_N_ERROR,
+} sr_localsid_error_t;
+
+static char *sr_localsid_error_strings[] = {
+#define _(sym,string) string,
+  foreach_sr_localsid_error
+#undef _
+};
+
+#define foreach_sr_localsid_next        \
+_(ERROR, "error-drop")                  \
+_(IP6_LOOKUP, "ip6-lookup")             \
+_(IP4_LOOKUP, "ip4-lookup")             \
+_(IP6_REWRITE, "ip6-rewrite")           \
+_(IP4_REWRITE, "ip4-rewrite")           \
+_(INTERFACE_OUTPUT, "interface-output")
+
+typedef enum
+{
+#define _(s,n) SR_LOCALSID_NEXT_##s,
+  foreach_sr_localsid_next
+#undef _
+    SR_LOCALSID_N_NEXT,
+} sr_localsid_next_t;
+
+/**
+ * @brief SR LocalSID graph node trace function
+ *
+ * @see sr_localsid
+ */
+u8 *
+format_sr_localsid_trace (u8 * s, va_list * args)
+{
+  CLIB_UNUSED (vlib_main_t * vm) = va_arg (*args, vlib_main_t *);
+  CLIB_UNUSED (vlib_node_t * node) = va_arg (*args, vlib_node_t *);
+  ip6_sr_main_t *sm = &sr_main;
+  sr_localsid_trace_t *t = va_arg (*args, sr_localsid_trace_t *);
+
+  ip6_sr_localsid_t *ls =
+    pool_elt_at_index (sm->localsids, t->localsid_index);
+
+  s =
+    format (s, "SR-LOCALSID:\n\tLocalsid: %U\n", format_ip6_address,
+	    &ls->localsid);
+  switch (ls->behavior)
+    {
+    case SR_BEHAVIOR_END:
+      s = format (s, "\tBehavior: End\n");
+      break;
+    case SR_BEHAVIOR_DX6:
+      s = format (s, "\tBehavior: Decapsulation with IPv6 L3 xconnect\n");
+      break;
+    case SR_BEHAVIOR_DX4:
+      s = format (s, "\tBehavior: Decapsulation with IPv4 L3 xconnect\n");
+      break;
+    case SR_BEHAVIOR_X:
+      s = format (s, "\tBehavior: IPv6 L3 xconnect\n");
+      break;
+    case SR_BEHAVIOR_DT6:
+      s = format (s, "\tBehavior: Decapsulation with IPv6 Table lookup\n");
+      break;
+    case SR_BEHAVIOR_DT4:
+      s = format (s, "\tBehavior: Decapsulation with IPv4 Table lookup\n");
+      break;
+    case SR_BEHAVIOR_DX2:
+      s = format (s, "\tBehavior: Decapsulation with L2 xconnect\n");
+      break;
+    default:
+      s = format (s, "\tBehavior: defined in plugin\n");	//TODO
+      break;
+    }
+  if (t->num_segments != 0xFF)
+    {
+      if (t->num_segments > 0)
+	{
+	  s = format (s, "\tSegments left: %d\n", t->num_segments);
+	  s = format (s, "\tSID list: [in ietf order]");
+	  int i = 0;
+	  for (i = 0; i < t->num_segments; i++)
+	    {
+	      s = format (s, "\n\t-> %U", format_ip6_address,
+			  (ip6_address_t *) & t->sr[i *
+						    sizeof (ip6_address_t)]);
+	    }
+	}
+    }
+  return s;
+}
+
+/**
+ * @brief Function doing End processing.
+ */
+static_always_inline void
+end_srh_processing (vlib_node_runtime_t * node,
+		    vlib_buffer_t * b0,
+		    ip6_header_t * ip0,
+		    ip6_sr_header_t * sr0,
+		    ip6_sr_localsid_t * ls0, u32 * next0)
+{
+  ip6_address_t *new_dst0;
+
+  if (PREDICT_TRUE (sr0->type == ROUTING_HEADER_TYPE_SR))
+    {
+      if (PREDICT_TRUE (sr0->segments_left != 0))
+	{
+	  sr0->segments_left -= 1;
+	  new_dst0 = (ip6_address_t *) (sr0->segments);
+	  new_dst0 += sr0->segments_left;
+	  ip0->dst_address.as_u64[0] = new_dst0->as_u64[0];
+	  ip0->dst_address.as_u64[1] = new_dst0->as_u64[1];
+
+	  if (ls0->behavior == SR_BEHAVIOR_X)
+	    {
+	      vnet_buffer (b0)->ip.adj_index[VLIB_TX] = ls0->nh_adj;
+	      *next0 = SR_LOCALSID_NEXT_IP6_REWRITE;
+	    }
+	}
+      else
+	{
+	  *next0 = SR_LOCALSID_NEXT_ERROR;
+	  b0->error = node->errors[SR_LOCALSID_ERROR_NO_MORE_SEGMENTS];
+	}
+    }
+  else
+    {
+      /* Error. Routing header of type != SR */
+      *next0 = SR_LOCALSID_NEXT_ERROR;
+      b0->error = node->errors[SR_LOCALSID_ERROR_NO_SRH];
+    }
+}
+
+/*
+ * @brief Function doing SRH processing for D* variants
+ */
+//FixME. I must crosscheck that next_proto matches the localsid
+static_always_inline void
+end_decaps_srh_processing (vlib_node_runtime_t * node,
+			   vlib_buffer_t * b0,
+			   ip6_header_t * ip0,
+			   ip6_sr_header_t * sr0,
+			   ip6_sr_localsid_t * ls0, u32 * next0)
+{
+  /* Compute the size of the IPv6 header with all Ext. headers */
+  u8 next_proto;
+  ip6_ext_header_t *next_ext_header;
+  u16 total_size = 0;
+
+  next_proto = ip0->protocol;
+  next_ext_header = (void *) (ip0 + 1);
+  total_size = sizeof (ip6_header_t);
+  while (ip6_ext_hdr (next_proto))
+    {
+      total_size += ip6_ext_header_len (next_ext_header);
+      next_proto = next_ext_header->next_hdr;
+      next_ext_header = ip6_ext_next_header (next_ext_header);
+    }
+
+  /* Ensure this is the last segment. Otherwise drop. */
+  if (sr0 && sr0->segments_left != 0)
+    {
+      *next0 = SR_LOCALSID_NEXT_ERROR;
+      b0->error = node->errors[SR_LOCALSID_ERROR_NOT_LS];
+      return;
+    }
+
+  switch (next_proto)
+    {
+    case IP_PROTOCOL_IPV6:
+      /* Encap-End IPv6. Pop outer IPv6 header. */
+      if (ls0->behavior == SR_BEHAVIOR_DX6)
+	{
+	  vlib_buffer_advance (b0, total_size);
+	  vnet_buffer (b0)->ip.adj_index[VLIB_TX] = ls0->nh_adj;
+	  *next0 = SR_LOCALSID_NEXT_IP6_REWRITE;
+	  return;
+	}
+      else if (ls0->behavior == SR_BEHAVIOR_DT6)
+	{
+	  vlib_buffer_advance (b0, total_size);
+	  vnet_buffer (b0)->sw_if_index[VLIB_TX] = ls0->fib_table;
+	  return;
+	}
+      break;
+    case IP_PROTOCOL_IP_IN_IP:
+      /* Encap-End IPv4. Pop outer IPv6 header */
+      if (ls0->behavior == SR_BEHAVIOR_DX4)
+	{
+	  vlib_buffer_advance (b0, total_size);
+	  vnet_buffer (b0)->ip.adj_index[VLIB_TX] = ls0->nh_adj;
+	  *next0 = SR_LOCALSID_NEXT_IP4_REWRITE;
+	  return;
+	}
+      else if (ls0->behavior == SR_BEHAVIOR_DT4)
+	{
+	  vlib_buffer_advance (b0, total_size);
+	  vnet_buffer (b0)->sw_if_index[VLIB_TX] = ls0->fib_table;
+	  *next0 = SR_LOCALSID_NEXT_IP4_LOOKUP;
+	  return;
+	}
+      break;
+    case IP_PROTOCOL_IP6_NONXT:
+      /* L2 encaps */
+      if (ls0->behavior == SR_BEHAVIOR_DX2)
+	{
+	  vlib_buffer_advance (b0, total_size);
+	  vnet_buffer (b0)->sw_if_index[VLIB_TX] = ls0->sw_if_index;
+	  *next0 = SR_LOCALSID_NEXT_INTERFACE_OUTPUT;
+	  return;
+	}
+      break;
+    }
+  *next0 = SR_LOCALSID_NEXT_ERROR;
+  b0->error = node->errors[SR_LOCALSID_ERROR_NO_INNER_HEADER];
+  return;
+}
+
+/**
+ * @brief Function doing End processing with PSP
+ */
+static_always_inline void
+end_psp_srh_processing (vlib_node_runtime_t * node,
+			vlib_buffer_t * b0,
+			ip6_header_t * ip0,
+			ip6_ext_header_t * prev0,
+			ip6_sr_header_t * sr0,
+			ip6_sr_localsid_t * ls0, u32 * next0)
+{
+  u32 new_l0, sr_len;
+  u64 *copy_dst0, *copy_src0;
+  u32 copy_len_u64s0 = 0;
+  int i;
+
+  if (PREDICT_TRUE (sr0->type == ROUTING_HEADER_TYPE_SR))
+    {
+      if (PREDICT_TRUE (sr0->segments_left == 1))
+	{
+	  ip0->dst_address.as_u64[0] = sr0->segments->as_u64[0];
+	  ip0->dst_address.as_u64[1] = sr0->segments->as_u64[1];
+
+	  /* Remove the SRH taking care of the rest of IPv6 ext header */
+	  if (prev0)
+	    prev0->next_hdr = sr0->protocol;
+	  else
+	    ip0->protocol = sr0->protocol;
+
+	  sr_len = ip6_ext_header_len (sr0);
+	  vlib_buffer_advance (b0, sr_len);
+	  new_l0 = clib_net_to_host_u16 (ip0->payload_length) - sr_len;
+	  ip0->payload_length = clib_host_to_net_u16 (new_l0);
+	  copy_src0 = (u64 *) ip0;
+	  copy_dst0 = copy_src0 + (sr0->length + 1);
+	  /* number of 8 octet units to copy
+	   * By default in absence of extension headers it is equal to length of ip6 header
+	   * With extension headers it number of 8 octet units of ext headers preceding
+	   * SR header
+	   */
+	  copy_len_u64s0 =
+	    (((u8 *) sr0 - (u8 *) ip0) - sizeof (ip6_header_t)) >> 3;
+	  copy_dst0[4 + copy_len_u64s0] = copy_src0[4 + copy_len_u64s0];
+	  copy_dst0[3 + copy_len_u64s0] = copy_src0[3 + copy_len_u64s0];
+	  copy_dst0[2 + copy_len_u64s0] = copy_src0[2 + copy_len_u64s0];
+	  copy_dst0[1 + copy_len_u64s0] = copy_src0[1 + copy_len_u64s0];
+	  copy_dst0[0 + copy_len_u64s0] = copy_src0[0 + copy_len_u64s0];
+
+	  for (i = copy_len_u64s0 - 1; i >= 0; i--)
+	    {
+	      copy_dst0[i] = copy_src0[i];
+	    }
+
+	  if (ls0->behavior == SR_BEHAVIOR_X)
+	    {
+	      vnet_buffer (b0)->ip.adj_index[VLIB_TX] = ls0->nh_adj;
+	      *next0 = SR_LOCALSID_NEXT_IP6_REWRITE;
+	    }
+	  return;
+	}
+    }
+  /* Error. Routing header of type != SR */
+  *next0 = SR_LOCALSID_NEXT_ERROR;
+  b0->error = node->errors[SR_LOCALSID_ERROR_NO_PSP];
+}
+
+/**
+ * @brief SR LocalSID graph node. Supports all default SR Endpoint variants
+ */
+static uword
+sr_localsid_d_fn (vlib_main_t * vm, vlib_node_runtime_t * node,
+		  vlib_frame_t * from_frame)
+{
+  u32 n_left_from, next_index, *from, *to_next;
+  ip6_sr_main_t *sm = &sr_main;
+  from = vlib_frame_vector_args (from_frame);
+  n_left_from = from_frame->n_vectors;
+  next_index = node->cached_next_index;
+  u32 thread_index = vlib_get_thread_index ();
+
+  while (n_left_from > 0)
+    {
+      u32 n_left_to_next;
+      vlib_get_next_frame (vm, node, next_index, to_next, n_left_to_next);
+
+      /* Quad - Loop */
+      while (n_left_from >= 8 && n_left_to_next >= 4)
+	{
+	  u32 bi0, bi1, bi2, bi3;
+	  vlib_buffer_t *b0, *b1, *b2, *b3;
+	  ip6_header_t *ip0, *ip1, *ip2, *ip3;
+	  ip6_ext_header_t *prev0, *prev1, *prev2, *prev3;
+	  ip6_sr_header_t *sr0, *sr1, *sr2, *sr3;
+	  u32 next0, next1, next2, next3;
+	  next0 = next1 = next2 = next3 = SR_LOCALSID_NEXT_IP6_LOOKUP;
+	  ip6_sr_localsid_t *ls0, *ls1, *ls2, *ls3;
+
+	  /* Prefetch next iteration. */
+	  {
+	    vlib_buffer_t *p4, *p5, *p6, *p7;
+
+	    p4 = vlib_get_buffer (vm, from[4]);
+	    p5 = vlib_get_buffer (vm, from[5]);
+	    p6 = vlib_get_buffer (vm, from[6]);
+	    p7 = vlib_get_buffer (vm, from[7]);
+
+	    /* Prefetch the buffer header and packet for the N+4 loop iteration */
+	    vlib_prefetch_buffer_header (p4, LOAD);
+	    vlib_prefetch_buffer_header (p5, LOAD);
+	    vlib_prefetch_buffer_header (p6, LOAD);
+	    vlib_prefetch_buffer_header (p7, LOAD);
+
+	    CLIB_PREFETCH (p4->data, CLIB_CACHE_LINE_BYTES, STORE);
+	    CLIB_PREFETCH (p5->data, CLIB_CACHE_LINE_BYTES, STORE);
+	    CLIB_PREFETCH (p6->data, CLIB_CACHE_LINE_BYTES, STORE);
+	    CLIB_PREFETCH (p7->data, CLIB_CACHE_LINE_BYTES, STORE);
+	  }
+
+	  to_next[0] = bi0 = from[0];
+	  to_next[1] = bi1 = from[1];
+	  to_next[2] = bi2 = from[2];
+	  to_next[3] = bi3 = from[3];
+	  from += 4;
+	  to_next += 4;
+	  n_left_from -= 4;
+	  n_left_to_next -= 4;
+
+	  b0 = vlib_get_buffer (vm, bi0);
+	  b1 = vlib_get_buffer (vm, bi1);
+	  b2 = vlib_get_buffer (vm, bi2);
+	  b3 = vlib_get_buffer (vm, bi3);
+
+	  ls0 =
+	    pool_elt_at_index (sm->localsids,
+			       vnet_buffer (b0)->ip.adj_index[VLIB_TX]);
+	  ls1 =
+	    pool_elt_at_index (sm->localsids,
+			       vnet_buffer (b0)->ip.adj_index[VLIB_TX]);
+	  ls2 =
+	    pool_elt_at_index (sm->localsids,
+			       vnet_buffer (b0)->ip.adj_index[VLIB_TX]);
+	  ls3 =
+	    pool_elt_at_index (sm->localsids,
+			       vnet_buffer (b0)->ip.adj_index[VLIB_TX]);
+
+	  ip0 = vlib_buffer_get_current (b0);
+	  ip1 = vlib_buffer_get_current (b1);
+	  ip2 = vlib_buffer_get_current (b2);
+	  ip3 = vlib_buffer_get_current (b3);
+
+	  ip6_ext_header_find_t (ip0, prev0, sr0, IP_PROTOCOL_IPV6_ROUTE);
+	  ip6_ext_header_find_t (ip1, prev1, sr1, IP_PROTOCOL_IPV6_ROUTE);
+	  ip6_ext_header_find_t (ip2, prev2, sr2, IP_PROTOCOL_IPV6_ROUTE);
+	  ip6_ext_header_find_t (ip3, prev3, sr3, IP_PROTOCOL_IPV6_ROUTE);
+
+	  end_decaps_srh_processing (node, b0, ip0, sr0, ls0, &next0);
+	  end_decaps_srh_processing (node, b1, ip1, sr1, ls1, &next1);
+	  end_decaps_srh_processing (node, b2, ip2, sr2, ls2, &next2);
+	  end_decaps_srh_processing (node, b3, ip3, sr3, ls3, &next3);
+
+	  //TODO: trace.
+
+	  vlib_increment_combined_counter
+	    (((next0 ==
+	       SR_LOCALSID_NEXT_ERROR) ? &(sm->sr_ls_invalid_counters) :
+	      &(sm->sr_ls_valid_counters)), thread_index, ls0 - sm->localsids,
+	     1, vlib_buffer_length_in_chain (vm, b0));
+
+	  vlib_increment_combined_counter
+	    (((next1 ==
+	       SR_LOCALSID_NEXT_ERROR) ? &(sm->sr_ls_invalid_counters) :
+	      &(sm->sr_ls_valid_counters)), thread_index, ls1 - sm->localsids,
+	     1, vlib_buffer_length_in_chain (vm, b1));
+
+	  vlib_increment_combined_counter
+	    (((next2 ==
+	       SR_LOCALSID_NEXT_ERROR) ? &(sm->sr_ls_invalid_counters) :
+	      &(sm->sr_ls_valid_counters)), thread_index, ls2 - sm->localsids,
+	     1, vlib_buffer_length_in_chain (vm, b2));
+
+	  vlib_increment_combined_counter
+	    (((next3 ==
+	       SR_LOCALSID_NEXT_ERROR) ? &(sm->sr_ls_invalid_counters) :
+	      &(sm->sr_ls_valid_counters)), thread_index, ls3 - sm->localsids,
+	     1, vlib_buffer_length_in_chain (vm, b3));
+
+	  vlib_validate_buffer_enqueue_x4 (vm, node, next_index, to_next,
+					   n_left_to_next, bi0, bi1, bi2, bi3,
+					   next0, next1, next2, next3);
+	}
+
+      /* Single loop for potentially the last three packets */
+      while (n_left_from > 0 && n_left_to_next > 0)
+	{
+	  u32 bi0;
+	  vlib_buffer_t *b0;
+	  ip6_header_t *ip0;
+	  ip6_ext_header_t *prev0;
+	  ip6_sr_header_t *sr0;
+	  u32 next0 = SR_LOCALSID_NEXT_IP6_LOOKUP;
+	  ip6_sr_localsid_t *ls0;
+
+	  bi0 = from[0];
+	  to_next[0] = bi0;
+	  from += 1;
+	  to_next += 1;
+	  n_left_from -= 1;
+	  n_left_to_next -= 1;
+
+	  b0 = vlib_get_buffer (vm, bi0);
+	  ip0 = vlib_buffer_get_current (b0);
+
+	  /* Lookup the SR End behavior based on IP DA (adj) */
+	  ls0 =
+	    pool_elt_at_index (sm->localsids,
+			       vnet_buffer (b0)->ip.adj_index[VLIB_TX]);
+
+	  /* Find SRH as well as previous header */
+	  ip6_ext_header_find_t (ip0, prev0, sr0, IP_PROTOCOL_IPV6_ROUTE);
+
+	  /* SRH processing and End variants */
+	  end_decaps_srh_processing (node, b0, ip0, sr0, ls0, &next0);
+
+	  if (PREDICT_FALSE (b0->flags & VLIB_BUFFER_IS_TRACED))
+	    {
+	      sr_localsid_trace_t *tr =
+		vlib_add_trace (vm, node, b0, sizeof (*tr));
+	      tr->num_segments = 0;
+	      tr->localsid_index = ls0 - sm->localsids;
+
+	      if (ip0 == vlib_buffer_get_current (b0))
+		{
+		  clib_memcpy (tr->src.as_u8, ip0->src_address.as_u8,
+			       sizeof (tr->src.as_u8));
+		  clib_memcpy (tr->out_dst.as_u8, ip0->dst_address.as_u8,
+			       sizeof (tr->out_dst.as_u8));
+		  if (ip0->protocol == IP_PROTOCOL_IPV6_ROUTE
+		      && sr0->type == ROUTING_HEADER_TYPE_SR)
+		    {
+		      clib_memcpy (tr->sr, sr0->segments, sr0->length * 8);
+		      tr->num_segments =
+			sr0->length * 8 / sizeof (ip6_address_t);
+		      tr->segments_left = sr0->segments_left;
+		    }
+		}
+	      else
+		tr->num_segments = 0xFF;
+	    }
+
+	  /* Increase the counters */
+	  vlib_increment_combined_counter
+	    (((next0 ==
+	       SR_LOCALSID_NEXT_ERROR) ? &(sm->sr_ls_invalid_counters) :
+	      &(sm->sr_ls_valid_counters)), thread_index, ls0 - sm->localsids,
+	     1, vlib_buffer_length_in_chain (vm, b0));
+
+	  vlib_validate_buffer_enqueue_x1 (vm, node, next_index, to_next,
+					   n_left_to_next, bi0, next0);
+	}
+      vlib_put_next_frame (vm, node, next_index, n_left_to_next);
+    }
+  return from_frame->n_vectors;
+}
+
+/* *INDENT-OFF* */
+VLIB_REGISTER_NODE (sr_localsid_d_node) = {
+  .function = sr_localsid_d_fn,
+  .name = "sr-localsid-d",
+  .vector_size = sizeof (u32),
+  .format_trace = format_sr_localsid_trace,
+  .type = VLIB_NODE_TYPE_INTERNAL,
+  .n_errors = SR_LOCALSID_N_ERROR,
+  .error_strings = sr_localsid_error_strings,
+  .n_next_nodes = SR_LOCALSID_N_NEXT,
+  .next_nodes = {
+#define _(s,n) [SR_LOCALSID_NEXT_##s] = n,
+    foreach_sr_localsid_next
+#undef _
+  },
+};
+/* *INDENT-ON* */
+
+/**
+ * @brief SR LocalSID graph node. Supports all default SR Endpoint variants
+ */
+static uword
+sr_localsid_fn (vlib_main_t * vm, vlib_node_runtime_t * node,
+		vlib_frame_t * from_frame)
+{
+  u32 n_left_from, next_index, *from, *to_next;
+  ip6_sr_main_t *sm = &sr_main;
+  from = vlib_frame_vector_args (from_frame);
+  n_left_from = from_frame->n_vectors;
+  next_index = node->cached_next_index;
+  u32 thread_index = vlib_get_thread_index ();
+
+  while (n_left_from > 0)
+    {
+      u32 n_left_to_next;
+      vlib_get_next_frame (vm, node, next_index, to_next, n_left_to_next);
+
+      /* Quad - Loop */
+      while (n_left_from >= 8 && n_left_to_next >= 4)
+	{
+	  u32 bi0, bi1, bi2, bi3;
+	  vlib_buffer_t *b0, *b1, *b2, *b3;
+	  ip6_header_t *ip0, *ip1, *ip2, *ip3;
+	  ip6_sr_header_t *sr0, *sr1, *sr2, *sr3;
+	  ip6_ext_header_t *prev0, *prev1, *prev2, *prev3;
+	  u32 next0, next1, next2, next3;
+	  next0 = next1 = next2 = next3 = SR_LOCALSID_NEXT_IP6_LOOKUP;
+	  ip6_sr_localsid_t *ls0, *ls1, *ls2, *ls3;
+
+	  /* Prefetch next iteration. */
+	  {
+	    vlib_buffer_t *p4, *p5, *p6, *p7;
+
+	    p4 = vlib_get_buffer (vm, from[4]);
+	    p5 = vlib_get_buffer (vm, from[5]);
+	    p6 = vlib_get_buffer (vm, from[6]);
+	    p7 = vlib_get_buffer (vm, from[7]);
+
+	    /* Prefetch the buffer header and packet for the N+2 loop iteration */
+	    vlib_prefetch_buffer_header (p4, LOAD);
+	    vlib_prefetch_buffer_header (p5, LOAD);
+	    vlib_prefetch_buffer_header (p6, LOAD);
+	    vlib_prefetch_buffer_header (p7, LOAD);
+
+	    CLIB_PREFETCH (p4->data, CLIB_CACHE_LINE_BYTES, STORE);
+	    CLIB_PREFETCH (p5->data, CLIB_CACHE_LINE_BYTES, STORE);
+	    CLIB_PREFETCH (p6->data, CLIB_CACHE_LINE_BYTES, STORE);
+	    CLIB_PREFETCH (p7->data, CLIB_CACHE_LINE_BYTES, STORE);
+	  }
+
+	  to_next[0] = bi0 = from[0];
+	  to_next[1] = bi1 = from[1];
+	  to_next[2] = bi2 = from[2];
+	  to_next[3] = bi3 = from[3];
+	  from += 4;
+	  to_next += 4;
+	  n_left_from -= 4;
+	  n_left_to_next -= 4;
+
+	  b0 = vlib_get_buffer (vm, bi0);
+	  b1 = vlib_get_buffer (vm, bi1);
+	  b2 = vlib_get_buffer (vm, bi2);
+	  b3 = vlib_get_buffer (vm, bi3);
+
+	  ip0 = vlib_buffer_get_current (b0);
+	  ip1 = vlib_buffer_get_current (b1);
+	  ip2 = vlib_buffer_get_current (b2);
+	  ip3 = vlib_buffer_get_current (b3);
+
+	  ip6_ext_header_find_t (ip0, prev0, sr0, IP_PROTOCOL_IPV6_ROUTE);
+	  ip6_ext_header_find_t (ip1, prev1, sr1, IP_PROTOCOL_IPV6_ROUTE);
+	  ip6_ext_header_find_t (ip2, prev2, sr2, IP_PROTOCOL_IPV6_ROUTE);
+	  ip6_ext_header_find_t (ip3, prev3, sr3, IP_PROTOCOL_IPV6_ROUTE);
+
+	  ls0 =
+	    pool_elt_at_index (sm->localsids,
+			       vnet_buffer (b0)->ip.adj_index[VLIB_TX]);
+	  ls1 =
+	    pool_elt_at_index (sm->localsids,
+			       vnet_buffer (b0)->ip.adj_index[VLIB_TX]);
+	  ls2 =
+	    pool_elt_at_index (sm->localsids,
+			       vnet_buffer (b0)->ip.adj_index[VLIB_TX]);
+	  ls3 =
+	    pool_elt_at_index (sm->localsids,
+			       vnet_buffer (b0)->ip.adj_index[VLIB_TX]);
+
+	  if (ls0->end_psp)
+	    end_psp_srh_processing (node, b0, ip0, prev0, sr0, ls0, &next0);
+	  else
+	    end_srh_processing (node, b0, ip0, sr0, ls0, &next0);
+
+	  if (ls1->end_psp)
+	    end_psp_srh_processing (node, b1, ip1, prev1, sr1, ls1, &next1);
+	  else
+	    end_srh_processing (node, b1, ip1, sr1, ls1, &next1);
+
+	  if (ls2->end_psp)
+	    end_psp_srh_processing (node, b2, ip2, prev2, sr2, ls2, &next2);
+	  else
+	    end_srh_processing (node, b2, ip2, sr2, ls2, &next2);
+
+	  if (ls3->end_psp)
+	    end_psp_srh_processing (node, b3, ip3, prev3, sr3, ls3, &next3);
+	  else
+	    end_srh_processing (node, b3, ip3, sr3, ls3, &next3);
+
+	  //TODO: proper trace.
+
+	  vlib_increment_combined_counter
+	    (((next0 ==
+	       SR_LOCALSID_NEXT_ERROR) ? &(sm->sr_ls_invalid_counters) :
+	      &(sm->sr_ls_valid_counters)), thread_index, ls0 - sm->localsids,
+	     1, vlib_buffer_length_in_chain (vm, b0));
+
+	  vlib_increment_combined_counter
+	    (((next1 ==
+	       SR_LOCALSID_NEXT_ERROR) ? &(sm->sr_ls_invalid_counters) :
+	      &(sm->sr_ls_valid_counters)), thread_index, ls1 - sm->localsids,
+	     1, vlib_buffer_length_in_chain (vm, b1));
+
+	  vlib_increment_combined_counter
+	    (((next2 ==
+	       SR_LOCALSID_NEXT_ERROR) ? &(sm->sr_ls_invalid_counters) :
+	      &(sm->sr_ls_valid_counters)), thread_index, ls2 - sm->localsids,
+	     1, vlib_buffer_length_in_chain (vm, b2));
+
+	  vlib_increment_combined_counter
+	    (((next3 ==
+	       SR_LOCALSID_NEXT_ERROR) ? &(sm->sr_ls_invalid_counters) :
+	      &(sm->sr_ls_valid_counters)), thread_index, ls3 - sm->localsids,
+	     1, vlib_buffer_length_in_chain (vm, b3));
+
+	  vlib_validate_buffer_enqueue_x4 (vm, node, next_index, to_next,
+					   n_left_to_next, bi0, bi1, bi2, bi3,
+					   next0, next1, next2, next3);
+	}
+
+      /* Single loop for potentially the last three packets */
+      while (n_left_from > 0 && n_left_to_next > 0)
+	{
+	  u32 bi0;
+	  vlib_buffer_t *b0;
+	  ip6_header_t *ip0 = 0;
+	  ip6_ext_header_t *prev0;
+	  ip6_sr_header_t *sr0;
+	  u32 next0 = SR_LOCALSID_NEXT_IP6_LOOKUP;
+	  ip6_sr_localsid_t *ls0;
+
+	  bi0 = from[0];
+	  to_next[0] = bi0;
+	  from += 1;
+	  to_next += 1;
+	  n_left_from -= 1;
+	  n_left_to_next -= 1;
+
+	  b0 = vlib_get_buffer (vm, bi0);
+	  ip0 = vlib_buffer_get_current (b0);
+	  ip6_ext_header_find_t (ip0, prev0, sr0, IP_PROTOCOL_IPV6_ROUTE);
+
+	  /* Lookup the SR End behavior based on IP DA (adj) */
+	  ls0 =
+	    pool_elt_at_index (sm->localsids,
+			       vnet_buffer (b0)->ip.adj_index[VLIB_TX]);
+
+	  /* SRH processing */
+	  if (ls0->end_psp)
+	    end_psp_srh_processing (node, b0, ip0, prev0, sr0, ls0, &next0);
+	  else
+	    end_srh_processing (node, b0, ip0, sr0, ls0, &next0);
+
+	  if (PREDICT_FALSE (b0->flags & VLIB_BUFFER_IS_TRACED))
+	    {
+	      sr_localsid_trace_t *tr =
+		vlib_add_trace (vm, node, b0, sizeof (*tr));
+	      tr->num_segments = 0;
+	      tr->localsid_index = ls0 - sm->localsids;
+
+	      if (ip0 == vlib_buffer_get_current (b0))
+		{
+		  clib_memcpy (tr->src.as_u8, ip0->src_address.as_u8,
+			       sizeof (tr->src.as_u8));
+		  clib_memcpy (tr->out_dst.as_u8, ip0->dst_address.as_u8,
+			       sizeof (tr->out_dst.as_u8));
+		  if (ip0->protocol == IP_PROTOCOL_IPV6_ROUTE
+		      && sr0->type == ROUTING_HEADER_TYPE_SR)
+		    {
+		      clib_memcpy (tr->sr, sr0->segments, sr0->length * 8);
+		      tr->num_segments =
+			sr0->length * 8 / sizeof (ip6_address_t);
+		      tr->segments_left = sr0->segments_left;
+		    }
+		}
+	      else
+		{
+		  tr->num_segments = 0xFF;
+		}
+	    }
+
+	  vlib_increment_combined_counter
+	    (((next0 ==
+	       SR_LOCALSID_NEXT_ERROR) ? &(sm->sr_ls_invalid_counters) :
+	      &(sm->sr_ls_valid_counters)), thread_index, ls0 - sm->localsids,
+	     1, vlib_buffer_length_in_chain (vm, b0));
+
+	  vlib_validate_buffer_enqueue_x1 (vm, node, next_index, to_next,
+					   n_left_to_next, bi0, next0);
+	}
+      vlib_put_next_frame (vm, node, next_index, n_left_to_next);
+    }
+  return from_frame->n_vectors;
+}
+
+/* *INDENT-OFF* */
+VLIB_REGISTER_NODE (sr_localsid_node) = {
+  .function = sr_localsid_fn,
+  .name = "sr-localsid",
+  .vector_size = sizeof (u32),
+  .format_trace = format_sr_localsid_trace,
+  .type = VLIB_NODE_TYPE_INTERNAL,
+  .n_errors = SR_LOCALSID_N_ERROR,
+  .error_strings = sr_localsid_error_strings,
+  .n_next_nodes = SR_LOCALSID_N_NEXT,
+  .next_nodes = {
+#define _(s,n) [SR_LOCALSID_NEXT_##s] = n,
+    foreach_sr_localsid_next
+#undef _
+  },
+};
+/* *INDENT-ON* */
+
+static u8 *
+format_sr_dpo (u8 * s, va_list * args)
+{
+  index_t index = va_arg (*args, index_t);
+  CLIB_UNUSED (u32 indent) = va_arg (*args, u32);
+
+  return (format (s, "SR: localsid_index:[%d]", index));
+}
+
+const static dpo_vft_t sr_loc_vft = {
+  .dv_lock = sr_dpo_lock,
+  .dv_unlock = sr_dpo_unlock,
+  .dv_format = format_sr_dpo,
+};
+
+const static char *const sr_loc_ip6_nodes[] = {
+  "sr-localsid",
+  NULL,
+};
+
+const static char *const *const sr_loc_nodes[DPO_PROTO_NUM] = {
+  [DPO_PROTO_IP6] = sr_loc_ip6_nodes,
+};
+
+const static char *const sr_loc_d_ip6_nodes[] = {
+  "sr-localsid-d",
+  NULL,
+};
+
+const static char *const *const sr_loc_d_nodes[DPO_PROTO_NUM] = {
+  [DPO_PROTO_IP6] = sr_loc_d_ip6_nodes,
+};
+
+
+/*************************** SR LocalSID plugins ******************************/
+/**
+ * @brief SR LocalSID plugin registry
+ */
+int
+sr_localsid_register_function (vlib_main_t * vm, u8 * fn_name,
+			       u8 * keyword_str, u8 * def_str,
+			       u8 * params_str, dpo_type_t * dpo,
+			       format_function_t * ls_format,
+			       unformat_function_t * ls_unformat,
+			       sr_plugin_callback_t * creation_fn,
+			       sr_plugin_callback_t * removal_fn)
+{
+  ip6_sr_main_t *sm = &sr_main;
+  uword *p;
+
+  sr_localsid_fn_registration_t *plugin;
+
+  /* Did this function exist? If so update it */
+  p = hash_get_mem (sm->plugin_functions_by_key, fn_name);
+  if (p)
+    {
+      plugin = pool_elt_at_index (sm->plugin_functions, p[0]);
+    }
+  /* Else create a new one and set hash key */
+  else
+    {
+      pool_get (sm->plugin_functions, plugin);
+      hash_set_mem (sm->plugin_functions_by_key, fn_name,
+		    plugin - sm->plugin_functions);
+    }
+
+  memset (plugin, 0, sizeof (*plugin));
+
+  plugin->sr_localsid_function_number = (plugin - sm->plugin_functions);
+  plugin->sr_localsid_function_number += SR_BEHAVIOR_LAST;
+  plugin->ls_format = ls_format;
+  plugin->ls_unformat = ls_unformat;
+  plugin->creation = creation_fn;
+  plugin->removal = removal_fn;
+  clib_memcpy (&plugin->dpo, dpo, sizeof (dpo_type_t));
+  plugin->function_name = format (0, "%s%c", fn_name, 0);
+  plugin->keyword_str = format (0, "%s%c", keyword_str, 0);
+  plugin->def_str = format (0, "%s%c", def_str, 0);
+  plugin->params_str = format (0, "%s%c", params_str, 0);
+
+  return plugin->sr_localsid_function_number;
+}
+
+/**
+ * @brief CLI function to 'show' all available SR LocalSID behaviors
+ */
+static clib_error_t *
+show_sr_localsid_behaviors_command_fn (vlib_main_t * vm,
+				       unformat_input_t * input,
+				       vlib_cli_command_t * cmd)
+{
+  ip6_sr_main_t *sm = &sr_main;
+  sr_localsid_fn_registration_t *plugin;
+  sr_localsid_fn_registration_t **plugins_vec = 0;
+  int i;
+
+  vlib_cli_output (vm,
+		   "SR LocalSIDs behaviors:\n-----------------------\n\n");
+
+  /* *INDENT-OFF* */
+  pool_foreach (plugin, sm->plugin_functions,
+    ({ vec_add1 (plugins_vec, plugin); }));
+  /* *INDENT-ON* */
+
+  /* Print static behaviors */
+  vlib_cli_output (vm, "Default behaviors:\n"
+		   "\tEnd\t-> Endpoint.\n"
+		   "\tEnd.X\t-> Endpoint with decapsulation and Layer-3 cross-connect.\n"
+		   "\t\tParameters: '<iface> <ip6_next_hop>'\n"
+		   "\tEnd.DX2\t-> Endpoint with decapsulation and Layer-2 cross-connect.\n"
+		   "\t\tParameters: '<iface>'\n"
+		   "\tEnd.DX6\t-> Endpoint with decapsulation and IPv6 cross-connect.\n"
+		   "\t\tParameters: '<iface> <ip6_next_hop>'\n"
+		   "\tEnd.DX4\t-> Endpoint with decapsulation and IPv4 cross-connect.\n"
+		   "\t\tParameters: '<iface> <ip4_next_hop>'\n"
+		   "\tEnd.DT6\t-> Endpoint with decapsulation and specific IPv6 table lookup.\n"
+		   "\t\tParameters: '<ip6_fib_table>'\n"
+		   "\tEnd.DT4\t-> Endpoint with decapsulation and specific IPv4 table lookup.\n"
+		   "\t\tParameters: '<ip4_fib_table>'\n");
+  vlib_cli_output (vm, "Plugin behaviors:\n");
+  for (i = 0; i < vec_len (plugins_vec); i++)
+    {
+      plugin = plugins_vec[i];
+      vlib_cli_output (vm, "\t%s\t-> %s.\n", plugin->keyword_str,
+		       plugin->def_str);
+      vlib_cli_output (vm, "\t\tParameters: '%s'\n", plugin->params_str);
+    }
+  return 0;
+}
+
+/* *INDENT-OFF* */
+VLIB_CLI_COMMAND (show_sr_localsid_behaviors_command, static) = {
+  .path = "show sr localsids behaviors",
+  .short_help = "show sr localsids behaviors",
+  .function = show_sr_localsid_behaviors_command_fn,
+};
+/* *INDENT-ON* */
+
+/**
+ * @brief SR LocalSID initialization
+ */
+clib_error_t *
+sr_localsids_init (vlib_main_t * vm)
+{
+  /* Init memory for function keys */
+  ip6_sr_main_t *sm = &sr_main;
+  mhash_init (&sm->sr_localsids_index_hash, sizeof (uword),
+	      sizeof (ip6_address_t));
+  /* Init SR behaviors DPO type */
+  sr_localsid_dpo_type = dpo_register_new_type (&sr_loc_vft, sr_loc_nodes);
+  /* Init SR behaviors DPO type */
+  sr_localsid_d_dpo_type =
+    dpo_register_new_type (&sr_loc_vft, sr_loc_d_nodes);
+  /* Init memory for localsid plugins */
+  sm->plugin_functions_by_key = hash_create_string (0, sizeof (uword));
+  return 0;
+}
+
+VLIB_INIT_FUNCTION (sr_localsids_init);
+/*
+* fd.io coding-style-patch-verification: ON
+*
+* Local Variables:
+* eval: (c-set-style "gnu")
+* End:
+*/
