From: Adam Beneschan <adam@irvine.com>
Subject: Re: Problems with Ada.Streams.Read (blocking)
Date: Fri, 8 Aug 2008 07:48:42 -0700 (PDT)
Date: 2008-08-08T07:48:42-07:00 [thread overview]
Message-ID: <103f4912-d96b-4c11-b9b2-d7a6d6ffcff3@i24g2000prf.googlegroups.com> (raw)
In-Reply-To: g7hher$mtt$1@aioe.org
On Aug 8, 6:24 am, Dennis Hoppe <dennis.ho...@hoppinet.de> wrote:
> Hi,
>
> I've written a minimal example to access an ftp server (like FileZilla).
> First, let's have a look at the code snippet:
>
> -- START
> with Ada.Text_IO;
> with Ada.Streams;
> with GNAT.Sockets; use GNAT.Sockets;
> use type Ada.Streams.Stream_Element_Count;
>
> procedure Test is
> Client: Socket_Type;
> Address: Sock_Addr_Type;
> Channel: Stream_Access;
> Data : Ada.Streams.Stream_Element_Array (1 .. 1);
> Offset : Ada.Streams.Stream_Element_Count;
>
> begin
> Initialize;
> Create_Socket(Client);
> Address.Addr := Inet_Addr("127.0.0.1");
> Address.Port := 21;
> Connect_Socket (Client,Address);
> Channel := Stream(Client);
>
> loop -- reads in the welcome message
> Ada.Streams.Read (Channel.all, Data(1..1), Offset);
> exit when Offset = 0;
> -- alternative: exit when Offset /= Data'Last
> for I in 1 .. Offset loop
> Ada.Text_IO.Put (Character'Val (Data (I)));
> end loop;
> end loop;
> end Test;
> -- END
>
> The problem is, that Ada.Streams.Read is blocking, if the end of the
> stream is reached. I found many examples, that outline, that the
> variable Offset will be 0, if no further elements are on the stream.
> But this seems not to be the case, unfortunately.
>
> For a ftp server/client situation, each command is terminate by <CRLF>,
> so I enhanced the exit condition to:
>
> loop
> Ada.Streams.Read (Channel.all, Data(1..2), Offset);
> exit when (Character'Val (Data(1)) = ASCII.CR and Character'Val
> (Data(2)) = ASCII.LF);
> -- code omitted
> end loop;
>
> Of course, the Stream_Element_Array is enhanced to (1..2).
>
> This approach works very well, but some ftp commands send a messages
> over several lines. I do not know in advance, how many lines I should
> read in. Subsequently, Ada.Streams.Read has to be called in a loop,
> which will eventually block, again.
>
> How can I query the stream, if new elements are ready to read?
I'm not familiar with GNAT.Sockets, but looking at the spec it appears
that there are a couple routines that might help: Control_Socket which
lets you specify non-blocking I/O, and Check_Selector which I think
can be used to query whether data is available, if you give it a
Timeout of zero. Anyway, I haven't tried anything and I have no idea
whether it's appropriate for your problem, but it seems like it might
help. If not, my apologies.
-- Adam
next prev parent reply other threads:[~2008-08-08 14:48 UTC|newest]
Thread overview: 11+ messages / expand[flat|nested] mbox.gz Atom feed top
2008-08-08 13:24 Problems with Ada.Streams.Read (blocking) Dennis Hoppe
2008-08-08 13:56 ` Dmitry A. Kazakov
2008-08-08 18:00 ` Dennis Hoppe
2008-08-08 18:51 ` Dmitry A. Kazakov
2008-08-08 19:37 ` Dennis Hoppe
2008-08-08 21:25 ` Maciej Sobczak
2008-08-09 7:30 ` Dmitry A. Kazakov
2008-08-08 14:48 ` Adam Beneschan [this message]
2008-08-08 18:08 ` Dennis Hoppe
2008-08-09 3:04 ` anon
2008-08-22 22:13 ` Paweł 'Nivertius' Płazieński
replies disabled
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox