aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSean Dewar <seandewar@users.noreply.github.com>2021-05-22 20:21:44 +0100
committerSean Dewar <seandewar@users.noreply.github.com>2021-09-11 15:33:20 +0100
commitb6d9e92805b4cf37680be61c1c22ddf7a061d649 (patch)
tree8bcc94d8bc359470a6d08f82fa07171745d13cb0
parent6617629ad6eceeb77d49633780a7213eeb17a2c9 (diff)
downloadrneovim-b6d9e92805b4cf37680be61c1c22ddf7a061d649.tar.gz
rneovim-b6d9e92805b4cf37680be61c1c22ddf7a061d649.tar.bz2
rneovim-b6d9e92805b4cf37680be61c1c22ddf7a061d649.zip
vim-patch:8.1.2036: the str2nr() tests fail
Problem: The str2nr() tests fail. Solution: Add missing part of patch. https://github.com/vim/vim/commit/1ac90b4fa63414d56750559506a3e076df6923b0 Add extra tests for quoted numbers in vim_str2nr_spec.lua, as the included ones in this patch are somewhat lacking.
-rw-r--r--src/nvim/charset.c16
-rw-r--r--test/unit/charset/vim_str2nr_spec.lua20
2 files changed, 34 insertions, 2 deletions
diff --git a/src/nvim/charset.c b/src/nvim/charset.c
index 9f11e85b01..7b08488925 100644
--- a/src/nvim/charset.c
+++ b/src/nvim/charset.c
@@ -1396,6 +1396,7 @@ bool vim_isblankline(char_u *lbuf)
/// If "what" contains STR2NR_OCT recognize octal numbers.
/// If "what" contains STR2NR_HEX recognize hex numbers.
/// If "what" contains STR2NR_FORCE always assume bin/oct/hex.
+/// If "what" contains STR2NR_QUOTE ignore embedded single quotes
/// If maxlen > 0, check at a maximum maxlen chars.
/// If strict is true, check the number strictly. return *len = 0 if fail.
///
@@ -1434,7 +1435,7 @@ void vim_str2nr(const char_u *const start, int *const prep, int *const len,
if (what & STR2NR_FORCE) {
// When forcing main consideration is skipping the prefix. Octal and decimal
// numbers have no prefixes to skip. pre is not set.
- switch ((unsigned)what & (~(unsigned)STR2NR_FORCE)) {
+ switch (what & ~(STR2NR_FORCE | STR2NR_QUOTE)) {
case STR2NR_HEX: {
if (!STRING_ENDED(ptr + 2)
&& ptr[0] == '0'
@@ -1504,7 +1505,18 @@ void vim_str2nr(const char_u *const start, int *const prep, int *const len,
abort(); // Should’ve used goto earlier.
#define PARSE_NUMBER(base, cond, conv) \
do { \
- while (!STRING_ENDED(ptr) && (cond)) { \
+ const char *const after_prefix = ptr; \
+ while (!STRING_ENDED(ptr)) { \
+ if ((what & STR2NR_QUOTE) && ptr > after_prefix && *ptr == '\'') { \
+ ptr++; \
+ if (!STRING_ENDED(ptr) && (cond)) { \
+ continue; \
+ } \
+ ptr--; \
+ } \
+ if (!(cond)) { \
+ break; \
+ } \
const uvarnumber_T digit = (uvarnumber_T)(conv); \
/* avoid ubsan error for overflow */ \
if (un < UVARNUMBER_MAX / base \
diff --git a/test/unit/charset/vim_str2nr_spec.lua b/test/unit/charset/vim_str2nr_spec.lua
index 2728a16e20..ebcceca7ae 100644
--- a/test/unit/charset/vim_str2nr_spec.lua
+++ b/test/unit/charset/vim_str2nr_spec.lua
@@ -354,4 +354,24 @@ describe('vim_str2nr()', function()
end
end
end)
+ -- Test_str2nr() in test_functions.vim already tests normal usage
+ itp('works with weirdly quoted numbers', function()
+ local flags = lib.STR2NR_DEC + lib.STR2NR_QUOTE
+ test_vim_str2nr("'027", flags, {len = 0}, 0)
+ test_vim_str2nr("'027", flags, {len = 0}, 0, false)
+ test_vim_str2nr("1'2'3'4", flags, {len = 7, num = 1234, unum = 1234, pre = 0}, 0)
+
+ -- counter-intuitive, but like Vim, strict=true should partially accept
+ -- these: (' and - are not alpha-numeric)
+ test_vim_str2nr("7''331", flags, {len = 1, num = 7, unum = 7, pre = 0}, 0)
+ test_vim_str2nr("123'x4", flags, {len = 3, num = 123, unum = 123, pre = 0}, 0)
+ test_vim_str2nr("1337'", flags, {len = 4, num = 1337, unum = 1337, pre = 0}, 0)
+ test_vim_str2nr("-'", flags, {len = 1, num = 0, unum = 0, pre = 0}, 0)
+
+ flags = lib.STR2NR_HEX + lib.STR2NR_QUOTE
+ local hex = ('x'):byte()
+ test_vim_str2nr("0x'abcd", flags, {len = 0}, 0)
+ test_vim_str2nr("0x'abcd", flags, {len = 1, num = 0, unum = 0, pre = 0}, 0, false)
+ test_vim_str2nr("0xab''cd", flags, {len = 4, num = 171, unum = 171, pre = hex}, 0)
+ end)
end)