dpdk: rework cryptodev ipsec build and setup 06/4806/12
authorSergio Gonzalez Monroy <sergio.gonzalez.monroy@intel.com>
Fri, 20 Jan 2017 15:35:23 +0000 (15:35 +0000)
committerDamjan Marion <dmarion.lists@gmail.com>
Fri, 27 Jan 2017 20:52:17 +0000 (20:52 +0000)
Build Cryptodev IPsec support by default when DPDK is enabled but only build
hardware Cryptodev PMDs.

To enable Cryptodev support, a new startup.conf option for dpdk has been
introduced 'enable-cryptodev'.

During VPP init, if Cryptodev support is not enabled or not enough cryptodev
resources are available then default to OpenSSL ipsec implementation.

Change-Id: I5aa7e0d5c2676bdb41d775ef40364536a081956d
Signed-off-by: Sergio Gonzalez Monroy <sergio.gonzalez.monroy@intel.com>
29 files changed:
build-data/packages/dpdk.mk
build-data/packages/vpp.mk
build-data/platforms/vpp.mk
dpdk/Makefile
src/Makefile.am
src/configure.ac
src/vat/api_format.c
src/vnet.am
src/vnet/devices/dpdk/dpdk.h
src/vnet/devices/dpdk/format.c
src/vnet/devices/dpdk/init.c
src/vnet/devices/dpdk/ipsec/cli.c
src/vnet/devices/dpdk/ipsec/crypto_node.c
src/vnet/devices/dpdk/ipsec/dpdk_crypto_ipsec_doc.md
src/vnet/devices/dpdk/ipsec/esp.h
src/vnet/devices/dpdk/ipsec/esp_decrypt.c
src/vnet/devices/dpdk/ipsec/esp_encrypt.c
src/vnet/devices/dpdk/ipsec/ipsec.c
src/vnet/devices/dpdk/ipsec/ipsec.h
src/vnet/ipsec-gre/interface.c
src/vnet/ipsec/ipsec.c
src/vnet/ipsec/ipsec.h
src/vnet/ipsec/ipsec_api.c
src/vnet/ipsec/ipsec_cli.c
src/vnet/ipsec/ipsec_if.c
src/vnet/ipsec/ipsec_if_in.c
src/vnet/ipsec/ipsec_if_out.c
src/vnet/ipsec/ipsec_input.c
src/vnet/ipsec/ipsec_output.c

index 6c13682..6938392 100644 (file)
@@ -22,9 +22,9 @@ DPDK_MAKE_ARGS = -C $(call find_source_fn,$(PACKAGE_SOURCE)) \
        DPDK_TUNE=$(DPDK_TUNE) \
        DPDK_DEBUG=$(DPDK_DEBUG)
 
-DPDK_CRYPTO_PMD=$(strip $($(PLATFORM)_uses_dpdk_cryptodev))
-ifneq ($(DPDK_CRYPTO_PMD),)
-DPDK_MAKE_ARGS += DPDK_CRYPTO_PMD=y
+DPDK_CRYPTO_SW_PMD=$(strip $($(PLATFORM)_uses_dpdk_cryptodev_sw))
+ifneq ($(DPDK_CRYPTO_SW_PMD),)
+DPDK_MAKE_ARGS += DPDK_CRYPTO_SW_PMD=y
 endif
 
 DPDK_MLX5_PMD=$(strip $($(PLATFORM)_uses_dpdk_mlx5_pmd))
index 81aeab6..64eb0d8 100644 (file)
@@ -23,8 +23,8 @@ vpp_CPPFLAGS += $(call installed_includes_fn, dpdk)/dpdk
 vpp_LDFLAGS += $(call installed_libs_fn, dpdk)
 vpp_CPPFLAGS += -I/usr/include/dpdk
 endif
-ifeq ($($(PLATFORM)_uses_dpdk_cryptodev),yes)
-vpp_configure_args += --with-dpdk-crypto
+ifeq ($($(PLATFORM)_uses_dpdk_cryptodev_sw),yes)
+vpp_configure_args += --with-dpdk-crypto-sw
 endif
 ifeq ($($(PLATFORM)_uses_dpdk_mlx5_pmd),yes)
 vpp_configure_args += --with-dpdk-mlx5-pmd
index dd6f9dc..5b20058 100644 (file)
@@ -44,7 +44,7 @@ vpp_configure_args_vpp = --with-dpdk
 vlib_configure_args_vpp = --with-pre-data=128
 
 # DPDK configuration parameters
-# vpp_uses_dpdk_cryptodev = yes
+# vpp_uses_dpdk_cryptodev_sw = yes
 # vpp_uses_dpdk_mlx5_pmd = yes
 # vpp_uses_external_dpdk = yes
 # vpp_dpdk_inc_dir = /usr/include/dpdk
index 586d242..22e9787 100644 (file)
@@ -21,13 +21,13 @@ DPDK_DOWNLOAD_DIR     ?= $(HOME)/Downloads
 DPDK_MARCH            ?= native
 DPDK_TUNE             ?= generic
 DPDK_DEBUG            ?= n
-DPDK_CRYPTO_PMD       ?= n
+DPDK_CRYPTO_SW_PMD    ?= n
 DPDK_MLX5_PMD         ?= n
 
 B := $(DPDK_BUILD_DIR)
 I := $(DPDK_INSTALL_DIR)
 DPDK_VERSION ?= 16.11
-PKG_SUFFIX ?= vpp1
+PKG_SUFFIX ?= vpp2
 DPDK_BASE_URL ?= http://fast.dpdk.org/rel
 DPDK_TARBALL := dpdk-$(DPDK_VERSION).tar.xz
 DPDK_TAR_URL := $(DPDK_BASE_URL)/$(DPDK_TARBALL)
@@ -121,9 +121,9 @@ $(B)/custom-config: $(B)/.patch.ok Makefile
        $(call set,RTE_LIBRTE_VMXNET3_DEBUG_INIT,$(DPDK_DEBUG))
        $(call set,RTE_LIBRTE_PMD_BOND,y)
        $(call set,RTE_LIBRTE_IP_FRAG,y)
-       $(call set,RTE_LIBRTE_PMD_AESNI_MB,$(DPDK_CRYPTO_PMD))
-       $(call set,RTE_LIBRTE_PMD_AESNI_GCM,$(DPDK_CRYPTO_PMD))
-       $(call set,RTE_LIBRTE_PMD_QAT,$(DPDK_CRYPTO_PMD))
+       $(call set,RTE_LIBRTE_PMD_QAT,y)
+       $(call set,RTE_LIBRTE_PMD_AESNI_MB,$(DPDK_CRYPTO_SW_PMD))
+       $(call set,RTE_LIBRTE_PMD_AESNI_GCM,$(DPDK_CRYPTO_SW_PMD))
        $(call set,RTE_LIBRTE_MLX5_PMD,$(DPDK_MLX5_PMD))
        @# not needed
        $(call set,RTE_LIBRTE_TIMER,n)
index 5e24897..239afea 100644 (file)
@@ -47,7 +47,7 @@ DPDK_LD_FLAGS = -Wl,--whole-archive,-ldpdk,--no-whole-archive
 else
 DPDK_LD_FLAGS = -Wl,--whole-archive,-l:libdpdk.a,--no-whole-archive,-lm,-ldl
 endif
-if WITH_DPDK_CRYPTO
+if WITH_DPDK_CRYPTO_SW
 DPDK_LD_ADD = -L$(AESNI_MULTI_BUFFER_LIB_PATH) -lIPSec_MB
 endif
 if WITH_DPDK_MLX5_PMD
index fbedabf..49da624 100644 (file)
@@ -98,7 +98,7 @@ DISABLE_ARG(japi,     [Disable Java API bindings])
 
 # --with-X
 WITH_ARG(dpdk,         [Use use DPDK])
-WITH_ARG(dpdk_crypto,  [Use DPDK cryptodev])
+WITH_ARG(dpdk_crypto_sw,[Use DPDK cryptodev SW PMDs])
 WITH_ARG(dpdk_mlx5_pmd,        [Use DPDK with mlx5 PMD])
 
 # --without-X
@@ -132,7 +132,7 @@ AC_SUBST(APICLI,            [-DVPP_API_TEST_BUILTIN=${n_with_apicli}])
 
 AC_DEFINE_UNQUOTED(DPDK,               [${n_with_dpdk}])
 AC_DEFINE_UNQUOTED(DPDK_SHARED_LIB,    [${n_enable_dpdk_shared}])
-AC_DEFINE_UNQUOTED(DPDK_CRYPTO,                [${n_with_dpdk_crypto}])
+AC_DEFINE_UNQUOTED(DPDK_CRYPTO_SW,     [${n_with_dpdk_crypto_sw}])
 AC_DEFINE_UNQUOTED(WITH_LIBSSL,                [${n_with_libssl}])
 
 
index 4cfe4a5..6b8c5fb 100644 (file)
@@ -12199,11 +12199,7 @@ api_ipsec_sad_add_del_entry (vat_main_t * vam)
        if (unformat
            (i, "integ_alg %U", unformat_ipsec_integ_alg, &integ_alg))
        {
-#if DPDK_CRYPTO==1
-         if (integ_alg < IPSEC_INTEG_ALG_NONE ||
-#else
          if (integ_alg < IPSEC_INTEG_ALG_SHA1_96 ||
-#endif
              integ_alg >= IPSEC_INTEG_N_ALG)
            {
              clib_warning ("unsupported integ-alg: '%U'",
@@ -12221,33 +12217,6 @@ api_ipsec_sad_add_del_entry (vat_main_t * vam)
 
     }
 
-#if DPDK_CRYPTO==1
-  /*Special cases, aes-gcm-128 encryption */
-  if (crypto_alg == IPSEC_CRYPTO_ALG_AES_GCM_128)
-    {
-      if (integ_alg != IPSEC_INTEG_ALG_NONE
-         && integ_alg != IPSEC_INTEG_ALG_AES_GCM_128)
-       {
-         clib_warning
-           ("unsupported: aes-gcm-128 crypto-alg needs none as integ-alg");
-         return -99;
-       }
-      else                     /*set integ-alg internally to aes-gcm-128 */
-       integ_alg = IPSEC_INTEG_ALG_AES_GCM_128;
-    }
-  else if (integ_alg == IPSEC_INTEG_ALG_AES_GCM_128)
-    {
-      clib_warning ("unsupported integ-alg: aes-gcm-128");
-      return -99;
-    }
-  else if (integ_alg == IPSEC_INTEG_ALG_NONE)
-    {
-      clib_warning ("unsupported integ-alg: none");
-      return -99;
-    }
-#endif
-
-
   M (IPSEC_SAD_ADD_DEL_ENTRY, ipsec_sad_add_del_entry);
 
   mp->sad_id = ntohl (sad_id);
index 28a1b19..96cfa55 100644 (file)
@@ -400,7 +400,7 @@ libvnet_la_SOURCES +=                               \
 
 API_FILES += vnet/ipsec/ipsec.api
 
-if WITH_DPDK_CRYPTO
+if WITH_DPDK
 libvnet_la_SOURCES +=                          \
  vnet/devices/dpdk/ipsec/esp_encrypt.c         \
  vnet/devices/dpdk/ipsec/esp_decrypt.c         \
@@ -419,7 +419,7 @@ nobase_include_HEADERS +=                   \
  vnet/ipsec/ikev2.h                            \
  vnet/ipsec/ikev2_priv.h                       \
  vnet/ipsec/ipsec.api.h
-if WITH_DPDK_CRYPTO
+if WITH_DPDK
 nobase_include_HEADERS +=                      \
  vnet/devices/dpdk/ipsec/ipsec.h               \
  vnet/devices/dpdk/ipsec/esp.h
index a91e87d..1b54460 100644 (file)
@@ -338,6 +338,7 @@ typedef struct
   u8 *uio_driver_name;
   u8 no_multi_seg;
   u8 enable_tcp_udp_checksum;
+  u8 cryptodev;
 
   /* Required config parameters */
   u8 coremask_set_manually;
index ff7c7a5..cc0d71a 100644 (file)
@@ -684,6 +684,8 @@ format_dpdk_rte_mbuf (u8 * s, va_list * va)
   return s;
 }
 
+/* FIXME is this function used? */
+#if 0
 uword
 unformat_socket_mem (unformat_input_t * input, va_list * va)
 {
@@ -710,6 +712,7 @@ unformat_socket_mem (unformat_input_t * input, va_list * va)
 done:
   return 1;
 }
+#endif
 
 clib_error_t *
 unformat_rss_fn (unformat_input_t * input, uword * rss_fn)
index 3fa656e..01ef48c 100755 (executable)
@@ -1054,6 +1054,9 @@ dpdk_config (vlib_main_t * vm, unformat_input_t * input)
       else if (unformat (input, "no-multi-seg"))
        conf->no_multi_seg = 1;
 
+      else if (unformat (input, "enable-cryptodev"))
+       conf->cryptodev = 1;
+
       else if (unformat (input, "dev default %U", unformat_vlib_cli_sub_input,
                         &sub_input))
        {
index 3b634e0..93df4a6 100644 (file)
  */
 
 #include <vnet/vnet.h>
+#include <vnet/devices/dpdk/dpdk.h>
 #include <vnet/devices/dpdk/ipsec/ipsec.h>
 
 static void
 dpdk_ipsec_show_mapping (vlib_main_t * vm, u16 detail_display)
 {
+  dpdk_config_main_t *conf = &dpdk_config_main;
   dpdk_crypto_main_t *dcm = &dpdk_crypto_main;
   vlib_thread_main_t *tm = vlib_get_thread_main ();
   u32 i, skip_master;
 
+  if (!conf->cryptodev)
+    {
+      vlib_cli_output (vm, "DPDK Cryptodev support is disabled\n");
+      return;
+    }
+
   if (detail_display)
     vlib_cli_output (vm, "worker\t%10s\t%15s\tdir\tdev\tqp\n",
                     "cipher", "auth");
index 7b32704..e8fef23 100644 (file)
@@ -22,6 +22,8 @@
 #include <vnet/ethernet/ethernet.h>
 #include <vnet/ipsec/ipsec.h>
 
+#include <vnet/devices/dpdk/dpdk.h>
+#include <vnet/devices/dpdk/dpdk_priv.h>
 #include <vnet/devices/dpdk/ipsec/ipsec.h>
 
 #define foreach_dpdk_crypto_input_next         \
@@ -183,24 +185,27 @@ dpdk_crypto_input_fn (vlib_main_t * vm, vlib_node_runtime_t * node,
   return n_deq;
 }
 
+/* *INDENT-OFF* */
 VLIB_REGISTER_NODE (dpdk_crypto_input_node) =
 {
-  .function = dpdk_crypto_input_fn,.name = "dpdk-crypto-input",.format_trace =
-    format_dpdk_crypto_input_trace,.type = VLIB_NODE_TYPE_INPUT,.state =
-    VLIB_NODE_STATE_DISABLED,.n_errors =
-    DPDK_CRYPTO_INPUT_N_ERROR,.error_strings =
-    dpdk_crypto_input_error_strings,.n_next_nodes =
-    DPDK_CRYPTO_INPUT_N_NEXT,.next_nodes =
+  .function = dpdk_crypto_input_fn,
+  .name = "dpdk-crypto-input",
+  .format_trace = format_dpdk_crypto_input_trace,
+  .type = VLIB_NODE_TYPE_INPUT,
+  .state = VLIB_NODE_STATE_DISABLED,
+  .n_errors = DPDK_CRYPTO_INPUT_N_ERROR,
+  .error_strings = dpdk_crypto_input_error_strings,
+  .n_next_nodes = DPDK_CRYPTO_INPUT_N_NEXT,
+  .next_nodes =
   {
 #define _(s,n) [DPDK_CRYPTO_INPUT_NEXT_##s] = n,
     foreach_dpdk_crypto_input_next
 #undef _
-  }
-,};
+  },
+};
+/* *INDENT-ON* */
 
-#if DPDK_CRYPTO==1
 VLIB_NODE_FUNCTION_MULTIARCH (dpdk_crypto_input_node, dpdk_crypto_input_fn)
-#endif
 /*
  * fd.io coding-style-patch-verification: ON
  *
index 8089696..fed2fe0 100644 (file)
@@ -7,43 +7,55 @@ This document is meant to contain all related information about implementation a
 
 DPDK Cryptodev is an asynchronous crypto API that supports both Hardware and Software implementations (for more details refer to [DPDK Cryptography Device Library documentation](http://dpdk.org/doc/guides/prog_guide/cryptodev_lib.html)).
 
-When DPDK Cryptodev support is enabled, the node graph is modified by adding and replacing some of the nodes.
-
-The following nodes are replaced:
-* esp-encrypt -> dpdk-esp-encrypt
-* esp-decrypt -> dpdk-esp-decrypt
+When DPDK support is enabled and there are enough Cryptodev resources for all workers, the node graph is reconfigured by adding and changing default next nodes.
 
 The following nodes are added:
 * dpdk-crypto-input : polling input node, basically dequeuing from crypto devices.
+* dpdk-esp-encrypt : internal node.
+* dpdk-esp-decrypt : internal node.
 * dpdk-esp-encrypt-post : internal node.
 * dpdk-esp-decrypt-post : internal node.
 
+Set new default next nodes:
+* for esp encryption: esp-encrypt -> dpdk-esp-encrypt
+* for esp decryption: esp-decrypt -> dpdk-esp-decrypt
+
 
 ### How to enable VPP IPSec with DPDK Cryptodev support
 
-To enable DPDK Cryptodev support (disabled by default), we need the following env option:
+DPDK Cryptodev is supported in DPDK enabled VPP.
+By default, only HW Cryptodev is supported but needs to be explicetly enabled with the following config option:
+
+```
+dpdk {
+    enable-cryptodev
+}
+```
+
+To enable SW Cryptodev support (AESNI-MB-PMD and GCM-PMD), we need the following env option:
 
-    vpp_uses_dpdk_cryptodev=yes
+    vpp_uses_dpdk_cryptodev_sw=yes
 
 A couple of ways to achive this:
 * uncomment/add it in the platforms config (ie. build-data/platforms/vpp.mk)
-* set the option when building vpp (ie. make vpp_uses_dpdk_cryptodev=yes build-release)
+* set the option when building vpp (ie. make vpp_uses_dpdk_cryptodev_sw=yes build-release)
+
+When enabling SW Cryptodev support, it means that you need to pre-build the required crypto libraries needed by those SW Cryptodev PMDs.
 
 
 ### Crypto Resources allocation
 
 VPP allocates crypto resources based on a best effort approach:
 * first allocate Hardware crypto resources, then Software.
-* if there are not enough crypto resources for all workers, all packets will be dropped if they reach ESP encrypt/decrypt nodes, displaying the warning:
+* if there are not enough crypto resources for all workers, the graph node is not modifed, therefore the default VPP IPsec implementation based in OpenSSL is used. The following message is displayed:
 
       0: dpdk_ipsec_init: not enough cryptodevs for ipsec
 
 
 ### Configuration example
 
-No especial IPsec configuration is required.
-
-Once DPDK Cryptodev is enabled, the user just needs to provide cryptodevs in the startup.conf.
+To enable DPDK Cryptodev the user just need to provide the startup.conf option
+as mentioned previously.
 
 Example startup.conf:
 
@@ -53,6 +65,7 @@ dpdk {
     num-mbufs 131072
     dev 0000:81:00.0
     dev 0000:81:00.1
+    enable-cryptodev
     dev 0000:85:01.0
     dev 0000:85:01.1
     vdev cryptodev_aesni_mb_pmd,socket_id=1
index 7ef90c4..d414d67 100644 (file)
@@ -97,60 +97,11 @@ dpdk_esp_init ()
 }
 
 static_always_inline int
-add_del_sa_sess (u32 sa_index, u8 is_add)
-{
-  dpdk_crypto_main_t *dcm = &dpdk_crypto_main;
-  crypto_worker_main_t *cwm;
-  u8 skip_master = vlib_num_workers () > 0;
-
-  /* *INDENT-OFF* */
-  vec_foreach (cwm, dcm->workers_main)
-    {
-      crypto_sa_session_t *sa_sess;
-      u8 is_outbound;
-
-      if (skip_master)
-       {
-         skip_master = 0;
-         continue;
-       }
-
-      for (is_outbound = 0; is_outbound < 2; is_outbound++)
-       {
-         if (is_add)
-           {
-             pool_get (cwm->sa_sess_d[is_outbound], sa_sess);
-           }
-         else
-           {
-             u8 dev_id;
-
-             sa_sess = pool_elt_at_index (cwm->sa_sess_d[is_outbound], sa_index);
-             dev_id = cwm->qp_data[sa_sess->qp_index].dev_id;
-
-             if (!sa_sess->sess)
-               continue;
-
-             if (rte_cryptodev_sym_session_free(dev_id, sa_sess->sess))
-               {
-                 clib_warning("failed to free session");
-                 return -1;
-               }
-             memset(sa_sess, 0, sizeof(sa_sess[0]));
-           }
-       }
-    }
-  /* *INDENT-OFF* */
-
-  return 0;
-}
-
-static_always_inline int
-translate_crypto_algo(ipsec_crypto_alg_t crypto_algo,
-                     struct rte_crypto_sym_xform *cipher_xform)
+translate_crypto_algo (ipsec_crypto_alg_t crypto_algo,
+                      struct rte_crypto_sym_xform *cipher_xform)
 {
   switch (crypto_algo)
-  {
+    {
     case IPSEC_CRYPTO_ALG_NONE:
       cipher_xform->cipher.algo = RTE_CRYPTO_CIPHER_NULL;
       break;
@@ -164,7 +115,7 @@ translate_crypto_algo(ipsec_crypto_alg_t crypto_algo,
       break;
     default:
       return -1;
-  }
+    }
 
   cipher_xform->type = RTE_CRYPTO_SYM_XFORM_CIPHER;
 
@@ -172,10 +123,11 @@ translate_crypto_algo(ipsec_crypto_alg_t crypto_algo,
 }
 
 static_always_inline int
-translate_integ_algo(ipsec_integ_alg_t integ_alg,
-                    struct rte_crypto_sym_xform *auth_xform, int use_esn)
+translate_integ_algo (ipsec_integ_alg_t integ_alg,
+                     struct rte_crypto_sym_xform *auth_xform, int use_esn)
 {
-  switch (integ_alg) {
+  switch (integ_alg)
+    {
     case IPSEC_INTEG_ALG_NONE:
       auth_xform->auth.algo = RTE_CRYPTO_AUTH_NULL;
       auth_xform->auth.digest_length = 0;
@@ -203,11 +155,11 @@ translate_integ_algo(ipsec_integ_alg_t integ_alg,
     case IPSEC_INTEG_ALG_AES_GCM_128:
       auth_xform->auth.algo = RTE_CRYPTO_AUTH_AES_GCM;
       auth_xform->auth.digest_length = 16;
-      auth_xform->auth.add_auth_data_length = use_esn? 12 : 8;
+      auth_xform->auth.add_auth_data_length = use_esn ? 12 : 8;
       break;
     default:
       return -1;
-  }
+    }
 
   auth_xform->type = RTE_CRYPTO_SYM_XFORM_AUTH;
 
@@ -215,25 +167,26 @@ translate_integ_algo(ipsec_integ_alg_t integ_alg,
 }
 
 static_always_inline int
-create_sym_sess(ipsec_sa_t *sa, crypto_sa_session_t *sa_sess, u8 is_outbound)
+create_sym_sess (ipsec_sa_t * sa, crypto_sa_session_t * sa_sess,
+                u8 is_outbound)
 {
-  u32 cpu_index = os_get_cpu_number();
-  dpdk_crypto_main_t * dcm = &dpdk_crypto_main;
+  u32 cpu_index = os_get_cpu_number ();
+  dpdk_crypto_main_t *dcm = &dpdk_crypto_main;
   crypto_worker_main_t *cwm = &dcm->workers_main[cpu_index];
-  struct rte_crypto_sym_xform cipher_xform = {0};
-  struct rte_crypto_sym_xform auth_xform = {0};
+  struct rte_crypto_sym_xform cipher_xform = { 0 };
+  struct rte_crypto_sym_xform auth_xform = { 0 };
   struct rte_crypto_sym_xform *xfs;
   uword key = 0, *data;
-  crypto_worker_qp_key_t *p_key = (crypto_worker_qp_key_t *)&key;
+  crypto_worker_qp_key_t *p_key = (crypto_worker_qp_key_t *) & key;
 
   if (sa->crypto_alg == IPSEC_CRYPTO_ALG_AES_GCM_128)
     {
       sa->crypto_key_len -= 4;
-      clib_memcpy(&sa->salt, &sa->crypto_key[sa->crypto_key_len], 4);
+      clib_memcpy (&sa->salt, &sa->crypto_key[sa->crypto_key_len], 4);
     }
   else
     {
-      sa->salt = (u32) rand();
+      sa->salt = (u32) rand ();
     }
 
   cipher_xform.type = RTE_CRYPTO_SYM_XFORM_CIPHER;
@@ -244,11 +197,11 @@ create_sym_sess(ipsec_sa_t *sa, crypto_sa_session_t *sa_sess, u8 is_outbound)
   auth_xform.auth.key.data = sa->integ_key;
   auth_xform.auth.key.length = sa->integ_key_len;
 
-  if (translate_crypto_algo(sa->crypto_alg, &cipher_xform) < 0)
+  if (translate_crypto_algo (sa->crypto_alg, &cipher_xform) < 0)
     return -1;
   p_key->cipher_algo = cipher_xform.cipher.algo;
 
-  if (translate_integ_algo(sa->integ_alg, &auth_xform, sa->use_esn) < 0)
+  if (translate_integ_algo (sa->integ_alg, &auth_xform, sa->use_esn) < 0)
     return -1;
   p_key->auth_algo = auth_xform.auth.algo;
 
@@ -269,17 +222,17 @@ create_sym_sess(ipsec_sa_t *sa, crypto_sa_session_t *sa_sess, u8 is_outbound)
 
   p_key->is_outbound = is_outbound;
 
-  data = hash_get(cwm->algo_qp_map, key);
+  data = hash_get (cwm->algo_qp_map, key);
   if (!data)
     return -1;
 
   sa_sess->sess =
-    rte_cryptodev_sym_session_create(cwm->qp_data[*data].dev_id, xfs);
+    rte_cryptodev_sym_session_create (cwm->qp_data[*data].dev_id, xfs);
 
   if (!sa_sess->sess)
     return -1;
 
-  sa_sess->qp_index = (u8)*data;
+  sa_sess->qp_index = (u8) * data;
 
   return 0;
 }
index 89ab9f9..53b2d12 100644 (file)
@@ -22,6 +22,8 @@
 #include <vnet/ipsec/ipsec.h>
 #include <vnet/devices/dpdk/ipsec/ipsec.h>
 #include <vnet/devices/dpdk/ipsec/esp.h>
+#include <vnet/devices/dpdk/dpdk.h>
+#include <vnet/devices/dpdk/dpdk_priv.h>
 
 #define foreach_esp_decrypt_next              \
 _(DROP, "error-drop")                         \
@@ -189,7 +191,14 @@ dpdk_esp_decrypt_node_fn (vlib_main_t * vm,
          if (PREDICT_FALSE(!sa_sess->sess))
            {
              int ret = create_sym_sess(sa0, sa_sess, 0);
-             ASSERT(ret == 0);
+
+             if (PREDICT_FALSE (ret))
+               {
+                 to_next[0] = bi0;
+                 to_next += 1;
+                 n_left_to_next -= 1;
+                 goto trace;
+               }
            }
 
          sess = sa_sess->sess;
index 10bb461..b6f0000 100644 (file)
@@ -22,6 +22,8 @@
 #include <vnet/ipsec/ipsec.h>
 #include <vnet/devices/dpdk/ipsec/ipsec.h>
 #include <vnet/devices/dpdk/ipsec/esp.h>
+#include <vnet/devices/dpdk/dpdk.h>
+#include <vnet/devices/dpdk/dpdk_priv.h>
 
 #define foreach_esp_encrypt_next                   \
 _(DROP, "error-drop")                              \
@@ -179,7 +181,14 @@ dpdk_esp_encrypt_node_fn (vlib_main_t * vm,
          if (PREDICT_FALSE (!sa_sess->sess))
            {
              int ret = create_sym_sess (sa0, sa_sess, 1);
-             ASSERT (ret == 0);
+
+             if (PREDICT_FALSE (ret))
+               {
+                 to_next[0] = bi0;
+                 to_next += 1;
+                 n_left_to_next -= 1;
+                 goto trace;
+               }
            }
 
          qp_index = sa_sess->qp_index;
index de253f0..05c17c9 100644 (file)
 #include <vnet/vnet.h>
 #include <vnet/ip/ip.h>
 #include <vnet/api_errno.h>
+#include <vnet/ipsec/ipsec.h>
+#include <vlib/node_funcs.h>
+
 #include <vnet/devices/dpdk/dpdk.h>
 #include <vnet/devices/dpdk/ipsec/ipsec.h>
 #include <vnet/devices/dpdk/ipsec/esp.h>
-#include <vnet/ipsec/ipsec.h>
 
-#define DPDK_CRYPTO_NB_OBJS      2048
+#define DPDK_CRYPTO_NB_SESS_OBJS  20000
 #define DPDK_CRYPTO_CACHE_SIZE   512
 #define DPDK_CRYPTO_PRIV_SIZE    128
-#define DPDK_CRYPTO_N_QUEUE_DESC  512
+#define DPDK_CRYPTO_N_QUEUE_DESC  1024
 #define DPDK_CRYPTO_NB_COPS      (1024 * 4)
 
-/*
- * return:
- * -1:         update failed
- * 0:  already exist
- * 1:  mapped
- */
 static int
+add_del_sa_sess (u32 sa_index, u8 is_add)
+{
+  dpdk_crypto_main_t *dcm = &dpdk_crypto_main;
+  crypto_worker_main_t *cwm;
+  u8 skip_master = vlib_num_workers () > 0;
+
+  /* *INDENT-OFF* */
+  vec_foreach (cwm, dcm->workers_main)
+    {
+      crypto_sa_session_t *sa_sess;
+      u8 is_outbound;
+
+      if (skip_master)
+       {
+         skip_master = 0;
+         continue;
+       }
+
+      for (is_outbound = 0; is_outbound < 2; is_outbound++)
+       {
+         if (is_add)
+           {
+             pool_get (cwm->sa_sess_d[is_outbound], sa_sess);
+           }
+         else
+           {
+             u8 dev_id;
+
+             sa_sess = pool_elt_at_index (cwm->sa_sess_d[is_outbound], sa_index);
+             dev_id = cwm->qp_data[sa_sess->qp_index].dev_id;
+
+             if (!sa_sess->sess)
+               continue;
+
+             if (rte_cryptodev_sym_session_free(dev_id, sa_sess->sess))
+               {
+                 clib_warning("failed to free session");
+                 return -1;
+               }
+             memset(sa_sess, 0, sizeof(sa_sess[0]));
+           }
+       }
+    }
+  /* *INDENT-OFF* */
+
+  return 0;
+}
+
+static void
 update_qp_data (crypto_worker_main_t * cwm,
                u8 cdev_id, u16 qp_id, u8 is_outbound, u16 * idx)
 {
@@ -45,7 +90,7 @@ update_qp_data (crypto_worker_main_t * cwm,
 
       if (qpd->dev_id == cdev_id && qpd->qp_id == qp_id &&
          qpd->is_outbound == is_outbound)
-         return 0;
+         return;
     }
   /* *INDENT-ON* */
 
@@ -54,13 +99,10 @@ update_qp_data (crypto_worker_main_t * cwm,
   qpd->dev_id = cdev_id;
   qpd->qp_id = qp_id;
   qpd->is_outbound = is_outbound;
-
-  return 1;
 }
 
 /*
  * return:
- *     -1: error
  *     0: already exist
  *     1: mapped
  */
@@ -70,7 +112,6 @@ add_mapping (crypto_worker_main_t * cwm,
             const struct rte_cryptodev_capabilities *cipher_cap,
             const struct rte_cryptodev_capabilities *auth_cap)
 {
-  int mapped;
   u16 qp_index;
   uword key = 0, data, *ret;
   crypto_worker_qp_key_t *p_key = (crypto_worker_qp_key_t *) & key;
@@ -83,17 +124,12 @@ add_mapping (crypto_worker_main_t * cwm,
   if (ret)
     return 0;
 
-  mapped = update_qp_data (cwm, cdev_id, qp, is_outbound, &qp_index);
-  if (mapped < 0)
-    return -1;
+  update_qp_data (cwm, cdev_id, qp, is_outbound, &qp_index);
 
   data = (uword) qp_index;
+  hash_set (cwm->algo_qp_map, key, data);
 
-  ret = hash_set (cwm->algo_qp_map, key, data);
-  if (!ret)
-    rte_panic ("Failed to insert hash table\n");
-
-  return mapped;
+  return 1;
 }
 
 /*
@@ -120,19 +156,13 @@ add_cdev_mapping (crypto_worker_main_t * cwm,
       for (j = dev_info->capabilities; j->op != RTE_CRYPTO_OP_TYPE_UNDEFINED;
           j++)
        {
-         int status = 0;
-
          if (j->sym.xform_type != RTE_CRYPTO_SYM_XFORM_AUTH)
            continue;
 
          if (check_algo_is_supported (j, NULL) != 0)
            continue;
 
-         status = add_mapping (cwm, cdev_id, qp, is_outbound, i, j);
-         if (status == 1)
-           mapped += 1;
-         if (status < 0)
-           return status;
+         mapped |= add_mapping (cwm, cdev_id, qp, is_outbound, i, j);
        }
     }
 
@@ -169,8 +199,33 @@ check_cryptodev_queues ()
 }
 
 static clib_error_t *
-dpdk_ipsec_init (vlib_main_t * vm)
+dpdk_ipsec_check_support (ipsec_sa_t * sa)
+{
+  if (sa->crypto_alg == IPSEC_CRYPTO_ALG_AES_GCM_128)
+    {
+      if (sa->integ_alg != IPSEC_INTEG_ALG_NONE)
+       return clib_error_return (0, "unsupported integ-alg %U with "
+                                 "crypto-algo aes-gcm-128",
+                                 format_ipsec_integ_alg, sa->integ_alg);
+      sa->integ_alg = IPSEC_INTEG_ALG_AES_GCM_128;
+    }
+  else
+    {
+      if (sa->integ_alg == IPSEC_INTEG_ALG_NONE ||
+         sa->integ_alg == IPSEC_INTEG_ALG_AES_GCM_128)
+       return clib_error_return (0, "unsupported integ-alg %U",
+                                 format_ipsec_integ_alg, sa->integ_alg);
+    }
+
+  return 0;
+}
+
+static uword
+dpdk_ipsec_process (vlib_main_t * vm, vlib_node_runtime_t * rt,
+                   vlib_frame_t * f)
 {
+  dpdk_config_main_t *conf = &dpdk_config_main;
+  ipsec_main_t *im = &ipsec_main;
   dpdk_crypto_main_t *dcm = &dpdk_crypto_main;
   vlib_thread_main_t *tm = vlib_get_thread_main ();
   struct rte_cryptodev_config dev_conf;
@@ -180,8 +235,19 @@ dpdk_ipsec_init (vlib_main_t * vm)
   i32 dev_id, ret;
   u32 i, skip_master;
 
+  if (!conf->cryptodev)
+    {
+      clib_warning ("DPDK Cryptodev support is disabled, "
+                   "default to OpenSSL IPsec");
+      return 0;
+    }
+
   if (check_cryptodev_queues () < 0)
-    return clib_error_return (0, "not enough cryptodevs for ipsec");
+    {
+      conf->cryptodev = 0;
+      clib_warning ("not enough Cryptodevs, default to OpenSSL IPsec");
+      return 0;
+    }
 
   vec_alloc (dcm->workers_main, tm->n_vlib_mains);
   _vec_len (dcm->workers_main) = tm->n_vlib_mains;
@@ -221,24 +287,17 @@ dpdk_ipsec_init (vlib_main_t * vm)
            {
              map = hash_create (0, sizeof (crypto_worker_qp_key_t));
              if (!map)
-               return clib_error_return (0, "unable to create hash table "
-                                         "for worker %u",
-                                         vlib_mains[i]->cpu_index);
+               {
+                 clib_warning ("unable to create hash table for worker %u",
+                               vlib_mains[i]->cpu_index);
+                 goto error;
+               }
              cwm->algo_qp_map = map;
            }
 
          for (is_outbound = 0; is_outbound < 2 && qp < max_nb_qp;
               is_outbound++)
-           {
-             int mapped = add_cdev_mapping (cwm, &cdev_info,
-                                            dev_id, qp, is_outbound);
-             if (mapped > 0)
-               qp++;
-
-             if (mapped < 0)
-               return clib_error_return (0,
-                                         "too many queues for one worker");
-           }
+           qp += add_cdev_mapping (cwm, &cdev_info, dev_id, qp, is_outbound);
        }
 
       if (qp == 0)
@@ -246,12 +305,15 @@ dpdk_ipsec_init (vlib_main_t * vm)
 
       dev_conf.socket_id = rte_cryptodev_socket_id (dev_id);
       dev_conf.nb_queue_pairs = cdev_info.max_nb_queue_pairs;
-      dev_conf.session_mp.nb_objs = DPDK_CRYPTO_NB_OBJS;
+      dev_conf.session_mp.nb_objs = DPDK_CRYPTO_NB_SESS_OBJS;
       dev_conf.session_mp.cache_size = DPDK_CRYPTO_CACHE_SIZE;
 
       ret = rte_cryptodev_configure (dev_id, &dev_conf);
       if (ret < 0)
-       return clib_error_return (0, "cryptodev %u config error", dev_id);
+       {
+         clib_warning ("cryptodev %u config error", dev_id);
+         goto error;
+       }
 
       qp_conf.nb_descriptors = DPDK_CRYPTO_N_QUEUE_DESC;
       for (qp = 0; qp < dev_conf.nb_queue_pairs; qp++)
@@ -259,37 +321,64 @@ dpdk_ipsec_init (vlib_main_t * vm)
          ret = rte_cryptodev_queue_pair_setup (dev_id, qp, &qp_conf,
                                                dev_conf.socket_id);
          if (ret < 0)
-           return clib_error_return (0, "cryptodev %u qp %u setup error",
-                                     dev_id, qp);
+           {
+             clib_warning ("cryptodev %u qp %u setup error", dev_id, qp);
+             goto error;
+           }
        }
-      fprintf (stdout, "%u\t%u\t%u\t%u\n", dev_id, dev_conf.nb_queue_pairs,
-              DPDK_CRYPTO_NB_OBJS, DPDK_CRYPTO_CACHE_SIZE);
-    }
+      vec_validate_aligned (dcm->cop_pools, dev_conf.socket_id,
+                           CLIB_CACHE_LINE_BYTES);
 
-  u32 socket_id = rte_socket_id ();
+      if (!vec_elt (dcm->cop_pools, dev_conf.socket_id))
+       {
+         u8 *pool_name = format (0, "crypto_op_pool_socket%u%c",
+                                 dev_conf.socket_id, 0);
+
+         rmp = rte_crypto_op_pool_create ((char *) pool_name,
+                                          RTE_CRYPTO_OP_TYPE_SYMMETRIC,
+                                          DPDK_CRYPTO_NB_COPS *
+                                          (1 + vlib_num_workers ()),
+                                          DPDK_CRYPTO_CACHE_SIZE,
+                                          DPDK_CRYPTO_PRIV_SIZE,
+                                          dev_conf.socket_id);
+         vec_free (pool_name);
+
+         if (!rmp)
+           {
+             clib_warning ("failed to allocate mempool on socket %u",
+                           dev_conf.socket_id);
+             goto error;
+           }
+         vec_elt (dcm->cop_pools, dev_conf.socket_id) = rmp;
+       }
 
-  vec_validate_aligned (dcm->cop_pools, socket_id, CLIB_CACHE_LINE_BYTES);
+      fprintf (stdout, "%u\t%u\t%u\t%u\n", dev_id, dev_conf.nb_queue_pairs,
+              DPDK_CRYPTO_NB_SESS_OBJS, DPDK_CRYPTO_CACHE_SIZE);
+    }
 
-  /* pool already exists, nothing to do */
-  if (dcm->cop_pools[socket_id])
-    return 0;
+  dpdk_esp_init ();
 
-  u8 *pool_name = format (0, "crypto_op_pool_socket%u%c", socket_id, 0);
+  /* Add new next node and set as default */
+  vlib_node_t *node, *next_node;
 
-  rmp = rte_crypto_op_pool_create ((char *) pool_name,
-                                  RTE_CRYPTO_OP_TYPE_SYMMETRIC,
-                                  DPDK_CRYPTO_NB_COPS *
-                                  (1 + vlib_num_workers ()),
-                                  DPDK_CRYPTO_CACHE_SIZE,
-                                  DPDK_CRYPTO_PRIV_SIZE, socket_id);
-  vec_free (pool_name);
+  next_node = vlib_get_node_by_name (vm, (u8 *) "dpdk-esp-encrypt");
+  ASSERT (next_node);
+  node = vlib_get_node_by_name (vm, (u8 *) "ipsec-output-ip4");
+  ASSERT (node);
+  im->esp_encrypt_node_index = next_node->index;
+  im->esp_encrypt_next_index =
+    vlib_node_add_next (vm, node->index, next_node->index);
 
-  if (!rmp)
-    return clib_error_return (0, "failed to allocate mempool on socket %u",
-                             socket_id);
-  dcm->cop_pools[socket_id] = rmp;
+  next_node = vlib_get_node_by_name (vm, (u8 *) "dpdk-esp-decrypt");
+  ASSERT (next_node);
+  node = vlib_get_node_by_name (vm, (u8 *) "ipsec-input-ip4");
+  ASSERT (node);
+  im->esp_decrypt_node_index = next_node->index;
+  im->esp_decrypt_next_index =
+    vlib_node_add_next (vm, node->index, next_node->index);
 
-  dpdk_esp_init ();
+  im->cb.check_support_cb = dpdk_ipsec_check_support;
+  im->cb.add_del_sa_sess_cb = add_del_sa_sess;
 
   if (vec_len (vlib_mains) == 0)
     vlib_node_set_state (&vlib_global_main, dpdk_crypto_input_node.index,
@@ -299,10 +388,38 @@ dpdk_ipsec_init (vlib_main_t * vm)
       vlib_node_set_state (vlib_mains[i], dpdk_crypto_input_node.index,
                           VLIB_NODE_STATE_POLLING);
 
+  /* TODO cryptodev counters */
+
+  return 0;
+
+error:
+  ;
+  crypto_worker_main_t *cwm;
+  struct rte_mempool **mp;
+  /* *INDENT-OFF* */
+  vec_foreach (cwm, dcm->workers_main)
+    hash_free (cwm->algo_qp_map);
+
+  vec_foreach (mp, dcm->cop_pools)
+    {
+      if (mp)
+       rte_mempool_free (mp[0]);
+    }
+  /* *INDENT-ON* */
+  vec_free (dcm->workers_main);
+  vec_free (dcm->cop_pools);
+
   return 0;
 }
 
-VLIB_MAIN_LOOP_ENTER_FUNCTION (dpdk_ipsec_init);
+/* *INDENT-OFF* */
+VLIB_REGISTER_NODE (dpdk_ipsec_process_node,static) = {
+    .function = dpdk_ipsec_process,
+    .type = VLIB_NODE_TYPE_PROCESS,
+    .name = "dpdk-ipsec-process",
+    .process_log2_n_stack_bytes = 17,
+};
+/* *INDENT-ON* */
 
 /*
  * fd.io coding-style-patch-verification: ON
index e6c7498..3465b36 100644 (file)
@@ -167,7 +167,7 @@ check_algo_is_supported (const struct rte_cryptodev_capabilities *cap,
     .type = RTE_CRYPTO_SYM_XFORM_CIPHER,.cipher =
        RTE_CRYPTO_CIPHER_3DES_CBC,.name = "3DES-CBC"},
     {
-    .type = RTE_CRYPTO_SYM_XFORM_CIPHER,.auth =
+    .type = RTE_CRYPTO_SYM_XFORM_CIPHER,.cipher =
        RTE_CRYPTO_CIPHER_AES_GCM,.name = "AES-GCM"},
     {
     .type = RTE_CRYPTO_SYM_XFORM_AUTH,.auth =
index 56832ee..3b6e4ac 100644 (file)
 #include <vnet/ip/format.h>
 #include <vnet/ipsec/ipsec.h>
 
-#if DPDK_CRYPTO==1
-#include <vnet/devices/dpdk/ipsec/esp.h>
-#define ESP_NODE "dpdk-esp-encrypt"
-#else
 #include <vnet/ipsec/esp.h>
-#define ESP_NODE "esp-encrypt"
-#endif
 
 u8 *
 format_ipsec_gre_tunnel (u8 * s, va_list * args)
@@ -193,7 +187,7 @@ vnet_ipsec_gre_add_del_tunnel (vnet_ipsec_gre_add_del_tunnel_args_t * a,
       hash_set (igm->tunnel_by_key, key, t - igm->tunnels);
 
       slot = vlib_node_add_named_next_with_slot
-       (vnm->vlib_main, hi->tx_node_index, ESP_NODE,
+       (vnm->vlib_main, hi->tx_node_index, "esp-encrypt",
         IPSEC_GRE_OUTPUT_NEXT_ESP_ENCRYPT);
 
       ASSERT (slot == IPSEC_GRE_OUTPUT_NEXT_ESP_ENCRYPT);
index ee85c40..cfe434a 100644 (file)
 
 #include <vnet/ipsec/ipsec.h>
 #include <vnet/ipsec/ikev2.h>
-
-#if DPDK_CRYPTO==1
-#include <vnet/devices/dpdk/ipsec/esp.h>
-#define ESP_NODE "dpdk-esp-encrypt"
-#else
 #include <vnet/ipsec/esp.h>
-#define ESP_NODE "esp-encrypt"
-#endif
-
-#if DPDK_CRYPTO==0
-/* dummy function */
-static int
-add_del_sa_sess (u32 sa_index, u8 is_add)
-{
-  return 0;
-}
-#endif
 
 u32
 ipsec_get_sa_index_by_sa_id (u32 sa_id)
@@ -449,7 +433,9 @@ ipsec_add_del_sa (vlib_main_t * vm, ipsec_sa_t * new_sa, int is_add)
          return VNET_API_ERROR_SYSCALL_ERROR_1;        /* sa used in policy */
        }
       hash_unset (im->sa_index_by_sa_id, sa->id);
-      add_del_sa_sess (sa_index, is_add);
+      if (im->cb.add_del_sa_sess_cb &&
+         im->cb.add_del_sa_sess_cb (sa_index, is_add) < 0)
+       return VNET_API_ERROR_SYSCALL_ERROR_1;
       pool_put (im->sad, sa);
     }
   else                         /* create new SA */
@@ -458,7 +444,8 @@ ipsec_add_del_sa (vlib_main_t * vm, ipsec_sa_t * new_sa, int is_add)
       clib_memcpy (sa, new_sa, sizeof (*sa));
       sa_index = sa - im->sad;
       hash_set (im->sa_index_by_sa_id, sa->id, sa_index);
-      if (add_del_sa_sess (sa_index, is_add) < 0)
+      if (im->cb.add_del_sa_sess_cb &&
+         im->cb.add_del_sa_sess_cb (sa_index, is_add) < 0)
        return VNET_API_ERROR_SYSCALL_ERROR_1;
     }
   return 0;
@@ -497,7 +484,8 @@ ipsec_set_sa_key (vlib_main_t * vm, ipsec_sa_t * sa_update)
 
   if (sa->crypto_key_len + sa->integ_key_len > 0)
     {
-      if (add_del_sa_sess (sa_index, 0) < 0)
+      if (im->cb.add_del_sa_sess_cb &&
+         im->cb.add_del_sa_sess_cb (sa_index, 0) < 0)
        return VNET_API_ERROR_SYSCALL_ERROR_1;
     }
 
@@ -521,6 +509,19 @@ ipsec_rand_seed (void)
   RAND_seed ((const void *) &seed_data, sizeof (seed_data));
 }
 
+static clib_error_t *
+ipsec_check_support (ipsec_sa_t * sa)
+{
+  if (sa->crypto_alg == IPSEC_CRYPTO_ALG_AES_GCM_128)
+    return clib_error_return (0, "unsupported aes-gcm-128 crypto-alg");
+  if (sa->integ_alg == IPSEC_INTEG_ALG_NONE)
+    return clib_error_return (0, "unsupported none integ-alg");
+  if (sa->integ_alg == IPSEC_INTEG_ALG_AES_GCM_128)
+    return clib_error_return (0, "unsupported aes-gcm-128 integ-alg");
+
+  return 0;
+}
+
 static clib_error_t *
 ipsec_init (vlib_main_t * vm)
 {
@@ -547,14 +548,18 @@ ipsec_init (vlib_main_t * vm)
   ASSERT (node);
   im->error_drop_node_index = node->index;
 
-  node = vlib_get_node_by_name (vm, (u8 *) ESP_NODE);
-
+  node = vlib_get_node_by_name (vm, (u8 *) "esp-encrypt");
   ASSERT (node);
   im->esp_encrypt_node_index = node->index;
 
-  node = vlib_get_node_by_name (vm, (u8 *) "ip4-lookup");
+  node = vlib_get_node_by_name (vm, (u8 *) "esp-decrypt");
   ASSERT (node);
-  im->ip4_lookup_node_index = node->index;
+  im->esp_decrypt_node_index = node->index;
+
+  im->esp_encrypt_next_index = IPSEC_OUTPUT_NEXT_ESP_ENCRYPT;
+  im->esp_decrypt_next_index = IPSEC_INPUT_NEXT_ESP_DECRYPT;
+
+  im->cb.check_support_cb = ipsec_check_support;
 
   if ((error = vlib_call_init_function (vm, ipsec_cli_init)))
     return error;
index 32c7edf..6726dba 100644 (file)
 
 #define IPSEC_FLAG_IPSEC_GRE_TUNNEL (1 << 0)
 
+
+#define foreach_ipsec_output_next                \
+_(DROP, "error-drop")                            \
+_(ESP_ENCRYPT, "esp-encrypt")
+
+#define _(v, s) IPSEC_OUTPUT_NEXT_##v,
+typedef enum
+{
+  foreach_ipsec_output_next
+#undef _
+    IPSEC_OUTPUT_N_NEXT,
+} ipsec_output_next_t;
+
+
+#define foreach_ipsec_input_next                \
+_(DROP, "error-drop")                           \
+_(ESP_DECRYPT, "esp-decrypt")
+
+#define _(v, s) IPSEC_INPUT_NEXT_##v,
+typedef enum
+{
+  foreach_ipsec_input_next
+#undef _
+    IPSEC_INPUT_N_NEXT,
+} ipsec_input_next_t;
+
+
 #define foreach_ipsec_policy_action \
   _(0, BYPASS,  "bypass")          \
   _(1, DISCARD, "discard")         \
@@ -31,20 +58,12 @@ typedef enum
     IPSEC_POLICY_N_ACTION,
 } ipsec_policy_action_t;
 
-#if DPDK_CRYPTO==1
 #define foreach_ipsec_crypto_alg \
   _(0, NONE,  "none")               \
   _(1, AES_CBC_128, "aes-cbc-128")  \
   _(2, AES_CBC_192, "aes-cbc-192")  \
   _(3, AES_CBC_256, "aes-cbc-256")  \
   _(4, AES_GCM_128, "aes-gcm-128")
-#else
-#define foreach_ipsec_crypto_alg \
-  _(0, NONE,  "none")               \
-  _(1, AES_CBC_128, "aes-cbc-128")  \
-  _(2, AES_CBC_192, "aes-cbc-192")  \
-  _(3, AES_CBC_256, "aes-cbc-256")
-#endif
 
 typedef enum
 {
@@ -54,7 +73,6 @@ typedef enum
     IPSEC_CRYPTO_N_ALG,
 } ipsec_crypto_alg_t;
 
-#if DPDK_CRYPTO==1
 #define foreach_ipsec_integ_alg \
   _(0, NONE,  "none")                                                     \
   _(1, MD5_96, "md5-96")           /* RFC2403 */                          \
@@ -63,17 +81,7 @@ typedef enum
   _(4, SHA_256_128, "sha-256-128") /* RFC4868 */                          \
   _(5, SHA_384_192, "sha-384-192") /* RFC4868 */                          \
   _(6, SHA_512_256, "sha-512-256") /* RFC4868 */                          \
-  _(7, AES_GCM_128, "aes-gcm-128")
-#else
-#define foreach_ipsec_integ_alg \
-  _(0, NONE,  "none")                                                     \
-  _(1, MD5_96, "md5-96")           /* RFC2403 */                          \
-  _(2, SHA1_96, "sha1-96")         /* RFC2404 */                          \
-  _(3, SHA_256_96, "sha-256-96")   /* draft-ietf-ipsec-ciph-sha-256-00 */ \
-  _(4, SHA_256_128, "sha-256-128") /* RFC4868 */                          \
-  _(5, SHA_384_192, "sha-384-192") /* RFC4868 */                          \
-  _(6, SHA_512_256, "sha-512-256")     /* RFC4868 */
-#endif
+  _(7, AES_GCM_128, "aes-gcm-128")     /* RFC4106 */
 
 typedef enum
 {
@@ -223,6 +231,12 @@ typedef struct
   u32 hw_if_index;
 } ipsec_tunnel_if_t;
 
+typedef struct
+{
+  i32 (*add_del_sa_sess_cb) (u32 sa_index, u8 is_add);
+  clib_error_t *(*check_support_cb) (ipsec_sa_t * sa);
+} ipsec_main_callbacks_t;
+
 typedef struct
 {
   /* pool of tunnel instances */
@@ -250,11 +264,16 @@ typedef struct
   uword *sa_index_by_sa_id;
   uword *ipsec_if_pool_index_by_key;
 
-  /* node indexes */
+  /* node indeces */
   u32 error_drop_node_index;
-  u32 ip4_lookup_node_index;
   u32 esp_encrypt_node_index;
+  u32 esp_decrypt_node_index;
+  /* next node indeces */
+  u32 esp_encrypt_next_index;
+  u32 esp_decrypt_next_index;
 
+  /* callbacks */
+  ipsec_main_callbacks_t cb;
 } ipsec_main_t;
 
 ipsec_main_t ipsec_main;
index 9bcf63b..3073226 100644 (file)
@@ -177,6 +177,7 @@ static void vl_api_ipsec_sad_add_del_entry_t_handler
   vl_api_ipsec_sad_add_del_entry_reply_t *rmp;
   int rv;
 #if WITH_LIBSSL > 0
+  ipsec_main_t *im = &ipsec_main;
   ipsec_sa_t sa;
 
   memset (&sa, 0, sizeof (sa));
@@ -204,11 +205,7 @@ static void vl_api_ipsec_sad_add_del_entry_t_handler
   sa.crypto_key_len = mp->crypto_key_length;
   clib_memcpy (&sa.crypto_key, mp->crypto_key, sizeof (sa.crypto_key));
   /* check for unsupported integ-alg */
-#if DPDK_CRYPTO==1
   if (mp->integrity_algorithm < IPSEC_INTEG_ALG_NONE ||
-#else
-  if (mp->integrity_algorithm < IPSEC_INTEG_ALG_SHA1_96 ||
-#endif
       mp->integrity_algorithm >= IPSEC_INTEG_N_ALG)
     {
       clib_warning ("unsupported integ-alg: '%U'", format_ipsec_integ_alg,
@@ -217,35 +214,6 @@ static void vl_api_ipsec_sad_add_del_entry_t_handler
       goto out;
     }
 
-#if DPDK_CRYPTO==1
-  /*Special cases, aes-gcm-128 encryption */
-  if (mp->crypto_algorithm == IPSEC_CRYPTO_ALG_AES_GCM_128)
-    {
-      if (mp->integrity_algorithm != IPSEC_INTEG_ALG_NONE
-         && mp->integrity_algorithm != IPSEC_INTEG_ALG_AES_GCM_128)
-       {
-         clib_warning
-           ("unsupported: aes-gcm-128 crypto-alg needs none as integ-alg");
-         rv = VNET_API_ERROR_UNIMPLEMENTED;
-         goto out;
-       }
-      else                     /*set integ-alg internally to aes-gcm-128 */
-       mp->integrity_algorithm = IPSEC_INTEG_ALG_AES_GCM_128;
-    }
-  else if (mp->integrity_algorithm == IPSEC_INTEG_ALG_AES_GCM_128)
-    {
-      clib_warning ("unsupported integ-alg: aes-gcm-128");
-      rv = VNET_API_ERROR_UNIMPLEMENTED;
-      goto out;
-    }
-  else if (mp->integrity_algorithm == IPSEC_INTEG_ALG_NONE)
-    {
-      clib_warning ("unsupported integ-alg: none");
-      rv = VNET_API_ERROR_UNIMPLEMENTED;
-      goto out;
-    }
-#endif
-
   sa.integ_alg = mp->integrity_algorithm;
   sa.integ_key_len = mp->integrity_key_length;
   clib_memcpy (&sa.integ_key, mp->integrity_key, sizeof (sa.integ_key));
@@ -263,6 +231,15 @@ static void vl_api_ipsec_sad_add_del_entry_t_handler
       clib_memcpy (&sa.tunnel_dst_addr.ip4.data, mp->tunnel_dst_address, 4);
     }
 
+  ASSERT (im->cb.check_support_cb);
+  clib_error_t *err = im->cb.check_support_cb (&sa);
+  if (err)
+    {
+      clib_warning ("%s", err->what);
+      rv = VNET_API_ERROR_UNIMPLEMENTED;
+      goto out;
+    }
+
   rv = ipsec_add_del_sa (vm, &sa, mp->is_add);
 #else
   rv = VNET_API_ERROR_UNIMPLEMENTED;
index 7ab85d4..3c1e26f 100644 (file)
@@ -67,10 +67,12 @@ ipsec_sa_add_del_command_fn (vlib_main_t * vm,
                             unformat_input_t * input,
                             vlib_cli_command_t * cmd)
 {
+  ipsec_main_t *im = &ipsec_main;
   unformat_input_t _line_input, *line_input = &_line_input;
   ipsec_sa_t sa;
   int is_add = ~0;
   u8 *ck = 0, *ik = 0;
+  clib_error_t *err = 0;
 
   memset (&sa, 0, sizeof (sa));
 
@@ -109,11 +111,7 @@ ipsec_sa_add_del_command_fn (vlib_main_t * vm,
       else if (unformat (line_input, "integ-alg %U", unformat_ipsec_integ_alg,
                         &sa.integ_alg))
        {
-#if DPDK_CRYPTO==1
-         if (sa.integ_alg < IPSEC_INTEG_ALG_NONE ||
-#else
          if (sa.integ_alg < IPSEC_INTEG_ALG_SHA1_96 ||
-#endif
              sa.integ_alg >= IPSEC_INTEG_N_ALG)
            return clib_error_return (0, "unsupported integ-alg: '%U'",
                                      format_ipsec_integ_alg, sa.integ_alg);
@@ -141,23 +139,6 @@ ipsec_sa_add_del_command_fn (vlib_main_t * vm,
                                  format_unformat_error, line_input);
     }
 
-#if DPDK_CRYPTO==1
-  /*Special cases, aes-gcm-128 encryption */
-  if (sa.crypto_alg == IPSEC_CRYPTO_ALG_AES_GCM_128)
-    {
-      if (sa.integ_alg != IPSEC_INTEG_ALG_NONE
-         && sa.integ_alg != IPSEC_INTEG_ALG_AES_GCM_128)
-       return clib_error_return (0,
-                                 "unsupported: aes-gcm-128 crypto-alg needs none as integ-alg");
-      else                     /*set integ-alg internally to aes-gcm-128 */
-       sa.integ_alg = IPSEC_INTEG_ALG_AES_GCM_128;
-    }
-  else if (sa.integ_alg == IPSEC_INTEG_ALG_AES_GCM_128)
-    return clib_error_return (0, "unsupported integ-alg: aes-gcm-128");
-  else if (sa.integ_alg == IPSEC_INTEG_ALG_NONE)
-    return clib_error_return (0, "unsupported integ-alg: none");
-#endif
-
   unformat_free (line_input);
 
   if (sa.crypto_key_len > sizeof (sa.crypto_key))
@@ -172,6 +153,14 @@ ipsec_sa_add_del_command_fn (vlib_main_t * vm,
   if (ik)
     strncpy ((char *) sa.integ_key, (char *) ik, sa.integ_key_len);
 
+  if (is_add)
+    {
+      ASSERT (im->cb.check_support_cb);
+      err = im->cb.check_support_cb (&sa);
+      if (err)
+       return err;
+    }
+
   ipsec_add_del_sa (vm, &sa, is_add);
 
   return 0;
index a8da046..ca6b009 100644 (file)
 #include <vnet/ip/ip.h>
 
 #include <vnet/ipsec/ipsec.h>
-#if DPDK_CRYPTO==1
-#include <vnet/devices/dpdk/ipsec/esp.h>
-#else
 #include <vnet/ipsec/esp.h>
-#endif
-
-#if DPDK_CRYPTO==0
-/* dummy function */
-static int
-add_del_sa_sess (u32 sa_index, u8 is_add)
-{
-  return 0;
-}
-#endif
 
 void vl_api_rpc_call_main_thread (void *fp, u8 * data, u32 data_length);
 
@@ -52,6 +39,39 @@ dummy_interface_tx (vlib_main_t * vm,
   return frame->n_vectors;
 }
 
+static clib_error_t *
+ipsec_admin_up_down_function (vnet_main_t * vnm, u32 hw_if_index, u32 flags)
+{
+  ipsec_main_t *im = &ipsec_main;
+  clib_error_t *err = 0;
+  ipsec_tunnel_if_t *t;
+  vnet_hw_interface_t *hi;
+  ipsec_sa_t *sa;
+
+  hi = vnet_get_hw_interface (vnm, hw_if_index);
+  if (flags & VNET_SW_INTERFACE_FLAG_ADMIN_UP)
+    {
+      t = pool_elt_at_index (im->tunnel_interfaces, hi->hw_instance);
+      ASSERT (im->cb.check_support_cb);
+      sa = pool_elt_at_index (im->sad, t->input_sa_index);
+      err = im->cb.check_support_cb (sa);
+      if (err)
+       return err;
+
+      sa = pool_elt_at_index (im->sad, t->output_sa_index);
+      err = im->cb.check_support_cb (sa);
+      if (err)
+       return err;
+
+      vnet_sw_interface_set_flags (vnm, hi->sw_if_index,
+                                  VNET_HW_INTERFACE_FLAG_LINK_UP);
+    }
+  else
+    vnet_sw_interface_set_flags (vnm, hi->sw_if_index, 0 /* down */ );
+
+  return /* no error */ 0;
+}
+
 /* *INDENT-OFF* */
 VNET_DEVICE_CLASS (ipsec_device_class, static) =
 {
@@ -59,6 +79,7 @@ VNET_DEVICE_CLASS (ipsec_device_class, static) =
   .format_device_name = format_ipsec_name,
   .format_tx_trace = format_ipsec_if_output_trace,
   .tx_function = dummy_interface_tx,
+  .admin_up_down_function = ipsec_admin_up_down_function,
 };
 /* *INDENT-ON* */
 
@@ -138,7 +159,9 @@ ipsec_add_del_tunnel_if_internal (vnet_main_t * vnm,
                       args->remote_crypto_key_len);
        }
 
-      add_del_sa_sess (t->input_sa_index, args->is_add);
+      if (im->cb.add_del_sa_sess_cb &&
+         im->cb.add_del_sa_sess_cb (t->input_sa_index, args->is_add) < 0)
+       return VNET_API_ERROR_SYSCALL_ERROR_1;
 
       pool_get (im->sad, sa);
       memset (sa, 0, sizeof (*sa));
@@ -165,7 +188,9 @@ ipsec_add_del_tunnel_if_internal (vnet_main_t * vnm,
                       args->local_crypto_key_len);
        }
 
-      add_del_sa_sess (t->output_sa_index, args->is_add);
+      if (im->cb.add_del_sa_sess_cb &&
+         im->cb.add_del_sa_sess_cb (t->output_sa_index, args->is_add) < 0)
+       return VNET_API_ERROR_SYSCALL_ERROR_1;
 
       hash_set (im->ipsec_if_pool_index_by_key, key,
                t - im->tunnel_interfaces);
@@ -211,14 +236,16 @@ ipsec_add_del_tunnel_if_internal (vnet_main_t * vnm,
       /* delete input and output SA */
       sa = pool_elt_at_index (im->sad, t->input_sa_index);
 
-      if (add_del_sa_sess (t->input_sa_index, args->is_add) < 0)
+      if (im->cb.add_del_sa_sess_cb &&
+         im->cb.add_del_sa_sess_cb (t->input_sa_index, args->is_add) < 0)
        return VNET_API_ERROR_SYSCALL_ERROR_1;
 
       pool_put (im->sad, sa);
 
       sa = pool_elt_at_index (im->sad, t->output_sa_index);
 
-      if (add_del_sa_sess (t->output_sa_index, args->is_add) < 0)
+      if (im->cb.add_del_sa_sess_cb &&
+         im->cb.add_del_sa_sess_cb (t->output_sa_index, args->is_add) < 0)
        return VNET_API_ERROR_SYSCALL_ERROR_1;
 
       pool_put (im->sad, sa);
@@ -310,7 +337,8 @@ ipsec_set_interface_key (vnet_main_t * vnm, u32 hw_if_index,
       sa->crypto_key_len = vec_len (key);
       clib_memcpy (sa->crypto_key, key, vec_len (key));
 
-      if (add_del_sa_sess (t->input_sa_index, 0) < 0)
+      if (im->cb.add_del_sa_sess_cb &&
+         im->cb.add_del_sa_sess_cb (t->output_sa_index, 0) < 0)
        return VNET_API_ERROR_SYSCALL_ERROR_1;
     }
   else if (type == IPSEC_IF_SET_KEY_TYPE_LOCAL_INTEG)
@@ -320,7 +348,8 @@ ipsec_set_interface_key (vnet_main_t * vnm, u32 hw_if_index,
       sa->integ_key_len = vec_len (key);
       clib_memcpy (sa->integ_key, key, vec_len (key));
 
-      if (add_del_sa_sess (t->output_sa_index, 0) < 0)
+      if (im->cb.add_del_sa_sess_cb &&
+         im->cb.add_del_sa_sess_cb (t->output_sa_index, 0) < 0)
        return VNET_API_ERROR_SYSCALL_ERROR_1;
     }
   else if (type == IPSEC_IF_SET_KEY_TYPE_REMOTE_CRYPTO)
@@ -330,7 +359,8 @@ ipsec_set_interface_key (vnet_main_t * vnm, u32 hw_if_index,
       sa->crypto_key_len = vec_len (key);
       clib_memcpy (sa->crypto_key, key, vec_len (key));
 
-      if (add_del_sa_sess (t->input_sa_index, 0) < 0)
+      if (im->cb.add_del_sa_sess_cb &&
+         im->cb.add_del_sa_sess_cb (t->input_sa_index, 0) < 0)
        return VNET_API_ERROR_SYSCALL_ERROR_1;
     }
   else if (type == IPSEC_IF_SET_KEY_TYPE_REMOTE_INTEG)
@@ -340,7 +370,8 @@ ipsec_set_interface_key (vnet_main_t * vnm, u32 hw_if_index,
       sa->integ_key_len = vec_len (key);
       clib_memcpy (sa->integ_key, key, vec_len (key));
 
-      if (add_del_sa_sess (t->output_sa_index, 0) < 0)
+      if (im->cb.add_del_sa_sess_cb &&
+         im->cb.add_del_sa_sess_cb (t->input_sa_index, 0) < 0)
        return VNET_API_ERROR_SYSCALL_ERROR_1;
     }
   else
index db75ab9..bd2a9f7 100644 (file)
 #include <vnet/ipsec/ipsec.h>
 #include <vnet/ipsec/esp.h>
 
-#if DPDK_CRYPTO==1
-#define ESP_NODE "dpdk-esp-decrypt"
-#else
-#define ESP_NODE "esp-decrypt"
-#endif
-
 /* Statistics (not really errors) */
 #define foreach_ipsec_if_input_error    \
 _(RX, "good packets received")
@@ -46,12 +40,6 @@ typedef enum
     IPSEC_IF_INPUT_N_ERROR,
 } ipsec_if_input_error_t;
 
-typedef enum
-{
-  IPSEC_IF_INPUT_NEXT_ESP_DECRYPT,
-  IPSEC_IF_INPUT_NEXT_DROP,
-  IPSEC_IF_INPUT_N_NEXT,
-} ipsec_if_input_next_t;
 
 typedef struct
 {
@@ -59,7 +47,6 @@ typedef struct
   u32 seq;
 } ipsec_if_input_trace_t;
 
-
 u8 *
 format_ipsec_if_input_trace (u8 * s, va_list * args)
 {
@@ -106,7 +93,7 @@ ipsec_if_input_node_fn (vlib_main_t * vm, vlib_node_runtime_t * node,
          ip0 = vlib_buffer_get_current (b0);
          esp0 = (esp_header_t *) ((u8 *) ip0 + ip4_header_bytes (ip0));
 
-         next0 = IPSEC_IF_INPUT_NEXT_DROP;
+         next0 = IPSEC_INPUT_NEXT_DROP;
 
          u64 key = (u64) ip0->src_address.as_u32 << 32 |
            (u64) clib_net_to_host_u32 (esp0->spi);
@@ -121,7 +108,7 @@ ipsec_if_input_node_fn (vlib_main_t * vm, vlib_node_runtime_t * node,
              vnet_buffer (b0)->ipsec.flags =
                t->hw_if_index == ~0 ? IPSEC_FLAG_IPSEC_GRE_TUNNEL : 0;
              vlib_buffer_advance (b0, ip4_header_bytes (ip0));
-             next0 = IPSEC_IF_INPUT_NEXT_ESP_DECRYPT;
+             next0 = im->esp_decrypt_next_index;
            }
 
          if (PREDICT_FALSE (b0->flags & VLIB_BUFFER_IS_TRACED))
@@ -156,12 +143,7 @@ VLIB_REGISTER_NODE (ipsec_if_input_node) = {
   .n_errors = ARRAY_LEN(ipsec_if_input_error_strings),
   .error_strings = ipsec_if_input_error_strings,
 
-  .n_next_nodes = IPSEC_IF_INPUT_N_NEXT,
-
-  .next_nodes = {
-       [IPSEC_IF_INPUT_NEXT_ESP_DECRYPT] = ESP_NODE,
-       [IPSEC_IF_INPUT_NEXT_DROP] = "error-drop",
-  },
+  .sibling_of = "ipsec-input-ip4",
 };
 /* *INDENT-ON* */
 
index 8f06282..62ff67a 100644 (file)
 
 #include <vnet/ipsec/ipsec.h>
 
-#if DPDK_CRYPTO==1
-#define ESP_NODE "dpdk-esp-encrypt"
-#else
-#define ESP_NODE "esp-encrypt"
-#endif
-
 /* Statistics (not really errors) */
 #define foreach_ipsec_if_output_error    \
 _(TX, "good packets transmitted")
@@ -45,12 +39,6 @@ typedef enum
     IPSEC_IF_OUTPUT_N_ERROR,
 } ipsec_if_output_error_t;
 
-typedef enum
-{
-  IPSEC_IF_OUTPUT_NEXT_ESP_ENCRYPT,
-  IPSEC_IF_OUTPUT_NEXT_DROP,
-  IPSEC_IF_OUTPUT_N_NEXT,
-} ipsec_if_output_next_t;
 
 typedef struct
 {
@@ -58,7 +46,6 @@ typedef struct
   u32 seq;
 } ipsec_if_output_trace_t;
 
-
 u8 *
 format_ipsec_if_output_trace (u8 * s, va_list * args)
 {
@@ -106,7 +93,7 @@ ipsec_if_output_node_fn (vlib_main_t * vm, vlib_node_runtime_t * node,
          hi0 = vnet_get_sup_hw_interface (vnm, sw_if_index0);
          t0 = pool_elt_at_index (im->tunnel_interfaces, hi0->dev_instance);
          vnet_buffer (b0)->ipsec.sad_index = t0->output_sa_index;
-         next0 = IPSEC_IF_OUTPUT_NEXT_ESP_ENCRYPT;
+         next0 = im->esp_encrypt_next_index;
 
          if (PREDICT_FALSE (b0->flags & VLIB_BUFFER_IS_TRACED))
            {
@@ -142,12 +129,7 @@ VLIB_REGISTER_NODE (ipsec_if_output_node) = {
   .n_errors = ARRAY_LEN(ipsec_if_output_error_strings),
   .error_strings = ipsec_if_output_error_strings,
 
-  .n_next_nodes = IPSEC_IF_OUTPUT_N_NEXT,
-
-  .next_nodes = {
-        [IPSEC_IF_OUTPUT_NEXT_ESP_ENCRYPT] = ESP_NODE,
-        [IPSEC_IF_OUTPUT_NEXT_DROP] = "error-drop",
-  },
+  .sibling_of = "ipsec-output-ip4",
 };
 /* *INDENT-ON* */
 
index 4662c1a..deaa7b7 100644 (file)
 #include <vnet/ipsec/ipsec.h>
 #include <vnet/ipsec/esp.h>
 
-#if DPDK_CRYPTO==1
-#define ESP_NODE "dpdk-esp-decrypt"
-#else
-#define ESP_NODE "esp-decrypt"
-#endif
-
-#define foreach_ipsec_input_next                \
-_(DROP, "error-drop")                           \
-_(ESP_DECRYPT, ESP_NODE)
-
-#define _(v, s) IPSEC_INPUT_NEXT_##v,
-typedef enum
-{
-  foreach_ipsec_input_next
-#undef _
-    IPSEC_INPUT_N_NEXT,
-} ipsec_input_next_t;
-
-
 #define foreach_ipsec_input_error                   \
  _(RX_PKTS, "IPSEC pkts received")                  \
  _(DECRYPTION_FAILED, "IPSEC decryption failed")
 
-
 typedef enum
 {
 #define _(sym,str) IPSEC_INPUT_ERROR_##sym,
@@ -262,7 +242,7 @@ ipsec_input_ip4_node_fn (vlib_main_t * vm,
                  p0->counter.bytes += clib_net_to_host_u16 (ip0->length);
                  vnet_buffer (b0)->ipsec.sad_index = p0->sa_index;
                  vnet_buffer (b0)->ipsec.flags = 0;
-                 next0 = IPSEC_INPUT_NEXT_ESP_DECRYPT;
+                 next0 = im->esp_decrypt_next_index;
                  vlib_buffer_advance (b0, ip4_header_bytes (ip0));
                  goto trace0;
                }
@@ -392,7 +372,7 @@ VLIB_NODE_FUNCTION_MULTIARCH (ipsec_input_ip4_node, ipsec_input_ip4_node_fn)
                  p0->counter.bytes += header_size;
                  vnet_buffer (b0)->ipsec.sad_index = p0->sa_index;
                  vnet_buffer (b0)->ipsec.flags = 0;
-                 next0 = IPSEC_INPUT_NEXT_ESP_DECRYPT;
+                 next0 = im->esp_decrypt_next_index;
                  vlib_buffer_advance (b0, header_size);
                  goto trace0;
                }
index df93b5e..1b8070d 100644 (file)
 
 #include <vnet/ipsec/ipsec.h>
 
-#if DPDK_CRYPTO==1
-#define ESP_NODE "dpdk-esp-encrypt"
-#else
-#define ESP_NODE "esp-encrypt"
-#endif
-
 #if WITH_LIBSSL > 0
 
-#define foreach_ipsec_output_next                \
-_(DROP, "error-drop")                            \
-_(ESP_ENCRYPT, ESP_NODE)
-
-#define _(v, s) IPSEC_OUTPUT_NEXT_##v,
-typedef enum
-{
-  foreach_ipsec_output_next
-#undef _
-    IPSEC_OUTPUT_N_NEXT,
-} ipsec_output_next_t;
-
-
 #define foreach_ipsec_output_error                   \
  _(RX_PKTS, "IPSec pkts received")                   \
  _(POLICY_DISCARD, "IPSec policy discard")           \
@@ -50,7 +31,6 @@ typedef enum
  _(POLICY_BYPASS, "IPSec policy bypass")             \
  _(ENCAPS_FAILED, "IPSec encapsulation failed")
 
-
 typedef enum
 {
 #define _(sym,str) IPSEC_OUTPUT_ERROR_##sym,