Bug 71935

Summary: weston-terminal: artifacts (lingering character glyphs) when scrolling in vim (ncurses)
Product: Wayland Reporter: emiettin
Component: westonAssignee: Wayland bug list <wayland-bugs>
Status: RESOLVED FIXED QA Contact:
Severity: minor    
Priority: medium    
Version: 1.3.0   
Hardware: x86-64 (AMD64)   
OS: Linux (All)   
Whiteboard:
i915 platform: i915 features:
Attachments: screenshot exhibiting bugged behavior
patch to fix the 'clear entire screen' escape sequence handler
more sane version of the previously proposed patch

Description emiettin 2013-11-23 10:25:06 UTC
Created attachment 89677 [details]
screenshot exhibiting bugged behavior

On weston-git 1.3.1 (commit dcfff55ef3209cb089aae0906a6235717409a81c, occurs on some earlier revisions as well), steps to reproduce:

1. launch weston-terminal
2. open a text file with more lines than the current terminal window can display
3. use the motion 'G' to go to the end of the buffer (or just about any other motion involving scrolling)

result: the editing display (not the underlying vim editing buffer) becomes corrupted.

The attached screenshot shows almost completely garbled output in vim (the original source file in question is syntactically valid); this was achieved by spamming some vim scrolling motions (such as '20 j' '30 k' '60 j' etc etc). The degree of corruptness varies; the display can go from completely messed up to completely fine and vice versa when using a vim scroll motion. 

I suppose it could have something to do with the addition of the scrollback feature (to weston-terminal itself), since the bug doesn't occur on one that doesn't yet include that feature (e.g. the one packaged by arch linux, labeled 1.3.1-1).
Comment 1 Kristian Høgsberg 2013-11-23 17:05:51 UTC
I just committed this on git master:

commit dcfff55ef3209cb089aae0906a6235717409a81c
Author: Kristian Høgsberg <krh@bitplanet.net>
Date:   Fri Nov 22 22:43:20 2013 -0800

    terminal: Init tab ruler after setting terminal->width
    
    terminal_init_tabs() needs an accurate terminal->width to be able
    to correctly initialize the tab ruler.

Does that fix it?
Comment 2 emiettin 2013-11-23 23:59:05 UTC
Nope, sorry.

Further testing suggests that the problem was indeed introduced with commit 14f39b290b764a84a6e12039d33e7a93a47329de (the one with all the scrollback stuff), since it doesn't occur when using the previous one (5d380c3c5f20de5ba15838a3b73632cc0993743e).

The terminal.c diff isn't exactly trivial between these two revisions.. I'll see if I can carry out some more tests later.
Comment 3 emiettin 2013-11-24 11:07:16 UTC
Created attachment 89708 [details] [review]
patch to fix the 'clear entire screen' escape sequence handler

Reverts the "\033[2J" handling block to a working implementation from a previous revision.
Comment 4 emiettin 2013-11-24 11:20:56 UTC
Comment on attachment 89708 [details] [review]
patch to fix the 'clear entire screen' escape sequence handler

--- weston_a/clients/terminal.c 2013-11-24 13:18:57.020992332 +0200
+++ weston_b/clients/terminal.c 2013-11-24 13:19:28.517658360 +0200
@@ -1415,8 +1415,12 @@
                        }
                } else if (args[0] == 2) {
                        /* Clear screen by scrolling contents out */
-                       terminal_scroll_buffer(terminal,
-                                              terminal->end - terminal->start);
+                       for (i = 0; i < terminal->height; i++) {
+                               memset(terminal_get_row(terminal, i),
+                                   0, terminal->data_pitch);
+                               attr_init(terminal_get_attr_row(terminal, i),
+                                   terminal->curr_attr, terminal->width);
+                       }
                }
                break;
        case 'K':    /* EL */
Comment 5 emiettin 2013-11-24 11:21:37 UTC
Comment on attachment 89708 [details] [review]
patch to fix the 'clear entire screen' escape sequence handler

--- weston_a/clients/terminal.c 2013-11-24 13:18:57.020992332 +0200
+++ weston_b/clients/terminal.c 2013-11-24 13:19:28.517658360 +0200
@@ -1415,8 +1415,12 @@
                        }
                } else if (args[0] == 2) {
                        /* Clear screen by scrolling contents out */
-                       terminal_scroll_buffer(terminal,
-                                              terminal->end - terminal->start);
+                       for (i = 0; i < terminal->height; i++) {
+                               memset(terminal_get_row(terminal, i),
+                                   0, terminal->data_pitch);
+                               attr_init(terminal_get_attr_row(terminal, i),
+                                   terminal->curr_attr, terminal->width);
+                       }
                }
                break;
        case 'K':    /* EL */
Comment 6 emiettin 2013-11-24 11:28:56 UTC
Created attachment 89710 [details] [review]
more sane version of the previously proposed patch

Reverts the 'clear entire screen' escape sequence ("\033[2J") handling block to a working implementation from a previous revision (namely commit 5d380c3c5f20de5ba15838a3b73632cc0993743e). 

The actual problem might lie within the terminal_scroll_buffer implementation.
Comment 7 emiettin 2013-11-24 12:02:11 UTC
Whoops, that's actually a bad patch. 

Sure, it fixes the vim issues, but produces a lot of other bad behavior, since that implementation didn't have to worry about the user ever scrolling up. At any rate, I'm quite sure the problem lies within the \033[2J block.
Comment 8 Kristian Høgsberg 2013-11-25 01:02:53 UTC
Ok, this should fix it:

commit 1d781ee204595120657dd255f1a5ca75dfe01237
Author: Kristian Høgsberg <krh@bitplanet.net>
Date:   Sun Nov 24 16:54:12 2013 -0800

    terminal: Update terminal->end whenever we write a character
    
    We used to only update it on newline, which breaks when somebody moves
    the cursor below terminal->end and writes stuff.  Instead update it whenever
    we write a character to the terminal.

Use of freedesktop.org services, including Bugzilla, is subject to our Code of Conduct. How we collect and use information is described in our Privacy Policy.