WOL 唤醒主机

家里有个小主机,由于晚上没有待机的需要,就在系统中设置了定时关机以及在BIOS中开启了通电开机,然后配合小米智能插座每天早上定时通电使小主机工作。

alt text

但后面发现小主机每天的耗电量过于稳定(1天耗电0.1~0.2度),就没必要给他加上智能插座检测用电量,于是就考虑了用WOL唤醒主机。

1. WOL 介绍

WOL 全称 Wake On Lan,即唤醒网络,是网络唤醒技术,通过发送一个称为魔法数据包(Magic Packet)的广播帧,来唤醒处于关机状态下且支持WOL的计算机。

使用 Wireshark 抓包,得到的 WOL 数据包结构如下:

alt text

可以看到,WOL 默认工作在数据链路层,目标MAC地址为广播地址,由于未工作在网络层,因此不使用IP地址通信。有效载荷中包含了需要开机的计算机的MAC地址(00:50:56:c0:00:08)。

目标主机在关机状态下,处于极低功耗模式下的网卡收到WOL广播帧后,会对比有效载荷中的MAC地址,如果匹配自身的MAC地址,就会唤醒主板供电以实现开机。因此,需要局域网唤醒的计算机的网卡以及主板都需要支持WOL。

注意:WOL 只支持物理连接的网卡唤醒,无线网卡唤醒属于WoWLAN,并不在本文的讨论范围中!

2. 被唤醒端配置

2.1 BIOS 配置

不同品牌主板的 BIOS/UEFI 进入方法以及配置方法大有不同,建议自行百度。
这里以我的 GMK 小主机的 BIOS 设置为例, 开机时连续按 ESC 键进入 BIOS 设置,进入后找到 chipset 菜单,将其中的 Wake on LAN 开启即可:

alt text

2.2 网卡配置

2.2.1 Linux

通常如果网卡支持WOL,Linux 内核会自动开启。比如我使用的 Ubuntu 22.04 默认就是开启网卡唤醒功能的,因此不需要额外配置。

如果需要查看网卡是否支持WOL,可以使用以下命令:

1
2
3
sudo apt install ethtool  # 安装 ethtool
sudo ethtool [网卡名称] # 查看网卡支持的功能
sudo ethtool -s [网卡名称] wol g # 开启网卡唤醒功能

alt text

alt text

2.2.3 Windows

WIN + R 打开运行窗口,输入 `ncpa.cpl` 进入网络适配器管理界面,找到正在使用的物理网卡,右键选择属性,在属性界面找到"配置"选项,在高级菜单中找到"唤醒幻数据包"(经典微软式翻译),将其启用即可:

alt text

然后再到”电源管理”菜单中勾选2、3选项即可:

alt text

注意:如果”电源管理”菜单不存在,则需要在管理员终端下执行 reg add HKLM\System\CurrentControlSet\Control\Power /v PlatformAoAcOverride /t REG_DWORD /d 0 /f 命令关闭新式待机,重启电脑后即可恢复”电源管理”菜单。要恢复新式待机,执行 reg delete "HKLM\System\CurrentControlSet\Control\Power" /v PlatformAoAcOverride /f 命令并重启即可。

如果网卡不支持WOL,则在”高级”菜单中不会显示”唤醒幻数据包”选项:

alt text

3. 唤醒端配置

唤醒端只要能用软件发送 WOL 广播帧即可,因此对硬件没有要求。下面演示 OpenWrt、Android 系统上发送 WOL 广播帧的方法:

3.1 OpenWrt

在 OpenWrt 的管理页或者命令行中安装 luci-i18n-wol-zh-cn 或 luci-i18n-timewol-zh-cn 即可(一个是手动唤醒插件,一个是定时唤醒插件):

1
2
3
opkg update  # 更新软件包列表
opkg install luci-i18n-wol-zh-cn # 手动唤醒插件
opkg install luci-i18n-timewol-zh-cn # 定时唤醒插件

alt text

手动唤醒插件界面如下:

alt text

选择好要唤醒的计算机的 MAC 地址,点击”唤醒主机”按钮即可发送唤醒计算机。如果要唤醒的计算机开启了随机 MAC 地址功能,则建议勾选 “发送到广播地址” 选项再唤醒。

定时唤醒插件界面如下:

alt text

添加需要唤醒主机的 MAC 地址,设定唤醒时间并保存即可。日、月、周留空表示不限制日期。

3.2 Android

Google Play 商店下载安装 Wake On Lan:https://play.google.com/store/apps/details?id=co.uk.mrwebb.wakeonlan&hl=zh_cn

alt text

访问不了 Google 的也可以通过蓝奏云下载安装:https://lololowe.lanzoui.com/iolxD28tauqb

安装完成后打开APP,右下角加号手动添加需要唤醒的计算机的 MAC 地址,之后点击列表中的目标主机即可唤醒:

alt text

3.3 公网唤醒

出门在外的时候,如果目标主机没有开机并且 OpenWrt 上的定时开机任务距离开机时间还差很久,那么我建议使用 SSH 连接到 OpenWrt,然后利用SSH 隧道来访问OPenWrt 的管理页(不建议直接将管理页暴露在公网环境),然后通过手动唤醒插件来唤醒目标主机。当然了,由于 OpenWrt 是基于 Linux 的开源操作系统,因此也可以在 OpenWrt 上安装 Python,然后通过代码发送 WOL 广播帧唤醒目标主机:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
import socket


def wol(luna_mac_address: bytes) -> None:
"""Send a Wake-on-LAN magic packet to the specified MAC address."""
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
s.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST, 1)
magic = b"\xff" * 6 + luna_mac_address * 16
s.sendto(magic, ("<broadcast>", 7))


if __name__ == "__main__":
# Pass to wol the MAC address of the Ethernet port of the appliance to wake up
wol(b"\x00\x15\xB2\xAA\x5B\x00")

或者使用 Etherwake 工具在命令终端唤醒目标:https://openwrt.org/docs/guide-user/services/w_o_l/etherwake

4. 查看唤醒时间

Linux 系统上执行 who -b 命令即可看到开机时的时间:

alt text

Windows 系统上执行 systeminfo | findstr "系统启动时间" 命令查看到开机时的时间:

alt text

5. 参考

https://en.wikipedia.org/wiki/Wake-on-LAN
https://www.howtogeek.com/70374/how-to-geek-explains-what-is-wake-on-lan-and-how-do-i-enable-it/#what-is-wake-on-lan
https://learn.microsoft.com/zh-cn/troubleshoot/windows-client/setup-upgrade-and-drivers/wake-on-lan-feature#windows-10
https://winaero.com/how-to-disable-modern-standby-in-windows-11-and-windows-10/