aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/nvim/strings.c9
-rw-r--r--test/functional/ui/screen_basic_spec.lua40
-rw-r--r--test/unit/strings_spec.lua39
3 files changed, 83 insertions, 5 deletions
diff --git a/src/nvim/strings.c b/src/nvim/strings.c
index f19cf7a261..c5fd8741b8 100644
--- a/src/nvim/strings.c
+++ b/src/nvim/strings.c
@@ -428,16 +428,15 @@ int vim_strnicmp(const char *s1, const char *s2, size_t len)
/// strchr() version which handles multibyte strings
///
/// @param[in] string String to search in.
-/// @param[in] c Character to search for. Must be a valid character.
+/// @param[in] c Character to search for.
///
/// @return Pointer to the first byte of the found character in string or NULL
-/// if it was not found. NUL character is never found, use `strlen()`
-/// instead.
+/// if it was not found or character is invalid. NUL character is never
+/// found, use `strlen()` instead.
char_u *vim_strchr(const char_u *const string, const int c)
FUNC_ATTR_NONNULL_ALL FUNC_ATTR_PURE FUNC_ATTR_WARN_UNUSED_RESULT
{
- assert(c >= 0);
- if (c == 0) {
+ if (c <= 0) {
return NULL;
} else if (c < 0x80) {
return (char_u *)strchr((const char *)string, c);
diff --git a/test/functional/ui/screen_basic_spec.lua b/test/functional/ui/screen_basic_spec.lua
index 5d89416e4a..bfcdc7f652 100644
--- a/test/functional/ui/screen_basic_spec.lua
+++ b/test/functional/ui/screen_basic_spec.lua
@@ -565,6 +565,46 @@ describe('Screen', function()
]])
end)
end)
+
+ describe('press enter', function()
+ it('does not crash on <F1> at “Press ENTER”', function()
+ command('nnoremap <F1> :echo "TEST"<CR>')
+ feed(':ls<CR>')
+ screen:expect([[
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ :ls |
+ 1 %a "[No Name]" line 1 |
+ {7:Press ENTER or type command to continue}^ |
+ ]])
+ feed('<F1>')
+ screen:expect([[
+ ^ |
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ {0:~ }|
+ TEST |
+ ]])
+ end)
+ end)
end)
describe('nvim_ui_attach()', function()
diff --git a/test/unit/strings_spec.lua b/test/unit/strings_spec.lua
index 3bc3dc7130..e54c82b26a 100644
--- a/test/unit/strings_spec.lua
+++ b/test/unit/strings_spec.lua
@@ -99,3 +99,42 @@ describe('vim_strnsave_unquoted()', function()
eq('/Program\\nFiles/sh', vim_strnsave_unquoted('/Program"\\n"Files/sh'))
end)
end)
+
+describe('vim_strchr()', function()
+ local vim_strchr = function(s, c)
+ local str = to_cstr(s)
+ local res = strings.vim_strchr(str, c)
+ if res == nil then
+ return nil
+ else
+ return res - str
+ end
+ end
+ itp('handles NUL and <0 correctly', function()
+ eq(nil, vim_strchr('abc', 0))
+ eq(nil, vim_strchr('abc', -1))
+ end)
+ itp('works', function()
+ eq(0, vim_strchr('abc', ('a'):byte()))
+ eq(1, vim_strchr('abc', ('b'):byte()))
+ eq(2, vim_strchr('abc', ('c'):byte()))
+ eq(0, vim_strchr('a«b»c', ('a'):byte()))
+ eq(3, vim_strchr('a«b»c', ('b'):byte()))
+ eq(6, vim_strchr('a«b»c', ('c'):byte()))
+
+ eq(nil, vim_strchr('«»', ('«'):byte()))
+ -- 0xAB == 171 == '«'
+ eq(nil, vim_strchr('\171', 0xAB))
+ eq(0, vim_strchr('«»', 0xAB))
+ eq(3, vim_strchr('„«»“', 0xAB))
+
+ eq(7, vim_strchr('„«»“', 0x201C))
+ eq(nil, vim_strchr('„«»“', 0x201D))
+ eq(0, vim_strchr('„«»“', 0x201E))
+
+ eq(0, vim_strchr('\244\143\188\128', 0x10FF00))
+ eq(2, vim_strchr('«\244\143\188\128»', 0x10FF00))
+ -- |0xDBFF |0xDF00 - surrogate pair for 0x10FF00
+ eq(nil, vim_strchr('«\237\175\191\237\188\128»', 0x10FF00))
+ end)
+end)