MaxLevs
@MaxLevs

Асинхронный UDP-клиент на C#. Где происходит получение данных?

Прочитал вот этот пост - https://habr.com/ru/post/238377. Выглядит интересно.
Но не могу понять, где происходит получение ответа от сервера.
Вижу код
public async Task<byte[]> SendReceiveAsync(byte[] msg, string ip, int port, int timeOut)
        {
            var endPoint = new IPEndPoint(IPAddress.Parse(ip), port);
            var tcs = new TaskCompletionSource<byte[]>();

            try
            {
                var tokenSource = new CancellationTokenSource(timeOut);
                var token = tokenSource.Token;
                if (!_tcsDictionary.ContainsKey(endPoint)) _tcsDictionary.TryAdd(endPoint, tcs);
                _client.Send(msg, msg.Length, ip, port);

                var result = await tcs.Task.WithCancellation(token);
                return result;
            }

            finally
            {
                _tcsDictionary.TryRemove(endPoint, out tcs);
            }
        }


И расширение
static class TaskExtension
    {
        public static async Task<T> WithCancellation<T>(this Task<T> task, CancellationToken cancellationToken)
        {
            var tcs = new TaskCompletionSource<bool>();

            using (cancellationToken.Register(
                        s => ((TaskCompletionSource<bool>)s).TrySetResult(true), tcs))
                if (task != await Task.WhenAny(task, tcs.Task))
                    throw new OperationCanceledException(cancellationToken);
            return await task;
        }
    }


И не вижу, где вызывается, например, _client.Receive().

Подскажите, пожалуйста, откуда берутся данные результата?
  • Вопрос задан
  • 64 просмотра
Решения вопроса 1
@none7
Там ниже код
Task.Run(() =>
            {
                IPEndPoint ipEndPoint = null;

                while (true)
                {
                    try
                    {
                        var receivedBytes = _client.Receive(ref ipEndPoint);
                        TaskCompletionSource<byte[]> tcs;
                        if (_tcsDictionary.TryGetValue(ipEndPoint, out tcs)) tcs.SetResult(receivedBytes);
                    }
                    catch (SocketException)
                    {
                        ;//при невозможности соединения продолжаем работать
                    }

                }
            });

Здесь при помощи tcs.SetResult данные передаются в первый кусок кода.
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы