summaryrefslogtreecommitdiffstats
path: root/src/vnet/ipsec
diff options
context:
space:
mode:
Diffstat (limited to 'src/vnet/ipsec')
-rw-r--r--src/vnet/ipsec/esp_encrypt.c4
-rw-r--r--src/vnet/ipsec/ipsec.api7
-rw-r--r--src/vnet/ipsec/ipsec.h2
-rw-r--r--src/vnet/ipsec/ipsec_api.c5
-rw-r--r--src/vnet/ipsec/ipsec_cli.c16
-rw-r--r--src/vnet/ipsec/ipsec_if.c8
6 files changed, 36 insertions, 6 deletions
diff --git a/src/vnet/ipsec/esp_encrypt.c b/src/vnet/ipsec/esp_encrypt.c
index ff9c1e63097..16f985c6cfe 100644
--- a/src/vnet/ipsec/esp_encrypt.c
+++ b/src/vnet/ipsec/esp_encrypt.c
@@ -279,7 +279,7 @@ esp_encrypt_inline (vlib_main_t * vm,
oh0->ip4.src_address.as_u32 = sa0->tunnel_src_addr.ip4.as_u32;
oh0->ip4.dst_address.as_u32 = sa0->tunnel_dst_addr.ip4.as_u32;
- vnet_buffer (o_b0)->sw_if_index[VLIB_TX] = (u32) ~ 0;
+ vnet_buffer (o_b0)->sw_if_index[VLIB_TX] = sa0->tx_fib_index;
}
else if (is_ip6 && sa0->is_tunnel && sa0->is_tunnel_ip6)
{
@@ -292,7 +292,7 @@ esp_encrypt_inline (vlib_main_t * vm,
oh6_0->ip6.dst_address.as_u64[1] =
sa0->tunnel_dst_addr.ip6.as_u64[1];
- vnet_buffer (o_b0)->sw_if_index[VLIB_TX] = (u32) ~ 0;
+ vnet_buffer (o_b0)->sw_if_index[VLIB_TX] = sa0->tx_fib_index;
}
else
{
diff --git a/src/vnet/ipsec/ipsec.api b/src/vnet/ipsec/ipsec.api
index 610f2325ebc..2b015f9c223 100644
--- a/src/vnet/ipsec/ipsec.api
+++ b/src/vnet/ipsec/ipsec.api
@@ -13,7 +13,7 @@
* limitations under the License.
*/
-option version = "2.0.0";
+option version = "2.1.0";
/** \brief IPsec: Add/delete Security Policy Database
@param client_index - opaque cookie to identify the sender
@@ -563,6 +563,7 @@ define ipsec_spd_interface_details {
@param renumber - intf display name uses a specified instance if != 0
@param show_instance - instance to display for intf if renumber is set
@param udp_encap - enable UDP encapsulation for NAT traversal
+ @param tx_table_id - the FIB id used after packet encap
*/
define ipsec_tunnel_if_add_del {
u32 client_index;
@@ -587,6 +588,7 @@ define ipsec_tunnel_if_add_del {
u8 renumber;
u32 show_instance;
u8 udp_encap;
+ u32 tx_table_id;
};
/** \brief Add/delete IPsec tunnel interface response
@@ -637,6 +639,7 @@ define ipsec_sa_dump {
@param replay_window - bit map of seq nums received relative to last_seq if using anti-replay
@param total_data_size - total bytes sent or received
@param udp_encap - 1 if UDP encap enabled, 0 otherwise
+ @param tx_table_id - the FIB id used for encapsulated packets
*/
define ipsec_sa_details {
u32 context;
@@ -669,6 +672,8 @@ define ipsec_sa_details {
u64 total_data_size;
u8 udp_encap;
+
+ u32 tx_table_id;
};
/** \brief Set key on IPsec interface
diff --git a/src/vnet/ipsec/ipsec.h b/src/vnet/ipsec/ipsec.h
index d40767001b8..691bc071bba 100644
--- a/src/vnet/ipsec/ipsec.h
+++ b/src/vnet/ipsec/ipsec.h
@@ -139,6 +139,7 @@ typedef struct
ip46_address_t tunnel_src_addr;
ip46_address_t tunnel_dst_addr;
+ u32 tx_fib_index;
u32 salt;
/* runtime */
@@ -183,6 +184,7 @@ typedef struct
u8 renumber;
u32 show_instance;
u8 udp_encap;
+ u32 tx_table_id;
} ipsec_add_del_tunnel_args_t;
typedef struct
diff --git a/src/vnet/ipsec/ipsec_api.c b/src/vnet/ipsec/ipsec_api.c
index 3f30a7dc321..59fb868f878 100644
--- a/src/vnet/ipsec/ipsec_api.c
+++ b/src/vnet/ipsec/ipsec_api.c
@@ -23,6 +23,7 @@
#include <vnet/interface.h>
#include <vnet/api_errno.h>
#include <vnet/ip/ip.h>
+#include <vnet/fib/fib.h>
#include <vnet/vnet_msg_enum.h>
@@ -471,6 +472,7 @@ vl_api_ipsec_tunnel_if_add_del_t_handler (vl_api_ipsec_tunnel_if_add_del_t *
tun.local_integ_key_len = mp->local_integ_key_len;
tun.remote_integ_key_len = mp->remote_integ_key_len;
tun.udp_encap = mp->udp_encap;
+ tun.tx_table_id = ntohl (mp->tx_table_id);
memcpy (&tun.local_ip, mp->local_ip, 4);
memcpy (&tun.remote_ip, mp->remote_ip, 4);
memcpy (&tun.local_crypto_key, &mp->local_crypto_key,
@@ -555,6 +557,9 @@ send_ipsec_sa_details (ipsec_sa_t * sa, vl_api_registration_t * reg,
mp->total_data_size = clib_host_to_net_u64 (sa->total_data_size);
mp->udp_encap = sa->udp_encap;
+ mp->tx_table_id =
+ htonl (fib_table_get_table_id (sa->tx_fib_index, FIB_PROTOCOL_IP4));
+
vl_api_send_msg (reg, (u8 *) mp);
}
diff --git a/src/vnet/ipsec/ipsec_cli.c b/src/vnet/ipsec/ipsec_cli.c
index f96551429af..f0717e91dd1 100644
--- a/src/vnet/ipsec/ipsec_cli.c
+++ b/src/vnet/ipsec/ipsec_cli.c
@@ -19,6 +19,7 @@
#include <vnet/api_errno.h>
#include <vnet/ip/ip.h>
#include <vnet/interface.h>
+#include <vnet/fib/fib.h>
#include <vnet/ipsec/ipsec.h>
@@ -80,6 +81,7 @@ ipsec_sa_add_del_command_fn (vlib_main_t * vm,
clib_error_t *error = NULL;
clib_memset (&sa, 0, sizeof (sa));
+ sa.tx_fib_index = ~((u32) 0); /* Only supported for ipsec interfaces */
if (!unformat_user (input, unformat_line_input, line_input))
return 0;
@@ -458,6 +460,7 @@ show_ipsec_command_fn (vlib_main_t * vm,
vnet_hw_interface_t *hi;
u8 *protocol = NULL;
u8 *policy = NULL;
+ u32 tx_table_id;
/* *INDENT-OFF* */
pool_foreach (sa, im->sad, ({
@@ -670,8 +673,11 @@ show_ipsec_command_fn (vlib_main_t * vm,
hi = vnet_get_hw_interface (im->vnet_main, t->hw_if_index);
vlib_cli_output(vm, " %s seq", hi->name);
sa = pool_elt_at_index(im->sad, t->output_sa_index);
- vlib_cli_output(vm, " seq %u seq-hi %u esn %u anti-replay %u udp-encap %u",
- sa->seq, sa->seq_hi, sa->use_esn, sa->use_anti_replay, sa->udp_encap);
+
+ tx_table_id = fib_table_get_table_id(sa->tx_fib_index, FIB_PROTOCOL_IP4);
+
+ vlib_cli_output(vm, " seq %u seq-hi %u esn %u anti-replay %u udp-encap %u tx-table %u",
+ sa->seq, sa->seq_hi, sa->use_esn, sa->use_anti_replay, sa->udp_encap, tx_table_id);
vlib_cli_output(vm, " local-spi %u local-ip %U", sa->spi,
format_ip4_address, &sa->tunnel_src_addr.ip4);
vlib_cli_output(vm, " local-crypto %U %U",
@@ -910,6 +916,8 @@ create_ipsec_tunnel_command_fn (vlib_main_t * vm,
a.is_add = 0;
else if (unformat (line_input, "udp-encap"))
a.udp_encap = 1;
+ else if (unformat (line_input, "tx-table %u", &a.tx_table_id))
+ ;
else
{
error = clib_error_return (0, "unknown input `%U'",
@@ -952,7 +960,9 @@ done:
/* *INDENT-OFF* */
VLIB_CLI_COMMAND (create_ipsec_tunnel_command, static) = {
.path = "create ipsec tunnel",
- .short_help = "create ipsec tunnel local-ip <addr> local-spi <spi> remote-ip <addr> remote-spi <spi> [instance <inst_num>] [udp-encap]",
+ .short_help = "create ipsec tunnel local-ip <addr> local-spi <spi> "
+ "remote-ip <addr> remote-spi <spi> [instance <inst_num>] [udp-encap] "
+ "[tx-table <table-id>]",
.function = create_ipsec_tunnel_command_fn,
};
/* *INDENT-ON* */
diff --git a/src/vnet/ipsec/ipsec_if.c b/src/vnet/ipsec/ipsec_if.c
index 2e0dae0a35d..3054af16765 100644
--- a/src/vnet/ipsec/ipsec_if.c
+++ b/src/vnet/ipsec/ipsec_if.c
@@ -18,6 +18,7 @@
#include <vnet/vnet.h>
#include <vnet/api_errno.h>
#include <vnet/ip/ip.h>
+#include <vnet/fib/fib.h>
#include <vnet/ipsec/ipsec.h>
#include <vnet/ipsec/esp.h>
@@ -262,6 +263,7 @@ ipsec_add_del_tunnel_if_internal (vnet_main_t * vnm,
ipsec_sa_t *sa;
u32 dev_instance;
u32 slot;
+ u32 tx_fib_index = ~0;
u64 key = (u64) args->remote_ip.as_u32 << 32 | (u64) args->remote_spi;
p = hash_get (im->ipsec_if_pool_index_by_key, key);
@@ -272,6 +274,10 @@ ipsec_add_del_tunnel_if_internal (vnet_main_t * vnm,
if (p)
return VNET_API_ERROR_INVALID_VALUE;
+ tx_fib_index = fib_table_find (FIB_PROTOCOL_IP4, args->tx_table_id);
+ if (tx_fib_index == ~((u32) 0))
+ return VNET_API_ERROR_NO_SUCH_FIB;
+
pool_get_aligned (im->tunnel_interfaces, t, CLIB_CACHE_LINE_BYTES);
clib_memset (t, 0, sizeof (*t));
@@ -301,6 +307,7 @@ ipsec_add_del_tunnel_if_internal (vnet_main_t * vnm,
sa->use_anti_replay = args->anti_replay;
sa->integ_alg = args->integ_alg;
sa->udp_encap = args->udp_encap;
+ sa->tx_fib_index = ~((u32) 0); /* Not used, but set for troubleshooting */
if (args->remote_integ_key_len <= sizeof (args->remote_integ_key))
{
sa->integ_key_len = args->remote_integ_key_len;
@@ -326,6 +333,7 @@ ipsec_add_del_tunnel_if_internal (vnet_main_t * vnm,
sa->use_anti_replay = args->anti_replay;
sa->integ_alg = args->integ_alg;
sa->udp_encap = args->udp_encap;
+ sa->tx_fib_index = tx_fib_index;
if (args->local_integ_key_len <= sizeof (args->local_integ_key))
{
sa->integ_key_len = args->local_integ_key_len;