简体   繁体   中英

How to receive data from server with client on c#?

I am making a little game. Server on C++ and client based on C#. I have problems with data receiving, I dont properly understand how it works, do I need second socket to receive? Or the first socket connect and usable for receiving at the same time? This is the client

public class Connection
{
    static private string ip = "127.0.0.1";
    static private int port = 54000;

    static Socket socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
   // static Socket acpSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);

    public static void connectToServer()
    {
        socket.Connect(ip, port);

    }

    public static void sendData(byte[] buffer)
    {
        socket.Send(buffer);
    }

    public static byte[] encodeMessage(string message)
    {
        byte[] bf = Encoding.ASCII.GetBytes(message);
        return bf;
    }

    public static void recvData()
    {
        byte[] buf = new byte[256];
        byte[] copy = new byte[256];

        try
        {
            socket.Receive(buf);
        }
        catch (Exception e)
        {
            Console.WriteLine("Error");
        }

        if (buf != copy)
        {
            Console.WriteLine(Encoding.ASCII.GetChars(buf).ToString());

            buf = copy;
        }
    }

}

And this is the server:

int main() {

//init sock
WSADATA wsData;
WORD ver = MAKEWORD(2, 2);

int wsok = WSAStartup(ver, &wsData);
if (wsok != 0) {
    cerr << "Error while init\n";
    return 0;
}

//create
SOCKET listening = socket(AF_INET, SOCK_STREAM, 0);
if (listening == INVALID_SOCKET) {
    cerr << "Error while creating\n";
    return 0;
}

//bind
sockaddr_in hint;
hint.sin_family = AF_INET;
hint.sin_port = htons(54000);
hint.sin_addr.S_un.S_addr = INADDR_ANY;

bind(listening, (sockaddr*)&hint, sizeof(hint));

//tell winsock that the socket is for listen
listen(listening, SOMAXCONN);


fd_set master;

FD_ZERO(&master);
FD_SET(listening, &master);

while (true) {
    fd_set copy = master;

    int socketCount = select(0, &copy, nullptr, nullptr, nullptr);

    for (int i = 0; i < socketCount; i++) {
        SOCKET sock = copy.fd_array[i];
        if (sock == listening) {
            //accept connection
            SOCKET client = accept(listening, nullptr, nullptr);

            //add connection to list(&master)
            FD_SET(client, &master);

            //send welcome msg to connected client
            string welcomeMsg = "Your connected!";
            send(client, welcomeMsg.c_str(), welcomeMsg.size() + 1, 0);
        }
        else{

            //accept message
            char buf[32];
            ZeroMemory(buf, 32);
            string str;
            int cnt = 0;
            int bytesIn = recv(sock, buf, 32, 0);

            for (int i = 0; i < sizeof(buf); i++) {
                if (buf[i] != '0') {
                    content[cnt] = buf[i];
                    cnt++;
                }
            }
            if (bytesIn <= 0) {
                closesocket(sock);
                FD_CLR(sock, &master);
            }
            else {
                for (int i = 0; i < sizeof(buf); i++) {
                    cout << content[i];
                }
                for (int i = 0; i < master.fd_count; i++) {
                    SOCKET outSock = master.fd_array[i];
                    if (outSock != listening && outSock != sock) {
                        send(outSock, content, cnt, 0);
                        cout << "Message Send..." << endl;
                    }
                } 
            }
        }
    }

}

And I have timer where i call recvData(). The problem is that After connection it returns "You're Connected!" but after that it just stuck, doesn't work. If i comment the Socket.Receive I have no problem, but i need this receiving. Thanks

You don't have to use a second socket to receive data, but Send and Receive are synchronous functions, so the thread is blocked until the current operation finishes doing its job. For receiving, the socket has to receive at least on byte in order to unblock the application. If no data is available, Receive will wait indefinitely unless you specify a timeout using ReceiveTimeout property. To avoid the blocking part, use the asynchronous functions BeginReceive and BeginSend . MSDN has a full server - client example using asynchronous sockets.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM