shixudong@163.com

疫情期间,因工作需要远程唤醒办公电脑(已通过wireguard组网),以前通过在家里树莓派上运行wolf(Wake on Lan Forwarder)实现网络唤醒包的接收和转广播来唤醒家里电脑。现在则需要将唤醒包转发到异地后广播以唤醒办公电脑,顺便试一下新方法,看看能否不借助转发软件(如专用wolf或通用socat)而直接通过iptables DNAT解决。经过网上搜索资料,反复验证测试,发现iptables确实能通过DNAT实现unicast与broadcast之间相互映射,从而轻易解决远程唤醒异地广播问题,现把问题解决过程分享如下。

一、DNAT实现unicast到broadcast映射

关于DNAT实现unicast到broadcast的映射,网上资料较多,已有成熟解决方案,本人在这里主要起到收集整理资料的作用,没花多少脑子。解决方案根据kernel版本不同分两种情况:
1、sysctl支持bc_forwarding参数的linux较新内核,同时通过如下两条命令即可允许iptables将unicast DNAT到broadcast。
sudo sysctl -w net.ipv4.conf.eth0.bc_forwarding=1
sudo sysctl -w net.ipv4.conf.all.bc_forwarding=1

几点注意事项:
(1)    命令中eth0对应DNAT前数据包的入口设备(cisco是在广播包的出口接口设置ip directed-broadcast),必须是三层设备(在网桥情况下必须是桥设备br0,而不能是桥端口设备eth0)
(2)    以上两条命令缺一不可
(3)    由于linux自身的IP路由机制,DNAT转换后的broadcast必须是定向广播,而不能是本地广播(255.255.255.255)

2、不支持bc_forwarding参数的linux老内核,利用一个平时不用的单播IP,在Linux上为这个IP设置一个静态ARP表项(ff:ff:ff:ff:ff:ff),然后通过iptables将unicast DNAT到该单播IP,即可将三层unicast IP转换成二层以太网广播地址,可达到和1同样的效果。

上述两种情况的区别在于,前者是真正的二层和三层广播,不仅能用于远程网络唤醒,还可用于广播UDP数据;而后者在三层上不是广播,一般只能用于远程网络唤醒(网卡硬件层面处理)。

顺便提一下,如仅在内部网络上使用远程唤醒,实际上并不需要借助iptables,只需在远端linux作上述配置,便可直接针对远程广播地址或特定的单播IP发送唤醒包。

二、DNAT实现broadcast到unicast映射

网上很难搜到DNAT成功实现broadcast到unicast映射的相关资料,但我在树莓派上却能一次性成功,这种感觉很怪异,难道我的树莓派有特殊配置。于是在虚拟机上测试了一下broadcast到unicast的DNAT映射,确实和网上说的一样,无法成功。经对比分析,树莓派启用了br_netfilter模块,试着在树莓派上卸载该模块(sudo rmmod br_netfilter),再次测试,果然无法成功。
经分析br_netfilter和ip_forward源码,发现ip_forward在包类型不是PACKET_HOST时,一律DROP。由于包类型是在网卡二层收包时间接调用eth_type_trans赋值,如仅在三层调用iptables对broadcast做DNAT,iptables代码并不对二层包类型进行修改,而broadcast因包类型不为PACKET_HOST从而无法被三层转发,导致DNAT无法成功。而启用br_netfilter模块后,在二层调用iptables对broadcast做DNAT,如判断DNAT后数据包目的地和进入包在同一网桥可在二层直接转发;如两者不在同一网桥,br_netfilter会将DNAT后数据包的二层目标地址修改为桥MAC,并将原broadcast包类型修改为PACKET_HOST,后续交由三层处理并顺利通过ip_forward完成转发。所以DNAT实现broadcast到unicast映射的最简单办法就是启用br_netfilter模块。
但上述方法存在一个不足,由于桥转发本身的内在机制,当DNAT后数据包目的地和初始进入包都位于网桥同一物理端口时,无法顺利二层转发,当然也无法实现broadcast到unicast的DNAT映射了。为避免这种情况,仍需设法回到三层来处理DNAT,或者说在不启用br_netfilter模块的前提下,实现broadcast到unicast的DNAT映射。
根据上文介绍和相关源码分析,可通过ebtables将二层广播地址修改为桥MAC,并将broadcast包类型修改为PACKET_HOST,然后强制移交三层处理DNAT映射,这样既绕开了网桥同一端口无法转发的机制,也解决了ip_forward DROP包的限制。经验证,ebtables BROUTING使用-j redirect --redirect-target DROP可对需要DNAT的broadcast包进行redirect后移交三层iptables实现broadcast到unicast的DNAT映射。
综上,要使DNAT能成功实现broadcast到unicast映射,上文提到的br_netfilter模块和ebtables工具都必须在bridge环境下方能生效。如bridge不存在,就无法成功操作ebtables和br_netfilter。
三、网络唤醒包的分流
原先网络唤醒包只要发往一处,现在则需要同时发往异地,也就是说最好能实现唤醒包的复制和转发,然而通过TEE目标实现较为复杂。因为TEE包没有使用conntrack,直接通过ip_local_out发出,很难对其进行必要的NAT处理,可在nat表PREROUTING链通过string匹配唤醒电脑的MAC地址加以分流。

Iptables DNAT实现broadcast与unicast之间相互映射相关推荐

  1. 验证docker容器相当轻量级Linux运行环境,每个容器内有属于自己的文件系统,容器之间相互隔离

    一.docker的三个重要概念 1.镜像:打包项目带上环境,即镜像 Docker镜像是一个特殊的文件系统,除了提供容器运行时所需的程序.库.资源.配置等文件外,还包含了一些为运行时准备的配置参数.镜像 ...

  2. 【初阶】unity3d官方案例_太空射击SpacingShooter 学习笔记 显示分数时,如何让函数之间相互交流...

    [初阶]unity3d官方案例_太空射击SpacingShooter 学习笔记 显示分数时,如何让函数之间相互交流 一.关于 显示分数时,如何让函数之间相互交流 这是一个非常好的逻辑问题 1 思路:主 ...

  3. git之工作区、版本区、远程仓库之间相互操作

    工作区.版本区.远程仓库之间相互操作示意图 工作区: IDE操作源码的⽬录. 版本库 版本库⼜名仓库,英⽂名repository. 这个⽬录⾥⾯的所有⽂件都可以被Git管理起来,每个⽂件的修改.删除, ...

  4. Android中BroadCast与Activity之间的通信

    在看本文之前,假设你对于Android的广播机制不是非常了解.建议先行阅读我转载的一篇博文:图解 Android 广播机制. 因为本案例比較简单,故直接在此贴出代码,不做过多的阐述. 先上效果截图: ...

  5. 前台为html后台是asp在vs2012中建立什么,Asp.net中后台*.cs与前台JS脚本之间相互调用的几点心得...

    Asp.net中后台*.cs与前台JS脚本之间相互调用的几点心得 < type="text/javascript"> < type="text/java ...

  6. qt如何把父窗口的变量传给子窗口_父窗口和iframe子窗口之间相互传递参数和调用函数或方法...

    1.父窗口向子窗口传递参数: 可以在url中添加参数:2.html?a=1&b=2&c=3 然后在子页面上可用js解析,提供一个函数: function getQueryStr(sAr ...

  7. maven学习笔记第一节一-maven install 模块之间相互引用

    为什么80%的码农都做不了架构师?>>>    我们再做项目的时候,有很多模块是可以重复使用的,maven提供了很好的解决模块之间相互引用的方法,具体流程如下: 1.建立共用模块 2 ...

  8. java 多个项目间事物_Java-web-多个独立项目之间相互调用实践

    本篇文章只涉及到应用层面,没有涉及到什么底层原理之类的,我目前的实力还没有达到那个级别.如果是大神级别的人看到这篇文章,请跳过. 项目框架也已经是搭建好了的,springboot版本为1.5,数据库操 ...

  9. Spring Cloud之微服务之间相互调用、如何让一个微服务调用另外一个微服务

    在使用微服务架构中,可能遇到一些业务情况会涉及服务之间相互调用,下面通过一个简单的demo给大家演示下,演示的是oms服务需要调用ump服务. 代码如下: 1.oms服务提供者 主要是这个注解: @E ...

最新文章

  1. Python NumPy-快速处理数据
  2. python外卷(12)-sort(),sorted(),ord(),chr()
  3. 算法设计中的基础常用代码
  4. C++ 引用计数技术简介(1)
  5. [Python] 绘制Python代码的函数调用关系:graphviz+pycallgraph
  6. P40Pro鸿蒙OS刷机包,华为P40Pro+刷机包(官方系统最新固件下载10.1.0.145)
  7. elasticsearch整体结构示意图
  8. mac安装pillow
  9. Cpp 语法基础总结
  10. 2022-2028全球环氧水泥地坪漆行业调研及趋势分析报告
  11. 深入理解Flash的沙箱 – Application Domains
  12. 【第一期】大话计算机网络(猫、路由器、wifi)
  13. 【数据结构与算法】之深入解析“滑动谜题”的求解思路与算法示例
  14. 变分推断 python_变分推断(Variational Inference)
  15. CSS中的代表的什么
  16. python自动识别简单图片中的文字
  17. PHP数据库操作类ADODB 详解
  18. 智慧物流车联网远程管理终端设备横向评估与优劣势对比
  19. RTSP 流媒体播放地址
  20. 线性代数【16】再从向量空间理解行列式和重要的右手原则

热门文章

  1. SAP-FI-查看供应商,客户,总账科目记账明细
  2. 补码加法器中低位进位信息是什么?
  3. css中“~”(波浪号)、“,”(逗号)、 “ + ”(加号)和 “ ”(大于号)是什么意思?
  4. 怎么把pdf转为html?PDF转HTML转换器推荐
  5. Using the URLconf defined in test1.urls, Django tried these URL patterns, in this order: ^admin/解决
  6. Hexo界面美化_实用插件配置
  7. 代码diff服务改进方案
  8. 微信公众号最佳实践 ( 9.1)会员卡
  9. 医院PACS系统工作原理
  10. Jzoj4745 看电影