commit 46fb52fe518d09f9855024bc88fda71d6c91d827
parent 19ba5899460ffdbf159ad4323ae5f3af6ce2eb53
Author: zeertzjq <zeertzjq@outlook.com>
Date: Sun, 21 Sep 2025 07:19:17 +0800
Merge pull request #35849 from zeertzjq/vim-9.1.1774
vim-patch:9.1.{1774,1778}: cannot calculate sha256 of a Blob
Diffstat:
5 files changed, 47 insertions(+), 24 deletions(-)
diff --git a/runtime/doc/vimfn.txt b/runtime/doc/vimfn.txt
@@ -9468,12 +9468,13 @@ setwinvar({nr}, {varname}, {val}) *setwinvar()*
Return: ~
(`any`)
-sha256({string}) *sha256()*
+sha256({expr}) *sha256()*
Returns a String with 64 hex characters, which is the SHA256
- checksum of {string}.
+ checksum of {expr}.
+ {expr} is a String or a Blob.
Parameters: ~
- • {string} (`string`)
+ • {expr} (`string`)
Return: ~
(`string`)
diff --git a/runtime/lua/vim/_meta/vimfn.lua b/runtime/lua/vim/_meta/vimfn.lua
@@ -8631,11 +8631,12 @@ function vim.fn.settagstack(nr, dict, action) end
function vim.fn.setwinvar(nr, varname, val) end
--- Returns a String with 64 hex characters, which is the SHA256
---- checksum of {string}.
+--- checksum of {expr}.
+--- {expr} is a String or a Blob.
---
---- @param string string
+--- @param expr string
--- @return string
-function vim.fn.sha256(string) end
+function vim.fn.sha256(expr) end
--- Escape {string} for use as a shell command argument.
---
diff --git a/src/nvim/eval.lua b/src/nvim/eval.lua
@@ -10419,13 +10419,14 @@ M.funcs = {
base = 1,
desc = [=[
Returns a String with 64 hex characters, which is the SHA256
- checksum of {string}.
+ checksum of {expr}.
+ {expr} is a String or a Blob.
]=],
name = 'sha256',
- params = { { 'string', 'string' } },
+ params = { { 'expr', 'string' } },
returns = 'string',
- signature = 'sha256({string})',
+ signature = 'sha256({expr})',
},
shellescape = {
args = { 1, 2 },
diff --git a/src/nvim/eval/funcs.c b/src/nvim/eval/funcs.c
@@ -7189,15 +7189,22 @@ static void f_settagstack(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
}
}
-/// f_sha256 - sha256({string}) function
+/// "sha256({expr})" function
static void f_sha256(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
{
- const char *p = tv_get_string(&argvars[0]);
- const char *hash = sha256_bytes((const uint8_t *)p, strlen(p), NULL, 0);
-
- // make a copy of the hash (sha256_bytes returns a static buffer)
- rettv->vval.v_string = xstrdup(hash);
rettv->v_type = VAR_STRING;
+ rettv->vval.v_string = NULL;
+
+ if (argvars[0].v_type == VAR_BLOB) {
+ blob_T *blob = argvars[0].vval.v_blob;
+ const uint8_t *p = blob != NULL ? (uint8_t *)blob->bv_ga.ga_data : (uint8_t *)"";
+ int len = blob != NULL ? blob->bv_ga.ga_len : 0;
+ rettv->vval.v_string = xstrdup(sha256_bytes(p, (size_t)len, NULL, 0));
+ } else {
+ const char *p = tv_get_string(&argvars[0]);
+ const char *hash = sha256_bytes((const uint8_t *)p, strlen(p), NULL, 0);
+ rettv->vval.v_string = xstrdup(hash);
+ }
}
/// "shellescape({string})" function
diff --git a/test/old/testdir/test_sha256.vim b/test/old/testdir/test_sha256.vim
@@ -5,18 +5,31 @@ source check.vim
CheckFunction sha256
function Test_sha256()
- " test for empty string:
+ " tests for string:
+ " empty string
call assert_equal('e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855', sha256(""))
-
- "'test for 1 char:
+ " null string
+ call assert_equal('e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855', sha256(v:_null_string))
+ " string with 1 char
call assert_equal('ca978112ca1bbdcafac231b39a23dc4da786eff8147c4e72b9807785afee48bb', sha256("a"))
- "
- "test for 3 chars:
+ " string with 3 chars
call assert_equal('ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad', "abc"->sha256())
-
- " test for contains meta char:
+ " string containing meta char
call assert_equal('807eff6267f3f926a21d234f7b0cf867a86f47e07a532f15e8cc39ed110ca776', sha256("foo\nbar"))
-
- " test for contains non-ascii char:
+ " string containing non-ascii char
call assert_equal('5f78c33274e43fa9de5659265c1d917e25c03722dcb0b8d27db8d5feaa813953', sha256("\xde\xad\xbe\xef"))
+
+ " tests for blob:
+ " empty blob
+ call assert_equal('e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855', sha256(0z))
+ " null blob
+ call assert_equal('e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855', sha256(v:_null_blob))
+ " blob with single byte
+ call assert_equal('ca978112ca1bbdcafac231b39a23dc4da786eff8147c4e72b9807785afee48bb', sha256(0z61))
+ " blob with "abc"
+ call assert_equal('ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad', sha256(0z616263))
+ " blob with non-ascii bytes
+ call assert_equal('5f78c33274e43fa9de5659265c1d917e25c03722dcb0b8d27db8d5feaa813953', sha256(0zdeadbeef))
endfunction
+
+" vim: shiftwidth=2 sts=2 expandtab