bug-gnu-emacs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

bug#19117: 25.0.50; emacs on x11 chooses different fonts for the same fa


From: Dima Kogan
Subject: bug#19117: 25.0.50; emacs on x11 chooses different fonts for the same face sometimes
Date: Tue, 16 Dec 2014 21:36:14 -0800

Eli Zaretskii <address@hidden> writes:

>> From: Dima Kogan <address@hidden>
>> Date: Sat, 06 Dec 2014 23:28:34 -0800
>> 
>> > Put a breakpoint where Emacs loads new fonts, and see who calls that
>> > code.
>> 
>> I'm digging through the code. It's slow going so far, but I'm getting
>> more familiar with it. In my init.el I have in my default-frame-alist
>> 
>>  (font . "-adobe-courier-medium-r-*-*-*-80-*-*-m-*-iso8859-1")

I just dumped more time into this, and have more information, some of it
(hopefully) actionable.

I just built a optimization-free copy of emacs from the latest git:
e2815bf. This uses the lucid UI. I'm on a recent Debian/sid box.

This allows me to use gdb effectively. I also have a mostly reproducible
way to both break it and to fix it with emacs -Q. I suspect this recipe
is dependent on my window manager and font setup, so it probably
wouldn't trigger failures on other boxes, but it's useful to illustrate
what I'm doing. Recipe:

1. emacs -Q --eval "(progn (custom-set-variables '(default-frame-alist '( (font 
. \"-adobe-courier-medium-r-*-*-*-80-*-*-m-*-iso8859-1\")))) (kill-new 
\"(face-font \\\"italic\\\")\"))"

2. M-: (face-font "italic")

   The commandline eval places this string into the kill-ring so you can
   simply M-: C-y, but this is a detail. I expect it to give me an
   -adobe-courier font, but at this point it gives me an (ugly)
   -urw-.... font. Happens about 80% of the time

3. C-x 5 2

   New frame

4. Kill that new frame with my window manager

5. M-: (face-font "italic")

   Same font lookup as before. This time it gives me the correct font.


I traced various parts of the data flow. Internally emacs generates a
list of candidate fonts, scores each one against the requested font
spec, and picks the font with the best score. The issue is two-fold:

- The list of candidate fonts changes over time. This is why the issue
  self-corrects

- In the above recipe, the "right" font is in the list both times,
  however the first (wrong) time there's another candidate in the list
  that scores highly, and produces an ugly result


The top-level code flow is

 font_find_for_lface()      calls
   font_list_entities()     to get the candidate font list and
   font_select_entity()     to pick the best candidate; this calls
     font_sort_entities()   which calls
       font_score()         to evaluate a specific candidate

The "reference" font that font_score() is asked to match appears to
always be

 #<font-spec nil nil nil nil nil medium italic normal 11 nil nil nil nil>

In font_list_entities(), need_filtering = 0 is always true.



When the incorrect font is chosen at the start I see that

font_list_entities() gets a list of fonts from the cache (not from the
driver; driver_list->driver->list() is not invoked here).
font_list_entities() returns this candidate list (a vector):

#<font-entity x adobe courier ## iso8859-1 medium r normal 8 75 100 50 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 34 100 100 200 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 25 100 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 24 75 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 20 100 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 18 75 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 17 100 100 100 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 14 75 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 14 100 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 12 75 100 70 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 11 100 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 10 75 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 0 0 0 0 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 8 75 100 50 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 34 100 100 200 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 25 100 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 24 75 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 20 100 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 18 75 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 17 100 100 100 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 14 75 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 14 100 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 12 75 100 70 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 11 100 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 10 75 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 0 0 0 0 nil>
#<font-entity x adobe courier ## iso8859-1 medium i normal 0 0 0 0 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 8 75 100 50 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 34 100 100 200 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 25 100 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 24 75 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 20 100 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 18 75 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 17 100 100 100 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 14 75 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 14 100 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 12 75 100 70 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 11 100 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 10 75 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 0 0 0 0 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 8 75 100 50 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 34 100 100 200 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 25 100 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 24 75 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 20 100 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 18 75 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 17 100 100 100 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 14 75 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 14 100 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 12 75 100 70 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 11 100 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 10 75 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 0 0 0 0 nil>
#<font-entity x adobe courier ## iso8859-1 bold i normal 0 0 0 0 nil>

font_score() is given a subset of these. Candidates and returned scores:

| font                                                                          
 |   score |
|--------------------------------------------------------------------------------+---------|
| #<font-entity x adobe courier ## iso8859-1 medium r normal 8 75 100 50 nil>   
 |  393616 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 34 100 100 200 
nil> |         |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 25 100 100 150 
nil> |         |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 24 75 100 150 nil> 
 |         |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 20 100 100 110 
nil> | 1180048 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 18 75 100 110 nil> 
 |  917904 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 17 100 100 100 
nil> |  786832 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 14 75 100 90 nil>  
 |  393616 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 14 100 100 90 nil> 
 |  393616 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 12 75 100 70 nil>  
 |  131472 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 11 100 100 60 nil> 
 |     400 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 10 75 100 60 nil>  
 |  131472 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 0 0 0 0 nil>       
 |     400 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 8 75 100 50 nil>   
 |  393256 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 34 100 100 200 
nil> |         |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 25 100 100 150 
nil> |         |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 24 75 100 150 nil> 
 |         |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 20 100 100 110 
nil> | 1179688 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 18 75 100 110 nil> 
 |  917544 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 17 100 100 100 
nil> |  786472 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 14 75 100 90 nil>  
 |  393256 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 14 100 100 90 nil> 
 |  393256 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 12 75 100 70 nil>  
 |  131112 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 11 100 100 60 nil> 
 |      40 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 10 75 100 60 nil>  
 |  131112 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 0 0 0 0 nil>       
 |      40 |
| #<font-entity x adobe courier ## iso8859-1 medium i normal 0 0 0 0 nil>       
 |       0 |

Fonts with blank scores are disqualified. Lower scores are better, so
the last font with a score of 0 is chosen. This, unfortunately produces
poor results.



When the correct font is chosen further down in the recipe, I see that

font_list_entities() again gets a list of fonts from the cache:

#<font-entity x adobe courier ## iso8859-1 medium r normal 8 75 100 50 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 34 100 100 200 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 25 100 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 24 75 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 20 100 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 18 75 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 17 100 100 100 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 14 75 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 14 100 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 12 75 100 70 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 11 100 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 medium r normal 10 75 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 8 75 100 50 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 34 100 100 200 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 25 100 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 24 75 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 20 100 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 18 75 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 17 100 100 100 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 14 75 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 14 100 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 12 75 100 70 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 11 100 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 medium o normal 10 75 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 8 75 100 50 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 34 100 100 200 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 25 100 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 24 75 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 20 100 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 18 75 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 17 100 100 100 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 14 75 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 14 100 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 12 75 100 70 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 11 100 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 bold r normal 10 75 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 8 75 100 50 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 34 100 100 200 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 25 100 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 24 75 100 150 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 20 100 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 18 75 100 110 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 17 100 100 100 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 14 75 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 14 100 100 90 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 12 75 100 70 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 11 100 100 60 nil>
#<font-entity x adobe courier ## iso8859-1 bold o normal 10 75 100 60 nil>

and the corresponding scores:

| font                                                                          
 |   score |
|--------------------------------------------------------------------------------+---------|
| #<font-entity x adobe courier ## iso8859-1 medium r normal 8 75 100 50 nil>   
 |  393616 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 34 100 100 200 
nil> |         |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 25 100 100 150 
nil> |         |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 24 75 100 150 nil> 
 |         |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 20 100 100 110 
nil> | 1180048 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 18 75 100 110 nil> 
 |  917904 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 17 100 100 100 
nil> |  786832 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 14 75 100 90 nil>  
 |  393616 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 14 100 100 90 nil> 
 |  393616 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 12 75 100 70 nil>  
 |  131472 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 11 100 100 60 nil> 
 |     400 |
| #<font-entity x adobe courier ## iso8859-1 medium r normal 10 75 100 60 nil>  
 |  131472 |
| #<ont-entity x adobe courier ## iso8859-1 medium o normal 8 75 100 50 nil>    
 |  393256 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 34 100 100 200 
nil> |         |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 25 100 100 150 
nil> |         |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 24 75 100 150 nil> 
 |         |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 20 100 100 110 
nil> | 1179688 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 18 75 100 110 nil> 
 |  917544 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 17 100 100 100 
nil> |  786472 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 14 75 100 90 nil>  
 |  393256 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 14 100 100 90 nil> 
 |  393256 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 12 75 100 70 nil>  
 |  131112 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 11 100 100 60 nil> 
 |      40 |
| #<font-entity x adobe courier ## iso8859-1 medium o normal 10 75 100 60 nil>  
 |  131112 |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 8 75 100 50 nil>     
 |  444816 |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 34 100 100 200 nil>  
 |         |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 25 100 100 150 nil>  
 |         |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 24 75 100 150 nil>   
 |         |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 20 100 100 110 nil>  
 | 1231248 |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 18 75 100 110 nil>   
 |  969104 |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 17 100 100 100 nil>  
 |  838032 |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 14 75 100 90 nil>    
 |  444816 |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 14 100 100 90 nil>   
 |  444816 |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 12 75 100 70 nil>    
 |  182672 |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 11 100 100 60 nil>   
 |   51600 |
| #<font-entity x adobe courier ## iso8859-1 bold r normal 10 75 100 60 nil>    
 |  182672 |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 8 75 100 50 nil>     
 |  444456 |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 34 100 100 200 nil>  
 |         |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 25 100 100 150 nil>  
 |         |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 24 75 100 150 nil>   
 |         |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 20 100 100 110 nil>  
 | 1230888 |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 18 75 100 110 nil>   
 |  968744 |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 17 100 100 100 nil>  
 |  837672 |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 14 75 100 90 nil>    
 |  444456 |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 14 100 100 90 nil>   
 |  444456 |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 12 75 100 70 nil>    
 |  182312 |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 11 100 100 60 nil>   
 |   51240 |
| #<font-entity x adobe courier ## iso8859-1 bold o normal 10 75 100 60 nil>    
 |  182312 |

The best font has a score of 40, and it is the "right" answer.



I'm not an expert, but it seems wrong to me that the candidate list does
not stay constant. Furthermore, it's odd that the bold fonts are not
passed to font_score() during the "bad" pass, but ARE passed to it during
the "good" pass. Furthermore, the fonts that have "0 0 0 0" all score
relatively well in the "bad" pass, and the best match is one of those.
In the "good" pass those "0 0 0 0" fonts aren't there at all.

I'm going to stop investigating for today. If this is enough for
somebody knowledgeable to investigate, then that's great. Otherwise I'll
keep digging myself later. What's the "right" behavior? I suspect that
blocking out the "0 0 0 0" fonts would be sufficient to solve my issue,
but wouldn't address the other things that look wrong and possibly are
an issue for others.





reply via email to

[Prev in Thread] Current Thread [Next in Thread]