lynx-dev
[Top][All Lists]
Advanced

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

Re: lynx-dev peculiar behavior


From: Klaus Weide
Subject: Re: lynx-dev peculiar behavior
Date: Sat, 10 Jul 1999 19:48:41 -0500 (CDT)

On Sat, 10 Jul 1999, T.E.Dickey wrote:

> > Then please try replacing it with another interactive program that can 
> > be suspended - less, some other editor, even lynx itself.  Try several. 
> > My guess is you'll see similar behaviour. 
> >  
> > I have seen something like this in the past with lynx.  I think the 
> > problem lies in the implementation of system(). 

I now also see strange behavior with lynx.  And I thought this was gone.
:(
This is not exactly the lastest dev code, but nothing substantial should
have changed.  It's linked against a libncurses pre5.0.

> It's not 100% ncurses (small relief).  I tried lynx with Solaris curses and 
> vi,
> and get some odd behavior (using a mail link):

Can you try with just textarea editing (whatever it's bound to for you,
^Ve or ^Xe if using Bash-like Bindings)?
(So we talk about the same thing.  Mail may do some additional things, at
least for the ^C signal.  Normal 'e' on a file may mask some of the
effects by lynx doing more refreshing.)
Try the little practice textarea in bashlike_edit_help.html if you
need an example (no danger to accidentally submit anything).

>       + when I do 'fg', it does come back to vi, but the video attributes
>         are incorrect (so all of the text is in reverse-video).  That
>         indicates (to me) that Lynx (or Solaris curses) is writing something.


I do '^Xe' in the textarea (bash-like bindings).
Editor is nvi. (I also tried with (non-X) emacs, basically the same things
happen.)
After ^Z, 'fg':
- I (sometimes) see the lynx screen flash up then immediately overwritten
  with a refreshed nvi screen.  (This is consistent with your
  reverse-video observation.  It's different from Larry's observations,
  but what the screen ends up looking like would just depend on the order
  of writes.)
- The tty settings seem ok, as nvi wants them. (at least, no noticeable
  problems).

On :q from nvi:

- Lynx screen is not fully refreshed.  Mostly the screen contents is as
  left by nvi.  Lynx is in control, ^L fixes the screen.
- The tty settings are wrong.  Input is processed immediately, but
  echo is on. (visible at least when going up/down over the empty textarea
  line.)

>       + quitting from vi, the control/G doesn't cancel the operation
>         (control/C still kills it, but that's not quite what I'd like).

^G thing may be just because termios settings are screwed up at that
point, tty is in canonical mode when it shouldn't.

> I can see similar behavior on Linux using nvi (linked with ncurses).

The differences may be due to differences in which flags ncurses vs.
Solaris modifies, but the basic reason for the problem may be the same.

For ncurses, it is that when system() gets a SIGTSTP while in wait*(),
the ncurses signal handler tstp() gets called and messes things up.

Here is a syscall trace obtained as follows:
Do stuff as above.  up to ^Z.  Then attach (from different console)
with strace to the process, as in  strace -p 3494 2>&1 | less .
Then 'fg'.

sigaction(SIGTSTP, {0x4003be30, [], SA_RESTART}, NULL) = 0
ioctl(1, TCFLSH, TCIFLUSH)              = 0
ioctl(1, TCGETS, {B38400 opost -isig -icanon -echo ...}) = 0
sigaction(SIGTSTP, {SIG_IGN}, {0x4003be30, [], SA_RESTART}) = 0
ioctl(1, TCGETS, {B38400 opost -isig -icanon -echo ...}) = 0
ioctl(1, TIOCGWINSZ, {ws_row=32, ws_col=100, ws_xpixel=0, ws_ypixel=0}) = 0
ioctl(1, SNDCTL_TMR_STOP, {B38400 opost isig icanon echo ...}) = 0
write(1, "\33[1;32r\33[39;49m\33[0;10m\33["..., 1352) = 1352
sigaction(SIGTSTP, {0x4003be30, [], SA_RESTART}, NULL) = 0
sigprocmask(SIG_SETMASK, [CHLD TSTP], NULL) = 0
sigreturn()                             = ? (mask now [CHLD])

(Note that the actually visual behavior may be different from my
description above if the lynx process is traced, because trace influences
the behavior.  In this case it seems to be a timing thing,  lynx is
slower in reacting, so it is second in updating the screen in
competition with the nvi process, so the lynx screen "wins".  With this
I get behavior very much like what Larry reported, including screwed-up 
tty state while in nvi.)

The sigreturn() at the end of the trace shows that the calles happen in
a signal handler.  That must be ncurses's tstp().

Strace attaches to the process while tstp() has stopped it in
lib_tstp.c:
        kill(getpid(), SIGTSTP);

Upon 'fg', execution resumes and calls are traced.  Looking at ncurses
source from this point on, most of the system calls are generated
by the doupdate() near the end of tstp().

Basically, the lynx process shouldn't be doing a doupdate() while
it's supposed to wait*() for a child process!  Especially since
lynx has explicitly done a stop_curses(), and expects curses to
be off until an explicit start_curses() after the system() call.

All theses things may be screwed up by the unexpected interference
of the tstp() handler:
 - actual screen contents
 - actually tty states
 - saved tty states (ncurses's attempt to keep track of them)

The easiest way to prevent Bad Things from happening here is to
disable the SIGTSTP handler in this situation (use SIG_DFL).

Should it be (n)curses' job to do this (probably always while in 
'shell' mode)?

Should lynx do this?
(It could be put into LYSystem().  Or into stop_curses/start_curses.
There would be differences between the two choices, especially if there
are LYSystem() or system() calls that are not preceded by stop_curses().)

Or both?

 ----

Dos anyone have a different analysis or theory?  Do curses standards
say anything about how the SIGTSTP handler should behave after endwin()?

   Klaus


reply via email to

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