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

3234 lines
112 KiB
C

/* ipmacsec_debug.c - MACsec Debug implementation */
/*
* Copyright (c) 2010 Wind River Systems, Inc.
*
* The right to copy, distribute, modify, or otherwise make use
* of this software may be licensed only pursuant to the terms
* of an applicable Wind River license agreement.
*
*/
/*
modification history
--------------------
01a,04Mar10,mry Created
*/
/*
****************************************************************************
* 1 DESCRIPTION
****************************************************************************
*/
/*
* Implements the MACsec debug functionality (mostly used for debugging and
* unit/dev testing, and is typically not part of a production system).
* NOTE that all code protected by #ifdef IPMACSEC_UNIT_TEST is non supported
* code and not guaranteed to work as advertised.
*/
/*
****************************************************************************
* 2 INCLUDE FILES
****************************************************************************
*/
#define IPCOM_USE_CLIB_PROTO
#include <ipcom_type.h>
#include <ipcom_cstyle.h>
#include <ipcom_clib.h>
#include <ipcom_err.h>
#include <ipcom_sock.h>
#include <ipcom_syslog.h>
#include <ipcom_sysvar.h>
#include <ipcom_errno.h>
#include <ipcom_err.h>
#include <ipcom_os.h>
#include "ipmacsec_debug.h"
#include "ipmacsec_sysvar.h"
#include "ipmacsec_secy_mgmt.h"
#include "ipmacsec_h.h"
#include "ipmacsec.h"
#include "ipmacsec_netlink.h"
#include "ipmacsec_lmi.h"
/*
****************************************************************************
* 3 CONFIGURATION
****************************************************************************
*/
#include "ipmacsec_config.h"
/*
****************************************************************************
* 4 DEFINES
****************************************************************************
*/
#ifdef IPMACSEC_UNIT_TEST
/* Sysvars used in Unit Testing profiles */
#define IPMACSEC_UT_SYSVAR_SCI "ipmacsec.ut.secy.sci"
#define IPMACSEC_UT_SYSVAR_RX_SCI_1 "ipmacsec.ut.secy.rx.sci.1"
#endif
/*
****************************************************************************
* 5 TYPES
****************************************************************************
*/
/*
****************************************************************************
* 6 EXTERN PROTOTYPES
****************************************************************************
*/
/*
****************************************************************************
* 7 LOCAL PROTOTYPES
****************************************************************************
*/
/*
*
****************************************************************************
* 8 DATA
****************************************************************************
*/
#ifdef IPMACSEC_UNIT_TEST
/* Unit Test Keying material (Note that since this is only used for unit testing, keying material secrecy is not crucial )
* WARNING: DO NOT USE THE FOLLOWING KEYING MATERIAL AS PART OF A PRODUCTION SYSTEM. This will greatly diminish the security
* of the system.
*/
IP_STATIC Ip_u8 ipmacsec_ut_128b_keymaterial_1[16] =
{
0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F
};
IP_STATIC Ip_u8 ipmacsec_ut_128b_keymaterial_2[16] =
{
0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27,
0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x2D, 0x2E, 0x2F
};
IP_STATIC Ip_u8 ipmacsec_ut_128b_keymaterial_3[16] =
{
0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37,
0x38, 0x39, 0x3A, 0x3B, 0x3C, 0x3D, 0x3E, 0x3F
};
IP_STATIC Ip_u8 ipmacsec_ut_128b_keymaterial_4[16] =
{
0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47,
0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F
};
/* Unit Test SAK profiles */
IP_STATIC Ipmacsec_sak_profile ipmacsec_ut_sak_128b_key_1 =
{
0x0000000100008001ULL,
128/8,
ipmacsec_ut_128b_keymaterial_1
};
IP_STATIC Ipmacsec_sak_profile ipmacsec_ut_sak_128b_key_2 =
{
0x0000000100008002ULL,
128/8,
ipmacsec_ut_128b_keymaterial_2
};
IP_STATIC Ipmacsec_sak_profile ipmacsec_ut_sak_128b_key_3 =
{
0x0000000100008003ULL,
128/8,
ipmacsec_ut_128b_keymaterial_3
};
IP_STATIC Ipmacsec_sak_profile ipmacsec_ut_sak_128b_key_4 =
{
0x0000000100008004ULL,
128/8,
ipmacsec_ut_128b_keymaterial_4
};
/* Unit Test Profile #1: Use on Station A */
Ipmacsec_secy_profile ipmacsec_ut_profile_1A =
{
IPMACSEC_UT_SYSVAR_SCI, /*sci_sysvar*/
IPMACSEC_CIPHERSUITE_GCM_AES_128, /*cipher_suite_index*/
IP_TRUE, /*protectFrames*/
IP_TRUE, /*alwaysIncludeSCI*/
IP_TRUE, /*useES*/
IP_FALSE, /*useSCB*/
IPMACSEC_SECY_VALIDATEFRAMES_STRICT, /*validateFrames*/
IP_FALSE, /*replayProtect*/
0, /*replayWindow*/
0, /*confidentialityOffset*/
0, /*pn_threshold*/
IP_TRUE, /*info_notify*/
{
IP_TRUE, /*ControlledPortEnabled*/
IP_PORTIF_ADMIN_PTP_MAC_FORCE_AUTO /*adminPointToPointMAC*/
}, /*cp_profile*/
{
IP_TRUE, /*create*/
IP_NULL, /*sci_sysvar*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00010001, /*ref*/
&ipmacsec_ut_sak_128b_key_1, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_ON, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00010002, /*ref*/
&ipmacsec_ut_sak_128b_key_2, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_OFF, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
}, /*tx_sc_profile*/
{
{
IP_TRUE, /*create*/
IPMACSEC_UT_SYSVAR_RX_SCI_1, /*sci*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00020001, /*ref*/
&ipmacsec_ut_sak_128b_key_3, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00020002, /*ref*/
&ipmacsec_ut_sak_128b_key_4, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_OFF /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
} /*rx_sc_profile[0]*/
}
};
/* Unit Test Profile #1: Use on Station B */
Ipmacsec_secy_profile ipmacsec_ut_profile_1B =
{
IPMACSEC_UT_SYSVAR_SCI, /*sci_sysvar*/
IPMACSEC_CIPHERSUITE_GCM_AES_128, /*cipher_suite_index*/
IP_TRUE, /*protectFrames*/
IP_TRUE, /*alwaysIncludeSCI*/
IP_TRUE, /*useES*/
IP_FALSE, /*useSCB*/
IPMACSEC_SECY_VALIDATEFRAMES_STRICT, /*validateFrames*/
IP_FALSE, /*replayProtect*/
0, /*replayWindow*/
0, /*confidentialityOffset*/
0, /*pn_threshold*/
IP_TRUE, /*info_notify*/
{
IP_TRUE, /*ControlledPortEnabled*/
IP_PORTIF_ADMIN_PTP_MAC_FORCE_AUTO /*adminPointToPointMAC*/
}, /*cp_profile*/
{
IP_TRUE, /*create*/
IP_NULL, /*sci_sysvar*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00010001, /*ref*/
&ipmacsec_ut_sak_128b_key_3, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_ON, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00010002, /*ref*/
&ipmacsec_ut_sak_128b_key_4, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_OFF, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
}, /*tx_sc_profile*/
{
{
IP_TRUE, /*create*/
IPMACSEC_UT_SYSVAR_RX_SCI_1, /*sci*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00020001, /*ref*/
&ipmacsec_ut_sak_128b_key_1, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00020002, /*ref*/
&ipmacsec_ut_sak_128b_key_2, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
} /*rx_sc_profile[0]*/
}
};
/* Unit Test Profile #2: Use on Station A to test PN exhaustion */
Ipmacsec_secy_profile ipmacsec_ut_profile_2A =
{
IPMACSEC_UT_SYSVAR_SCI, /*sci_sysvar*/
IPMACSEC_CIPHERSUITE_GCM_AES_128, /*cipher_suite_index*/
IP_TRUE, /*protectFrames*/
IP_TRUE, /*alwaysIncludeSCI*/
IP_TRUE, /*useES*/
IP_FALSE, /*useSCB*/
IPMACSEC_SECY_VALIDATEFRAMES_STRICT, /*validateFrames*/
IP_FALSE, /*replayProtect*/
0, /*replayWindow*/
0, /*confidentialityOffset*/
0, /*pn_threshold*/
IP_TRUE, /*info_notify*/
{
IP_TRUE, /*ControlledPortEnabled*/
IP_PORTIF_ADMIN_PTP_MAC_FORCE_AUTO /*adminPointToPointMAC*/
}, /*cp_profile*/
{
IP_TRUE, /*create*/
IP_NULL, /*sci_sysvar*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00010001, /*ref*/
&ipmacsec_ut_sak_128b_key_1, /*sak_profile*/
0xfffffff0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_ON, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00010002, /*ref*/
&ipmacsec_ut_sak_128b_key_2, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_OFF, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
}, /*tx_sc_profile*/
{
{
IP_TRUE, /*create*/
IPMACSEC_UT_SYSVAR_RX_SCI_1, /*sci*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00020001, /*ref*/
&ipmacsec_ut_sak_128b_key_3, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00020002, /*ref*/
&ipmacsec_ut_sak_128b_key_4, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_OFF /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
} /*rx_sc_profile[0]*/
}
};
/* Unit Test Profile #2: Use on Station B. Can be used to test Replay Windows with profile 1 or exhaustion with profile 2 */
Ipmacsec_secy_profile ipmacsec_ut_profile_2B =
{
IPMACSEC_UT_SYSVAR_SCI, /*sci_sysvar*/
IPMACSEC_CIPHERSUITE_GCM_AES_128, /*cipher_suite_index*/
IP_TRUE, /*protectFrames*/
IP_TRUE, /*alwaysIncludeSCI*/
IP_TRUE, /*useES*/
IP_FALSE, /*useSCB*/
IPMACSEC_SECY_VALIDATEFRAMES_STRICT, /*validateFrames*/
IP_TRUE, /*replayProtect*/
2, /*replayWindow*/
0, /*confidentialityOffset*/
0, /*pn_threshold*/
IP_TRUE, /*info_notify*/
{
IP_TRUE, /*ControlledPortEnabled*/
IP_PORTIF_ADMIN_PTP_MAC_FORCE_AUTO /*adminPointToPointMAC*/
}, /*cp_profile*/
{
IP_TRUE, /*create*/
IP_NULL, /*sci_sysvar*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00010001, /*ref*/
&ipmacsec_ut_sak_128b_key_3, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_ON, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00010002, /*ref*/
&ipmacsec_ut_sak_128b_key_4, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_OFF, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
}, /*tx_sc_profile*/
{
{
IP_TRUE, /*create*/
IPMACSEC_UT_SYSVAR_RX_SCI_1, /*sci*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00020001, /*ref*/
&ipmacsec_ut_sak_128b_key_1, /*sak_profile*/
7, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
5, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00020002, /*ref*/
&ipmacsec_ut_sak_128b_key_2, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
} /*rx_sc_profile[0]*/
}
};
/* Unit Test Profile #3: Use on Station A */
Ipmacsec_secy_profile ipmacsec_ut_profile_3A =
{
IPMACSEC_UT_SYSVAR_SCI, /*sci_sysvar*/
IPMACSEC_CIPHERSUITE_GCM_AES_128, /*cipher_suite_index*/
IP_TRUE, /*protectFrames*/
IP_TRUE, /*alwaysIncludeSCI*/
IP_TRUE, /*useES*/
IP_FALSE, /*useSCB*/
IPMACSEC_SECY_VALIDATEFRAMES_CHECK, /*validateFrames*/
IP_FALSE, /*replayProtect*/
0, /*replayWindow*/
0, /*confidentialityOffset*/
0, /*pn_threshold*/
IP_TRUE, /*info_notify*/
{
IP_TRUE, /*ControlledPortEnabled*/
IP_PORTIF_ADMIN_PTP_MAC_FORCE_AUTO /*adminPointToPointMAC*/
}, /*cp_profile*/
{
IP_TRUE, /*create*/
IP_NULL, /*sci_sysvar*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00010001, /*ref*/
&ipmacsec_ut_sak_128b_key_1, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_OFF, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_ON, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00010002, /*ref*/
&ipmacsec_ut_sak_128b_key_2, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_OFF, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_OFF, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
}, /*tx_sc_profile*/
{
{
IP_TRUE, /*create*/
IPMACSEC_UT_SYSVAR_RX_SCI_1, /*sci*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00020001, /*ref*/
&ipmacsec_ut_sak_128b_key_3, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_OFF, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00020002, /*ref*/
&ipmacsec_ut_sak_128b_key_4, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_OFF, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_OFF /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
} /*rx_sc_profile[0]*/
}
};
/* Unit Test Profile #3: Use on Station B */
Ipmacsec_secy_profile ipmacsec_ut_profile_3B =
{
IPMACSEC_UT_SYSVAR_SCI, /*sci_sysvar*/
IPMACSEC_CIPHERSUITE_GCM_AES_128, /*cipher_suite_index*/
IP_FALSE, /*protectFrames*/
IP_TRUE, /*alwaysIncludeSCI*/
IP_TRUE, /*useES*/
IP_FALSE, /*useSCB*/
IPMACSEC_SECY_VALIDATEFRAMES_DISABLED, /*validateFrames*/
IP_FALSE, /*replayProtect*/
0, /*replayWindow*/
0, /*confidentialityOffset*/
0, /*pn_threshold*/
IP_TRUE, /*info_notify*/
{
IP_TRUE, /*ControlledPortEnabled*/
IP_PORTIF_ADMIN_PTP_MAC_FORCE_AUTO /*adminPointToPointMAC*/
}, /*cp_profile*/
{
IP_TRUE, /*create*/
IP_NULL, /*sci_sysvar*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00010001, /*ref*/
&ipmacsec_ut_sak_128b_key_3, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_OFF, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_ON, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00010002, /*ref*/
&ipmacsec_ut_sak_128b_key_4, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_OFF, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_OFF, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
}, /*tx_sc_profile*/
{
{
IP_TRUE, /*create*/
IPMACSEC_UT_SYSVAR_RX_SCI_1, /*sci*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00020001, /*ref*/
&ipmacsec_ut_sak_128b_key_1, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_OFF, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00020002, /*ref*/
&ipmacsec_ut_sak_128b_key_2, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_OFF, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
} /*rx_sc_profile[0]*/
}
};
#ifdef IPMACSEC_CRYPTO_ALLOW_NULL_CIPHER
/* NULL Cipher Unit Test Profile #1: Use on Station A */
Ipmacsec_secy_profile ipmacsec_ut_profile_null_ciph_1A =
{
IPMACSEC_UT_SYSVAR_SCI, /*sci_sysvar*/
IPMACSEC_CIPHERSUITE_NULL_CIPHER_128, /*cipher_suite_index*/
IP_TRUE, /*protectFrames*/
IP_TRUE, /*alwaysIncludeSCI*/
IP_TRUE, /*useES*/
IP_FALSE, /*useSCB*/
IPMACSEC_SECY_VALIDATEFRAMES_STRICT, /*validateFrames*/
IP_FALSE, /*replayProtect*/
0, /*replayWindow*/
0, /*confidentialityOffset*/
0, /*pn_threshold*/
IP_TRUE, /*info_notify*/
{
IP_TRUE, /*ControlledPortEnabled*/
IP_PORTIF_ADMIN_PTP_MAC_FORCE_AUTO /*adminPointToPointMAC*/
}, /*cp_profile*/
{
IP_TRUE, /*create*/
IP_NULL, /*sci_sysvar*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00010001, /*ref*/
&ipmacsec_ut_sak_128b_key_1, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_ON, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00010002, /*ref*/
&ipmacsec_ut_sak_128b_key_2, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_OFF, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
}, /*tx_sc_profile*/
{
{
IP_TRUE, /*create*/
IPMACSEC_UT_SYSVAR_RX_SCI_1, /*sci*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00020001, /*ref*/
&ipmacsec_ut_sak_128b_key_3, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00020002, /*ref*/
&ipmacsec_ut_sak_128b_key_4, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_OFF /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
} /*rx_sc_profile[0]*/
}
};
/* NULL Cipher Unit Test Profile #1: Use on Station A */
Ipmacsec_secy_profile ipmacsec_ut_profile_null_ciph_1B =
{
IPMACSEC_UT_SYSVAR_SCI, /*sci_sysvar*/
IPMACSEC_CIPHERSUITE_NULL_CIPHER_128, /*cipher_suite_index*/
IP_TRUE, /*protectFrames*/
IP_TRUE, /*alwaysIncludeSCI*/
IP_TRUE, /*useES*/
IP_FALSE, /*useSCB*/
IPMACSEC_SECY_VALIDATEFRAMES_STRICT, /*validateFrames*/
IP_FALSE, /*replayProtect*/
0, /*replayWindow*/
0, /*confidentialityOffset*/
0, /*pn_threshold*/
IP_TRUE, /*info_notify*/
{
IP_TRUE, /*ControlledPortEnabled*/
IP_PORTIF_ADMIN_PTP_MAC_FORCE_AUTO /*adminPointToPointMAC*/
}, /*cp_profile*/
{
IP_TRUE, /*create*/
IP_NULL, /*sci_sysvar*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00010001, /*ref*/
&ipmacsec_ut_sak_128b_key_3, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_ON, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00010002, /*ref*/
&ipmacsec_ut_sak_128b_key_4, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_OFF, /*enableTx*/
IPMACSEC_ENABLEFLAG_IGNORE /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
}, /*tx_sc_profile*/
{
{
IP_TRUE, /*create*/
IPMACSEC_UT_SYSVAR_RX_SCI_1, /*sci*/
{
{
IP_TRUE, /*create*/
0, /*an*/
0x00020001, /*ref*/
&ipmacsec_ut_sak_128b_key_1, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
}, /*Ipmacsec_sa_profile[0]*/
{
IP_TRUE, /*create*/
1, /*an*/
0x00020002, /*ref*/
&ipmacsec_ut_sak_128b_key_2, /*sak_profile*/
0, /*nextPN*/
IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, /*confidentiality*/
0, /*lowestPN*/
IPMACSEC_ENABLEFLAG_IGNORE, /*enableTx*/
IPMACSEC_ENABLEFLAG_ON /*enableRx*/
} /*Ipmacsec_sa_profile[1]*/
}
} /*rx_sc_profile[0]*/
}
};
#endif
#endif
/*
****************************************************************************
* 9 FUNCTIONS
****************************************************************************
*/
#ifdef IPMACSEC_UNIT_TEST
#ifdef IPMACSEC_UNIT_TEST_INLINE_HARDCODED_CONFIG
Ip_bool ipmacsec_dummy_key_change = IP_FALSE;
/*
*===========================================================================
* ipmacsec_secy_unittest_create_dummy_key
*===========================================================================
* Description:
* Parameters:
* Returns:
*
*/
IP_STATIC Ipmacsec_secy_key *
ipmacsec_secy_unittest_create_dummy_key(Ipnet_secy *secy) {
Ip_u32 i;
Ipmacsec_secy_sak dummy_sak;
IP_STATIC Ip_u64 id = 0;
Ipmacsec_secy_key_id key_id;
dummy_sak.num_octets = 128/8;
dummy_sak.buf = ipcom_malloc(dummy_sak.num_octets);
if (!dummy_sak.buf) {
return IP_NULL;
}
for (i=0; i < dummy_sak.num_octets; i++)
ipcom_memset(dummy_sak.buf, 0xae^(1<<i), dummy_sak.num_octets);
if (ipmacsec_dummy_key_change)
dummy_sak.buf[0] = 0;
key_id.val = ++id;
return ipmacsec_secy_create_key(secy, &dummy_sak, &key_id);
}
/*
*===========================================================================
* ipmacsec_secy_unittest_create_all
*===========================================================================
* Description:
* Parameters:
* Returns:
*
*/
IP_STATIC int
ipmacsec_secy_unittest_create_all(Ipnet_secy *secy) {
Ip_u8 an;
Ip_u8 dummy_sci[IPMACSEC_SCI_LEN];
Ipmacsec_secy_sc *sc;
ip_assert(secy);
for (an=0; an < secy->config.maxTxKeys; an++) {
Ipmacsec_secy_sa *sa;
Ipmacsec_secy_key *dummy_key;
dummy_key = ipmacsec_secy_unittest_create_dummy_key(secy);
if (!dummy_key) {
return -1;
}
if (ipmacsec_secy_install_key(secy, dummy_key, IPMACSEC_KEYTYPE_TRANSMIT | IPMACSEC_KEYTYPE_RECEIVE) != 0) {
return -1;
}
sa = ipmacsec_secy_create_tx_sa(secy, an, (an+1)<<8, 1, IPMACSEC_CONFIDENTIALITY_UNSPECIFIED, dummy_key);
if (sa == IP_NULL) {
return -1;
}
if (ipmacsec_secy_enable_tx_sa(secy, sa, IP_TRUE) != 0) {
return -1;
}
}
IPCOM_LOG1(INFO, "IPMACSEC-UTEST: Successfully created SecY Tx SAs for interface %s", secy->netif->ipcom.name);
ipcom_memset(dummy_sci, 0xAE, IPMACSEC_SCI_LEN);
sc = ipmacsec_secy_create_rx_sc(secy, dummy_sci);
if (!sc) {
return -1;
}
IPCOM_LOG1(INFO, "IPMACSEC-UTEST: Successfully created SecY Rx SC for interface %s", secy->netif->ipcom.name);
for (an=0; an < secy->config.maxRxKeys; an++) {
Ipmacsec_secy_sa *sa;
Ipmacsec_secy_key *dummy_key;
dummy_key = ipmacsec_secy_unittest_create_dummy_key(secy);
if (!dummy_key) {
return -1;
}
if (ipmacsec_secy_install_key(secy, dummy_key, IPMACSEC_KEYTYPE_TRANSMIT | IPMACSEC_KEYTYPE_RECEIVE) != 0) {
return -1;
}
sa = ipmacsec_secy_create_rx_sa(secy, sc, an, (an+1)<<16, 1, 0, dummy_key);
if (sa == IP_NULL) {
return -1;
}
if (ipmacsec_secy_enable_rx_sa(secy, sa, IP_TRUE) != 0) {
return -1;
}
}
IPCOM_LOG1(INFO, "IPMACSEC-UTEST: Successfully created SecY Rx SAs for interface %s", secy->netif->ipcom.name);
return 0;
}
/*
*===========================================================================
* ipmacsec_secy_unittest_delete_all
*===========================================================================
* Description:
* Parameters:
* Returns:
*
*/
IPMACSEC_PRIVATE int
ipmacsec_secy_unittest_delete_all(Ipnet_secy *secy) {
Ipmacsec_secy_sc *sc;
Ip_u8 dummy_sci[IPMACSEC_SCI_LEN];
sc = ipmacsec_secy_lookup_rx_sc(secy, dummy_sci);
if (!sc) {
return -1;
}
if (ipmacsec_secy_delete_rx_sc(secy, sc) != 0) {
return -1;
}
return 0;
}
/*
*===========================================================================
* ipmacsec_secy_unittest_setup
*===========================================================================
* Description:
* Parameters:
* Returns:
*
*/
IPMACSEC_PRIVATE int
ipmacsec_secy_unittest_setup(Ipnet_secy *secy) {
if (ipmacsec_secy_unittest_create_all(secy) != 0) {
IPCOM_LOG1(ERR, "IPMACSEC-UTEST: Failed to create Tx SAs for interface %s", secy->netif->ipcom.name);
return -1;
}
return 0;
}
/*
*===========================================================================
* ipmacsec_secy_unittest_destroy
*===========================================================================
* Description:
* Parameters:
* Returns:
*
*/
IPMACSEC_PRIVATE int
ipmacsec_secy_unittest_destroy(Ipnet_secy *secy) {
(void)ipmacsec_secy_unittest_delete_all(secy);
return 0;
}
#endif /* IPMACSEC_UNIT_TEST_INLINE_HARDCODED_CONFIG */
IP_STATIC Ip_bool ipmacsec_netlink_monitor_test_exit = IP_FALSE;
/*
*===========================================================================
* ipmacsec_netlink_monitor_test_callback
*===========================================================================
* Description: SecY Monitor test callback routine
* Parameters:
* Returns:
*
*/
IP_STATIC int ipmacsec_netlink_monitor_test_callback(struct Ip_nlmsghdr *nlmsg, int error) {
IPCOM_LOG1(DEBUG2, "IPMACSEC-NLMON_TEST: callback invoked with error = %d", error);
if (nlmsg) {
IPCOM_LOG3(DEBUG2,"IPMACSEC-NLMON_TEST: callback received nlmsg->nlmsg_type=%d (%s), nlmsg->nlmsg_len=%u",
nlmsg->nlmsg_type, ipmacsec_netlink_type_name(nlmsg->nlmsg_type), nlmsg->nlmsg_len);
}
if (ipmacsec_netlink_monitor_test_exit) {
/* User indicated exit condition */
ipmacsec_netlink_monitor_test_exit = IP_FALSE;
return -1;
}
return 0;
}
/*
*===========================================================================
* ipmacsec_netlink_monitor_test
*===========================================================================
* Description: Start a netlink monitor to capture all notifications
* Runs in the caller context
* Parameters: timeout- timeout value in seconds
* Returns: 0 upon success, <0 otherwise
*
*/
IP_GLOBAL int ipmacsec_netlink_monitor_test(Ip_u32 timeout) {
Ipmacsec_netlink_handle *nlhandle;
struct Ip_timeval tv;
Ip_u32 groups;
int ret = -1;
tv.tv_sec = timeout;
tv.tv_usec = 0;
groups = IP_NLMSG_GROUP_MASK(IPMACSEC_NLGRP_NOTIFY) | IP_NLMSG_GROUP_MASK(IPMACSEC_NLGRP_MONITOR);
nlhandle = ipmacsec_netlink_open(groups);
if (!nlhandle) {
IPCOM_LOG0(ERR, "IPMACSEC-NLMON_TEST: ipmacsec_netlink_open() returned NULL handle");
goto error_out;
}
IPCOM_LOG1(DEBUG2, "IPMACSEC-NLMON_TEST: nlhandle = 0x%x", nlhandle);
/* Register */
ret = ipmacsec_netlink_register(nlhandle, ipmacsec_netlink_monitor_test_callback, &tv, IP_TRUE);
if (ret < 0) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMON_TEST: ipmacsec_netlink_register() returned %d", ret);
goto error_out;
}
/* Invoke the netlink loop */
ret = ipmacsec_netlink_loop(nlhandle);
IPCOM_LOG0(INFO, "IPMACSEC-NLMON_TEST: ipmacsec_netlink_loop() terminated");
error_out:
ipmacsec_netlink_close(nlhandle);
IPCOM_LOG1(INFO, "IPMACSEC-NLMON_TEST: Exiting with ret = %d", ret);
return ret;
}
/*
*===========================================================================
* ipmacsec_secy_mon_testd
*===========================================================================
* Description: MACsec SecY Uncontrolled Port reception test daemon
* Parameters:
* Returns:
*
*/
IP_STATIC
IPCOM_PROCESS(ipmacsec_secy_mon_testd) {
char ifname[IP_IFNAMSIZ];
Ip_size_t len;
int ret;
Ip_u32 timeout;
char *sysvar;
char strval[16];
Ip_u32 pid;
IPCOM_LOG0(DEBUG2, "ipmacsec_secy_mon_testd :: Started");
ipcom_proc_init();
sysvar = "ipmacsec.secy.ut.montestd.ifname";
len = IP_IFNAMSIZ;
if (ipcom_sysvar_get(sysvar, ifname, &len) == IP_NULL) {
IPCOM_LOG1(WARNING, "ipmacsec_secy_mon_testd :: Failed to get sysvar %s", sysvar);
goto exit;
}
sysvar = "ipmacsec.secy.ut.montestd.timeout";
len = sizeof(strval);
if (ipcom_sysvar_get(sysvar, strval, &len) == IP_NULL) {
IPCOM_LOG1(WARNING, "ipmacsec_secy_ucp_testd :: Failed to get sysvar %s", sysvar);
goto exit;
}
timeout = ipcom_atoi(strval);
ret = ipmacsec_lmi_monitor_start(timeout, IP_TRUE, &pid, IP_NULL, 0);
exit:
IPCOM_LOG1(DEBUG2, "ipmacsec_secy_mon_testd :: Exiting (ret = %d)", ret);
ipcom_proc_exit();
}
/*
*===========================================================================
* ipmacsec_secy_monitor_test_start_daemon
*===========================================================================
* Description: Start a MACsec SecY Monitor test daemon
* Should only start one daemon at a time.
* Parameters: ifname - Interface bame
* num_expected_pkts - # of packets to expect before existing (0 ==> loop forever or until timeout)
* timeout - # of seconds before timing out (in seconds) (0 ==> no timeout)
* Returns: 0 upon successfully starting the daemon, <0 on error
*
*/
IP_GLOBAL int ipmacsec_secy_monitor_test_start_daemon(char *ifname, Ip_u32 timeout) {
Ipcom_proc_attr proc_attr;
char *sysvar;
char strval[16];
Ip_err rc;
sysvar = "ipmacsec.secy.ut.montestd.ifname";
if ((rc = ipcom_sysvar_set(sysvar, ifname, IPCOM_SYSVAR_FLAG_OVERWRITE)) != IPCOM_SUCCESS) {
IPCOM_LOG1(CRIT, "ipmacsec_secy_monitor_test_start_daemon :: Failed to set sysvar %s", sysvar);
return rc;
}
ipcom_snprintf(strval, sizeof(strval), "%d", timeout);
sysvar = "ipmacsec.secy.ut.montestd.timeout";
if ((rc = ipcom_sysvar_set(sysvar, strval, IPCOM_SYSVAR_FLAG_OVERWRITE)) != IPCOM_SUCCESS) {
IPCOM_LOG1(CRIT, "ipmacsec_secy_monitor_test_start_daemon :: Failed to set sysvar %s", sysvar);
return rc;
}
ipcom_proc_attr_init(&proc_attr);
proc_attr.stacksize = IPCOM_PROC_STACK_SMALL;
rc = ipcom_proc_acreate("secy_mon_testd", ipmacsec_secy_mon_testd, &proc_attr, IP_NULL);
return rc;
}
/*
*===========================================================================
* ipmacsec_netlink_test
*===========================================================================
* Description: Execute some netlink message tests
* Parameters: none
* Returns: 0 upon success, <0 otherwise
*
*/
IP_GLOBAL int ipmacsec_netlink_test(void) {
Ipmacsec_netlink_handle *nlhandle;
struct Ip_nlmsghdr empty_request;
struct {
struct Ip_nlmsghdr nlh;
Ip_u32 command;
} request;
Ipmacsec_buffer response;
int ret = -1;
Ip_u32 num_exec_tests = 0, num_failed_tests = 0;
nlhandle = ipmacsec_netlink_open(IPMACSEC_NLGRP_NONE);
if (!nlhandle) {
IPCOM_LOG0(ERR, "IPMACSEC-NLTEST: ipmacsec_netlink_open() returned NULL handle");
goto nl_test_done;
}
/* send an uninitialized request */
num_exec_tests++;
IPCOM_LOG1(INFO, "IPMACSEC-NLTEST: Executing test #%u", num_exec_tests);
ipcom_memset(&empty_request, 0, sizeof(empty_request));
empty_request.nlmsg_len = IP_NLMSG_LENGTH(0);
ret = ipmacsec_netlink_request(nlhandle, &empty_request, IP_NULL);
if (ret < 0) {
IPCOM_LOG0(INFO,
"IPMACSEC-NLTEST: ipmacsec_netlink_request() with INVALID request/NULL response failed (expepcted result)");
} else {
IPCOM_LOG0(ERR,
"IPMACSEC-NLTEST: ipmacsec_netlink_request() with INVALID request/NULL response succeeded (unexpepcted result)");
num_failed_tests++;
}
/* Just send an empty request */
num_exec_tests++;
IPCOM_LOG1(INFO, "IPMACSEC-NLTEST: Executing test #%u", num_exec_tests);
ipcom_memset(&empty_request, 0, sizeof(empty_request));
empty_request.nlmsg_len = IP_NLMSG_LENGTH(0);
empty_request.nlmsg_type = IPMACSEC_NLTYPE_TEST;
ret = ipmacsec_netlink_request(nlhandle, &empty_request, IP_NULL);
if (ret < 0) {
IPCOM_LOG0(ERR, "IPMACSEC-NLTEST: ipmacsec_netlink_request() with EMPTY TEST request/NULL response failed");
num_failed_tests++;
} else {
IPCOM_LOG0(INFO, "IPMACSEC-NLTEST: ipmacsec_netlink_request() with EMPTY TEST request/NULL response succeeded");
}
/* Now send a non empty test request with a NULL response */
num_exec_tests++;
IPCOM_LOG1(INFO, "IPMACSEC-NLTEST: Executing test #%u", num_exec_tests);
ipcom_memset(&request, 0, sizeof(request));
request.nlh.nlmsg_type = IPMACSEC_NLTYPE_TEST;
request.nlh.nlmsg_len = IP_NLMSG_LENGTH(sizeof(request.command));
request.command = 0;
ret = ipmacsec_netlink_request(nlhandle, &request.nlh, IP_NULL);
if (ret < 0) {
IPCOM_LOG0(ERR, "IPMACSEC-NLTEST: ipmacsec_netlink_request() with TEST request/NULL response failed");
num_failed_tests++;
} else {
IPCOM_LOG0(INFO, "IPMACSEC-NLTEST: ipmacsec_netlink_request() with TEST request/NULL response succeeded");
}
/* Now send a non empty test request with an expcted response */
num_exec_tests++;
IPCOM_LOG1(INFO, "IPMACSEC-NLTEST: Executing test #%u", num_exec_tests);
IPMACSEC_BUF_INIT(&response);
IPMACSEC_BUF_ALLOC(&response, IP_NLMSG_LENGTH(0));
if (!IPMACSEC_BUF_VERIFY(&response)) {
IPCOM_LOG0(CRIT, "IPMACSEC-NLTEST: failed to alloc response");
goto nl_test_done;
}
ipcom_memset(&request, 0, sizeof(request));
request.nlh.nlmsg_type = IPMACSEC_NLTYPE_TEST;
request.nlh.nlmsg_len = IP_NLMSG_LENGTH(sizeof(request.command));
request.command = 0;
ret = ipmacsec_netlink_request(nlhandle, &request.nlh, &response);
if (ret < 0) {
IPCOM_LOG0(ERR, "IPMACSEC-NLTEST: ipmacsec_netlink_request() with TEST request/response failed");
num_failed_tests++;
goto nl_test_done;
}
if (!IPMACSEC_BUF_VERIFY(&response)) {
IPCOM_LOG0(ERR, "IPMACSEC-NLTEST: invalid response");
num_failed_tests++;
goto nl_test_done;
}
if (response.size < IP_NLMSG_LENGTH(0)) {
IPCOM_LOG1(ERR, "IPMACSEC-NLTEST: invalid response size %u", response.size);
num_failed_tests++;
goto nl_test_done;
}
if (response.truncated) {
IPCOM_LOG0(DEBUG2, "IPMACSEC-NLTEST: response truncated");
}
IPCOM_LOG0(INFO, "IPMACSEC-NLTEST: ipmacsec_netlink_request() with TEST request/ response succeeded");
nl_test_done:
ipmacsec_netlink_close(nlhandle);
if (num_failed_tests) {
IPCOM_LOG2(ERR, "IPMACSEC-NLTEST: COMPLETED WITH FAILURES - %u tests executed, %u failed",
num_exec_tests, num_failed_tests);
ret = -1;
} else {
IPCOM_LOG1(INFO, "IPMACSEC-NLTEST: COMPLETED SUCCESSFULLY - %u tests executed successfully", num_exec_tests);
ret = 0;
}
return ret;
}
/*
*===========================================================================
* ipmacsec_netlink_multi_test
*===========================================================================
* Description: Send a Mutli netlink message requests (without using an lmi handle)
* Parameters: ifname - Interface name to send to. Must be attached 1st
* otherwise this test will fail.
* Returns: 0 upon success, <0 otherwise
*
*/
IP_GLOBAL int ipmacsec_netlink_multi_test(char *ifname) {
Ipmacsec_buffer request, response;
Ip_bool en = IP_FALSE, doEnable = IP_FALSE;
int ret = -1;
Ip_u32 num_exec_tests = 0, num_failed_tests = 0;
if (!ifname) {
IPCOM_LOG0(ERR, "IPMACSEC-NLMULTI_TEST: NULL ifname. Test not executed.");
return -1;
}
/* Init and alloc buffers */
IPMACSEC_BUF_INIT(&request);
IPMACSEC_BUF_INIT(&response);
if (ipmacsec_nlmsg_alloc(&request) == IP_NULL) {
IPCOM_LOG0(CRIT, "IPMACSEC-NLMULTI_TEST: failed to alloc request");
goto err_out;
}
if (ipmacsec_nlmsg_alloc(&response) == IP_NULL) {
IPCOM_LOG0(CRIT, "IPMACSEC-NLMULTI_TEST: failed to alloc response");
goto err_out;
}
/* 1- Disable and check status */
num_exec_tests++;
IPCOM_LOG1(INFO, "IPMACSEC-NLMULTI_TEST: Executing test #%u", num_exec_tests);
doEnable = IP_FALSE;
ret = ipmacsec_lmi_secy_set_cmd_append(&request, IP_NULL, ifname, IPMACSEC_LMICMD_SECY_ENABLED, &doEnable, sizeof(doEnable));
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_secy_set_cmd_append() failed (ret=%d)", ret);
num_failed_tests++;
goto test_2;
}
ret = ipmacsec_lmi_secy_get_cmd_append(&request, IP_NULL, ifname, IPMACSEC_LMICMD_SECY_ENABLED, IP_NULL, 0);
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_secy_get_cmd_append() failed (ret=%d)", ret);
num_failed_tests++;
goto test_2;
}
ret = ipmacsec_lmi_cmd_send(IP_NULL, &request, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_cmd_send() failed (ret=%d)", ret);
num_failed_tests++;
goto test_2;
}
ret = ipmacsec_lmi_cmd_parse_response(&response, ifname, IPMACSEC_LMICMD_SECY_ENABLED, &en, sizeof(en));
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_cmd_parse_response() failed (ret=%d)", ret);
num_failed_tests++;
goto test_2;
}
if (en != doEnable) {
IPCOM_LOG2(ERR, "IPMACSEC-NLMULTI_TEST: mismatched results (en=%u, doEnable=%u)", en, doEnable);
num_failed_tests++;
goto test_2;
}
test_2:
/* 2- Enable and check status */
num_exec_tests++;
IPCOM_LOG1(INFO, "IPMACSEC-NLMULTI_TEST: Executing test #%u", num_exec_tests);
IPMACSEC_BUF_WIPE(&request);
IPMACSEC_BUF_WIPE(&response);
doEnable = IP_TRUE;
ret = ipmacsec_lmi_secy_set_cmd_append(&request, IP_NULL, ifname, IPMACSEC_LMICMD_SECY_ENABLED, &doEnable, sizeof(doEnable));
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_secy_set_cmd_append() failed (ret=%d)", ret);
num_failed_tests++;
goto test_3;
}
ret = ipmacsec_lmi_secy_get_cmd_append(&request, IP_NULL, ifname, IPMACSEC_LMICMD_SECY_ENABLED, IP_NULL, 0);
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_secy_get_cmd_append() failed (ret=%d)", ret);
num_failed_tests++;
goto test_3;
}
ret = ipmacsec_lmi_cmd_send(IP_NULL, &request, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_cmd_send() failed (ret=%d)", ret);
num_failed_tests++;
goto test_3;
}
ret = ipmacsec_lmi_cmd_parse_response(&response, ifname, IPMACSEC_LMICMD_SECY_ENABLED, &en, sizeof(en));
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_cmd_parse_response() failed (ret=%d)", ret);
num_failed_tests++;
goto test_3;
}
if (en != doEnable) {
IPCOM_LOG2(ERR, "IPMACSEC-NLMULTI_TEST: mismatched results (en=%u, doEnable=%u)", en, doEnable);
num_failed_tests++;
goto test_3;
}
test_3:
/* 3- Disable/Enable and check status */
num_exec_tests++;
IPCOM_LOG1(INFO, "IPMACSEC-NLMULTI_TEST: Executing test #%u", num_exec_tests);
IPMACSEC_BUF_WIPE(&request);
IPMACSEC_BUF_WIPE(&response);
doEnable = IP_FALSE;
ret = ipmacsec_lmi_secy_set_cmd_append(&request, IP_NULL, ifname, IPMACSEC_LMICMD_SECY_ENABLED, &doEnable, sizeof(doEnable));
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_secy_set_cmd_append() failed (ret=%d)", ret);
num_failed_tests++;
goto test_4;
}
doEnable = IP_TRUE;
ret = ipmacsec_lmi_secy_set_cmd_append(&request, IP_NULL, ifname, IPMACSEC_LMICMD_SECY_ENABLED, &doEnable, sizeof(doEnable));
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_secy_set_cmd_append() failed (ret=%d)", ret);
num_failed_tests++;
goto test_4;
}
ret = ipmacsec_lmi_secy_get_cmd_append(&request, IP_NULL, ifname, IPMACSEC_LMICMD_SECY_ENABLED, IP_NULL, 0);
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_secy_get_cmd_append() failed (ret=%d)", ret);
num_failed_tests++;
goto test_4;
}
ret = ipmacsec_lmi_cmd_send(IP_NULL, &request, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_cmd_send() failed (ret=%d)", ret);
num_failed_tests++;
goto test_4;
}
ret = ipmacsec_lmi_cmd_parse_response(&response, ifname, IPMACSEC_LMICMD_SECY_ENABLED, &en, sizeof(en));
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_cmd_parse_response() failed (ret=%d)", ret);
num_failed_tests++;
goto test_4;
}
if (en != doEnable) {
IPCOM_LOG2(ERR, "IPMACSEC-NLMULTI_TEST: mismatched results (en=%u, doEnable=%u)", en, doEnable);
num_failed_tests++;
goto test_4;
}
test_4:
/* 4- Disable/Enable/Disable and check status */
num_exec_tests++;
IPCOM_LOG1(INFO, "IPMACSEC-NLMULTI_TEST: Executing test #%u", num_exec_tests);
IPMACSEC_BUF_WIPE(&request);
IPMACSEC_BUF_WIPE(&response);
doEnable = IP_FALSE;
ret = ipmacsec_lmi_secy_set_cmd_append(&request, IP_NULL, ifname, IPMACSEC_LMICMD_SECY_ENABLED, &doEnable, sizeof(doEnable));
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_secy_set_cmd_append() failed (ret=%d)", ret);
num_failed_tests++;
goto test_5;
}
doEnable = IP_TRUE;
ret = ipmacsec_lmi_secy_set_cmd_append(&request, IP_NULL, ifname, IPMACSEC_LMICMD_SECY_ENABLED, &doEnable, sizeof(doEnable));
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_secy_set_cmd_append() failed (ret=%d)", ret);
num_failed_tests++;
goto test_5;
}
doEnable = IP_FALSE;
ret = ipmacsec_lmi_secy_set_cmd_append(&request, IP_NULL, ifname, IPMACSEC_LMICMD_SECY_ENABLED, &doEnable, sizeof(doEnable));
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_secy_set_cmd_append() failed (ret=%d)", ret);
num_failed_tests++;
goto test_5;
}
ret = ipmacsec_lmi_secy_get_cmd_append(&request, IP_NULL, ifname, IPMACSEC_LMICMD_SECY_ENABLED, IP_NULL, 0);
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_secy_get_cmd_append() failed (ret=%d)", ret);
num_failed_tests++;
goto test_5;
}
ret = ipmacsec_lmi_cmd_send(IP_NULL, &request, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_cmd_send() failed (ret=%d)", ret);
num_failed_tests++;
goto test_5;
}
ret = ipmacsec_lmi_cmd_parse_response(&response, ifname, IPMACSEC_LMICMD_SECY_ENABLED, &en, sizeof(en));
if (ret != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-NLMULTI_TEST: ipmacsec_lmi_cmd_parse_response() failed (ret=%d)", ret);
num_failed_tests++;
goto test_5;
}
if (en != doEnable) {
IPCOM_LOG2(ERR, "IPMACSEC-NLMULTI_TEST: mismatched results (en=%u, doEnable=%u)", en, doEnable);
num_failed_tests++;
goto test_5;
}
test_5:
err_out:
ipmacsec_nlmsg_free(&request);
ipmacsec_nlmsg_free(&response);
if (num_failed_tests) {
IPCOM_LOG2(ERR, "IPMACSEC-NLMULTI_TEST: COMPLETED WITH FAILURES - %u tests executed, %u failed",
num_exec_tests, num_failed_tests);
ret = -1;
} else {
IPCOM_LOG1(INFO, "IPMACSEC-NLMULTI_TEST: COMPLETED SUCCESSFULLY - %u tests executed successfully", num_exec_tests);
ret = 0;
}
return ret;
}
/*
*===========================================================================
* ipmacsec_key_test
*===========================================================================
* Description: Test the key install/remove operations.
* Parameters: ifname - Interface name to send to. Must be attached 1st
* otherwise this test will fail.
* Returns: 0 upon success, <0 otherwise
*
*/
IP_GLOBAL int ipmacsec_key_test(char *ifname) {
Ipmacsec_secy_key_descriptor key_desc;
IPMACSEC_LMI_HANDLE lh = IP_NULL;
Ipmacsec_lmi_error ret = IPMACSEC_LMIERR_UNSPECIFIED_ERROR;
Ip_u32 i=0, num_exec_tests = 0, num_failed_tests = 0;
Ip_u64 key_id = 0xdeadbeef;
Ip_u8 dummy_key[16];
Ipmacsec_buffer key_info;
if (!ifname) {
IPCOM_LOG0(ERR, "IPMACSEC-KEY_TEST: NULL ifname. Test not executed.");
return -1;
}
lh = ipmacsec_lmi_handle_create();
if (!lh) {
IPCOM_LOG0(ERR, "IPMACSEC-KEY_TEST: Failed to create lmi handle. Test not executed.");
return -1;
}
/* Allocate enough buffer space for key descriptors */
IPMACSEC_BUF_INIT(&key_info);
if (ipmacsec_buf_alloc(&key_info, sizeof(Ipmacsec_secy_key_descriptor)*IPMACSEC_SECY_KEYDB_SIZE) == IP_NULL) {
IPCOM_LOG0(CRIT, "IPMACSEC-KEY_TEST: failed to alloc key_info buffer");
goto err_out;
}
/* 1- Install a Key (should succeed) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = key_id;
key_desc.key_size = sizeof(dummy_key);
key_desc.key_type |= IPMACSEC_KEYTYPE_TRANSMIT;
ret = ipmacsec_lmi_secy_key_install(lh, ifname, &key_desc, dummy_key);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG4(ERR, "IPMACSEC-KEY_TEST: Failed to install key with key_id 0x%llx, keysize %u. (ret=%d, %s).",
key_desc.key_id.val, key_desc.key_size, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
} else {
IPCOM_LOG2(INFO, "IPMACSEC-KEY_TEST: Successfully installed key with key_id 0x%llx, keysize %u.",
key_desc.key_id.val, sizeof(dummy_key));
}
/* 2- Retrieve key info (should succeed) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = key_id;
IPMACSEC_BUF_WIPE(&key_info);
ret = ipmacsec_lmi_secy_get_key_info(lh, ifname, &key_desc, &key_info);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-KEY_TEST: Failed to retrieve key info for key_id 0x%llx (ret=%d, %s).",
key_desc.key_id.val, ret, ipmacsec_lmi_error_name(ret));
} else {
Ipmacsec_secy_key_descriptor *kdesc = (Ipmacsec_secy_key_descriptor *)IPMACSEC_BUF_HEAD(&key_info);
if (key_info.size < sizeof(Ipmacsec_secy_key_descriptor)) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-KEY_TEST: Invalid key descriptor for key_id 0x%llx (size = %u < %u).",
key_desc.key_id.val, key_info.size, sizeof(Ipmacsec_secy_key_descriptor));
} else if (kdesc->key_id.val != key_desc.key_id.val) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-KEY_TEST: Invalid key descriptor key_id (0x%llx != 0x%llx).",
kdesc->key_id.val, key_desc.key_id.val);
} else {
IPMACSEC_TIMEBUF(tbuf);
IPMACSEC_STRFTIME(tbuf, kdesc->created_time);
IPCOM_LOG6(INFO, "IPMACSEC-KEY_TEST: Successfully retrieved info for key: key_id 0x%llx, keysize %u, "
"transmits %s, receives %s, inUse %s, created_time %s",
kdesc->key_id.val, kdesc->key_size,
IPMACSEC_BOOL_STRING(kdesc->key_type & IPMACSEC_KEYTYPE_TRANSMIT),
IPMACSEC_BOOL_STRING(kdesc->key_type & IPMACSEC_KEYTYPE_RECEIVE),
IPMACSEC_BOOL_STRING(kdesc->inUse), tbuf);
}
}
/* 3- Try to Install the same Key again (should fail) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = key_id;
key_desc.key_size = sizeof(dummy_key);
key_desc.key_type |= IPMACSEC_KEYTYPE_TRANSMIT;
ret = ipmacsec_lmi_secy_key_install(lh, ifname, &key_desc, dummy_key);
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-KEY_TEST: Succeeded in installing key with same key_id 0x%llx. Incorrect result",
key_desc.key_id.val);
} else {
IPCOM_LOG3(INFO, "IPMACSEC-KEY_TEST: Failed to re-install key with same key_id 0x%llx (ret=%d, %s). Expected Result",
key_desc.key_id.val, ret, ipmacsec_lmi_error_name(ret));
}
/* 4- Try to remove a key with a different key id (should fail) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = 0;
ret = ipmacsec_lmi_secy_key_remove(lh, ifname, &key_desc);
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-KEY_TEST: Succeeded in removing key with differet key_id 0x%llx. Incorrect result", key_desc.key_id.val);
} else {
IPCOM_LOG3(INFO, "IPMACSEC-KEY_TEST: Failed to remove key with differet key_id 0x%llx (ret=%d, %s). Expected Result",
key_desc.key_id.val, ret, ipmacsec_lmi_error_name(ret));
}
/* 5- Try to remove the correct key now (should succeed) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = key_id;
ret = ipmacsec_lmi_secy_key_remove(lh, ifname, &key_desc);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-KEY_TEST: Failed to remove key with same key_id 0x%llx (ret=%d, %s).",
key_desc.key_id.val, ret, ipmacsec_lmi_error_name(ret));
} else {
IPCOM_LOG1(INFO, "IPMACSEC-KEY_TEST: Succeeded in removing key with same key_id 0x%llx.", key_desc.key_id.val);
}
/* 6- Try to retrieve key info (should fail) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = key_id;
IPMACSEC_BUF_WIPE(&key_info);
ret = ipmacsec_lmi_secy_get_key_info(lh, ifname, &key_desc, &key_info);
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-KEY_TEST: Successfully retrieve key info for removed key_id 0x%llx (ret=%d, %s). Incorrect result",
key_desc.key_id.val, ret, ipmacsec_lmi_error_name(ret));
} else {
IPCOM_LOG1(INFO, "IPMACSEC-KEY_TEST: Failed to retrieve key info for removed key_id 0x%llx. Expected Result",
key_desc.key_id.val);
}
/* 7- Try to remove the same key again (should fail) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = key_id;
ret = ipmacsec_lmi_secy_key_remove(lh, ifname, &key_desc);
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-KEY_TEST: Succeeded in removing key with same key_id 0x%llx. Incorrect result", key_desc.key_id.val);
} else {
IPCOM_LOG3(INFO, "IPMACSEC-KEY_TEST: Failed to remove key with same key_id 0x%llx (ret=%d, %s). Expected result",
key_desc.key_id.val, ret, ipmacsec_lmi_error_name(ret));
}
/* 8- Delete all keys (should succeed) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
ret = ipmacsec_lmi_secy_key_purge(lh, ifname);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG0(ERR, "IPMACSEC-KEY_TEST: Failed to purge keys.");
} else {
IPCOM_LOG0(INFO, "IPMACSEC-KEY_TEST: Succeeded in purging keys.");
}
/* 9- Retrieve all key info (should succeed, but return none) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
IPMACSEC_BUF_WIPE(&key_info);
ret = ipmacsec_lmi_secy_get_key_info(lh, ifname, IP_NULL, &key_info);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-KEY_TEST: Failed to retrieve key info list (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
} else {
if (key_info.size != 0) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-KEY_TEST: key info returned when there should be none (key_info.size = %u).",
key_info.size);
for (i = 1; i <= IPMACSEC_SECY_KEYDB_SIZE; i++) {
Ip_u32 remlen;
Ipmacsec_secy_key_descriptor *kdesc = (Ipmacsec_secy_key_descriptor *)
ipmacsec_buf_ptr(&key_info, (i-1)*sizeof(Ipmacsec_secy_key_descriptor), &remlen);
if (!kdesc) {
IPCOM_LOG0(ERR, "IPMACSEC-KEY_TEST: kdesc NULL!");
} else {
IPMACSEC_TIMEBUF(tbuf);
IPMACSEC_STRFTIME(tbuf, kdesc->created_time);
IPCOM_LOG7(INFO, "IPMACSEC-KEY_TEST: Retrieved info for key #%u: key_id 0x%llx, keysize %u, "
"transmits %s, receives %s, inUse %s, created_time %s",
i, kdesc->key_id.val, kdesc->key_size,
IPMACSEC_BOOL_STRING(kdesc->key_type & IPMACSEC_KEYTYPE_TRANSMIT),
IPMACSEC_BOOL_STRING(kdesc->key_type & IPMACSEC_KEYTYPE_RECEIVE),
IPMACSEC_BOOL_STRING(kdesc->inUse), tbuf);
}
}
} else {
IPCOM_LOG0(INFO, "IPMACSEC-KEY_TEST: No key info retrieved. Expected result");
}
}
/* 10- Install Max keys (should succeed) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
for (i = 1; i <= IPMACSEC_SECY_KEYDB_SIZE; i++) {
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = ((Ip_u64)i << 32 | key_id);
key_desc.key_size = sizeof(dummy_key);
key_desc.key_type |= IPMACSEC_KEYTYPE_TRANSMIT;
ret = ipmacsec_lmi_secy_key_install(lh, ifname, &key_desc, dummy_key);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG5(ERR, "IPMACSEC-KEY_TEST: Failed to install key #%u with key_id 0x%llx, keysize %u. (ret=%d, %s).",
i, key_desc.key_id.val, key_desc.key_size, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
} else {
IPCOM_LOG3(INFO, "IPMACSEC-KEY_TEST: Successfully installed key #%u with key_id 0x%llx, keysize %u.",
i, key_desc.key_id.val, sizeof(dummy_key));
}
}
/* 11- Install 1 more key than mac (should fail) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = ((Ip_u64)i << 32 | key_id);
key_desc.key_size = sizeof(dummy_key);
key_desc.key_type |= IPMACSEC_KEYTYPE_TRANSMIT;
ret = ipmacsec_lmi_secy_key_install(lh, ifname, &key_desc, dummy_key);
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-KEY_TEST: Successfully installed key #%u with key_id 0x%llx, keysize %u. Incorrect result",
i, key_desc.key_id.val, sizeof(dummy_key));
} else {
IPCOM_LOG5(INFO, "IPMACSEC-KEY_TEST: Failed to install key #%u with key_id 0x%llx, keysize %u. (ret=%d, %s). Expected result",
i, key_desc.key_id.val, key_desc.key_size, ret, ipmacsec_lmi_error_name(ret));
}
/* 12- Retreive all key info (should succeed with max # of key info returned) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
IPMACSEC_BUF_WIPE(&key_info);
ret = ipmacsec_lmi_secy_get_key_info(lh, ifname, IP_NULL, &key_info);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-KEY_TEST: Failed to retrieve key info list (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
} else {
if (key_info.size != IPMACSEC_SECY_KEYDB_SIZE*sizeof(Ipmacsec_secy_key_descriptor)) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-KEY_TEST: Incorrect number of key info returned (%u != %u). Incorrect result",
key_info.size, IPMACSEC_SECY_KEYDB_SIZE*sizeof(Ipmacsec_secy_key_descriptor));
} else if (key_info.truncated) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-KEY_TEST: key info buffer truncated (size = %u, alloc_size = %u).",
key_info.size, key_info.alloc_size);
} else {
IPCOM_LOG0(INFO, "IPMACSEC-KEY_TEST: Complete key info retrieved successfully.");
for (i = 1; i <= IPMACSEC_SECY_KEYDB_SIZE; i++) {
Ip_u32 remlen;
Ipmacsec_secy_key_descriptor *kdesc = (Ipmacsec_secy_key_descriptor *)
ipmacsec_buf_ptr(&key_info, (i-1)*sizeof(Ipmacsec_secy_key_descriptor), &remlen);
if (!kdesc) {
IPCOM_LOG0(WARNING, "IPMACSEC-KEY_TEST: kdesc NULL!");
} else {
IPMACSEC_TIMEBUF(tbuf);
IPMACSEC_STRFTIME(tbuf, kdesc->created_time);
IPCOM_LOG7(INFO, "IPMACSEC-KEY_TEST: Successfully retrieved info for key #%u: key_id 0x%llx, keysize %u, "
"transmits %s, receives %s, inUse %s, created_time %s",
i, kdesc->key_id.val, kdesc->key_size,
IPMACSEC_BOOL_STRING(kdesc->key_type & IPMACSEC_KEYTYPE_TRANSMIT),
IPMACSEC_BOOL_STRING(kdesc->key_type & IPMACSEC_KEYTYPE_RECEIVE),
IPMACSEC_BOOL_STRING(kdesc->inUse), tbuf);
}
}
}
}
/* 13- Delete all keys (should succeed) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
ret = ipmacsec_lmi_secy_key_purge(lh, ifname);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG0(ERR, "IPMACSEC-KEY_TEST: Failed to purge keys.");
} else {
IPCOM_LOG0(INFO, "IPMACSEC-KEY_TEST: Succeeded in purging keys.");
}
/* 14- Retreive all key info (should succeed 0 key info returned) */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-KEY_TEST: Executing test #%u *****", num_exec_tests);
IPMACSEC_BUF_WIPE(&key_info);
ret = ipmacsec_lmi_secy_get_key_info(lh, ifname, IP_NULL, &key_info);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-KEY_TEST: Failed to retrieve key info list (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
} else {
if (key_info.size != 0) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-KEY_TEST: key info returned when there should be none (key_info.size = %u).",
key_info.size);
} else {
IPCOM_LOG0(INFO, "IPMACSEC-KEY_TEST: No key info retrieved. Expected result");
}
}
err_out:
if (num_failed_tests) {
IPCOM_LOG2(ERR, "IPMACSEC-KEY_TEST: COMPLETED WITH FAILURES - %u tests executed, %u failed",
num_exec_tests, num_failed_tests);
ret = -1;
} else {
IPCOM_LOG1(INFO, "IPMACSEC-KEY_TEST: COMPLETED SUCCESSFULLY - %u tests executed successfully", num_exec_tests);
ret = 0;
}
(void)ipmacsec_buf_free(&key_info);
(void)ipmacsec_lmi_handle_delete(lh);
return ret;
}
/*
*===========================================================================
* ipmacsec_ctrl_cmd_test
*===========================================================================
* Description: Test the SecY Control Set/Get operations.
* Set commands will fail if executed when the Secy is enabled.
* Parameters: ifname - Interface name to send to. Must be attached 1st
* otherwise this test will fail.
* Returns: 0 upon success, <0 otherwise
*
*/
IP_GLOBAL int ipmacsec_ctrl_cmd_test(char *ifname) {
Ipmacsec_lmi_command bool_cmds[] = {IPMACSEC_LMICMD_SECY_PROTECT_FRAMES,
IPMACSEC_LMICMD_SECY_ALWAYS_INC_SCI,
IPMACSEC_LMICMD_SECY_USE_ES,
IPMACSEC_LMICMD_SECY_USE_SCB,
IPMACSEC_LMICMD_SECY_REPLAY_PROTECT};
Ipmacsec_lmi_command ipu32_cmds[] = {IPMACSEC_LMICMD_SECY_REPLAY_WINDOW};
Ipmacsec_validateFrames_type validateFrames;
IPMACSEC_LMI_HANDLE lh = IP_NULL;
Ipmacsec_lmi_error ret = IPMACSEC_LMIERR_UNSPECIFIED_ERROR;
Ip_u32 i = 0;
Ipmacsec_buffer request, response;
Ipmacsec_lmi_command cmd;
if (!ifname) {
IPCOM_LOG0(ERR, "IPMACSEC-CTRL_TEST: NULL ifname. Test not executed.");
return -1;
}
lh = ipmacsec_lmi_handle_create();
if (!lh) {
IPCOM_LOG0(ERR, "IPMACSEC-CTRL_TEST: Failed to create lmi handle. Test not executed.");
return -1;
}
IPMACSEC_BUF_INIT(&request);
if (ipmacsec_nlmsg_alloc(&request) == IP_NULL) {
ret = IPMACSEC_LMIERR_ALLOC_FAILED;
goto err_out;
}
IPMACSEC_BUF_INIT(&response);
if (ipmacsec_nlmsg_alloc(&response) == IP_NULL) {
ret = IPMACSEC_LMIERR_ALLOC_FAILED;
goto err_out;
}
for (i=0; i < sizeof(bool_cmds)/sizeof(bool_cmds[0]); i++) {
Ip_bool bool_val;
for (bool_val = 0; bool_val <= 1; bool_val++) {
Ip_bool val = bool_val;
cmd = bool_cmds[i];
ret = ipmacsec_lmi_cmd_send_bool(lh, ifname, cmd, &val, IPMACSEC_LMICMD_ISSET);
if (ret != IPMACSEC_LMIERR_NONE) {
goto set_cmd_send_err;
}
ret = ipmacsec_lmi_cmd_send_bool(lh, ifname, cmd, &val, IPMACSEC_LMICMD_ISGET);
if (ret != IPMACSEC_LMIERR_NONE) {
goto get_cmd_send_err;
}
if (val != bool_val) {
IPCOM_LOG3(ERR, "IPMACSEC-CTRL_TEST: cmd %s result mismatch (%s, expected %s)",
ipmacsec_lmi_cmd_name(cmd), IPMACSEC_BOOL_STRING(val), IPMACSEC_BOOL_STRING(bool_val));
goto err_out;
}
}
}
for (i=0; i < sizeof(ipu32_cmds)/sizeof(ipu32_cmds[0]); i++) {
Ip_u32 ipu32_val = 0;
cmd = ipu32_cmds[i];
for (;;) {
Ip_u32 val = ipu32_val;
ret = ipmacsec_lmi_cmd_send_u32(lh, ifname, cmd, &val, IPMACSEC_LMICMD_ISSET);
if (ret != IPMACSEC_LMIERR_NONE) {
goto set_cmd_send_err;
}
ret = ipmacsec_lmi_cmd_send_u32(lh, ifname, cmd, &val, IPMACSEC_LMICMD_ISGET);
if (ret != IPMACSEC_LMIERR_NONE) {
goto get_cmd_send_err;
}
if (val != ipu32_val) {
IPCOM_LOG3(ERR, "IPMACSEC-CTRL_TEST: cmd %s result mismatch (%u, expected %u)",
ipmacsec_lmi_cmd_name(cmd), val, ipu32_val);
goto err_out;
}
if (ipu32_val == 0xffffffffL)
break;
ipu32_val++;
if (ipu32_val == 1)
ipu32_val = 0xffffffffL;
}
}
for (validateFrames=__IPMACSEC_SECY_VALIDATEFRAMES_INVALID;
validateFrames<= __IPMACSEC_SECY_VALIDATEFRAMES_MAX; validateFrames++) {
Ipmacsec_validateFrames_type val = validateFrames;
cmd = IPMACSEC_LMICMD_SECY_VALIDATE_FRAMES;
IPMACSEC_BUF_WIPE(&request);
ret = ipmacsec_lmi_secy_set_cmd_append(&request, IP_NULL, ifname, cmd, &val, sizeof(val));
if (ret != IPMACSEC_LMIERR_NONE) {
goto set_cmd_append_err;
}
ret = ipmacsec_lmi_cmd_send(IPMACSEC_LMI_TO_NETLINK_HANDLE(lh), &request, IP_NULL);
if (IPMACSEC_VALIDATEFRAMES_VALID(validateFrames)) {
if (ret != IPMACSEC_LMIERR_NONE) {
goto set_cmd_send_err;
}
} else {
if (ret == IPMACSEC_LMIERR_NONE) {
ret = -1;
goto set_cmd_send_err;
}
ret = 0;
continue;
}
IPMACSEC_BUF_WIPE(&request);
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_cmd_append(&request, IP_NULL, ifname, cmd, &val, sizeof(val));
if (ret != IPMACSEC_LMIERR_NONE) {
goto get_cmd_append_err;
}
ret = ipmacsec_lmi_cmd_send(IPMACSEC_LMI_TO_NETLINK_HANDLE(lh), &request, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
goto get_cmd_send_err;
}
if (IPMACSEC_VALIDATEFRAMES_VALID(validateFrames) && (val != validateFrames)) {
IPCOM_LOG3(ERR, "IPMACSEC-CTRL_TEST: cmd %s result mismatch (%u, expected %u)",
ipmacsec_lmi_cmd_name(cmd), val, validateFrames);
goto err_out;
}
}
goto err_out;
set_cmd_append_err:
IPCOM_LOG1(ERR, "IPMACSEC-CTRL_TEST: Failed to append set cmd %s", ipmacsec_lmi_cmd_name(cmd));
goto err_out;
get_cmd_append_err:
IPCOM_LOG1(ERR, "IPMACSEC-CTRL_TEST: Failed to append get cmd %s", ipmacsec_lmi_cmd_name(cmd));
goto err_out;
set_cmd_send_err:
IPCOM_LOG1(ERR, "IPMACSEC-CTRL_TEST: Unexpected result for set cmd %s", ipmacsec_lmi_cmd_name(cmd));
goto err_out;
get_cmd_send_err:
IPCOM_LOG1(ERR, "IPMACSEC-CTRL_TEST: Unexpected result for get cmd %s", ipmacsec_lmi_cmd_name(cmd));
goto err_out;
err_out:
(void)ipmacsec_nlmsg_free(&request);
(void)ipmacsec_nlmsg_free(&response);
return ret;
}
/*
*===========================================================================
* ipmacsec_sc_sa_test
*===========================================================================
* Description: Test the SecY SC/SA Create/Delete/Control operations.
* Parameters: ifname - Interface name to send to. Must be attached 1st
* otherwise this test will fail.
* Returns: 0 upon success, <0 otherwise
*
*/
IP_GLOBAL int ipmacsec_sc_sa_test(char *ifname) {
IPMACSEC_LMI_HANDLE lh = IP_NULL;
Ipmacsec_lmi_error ret = IPMACSEC_LMIERR_UNSPECIFIED_ERROR;
Ip_u32 num_exec_tests = 0, num_failed_tests = 0;
Ipmacsec_buffer response;
Ipmacsec_secy_sc_info sc_info, *scinf = IP_NULL;
#ifdef IPMACSEC_USE_STATS
Ipmacsec_secy_sc_stats sc_stats;
#endif
Ipmacsec_secy_sa_info *sai = IP_NULL;
Ip_u8 my_sci[IPMACSEC_SCI_LEN], sci[IPMACSEC_SCI_LEN];
Ip_u16 maxTxSAs = 0, maxRxSCs =0, maxRxSAs = 0;
Ip_u8 an = 0;
Ip_u16 sc = 0;
Ip_u32 remlen = 0;
/* Verify param */
if (!ifname) {
IPCOM_LOG0(ERR, "IPMACSEC-SC_SA_TEST: NULL ifname. Test not executed.");
return IPMACSEC_LMIERR_INVALID_PARAMETER;
}
/* Initialize things */
IPMACSEC_BUF_INIT(&response);
if (ipmacsec_nlmsg_alloc(&response) == IP_NULL) {
ret = IPMACSEC_LMIERR_ALLOC_FAILED;
goto err_out;
}
IPCOM_LOG1(INFO, "IPMACSEC-SC_SA_TEST: STARTING tests on interface %s.", ifname);
/* Create an LMI handle */
lh = ipmacsec_lmi_handle_create();
if (!lh) {
IPCOM_LOG0(ERR, "IPMACSEC-SC_SA_TEST: Failed to create lmi handle. Test not executed.");
return -1;
}
/* 1st Disable the SecY to make sure everything is started from a clean slate
* This also serves as a test for the SecY existence
*/
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Disabling SecY *****", num_exec_tests);
ret = ipmacsec_lmi_secy_enable(lh, ifname, IP_FALSE);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to disable SecY (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Set the TX SCI */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Setting the TX SCI *****", num_exec_tests);
ipcom_memset(my_sci, 0x11, IPMACSEC_SCI_LEN);
ret = ipmacsec_lmi_secy_set_tx_sci(lh, ifname, my_sci);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to set the TX SCI (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Verify the TX SCI */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Retrieving the TX SCI *****", num_exec_tests);
ret = ipmacsec_lmi_secy_get_tx_sci(lh, ifname, sci);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to get the TX SCI (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
if (ipcom_memcmp(my_sci, sci, IPMACSEC_SCI_LEN) != 0) {
num_failed_tests++;
IPCOM_LOG0(ERR, "IPMACSEC-SC_SA_TEST: TX SCI mismatch");
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Now Enable the SecY, which creates the SecY TX SC */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Enabling SecY *****", num_exec_tests);
ret = ipmacsec_lmi_secy_enable(lh, ifname, IP_TRUE);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to enable SecY (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Verify that the TX SC was created and verify some sc_info fields and stats */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Verifying TX SC status and statistics *****",
num_exec_tests);
ipcom_memset(&sc_info, 0, sizeof(sc_info));
ret = ipmacsec_lmi_secy_get_tx_sc_status(lh, ifname, &sc_info);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve TX SC (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
if (ipcom_memcmp(my_sci, sc_info.sci, IPMACSEC_SCI_LEN) != 0) {
num_failed_tests++;
IPCOM_LOG0(ERR, "IPMACSEC-SC_SA_TEST: TX SCI mismatch in sc_info");
goto err_out;
}
if (sc_info.dir != IPMACSEC_TX) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: TX SCI direction mismatch (%s, %u)", IPMACSEC_DIR_STRING(sc_info.dir), sc_info.dir);
goto err_out;
}
if (sc_info.status.tx.transmitting) {
num_failed_tests++;
IPCOM_LOG0(ERR, "IPMACSEC-SC_SA_TEST: TX SCI should not be transmitting");
goto err_out;
}
#ifdef IPMACSEC_USE_STATS
ret = ipmacsec_lmi_secy_get_tx_sc_stats(lh, ifname, &sc_stats);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve TX SC stats (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
#endif
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Retrieve the max # of TX SAs */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Retrieving max # of supported TX SAs *****", num_exec_tests);
ret = ipmacsec_lmi_secy_get_maxTxKeys(lh, ifname, &maxTxSAs);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve maxTxKeys (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
if (maxTxSAs != IPMACSEC_MAX_SA ) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Invalid maxTxSAs=%u (!= %u)", maxTxSAs, IPMACSEC_MAX_SA);
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Create max # of TX SAs + 1, last one should fail*/
num_exec_tests++;
IPCOM_LOG2(INFO,
"***** IPMACSEC-SC_SA_TEST: Executing test #%u: Create+Get Status+Get Stats+Control %u TX SAs (Last one should fail) *****",
num_exec_tests, maxTxSAs+1);
for (an=0; an <= (Ip_u8)maxTxSAs; an++) {
Ipmacsec_secy_key_descriptor key_desc;
Ipmacsec_secy_sa_descriptor sa_desc;
Ipmacsec_secy_sa_info sa_info;
Ip_u32 ref = (an+1)<<8;
Ip_u8 dummy_key[16];
Ip_u32 nextPN=1;
Ipmacsec_confidentiality confidentiality = IPMACSEC_CONFIDENTIALITY_UNSPECIFIED;
/* Install a key */
ipcom_memset(dummy_key, 0xAE, sizeof(dummy_key));
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = (Ip_u64)(an+1);
key_desc.key_size = sizeof(dummy_key);
key_desc.key_type |= IPMACSEC_KEYTYPE_TRANSMIT;
ret = ipmacsec_lmi_secy_key_install(lh, ifname, &key_desc, dummy_key);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG4(ERR, "IPMACSEC-SC_SA_TEST: Failed to install key with key_id 0x%llx, keysize %u. (ret=%d, %s).",
key_desc.key_id.val, key_desc.key_size, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
/* Init the SA descriptor and info structures */
if (an < (Ip_u8)maxTxSAs) {
if (ipmacsec_lmi_secy_sa_descriptor_init(&sa_desc, my_sci, an, IPMACSEC_TX, ref, &key_desc.key_id) == IP_NULL) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Failed to initialize RX SA descriptor for AN = %u.", an);
goto err_out;
}
} else {
/* For an invalid AN, we need to do it manually since ipmacsec_lmi_secy_sa_descriptor_init() does not allow it */
IPMACSEC_COPY_SCI(sa_desc.sci, my_sci);
sa_desc.an = an;
sa_desc.dir = IPMACSEC_TX;
sa_desc.ref = ref;
sa_desc.key_id.val = key_desc.key_id.val;
}
if (ipmacsec_lmi_secy_tx_sa_info_init(&sa_info, nextPN, confidentiality) == IP_NULL) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Failed to initialize RX SA info for AN = %u.", an);
goto err_out;
}
nextPN++;
/* Create the SA and verify you can retrieve its info and control it */
ret = ipmacsec_lmi_secy_create_tx_sa(lh, ifname, &sa_desc, &sa_info);
if (an < (Ip_u8)maxTxSAs) {
#ifdef IPMACSEC_USE_STATS
Ipmacsec_secy_sa_stats sa_stats;
#endif
Ipmacsec_secy_sa_ctrl sa_ctrl;
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to create TX SA with AN %u (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
/* Retrieve SA status, should succeed */
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_tx_sa_status(lh, ifname, an, ref, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to get status for TX SA with AN %u (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
remlen = 0;
sai = (Ipmacsec_secy_sa_info *)ipmacsec_buf_ptr(&response, 0, &remlen);
if (!sai || (remlen < sizeof(Ipmacsec_secy_sa_info))) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Invalid status for TX SA with AN %u (sai=%p, remlen=%u < %u).",
(void *)sai, remlen, sizeof(Ipmacsec_secy_sa_info));
goto err_out;
}
#ifdef IPMACSEC_USE_STATS
/* Retrieve SA staistics, should succeed */
ret = ipmacsec_lmi_secy_get_tx_sa_stats(lh, ifname, &sa_stats, an, ref);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to get statistics for TX SA with AN %u (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
#endif
/* Control the SA, should succeed */
if (ipmacsec_lmi_secy_rx_sa_ctrl_init(&sa_ctrl, IPMACSEC_ENABLEFLAG_ON, 2, IPMACSEC_CONFIDENTIALITY_UNSPECIFIED)
== IP_NULL) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Failed to initialize RX SA control struct for AN = %u.", an);
goto err_out;
}
ret = ipmacsec_lmi_secy_control_tx_sa(lh, ifname, &sa_desc, &sa_ctrl);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to control TX SA with AN %u (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
/* TX SC should be transmitting */
ipcom_memset(&sc_info, 0, sizeof(sc_info));
ret = ipmacsec_lmi_secy_get_tx_sc_status(lh, ifname, &sc_info);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve TX SC (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
if (!sc_info.status.tx.transmitting) {
num_failed_tests++;
IPCOM_LOG0(ERR, "IPMACSEC-SC_SA_TEST: TX SCI should be transmitting");
goto err_out;
}
} else {
/* Remove the unused key */
if (ipmacsec_lmi_secy_key_remove(lh, ifname, &key_desc) != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Failed in removing key with key_id 0x%llx.",
key_desc.key_id.val);
}
/* Should have failed to install 1 more SA than Max */
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Unexpected success creating TX SA with AN %u", an);
goto err_out;
}
}
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Retrieve TX SA list. There should be exactly maxTxSAs infos */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Retrieving TX SA list *****",
num_exec_tests);
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_tx_sa_status(lh, ifname, -1, 0, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve TX SA list (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
remlen = 0;
sai = (Ipmacsec_secy_sa_info *)ipmacsec_buf_ptr(&response, 0, &remlen);
if (!sai || (remlen < sizeof(Ipmacsec_secy_sa_info)*maxTxSAs)) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Invalid TX SA list (sai=%p, remlen=%u < %u).",
(void *)sai, remlen, sizeof(Ipmacsec_secy_sa_info)*maxTxSAs);
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Delete # of TX SAs + 1, last one should fail*/
num_exec_tests++;
IPCOM_LOG2(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Deleting %u TX SAs (Last one should fail) *****",
num_exec_tests, maxTxSAs+1);
for (an=0; an <= (Ip_u8)maxTxSAs; an++) {
Ipmacsec_secy_key_descriptor key_desc;
Ipmacsec_secy_sa_descriptor sa_desc;
Ip_u32 ref = (an+1)<<8;
/* Init the key descriptor */
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = (Ip_u64)(an+1);
key_desc.key_type |= IPMACSEC_KEYTYPE_TRANSMIT;
/* Init the SA descriptor */
if (an < (Ip_u8)maxTxSAs) {
if (ipmacsec_lmi_secy_sa_descriptor_init(&sa_desc, my_sci, an, IPMACSEC_TX, ref, &key_desc.key_id) == IP_NULL) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Failed to initialize RX SA descriptor for AN = %u.", an);
goto err_out;
}
} else {
/* For an invalid AN, we need to do it manually since ipmacsec_lmi_secy_sa_descriptor_init() does not allow it */
IPMACSEC_COPY_SCI(sa_desc.sci, my_sci);
sa_desc.an = an;
sa_desc.dir = IPMACSEC_TX;
sa_desc.ref = ref;
sa_desc.key_id.val = key_desc.key_id.val;
}
/* Delete the SA */
ret = ipmacsec_lmi_secy_delete_tx_sa(lh, ifname, &sa_desc);
if (an < (Ip_u8)maxTxSAs) {
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to delete TX SA with AN %u (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
/* Remove the key */
ret = ipmacsec_lmi_secy_key_remove(lh, ifname, &key_desc);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to remove key with key_id 0x%llx. (ret=%d, %s).",
key_desc.key_id.val, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
} else {
/* Should have failed to delete 1 more SA than Max */
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Unexpected success deleting TX SA with AN %u", an);
goto err_out;
}
}
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Retrieve TX SA list. There should be none */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Retrieving TX SA list *****",
num_exec_tests);
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_tx_sa_status(lh, ifname, -1, 0, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve TX SA list (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
remlen = 0;
sai = (Ipmacsec_secy_sa_info *)ipmacsec_buf_ptr(&response, 0, &remlen);
if (remlen != 0) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Invalid TX SA list (sai=%p, remlen=%u).",
(void *)sai, remlen);
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Verify the TX SC is not transmitting anymore */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Retrieving TX SA list *****",
num_exec_tests);
ipcom_memset(&sc_info, 0, sizeof(sc_info));
ret = ipmacsec_lmi_secy_get_tx_sc_status(lh, ifname, &sc_info);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve TX SC (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
if (sc_info.status.tx.transmitting) {
num_failed_tests++;
IPCOM_LOG0(ERR, "IPMACSEC-SC_SA_TEST: TX SCI should not be transmitting");
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Retrieve the max # of RX SCs */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Retrieving max # of supported RX SCs *****", num_exec_tests);
ret = ipmacsec_lmi_secy_get_maxRxSCs(lh, ifname, &maxRxSCs);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve TX SC (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
if (maxRxSCs != IPMACSEC_MAX_RX_SC) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Invalid maxTxSAs=%u (!= %u).", maxRxSCs, IPMACSEC_MAX_RX_SC);
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Create and verify maxRxSCs RX SCs + 1 (last one should fail) */
for (sc=1; sc <= maxRxSCs+1; sc++) {
Ip_u8 rx_sci[IPMACSEC_SCI_LEN];
num_exec_tests++;
if (sc < maxRxSCs+1)
IPCOM_LOG2(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Creating RX SC #%u *****", num_exec_tests, sc);
else
IPCOM_LOG2(INFO,
"***** IPMACSEC-SC_SA_TEST: Executing test #%u: Trying to create one more RX SC that suported (#%u should fail) *****",
num_exec_tests, sc);
ipcom_memset(rx_sci, (Ip_u8)sc, IPMACSEC_SCI_LEN);
ret = ipmacsec_lmi_secy_create_rx_sc(lh, ifname, rx_sci);
if (sc < maxRxSCs+1) {
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to create RX SC #%u (ret=%d, %s).",
sc, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
} else {
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Unexpected success in creating RX SC #%u (ret=%d, %s).",
sc, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Verify that the RX SC was created and verify some sc_info fields and stats */
num_exec_tests++;
IPCOM_LOG2(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Verifying RX SC #%u status and statistics *****",
num_exec_tests, sc);
ipcom_memset(&sc_info, 0, sizeof(sc_info));
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_rx_sc_status(lh, ifname, rx_sci, &response);
if (sc < maxRxSCs+1) {
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve RX SC #%u (ret=%d, %s).",
sc, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
scinf = (Ipmacsec_secy_sc_info *)ipmacsec_buf_ptr(&response, 0, &remlen);
if (!scinf || (remlen < sizeof(Ipmacsec_secy_sc_info))) {
num_failed_tests++;
IPCOM_LOG4(ERR, "IPMACSEC-SC_SA_TEST: Invalid RX SC status for sc #%u (scinf=%p, remlen=%u < %u).",
sc, (void *)scinf, remlen, sizeof(Ipmacsec_secy_sc_info));
goto err_out;
}
if (ipcom_memcmp(rx_sci, scinf->sci, IPMACSEC_SCI_LEN) != 0) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: RX SCI mismatch in sc_info for sc #%u", sc);
goto err_out;
}
if (scinf->dir != IPMACSEC_RX) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: RX SCI direction mismatch for sc #%u (%s, %u)",
sc, IPMACSEC_DIR_STRING(scinf->dir), scinf->dir);
goto err_out;
}
if (scinf->status.rx.receiving) {
num_failed_tests++;
IPCOM_LOG0(ERR, "IPMACSEC-SC_SA_TEST: RX SCI #%u should not be receiving");
goto err_out;
}
} else {
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Unexpected success in retrieving RX SC #%u (ret=%d, %s).",
sc, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
}
#ifdef IPMACSEC_USE_STATS
ret = ipmacsec_lmi_secy_get_rx_sc_stats(lh, ifname, &sc_stats, rx_sci);
if (sc < maxRxSCs+1) {
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve TX SC stats (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
} else {
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Unexpected success in retrieving stats for RX SC #%u (ret=%d, %s).",
sc, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
}
#endif
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Retrieve the max # of RX SAs */
num_exec_tests++;
IPCOM_LOG2(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Retrieving max # of supported RX SAs for SC #%u *****",
num_exec_tests, sc);
ret = ipmacsec_lmi_secy_get_maxRxKeys(lh, ifname, &maxRxSAs);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve maxRxKeys (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
if (maxRxSAs != IPMACSEC_MAX_SA) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Invalid maxRxSAs=%u (!= %u)", maxRxSAs, IPMACSEC_MAX_SA);
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Create max # of RX SAs + 1, last one should fail*/
num_exec_tests++;
IPCOM_LOG3(INFO,
"***** IPMACSEC-SC_SA_TEST: Executing test #%u: Create+Get Status+Get Stats+Control %u RX SAs for SC #%u (Last one should fail) *****",
num_exec_tests, maxRxSAs+1, sc);
for (an=0; (sc < maxRxSCs+1) && (an <= (Ip_u8)maxRxSAs); an++) {
Ipmacsec_secy_key_descriptor key_desc;
Ipmacsec_secy_sa_descriptor sa_desc;
Ipmacsec_secy_sa_info sa_info;
Ip_u32 ref = (an+1)<<16;
Ip_u8 dummy_key[16];
Ip_u32 nextPN=1, lowestPN = 1;
/* Install a key */
ipcom_memset(dummy_key, 0xAE, sizeof(dummy_key));
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = (Ip_u64)((sc<<8)+an+1);
key_desc.key_size = sizeof(dummy_key);
key_desc.key_type |= IPMACSEC_KEYTYPE_RECEIVE;
ret = ipmacsec_lmi_secy_key_install(lh, ifname, &key_desc, dummy_key);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG4(ERR, "IPMACSEC-SC_SA_TEST: Failed to install key with key_id 0x%llx, keysize %u. (ret=%d, %s).",
key_desc.key_id.val, key_desc.key_size, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
/* Init the SA descriptor and info structures */
if (an < (Ip_u8)maxRxSAs) {
if (ipmacsec_lmi_secy_sa_descriptor_init(&sa_desc, rx_sci, an, IPMACSEC_RX, ref, &key_desc.key_id) == IP_NULL) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Failed to initialize RX SA descriptor for AN = %u.", an);
goto err_out;
}
} else {
/* For an invalid AN, we need to do it manually since ipmacsec_lmi_secy_sa_descriptor_init() does not allow it */
IPMACSEC_COPY_SCI(sa_desc.sci, rx_sci);
sa_desc.an = an;
sa_desc.dir = IPMACSEC_RX;
sa_desc.ref = ref;
sa_desc.key_id.val = key_desc.key_id.val;
}
if (ipmacsec_lmi_secy_rx_sa_info_init(&sa_info, nextPN, lowestPN) == IP_NULL) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Failed to initialize RX SA info for AN = %u.", an);
goto err_out;
}
nextPN = ++lowestPN;
/* Create the SA and verify you can retrieve its info and control it */
ret = ipmacsec_lmi_secy_create_rx_sa(lh, ifname, &sa_desc, &sa_info);
if (an < (Ip_u8)maxRxSAs) {
#ifdef IPMACSEC_USE_STATS
Ipmacsec_secy_sa_stats sa_stats;
#endif
Ipmacsec_secy_sa_ctrl sa_ctrl;
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to create RX SA with AN %u (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
/* Retrieve SA status, should succeed */
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_rx_sa_status(lh, ifname, rx_sci, an, ref, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to get status for RX SA with AN %u (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
remlen = 0;
sai = (Ipmacsec_secy_sa_info *)ipmacsec_buf_ptr(&response, 0, &remlen);
if (!sai || (remlen < sizeof(Ipmacsec_secy_sa_info))) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Invalid status for RX SA with AN %u (sai=%p, remlen=%u < %u).",
(void *)sai, remlen, sizeof(Ipmacsec_secy_sa_info));
goto err_out;
}
#ifdef IPMACSEC_USE_STATS
/* Retrieve SA staistics, should succeed */
ret = ipmacsec_lmi_secy_get_rx_sa_stats(lh, ifname, &sa_stats, rx_sci, an, ref);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to get statistics for RX SA with AN %u (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
#endif
/* Control the SA, should succeed */
if (ipmacsec_lmi_secy_rx_sa_ctrl_init(&sa_ctrl, IPMACSEC_ENABLEFLAG_ON, 2, 1) == IP_NULL) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Failed to initialize RX SA control struct for AN = %u.", an);
goto err_out;
}
ret = ipmacsec_lmi_secy_control_rx_sa(lh, ifname, &sa_desc, &sa_ctrl);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to control RX SA with AN %u (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
/* RX SC should be receiving */
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_rx_sc_status(lh, ifname, rx_sci, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve RX SC #%u (ret=%d, %s).",
sc, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
remlen = 0;
scinf = (Ipmacsec_secy_sc_info *)ipmacsec_buf_ptr(&response, 0, &remlen);
if (!scinf || (remlen < sizeof(Ipmacsec_secy_sc_info))) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Invalid RX SC list (scinf=%p, remlen=%u < %u).",
(void *)scinf, remlen, sizeof(Ipmacsec_secy_sc_info));
goto err_out;
}
if (!scinf->status.rx.receiving) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: RX SC #%u should be receiving", sc);
goto err_out;
}
} else {
/* Remove the unused key */
if (ipmacsec_lmi_secy_key_remove(lh, ifname, &key_desc) != IPMACSEC_LMIERR_NONE) {
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Failed in removing key with key_id 0x%llx.",
key_desc.key_id.val);
}
/* Should have failed to install 1 more SA than Max */
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Unexpected success creating RX SA with AN %u", an);
goto err_out;
}
}
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Retrieve RX SA list. There should be exactly maxRxSAs infos */
num_exec_tests++;
IPCOM_LOG2(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Retrieving RX SA for Rx SC #%u list *****",
num_exec_tests, sc);
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_rx_sa_status(lh, ifname, rx_sci, -1, 0, &response);
if (sc < maxRxSCs+1) {
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve RX SA list for sc #%u (ret=%d, %s).",
sc, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
remlen = 0;
sai = (Ipmacsec_secy_sa_info *)ipmacsec_buf_ptr(&response, 0, &remlen);
if (!sai || (remlen < sizeof(Ipmacsec_secy_sa_info)*maxRxSAs)) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Invalid RX SA list (sai=%p, remlen=%u < %u).",
(void *)sai, remlen, sizeof(Ipmacsec_secy_sa_info)*maxRxSAs);
goto err_out;
}
} else {
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Unexpected success in retrieving RX SA list for sc #%u (ret=%d, %s).",
sc, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Delete # of RX SAs + 1, last one should fail*/
num_exec_tests++;
IPCOM_LOG3(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Deleting %u RX SAs for RX SC #%u (Last one should fail) *****",
num_exec_tests, maxRxSAs+1, sc);
for (an=0; (sc < maxRxSCs+1) && (an <= (Ip_u8)maxRxSAs); an++) {
Ipmacsec_secy_key_descriptor key_desc;
Ipmacsec_secy_sa_descriptor sa_desc;
Ip_u32 ref = (an+1)<<16;
/* Init the key descriptor */
ipcom_memset(&key_desc, 0, sizeof(key_desc));
key_desc.key_id.val = (Ip_u64)((sc<<8)+an+1);
key_desc.key_type |= IPMACSEC_KEYTYPE_RECEIVE;
/* Init the SA descriptor */
if (an < (Ip_u8)maxRxSAs) {
if (ipmacsec_lmi_secy_sa_descriptor_init(&sa_desc, rx_sci, an, IPMACSEC_RX, ref, &key_desc.key_id) == IP_NULL) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Failed to initialize RX SA descriptor for AN = %u.", an);
goto err_out;
}
} else {
/* For an invalid AN, we need to do it manually since ipmacsec_lmi_secy_sa_descriptor_init() does not allow it */
IPMACSEC_COPY_SCI(sa_desc.sci, rx_sci);
sa_desc.an = an;
sa_desc.dir = IPMACSEC_RX;
sa_desc.ref = ref;
sa_desc.key_id.val = key_desc.key_id.val;
}
/* Delete the SA */
ret = ipmacsec_lmi_secy_delete_rx_sa(lh, ifname, &sa_desc);
if (an < (Ip_u8)maxRxSAs) {
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to delete RX SA with AN %u (ret=%d, %s).",
an, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
/* Remove the key */
ret = ipmacsec_lmi_secy_key_remove(lh, ifname, &key_desc);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to remove key with key_id 0x%llx. (ret=%d, %s).",
key_desc.key_id.val, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
} else {
/* Should have failed to delete 1 more SA than Max */
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Unexpected success deleting RX SA with AN %u", an);
goto err_out;
}
}
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Retrieve RX SA list. There should be none */
if (sc < maxRxSCs+1) {
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Retrieving RX SA list *****",
num_exec_tests);
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_rx_sa_status(lh, ifname, rx_sci, -1, 0, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve RX SA list (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
remlen = 0;
sai = (Ipmacsec_secy_sa_info *)ipmacsec_buf_ptr(&response, 0, &remlen);
if (remlen != 0) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Invalid RX SA list (sai=%p, remlen=%u).",
(void *)sai, remlen);
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Verify the RX SC is not receiving anymore */
num_exec_tests++;
IPCOM_LOG2(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Verifyign RX SC #%u is not receiving *****",
num_exec_tests, sc);
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_rx_sc_status(lh, ifname, rx_sci, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve RX SC #%u (ret=%d, %s).",
sc, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
remlen = 0;
scinf = (Ipmacsec_secy_sc_info *)ipmacsec_buf_ptr(&response, 0, &remlen);
if (!scinf || (remlen < sizeof(Ipmacsec_secy_sc_info))) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Invalid RX SC list (scinf=%p, remlen=%u < %u).",
(void *)scinf, remlen, sizeof(Ipmacsec_secy_sc_info));
goto err_out;
}
if (scinf->status.rx.receiving) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: RX SC #%u should not be receiving", sc);
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
}
}
/* Retrieve RX SC list. Should be maxRxSCs */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Verifying RX SC list retrieval *****",
num_exec_tests);
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_rx_sc_status(lh, ifname, IP_NULL, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve TX SC list (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
remlen = 0;
scinf = (Ipmacsec_secy_sc_info *)ipmacsec_buf_ptr(&response, 0, &remlen);
if (!scinf || (remlen < sizeof(Ipmacsec_secy_sc_info)*maxRxSCs)) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Invalid RX SC list (scinf=%p, remlen=%u < %u).",
(void *)scinf, remlen, sizeof(Ipmacsec_secy_sc_info)*maxRxSCs);
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
/* Delete maxRxSCs RX SCs + 1 (last one should fail) */
for (sc=1; sc <= maxRxSCs+1; sc++) {
Ip_u8 rx_sci[IPMACSEC_SCI_LEN];
num_exec_tests++;
if (sc < maxRxSCs+1)
IPCOM_LOG2(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Deleting RX SC #%u *****", num_exec_tests, sc);
else
IPCOM_LOG2(INFO,
"***** IPMACSEC-SC_SA_TEST: Executing test #%u: Trying to delete one more RX SC that suported (#%u should fail) *****",
num_exec_tests, sc);
ipcom_memset(rx_sci, (Ip_u8)sc, IPMACSEC_SCI_LEN);
ret = ipmacsec_lmi_secy_delete_rx_sc(lh, ifname, rx_sci);
if (sc < maxRxSCs+1) {
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Failed to delete RX SC #%u (ret=%d, %s).",
sc, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
} else {
if (ret == IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: Unexpected success in deleting RX SC #%u (ret=%d, %s).",
sc, ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
}
/* Retrieve RX SC list. Should be none */
num_exec_tests++;
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Executing test #%u: Verifying RX SC list retrieval returns nothing *****",
num_exec_tests);
IPMACSEC_BUF_WIPE(&response);
ret = ipmacsec_lmi_secy_get_rx_sc_status(lh, ifname, IP_NULL, &response);
if (ret != IPMACSEC_LMIERR_NONE) {
num_failed_tests++;
IPCOM_LOG2(ERR, "IPMACSEC-SC_SA_TEST: Failed to retrieve TX SC list (ret=%d, %s).",
ret, ipmacsec_lmi_error_name(ret));
goto err_out;
}
remlen = 0;
scinf = (Ipmacsec_secy_sc_info *)ipmacsec_buf_ptr(&response, 0, &remlen);
if (remlen != 0) {
num_failed_tests++;
IPCOM_LOG1(ERR, "IPMACSEC-SC_SA_TEST: Unexpected RX SC list not empty (remlen=%u).",
remlen);
goto err_out;
}
IPCOM_LOG1(INFO, "***** IPMACSEC-SC_SA_TEST: Test #%u Successfully executed *****", num_exec_tests);
err_out:
if (num_failed_tests) {
IPCOM_LOG3(ERR, "IPMACSEC-SC_SA_TEST: COMPLETED WITH FAILURES - %u tests executed, %u failed for interface %s",
num_exec_tests, num_failed_tests, ifname);
ret = -1;
} else {
IPCOM_LOG2(INFO, "IPMACSEC-SC_SA_TEST: COMPLETED SUCCESSFULLY - %u tests executed successfully for interface %s",
num_exec_tests, ifname);
ret = 0;
}
(void)ipmacsec_lmi_handle_delete(lh);
(void)ipmacsec_nlmsg_free(&response);
return ret;
}
/*
*===========================================================================
* ipmacsec_counter_format_test
*===========================================================================
* Description: Test the ipmacsec_secy_counter_format() routine
* Parameters: none
* Returns: none
*
*/
IP_GLOBAL void ipmacsec_counter_format_test(void) {
Ipmacsec_secy_counter64 count;
char str[80];
for (count=1; count < 10*IPMACSEC_SECY_COUNTER_1E;) {
ipcom_printf("count %llu = %s\n", count-1, ipmacsec_secy_counter_format(str, sizeof(str), count-1));
ipcom_printf("count %llu = %s\n", count, ipmacsec_secy_counter_format(str, sizeof(str), count));
ipcom_printf("count %llu = %s\n", count+1, ipmacsec_secy_counter_format(str, sizeof(str), count+1));
ipcom_printf("count %llu = %s\n", count+count/1000, ipmacsec_secy_counter_format(str, sizeof(str), count+count/1000));
count = count*10;
}
count = 0xFFFFFFFFFFFFFFFFULL;
ipcom_printf("max count %llu = %s\n", count, ipmacsec_secy_counter_format(str, sizeof(str), count));
}
/*
*===========================================================================
* ipmacsec_parse_sci_string_test
*===========================================================================
* Description: Test the ipmacsec_parse_sci_string() routine
* Parameters: none
* Returns: none
*
*/
IP_GLOBAL int
ipmacsec_parse_sci_string_test(void) {
Ip_u8 sci[IPMACSEC_SCI_LEN];
Ip_u8 scival[IPMACSEC_SCI_LEN] = {0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77};
int ret = -1000;
ret = ipmacsec_parse_sci_string("00-11-22-33-44-55-66-77", sci);
if ((ret < 0) || (!IPMACSEC_SCI_MATCH(sci, scival))) {
return -1;
}
ret = ipmacsec_parse_sci_string("00:11:22:33:44:55:66:77", sci);
if ((ret < 0) || (!IPMACSEC_SCI_MATCH(sci, scival))) {
return -2;
}
ret = ipmacsec_parse_sci_string("00 11 22 33 44 55 66 77", sci);
if ((ret < 0) || (!IPMACSEC_SCI_MATCH(sci, scival))) {
return -3;
}
ret = ipmacsec_parse_sci_string("0011223344556677", sci);
if ((ret < 0) || (!IPMACSEC_SCI_MATCH(sci, scival))) {
return -4;
}
ret = ipmacsec_parse_sci_string("FF-FF-FF-FF-FF-FF-FF-FF", sci);
if ((ret < 0) || (!IPMACSEC_INVALID_SCI(sci))) {
return -5;
}
ret = ipmacsec_parse_sci_string("00*11*22*33*44*55*66*77", sci);
if (ret >= 0) {
return -6;
}
ret = ipmacsec_parse_sci_string("00-11-22-33-44-55-66-", sci);
if (ret >= 0) {
return -7;
}
ret = ipmacsec_parse_sci_string("00-11-22-33-44-55-66*77", sci);
if (ret >= 0) {
return -8;
}
ret = ipmacsec_parse_sci_string("00-11-22-33-44-55-66-77-", sci);
if (ret >= 0) {
return -9;
}
ret = ipmacsec_parse_sci_string("001122334455667", sci);
if (ret >= 0) {
return -10;
}
ret = ipmacsec_parse_sci_string("00112233445566778", sci);
if (ret >= 0) {
return -11;
}
ret = ipmacsec_parse_sci_string("X0-00-00-00-00-00-00-00", sci);
if (ret >= 0) {
return -12;
}
return 0;
}
/*
*===========================================================================
* ipmacsec_secy_ucp_test
*===========================================================================
* Description: Test the MACsec SecY Uncontrolled Port reception
* Parameters: ifname - Interface bame
* num_expected_pkts - # of packets to expect before existing (0 ==> loop forever or until timeout)
* timeout - # of seconds before timing out (in seconds) (0 ==> no timeout)
* Returns: # of UCP received packets upon success, <0 on error
*
*/
IP_GLOBAL int ipmacsec_secy_ucp_test(char *ifname, Ip_u32 num_expected_pkts, Ip_u32 timeout) {
Ip_fd sock = IP_INVALID_SOCKET;
struct Ip_sockaddr_ll ll;
int ret = -1;
Ip_u8 *pkt = IP_NULL;
Ip_u32 npkts = 0, nseconds = 0;
if(!ifname || ifname[0] == 0) {
IPCOM_LOG0(ERR, "ipmacsec_secy_ucp_test :: ifname not set");
goto err_out;
}
sock = ipcom_socket(IP_PF_PACKET, IP_SOCK_RAW, IPNET_ETHFRAME_MACSEC);
if (sock == IP_INVALID_SOCKET) {
IPCOM_LOG1(ERR, "ipmacsec_secy_ucp_test :: ipcom_socket() failed, errno: %d\n", ipcom_errno);
goto err_out;
}
IPCOM_LOG1(INFO, "ipmacsec_secy_ucp_test ::opened MACsec raw socket (fd = %u)\n", sock);
ipcom_memset(&ll, 0, sizeof(ll));
ll.sll_family = IP_AF_PACKET;
ll.sll_ifindex = ipcom_if_nametoindex(ifname);
if(ll.sll_ifindex == 0) {
IPCOM_LOG1(ERR, "ipmacsec_secy_ucp_test :: ipcom_if_nametoindex failed for %s", ifname);
goto err_out;
}
/* Bind raw socket to device */
if (ipcom_setsockopt(sock, IP_SOL_SOCKET, IP_SO_BINDTODEVICE,
ifname, IP_IFNAMSIZ) == IP_SOCKERR) {
IPCOM_LOG3(ERR, "ipmacsec_secy_ucp_test :: ipcom_setsockopt(bindtodevice,%s) failed : %s [%d]",
ifname, ipcom_strerror(ipcom_errno), ipcom_errno);;
goto err_out;
}
IPCOM_LOG2(INFO, "ipmacsec_secy_ucp_test :: bound sock to %s (index %u)", ifname, ll.sll_ifindex);
pkt = ipcom_malloc(1514);
if (!pkt) {
IPCOM_LOG0(ERR, "ipmacsec_secy_ucp_test :: failed to allocate packet");
goto err_out;
}
while(1) {
int rc;
Ip_fd_set rset;
struct Ip_timeval tv;
IP_FD_ZERO(&rset);
IP_FD_SET(sock, &rset);
tv.tv_sec = 1;
tv.tv_usec = 0;
IPCOM_LOG1(DEBUG2, "ipmacsec_secy_ucp_test :: blocking on socket %u", sock);
ret = ipcom_socketselect(sock + 1, &rset, IP_NULL, IP_NULL, &tv);
if (ret < 0) {
IPCOM_LOG1(ERR, "ipmacsec_secy_ucp_test :: ipcom_socketselect failed (%d)", rc);
goto err_out;
}
if (ret == 0) {
nseconds++;
}
while (ret) {
rc = ipcom_recvfrom(sock, pkt, 1514, 0, IP_NULL, IP_NULL);
if (rc <= 0) {
IPCOM_LOG1(ERR, "ipmacsec_secy_ucp_test :: ipcom_recvfrom failed (%d)", rc);
goto err_out;
}
npkts++;
ret--;
IPCOM_LOG2(DEBUG2, "ipmacsec_secy_ucp_test ::rc = %d on socket %u", rc, sock);
ipmacsec_dump_buffer("MACsec received frame: ", pkt, rc);
}
if (num_expected_pkts && (npkts >= num_expected_pkts)) {
break;
}
if (timeout && (nseconds >= timeout))
break;
}
ret = npkts;
err_out:
if(sock != IP_INVALID_SOCKET) {
ipcom_socketclose(sock);
sock = IP_INVALID_SOCKET;
}
if (pkt) {
ipcom_free(pkt);
pkt = IP_NULL;
}
IPCOM_LOG1(INFO, "ipmacsec_secy_ucp_test :: Exiting (ret = %d)", ret);
return ret;
}
/* Variable used to store # of pkts received by the MACsec SecY Uncontrolled Port reception daemon */
IP_STATIC int ucp_test_daemon_nrcv_pkts = 0;
/*
*===========================================================================
* ipmacsec_secy_ucp_testd
*===========================================================================
* Description: MACsec SecY Uncontrolled Port reception test daemon
* Parameters:
* Returns:
*
*/
IP_STATIC
IPCOM_PROCESS(ipmacsec_secy_ucp_testd) {
char ifname[IP_IFNAMSIZ];
Ip_size_t len;
Ip_u32 num_expected_pkts;
Ip_u32 timeout;
char strval[16];
char *sysvar;
IPCOM_LOG0(DEBUG2, "ipmacsec_secy_ucp_testd :: Started");
ucp_test_daemon_nrcv_pkts = -1;
ipcom_proc_init();
sysvar = "ipmacsec.secy.ut.ucptestd.ifname";
len = IP_IFNAMSIZ;
if (ipcom_sysvar_get(sysvar, ifname, &len) == IP_NULL) {
IPCOM_LOG1(WARNING, "ipmacsec_secy_ucp_testd :: Failed to get sysvar %s", sysvar);
goto exit;
}
sysvar = "ipmacsec.secy.ut.ucptestd.npkts";
len = sizeof(strval);
if (ipcom_sysvar_get(sysvar, strval, &len) == IP_NULL) {
IPCOM_LOG1(WARNING, "ipmacsec_secy_ucp_testd :: Failed to get sysvar %s", sysvar);
goto exit;
}
num_expected_pkts = ipcom_atoi(strval);
sysvar = "ipmacsec.secy.ut.ucptestd.timeout";
len = sizeof(strval);
if (ipcom_sysvar_get(sysvar, strval, &len) == IP_NULL) {
IPCOM_LOG1(WARNING, "ipmacsec_secy_ucp_testd :: Failed to get sysvar %s", sysvar);
goto exit;
}
timeout = ipcom_atoi(strval);
ucp_test_daemon_nrcv_pkts = ipmacsec_secy_ucp_test(ifname, num_expected_pkts, timeout);
exit:
IPCOM_LOG1(DEBUG2, "ipmacsec_secy_ucp_testd :: Exiting (ucp_test_daemon_nrcv_pkts = %d)", ucp_test_daemon_nrcv_pkts);
ipcom_proc_exit();
}
/*
*===========================================================================
* ipmacsec_secy_ucp_test_start_daemon
*===========================================================================
* Description: Start a MACsec SecY Uncontrolled Port reception test daemon
* Should only start one daemon at a time.
* Parameters: ifname - Interface bame
* num_expected_pkts - # of packets to expect before existing (0 ==> loop forever or until timeout)
* timeout - # of seconds before timing out (in seconds) (0 ==> no timeout)
* Returns: 0 upon successfully starting the daemon, <0 on error
*
*/
IP_GLOBAL int ipmacsec_secy_ucp_test_start_daemon(char *ifname, Ip_u32 num_expected_pkts, Ip_u32 timeout) {
Ipcom_proc_attr proc_attr;
char strval[16];
char *sysvar;
Ip_err rc;
sysvar = "ipmacsec.secy.ut.ucptestd.ifname";
if ((rc = ipcom_sysvar_set(sysvar, ifname, IPCOM_SYSVAR_FLAG_OVERWRITE)) != IPCOM_SUCCESS) {
IPCOM_LOG1(CRIT, "ipmacsec_secy_ucp_testd :: Failed to set sysvar %s", sysvar);
return rc;
}
ipcom_snprintf(strval, sizeof(strval), "%d", num_expected_pkts);
sysvar = "ipmacsec.secy.ut.ucptestd.npkts";
if ((rc = ipcom_sysvar_set(sysvar, strval, IPCOM_SYSVAR_FLAG_OVERWRITE)) != IPCOM_SUCCESS) {
IPCOM_LOG1(CRIT, "ipmacsec_secy_ucp_testd :: Failed to set sysvar %s", sysvar);
return rc;
}
ipcom_snprintf(strval, sizeof(strval), "%d", timeout);
sysvar = "ipmacsec.secy.ut.ucptestd.timeout";
if ((rc = ipcom_sysvar_set(sysvar, strval, IPCOM_SYSVAR_FLAG_OVERWRITE)) != IPCOM_SUCCESS) {
IPCOM_LOG1(CRIT, "ipmacsec_secy_ucp_testd :: Failed to set sysvar %s", sysvar);
return rc;
}
ipcom_proc_attr_init(&proc_attr);
proc_attr.stacksize = IPCOM_PROC_STACK_SMALL;
rc = ipcom_proc_acreate("secy_ucp_testd", ipmacsec_secy_ucp_testd, &proc_attr, IP_NULL);
return rc;
}
/*
*===========================================================================
* ipmacsec_secy_ucp_test_daemon_num_rcv_pkts
*===========================================================================
* Description: Return the # of pkts received by the MACsec SecY Uncontrolled Port reception daemon
* Parameters: None
* Returns: # of pkts rcvd
*
*/
IP_GLOBAL Ip_u32 ipmacsec_secy_ucp_test_daemon_num_rcv_pkts(void) {
return ucp_test_daemon_nrcv_pkts;
}
/* UNIT TEST CODE FOR EASILY SETTING UP SECY CONFIGURATION */
Ipmacsec_secy_profile *Ipmacsec_secy_ut_profiles[] = {
&ipmacsec_ut_profile_1A,
&ipmacsec_ut_profile_1B,
&ipmacsec_ut_profile_2A,
&ipmacsec_ut_profile_2B,
&ipmacsec_ut_profile_3A,
&ipmacsec_ut_profile_3B
};
/*
*===========================================================================
* ipmacsec_lmi_secy_setup_ut_profile
*===========================================================================
* Description: Setup the specified Unit Test SecY profile
* Parameters: ifname - Interface bame
* ut_profile_index - Index of the unit test profile to setup
* Returns: IPMACSEC_LMIERR_NONE upon success,
* an Ipmacsec_lmi_error <0 upon error
*
*/
IP_GLOBAL Ipmacsec_lmi_error
ipmacsec_lmi_secy_setup_ut_profile(char *ifname, Ip_u8 ut_profile_index) {
if (ut_profile_index >= sizeof(Ipmacsec_secy_ut_profiles)/sizeof(Ipmacsec_secy_profile *)) {
return IPMACSEC_LMIERR_INVALID_PARAMETER;
}
return ipmacsec_lmi_secy_setup_profile(ifname, Ipmacsec_secy_ut_profiles[ut_profile_index]);
}
#endif