This is an automated email from the ASF dual-hosted git repository.

kou pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/arrow.git


The following commit(s) were added to refs/heads/main by this push:
     new 2fe4da09bf GH-45693: [C++][Gandiva] Fix aes_encrypt/decrypt algorithm 
selection (#45695)
2fe4da09bf is described below

commit 2fe4da09bf01a1ad8694dc3a989e8140bc2b596f
Author: lriggs <[email protected]>
AuthorDate: Thu Mar 13 19:30:31 2025 -0700

    GH-45693: [C++][Gandiva] Fix aes_encrypt/decrypt algorithm selection 
(#45695)
    
    ### Rationale for this change
    AES encrypt was only using a 128 bit algorithm which allowed limited cipher 
length and provided no warning when the cipher provided was longer than that 
which is supported.
    
    ### What changes are included in this PR?
    Update the C++ Gandiva functions to support 128, 192, 256 bits and 
corresponding cipher lengths. Throw an error if its incompatible.
    
    ### Are these changes tested?
    Yes, unit test and tested at Dremio.
    
    ### Are there any user-facing changes?
    Decryption may not work if the previously used encryption method used a 
truncated cipher.
    
    **This PR includes breaking changes to public APIs.**
    Decryption of previously encrypted values may not work. Previously 
supported cipher keys may not be supported. They must now be 128, 192, or 256 
bits (16, 24 or 32 characters).
    
    * GitHub Issue: #45693
    
    Lead-authored-by: Logan Riggs <[email protected]>
    Co-authored-by: Ivan Chesnov <[email protected]>
    Co-authored-by: lriggs <[email protected]>
    Co-authored-by: Sutou Kouhei <[email protected]>
    Signed-off-by: Sutou Kouhei <[email protected]>
---
 cpp/src/gandiva/encrypt_utils.cc           |  42 ++++++++++-
 cpp/src/gandiva/encrypt_utils.h            |   4 +-
 cpp/src/gandiva/encrypt_utils_test.cc      | 116 +++++++++--------------------
 cpp/src/gandiva/gdv_function_stubs.cc      |  35 +++++++--
 cpp/src/gandiva/gdv_function_stubs_test.cc |  80 ++++++++++++++++++++
 cpp/src/gandiva/tests/projector_test.cc    |  25 ++-----
 6 files changed, 195 insertions(+), 107 deletions(-)

diff --git a/cpp/src/gandiva/encrypt_utils.cc b/cpp/src/gandiva/encrypt_utils.cc
index 7a274af792..16c195d494 100644
--- a/cpp/src/gandiva/encrypt_utils.cc
+++ b/cpp/src/gandiva/encrypt_utils.cc
@@ -17,21 +17,41 @@
 
 #include "gandiva/encrypt_utils.h"
 
+#include <sstream>
 #include <stdexcept>
 
+namespace {
+const EVP_CIPHER* get_cipher_algo(int32_t key_length) {
+  switch (key_length) {
+    case 16:
+      return EVP_aes_128_ecb();
+    case 24:
+      return EVP_aes_192_ecb();
+    case 32:
+      return EVP_aes_256_ecb();
+    default: {
+      std::ostringstream oss;
+      oss << "unsupported key length: " << key_length;
+      throw std::runtime_error(oss.str());
+    }
+  }
+}
+}  // namespace
+
 namespace gandiva {
 GANDIVA_EXPORT
 int32_t aes_encrypt(const char* plaintext, int32_t plaintext_len, const char* 
key,
-                    unsigned char* cipher) {
+                    int32_t key_len, unsigned char* cipher) {
   int32_t cipher_len = 0;
   int32_t len = 0;
   EVP_CIPHER_CTX* en_ctx = EVP_CIPHER_CTX_new();
+  const EVP_CIPHER* cipher_algo = get_cipher_algo(key_len);
 
   if (!en_ctx) {
     throw std::runtime_error("could not create a new evp cipher ctx for 
encryption");
   }
 
-  if (!EVP_EncryptInit_ex(en_ctx, EVP_aes_128_ecb(), nullptr,
+  if (!EVP_EncryptInit_ex(en_ctx, cipher_algo, nullptr,
                           reinterpret_cast<const unsigned char*>(key), 
nullptr)) {
     throw std::runtime_error("could not initialize evp cipher ctx for 
encryption");
   }
@@ -56,16 +76,17 @@ int32_t aes_encrypt(const char* plaintext, int32_t 
plaintext_len, const char* ke
 
 GANDIVA_EXPORT
 int32_t aes_decrypt(const char* ciphertext, int32_t ciphertext_len, const 
char* key,
-                    unsigned char* plaintext) {
+                    int32_t key_len, unsigned char* plaintext) {
   int32_t plaintext_len = 0;
   int32_t len = 0;
   EVP_CIPHER_CTX* de_ctx = EVP_CIPHER_CTX_new();
+  const EVP_CIPHER* cipher_algo = get_cipher_algo(key_len);
 
   if (!de_ctx) {
     throw std::runtime_error("could not create a new evp cipher ctx for 
decryption");
   }
 
-  if (!EVP_DecryptInit_ex(de_ctx, EVP_aes_128_ecb(), nullptr,
+  if (!EVP_DecryptInit_ex(de_ctx, cipher_algo, nullptr,
                           reinterpret_cast<const unsigned char*>(key), 
nullptr)) {
     throw std::runtime_error("could not initialize evp cipher ctx for 
decryption");
   }
@@ -87,4 +108,17 @@ int32_t aes_decrypt(const char* ciphertext, int32_t 
ciphertext_len, const char*
   EVP_CIPHER_CTX_free(de_ctx);
   return plaintext_len;
 }
+
+const EVP_CIPHER* get_cipher_algo(int32_t key_length) {
+  switch (key_length) {
+    case 16:
+      return EVP_aes_128_ecb();
+    case 24:
+      return EVP_aes_192_ecb();
+    case 32:
+      return EVP_aes_256_ecb();
+    default:
+      throw std::runtime_error("unsupported key length");
+  }
+}
 }  // namespace gandiva
diff --git a/cpp/src/gandiva/encrypt_utils.h b/cpp/src/gandiva/encrypt_utils.h
index ea0e358082..06e178fd65 100644
--- a/cpp/src/gandiva/encrypt_utils.h
+++ b/cpp/src/gandiva/encrypt_utils.h
@@ -28,13 +28,13 @@ namespace gandiva {
  **/
 GANDIVA_EXPORT
 int32_t aes_encrypt(const char* plaintext, int32_t plaintext_len, const char* 
key,
-                    unsigned char* cipher);
+                    int32_t key_len, unsigned char* cipher);
 
 /**
  * Decrypt data using aes algorithm
  **/
 GANDIVA_EXPORT
 int32_t aes_decrypt(const char* ciphertext, int32_t ciphertext_len, const 
char* key,
-                    unsigned char* plaintext);
+                    int32_t key_len, unsigned char* plaintext);
 
 }  // namespace gandiva
diff --git a/cpp/src/gandiva/encrypt_utils_test.cc 
b/cpp/src/gandiva/encrypt_utils_test.cc
index 9c75515aed..5bc4c3957f 100644
--- a/cpp/src/gandiva/encrypt_utils_test.cc
+++ b/cpp/src/gandiva/encrypt_utils_test.cc
@@ -20,36 +20,40 @@
 #include <gtest/gtest.h>
 
 TEST(TestShaEncryptUtils, TestAesEncryptDecrypt) {
-  // 8 bytes key
-  auto* key = "1234abcd";
+  // 16 bytes key
+  auto* key = "12345678abcdefgh";
   auto* to_encrypt = "some test string";
 
+  auto key_len = static_cast<int32_t>(strlen(reinterpret_cast<const 
char*>(key)));
   auto to_encrypt_len =
       static_cast<int32_t>(strlen(reinterpret_cast<const char*>(to_encrypt)));
   unsigned char cipher_1[64];
 
-  int32_t cipher_1_len = gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, 
cipher_1);
+  int32_t cipher_1_len =
+      gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, key_len, cipher_1);
 
   unsigned char decrypted_1[64];
   int32_t decrypted_1_len = gandiva::aes_decrypt(reinterpret_cast<const 
char*>(cipher_1),
-                                                 cipher_1_len, key, 
decrypted_1);
+                                                 cipher_1_len, key, key_len, 
decrypted_1);
 
   EXPECT_EQ(std::string(reinterpret_cast<const char*>(to_encrypt), 
to_encrypt_len),
             std::string(reinterpret_cast<const char*>(decrypted_1), 
decrypted_1_len));
 
-  // 16 bytes key
-  key = "12345678abcdefgh";
+  // 24 bytes key
+  key = "12345678abcdefgh12345678";
   to_encrypt = "some\ntest\nstring";
 
+  key_len = static_cast<int32_t>(strlen(reinterpret_cast<const char*>(key)));
   to_encrypt_len =
       static_cast<int32_t>(strlen(reinterpret_cast<const char*>(to_encrypt)));
   unsigned char cipher_2[64];
 
-  int32_t cipher_2_len = gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, 
cipher_2);
+  int32_t cipher_2_len =
+      gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, key_len, cipher_2);
 
   unsigned char decrypted_2[64];
   int32_t decrypted_2_len = gandiva::aes_decrypt(reinterpret_cast<const 
char*>(cipher_2),
-                                                 cipher_2_len, key, 
decrypted_2);
+                                                 cipher_2_len, key, key_len, 
decrypted_2);
 
   EXPECT_EQ(std::string(reinterpret_cast<const char*>(to_encrypt), 
to_encrypt_len),
             std::string(reinterpret_cast<const char*>(decrypted_2), 
decrypted_2_len));
@@ -58,97 +62,51 @@ TEST(TestShaEncryptUtils, TestAesEncryptDecrypt) {
   key = "12345678abcdefgh12345678abcdefgh";
   to_encrypt = "New\ntest\nstring";
 
+  key_len = static_cast<int32_t>(strlen(reinterpret_cast<const char*>(key)));
   to_encrypt_len =
       static_cast<int32_t>(strlen(reinterpret_cast<const char*>(to_encrypt)));
   unsigned char cipher_3[64];
 
-  int32_t cipher_3_len = gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, 
cipher_3);
+  int32_t cipher_3_len =
+      gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, key_len, cipher_3);
 
   unsigned char decrypted_3[64];
   int32_t decrypted_3_len = gandiva::aes_decrypt(reinterpret_cast<const 
char*>(cipher_3),
-                                                 cipher_3_len, key, 
decrypted_3);
+                                                 cipher_3_len, key, key_len, 
decrypted_3);
 
   EXPECT_EQ(std::string(reinterpret_cast<const char*>(to_encrypt), 
to_encrypt_len),
             std::string(reinterpret_cast<const char*>(decrypted_3), 
decrypted_3_len));
 
-  // 64 bytes key
+  // check exception
+  char cipher[64] = "JBB7oJAQuqhDCx01fvBRi8PcljW1+nbnOSMk+R0Sz7E==";
+  int32_t cipher_len =
+      static_cast<int32_t>(strlen(reinterpret_cast<const char*>(cipher)));
+  unsigned char plain_text[64];
+
   key = "12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh";
   to_encrypt = "New\ntest\nstring";
 
+  key_len = static_cast<int32_t>(strlen(reinterpret_cast<const char*>(key)));
   to_encrypt_len =
       static_cast<int32_t>(strlen(reinterpret_cast<const char*>(to_encrypt)));
   unsigned char cipher_4[64];
+  ASSERT_THROW(
+      { gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, key_len, 
cipher_4); },
+      std::runtime_error);
 
-  int32_t cipher_4_len = gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, 
cipher_4);
-
-  unsigned char decrypted_4[64];
-  int32_t decrypted_4_len = gandiva::aes_decrypt(reinterpret_cast<const 
char*>(cipher_4),
-                                                 cipher_4_len, key, 
decrypted_4);
-
-  EXPECT_EQ(std::string(reinterpret_cast<const char*>(to_encrypt), 
to_encrypt_len),
-            std::string(reinterpret_cast<const char*>(decrypted_4), 
decrypted_4_len));
-
-  // 128 bytes key
-  key =
-      
"12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12"
-      "345678abcdefgh12345678abcdefgh12345678abcdefgh";
-  to_encrypt = "A much more longer string then the previous one, but without 
newline";
-
-  to_encrypt_len =
-      static_cast<int32_t>(strlen(reinterpret_cast<const char*>(to_encrypt)));
-  unsigned char cipher_5[128];
-
-  int32_t cipher_5_len = gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, 
cipher_5);
-
-  unsigned char decrypted_5[128];
-  int32_t decrypted_5_len = gandiva::aes_decrypt(reinterpret_cast<const 
char*>(cipher_5),
-                                                 cipher_5_len, key, 
decrypted_5);
-
-  EXPECT_EQ(std::string(reinterpret_cast<const char*>(to_encrypt), 
to_encrypt_len),
-            std::string(reinterpret_cast<const char*>(decrypted_5), 
decrypted_5_len));
-
-  // 192 bytes key
-  key =
-      
"12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12"
-      
"345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh1234"
-      "5678abcdefgh12345678abcdefgh";
-  to_encrypt =
-      "A much more longer string then the previous one, but with \nnewline, 
pretty cool, "
-      "right?";
-
-  to_encrypt_len =
-      static_cast<int32_t>(strlen(reinterpret_cast<const char*>(to_encrypt)));
-  unsigned char cipher_6[256];
-
-  int32_t cipher_6_len = gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, 
cipher_6);
-
-  unsigned char decrypted_6[256];
-  int32_t decrypted_6_len = gandiva::aes_decrypt(reinterpret_cast<const 
char*>(cipher_6),
-                                                 cipher_6_len, key, 
decrypted_6);
+  ASSERT_THROW({ gandiva::aes_decrypt(cipher, cipher_len, key, key_len, 
plain_text); },
+               std::runtime_error);
 
-  EXPECT_EQ(std::string(reinterpret_cast<const char*>(to_encrypt), 
to_encrypt_len),
-            std::string(reinterpret_cast<const char*>(decrypted_6), 
decrypted_6_len));
-
-  // 256 bytes key
-  key =
-      
"12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12"
-      
"345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh1234"
-      
"5678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh123456"
-      "78abcdefgh";
-  to_encrypt =
-      "A much more longer string then the previous one, but with \nnewline, 
pretty cool, "
-      "right?";
+  key = "12345678";
+  to_encrypt = "New\ntest\nstring";
 
+  key_len = static_cast<int32_t>(strlen(reinterpret_cast<const char*>(key)));
   to_encrypt_len =
       static_cast<int32_t>(strlen(reinterpret_cast<const char*>(to_encrypt)));
-  unsigned char cipher_7[256];
-
-  int32_t cipher_7_len = gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, 
cipher_7);
-
-  unsigned char decrypted_7[256];
-  int32_t decrypted_7_len = gandiva::aes_decrypt(reinterpret_cast<const 
char*>(cipher_7),
-                                                 cipher_7_len, key, 
decrypted_7);
-
-  EXPECT_EQ(std::string(reinterpret_cast<const char*>(to_encrypt), 
to_encrypt_len),
-            std::string(reinterpret_cast<const char*>(decrypted_7), 
decrypted_7_len));
+  unsigned char cipher_5[64];
+  ASSERT_THROW(
+      { gandiva::aes_encrypt(to_encrypt, to_encrypt_len, key, key_len, 
cipher_5); },
+      std::runtime_error);
+  ASSERT_THROW({ gandiva::aes_decrypt(cipher, cipher_len, key, key_len, 
plain_text); },
+               std::runtime_error);
 }
diff --git a/cpp/src/gandiva/gdv_function_stubs.cc 
b/cpp/src/gandiva/gdv_function_stubs.cc
index bcef954a47..7a47f7491a 100644
--- a/cpp/src/gandiva/gdv_function_stubs.cc
+++ b/cpp/src/gandiva/gdv_function_stubs.cc
@@ -20,6 +20,7 @@
 #include <utf8proc.h>
 
 #include <boost/crc.hpp>
+#include <sstream>
 #include <string>
 #include <vector>
 
@@ -306,8 +307,6 @@ CAST_NUMERIC_FROM_VARBINARY(double, arrow::DoubleType, 
FLOAT8)
 #undef GDV_FN_CAST_VARCHAR_INTEGER
 #undef GDV_FN_CAST_VARCHAR_REAL
 
-static constexpr int64_t kAesBlockSize = 16;  // bytes
-
 GANDIVA_EXPORT
 const char* gdv_fn_aes_encrypt(int64_t context, const char* data, int32_t 
data_len,
                                const char* key_data, int32_t key_data_len,
@@ -318,6 +317,17 @@ const char* gdv_fn_aes_encrypt(int64_t context, const 
char* data, int32_t data_l
     return "";
   }
 
+  int64_t kAesBlockSize = 0;
+  if (key_data_len == 16 || key_data_len == 24 || key_data_len == 32) {
+    kAesBlockSize = static_cast<int64_t>(key_data_len);
+  } else {
+    std::ostringstream oss;
+    oss << "invalid key length: " << key_data_len;
+    gdv_fn_context_set_error_msg(context, oss.str().c_str());
+    *out_len = 0;
+    return nullptr;
+  }
+
   *out_len =
       static_cast<int32_t>(arrow::bit_util::RoundUpToPowerOf2(data_len, 
kAesBlockSize));
   char* ret = reinterpret_cast<char*>(gdv_fn_context_arena_malloc(context, 
*out_len));
@@ -325,14 +335,16 @@ const char* gdv_fn_aes_encrypt(int64_t context, const 
char* data, int32_t data_l
     std::string err_msg =
         "Could not allocate memory for returning aes encrypt cypher text";
     gdv_fn_context_set_error_msg(context, err_msg.data());
+    *out_len = 0;
     return nullptr;
   }
 
   try {
-    *out_len = gandiva::aes_encrypt(data, data_len, key_data,
+    *out_len = gandiva::aes_encrypt(data, data_len, key_data, key_data_len,
                                     reinterpret_cast<unsigned char*>(ret));
   } catch (const std::runtime_error& e) {
     gdv_fn_context_set_error_msg(context, e.what());
+    *out_len = 0;
     return nullptr;
   }
 
@@ -349,6 +361,17 @@ const char* gdv_fn_aes_decrypt(int64_t context, const 
char* data, int32_t data_l
     return "";
   }
 
+  int64_t kAesBlockSize = 0;
+  if (key_data_len == 16 || key_data_len == 24 || key_data_len == 32) {
+    kAesBlockSize = static_cast<int64_t>(key_data_len);
+  } else {
+    std::ostringstream oss;
+    oss << "invalid key length: " << key_data_len;
+    gdv_fn_context_set_error_msg(context, oss.str().c_str());
+    *out_len = 0;
+    return nullptr;
+  }
+
   *out_len =
       static_cast<int32_t>(arrow::bit_util::RoundUpToPowerOf2(data_len, 
kAesBlockSize));
   char* ret = reinterpret_cast<char*>(gdv_fn_context_arena_malloc(context, 
*out_len));
@@ -356,17 +379,19 @@ const char* gdv_fn_aes_decrypt(int64_t context, const 
char* data, int32_t data_l
     std::string err_msg =
         "Could not allocate memory for returning aes encrypt cypher text";
     gdv_fn_context_set_error_msg(context, err_msg.data());
+    *out_len = 0;
     return nullptr;
   }
 
   try {
-    *out_len = gandiva::aes_decrypt(data, data_len, key_data,
+    *out_len = gandiva::aes_decrypt(data, data_len, key_data, key_data_len,
                                     reinterpret_cast<unsigned char*>(ret));
   } catch (const std::runtime_error& e) {
     gdv_fn_context_set_error_msg(context, e.what());
+    *out_len = 0;
     return nullptr;
   }
-
+  ret[*out_len] = '\0';
   return ret;
 }
 
diff --git a/cpp/src/gandiva/gdv_function_stubs_test.cc 
b/cpp/src/gandiva/gdv_function_stubs_test.cc
index 3e403828a4..cbe24b7423 100644
--- a/cpp/src/gandiva/gdv_function_stubs_test.cc
+++ b/cpp/src/gandiva/gdv_function_stubs_test.cc
@@ -1345,4 +1345,84 @@ TEST(TestGdvFnStubs, TestMask) {
   EXPECT_EQ(std::string(result, out_len), expected);
 }
 
+TEST(TestGdvFnStubs, TestAesEncryptDecrypt16) {
+  gandiva::ExecutionContext ctx;
+  std::string key16 = "12345678abcdefgh";
+  auto key16_len = static_cast<int32_t>(key16.length());
+  int32_t cipher_len = 0;
+  int32_t decrypted_len = 0;
+  std::string data = "test string";
+  auto data_len = static_cast<int32_t>(data.length());
+  int64_t ctx_ptr = reinterpret_cast<int64_t>(&ctx);
+
+  const char* cipher = gdv_fn_aes_encrypt(ctx_ptr, data.c_str(), data_len, 
key16.c_str(),
+                                          key16_len, &cipher_len);
+  const char* decrypted_value = gdv_fn_aes_decrypt(
+      ctx_ptr, cipher, cipher_len, key16.c_str(), key16_len, &decrypted_len);
+
+  EXPECT_EQ(data,
+            std::string(reinterpret_cast<const char*>(decrypted_value), 
decrypted_len));
+}
+
+TEST(TestGdvFnStubs, TestAesEncryptDecrypt24) {
+  gandiva::ExecutionContext ctx;
+  std::string key24 = "12345678abcdefgh12345678";
+  auto key24_len = static_cast<int32_t>(key24.length());
+  int32_t cipher_len = 0;
+  int32_t decrypted_len = 0;
+  std::string data = "test string";
+  auto data_len = static_cast<int32_t>(data.length());
+  int64_t ctx_ptr = reinterpret_cast<int64_t>(&ctx);
+
+  const char* cipher = gdv_fn_aes_encrypt(ctx_ptr, data.c_str(), data_len, 
key24.c_str(),
+                                          key24_len, &cipher_len);
+
+  const char* decrypted_value = gdv_fn_aes_decrypt(
+      ctx_ptr, cipher, cipher_len, key24.c_str(), key24_len, &decrypted_len);
+
+  EXPECT_EQ(data,
+            std::string(reinterpret_cast<const char*>(decrypted_value), 
decrypted_len));
+}
+
+TEST(TestGdvFnStubs, TestAesEncryptDecrypt32) {
+  gandiva::ExecutionContext ctx;
+  std::string key32 = "12345678abcdefgh12345678abcdefgh";
+  auto key32_len = static_cast<int32_t>(key32.length());
+  int32_t cipher_len = 0;
+  int32_t decrypted_len = 0;
+  std::string data = "test string";
+  auto data_len = static_cast<int32_t>(data.length());
+  int64_t ctx_ptr = reinterpret_cast<int64_t>(&ctx);
+
+  const char* cipher = gdv_fn_aes_encrypt(ctx_ptr, data.c_str(), data_len, 
key32.c_str(),
+                                          key32_len, &cipher_len);
+
+  const char* decrypted_value = gdv_fn_aes_decrypt(
+      ctx_ptr, cipher, cipher_len, key32.c_str(), key32_len, &decrypted_len);
+
+  EXPECT_EQ(data,
+            std::string(reinterpret_cast<const char*>(decrypted_value), 
decrypted_len));
+}
+
+TEST(TestGdvFnStubs, TestAesEncryptDecryptValidation) {
+  gandiva::ExecutionContext ctx;
+  std::string key33 = "12345678abcdefgh12345678abcdefghb";
+  auto key33_len = static_cast<int32_t>(key33.length());
+  int32_t decrypted_len = 0;
+  std::string data = "test string";
+  auto data_len = static_cast<int32_t>(data.length());
+  int64_t ctx_ptr = reinterpret_cast<int64_t>(&ctx);
+  std::string cipher = "12345678abcdefgh12345678abcdefghb";
+  auto cipher_len = static_cast<int32_t>(cipher.length());
+
+  gdv_fn_aes_encrypt(ctx_ptr, data.c_str(), data_len, key33.c_str(), key33_len,
+                     &cipher_len);
+  EXPECT_THAT(ctx.get_error(), ::testing::HasSubstr("invalid key length"));
+  ctx.Reset();
+
+  gdv_fn_aes_decrypt(ctx_ptr, cipher.c_str(), cipher_len, key33.c_str(), 
key33_len,
+                     &decrypted_len);
+  EXPECT_THAT(ctx.get_error(), ::testing::HasSubstr("invalid key length"));
+  ctx.Reset();
+}
 }  // namespace gandiva
diff --git a/cpp/src/gandiva/tests/projector_test.cc 
b/cpp/src/gandiva/tests/projector_test.cc
index 9bf568f841..3fbe80d4cc 100644
--- a/cpp/src/gandiva/tests/projector_test.cc
+++ b/cpp/src/gandiva/tests/projector_test.cc
@@ -2817,27 +2817,18 @@ TEST_F(TestProjector, TestAesEncryptDecrypt) {
   std::shared_ptr<Projector> projector_en;
   ASSERT_OK(Projector::Make(schema, {encrypt_expr}, TestConfiguration(), 
&projector_en));
 
-  int num_records = 4;
+  int num_records = 3;
 
+  const char* key_16_bytes = "12345678abcdefgh";
+  const char* key_24_bytes = "12345678abcdefgh12345678";
   const char* key_32_bytes = "12345678abcdefgh12345678abcdefgh";
-  const char* key_64_bytes =
-      "12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh";
-  const char* key_128_bytes =
-      
"12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12"
-      "345678abcdefgh12345678abcdefgh12345678abcdefgh";
-  const char* key_256_bytes =
-      
"12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12"
-      
"345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh1234"
-      
"5678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh12345678abcdefgh123456"
-      "78abcdefgh";
-
-  auto array_data = MakeArrowArrayUtf8({"abc", "some words", "to be 
encrypted", "hyah\n"},
-                                       {true, true, true, true});
+
+  auto array_data =
+      MakeArrowArrayUtf8({"abc", "some words", "to be encrypted"}, {true, 
true, true});
   auto array_key =
-      MakeArrowArrayUtf8({key_32_bytes, key_64_bytes, key_128_bytes, 
key_256_bytes},
-                         {true, true, true, true});
+      MakeArrowArrayUtf8({key_16_bytes, key_24_bytes, key_32_bytes}, {true, 
true, true});
 
-  auto array_holder_en = MakeArrowArrayUtf8({"", "", "", ""}, {true, true, 
true, true});
+  auto array_holder_en = MakeArrowArrayUtf8({"", "", ""}, {true, true, true});
 
   auto in_batch = arrow::RecordBatch::Make(schema, num_records, {array_data, 
array_key});
 

Reply via email to