kevinhwang91 / nvim-ufo

Not UFO in the sky, but an ultra fold in Neovim.
BSD 3-Clause "New" or "Revised" License
2.34k stars 49 forks source link

nvim often becomes unresponsive due to recursion stack overflow when having vertical splits #32

Closed wookayin closed 2 years ago

wookayin commented 2 years ago

Neovim version (nvim -v | head -n1)

NVIM v0.8.0-dev+1856-g58323b1fe

Operating system/version

macOS 12.x

How to reproduce the issue

nvim-ufo version: f3662fe (latest as of now). The bug was reproducible when a minimal config is used, i.e., require 'ufo'.setup {} only.

It's quite hard for me to specify the exact condition for this bug to happen, as I don't have a deterministic way/scenario to 100% reproduce the bug, but here's some steps:

  1. Open a file with lots of folds
  2. :vsplit to open the buffer in two different windows
  3. Do some fold operations: activate nvim-ufo, open/close folds, jumping between windows, moving cursors, etc.
  4. The nvim sometimes becomes barely responsive (perhaps while updating folds, etc.)

Expected behavior

There should be no lag or errors and everything should work smoothly.

Actual behavior

An error message shows as a virtual text or maybe in a floating window:

 ufo: Error executing lua: /Users/wookayin/.vim/plugged/nvim-ufo/lua/ufo/decorator.lua:203: Vim:E169: Command too recursive                                                     
                 ⋯                                                                                                         stack traceback:                         [C]: in func
                                                                                                                                            [C]: in function 'cmd'  
image

decorator.lua:L203 is cmd('redraw'). For some reason or specific to my config, some heavy routines seem to be running while redrawing the vim screen.

Unfortunately, I was unable to get the stacktrace because the full error message was truncated.

Interestingly, this usually doesn't happen when a buffer is in a horizontally split. When there is no vertical split or only horizontal splits are made, the UI works fine.

kevinhwang91 commented 2 years ago

Thanks, reproduced.

wookayin commented 2 years ago

Thank you, the fix works for the specific scenario I reported. However, once in a while I still see a similar issue where nvim UI becomes unresponsive upon some (unknown) conditions, hitting 100% CPU. Do you have any idea if there's any good way to debug/troubleshoot so I can provide you with more debugging information?

Looking at neovim's (not lua) stacktrace, the stack is almost overflowing due to infinite recursion on redraw:

Click to open the stacktrace excerpt ``` + ! 142 ex_redraw (in nvim) + 204 [0x10078dca4] + ! 142 update_screen (in nvim) + 3548 [0x10087b180] + ! 142 decor_providers_invoke_end (in nvim) + 176 [0x10070e98c] + ! 142 decor_provider_invoke (in nvim) + 148 [0x10070e2f4] + ! 142 nlua_call_ref (in nvim) + 216 [0x1007da6bc] + ! 142 lua_pcall (in libluajit-5.1.2.1.0.dylib) + 148 [0x100e07910] + ! 142 lj_BC_FUNCC (in libluajit-5.1.2.1.0.dylib) + 44 [0x100dfaca8] + ! 142 nlua_api_nvim_exec (in nvim) + 356 [0x1006c26c8] + ! 142 nvim_exec (in nvim) + 232 [0x1006e8eb4] + ! 142 source_using_linegetter (in nvim) + 220 [0x10077a84c] + ! 142 do_cmdline (in nvim) + 12308 [0x10077fcb4] + ! 142 ex_redraw (in nvim) + 204 [0x10078dca4] + ! 142 update_screen (in nvim) + 3548 [0x10087b180] + ! 142 decor_providers_invoke_end (in nvim) + 176 [0x10070e98c] + ! 142 decor_provider_invoke (in nvim) + 148 [0x10070e2f4] + ! 142 nlua_call_ref (in nvim) + 216 [0x1007da6bc] + ! 142 lua_pcall (in libluajit-5.1.2.1.0.dylib) + 148 [0x100e07910] + ! 142 lj_BC_FUNCC (in libluajit-5.1.2.1.0.dylib) + 44 [0x100dfaca8] + ! 142 nlua_api_nvim_exec (in nvim) + 356 [0x1006c26c8] + ! 142 nvim_exec (in nvim) + 232 [0x1006e8eb4] + ! 142 source_using_linegetter (in nvim) + 220 [0x10077a84c] + ! 142 do_cmdline (in nvim) + 12308 [0x10077fcb4] ```
kevinhwang91 commented 2 years ago

It's weird, I can't reproduce the issue after the commit. The stack looks like caused by cmd('redraw'). I guess some plugin change your folds. UFO_LOG=debug nvim, the log path is ~/.cache/nvim/ufo.log. You can also change the log level on the fly by lua require('ufo.lib.log').setLevel('debug')