IntuneでWindows デバイスにNTPクライアントの設定を配信する
WindowsのNTPクライアント
IntuneでWindowsにNTPクライアントの設定を配信しようとしたのですが、思ったよりも大変だったのでやったことを残しておきます。
WindowsのNTPサーバーとの時刻同期はW32Time(Windows Time)というサービスが行います。
Intuneの構成プロファイル内の設定カタログに項目があるのですが、この設定だけでは時刻同期が行われないケースがあるようでした。
最終的にW32TimeのNTPクライアントとしての設定と、W32Timeサービスの起動をそれぞれ行いました。
NTP Clientの設定
- ポーリング間隔に
SpecialPollIntervalを使用している - NTPサーバーとNTPクライアントの時刻のオフセットが
LargePhaseOffsetよりも大きくなる
という条件の場合に、NTPクライアントが時刻を修正できなくなるという現象があるそうです。
ポーリング間隔のタイプはNTPサーバの後ろに付けるフラグで決まります。
デフォルト値は0x9で、これは0x1と0x8という2つのフラグが有効になっている状態です。
フラグの意味は以下の通りです。
| 値 | 動作 |
|---|---|
| 0x1 | Symmetric Activeモード。一定間隔(SpecialPollInterval)で相互同期を行う。 |
| 0x8 | Clientモード。RFC1305に準拠した間隔で同期を行う。 |
| 0x9 | Clientモード.一定間隔(SpecialPollInterval)で同期を行う。 |
このフラグを0x8に設定することで、時刻が同期できなくなる不具合を回避できるようです。
参考: Windowsネットワーク時刻同期の基礎とノウハウ(改訂版) 第2回 Active Directoryおよびワークグループ環境での時刻同期 | @IT itmedia.co.jp
W32Timeの起動
デフォルトでW32Timeの起動タイミングは次の3つが設定されており、いずれかの条件に一致すると起動するようです。
- 手動
- トリガー開始
- タスクスケジューラによる起動
トリガー条件はドメインの参加になっており、ドメインに参加しないPCの場合は機能しません。
タスクスケジューラによる起動も上手く行っていないケースがあるみたいでしたが、詳しい条件などはよくわかりませんでした。
これについては以下の3つをスクリプトで行う事にしました。
- W32Timeのスタートアップ設定を自動開始にする
- W32Timeが開始していなければ開始する
- W32Timeのトリガーを変更する
先に挙げた記事によるとトリガーは削除してしまっても問題ないようですが、Intuneから配信する際の検出ルールとして使いたかったので設定しています。
つまづきポイントとしては、W32timeのスタートアップ設定が無効になっているとW32timeを起動するコマンドが失敗します。
そのため、先にスタートアップ設定を確認(必要であれば変更)して、その後にW32timeの状態を確認(必要であれば起動)しています。
$ServiceStatus = Get-Service -Name W32time
if ( ( $ServiceStatus | ForEach-Object StartType ) -ne "Automatic" ) {
Set-Service -Name W32Time -startupType Automatic
}
if ( ( $ServiceStatus | ForEach-Object Status ) -ne "Running" ) {
Start-Service -Name W32Time
}
C:\WINDOWS\system32\sc.exe triggerinfo w32time start/networkon stop/networkoff
ローカルで実行する場合は管理者権限が必要です。
PowerShellはコマンドの結果を扱うのが大変簡単なのがとても良かったです。
Intuneで設定を配信する
先の2つの設定をそれぞれ配信します。
構成プロファイルの配布
Windowsデバイスの構成プロファイルを新規作成します。
| 項目 | 内容 |
|---|---|
| プラットフォーム | Windows 10 以降 |
| プロファイルの種類 | 設定カタログ |
設定の追加から
管理用テンプレート > システム > Windows タイム サービス > タイム プロバイダー
を開き、
Enable Windows NTP ClientConfigure Windows NTP Client
を選択します。
どちらもEnableにし、Configure Windows NTP Clientの設定を
| 項目 | 内容 |
|---|---|
| NtpServer | ntp.nict.jp,0x8 |
| Type(Device) | NTP |
とします。それ以外はデフォルト値にしました。
NTPサーバはどこでも良いのですが、GUIと設定内容が一致しない事を確認しやすいように変えています。
配信のスコープはデバイスです。
スクリプトの配布
スクリプトとして配信しても良いのですが、今回はWin32 Content Prep Toolを使いintunewin形式に変換して配信しました。
アプリとして配信することで検出ルールを使って適用状況を判断出来るため、クライアントがIntuneに接続したタイミングで検出ルールを満たしていない場合にスクリプトの再実行が可能になります。
powershell.exe -NoProfile -ExecutionPolicy Bypass -File w32timeIgniter.ps1
今回はWin32 Content Prep Toolの使い方について特に触れないので、下記ドキュメントや他の方のBlog等をご参照下さい。
状態の検出による再実行が必要なければスクリプトとして配信することもできるので、そのへんはお好みで。
検出ルールは2つ設定しました。
サービスのトリガを検出
初回の実行を想定したルールです。
もともと設定されているトリガは1つだけでしたが、スクリプトによって2つのトリガーが作成されます。
そのため、2つめのトリガーが検出されたらインストールされているとみなします。
| 項目 | 内容 |
|---|---|
| 規則の種類 | レジストリ |
| キーパス | HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\W32Time\TriggerInfo\1 |
| 値の名前 | Action |
| 検出方法 | 値が存在する |
サービスのスタートアップの種類を検出
初回の実行時の他に、ユーザーが誤って時刻同期を無効にしてしまったケースを想定したルールです。
W32Timeサービスのスタートアップの種類が3(手動)もしくは4(無効)の場合を検出します。
GUIで時刻同期をオフにするとこの値が4となり、検出されるとスクリプトが実行されます。
GUIで時刻同期を無効にしたあとにスクリプトが実行されても、GUI上では無効になったままに見えます。
| 項目 | 内容 |
|---|---|
| 規則の種類 | レジストリ |
| キーパス | HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\W32Time |
| 値の名前 | Start |
| 検出方法 | 整数値を比較 |
| 演算子 | より小さい |
| 値 | 3 |
配信のスコープはデバイスにしました。
クライアント側の表示
これらの設定はGUIの表示を変更しないため、設定が配信されたあともGUIではタイムサーバーがtime.windows.comと表示されます。

実際に時刻同期した際の情報は、PowerShellでw32tm /query /statusを実行することで確認できます。

GUIの表示と設定を一致させたい場合はレジストリを配布することで対応出来そうです。
さいごに
Windowsに不慣れなため、レジストリ?サービス??グループポリシー???みたいな状態からのスタートだったので大変学びが多かったです。
NTPクライアントの設定やサービスの起動について個別に触れられている記事はあったのですが、両方をIntuneで配信する内容は見つけられませんでした。
もしかしたら他にもっと良い方法があるのかもしれないので、ご存知の方はこっそり教えて下さい。
Discussion