reset after binary data

Andrei Paskevich andrei at capet.iut-fbleau.fr
Sat Aug 11 13:23:19 CEST 2007


Short answer:

rxvt-unicode does not and, I guess, should not reset reverse video 
on reset. What it does, though, is resetting its internal reverse 
video state flags -- and this is exactly what causes your problem.
You can try this patch:

=========================== urxvt-rvideo.diff ========================
diff -ur rxvt-unicode-8.3/src/screen.C rxvt-unicode-8.3-ap/src/screen.C
--- rxvt-unicode-8.3/src/screen.C	2007-06-26 02:47:14.000000000 +0300
+++ rxvt-unicode-8.3-ap/src/screen.C	2007-08-11 13:22:43.000000000 +0300
@@ -239,7 +239,6 @@
       selection.op = SELECTION_CLEAR;
       selection.screen = PRIMARY;
       selection.clicks = 0;
-      rvideo_state = rvideo_mode = false;
     }
   else
     {
=========================== urxvt-rvideo.diff ========================

Long answer:

Martin, your magic binary string can be reduced just to three
characters: 0x07 0x1b 0x63, that is: BEL ESC c. When you send
this string to the terminal, with video bell turned on, 
the following happens:

1. [command.C:2544] The BEL character is processed 
and the method scr_bell() [screen.C:1885] is called.

2. [screen.C:1911] scr_bell() raises the flag rvideo_bell
and calls scr_rvideo_mode(rvideo_mode) [screen.C:1640]
The rvideo_mode is currently false, as it should be.

  3. [screen.C:1640] scr_rvideo_mode() compares the flag
  rvideo_state (currently false) with rvideo_mode^rvideo_bell 
  (false^true = true) and toggles reverse video:

    4. [screen.C:1650] the flag rvideo_state is raised and

    5. [screen.C:1652] reverse video is activated

  6. [screen.C:1669] then we return to scr_bell()

7. [screen.C:1915] after setting reverse video, scr_bell sets
the timer bell_ev, in order to switch reverse video off after
a fraction of second. 

8. So, now the state of the three flags is:

  rvideo_mode == false,  rvideo_state == true,  rvideo_bell == true

the video is reversed and the timer bell_ev is set.

9. [command.C:2753] The escape sequence ESC c is processed
and the method scr_poweron() [screen.C:451] is called, which,
in turn, calls the method scr_reset() [screen.C:160].

10. [screen.C:242] scr_reset() sets rvideo_state = rvideo_mode = false.
However, the actual reverse video is still on.

11. The string processing is finished.

12. Now, the timer expires and the callback bell_cb() [screen.C:1876]
is called. The callback function sets the flag rvideo_bell to false
and calls scr_rvideo_mode(rvideo_mode). 

  13. [screen.C:1640] scr_rvideo_mode() compares the flag
  rvideo_state (false, by step 10) with rvideo_mode^rvideo_bell
  (false^false = false) and, as the values are equal, does nothing.
  
14. So, now the state of the three flags is:

  rvideo_mode == false,  rvideo_state == false,  rvideo_bell == false

the video is reversed and you file a bug report.

Had you no ESC c after the bell, the flag rvideo_state would not be
dropped and the callback bell_cb would correctly turn reverse video off.

Instead of deleting the line at [screen.C:242], one could check 
rvideo_bell at scr_reset() and, if raised, stop the timer and call 
bell_cb manually. Though I don't see too much sense in it.

Best regards,
Andrei





More information about the rxvt-unicode mailing list