しばらく前から macOS 上で LSP を有効にして Neovim で開発を行っていると、唐突に

Process failed to start: too many open files: ...

と表示され、その後ファイルの保存も何もできなくなるという問題が発生していた.

どうやら原因は macOS 自体の「ファイルを開ける最大数」の設定だったようだ.

ターミナル上で launchctl を用いて設定を確認してみる.

$ launchctl limit
        cpu         unlimited      unlimited
        filesize    unlimited      unlimited
        data        unlimited      unlimited
        stack       8372224        67092480
        core        0              unlimited
        rss         unlimited      unlimited
        memlock     unlimited      unlimited
        maxproc     10666          16000
        maxfiles    256            unlimited

ということで maxfiles256 (デフォルト) に設定されている. 左側に表示されている値が "ソフトリミット" で、右側に表示されている値が "ハードリミット" であるとのこと.

基本的にはソフトリミットの上限値が適用されているらしく、この値を変更すれば良いらしい.

/Library/LaunchDaemons/limit.maxfiles.plist というファイルを作成し、そこに更新後の maxfiles の値を書いておく. (このファイルはデフォルトでは存在しないらしいので、新規に作成する必要がある. 書き込み時には sudo 権限が必要なはず.)

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
  <dict>
    <key>Label</key>
    <string>limit.maxfiles</string>
    <key>ProgramArguments</key>
    <array>
      <string>launchctl</string>
      <string>limit</string>
      <string>maxfiles</string>
      <string>999999</string>
      <string>999999</string>
    </array>
    <key>RunAtLoad</key>
    <true/>
    <key>ServiceIPC</key>
    <false/>
  </dict>
</plist>

内容としては大体 launchctl limit maxfiles 999999 999999 相当の設定である.

後は macOS の再起動を行うか、以下のコマンドを実行することで設定を反映させることができる.

$ sudo launchctl load -w /Library/LaunchDaemons/limit.maxfiles.plist

launchctl で確認してみると、変更が反映されたことがわかる.

$ launchctl limit
        cpu         unlimited      unlimited
        filesize    unlimited      unlimited
        data        unlimited      unlimited
        stack       8372224        67092480
        core        0              unlimited
        rss         unlimited      unlimited
        memlock     unlimited      unlimited
        maxproc     10666          16000
        maxfiles    999999         unlimited