jstedfast/MailKit · error · ArgumentException

The specified host address must be IPv4.

Error message

The specified host address must be IPv4.

What it means

When Socks4Client.Connect is given an IPAddress directly instead of a host name, it requires AddressFamily.InterNetwork; an IPv6 address throws ArgumentException('The specified host address must be IPv4.'). SOCKS4 protocol cannot carry IPv6 addresses.

Solutions

  1. Pass an IPv4 IPAddress or literal (e.g. 127.0.0.1, not ::1).
  2. Filter resolved addresses for AddressFamily.InterNetwork before passing one in.
  3. Use Socks5Client if the target is only reachable over IPv6.
  4. Replace the IPv6 loopback with IPAddress.Loopback (127.0.0.1) in tests.

Example fix

// before
var proxy = new Socks4Client();
proxy.Connect(new IPEndPoint(IPAddress.Parse("::1"), 995), "user"); // IPv6 -> throws
// after
proxy.Connect(new IPEndPoint(IPAddress.Loopback, 995), "user"); // 127.0.0.1
Defensive patterns

Strategy: validation

Validate before calling

if (ip.AddressFamily != AddressFamily.InterNetwork)
    throw new InvalidOperationException($"SOCKS4 requires IPv4, got {ip}");

Type guard

bool IsIPv4(IPAddress ip) => ip.AddressFamily == AddressFamily.InterNetwork;

Try / catch

try {
    proxy.Connect(new IPEndPoint(ip, port), cancellationToken);
} catch (ArgumentException ex) when (ex.Message.Contains("must be IPv4")) {
    // resolve/select an IPv4 address or use Socks5Client
}

Prevention

When it happens

Trigger: Calling Socks4Client.Connect passing an IPEndPoint/IPAddress built from an IPv6 literal (e.g. ::1 or a resolved AAAA address) — for instance IPAddress.IPv6Loopback or the result of DNS.GetHostAddresses picking the v6 entry.

Common situations: Hard-coding 'localhost' and using IPAddress.Parse("::1") or Dns resolution returning ::1; test code constructing endpoints with Any/IPv6Any; migrating code from Socks5 (IPv6-capable) to Socks4 without updating addresses.

Understand the failure class

Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.

Related errors


AI-assisted analysis of jstedfast/MailKit@9d3859a785 (2026-09-15). Data as JSON: /api/errors/487add2fe90ed443. Report an issue: GitHub.

Appendix: source

Thrown at MailKit/Net/Proxy/Socks4Client.cs:241

		/// </exception>
		public override Stream Connect (string host, int port, CancellationToken cancellationToken = default)
		{
			byte[]? domain = null;
			byte[] addr;

			ValidateArguments (host, port);

			if (!IPAddress.TryParse (host, out var ip)) {
				if (IsSocks4a) {
					domain = Encoding.UTF8.GetBytes (host);
					addr = InvalidIPAddress;
				} else {
					ip = Resolve (host, cancellationToken);
					addr = ip.GetAddressBytes ();
				}
			} else {
				if (ip.AddressFamily != AddressFamily.InterNetwork)
					throw new ArgumentException ("The specified host address must be IPv4.", nameof (host));

				addr = ip.GetAddressBytes ();
			}

			cancellationToken.ThrowIfCancellationRequested ();

			var socket = SocketUtils.Connect (ProxyHost, ProxyPort, LocalEndPoint, cancellationToken);

			try {
				var buffer = GetConnectCommand (domain, addr, port);

				Send (socket, buffer, 0, buffer.Length, cancellationToken);

				// +-----+-----+----------+----------+
				// | VER | REP | BND.PORT | BND.ADDR |
				// +-----+-----+----------+----------+
				// |  1  |  1  |    2     |    4     |
				// +-----+-----+----------+----------+

View on GitHub (pinned to 9d3859a785)