Skip to content

UDP DNS transfer with retry

This operation owns all of the library's network transport behavior. It stamps a fresh transaction identifier into the outbound request on every attempt, sends the datagram to the selected DNS server, waits up to one second for a reply, and retries on timeout before finally giving up and raising NoResponseException.

Field Value
Operation ID OP-DNS-004
Trigger Generic DNS lookup needs to send a serialized request and receive a reply
Inputs Target IPEndPoint (server), request byte[] (requestMessage)
Outputs Reply byte[]; throws NoResponseException once retries are exhausted
Primary components Resolver.UdpTransfer, Socket
Entry point SAIF.Framework.DNS\Resolver.cs

Steps

  1. Initialize attempts to zero and enter a loop that continues while attempts <= _udpRetryAttempts; with _udpRetryAttempts set to 2, this allows the initial send plus two additional timed-out retries (BR-005).
  2. On each iteration, stamp the current _uniqueId into the first two bytes of requestMessage, giving the outbound datagram a fresh transaction identifier.
  3. Create a UDP Socket configured for IPv4 datagram transport.
  4. Set the socket's receive timeout to 1000 milliseconds.
  5. Send the request bytes to the supplied server endpoint.
  6. Allocate a 512-byte buffer to receive the reply.
  7. Attempt to receive a reply into that buffer.
  8. If the first two reply bytes match the transaction identifier just stamped, accept the datagram and return it immediately (BR-006).
  9. If the reply identifier does not match, discard the datagram and continue to another loop iteration (BR-006).
  10. If socket.Receive throws SocketException (typically the 1-second timeout elapsing), increment attempts and let the loop retry the send/receive cycle (BR-005).
  11. In a finally block for every iteration, increment _uniqueId and close the socket, regardless of whether the attempt succeeded, timed out, or received a mismatched reply.
  12. If the loop exhausts all allowed attempts without returning a matching datagram, throw NoResponseException (BR-005).

Process flow

The following diagram visualizes this operation's control flow.

flowchart TD
    Start([UdpTransfer called]) --> Stamp[Stamp fresh transaction id]
    Stamp --> Send[Send UDP datagram]
    Send --> Wait[Wait up to 1 second for a reply]
    Wait --> Match{Reply id matches?}
    Match -->|Yes| EndOk([Return reply bytes])
    Match -->|No, or timeout| Retry{Attempts remaining?}
    Retry -->|Yes| Stamp
    Retry -->|No| EndFail([Throw NoResponseException])

Failure and edge-case behavior

  • A receive timeout surfaces internally as SocketException, which this operation converts into a retry attempt rather than an immediate failure.
  • A reply with a mismatched transaction identifier is discarded silently; the caller has no way to observe that a stray or unrelated packet was received.
  • _uniqueId advances after every iteration, including timed-out and mismatched attempts, so consecutive attempts never reuse the same transaction identifier.
  • A new Socket is created and torn down on every iteration; no socket is reused across attempts.

Sources

  • SAIF.Framework.DNS\Resolver.cs