Files
m241Neelima/components/ip_net2-6.9/ipike/src/ipike_payload_delete.c
T
2026-07-30 11:19:44 +05:30

350 lines
12 KiB
C

/*
******************************************************************************
* SOURCE FILE
*
* Document no: @(#) $Name: VXWORKS_ITER40_2019102207 $ $RCSfile: ipike_payload_delete.c,v $ $Revision: 1.30.16.3 $
* $Source: /home/interpeak/CVSRoot/ipike/src/ipike_payload_delete.c,v $
* $Author: zan $ $Date: 2013-06-18 11:20:06 $
* $State: Exp $ $Locker: $
*
* INTERPEAK_COPYRIGHT_STRING
* Design and implementation by Kenneth Jonsson <kenneth@interpeak.se>
******************************************************************************
*/
/*
****************************************************************************
* 1 DESCRIPTION
****************************************************************************
*/
/* Delete payload (RFC 2408, chapter 3.15) */
/*
****************************************************************************
* 2 CONFIGURATION
****************************************************************************
*/
/*
****************************************************************************
* 3 INCLUDE FILES
****************************************************************************
*/
#include "ipike_h.h"
#include "ipike_config.h"
#include "ipike_exchange_informational.h"
#include "ipike_payload_delete.h"
#include "ipike_payload_proposal.h"
#include "ipike_doi.h"
#include "ipike_util.h"
#include "ipike_ipsec_sadb.h"
#include "ipike_pfkeyv2.h"
#include "ipike_sadb.h"
#include <ipcom_clib.h>
#include <ipcom_syslog.h>
/*
****************************************************************************
* 4 EXTERN PROTOTYPES
****************************************************************************
*/
/*
****************************************************************************
* 5 DEFINES
****************************************************************************
*/
/*
****************************************************************************
* 6 TYPES
****************************************************************************
*/
/*
****************************************************************************
* 7 LOCAL PROTOTYPES
****************************************************************************
*/
/*
*===========================================================================
* ipike_payload_delete_spi_data
*===========================================================================
* Description: Returns a pointer to the first SPI in the payload.
* Parameters: del - A delete payload.
* Returns: A pointer to the SPI data.
*
*/
IP_STATIC Ip_u8*
ipike_payload_delete_spi_data(Ipike_delete_payload* del);
/*
*===========================================================================
* ipike_payload_delete_ike_sa
*===========================================================================
* Description: Marks all IKE SA that was in the message for deletion.
* Parameters: del - A delete payload.
* Returns: IPIKE_SUCCESS
*
*/
IP_STATIC Ipike_error
ipike_payload_delete_ike_sa(Ipike_delete_payload* del);
/*
*===========================================================================
* ipike_payload_delete_ipsec_sa
*===========================================================================
* Description: Deletes all IPSec SAs that was in the message.
* Parameters: del - A delete payload.
* Returns: IPIKE_SUCCESS
*
*/
IP_STATIC Ipike_error
ipike_payload_delete_ipsec_sa(
Ipike_sadb_entry* ike_sa,
Ipike_delete_payload* del);
/*
****************************************************************************
* 8 DATA
****************************************************************************
*/
/*
****************************************************************************
* 9 LOCAL FUNCTIONS
****************************************************************************
*/
/*
*===========================================================================
* ipike_payload_delete_spi_data
*===========================================================================
*/
IP_STATIC Ip_u8 *
ipike_payload_delete_spi_data(Ipike_delete_payload *del)
{
return (Ip_u8 *) del + IPIKE_DELETE_HEADER_LENGTH;
}
/*
*===========================================================================
* ipike_payload_delete_ike_sa
*===========================================================================
*/
IP_STATIC Ipike_error
ipike_payload_delete_ike_sa(Ipike_delete_payload *del)
{
Ipike_sadb_entry* ike_sa;
Ip_u8* initiator_cookie;
Ip_u8* responder_cookie;
int i;
if (del->spi_size % IPIKE_ISAKMP_COOKIE_SIZE * 2 != 0)
return IPIKE_INVALID_VALUE;
for (i = 0; i < ip_ntohs(del->spi_count); i++)
{
initiator_cookie = ipike_payload_delete_spi_data(del) + i * IPIKE_ISAKMP_COOKIE_SIZE * 2;
responder_cookie = initiator_cookie + IPIKE_ISAKMP_COOKIE_SIZE;
if (IPIKE_SUCCESS == ipike_sadb_get(initiator_cookie,
responder_cookie,
IPIKE_SA_ACTIVE,
&ike_sa))
{
(void)ipike_sadb_set_state(IP_NULL, ike_sa, IPIKE_SA_DYING);
ipike_sadb_release(ike_sa);
}
}
return IPIKE_SUCCESS;
}
/*
*===========================================================================
* ipike_payload_delete_ipsec_sa
*===========================================================================
*/
IP_STATIC Ipike_error
ipike_payload_delete_ipsec_sa(
Ipike_sadb_entry* ike_sa,
Ipike_delete_payload* del)
{
Ipike_ipsec_sadb_entry* ipsec_sa, *nested_sa = IP_NULL;
Ip_u8* spi;
int i;
Ipike_value v;
if (ip_ntohs(del->spi_count) * 4 % del->spi_size != 0)
return IPIKE_INVALID_VALUE;
/* We should only receive delete on the peers inbound traffic. */
for (i = 0; i < ip_ntohs(del->spi_count); i++)
{
spi = ipike_payload_delete_spi_data(del) + i * 4;
if (IPIKE_SUCCESS == ipike_ipsec_sadb_hash_get(spi,
del->proto_id,
&ike_sa->peer_addr,
&ike_sa->local_addr,
&ipsec_sa))
{
if (ipsec_sa->nested != IP_NULL)
{
nested_sa = ipsec_sa->nested;
}
/* Report delete from our side. */
if (ipsec_sa->other != IP_NULL)
{
v.value = ipsec_sa->other->spi;
v.len = sizeof(ipsec_sa->other->spi);
ipike_informational_report_sa_delete(ike_sa, del->proto_id, &v);
ipike_ipsec_sadb_delete_sa(ipsec_sa->other);
}
/* Recheck if outbound SA delete caused a pfkeyv2 response
which invalidated the inbound SA.(for example triggered
by a keyadm flush */
if (IPIKE_SUCCESS == ipike_ipsec_sadb_hash_get(spi,
del->proto_id,
&ike_sa->peer_addr,
&ike_sa->local_addr,
&ipsec_sa))
{
ipike_ipsec_sadb_delete_sa(ipsec_sa);
/* remove any grouped SA's */
if(nested_sa != IP_NULL)
{
/* Delete internally! No report Vista style */
IPCOM_LOG0(DEBUG2,"ipike_payload_delete_ipsec_sa: Deleting grouped IPSEC SA");
ipike_ipsec_sadb_delete_sa(nested_sa->other);
ipike_ipsec_sadb_delete_sa(nested_sa);
nested_sa = IP_NULL;
}
}
}
}
return IPIKE_SUCCESS;
}
/*
****************************************************************************
* 10 PUBLIC FUNCTIONS
****************************************************************************
*/
/*
*===========================================================================
* ipike_payload_delete_new
*===========================================================================
*/
IP_GLOBAL Ipike_delete_payload*
ipike_payload_delete_new(
Ip_u32 doi,
Ip_u8 proto_id,
Ip_u8 spi_size,
Ip_u8* spi_data)
{
Ipike_delete_payload *ret;
ret = ipcom_calloc(1, IPIKE_DELETE_HEADER_LENGTH + spi_size);
if (IP_NULL == ret)
return IP_NULL;
ret->header.length = ip_htons(IPIKE_DELETE_HEADER_LENGTH + spi_size);
ret->header.next_payload = IPIKE_PAYLOAD_DELETE;
ret->doi = ip_htonl(doi);
ret->proto_id = proto_id;
ret->spi_size = spi_size;
ret->spi_count = ip_htons(1);
ipcom_memcpy(ipike_payload_delete_spi_data(ret), spi_data, ret->spi_size);
return ret;
}
/*
*===========================================================================
* ipike_payload_delete_check
*===========================================================================
*/
IP_GLOBAL Ipike_error
ipike_payload_delete_check(Ipike_delete_payload* del)
{
if (ip_ntohs(del->header.length) != IPIKE_DELETE_HEADER_LENGTH +
(Ip_u32) ip_ntohs(del->spi_count) * (Ip_u32) del->spi_size)
return IPIKE_ISAKMP_PAYLOAD_LENGTH_ERROR;
if (del->spi_size == 0)
{
IPCOM_LOG0(ERR, "ipike_payload_delete_check_payload: SPI size is 0");
return IPIKE_INVALID_VALUE;
}
return IPIKE_SUCCESS;
}
/*
*===========================================================================
* ipike_payload_delete_process_message
*===========================================================================
*/
IP_GLOBAL Ipike_error
ipike_payload_delete_process_message(
Ipike_sadb_entry* ike_sa,
Ipike_delete_payload* payload)
{
if (ip_ntohl(payload->doi) != IPIKE_DOI_IPSEC)
return IPIKE_DOI_UNSUPPORTED;
/*RFC2408 5.15
Deletion of Security Associations MUST always be performed under the protection of an ISAKMP SA.*/
if(ike_sa->state != IPIKE_SA_ACTIVE)
{
return IPIKE_FAILED;
}
if (payload->proto_id == IPIKE_PROTO_ISAKMP)
return ipike_payload_delete_ike_sa(payload);
else if(payload->proto_id == IPIKE_PROTO_IPSEC_AH || payload->proto_id == IPIKE_PROTO_IPSEC_ESP)
return ipike_payload_delete_ipsec_sa(ike_sa, payload);
return IPIKE_SUCCESS;
}
/*
*===========================================================================
* ipike_payload_delete_print
*===========================================================================
*/
IP_GLOBAL void
ipike_payload_delete_print(Ipike_delete_payload* del)
{
int i;
IPCOM_LOG1(DEBUG2, " DOI: %s",
ipike_doi_to_string(ip_ntohl(del->doi)));
IPCOM_LOG1(DEBUG2, " protocol ID: %s",
ipike_proposal_proto_id_to_string(del->proto_id));
for (i = 0; i < ip_ntohs(del->spi_count); i++)
{
char* spi_hex;
spi_hex = ipike_memory_to_string(ipike_payload_delete_spi_data(del) + i * del->spi_size,
del->spi_size, 4);
if (IP_NULL == spi_hex)
{
IPCOM_LOG0(CRIT, "ipike_payload_delete_print_payload: out of memory");
return;
}
IPCOM_LOG2(DEBUG2, " SPI %d: %s",
i + 1,
spi_hex);
ipcom_free(spi_hex);
}
}
/*
****************************************************************************
* END OF FILE
****************************************************************************
*/