FIPS (Federal Information Processing Standard) 140 series are U.S. government computer security standards that specify requirements for cryptography modules. The latest version is FIPS 140-3 (ISO standard 19790).
The National Institute of Standards and Technology (NIST) issues the 140 Publication Series to coordinate the requirements and standards for cryptographic modules which include HW, SW, and/or FW components for use by departments and agencies of the U.S. government. In U.S., government agencies desiring to deploy cryptographic modules should confirm that the module they are using has a valid FIPS 140 certificate. The Government of Canada also recommends the use of FIPS 140 validated cryptographic modules in unclassified applications of its departments. In addition, in recent years FIPS 140 has become a more and more popular requirement in financial and health care sectors as well.
FIPS 140-3 defines 4 security levels (from level 1 - the easiest to level 4 - the most stringent). In general, software may be certified at up to level 2.
Intel® Cryptography Primitives Library provides building blocks of FIPS-mode API (such as self-tests, FIPS-approved functionality status query) which can help the end users to fulfill FIPS level 1 requirements. Please, refer to Covered Algorithms section for the full list of FIPS-Approved API which are covered with the selftests.
NOTE: Intel® Cryptography Primitives Library is not FIPS-Certified on its own but FIPS-Compliant: that means Intel® Cryptography Primitives Library releases will have Cryptographic Algorithm Validation Program (CAVP) testing and certification done but don't have full Cryptographic Module Validation Program certificate as the context of the usage of Intel® Cryptography Primitives Library's high-performant primitives depends on a more high-level application.
For the results of CAVP testing please refer to Latest Certification chapter.
Intel® Cryptography Primitives Library may be built in FIPS-mode with IPPCP_FIPS_MODE=on configuration for ippcp and MBX_FIPS_MODE=on for crypto_MB (see details in Build section).
Application, which uses Intel® Cryptography Primitives Library may be FIPS-Certified by matching FIPS 140 requirement and obtaining NIST certificate or also be FIPS-Compliant for their own customers.
Please, refer to Level 1 Specific Requirements for the detailed description of what is done on Intel® Cryptography Primitives Library-side and what should be done by a more high-level application.
# | Requirement | Note |
---|---|---|
1 | Provide service to output module's name / identifier and version to User | Intel® Cryptography Primitives Library provides such functionality via ippcpGetLibVersion() API for IPPCP and mbx_getversion() API for crypto_MB |
2 | For every service, output to the user whether it is a FIPS-approved service or not | Intel® Cryptography Primitives Library provides such functionality via ippcp_is_fips_approved_func for ippcp and mbx_is_fips_approved_func for crypto_MB |
3 | Zeroize unprotected keys using manual/procedural destruction method | User's application effort required |
4 | Run integrity selftest at power on for SW component | User's application effort required |
5 | Run known-answer or comparison or fault-detection selftest for individual crypto algorithms before first use | Intel® Cryptography Primitives Library provides fips_selftest_ippcp API to run selftests. User's application should call them before the first use of algorithm (see Example) |
6 | Run pairwise consistency selftest for newly generated RSA/ECC keypair | Intel® Cryptography Primitives Library provides fips_selftest_ippcp API to run selftests |
7 | Module to guarantee uniqueness of GCM key + IV | User's application effort required |
8 | Module to guarantee XTS key1 != key2 | Intel® Cryptography Primitives Library-side check |
9 | (non-production) Extract raw noise source output samples of RBG for quality analysis | DBRNG is currently out of the cryptography boundary |
10 | (non-production) Run crypto algorithm testing with NIST-generated vectors | Done offline by Intel® Cryptography Primitives Library for the covered algorithms |
For the implementation details about the steps in Level 1 Specific Requirements specified as User's application effort required please refer to the Implementation Guidance for FIPS 140-3 and the Cryptographic Module Validation Program by the National Institute of Standards and Technology.
- Intel® Cryptography Primitives Library uses special structures (Spec and States) to store context information and provides service functions to work with context (e.g. Initialization).
Note: Application responsible for the life-cycle of context. All memory allocations and sanitizing happens on application side (including #3 in Level 1 Specific Requirements).
- Cryptographic Algorithms API (both FIPS-Compliant and not FIPS Compliant).
- FIPS Self-tests API and service to query if algorithm is FIPS-Compliant (API for #2, #5, #6 in Level 1 Specific Requirements).
- Version information (API for #1 in Level 1 Specific Requirements), Dispatcher control.
- Intel® Cryptography Primitives Library chooses the optimal code path depending on hardware features and application settings (via Dispatcher control API).
- The algorithms may have multiple code branches for different hardware architecture and different compilation flags may be used to achieve better performance.
Refer to Covered Algorithms section to check which algorithms are within the cryptographic boundary.
Note: For #10 in Level 1 Specific Requirements Intel® Cryptography Primitives Library tests all code-paths and algorithms modes as the implementation may vary depending on the target hardware.
CMake flag -DIPPCP_FIPS_MODE:BOOL=on should be used to build ippcp library and -DMBX_FIPS_MODE:BOOL=on for crypto_MB in FIPS-mode. These modes enable extra API for self-tests and FIPS-support query (see covered algorithms for the details). Selftests can be build in two modes - with internal memory allocation or without it.
Configuration example for ippcp with Intel® oneAPI DPC++/C++ Compiler:
CC=icx CXX=icpx cmake CMakeLists.txt -B_build -DARCH=intel64 -DIPPCP_FIPS_MODE:BOOL=on [-DIPPCP_SELFTEST_USE_MALLOC:BOOL=on]
Note: selftests with internal memory allocation uses malloc, which introduces a c runtime dependency. To avoid the dependency, use IPPCP_SELFTEST_USE_MALLOC:BOOL=off or do not specify it as this as the default. In this case, all self-tests will require external memory allocation.
Configuration example for crypto_MB with GCC:
CC=gcc CXX=g++ cmake CMakeLists.txt -B_build -DARCH=intel64 -DMBX_FIPS_MODE:BOOL=on
//------ FIPS-required part
// 1. check that the function is FIPS-approved:
if(!ippcp_is_fips_approved_func(AESEncryptCBC)) {
return -1; // cannot use this function in FIPS mode.
}
// 2. Run the Selftest
fips_test_status selftest_status = IPPCP_ALGO_SELFTEST_OK;
// Query buffer size for the test and allocate it (it can be done on Intel® Cryptography Primitives Library side with IPPCP_SELFTEST_USE_MALLOC=on)
int BuffSize = 0;
selftest_status += fips_selftest_ippsAESEncryptDecrypt_get_size(&BuffSize);
std::vector<Ipp8u> pBuff(BuffSize);
// Run the test
selftest_status += fips_selftest_ippsAESEncryptCBC(pBuff.data());
// Check selftest status
if (IPPCP_ALGO_SELFTEST_OK != selftest_status) {
return -1; // selftest is not successful -> cannot use this function in FIPS mode.
}
//------ FIPS-required part ends (only needed before the first use of algorithm)
//------ Common Intel® Cryptography Primitives Library usage
// ...
IppStatus status = ippsAESEncryptCBC(plain, cipher, block_size, pAES, cipherV);
// ...
//------ FIPS-required part
// 1. check that the function is FIPS-approved:
if(!mbx_is_fips_approved_func(nistp256_ecdh_mb8)) {
return -1; // cannot use this function in FIPS mode.
}
// 2. Run the Selftest
if (fips_selftest_mbx_nistp256_ecdh_mb8() != MBX_ALGO_SELFTEST_OK) {
return -1; // selftest is not successful -> cannot use this function in FIPS mode.
}
//------ FIPS-required part ends (only needed before the first use of algorithm)
//------ Common Crypto Multi-buffer Library usage
// ...
mbx_nistp256_ecdh_mb8(sharedAB, prvA, pubBx, pubBy, pubBz_curr, 0);
mbx_nistp256_ecdh_mb8(sharedBA, prvB, pubAx, pubAy, pubAz_curr, 0);
// ...
Each API from the list is covered with the selftest fips_selftest_ipps<API_name> available in Intel® Cryptography Primitives Library build in FIPS mode.
fips_test_status fips_selftest_ippsAESEncryptDecrypt_get_size (int *pBuffSize);
fips_test_status fips_selftest_ippsAESEncryptCBC (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESDecryptCBC (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESEncryptCBC_CS1 (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESEncryptCBC_CS2 (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESEncryptCBC_CS3 (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESDecryptCBC_CS1 (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESDecryptCBC_CS2 (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESDecryptCBC_CS3 (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESEncryptCFB (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESDecryptCFB (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESEncryptOFB (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESDecryptOFB (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESEncryptCTR (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAESDecryptCTR (Ipp8u *pBuffer);
, where pBuffer
is the valid buffer for selftest of size indicated by fips_selftest_ippsAESEncryptDecrypt_get_size
.
fips_test_status fips_selftest_ippsAESEncryptDecryptCCM_get_size (int *pBuffSize);
fips_test_status fips_selftest_ippsAES_CCMEncrypt (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAES_CCMDecrypt (Ipp8u *pBuffer);
, where pBuffer
is the valid buffer for selftest of size indicated by fips_selftest_ippsAESEncryptDecryptCCM_get_size
.
fips_test_status fips_selftest_ippsAES_GCM_get_size (int *pBufferSize);
fips_test_status fips_selftest_ippsAES_GCMEncrypt (Ipp8u *pBuffer);
fips_test_status fips_selftest_ippsAES_GCMDecrypt (Ipp8u *pBuffer);
, where pBuffer
is the valid buffer for selftest of size indicated by fips_selftest_ippsAES_GCM_get_size
.
fips_test_status fips_selftest_ippsAES_CMAC_get_size (int *pBuffSize);
fips_test_status fips_selftest_ippsAES_CMACUpdate (Ipp8u *pBuffer);
, where pBuffer
is the valid buffer for selftest of size indicated by fips_selftest_ippsAES_CMAC_get_size
.
fips_test_status fips_selftest_ippsRSAEncryptDecrypt_OAEP_rmf_get_size_keys (int *pKeysBufferSize);
fips_test_status fips_selftest_ippsRSAEncryptDecrypt_OAEP_rmf_get_size (int *pBufferSize Ipp8u *pKeysBuffer);
fips_test_status fips_selftest_ippsRSAEncrypt_OAEP_rmf (Ipp8u *pBuffer Ipp8u *pKeysBuffer);
fips_test_status fips_selftest_ippsRSADecrypt_OAEP_rmf (Ipp8u *pBuffer Ipp8u *pKeysBuffer);
, where pBuffer
is the valid buffer for selftest of size indicated by
fips_selftest_ippsRSAEncryptDecrypt_OAEP_rmf_get_size
and pKeysBuffer
is the
valid buffer for selftest of size indicated by fips_selftest_ippsRSAEncryptDecrypt_OAEP_rmf_get_size_keys
.
fips_test_status fips_selftest_ippsHash_rmf_get_size (int *pBuffSize);
fips_test_status fips_selftest_ippsHashUpdate_rmf (IppHashAlgId hashAlgId, Ipp8u *pBuffer);
, where pBuffer
is the valid buffer for selftest of size indicated by fips_selftest_ippsHash_rmf_get_size
.
fips_test_status fips_selftest_ippsHashMessage_rmf (IppHashAlgId hashAlgId);
fips_test_status fips_selftest_ippsHMAC_rmf_get_size (int *pBuffSize);
fips_test_status fips_selftest_ippsHMACUpdate_rmf (Ipp8u *pBuffer);
, where pBuffer
is the valid buffer for selftest of size indicated by fips_selftest_ippsHMAC_rmf_get_size
.
fips_test_status fips_selftest_ippsHMACMessage_rmf (void);
fips_test_status fips_selftest_ippsRSASignVerify_PKCS1v15_rmf_get_size_keys (int *pKeysBufferSize);
fips_test_status fips_selftest_ippsRSASignVerify_PKCS1v15_rmf_get_size (int *pBufferSize Ipp8u *pKeysBuffer);
fips_test_status fips_selftest_ippsRSASign_PKCS1v15_rmf (Ipp8u *pBuffer Ipp8u *pKeysBuffer);
fips_test_status fips_selftest_ippsRSAVerify_PKCS1v15_rmf (Ipp8u *pBuffer Ipp8u *pKeysBuffer);
, where pBuffer
is the valid buffer for selftest of size indicated by
fips_selftest_ippsRSASignVerify_PKCS1v15_rmf_get_size
and pKeysBuffer
is the
valid buffer for selftest of size indicated by fips_selftest_ippsRSASignVerify_PKCS1v15_rmf_get_size_keys
.
fips_test_status fips_selftest_ippsRSASignVerify_PSS_rmf_get_size_keys (int *pKeysBufferSize);
fips_test_status fips_selftest_ippsRSASignVerify_PSS_rmf_get_size (int *pBufferSize Ipp8u *pKeysBuffer);
fips_test_status fips_selftest_ippsRSASign_PSS_rmf (Ipp8u *pBuffer Ipp8u *pKeysBuffer);
fips_test_status fips_selftest_ippsRSAVerify_PSS_rmf (Ipp8u *pBuffer Ipp8u *pKeysBuffer);
fips_test_status fips_selftest_ippsRSA_GenerateKeys (Ipp8u *pBuffer Ipp8u *pKeysBuffer);
, where pBuffer
is the valid buffer for selftest of size indicated by
fips_selftest_ippsRSASignVerify_PSS_rmf_get_size
and pKeysBuffer
is the
valid buffer for selftest of of size indicated by fips_selftest_ippsRSASignVerify_PSS_rmf_get_size_keys
.
fips_test_status fips_selftest_ippsGFpECSignVerifyDSA_get_size_GFp_buff (int *pGFpBuffSize);
fips_test_status fips_selftest_ippsGFpECSignVerifyDSA_get_size_GFpEC_buff (int *pGFpECBuffSize Ipp8u *pGFpBuff);
fips_test_status fips_selftest_ippsGFpECSignVerifyDSA_get_size_data_buff (int *pDataBuffSize Ipp8u *pGFpBuff Ipp8u *pGFpECBuff);
fips_test_status fips_selftest_ippsGFpECSignDSA (Ipp8u *pGFpBuff Ipp8u *pGFpECBuff Ipp8u *pDataBuff);
fips_test_status fips_selftest_ippsGFpECVerifyDSA (Ipp8u *pGFpBuff Ipp8u *pGFpECBuff Ipp8u *pDataBuff);
fips_test_status fips_selftest_ippsGFpECPublicKey (Ipp8u *pGFpBuff Ipp8u *pGFpECBuff Ipp8u *pDataBuff);
fips_test_status fips_selftest_ippsGFpECPrivateKey (Ipp8u *pGFpBuff Ipp8u *pGFpECBuff Ipp8u *pDataBuff);
fips_test_status fips_selftest_ippsGFpECSharedSecretDH (Ipp8u *pGFpBuff Ipp8u *pGFpECBuff Ipp8u *pDataBuff);
, where pGFpBuff
is the valid buffer for selftest of size indicated by
fips_selftest_ippsGFpECSignVerifyDSA_get_size_GFp_buff
, pGFpECBuff
is the
valid buffer for selftest of size indicated by fips_selftest_ippsGFpECSignVerifyDSA_get_size_GFpEC_buff
and pDataBuff
is the valid buffer for selftest of size indicated by fips_selftest_ippsGFpECSignVerifyDSA_get_size_data_buff
.
fips_test_status fips_selftest_ippsLMSVerify_get_size (int *pBuffSize);
fips_test_status fips_selftest_ippsLMSVerify (Ipp8u *pBuffer);
, where pBuffer
is the valid buffer for selftest of size indicated by fips_selftest_ippsLMSVerify_get_size
.
func_fips_approved ippcp_is_fips_approved_func(enum FIPS_IPPCP_FUNC function);
Which APIs are not supported by this query:
- auxiliary API regulating code dispatching process or general library settings (ippcpGetCpuFeatures, ippcpSetNumThreads, ippcpGetStatusString, ippcpGetLibVersion, etc.)
- API to work with IPPCP-specific context (ippsInit, ippsSetKey, ippsGetSize, ippsReset, ippsDuplicate, ippsSet* etc.)
- API implementing the base mathematic functions, which are not defined as a cryptographic algorithm (ippsAdd_BN, ippsMul_BN, ippsGFpNeg, etc)
- deprecated API
For the exact list of the supported symbols please, refer to FIPS_IPPCP_FUNC
enumerator in include/ippcp/fips_cert.h.
fips_test_status fips_selftest_mbx_nistp256_ecpublic_key_mb8(void);
fips_test_status fips_selftest_mbx_nistp384_ecpublic_key_mb8(void);
fips_test_status fips_selftest_mbx_nistp521_ecpublic_key_mb8(void);
fips_test_status fips_selftest_mbx_nistp256_ecdh_mb8(void);
fips_test_status fips_selftest_mbx_nistp384_ecdh_mb8(void);
fips_test_status fips_selftest_mbx_nistp521_ecdh_mb8(void);
fips_test_status fips_selftest_mbx_nistp256_ecdsa_sign_mb8(void);
fips_test_status fips_selftest_mbx_nistp384_ecdsa_sign_mb8(void);
fips_test_status fips_selftest_mbx_nistp521_ecdsa_sign_mb8(void);
fips_test_status fips_selftest_mbx_nistp256_ecdsa_sign_setup_complete_mb8(void);
fips_test_status fips_selftest_mbx_nistp384_ecdsa_sign_setup_complete_mb8(void);
fips_test_status fips_selftest_mbx_nistp521_ecdsa_sign_setup_complete_mb8(void);
fips_test_status fips_selftest_mbx_nistp256_ecdsa_verify_mb8(void);
fips_test_status fips_selftest_mbx_nistp384_ecdsa_verify_mb8(void);
fips_test_status fips_selftest_mbx_nistp521_ecdsa_verify_mb8(void);
fips_test_status fips_selftest_mbx_ed25519_public_key_mb8(void);
fips_test_status fips_selftest_mbx_ed25519_sign_mb8(void);
fips_test_status fips_selftest_mbx_ed25519_verify_mb8(void);
fips_test_status fips_selftest_mbx_x25519_public_key_mb8(void);
fips_test_status fips_selftest_mbx_x25519_mb8(void);
fips_test_status fips_selftest_mbx_nistp256_ecpublic_key_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp384_ecpublic_key_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp521_ecpublic_key_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp256_ecdh_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp384_ecdh_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp521_ecdh_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp256_ecdsa_sign_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp384_ecdsa_sign_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp521_ecdsa_sign_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp256_ecdsa_sign_setup_complete_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp384_ecdsa_sign_setup_complete_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp521_ecdsa_sign_setup_complete_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp256_ecdsa_verify_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp384_ecdsa_verify_ssl_mb8(void);
fips_test_status fips_selftest_mbx_nistp521_ecdsa_verify_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa1k_public_mb8(void);
fips_test_status fips_selftest_mbx_rsa2k_public_mb8(void);
fips_test_status fips_selftest_mbx_rsa3k_public_mb8(void);
fips_test_status fips_selftest_mbx_rsa4k_public_mb8(void);
fips_test_status fips_selftest_mbx_rsa1k_private_mb8(void);
fips_test_status fips_selftest_mbx_rsa2k_private_mb8(void);
fips_test_status fips_selftest_mbx_rsa3k_private_mb8(void);
fips_test_status fips_selftest_mbx_rsa4k_private_mb8(void);
fips_test_status fips_selftest_mbx_rsa1k_private_crt_mb8(void);
fips_test_status fips_selftest_mbx_rsa2k_private_crt_mb8(void);
fips_test_status fips_selftest_mbx_rsa3k_private_crt_mb8(void);
fips_test_status fips_selftest_mbx_rsa4k_private_crt_mb8(void);
fips_test_status fips_selftest_mbx_rsa1k_public_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa2k_public_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa3k_public_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa4k_public_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa1k_private_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa2k_private_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa3k_private_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa4k_private_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa1k_private_crt_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa2k_private_crt_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa3k_private_crt_ssl_mb8(void);
fips_test_status fips_selftest_mbx_rsa4k_private_crt_ssl_mb8(void);
func_fips_approved mbx_is_fips_approved_func(enum FIPS_CRYPTO_MB_FUNC function);
For the exact list of the supported symbols please, refer to FIPS_CRYPTO_MB_FUNC
enumerator in include/crypto_mb/fips_cert.h.