Merge pull request #39074 from bfredl/retromania

build(zig): run oldtests in zig builds (RETROMANIA HYPERDRIVE)
This commit is contained in:
bfredl
2026-06-02 12:34:40 +02:00
committed by GitHub
10 changed files with 208 additions and 18 deletions

View File

@@ -258,10 +258,12 @@ jobs:
version: 0.16.0
- run: sudo apt-get install -y inotify-tools
- run: mkdir -p build/ # build/ is used for shared log paths, see global ENV defs
- run: zig build $OPTS test_nlua0
- run: zig build $OPTS nvim_bin && ./zig-out/bin/nvim --version
- run: zig build $OPTS unittest
- run: zig build $OPTS functionaltest
- run: zig build $OPTS oldtest
# `zig build` uses a lua script for doctags in order to support cross-compiling
# compare with the builtin generator that they match
- run: cd runtime; ../zig-out/bin/nvim -u NONE -i NONE -e --headless -c "helptags ++t doc" -c quit
@@ -271,6 +273,8 @@ jobs:
runs-on: macos-15
timeout-minutes: 45
name: build using zig build (macos 15)
env:
OPTS: # empty
steps:
- uses: actions/checkout@v6
with:
@@ -280,9 +284,11 @@ jobs:
with:
version: 0.16.0
- run: zig build test_nlua0 -Dluajit=false
- run: zig build nvim_bin -Dluajit=false && ./zig-out/bin/nvim --version
- run: zig build functionaltest -Dluajit=false
- run: mkdir -p build/ # build/ is used for shared log paths, see global ENV defs
- run: zig build $OPTS test_nlua0
- run: zig build $OPTS nvim_bin && ./zig-out/bin/nvim --version
- run: zig build $OPTS functionaltest
- run: zig build $OPTS oldtest
zig-build-windows:
runs-on: windows-2025
@@ -297,6 +303,7 @@ jobs:
with:
version: 0.16.0
- run: mkdir -p build/ # build/ is used for shared log paths, see global ENV defs
- run: zig build test_nlua0
- run: zig build nvim_bin
- run: ./zig-out/bin/nvim --version

View File

@@ -6,8 +6,8 @@
.dependencies = .{
.zlua = .{
.url = "git+https://github.com/natecraddock/ziglua#8f271c82baa5fc43aa02a72f6da020c2025d9436",
.hash = "zlua-0.1.0-hGRpC2aABQD4D9PBVH3wAW8k32-I4969MRQ0CpOwoley",
.url = "git+https://github.com/natecraddock/ziglua#1dcb9f2b7b466a1609cc11e746c2efc4f17685da",
.hash = "zlua-0.1.0-hGRpC22ABQA4y12Uz7QaHuCkKrpaa_66xidApjtFuKFg",
},
.lpeg = .{
.url = "https://github.com/neovim/deps/raw/d495ee6f79e7962a53ad79670cb92488abe0b9b4/opt/lpeg-1.1.0.tar.gz",

View File

@@ -97,12 +97,12 @@ function M.get_parser(buf, lang, opts)
if not api.nvim_buf_is_loaded(buf) then
return nil, string.format('Buffer %s must be loaded to create parser', buf)
end
local parser = vim.npcall(M._create_parser, buf, lang, opts)
if not parser then
return nil,
string.format('Parser could not be created for buffer %s and language "%s"', buf, lang)
local status, res = pcall(M._create_parser, buf, lang, opts)
if not status then
local msg = 'Parser could not be created for buffer %s and language "%s": %s'
return nil, string.format(msg, buf, lang, res)
end
parsers[buf] = parser
parsers[buf] = res
end
parsers[buf]:register_cbs(opts.buf_attach_cbs)

View File

@@ -212,9 +212,7 @@ void eval_clear(void)
{
evalvars_clear();
free_scriptnames(); // must come after evalvars_clear().
# ifdef HAVE_WORKING_LIBINTL
free_locales();
# endif
// autoloaded script names
free_autoload_scriptnames();

View File

@@ -338,8 +338,15 @@ char *get_locales(expand_T *xp, int idx)
void lang_init(void)
{
#if defined(__APPLE__) && !defined(ZIG_BUILD)
#if defined(__APPLE__)
if (!os_env_exists("LANG", true)) {
# if defined(ZIG_BUILD)
// fuck it just use the objectively correct values:
os_setenv("LANG", "C.UTF-8", true);
setlocale(LC_ALL, "C.UTF-8");
// Make sure strtod() uses a decimal point, not a comma.
setlocale(LC_NUMERIC, "C");
# else
char buf[50] = { 0 };
// $LANG is not set, either because it was unset or Nvim was started
@@ -358,6 +365,7 @@ void lang_init(void)
} else {
ELOG("$LANG is empty and the macOS primary language cannot be inferred.");
}
# endif
}
#endif
}

View File

@@ -1789,7 +1789,7 @@ static idx_T read_tree_node(FILE *fd, uint8_t *byts, idx_T *idxs, int maxidx, id
c = (getc(fd) << 16) + c; // <region>
}
if (c & WF_AFX) {
c = (getc(fd) << 24) + c; // <affixID>
c = (int)((unsigned)getc(fd) << 24) + c; // <affixID>
}
}

View File

@@ -77,9 +77,7 @@ static const char *command_complete[] = {
[EXPAND_HIGHLIGHT] = "highlight",
[EXPAND_HISTORY] = "history",
[EXPAND_KEYMAP] = "keymap",
#ifdef HAVE_WORKING_LIBINTL
[EXPAND_LOCALES] = "locale",
#endif
[EXPAND_LUA] = "lua",
[EXPAND_MAPCLEAR] = "mapclear",
[EXPAND_MAPPINGS] = "mapping",

View File

@@ -19,7 +19,10 @@ describe('treesitter language API', function()
return vim.treesitter.get_parser(0, 'borklang')
end)
eq(NIL, parser)
eq('Parser could not be created for buffer 1 and language "borklang"', error)
matches(
'^Parser could not be created for buffer 1 and language "borklang": .+: No parser for language "borklang"$',
error
)
-- actual message depends on platform
matches(
@@ -110,7 +113,10 @@ describe('treesitter language API', function()
return vim.treesitter.get_parser(0, 'borklang')
end)
eq(NIL, parser)
eq('Parser could not be created for buffer 1 and language "borklang"', error)
matches(
'^Parser could not be created for buffer 1 and language "borklang": .+: No parser for language "borklang"$',
error
)
end
)

160
test/old/runner.lua Normal file
View File

@@ -0,0 +1,160 @@
-- execute old style tests
-- when compared to the testdir/Makefile based approach, this replaces
-- all wrapper process logic:
-- Makefile
-- runnvim.sh and its library test.sh
-- runnvim.vim (wrapper which runs a nested vim inside a terminal)
-- it DOES NOT not replace the logic running inside the nvim-under-test
-- runtest.vim and its libraries setup.vim, shared.vim, check.vim
local nvim_bin = vim.v.progpath -- must be absolute
vim.api.nvim_set_current_dir('test/old/testdir/')
local function readable(fn)
return vim.fn.filereadable(fn) ~= 0
end
local errlog = 'test.log'
local messages = 'messages'
local starttime = 'starttime'
local gen_opt_log = 'gen_opt_test.log'
function oksystem(args)
local res = vim.system(args, {}):wait()
if res.code ~= 0 then
error(vim.inspect(args) .. ' failed:\n' .. res.stdout .. res.stderr)
end
return res
end
function clean_output()
for _, f in ipairs { errlog, messages, starttime, gen_opt_log, 'opt_test.vim' } do
vim.uv.fs_unlink(f)
end
-- check status, some tests mess with perms so this could fail:
oksystem { 'bash', '-c', 'rm -rf X* viminfo test.out test.ok' }
end
function if_nonempty(rawtext, name)
text = vim.trim(rawtext)
if #text > 0 then
if name then
print('== ' .. name)
end
print(text)
print(name and '== END ' .. name or '\n')
end
end
function if_exists(fn, name)
local fil = io.open(fn)
if fil then
if_nonempty(fil:read '*a', name)
fil:close()
return true
end
end
local verbose = vim.env.VERBOSE
function run_nvim(...)
local cmd = vim.system(
{ nvim_bin, '-u', 'NONE', '-i', 'NONE', '--headless', ... },
{ env = { VIMRUNTIME = '../../../runtime' } }
)
return cmd:wait()
end
function run_test(testfile)
if not vim.endswith(testfile, '.vim') then
error 'not an oldtest'
end
clean_output()
if testfile == 'test_options_all.vim' then
local res = run_nvim(
'-S',
'gen_opt_test.vim',
'../../../src/nvim/options.lua',
'../../../runtime/doc/options.txt'
)
if if_exists(gen_opt_log, 'GEN opt_test.vim') or res.code > 0 then
return false
end
end
local resfile = string.sub(testfile, 1, -4) .. 'res'
vim.uv.fs_unlink(resfile)
assert(not readable(resfile))
local opts = 'set shortmess-=F backupdir=. undodir=. viewdir=.'
local res = run_nvim('--cmd', opts, '-S', 'runtest.vim', testfile)
local passed = (readable(resfile) and res.code == 0)
if_exists(messages)
if verbose or not passed then
if_nonempty(res.stdout, 'STDOUT')
if_nonempty(res.stderr, 'STDERR')
-- if_exists(starttime, "starttime")
if_exists(errlog, 'test.log')
end
return passed
end
local function all_tests()
local nested_tests = {}
local alot = io.open('test_alot.vim')
local sourcepat = '^source (test_.*%.vim)$'
for line in alot:lines() do
local m = string.match(line, sourcepat)
if m then
nested_tests[m] = true
end
end
alot:close()
local files = {}
for name, type in vim.fs.dir('.') do
match = string.match(name, '^test_.*%.vim$')
if match then
if nested_tests[match] then
nested_tests[match] = nil
elseif match == 'test_largefile.vim' then
-- ignored: uses too much resources to run on CI
else
table.insert(files, match)
end
end
end
return files
end
local files
if #arg > 0 then
files = {}
for _, a in ipairs(arg) do
table.insert(files, string.match(a, '[^/]*$'))
end
else
files = all_tests()
end
local count = #files
local failures = {}
for i, fil in ipairs(files) do
print('run: ', fil)
if not run_test(fil) then
table.insert(failures, fil)
end
end
if #failures > 0 then
print('failed:', vim.inspect(failures))
vim.cmd 'cquit'
end

View File

@@ -50,6 +50,19 @@ pub fn test_steps(b: *std.Build, nvim_bin: *std.Build.Step.Compile, depend_on: *
const functionaltest_step = b.step("functionaltest", "run functional tests");
functionaltest_step.dependOn(&functional_tests.step);
const old_tests = b.addRunArtifact(nvim_bin);
old_tests.addArg("-l");
old_tests.addFileArg(b.path("./test/old/runner.lua"));
if (b.args) |args| {
old_tests.addArgs(args); // accept TEST_FILE as a positional argument
}
const env = old_tests.getEnvMap();
try env.put("BUILD_DIR", b.install_path);
const oldtest_step = b.step("oldtest", "run old tests");
oldtest_step.dependOn(&old_tests.step);
oldtest_step.dependOn(depend_on);
if (unit_paths) |paths| {
const unit_tests = try testStep(b, "unit", nvim_bin, config_dir, paths);
unit_tests.step.dependOn(depend_on);