Author: rinrab
Date: Sun Jan  4 12:24:35 2026
New Revision: 1931093

Log:
bcrypt: Eliminate heap allocations when computing checksum contextless of a
single data block. Use forbidden alloca() function to create the buffer and
pass it to the initialization function. According to the documentation
[1]#pbHashObject, we should not call BCryptDestroyHash() if non-null buffer
is supplied.

* subversion/libsvn_subr/checksum_bcrypt.c
  (bcrypt_checksum): Manually initialize the context and the algorithm.
   Remove BCryptDestroyHash() call.
  
[1] 
https://learn.microsoft.com/en-us/windows/win32/api/bcrypt/nf-bcrypt-bcryptcreatehash

Modified:
   subversion/trunk/subversion/libsvn_subr/checksum_bcrypt.c

Modified: subversion/trunk/subversion/libsvn_subr/checksum_bcrypt.c
==============================================================================
--- subversion/trunk/subversion/libsvn_subr/checksum_bcrypt.c   Sun Jan  4 
12:10:02 2026        (r1931092)
+++ subversion/trunk/subversion/libsvn_subr/checksum_bcrypt.c   Sun Jan  4 
12:24:35 2026        (r1931093)
@@ -177,22 +177,29 @@ bcrypt_checksum(algorithm_state_t *algor
                 const void *data,
                 apr_size_t len)
 {
-  bcrypt_ctx_t bcrypt_ctx;
-  svn_error_t *err = SVN_NO_ERROR;
+  bcrypt_ctx_t bcrypt_ctx = { 0 };
+  void *object_buf;
 
-  SVN_ERR(bcrypt_ctx_init(algorithm, &bcrypt_ctx));
+  SVN_ERR(svn_atomic__init_once(&algorithm->initialized, algorithm_init,
+                                algorithm, NULL));
 
-  err = bcrypt_ctx_update(algorithm, &bcrypt_ctx, data, len);
-  if (err)
-    {
-      bcrypt_ctx_cleanup(&bcrypt_ctx);
-      return err;
-    }
+  SVN_ERR_ASSERT(algorithm->object_length < 4096);
+  object_buf = alloca(algorithm->object_length);
 
-  SVN_ERR(bcrypt_ctx_final(algorithm, &bcrypt_ctx, digest));
+  SVN_ERR(handle_error(BCryptCreateHash(algorithm->alg_handle,
+                                        &bcrypt_ctx.handle,
+                                        object_buf, algorithm->object_length,
+                                        /* pbSecret */ NULL,
+                                        /* cbSecret */ 0,
+                                        /* dwFlags */ 0)));
 
-  bcrypt_ctx_cleanup(&bcrypt_ctx);
-  return err;
+  SVN_ERR(bcrypt_ctx_update(algorithm, &bcrypt_ctx,
+                            data, len));
+
+  SVN_ERR(bcrypt_ctx_final(algorithm, &bcrypt_ctx,
+                           digest));
+
+  return SVN_NO_ERROR;
 }
 
 

Reply via email to