Subject: 27.1.50; Assertion failure in window_box_height

From: martin rudalics <[email-masked]>
Date: Sat, 9 Jan 2021 10:33:02 +0100

With the current release version running emacs -Q, evaluating

(progn
   (tab-line-mode)
   (split-window (split-window) nil t)
   (split-window)
   (split-window (split-window nil nil t) nil t))

and resizing the frame by dragging its lower right corner with the mouse
to very small rectangles I can trigger the following assertion failure:

../../src/xdisp.c:1170: Emacs fatal error: assertion failed: height >= 0

The backtrace

(gdb) bt
#0  0x000000000063e1b3 in terminate_due_to_signal (sig=6, backtrace_limit=2147483647) at ../../src/emacs.c:379
#1  0x000000000075894d in die (msg=0x96109c "height >= 0", file=0x961032 "../../src/xdisp.c", line=1170) at ../../src/alloc.c:7240
#2  0x0000000000458382 in window_box_height (w=0x149d100) at ../../src/xdisp.c:1170
#3  0x00000000004212da in required_matrix_height (w=0x149d100) at ../../src/dispnew.c:1740
#4  0x000000000042147d in allocate_matrices_for_window_redisplay (w=0x149d100) at ../../src/dispnew.c:1806
#5  0x00000000004220ed in adjust_frame_glyphs_for_window_redisplay (f=0x1422c60) at ../../src/dispnew.c:2123
#6  0x0000000000421547 in adjust_frame_glyphs (f=0x1422c60) at ../../src/dispnew.c:1827
#7  0x00000000004fd9f9 in resize_mini_window_apply (w=0x149d100, delta=-72) at ../../src/window.c:5216
#8  0x00000000004fdb98 in grow_mini_window (w=0x149d100, delta=18) at ../../src/window.c:5251
#9  0x0000000000481952 in resize_mini_window (w=0x149d100, exact_p=false) at ../../src/xdisp.c:11715
#10 0x0000000000480969 in display_echo_area_1 (a1=21614848, a2=XIL(0)) at ../../src/xdisp.c:11557
#11 0x000000000047fc66 in with_echo_area_buffer (w=0x149d100, which=1, fn=0x480933 <display_echo_area_1>, a1=21614848, a2=XIL(0)) at ../../src/xdisp.c:11327
#12 0x00000000004808de in display_echo_area (w=0x149d100) at ../../src/xdisp.c:11523
#13 0x0000000000483022 in echo_area_display (update_frame_p=false) at ../../src/xdisp.c:12038
#14 0x00000000004898c5 in redisplay_internal () at ../../src/xdisp.c:15456
#15 0x000000000048b5e3 in redisplay_preserve_echo_area (from_where=11) at ../../src/xdisp.c:16125
#16 0x000000000084ed6c in wait_reading_process_output (time_limit=30, nsecs=0, read_kbd=-1, do_display=true, wait_for_cell=XIL(0), wait_proc=0x0, just_wait_proc=0) at ../../src/process.c:5482
#17 0x000000000042cbb2 in sit_for (timeout=make_fixnum(30), reading=true, display_option=1) at ../../src/dispnew.c:6064
#18 0x000000000064fe21 in read_char (commandflag=1, map=XIL(0x10878b3), prev_event=XIL(0), used_mouse_menu=0x7fffffffe10f, end_time=0x0) at ../../src/keyboard.c:2738
#19 0x00000000006621ef in read_key_sequence (keybuf=0x7fffffffe2a0, prompt=XIL(0), dont_downcase_last=false, can_return_switch_frame=true, fix_current_buffer=true, prevent_redisplay=false) at ../../src/keyboard.c:9554
#20 0x000000000064b774 in command_loop_1 () at ../../src/keyboard.c:1350
#21 0x00000000007afe18 in internal_condition_case (bfun=0x64b2f8 <command_loop_1>, handlers=XIL(0x90), hfun=0x64a907 <cmd_error>) at ../../src/eval.c:1356
#22 0x000000000064aedd in command_loop_2 (ignore=XIL(0)) at ../../src/keyboard.c:1091
#23 0x00000000007af2cc in internal_catch (tag=XIL(0xd110), func=0x64aeb0 <command_loop_2>, arg=XIL(0)) at ../../src/eval.c:1117
#24 0x000000000064ae7b in command_loop () at ../../src/keyboard.c:1070
#25 0x000000000064a3ee in recursive_edit_1 () at ../../src/keyboard.c:714
#26 0x000000000064a5e6 in Frecursive_edit () at ../../src/keyboard.c:786
#27 0x00000000006409ef in main (argc=4, argv=0x7fffffffe798) at ../../src/emacs.c:2066

Lisp Backtrace:
"redisplay_internal (C function)" (0x0)
(gdb) frame 2
#2  0x0000000000458382 in window_box_height (w=0x149d100) at ../../src/xdisp.c:1170
1170	  eassert (height >= 0);
(gdb) p height
$2 = -54
(gdb)

indicates that the total height of one of the windows dropped to -54
pixels.  The problematic code is in 'window-sizable' which is not
prepared for the case that window sizes can drop below their minimum
size, something which can happen when a frame with many windows is made
very small.  I propose the attached patch to fix this.  OK to install?

martin

In GNU Emacs 27.1.90 (build 2, x86_64-pc-linux-gnu, GTK+ Version 3.24.5)
  of 2021-01-09 built on restno
Repository revision: 74d18957b898e687dcc07ba86559367c8d8ba482
Repository branch: emacs-27
Windowing system distributor 'The X.Org Foundation', version 11.0.12004000
System Description: Debian GNU/Linux 10 (buster)

Recent messages:
For information about GNU Emacs and the GNU system, type C-h C-a.

Configured using:
  'configure --with-gif=ifavailable --with-tiff=ifavailable
  --with-gnutls=no --without-pop --enable-gcc-warnings=warn-only
  --enable-checking=yes --enable-check-lisp-object-type=yes 'CFLAGS=-O0
  -g3 -no-pie''

Configured features:
XPM JPEG GIF PNG SOUND DBUS GSETTINGS GLIB NOTIFY INOTIFY LIBSELINUX
FREETYPE HARFBUZZ XFT ZLIB TOOLKIT_SCROLL_BARS GTK3 X11 XDBE XIM MODULES
THREADS PDUMPER

Important settings:
   value of $LANG: de_AT.UTF-8
   value of $XMODIFIERS: @im=ibus
   locale-coding-system: utf-8-unix

Major mode: Lisp Interaction

Minor modes in effect:
   tooltip-mode: t
   global-eldoc-mode: t
   eldoc-mode: t
   electric-indent-mode: t
   mouse-wheel-mode: t
   tool-bar-mode: t
   menu-bar-mode: t
   file-name-shadow-mode: t
   global-font-lock-mode: t
   font-lock-mode: t
   blink-cursor-mode: t
   auto-composition-mode: t
   auto-encryption-mode: t
   auto-compression-mode: t
   line-number-mode: t
   transient-mark-mode: t

Load-path shadows:
None found.

Features:
(shadow sort mail-extr emacsbug message rmc puny dired dired-loaddefs
format-spec rfc822 mml easymenu mml-sec password-cache epa derived epg
epg-config gnus-util rmail rmail-loaddefs text-property-search time-date
subr-x seq byte-opt gv bytecomp byte-compile cconv mm-decode mm-bodies
mm-encode mail-parse rfc2231 mailabbrev gmm-utils mailheader cl-loaddefs
cl-lib sendmail rfc2047 rfc2045 ietf-drums mm-util mail-prsvr mail-utils
tooltip eldoc electric uniquify ediff-hook vc-hooks lisp-float-type
mwheel term/x-win x-win term/common-win x-dnd tool-bar dnd fontset image
regexp-opt fringe tabulated-list replace newcomment text-mode elisp-mode
lisp-mode prog-mode register page tab-bar menu-bar rfn-eshadow isearch
timer select scroll-bar mouse jit-lock font-lock syntax facemenu
font-core term/tty-colors frame minibuffer cl-generic cham georgian
utf-8-lang misc-lang vietnamese tibetan thai tai-viet lao korean
japanese eucjp-ms cp51932 hebrew greek romanian slovak czech european
ethiopic indian cyrillic chinese composite charscript charprop
case-table epa-hook jka-cmpr-hook help simple abbrev obarray
cl-preloaded nadvice loaddefs button faces cus-face macroexp files
text-properties overlay sha1 md5 base64 format env code-pages mule
custom widget hashtable-print-readable backquote threads dbusbind
inotify dynamic-setting system-font-setting font-render-setting
move-toolbar gtk x-toolkit x multi-tty make-network-process emacs)

Memory information:
((conses 16 43920 4887)
  (symbols 48 5978 1)
  (strings 32 15451 1816)
  (string-bytes 1 503632)
  (vectors 16 9266)
  (vector-slots 8 124434 11300)
  (floats 8 20 29)
  (intervals 56 195 0)
  (buffers 1000 11))
--- a/lisp/window.el
+++ b/lisp/window.el
@@ -1716,9 +1716,11 @@ window-sizable
   (setq window (window-normalize-window window))
   (cond
    ((< delta 0)
-    (max (- (window-min-size window horizontal ignore pixelwise)
-	    (window-size window horizontal pixelwise))
-	 delta))
+    (let ((min-size (window-min-size window horizontal ignore pixelwise))
+          (size (window-size window horizontal pixelwise)))
+      (if (<= size min-size)
+          0
+        (max (- min-size size) delta))))
    ((> delta 0)
     (if (window-size-fixed-p window horizontal ignore)
 	0