On Tue, 23 Feb 1999, Jean-Marc Lasgouttes wrote:
>
> Hello,
>
> On my station, when trying to setup a lyxserver with
> \serverpipe "/tmp/lyxpipe"
> all I get when running 'lyx -dbg 8192' is
>
> fantomas: lyx -dbg 8192
> Setting debug level to 8192
> LyXComm: Opening connection
> LyXComm: Connection established
> LyXComm: Receiving from fd 8
> LyXComm: Closing connection
> LyXComm: Opening connection
> LyXComm: Connection established
> LyXComm: Receiving from fd 8
> LyXComm: Closing connection
> LyXComm: Opening connection
> LyXComm: Connection established
> LyXComm: Receiving from fd 8
> LyXComm: Closing connection
> ...
>
> So it seems that as soon as the socket is open, the server reads from
> it and, since read() returns 0 (as documented when the pipe is not
> open for writing by another process) lyx decides to close the pipe and
> open another one...
>
> I'm not sure that what I explain is very clear there, but I do not
> understand what the code is supposed to do. Joacim, can you shed some
> light? I'm sure I got it to work at some point.
On (intel) Linux, I only get:
LyXComm: Opening connection
LyXComm: Connection established
on startup. (When not writing anything to the pipe)
LyXComm::callback should only be called /when there is data waiting/ on the
file descriptor (according to the docs for fl_add_io_callback()).
The loop in LyXComm::callback():
"while((status = read(fd,charbuf,CMDBUFLEN-1)))" is left when status==0,
i.e. end of file, and the connection is closed to stop Forms from watching
the file descriptor any further (wasting cpu), and immediately reopened to
wait for a new connection. The callback may also return (from inside the
loop) if read() yielded an EAGAIN, meaning there is still someone writing
to the pipe, but there's nothing in the buffer right now.
On other errors (errno != 0), the connection is reset (the "break; //
reset connection") and if a fragment of a command has been read but not all
of it, the fragment is first thrown away (assuming the client was killed in
the middle of a command -- safest guess -- and the fragment is thrown away
so it won't mess up the first command of the next connection).
If you connect to the pipe with a shell script and do things like:
echo "foo" > path/to/.lyxpipe.in;
the pipe is /opened and closed/ by each echo-statement (that's how
redirections of stdout works in this case), and the ::callback will read,
close and reopen the pipe accordingly. (It can't know in advance if you
plan to reopen it right away, so it resets the connection to avoid an idle
loop)
If ::callback is called from libforms allthough there is /no data/ waiting,
we may have a bug in libforms (on sparc-Solaris I take it?)
It may have something to do with interrupted read()-calls though (see
read(2)). ...hmm, that could be it actually. if Solaris read() returns -1
on an interrupted read(), the remaining bytes wouldn't be read from the
buffer. ...but in that case, why does it go on returning -1. Sooner or
later it ought to be able to read the buffer again? Was the pipe located
on an NFS-mounted disk or something?
BTW, it's not a "socket", it's a "named pipe" (or FIFO, ..two of them
actually). A named socket (only way to make a /socket/ appear in the file
system) is what you get if you create an AF_UNIX socket (with socket(2))
and bind(2) it to a name in the file system. A socket is connected to with
connect() (client side) and listen()/accept() (server side) whereas a
/named pipe/ is created by the user with mknod(1) or mkfifo(1), or from a
programme with mknod(2) or mkfifo(3) (what LyX does) and connected to with
open(2) on both ends.
A pipe is unidirectional, and if it is closed and reopened, it's still the
same named pipe. A named socket on the other hand is usually a stream,
i.e. it's bidirectional, and connections to a socket can be redirected to
another socket so that the original socket can be connect()ed to by another
client without the two connections interfering eachother.
(almost typed "interfearing" ;)
Needless to say, multiple readers will NOT get multiple copies of what is
written to the pipe, they will grab whatever they can for themselves (so
the current design won't work with multiple clients connected to the
lyx-server -- the client name `tag' in the protocol is completely useless).
Joacim
-
With both feet on the ground, you won't get very far.
-- Loesje