[Mono-list] Socket.Select problem

P Oscar Boykin boykin@pobox.com
Tue, 4 May 2004 17:46:31 -0700


--tKy6e3LXpfmanBFM
Content-Type: text/plain; charset=us-ascii
Content-Disposition: inline
Content-Transfer-Encoding: quoted-printable

There are a couple of problems here:

1) Select modifies the list you pass it so that only the elements that
remain in the list are the ones that are ready for action.  So, before
each call you will need to make a copy of the original list.

2) the time is in *microseconds*, so your code waits for a total of 5
milliseconds before giving up (and listenList will be empty in that
case).

3) After 1 timeout, your read variable will be false, and you will give
up for good.  Is that what you want?

You said that Select does not work correctly, I think it is because
after one timeout it quits.

As a previous poster mentioned, you really just want to use Poll in this
case.  Select is for the case where there are many sockets, and you want
to read from all the ones that have data waiting, or write to all of the
ones that are ready for writing.

I also highly recommend using Poll when you only have 1 socket.

In theory, the BeginSend and BeginReceive (Async socket methods) would
also be a good choice, but I have had issues with them and I am not
convinced they are working properly.

Finally, just doing a blocking Receive or Send call might not be bad if
you plan to use an infinite timeout anyway.

You can use Select here, and just to give you an example:
To make your code work, I think you need something like this:

ArrayList listenList =3D new ArrayList();
listenList.Add(socket);

while(true)
{
  ArrayList read_list =3D new ArrayList(listenList);
  Socket.Select(read_list, null, null, 1000000); //1 second timeout
  if( read_list.Count > 0 )
  {
    Socket read_sock =3D (Socket)read_list[0];
    read_sock.Receive(buffer, 1, SocketFlags.None);
    //Do you really want the '\n' character in the string?
    message +=3D (char)buffer[0];
    if ((char)buffer[0] =3D=3D '\n')
    {
      //This breaks us out of the outer infinite while loop
      return message;
    }
  }
  else
  {
    //Just had a timeout.  We might want to quit after some number of
    //them.
  }
}

On Mon, May 03, 2004 at 10:36:56PM +0200, Dennis Jarosch wrote:
> Hi!!
>=20
> This is probably not mono-devel related but I'd really appreciate it, if
> somebody could help.
>=20
> I am writing a client application (w/ mono and C#) that communicates
> with the server via message-strings. These strings are terminated by the
> usual '\n'. The '\n' may be followed by additional data, which is why
> the string has to be processed before reading the rest.
>=20
> I am currently getting one character at a time, checking the
> socket-state with Socket.Select. Yes, using a buffer would be nice, but
> the server-protocol forces me to do it this way. ;-)
>=20
> Somehow Select (and Poll, which I have also tried) does not seem to work
> correctly. Sometimes I get correct results, mostly nothing is read
> though. When using a buffer, everything works rather fine. When using -1
> as timeout value, everything works fine but blocks after the last char.
>=20
> This is my code:
> ++++++++++++++++++++++++ Select
>=20
> ArrayList listenList =3D new ArrayList();
> listenList.Add(socket);
>=20
> int count =3D 0;
> bool read =3D true;
>=20
> while (read)
> {
> 	read =3D false;
> 	Socket.Select(listenList, null, null, 5000);
> 			=09
> 	if (listenList.Contains(socket))
> 	{				=09
> 		read =3D true;
> 		count =3D socket.Receive(buffer, 1, SocketFlags.None);
>=20
> 		Console.WriteLine("count: " + count);
>=20
> 		message +=3D (char)buffer[0];
> 			=09
> 		if ((char)buffer[0] =3D=3D '\n')
> 			return message;
> 	}
> }
>=20
> ++++++++++++++++++++++++ Poll
>=20
> while (socket.Poll(-1, SelectMode.SelectRead))
> {
> 	count =3D socket.Receive(buffer, 1, SocketFlags.None);
>=20
> 	message +=3D (char)buffer[0];
> 			=09
> 	if ((char)buffer[0] =3D=3D '\n')
> 		return message;=09
> }
>=20
> ++++++++++++++++++++++++
>=20
> Thanks for reading!
> Dennis
>=20
>=20
> _______________________________________________
> Mono-list maillist  -  Mono-list@lists.ximian.com
> http://lists.ximian.com/mailman/listinfo/mono-list

--=20
boykin@pobox.com    http://pobox.com/~boykin    jabber: johnynek@jabber.org
fingerprint=3DD250 4AD9 4544 B7D2 A17C  911D D608 D387 6718 D75F
Understand Free Software: http://www.gnu.org/philosophy/philosophy.html

--tKy6e3LXpfmanBFM
Content-Type: application/pgp-signature; name="signature.asc"
Content-Description: Digital signature
Content-Disposition: inline

-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.2.4 (GNU/Linux)

iD8DBQFAmDln1gjTh2cY118RApi0AJ4jaZD0/kBT5TtdXueSf90Z9xxD7gCaA5Sk
UYopy8NnoAbX8x0kDHH2Gz8=
=cD+n
-----END PGP SIGNATURE-----

--tKy6e3LXpfmanBFM--