all messages for Emacs-related lists mirrored at yhetil.org
 help / color / mirror / code / Atom feed
* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
@ 2024-07-01  3:14 Dmitry Gutov
  2024-07-01 11:36 ` Eli Zaretskii
  2024-07-02 23:42 ` Stefan Kangas
  0 siblings, 2 replies; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-01  3:14 UTC (permalink / raw
  To: 71866

[-- Attachment #1: Type: text/plain, Size: 1362 bytes --]

Repro script is attached. Disabling blink-cursor-mode is not a
hard requirement, but it makes the bug easier to see. The font and face
customizations are both necessary.

1. emacs -Q -l nocursor-repro.el
2. Type 'asdasd' (without quotes)
3. Move point to either of the 's' chars
4. Create a new frame with 'C-x 5 2'

The character under cursor won't be visible - just a blank cell (the
cursor is blank as well). Then I move point with e.g. C-f and it's
visible again.

Switching between the frames (C-x 5 o) will make the char again 
invisible, as long as the point is on an 's' (in this specific scenario, 
that is). And only in the second frame (or others created later) but not 
the first one.

This only happens on my macOS machine.

The face customization is a part of a 3rd party theme (tango-plus).  I'm
pretty sure the :inverse-video customization should be a no-op but it
isn't. Seems like a subtle bug somewhere. As a user of the theme it's
taken me a while to narrow down the problem, so it'd be great if someone
could look into it.

In GNU Emacs 30.0.50 (build 3, aarch64-apple-darwin23.3.0, NS
appkit-2487.40 Version 14.3 (Build 23D56)) of 2024-06-04 built on
dizzy.local
Repository revision: 43c354a0004145c04bbc6adf0cfaa8c21403ad8c
Repository branch: master
Windowing system distributor 'Apple', version 10.3.2487
System Description:  macOS 14.3


[-- Attachment #2: nocursor-repro.el --]
[-- Type: application/octet-stream, Size: 393 bytes --]

;; This buffer is for text that is not saved, and for Lisp evaluation.
;; To create a file, visit it with ‘C-x C-f’ and enter text in its buffer.

(set-face-attribute 'default nil :family "Cascadia Mono")

(blink-cursor-mode -1)

(custom-theme-set-faces
 'user
 '(cursor                         ((((class color) (min-colors 89))
                                    (:inverse-video t)))))


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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-01  3:14 bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization Dmitry Gutov
@ 2024-07-01 11:36 ` Eli Zaretskii
  2024-07-02  1:07   ` Dmitry Gutov
  2024-07-02 23:42 ` Stefan Kangas
  1 sibling, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-01 11:36 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: 71866

> Date: Mon, 1 Jul 2024 06:14:28 +0300
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> Repro script is attached. Disabling blink-cursor-mode is not a
> hard requirement, but it makes the bug easier to see. The font and face
> customizations are both necessary.
> 
> 1. emacs -Q -l nocursor-repro.el
> 2. Type 'asdasd' (without quotes)
> 3. Move point to either of the 's' chars
> 4. Create a new frame with 'C-x 5 2'
> 
> The character under cursor won't be visible - just a blank cell (the
> cursor is blank as well). Then I move point with e.g. C-f and it's
> visible again.

This is definitely macOS specific.  I cannot reproduce on my system
(although by some miracle I do have the Cascadia Mono font installed).
Basically, what happens is that redisplay has some bug in how it draws
the cursor.  Given all the tricks that redisplay plays on macOS, I'm
not surprised.

On other platforms, the code which draws the cursor is in draw_glyphs,
called from XXX_draw_window_cursor function (where XXX is the GUI
backend, in your case probably XXX = ns).  If the same is true on
macOS, you could try stepping through that code.

> The face customization is a part of a 3rd party theme (tango-plus).  I'm
> pretty sure the :inverse-video customization should be a no-op but it
> isn't. Seems like a subtle bug somewhere. As a user of the theme it's
> taken me a while to narrow down the problem, so it'd be great if someone
> could look into it.

So if inverse-video is not used, the problem goes away?  If so, just
don't use it.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-01 11:36 ` Eli Zaretskii
@ 2024-07-02  1:07   ` Dmitry Gutov
  2024-07-06  8:56     ` Eli Zaretskii
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-02  1:07 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: 71866

On 01/07/2024 14:36, Eli Zaretskii wrote:
>> Date: Mon, 1 Jul 2024 06:14:28 +0300
>> From: Dmitry Gutov <dmitry@gutov.dev>
>>
>> Repro script is attached. Disabling blink-cursor-mode is not a
>> hard requirement, but it makes the bug easier to see. The font and face
>> customizations are both necessary.
>>
>> 1. emacs -Q -l nocursor-repro.el
>> 2. Type 'asdasd' (without quotes)
>> 3. Move point to either of the 's' chars
>> 4. Create a new frame with 'C-x 5 2'
>>
>> The character under cursor won't be visible - just a blank cell (the
>> cursor is blank as well). Then I move point with e.g. C-f and it's
>> visible again.
> 
> This is definitely macOS specific.  I cannot reproduce on my system
> (although by some miracle I do have the Cascadia Mono font installed).
> Basically, what happens is that redisplay has some bug in how it draws
> the cursor.  Given all the tricks that redisplay plays on macOS, I'm
> not surprised.

Indeed, it never happens on my Linux system either. Thanks for checking 
anyway.

> On other platforms, the code which draws the cursor is in draw_glyphs,
> called from XXX_draw_window_cursor function (where XXX is the GUI
> backend, in your case probably XXX = ns).  If the same is true on
> macOS, you could try stepping through that code.

I can try following some more detailed instructions. I.e. I can set up a 
breakpoint, but would there be anything to look out for when stepping 
through the code?

BTW, this happens only right after I switch frames. Things start looking 
right again if I simply move point.

>> The face customization is a part of a 3rd party theme (tango-plus).  I'm
>> pretty sure the :inverse-video customization should be a no-op but it
>> isn't. Seems like a subtle bug somewhere. As a user of the theme it's
>> taken me a while to narrow down the problem, so it'd be great if someone
>> could look into it.
> 
> So if inverse-video is not used, the problem goes away?  If so, just
> don't use it.

Yeah, I plan on submitting a patch to that effect to the theme.

But the bug looks odd enough and the same time very stable, that I think 
it's worth investigating.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-01  3:14 bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization Dmitry Gutov
  2024-07-01 11:36 ` Eli Zaretskii
@ 2024-07-02 23:42 ` Stefan Kangas
  2024-07-07  2:03   ` Dmitry Gutov
  1 sibling, 1 reply; 50+ messages in thread
From: Stefan Kangas @ 2024-07-02 23:42 UTC (permalink / raw
  To: Dmitry Gutov, 71866

Dmitry Gutov <dmitry@gutov.dev> writes:

> Repro script is attached. Disabling blink-cursor-mode is not a
> hard requirement, but it makes the bug easier to see. The font and face
> customizations are both necessary.
>
> 1. emacs -Q -l nocursor-repro.el
> 2. Type 'asdasd' (without quotes)
> 3. Move point to either of the 's' chars
> 4. Create a new frame with 'C-x 5 2'
>
> The character under cursor won't be visible - just a blank cell (the
> cursor is blank as well). Then I move point with e.g. C-f and it's
> visible again.
>
> Switching between the frames (C-x 5 o) will make the char again
> invisible, as long as the point is on an 's' (in this specific scenario,
> that is). And only in the second frame (or others created later) but not
> the first one.
>
> This only happens on my macOS machine.
>
> The face customization is a part of a 3rd party theme (tango-plus).  I'm
> pretty sure the :inverse-video customization should be a no-op but it
> isn't. Seems like a subtle bug somewhere. As a user of the theme it's
> taken me a while to narrow down the problem, so it'd be great if someone
> could look into it.

I can't reproduce that here, using the above recipe.

Maybe try upgrading to macOS 14.5 to see if the problem goes away?

In GNU Emacs 31.0.50 (build 1, aarch64-apple-darwin23.5.0, NS
 appkit-2487.60 Version 14.5 (Build 23F79)) of 2024-07-01 built on
 foo.local
Repository revision: 4008385b8d48b1a8e670ac497c3b8a12b9605a4e
Repository branch: master
Windowing system distributor 'Apple', version 10.3.2487
System Description:  macOS 14.5

> In GNU Emacs 30.0.50 (build 3, aarch64-apple-darwin23.3.0, NS
> appkit-2487.40 Version 14.3 (Build 23D56)) of 2024-06-04 built on
> dizzy.local
> Repository revision: 43c354a0004145c04bbc6adf0cfaa8c21403ad8c
> Repository branch: master
> Windowing system distributor 'Apple', version 10.3.2487
> System Description:  macOS 14.3





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-02  1:07   ` Dmitry Gutov
@ 2024-07-06  8:56     ` Eli Zaretskii
  2024-07-09  2:37       ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-06  8:56 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: 71866

> Date: Tue, 2 Jul 2024 04:07:11 +0300
> Cc: 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> On 01/07/2024 14:36, Eli Zaretskii wrote:
> > On other platforms, the code which draws the cursor is in draw_glyphs,
> > called from XXX_draw_window_cursor function (where XXX is the GUI
> > backend, in your case probably XXX = ns).  If the same is true on
> > macOS, you could try stepping through that code.
> 
> I can try following some more detailed instructions. I.e. I can set up a 
> breakpoint, but would there be anything to look out for when stepping 
> through the code?

For starters, put a breakpoint in ns_draw_window_cursor and see if it
gets called in the scenario where you see the problem.

If it does get called, it should call draw_phys_cursor_glyph in this
case (because the cursor type is FILLED_BOX_CURSOR).  If it calls that
function, step through it.  You should see there that it calls
draw_glyphs to draw the single character under the cursor.  The actual
drawing happens here:

  /* Draw all strings.  */
  for (s = head; s; s = s->next)
    FRAME_RIF (f)->draw_glyph_string (s);

where the draw_glyph_string method is a function in nsterm.m,
ns_draw_glyph_string.  AFAICT, it should draw a character with the
foreground taken from the frame's background color and background
color taken from the cursor color.

Something in this chain of calls doesn't happen in the scenario which
shows the problem.

> BTW, this happens only right after I switch frames. Things start looking 
> right again if I simply move point.

Then step through the code after switching frames.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-02 23:42 ` Stefan Kangas
@ 2024-07-07  2:03   ` Dmitry Gutov
  2024-07-09 18:22     ` Stefan Kangas
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-07  2:03 UTC (permalink / raw
  To: Stefan Kangas, 71866

On 03/07/2024 02:42, Stefan Kangas wrote:

> I can't reproduce that here, using the above recipe.

Thanks for trying anyway.

> Maybe try upgrading to macOS 14.5 to see if the problem goes away?

Upgraded to 14.5 now (apparently the upgrades were being blocked by a 
vpn being always on) - but the problem remains the same.

Not sure what is the difference between our machines - but mine is an M3 
Pro, FWIW.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-06  8:56     ` Eli Zaretskii
@ 2024-07-09  2:37       ` Dmitry Gutov
  2024-07-09 11:31         ` Eli Zaretskii
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-09  2:37 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: 71866

Hi Eli,

On 06/07/2024 11:56, Eli Zaretskii wrote:
>> Date: Tue, 2 Jul 2024 04:07:11 +0300
>> Cc: 71866@debbugs.gnu.org
>> From: Dmitry Gutov <dmitry@gutov.dev>
>>
>> On 01/07/2024 14:36, Eli Zaretskii wrote:
>>> On other platforms, the code which draws the cursor is in draw_glyphs,
>>> called from XXX_draw_window_cursor function (where XXX is the GUI
>>> backend, in your case probably XXX = ns).  If the same is true on
>>> macOS, you could try stepping through that code.
>>
>> I can try following some more detailed instructions. I.e. I can set up a
>> breakpoint, but would there be anything to look out for when stepping
>> through the code?
> 
> For starters, put a breakpoint in ns_draw_window_cursor and see if it
> gets called in the scenario where you see the problem.

Thank you.

It does get called. Unfortunately, as soon as I put a breakpoint there, 
any attempt to switch to the Emacs window drops into the debugger again 
- and I have switch back to the terminal emulator to enter 'c RET' 20 
times or so.

So it seems difficult to go through the exact scenario where I'm 
switching between frames, where switching back to one draws the glyph 
incorrectly. Any advice with that?

> If it does get called, it should call draw_phys_cursor_glyph in this
> case (because the cursor type is FILLED_BOX_CURSOR).  If it calls that
> function, step through it.  You should see there that it calls
> draw_glyphs to draw the single character under the cursor.  The actual
> drawing happens here:
> 
>    /* Draw all strings.  */
>    for (s = head; s; s = s->next)
>      FRAME_RIF (f)->draw_glyph_string (s);
> 
> where the draw_glyph_string method is a function in nsterm.m,
> ns_draw_glyph_string.  AFAICT, it should draw a character with the
> foreground taken from the frame's background color and background
> color taken from the cursor color.
> 
> Something in this chain of calls doesn't happen in the scenario which
> shows the problem.
> 
>> BTW, this happens only right after I switch frames. Things start looking
>> right again if I simply move point.
> 
> Then step through the code after switching frames.






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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-09  2:37       ` Dmitry Gutov
@ 2024-07-09 11:31         ` Eli Zaretskii
  2024-07-10  2:46           ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-09 11:31 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: 71866

> Date: Tue, 9 Jul 2024 05:37:10 +0300
> Cc: 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> > For starters, put a breakpoint in ns_draw_window_cursor and see if it
> > gets called in the scenario where you see the problem.
> 
> Thank you.
> 
> It does get called. Unfortunately, as soon as I put a breakpoint there, 
> any attempt to switch to the Emacs window drops into the debugger again 
> - and I have switch back to the terminal emulator to enter 'c RET' 20 
> times or so.

I don't think I understand what you are trying to do.  I thought you
needed to "switch to the Emacs window" just once: to trigger the
situation which you want to investigate.  Once you trigger it, the
debugger will indeed kick in, but all you need to do next is step
through the code, so why do you care about switching to Emacs again?

If you want to trigger this situation several times, and be able to
activate and deactivate the breakpoint at will, I suggest the
following technique:

  . put a breakpoint in some function that is easy to invoke
    interactively, but which otherwise is rarely called (my personal
    favorite is Frecenter, which you can then trigger with C-l)
  . put a breakpoint in ns_draw_window_cursor (or wherever you need),
    but make it disabled (the GDB command is "disable N" where N is
    the breakpoint number)
  . when you are ready to trigger the issue, type C-l, which will
    cause the debugger to kick in, and enable the breakpoint in
    ns_draw_window_cursor
  . continue Emacs, then trigger the ns_draw_window_cursor breakpoint
    and investigate
  . when you are done investigating and want to, say, set a breakpoint
    in some other place, do that, make the breakpoint disabled again
    and continue Emacs
  . when ready, type C-l again, enable the disabled breakpoint, and
    repeat the above procedure

Another, or perhaps complementary, technique is to define conditions
for breakpoints so that they trigger only when you want.  For example,
if you want a breakpoint to trigger only for a specific frame or
window, find out the address of the corresponding struct window or
struct frame (assuming there are variables of these types in the same
scope as the breakpoint), then make the breakpoint conditioned on
those variables having (or not having) those specific values.  The
usual method of finding out these addresses is the first time the
breakpoint triggers.  Then you can do:

  (gdb) print f
    $1 = (struct frame *) 0x1234567812345600
  (gdb) condition 3 f == 0x1234567812345600

This makes breakpoint 3 trigger only when struct frame variable f has
the value of this frame.

HTH





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-07  2:03   ` Dmitry Gutov
@ 2024-07-09 18:22     ` Stefan Kangas
  2024-07-10  2:56       ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Stefan Kangas @ 2024-07-09 18:22 UTC (permalink / raw
  To: Dmitry Gutov, 71866

Dmitry Gutov <dmitry@gutov.dev> writes:

> Not sure what is the difference between our machines - but mine is an M3
> Pro, FWIW.

M2 Pro here, using the latest version of various libraries available on
Homebrew.

Maybe some build flags or features are different?

Configured using:
 'configure --enable-checking=yes,glyphs
 --enable-check-lisp-object-type'

Configured features:
ACL GNUTLS LCMS2 LIBXML2 MODULES NOTIFY KQUEUE NS PDUMPER PNG SQLITE3
THREADS TOOLKIT_SCROLL_BARS TREE_SITTER ZLIB





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-09 11:31         ` Eli Zaretskii
@ 2024-07-10  2:46           ` Dmitry Gutov
  2024-07-10 11:58             ` Eli Zaretskii
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-10  2:46 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: 71866

On 09/07/2024 14:31, Eli Zaretskii wrote:
>> Date: Tue, 9 Jul 2024 05:37:10 +0300
>> Cc: 71866@debbugs.gnu.org
>> From: Dmitry Gutov <dmitry@gutov.dev>
>>
>>> For starters, put a breakpoint in ns_draw_window_cursor and see if it
>>> gets called in the scenario where you see the problem.
>>
>> Thank you.
>>
>> It does get called. Unfortunately, as soon as I put a breakpoint there,
>> any attempt to switch to the Emacs window drops into the debugger again
>> - and I have switch back to the terminal emulator to enter 'c RET' 20
>> times or so.
> 
> I don't think I understand what you are trying to do.  I thought you
> needed to "switch to the Emacs window" just once: to trigger the
> situation which you want to investigate.  Once you trigger it, the
> debugger will indeed kick in, but all you need to do next is step
> through the code, so why do you care about switching to Emacs again?

Somehow, the problem manifests when I switch between frames (two frames 
in the current repro) using C-` (bound to `other-frame').

But if I Alt-Tab to a different application and then Alt-Tab back to 
Emacs, then the glyph is rendered fine - even if the "problematic" frame 
gets selected.

> If you want to trigger this situation several times, and be able to
> activate and deactivate the breakpoint at will, I suggest the
> following technique:
> 
>    . put a breakpoint in some function that is easy to invoke
>      interactively, but which otherwise is rarely called (my personal
>      favorite is Frecenter, which you can then trigger with C-l)
>    . put a breakpoint in ns_draw_window_cursor (or wherever you need),
>      but make it disabled (the GDB command is "disable N" where N is
>      the breakpoint number)
>    . when you are ready to trigger the issue, type C-l, which will
>      cause the debugger to kick in, and enable the breakpoint in
>      ns_draw_window_cursor
>    . continue Emacs, then trigger the ns_draw_window_cursor breakpoint
>      and investigate

At this point the breakpoint will start hitting as soon as I switch to 
an Emacs frame. I guess what would be ideal is a breakpoint which won't 
hit until after I switch to another frame.

>    . when you are done investigating and want to, say, set a breakpoint
>      in some other place, do that, make the breakpoint disabled again
>      and continue Emacs
>    . when ready, type C-l again, enable the disabled breakpoint, and
>      repeat the above procedure
> 
> Another, or perhaps complementary, technique is to define conditions
> for breakpoints so that they trigger only when you want.  For example,
> if you want a breakpoint to trigger only for a specific frame or
> window, find out the address of the corresponding struct window or
> struct frame (assuming there are variables of these types in the same
> scope as the breakpoint), then make the breakpoint conditioned on
> those variables having (or not having) those specific values.  The
> usual method of finding out these addresses is the first time the
> breakpoint triggers.  Then you can do:
> 
>    (gdb) print f
>      $1 = (struct frame *) 0x1234567812345600
>    (gdb) condition 3 f == 0x1234567812345600
> 
> This makes breakpoint 3 trigger only when struct frame variable f has
> the value of this frame.

So step 1 find out the address of the second frame, step 2 switch to 
first frame, step 3 enable a conditional breakpoint.

Thank you, I'll try experimenting with that.






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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-09 18:22     ` Stefan Kangas
@ 2024-07-10  2:56       ` Dmitry Gutov
  2024-07-23  7:40         ` Gerd Möllmann
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-10  2:56 UTC (permalink / raw
  To: Stefan Kangas, 71866

On 09/07/2024 21:22, Stefan Kangas wrote:
> Dmitry Gutov <dmitry@gutov.dev> writes:
> 
>> Not sure what is the difference between our machines - but mine is an M3
>> Pro, FWIW.
> 
> M2 Pro here, using the latest version of various libraries available on
> Homebrew.
> 
> Maybe some build flags or features are different?

Right, I don't have pass any explicit flags to configure.

> Configured using:
>   'configure --enable-checking=yes,glyphs
>   --enable-check-lisp-object-type'

...but I have just recompiled after re-running configure with the above 
options, and the bug still reproduces. Not 'make boostrap', though, just 
'./configure ...' and then 'make'.

> Configured features:
> ACL GNUTLS LCMS2 LIBXML2 MODULES NOTIFY KQUEUE NS PDUMPER PNG SQLITE3
> THREADS TOOLKIT_SCROLL_BARS TREE_SITTER ZLIB

LCMS2, PNG, SQLITE3 are not in my list, otherwise it's the same.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-10  2:46           ` Dmitry Gutov
@ 2024-07-10 11:58             ` Eli Zaretskii
  2024-07-19  1:57               ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-10 11:58 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: 71866

> Date: Wed, 10 Jul 2024 05:46:35 +0300
> Cc: 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> >> It does get called. Unfortunately, as soon as I put a breakpoint there,
> >> any attempt to switch to the Emacs window drops into the debugger again
> >> - and I have switch back to the terminal emulator to enter 'c RET' 20
> >> times or so.
> > 
> > I don't think I understand what you are trying to do.  I thought you
> > needed to "switch to the Emacs window" just once: to trigger the
> > situation which you want to investigate.  Once you trigger it, the
> > debugger will indeed kick in, but all you need to do next is step
> > through the code, so why do you care about switching to Emacs again?
> 
> Somehow, the problem manifests when I switch between frames (two frames 
> in the current repro) using C-` (bound to `other-frame').
> 
> But if I Alt-Tab to a different application and then Alt-Tab back to 
> Emacs, then the glyph is rendered fine - even if the "problematic" frame 
> gets selected.

I thought you see the problem when you switch from another application
to Emacs, not only when you switch between two Emacs frames.  I see I
was mistaken.

> >    (gdb) print f
> >      $1 = (struct frame *) 0x1234567812345600
> >    (gdb) condition 3 f == 0x1234567812345600
> > 
> > This makes breakpoint 3 trigger only when struct frame variable f has
> > the value of this frame.
> 
> So step 1 find out the address of the second frame, step 2 switch to 
> first frame, step 3 enable a conditional breakpoint.

Yes.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-10 11:58             ` Eli Zaretskii
@ 2024-07-19  1:57               ` Dmitry Gutov
  2024-07-20  8:30                 ` Eli Zaretskii
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-19  1:57 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: 71866

[-- Attachment #1: Type: text/plain, Size: 2616 bytes --]

On 10/07/2024 14:58, Eli Zaretskii wrote:
>> Date: Wed, 10 Jul 2024 05:46:35 +0300
>> Cc: 71866@debbugs.gnu.org
>> From: Dmitry Gutov <dmitry@gutov.dev>
>>
>>>> It does get called. Unfortunately, as soon as I put a breakpoint there,
>>>> any attempt to switch to the Emacs window drops into the debugger again
>>>> - and I have switch back to the terminal emulator to enter 'c RET' 20
>>>> times or so.
>>>
>>> I don't think I understand what you are trying to do.  I thought you
>>> needed to "switch to the Emacs window" just once: to trigger the
>>> situation which you want to investigate.  Once you trigger it, the
>>> debugger will indeed kick in, but all you need to do next is step
>>> through the code, so why do you care about switching to Emacs again?
>>
>> Somehow, the problem manifests when I switch between frames (two frames
>> in the current repro) using C-` (bound to `other-frame').
>>
>> But if I Alt-Tab to a different application and then Alt-Tab back to
>> Emacs, then the glyph is rendered fine - even if the "problematic" frame
>> gets selected.
> 
> I thought you see the problem when you switch from another application
> to Emacs, not only when you switch between two Emacs frames.  I see I
> was mistaken.
> 
>>>     (gdb) print f
>>>       $1 = (struct frame *) 0x1234567812345600
>>>     (gdb) condition 3 f == 0x1234567812345600
>>>
>>> This makes breakpoint 3 trigger only when struct frame variable f has
>>> the value of this frame.
>>
>> So step 1 find out the address of the second frame, step 2 switch to
>> first frame, step 3 enable a conditional breakpoint.
> 
> Yes.

Okay, I have tried that, and the results might or might not be useful.

Similarly to the case of switching from another application, when I have 
to switch to another application to handle the breakpoints (just typing 
'c RET'), the behavior is different.

BUT the last call to ns_draw_window_cursor (out of 14) before the 
control is returned results in the cursor getting hidden (in the new 
selected Emacs frame only). Unlike the problem I described, the 
character under the cursor stays drawn, but the cursor rectangle goes 
away (and that happens after the last breakpoint hit, before that the 
text and the cursor look correctly - hollow cursor around the character).

I'm attaching the last debugging log - maybe the backtrace can be 
useful? - but note that the backtrace printing is halfway broken as well 
- it freezes and I have to press ^C a bunch of times to see something.

Anyway, while wrong, the behavior is not the same, so I can't be sure 
it's the same problem that is being triggered.

[-- Attachment #2: emacs-lldb-log.txt --]
[-- Type: text/plain, Size: 9973 bytes --]

Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4188, glyph_row=0x0000000132ad0000, x=<unavailable>, y=<unavailable>, cursor_type=FILLED_BOX_CURSOR, cursor_width=1, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4188, glyph_row=0x0000000132ad0000, x=<unavailable>, y=<unavailable>, cursor_type=FILLED_BOX_CURSOR, cursor_width=1, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4430, glyph_row=0x00000001308d1200, x=<unavailable>, y=<unavailable>, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
2024-07-19 04:39:54.538871+0300 emacs[82461:2830026] [CursorUI] -[TUINSCursorUIController activate:]: EmacsView doesn't conform to NSTextInputClient protocol.
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4188, glyph_row=0x0000000132ad0000, x=<unavailable>, y=<unavailable>, cursor_type=HOLLOW_BOX_CURSOR, cursor_width=1, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4430, glyph_row=0x00000001308d1200, x=<unavailable>, y=<unavailable>, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4188, glyph_row=0x0000000132ad0000, x=<unavailable>, y=<unavailable>, cursor_type=FILLED_BOX_CURSOR, cursor_width=1, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4188, glyph_row=0x0000000132ad0000, x=<unavailable>, y=<unavailable>, cursor_type=FILLED_BOX_CURSOR, cursor_width=1, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4430, glyph_row=0x00000001308d1200, x=<unavailable>, y=<unavailable>, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
2024-07-19 04:40:10.523120+0300 emacs[82461:2830026] [CursorUI] -[TUINSCursorUIController activate:]: EmacsView doesn't conform to NSTextInputClient protocol.
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4188, glyph_row=0x0000000132ad0000, x=<unavailable>, y=<unavailable>, cursor_type=HOLLOW_BOX_CURSOR, cursor_width=1, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4430, glyph_row=0x00000001308d1200, x=<unavailable>, y=<unavailable>, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4430, glyph_row=0x00000001308d1200, x=<unavailable>, y=<unavailable>, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4188, glyph_row=0x0000000132ad0000, x=<unavailable>, y=<unavailable>, cursor_type=HOLLOW_BOX_CURSOR, cursor_width=1, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4430, glyph_row=0x00000001308d1200, x=<unavailable>, y=<unavailable>, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) c
Process 82461 resuming
Process 82461 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
    frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4430, glyph_row=0x00000001308d1200, x=<unavailable>, y=<unavailable>, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) bt
^C
^C*** exception in child provider update for Lisp_Symbol
^C^C*** exception in child provider update for Lisp_Symbol
^C^C* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 4.1
  * frame #0: 0x000000010027da6c emacs`ns_draw_window_cursor(w=0x00000001328b4430, glyph_row=0x00000001308d1200, x=<unavailable>, y=<unavailable>, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=<unavailable>) at nsterm.m:3045:23 [opt]
    frame #1: 0x0000000100009120 emacs`gui_update_window_end(w=0x00000001328b4430, cursor_on_p=true, mouse_face_overwritten_p=false) at dispnew.c:3941:2 [opt]
    frame #2: 0x0000000100007e94 emacs`update_window(w=0x00000001328b4430, force_p=<unavailable>) at dispnew.c:3869:7 [opt]
    frame #3: 0x000000010000835c emacs`update_window_tree(w=0x00000001328b4430, force_p=true) at dispnew.c:3491:14 [opt]
    frame #4: 0x0000000100005c8c emacs`update_frame(f=0x00000001328b3f38, force_p=true, inhibit_hairy_id_p=<unavailable>) at dispnew.c:3326:18 [opt]
    frame #5: 0x000000010003b130 emacs`redisplay_internal at xdisp.c:17480:16 [opt]
    frame #6: 0x0000000100041620 emacs`redisplay at xdisp.c:16575:3 [opt] [artificial]
    frame #7: 0x000000010010d1e0 emacs`read_char(commandflag=<unavailable>, map=<unavailable>, prev_event=(struct Lisp_Symbol *) $35043 = 0x0000000100a8cf38, used_mouse_menu=<unavailable>, end_time=<unavailable>) at keyboard.c:2678:6 [opt]

... Interrupted.
(lldb) c
Process 82461 resuming

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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-19  1:57               ` Dmitry Gutov
@ 2024-07-20  8:30                 ` Eli Zaretskii
  2024-07-20 15:46                   ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-20  8:30 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: 71866

> Date: Fri, 19 Jul 2024 04:57:12 +0300
> Cc: 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> Okay, I have tried that, and the results might or might not be useful.
> 
> Similarly to the case of switching from another application, when I have 
> to switch to another application to handle the breakpoints (just typing 
> 'c RET'), the behavior is different.
> 
> BUT the last call to ns_draw_window_cursor (out of 14) before the 
> control is returned results in the cursor getting hidden (in the new 
> selected Emacs frame only). Unlike the problem I described, the 
> character under the cursor stays drawn, but the cursor rectangle goes 
> away (and that happens after the last breakpoint hit, before that the 
> text and the cursor look correctly - hollow cursor around the character).
> 
> I'm attaching the last debugging log - maybe the backtrace can be 
> useful? - but note that the backtrace printing is halfway broken as well 
> - it freezes and I have to press ^C a bunch of times to see something.
> 
> Anyway, while wrong, the behavior is not the same, so I can't be sure 
> it's the same problem that is being triggered.

I don't really see any useful information here, except that the last
call tells Emacs to show the cursor using type NO_CURSOR (i.e. not to
display anything).  I don't understand why this happens; the value is
returned by get_window_cursor_type called inside
display_and_set_cursor (which is what gui_update_window_end calls on
line 3941 of dispnew.c, but the backtrace doesn't even mention that).

But before we try to analyze this situation, shouldn't we try to stick
to the original issue?  Why could not you investigate what happens in
that case?

Also, if the problem persists in a non-optimized build, I suggest to
use that, since then the backtraces will be much more helpful, and
there will be no "optimized-out" variables whose values you cannot see
in the debugger.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-20  8:30                 ` Eli Zaretskii
@ 2024-07-20 15:46                   ` Dmitry Gutov
  2024-07-20 16:03                     ` Eli Zaretskii
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-20 15:46 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: 71866

On 20/07/2024 11:30, Eli Zaretskii wrote:

>> Anyway, while wrong, the behavior is not the same, so I can't be sure
>> it's the same problem that is being triggered.
> 
> I don't really see any useful information here, except that the last
> call tells Emacs to show the cursor using type NO_CURSOR (i.e. not to
> display anything).

I do see a bunch of such calls earlier as well, but they don't seem to 
result in no cursor being displayed - just in it not being updated, maybe?

> I don't understand why this happens; the value is
> returned by get_window_cursor_type called inside
> display_and_set_cursor (which is what gui_update_window_end calls on
> line 3941 of dispnew.c, but the backtrace doesn't even mention that).
> 
> But before we try to analyze this situation, shouldn't we try to stick
> to the original issue?  Why could not you investigate what happens in
> that case?

The scenario that I'm trying is the same that creates the original problem.

When I have to switch to another application to handle the breakpoints 
(just typing 'c RET'), the behavior becomes different.

> Also, if the problem persists in a non-optimized build, I suggest to
> use that, since then the backtraces will be much more helpful, and
> there will be no "optimized-out" variables whose values you cannot see
> in the debugger.

Would the same backtrace that I sent, but without optimized-out 
variables, be more useful?





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-20 15:46                   ` Dmitry Gutov
@ 2024-07-20 16:03                     ` Eli Zaretskii
  2024-07-21  0:53                       ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-20 16:03 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: 71866

> Date: Sat, 20 Jul 2024 18:46:50 +0300
> Cc: 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> > I don't really see any useful information here, except that the last
> > call tells Emacs to show the cursor using type NO_CURSOR (i.e. not to
> > display anything).
> 
> I do see a bunch of such calls earlier as well, but they don't seem to 
> result in no cursor being displayed - just in it not being updated, maybe?

It depends on what was redrawn before that.

> > I don't understand why this happens; the value is
> > returned by get_window_cursor_type called inside
> > display_and_set_cursor (which is what gui_update_window_end calls on
> > line 3941 of dispnew.c, but the backtrace doesn't even mention that).
> > 
> > But before we try to analyze this situation, shouldn't we try to stick
> > to the original issue?  Why could not you investigate what happens in
> > that case?
> 
> The scenario that I'm trying is the same that creates the original problem.

That's not what you said, or maybe I misunderstood.

But anyway, if this is the same scenario, then why are you only
looking at what happens inside ns_draw_window_cursor?  Redrawing the
block cursor involves displaying the character under cursor with
special colors, and ns_draw_window_cursor is just the beginning: it
calls other functions which actually do the job.

In addition, I don't think I understand from the debug session which
call to ns_draw_window_cursor was done in what situation.  If they all
were part of the single repetition of the scenario, then without fully
functional backtraces it is very hard to understand anything that goes
on here.  Using an unoptimized build might help, which is why I
suggested that (unless the problem disappears in an unoptimized
build).





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-20 16:03                     ` Eli Zaretskii
@ 2024-07-21  0:53                       ` Dmitry Gutov
  2024-07-21  7:20                         ` Eli Zaretskii
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-21  0:53 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: 71866

[-- Attachment #1: Type: text/plain, Size: 3008 bytes --]

On 20/07/2024 19:03, Eli Zaretskii wrote:
>> Date: Sat, 20 Jul 2024 18:46:50 +0300
>> Cc: 71866@debbugs.gnu.org
>> From: Dmitry Gutov <dmitry@gutov.dev>
>>
>>> I don't really see any useful information here, except that the last
>>> call tells Emacs to show the cursor using type NO_CURSOR (i.e. not to
>>> display anything).
>>
>> I do see a bunch of such calls earlier as well, but they don't seem to
>> result in no cursor being displayed - just in it not being updated, maybe?
> 
> It depends on what was redrawn before that.

Perhaps it'll be easier to share a video. Sorry, it's a large file, so I 
just uploaded it to a free online hosting: https://streamable.com/d6775w

The first (smaller) part is me reproducing the bug, then I switch to the 
terminal emulator, enable the breakpoint and demonstrate how the 
behavior of the same command (other-frame) changes.

After the video was finished, I also repeated the same scenario, and 
saved the backtrace of the last (12th) breakpoint hit.

>>> I don't understand why this happens; the value is
>>> returned by get_window_cursor_type called inside
>>> display_and_set_cursor (which is what gui_update_window_end calls on
>>> line 3941 of dispnew.c, but the backtrace doesn't even mention that).
>>>
>>> But before we try to analyze this situation, shouldn't we try to stick
>>> to the original issue?  Why could not you investigate what happens in
>>> that case?
>>
>> The scenario that I'm trying is the same that creates the original problem.
> 
> That's not what you said, or maybe I misunderstood.
> 
> But anyway, if this is the same scenario, then why are you only
> looking at what happens inside ns_draw_window_cursor?  Redrawing the
> block cursor involves displaying the character under cursor with
> special colors, and ns_draw_window_cursor is just the beginning: it
> calls other functions which actually do the job.

More breakpoints means more chances for the behavior to change. I also 
don't really know which other places to look at. Stepping through all 
the callees is both time-consuming and something that is unlikely to 
help until I manage to read all of the underlying implementation and 
start making sense of the data that's being used, to be able to notice 
when this or that variable has an odd value.

But maybe at this point some print-debugging might be more beneficial 
(since that shouldn't change the existing behavior). See the linked 
video and the attached backtrace, though.

> In addition, I don't think I understand from the debug session which
> call to ns_draw_window_cursor was done in what situation.  If they all
> were part of the single repetition of the scenario, then without fully
> functional backtraces it is very hard to understand anything that goes
> on here.  Using an unoptimized build might help, which is why I
> suggested that (unless the problem disappears in an unoptimized
> build).

Yes, I've reconfigured and rebuilt with CFLAGS="-O0 -g3". That fixed the 
backtrace printing, at least.

[-- Attachment #2: emacs-lldb-bt-2.txt --]
[-- Type: text/plain, Size: 5407 bytes --]

* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x00000001280208f8, glyph_row=0x00000001280bc800, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x00000001280208f8, glyph_row=0x00000001280bc800, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x00000001280208f8, on=true, hpos=0, vpos=0, x=0, y=0) at xdisp.c:34205:5
    frame #2: 0x0000000100070d24 emacs`update_window_cursor(w=0x00000001280208f8, on=true) at xdisp.c:34240:7
    frame #3: 0x0000000100070b1c emacs`update_cursor_in_window_tree(w=0x00000001280208f8, on_p=true) at xdisp.c:34258:2
    frame #4: 0x0000000100070aa0 emacs`gui_update_cursor(f=0x0000000128020400, on_p=true) at xdisp.c:34272:3
    frame #5: 0x0000000100344770 emacs`-[EmacsView windowDidResignKey:](self=0x000000011e912750, _cmd="windowDidResignKey:", notification=@"NSWindowDidResignKeyNotification") at nsterm.m:7960:7
    frame #6: 0x0000000184db3144 CoreFoundation`__CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ + 148
    frame #7: 0x0000000184e473d8 CoreFoundation`___CFXRegistrationPost_block_invoke + 88
    frame #8: 0x0000000184e47320 CoreFoundation`_CFXRegistrationPost + 440
    frame #9: 0x0000000184d81678 CoreFoundation`_CFXNotificationPost + 768
    frame #10: 0x0000000185e9e4e4 Foundation`-[NSNotificationCenter postNotificationName:object:userInfo:] + 88
    frame #11: 0x00000001887776fc AppKit`-[NSWindow resignKeyWindow] + 640
    frame #12: 0x00000001887773e4 AppKit`_NXEndKeyAndMain + 128
    frame #13: 0x00000001887764ec AppKit`-[NSApplication _handleDeactivateEvent:] + 724
    frame #14: 0x0000000188e106b8 AppKit`-[NSApplication(NSEventRouting) sendEvent:] + 1236
    frame #15: 0x000000010033bcd8 emacs`-[EmacsApp sendEvent:](self=0x000000012f01ee10, _cmd="sendEvent:", theEvent=0x0000600003cf5800) at nsterm.m:6073:3
    frame #16: 0x0000000188a5e89c AppKit`-[NSApplication _handleEvent:] + 60
    frame #17: 0x000000018860f0c0 AppKit`-[NSApplication run] + 512
    frame #18: 0x000000010033b838 emacs`-[EmacsApp run](self=0x000000012f01ee10, _cmd="run") at nsterm.m:5942:7
    frame #19: 0x00000001003560b0 emacs`ns_read_socket_1(terminal=0x000000012f858610, hold_quit=0x000000016fdfaf70, no_release=NO) at nsterm.m:4816:11
    frame #20: 0x000000010034fa18 emacs`ns_read_socket(terminal=0x000000012f858610, hold_quit=0x000000016fdfaf70) at nsterm.m:4834:10
    frame #21: 0x000000010016a6dc emacs`gobble_input at keyboard.c:7919:17
    frame #22: 0x000000010016ae10 emacs`handle_async_input at keyboard.c:8158:19
    frame #23: 0x000000010016adf0 emacs`process_pending_signals at keyboard.c:8172:3
    frame #24: 0x000000010016ae9c emacs`unblock_input_to(level=0) at keyboard.c:8187:2
    frame #25: 0x00000001001683a8 emacs`unblock_input at keyboard.c:8206:3
    frame #26: 0x0000000100007504 emacs`gui_update_window_end(w=0x00000001280208f8, cursor_on_p=true, mouse_face_overwritten_p=false) at dispnew.c:3955:7
    frame #27: 0x000000010000603c emacs`update_window(w=0x00000001280208f8, force_p=true) at dispnew.c:3869:7
    frame #28: 0x00000001000061c0 emacs`update_window_tree(w=0x00000001280208f8, force_p=true) at dispnew.c:3491:14
    frame #29: 0x00000001000053a0 emacs`update_frame(f=0x0000000128020400, force_p=true, inhibit_hairy_id_p=false) at dispnew.c:3326:18
    frame #30: 0x000000010004f424 emacs`redisplay_internal at xdisp.c:17480:16
    frame #31: 0x0000000100055ef8 emacs`redisplay at xdisp.c:16575:3
    frame #32: 0x0000000100161e74 emacs`read_char(commandflag=1, map=0x00000001300cbb03, prev_event=0x0000000000000000, used_mouse_menu=0x000000016fdfe807, end_time=0x0000000000000000) at keyboard.c:2678:6
    frame #33: 0x000000010015ea30 emacs`read_key_sequence(keybuf=0x000000016fdfebe8, prompt=0x0000000000000000, dont_downcase_last=false, can_return_switch_frame=true, fix_current_buffer=true, prevent_redisplay=false, disable_text_conversion_p=false) at keyboard.c:10743:12
    frame #34: 0x000000010015cdf8 emacs`command_loop_1 at keyboard.c:1429:15
    frame #35: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #36: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #37: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #38: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #39: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #40: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #41: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #42: 0x00000001849560e0 dyld`start + 2360

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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-21  0:53                       ` Dmitry Gutov
@ 2024-07-21  7:20                         ` Eli Zaretskii
  2024-07-21  9:04                           ` Eli Zaretskii
  2024-07-21 13:50                           ` Dmitry Gutov
  0 siblings, 2 replies; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-21  7:20 UTC (permalink / raw
  To: Dmitry Gutov, Alan Third; +Cc: 71866

> Date: Sun, 21 Jul 2024 03:53:26 +0300
> Cc: 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> Perhaps it'll be easier to share a video. Sorry, it's a large file, so I 
> just uploaded it to a free online hosting: https://streamable.com/d6775w
> 
> The first (smaller) part is me reproducing the bug, then I switch to the 
> terminal emulator, enable the breakpoint and demonstrate how the 
> behavior of the same command (other-frame) changes.
> 
> After the video was finished, I also repeated the same scenario, and 
> saved the backtrace of the last (12th) breakpoint hit.

Thanks.  The video shows some parts of the problem, but not enough
details.  It doesn't help that I don't know enough about the macOS GUI
system and conventions.  Here are some details that I'm missing:

  . The two frames are arranged in a way that the cursor in the
    left-most frame is not really visible when the right-most frame
    partially obscures it.  So it's hard to tell at all times what
    kind of cursor (or no cursor) is shown in that frame.  Could you
    please repeat the experiment after moving the right-most frame a
    bit to the right, so as not to obscure the cursor of the other
    frame?  IOW, I'd like to be able to see cursors in both frames
    regardless of which frame is selected/has focus.
  . Sometimes an Emacs frame shows its window as selected (judging by
    the way the mode line is displayed), but the 3 colored circles at
    the top left corner of the frame are shown in gray.  What does
    this mean, in Emacs terms, and how is that different from the
    situation where both the mode line is shown as active and the
    circles are shown in red/yellow/green colors?
  . What exactly are you doing with keyboard or mouse in the first
    part, where you quickly alternate the frames?  All I see is
    the initial mouse click inside the left-most frame, but the
    subsequent changes seemingly happen "by themselves", without any
    visible trigger.
  . The backtrace indicates that ns_draw_window_cursor is called from
    windowDidResignKey, which AFAIU is called when the focus changes.
    For some reason, display_and_set_cursor, which calls
    ns_draw_window_cursor, decided that cursor type should be
    NO_CURSOR, although gui_update_cursor was called with
    cursor_on_p=true, and the question is why?  You don't show any
    other backtraces, although in the video I clearly see them, and
    they use other values of cursor type.  In addition, I don't know
    which window passed to ns_draw_window_cursor (the 'w' argument)
    belongs to which frame, and without that, it is very hard to
    interpret the data of the debugging session, because I need to
    compare the calls with what I see in the Emacs frames.

IOW, the important question is: was the problematic display, where no
cursor is shown, caused by an incorrect call to ns_draw_window_cursor,
or was it caused by some other factor?  The data and the video you
presented does not allow to answer this questions.  Adding the missing
details I mentioned will probably help answer them.

> > But anyway, if this is the same scenario, then why are you only
> > looking at what happens inside ns_draw_window_cursor?  Redrawing the
> > block cursor involves displaying the character under cursor with
> > special colors, and ns_draw_window_cursor is just the beginning: it
> > calls other functions which actually do the job.
> 
> More breakpoints means more chances for the behavior to change. I also 
> don't really know which other places to look at. Stepping through all 
> the callees is both time-consuming and something that is unlikely to 
> help until I manage to read all of the underlying implementation and 
> start making sense of the data that's being used, to be able to notice 
> when this or that variable has an odd value.

I can explain the overall logic of the implementation if it can help.

> But maybe at this point some print-debugging might be more beneficial 
> (since that shouldn't change the existing behavior). See the linked 
> video and the attached backtrace, though.

At this point, I'm not yet sure printf-debugging could help.  Maybe
later.

Thanks.

P.S. I've added Alan to this discussion, in the hope that he could
help with understanding what is going on here.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-21  7:20                         ` Eli Zaretskii
@ 2024-07-21  9:04                           ` Eli Zaretskii
  2024-07-21 23:22                             ` Dmitry Gutov
  2024-07-21 13:50                           ` Dmitry Gutov
  1 sibling, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-21  9:04 UTC (permalink / raw
  To: dmitry; +Cc: alan, 71866

> Cc: 71866@debbugs.gnu.org
> Date: Sun, 21 Jul 2024 10:20:19 +0300
> From: Eli Zaretskii <eliz@gnu.org>
> 
> IOW, the important question is: was the problematic display, where no
> cursor is shown, caused by an incorrect call to ns_draw_window_cursor,
> or was it caused by some other factor?  The data and the video you
> presented does not allow to answer this questions.  Adding the missing
> details I mentioned will probably help answer them.

And one more request: please turn off blink-cursor-mode, so that it
doesn't get in the way.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-21  7:20                         ` Eli Zaretskii
  2024-07-21  9:04                           ` Eli Zaretskii
@ 2024-07-21 13:50                           ` Dmitry Gutov
  2024-07-21 14:55                             ` Eli Zaretskii
  1 sibling, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-21 13:50 UTC (permalink / raw
  To: Eli Zaretskii, Alan Third; +Cc: 71866

On 21/07/2024 10:20, Eli Zaretskii wrote:
>> Date: Sun, 21 Jul 2024 03:53:26 +0300
>> Cc: 71866@debbugs.gnu.org
>> From: Dmitry Gutov <dmitry@gutov.dev>
>>
>> Perhaps it'll be easier to share a video. Sorry, it's a large file, so I
>> just uploaded it to a free online hosting: https://streamable.com/d6775w
>>
>> The first (smaller) part is me reproducing the bug, then I switch to the
>> terminal emulator, enable the breakpoint and demonstrate how the
>> behavior of the same command (other-frame) changes.
>>
>> After the video was finished, I also repeated the same scenario, and
>> saved the backtrace of the last (12th) breakpoint hit.
> 
> Thanks.  The video shows some parts of the problem, but not enough
> details.  It doesn't help that I don't know enough about the macOS GUI
> system and conventions.  Here are some details that I'm missing:
> 
>    . The two frames are arranged in a way that the cursor in the
>      left-most frame is not really visible when the right-most frame
>      partially obscures it.  So it's hard to tell at all times what
>      kind of cursor (or no cursor) is shown in that frame.  Could you
>      please repeat the experiment after moving the right-most frame a
>      bit to the right, so as not to obscure the cursor of the other
>      frame?  IOW, I'd like to be able to see cursors in both frames
>      regardless of which frame is selected/has focus.

I can repeat the experiment, but in my testing the problem only occurs 
in (all) frames other than the first/original one, regardless of their 
positioning.

Also FWIW it doesn't matter whether the frames display the same buffer 
or different ones.

>    . Sometimes an Emacs frame shows its window as selected (judging by
>      the way the mode line is displayed), but the 3 colored circles at
>      the top left corner of the frame are shown in gray.  What does
>      this mean, in Emacs terms, and how is that different from the
>      situation where both the mode line is shown as active and the
>      circles are shown in red/yellow/green colors?

It seems to me a consequence of our having a breakpoint inside a 
function that updates how the frame looks (which includes its contents, 
the "selected" status and etc) - when I switch the focus away manually 
to a different program in the middle of that (to handle the breakpoint), 
probably that created a de-synchronization that never happens in other 
circumstances.

>    . What exactly are you doing with keyboard or mouse in the first
>      part, where you quickly alternate the frames?  All I see is
>      the initial mouse click inside the left-most frame, but the
>      subsequent changes seemingly happen "by themselves", without any
>      visible trigger.

That's 'other-frame', bound to 'M-`'.

>    . The backtrace indicates that ns_draw_window_cursor is called from
>      windowDidResignKey, which AFAIU is called when the focus changes.
>      For some reason, display_and_set_cursor, which calls
>      ns_draw_window_cursor, decided that cursor type should be
>      NO_CURSOR, although gui_update_cursor was called with
>      cursor_on_p=true, and the question is why?  You don't show any
>      other backtraces, although in the video I clearly see them, and
>      they use other values of cursor type.  In addition, I don't know
>      which window passed to ns_draw_window_cursor (the 'w' argument)
>      belongs to which frame, and without that, it is very hard to
>      interpret the data of the debugging session, because I need to
>      compare the calls with what I see in the Emacs frames.

Would you like to see all the other backtraces, or some specific ones? 
In the former case, that will be a lot of text to sort through.

> IOW, the important question is: was the problematic display, where no
> cursor is shown, caused by an incorrect call to ns_draw_window_cursor,
> or was it caused by some other factor?  The data and the video you
> presented does not allow to answer this questions.  Adding the missing
> details I mentioned will probably help answer them.

...and whether that all is a red herring, caused by our breakpoints, 
whereas the code reading to the original problem might reside somewhere 
else. ;-(

>>> But anyway, if this is the same scenario, then why are you only
>>> looking at what happens inside ns_draw_window_cursor?  Redrawing the
>>> block cursor involves displaying the character under cursor with
>>> special colors, and ns_draw_window_cursor is just the beginning: it
>>> calls other functions which actually do the job.
>>
>> More breakpoints means more chances for the behavior to change. I also
>> don't really know which other places to look at. Stepping through all
>> the callees is both time-consuming and something that is unlikely to
>> help until I manage to read all of the underlying implementation and
>> start making sense of the data that's being used, to be able to notice
>> when this or that variable has an odd value.
> 
> I can explain the overall logic of the implementation if it can help.

Maybe I'll ask some questions later, which I know what to ask. I can 
understand some high-level things from the backtrace already, but the 
devil is in the details.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-21 13:50                           ` Dmitry Gutov
@ 2024-07-21 14:55                             ` Eli Zaretskii
  2024-07-21 23:58                               ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-21 14:55 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: alan, 71866

> Date: Sun, 21 Jul 2024 16:50:18 +0300
> Cc: 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> >    . The two frames are arranged in a way that the cursor in the
> >      left-most frame is not really visible when the right-most frame
> >      partially obscures it.  So it's hard to tell at all times what
> >      kind of cursor (or no cursor) is shown in that frame.  Could you
> >      please repeat the experiment after moving the right-most frame a
> >      bit to the right, so as not to obscure the cursor of the other
> >      frame?  IOW, I'd like to be able to see cursors in both frames
> >      regardless of which frame is selected/has focus.
> 
> I can repeat the experiment, but in my testing the problem only occurs 
> in (all) frames other than the first/original one, regardless of their 
> positioning.

I believe you.  But I want to see both cursors, because they are
usually redrawn in tandem.

> Also FWIW it doesn't matter whether the frames display the same buffer 
> or different ones.

Yes, I know.

> >    . Sometimes an Emacs frame shows its window as selected (judging by
> >      the way the mode line is displayed), but the 3 colored circles at
> >      the top left corner of the frame are shown in gray.  What does
> >      this mean, in Emacs terms, and how is that different from the
> >      situation where both the mode line is shown as active and the
> >      circles are shown in red/yellow/green colors?
> 
> It seems to me a consequence of our having a breakpoint inside a 
> function that updates how the frame looks (which includes its contents, 
> the "selected" status and etc) - when I switch the focus away manually 
> to a different program in the middle of that (to handle the breakpoint), 
> probably that created a de-synchronization that never happens in other 
> circumstances.

If you are sure that this happens only when Emacs is stopped at a
breakpoint, this aspect of the issue can be disregarded.

> >    . What exactly are you doing with keyboard or mouse in the first
> >      part, where you quickly alternate the frames?  All I see is
> >      the initial mouse click inside the left-most frame, but the
> >      subsequent changes seemingly happen "by themselves", without any
> >      visible trigger.
> 
> That's 'other-frame', bound to 'M-`'.

OK.

> >    . The backtrace indicates that ns_draw_window_cursor is called from
> >      windowDidResignKey, which AFAIU is called when the focus changes.
> >      For some reason, display_and_set_cursor, which calls
> >      ns_draw_window_cursor, decided that cursor type should be
> >      NO_CURSOR, although gui_update_cursor was called with
> >      cursor_on_p=true, and the question is why?  You don't show any
> >      other backtraces, although in the video I clearly see them, and
> >      they use other values of cursor type.  In addition, I don't know
> >      which window passed to ns_draw_window_cursor (the 'w' argument)
> >      belongs to which frame, and without that, it is very hard to
> >      interpret the data of the debugging session, because I need to
> >      compare the calls with what I see in the Emacs frames.
> 
> Would you like to see all the other backtraces, or some specific ones? 

All of the backtraces from all the calls produced by a single M-`
press.  It is best to have only the backtraces that happen when the
problem with the cursor is visible, if you can easily arrange for
that.

> In the former case, that will be a lot of text to sort through.

Yes, but it is imperative to see all the calls.

> > IOW, the important question is: was the problematic display, where no
> > cursor is shown, caused by an incorrect call to ns_draw_window_cursor,
> > or was it caused by some other factor?  The data and the video you
> > presented does not allow to answer this questions.  Adding the missing
> > details I mentioned will probably help answer them.
> 
> ...and whether that all is a red herring, caused by our breakpoints, 
> whereas the code reading to the original problem might reside somewhere 
> else. ;-(

Could be, but in general ns_draw_window_cursor is AFAIK the only way
of redrawing the cursor, so I think we are on a good track here.

> >>> But anyway, if this is the same scenario, then why are you only
> >>> looking at what happens inside ns_draw_window_cursor?  Redrawing the
> >>> block cursor involves displaying the character under cursor with
> >>> special colors, and ns_draw_window_cursor is just the beginning: it
> >>> calls other functions which actually do the job.
> >>
> >> More breakpoints means more chances for the behavior to change. I also
> >> don't really know which other places to look at. Stepping through all
> >> the callees is both time-consuming and something that is unlikely to
> >> help until I manage to read all of the underlying implementation and
> >> start making sense of the data that's being used, to be able to notice
> >> when this or that variable has an odd value.
> > 
> > I can explain the overall logic of the implementation if it can help.
> 
> Maybe I'll ask some questions later, which I know what to ask. I can 
> understand some high-level things from the backtrace already, but the 
> devil is in the details.

Eventually, if and when we find the call which causes this incomplete
redraw, you will need to step through the code and see what happens
there.  When we get there, I will try to explain the main ideas of the
code.

Thanks.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-21  9:04                           ` Eli Zaretskii
@ 2024-07-21 23:22                             ` Dmitry Gutov
  0 siblings, 0 replies; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-21 23:22 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: alan, 71866

On 21/07/2024 12:04, Eli Zaretskii wrote:
>> Cc:71866@debbugs.gnu.org
>> Date: Sun, 21 Jul 2024 10:20:19 +0300
>> From: Eli Zaretskii<eliz@gnu.org>
>>
>> IOW, the important question is: was the problematic display, where no
>> cursor is shown, caused by an incorrect call to ns_draw_window_cursor,
>> or was it caused by some other factor?  The data and the video you
>> presented does not allow to answer this questions.  Adding the missing
>> details I mentioned will probably help answer them.
> And one more request: please turn off blink-cursor-mode, so that it
> doesn't get in the way.

FWIW, already disabled in the repro script. Just to minimize the number 
of times the cursor has to be redrawn.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-21 14:55                             ` Eli Zaretskii
@ 2024-07-21 23:58                               ` Dmitry Gutov
  2024-07-22 14:45                                 ` Eli Zaretskii
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-21 23:58 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: alan, 71866

[-- Attachment #1: Type: text/plain, Size: 5006 bytes --]

On 21/07/2024 17:55, Eli Zaretskii wrote:
>> Date: Sun, 21 Jul 2024 16:50:18 +0300
>> Cc: 71866@debbugs.gnu.org
>> From: Dmitry Gutov <dmitry@gutov.dev>
>>
>>>     . The two frames are arranged in a way that the cursor in the
>>>       left-most frame is not really visible when the right-most frame
>>>       partially obscures it.  So it's hard to tell at all times what
>>>       kind of cursor (or no cursor) is shown in that frame.  Could you
>>>       please repeat the experiment after moving the right-most frame a
>>>       bit to the right, so as not to obscure the cursor of the other
>>>       frame?  IOW, I'd like to be able to see cursors in both frames
>>>       regardless of which frame is selected/has focus.
>>
>> I can repeat the experiment, but in my testing the problem only occurs
>> in (all) frames other than the first/original one, regardless of their
>> positioning.
> 
> I believe you.  But I want to see both cursors, because they are
> usually redrawn in tandem.

No problem.

>>>     . Sometimes an Emacs frame shows its window as selected (judging by
>>>       the way the mode line is displayed), but the 3 colored circles at
>>>       the top left corner of the frame are shown in gray.  What does
>>>       this mean, in Emacs terms, and how is that different from the
>>>       situation where both the mode line is shown as active and the
>>>       circles are shown in red/yellow/green colors?
>>
>> It seems to me a consequence of our having a breakpoint inside a
>> function that updates how the frame looks (which includes its contents,
>> the "selected" status and etc) - when I switch the focus away manually
>> to a different program in the middle of that (to handle the breakpoint),
>> probably that created a de-synchronization that never happens in other
>> circumstances.
> 
> If you are sure that this happens only when Emacs is stopped at a
> breakpoint, this aspect of the issue can be disregarded.

Seems so to me. You could see the way Emacs behaves without breakpoints 
at the beginning of the previous video.

>>>     . What exactly are you doing with keyboard or mouse in the first
>>>       part, where you quickly alternate the frames?  All I see is
>>>       the initial mouse click inside the left-most frame, but the
>>>       subsequent changes seemingly happen "by themselves", without any
>>>       visible trigger.
>>
>> That's 'other-frame', bound to 'M-`'.
> 
> OK.
> 
>>>     . The backtrace indicates that ns_draw_window_cursor is called from
>>>       windowDidResignKey, which AFAIU is called when the focus changes.
>>>       For some reason, display_and_set_cursor, which calls
>>>       ns_draw_window_cursor, decided that cursor type should be
>>>       NO_CURSOR, although gui_update_cursor was called with
>>>       cursor_on_p=true, and the question is why?  You don't show any
>>>       other backtraces, although in the video I clearly see them, and
>>>       they use other values of cursor type.  In addition, I don't know
>>>       which window passed to ns_draw_window_cursor (the 'w' argument)
>>>       belongs to which frame, and without that, it is very hard to
>>>       interpret the data of the debugging session, because I need to
>>>       compare the calls with what I see in the Emacs frames.
>>
>> Would you like to see all the other backtraces, or some specific ones?
> 
> All of the backtraces from all the calls produced by a single M-`
> press.  It is best to have only the backtraces that happen when the
> problem with the cursor is visible, if you can easily arrange for
> that.

Yup, done that, see below.

>> In the former case, that will be a lot of text to sort through.
> 
> Yes, but it is imperative to see all the calls.

Very good, see this longer video where I also print the backtrace every 
time the breakpoint is hit (and then sometimes scroll up to make its top 
visible). Also attached is the text log with all 12 backtraces together.

https://streamable.com/4a1vb2

The video will be up for 24 hours at this free hosting, but I can 
reupload it later as well if somebody asks.

>>> IOW, the important question is: was the problematic display, where no
>>> cursor is shown, caused by an incorrect call to ns_draw_window_cursor,
>>> or was it caused by some other factor?  The data and the video you
>>> presented does not allow to answer this questions.  Adding the missing
>>> details I mentioned will probably help answer them.
>>
>> ...and whether that all is a red herring, caused by our breakpoints,
>> whereas the code reading to the original problem might reside somewhere
>> else. ;-(
> 
> Could be, but in general ns_draw_window_cursor is AFAIK the only way
> of redrawing the cursor, so I think we are on a good track here.

Here's hoping.

> Eventually, if and when we find the call which causes this incomplete
> redraw, you will need to step through the code and see what happens
> there.  When we get there, I will try to explain the main ideas of the
> code.

Sounds great!

[-- Attachment #2: emacs-lldb-bt-3-list.txt --]
[-- Type: text/plain, Size: 60848 bytes --]

2024-07-22 01:52:55.096460+0300 emacs[7616:3253530] [CursorUI] -[TUINSCursorUIController activate:]: EmacsView doesn't conform to NSTextInputClient protocol.
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=FILLED_BOX_CURSOR, cursor_width=1, on_p=true, active_p=true) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 1
error: '1' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=FILLED_BOX_CURSOR, cursor_width=1, on_p=true, active_p=true) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e0166d0, on=true, hpos=4, vpos=3, x=28, y=42) at xdisp.c:34205:5
    frame #2: 0x0000000100070d24 emacs`update_window_cursor(w=0x000000011e0166d0, on=true) at xdisp.c:34240:7
    frame #3: 0x0000000100070b1c emacs`update_cursor_in_window_tree(w=0x000000011e0166d0, on_p=true) at xdisp.c:34258:2
    frame #4: 0x0000000100070aa0 emacs`gui_update_cursor(f=0x000000011e016480, on_p=true) at xdisp.c:34272:3
    frame #5: 0x0000000100344638 emacs`ns_frame_rehighlight(frame=0x000000011e016480) at nsterm.m:1486:11
    frame #6: 0x0000000100344468 emacs`-[EmacsView windowDidBecomeKey](self=0x000000011b1114a0, _cmd="windowDidBecomeKey") at nsterm.m:7935:3
    frame #7: 0x00000001003443a8 emacs`-[EmacsView windowDidBecomeKey:](self=0x000000011b1114a0, _cmd="windowDidBecomeKey:", notification=@"NSWindowDidBecomeKeyNotification") at nsterm.m:7918:3
    frame #8: 0x0000000184db3144 CoreFoundation`__CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ + 148
    frame #9: 0x0000000184e473d8 CoreFoundation`___CFXRegistrationPost_block_invoke + 88
    frame #10: 0x0000000184e47320 CoreFoundation`_CFXRegistrationPost + 440
    frame #11: 0x0000000184d81678 CoreFoundation`_CFXNotificationPost + 768
    frame #12: 0x0000000185e9e4e4 Foundation`-[NSNotificationCenter postNotificationName:object:userInfo:] + 88
    frame #13: 0x000000018877062c AppKit`-[NSWindow becomeKeyWindow] + 844
    frame #14: 0x000000018871751c AppKit`-[NSWindow _changeKeyAndMainLimitedOK:] + 748
    frame #15: 0x00000001887171f0 AppKit`-[NSWindow makeKeyWindow] + 172
    frame #16: 0x0000000188716fa8 AppKit`-[NSWindow _makeKeyRegardlessOfVisibility] + 56
    frame #17: 0x000000018870f6a0 AppKit`-[NSWindow makeKeyAndOrderFront:] + 24
    frame #18: 0x0000000100349c10 emacs`-[EmacsWindow makeKeyAndOrderFront:](self=0x000000011b1118e0, _cmd="makeKeyAndOrderFront:", sender=0x000000013a61f360) at nsterm.m:9485:5
    frame #19: 0x00000001003378ec emacs`ns_raise_frame(f=0x000000011e016480, make_key=YES) at nsterm.m:1411:9
    frame #20: 0x0000000100350434 emacs`ns_frame_raise_lower(f=0x000000011e016480, raise=true) at nsterm.m:1444:5
    frame #21: 0x000000010001ebb0 emacs`Fraise_frame(frame=0x000000011e016485) at frame.c:3023:5
    frame #22: 0x000000010024c8a0 emacs`funcall_subr(subr=0x0000000100945bb0, numargs=1, args=0x0000000130100140) at eval.c:3161:15
    frame #23: 0x00000001002b2db0 emacs`exec_byte_code(fun=0x00000001024f73d5, args_template=513, nargs=1, args=0x0000000130100108) at bytecode.c:812:14
    frame #24: 0x000000010024cc58 emacs`funcall_lambda(fun=0x0000000101b2a80d, nargs=1, arg_vector=0x000000016fdfd790) at eval.c:3252:9
    frame #25: 0x000000010024c5ec emacs`funcall_general(fun=0x0000000101b2a80d, numargs=1, args=0x000000016fdfd790) at eval.c:3044:12
    frame #26: 0x0000000100245e8c emacs`Ffuncall(nargs=2, args=0x000000016fdfd788) at eval.c:3093:21
    frame #27: 0x000000010023fb20 emacs`Ffuncall_interactively(nargs=2, args=0x000000016fdfd788) at callint.c:250:32
    frame #28: 0x000000010024ca88 emacs`funcall_subr(subr=0x0000000100950f80, numargs=2, args=0x000000016fdfd788) at eval.c:3184:9
    frame #29: 0x000000010024c5a4 emacs`funcall_general(fun=0x0000000100950f85, numargs=2, args=0x000000016fdfd788) at eval.c:3040:12
    frame #30: 0x0000000100245e8c emacs`Ffuncall(nargs=3, args=0x000000016fdfd780) at eval.c:3093:21
    frame #31: 0x0000000100241d40 emacs`Fcall_interactively(function=0x000000000114a1f8, record_flag=0x0000000000000000, keys=0x00000001024ea055) at callint.c:789:21
    frame #32: 0x000000010024c8f0 emacs`funcall_subr(subr=0x0000000100950f48, numargs=3, args=0x0000000130100060) at eval.c:3165:15
    frame #33: 0x00000001002b2db0 emacs`exec_byte_code(fun=0x0000000102505935, args_template=1025, nargs=1, args=0x000000016fdfebe8) at bytecode.c:812:14
    frame #34: 0x000000010024cc58 emacs`funcall_lambda(fun=0x0000000102505935, nargs=1, arg_vector=0x000000016fdfebe0) at eval.c:3252:9
    frame #35: 0x000000010024c5ec emacs`funcall_general(fun=0x0000000102505935, numargs=1, args=0x000000016fdfebe0) at eval.c:3044:12
    frame #36: 0x0000000100245e8c emacs`Ffuncall(nargs=2, args=0x000000016fdfebd8) at eval.c:3093:21
    frame #37: 0x000000010015d28c emacs`command_loop_1 at keyboard.c:1550:13
    frame #38: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #39: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #40: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #41: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #42: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #43: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #44: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #45: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 2
error: '2' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e016978, on=true, hpos=0, vpos=0, x=0, y=0) at xdisp.c:34205:5
    frame #2: 0x0000000100070d24 emacs`update_window_cursor(w=0x000000011e016978, on=true) at xdisp.c:34240:7
    frame #3: 0x0000000100070b1c emacs`update_cursor_in_window_tree(w=0x000000011e016978, on_p=true) at xdisp.c:34258:2
    frame #4: 0x0000000100070aa0 emacs`gui_update_cursor(f=0x000000011e016480, on_p=true) at xdisp.c:34272:3
    frame #5: 0x0000000100344638 emacs`ns_frame_rehighlight(frame=0x000000011e016480) at nsterm.m:1486:11
    frame #6: 0x0000000100344468 emacs`-[EmacsView windowDidBecomeKey](self=0x000000011b1114a0, _cmd="windowDidBecomeKey") at nsterm.m:7935:3
    frame #7: 0x00000001003443a8 emacs`-[EmacsView windowDidBecomeKey:](self=0x000000011b1114a0, _cmd="windowDidBecomeKey:", notification=@"NSWindowDidBecomeKeyNotification") at nsterm.m:7918:3
    frame #8: 0x0000000184db3144 CoreFoundation`__CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ + 148
    frame #9: 0x0000000184e473d8 CoreFoundation`___CFXRegistrationPost_block_invoke + 88
    frame #10: 0x0000000184e47320 CoreFoundation`_CFXRegistrationPost + 440
    frame #11: 0x0000000184d81678 CoreFoundation`_CFXNotificationPost + 768
    frame #12: 0x0000000185e9e4e4 Foundation`-[NSNotificationCenter postNotificationName:object:userInfo:] + 88
    frame #13: 0x000000018877062c AppKit`-[NSWindow becomeKeyWindow] + 844
    frame #14: 0x000000018871751c AppKit`-[NSWindow _changeKeyAndMainLimitedOK:] + 748
    frame #15: 0x00000001887171f0 AppKit`-[NSWindow makeKeyWindow] + 172
    frame #16: 0x0000000188716fa8 AppKit`-[NSWindow _makeKeyRegardlessOfVisibility] + 56
    frame #17: 0x000000018870f6a0 AppKit`-[NSWindow makeKeyAndOrderFront:] + 24
    frame #18: 0x0000000100349c10 emacs`-[EmacsWindow makeKeyAndOrderFront:](self=0x000000011b1118e0, _cmd="makeKeyAndOrderFront:", sender=0x000000013a61f360) at nsterm.m:9485:5
    frame #19: 0x00000001003378ec emacs`ns_raise_frame(f=0x000000011e016480, make_key=YES) at nsterm.m:1411:9
    frame #20: 0x0000000100350434 emacs`ns_frame_raise_lower(f=0x000000011e016480, raise=true) at nsterm.m:1444:5
    frame #21: 0x000000010001ebb0 emacs`Fraise_frame(frame=0x000000011e016485) at frame.c:3023:5
    frame #22: 0x000000010024c8a0 emacs`funcall_subr(subr=0x0000000100945bb0, numargs=1, args=0x0000000130100140) at eval.c:3161:15
    frame #23: 0x00000001002b2db0 emacs`exec_byte_code(fun=0x00000001024f73d5, args_template=513, nargs=1, args=0x0000000130100108) at bytecode.c:812:14
    frame #24: 0x000000010024cc58 emacs`funcall_lambda(fun=0x0000000101b2a80d, nargs=1, arg_vector=0x000000016fdfd790) at eval.c:3252:9
    frame #25: 0x000000010024c5ec emacs`funcall_general(fun=0x0000000101b2a80d, numargs=1, args=0x000000016fdfd790) at eval.c:3044:12
    frame #26: 0x0000000100245e8c emacs`Ffuncall(nargs=2, args=0x000000016fdfd788) at eval.c:3093:21
    frame #27: 0x000000010023fb20 emacs`Ffuncall_interactively(nargs=2, args=0x000000016fdfd788) at callint.c:250:32
    frame #28: 0x000000010024ca88 emacs`funcall_subr(subr=0x0000000100950f80, numargs=2, args=0x000000016fdfd788) at eval.c:3184:9
    frame #29: 0x000000010024c5a4 emacs`funcall_general(fun=0x0000000100950f85, numargs=2, args=0x000000016fdfd788) at eval.c:3040:12
    frame #30: 0x0000000100245e8c emacs`Ffuncall(nargs=3, args=0x000000016fdfd780) at eval.c:3093:21
    frame #31: 0x0000000100241d40 emacs`Fcall_interactively(function=0x000000000114a1f8, record_flag=0x0000000000000000, keys=0x00000001024ea055) at callint.c:789:21
    frame #32: 0x000000010024c8f0 emacs`funcall_subr(subr=0x0000000100950f48, numargs=3, args=0x0000000130100060) at eval.c:3165:15
    frame #33: 0x00000001002b2db0 emacs`exec_byte_code(fun=0x0000000102505935, args_template=1025, nargs=1, args=0x000000016fdfebe8) at bytecode.c:812:14
    frame #34: 0x000000010024cc58 emacs`funcall_lambda(fun=0x0000000102505935, nargs=1, arg_vector=0x000000016fdfebe0) at eval.c:3252:9
    frame #35: 0x000000010024c5ec emacs`funcall_general(fun=0x0000000102505935, numargs=1, args=0x000000016fdfebe0) at eval.c:3044:12
    frame #36: 0x0000000100245e8c emacs`Ffuncall(nargs=2, args=0x000000016fdfebd8) at eval.c:3093:21
    frame #37: 0x000000010015d28c emacs`command_loop_1 at keyboard.c:1550:13
    frame #38: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #39: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #40: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #41: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #42: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #43: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #44: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #45: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming
2024-07-22 01:53:24.789888+0300 emacs[7616:3253530] [CursorUI] -[TUINSCursorUIController activate:]: EmacsView doesn't conform to NSTextInputClient protocol.
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=HOLLOW_BOX_CURSOR, cursor_width=1, on_p=true, active_p=false) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 3
error: '3' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=HOLLOW_BOX_CURSOR, cursor_width=1, on_p=true, active_p=false) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e0166d0, on=true, hpos=4, vpos=3, x=28, y=42) at xdisp.c:34205:5
    frame #2: 0x0000000100070d24 emacs`update_window_cursor(w=0x000000011e0166d0, on=true) at xdisp.c:34240:7
    frame #3: 0x0000000100070b1c emacs`update_cursor_in_window_tree(w=0x000000011e0166d0, on_p=true) at xdisp.c:34258:2
    frame #4: 0x0000000100070aa0 emacs`gui_update_cursor(f=0x000000011e016480, on_p=true) at xdisp.c:34272:3
    frame #5: 0x0000000100344770 emacs`-[EmacsView windowDidResignKey:](self=0x000000011b1114a0, _cmd="windowDidResignKey:", notification=@"NSWindowDidResignKeyNotification") at nsterm.m:7960:7
    frame #6: 0x0000000184db3144 CoreFoundation`__CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ + 148
    frame #7: 0x0000000184e473d8 CoreFoundation`___CFXRegistrationPost_block_invoke + 88
    frame #8: 0x0000000184e47320 CoreFoundation`_CFXRegistrationPost + 440
    frame #9: 0x0000000184d81678 CoreFoundation`_CFXNotificationPost + 768
    frame #10: 0x0000000185e9e4e4 Foundation`-[NSNotificationCenter postNotificationName:object:userInfo:] + 88
    frame #11: 0x00000001887776fc AppKit`-[NSWindow resignKeyWindow] + 640
    frame #12: 0x00000001887773e4 AppKit`_NXEndKeyAndMain + 128
    frame #13: 0x00000001887764ec AppKit`-[NSApplication _handleDeactivateEvent:] + 724
    frame #14: 0x0000000188e106b8 AppKit`-[NSApplication(NSEventRouting) sendEvent:] + 1236
    frame #15: 0x000000010033bcd8 emacs`-[EmacsApp sendEvent:](self=0x000000013a61f360, _cmd="sendEvent:", theEvent=0x0000600000c44a80) at nsterm.m:6073:3
    frame #16: 0x0000000188a5e89c AppKit`-[NSApplication _handleEvent:] + 60
    frame #17: 0x000000018860f0c0 AppKit`-[NSApplication run] + 512
    frame #18: 0x000000010033b838 emacs`-[EmacsApp run](self=0x000000013a61f360, _cmd="run") at nsterm.m:5942:7
    frame #19: 0x00000001003560b0 emacs`ns_read_socket_1(terminal=0x000000012a834c10, hold_quit=0x000000016fdfcae0, no_release=NO) at nsterm.m:4816:11
    frame #20: 0x000000010034fa18 emacs`ns_read_socket(terminal=0x000000012a834c10, hold_quit=0x000000016fdfcae0) at nsterm.m:4834:10
    frame #21: 0x000000010016a6dc emacs`gobble_input at keyboard.c:7919:17
    frame #22: 0x000000010016ae10 emacs`handle_async_input at keyboard.c:8158:19
    frame #23: 0x000000010016adf0 emacs`process_pending_signals at keyboard.c:8172:3
    frame #24: 0x000000010016ae9c emacs`unblock_input_to(level=0) at keyboard.c:8187:2
    frame #25: 0x00000001001683a8 emacs`unblock_input at keyboard.c:8206:3
    frame #26: 0x000000010033791c emacs`ns_raise_frame(f=0x000000011e016480, make_key=YES) at nsterm.m:1415:3
    frame #27: 0x0000000100350434 emacs`ns_frame_raise_lower(f=0x000000011e016480, raise=true) at nsterm.m:1444:5
    frame #28: 0x000000010001ebb0 emacs`Fraise_frame(frame=0x000000011e016485) at frame.c:3023:5
    frame #29: 0x000000010024c8a0 emacs`funcall_subr(subr=0x0000000100945bb0, numargs=1, args=0x0000000130100140) at eval.c:3161:15
    frame #30: 0x00000001002b2db0 emacs`exec_byte_code(fun=0x00000001024f73d5, args_template=513, nargs=1, args=0x0000000130100108) at bytecode.c:812:14
    frame #31: 0x000000010024cc58 emacs`funcall_lambda(fun=0x0000000101b2a80d, nargs=1, arg_vector=0x000000016fdfd790) at eval.c:3252:9
    frame #32: 0x000000010024c5ec emacs`funcall_general(fun=0x0000000101b2a80d, numargs=1, args=0x000000016fdfd790) at eval.c:3044:12
    frame #33: 0x0000000100245e8c emacs`Ffuncall(nargs=2, args=0x000000016fdfd788) at eval.c:3093:21
    frame #34: 0x000000010023fb20 emacs`Ffuncall_interactively(nargs=2, args=0x000000016fdfd788) at callint.c:250:32
    frame #35: 0x000000010024ca88 emacs`funcall_subr(subr=0x0000000100950f80, numargs=2, args=0x000000016fdfd788) at eval.c:3184:9
    frame #36: 0x000000010024c5a4 emacs`funcall_general(fun=0x0000000100950f85, numargs=2, args=0x000000016fdfd788) at eval.c:3040:12
    frame #37: 0x0000000100245e8c emacs`Ffuncall(nargs=3, args=0x000000016fdfd780) at eval.c:3093:21
    frame #38: 0x0000000100241d40 emacs`Fcall_interactively(function=0x000000000114a1f8, record_flag=0x0000000000000000, keys=0x00000001024ea055) at callint.c:789:21
    frame #39: 0x000000010024c8f0 emacs`funcall_subr(subr=0x0000000100950f48, numargs=3, args=0x0000000130100060) at eval.c:3165:15
    frame #40: 0x00000001002b2db0 emacs`exec_byte_code(fun=0x0000000102505935, args_template=1025, nargs=1, args=0x000000016fdfebe8) at bytecode.c:812:14
    frame #41: 0x000000010024cc58 emacs`funcall_lambda(fun=0x0000000102505935, nargs=1, arg_vector=0x000000016fdfebe0) at eval.c:3252:9
    frame #42: 0x000000010024c5ec emacs`funcall_general(fun=0x0000000102505935, numargs=1, args=0x000000016fdfebe0) at eval.c:3044:12
    frame #43: 0x0000000100245e8c emacs`Ffuncall(nargs=2, args=0x000000016fdfebd8) at eval.c:3093:21
    frame #44: 0x000000010015d28c emacs`command_loop_1 at keyboard.c:1550:13
    frame #45: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #46: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #47: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #48: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #49: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #50: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #51: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #52: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 4
error: '4' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e016978, on=true, hpos=0, vpos=0, x=0, y=0) at xdisp.c:34205:5
    frame #2: 0x0000000100070d24 emacs`update_window_cursor(w=0x000000011e016978, on=true) at xdisp.c:34240:7
    frame #3: 0x0000000100070b1c emacs`update_cursor_in_window_tree(w=0x000000011e016978, on_p=true) at xdisp.c:34258:2
    frame #4: 0x0000000100070aa0 emacs`gui_update_cursor(f=0x000000011e016480, on_p=true) at xdisp.c:34272:3
    frame #5: 0x0000000100344770 emacs`-[EmacsView windowDidResignKey:](self=0x000000011b1114a0, _cmd="windowDidResignKey:", notification=@"NSWindowDidResignKeyNotification") at nsterm.m:7960:7
    frame #6: 0x0000000184db3144 CoreFoundation`__CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ + 148
    frame #7: 0x0000000184e473d8 CoreFoundation`___CFXRegistrationPost_block_invoke + 88
    frame #8: 0x0000000184e47320 CoreFoundation`_CFXRegistrationPost + 440
    frame #9: 0x0000000184d81678 CoreFoundation`_CFXNotificationPost + 768
    frame #10: 0x0000000185e9e4e4 Foundation`-[NSNotificationCenter postNotificationName:object:userInfo:] + 88
    frame #11: 0x00000001887776fc AppKit`-[NSWindow resignKeyWindow] + 640
    frame #12: 0x00000001887773e4 AppKit`_NXEndKeyAndMain + 128
    frame #13: 0x00000001887764ec AppKit`-[NSApplication _handleDeactivateEvent:] + 724
    frame #14: 0x0000000188e106b8 AppKit`-[NSApplication(NSEventRouting) sendEvent:] + 1236
    frame #15: 0x000000010033bcd8 emacs`-[EmacsApp sendEvent:](self=0x000000013a61f360, _cmd="sendEvent:", theEvent=0x0000600000c44a80) at nsterm.m:6073:3
    frame #16: 0x0000000188a5e89c AppKit`-[NSApplication _handleEvent:] + 60
    frame #17: 0x000000018860f0c0 AppKit`-[NSApplication run] + 512
    frame #18: 0x000000010033b838 emacs`-[EmacsApp run](self=0x000000013a61f360, _cmd="run") at nsterm.m:5942:7
    frame #19: 0x00000001003560b0 emacs`ns_read_socket_1(terminal=0x000000012a834c10, hold_quit=0x000000016fdfcae0, no_release=NO) at nsterm.m:4816:11
    frame #20: 0x000000010034fa18 emacs`ns_read_socket(terminal=0x000000012a834c10, hold_quit=0x000000016fdfcae0) at nsterm.m:4834:10
    frame #21: 0x000000010016a6dc emacs`gobble_input at keyboard.c:7919:17
    frame #22: 0x000000010016ae10 emacs`handle_async_input at keyboard.c:8158:19
    frame #23: 0x000000010016adf0 emacs`process_pending_signals at keyboard.c:8172:3
    frame #24: 0x000000010016ae9c emacs`unblock_input_to(level=0) at keyboard.c:8187:2
    frame #25: 0x00000001001683a8 emacs`unblock_input at keyboard.c:8206:3
    frame #26: 0x000000010033791c emacs`ns_raise_frame(f=0x000000011e016480, make_key=YES) at nsterm.m:1415:3
    frame #27: 0x0000000100350434 emacs`ns_frame_raise_lower(f=0x000000011e016480, raise=true) at nsterm.m:1444:5
    frame #28: 0x000000010001ebb0 emacs`Fraise_frame(frame=0x000000011e016485) at frame.c:3023:5
    frame #29: 0x000000010024c8a0 emacs`funcall_subr(subr=0x0000000100945bb0, numargs=1, args=0x0000000130100140) at eval.c:3161:15
    frame #30: 0x00000001002b2db0 emacs`exec_byte_code(fun=0x00000001024f73d5, args_template=513, nargs=1, args=0x0000000130100108) at bytecode.c:812:14
    frame #31: 0x000000010024cc58 emacs`funcall_lambda(fun=0x0000000101b2a80d, nargs=1, arg_vector=0x000000016fdfd790) at eval.c:3252:9
    frame #32: 0x000000010024c5ec emacs`funcall_general(fun=0x0000000101b2a80d, numargs=1, args=0x000000016fdfd790) at eval.c:3044:12
    frame #33: 0x0000000100245e8c emacs`Ffuncall(nargs=2, args=0x000000016fdfd788) at eval.c:3093:21
    frame #34: 0x000000010023fb20 emacs`Ffuncall_interactively(nargs=2, args=0x000000016fdfd788) at callint.c:250:32
    frame #35: 0x000000010024ca88 emacs`funcall_subr(subr=0x0000000100950f80, numargs=2, args=0x000000016fdfd788) at eval.c:3184:9
    frame #36: 0x000000010024c5a4 emacs`funcall_general(fun=0x0000000100950f85, numargs=2, args=0x000000016fdfd788) at eval.c:3040:12
    frame #37: 0x0000000100245e8c emacs`Ffuncall(nargs=3, args=0x000000016fdfd780) at eval.c:3093:21
    frame #38: 0x0000000100241d40 emacs`Fcall_interactively(function=0x000000000114a1f8, record_flag=0x0000000000000000, keys=0x00000001024ea055) at callint.c:789:21
    frame #39: 0x000000010024c8f0 emacs`funcall_subr(subr=0x0000000100950f48, numargs=3, args=0x0000000130100060) at eval.c:3165:15
    frame #40: 0x00000001002b2db0 emacs`exec_byte_code(fun=0x0000000102505935, args_template=1025, nargs=1, args=0x000000016fdfebe8) at bytecode.c:812:14
    frame #41: 0x000000010024cc58 emacs`funcall_lambda(fun=0x0000000102505935, nargs=1, arg_vector=0x000000016fdfebe0) at eval.c:3252:9
    frame #42: 0x000000010024c5ec emacs`funcall_general(fun=0x0000000102505935, numargs=1, args=0x000000016fdfebe0) at eval.c:3044:12
    frame #43: 0x0000000100245e8c emacs`Ffuncall(nargs=2, args=0x000000016fdfebd8) at eval.c:3093:21
    frame #44: 0x000000010015d28c emacs`command_loop_1 at keyboard.c:1550:13
    frame #45: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #46: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #47: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #48: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #49: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #50: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #51: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #52: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=HOLLOW_BOX_CURSOR, cursor_width=1, on_p=true, active_p=false) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 5
error: '5' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=HOLLOW_BOX_CURSOR, cursor_width=1, on_p=true, active_p=false) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e0166d0, on=true, hpos=4, vpos=3, x=28, y=42) at xdisp.c:34205:5
    frame #2: 0x000000010000740c emacs`gui_update_window_end(w=0x000000011e0166d0, cursor_on_p=true, mouse_face_overwritten_p=false) at dispnew.c:3941:2
    frame #3: 0x000000010000603c emacs`update_window(w=0x000000011e0166d0, force_p=true) at dispnew.c:3869:7
    frame #4: 0x00000001000061c0 emacs`update_window_tree(w=0x000000011e0166d0, force_p=true) at dispnew.c:3491:14
    frame #5: 0x00000001000053a0 emacs`update_frame(f=0x000000011e016480, force_p=true, inhibit_hairy_id_p=false) at dispnew.c:3326:18
    frame #6: 0x000000010004f424 emacs`redisplay_internal at xdisp.c:17480:16
    frame #7: 0x0000000100055ef8 emacs`redisplay at xdisp.c:16575:3
    frame #8: 0x0000000100161e74 emacs`read_char(commandflag=1, map=0x000000013004cd23, prev_event=0x0000000000000000, used_mouse_menu=0x000000016fdfe807, end_time=0x0000000000000000) at keyboard.c:2678:6
    frame #9: 0x000000010015ea30 emacs`read_key_sequence(keybuf=0x000000016fdfebe8, prompt=0x0000000000000000, dont_downcase_last=false, can_return_switch_frame=true, fix_current_buffer=true, prevent_redisplay=false, disable_text_conversion_p=false) at keyboard.c:10743:12
    frame #10: 0x000000010015cdf8 emacs`command_loop_1 at keyboard.c:1429:15
    frame #11: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #12: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #13: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #14: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #15: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #16: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #17: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #18: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=HOLLOW_BOX_CURSOR, cursor_width=1, on_p=true, active_p=false) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 6
error: '6' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=HOLLOW_BOX_CURSOR, cursor_width=1, on_p=true, active_p=false) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e0166d0, on=true, hpos=4, vpos=3, x=28, y=42) at xdisp.c:34205:5
    frame #2: 0x000000010000740c emacs`gui_update_window_end(w=0x000000011e0166d0, cursor_on_p=true, mouse_face_overwritten_p=false) at dispnew.c:3941:2
    frame #3: 0x000000010000603c emacs`update_window(w=0x000000011e0166d0, force_p=true) at dispnew.c:3869:7
    frame #4: 0x00000001000061c0 emacs`update_window_tree(w=0x000000011e0166d0, force_p=true) at dispnew.c:3491:14
    frame #5: 0x00000001000053a0 emacs`update_frame(f=0x000000011e016480, force_p=true, inhibit_hairy_id_p=false) at dispnew.c:3326:18
    frame #6: 0x000000010004f424 emacs`redisplay_internal at xdisp.c:17480:16
    frame #7: 0x0000000100055ef8 emacs`redisplay at xdisp.c:16575:3
    frame #8: 0x0000000100161e74 emacs`read_char(commandflag=1, map=0x000000013004cd23, prev_event=0x0000000000000000, used_mouse_menu=0x000000016fdfe807, end_time=0x0000000000000000) at keyboard.c:2678:6
    frame #9: 0x000000010015ea30 emacs`read_key_sequence(keybuf=0x000000016fdfebe8, prompt=0x0000000000000000, dont_downcase_last=false, can_return_switch_frame=true, fix_current_buffer=true, prevent_redisplay=false, disable_text_conversion_p=false) at keyboard.c:10743:12
    frame #10: 0x000000010015cdf8 emacs`command_loop_1 at keyboard.c:1429:15
    frame #11: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #12: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #13: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #14: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #15: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #16: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #17: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #18: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=FILLED_BOX_CURSOR, cursor_width=1, on_p=true, active_p=true) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 7
error: '7' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=FILLED_BOX_CURSOR, cursor_width=1, on_p=true, active_p=true) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e0166d0, on=true, hpos=4, vpos=3, x=28, y=42) at xdisp.c:34205:5
    frame #2: 0x0000000100070d24 emacs`update_window_cursor(w=0x000000011e0166d0, on=true) at xdisp.c:34240:7
    frame #3: 0x0000000100070b1c emacs`update_cursor_in_window_tree(w=0x000000011e0166d0, on_p=true) at xdisp.c:34258:2
    frame #4: 0x0000000100070aa0 emacs`gui_update_cursor(f=0x000000011e016480, on_p=true) at xdisp.c:34272:3
    frame #5: 0x0000000100344638 emacs`ns_frame_rehighlight(frame=0x000000011e016480) at nsterm.m:1486:11
    frame #6: 0x0000000100344468 emacs`-[EmacsView windowDidBecomeKey](self=0x000000011b1114a0, _cmd="windowDidBecomeKey") at nsterm.m:7935:3
    frame #7: 0x00000001003443a8 emacs`-[EmacsView windowDidBecomeKey:](self=0x000000011b1114a0, _cmd="windowDidBecomeKey:", notification=@"NSWindowDidBecomeKeyNotification") at nsterm.m:7918:3
    frame #8: 0x0000000184db3144 CoreFoundation`__CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ + 148
    frame #9: 0x0000000184e473d8 CoreFoundation`___CFXRegistrationPost_block_invoke + 88
    frame #10: 0x0000000184e47320 CoreFoundation`_CFXRegistrationPost + 440
    frame #11: 0x0000000184d81678 CoreFoundation`_CFXNotificationPost + 768
    frame #12: 0x0000000185e9e4e4 Foundation`-[NSNotificationCenter postNotificationName:object:userInfo:] + 88
    frame #13: 0x000000018877062c AppKit`-[NSWindow becomeKeyWindow] + 844
    frame #14: 0x000000018876f55c AppKit`_NXShowKeyAndMain + 132
    frame #15: 0x000000018876d924 AppKit`-[NSApplication _handleActivatedEvent:] + 1332
    frame #16: 0x0000000188e108d8 AppKit`-[NSApplication(NSEventRouting) sendEvent:] + 1780
    frame #17: 0x000000010033bcd8 emacs`-[EmacsApp sendEvent:](self=0x000000013a61f360, _cmd="sendEvent:", theEvent=0x0000600000c7c240) at nsterm.m:6073:3
    frame #18: 0x0000000188a5e89c AppKit`-[NSApplication _handleEvent:] + 60
    frame #19: 0x000000018860f0c0 AppKit`-[NSApplication run] + 512
    frame #20: 0x000000010033b838 emacs`-[EmacsApp run](self=0x000000013a61f360, _cmd="run") at nsterm.m:5942:7
    frame #21: 0x00000001003560b0 emacs`ns_read_socket_1(terminal=0x000000012a834c10, hold_quit=0x000000016fdfaf70, no_release=NO) at nsterm.m:4816:11
    frame #22: 0x000000010034fa18 emacs`ns_read_socket(terminal=0x000000012a834c10, hold_quit=0x000000016fdfaf70) at nsterm.m:4834:10
    frame #23: 0x000000010016a6dc emacs`gobble_input at keyboard.c:7919:17
    frame #24: 0x000000010016ae10 emacs`handle_async_input at keyboard.c:8158:19
    frame #25: 0x000000010016adf0 emacs`process_pending_signals at keyboard.c:8172:3
    frame #26: 0x000000010016ae9c emacs`unblock_input_to(level=0) at keyboard.c:8187:2
    frame #27: 0x00000001001683a8 emacs`unblock_input at keyboard.c:8206:3
    frame #28: 0x0000000100007504 emacs`gui_update_window_end(w=0x000000011e0166d0, cursor_on_p=true, mouse_face_overwritten_p=false) at dispnew.c:3955:7
    frame #29: 0x000000010000603c emacs`update_window(w=0x000000011e0166d0, force_p=true) at dispnew.c:3869:7
    frame #30: 0x00000001000061c0 emacs`update_window_tree(w=0x000000011e0166d0, force_p=true) at dispnew.c:3491:14
    frame #31: 0x00000001000053a0 emacs`update_frame(f=0x000000011e016480, force_p=true, inhibit_hairy_id_p=false) at dispnew.c:3326:18
    frame #32: 0x000000010004f424 emacs`redisplay_internal at xdisp.c:17480:16
    frame #33: 0x0000000100055ef8 emacs`redisplay at xdisp.c:16575:3
    frame #34: 0x0000000100161e74 emacs`read_char(commandflag=1, map=0x000000013004cd23, prev_event=0x0000000000000000, used_mouse_menu=0x000000016fdfe807, end_time=0x0000000000000000) at keyboard.c:2678:6
    frame #35: 0x000000010015ea30 emacs`read_key_sequence(keybuf=0x000000016fdfebe8, prompt=0x0000000000000000, dont_downcase_last=false, can_return_switch_frame=true, fix_current_buffer=true, prevent_redisplay=false, disable_text_conversion_p=false) at keyboard.c:10743:12
    frame #36: 0x000000010015cdf8 emacs`command_loop_1 at keyboard.c:1429:15
    frame #37: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #38: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #39: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #40: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #41: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #42: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #43: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #44: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 8
error: '8' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e016978, on=true, hpos=0, vpos=0, x=0, y=0) at xdisp.c:34205:5
    frame #2: 0x0000000100070d24 emacs`update_window_cursor(w=0x000000011e016978, on=true) at xdisp.c:34240:7
    frame #3: 0x0000000100070b1c emacs`update_cursor_in_window_tree(w=0x000000011e016978, on_p=true) at xdisp.c:34258:2
    frame #4: 0x0000000100070aa0 emacs`gui_update_cursor(f=0x000000011e016480, on_p=true) at xdisp.c:34272:3
    frame #5: 0x0000000100344638 emacs`ns_frame_rehighlight(frame=0x000000011e016480) at nsterm.m:1486:11
    frame #6: 0x0000000100344468 emacs`-[EmacsView windowDidBecomeKey](self=0x000000011b1114a0, _cmd="windowDidBecomeKey") at nsterm.m:7935:3
    frame #7: 0x00000001003443a8 emacs`-[EmacsView windowDidBecomeKey:](self=0x000000011b1114a0, _cmd="windowDidBecomeKey:", notification=@"NSWindowDidBecomeKeyNotification") at nsterm.m:7918:3
    frame #8: 0x0000000184db3144 CoreFoundation`__CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ + 148
    frame #9: 0x0000000184e473d8 CoreFoundation`___CFXRegistrationPost_block_invoke + 88
    frame #10: 0x0000000184e47320 CoreFoundation`_CFXRegistrationPost + 440
    frame #11: 0x0000000184d81678 CoreFoundation`_CFXNotificationPost + 768
    frame #12: 0x0000000185e9e4e4 Foundation`-[NSNotificationCenter postNotificationName:object:userInfo:] + 88
    frame #13: 0x000000018877062c AppKit`-[NSWindow becomeKeyWindow] + 844
    frame #14: 0x000000018876f55c AppKit`_NXShowKeyAndMain + 132
    frame #15: 0x000000018876d924 AppKit`-[NSApplication _handleActivatedEvent:] + 1332
    frame #16: 0x0000000188e108d8 AppKit`-[NSApplication(NSEventRouting) sendEvent:] + 1780
    frame #17: 0x000000010033bcd8 emacs`-[EmacsApp sendEvent:](self=0x000000013a61f360, _cmd="sendEvent:", theEvent=0x0000600000c7c240) at nsterm.m:6073:3
    frame #18: 0x0000000188a5e89c AppKit`-[NSApplication _handleEvent:] + 60
    frame #19: 0x000000018860f0c0 AppKit`-[NSApplication run] + 512
    frame #20: 0x000000010033b838 emacs`-[EmacsApp run](self=0x000000013a61f360, _cmd="run") at nsterm.m:5942:7
    frame #21: 0x00000001003560b0 emacs`ns_read_socket_1(terminal=0x000000012a834c10, hold_quit=0x000000016fdfaf70, no_release=NO) at nsterm.m:4816:11
    frame #22: 0x000000010034fa18 emacs`ns_read_socket(terminal=0x000000012a834c10, hold_quit=0x000000016fdfaf70) at nsterm.m:4834:10
    frame #23: 0x000000010016a6dc emacs`gobble_input at keyboard.c:7919:17
    frame #24: 0x000000010016ae10 emacs`handle_async_input at keyboard.c:8158:19
    frame #25: 0x000000010016adf0 emacs`process_pending_signals at keyboard.c:8172:3
    frame #26: 0x000000010016ae9c emacs`unblock_input_to(level=0) at keyboard.c:8187:2
    frame #27: 0x00000001001683a8 emacs`unblock_input at keyboard.c:8206:3
    frame #28: 0x0000000100007504 emacs`gui_update_window_end(w=0x000000011e0166d0, cursor_on_p=true, mouse_face_overwritten_p=false) at dispnew.c:3955:7
    frame #29: 0x000000010000603c emacs`update_window(w=0x000000011e0166d0, force_p=true) at dispnew.c:3869:7
    frame #30: 0x00000001000061c0 emacs`update_window_tree(w=0x000000011e0166d0, force_p=true) at dispnew.c:3491:14
    frame #31: 0x00000001000053a0 emacs`update_frame(f=0x000000011e016480, force_p=true, inhibit_hairy_id_p=false) at dispnew.c:3326:18
    frame #32: 0x000000010004f424 emacs`redisplay_internal at xdisp.c:17480:16
    frame #33: 0x0000000100055ef8 emacs`redisplay at xdisp.c:16575:3
    frame #34: 0x0000000100161e74 emacs`read_char(commandflag=1, map=0x000000013004cd23, prev_event=0x0000000000000000, used_mouse_menu=0x000000016fdfe807, end_time=0x0000000000000000) at keyboard.c:2678:6
    frame #35: 0x000000010015ea30 emacs`read_key_sequence(keybuf=0x000000016fdfebe8, prompt=0x0000000000000000, dont_downcase_last=false, can_return_switch_frame=true, fix_current_buffer=true, prevent_redisplay=false, disable_text_conversion_p=false) at keyboard.c:10743:12
    frame #36: 0x000000010015cdf8 emacs`command_loop_1 at keyboard.c:1429:15
    frame #37: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #38: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #39: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #40: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #41: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #42: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #43: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #44: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming
2024-07-22 01:54:26.708313+0300 emacs[7616:3253530] [CursorUI] -[TUINSCursorUIController activate:]: EmacsView doesn't conform to NSTextInputClient protocol.
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=HOLLOW_BOX_CURSOR, cursor_width=1, on_p=true, active_p=false) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 9
error: '9' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e0166d0, glyph_row=0x000000011e91fd00, x=28, y=42, cursor_type=HOLLOW_BOX_CURSOR, cursor_width=1, on_p=true, active_p=false) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e0166d0, on=true, hpos=4, vpos=3, x=28, y=42) at xdisp.c:34205:5
    frame #2: 0x0000000100070d24 emacs`update_window_cursor(w=0x000000011e0166d0, on=true) at xdisp.c:34240:7
    frame #3: 0x0000000100070b1c emacs`update_cursor_in_window_tree(w=0x000000011e0166d0, on_p=true) at xdisp.c:34258:2
    frame #4: 0x0000000100070aa0 emacs`gui_update_cursor(f=0x000000011e016480, on_p=true) at xdisp.c:34272:3
    frame #5: 0x0000000100344770 emacs`-[EmacsView windowDidResignKey:](self=0x000000011b1114a0, _cmd="windowDidResignKey:", notification=@"NSWindowDidResignKeyNotification") at nsterm.m:7960:7
    frame #6: 0x0000000184db3144 CoreFoundation`__CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ + 148
    frame #7: 0x0000000184e473d8 CoreFoundation`___CFXRegistrationPost_block_invoke + 88
    frame #8: 0x0000000184e47320 CoreFoundation`_CFXRegistrationPost + 440
    frame #9: 0x0000000184d81678 CoreFoundation`_CFXNotificationPost + 768
    frame #10: 0x0000000185e9e4e4 Foundation`-[NSNotificationCenter postNotificationName:object:userInfo:] + 88
    frame #11: 0x00000001887776fc AppKit`-[NSWindow resignKeyWindow] + 640
    frame #12: 0x00000001887773e4 AppKit`_NXEndKeyAndMain + 128
    frame #13: 0x00000001887764ec AppKit`-[NSApplication _handleDeactivateEvent:] + 724
    frame #14: 0x0000000188e106b8 AppKit`-[NSApplication(NSEventRouting) sendEvent:] + 1236
    frame #15: 0x000000010033bcd8 emacs`-[EmacsApp sendEvent:](self=0x000000013a61f360, _cmd="sendEvent:", theEvent=0x0000600000c74540) at nsterm.m:6073:3
    frame #16: 0x0000000188a5e89c AppKit`-[NSApplication _handleEvent:] + 60
    frame #17: 0x000000018860f0c0 AppKit`-[NSApplication run] + 512
    frame #18: 0x000000010033b838 emacs`-[EmacsApp run](self=0x000000013a61f360, _cmd="run") at nsterm.m:5942:7
    frame #19: 0x00000001003560b0 emacs`ns_read_socket_1(terminal=0x000000012a834c10, hold_quit=0x000000016fdfaf70, no_release=NO) at nsterm.m:4816:11
    frame #20: 0x000000010034fa18 emacs`ns_read_socket(terminal=0x000000012a834c10, hold_quit=0x000000016fdfaf70) at nsterm.m:4834:10
    frame #21: 0x000000010016a6dc emacs`gobble_input at keyboard.c:7919:17
    frame #22: 0x000000010016ae10 emacs`handle_async_input at keyboard.c:8158:19
    frame #23: 0x000000010016adf0 emacs`process_pending_signals at keyboard.c:8172:3
    frame #24: 0x000000010016ae9c emacs`unblock_input_to(level=0) at keyboard.c:8187:2
    frame #25: 0x00000001001683a8 emacs`unblock_input at keyboard.c:8206:3
    frame #26: 0x0000000100007504 emacs`gui_update_window_end(w=0x000000011e0166d0, cursor_on_p=true, mouse_face_overwritten_p=false) at dispnew.c:3955:7
    frame #27: 0x000000010000603c emacs`update_window(w=0x000000011e0166d0, force_p=true) at dispnew.c:3869:7
    frame #28: 0x00000001000061c0 emacs`update_window_tree(w=0x000000011e0166d0, force_p=true) at dispnew.c:3491:14
    frame #29: 0x00000001000053a0 emacs`update_frame(f=0x000000011e016480, force_p=true, inhibit_hairy_id_p=false) at dispnew.c:3326:18
    frame #30: 0x000000010004f424 emacs`redisplay_internal at xdisp.c:17480:16
    frame #31: 0x0000000100055ef8 emacs`redisplay at xdisp.c:16575:3
    frame #32: 0x0000000100161e74 emacs`read_char(commandflag=1, map=0x000000013004cd23, prev_event=0x0000000000000000, used_mouse_menu=0x000000016fdfe807, end_time=0x0000000000000000) at keyboard.c:2678:6
    frame #33: 0x000000010015ea30 emacs`read_key_sequence(keybuf=0x000000016fdfebe8, prompt=0x0000000000000000, dont_downcase_last=false, can_return_switch_frame=true, fix_current_buffer=true, prevent_redisplay=false, disable_text_conversion_p=false) at keyboard.c:10743:12
    frame #34: 0x000000010015cdf8 emacs`command_loop_1 at keyboard.c:1429:15
    frame #35: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #36: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #37: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #38: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #39: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #40: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #41: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #42: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 10
error: '10' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e016978, on=true, hpos=0, vpos=0, x=0, y=0) at xdisp.c:34205:5
    frame #2: 0x0000000100070d24 emacs`update_window_cursor(w=0x000000011e016978, on=true) at xdisp.c:34240:7
    frame #3: 0x0000000100070b1c emacs`update_cursor_in_window_tree(w=0x000000011e016978, on_p=true) at xdisp.c:34258:2
    frame #4: 0x0000000100070aa0 emacs`gui_update_cursor(f=0x000000011e016480, on_p=true) at xdisp.c:34272:3
    frame #5: 0x0000000100344770 emacs`-[EmacsView windowDidResignKey:](self=0x000000011b1114a0, _cmd="windowDidResignKey:", notification=@"NSWindowDidResignKeyNotification") at nsterm.m:7960:7
    frame #6: 0x0000000184db3144 CoreFoundation`__CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ + 148
    frame #7: 0x0000000184e473d8 CoreFoundation`___CFXRegistrationPost_block_invoke + 88
    frame #8: 0x0000000184e47320 CoreFoundation`_CFXRegistrationPost + 440
    frame #9: 0x0000000184d81678 CoreFoundation`_CFXNotificationPost + 768
    frame #10: 0x0000000185e9e4e4 Foundation`-[NSNotificationCenter postNotificationName:object:userInfo:] + 88
    frame #11: 0x00000001887776fc AppKit`-[NSWindow resignKeyWindow] + 640
    frame #12: 0x00000001887773e4 AppKit`_NXEndKeyAndMain + 128
    frame #13: 0x00000001887764ec AppKit`-[NSApplication _handleDeactivateEvent:] + 724
    frame #14: 0x0000000188e106b8 AppKit`-[NSApplication(NSEventRouting) sendEvent:] + 1236
    frame #15: 0x000000010033bcd8 emacs`-[EmacsApp sendEvent:](self=0x000000013a61f360, _cmd="sendEvent:", theEvent=0x0000600000c74540) at nsterm.m:6073:3
    frame #16: 0x0000000188a5e89c AppKit`-[NSApplication _handleEvent:] + 60
    frame #17: 0x000000018860f0c0 AppKit`-[NSApplication run] + 512
    frame #18: 0x000000010033b838 emacs`-[EmacsApp run](self=0x000000013a61f360, _cmd="run") at nsterm.m:5942:7
    frame #19: 0x00000001003560b0 emacs`ns_read_socket_1(terminal=0x000000012a834c10, hold_quit=0x000000016fdfaf70, no_release=NO) at nsterm.m:4816:11
    frame #20: 0x000000010034fa18 emacs`ns_read_socket(terminal=0x000000012a834c10, hold_quit=0x000000016fdfaf70) at nsterm.m:4834:10
    frame #21: 0x000000010016a6dc emacs`gobble_input at keyboard.c:7919:17
    frame #22: 0x000000010016ae10 emacs`handle_async_input at keyboard.c:8158:19
    frame #23: 0x000000010016adf0 emacs`process_pending_signals at keyboard.c:8172:3
    frame #24: 0x000000010016ae9c emacs`unblock_input_to(level=0) at keyboard.c:8187:2
    frame #25: 0x00000001001683a8 emacs`unblock_input at keyboard.c:8206:3
    frame #26: 0x0000000100007504 emacs`gui_update_window_end(w=0x000000011e0166d0, cursor_on_p=true, mouse_face_overwritten_p=false) at dispnew.c:3955:7
    frame #27: 0x000000010000603c emacs`update_window(w=0x000000011e0166d0, force_p=true) at dispnew.c:3869:7
    frame #28: 0x00000001000061c0 emacs`update_window_tree(w=0x000000011e0166d0, force_p=true) at dispnew.c:3491:14
    frame #29: 0x00000001000053a0 emacs`update_frame(f=0x000000011e016480, force_p=true, inhibit_hairy_id_p=false) at dispnew.c:3326:18
    frame #30: 0x000000010004f424 emacs`redisplay_internal at xdisp.c:17480:16
    frame #31: 0x0000000100055ef8 emacs`redisplay at xdisp.c:16575:3
    frame #32: 0x0000000100161e74 emacs`read_char(commandflag=1, map=0x000000013004cd23, prev_event=0x0000000000000000, used_mouse_menu=0x000000016fdfe807, end_time=0x0000000000000000) at keyboard.c:2678:6
    frame #33: 0x000000010015ea30 emacs`read_key_sequence(keybuf=0x000000016fdfebe8, prompt=0x0000000000000000, dont_downcase_last=false, can_return_switch_frame=true, fix_current_buffer=true, prevent_redisplay=false, disable_text_conversion_p=false) at keyboard.c:10743:12
    frame #34: 0x000000010015cdf8 emacs`command_loop_1 at keyboard.c:1429:15
    frame #35: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #36: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #37: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #38: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #39: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #40: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #41: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #42: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 11
error: '11' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e016978, on=true, hpos=0, vpos=0, x=0, y=0) at xdisp.c:34205:5
    frame #2: 0x000000010000740c emacs`gui_update_window_end(w=0x000000011e016978, cursor_on_p=true, mouse_face_overwritten_p=false) at dispnew.c:3941:2
    frame #3: 0x000000010000603c emacs`update_window(w=0x000000011e016978, force_p=true) at dispnew.c:3869:7
    frame #4: 0x00000001000061c0 emacs`update_window_tree(w=0x000000011e016978, force_p=true) at dispnew.c:3491:14
    frame #5: 0x00000001000053a0 emacs`update_frame(f=0x000000011e016480, force_p=true, inhibit_hairy_id_p=false) at dispnew.c:3326:18
    frame #6: 0x000000010004f424 emacs`redisplay_internal at xdisp.c:17480:16
    frame #7: 0x0000000100055ef8 emacs`redisplay at xdisp.c:16575:3
    frame #8: 0x0000000100161e74 emacs`read_char(commandflag=1, map=0x000000013004cd23, prev_event=0x0000000000000000, used_mouse_menu=0x000000016fdfe807, end_time=0x0000000000000000) at keyboard.c:2678:6
    frame #9: 0x000000010015ea30 emacs`read_key_sequence(keybuf=0x000000016fdfebe8, prompt=0x0000000000000000, dont_downcase_last=false, can_return_switch_frame=true, fix_current_buffer=true, prevent_redisplay=false, disable_text_conversion_p=false) at keyboard.c:10743:12
    frame #10: 0x000000010015cdf8 emacs`command_loop_1 at keyboard.c:1429:15
    frame #11: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #12: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #13: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #14: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #15: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #16: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #17: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #18: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming
Process 7616 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
    frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
   3042	  if (!on_p)
   3043	    return;
   3044
-> 3045	  w->phys_cursor_type = cursor_type;
   3046	  w->phys_cursor_on_p = on_p;
   3047
   3048	  if (cursor_type == NO_CURSOR)
Target 0: (emacs) stopped.
(lldb) 12
error: '12' is not a valid command.
(lldb) bt
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 2.1
  * frame #0: 0x0000000100354f44 emacs`ns_draw_window_cursor(w=0x000000011e016978, glyph_row=0x000000011e81f000, x=0, y=0, cursor_type=NO_CURSOR, cursor_width=0, on_p=true, active_p=false) at nsterm.m:3045:25
    frame #1: 0x000000010007035c emacs`display_and_set_cursor(w=0x000000011e016978, on=true, hpos=0, vpos=0, x=0, y=0) at xdisp.c:34205:5
    frame #2: 0x000000010000740c emacs`gui_update_window_end(w=0x000000011e016978, cursor_on_p=true, mouse_face_overwritten_p=false) at dispnew.c:3941:2
    frame #3: 0x000000010000603c emacs`update_window(w=0x000000011e016978, force_p=true) at dispnew.c:3869:7
    frame #4: 0x00000001000061c0 emacs`update_window_tree(w=0x000000011e016978, force_p=true) at dispnew.c:3491:14
    frame #5: 0x00000001000053a0 emacs`update_frame(f=0x000000011e016480, force_p=true, inhibit_hairy_id_p=false) at dispnew.c:3326:18
    frame #6: 0x000000010004f424 emacs`redisplay_internal at xdisp.c:17480:16
    frame #7: 0x0000000100055ef8 emacs`redisplay at xdisp.c:16575:3
    frame #8: 0x0000000100161e74 emacs`read_char(commandflag=1, map=0x000000013004cd23, prev_event=0x0000000000000000, used_mouse_menu=0x000000016fdfe807, end_time=0x0000000000000000) at keyboard.c:2678:6
    frame #9: 0x000000010015ea30 emacs`read_key_sequence(keybuf=0x000000016fdfebe8, prompt=0x0000000000000000, dont_downcase_last=false, can_return_switch_frame=true, fix_current_buffer=true, prevent_redisplay=false, disable_text_conversion_p=false) at keyboard.c:10743:12
    frame #10: 0x000000010015cdf8 emacs`command_loop_1 at keyboard.c:1429:15
    frame #11: 0x000000010024923c emacs`internal_condition_case(bfun=(emacs`command_loop_1 at keyboard.c:1324), handlers=0x0000000000000090, hfun=(emacs`cmd_error at keyboard.c:970)) at eval.c:1613:25
    frame #12: 0x000000010015c8c4 emacs`command_loop_2(handlers=0x0000000000000090) at keyboard.c:1168:11
    frame #13: 0x00000001002484d4 emacs`internal_catch(tag=0x0000000000011220, func=(emacs`command_loop_2 at keyboard.c:1164), arg=0x0000000000000090) at eval.c:1292:25
    frame #14: 0x000000010015bc10 emacs`command_loop at keyboard.c:1146:2
    frame #15: 0x000000010015b9fc emacs`recursive_edit_1 at keyboard.c:754:9
    frame #16: 0x000000010015bee8 emacs`Frecursive_edit at keyboard.c:837:3
    frame #17: 0x0000000100158ac8 emacs`main(argc=4, argv=0x000000016fdff4b0) at emacs.c:2624:3
    frame #18: 0x00000001849560e0 dyld`start + 2360
(lldb) c
Process 7616 resuming

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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-21 23:58                               ` Dmitry Gutov
@ 2024-07-22 14:45                                 ` Eli Zaretskii
  2024-07-22 15:27                                   ` Alan Third
  2024-07-23  1:06                                   ` Dmitry Gutov
  0 siblings, 2 replies; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-22 14:45 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: alan, 71866

> Date: Mon, 22 Jul 2024 02:58:33 +0300
> Cc: alan@idiocy.org, 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> >>>     . Sometimes an Emacs frame shows its window as selected (judging by
> >>>       the way the mode line is displayed), but the 3 colored circles at
> >>>       the top left corner of the frame are shown in gray.  What does
> >>>       this mean, in Emacs terms, and how is that different from the
> >>>       situation where both the mode line is shown as active and the
> >>>       circles are shown in red/yellow/green colors?
> >>
> >> It seems to me a consequence of our having a breakpoint inside a
> >> function that updates how the frame looks (which includes its contents,
> >> the "selected" status and etc) - when I switch the focus away manually
> >> to a different program in the middle of that (to handle the breakpoint),
> >> probably that created a de-synchronization that never happens in other
> >> circumstances.
> > 
> > If you are sure that this happens only when Emacs is stopped at a
> > breakpoint, this aspect of the issue can be disregarded.
> 
> Seems so to me. You could see the way Emacs behaves without breakpoints 
> at the beginning of the previous video.

But note that both at the beginning of this new video and at its end,
where the debugger says "resuming" (which means Emacs is running), the
3 circles of both Emacs frames are gray.  So I guess (a) this does
happen when Emacs runs, and (b) it probably means focus is in some
other window, not in any of the Emacs frames.

> > All of the backtraces from all the calls produced by a single M-`
> > press.  It is best to have only the backtraces that happen when the
> > problem with the cursor is visible, if you can easily arrange for
> > that.
> 
> Yup, done that, see below.

Thanks.  There's a disturbing discrepancy between what the debugger
says about the calls to ns_draw_window_cursor and what I see on
display.  For example, there are only 2 events where one of the two
Emacs frames begins showing a filled-block cursor (from some other
cursor display): at step "1" and step "3".  But the backtraces you
collected tell a different story: the only calls with
FILLED_BOX_CURSOR are at steps "1" and "7".  At step "3", the debugger
claims we called ns_draw_window_cursor with NO_CURSOR, whereas the
video clearly shows that the cursor is drawn as a filled block!  This
issue alone already makes all this quite mysterious and hard to
interpret.

Moreover, the only event in the video where a previously-displayed
cursor disappears in one of the windows is the last part, where you
type "c" and the debugger says "Process 7616 resuming".  And that
happens without ns_draw_window_cursor being called!

So I think there's some factor at work here that we are not
considering.  Perhaps it's the macOS window-system or something.

I also don't understand the calls where cursor_type=NO_CURSOR,
on_p=true, and active_p=false.  I would expect to see
HOLLOW_BOX_CURSOR there, because these are the calls where we display
the cursor in a non-selected window.  Could you step inside
get_window_cursor_type and see how this happens?  To arrange for that,
get to the step before the one where the breakpoint in
ns_draw_window_cursor will break with the above combination of
arguments (for example, get to step "3" in your session), then add a
breakpoint in display_and_set_cursor, trigger the next cursor display
by typing "continue", then step through display_and_set_cursor and
into get_window_cursor_type, and see why we end up deciding to display
NO_CURSOR in that case.

Also, what are your values of cursor-type and
cursor-in-non-selected-windows?

> >> ...and whether that all is a red herring, caused by our breakpoints,
> >> whereas the code reading to the original problem might reside somewhere
> >> else. ;-(
> > 
> > Could be, but in general ns_draw_window_cursor is AFAIK the only way
> > of redrawing the cursor, so I think we are on a good track here.
> 
> Here's hoping.

I'm no longer so sure about the above assertion, sadly.

Thanks.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-22 14:45                                 ` Eli Zaretskii
@ 2024-07-22 15:27                                   ` Alan Third
  2024-07-22 16:02                                     ` Alan Third
  2024-07-22 16:10                                     ` Eli Zaretskii
  2024-07-23  1:06                                   ` Dmitry Gutov
  1 sibling, 2 replies; 50+ messages in thread
From: Alan Third @ 2024-07-22 15:27 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: Dmitry Gutov, 71866

On Mon, Jul 22, 2024 at 05:45:44PM +0300, Eli Zaretskii wrote:
> 
> Thanks.  There's a disturbing discrepancy between what the debugger
> says about the calls to ns_draw_window_cursor and what I see on
> display.  For example, there are only 2 events where one of the two
> Emacs frames begins showing a filled-block cursor (from some other
> cursor display): at step "1" and step "3".  But the backtraces you
> collected tell a different story: the only calls with
> FILLED_BOX_CURSOR are at steps "1" and "7".  At step "3", the debugger
> claims we called ns_draw_window_cursor with NO_CURSOR, whereas the
> video clearly shows that the cursor is drawn as a filled block!  This
> issue alone already makes all this quite mysterious and hard to
> interpret.
> 
> Moreover, the only event in the video where a previously-displayed
> cursor disappears in one of the windows is the last part, where you
> type "c" and the debugger says "Process 7616 resuming".  And that
> happens without ns_draw_window_cursor being called!
> 
> So I think there's some factor at work here that we are not
> considering.  Perhaps it's the macOS window-system or something.

Hi Eli,

The macOS display system is inherently double buffered, so there's no
way to draw directly to the screen. This means any action taken won't
be displayed on the screen until the NS run loop has run at least
once. That occurs in the ns_select and ns_read_socket functions.

> > > Could be, but in general ns_draw_window_cursor is AFAIK the only way
> > > of redrawing the cursor, so I think we are on a good track here.
> > 
> > Here's hoping.
> 
> I'm no longer so sure about the above assertion, sadly.

AFAIK it's the only way of *drawing* the cursor, but it's certainly
possible that something else is *clearing* that space and not
redrawing the cursor. Unfortunately I've no idea what that might be.

I had a bug open myself about a very similar problem, possibly the
same problem, but I closed it years ago because it just disappeared
and nobody else had ever reported anything similar. I was never able
to get to the bottom of it.
-- 
Alan Third





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-22 15:27                                   ` Alan Third
@ 2024-07-22 16:02                                     ` Alan Third
  2024-07-23  1:11                                       ` Dmitry Gutov
  2024-07-22 16:10                                     ` Eli Zaretskii
  1 sibling, 1 reply; 50+ messages in thread
From: Alan Third @ 2024-07-22 16:02 UTC (permalink / raw
  To: Eli Zaretskii, Dmitry Gutov, 71866

On Mon, Jul 22, 2024 at 04:27:30PM +0100, Alan Third wrote:
> 
> AFAIK it's the only way of *drawing* the cursor, but it's certainly
> possible that something else is *clearing* that space and not
> redrawing the cursor. Unfortunately I've no idea what that might be.

FWIW, and apologies if you've already noticed this, but on my Mac I
can see it drawing a white hollow box cursor on the second frame when
the first frame is selected. I can see it overlapping some of the
characters.

Is it possible you're seeing a white box cursor with white text
instead of a black box cursor with white text?

A little git archaeology shows that the colour handling used to be a
lot more complicated, but it was simplified some time ago. I don't
understand what the old code was doing, and colour handling on the NS
port was always a little different for some reason...
-- 
Alan Third





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-22 15:27                                   ` Alan Third
  2024-07-22 16:02                                     ` Alan Third
@ 2024-07-22 16:10                                     ` Eli Zaretskii
  2024-07-22 19:02                                       ` Alan Third
  1 sibling, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-22 16:10 UTC (permalink / raw
  To: Alan Third; +Cc: dmitry, 71866

> Date: Mon, 22 Jul 2024 16:27:30 +0100
> From: Alan Third <alan@idiocy.org>
> Cc: Dmitry Gutov <dmitry@gutov.dev>, 71866@debbugs.gnu.org
> 
> On Mon, Jul 22, 2024 at 05:45:44PM +0300, Eli Zaretskii wrote:
> > 
> > Thanks.  There's a disturbing discrepancy between what the debugger
> > says about the calls to ns_draw_window_cursor and what I see on
> > display.  For example, there are only 2 events where one of the two
> > Emacs frames begins showing a filled-block cursor (from some other
> > cursor display): at step "1" and step "3".  But the backtraces you
> > collected tell a different story: the only calls with
> > FILLED_BOX_CURSOR are at steps "1" and "7".  At step "3", the debugger
> > claims we called ns_draw_window_cursor with NO_CURSOR, whereas the
> > video clearly shows that the cursor is drawn as a filled block!  This
> > issue alone already makes all this quite mysterious and hard to
> > interpret.
> > 
> > Moreover, the only event in the video where a previously-displayed
> > cursor disappears in one of the windows is the last part, where you
> > type "c" and the debugger says "Process 7616 resuming".  And that
> > happens without ns_draw_window_cursor being called!
> > 
> > So I think there's some factor at work here that we are not
> > considering.  Perhaps it's the macOS window-system or something.
> 
> Hi Eli,
> 
> The macOS display system is inherently double buffered, so there's no
> way to draw directly to the screen. This means any action taken won't
> be displayed on the screen until the NS run loop has run at least
> once. That occurs in the ns_select and ns_read_socket functions.

So how would you suggest to arrange the breakpoints to be able to
match calls to ns_draw_window_cursor with what appears on the screen?

Or maybe we can call some function after ns_draw_window_cursor returns
to make sure the results of ns_draw_window_cursor are immediately
shown on the glass?





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-22 16:10                                     ` Eli Zaretskii
@ 2024-07-22 19:02                                       ` Alan Third
  2024-07-22 19:15                                         ` Eli Zaretskii
  0 siblings, 1 reply; 50+ messages in thread
From: Alan Third @ 2024-07-22 19:02 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: dmitry, 71866

On Mon, Jul 22, 2024 at 07:10:18PM +0300, Eli Zaretskii wrote:
> So how would you suggest to arrange the breakpoints to be able to
> match calls to ns_draw_window_cursor with what appears on the screen?
>
> Or maybe we can call some function after ns_draw_window_cursor returns
> to make sure the results of ns_draw_window_cursor are immediately
> shown on the glass?

I'm not sure if it's possible. The whole thing runs asynchronously.
The best bet would be to put this:

  [[FRAME_NS_VIEW (f) layer] display];

at the end of ns_draw_window_cursor and look at it after that, but the
display function passes a bitmap off to a system that supposedly tells
the graphics card to pull in the bitmap using DMA and display it, all
in a separate thread. So whether it will work or not I don't know.

It may be possible to access the bitmap and dump it to a file...

  CGContextRef context = [(EmacsLayer *)[FRAME_NS_VIEW (f) layer] getContext];
  CGContextFlush (context);
  void *pixels = CGBitmapContextGetData (context);
  NSLog(@"pixels: %p, bytes: %lu, %lux%lu", pixels,
        CGBitmapContextGetHeight (context) *
        CGBitmapContextGetBytesPerRow (context),
        CGBitmapContextGetHeight (context),
        CGBitmapContextGetWidth (context));

Just before the final ns_unfocus in ns_draw_window_cursor should
provide data about the image, and in lldb something like

  mem read -o ~/image.raw --count 10000 pixels --force

should dump the raw pixels to disk and in theory imagemagick or
something could read them, but I'm failing to make this work. I think
count is not bytes, and either way I can't convince imagemagick to
read the output.

Sorry, I'm not a lot of help.
-- 
Alan Third





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-22 19:02                                       ` Alan Third
@ 2024-07-22 19:15                                         ` Eli Zaretskii
  2024-07-22 19:47                                           ` Alan Third
  0 siblings, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-22 19:15 UTC (permalink / raw
  To: Alan Third; +Cc: dmitry, 71866

> Date: Mon, 22 Jul 2024 20:02:25 +0100
> From: Alan Third <alan@idiocy.org>
> Cc: dmitry@gutov.dev, 71866@debbugs.gnu.org
> 
> On Mon, Jul 22, 2024 at 07:10:18PM +0300, Eli Zaretskii wrote:
> > So how would you suggest to arrange the breakpoints to be able to
> > match calls to ns_draw_window_cursor with what appears on the screen?
> >
> > Or maybe we can call some function after ns_draw_window_cursor returns
> > to make sure the results of ns_draw_window_cursor are immediately
> > shown on the glass?
> 
> I'm not sure if it's possible. The whole thing runs asynchronously.
> The best bet would be to put this:
> 
>   [[FRAME_NS_VIEW (f) layer] display];
> 
> at the end of ns_draw_window_cursor and look at it after that, but the
> display function passes a bitmap off to a system that supposedly tells
> the graphics card to pull in the bitmap using DMA and display it, all
> in a separate thread. So whether it will work or not I don't know.
> 
> It may be possible to access the bitmap and dump it to a file...
> 
>   CGContextRef context = [(EmacsLayer *)[FRAME_NS_VIEW (f) layer] getContext];
>   CGContextFlush (context);
>   void *pixels = CGBitmapContextGetData (context);
>   NSLog(@"pixels: %p, bytes: %lu, %lux%lu", pixels,
>         CGBitmapContextGetHeight (context) *
>         CGBitmapContextGetBytesPerRow (context),
>         CGBitmapContextGetHeight (context),
>         CGBitmapContextGetWidth (context));
> 
> Just before the final ns_unfocus in ns_draw_window_cursor should
> provide data about the image, and in lldb something like
> 
>   mem read -o ~/image.raw --count 10000 pixels --force
> 
> should dump the raw pixels to disk and in theory imagemagick or
> something could read them, but I'm failing to make this work. I think
> count is not bytes, and either way I can't convince imagemagick to
> read the output.

Hmm... doesn't sound very practical to me.

Are there any other ways of understanding why the cursor is sometimes
not shown (and at times even the character under the cursor is not
shown as well)?  If the relation between what the code does and what's
on display is basically impenetrable, how do people debug Emacs
display issues on macOS?





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-22 19:15                                         ` Eli Zaretskii
@ 2024-07-22 19:47                                           ` Alan Third
  0 siblings, 0 replies; 50+ messages in thread
From: Alan Third @ 2024-07-22 19:47 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: dmitry, 71866

On Mon, Jul 22, 2024 at 10:15:17PM +0300, Eli Zaretskii wrote:
> 
> Are there any other ways of understanding why the cursor is sometimes
> not shown (and at times even the character under the cursor is not
> shown as well)?  If the relation between what the code does and what's
> on display is basically impenetrable, how do people debug Emacs
> display issues on macOS?

With great difficulty. My usual go-to is to make things print in
unusual colours, like using:

  [[NSColor systemRedColor] set]

before some graphics code. Or just print endless reams of text with
coordinates, etc.

There's probably some smart way of doing it, but I don't know it.

-- 
Alan Third





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-22 14:45                                 ` Eli Zaretskii
  2024-07-22 15:27                                   ` Alan Third
@ 2024-07-23  1:06                                   ` Dmitry Gutov
  2024-07-23 11:17                                     ` Eli Zaretskii
  1 sibling, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-23  1:06 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: alan, 71866

On 22/07/2024 17:45, Eli Zaretskii wrote:

> But note that both at the beginning of this new video and at its end,
> where the debugger says "resuming" (which means Emacs is running), the
> 3 circles of both Emacs frames are gray.  So I guess (a) this does
> happen when Emacs runs, and (b) it probably means focus is in some
> other window, not in any of the Emacs frames.

Yes, I started this second video with focus in the terminal emulator (on 
the right - you could see that I was typing there some into text for the 
person watching). So that seems fine, no bug there.

Then I switch to the first Emacs frame, and its chrome becomes colored.

We spend most of the video in the terminal emulator as well (which is 
necessary for me to handle the breakpoints), so overall that's expected. 
You could notice somewhere in the middle of the video that after I 
handle a bunch of breakpoints the focus finally shifts to Emacs, second 
frame. But more breakpoints hit, so I have to switch back to the 
terminal emulator until the end of the recording.

>>> All of the backtraces from all the calls produced by a single M-`
>>> press.  It is best to have only the backtraces that happen when the
>>> problem with the cursor is visible, if you can easily arrange for
>>> that.
>>
>> Yup, done that, see below.
> 
> Thanks.  There's a disturbing discrepancy between what the debugger
> says about the calls to ns_draw_window_cursor and what I see on
> display.  For example, there are only 2 events where one of the two
> Emacs frames begins showing a filled-block cursor (from some other
> cursor display): at step "1" and step "3".  But the backtraces you
> collected tell a different story: the only calls with
> FILLED_BOX_CURSOR are at steps "1" and "7".  At step "3", the debugger
> claims we called ns_draw_window_cursor with NO_CURSOR, whereas the
> video clearly shows that the cursor is drawn as a filled block!  This
> issue alone already makes all this quite mysterious and hard to
> interpret.

That sounds interesting but a bit too complex for me to address, for now.

> Moreover, the only event in the video where a previously-displayed
> cursor disappears in one of the windows is the last part, where you
> type "c" and the debugger says "Process 7616 resuming".  And that
> happens without ns_draw_window_cursor being called!

I think that could still have happened in ns_draw_window_cursor.

We hit the breakpoint at the beginning of the function, right? So when I 
just choose 'continue' the rest of the function executes, and the thing 
with the cursor might happen then.

> I also don't understand the calls where cursor_type=NO_CURSOR,
> on_p=true, and active_p=false.  I would expect to see
> HOLLOW_BOX_CURSOR there, because these are the calls where we display
> the cursor in a non-selected window.  Could you step inside
> get_window_cursor_type and see how this happens?  To arrange for that,
> get to the step before the one where the breakpoint in
> ns_draw_window_cursor will break with the above combination of
> arguments (for example, get to step "3" in your session), then add a
> breakpoint in display_and_set_cursor, trigger the next cursor display
> by typing "continue", then step through display_and_set_cursor and
> into get_window_cursor_type, and see why we end up deciding to display
> NO_CURSOR in that case.

Thanks for the instructions, I think I'll do that tomorrow.

> Also, what are your values of cursor-type and
> cursor-in-non-selected-windows?

The defaults (or the default for the platform, maybe): cursor-type is t, 
cursor-in-non-selected-windows is t.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-22 16:02                                     ` Alan Third
@ 2024-07-23  1:11                                       ` Dmitry Gutov
  2024-07-23 11:19                                         ` Eli Zaretskii
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-23  1:11 UTC (permalink / raw
  To: Alan Third, Eli Zaretskii, 71866

On 22/07/2024 19:02, Alan Third wrote:
> On Mon, Jul 22, 2024 at 04:27:30PM +0100, Alan Third wrote:
>>
>> AFAIK it's the only way of *drawing* the cursor, but it's certainly
>> possible that something else is *clearing* that space and not
>> redrawing the cursor. Unfortunately I've no idea what that might be.
> 
> FWIW, and apologies if you've already noticed this, but on my Mac I
> can see it drawing a white hollow box cursor on the second frame when
> the first frame is selected. I can see it overlapping some of the
> characters.

Not really - I've never seen what you've described. :-(

The artifact that I see only happens when the frame in question is the 
selected one.  When I switch to the frame, the character under cursor 
becomes blank. When I switch away, the character becomes visible again.

> Is it possible you're seeing a white box cursor with white text
> instead of a black box cursor with white text?

Perhaps if Emacs only uses the said "white box cursor" for the active 
frame only? And only when certain characters are under the cursor?

TBF in my custom config I see a more advanced version of this (many/most 
characters become blank under cursor after switching to some secondary 
frame) - but still that doesn't seem to happen in non-selected frames.

> A little git archaeology shows that the colour handling used to be a
> lot more complicated, but it was simplified some time ago. I don't
> understand what the old code was doing, and colour handling on the NS
> port was always a little different for some reason...






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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-10  2:56       ` Dmitry Gutov
@ 2024-07-23  7:40         ` Gerd Möllmann
  2024-07-24  0:56           ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Gerd Möllmann @ 2024-07-23  7:40 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: Stefan Kangas, 71866

Dmitry Gutov <dmitry@gutov.dev> writes:

> On 09/07/2024 21:22, Stefan Kangas wrote:
>> Dmitry Gutov <dmitry@gutov.dev> writes:
>> 
>>> Not sure what is the difference between our machines - but mine is an M3
>>> Pro, FWIW.
>> M2 Pro here, using the latest version of various libraries available
>> on
>> Homebrew.
>> Maybe some build flags or features are different?
>
> Right, I don't have pass any explicit flags to configure.
>
>> Configured using:
>>   'configure --enable-checking=yes,glyphs
>>   --enable-check-lisp-object-type'
>
> ...but I have just recompiled after re-running configure with the
> above options, and the bug still reproduces. Not 'make boostrap',
> though, just './configure ...' and then 'make'.
>
>> Configured features:
>> ACL GNUTLS LCMS2 LIBXML2 MODULES NOTIFY KQUEUE NS PDUMPER PNG SQLITE3
>> THREADS TOOLKIT_SCROLL_BARS TREE_SITTER ZLIB
>
> LCMS2, PNG, SQLITE3 are not in my list, otherwise it's the same.

I can reproduce this with current master, but only with the font
Cascadia Mono. Tried a number of different fonts like Fira Code and
Monaco. Cascadia comes from Homebrew, BTW.

And now to my pet peeve :-). Dmitry could you please comment out the
calls to redisplay (2 of them) in nsterm.m and try again?

(A little background: When compiled with ASAN, one can see that these
calls can access invalid data in a face cache and so on.)






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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-23  1:06                                   ` Dmitry Gutov
@ 2024-07-23 11:17                                     ` Eli Zaretskii
  0 siblings, 0 replies; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-23 11:17 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: alan, 71866

> Date: Tue, 23 Jul 2024 04:06:39 +0300
> Cc: alan@idiocy.org, 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> > Moreover, the only event in the video where a previously-displayed
> > cursor disappears in one of the windows is the last part, where you
> > type "c" and the debugger says "Process 7616 resuming".  And that
> > happens without ns_draw_window_cursor being called!
> 
> I think that could still have happened in ns_draw_window_cursor.
> 
> We hit the breakpoint at the beginning of the function, right? So when I 
> just choose 'continue' the rest of the function executes, and the thing 
> with the cursor might happen then.

No, because ns_draw_window_cursor was called with
cursor_type=NO_CURSOR, and in that case the function returns a couple
of lines below the breakpoint without doing anything.

So I think Alan is right, and this is the effect of the macOS built-in
double-buffering of the GUI display.  But in that case there's no hope
for us to match the code being stepped through with what's on the
glass.

> > Also, what are your values of cursor-type and
> > cursor-in-non-selected-windows?
> 
> The defaults (or the default for the platform, maybe): cursor-type is t, 
> cursor-in-non-selected-windows is t.

That's what I thought, in which case the mystery of NO_CURSOR still
stands.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-23  1:11                                       ` Dmitry Gutov
@ 2024-07-23 11:19                                         ` Eli Zaretskii
  2024-07-24  0:48                                           ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-23 11:19 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: alan, 71866

> Date: Tue, 23 Jul 2024 04:11:56 +0300
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> > Is it possible you're seeing a white box cursor with white text
> > instead of a black box cursor with white text?
> 
> Perhaps if Emacs only uses the said "white box cursor" for the active 
> frame only? And only when certain characters are under the cursor?
> 
> TBF in my custom config I see a more advanced version of this (many/most 
> characters become blank under cursor after switching to some secondary 
> frame) - but still that doesn't seem to happen in non-selected frames.

That sounds like clipping to me.  (It should be followed by drawing in
the clipped region, but for some reason isn't.)  Emacs sometimes clips
and clears a region around the cursor if it thinks redrawing the
cursor will affect neighboring characters.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-23 11:19                                         ` Eli Zaretskii
@ 2024-07-24  0:48                                           ` Dmitry Gutov
  2024-07-24 11:32                                             ` Eli Zaretskii
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-24  0:48 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: alan, 71866

On 23/07/2024 14:19, Eli Zaretskii wrote:
>> Date: Tue, 23 Jul 2024 04:11:56 +0300
>> From: Dmitry Gutov<dmitry@gutov.dev>
>>
>>> Is it possible you're seeing a white box cursor with white text
>>> instead of a black box cursor with white text?
>> Perhaps if Emacs only uses the said "white box cursor" for the active
>> frame only? And only when certain characters are under the cursor?
>>
>> TBF in my custom config I see a more advanced version of this (many/most
>> characters become blank under cursor after switching to some secondary
>> frame) - but still that doesn't seem to happen in non-selected frames.
> That sounds like clipping to me.  (It should be followed by drawing in
> the clipped region, but for some reason isn't.)  Emacs sometimes clips
> and clears a region around the cursor if it thinks redrawing the
> cursor will affect neighboring characters.

Just to clarify: in each of those cases only one char is blanked at a 
time, it's just that with my personal config I don't have to try so hard 
to reproduce it (don't have to put the cursor over 's', let's just say).





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-23  7:40         ` Gerd Möllmann
@ 2024-07-24  0:56           ` Dmitry Gutov
  2024-07-24  3:48             ` Gerd Möllmann
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-24  0:56 UTC (permalink / raw
  To: Gerd Möllmann; +Cc: Stefan Kangas, 71866

On 23/07/2024 10:40, Gerd Möllmann wrote:

> I can reproduce this with current master, but only with the font
> Cascadia Mono. Tried a number of different fonts like Fira Code and
> Monaco. Cascadia comes from Homebrew, BTW.

Thanks! Indeed, the font is a requirement. I installed it from somewhere 
else, though (an archive on Github, maybe).

> And now to my pet peeve :-). Dmitry could you please comment out the
> calls to redisplay (2 of them) in nsterm.m and try again?

I've tried that now, but it didn't seem to help. Does it make a 
difference on your system?

> (A little background: When compiled with ASAN, one can see that these
> calls can access invalid data in a face cache and so on.)






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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-24  0:56           ` Dmitry Gutov
@ 2024-07-24  3:48             ` Gerd Möllmann
  2024-07-24 19:16               ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Gerd Möllmann @ 2024-07-24  3:48 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: Stefan Kangas, 71866

Dmitry Gutov <dmitry@gutov.dev> writes:

> On 23/07/2024 10:40, Gerd Möllmann wrote:
>
>> I can reproduce this with current master, but only with the font
>> Cascadia Mono. Tried a number of different fonts like Fira Code and
>> Monaco. Cascadia comes from Homebrew, BTW.
>
> Thanks! Indeed, the font is a requirement. I installed it from
> somewhere else, though (an archive on Github, maybe).
>
>> And now to my pet peeve :-). Dmitry could you please comment out the
>> calls to redisplay (2 of them) in nsterm.m and try again?
>
> I've tried that now, but it didn't seem to help. Does it make a
> difference on your system?

Yes, without the calls to redisplay, I can no longer reproduce it 🤷

That's on a MBP with M1 Pro chip, macOS 14.5.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-24  0:48                                           ` Dmitry Gutov
@ 2024-07-24 11:32                                             ` Eli Zaretskii
  2024-07-24 14:34                                               ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-24 11:32 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: alan, 71866

> Date: Wed, 24 Jul 2024 03:48:22 +0300
> Cc: alan@idiocy.org, 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> On 23/07/2024 14:19, Eli Zaretskii wrote:
> >>
> >> TBF in my custom config I see a more advanced version of this (many/most
> >> characters become blank under cursor after switching to some secondary
> >> frame) - but still that doesn't seem to happen in non-selected frames.
> > That sounds like clipping to me.  (It should be followed by drawing in
> > the clipped region, but for some reason isn't.)  Emacs sometimes clips
> > and clears a region around the cursor if it thinks redrawing the
> > cursor will affect neighboring characters.
> 
> Just to clarify: in each of those cases only one char is blanked at a 
> time

Then I don't understand what you mean by "many/most characters become
blank under cursor".  It seems to contradict what you say now: that
"only one char is blanked".





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-24 11:32                                             ` Eli Zaretskii
@ 2024-07-24 14:34                                               ` Dmitry Gutov
  2024-07-24 16:29                                                 ` Eli Zaretskii
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-24 14:34 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: alan, 71866

On 24/07/2024 14:32, Eli Zaretskii wrote:
>> Date: Wed, 24 Jul 2024 03:48:22 +0300
>> Cc:alan@idiocy.org,71866@debbugs.gnu.org
>> From: Dmitry Gutov<dmitry@gutov.dev>
>>
>> On 23/07/2024 14:19, Eli Zaretskii wrote:
>>>> TBF in my custom config I see a more advanced version of this (many/most
>>>> characters become blank under cursor after switching to some secondary
>>>> frame) - but still that doesn't seem to happen in non-selected frames.
>>> That sounds like clipping to me.  (It should be followed by drawing in
>>> the clipped region, but for some reason isn't.)  Emacs sometimes clips
>>> and clears a region around the cursor if it thinks redrawing the
>>> cursor will affect neighboring characters.
>> Just to clarify: in each of those cases only one char is blanked at a
>> time
> Then I don't understand what you mean by "many/most characters become
> blank under cursor".  It seems to contradict what you say now: that
> "only one char is blanked".

In the recipe I managed to produce starting with 'emacs -Q', only 's' is 
such a character (see the original description). When point is over 'a' 
or 'd', no bug.

In actual practice, many/all characters exhibit the problem, I just 
haven't managed to create a simple repro for this.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-24 14:34                                               ` Dmitry Gutov
@ 2024-07-24 16:29                                                 ` Eli Zaretskii
  2024-07-24 19:22                                                   ` Dmitry Gutov
  0 siblings, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-24 16:29 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: alan, 71866

> Date: Wed, 24 Jul 2024 17:34:18 +0300
> Cc: alan@idiocy.org, 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> > Then I don't understand what you mean by "many/most characters become
> > blank under cursor".  It seems to contradict what you say now: that
> > "only one char is blanked".
> 
> In the recipe I managed to produce starting with 'emacs -Q', only 's' is 
> such a character (see the original description). When point is over 'a' 
> or 'd', no bug.
> 
> In actual practice, many/all characters exhibit the problem, I just 
> haven't managed to create a simple repro for this.

Curiouser and curiouser.  And when you say that 's' is a character
that is blanked, does it mean that if you have several such
characters, then moving the cursor to any of them will show the
problem?

I don't understand even in principle how a display problem could be
specific to some characters, unless it's something related very
strongly to the font that is being used.  So what happens in a session
in which 's' is a problematic character if you put a face property on
's' that forces Emacs to use a different font?





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-24  3:48             ` Gerd Möllmann
@ 2024-07-24 19:16               ` Dmitry Gutov
  2024-07-25  3:03                 ` Gerd Möllmann
  0 siblings, 1 reply; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-24 19:16 UTC (permalink / raw
  To: Gerd Möllmann; +Cc: Stefan Kangas, 71866

On 24/07/2024 06:48, Gerd Möllmann wrote:
>>> And now to my pet peeve 🙂. Dmitry could you please comment out the
>>> calls to redisplay (2 of them) in nsterm.m and try again?
>> I've tried that now, but it didn't seem to help. Does it make a
>> difference on your system?
> Yes, without the calls to redisplay, I can no longer reproduce it 🤷
> 
> That's on a MBP with M1 Pro chip, macOS 14.5.

Oh well. I've tried re-bootstrapping with that change applied, but the 
problem remains.

M3 Pro, macOS 14.5.

Or maybe this is about the slightly different font files:

 > ls -l ~/Library/Fonts/
total 3352
...  290368 Dec 13  2021 CascadiaMono-Bold.otf
...  273200 Dec 13  2021 CascadiaMono-ExtraLight.otf
...  282548 Dec 13  2021 CascadiaMono-Light.otf
...  285336 Dec 13  2021 CascadiaMono-Regular.otf
...  292316 Dec 13  2021 CascadiaMono-SemiBold.otf
...  285944 Dec 13  2021 CascadiaMono-SemiLight.otf





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-24 16:29                                                 ` Eli Zaretskii
@ 2024-07-24 19:22                                                   ` Dmitry Gutov
  2024-07-24 20:08                                                     ` Dmitry Gutov
  2024-07-25  5:01                                                     ` Eli Zaretskii
  0 siblings, 2 replies; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-24 19:22 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: alan, 71866

On 24/07/2024 19:29, Eli Zaretskii wrote:
>> Date: Wed, 24 Jul 2024 17:34:18 +0300
>> Cc: alan@idiocy.org, 71866@debbugs.gnu.org
>> From: Dmitry Gutov <dmitry@gutov.dev>
>>
>>> Then I don't understand what you mean by "many/most characters become
>>> blank under cursor".  It seems to contradict what you say now: that
>>> "only one char is blanked".
>>
>> In the recipe I managed to produce starting with 'emacs -Q', only 's' is
>> such a character (see the original description). When point is over 'a'
>> or 'd', no bug.
>>
>> In actual practice, many/all characters exhibit the problem, I just
>> haven't managed to create a simple repro for this.
> 
> Curiouser and curiouser.  And when you say that 's' is a character
> that is blanked, does it mean that if you have several such
> characters, then moving the cursor to any of them will show the
> problem?

Yes: with buffer contents 'asdasdasdasd' (or any small variations of 
that), only the 's' chars exhibit the problem with the repro script.

With my custom init, all of the chars exhibit the problem.

> I don't understand even in principle how a display problem could be
> specific to some characters, unless it's something related very
> strongly to the font that is being used.  So what happens in a session
> in which 's' is a problematic character if you put a face property on
> 's' that forces Emacs to use a different font?

I tried something different: enabled variable-pitch-mode.

* With the small repro script in the first message, the problem is gone.

* With my custom init, the problem remains for all chars. *shrug*





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-24 19:22                                                   ` Dmitry Gutov
@ 2024-07-24 20:08                                                     ` Dmitry Gutov
  2024-07-25  5:01                                                     ` Eli Zaretskii
  1 sibling, 0 replies; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-24 20:08 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: alan, 71866

On 24/07/2024 22:22, Dmitry Gutov wrote:
> On 24/07/2024 19:29, Eli Zaretskii wrote:
>>> Date: Wed, 24 Jul 2024 17:34:18 +0300
>>> Cc: alan@idiocy.org, 71866@debbugs.gnu.org
>>> From: Dmitry Gutov <dmitry@gutov.dev>
>>>
>>>> Then I don't understand what you mean by "many/most characters become
>>>> blank under cursor".  It seems to contradict what you say now: that
>>>> "only one char is blanked".
>>>
>>> In the recipe I managed to produce starting with 'emacs -Q', only 's' is
>>> such a character (see the original description). When point is over 'a'
>>> or 'd', no bug.
>>>
>>> In actual practice, many/all characters exhibit the problem, I just
>>> haven't managed to create a simple repro for this.
>>
>> Curiouser and curiouser.  And when you say that 's' is a character
>> that is blanked, does it mean that if you have several such
>> characters, then moving the cursor to any of them will show the
>> problem?
> 
> Yes: with buffer contents 'asdasdasdasd' (or any small variations of 
> that), only the 's' chars exhibit the problem with the repro script.
> 
> With my custom init, all of the chars exhibit the problem.
> 
>> I don't understand even in principle how a display problem could be
>> specific to some characters, unless it's something related very
>> strongly to the font that is being used.  So what happens in a session
>> in which 's' is a problematic character if you put a face property on
>> 's' that forces Emacs to use a different font?
> 
> I tried something different: enabled variable-pitch-mode.
> 
> * With the small repro script in the first message, the problem is gone.
> 
> * With my custom init, the problem remains for all chars. *shrug*

OTOH, for example

  (put-text-property (point) (1+ (point) 'font-lock-face '(:family "Arial"))

doesn't have that effect (when point is at one of the 's'-es) - the 
bug's still there.

A couple of more experiments:

- Buffer text 'asdasdasdasdsssssssss' - the problem occurs only on at 
the first 3 's'-es.

- Buffer text 'asdasdasdasdaaaaaaaaa' - the problem occurs at positions

2, 5, 8, 11 and [14..] - that is, the first 3 's'-es, and then for all 
'a'-s at the end except the first one (that comes after the last 'd').





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-24 19:16               ` Dmitry Gutov
@ 2024-07-25  3:03                 ` Gerd Möllmann
  2024-07-25  5:39                   ` Eli Zaretskii
  2024-07-25 14:46                   ` Dmitry Gutov
  0 siblings, 2 replies; 50+ messages in thread
From: Gerd Möllmann @ 2024-07-25  3:03 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: Stefan Kangas, 71866

Dmitry Gutov <dmitry@gutov.dev> writes:

> On 24/07/2024 06:48, Gerd Möllmann wrote:
>>>> And now to my pet peeve 🙂. Dmitry could you please comment out the
>>>> calls to redisplay (2 of them) in nsterm.m and try again?
>>> I've tried that now, but it didn't seem to help. Does it make a
>>> difference on your system?
>> Yes, without the calls to redisplay, I can no longer reproduce it 🤷
>> That's on a MBP with M1 Pro chip, macOS 14.5.
>
> Oh well. I've tried re-bootstrapping with that change applied, but the
> problem remains.
>
> M3 Pro, macOS 14.5.
>
> Or maybe this is about the slightly different font files:
>
>> ls -l ~/Library/Fonts/
> total 3352
> ...  290368 Dec 13  2021 CascadiaMono-Bold.otf
> ...  273200 Dec 13  2021 CascadiaMono-ExtraLight.otf
> ...  282548 Dec 13  2021 CascadiaMono-Light.otf
> ...  285336 Dec 13  2021 CascadiaMono-Regular.otf
> ...  292316 Dec 13  2021 CascadiaMono-SemiBold.otf
> ...  285944 Dec 13  2021 CascadiaMono-SemiLight.otf

The fonts from Homebrew are .ttf files

-rw-r--r--@ 1 gerd  admin  715000 Apr 26 02:49 CascadiaMono.ttf
-rw-r--r--@ 1 gerd  admin  524508 Apr 26 02:49 CascadiaMonoItalic.ttf

The ASAN bug I was referring to is bug#58334. I think there's some chance
that this is also timing dependent, so maybe it's your faster CPU 🤷





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-24 19:22                                                   ` Dmitry Gutov
  2024-07-24 20:08                                                     ` Dmitry Gutov
@ 2024-07-25  5:01                                                     ` Eli Zaretskii
  2024-07-25 16:14                                                       ` Dmitry Gutov
  1 sibling, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-25  5:01 UTC (permalink / raw
  To: Dmitry Gutov; +Cc: alan, 71866

> Date: Wed, 24 Jul 2024 22:22:33 +0300
> Cc: alan@idiocy.org, 71866@debbugs.gnu.org
> From: Dmitry Gutov <dmitry@gutov.dev>
> 
> > Curiouser and curiouser.  And when you say that 's' is a character
> > that is blanked, does it mean that if you have several such
> > characters, then moving the cursor to any of them will show the
> > problem?
> 
> Yes: with buffer contents 'asdasdasdasd' (or any small variations of 
> that), only the 's' chars exhibit the problem with the repro script.
> 
> With my custom init, all of the chars exhibit the problem.
> 
> > I don't understand even in principle how a display problem could be
> > specific to some characters, unless it's something related very
> > strongly to the font that is being used.  So what happens in a session
> > in which 's' is a problematic character if you put a face property on
> > 's' that forces Emacs to use a different font?
> 
> I tried something different: enabled variable-pitch-mode.
> 
> * With the small repro script in the first message, the problem is gone.
> 
> * With my custom init, the problem remains for all chars. *shrug*

OK, so it isn't the font.

The only other explanation is some kind of display-related caching,
somewhere.  One of those is in Emacs: when we decide to redraw some
part of a window, we compute the minimum set of changes that need to
be done on the glass, trying to avoid redrawing what is already there.
Look at dispnew.c:update_text_area -- can you modify its code so that
it always draws the entire screen line?  That is, make the first if
clause:

  /* If rows are at different X or Y, or rows have different height,
     or the current row is marked invalid, write the entire line.  */
  if (!current_row->enabled_p
      || desired_row->y != current_row->y
      || desired_row->ascent != current_row->ascent
      || desired_row->phys_ascent != current_row->phys_ascent
      || desired_row->phys_height != current_row->phys_height
      || desired_row->visible_height != current_row->visible_height
      || current_row->overlapped_p
      /* This next line is necessary for correctly redrawing
	 mouse-face areas after scrolling and other operations.
	 However, it causes excessive flickering when mouse is moved
	 across the mode line.  Luckily, turning it off for the mode
	 line doesn't seem to hurt anything. -- cyd.
         But it is still needed for the header line. -- kfs.
         The header line vpos is 1 if a tab line is enabled.  (18th
         Apr 2022) */
      || (current_row->mouse_face_p
	  && !(current_row->mode_line_p
	       && (vpos > (w->current_matrix->tab_line_p
			   && w->current_matrix->header_line_p))))
      || current_row->x != desired_row->x)

always yield true.  Then see if the problem goes away.

Another redisplay optimization of the same kind is in function
scrolling_window, also in dispnew.c.  I don't think it is being used
in this scenario, but to be sure, change the code in its caller
update_window, so that the condition for its call, viz.:

      /* Try reusing part of the display by copying.  */
      if (row < end && !desired_matrix->no_scrolling_p)

is always false.

I don't think these optimizations are relevant to the situations you
describe, but just in case I'm missing something, please try disabling
them both and see if anything changes.

If disabling those optimizations doesn't help, the only other
hypothesis I can come with is some display wizardry done by your video
driver, whereby it attempts to "optimize" redisplay by redrawing only
parts of the screen.  If your video driver has some customization
features you can control, and if some of those customizations are
named "SOME optimization" or "fast SOMETHING" or anything else to that
effect, try disabling those "optimizations".





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-25  3:03                 ` Gerd Möllmann
@ 2024-07-25  5:39                   ` Eli Zaretskii
  2024-07-25  5:58                     ` Gerd Möllmann
  2024-07-25 14:46                   ` Dmitry Gutov
  1 sibling, 1 reply; 50+ messages in thread
From: Eli Zaretskii @ 2024-07-25  5:39 UTC (permalink / raw
  To: Gerd Möllmann; +Cc: dmitry, stefankangas, 71866

> Cc: Stefan Kangas <stefankangas@gmail.com>, 71866@debbugs.gnu.org
> From: Gerd Möllmann <gerd.moellmann@gmail.com>
> Date: Thu, 25 Jul 2024 05:03:03 +0200
> 
> Dmitry Gutov <dmitry@gutov.dev> writes:
> 
> > On 24/07/2024 06:48, Gerd Möllmann wrote:
> >>>> And now to my pet peeve 🙂. Dmitry could you please comment out the
> >>>> calls to redisplay (2 of them) in nsterm.m and try again?
> >>> I've tried that now, but it didn't seem to help. Does it make a
> >>> difference on your system?
> >> Yes, without the calls to redisplay, I can no longer reproduce it 🤷
> >> That's on a MBP with M1 Pro chip, macOS 14.5.
> >
> > Oh well. I've tried re-bootstrapping with that change applied, but the
> > problem remains.
> >
> > M3 Pro, macOS 14.5.
> >
> > Or maybe this is about the slightly different font files:
> >
> >> ls -l ~/Library/Fonts/
> > total 3352
> > ...  290368 Dec 13  2021 CascadiaMono-Bold.otf
> > ...  273200 Dec 13  2021 CascadiaMono-ExtraLight.otf
> > ...  282548 Dec 13  2021 CascadiaMono-Light.otf
> > ...  285336 Dec 13  2021 CascadiaMono-Regular.otf
> > ...  292316 Dec 13  2021 CascadiaMono-SemiBold.otf
> > ...  285944 Dec 13  2021 CascadiaMono-SemiLight.otf
> 
> The fonts from Homebrew are .ttf files
> 
> -rw-r--r--@ 1 gerd  admin  715000 Apr 26 02:49 CascadiaMono.ttf
> -rw-r--r--@ 1 gerd  admin  524508 Apr 26 02:49 CascadiaMonoItalic.ttf

Given the latest information from Dmitry, I very much doubt that fonts
are related to this.

> The ASAN bug I was referring to is bug#58334. I think there's some chance
> that this is also timing dependent, so maybe it's your faster CPU 🤷

If the other ideas I just described prove fruitless, then yes, I would
claim that the weird things the NS display does with its async nature
(which no other platform I'm familiar with does) could cause ASAN
bugs, and are the only explanation that is left un-rebuffed.

In general, as long as we don't have on board an active developer who
has a good grip on the intricacies of the NS redisplay in Emacs, we
will continue hearing about display problems like this one, and
there's nothing that can be done about it except stop using macOS.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-25  5:39                   ` Eli Zaretskii
@ 2024-07-25  5:58                     ` Gerd Möllmann
  0 siblings, 0 replies; 50+ messages in thread
From: Gerd Möllmann @ 2024-07-25  5:58 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: dmitry, stefankangas, 71866

Eli Zaretskii <eliz@gnu.org> writes:

> In general, as long as we don't have on board an active developer who
> has a good grip on the intricacies of the NS redisplay in Emacs, we
> will continue hearing about display problems like this one, and
> there's nothing that can be done about it except stop using macOS.

There is BTW this

  https://www.gtk.org/docs/installations/macos

Haven't tried it though because I know even less about Gtk than Cocoa.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-25  3:03                 ` Gerd Möllmann
  2024-07-25  5:39                   ` Eli Zaretskii
@ 2024-07-25 14:46                   ` Dmitry Gutov
  1 sibling, 0 replies; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-25 14:46 UTC (permalink / raw
  To: Gerd Möllmann; +Cc: Stefan Kangas, 71866

On 25/07/2024 06:03, Gerd Möllmann wrote:
> The ASAN bug I was referring to is bug#58334. I think there's some chance
> that this is also timing dependent, so maybe it's your faster CPU 🤷

Makes sense, could be. The effect is pretty stable, though.

Not something that happens in one iteration but disappears in another.





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

* bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization
  2024-07-25  5:01                                                     ` Eli Zaretskii
@ 2024-07-25 16:14                                                       ` Dmitry Gutov
  0 siblings, 0 replies; 50+ messages in thread
From: Dmitry Gutov @ 2024-07-25 16:14 UTC (permalink / raw
  To: Eli Zaretskii; +Cc: alan, 71866

On 25/07/2024 08:01, Eli Zaretskii wrote:
>> Date: Wed, 24 Jul 2024 22:22:33 +0300
>> Cc: alan@idiocy.org, 71866@debbugs.gnu.org
>> From: Dmitry Gutov <dmitry@gutov.dev>
>>
>>> Curiouser and curiouser.  And when you say that 's' is a character
>>> that is blanked, does it mean that if you have several such
>>> characters, then moving the cursor to any of them will show the
>>> problem?
>>
>> Yes: with buffer contents 'asdasdasdasd' (or any small variations of
>> that), only the 's' chars exhibit the problem with the repro script.
>>
>> With my custom init, all of the chars exhibit the problem.
>>
>>> I don't understand even in principle how a display problem could be
>>> specific to some characters, unless it's something related very
>>> strongly to the font that is being used.  So what happens in a session
>>> in which 's' is a problematic character if you put a face property on
>>> 's' that forces Emacs to use a different font?
>>
>> I tried something different: enabled variable-pitch-mode.
>>
>> * With the small repro script in the first message, the problem is gone.
>>
>> * With my custom init, the problem remains for all chars. *shrug*
> 
> OK, so it isn't the font.

I guess not.

> The only other explanation is some kind of display-related caching,
> somewhere.  One of those is in Emacs: when we decide to redraw some
> part of a window, we compute the minimum set of changes that need to
> be done on the glass, trying to avoid redrawing what is already there.
> Look at dispnew.c:update_text_area -- can you modify its code so that
> it always draws the entire screen line?  That is, make the first if
> clause:
> 
>    /* If rows are at different X or Y, or rows have different height,
>       or the current row is marked invalid, write the entire line.  */
>    if (!current_row->enabled_p
>        || desired_row->y != current_row->y
>        || desired_row->ascent != current_row->ascent
>        || desired_row->phys_ascent != current_row->phys_ascent
>        || desired_row->phys_height != current_row->phys_height
>        || desired_row->visible_height != current_row->visible_height
>        || current_row->overlapped_p
>        /* This next line is necessary for correctly redrawing
> 	 mouse-face areas after scrolling and other operations.
> 	 However, it causes excessive flickering when mouse is moved
> 	 across the mode line.  Luckily, turning it off for the mode
> 	 line doesn't seem to hurt anything. -- cyd.
>           But it is still needed for the header line. -- kfs.
>           The header line vpos is 1 if a tab line is enabled.  (18th
>           Apr 2022) */
>        || (current_row->mouse_face_p
> 	  && !(current_row->mode_line_p
> 	       && (vpos > (w->current_matrix->tab_line_p
> 			   && w->current_matrix->header_line_p))))
>        || current_row->x != desired_row->x)
> 
> always yield true.  Then see if the problem goes away.
> 
> Another redisplay optimization of the same kind is in function
> scrolling_window, also in dispnew.c.  I don't think it is being used
> in this scenario, but to be sure, change the code in its caller
> update_window, so that the condition for its call, viz.:
> 
>        /* Try reusing part of the display by copying.  */
>        if (row < end && !desired_matrix->no_scrolling_p)
> 
> is always false.
> 
> I don't think these optimizations are relevant to the situations you
> describe, but just in case I'm missing something, please try disabling
> them both and see if anything changes.

Alas, no change. Tried just the first (changing the condition to "true 
|| ..."), the two together (the second changed to just "false" as well), 
and also combined with commenting out both redisplay calls in nsterm.m.

> If disabling those optimizations doesn't help, the only other
> hypothesis I can come with is some display wizardry done by your video
> driver, whereby it attempts to "optimize" redisplay by redrawing only
> parts of the screen.  If your video driver has some customization
> features you can control, and if some of those customizations are
> named "SOME optimization" or "fast SOMETHING" or anything else to that
> effect, try disabling those "optimizations".

I don't know macOS very well, but it seems like it doesn't have any 
options like "Disable video acceleration" one would find in other OSes: 
https://discussions.apple.com/thread/253590597?sortBy=rank





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

end of thread, other threads:[~2024-07-25 16:14 UTC | newest]

Thread overview: 50+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2024-07-01  3:14 bug#71866: 30.0.50; [macOS] Cursor hiding char behind it with certain theme customization Dmitry Gutov
2024-07-01 11:36 ` Eli Zaretskii
2024-07-02  1:07   ` Dmitry Gutov
2024-07-06  8:56     ` Eli Zaretskii
2024-07-09  2:37       ` Dmitry Gutov
2024-07-09 11:31         ` Eli Zaretskii
2024-07-10  2:46           ` Dmitry Gutov
2024-07-10 11:58             ` Eli Zaretskii
2024-07-19  1:57               ` Dmitry Gutov
2024-07-20  8:30                 ` Eli Zaretskii
2024-07-20 15:46                   ` Dmitry Gutov
2024-07-20 16:03                     ` Eli Zaretskii
2024-07-21  0:53                       ` Dmitry Gutov
2024-07-21  7:20                         ` Eli Zaretskii
2024-07-21  9:04                           ` Eli Zaretskii
2024-07-21 23:22                             ` Dmitry Gutov
2024-07-21 13:50                           ` Dmitry Gutov
2024-07-21 14:55                             ` Eli Zaretskii
2024-07-21 23:58                               ` Dmitry Gutov
2024-07-22 14:45                                 ` Eli Zaretskii
2024-07-22 15:27                                   ` Alan Third
2024-07-22 16:02                                     ` Alan Third
2024-07-23  1:11                                       ` Dmitry Gutov
2024-07-23 11:19                                         ` Eli Zaretskii
2024-07-24  0:48                                           ` Dmitry Gutov
2024-07-24 11:32                                             ` Eli Zaretskii
2024-07-24 14:34                                               ` Dmitry Gutov
2024-07-24 16:29                                                 ` Eli Zaretskii
2024-07-24 19:22                                                   ` Dmitry Gutov
2024-07-24 20:08                                                     ` Dmitry Gutov
2024-07-25  5:01                                                     ` Eli Zaretskii
2024-07-25 16:14                                                       ` Dmitry Gutov
2024-07-22 16:10                                     ` Eli Zaretskii
2024-07-22 19:02                                       ` Alan Third
2024-07-22 19:15                                         ` Eli Zaretskii
2024-07-22 19:47                                           ` Alan Third
2024-07-23  1:06                                   ` Dmitry Gutov
2024-07-23 11:17                                     ` Eli Zaretskii
2024-07-02 23:42 ` Stefan Kangas
2024-07-07  2:03   ` Dmitry Gutov
2024-07-09 18:22     ` Stefan Kangas
2024-07-10  2:56       ` Dmitry Gutov
2024-07-23  7:40         ` Gerd Möllmann
2024-07-24  0:56           ` Dmitry Gutov
2024-07-24  3:48             ` Gerd Möllmann
2024-07-24 19:16               ` Dmitry Gutov
2024-07-25  3:03                 ` Gerd Möllmann
2024-07-25  5:39                   ` Eli Zaretskii
2024-07-25  5:58                     ` Gerd Möllmann
2024-07-25 14:46                   ` Dmitry Gutov

Code repositories for project(s) associated with this external index

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

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.