aboutsummaryrefslogtreecommitdiff
path: root/runtime
diff options
context:
space:
mode:
Diffstat (limited to 'runtime')
-rw-r--r--runtime/doc/lua.txt43
-rw-r--r--runtime/doc/various.txt6
-rw-r--r--runtime/filetype.lua2
-rw-r--r--runtime/lua/vim/filetype.lua88
-rw-r--r--runtime/pack/dist/opt/termdebug/plugin/termdebug.vim3
5 files changed, 115 insertions, 27 deletions
diff --git a/runtime/doc/lua.txt b/runtime/doc/lua.txt
index 9f8d4a8479..f40b32c469 100644
--- a/runtime/doc/lua.txt
+++ b/runtime/doc/lua.txt
@@ -2064,14 +2064,45 @@ add({filetypes}) *vim.filetype.add()*
{filetypes} (table) A table containing new filetype maps
(see example).
-match({name}, {bufnr}) *vim.filetype.match()*
- Find the filetype for the given filename and buffer.
+match({arg}) *vim.filetype.match()*
+ Perform filetype detection.
+
+ The filetype can be detected using one of three methods:
+ 1. Using an existing buffer
+ 2. Using only a file name
+ 3. Using only file contents
+
+ Of these, option 1 provides the most accurate result as it
+ uses both the buffer's filename and (optionally) the buffer
+ contents. Options 2 and 3 can be used without an existing
+ buffer, but may not always provide a match in cases where the
+ filename (or contents) cannot unambiguously determine the
+ filetype.
+
+ Each of the three options is specified using a key to the
+ single argument of this function. Example:
+>
+
+ -- Using a buffer number
+ vim.filetype.match({ buf = 42 })
+
+ -- Using a filename
+ vim.filetype.match({ filename = "main.lua" })
+
+ -- Using file contents
+ vim.filetype.match({ contents = {"#!/usr/bin/env bash"} })
+<
Parameters: ~
- {name} (string) File name (can be an absolute or
- relative path)
- {bufnr} (number|nil) The buffer to set the filetype for.
- Defaults to the current buffer.
+ {arg} (table) Table specifying which matching strategy to
+ use. It is an error to provide more than one
+ strategy. Accepted keys are:
+ • buf (number): Buffer number to use for matching
+ • filename (string): Filename to use for matching.
+ Note that the file need not actually exist in the
+ filesystem, only the name itself is used.
+ • contents (table): An array of lines representing
+ file contents to use for matching.
Return: ~
(string|nil) If a match was found, the matched filetype.
diff --git a/runtime/doc/various.txt b/runtime/doc/various.txt
index 562faeaa2c..9eb6470962 100644
--- a/runtime/doc/various.txt
+++ b/runtime/doc/various.txt
@@ -346,7 +346,11 @@ g8 Print the hex values of the bytes used in the
Only string variables can be used. After the
redirection starts, if the variable is removed or
locked or the variable type is changed, then further
- command output messages will cause errors.
+ command output messages will cause errors. When using
+ a local variable (l:var in a function or s:var in a
+ script) and another `:redir` causes the current one to
+ end, the scope might be different and the assignment
+ fails.
To get the output of one command the |execute()|
function can be used instead of redirection.
diff --git a/runtime/filetype.lua b/runtime/filetype.lua
index b002b8971b..35bb31edce 100644
--- a/runtime/filetype.lua
+++ b/runtime/filetype.lua
@@ -12,7 +12,7 @@ vim.api.nvim_create_augroup('filetypedetect', { clear = false })
vim.api.nvim_create_autocmd({ 'BufRead', 'BufNewFile' }, {
group = 'filetypedetect',
callback = function(args)
- local ft, on_detect = vim.filetype.match(args.file, args.buf)
+ local ft, on_detect = vim.filetype.match({ buf = args.buf })
if ft then
vim.api.nvim_buf_set_option(args.buf, 'filetype', ft)
if on_detect then
diff --git a/runtime/lua/vim/filetype.lua b/runtime/lua/vim/filetype.lua
index 6c4894208f..3e86159489 100644
--- a/runtime/lua/vim/filetype.lua
+++ b/runtime/lua/vim/filetype.lua
@@ -2047,7 +2047,7 @@ local pattern = {
end
end, { priority = -math.huge + 1 }),
['XF86Config.*'] = starsetf(function(path, bufnr)
- return require('vim.filetype.detect').xfree86(bufnr)
+ return require('vim.filetype.detect').xfree86()
end),
['%.zcompdump.*'] = starsetf('zsh'),
-- .zlog* and zlog*
@@ -2185,17 +2185,24 @@ end
local function dispatch(ft, path, bufnr, ...)
local on_detect
if type(ft) == 'function' then
- ft, on_detect = ft(path, bufnr, ...)
+ if bufnr then
+ ft, on_detect = ft(path, bufnr, ...)
+ else
+ -- If bufnr is nil (meaning we are matching only against the filename), set it to an invalid
+ -- value (-1) and catch any errors from the filetype detection function. If the function tries
+ -- to use the buffer then it will fail, but this enables functions which do not need a buffer
+ -- to still work.
+ local ok
+ ok, ft, on_detect = pcall(ft, path, -1, ...)
+ if not ok then
+ return
+ end
+ end
end
if type(ft) == 'string' then
return ft, on_detect
end
-
- -- Any non-falsey value (that is, anything other than 'nil' or 'false') will
- -- end filetype matching. This is useful for e.g. the dist#ft functions that
- -- return 0, but set the buffer's filetype themselves
- return ft
end
---@private
@@ -2214,29 +2221,74 @@ local function match_pattern(name, path, tail, pat)
return matches
end
---- Find the filetype for the given filename and buffer.
+--- Perform filetype detection.
+---
+--- The filetype can be detected using one of three methods:
+--- 1. Using an existing buffer
+--- 2. Using only a file name
+--- 3. Using only file contents
+---
+--- Of these, option 1 provides the most accurate result as it uses both the buffer's filename and
+--- (optionally) the buffer contents. Options 2 and 3 can be used without an existing buffer, but
+--- may not always provide a match in cases where the filename (or contents) cannot unambiguously
+--- determine the filetype.
+---
+--- Each of the three options is specified using a key to the single argument of this function.
+--- Example:
+---
+--- <pre>
+--- -- Using a buffer number
+--- vim.filetype.match({ buf = 42 })
---
----@param name string File name (can be an absolute or relative path)
----@param bufnr number|nil The buffer to set the filetype for. Defaults to the current buffer.
+--- -- Using a filename
+--- vim.filetype.match({ filename = "main.lua" })
+---
+--- -- Using file contents
+--- vim.filetype.match({ contents = {"#!/usr/bin/env bash"} })
+--- </pre>
+---
+---@param arg table Table specifying which matching strategy to use. It is an error to provide more
+--- than one strategy. Accepted keys are:
+--- * buf (number): Buffer number to use for matching
+--- * filename (string): Filename to use for matching. Note that the file need not
+--- actually exist in the filesystem, only the name itself is
+--- used.
+--- * contents (table): An array of lines representing file contents to use for
+--- matching.
---@return string|nil If a match was found, the matched filetype.
---@return function|nil A function that modifies buffer state when called (for example, to set some
--- filetype specific buffer variables). The function accepts a buffer number as
--- its only argument.
-function M.match(name, bufnr)
+function M.match(arg)
vim.validate({
- name = { name, 's' },
- bufnr = { bufnr, 'n', true },
+ arg = { arg, 't' },
})
- -- When fired from the main filetypedetect autocommand the {bufnr} argument is omitted, so we use
- -- the current buffer. The {bufnr} argument is provided to allow extensibility in case callers
- -- wish to perform filetype detection on buffers other than the current one.
- bufnr = bufnr or api.nvim_get_current_buf()
+ if not (arg.buf or arg.filename or arg.contents) then
+ error('One of "buf", "filename", or "contents" must be given')
+ end
+
+ if (arg.buf and arg.filename) or (arg.buf and arg.contents) or (arg.filename and arg.contents) then
+ error('Only one of "buf", "filename", or "contents" must be given')
+ end
+
+ local bufnr = arg.buf
+ local name = bufnr and api.nvim_buf_get_name(bufnr) or arg.filename
+ local contents = arg.contents
- name = normalize_path(name)
+ if name then
+ name = normalize_path(name)
+ end
local ft, on_detect
+ if not (bufnr or name) then
+ -- Sanity check: this should not happen
+ assert(contents, 'contents should be non-nil when bufnr and filename are nil')
+ -- TODO: "scripts.lua" content matching
+ return
+ end
+
-- First check for the simple case where the full path exists as a key
local path = vim.fn.resolve(vim.fn.fnamemodify(name, ':p'))
ft, on_detect = dispatch(filename[path], path, bufnr)
diff --git a/runtime/pack/dist/opt/termdebug/plugin/termdebug.vim b/runtime/pack/dist/opt/termdebug/plugin/termdebug.vim
index f76bdebe9b..c4e90eb373 100644
--- a/runtime/pack/dist/opt/termdebug/plugin/termdebug.vim
+++ b/runtime/pack/dist/opt/termdebug/plugin/termdebug.vim
@@ -2,7 +2,7 @@
"
" Author: Bram Moolenaar
" Copyright: Vim license applies, see ":help license"
-" Last Change: 2022 Jun 22
+" Last Change: 2022 Jun 24
"
" WORK IN PROGRESS - The basics works stable, more to come
" Note: In general you need at least GDB 7.12 because this provides the
@@ -539,6 +539,7 @@ func TermDebugSendCommand(cmd)
endif
sleep 10m
endif
+ " TODO: should we prepend CTRL-U to clear the command?
call chansend(s:gdb_job_id, a:cmd . "\r")
if do_continue
Continue