如何让套接字仅接受来自本地主机的连接(在Java中)?
我有一个Java应用程序(不在任何应用程序容器中运行),它在ServerSocket上侦听连接。我希望它只接受来自本地主机的连接。当前,在接受连接后,它会检查对等IP并拒绝它(如果它不是环回地址),但是我知道可以欺骗对等IP地址。因此,如果可能的话,我希望绑定到仅在回送接口上侦听的套接字。这可能吗?
我已经尝试了一些其他方法(例如,在调用bind()时将" 127.0.0.1"指定为本地地址)没有任何运气。提前致谢。
谢谢大家的帮助。我很尴尬地承认这是我的全部错误。我们的应用程序侦听两个不同的端口,我将一个绑定到回送接口,但针对另一个进行测试。当我实际尝试telnet到正确的端口时,一切工作正常(即,绑定到" 127.0.0.1"的功能与预期的完全一样)。
至于欺骗回送地址,你们是正确的。我不应该让它听起来像是最主要的问题。实际上,所需的行为是仅建立本地连接,并且仅绑定到本地接口是一种比直接接受所有连接然后关闭非本地连接更直接的方法。
解决方案
对等IP地址不能以这种方式被欺骗,使用检查对等体并决定在建立过程中断开连接的技术,我们无需担心。
但是:绑定到127.0.0.1应该会起作用,并导致操作系统告诉连接主机,如果它们在系统的其他IP地址之一上进行连接,则没有任何监听。我们可以用可编译的示例来修改此问题吗?也许我们犯了一个简单的错误。
绑定ServerSocket时,指定本地主机应使TCP / IP堆栈拒绝连接。即使这在系统上不起作用,本地主机也无法被欺骗(好的,也许有人入侵了TCP / IP堆栈和默认网关路由器),因为该地址没有通过物理接口路由。
我很好奇为什么绑定无法成功,操作系统,Java版本是什么?
我们似乎已经可以这样做,仍然可以使用accept()连接,然后使用getInetAddress()来确保该地址是经过授权的地址。如果没有,只需直接关闭套接字。 " 127.0.0.1"不是可以被欺骗的地址。
或者,我们可以安装自己的安全管理器,该管理器将使用其远程站点的地址和端口调用其checkAccept()方法。自从第一个解决方案一直适合我以来,我就再也没有尝试过。
如果对等地址被欺骗,则我们无能为力。
但是,欺骗127.0.0.1并不容易。我们必须具有足够哑的TCP / IP堆栈才能接受此类数据包。欺骗者将无法接收回包。在一个好的TCP / IP堆栈上,它应该不能猜测序列号,因此它不能跟上预期的对话。