diff options
-rw-r--r-- | runtime/autoload/gzip.vim | 7 | ||||
-rw-r--r-- | runtime/autoload/zip.vim | 4 | ||||
-rw-r--r-- | runtime/ftplugin/eruby.vim | 12 | ||||
-rw-r--r-- | runtime/ftplugin/perl.vim | 3 | ||||
-rw-r--r-- | runtime/ftplugin/ruby.vim | 8 | ||||
-rw-r--r-- | runtime/ftplugin/zig.vim | 4 | ||||
-rw-r--r-- | runtime/indent/ruby.vim | 4 | ||||
-rw-r--r-- | runtime/lua/vim/lsp/handlers.lua | 2 | ||||
-rw-r--r-- | runtime/makemenu.vim | 1 | ||||
-rw-r--r-- | runtime/synmenu.vim | 1 | ||||
-rw-r--r-- | runtime/syntax/ruby.vim | 26 | ||||
-rw-r--r-- | runtime/syntax/zserio.vim | 112 | ||||
-rw-r--r-- | src/nvim/eval/userfunc.c | 2 | ||||
-rw-r--r-- | src/nvim/lua/treesitter.c | 18 | ||||
-rw-r--r-- | src/nvim/mbyte.c | 19 | ||||
-rw-r--r-- | src/nvim/normal.c | 8 | ||||
-rw-r--r-- | src/nvim/plines.c | 4 | ||||
-rw-r--r-- | src/nvim/spellfile.c | 8 | ||||
-rw-r--r-- | test/functional/shada/marks_spec.lua | 7 | ||||
-rw-r--r-- | test/functional/treesitter/parser_spec.lua | 8 | ||||
-rw-r--r-- | test/functional/ui/decorations_spec.lua | 13 |
21 files changed, 204 insertions, 67 deletions
diff --git a/runtime/autoload/gzip.vim b/runtime/autoload/gzip.vim index 95dd906794..ac9e37bf85 100644 --- a/runtime/autoload/gzip.vim +++ b/runtime/autoload/gzip.vim @@ -10,12 +10,17 @@ fun s:check(cmd) let name = substitute(a:cmd, '\(\S*\).*', '\1', '') if !exists("s:have_" . name) + " safety check, don't execute anything from the current directory + let f = fnamemodify(exepath(name), ":p:h") !=# getcwd() + if !f + echoerr "Warning: NOT executing " .. name .. " from current directory!" + endif let e = executable(name) if e < 0 let r = system(name . " --version") let e = (r !~ "not found" && r != "") endif - exe "let s:have_" . name . "=" . e + exe "let s:have_" . name . "=" . (e && f) endif exe "return s:have_" . name endfun diff --git a/runtime/autoload/zip.vim b/runtime/autoload/zip.vim index 8dda30c418..0331a542ac 100644 --- a/runtime/autoload/zip.vim +++ b/runtime/autoload/zip.vim @@ -57,6 +57,10 @@ if !exists("g:zip_extractcmd") let g:zip_extractcmd= g:zip_unzipcmd endif +if fnamemodify(exepath(g:zip_unzipcmd), ":p:h") ==# getcwd() + echoerr "Warning: NOT executing " .. g:zip_unzipcmd .. " from current directory!" + finish +endif " ---------------- " Functions: {{{1 " ---------------- diff --git a/runtime/ftplugin/eruby.vim b/runtime/ftplugin/eruby.vim index e67b00b278..893fa58d32 100644 --- a/runtime/ftplugin/eruby.vim +++ b/runtime/ftplugin/eruby.vim @@ -3,7 +3,7 @@ " Maintainer: Tim Pope <vimNOSPAM@tpope.org> " URL: https://github.com/vim-ruby/vim-ruby " Release Coordinator: Doug Kearns <dougkearns@gmail.com> -" Last Change: 2020 Jun 28 +" Last Change: 2022 May 15 " Only do this when not done yet for this buffer if exists("b:did_ftplugin") @@ -86,8 +86,12 @@ runtime! ftplugin/ruby.vim ftplugin/ruby_*.vim ftplugin/ruby/*.vim let b:did_ftplugin = 1 " Combine the new set of values with those previously included. -if exists("b:undo_ftplugin") - let s:undo_ftplugin = b:undo_ftplugin . " | " . s:undo_ftplugin +if !exists('b:undo_ftplugin') + " No-op + let b:undo_ftplugin = 'exe' +endif +if !empty(s:undo_ftplugin) + let b:undo_ftplugin .= '|' . s:undo_ftplugin endif if exists ("b:browsefilter") let s:browsefilter = substitute(b:browsefilter,'\cAll Files (\*\.\*)\t\*\.\*\n','','') . s:browsefilter @@ -119,7 +123,7 @@ endif setlocal commentstring=<%#%s%> let b:undo_ftplugin = "setl cms< " . - \ " | unlet! b:browsefilter b:match_words | " . s:undo_ftplugin + \ " | unlet! b:browsefilter b:match_words | " . b:undo_ftplugin let &cpo = s:save_cpo unlet s:save_cpo diff --git a/runtime/ftplugin/perl.vim b/runtime/ftplugin/perl.vim index d0bdbc0cfb..edc7b960f1 100644 --- a/runtime/ftplugin/perl.vim +++ b/runtime/ftplugin/perl.vim @@ -54,7 +54,8 @@ endif " Set this once, globally. if !exists("perlpath") - if executable("perl") + " safety check: don't execute perl from current directory + if executable("perl") && fnamemodify(exepath("perl"), ":p:h") != getcwd() try if &shellxquote != '"' let perlpath = system('perl -e "print join(q/,/,@INC)"') diff --git a/runtime/ftplugin/ruby.vim b/runtime/ftplugin/ruby.vim index 8c1f47731c..1262099d88 100644 --- a/runtime/ftplugin/ruby.vim +++ b/runtime/ftplugin/ruby.vim @@ -3,7 +3,7 @@ " Maintainer: Tim Pope <vimNOSPAM@tpope.org> " URL: https://github.com/vim-ruby/vim-ruby " Release Coordinator: Doug Kearns <dougkearns@gmail.com> -" Last Change: 2022 Mar 21 +" Last Change: 2023 Sep 1st if (exists("b:did_ftplugin")) finish @@ -77,7 +77,11 @@ function! s:query_path(root) abort let cwd = fnameescape(getcwd()) try exe cd fnameescape(a:root) - let path = split(system(path_check),',') + if fnamemodify(exepath('ruby'), ':p:h') ==# getcwd() + let path = [] + else + let path = split(system(path_check),',') + endif exe cd cwd return path finally diff --git a/runtime/ftplugin/zig.vim b/runtime/ftplugin/zig.vim index 5f453fc8d1..cd18bfe2bd 100644 --- a/runtime/ftplugin/zig.vim +++ b/runtime/ftplugin/zig.vim @@ -39,7 +39,9 @@ endif let &l:define='\v(<fn>|<const>|<var>|^\s*\#\s*define)' -if !exists('g:zig_std_dir') && exists('*json_decode') && executable('zig') +" Safety check: don't execute zip from current directory +if !exists('g:zig_std_dir') && exists('*json_decode') && + \ executable('zig') && fnamemodify(exepath("zig"), ":p:h") != getcwd() silent let s:env = system('zig env') if v:shell_error == 0 let g:zig_std_dir = json_decode(s:env)['std_dir'] diff --git a/runtime/indent/ruby.vim b/runtime/indent/ruby.vim index 6ce8529fd1..ea5a2a7494 100644 --- a/runtime/indent/ruby.vim +++ b/runtime/indent/ruby.vim @@ -4,7 +4,7 @@ " Previous Maintainer: Nikolai Weibull <now at bitwi.se> " URL: https://github.com/vim-ruby/vim-ruby " Release Coordinator: Doug Kearns <dougkearns@gmail.com> -" Last Change: 2022 Mar 22 +" Last Change: 2022 Jun 30 " 0. Initialization {{{1 " ================= @@ -93,7 +93,7 @@ let s:ruby_indent_keywords = \ '\<\%(if\|for\|while\|until\|case\|unless\|begin\):\@!\>' " Def without an end clause: def method_call(...) = <expression> -let s:ruby_endless_def = '\<def\s\+\k\+[!?]\=\%((.*)\|\s\)\s*=' +let s:ruby_endless_def = '\<def\s\+\%(\k\+\.\)\=\k\+[!?]\=\%((.*)\|\s\)\s*=' " Regex used for words that, at the start of a line, remove a level of indent. let s:ruby_deindent_keywords = diff --git a/runtime/lua/vim/lsp/handlers.lua b/runtime/lua/vim/lsp/handlers.lua index 6fe4b7f939..a6b70ac911 100644 --- a/runtime/lua/vim/lsp/handlers.lua +++ b/runtime/lua/vim/lsp/handlers.lua @@ -112,7 +112,7 @@ M[ms.client_registerCapability] = function(_, result, ctx) local client = vim.lsp.get_client_by_id(client_id) client.dynamic_capabilities:register(result.registrations) - for bufnr, _ in ipairs(client.attached_buffers) do + for bufnr, _ in pairs(client.attached_buffers) do vim.lsp._set_defaults(client, bufnr) end diff --git a/runtime/makemenu.vim b/runtime/makemenu.vim index 8da7c0b68c..bf9f43cf16 100644 --- a/runtime/makemenu.vim +++ b/runtime/makemenu.vim @@ -676,6 +676,7 @@ SynMenu WXYZ.XFree86\ Config:xf86conf SynMenu WXYZ.YAML:yaml SynMenu WXYZ.Yacc:yacc SynMenu WXYZ.Zimbu:zimbu +SynMenu WXYZ.Zserio:zserio call append(s:lnum, "") diff --git a/runtime/synmenu.vim b/runtime/synmenu.vim index 8a8c6a2b90..b75a0e9497 100644 --- a/runtime/synmenu.vim +++ b/runtime/synmenu.vim @@ -650,6 +650,7 @@ an 50.170.390 &Syntax.WXYZ.XFree86\ Config :cal SetSyn("xf86conf")<CR> an 50.170.410 &Syntax.WXYZ.YAML :cal SetSyn("yaml")<CR> an 50.170.420 &Syntax.WXYZ.Yacc :cal SetSyn("yacc")<CR> an 50.170.440 &Syntax.WXYZ.Zimbu :cal SetSyn("zimbu")<CR> +an 50.170.440 &Syntax.WXYZ.Zserio:cal SetSyn("zserio")<CR> " The End Of The Syntax Menu diff --git a/runtime/syntax/ruby.vim b/runtime/syntax/ruby.vim index c951fcfe1d..e19d61a051 100644 --- a/runtime/syntax/ruby.vim +++ b/runtime/syntax/ruby.vim @@ -3,7 +3,7 @@ " Maintainer: Doug Kearns <dougkearns@gmail.com> " URL: https://github.com/vim-ruby/vim-ruby " Release Coordinator: Doug Kearns <dougkearns@gmail.com> -" Last Change: 2021 Nov 03 +" Last Change: 2023 Mar 16 " ---------------------------------------------------------------------------- " " Previous Maintainer: Mirko Nasato @@ -145,9 +145,9 @@ syn cluster rubyStringSpecial contains=rubyInterpolation,rubyStringEscape syn cluster rubyStringNotTop contains=@rubyStringSpecial,@rubyNestedBrackets,@rubySingleCharEscape " Regular Expression Metacharacters {{{1 -syn region rubyRegexpComment matchgroup=rubyRegexpSpecial start="(?#" skip="\\\\\|\\)" end=")" contained -syn region rubyRegexpParens matchgroup=rubyRegexpSpecial start="(\(?:\|?<\=[=!]\|?>\|?<[a-z_]\w*>\|?[imx]*-[imx]*:\=\|\%(?#\)\@!\)" skip="\\\\\|\\)" end=")" contained transparent contains=@rubyRegexpSpecial -syn region rubyRegexpBrackets matchgroup=rubyRegexpCharClass start="\[\^\=" skip="\\\\\|\\\]" end="\]" contained transparent contains=rubyRegexpBrackets,rubyStringEscape,rubyRegexpEscape,rubyRegexpCharClass,rubyRegexpIntersection oneline +syn region rubyRegexpComment matchgroup=rubyRegexpSpecial start="(?#" skip="\\\\\|\\)" end=")" contained +syn region rubyRegexpParens matchgroup=rubyRegexpSpecial start="(\%(?:\|?<\=[=!]\|?>\|?<[a-z_]\w*>\|?[imx]*-[imx]*:\=\|\%(?#\)\@!\)" skip="\\\\\|\\)" end=")" contained transparent contains=@rubyRegexpSpecial +syn region rubyRegexpBrackets matchgroup=rubyRegexpCharClass start="\[\^\=" skip="\\\\\|\\\]" end="\]" contained transparent contains=rubyRegexpBrackets,rubyStringEscape,rubyRegexpEscape,rubyRegexpCharClass,rubyRegexpIntersection oneline syn match rubyRegexpCharClass "\\[DdHhRSsWw]" contained display syn match rubyRegexpCharClass "\[:\^\=\%(alnum\|alpha\|ascii\|blank\|cntrl\|digit\|graph\|lower\|print\|punct\|space\|upper\|word\|xdigit\):\]" contained syn match rubyRegexpCharClass "\\[pP]{^\=.\{-}}" contained display @@ -346,7 +346,7 @@ syn cluster rubyDeclaration contains=rubyAliasDeclaration,rubyAliasDeclaration2, syn match rubyControl "\%#=1\<\%(break\|in\|next\|redo\|retry\|return\)\>" syn match rubyKeyword "\%#=1\<\%(super\|yield\)\>" syn match rubyBoolean "\%#=1\<\%(true\|false\)\>[?!]\@!" -syn match rubyPseudoVariable "\%#=1\<\(self\|nil\)\>[?!]\@!" +syn match rubyPseudoVariable "\%#=1\<\%(self\|nil\)\>[?!]\@!" syn match rubyPseudoVariable "\%#=1\<__\%(ENCODING\|dir\|FILE\|LINE\|callee\|method\)__\>" syn match rubyBeginEnd "\%#=1\<\%(BEGIN\|END\)\>" @@ -399,11 +399,6 @@ if !exists("b:ruby_no_expensive") && !exists("ruby_no_expensive") SynFold 'for' syn region rubyRepeatExpression start="\<for\>" start="\%(\%(^\|\.\.\.\=\|[{:,;([<>~\*/%&^|+=-]\|\%(\<\%(\h\|[^\x00-\x7F]\)\%(\w\|[^\x00-\x7F]\)*\)\@<![!?]\)\s*\)\@<=\<\%(until\|while\)\>" matchgroup=rubyRepeat skip="\<end:" end="\<end\>" contains=ALLBUT,@rubyNotTop nextgroup=rubyOptionalDoLine - if !exists("ruby_minlines") - let ruby_minlines = 500 - endif - exe "syn sync minlines=" . ruby_minlines - else syn match rubyControl "\<def\>" nextgroup=rubyMethodDeclaration skipwhite skipnl syn match rubyControl "\<class\>" nextgroup=rubyClassDeclaration skipwhite skipnl @@ -412,13 +407,18 @@ else syn match rubyKeyword "\<\%(alias\|undef\)\>" endif +if !exists("ruby_minlines") + let ruby_minlines = 500 +endif +exe "syn sync minlines=" . ruby_minlines + " Special Methods {{{1 if !exists("ruby_no_special_methods") syn match rubyAccess "\<\%(public\|protected\|private\)\>" " use re=2 syn match rubyAccess "\%#=1\<\%(public\|private\)_class_method\>" syn match rubyAccess "\%#=1\<\%(public\|private\)_constant\>" syn match rubyAccess "\%#=1\<module_function\>" - syn match rubyAttribute "\%#=1\%(\%(^\|;\)\s*\)\@<=attr\>\(\s*[.=]\)\@!" " attr is a common variable name + syn match rubyAttribute "\%#=1\%(\%(^\|;\)\s*\)\@<=attr\>\%(\s*[.=]\)\@!" " attr is a common variable name syn match rubyAttribute "\%#=1\<attr_\%(accessor\|reader\|writer\)\>" syn match rubyControl "\%#=1\<\%(abort\|at_exit\|exit\|fork\|loop\|trap\)\>" syn match rubyEval "\%#=1\<eval\>" @@ -435,8 +435,8 @@ syn match rubySharpBang "\%^#!.*" display syn keyword rubyTodo FIXME NOTE TODO OPTIMIZE HACK REVIEW XXX todo contained syn match rubyEncoding "[[:alnum:]-_]\+" contained display syn match rubyMagicComment "\c\%<3l#\s*\zs\%(coding\|encoding\):" contained nextgroup=rubyEncoding skipwhite -syn match rubyMagicComment "\c\%<10l#\s*\zs\%(frozen_string_literal\|warn_indent\|warn_past_scope\):" contained nextgroup=rubyBoolean skipwhite -syn match rubyMagicComment "\c\%<10l#\s*\zs\%(shareable_constant_value\):" contained nextgroup=rubyEncoding skipwhite +syn match rubyMagicComment "\c\%<10l#\s*\zs\%(frozen[-_]string[-_]literal\|warn[-_]indent\|warn[-_]past[-_]scope\):" contained nextgroup=rubyBoolean skipwhite +syn match rubyMagicComment "\c\%<10l#\s*\zs\%(shareable[-_]constant[-_]value\):" contained nextgroup=rubyEncoding skipwhite syn match rubyComment "#.*" contains=@rubyCommentSpecial,rubySpaceError,@Spell syn cluster rubyCommentSpecial contains=rubySharpBang,rubyTodo,rubyMagicComment diff --git a/runtime/syntax/zserio.vim b/runtime/syntax/zserio.vim new file mode 100644 index 0000000000..5459915c01 --- /dev/null +++ b/runtime/syntax/zserio.vim @@ -0,0 +1,112 @@ +" Vim syntax file +" Language: Zserio +" Maintainer: Dominique Pellé <dominique.pelle@gmail.com> +" Last Change: 2023 Jun 18 +" +" Zserio is a serialization schema language for modeling binary +" data types, bitstreams or file formats. Based on the zserio +" language it is possible to automatically generate encoders and +" decoders for a given schema in various target languages +" (e.g. Java, C++, Python). +" +" Zserio is an evolution of the DataScript language. +" +" For more information, see: +" - http://zserio.org/ +" - https://github.com/ndsev/zserio + +" quit when a syntax file was already loaded +if exists("b:current_syntax") + finish +endif + +let s:keepcpo= &cpo +set cpo&vim + +syn case match + +syn keyword zserioPackage import package zserio_compatibility_version +syn keyword zserioType bit bool string +syn keyword zserioType int int8 int16 int32 int64 +syn keyword zserioType uint8 uint16 uint32 uint64 +syn keyword zserioType float16 float32 float64 +syn keyword zserioType varint varint16 varint32 varint64 +syn keyword zserioType varuint varsize varuint16 varuint32 varuint64 +syn keyword zserioAlign align +syn keyword zserioLabel case default +syn keyword zserioConditional if condition +syn keyword zserioBoolean true false +syn keyword zserioCompound struct union choice on enum bitmask subtype +syn keyword zserioKeyword function return +syn keyword zserioOperator lengthof valueof instanceof numbits isset +syn keyword zserioRpc service pubsub topic publish subscribe +syn keyword zserioRule rule_group rule +syn keyword zserioStorageClass const implicit packed instantiate +syn keyword zserioTodo contained TODO FIXME XXX +syn keyword zserioSql sql sql_table sql_database sql_virtual sql_without_rowid +syn keyword zserioSql explicit using + +" zserioCommentGroup allows adding matches for special things in comments. +syn cluster zserioCommentGroup contains=zserioTodo + +syn match zserioOffset display "^\s*[a-zA-Z_:\.][a-zA-Z0-9_:\.]*\s*:" + +syn match zserioNumber display "\<\d\+\>" +syn match zserioNumberHex display "\<0[xX]\x\+\>" +syn match zserioNumberBin display "\<[01]\+[bB]\>" contains=zserioBinaryB +syn match zserioBinaryB display contained "[bB]\>" +syn match zserioOctal display "\<0\o\+\>" contains=zserioOctalZero +syn match zserioOctalZero display contained "\<0" + +syn match zserioOctalError display "\<0\o*[89]\d*\>" + +syn match zserioCommentError display "\*/" +syn match zserioCommentStartError display "/\*"me=e-1 contained + +syn region zserioCommentL + \ start="//" skip="\\$" end="$" keepend + \ contains=@zserioCommentGroup,@Spell +syn region zserioComment + \ matchgroup=zserioCommentStart start="/\*" end="\*/" + \ contains=@zserioCommentGroup,zserioCommentStartError,@Spell extend + +syn region zserioString + \ start=+L\="+ skip=+\\\\\|\\"+ end=+"+ contains=@Spell + +syn sync ccomment zserioComment + +" Define the default highlighting. +hi def link zserioType Type +hi def link zserioEndian StorageClass +hi def link zserioStorageClass StorageClass +hi def link zserioAlign Label +hi def link zserioLabel Label +hi def link zserioOffset Label +hi def link zserioSql PreProc +hi def link zserioCompound Structure +hi def link zserioConditional Conditional +hi def link zserioBoolean Boolean +hi def link zserioKeyword Statement +hi def link zserioRpc Keyword +hi def link zserioRule Keyword +hi def link zserioString String +hi def link zserioNumber Number +hi def link zserioNumberBin Number +hi def link zserioBinaryB Special +hi def link zserioOctal Number +hi def link zserioOctalZero Special +hi def link zserioOctalError Error +hi def link zserioNumberHex Number +hi def link zserioTodo Todo +hi def link zserioOperator Operator +hi def link zserioPackage Include +hi def link zserioCommentError Error +hi def link zserioCommentStartError Error +hi def link zserioCommentStart zserioComment +hi def link zserioCommentL zserioComment +hi def link zserioComment Comment + +let b:current_syntax = "zserio" + +let &cpo = s:keepcpo +unlet s:keepcpo diff --git a/src/nvim/eval/userfunc.c b/src/nvim/eval/userfunc.c index a52b8d3f18..a5d7ed2758 100644 --- a/src/nvim/eval/userfunc.c +++ b/src/nvim/eval/userfunc.c @@ -2702,7 +2702,7 @@ void ex_function(exarg_T *eap) // Give the function a sequential number. Can only be used with a // Funcref! xfree(name); - sprintf(numbuf, "%d", ++func_nr); // NOLINT(runtime/printf) + snprintf(numbuf, sizeof(numbuf), "%d", ++func_nr); name = xstrdup(numbuf); } diff --git a/src/nvim/lua/treesitter.c b/src/nvim/lua/treesitter.c index 48057b0c65..45fe7f6129 100644 --- a/src/nvim/lua/treesitter.c +++ b/src/nvim/lua/treesitter.c @@ -1582,25 +1582,19 @@ static void query_err_string(const char *src, int error_offset, TSQueryError err int error_line_len = 0; const char *end_str; - const char *src_tmp = src; - while ((end_str = strchr(src_tmp, '\n')) != NULL) { - int line_length = (int)(end_str - src_tmp) + 1; + do { + const char *src_tmp = src + line_start; + end_str = strchr(src_tmp, '\n'); + int line_length = end_str != NULL ? (int)(end_str - src_tmp) : (int)strlen(src_tmp); int line_end = line_start + line_length; if (line_end > error_offset) { error_line = src_tmp; error_line_len = line_length; break; } - line_start = line_end; + line_start = line_end + 1; row++; - src_tmp += line_length; - } - - // Additional check for the last line - if (line_start <= error_offset) { - error_line = src_tmp; - error_line_len = (int)strlen(src_tmp); - } + } while (end_str != NULL); int column = error_offset - line_start; diff --git a/src/nvim/mbyte.c b/src/nvim/mbyte.c index 92e70350bb..fd9efb1387 100644 --- a/src/nvim/mbyte.c +++ b/src/nvim/mbyte.c @@ -1522,21 +1522,17 @@ int mb_stricmp(const char *s1, const char *s2) // 'encoding' has been set to. void show_utf8(void) { - int len; - int rlen = 0; - char *line; - int clen; - // Get the byte length of the char under the cursor, including composing // characters. - line = get_cursor_pos_ptr(); - len = utfc_ptr2len(line); + char *line = get_cursor_pos_ptr(); + int len = utfc_ptr2len(line); if (len == 0) { msg("NUL"); return; } - clen = 0; + size_t rlen = 0; + int clen = 0; for (int i = 0; i < len; i++) { if (clen == 0) { // start of (composing) character, get its length @@ -1546,10 +1542,11 @@ void show_utf8(void) } clen = utf_ptr2len(line + i); } - sprintf(IObuff + rlen, "%02x ", // NOLINT(runtime/printf) - (line[i] == NL) ? NUL : (uint8_t)line[i]); // NUL is stored as NL + assert(IOSIZE > rlen); + snprintf(IObuff + rlen, IOSIZE - rlen, "%02x ", + (line[i] == NL) ? NUL : (uint8_t)line[i]); // NUL is stored as NL clen--; - rlen += (int)strlen(IObuff + rlen); + rlen += strlen(IObuff + rlen); if (rlen > IOSIZE - 20) { break; } diff --git a/src/nvim/normal.c b/src/nvim/normal.c index 0764cbec7a..513fb5b202 100644 --- a/src/nvim/normal.c +++ b/src/nvim/normal.c @@ -2350,13 +2350,13 @@ bool find_decl(char *ptr, size_t len, bool locally, bool thisblock, int flags_ar bool incll; int searchflags = flags_arg; - pat = xmalloc(len + 7); + size_t patlen = len + 7; + pat = xmalloc(patlen); // Put "\V" before the pattern to avoid that the special meaning of "." // and "~" causes trouble. - assert(len <= INT_MAX); - sprintf(pat, vim_iswordp(ptr) ? "\\V\\<%.*s\\>" : "\\V%.*s", // NOLINT(runtime/printf) - (int)len, ptr); + assert(patlen <= INT_MAX); + snprintf(pat, patlen, vim_iswordp(ptr) ? "\\V\\<%.*s\\>" : "\\V%.*s", (int)len, ptr); old_pos = curwin->w_cursor; save_p_ws = p_ws; save_p_scs = p_scs; diff --git a/src/nvim/plines.c b/src/nvim/plines.c index f59a1754f5..82554c7785 100644 --- a/src/nvim/plines.c +++ b/src/nvim/plines.c @@ -216,6 +216,7 @@ int win_lbr_chartabsize(chartabsize_T *cts, int *headp) if (*s == NUL && !has_lcs_eol) { size = 0; // NUL is not displayed } + bool is_doublewidth = size == 2 && MB_BYTE2LEN((uint8_t)(*s)) > 1; if (cts->cts_has_virt_text) { int tab_size = size; @@ -247,8 +248,7 @@ int win_lbr_chartabsize(chartabsize_T *cts, int *headp) } } - if (size == 2 && MB_BYTE2LEN((uint8_t)(*s)) > 1 - && wp->w_p_wrap && in_win_border(wp, vcol)) { + if (is_doublewidth && wp->w_p_wrap && in_win_border(wp, vcol + size - 2)) { // Count the ">" in the last column. size++; mb_added = 1; diff --git a/src/nvim/spellfile.c b/src/nvim/spellfile.c index 3337169199..d7dc7fb672 100644 --- a/src/nvim/spellfile.c +++ b/src/nvim/spellfile.c @@ -2472,11 +2472,7 @@ static afffile_T *spell_read_aff(spellinfo_T *spin, char *fname) char buf[MAXLINELEN]; aff_entry->ae_cond = getroom_save(spin, items[4]); - if (*items[0] == 'P') { - sprintf(buf, "^%s", items[4]); // NOLINT(runtime/printf) - } else { - sprintf(buf, "%s$", items[4]); // NOLINT(runtime/printf) - } + snprintf(buf, sizeof(buf), *items[0] == 'P' ? "^%s" : "%s$", items[4]); aff_entry->ae_prog = vim_regcomp(buf, RE_MAGIC + RE_STRING + RE_STRICT); if (aff_entry->ae_prog == NULL) { smsg(_("Broken condition in %s line %d: %s"), @@ -2520,7 +2516,7 @@ static afffile_T *spell_read_aff(spellinfo_T *spin, char *fname) onecap_copy(items[4], buf, true); aff_entry->ae_cond = getroom_save(spin, buf); if (aff_entry->ae_cond != NULL) { - sprintf(buf, "^%s", aff_entry->ae_cond); // NOLINT(runtime/printf) + snprintf(buf, MAXLINELEN, "^%s", aff_entry->ae_cond); vim_regfree(aff_entry->ae_prog); aff_entry->ae_prog = vim_regcomp(buf, RE_MAGIC + RE_STRING); } diff --git a/test/functional/shada/marks_spec.lua b/test/functional/shada/marks_spec.lua index 07364382e8..a73e9a244d 100644 --- a/test/functional/shada/marks_spec.lua +++ b/test/functional/shada/marks_spec.lua @@ -250,7 +250,7 @@ describe('ShaDa support code', function() eq(0, exc_exec('rshada')) end) - it('updates deleted marks', function() + it('updates deleted marks with :delmarks', function() nvim_command('edit ' .. testfilename) nvim_command('mark A') @@ -259,12 +259,15 @@ describe('ShaDa support code', function() -- since it can't be set via :mark feed('ggifoobar<esc>') nvim_command('wshada') - nvim_command('normal! `A`a`.') + reset() + nvim_command('edit ' .. testfilename) + nvim_command('normal! `A`a`.') nvim_command('delmarks A a .') nvim_command('wshada') reset() + nvim_command('edit ' .. testfilename) eq('Vim(normal):E20: Mark not set', exc_exec('normal! `A')) eq('Vim(normal):E20: Mark not set', exc_exec('normal! `a')) eq('Vim(normal):E20: Mark not set', exc_exec('normal! `.')) diff --git a/test/functional/treesitter/parser_spec.lua b/test/functional/treesitter/parser_spec.lua index 37dde37a64..8222bb59c4 100644 --- a/test/functional/treesitter/parser_spec.lua +++ b/test/functional/treesitter/parser_spec.lua @@ -1090,9 +1090,9 @@ int x = INT_MAX; -- Invalid capture name test( - '.../query.lua:0: Query error at 1:30. Invalid capture name "ok.capture":\n'.. - '((identifier) @id (#eq? @id @ok.capture))\n'.. - ' ^', - '((identifier) @id (#eq? @id @ok.capture))') + '.../query.lua:0: Query error at 3:2. Invalid capture name "ok.capture":\n'.. + '@ok.capture\n'.. + ' ^', + '((identifier) @id \n(#eq? @id\n@ok.capture\n))') end) end) diff --git a/test/functional/ui/decorations_spec.lua b/test/functional/ui/decorations_spec.lua index ba8d548a57..62dbd57202 100644 --- a/test/functional/ui/decorations_spec.lua +++ b/test/functional/ui/decorations_spec.lua @@ -3244,6 +3244,19 @@ describe('decorations: inline virtual text', function() | ]]} end) + + it('before double-width char that wraps', function() + exec([[ + call setline(1, repeat('a', 40) .. '口' .. '12345') + normal! $ + ]]) + meths.buf_set_extmark(0, ns, 0, 40, { virt_text = { { ('b'):rep(9) } }, virt_text_pos = 'inline' }) + screen:expect{grid=[[ + aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaabbbbbbbbb{1:>}| + 口1234^5 | + | + ]]} + end) end) describe('decorations: virtual lines', function() |