Hi All, In our application, net-snmp library is used for making snmpget calls and processing snmp traps. it works perfectly. But with enabling OpenSSL FIPS mode application crashes when AES encryption algorithm is used. AES is FIPS compliant algorithms application should not crash when using AES.
application crashes from OpenSSL with message : aes_misc.c(74): OpenSSL internal error, assertion failed: Low level API call to cipher AES forbidden in FIPS mode! It can be seen in code for encryption and decryption, OpenSSL low level APIs are used. which gets blocked when OpenSSL is in FIPS mode. Here is the code snippet from library(snmplib/scapi.c) For Encryption: int sc_encrypt () { ... #ifdef HAVE_AES if (ISTRANSFORM(privtype, AESPriv)) { (void) AES_set_encrypt_key(key, properlength*8, &aes_key); memcpy(my_iv, iv, ivlen); /* * encrypt the data */ AES_cfb128_encrypt(plaintext, ciphertext, ptlen, &aes_key, my_iv, &new_ivlen, AES_ENCRYPT); *ctlen = ptlen; } #endif ... } For Decryption: int sc_decrypt() { ... #ifdef HAVE_AES if (ISTRANSFORM(privtype, AESPriv)) { (void) AES_set_encrypt_key(key, properlength*8, &aes_key); memcpy(my_iv, iv, ivlen); /* * encrypt the data */ AES_cfb128_encrypt(ciphertext, plaintext, ctlen, &aes_key, my_iv, &new_ivlen, AES_DECRYPT); *ptlen = ctlen; } #endif ... } OpenSSL api AES_set_encrypt_key() is blocked from openssl if it runs in FIPS mode. I have tried modifying the above code to use Openssl EVP apis instead of low level apis for encryption and decryption for AES. Below are the changes: For Encryption: int sc_encrypt() { ... #ifdef HAVE_AES if (ISTRANSFORM(privtype, AESPriv)) { EVP_CIPHER_CTX ctx; int outlen = 0; int tmplen = 0; EVP_CIPHER_CTX_init(&ctx); EVP_EncryptInit_ex(&ctx, EVP_aes_128_cfb(), NULL, key, iv); EVP_CIPHER_CTX_set_key_length(&ctx, keylen); if(!EVP_EncryptUpdate(&ctx, ciphertext, &outlen, plaintext, ptlen)) { snmp_log(LOG_ERR, "Cipher encryption update of plaintext failed\n"); return FALSE; } /* Buffer passed to EVP_EncryptFinal() must be after data just * encrypted to avoid overwriting it. */ if(!EVP_EncryptFinal_ex(&ctx, ciphertext + outlen, &tmplen)) { snmp_log(LOG_ERR, "Final cipher encryption of plaintext failed\n"); return FALSE; } outlen += tmplen; EVP_CIPHER_CTX_cleanup(&ctx); *ctlen = outlen; } #endif ... } For Decryption: int sc_decrypt(){ ... #ifdef HAVE_AES if (ISTRANSFORM(privtype, AESPriv)) { int decryptedLength = 0; int lastDecryptLength = 0; EVP_CIPHER_CTX cryptCtx; // Initialization EVP_CIPHER_CTX_init(&cryptCtx); if (EVP_DecryptInit_ex(&cryptCtx, EVP_aes_128_cfb(), NULL, key, iv) == 1) { EVP_CIPHER_CTX_set_key_length(&cryptCtx, keylen); /* Note that EVP_DecryptUpdate will alter the value of the third parameter to be equal to the amount of data that was written. */ /* This is not always the entire length of the decrypted data! To finish the decryption process, use EVP_DecryptFinal_ex. */ /* This will decrypt any remaining data */ if (EVP_DecryptUpdate(&cryptCtx, plaintext, &decryptedLength, ciphertext, ctlen) == 1) { // Stick the final data at the end of the last // decrypted data. if(EVP_DecryptFinal_ex(&cryptCtx, plaintext + decryptedLength, &lastDecryptLength) == 1) { decryptedLength = decryptedLength + lastDecryptLength; plaintext[decryptedLength] = 0; } else { snmp_log(LOG_ERR, "EVP_DecryptFinal_ex final decryption failed.\n"); return FALSE; } } else { snmp_log(LOG_ERR, "EVP_DecryptUpdate update decryption failed.\n"); return FALSE; } } else { snmp_log(LOG_ERR,"EVP_DecryptInit_ex init decryption failed.\n"); return FALSE; } } #endif ... } With these changes, application works without any problem. Kindly let me know if the above scenario is considered as issues and will be fixed in library. Please provide comments and let me know if any patch addressing the issue will be released. Thanks & Regards, Pushpendra
------------------------------------------------------------------------------
_______________________________________________ Net-snmp-coders mailing list Net-snmp-coders@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/net-snmp-coders