[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
RE: Emacs - cannot connect to X server
From: |
Muggeridge, Matt |
Subject: |
RE: Emacs - cannot connect to X server |
Date: |
Fri, 11 Oct 2002 15:01:55 +1000 |
Hi Richard,
I believe I have uncovered the source of a bug I reported back in June.
I am not certain of the best fix here and would refer the problem to the
code author.
The overview:
-------------
XtOpenDisplay() attempts to connect() to the Xserver. However, the
connect() call would be interrupted with errno=EINTR due to a SIGALRM.
The SIGALRM was generated by a call to setitimer().
Proposed Solutions:
-------------------
Either (1) the timeout period has to be extended to account for slow
links, or (2) the call to setitimer() must be postponed until after the
call to XtOpenDisplay(). I prefer option (2) since it doesn't have a
dependency on the speed of a WAN link. The code diffs are shown below.
I have tested both scenarios.
The code diffs for option (1):
# diff atimer.c atimer.c.DIST
325d324
< #if 0
328,331d326
< #else
< EMACS_SET_SECS (time, 3);
< EMACS_SET_USECS (time, 0);
< #endif
The code diffs for option (2):
# diff xterm.c xterm-DIST.c
14231,14241d14230
< /* Install an asynchronous timer that processes Xt timeout events
< every 0.1s. This is necessary because some widget sets use
< timeouts internally, for example the LessTif menu bar, or the
< Xaw3d scroll bar. When Xt timouts aren't processed, these
< widgets don't behave normally. */
< {
< EMACS_TIME interval;
< EMACS_SET_SECS_USECS (interval, 0, 100000);
< start_atimer (ATIMER_CONTINUOUS, interval, x_process_timeouts,
0);
< }
<
14691a14681,14691
>
> /* Install an asynchronous timer that processes Xt timeout events
> every 0.1s. This is necessary because some widget sets use
> timeouts internally, for example the LessTif menu bar, or the
> Xaw3d scroll bar. When Xt timouts aren't processed, these
> widgets don't behave normally. */
> {
> EMACS_TIME interval;
> EMACS_SET_SECS_USECS (interval, 0, 100000);
> start_atimer (ATIMER_CONTINUOUS, interval, x_process_timeouts,
0);
> }
The problem call-tree is:
x_term_init() -> x_initialize() -> start_atimer() -> setitimer()
-> XtOpenDisplay() -> connect() -> EINTR due to SIGALRM
Comments in x_initialize() suggest that calling start_atimer() is
necessary. Viz.
> /* Install an asynchronous timer that processes Xt timeout events
> every 0.1s. This is necessary because some widget sets use
> timeouts internally, for example the LessTif menu bar, or the
> Xaw3d scroll bar. When Xt timouts aren't processed, these
> widgets don't behave normally. */
If the 0.1s timer is needed for the correct functioning of X, then
option (2) is the only viable option. I don't know if option (2) has
other unintended side-effects. I am not an X-pert.
I have attached two traces. The first trace (Xlib_trace.txt) shows how
the call to XtOpenDisplay() fails due to connect() returning EINTR. The
second trace file (Signal Trace.txt) shows that the SIGALRM is
responsible for EINTR I have annotated the second trace with:
"--- INTERESTING STUFF BELOW ---"
You may like to scan for that to see where the signal interruption is
occurring.
Furthter Analysis:
If I understand the trace output, I think the most interesting code
fragment is the call to setitimer() which will generate a SIGALRM when
the timer expires. The interval initially used is 98047 microseconds.
Subsequent intervals are then 1000us, which seems way to brief. On
links where the round-trip-time exceeds this will result in the
behaviour I am seeing.
The trace snippets:
Setup a timer to expire in approx. 98ms...
setitimer (ITIMER_REAL, 0x11fffa808={{0,0}, {0,98047}}, 0x0) = 0
sigaction (SIGWINCH, {{0x0,0x0,SA_RESTART}}, 0x11fffa828) = 0, [ , ,
{{0x0,0x0,0}} ]
sigaction (SIGPIPE, {{0x1200d40a0,0x0,SA_RESTART}}, 0x11fffa828) = 0,
[ , , {{0x0,0x0,0}} ]
obreak (0x140535000) = 0
socket (AF_INET, SOCK_STREAM, PF_UNSPEC) = 5
setsockopt (5, IPPROTO_TCP, TCP_NODELAY, 0x11fffa4b8=1, 4) = 0
setsockopt (5, SOL_SOCKET, SO_KEEPALIVE, 0x11fffa4b8=1, 4) = 0
connect (5, 0x11fff7c10=<2/INET, 6000, 16.176.234.79>, 16) = SIGNAL
[14 SIGALRM]
-1, Errno 4 (Interrupted system call)
Subsequent calls to setitimer() use a 1ms interval. This seems way too
short for it to be practical.
setitimer (ITIMER_REAL, 0x11fffa208={{0,0}, {0,1000}}, 0x0) = 0
sigreturn (0x11fffa278) = -1
gettimeofday (0x11fffa4e8, 0x0) = 0, [ {1034300109, 135631}, {} ]
socket (AF_INET, SOCK_STREAM, PF_UNSPEC) = 5
setsockopt (5, IPPROTO_TCP, TCP_NODELAY, 0x11fffa4b8=1, 4) = 0
setsockopt (5, SOL_SOCKET, SO_KEEPALIVE, 0x11fffa4b8=1, 4) = 0
connect (5, 0x11fff7c10=<2/INET, 6000, 16.176.234.79>, 16) = SIGNAL
[14 SIGALRM]
-1, Errno 4 (Interrupted system call)
I modified the emacs distribution by setting the timer to 3 seconds and
this has fixed my problem. I also tested an option where setitimer() is
called after XtOpenDisplay() and this also fixed the problem.
Cheers,
Matt.
Xlib trace.txt
Description: Xlib trace.txt
Signal Trace.txt
Description: Signal Trace.txt
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- RE: Emacs - cannot connect to X server,
Muggeridge, Matt <=