GNOME Bugzilla – Bug 156935
backwards scrolling in vte is extremely slow and temporarily even corrupts the screen
Last modified: 2004-12-22 21:47:04 UTC
I use "Fixed Bold 12" font in both gnome-terminal, standalone vte application, and also in konsole. My terminal is usually much taller than 24 lines, let's say, it's 80x60 or similar size. My computer is quite fast: 2.6GHz P4, 1GB RAM, Matrox G400. Backward scrolling with the PageUp key is painfully slow in "less". For example when reading "man bash" and pressing PageUp to go up. In plain xterm and in konsole the previous 60 lines appear immediately, just as PageDown shows the next 60 lines immediately even in vte. However, after pressing PageUp in vte, it takes approx 0.2 seconds for the previous page to appear. During this time it's clearly observable that as the old content goes downwards, new content doesn't appear at the top of the screen, the old topmost line gets duplicated as the 2nd line, then as the 3rd line, finally all these 60 lines contain the same string, namely the old topmost line. And then suddenly the contents of the whole window is repainted correctly. If you continuously press PageUp for a longer time, this behavior is more visible. Often the whole window area contains the same string in all the 60 lines and this screen remains unchanged for 2-3 seconds. Furthermore, often a line of the manpage is not printed up to its whole length, only partially, and an empty or full rectangular character also shows up in the line, hence the screen is totally corrupted. Fortunately it is only a temporary situation, since as soon as vte happens to process all these PageUp's, it repairs the screen. Now let's do some non-interactive tests. Inside a 'script' I studied the output of "less" and found that it uses the sequence "ESC [ H ESC M" to scroll one line downwards and then print to the upmost line. I took a long-long (nearly 10.000 lines) text file, namely /etc/services, and prepended this sequence to all of its lines: sed -e 's,^,\x1b[H\x1bM,' </etc/services >/etc/services-rev Cat'ing this new file to the terminal prints the services in the upside-down way: new lines are printed to the top of the screen and then the whole contents of the terminal is scrolled downwards. Here are some timings ("real" times printed by the "time" bash builtin). The terminal is 80x60 and fully visible in all cases. Inside xterm I use the default 6x13 (fixed) charset, inside vte and konsole the same "Fixed Bold 12" font. Normal forward scrolling: cat /etc/services: xterm: 0.8--0.9 seconds konsole: 0.4 seconds mainstream vte 0.11.11: 1.1--1.2 seconds vte 0.11.11 with some performance tuning patches: 0.3--0.4 seconds and now backward scrolling: cat /etc/services-rev: xterm: 0.6 seconds konsole: 0.4 seconds mainstream vte 0.11.11: 35--36 seconds vte 0.11.11 with the performance tuning patches: 28--29 seconds Yes, half minute using 100% CPU time! The factor between konsole and vte is nearly one hundred! As described at "less", this time I also can't see any worthful piece of information inside the terminal. One line of the file is printed in every line of the terminal, and it remains there for half second or 1 second (mainstream) or even 5 or maybe 10 seconds (with patches), then suddenly another line scrolls in and pushes out downwards the old one and then I see this new line in 60 pieces for another short time. And, as usual, half minute later, when the cat command completes, the terminal's content is perfect. It's also worth mentioning that during the time the screen's content doesn't change, it doesn't even repair its hidden and later obscured parts. E.g. if I hide the scrollbar with another window for a short time, it's not repainted correctly, only when a new line appears in the terminal window. (I could only test it with the patched version.) So somehow it seems that vte is flooded by thousands of events it should process but it cannot cope with them in time. I started studying the code and I found the following: In case of forward (normal) scrolling vte_terminal_scroll_region() is called with large negative "delta" values, around -150 with mainstream vte, and around -2000 with the patched version. This means that subsequent scroll events are grouped in one and handled at once. Also this happens when I grab the scrollbar with my mouse and move it up-down or press Shift+Page{Up,Down}. In case of backward scrolling, however, this function is always called with delta=1, that is, in case of services-rev, it is called about 10000 times, each time asking it to scroll one line. No wonder this yields in the awful performance we've seen. PS1: PageUp works perfectly in "vim" and "joe", most likely these applications use different sequences than "less" to scroll their content. PS2: I know there are plenty of vte bugs about vte being soooooooo slow... I even applied some of these patches which made vte faster in certain circumstances, namely from comment 1 of bug #143914 and comment 31 of bug #122656. But none of these bugreports and patches I saw dealt with this particular problem. Please don't think of marking this bugreport as a duplicate of bug #143914 or bug #122656 or bug #137864 because it isn't.
*** This bug has been marked as a duplicate of 120401 ***