return s;
}
+#define IKEV2_GENERATE_SA_INIT_OK_str ""
+#define IKEV2_GENERATE_SA_INIT_OK_ERR_NO_DH_STR \
+ "no DH group configured for IKE proposals!"
+#define IKEV2_GENERATE_SA_INIT_OK_ERR_UNSUPP_STR \
+ "DH group not supported!"
+
+typedef enum
+{
+ IKEV2_GENERATE_SA_INIT_OK,
+ IKEV2_GENERATE_SA_INIT_ERR_NO_DH,
+ IKEV2_GENERATE_SA_INIT_ERR_UNSUPPORTED_DH,
+} ikev2_generate_sa_error_t;
+
+static u8 *
+format_ikev2_gen_sa_error (u8 * s, va_list * args)
+{
+ ikev2_generate_sa_error_t e = va_arg (*args, ikev2_generate_sa_error_t);
+ switch (e)
+ {
+ case IKEV2_GENERATE_SA_INIT_OK:
+ break;
+ case IKEV2_GENERATE_SA_INIT_ERR_NO_DH:
+ s = format (s, IKEV2_GENERATE_SA_INIT_OK_ERR_NO_DH_STR);
+ break;
+ case IKEV2_GENERATE_SA_INIT_ERR_UNSUPPORTED_DH:
+ s = format (s, IKEV2_GENERATE_SA_INIT_OK_ERR_UNSUPP_STR);
+ break;
+ }
+ return s;
+}
+
#define foreach_ikev2_error \
_(PROCESSED, "IKEv2 packets processed") \
_(IKE_SA_INIT_RETRANSMIT, "IKE_SA_INIT retransmit ") \
}
}
-static void
+static ikev2_generate_sa_error_t
ikev2_generate_sa_init_data (ikev2_sa_t * sa)
{
ikev2_sa_transform_t *t = 0, *t2;
ikev2_main_t *km = &ikev2_main;
if (sa->dh_group == IKEV2_TRANSFORM_DH_TYPE_NONE)
- {
- return;
- }
+ return IKEV2_GENERATE_SA_INIT_ERR_NO_DH;
/* check if received DH group is on our list of supported groups */
vec_foreach (t2, km->supported_transforms)
if (!t)
{
sa->dh_group = IKEV2_TRANSFORM_DH_TYPE_NONE;
- return;
+ return IKEV2_GENERATE_SA_INIT_ERR_UNSUPPORTED_DH;
}
if (sa->is_initiator)
/* generate dh keys */
ikev2_generate_dh (sa, t);
+ return IKEV2_GENERATE_SA_INIT_OK;
}
static void
exchange, src, dst);
}
+static void
+ikev2_generate_sa_init_data_and_log (ikev2_sa_t * sa)
+{
+ ikev2_generate_sa_error_t rc = ikev2_generate_sa_init_data (sa);
+
+ if (PREDICT_TRUE (rc == IKEV2_GENERATE_SA_INIT_OK))
+ return;
+
+ if (rc == IKEV2_GENERATE_SA_INIT_ERR_NO_DH)
+ ikev2_elog_error (IKEV2_GENERATE_SA_INIT_OK_ERR_NO_DH_STR);
+ else if (rc == IKEV2_GENERATE_SA_INIT_ERR_UNSUPPORTED_DH)
+ ikev2_elog_error (IKEV2_GENERATE_SA_INIT_OK_ERR_UNSUPP_STR);
+}
+
static_always_inline uword
ikev2_node_internal (vlib_main_t * vm,
vlib_node_runtime_t * node, vlib_frame_t * frame,
sa0->r_proposals =
ikev2_select_proposal (sa0->i_proposals,
IKEV2_PROTOCOL_IKE);
- ikev2_generate_sa_init_data (sa0);
+ ikev2_generate_sa_init_data_and_log (sa0);
}
if (sa0->state == IKEV2_STATE_SA_INIT
valid_ip = 1;
}
- bi0 = ikev2_get_new_ike_header_buff (vm, &b0);
- if (!bi0)
- {
- char *errmsg = "buffer alloc failure";
- ikev2_log_error (errmsg);
- return clib_error_return (0, errmsg);
- }
- ike0 = vlib_buffer_get_current (b0);
-
/* Prepare the SA and the IKE payload */
ikev2_sa_t sa;
clib_memset (&sa, 0, sizeof (ikev2_sa_t));
sa.is_tun_itf_set = 1;
sa.initial_contact = 1;
sa.dst_port = IKEV2_PORT;
- ikev2_generate_sa_init_data (&sa);
+
+ ikev2_generate_sa_error_t rc = ikev2_generate_sa_init_data (&sa);
+ if (rc != IKEV2_GENERATE_SA_INIT_OK)
+ {
+ ikev2_sa_free_all_vec (&sa);
+ ikev2_payload_destroy_chain (chain);
+ return clib_error_return (0, "%U", format_ikev2_gen_sa_error, rc);
+ }
+
ikev2_payload_add_ke (chain, sa.dh_group, sa.i_dh_data);
ikev2_payload_add_nonce (chain, sa.i_nonce);
sig_hash_algo);
vec_free (sig_hash_algo);
+ bi0 = ikev2_get_new_ike_header_buff (vm, &b0);
+ if (!bi0)
+ {
+ ikev2_sa_free_all_vec (&sa);
+ ikev2_payload_destroy_chain (chain);
+ char *errmsg = "buffer alloc failure";
+ ikev2_log_error (errmsg);
+ return clib_error_return (0, errmsg);
+ }
+ ike0 = vlib_buffer_get_current (b0);
+
/* Buffer update and boilerplate */
len += vec_len (chain->data);
ike0->nextpayload = chain->first_payload_type;
p = pool_elt_at_index (km->profiles, sa->profile_index);
if (p)
{
- ikev2_initiate_sa_init (vm, p->name);
+ clib_error_t *e = ikev2_initiate_sa_init (vm, p->name);
+ if (e)
+ {
+ ikev2_log_error ("%U", format_clib_error, e);
+ clib_error_free (e);
+ }
}
}
}
error = ikev2_set_liveness_params (clib_net_to_host_u32 (mp->period),
clib_net_to_host_u32 (mp->max_retries));
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
error = ikev2_add_del_profile (vm, tmp, mp->is_add);
vec_free (tmp);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
vec_free (tmp);
vec_free (data);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
vec_free (tmp);
vec_free (data);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
error = ikev2_set_profile_udp_encap (vm, tmp);
vec_free (tmp);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
start_addr, end_addr, mp->ts.is_local);
vec_free (tmp);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
error = ikev2_set_local_key (vm, mp->key_file);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
error = ikev2_set_profile_responder (vm, tmp, sw_if_index, ip);
vec_free (tmp);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
ntohl (mp->tr.crypto_key_size));
vec_free (tmp);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
ntohl (mp->tr.crypto_key_size));
vec_free (tmp);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
(mp->lifetime_maxdata));
vec_free (tmp);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
ntohl (mp->sw_if_index));
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
vec_free (tmp);
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
error = ikev2_initiate_sa_init (vm, tmp);
vec_free (tmp);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
error = ikev2_initiate_delete_ike_sa (vm, mp->ispi);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
error = ikev2_initiate_delete_child_sa (vm, mp->ispi);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
error = ikev2_profile_natt_disable (tmp);
vec_free (tmp);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif
error = ikev2_initiate_rekey_child_sa (vm, mp->ispi);
if (error)
- rv = VNET_API_ERROR_UNSPECIFIED;
+ {
+ ikev2_log_error ("%U", format_clib_error, error);
+ clib_error_free (error);
+ rv = VNET_API_ERROR_UNSPECIFIED;
+ }
#else
rv = VNET_API_ERROR_UNIMPLEMENTED;
#endif