7

I have a socket server and am trying to receive a string from the client.

The client is perfect and when I use this

Socket s = myList.AcceptSocket();
Console.WriteLine("Connection accepted from " + s.RemoteEndPoint);

byte[] b = new byte[100];
int k = s.Receive(b);
Console.WriteLine(k);
Console.WriteLine("Recieved...");
for (int i = 0; i < k; i++) {
    Console.Write(Convert.ToChar(b[i]));
    ASCIIEncoding asen = new ASCIIEncoding();
    s.Send(asen.GetBytes("The string was recieved by the server."));
}

All is okay and I get my string in the console.

But how can I get now my receive into a string so I can use it in a switch case?

Like this:

string action = Convert.ToChar(b[i]);

Error:

The Name i isn't in the current context. its the only Error Message i get.

Anil
  • 2,430
  • 3
  • 37
  • 55
Hanselman
  • 171
  • 1
  • 2
  • 8
  • Please enhance your code example and show the definition of b and possibly s. Next, you certainly did not get the error you are describing because it clearly has typos in it. Please post a copy-pasted version of the exception plus the callstack, not a paraphrased write-up. I suspect you got the error described in this post: http://stackoverflow.com/questions/706603/the-name-controlname-does-not-exist-in-the-current-context – Christoph Sep 05 '15 at 12:03
  • Okey i updated my Code Part a bit. I will check the Link :) – Hanselman Sep 05 '15 at 12:07
  • @Christoph I checked your link but not much helpfull or informing for me. I must say iam not often program with C# – Hanselman Sep 05 '15 at 12:08
  • You can't just say `Convert.ToChar(b[i])` and expect it to return a string in which the variable `i` looped through all the bytes of the `b`-array. Explicity create the loop variable `i` in a `for` statement, otherwise the variable won't exist. `string action = ""; for(int i=0; i < b.Length; i++) action += Convert.ToChar(b[i]);` would fill the `action` variable appropiatly. – Maximilian Gerhardt Sep 05 '15 at 12:13
  • _"The Name i isn't in the current context"_ - then you're not showing your actual code. Do you have a semicolon after the `for();`? – CodeCaster Sep 05 '15 at 12:24
  • @CodeCaster No and i copy and pasted my exact code :) Please read the Answer below and my Comment to it – Hanselman Sep 05 '15 at 12:26

3 Answers3

5

This way no need set buffer size, it fits to response:

public static byte[] ReceiveAll(this Socket socket)
    {
        var buffer = new List<byte>();

        while (socket.Available > 0)
        {
            var currByte = new Byte[1];
            var byteCounter = socket.Receive(currByte, currByte.Length, SocketFlags.None);

            if (byteCounter.Equals(1))
            {
                buffer.Add(currByte[0]);
            }
        }

        return buffer.ToArray();
    }
Rodrigo Reis
  • 1,097
  • 12
  • 21
  • I think a minor optimization would be to put the currByte variable outside the while scope. Also, instead just taking a single byte at a time, you could take all the available. Nonetheless, a very robust solution! – TopchetoEU Nov 27 '21 at 17:24
4

Assuming s is a Socket object on which you call receive, you get an byte[] back. To convert this back to a string, use the appropiate encoding, e.g.

string szReceived = Encoding.ASCII.GetString(b);

Edit: Since the buffer b is always 100 bytes, but the actual number of bytes received varies with each connection, one should use the return value of the Socket.Receive() call to only convert the actual number of received bytes.

byte[] b = new byte[100];
int k = s.Receive(b);
string szReceived = Encoding.ASCII.GetString(b,0,k); 
Maximilian Gerhardt
  • 5,188
  • 3
  • 28
  • 61
  • It works half Thanks ! :) But now it is showing correct when i write it in Console.... but My Switch Case will not work.. happend nothing :o Console.WriteLine(szReceived); Console.WriteLine("Recieved..."); switch (szReceived) { case "ping": Console.WriteLine("Ping wird ausgeführt!"); break; case "somethingelse": break; } – Hanselman Sep 05 '15 at 12:24
  • My first intuition says that you should cut off the array at the number of bytes you received. `Socket.Receive()` has a return value, and you need that to chop off your array at the actual bytes received. Use this: `int k = s.Receive(b); string szReceived = Encoding.ASCII.GetString(b.Take(k).ToArray());` Then the string should be constructed perfectly. (You need a `using System.Linq;` for that, or use the second overload `string szReceived = Encoding.ASCII.GetString(b,0, k);`) – Maximilian Gerhardt Sep 05 '15 at 12:29
  • You did it ! :D Thanks for all. – Hanselman Sep 05 '15 at 12:31
4

Init socket

Socket socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
IPAddress ipAdd = System.Net.IPAddress.Parse(m_ip);
IPEndPoint remoteEP = new IPEndPoint(ipAdd, m_port);

Connect socket

socket.Connect(remoteEP);

Receive from socket

byte[] buffer = new byte[1024];
int iRx = socket.Receive(buffer);
char[] chars = new char[iRx];

System.Text.Decoder d = System.Text.Encoding.UTF8.GetDecoder();
int charLen = d.GetChars(buffer, 0, iRx, chars, 0);
System.String recv = new System.String(chars);

Send message

byte[] byData = System.Text.Encoding.ASCII.GetBytes("Message");
socket.Send(byData);

Close socket

socket.Disconnect(false);
socket.Close();
Masoud Siahkali
  • 5,100
  • 1
  • 29
  • 18