kiennq / emacs-mini-modeline

Display emacs mode line in minibuffer
GNU General Public License v3.0
197 stars 14 forks source link

Will freeze when using Info nodes #34

Open johnmwu opened 4 years ago

johnmwu commented 4 years ago

Reproducing is unreliable.

  1. Open an Info node (e.g. (Emacs))
  2. Press i (Info-index) and select the first item.
  3. Repeat step 2 in rapid succession with the second, third, fourth, etc. items. I'm using ivy.

Here is a screenshot where it freezes. image

I'm pretty sure the problem is with mini-modeline. Disabling mini-modeline solves things. (I'm using smart-mode-line but this happens even with smart-mode-line disabled).

The default value of mini-modeline-r-format is:

("%e" mode-line-front-space mode-line-mule-info mode-line-client mode-line-modified mode-line-remote mode-line-frame-identification mode-line-buffer-identification " " mode-line-position " " evil-mode-line-tag (:eval (string-trim (format-mode-line mode-line-modes))) mode-line-misc-info)

If we remove just mode-line-front-space:

(setq mini-modeline-r-format '("%e"  mode-line-mule-info mode-line-client mode-line-modified mode-line-remote mode-line-frame-identification mode-line-buffer-identification " "  " " evil-mode-line-tag (:eval (string-trim (format-mode-line mode-line-modes))) mode-line-misc-info))

everything works.

This is the solution I'll adopt. I tried to debug, but because it's unreliable and Emacs froze I couldn't get a good backtrace.

kiennq commented 4 years ago

I couldn't repro this either. Well, I don't think that mode-line-front-space needed as default item at all. Remove it with a8db97f

johnmwu commented 4 years ago

I investigated further an it actually has nothing to do with mode-line-front-space, but rather line-number-mode. In my case I'm using smart-mode-line and mode-line-front-space happened to contain the line number.

Could you retry with line-number-mode enabled? It doesn't matter whether you're using smart-mode-line.

My new solution is to turn off line-number-mode and dump line-number-at-pos directly into the mode line.

Finally, apologies but you shouldn't remove mode-line-front-space. Smart-mode-line puts file size, line number and column number there.

kiennq commented 4 years ago

Okay.

johnmwu commented 4 years ago

Could you retry reproducing with line-number-mode enabled?

kiennq commented 4 years ago

I can repro this now. Emacs enter infinite loop, however, since I don't have Emacs debug symbol, it's hard to tell where the infinite loop happened

oscarfv commented 4 years ago

For the record, this is the C backtrace:

(gdb) bt
#0  0x0000558c791fa4c0 in BUFFER_CEILING_OF (bytepos=557362)
    at ../../emacs/src/xdisp.c:26727
#1  display_count_lines
    (start_byte=557362, limit_byte=limit_byte@entry=703917, count=681760, 
    count@entry=681823, byte_pos_ptr=byte_pos_ptr@entry=0x7fff2cae4c08)
    at ../../emacs/src/xdisp.c:26651
#2  0x0000558c792178ca in decode_mode_spec
    (string=<synthetic pointer>, field_width=0, c=<optimized out>, w=<optimized out>)
    at ../../emacs/src/xdisp.c:26376
#3  display_mode_element
    (it=<optimized out>, depth=<optimized out>, field_width=<optimized out>, precision=<optimized out>, elt=<optimized out>, props=0x0, risky=<optimized out>)
    at ../../emacs/src/xdisp.c:25494
#4  0x0000558c792182fd in display_mode_element
    (it=0x7fff2cae5090, depth=<optimized out>, field_width=10, precision=-40, elt=<optimized out>, props=0x0, risky=<optimized out>) at ../../emacs/src/lisp.h:1450
#5  0x0000558c792182fd in display_mode_element
    (it=0x7fff2cae5090, depth=<optimized out>, field_width=-3, precision=-40, elt=<optimized out>, props=0x0, risky=<optimized out>) at ../../emacs/src/lisp.h:1450
#6  0x0000558c792182fd in display_mode_element
    (it=0x7fff2cae5090, depth=<optimized out>, field_width=0, precision=-37, elt=<optimized out>, props=0x0, risky=<optimized out>) at ../../emacs/src/lisp.h:1450
#7  0x0000558c792182fd in display_mode_element
    (it=0x7fff2cae5090, depth=<optimized out>, field_width=0, precision=0, elt=<optimized out>, props=0x0, risky=<optimized out>) at ../../emacs/src/lisp.h:1450
#8  0x0000558c79218cc6 in Fformat_mode_line
    (format=0x558c7cd189f3, face=<optimized out>, window=0x558c8721fe55, buffer=<optimized out>) at ../../emacs/src/lisp.h:1033
#9  0x0000558c79323c9a in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#10 0x0000558c79323762 in apply_lambda
    (fun=0x558c810684f3, args=<optimized out>, count=count@entry=45)
    at ../../emacs/src/eval.c:2922
#11 0x0000558c79323a73 in eval_sub (form=<optimized out>) at ../../emacs/src/eval.c:2349
--Type <RET> for more, q to quit, c to continue without paging--
#12 0x0000558c79324507 in Fsetq (args=<optimized out>) at ../../emacs/src/eval.c:509
#13 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#14 0x0000558c793243bd in Fprogn (body=0x558c81063503) at ../../emacs/src/eval.c:462
#15 Fif (args=<optimized out>) at ../../emacs/src/eval.c:418
#16 Fif (args=<optimized out>) at ../../emacs/src/eval.c:404
#17 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#18 0x0000558c79323f7d in Fprogn (body=0x558c8106ab43) at ../../emacs/src/eval.c:462
#19 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#20 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#21 0x0000558c7932500d in Fprogn (body=0x0) at ../../emacs/src/eval.c:462
#22 Flet (args=0x558c8106ab83) at ../../emacs/src/eval.c:987
#23 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#24 0x0000558c79323f7d in Fprogn (body=0x0, body@entry=0x558c8106abb3)
    at ../../emacs/src/eval.c:462
#25 0x0000558c793159ba in Fsave_current_buffer (args=0x558c8106abb3)
    at ../../emacs/src/editfns.c:855
#26 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#27 0x0000558c793243bd in Fprogn (body=0x0) at ../../emacs/src/eval.c:462
#28 Fif (args=<optimized out>) at ../../emacs/src/eval.c:418
#29 Fif (args=<optimized out>) at ../../emacs/src/eval.c:404
#30 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#31 0x0000558c79323f7d in Fprogn (body=0x0) at ../../emacs/src/eval.c:462
#32 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#33 0x0000558c793252af in Funwind_protect (args=0x558c8106a483)
    at ../../emacs/src/lisp.h:1444
#34 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#35 0x0000558c793251ff in Fprogn (body=0x0) at ../../emacs/src/eval.c:462
#36 FletX (args=0x558c8106a4d3) at ../../emacs/src/eval.c:919
#37 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#38 0x0000558c793254e9 in internal_lisp_condition_case
    (var=0x29e960379b48, bodyform=0x558c8106a4e3, handlers=<optimized out>)
    at ../../emacs/src/eval.c:1327
#39 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
--Type <RET> for more, q to quit, c to continue without paging--
#40 0x0000558c79323f7d in Fprogn (body=0x0) at ../../emacs/src/eval.c:462
#41 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#42 0x0000558c793252af in Funwind_protect (args=0x558c8106a583)
    at ../../emacs/src/lisp.h:1444
#43 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#44 0x0000558c7932500d in Fprogn (body=0x0) at ../../emacs/src/eval.c:462
#45 Flet (args=0x558c8106a5d3) at ../../emacs/src/eval.c:987
#46 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#47 0x0000558c79324255 in Fprogn (body=0x0) at ../../emacs/src/eval.c:462
#48 funcall_lambda (fun=0x558c8106a683, nargs=1, arg_vector=0x7fff2cae72a0)
    at ../../emacs/src/eval.c:3061
#49 0x0000558c793237a3 in apply_lambda
    (fun=0x558c8106a693, args=<optimized out>, count=count@entry=20)
    at ../../emacs/src/eval.c:2927
#50 0x0000558c79323a73 in eval_sub (form=<optimized out>) at ../../emacs/src/eval.c:2349
#51 0x0000558c793251ff in Fprogn (body=0x0) at ../../emacs/src/eval.c:462
#52 FletX (args=0x558c81068693) at ../../emacs/src/eval.c:919
#53 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#54 0x0000558c793243bd in Fprogn (body=0x0) at ../../emacs/src/eval.c:462
#55 Fif (args=<optimized out>) at ../../emacs/src/eval.c:418
#56 Fif (args=<optimized out>) at ../../emacs/src/eval.c:404
#57 0x0000558c79323be9 in eval_sub (form=<optimized out>) at ../../emacs/src/lisp.h:2110
#58 0x0000558c79324255 in Fprogn (body=0x0) at ../../emacs/src/eval.c:462
#59 funcall_lambda (fun=0x558c81068153, nargs=5, arg_vector=0x7fff2cae7668)
    at ../../emacs/src/eval.c:3061
#60 0x0000558c79321d47 in Ffuncall (nargs=6, args=0x7fff2cae7660)
    at ../../emacs/src/eval.c:2809
#61 0x0000558c79322072 in Fapply (nargs=3, args=0x7fff2cae7778)
    at ../../emacs/src/eval.c:2425
#62 0x0000558c79321de3 in Ffuncall (nargs=4, args=args@entry=0x7fff2cae7770)
    at ../../emacs/src/lisp.h:2110
#63 0x0000558c79355c48 in exec_byte_code
    (bytestr=<optimized out>, vector=<optimized out>, maxdepth=<optimized out>, args_template--Type <RET> for more, q to quit, c to continue without paging--
=<optimized out>, nargs=<optimized out>, args=<optimized out>)
    at ../../emacs/src/bytecode.c:633
#64 0x0000558c79321d47 in Ffuncall (nargs=5, args=args@entry=0x7fff2cae7a70)
    at ../../emacs/src/eval.c:2809
#65 0x0000558c79355c48 in exec_byte_code
    (bytestr=<optimized out>, vector=<optimized out>, maxdepth=<optimized out>, args_template=<optimized out>, nargs=<optimized out>, args=<optimized out>)
    at ../../emacs/src/bytecode.c:633
#66 0x0000558c79321d47 in Ffuncall (nargs=2, args=args@entry=0x7fff2cae7e68)
    at ../../emacs/src/eval.c:2809
#67 0x0000558c79355c48 in exec_byte_code
    (bytestr=<optimized out>, vector=<optimized out>, maxdepth=<optimized out>, args_template=<optimized out>, nargs=<optimized out>, args=<optimized out>)
    at ../../emacs/src/bytecode.c:633
#68 0x0000558c79321d47 in Ffuncall (nargs=nargs@entry=2, args=args@entry=0x7fff2cae83e8)
    at ../../emacs/src/eval.c:2809
#69 0x0000558c7931e7f1 in Ffuncall_interactively (nargs=2, args=0x7fff2cae83e8)
    at ../../emacs/src/callint.c:254
#70 0x0000558c79321de3 in Ffuncall (nargs=3, args=0x7fff2cae83e0)
    at ../../emacs/src/lisp.h:2110
#71 0x0000558c79322133 in Fapply (nargs=nargs@entry=3, args=args@entry=0x7fff2cae83e0)
    at ../../emacs/src/eval.c:2382
#72 0x0000558c7931fd0a in Fcall_interactively
    (function=0x29e960243620, record_flag=0x0, keys=0x558c8952c9b5)
    at ../../emacs/src/lisp.h:1033
#73 0x0000558c79321de3 in Ffuncall (nargs=4, args=args@entry=0x7fff2cae84d8)
    at ../../emacs/src/lisp.h:2110
#74 0x0000558c79355c48 in exec_byte_code
    (bytestr=<optimized out>, vector=<optimized out>, maxdepth=<optimized out>, args_template=<optimized out>, nargs=<optimized out>, args=<optimized out>)
    at ../../emacs/src/bytecode.c:633
#75 0x0000558c79321d47 in Ffuncall (nargs=2, args=0x7fff2cae8870)
    at ../../emacs/src/eval.c:2809
--Type <RET> for more, q to quit, c to continue without paging--
#76 0x0000558c79321e8a in call1 (fn=fn@entry=0x3d50, arg1=<optimized out>)
    at ../../emacs/src/eval.c:2655
#77 0x0000558c792bbec8 in command_loop_1 () at ../../emacs/src/lisp.h:1033
#78 0x0000558c793210f7 in internal_condition_case
    (bfun=bfun@entry=0x558c792bbaf0 <command_loop_1>, handlers=handlers@entry=0x90, hfun=hfun@entry=0x558c792b2d50 <cmd_error>) at ../../emacs/src/eval.c:1356
#79 0x0000558c792adbb4 in command_loop_2 (ignore=ignore@entry=0x0)
    at ../../emacs/src/lisp.h:1033
#80 0x0000558c79321051 in internal_catch
    (tag=tag@entry=0xcc60, func=func@entry=0x558c792adb90 <command_loop_2>, arg=arg@entry=0x0) at ../../emacs/src/eval.c:1117
#81 0x0000558c792adb5b in command_loop () at ../../emacs/src/lisp.h:1033
#82 0x0000558c792b2966 in recursive_edit_1 () at ../../emacs/src/keyboard.c:714
#83 0x0000558c792b2c92 in Frecursive_edit () at ../../emacs/src/keyboard.c:786
#84 0x0000558c791e4ae6 in main (argc=1, argv=<optimized out>)
    at ../../emacs/src/emacs.c:2062

And this is the Lisp backtrace:

(gdb) xbacktrace
"format-mode-line" (0x2cae6410)
"mini-modeline--multi-lr-render" (0x2cae6538)
"setq" (0x2cae6618)
"if" (0x2cae66e8)
"progn" (0x2cae67a8)
"if" (0x2cae6858)
"let" (0x2cae6998)
"save-current-buffer" (0x2cae6a78)
"if" (0x2cae6b48)
"progn" (0x2cae6c08)
"unwind-protect" (0x2cae6cd8)
"let*" (0x2cae6dd8)
"condition-case" (0x2cae6ef8)
"progn" (0x2cae6fb8)
"unwind-protect" (0x2cae7088)
"let" (0x2cae71a8)
"mini-modeline-display" (0x2cae72a0)
"let*" (0x2cae7438)
"if" (0x2cae7508)
"mini-modeline--reroute-msg" (0x2cae7668)
"apply" (0x2cae7778)
"message" (0x2cae7a78)
"Info-index-next" (0x2cae7e70)
"Info-index" (0x2cae83f0)
"funcall-interactively" (0x2cae83e8)
"call-interactively" (0x2cae84e0)
"command-execute" (0x2cae8878)
oscarfv commented 4 years ago

Filed http://debbugs.gnu.org/cgi/bugreport.cgi?bug=42220 with some more info.

Eli-Zaretskii commented 4 years ago

Thanks, but the backtrace alone is not enough: it doesn't convey enough information to understand how this happened.

It appears that display_count_lines was called with the value of start_byte at the gap point, and I don't think I understand how this happened. If you can figure out how it happened, please tell more details.

Alternatively, a recipe starting from emacs -Q is needed to understand what is going on and come up with a solution. Please post that information in the bug report you filed.

Eli-Zaretskii commented 4 years ago

Also, the value of count (681760) is greater than its value at function entry (681823), but the value of start_byte didn't change. How could that happen? Perhaps the values displayed by GDB are not reliable at all, given that this is an optimized build?

Eli-Zaretskii commented 4 years ago

I'm confused by this part of the recipe:

         Press i (Info-index) and select the first item.

Pressing i doesn't display any items, it prompts for a subject, so how can one select the first item? Does Ivy (or something else) modify how Info-index works?

kiennq commented 4 years ago

Here is the repo steps with emacs -Q, assume you've already have mini-modeline on your load-path.

  1. M-x package-initialize
  2. M-x mini-modeline-mode
  3. M-x info, open Emacs node
  4. i and press up/down arrow and select a subject with Enter
  5. Repeat step 4 a few times, you can observer Emacs is hang
Eli-Zaretskii commented 4 years ago

Thanks.

You are crazy^H^H^H^H^Hoverly optimistic calling format-mode-line (which exposes the display-engine code to Lisp) from an advice that wraps message (which is itself an entry point to redisplay). But the solution will be ready soon, stay tuned.

Eli-Zaretskii commented 4 years ago

Thanks, should be fixed now.

kiennq commented 4 years ago

Does that mean if I not call format-mode-line from an advice wraps message, the issue should be resolved? I've tried that before https://github.com/kiennq/emacs-mini-modeline/blob/bug/no-redisplay-immediately/mini-modeline.el but it seems doesn't working

Eli-Zaretskii commented 4 years ago

I'm not familiar with the code enough to answer that. The issue is that format-mode-line is called as side effect of calling message, when the buffer's restriction was changed, but the buffer was not yet redisplayed after that, so the window's starting point is incorrect (outside of the restriction).