AMD Ryzen 向け一部マザーボードでは UEFI から C6 ステートを disabled にできない件


これまで何度か AMD Ryzen 7 が不安定でなんとか安定させようと頑張ってきたが、カーネル 4.13 以降でもようやく安定してきたので書いておく。


C6 ステート

特に原因は判明していないが、RMA した上で

  • CONFIG_RCU_NOCB_CPU=y でカーネルを再コンパイルした上で、カーネルオプションに rcu_nocbs=0-15 などとしてすべての論理 CPU を指定する
  • UEFI / BIOS の設定で C6 ステートを disabled にする

と安定するという話が流れていた。

前回までにこれらを試してみたものの、やはりうちの Ryzen 7 1700 では

  • 高負荷をかけると rcu_sched detected stalls on CPUs/tasks で論理 CPU がストールする
  • 高負荷をかけなくてもやはり rcu_sched detected stalls on CPUs/tasks で論理 CPU がストールする

という問題があった。

実は UEFI から C6 ステートは切れないのではないかという疑惑

なんら解決策がなく、そろそろ Intel に乗り換えようかと思っていたところ、Kernel.org Bugzilla の該当チケット "196683 – Random Soft Lockup on new Ryzen build – Kernel.org Bugzilla" にこんな記述があった。

Comment 162 eric.c.morgan 2017-12-20 19:02:20 UTC
C6 disabled via bios, I’ll verify with that python script I posted earlier.

Mem is stock, memtested for 24 hours too.

Comment 163 eric.c.morgan 2017-12-20 19:14:20 UTC
Crap, the .py said C6 was still enabled! I disabled via said script. Fingers crossed.

これは結構大きい。UEFI では C6 ステートを disabled にしているのに C6 ステートが無効化されず、それが引き金になっている可能性がゼロではないということになる。

噂のスクリプトで確認してみた

そこで、自分の環境でも https://github.com/r4m0n/ZenStates-Linux から Python スクリプトを持ってきて試してみた。

まず、UEFI 側の設定はこのように C6 disabled になっていることを確認する。

次にスクリプトを clone する。

git clone https://github.com/r4m0n/ZenStates-Linux.git

そして、スクリプトを実行して C6 ステートがどうなっているか確認してみる。

$ cd ZenStates-Linux/
$ sudo python zenstates.py -l
P0 - Enabled - FID = 78 - DID = 8 - VID = 3A - Ratio = 30.00 - vCore = 1.18750
P1 - Enabled - FID = 87 - DID = A - VID = 50 - Ratio = 27.00 - vCore = 1.05000
P2 - Enabled - FID = 7C - DID = 10 - VID = 6C - Ratio = 15.50 - vCore = 0.87500
P3 - Disabled
P4 - Disabled
P5 - Disabled
P6 - Disabled
P7 - Disabled
C6 State - Package - Enabled
C6 State - Core - Enabled

うちの環境でも UEFI では無効化しているはずなのに C6 ステートが有効になっていた。

C6 ステートを改めて無効化する

C6 ステートの無効化はこのスクリプトで簡単にできる。

$ sudo python zenstates.py --c6-disable
Disabling C6 state

念のため、スクリプトで確認する。

$ sudo python zenstates.py -l
P0 - Enabled - FID = 78 - DID = 8 - VID = 3A - Ratio = 30.00 - vCore = 1.18750
P1 - Enabled - FID = 87 - DID = A - VID = 50 - Ratio = 27.00 - vCore = 1.05000
P2 - Enabled - FID = 7C - DID = 10 - VID = 6C - Ratio = 15.50 - vCore = 0.87500
P3 - Disabled
P4 - Disabled
P5 - Disabled
P6 - Disabled
P7 - Disabled
C6 State - Package - Disabled
C6 State - Core - Disabled

C6 ステートが無効化されているのをスクリプトでも確認できた。

実際、この状況で 1 週間近く実運用しているが、今のところ CPU のストールは全く発生していないし、Ryzen 起因と考えられる Segmentation Fault も起きていない。

ただし、再起動のタイミングで UEFI の設定に書き戻されるため、起動時に再度このスクリプトを実行する必要がある。うちの環境は OpenRC な Gentoo Linux なので、/etc/local.d/disable_c6.start というファイルでスクリプトを起動するように書いておいた。


今年後半は本当に Ryzen 7 に振り回された半年になった。まだ 1 週間しか経っていないために本当に安定したか断言できないので、しばらく様子見していきたいと思う。

なお、このブログはこれまで記事で書いてきた AMD Ryzen 7 1700 上の KVM でホストしている。

追記

2018 年 2 月 5 日追記

Asrock AB350M Pro4 の UEFI を最新の 4.50 にアップデートしてみたが、指示通りまず 3.60 に上げてから 4.50 に上げたにもかかわらず、POST しなくなってしまった。この blog も Asrock AB350M Pro4 でホストしていて緊急なので新規にマザーボードを買って交換することにしたが、同じ轍を踏みたくないので BIOSTAR 製の X370GT3 を買ってみた。

早速 X370GT3 に換装して試してみたところ、zenstates.py で強制的に変更しなくても UEFI 側の設定だけで C6 ステートを無効化できていた。

$ sudo python zenstates.py -l
P0 - Enabled - FID = 78 - DID = 8 - VID = 3A - Ratio = 30.00 - vCore = 1.18750
P1 - Enabled - FID = 87 - DID = A - VID = 50 - Ratio = 27.00 - vCore = 1.05000
P2 - Enabled - FID = 7C - DID = 10 - VID = 6C - Ratio = 15.50 - vCore = 0.87500
P3 - Disabled
P4 - Disabled
P5 - Disabled
P6 - Disabled
P7 - Disabled
C6 State - Package - Disabled
C6 State - Core - Disabled

なので、UEFI の設定で C6 ステートを本当に無効化できるかは CPU 依存ではなく UEFI の実装依存かと思われる。