问题是,如果IPAddress.Any
作为参数给出,则以下代码可以正常工作,但如果使用`IPAddress.IPv6Any则抛出错误。
我收到错误#10057
套接字未连接。
由于套接字是,因此不允许发送或接收数据的请求 未连接和(使用时在数据报套接字上发送) sendto)没有提供地址。任何其他类型的操作都可能 也返回此错误 - 例如,setsockopt设置SO_KEEPALIVE if 连接已重置。
为什么它不能像IPv6一样工作?我很确定它不是防火墙,因为端口保持不变并且它与IPv4一起使用(我的防火墙应该传递我的应用程序发出的任何请求)。
为了简化代码,它是这样的:
听众:
listener = new TcpListener(IPAddress.IPv6Any, portNr);
listener.AllowNatTraversal(true);
listener.Start();
listener.BeginAcceptTcpClient(this.AcceptClient, null);
客户:
client = new TcpClient();
client.NoDelay = true;
try
{
this.client.Connect(ip, port); //ip = "localhost" when connecting as server
}
catch (Exception ex)
{
FileLogger.LogMessage(ex);
Disconnect();
}
我正在尝试设置TCP连接的“服务器端”。
我所做的是在localhost启动一个监听器,然后作为客户端连接到它(并允许其他人作为客户端加入)。
我想要实现的是这个TCP服务器的直接可寻址性,遵循这篇文章:http://blogs.msdn.com/b/ncl/archive/2009/07/27/end-to-end-connectivity-with-nat-traversal-.aspx
我这样做的原因是我希望A人能够在他们都在NAT路由器后面时连接到B人。
答案 0 :(得分:1)
我解决了类似的问题,其中以下行只会阻止来自IPv4地址的连接:
listener = new TcpListener(IPAddress.IPv6Any, portNr);
默认情况下,配置为接受IPv6连接时,套接字似乎只接受IPv6连接。要解决此问题,我必须将我的代码更新为:
listener.Server.SetSocketOption(SocketOptionLevel.IPv6, SocketOptionName.IPv6Only, false);
listener.Start();
答案 1 :(得分:1)
我知道这个答案有点迟了,但我也有这个问题,而且与客户有关。问题是,你提供的代码......
client = new TcpClient();
...创建TcpClient
的IPv4实例,该实例无法解释IPv6地址。因此,如果您在初始化时已经拥有IP地址,请尝试初始化您的TcpClient,如下所示:
TcpClient client = new TcpClient(ip.AddressFamily);
如果变量ip
是一个字符串,则需要先将其转换为IPAddress类型:
IPAddress iAddr = IPAddress.Parse(ip);
实际上IPv6-TcpClient似乎也与IPv4地址兼容,因此您也可以按如下方式初始化您的客户端:
TcpClient client = new TcpClient(AddressFamily.InterNetworkV6)
虽然上层建议似乎是最干净的建议,但最底层的建议似乎是更普遍的建议。最后,这取决于您的偏好。
答案 2 :(得分:0)
IPAddress.Loopback == FAIL
IPAddress.IPv6Loopback == SUCCESS
或许localhost
映射到您的IPv4 Loopback
地址?
答案 3 :(得分:0)
当您使用TcpClient.Connect(string, int)
时,您可以因DNS解析而中断。
虽然Microsoft会首先尝试使用IPv6地址,但分辨率可能只返回IPv4地址。
http://msdn.microsoft.com/en-us/library/8s2yca91.aspx
因此,您是否可以尝试在客户端调用TcpClient.Connect(IPAddress.IPv6Loopback, port)
来测试它是否有效?