从版本8开始,FreeBSD支持IP_BINDANY套接字选项,手册页定义为:
如果在SOCK_STREAM,SOCK_DGRAM或a上启用了IP_BINDANY选项 SOCK_RAW套接字,可以将(2)绑定到任何地址,甚至是一个不绑定的地址 系统中任何可用的网络接口。此功能(in 与特殊防火墙规则结合使用)可用于实现 透明代理。设置需要PRIV_NETINET_BINDANY权限 这个选项。
是否可以编写可以使用此功能的Java程序?我检查了SocketOptions的文档,但显然没有列出此选项。那么有什么解决方法吗?
问候,
拉吉
答案 0 :(得分:1)
是否可以编写可以使用此功能的Java程序?
使用纯Java无法实现。
那么有什么解决方法吗?
有几个基于JNA / JNI的库用于从Java程序进行Posix系统调用;有关详细信息,请参阅此问题/答案:
我不知道这些是否可用于FreeBSD上的Java。
进一步思考,有可能在纯Java(尽管必然是非可移植的)Java中实现它。它需要创建SocketImpl和/或DatagramSocketImpl的子类以及使用它们的必要基础结构。这会很复杂。
答案 1 :(得分:0)
我在JNA中编写了一个库,可以合理地移植setsockopt
位。你可以找到它here。
但是,要更改bind
行为,您可能需要深入挖掘套接字代码。为什么,请参阅here,特别是这一点:
所以我们只需要创建一个新的
java.net.Socket
对象,调用setsockopt()
并最终在套接字上调用bind()
- 这很简单,对吧?不幸的是,它并不那么简单 - 在Java中创建一个新的Socket对象(在OpenJDK和Oracle JVM中)实际上并没有分配文件描述符。相反,文件描述符是在Java的bind()
函数本身内分配的 - 这使得在适当的位置调用setsockopt()
变得相当困难。
作者提出了一个相当复杂的解决方法 - 我不会在这里复制他的整篇文章。