首先来说,如果有可能的话尽可能查看发行版本的支持日期与 CPU 的发布日期尽可能的匹配。这里由于新的 CPU 都有着各种各样的节能技术,这会导致 OS 内核的 API 与 BIOS 不匹配,或者说 OS 内核就压根不支持这个新的特性。这就会导致特别多的问题出现,目前比较稳妥的方式是在对能耗要求不高的设备上,关闭所有的节能相关的选项会处理掉特别多的麻烦。
下面说说一些常见的方法怎么来处理,这里要介绍一个比较熟悉又陌生的内容——ACPI。 ACPI 在 LINUX 上的实现描述文章1 和 ACPI 在 LINUX 上的实现描述文章2 这两篇文章比较清晰地描述了 ACPI 在 LINUX 上的实现。ACPI 就是个高级的电源接口,为的就是保证 OS 与硬件之间的兼容性而设计的,这里面有很多的基础接口。所以围绕着上面的不能关机的问题,最后大概率的还是会落到 ACPI 上面。下面我来说说思路,首先应该去 DEBUG 关机的过程,从过程中去看到底是卡在哪。
DEBUG 的过程也比较简单,目前的 16.04 LTS 的系统使用的 systemd 来记录日志。
-
systemd 超时时间设置:systemd 默认是 90S,可以先改成 10S 看看效果,是不是因为超时卡住了。
-
关闭 swap,关闭 USB 3.0 的 legacy 模式:
sudo swapoff -a
-
尝试安装 TLP 实验一下。
-
看日志
journalctl -b -1 -e
,对比正常的日志与异常的日志,可以看出卡在哪。一般正常的日志应该是以journal stopped
结尾的。以这个为依据,用同样的 OS 来对比。先改一下配置文件记录日志:vim /etc/systemd/journald.conf [Journal] Storage=persistent sudo systemctl restart systemd-journald
然后改一下 GRUB,改完以后
sudo update-grub
生效。之后先重启一遍让这个生效。vim /etc/default/grub GRUB_CMDLINE_LINUX_DEFAULT="quiet splash" to GRUB_CMDLINE_LINUX_DEFAULT=""
这个配置可以打印出更多的信息,更容易判断问题。
systemd[1]: Reached target Shutdown. systemd[1]: Reached target Final Step. systemd[1]: systemd-reboot.service: Succeeded. systemd[1]: Finished Reboot. systemd[1]: Reached target Reboot. systemd[1]: Shutting down. systemd-shutdown[1]: Syncing filesystems and block devices. systemd-shutdown[1]: Sending SIGTERM to remaining processes... systemd-journald[262]: Journal stopped
下面是几种修改方法,能应对 90% 以上的问题,都是改 GRUB 的:
GRUB_CMDLINE_LINUX_DEFAULT="quiet splash"
to
GRUB_CMDLINE_LINUX_DEFAULT="quiet splash" acpi=force apm=power_off
sudo gedit /etc/modules
apm power_off=1
GRUB_CMDLINE_LINUX_DEFAULT="quite splash"
to
GRUB_CMDLINE_LINUX_DEFAULT="pci=nocrs acpi=force noefi"
GRUB_CMDLINE_LINUX_DEFAULT="quite splash"
to
GRUB_CMDLINE_LINUX_DEFAULT="intel_idle.max_cstate=1"
GRUB_CMDLINE_LINUX_DEFAULT="quite splash"
to
GRUB_CMDLINE_LINUX_DEFAULT="quiet splash acpi_rev_override=1"
GRUB_CMDLINE_LINUX_DEFAULT="quiet splash"To:GRUB_CMDLINE_LINUX_DEFAULT="quiet splash reboot=warm,cold,bios,smp,triple,kbd,acpi,efi,pci,force"
以上是针对关机问题的一些调试和解决方法,希望对你有所帮助。