Re: Reading data on Aysnchronous socket server



Macca,

I don't believe it is possible. Rather, you should store the bytes that
are read in a buffer somewhere, and read again until you have the contents
of the message that you are trying to read. If you know your message is
going to be a certain length, then you can indicate how many bytes you want
to read in the call to Receive/BeginReceive. Then, when you issue the next
call, you can decrement the number of bytes you need to read.

For example, if you know your message is 100 bytes long, and the first
call to Receive/BeginReceive returns 4 bytes, then the next call can be for
96 bytes.

Hope this helps.


--
- Nicholas Paldino [.NET/C# MVP]
- mvp@xxxxxxxxxxxxxxxxxxxxxxxxxxx

"Macca" <Macca@xxxxxxxxxxxxxxxxxxxxxxxxx> wrote in message
news:E40CE17A-1D77-48AF-A1B8-5027F939AE4A@xxxxxxxxxxxxxxxx
Hi,

I have a synchronous socket server which my app uses to read data from
clients.

To test this I have a simulated client that sends 100 byte packets.

I have set up the socket server so that its buffer is bigger than this.
I did this expecting the data to be read in one pass.

However what I find is that on the first pass it only reads the first 4
bytes and then on the second pass of begin.receive, reads the rest of the
message. Is this usual?

This happens each time I send my packet from the
The code I have been using is the MSDN example( shown below).

Can anyone tell me if it is possible to read the whole message sent form
the
client on the first pass rather than it taking 2 or more passes?

Thanks
Macca


using System;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading;

// State object for reading client data asynchronously
public class StateObject {
// Client socket.
public Socket workSocket = null;
// Size of receive buffer.
public const int BufferSize = 100;
// Receive buffer.
public byte[] buffer = new byte[BufferSize];
// Received data string.
public StringBuilder sb = new StringBuilder();
}

public class AsynchronousSocketListener {
// Thread signal.
public static ManualResetEvent allDone = new ManualResetEvent(false);

public AsynchronousSocketListener() {
}

public static void StartListening() {
// Data buffer for incoming data.
byte[] bytes = new Byte[1024];

// Establish the local endpoint for the socket.
// The DNS name of the computer
// running the listener is "host.contoso.com".
SN.IPHostEntry ipHostInfo = SN.Dns.GetHostEntry(hostname);
SN.IPAddress ipAddress = ipHostInfo.AddressList[0];
SN.IPEndPoint localEndPoint = new SN.IPEndPoint(ipAddress,
7777);

// Create a TCP/IP socket.
Socket listener = new Socket(AddressFamily.InterNetwork,
SocketType.Stream, ProtocolType.Tcp );

// Bind the socket to the local endpoint and listen for incoming
connections.
try {
listener.Bind(localEndPoint);
listener.Listen(100);

while (true) {
// Set the event to nonsignaled state.
allDone.Reset();

// Start an asynchronous socket to listen for connections.
Console.WriteLine("Waiting for a connection...");
listener.BeginAccept(
new AsyncCallback(AcceptCallback),
listener );

// Wait until a connection is made before continuing.
allDone.WaitOne();
}

} catch (Exception e) {
Console.WriteLine(e.ToString());
}

Console.WriteLine("\nPress ENTER to continue...");
Console.Read();

}

public static void AcceptCallback(IAsyncResult ar) {
// Signal the main thread to continue.
allDone.Set();

// Get the socket that handles the client request.
Socket listener = (Socket) ar.AsyncState;
Socket handler = listener.EndAccept(ar);

// Create the state object.
StateObject state = new StateObject();
state.workSocket = handler;
handler.BeginReceive( state.buffer, 0, StateObject.BufferSize, 0,
new AsyncCallback(ReadCallback), state);
}

public static void ReadCallback(IAsyncResult ar) {
String content = String.Empty;

// Retrieve the state object and the handler socket
// from the asynchronous state object.
StateObject state = (StateObject) ar.AsyncState;
Socket handler = state.workSocket;

// Read data from the client socket.
int bytesRead = handler.EndReceive(ar);

if (bytesRead > 0) {
// There might be more data, so store the data received so
far.
state.sb.Append(Encoding.ASCII.GetString(
state.buffer,0,bytesRead));

// Check for end-of-file tag. If it is not there, read
// more data.
content = state.sb.ToString();
if (content.IndexOf("<EOF>") > -1) {
// All the data has been read from the
// client. Display it on the console.
Console.WriteLine("Read {0} bytes from socket. \n Data :
{1}",
content.Length, content );
// Echo the data back to the client.
Send(handler, content);
} else {
// Not all data received. Get more.
handler.BeginReceive(state.buffer, 0,
StateObject.BufferSize, 0,
new AsyncCallback(ReadCallback), state);
}
}
}

private static void Send(Socket handler, String data) {
// Convert the string data to byte data using ASCII encoding.
byte[] byteData = Encoding.ASCII.GetBytes(data);

// Begin sending the data to the remote device.
handler.BeginSend(byteData, 0, byteData.Length, 0,
new AsyncCallback(SendCallback), handler);
}

private static void SendCallback(IAsyncResult ar) {
try {
// Retrieve the socket from the state object.
Socket handler = (Socket) ar.AsyncState;

// Complete sending the data to the remote device.
int bytesSent = handler.EndSend(ar);
Console.WriteLine("Sent {0} bytes to client.", bytesSent);

handler.Shutdown(SocketShutdown.Both);
handler.Close();

} catch (Exception e) {
Console.WriteLine(e.ToString());
}
}



.



Relevant Pages

  • Re: question about class Socket
    ... // Retrieve the state object and the handler socket ... // from the asynchronous state object. ... // Read data from the client socket. ... private static void StartClient() ...
    (microsoft.public.dotnet.framework)
  • Re: Socket switch delay
    ... both at the client and at the server (and why ... would you set the send buffer size to zero on a non-overlapped ... One glaring error is your client does ... So when you use a single socket, ...
    (microsoft.public.win32.programmer.networks)
  • Re: question about class Socket
    ... run the following code, the client send a test string, but it doesn't ... // State object for receiving data from remote device. ... // Client socket. ...
    (microsoft.public.dotnet.framework)
  • acynchronous client and server problem using socket
    ... run the following code, the client send a test string, but it doesn't ... // State object for receiving data from remote device. ... // Client socket. ...
    (microsoft.public.dotnet.framework)
  • Re: question about class Socket
    ... here is the client and server code, the client send a file "c:\test.txt" ... // Establish the local endpoint for the socket. ... // State object for reading client data asynchronously ... public static void StartListening() ...
    (microsoft.public.dotnet.framework)