注意:虽然现在有一个被接受的答案,但它只是一部分; 检查下面的最终iptables规则。
我正在一个接口上接收单播RTPstream,并希望通过第二个接口上的多播将其发送出去。 有问题的系统是一个运行Linux的embedded式处理器,但是我发现在Ubuntu 10.10主机上设置同样困难。 基于http://lists.netfilter.org/pipermail/netfilter/2002-October/038890.html和其他来源的简单明显的答案似乎是:
iptables -t nat -A PREROUTING -i [unicast-interface] -p udp --dport [unicast-incoming-port] -j DNAT --to-destination [multicast-addr]:[multicast-port]
一些额外的研究导致了这种配对:
iptables -t nat -A PREROUTING -i [unicast-interface] -p udp --dport [unicast-incoming-port] -j DNAT --to-destination [multicast-addr]:[multicast-port] iptables -A FORWARD -i [unicast-interface] -o [multicast-interface] -p udp --dport [unicast-incoming-port] -j ACCEPT
虽然列出的规则显示出来,tcpdump显示单播数据包进来,Wireshark在一台单独的机器上显示没有数据包出来。
我看了如何翻译单播通过DNAT与iptables广播? 但似乎与广播案件的具体情况有关。
注意:没有其他iptables规则已经设置。 我使用iptables -L(和-t nat -L)和iptables –flush进行了双重检查。
(我意识到还有其他的select,比如socat ,但是在我转换之前,我想确保我不会错过任何东西。)
编辑:我有ip_forward启用。
~ # sysctl -a 2>&1 |grep ip_forward net.ipv4.ip_forward = 1
编辑:它看起来像越来越多的数据包在我的NAT表( iptables -t nat -L -v -n ),但不是在主/筛选表( iptables -L -v -n )
编辑:经过尝试,我没有成功。 我看到一些人在思科上也有类似的工作,例如在这个网站上: http : //www.penrod.cc/?p=527
这看起来似乎在某个时间点有效,但是由于在原始的embedded式主机上或在Linux工作站上,我一直无法工作。
编辑:事实certificate,这个问题再次提出。
完全工作的最终解决scheme:
获取smcroute(静态组播路由守护进程)。 如果您在embedded式系统中,则可能需要使用smcroute -d
smcroute -a [unicast-interface] [source-ip] [multicast-addr] [multicast-interface] iptables -t nat -A PREROUTING -p UDP -d [unicast-interface-ip] -j NETMAP --to [multicast-addr]
例如:
smcroute -a eth0 192.168.0.101 239.1.1.1 eth0 iptables -t nat -A PREROUTING -p UDP -d 192.168.0.1 -j NETMAP --to 239.1.1.1
请注意,您可能需要改进iptables规则,以确保不会捕获您不想要的数据包 – 这只是一个简单的示例。
你有内核上启用IP转发吗?
# sysctl -a 2>&1 | grep ip_forward net.ipv4.ip_forward=1
您需要将stream量从一个接口传递到另一个接口(即FORWARD表规则)。
编辑:
还有其他的sysctl设置,我怀疑是相关的:
net.ipv4.conf.all.mc_forwarding
和每个接口,以及ipv6。
这个“mc”确实听起来是多播的,但是我手头上没有内核文档是100%确定的。
尝试设置为1,如果不工作总是可以返回到默认的0。
编辑:
来自networking / ip-sysctl.txt:
conf / all / mc_forwarding也必须设置为TRUE来启用组播路由
您需要操作路由表,以便在对数据包进行NAT转换之后,将其发送到正确的接口。
ip route add to $MULTICAST_ADDR dev $MULTICAST_IFACE
如果您通过传入接口发送多播,可能会导致问题,所以我们必须标记数据包
iptables -t mangle <rules to match the packets you want to multicast> -j MARK --mark <your favorite number> ip rule add order 10 fwmark <that favorite number> lookup table <another favorite number> ip route add to <multicast> dev <iface> table <2nd fav number>
最后,你必须认识到,conntrack将不能匹配返回数据包; 你必须做你自己的conntrack:
iptables -t nat -A POSTROUTING -d <multicast> -o <iface> -j SNAT <router's IP>:<a port> iptables -t nat -A PREROUTING -i <router's IP> -p udp --dport <a port> -j DNAT <orig sender>:<orig port>
在那里,一般的做法是做你想做的。 我希望我的(有限的)解释能使你走上正确的道路。
看起来,你将不得不使用特殊的守护进程 – 看看igmpproxy或mrouted – 因为iptables只是将传入的数据包转换并转发给给定范围内的一个地址/端口组合。
该内核模块在prerouting链中创build一个新的netfilter钩子,用于窃取单播报文,并根据“utomu”设置的规则将报文作为组播报文发送出去。
例如:入站单播会话接口为“eth0”,出站多播会话接口为“eth1”。 然后设置
假设单播源IP为“192.168.56.5”,并希望将其转换为组播“225.1.2.3”,则将该规则设置为
它将改变源端口和目标端口。