unofficial mirror of emacs-devel@gnu.org 
 help / color / mirror / code / Atom feed
* Rendering performace vs. line-spacing
@ 2021-01-08 11:34 Herman, Géza
  2021-01-08 12:22 ` Eli Zaretskii
  0 siblings, 1 reply; 7+ messages in thread
From: Herman, Géza @ 2021-01-08 11:34 UTC (permalink / raw)
  To: emacs-devel

Hi all,

I noticed that emacs's performance can depend on the font. For example, 
Consolas has a much worse performance (scrolling is sluggish) than 
BitStream Mono. I profiled emacs, and the main difference is 
"draw_glyphs". When emacs is slow (using consolas), this function takes 
50-60% of CPU time (measured by "perf record -g"). When emacs is fast 
(using BitStream), this function takes only ~2-3%.

I played with my font's ascent and descent settings to have more line on 
the screen (as emacs doesn't support negative line-spacing). Originally, 
"draw_glyphs" takes 2-3% with my font. But if I decrease the height of 
the font by modifying ascent/descent, then the same thing happens: 
draw_glyphs takes 50-60% CPU time. If I set line-spacing to 2, 
draw_glyphs become normal, 2-3% CPU time.

(I'm using a master build from yesterday)

Any ideas why this happens? Maybe this happens because lines may overlap 
and some caching mechanism gets disabled?

Thanks,
Geza



^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Rendering performace vs. line-spacing
  2021-01-08 11:34 Rendering performace vs. line-spacing Herman, Géza
@ 2021-01-08 12:22 ` Eli Zaretskii
  2021-01-08 13:46   ` Herman, Geza
  0 siblings, 1 reply; 7+ messages in thread
From: Eli Zaretskii @ 2021-01-08 12:22 UTC (permalink / raw)
  To: geza.herman; +Cc: emacs-devel

> From: Herman, Géza <geza.herman@gmail.com>
> Date: Fri, 8 Jan 2021 12:34:53 +0100
> 
> I noticed that emacs's performance can depend on the font. For example, 
> Consolas has a much worse performance (scrolling is sluggish) than 
> BitStream Mono. I profiled emacs, and the main difference is 
> "draw_glyphs". When emacs is slow (using consolas), this function takes 
> 50-60% of CPU time (measured by "perf record -g"). When emacs is fast 
> (using BitStream), this function takes only ~2-3%.
> 
> I played with my font's ascent and descent settings to have more line on 
> the screen (as emacs doesn't support negative line-spacing). Originally, 
> "draw_glyphs" takes 2-3% with my font. But if I decrease the height of 
> the font by modifying ascent/descent, then the same thing happens: 
> draw_glyphs takes 50-60% CPU time. If I set line-spacing to 2, 
> draw_glyphs become normal, 2-3% CPU time.
> 
> (I'm using a master build from yesterday)
> 
> Any ideas why this happens? Maybe this happens because lines may overlap 
> and some caching mechanism gets disabled?

When screen lines can overlap, we have code to handle that, and it
indeed could slow down redisplay.  However, you are saying that you
_decrease_ ascent/descent, and I'm not sure I understand how could
that cause overlaps?

In any case, I suggest to profile the code with perf, and see which
parts of the display code (below draw_glyphs) take those cycles with
the problematic font(s).  Then we will see which part is the culprit,
and could take it from there.



^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Rendering performace vs. line-spacing
  2021-01-08 12:22 ` Eli Zaretskii
@ 2021-01-08 13:46   ` Herman, Geza
  2021-01-08 14:35     ` Eli Zaretskii
  0 siblings, 1 reply; 7+ messages in thread
From: Herman, Geza @ 2021-01-08 13:46 UTC (permalink / raw)
  Cc: emacs-devel


On 2021-01-08 13:22, Eli Zaretskii wrote:
>> From: Herman, Géza <geza.herman@gmail.com>
>> Date: Fri, 8 Jan 2021 12:34:53 +0100
>>
>> I noticed that emacs's performance can depend on the font. For example,
>> Consolas has a much worse performance (scrolling is sluggish) than
>> BitStream Mono. I profiled emacs, and the main difference is
>> "draw_glyphs". When emacs is slow (using consolas), this function takes
>> 50-60% of CPU time (measured by "perf record -g"). When emacs is fast
>> (using BitStream), this function takes only ~2-3%.
>>
>> I played with my font's ascent and descent settings to have more line on
>> the screen (as emacs doesn't support negative line-spacing). Originally,
>> "draw_glyphs" takes 2-3% with my font. But if I decrease the height of
>> the font by modifying ascent/descent, then the same thing happens:
>> draw_glyphs takes 50-60% CPU time. If I set line-spacing to 2,
>> draw_glyphs become normal, 2-3% CPU time.
>>
>>
> When screen lines can overlap, we have code to handle that, and it
> indeed could slow down redisplay.  However, you are saying that you
> _decrease_ ascent/descent, and I'm not sure I understand how could
> that cause overlaps?
In fontforge, I made these values smaller. So, this causes that emacs 
will display the font as if line-spacing were negative. So, lines start 
to overlap, because the actual height of the glyph doesn't change, but 
the vertical spacing between them is smaller.

> In any case, I suggest to profile the code with perf, and see which
> parts of the display code (below draw_glyphs) take those cycles with
> the problematic font(s).  Then we will see which part is the culprit,
> and could take it from there.
I did a perf record with emacs -Q, the results are better than my full 
configuration, but the difference is still there (now I see that there 
is a function which has a telling name about overlap: 
gui_fix_overlapping_area):

- 27.75% draw_glyphs
       - 18.80% gui_fix_overlapping_area
          - 18.63% update_window
               update_window_tree
               update_frame
             - redisplay_internal
                - 10.33% read_char
                     read_key_sequence
                - 8.09% read_key_sequence
                     command_loop_1
          + 0.17% draw_phys_cursor_glyph
       - 8.86% gui_write_glyphs
          - 7.93% update_window_line
               update_window
               update_window_tree
               update_frame
             - redisplay_internal
                + 4.51% read_char
                + 3.33% read_key_sequence
          + 0.93% update_window


With larger line-spacing, this function takes 0.86%:

       0.86%
       - 0.76% gui_write_glyphs
            update_window_line
            update_window
            update_window_tree
            update_frame
          - redisplay_internal
             - 0.63% read_char
                  read_key_sequence
         0.10% draw_phys_cursor_glyph

But the overall effect is that with the overlapping setting, scrolling 
is sluggish. If there's no overlap, scrolling is smooth, so I think that 
actually there's a larger difference than the additional 25% CPU usage.

It's not a big deal of course (otherwise emacs works OK, it's just the 
scrolling which is not smooth).



^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Rendering performace vs. line-spacing
  2021-01-08 13:46   ` Herman, Geza
@ 2021-01-08 14:35     ` Eli Zaretskii
  2021-01-08 15:38       ` Herman, Geza
  0 siblings, 1 reply; 7+ messages in thread
From: Eli Zaretskii @ 2021-01-08 14:35 UTC (permalink / raw)
  To: Herman, Geza; +Cc: emacs-devel

> Cc: emacs-devel@gnu.org
> From: "Herman, Geza" <geza.herman@gmail.com>
> Date: Fri, 8 Jan 2021 14:46:10 +0100
> 
> - 27.75% draw_glyphs
>        - 18.80% gui_fix_overlapping_area
>           - 18.63% update_window
>                update_window_tree
>                update_frame
>              - redisplay_internal
>                 - 10.33% read_char
>                      read_key_sequence
>                 - 8.09% read_key_sequence
>                      command_loop_1
>           + 0.17% draw_phys_cursor_glyph
>        - 8.86% gui_write_glyphs
>           - 7.93% update_window_line
>                update_window
>                update_window_tree
>                update_frame
>              - redisplay_internal
>                 + 4.51% read_char
>                 + 3.33% read_key_sequence
>           + 0.93% update_window
> 
> 
> With larger line-spacing, this function takes 0.86%:
> 
>        0.86%
>        - 0.76% gui_write_glyphs
>             update_window_line
>             update_window
>             update_window_tree
>             update_frame
>           - redisplay_internal
>              - 0.63% read_char
>                   read_key_sequence
>          0.10% draw_phys_cursor_glyph
> 
> But the overall effect is that with the overlapping setting, scrolling 
> is sluggish. If there's no overlap, scrolling is smooth, so I think that 
> actually there's a larger difference than the additional 25% CPU usage.

If screen lines overlap with the offending font, then the difference
could be justified, because redrawing one screen line would require
redrawing the two adjacent screen lines.  I'm a bit surprised by the
large performance hit, though, so maybe it's worth looking at the code
which gets run in the slow case, to see maybe some unnecessary work we
are doing in that case.

Do you have very wide windows, per chance?  Does the problem becomes
smaller if you make your frames and windows narrower?



^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Rendering performace vs. line-spacing
  2021-01-08 14:35     ` Eli Zaretskii
@ 2021-01-08 15:38       ` Herman, Geza
  2021-01-08 15:46         ` Eli Zaretskii
  0 siblings, 1 reply; 7+ messages in thread
From: Herman, Geza @ 2021-01-08 15:38 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel



On 2021-01-08 15:35, Eli Zaretskii wrote:
> If screen lines overlap with the offending font, then the difference
> could be justified, because redrawing one screen line would require
> redrawing the two adjacent screen lines.  I'm a bit surprised by the
> large performance hit, though, so maybe it's worth looking at the code
> which gets run in the slow case, to see maybe some unnecessary work we
> are doing in that case.
>
> Do you have very wide windows, per chance?  Does the problem becomes
> smaller if you make your frames and windows narrower?
Yes, my full screen emacs has a width of ~270. Sometimes I use this as a 
full screen window, sometimes I split it into two with 
split-window-horizontally.

And yes, the problem becomes smaller if I make the window narrower, or 
if the screen contains less characters. This problem is most visible at 
a particular part of my code which contains a larger table, with long 
lines (~160).

I disabled redrawing caused by overlapping by commenting out the line 
which sets the "row->overlapping_p" flag (xdisp.c:21752), and the 
problem is gone away. But my fonts are clipped (not a surprise). But, it 
fixed the consolas case as well, and I don't see any clipping with this 
font. Maybe overlapping detection is too strict (I mean, emacs considers 
cases overlapping which are close to overlapping, but they aren't)? Or 
maybe I just don't notice the clipping.



^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Rendering performace vs. line-spacing
  2021-01-08 15:38       ` Herman, Geza
@ 2021-01-08 15:46         ` Eli Zaretskii
  2021-01-08 16:04           ` Herman, Geza
  0 siblings, 1 reply; 7+ messages in thread
From: Eli Zaretskii @ 2021-01-08 15:46 UTC (permalink / raw)
  To: Herman, Geza; +Cc: emacs-devel

> Cc: emacs-devel@gnu.org
> From: "Herman, Geza" <geza.herman@gmail.com>
> Date: Fri, 8 Jan 2021 16:38:10 +0100
> 
> I disabled redrawing caused by overlapping by commenting out the line 
> which sets the "row->overlapping_p" flag (xdisp.c:21752), and the 
> problem is gone away. But my fonts are clipped (not a surprise). But, it 
> fixed the consolas case as well, and I don't see any clipping with this 
> font. Maybe overlapping detection is too strict (I mean, emacs considers 
> cases overlapping which are close to overlapping, but they aren't)? Or 
> maybe I just don't notice the clipping.

It could be that in the case of Consolas the overlapping doesn't
actually happen, but some metrics we get from the font tell us they
are.  Or maybe they do happen, but only when very few characters from
the font are used.  Or maybe this also depends on the font backend,
like whether you build with or without Cairo.

This calls for some font expert(s) to study the Consolas case and see
why the problem happens there.  Perhaps we could speed up at least
that case, I don't know.



^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Rendering performace vs. line-spacing
  2021-01-08 15:46         ` Eli Zaretskii
@ 2021-01-08 16:04           ` Herman, Geza
  0 siblings, 0 replies; 7+ messages in thread
From: Herman, Geza @ 2021-01-08 16:04 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel



On 2021-01-08 16:46, Eli Zaretskii wrote:
>> Cc: emacs-devel@gnu.org
>> From: "Herman, Geza" <geza.herman@gmail.com>
>> Date: Fri, 8 Jan 2021 16:38:10 +0100
>>
>> I disabled redrawing caused by overlapping by commenting out the line
>> which sets the "row->overlapping_p" flag (xdisp.c:21752), and the
>> problem is gone away. But my fonts are clipped (not a surprise). But, it
>> fixed the consolas case as well, and I don't see any clipping with this
>> font. Maybe overlapping detection is too strict (I mean, emacs considers
>> cases overlapping which are close to overlapping, but they aren't)? Or
>> maybe I just don't notice the clipping.
> It could be that in the case of Consolas the overlapping doesn't
> actually happen, but some metrics we get from the font tell us they
> are.  Or maybe they do happen, but only when very few characters from
> the font are used.  Or maybe this also depends on the font backend,
> like whether you build with or without Cairo.
>
> This calls for some font expert(s) to study the Consolas case and see
> why the problem happens there.  Perhaps we could speed up at least
> that case, I don't know.
Okay, thanks for the help! I adjusted my font's ascent/descent, and now 
I don't see any clipping with this font either (for the record, I'm 
using Cairo).

If I have the time, I may have a look at this part of emacs's code and 
try to understand what's going on exactly.



^ permalink raw reply	[flat|nested] 7+ messages in thread

end of thread, other threads:[~2021-01-08 16:04 UTC | newest]

Thread overview: 7+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-01-08 11:34 Rendering performace vs. line-spacing Herman, Géza
2021-01-08 12:22 ` Eli Zaretskii
2021-01-08 13:46   ` Herman, Geza
2021-01-08 14:35     ` Eli Zaretskii
2021-01-08 15:38       ` Herman, Geza
2021-01-08 15:46         ` Eli Zaretskii
2021-01-08 16:04           ` Herman, Geza

Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).