web-dev-qa-db-ja.com

過度のシステムクロックドリフト? (1時間あたり2+分)

新しいシステムで17.10の適度に新しいインストールを実行し(完全にパッチ適用され、仮想化されていない)、/proc/statbtimeエントリにリストされているブート時間が変化し続けることに気付きました。これにより、特定のプロセスが開始された実時間を計算するためにこの情報を使用するスクリプトが破損しました。

デバッグを行った結果、btimenow() - uptimeとして計算され、btimeドリフトは、システムクロックがアップタイムクロックとは異なるレートでインクリメントしていたためです。

これは、systemd-timesyncd.service(つまり、ntpdの置き換え)によってシステムクロックに適用された何らかのクロックスルーによるものと想定したため、テストとしてtimesyncdを無効にして再起動しました。案の定、今ではアップタ​​イムカウンターとシステムクロックは同じレートでステップします。 (また、 adjtimex をインストールして、カーネルパラメーターをチェックし、クロックスルーが残っていないことを確認します。frequencyバイアスが適用されておらず、tick値は10000である必要があります。)

ただし、timesyncdをオンにしないと、システムクロックが非常に乱れていることが明らかです。クロックは135分間で約5分間失われました(〜-37000 ppm)。これは、システムクロックのドリフトを手動で推定するために約20分間でadjtimex -l -wを使用して得たものに似ています(〜 -40000 ppm)。 (実際、ストップウォッチを使用して確認するだけで、/proc/uptimeも間違ったレートで増加していることがわかりました;〜-41000 ppm。それは一貫しています。)

CMOSクロックも少しオフです(135分間で30秒増加しました)が、これはシステムクロックに影響を与えないことです。起動時に。ブート時にシステムクロックレートを変更する/etc/adjtimeファイルはありません。とにかく、上記のadjtimexは、クロックティックフュージョンがなかったことを報告します。そのため、CMOSクロックがシステムクロックで発生する問題をどのように引き起こしているのか想像できません。

それでも、 一部のレポート がシステムクロックの問題を奇跡的に修正できることを示唆しているように、CMOSバッテリーを変更します。 (これが発生する可能性のある明白なメカニズムはありませんが。)

しかし、システムクロックが非常に間違っている理由について、他に説明はありますか?また、システムタイマーが非常に大量にオフになっているという事実に対する解決策はありますか?明らかにtimesyncdを実行するだけでは問題は解決しません。これは、生成される過剰なクロックスルーに問題があるためです(上記を参照)。

adjtimexを使用してカーネルパラメーターを直接変更できます(少なくともアップタイムとシステムクロックカウンターの同期を維持する必要があります)が、実際には+-500 ppmの範囲のクロックエラーに対処するためのものです。私が見ているのは3桁大きいです、そしてそれはいくつかのより重要な問題を示しているのだろうかと思います。

記録として、非常によく似たマシンに17.10をインストールしても、この問題は発生しません。

更新:CMOSバッテリーの変更は何もしなかった(疑わしい)。問題の最終的な解決については、以下を参照してください。

2
zachrahan

TSCクロックソースに問題があることがわかりました。短期的には、クロックソースを 'hpet'に変更する(一時的にecho hpet > /sys/devices/system/clocksource/clocksource0/current_clocksourceで、またはclocksource=hpet/etc/default/grubのカーネルブートパラメーターに追加することで永続的に)この問題を回避できます。

さらに広く言えば、この問題は、Skylake XデスクトップCPUに関するLinuxカーネルのTSC処理のバグによるものです。これは 今後のカーネルリリース で修正する必要があります。

Update:上記のパッチからの1行の修正で現在のカーネルを再構築すると、実際には正しいTSCの動作が復元されます。

3
zachrahan