⌨️

x86_64-pc-msys 版の nvim をビルドする

2023/08/20に公開

MSYS2 環境向けの nvim。not MINGW
x86_64-pc-msys, MSYSTEM=MSYS をビルドします。

% ldd /usr/local/bin/nvim.exe
        ntdll.dll => /c/WINDOWS/SYSTEM32/ntdll.dll (0x7ff8f5c70000)
        KERNEL32.DLL => /c/WINDOWS/System32/KERNEL32.DLL (0x7ff8f4d20000)
        KERNELBASE.dll => /c/WINDOWS/System32/KERNELBASE.dll (0x7ff8f3410000)
        msys-iconv-2.dll => /usr/bin/msys-iconv-2.dll (0x5603f0000)
        msys-2.0.dll => /usr/bin/msys-2.0.dll (0x180040000) 👈 これ
        msys-intl-8.dll => /usr/bin/msys-intl-8.dll (0x430b30000)
        liblua.dll => /usr/bin/liblua.dll (0x4fe400000)
        msys-uv-1.dll => /usr/bin/msys-uv-1.dll (0x5475e0000)

通常ビルドと違うところ

msys-2.0.dll にリンクしている

msys のパス /c/Windows (C:\Windows ではなく) の世界の方のアプリとなる。
msys 上の QuickFix とかでフルパスに /c/ が含まれていてもちゃんと飛べる。

luajit が無い

動かないプラグインとか、なんかもっさりとしている。

概要

msys 版の luajit が無い

素の Lua-5.1 を使います。
紆余曲折を経て、 /usr/bin/liblua.dll を時前ビルドしてそれを使うことになりました。

treesitter の tar の解凍でエラーが出てビルドが止まる

msys 非対応のパーミッションとかが書いてあるのかもしれない。
手修正で無理やり突破

cmake の find_lua に '-llua` が付かない?

手で追加

release 版は実行時にクラッシュする

-DNVIM_LOG_DEBUG があると耐えることがわかったのでとりあえず。
SIGABRT で何も手がかりがなかった。

手順

以降の手順は、msys 上で実行します。

lua-5.1 をビルドする

https://github.com/ousttrue/dotfiles/blob/master/msys2/lua_build/subprojects/packagefiles/lua/meson.build

$ meson setup build --prefix /usr
$ meson install -C build

deps をビルドする

cmake -S cmake.deps -B .deps -G Ninja -DUSE_BUNDLED_LUAJIT=off -DCMAKE_BUILD_TYPE=RelWithDebInfo
  • USE_BUNDLED_LUAJIT=off: luajit をビルドしません
  • CMAKE_BUILD_TYPE=RelWithDebInfo: 適当に。省略すると Debug になります
cmake --build .deps
# error で止まる。

treesitter のアーカイブ解凍でエラーになるので手作業で回避します。

# .deps\build\src\treesitter-stamp\extract-treesitter.cmake
# 40行あたりをコメントアウト
# if(NOT rv EQUAL 0)
#   message(STATUS "extracting... [error clean up]")
#   file(REMOVE_RECURSE "${ut_dir}")
#   message(FATAL_ERROR "Extract of '${filename}' failed")
# endif()

失敗すると後始末して削除するようなので失敗しても続行するように修正。
さらに、手で解凍してコピーしてあげます。

> pushd .deps/build/downloads/treesitter
> ls
0a1c4d8466efed6ef5971aa03a84ebb0836128b1.tar.gz
> tar xf 0a1c4d8466efed6ef5971aa03a84ebb0836128b1.tar.gz
tar: tree-sitter-0a1c4d8466efed6ef5971aa03a84ebb0836128b1/CONTRIBUTING.md: Cannot create symlink to ‘docs/section-6-contributing.md’: No such file or directory # 👈謎のエラー
tar: tree-sitter-0a1c4d8466efed6ef5971aa03a84ebb0836128b1/script/reproduce: Cannot create symlink to ‘run-fuzzer’: No such file or directory
tar: Exiting with failure status due to previous errors
> popd
> cp -rp .deps/build/downloads/treesitter/tree-sitter-0a1c4d8466efed6ef5971aa03a84ebb0836128b1/* .deps/build/src/treesitter/

続きを実行

> cmake --build .deps
# error で止まる。もう一回コピー。
> cp -rp .deps/build/downloads/treesitter/tree-sitter-0a1c4d8466efed6ef5971aa03a84ebb0836128b1/* .deps/build/src/treesitter/
> cmake --build .deps
# 完成 w

以上で、luajit を使わずに、/usr/bin/liblua.dll を参照する .deps ができました。

本体ビルド

CMake 改造

find_lua がうまくいかないのか nlua0 に対して -llua がつかないので、手動で追加します。
あと NVIM_LOG_DEBUG を有効にする。

--- a/src/nvim/CMakeLists.txt
+++ b/src/nvim/CMakeLists.txt
@@ -42,6 +42,7 @@ target_link_libraries(main_lib INTERFACE
   unibilium
   lpeg)
 target_link_libraries(nlua0 PUBLIC lpeg)
+target_link_libraries(nlua0 PUBLIC lua) # 👈 これ

 # Libintl (not Intl) selects our FindLibintl.cmake script. #8464
 find_package(Libintl REQUIRED)
 @@ -396,7 +397,7 @@ if($ENV{CI})
   # TODO(bfredl): debug log level also exposes some errors with EXITFREE in ASAN build.
 else()
   # Minimize logging for release-type builds.
-  target_compile_definitions(nvim PRIVATE $<$<CONFIG:Debug>:NVIM_LOG_DEBUG>) # 👈
+  target_compile_definitions(nvim PRIVATE NVIM_LOG_DEBUG) # 👈 これ
 endif()

 if(ENABLE_ASAN_UBSAN OR ENABLE_MSAN OR ENABLE_TSAN)

ビルド

> cmake -S . -B build -G Ninja -DPREFER_LUA=on -DENABLE_LANGUAGES=off -DCMAKE_BUILD_TYPE=RelWithDebInfo
  • PREFER_LUA=on: luajit を無効化
  • ENABLE_LANGUAGES=off: 翻訳カタログ生成?でこけるのでやむを得ず
  • CMAKE_BUILD_TYPE=RelWithDebInfo: 適当に

ビルド

> cmake --build build
# /usr/local にインストール
> cmake --install build

msys ビルドは茨の道

msys 版はちょっと改造したらビルドは通る事が多い(ランタイムにクラッシュしたりするが)。ビルド職人の練習にはちょうどよいので、暇な人はどうぞ。

特に、pacman にあるやつを自前ビルドしたいという場合は、

https://repo.msys2.org/msys/sources/

から pacman に当てているパッチが入手できるのでわりと自前ビルドできます(tmux の絵文字対応とか emacs29 とか)。
無い場合は、cygwin 版のパッチが参考になるかもしれない。

Discussion