Beispiel #1
0
        private void TcpConnectCompleted(IAsyncResult ar)
        {
            DnsAsyncState state = (DnsAsyncState)ar.AsyncState;

            if (state.Timer != null)
            {
                state.Timer.Dispose();
            }

            if (state.TimedOut)
            {
                state.ServerIndex++;
                TcpBeginConnect(state);
            }
            else
            {
                state.TcpClient.EndConnect(ar);

                state.TcpStream = state.TcpClient.GetStream();

                int tmp = 0;

                state.TcpBuffer = new byte[2];
                DnsMessageBase.EncodeUShort(state.TcpBuffer, ref tmp, (ushort)state.QueryLength);

                IAsyncResult asyncResult = state.TcpStream.BeginWrite(state.TcpBuffer, 0, 2, TcpSendLengthCompleted, state);
                state.Timer = new Timer(TcpTimedOut, asyncResult, QueryTimeout, Timeout.Infinite);
            }
        }
Beispiel #2
0
        private void TcpReceiveLengthCompleted(IAsyncResult ar)
        {
            DnsAsyncState state = (DnsAsyncState)ar.AsyncState;

            if (state.Timer != null)
            {
                state.Timer.Dispose();
            }

            if (state.TimedOut)
            {
                state.ServerIndex++;
                TcpBeginConnect(state);
            }
            else
            {
                state.TcpStream.EndRead(ar);

                int tmp            = 0;
                int responseLength = DnsMessageBase.ParseUShort(state.TcpBuffer, ref tmp);

                state.TcpBuffer = new byte[responseLength];

                IAsyncResult asyncResult = state.TcpStream.BeginRead(state.TcpBuffer, 0, responseLength, TcpReceiveCompleted, state);
                state.Timer = new Timer(TcpTimedOut, asyncResult, QueryTimeout, Timeout.Infinite);
            }
        }
Beispiel #3
0
        private static void UdpTimedOut(object ar)
        {
            IAsyncResult asyncResult = (IAsyncResult)ar;

            if (!asyncResult.IsCompleted)
            {
                DnsAsyncState state = (DnsAsyncState)asyncResult.AsyncState;
                state.TimedOut = true;
                state.UdpClient.Close();
            }
        }
Beispiel #4
0
        private void UdpReceiveCompleted(IAsyncResult ar)
        {
            DnsAsyncState state = (DnsAsyncState)ar.AsyncState;

            if (state.Timer != null)
            {
                state.Timer.Dispose();
            }

            if (state.TimedOut)
            {
                state.ServerIndex++;
                UdpBeginSend(state);
            }
            else
            {
                byte[] responseData = state.UdpClient.EndReceive(ar, ref state.UdpEndpoint);

                state.UdpClient.Close();
                state.UdpClient   = null;
                state.UdpEndpoint = null;

                state.Response = new DnsMessage();
                state.Response.Parse(responseData, false, state.TSigKeySelector, state.TSigOriginalMac);

                if (state.Response.ReturnCode == ReturnCode.ServerFailure)
                {
                    if (state.ServerIndex++ < state.Servers.Count)
                    {
                        UdpBeginSend(state);
                        return;
                    }
                    else
                    {
                        state.SetCompleted();
                    }
                }
                else
                {
                    if (state.Response.IsTruncated)
                    {
                        TcpBeginConnect(state);
                        return;
                    }
                    else
                    {
                        state.SetCompleted();
                    }
                }
            }
        }
Beispiel #5
0
        private static void TcpTimedOut(object ar)
        {
            IAsyncResult asyncResult = (IAsyncResult)ar;

            if (!asyncResult.IsCompleted)
            {
                DnsAsyncState state = (DnsAsyncState)asyncResult.AsyncState;
                state.TimedOut = true;
                if (state.TcpStream != null)
                {
                    state.TcpStream.Close();
                }
                state.TcpClient.Close();
            }
        }
Beispiel #6
0
        /// <summary>
        /// Send a custom message to the dns server and returns the answer asynchronously.
        /// </summary>
        /// <param name="message">Message, that should be send to the dns server</param>
        /// <param name="requestCallback">An <see cref="System.AsyncCallback"/> delegate that references the method to invoked then the operation is complete.</param>
        /// <param name="state">A user-defined object that contains information about the receive operation. This object is passed to the <paramref name="requestCallback"/> delegate when the operation is complete.</param>
        /// <returns>An <see cref="System.IAsyncResult"/> IAsyncResult object that references the asynchronous receive.</returns>
        public IAsyncResult BeginSendMessage(DnsMessage message, AsyncCallback requestCallback, object state)
        {
            if (message == null)
            {
                throw new ArgumentNullException("message");
            }

            if ((message.Questions == null) || (message.Questions.Count == 0))
            {
                throw new ArgumentException("At least one question must be provided", "message");
            }

            if (message.TransactionID == 0)
            {
                message.TransactionID = (ushort)new Random().Next(0xffff);
            }

            byte[] queryData;
            int    queryLength = message.Encode(out queryData, true);

            DnsAsyncState asyncResult = new DnsAsyncState()
            {
                QueryData = queryData, QueryLength = queryLength, UserCallback = requestCallback, AsyncState = state, Servers = _dnsServers, ServerIndex = 0
            };

            if (message.TSigOptions != null)
            {
                asyncResult.TSigKeySelector = (a, n) => message.TSigOptions.KeyData;
                asyncResult.TSigOriginalMac = message.TSigOptions.OriginalMac;
            }

            bool sendByTcp = ((queryLength > 512) || (message.Questions[0].RecordType == RecordType.Axfr) || (message.Questions[0].RecordType == RecordType.Ixfr));

            if (sendByTcp)
            {
                TcpBeginConnect(asyncResult);
            }
            else
            {
                UdpBeginSend(asyncResult);
            }

            return(asyncResult);
        }
Beispiel #7
0
        private void TcpBeginConnect(DnsAsyncState state)
        {
            if (state.ServerIndex == state.Servers.Count)
            {
                state.Response  = null;
                state.TcpStream = null;
                state.TcpClient = null;
                state.SetCompleted();
                return;
            }

            IPAddress server = state.Servers[state.ServerIndex];

            state.TcpClient = new TcpClient(server.AddressFamily);
            state.TimedOut  = false;

            IAsyncResult asyncResult = state.TcpClient.BeginConnect(server, _DNS_PORT, TcpConnectCompleted, state);

            state.Timer = new Timer(TcpTimedOut, asyncResult, QueryTimeout, Timeout.Infinite);
        }
Beispiel #8
0
        private void UdpBeginSend(DnsAsyncState state)
        {
            if (state.ServerIndex == state.Servers.Count)
            {
                state.Response    = null;
                state.UdpClient   = null;
                state.UdpEndpoint = null;
                state.SetCompleted();
                return;
            }

            state.UdpEndpoint = new IPEndPoint(state.Servers[state.ServerIndex], _DNS_PORT);

            state.UdpClient = new UdpClient(state.UdpEndpoint.AddressFamily);
            state.UdpClient.Connect(state.UdpEndpoint);
            state.TimedOut = false;

            IAsyncResult asyncResult = state.UdpClient.BeginSend(state.QueryData, state.QueryLength, UdpSendCompleted, state);

            state.Timer = new Timer(UdpTimedOut, asyncResult, QueryTimeout, Timeout.Infinite);
        }
Beispiel #9
0
        private void TcpReceiveCompleted(IAsyncResult ar)
        {
            DnsAsyncState state = (DnsAsyncState)ar.AsyncState;

            if (state.Timer != null)
            {
                state.Timer.Dispose();
            }

            if (state.TimedOut)
            {
                state.ServerIndex++;
                TcpBeginConnect(state);
            }
            else
            {
                state.TcpStream.EndRead(ar);

                state.TcpStream.Close();
                state.TcpClient.Close();
                state.TcpStream = null;
                state.TcpClient = null;

                state.TcpBuffer = null;

                state.Response = new DnsMessage();
                state.Response.Parse(state.TcpBuffer, false, state.TSigKeySelector, state.TSigOriginalMac);

                if ((state.Response.ReturnCode == ReturnCode.ServerFailure) && (state.ServerIndex++ < state.Servers.Count))
                {
                    TcpBeginConnect(state);
                    return;
                }
                else
                {
                    state.SetCompleted();
                }
            }
        }
Beispiel #10
0
        private void TcpSendCompleted(IAsyncResult ar)
        {
            DnsAsyncState state = (DnsAsyncState)ar.AsyncState;

            if (state.Timer != null)
            {
                state.Timer.Dispose();
            }

            if (state.TimedOut)
            {
                state.ServerIndex++;
                TcpBeginConnect(state);
            }
            else
            {
                state.TcpStream.EndWrite(ar);

                IAsyncResult asyncResult = state.TcpStream.BeginRead(state.TcpBuffer, 0, 2, TcpReceiveLengthCompleted, state);
                state.Timer = new Timer(TcpTimedOut, asyncResult, QueryTimeout, Timeout.Infinite);
            }
        }
Beispiel #11
0
        private void UdpSendCompleted(IAsyncResult ar)
        {
            DnsAsyncState state = (DnsAsyncState)ar.AsyncState;

            if (state.Timer != null)
            {
                state.Timer.Dispose();
            }

            if (state.TimedOut)
            {
                state.ServerIndex++;
                UdpBeginSend(state);
            }
            else
            {
                state.UdpClient.EndSend(ar);

                IAsyncResult asyncResult = state.UdpClient.BeginReceive(UdpReceiveCompleted, state);
                state.Timer = new Timer(UdpTimedOut, asyncResult, QueryTimeout, Timeout.Infinite);
            }
        }
Beispiel #12
0
        /// <summary>
        /// Ends a pending asynchronous operation.
        /// </summary>
        /// <param name="ar">An <see cref="System.IAsyncResult"/> object returned by a call to <see cref="ARSoft.Tools.Net.Dns.DnsClient.BeginSendMessage"/>.</param>
        /// <returns>The complete response of the dns server</returns>
        public DnsMessage EndSendMessage(IAsyncResult ar)
        {
            DnsAsyncState state = (DnsAsyncState)ar;

            return(state.Response);
        }