@@ -2548,12 +2548,21 @@ int VerifyCallback(int preverify_ok, X509_STORE_CTX* ctx) {
25482548 return 1 ;
25492549}
25502550
2551- static bool IsSupportedAuthenticatedMode (int mode) {
2552- return mode == EVP_CIPH_CCM_MODE ||
2551+ static bool IsSupportedAuthenticatedMode (const EVP_CIPHER* cipher) {
2552+ const int mode = EVP_CIPHER_mode (cipher);
2553+ // Check `chacha20-poly1305` separately, it is also an AEAD cipher,
2554+ // but its mode is 0 which doesn't indicate
2555+ return EVP_CIPHER_nid (cipher) == NID_chacha20_poly1305 ||
2556+ mode == EVP_CIPH_CCM_MODE ||
25532557 mode == EVP_CIPH_GCM_MODE ||
25542558 IS_OCB_MODE (mode);
25552559}
25562560
2561+ static bool IsSupportedAuthenticatedMode (const EVP_CIPHER_CTX* ctx) {
2562+ const EVP_CIPHER* cipher = EVP_CIPHER_CTX_cipher (ctx);
2563+ return IsSupportedAuthenticatedMode (cipher);
2564+ }
2565+
25572566void CipherBase::Initialize (Environment* env, Local<Object> target) {
25582567 Local<FunctionTemplate> t = env->NewFunctionTemplate (New);
25592568
@@ -2601,7 +2610,7 @@ void CipherBase::CommonInit(const char* cipher_type,
26012610 " Failed to initialize cipher" );
26022611 }
26032612
2604- if (IsSupportedAuthenticatedMode (mode )) {
2613+ if (IsSupportedAuthenticatedMode (cipher )) {
26052614 CHECK_GE (iv_len, 0 );
26062615 if (!InitAuthenticated (cipher_type, iv_len, auth_tag_len))
26072616 return ;
@@ -2703,8 +2712,7 @@ void CipherBase::InitIv(const char* cipher_type,
27032712 }
27042713
27052714 const int expected_iv_len = EVP_CIPHER_iv_length (cipher);
2706- const int mode = EVP_CIPHER_mode (cipher);
2707- const bool is_authenticated_mode = IsSupportedAuthenticatedMode (mode);
2715+ const bool is_authenticated_mode = IsSupportedAuthenticatedMode (cipher);
27082716 const bool has_iv = iv_len >= 0 ;
27092717
27102718 // Throw if no IV was passed and the cipher requires an IV
@@ -2776,7 +2784,20 @@ bool CipherBase::InitAuthenticated(const char* cipher_type, int iv_len,
27762784 }
27772785
27782786 const int mode = EVP_CIPHER_CTX_mode (ctx_.get ());
2779- if (mode == EVP_CIPH_CCM_MODE || IS_OCB_MODE (mode)) {
2787+ if (mode == EVP_CIPH_GCM_MODE) {
2788+ if (auth_tag_len != kNoAuthTagLength ) {
2789+ if (!IsValidGCMTagLength (auth_tag_len)) {
2790+ char msg[50 ];
2791+ snprintf (msg, sizeof (msg),
2792+ " Invalid authentication tag length: %u" , auth_tag_len);
2793+ env ()->ThrowError (msg);
2794+ return false ;
2795+ }
2796+
2797+ // Remember the given authentication tag length for later.
2798+ auth_tag_len_ = auth_tag_len;
2799+ }
2800+ } else {
27802801 if (auth_tag_len == kNoAuthTagLength ) {
27812802 char msg[128 ];
27822803 snprintf (msg, sizeof (msg), " authTagLength required for %s" , cipher_type);
@@ -2809,21 +2830,6 @@ bool CipherBase::InitAuthenticated(const char* cipher_type, int iv_len,
28092830 if (iv_len == 12 ) max_message_size_ = 16777215 ;
28102831 if (iv_len == 13 ) max_message_size_ = 65535 ;
28112832 }
2812- } else {
2813- CHECK_EQ (mode, EVP_CIPH_GCM_MODE);
2814-
2815- if (auth_tag_len != kNoAuthTagLength ) {
2816- if (!IsValidGCMTagLength (auth_tag_len)) {
2817- char msg[50 ];
2818- snprintf (msg, sizeof (msg),
2819- " Invalid authentication tag length: %u" , auth_tag_len);
2820- env ()->ThrowError (msg);
2821- return false ;
2822- }
2823-
2824- // Remember the given authentication tag length for later.
2825- auth_tag_len_ = auth_tag_len;
2826- }
28272833 }
28282834
28292835 return true ;
@@ -2846,8 +2852,7 @@ bool CipherBase::CheckCCMMessageLength(int message_len) {
28462852bool CipherBase::IsAuthenticatedMode () const {
28472853 // Check if this cipher operates in an AEAD mode that we support.
28482854 CHECK (ctx_);
2849- const int mode = EVP_CIPHER_CTX_mode (ctx_.get ());
2850- return IsSupportedAuthenticatedMode (mode);
2855+ return IsSupportedAuthenticatedMode (ctx_.get ());
28512856}
28522857
28532858
@@ -2892,7 +2897,7 @@ void CipherBase::SetAuthTag(const FunctionCallbackInfo<Value>& args) {
28922897 } else {
28932898 // At this point, the tag length is already known and must match the
28942899 // length of the given authentication tag.
2895- CHECK (mode == EVP_CIPH_CCM_MODE || IS_OCB_MODE (mode ));
2900+ CHECK (IsSupportedAuthenticatedMode (cipher-> ctx_ . get () ));
28962901 CHECK_NE (cipher->auth_tag_len_ , kNoAuthTagLength );
28972902 is_valid = cipher->auth_tag_len_ == tag_len;
28982903 }
@@ -3099,7 +3104,7 @@ bool CipherBase::Final(unsigned char** out, int* out_len) {
30993104 *out = Malloc<unsigned char >(
31003105 static_cast <size_t >(EVP_CIPHER_CTX_block_size (ctx_.get ())));
31013106
3102- if (kind_ == kDecipher && IsSupportedAuthenticatedMode (mode )) {
3107+ if (kind_ == kDecipher && IsSupportedAuthenticatedMode (ctx_. get () )) {
31033108 MaybePassAuthTagToOpenSSL ();
31043109 }
31053110
0 commit comments