安然小屋 安然之家

安然小屋 安然之家

解锁PVE新玩法,按电源按钮召唤win11虚拟机 https://www.bilibili.com/opus/942081706108649479
2026-01-14

给家人像使用普通电脑一样使用直通的虚拟win11

为了减少功耗,虚拟的win11并没有一直开机,也没有设定随着PVE开机启动。于是就产生了这样的画面: 老婆大人要用电脑,习惯性的按电源按键,于是,PVE就自动关机了。然后再打开,还是没有画面,就叫我开机。我有时候不在家里,虽然可以通过远程在手机上开启虚拟机,还是不怎么方便,也不及时。

老婆大人问道:你不能弄个正常点的电脑吗?或者像小爱同学一样,喊一下就开机?我竟无言以对.....

也是,科技以人为本,我要研究一下,让不太懂电脑的人一样正常使用虚拟的win11。

经过一番探索,花了1个小时实现了功能: 按下电源按键,直接打开win11虚拟机,而不是关闭PVE宿主机。

各位看官跟着我来做一下,一点也不难,也能实现硬件级开关虚拟机

修改思路

众所周知,操作系统比如win11,按下电源按钮,是可以触发关机事件的,执行关机过程,和手动点击关机是一样的。电源按键,连接在主板的插线排针上,有两根线。当按下按钮时候,就是短接了这两根线,给出了信号,主板给信号到ATX电源通电开机。装机有时候用螺丝刀短接开机排针也是一样的。在开机状态下,按下电源按钮,就给出了信号并被操作系统检测到,os就会执行关机指令。

在win11里面电源按钮,睡眠按钮,合上盖子都是可以定义有限的功能的,那么,Linux是否也可以呢?我们就从此入手。

按电源按钮开关机,这条链路就涉及到几样东西: BIOS,ATX电源,操作按系统。ATX电源没有修改的地方。能动的就只有BIOS和操作系统。

现代电源都支持ACPI,在BIOS设定后,可以由操作系统直接发出指令操作。那么,我们应该可以在BIOS启用ACPI,然后修改操作系统的逻辑,使按下电源按键的功能可以自定义,应该就能达到目的。

Let's go

1-BIOS设定,开启ACPI

这块没法截图,每块主板的设定也不一样,总之一个原则:电源,节能里面有ACPI的尽量都打开,设定为由OS自动管控。我的主板是铭瑄MS-C Farm B660i,记得有好几个地方设定,我是提前都打开了。

2-屏蔽默认电源按钮事件

修改logind.conf

使用PVEweb界面或任意ssh工具连上pve,修改logind.conf。这一步修改完,你按电源按键,就不会自动关闭PVE宿主机了。 注意,我只在PVE8.2下实践,其他版本应该类似。这一步如果没有这个文件,那就直接跳转到下一步。

#先备份

cp /etc/systemd/logind.conf  /etc/systemd/logind.conf.bak

#编辑

nano /etc/systemd/logind.conf

文件内容如下,注意前面没有#的行是修改的结果,就是设置 HandlePowerKey=ignorePowerKeyIgnoreInhibited=no。 这两个值原本都是off。 看了这么多设置项,你们应该有所猜测,如果有reset按钮,或者是笔记本合上盖子,应该也能屏蔽掉把。

[Login]

#NAutoVTs=6

#ReserveVT=6

#KillUserProcesses=no

#KillOnlyUsers=

#KillExcludeUsers=root

#InhibitDelayMaxSec=5

#UserStopDelaySec=10

HandlePowerKey=ignore


#HandleSuspendKey=suspend

#HandleHibernateKey=hibernate

#HandleLidSwitch=ignore

#HandleLidSwitch=suspend

#HandleLidSwitchExternalPower=suspend

#HandleLidSwitchDocked=ignore

#HandleRebootKey=reboot

PowerKeyIgnoreInhibited=no

#SuspendKeyIgnoreInhibited=no

#HibernateKeyIgnoreInhibited=no

#LidSwitchIgnoreInhibited=yes

#RebootKeyIgnoreInhibited=no

#HoldoffTimeoutSec=30s

#IdleAction=ignore

#IdleActionSec=30min

#RuntimeDirectorySize=10%

#RuntimeDirectoryInodes=400k

#RemoveIPC=yes

#InhibitorsMax=8192

#SessionsMax=8192

重启服务和系统

systemctl restart systemd-logind

reboot

3-监听获取电源按钮事件ID

安装ACPI支持

apt install acpid acpi-support

如果报依赖冲突,没安装成功,请安装aptitude解决

监听电源按钮事件

执行acpi_listen,然后按下电源按钮

acpi_listen

#按下电源按钮,不用担心会关闭电脑。不出意外,会有下面的反馈

root@pve:~# acpi_listen

button/power PBTN 00000080 00000000

button/power LNXPWRBN:00 00000080 00000032



这里00000080就是id

4-拦截并自定义电源按钮事件

编辑ACPI事件文件

编辑ACPI事件

nano /etc/acpi/events/powerbtn  

黏贴一下内容: 根据上一步监听的内容来修改

event=button/power PBTN 00000080 00000000

action=/etc/acpi/power_btn.sh

编写关机按键触发的脚本,即上一步的的power_btn.sh

nano /etc/acpi/power_btn.sh

脚本内容如下,可以按需修改,这里的102就是虚拟机的id

#!/bin/bash

output=$(qm status 102)

if [[ $output == *"stopped"* ]]; then

qm start 102

else

qm status  102

fi

如果要按电源按钮还可以关机,则脚本需要修改成下面的样子。

qm shutdown 这部分,如果不生效,可以改成 qm stop

#!/bin/bash


output=$(qm status 102)

if [[ $output == *"running"* ]]; then

qm shutdown 102

else

qm start  102

fi

赋予执行权限

chmod +x /etc/acpi/power_btn.sh

重启acpi服务

systemctl restart acpid

5-虚拟机安装 agent

对按下按钮开机来说,这一步不是必须的。要电源按钮关机,还需要再虚拟机里面安装QEMU-guset-agent。 对于Windows来说,在https:/ / Index of

/groups/virt/virtio-win/direct-downloads,可以下载,在iso里面可以找到agent。windows就能响应宿主机PVE发出的关机命令了。

安装后,在虚拟机的选项界面,就可以看到启用了agent



使用效果

很简单,像正常电脑一样,按机箱上的电源按键,按一下,虚拟机就启动了。老婆大人使用毫无门槛。

还有附加效果:也不怕小孩子乱按了。

至于让小爱同学开启虚拟机,哎,有点难。开启物理机倒是有案例,开启虚拟机...... 缓缓吧