【发布时间】:2013-08-22 00:31:56
【问题描述】:
我有一个带有两个以太网适配器的 Linux 设备(实际上是一个用于原型的 BeagleBoard)。我想要的是这样的:
主以太网接口 (eth0) 连接到客户端的网络(可能是 DHCP 或分配的静态 IP)。
第二个以太网接口 (eth1) 直接连接到另一个 Linux 板。
Beagle 上的用户级 C 程序可以侦听来自客户端网络(在 eth0 上)的传入连接,根据需要做出响应,并可能连接到 eth1 上的其他设备
我们希望第二个设备对网络的其余部分完全隐藏,以便只有 Beagle 上的程序可以连接到它。
我希望这两个接口可以完全分开,并且我的代码可以选择它想要监听/打开连接的接口。典型代码:
socket_desc = socket(AF_INET, SOCK_STREAM, 0);
memset(&client_addr, 0, sizeof(client_addr));
client_addr.sin_family = AF_INET;
inet_pton( AF_INET, address, (void *)(&(client_addr.sin_addr.s_addr)) );
client_addr.sin_port = htons(port);
/* Connect to remote on TCP port: */
connect(*socket_desc, (struct sockaddr*) &client_addr, sizeof(client_addr) );
...
我们可以设置要连接的地址和端口,但不能设置以太网接口。我找到了this answer。这是否意味着我要实现的目标必须留给内核路由?
我知道我可以将 eth1 设置在它自己的子网上,但我有一个问题:鉴于我们对客户端的网络一无所知,我怎么知道我使用的任何子网都不会最终与客户的网络发生冲突?例如,我在这里使用 192.168.1.0,所以我可以将 eth1 放在 192.168.0.0... 但是如果客户端使用该范围怎么办?我们不想为每个部署重新配置 eth1 及其连接设备的设置,尽管我们可能必须配置 eth0。
那么有没有更好的方法来做到这一点?或者我可以为 eth1 上的子网使用一个保留的 IP 地址范围,保证不会与客户端的网络冲突(例如 169.254.1.x)?
对不起,这有点含糊,但我已经在谷歌上搜索了好几天,可能变得更加困惑而不是更少。
编辑 - 2013-08-29:
我刚刚发现 this question 提供了部分答案:您可以使用 setsockopt(...) 和 SO_BINDTODEVICE 绑定到特定设备/接口.这似乎可行,尽管我仍然无法弄清楚如何设置路由表以在“内部”网络恰好与连接到 eth0 的“外部”网络具有相同 IP 地址范围的情况下可靠地工作。
【问题讨论】:
-
客户端的网络是否可能位于路由器后面、使用 NAT 并使用分配私有 IPv4 地址(例如 10.x.x.x 或 172.16.x.x 或 192.168.x.x)的 DHCP 服务器?那么也许您可以在您的临时(eth1,直接连接)子网上使用非私有(即公共)IPv4 地址?当 Linux 系统有多个以太网接口(IP 地址属于 Linux 主机,而不是接口)时,请注意 ARP flux problem。
-
有可能...我 99% 确定客户端将在专用网络上,但不完全确定!是的,我已经遇到了 ARP 通量问题并设置了我的 arp_ignore 设置。
-
一个可靠的解决方案是禁用 eth1 直到 eth0 从客户端的 DHCP 服务器获得其 IP 地址。然后在(剩余的)私有 IP 地址范围中进行选择,并在未使用的子网中为 eth1 分配一个静态 IP 地址。打开 eth1 并为您的 ad hoc 子网启动 DHCP 服务器。然后 ad hoc 网络上的其他主机可以获得其动态 IP 地址。现在每个人都有一个唯一的 IP 地址,并且您的主板有两个子网可以轻松应对。
标签: c linux tcp interface subnet