Bug: resizing doesn't work properly in Windows Terminal #1972

Closed
opened 2026-01-30 22:43:10 +00:00 by claunia · 16 comments
Owner

Originally created by @Shorotshishir on GitHub (Jun 23, 2019).

Originally assigned to: @zadjii-msft on GitHub.

Environment

Windows build number: [Version 10.0.18362.175]
Windows Terminal version (0.2.1715.0):

Steps to reproduce

open any terminal (PowerShell/cmd/wsl). type any command (e.g. dir, ver, uname) and enter. resize the app window to the minimum and gradually enlarge the window.

Expected behavior

information should stay the same. shouldn't break and should render all the characters like below

powershell0
wsl0
cmd0

Actual behavior

breaks apart and doesn't render properly

powershell1
wsl1
cmd1

Originally created by @Shorotshishir on GitHub (Jun 23, 2019). Originally assigned to: @zadjii-msft on GitHub. <!-- This bug tracker is monitored by Windows Terminal development team and other technical folks. **Important: When reporting BSODs or security issues, DO NOT attach memory dumps, logs, or traces to Github issues**. Instead, send dumps/traces to secure@microsoft.com, referencing this GitHub issue. Please use this form and describe your issue, concisely but precisely, with as much detail as possible. --> # Environment ```none Windows build number: [Version 10.0.18362.175] Windows Terminal version (0.2.1715.0): ``` # Steps to reproduce open any terminal (PowerShell/cmd/wsl). type any command (e.g. `dir`, `ver`, `uname`) and enter. resize the app window to the minimum and gradually enlarge the window. # Expected behavior information should stay the same. shouldn't break and should render all the characters like below ![powershell0](https://user-images.githubusercontent.com/16465879/59974376-5a759380-95cd-11e9-9543-18d14bdfb7a5.png) ![wsl0](https://user-images.githubusercontent.com/16465879/59974377-5a759380-95cd-11e9-9c2c-1f7fbc5d2cc0.png) ![cmd0](https://user-images.githubusercontent.com/16465879/59974378-5b0e2a00-95cd-11e9-8037-f6b46569ed3f.png) # Actual behavior <!-- What's actually happening? --> breaks apart and doesn't render properly ![powershell1](https://user-images.githubusercontent.com/16465879/59974443-22bb1b80-95ce-11e9-8ccb-9191ef306526.png) ![wsl1](https://user-images.githubusercontent.com/16465879/59974444-22bb1b80-95ce-11e9-9bf7-0a4f96fe3827.png) ![cmd1](https://user-images.githubusercontent.com/16465879/59974442-22228500-95ce-11e9-92cd-0649f9f85a45.png)
Author
Owner

@JushBJJ commented on GitHub (Jun 23, 2019):

Kinda like #1433 but this time, its with all command lines.

@JushBJJ commented on GitHub (Jun 23, 2019): Kinda like #1433 but this time, its with all command lines.
Author
Owner

@HBelusca commented on GitHub (Jun 24, 2019):

Here is a screen movie to illustrate the described problems above (note how the scrollbar modifies):
2019-06-24_14-16-55

Auxiliary observations:

  • VtPipeTerm.exe misbehaves as well when resizing either of the background host window, or the front window.
  • OpenConsole.exe does not have this problem, but acts very slowly when trying to resize the window (why?)
@HBelusca commented on GitHub (Jun 24, 2019): Here is a screen movie to illustrate the described problems above (note how the scrollbar modifies): ![2019-06-24_14-16-55](https://user-images.githubusercontent.com/1969829/60018458-af77df00-968b-11e9-94b8-f3d3afa5ffd1.gif) Auxiliary observations: - VtPipeTerm.exe misbehaves as well when resizing either of the background host window, or the front window. - OpenConsole.exe does not have this problem, but acts very slowly when trying to resize the window (why?)
Author
Owner

@DHowett-MSFT commented on GitHub (Jun 24, 2019):

OpenConsole in debug or in release?

If vtpipeterm is hitting it too, that's definitely a conpty issue.

@DHowett-MSFT commented on GitHub (Jun 24, 2019): OpenConsole in debug or in release? If vtpipeterm is hitting it too, that's definitely a conpty issue.
Author
Owner

@HBelusca commented on GitHub (Jun 24, 2019):

(I should have added that I was testing with master a5f31f77 .

OpenConsole in debug or in release?

OK the slowness was just in debug mode; I recompiled and re-tested in release mode and it's back to the usual speed ("fast").

If vtpipeterm is hitting it too, that's definitely a conpty issue.

For this my interpretation of what's going on may be erroneous because I'm also looking at the background host window, while the front window only allows resizing but not scrolling. See the animation below.
2019-06-24_19-36-51

@HBelusca commented on GitHub (Jun 24, 2019): (I should have added that I was testing with master a5f31f77 . > OpenConsole in debug or in release? OK the slowness was just in debug mode; I recompiled and re-tested in release mode and it's back to the usual speed ("fast"). > If vtpipeterm is hitting it too, that's definitely a conpty issue. For this my interpretation of what's going on may be erroneous because I'm also looking at the background host window, while the front window only allows resizing but not scrolling. See the animation below. ![2019-06-24_19-36-51](https://user-images.githubusercontent.com/1969829/60039816-ea900780-96b7-11e9-803b-4281067d53fb.gif)
Author
Owner

@parkovski commented on GitHub (Jun 29, 2019):

I think I found one resize bug. A ConPTY sends two WINDOW_BUFFER_SIZE_EVENT messages when the window is restored from maximize, but the first one has the wrong size (not sure of the internals of this, but it appears in conhost/tmux/pwsh, alacritty/pwsh, and Windows Terminal).

Run this program as conevents -es in conhost and a different terminal to see the difference; maximize and restore the window. For example, restoring the WinTerm window reports 119 x 46 in the WINDOW_BUFFER_SIZE_EVENT message, but GetConsoleScreenBufferInfo returns the correct value 119 x 32.

@parkovski commented on GitHub (Jun 29, 2019): I think I found one resize bug. A ConPTY sends two `WINDOW_BUFFER_SIZE_EVENT` messages when the window is restored from maximize, but the first one has the wrong size (not sure of the internals of this, but it appears in conhost/tmux/pwsh, alacritty/pwsh, and Windows Terminal). Run [this program](https://github.com/parkovski/conutils/blob/master/conevents.cpp) as `conevents -es` in conhost and a different terminal to see the difference; maximize and restore the window. For example, restoring the WinTerm window reports `119 x 46` in the `WINDOW_BUFFER_SIZE_EVENT` message, but `GetConsoleScreenBufferInfo` returns the correct value `119 x 32`.
Author
Owner

@zadjii-msft commented on GitHub (Jul 1, 2019):

I'm moving the conpty maximize thing to its own separate issue, #1765.

This is definitely a conpty bug, but I'm not really sure the right way to fix it. If I had to guess, when we repaint the buffer due to a resize, we're painting more or less lines than the terminal expects, which is causing the old viewport contents to slide into the scrollback.

This is pretty bad and I really want to find some time to fix it.

@zadjii-msft commented on GitHub (Jul 1, 2019): I'm moving the conpty maximize thing to its own separate issue, #1765. This is definitely a conpty bug, but I'm not really sure the right way to fix it. If I had to guess, when we repaint the buffer due to a resize, we're painting more or less lines than the terminal expects, which is causing the old viewport contents to slide into the scrollback. This is pretty bad and I really want to find some time to fix it.
Author
Owner

@mcpiroman commented on GitHub (Jul 4, 2019):

My best bet to fix or at least simplify this is to not emit new resized buffer from conhost, but instead run the resize on terminall's buffer too. This way both buffers should be the same and additionally terminal will have access to context of the resize, which would e.g. enable us to track selection transform (#1368), and maybe to fix the bugs above too.

It should be at least as (in)efficient as it is now (especially over network), because despite doubled work, conhost wouldn't need to transfer the buffer back to terminal, which seems comparatively costly.

It could eventually be futher optimizied so thet when user drags window the resize runs only on terminal's buffer and is reported to conhost only when the user releases LMB (but this would reqiure to freeze sth like the conhost does when scrolling?).

And since you want to support existing 3-party terminals - they handle resize themselfs. So while the present solution should work, it will be unusual to them and may cause some troubles such as we have now (even if we resolve them on terminal side).

And finally, in passthrough mode terminal would have to resize the buffer itself.

@mcpiroman commented on GitHub (Jul 4, 2019): My best bet to fix or at least simplify this is to not emit new resized buffer from conhost, but instead run the resize on terminall's buffer too. This way both buffers should be the same and additionally terminal will have access to context of the resize, which would e.g. enable us to track selection transform (#1368), and maybe to fix the bugs above too. It should be at least as (in)efficient as it is now (especially over network), because despite doubled work, conhost wouldn't need to transfer the buffer back to terminal, which seems comparatively costly. It could eventually be futher optimizied so thet when user drags window the resize runs only on terminal's buffer and is reported to conhost only when the user releases LMB (but this would reqiure to freeze sth like the conhost does when scrolling?). And since you want to support existing 3-party terminals - they handle resize themselfs. So while the present solution should work, it will be unusual to them and may cause some troubles such as we have now (even if we resolve them on terminal side). And finally, in passthrough mode terminal would have to resize the buffer itself.
Author
Owner

@zadjii-msft commented on GitHub (Jul 29, 2019):

Currently, the terminal does also resize it's buffer at the same time as when it requests a resize with the conpty. We're using an older resize algorithim right now in the Terminal, that only does a "traditional resize". The terminal doesn't try to reflow text in its buffer at all (like conhost does). The result of this is that when there's text outside the viewport in the terminal, the rows of text are going to get clipped to the width of the terminal. If you resize down to 5 chars wide, every row is going to only have 5 chars in it.

Right now, when the console (conpty) resizes, it might reflow text, to try and maintain line wrapping. If conpty didn't re-emit the state of its buffer after the resize, then a terminal that didn't support resize with reflow would be in a torn state with the pseudoconsole.

What we should be doing is reusing conhost's ResizeWithReflow in the terminal. It's a method that's a little tightly tied to conhost itself currently, which is why we haven't had a chance to pull it out quite yet.

Now, there might actually be a better way to handle resizes that aren't so chatty. There's probably a class of resize operations that don't need to force a repaint. We might even want to experiment with having conpty disable resize with reflow entirely, though that might be a strictly worse experience (as text that's cut off from the conpty will be lost forever, and when it's repainted, the terminal will lose it too).

Part of the oddity of all this is due to the fact that conpty has to maintain its own buffer state - passthrough mode might not have so much difficulty with this scenario.

We could almost certainly have a mode for the terminal where it doesn't resize until the drag handle is released. That deserves its own issue (#2140)

@zadjii-msft commented on GitHub (Jul 29, 2019): Currently, the terminal _does_ also resize it's buffer at the same time as when it requests a resize with the conpty. We're using an older resize algorithim right now in the Terminal, that only does a "traditional resize". The terminal doesn't try to reflow text in its buffer at all (like conhost does). The result of this is that when there's text outside the viewport in the terminal, the rows of text are going to get clipped to the width of the terminal. If you resize down to 5 chars wide, _every_ row is going to only have 5 chars in it. Right now, when the console (conpty) resizes, it might reflow text, to try and maintain line wrapping. If conpty didn't re-emit the state of its buffer after the resize, then a terminal that didn't support resize with reflow would be in a torn state with the pseudoconsole. What we _should_ be doing is reusing conhost's `ResizeWithReflow` in the terminal. It's a method that's a little tightly tied to conhost itself currently, which is why we haven't had a chance to pull it out quite yet. Now, there might actually be a better way to handle resizes that aren't so chatty. There's probably a class of resize operations that don't need to force a repaint. We might even want to experiment with having conpty disable resize with reflow entirely, though that might be a strictly worse experience (as text that's cut off from the conpty will be lost forever, and when it's repainted, the terminal will lose it too). Part of the oddity of all this is due to the fact that conpty has to maintain its own buffer state - passthrough mode might not have so much difficulty with this scenario. We could almost certainly have a mode for the terminal where it doesn't resize until the drag handle is released. That deserves its own issue (#2140)
Author
Owner

@mcpiroman commented on GitHub (Jul 30, 2019):

Couldn't we just ResizeWithOverflow on both conhost and terminal, without any rendering and repainting in the process (VT, not graphical rendering ofc)? If the input (buffer) is the same and we run the same operation, then output should also be the same.

@mcpiroman commented on GitHub (Jul 30, 2019): Couldn't we just `ResizeWithOverflow` on both conhost and terminal, without any rendering and repainting in the process (VT, not graphical rendering ofc)? If the input (buffer) is the same and we run the same operation, then output should also be the same.
Author
Owner

@zadjii-msft commented on GitHub (Jul 30, 2019):

Part of the problem is that we don't know the terminal connected to conpty is the Windows Terminal. If it was something like xterm, and conpty reflowed its buffer, but xterm didn't, then the terminal and the conpty buffers will be in a torn state.

@zadjii-msft commented on GitHub (Jul 30, 2019): Part of the problem is that we don't _know_ the terminal connected to conpty is the Windows Terminal. If it was something like xterm, and conpty reflowed its buffer, but xterm didn't, then the terminal and the conpty buffers will be in a torn state.
Author
Owner

@mcpiroman commented on GitHub (Jul 30, 2019):

But is it appropriate for a terminal not to resize it's buffer, and even more, resize it the same way we do? I don't suppose there is a global standard for this, but I don't see any other way this could be done.

@mcpiroman commented on GitHub (Jul 30, 2019): But is it appropriate for a terminal not to resize it's buffer, and even more, resize it the same way we do? I don't suppose there is a global standard for this, but I don't see any other way this could be done.
Author
Owner

@jjoos commented on GitHub (Oct 6, 2019):

If I set "historySize" : 90000, resizing will be broken vs "historySize" : 9000, it will work fine. Version: 0.5.2762.0

@jjoos commented on GitHub (Oct 6, 2019): If I set `"historySize" : 90000,` resizing will be broken vs `"historySize" : 9000,` it will work fine. Version: 0.5.2762.0
Author
Owner

@danielskowronski commented on GitHub (Oct 7, 2019):

If I set "historySize" : 90000, resizing will be broken vs "historySize" : 9000, it will work fine. Version: 0.5.2762.0

OMG, it really works! version: 0.5.2681.0

@danielskowronski commented on GitHub (Oct 7, 2019): > If I set `"historySize" : 90000,` resizing will be broken vs `"historySize" : 9000,` it will work fine. Version: 0.5.2762.0 OMG, it really works! version: 0.5.2681.0
Author
Owner

@zadjii-msft commented on GitHub (Nov 21, 2019):

Another repro from another thread:

Steps to reproduce

  1. SSH to a linux. I tired centos7.
  2. Maximize the windows terminal window.
  3. Enter a command which print something to the terminal. for example "ls".
  4. Restore down the window.
  5. keep pressing enter to create new lines.

Expected behavior

Nothing happens.

Actual behavior

Previous message is shown again.

bugreportjpg

@zadjii-msft commented on GitHub (Nov 21, 2019): Another repro from another thread: > # Steps to reproduce > 1. SSH to a linux. I tired centos7. > 2. Maximize the windows terminal window. > 3. Enter a command which print something to the terminal. for example "ls". > 4. Restore down the window. > 5. keep pressing enter to create new lines. > > # Expected behavior > > Nothing happens. > # Actual behavior > > Previous message is shown again. > > ![bugreportjpg](https://user-images.githubusercontent.com/36209665/69176554-d54fc580-0afd-11ea-9f72-e0643d87b989.jpg)
Author
Owner

@espresso3389 commented on GitHub (Dec 16, 2019):

If I set "historySize" : 90000, resizing will be broken vs "historySize" : 9000, it will work fine. Version: 0.5.2762.0

It seems that the historySize limit seems 32K - possible_screen_rows. So if your terminal can have 120 lines at most, historySize should be 32648 or less. So practically, the value around 32600 can be good enough; 9999 is too small for me anyway.

@espresso3389 commented on GitHub (Dec 16, 2019): > If I set `"historySize" : 90000,` resizing will be broken vs `"historySize" : 9000,` it will work fine. Version: 0.5.2762.0 It seems that the `historySize` limit seems `32K - possible_screen_rows`. So if your terminal can have 120 lines at most, `historySize` should be 32648 or less. So practically, the value around 32600 can be good enough; 9999 is too small for me anyway.
Author
Owner

@lo-w commented on GitHub (Mar 16, 2020):

@jjoos thanks, it works, the max num seems 32 723,
"historySize": 32723,

@lo-w commented on GitHub (Mar 16, 2020): @jjoos thanks, it works, the max num seems 32 723, "historySize": 32723,
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: starred/terminal#1972