ITよろづや

ITから生活の参考になる情報を備忘録代わりに残していきます

WindowsServer2012R2、w32tmでのslewモード対策、設定方法

以前、Windows Serverのうるう秒対策について書かせてもらいましたが、Windows製品は基本的にうるう秒に影響を受けないのですが、サーバー上で稼働するアプリケーション、ミドルウェア、ソフトウェアによっては、うるう秒の影響を受けることがあります。


そこで、今回は、Windows Serverでのslewモードについて言及したいと思います。これが、Linuxと違ってかなりややこしいです。もっとシンプルにしてもらいたいのですが、簡単に説明できないくらいややこしいのです。


ということで、自分への情報整理も含めてslewモード対応についてまとめたいと思います。まず、マイクロソフトの公開されている情報です。

Windows Time サービスにおける時刻同期の仕組み
https://support.microsoft.com/ja-jp/help/2722681


こちら、対象がWindows Server 2003とありますが、2012R2でも同じ考え方が適用されるようです。


時刻修正についてですが、Windows Time サービスを使用し、NTP サーバと時刻同期を行う際は、以下のいずれかの方法で同期をしますとあります。

 

(a) 徐々に時刻を合わせる (Slew モード)
SetSystemTimeAdjustment APIをコールする事で、ターゲット時刻をローカル時刻に、徐々に時刻同期を行います。このモードによる時刻同期が実施される場合には、RTC への更新は行われません。

(b) 即座に時刻を合わせる (Step モード)
SetSystemTime API をコールすることで、即時にターゲット時刻をローカル時刻に設定します。この場合、RTC への更新も同時に行なわれます。
これですが、うるう秒対策とするなら、aのslewモードを設定したいということになります。
 
続いて、Widowsの場合は、以下 2 つの条件を満している場合、徐々に時刻を合わせる Slew モードになります。ここ【重要】です。

 

条件 1. NTP クライアントと NTP サーバーの時刻の差が MaxAllowedPhaseOffset で設定されている時間より小さい
条件 2. AbsoluteValueOfCurrentTimeOffset/PhaseCorrectRate/UpdateInterval < SystemClockRate/2 の不等式が満たされる


AbsoluateValueOfCurrentTimeOffset :
NTP クライアントが NTP サーバーに対して時刻同期要求を実施した際の NTP クライアントと NTP サーバーの時刻差のことです。

PhaseCorrectRate /  UpdateInterval :
W32Time のレジストリで設定し、Slew モードにおける時刻同期設定間隔を決定するために使用されます。大きく設定した場合、NTP クライアントが NTP サーバーと同期するまでの間隔が長くなり、レジストリの値が小さい場合、早い間隔で同期いたします。

System Clock Rate :
システムのクロックレートのことです。LastClockRate (W32Time のレジストリ値) とほぼ合致します。シングル プロセッサなら約 10ms 、マルチ プロセッサなら約 15ms となります。
 
ちなみに、、Windows Time サービスの精度についてはこんな言及があります。
 
Windows Time サービスは、Kerberos 認証が正常に動作する範囲で NTP Client と NTP Server の時刻を同期することを主な目的とした、ゆるやかな時刻同期を提供する設計となっています。このため、Windows Time サービスにおいては、常に時刻差異が僅少である (1 秒単位の誤差など) 状態を保証することはできません。

 

 
 
Slew モードの時刻の合わせ方
データベースのトランザクション管理などに影響を与えないために、NTP サーバーと NTP クライアントの時刻差を徐々に縮めることによって、時刻が戻ることを防ぎながら時刻を修正します。具体的には、NTP クライアントの方が時刻が遅れている場合には、例として、実際には 0.9 秒しか経っていないにもかかわらず、1 秒時刻を進めることにより、NTP サーバーと NTP クライアントの時刻差を徐々に縮めます。逆に、NTP クライアントの方が時刻が進んでいる場合には、例として、実際には 1.1 秒経っているにもかかわらず、1 秒だけ時刻を進めることにより、NTP サーバーと NTP クライアントの時刻差を徐々に縮めます。



そもそも、精度が高くないので、社内のNTPサーバは、LinuxCentOSを利用するようにしたいですね。ドメイン環境であれば、必然的にドメインコントローラーと同期することになってしまいますが。


さて、話を戻して、slewモードにする設定ですが、一番詳しく、分かりやすく書かれているのがこちらのMSのブログです。

https://social.technet.microsoft.com/Forums/office/ja-JP/f9f3f4ac-150e-463d-90ff-f5c77826ac15/windows-time-12469125401249912473-8211-slew-12514125401248912392-step?forum=Wcsupportja


まずは、slewモードとstepモードについて。

 
Step モードの時刻の合わせ方
Slew モードのように徐々に時間差を縮めるのではなく、目標の時刻に瞬時に変更します。NTP サーバーよりも NTP クライアントの方が時刻が進んでいる場合、NTP クライアントの時刻は過去に戻ります。

 

うるう秒対策につながるのですが、時間がずれた場合にすぐに調整するのがstepモード、徐々にゆっくりと時間をかけて時間を調整するのがslewモードです。閏秒だと時間調整の為に、上位NTPサーバから時間を調整するための時間を挿入されます。そこで、即座に時間調整されてしまうと色々と過去に問題が起きたので、今ではうるう秒対策として、slewモードを設定する企業が多いです。


そして、Windowsのslewモード対策の難しさの理由は、、、まず、slewモードだけで動作させるという設定がないことです。さらに、ブログにも書かれていますが、Slew モードと Step モードのいずれが使用されるかは、NTP Client と NTP Server の時刻差によって、動的に決定されるという点です。

 
そしてその動的に使用されるのにも、【重要】と書いた条件式ですが、環境によって値が変わってくるのです。これが本当に面倒。

ドメイン コントローラーか、ドメインのメンバー サーバーか、ワークグループ環境か」

この環境の違いによって、上記の条件式で使用される各パラメーターの既定値が異なるため、Slew モードで時刻同期できる 「NTP Server との時刻のずれ」 の値も異なるとあります。
 
 

ドメイン コントローラーの場合】

MaxAllowedPhaseOffset : 300
PhaseCorrectRate : 7
UpdateInterval : 100

 

ドメイン メンバー サーバーの場合】
MaxAllowedPhaseOffset : 300
PhaseCorrectRate : 1
UpdateInterval : 30000

 

【ワークグループの場合】
MaxAllowedPhaseOffset : 1 
PhaseCorrectRate : 1
UpdateInterval : 360000
 

そうなんです、これを計算していく必要があるのです。


まず、条件式1ですが、

ドメインコントローラー、ドメインメンバーの場合は、「MaxAllowedPhaseOffset : 300」が設定されているので、300秒以上時間がずれているとstepモードが動作することになります。これはまぁいいかなと思いますね。


続いて、条件式2ですが、


ドメイン コントローラーの場合】

- マルチ プロセッサーの場合
AbsoluteValueOfCurrentTimeOffset ÷ 7 ÷ 100 < 0.015 ÷ 2
AbsoluteValueOfCurrentTimeOffset < 5.25 秒

 

- シングル プロセッサーの場合
AbsoluteValueOfCurrentTimeOffset ÷ 7 ÷ 100 < 0.010 ÷ 2
AbsoluteValueOfCurrentTimeOffset < 3.5 秒


ドメイン メンバー サーバーの場合】
- マルチ プロセッサーの場合
AbsoluteValueOfCurrentTimeOffset ÷ 1 ÷ 30000 < 0.015 ÷ 2
AbsoluteValueOfCurrentTimeOffset < 225 秒

- シングル プロセッサーの場合
AbsoluteValueOfCurrentTimeOffset ÷ 1 ÷ 30000 < 0.010 ÷ 2
AbsoluteValueOfCurrentTimeOffset < 150 秒


プロセッサー数で変わるところも分かりにくいですが、

ドメイン コントローラーの場合】
条件1:300秒
条件2:5.25秒(マルチプロセッサー)、3.5秒(シングルプロセッサー

ドメイン メンバー サーバーの場合】
条件1:300秒
条件2:225秒(マルチプロセッサー)、150秒(シングルプロセッサー

つまり、シングルプロセッサーの場合は、3.5秒、マルチプロセッサーの場合は、5.25秒という計算になります。ワークグループの場合は、シングルプロセッサーの場合は、225秒、マルチプロセッサーの場合は、150秒という計算になります。理由としては、条件式1が「300秒」なので、それ以下である条件2が採用される為ですね。


問題はワークグループです。条件1がなんと「1秒」です。


【ワークグループの場合】

MaxAllowedPhaseOffset : 1 

PhaseCorrectRate : 1

UpdateInterval : 360000

 

条件 1.
AbsoluteValueOfCurrentTimeOffset < 1 秒

 

条件 2.

- マルチ プロセッサーの場合

AbsoluteValueOfCurrentTimeOffset ÷ 1 ÷ 360000 < 0.015 ÷ 2

AbsoluteValueOfCurrentTimeOffset < 2700 秒

- シングル プロセッサーの場合

AbsoluteValueOfCurrentTimeOffset ÷ 1 ÷ 360000 < 0.010 ÷ 2

AbsoluteValueOfCurrentTimeOffset < 1800 秒



プロセッサー数は環境次第ですが、調整するのは、「MaxAllowedPhaseOffset 」とブログにも紹介されています。条件2が2700秒か1800秒なので、ドメイン環境よりも値が広いのですが、条件1が「1秒」なので、必然的に1秒でstepモードで動作してしまいます。



つまり、ワークグループ環境のWindows Server 2012 R2にて、なるべくslewモードで動作させたい場合は、「MaxAllowedPhaseOffset 」の値を変更してあげることで、なるべくslewモードで動作するようになりますね。


例えば、条件2に合わせるなら、2700か1800に変更すればいいですね。長々と書きましたが、結論「MaxAllowedPhaseOffset 」を調整してくださいになります。


さらに、もっと時間を増やしたいなら、条件2の値を変更することになりますが、さすがに30分以上時間がずれるというのは想定していないと思うので、、、これくらいの幅があれば十分かと思いますね。ちなみに、Windows Server 2016はこのレジストリの値が変わるので、その件については、別途、紹介したいと思います。


まとめ

結論、ここだけ見てもらうでもいいのですが、ワークグループ環境のWindows Server 2012 R2でslewモードで動作させたい場合は、「MaxAllowedPhaseOffset 」の値を「1」から大きい数字に変更しましょう。時間の幅については、推奨値的なものはないので、会社で議論してください。