Как работает метод Socket.BeginAccept - C#

Узнай цену своей работы

Формулировка задачи:

Пожалуйста объясните "на пальцах" как работают некоторые функции в этом коде. Вопросы указаны в комментариях. Описанный ниже код принадлежит серверу, к которому обращаются клиенты с просьбой выслать им текущее время. Основная цель для меня научиться делать многопоточные серверы с помощью асинхронного обратного вызова. Не обидьте школьника, помогите советом.
namespace Multi_Server
{
    class Program
    {
        private static Socket _serverSocket;  
        private static readonly List<Socket> _clientSockets = new List<Socket>(); 
//1) для чего нужен этот список сокетов??
      
        private const int _BUFFER_SIZE = 2048; 
        private const int _PORT = 100; 
        private static readonly byte[] _buffer = new byte[_BUFFER_SIZE]; 
 
        static void Main()
        {
            Console.Title = "Server";
            SetupServer();
            Console.ReadLine(); 
            CloseAllSockets();
        }
 
        private static void SetupServer() 
        {
            Console.WriteLine("Setting up server...");
            _serverSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            _serverSocket.Bind(new IPEndPoint(IPAddress.Any, _PORT));
            _serverSocket.Listen(5);
            _serverSocket.BeginAccept(AcceptCallback, null); 
//2) AcceptCallback, это насколько я понял функция которая будет вызвана когда кто либо постучится в наш порт. А что здесь есть NULL??
           
 Console.WriteLine("Server setup complete");
        }

        /// Close all connected client (we do not need to shutdown the server socket as its connections
        /// are already closed with the clients)
   
        private static void CloseAllSockets()
        {
            foreach (Socket socket in _clientSockets)
            {
                socket.Shutdown(SocketShutdown.Both);
                socket.Close();
            }
 
            _serverSocket.Close();
        }
 
        private static void AcceptCallback(IAsyncResult AR)
 //3) Это та самая функция которая вызывается через Socket.BeginAccept (?). Какую роль здесь играет IAsyncResult? 
        {
            Socket socket; 
//4) Это открывают отдельный сокет для свежеподключившегося клиента?
            try
            {
                socket = _serverSocket.EndAccept(AR);
//5) Что происходит в этой строке? (Та что сверху)
         
   }
            catch (ObjectDisposedException) // I cannot seem to avoid this (on exit when properly closing sockets)
            {
                return;
            }
 
           _clientSockets.Add(socket);
           socket.BeginReceive(_buffer, 0, _BUFFER_SIZE, SocketFlags.None, ReceiveCallback, socket);
//6 ReceiveCallback, это функция которая будет вызвана после завершения BeginReceive, а какие данные будет содержать socket?
 
           Console.WriteLine("Client connected, waiting for request...");
 
           _serverSocket.BeginAccept(AcceptCallback, null);
//7 зачем здесь снова вызывается BeginAccept если обмен данными еще не закончен?
        }
 
        private static void ReceiveCallback(IAsyncResult AR)
        {
 
            Socket current = (Socket)AR.AsyncState;
//8) Что делает эта строка? (та что сверху)
     
       int received;
 
            try
            {
                received = current.EndReceive(AR);
            }
            catch (SocketException)
            {
                Console.WriteLine("Client forcefully disconnected");
                current.Close(); // Dont shutdown because the socket may be disposed and its disconnected anyway
                _clientSockets.Remove(current);
                return;
            }
 
            byte[] recBuf = new byte[received];
            Array.Copy(_buffer, recBuf, received);
            string text = Encoding.ASCII.GetString(recBuf);
            Console.WriteLine("Received Text: " + text);
 
            if (text.ToLower() == "get time") // Client requested time
            {
                Console.WriteLine("Text is a get time request");
                byte[] data = Encoding.ASCII.GetBytes(DateTime.Now.ToLongTimeString());
                current.Send(data);
                Console.WriteLine("Time sent to client");
            }
            else if (text.ToLower() == "exit") // Client wants to exit gracefully
            {
                // Always Shutdown before closing
                current.Shutdown(SocketShutdown.Both);
                current.Close();
                _clientSockets.Remove(current);
                Console.WriteLine("Client disconnected");
                return;
            }
            else
            {
                Console.WriteLine("Text is an invalid request");
                byte[] data = Encoding.ASCII.GetBytes("Invalid request");
                current.Send(data);
                Console.WriteLine("Warning Sent");
            }
 
            current.BeginReceive(_buffer, 0, _BUFFER_SIZE, SocketFlags.None, ReceiveCallback, current);
        }
    }
}
Пока это все вопросы. Пожалуйста помогите разобраться. Надеюсь ваши ответы помогут мне постичь истину) Если можно, объясните структуру и алгоритм работы метода socket.BeginAccept() своими словами или на простом примере, а не цитатами из msdn с корявым переводом. Код взят отсюда
https://www.youtube.com/watch?v=xgLRe7QV6QI

Решение задачи: «Как работает метод Socket.BeginAccept»

textual
Листинг программы
Socket current = (Socket)AR.AsyncState;

ИИ поможет Вам:


  • решить любую задачу по программированию
  • объяснить код
  • расставить комментарии в коде
  • и т.д
Попробуйте бесплатно

Оцени полезность:

7   голосов , оценка 3.571 из 5
Похожие ответы