この記事では、Windowsでの高精度な時刻同期方法としてMeinberg社のNTPソフトウェア(Windows版ntpd)の紹介と導入方法を解説します。
はじめに
※筆者は素人であり、自分なりに調査したものをまとめています。参考程度にしてください。間違い等あればご指摘頂ければ幸いです。
Windowsでの正確な時刻同期の方法はとても限られています。
Windowsでは基本的にはNTP(ネットワーク・タイム・プロトコル)という方法を用います。NTPサーバー(時刻情報を発信しているサーバー)にアクセスすることで時刻同期を行う方法です。
自宅LAN上に独自にサーバーを建てない限り、インターネット上に公開されているNTPサーバーにアクセスすることになります。
NTPの他にGPSを用いた時刻補正の方法もありますが、WindowsでGPSによって直接時刻補正するのは基本的には困難であるようです。
NTPには、サーバーとクライアント間の通信遅延を考慮する機能が備わっています。ですが、通信の往路と復路が同じ遅延であれば正確な補正が可能なのですが、実際はそうでは無いため、正確な補正ができません。このような揺らぎ(誤差)をジッターとも言います。当然、遅延(往復遅延)が大きいほどジッターも大きくなります。
例えば往復遅延が10msであれば、NTPは片道の遅延が5msだと仮定します。しかし誤差は最大で±5msあります(行き10ms帰り0ms、またはその反対が最大で想定される)。
往復遅延が20msであれば、最大誤差は±10msです。
これを解消するため、NTPではサーバーとの通信を何回も行い、その結果によって揺らぎをなるべく取り除こうとします。
ですが、Windowsで使用できるソフトには、このような複数回の通信によって揺らぎを取り除く機能を持ったNTPソフトがほぼありません。
この機能が無いと、単純に一回の通信によって時刻補正を行うため、往復遅延の半分の最大誤差が生まれます。その一回において、たまたま遅延が大きくなった時には、誤差もそれだけ大きくなります(しかし通信環境が良ければ、あまり大きな問題では無いかもしれません)。
それ以外にも、複数のNTPサーバーと通信を行い、最適なサーバーを選択する機能がNTPにはありますが、このような機能があるものはWindows用ソフトではほぼありません。
時刻補正を一気に行うのではなく徐々に行う機能(slewモード)———これは時刻情報を用いているプログラムのエラーを回避するために役立つ―――がNTPにはありますが、Windows Timeサービスではこの機能があります。
Windows Timeサービスや桜時計について
Windows標準の時刻同期サービスであるWindows Timeサービスでは、限定的なNTPを実装しています。
ただし、前述したような機能がどこまで実装されているのか私が調べた限りでは良く分かりませんでした(情報があればコメント頂けると幸いです)。
桜時計もWindowsの時刻同期ソフトとして有名です。Windows用の時刻同期ソフトは多くありますが、私が試した限り、その中では桜時計が使いやすいです。
というのも、桜時計では、一定以上の遅延がある場合は時刻補正しないという設定が可能なためです。通信環境が悪いと揺らぎ(ジッター)が大きく、時々大きな遅延が発生しますが、そのような場合に同期を行わせないようにできます。ですがこれは必要最低限の機能です。多くのソフトはその必要最低限の機能さえありません(ただし通信環境が良い場合はこのような機能が無くてもあまり問題では無いかもしれません)。
ただし桜時計は、私が試した限りでは誤差が10ms弱くらいあるように感じます。
少なくとも10msの遅延がある環境でも、稀に遅延が0msと表示されたり、何度も時刻補正しても10ms弱のオフセットが解消されなかったりする現象が起こるためです。
また、NetTimeというソフトもある程度の機能を備えているようですが、詳細は不明です。
NetTime - Network Time Synchronization Tool
※時刻同期ソフトを立ち上げる際には「管理者として実行」が必要です。
Meinberg NTP
唯一NTPのフル機能を備えたものがMeinberg社の提供するNTPソフトウェアです。これはLinuxのNTPソフト(ntpd)をWindowsに移植したものです。
通信環境が良く、NTPサーバーとの遅延が少ない環境であれば、シンプルな時刻同期ソフトでもそれなりの精度で時刻補正できるかもしれませんが、遅延がある環境や、より正確な時刻同期を行いたいという場合はMeinberg NTPの導入を検討しても良いと思います。
ただし、以下の制限・注意点があります。
・NTPサーバーへのアクセス頻度を64秒に設定する必要があると思われるため、サーバーへの負荷が高くなります。
・PCの内部クロックの時間の進み方(周波数オフセット)が安定しない環境では、正確な時刻同期が難しくなります。
詳しくは後述します。
導入方法を簡単に説明します。
以下からダウンロードできます。
Meinberg NTP Software Downloads
基本的にデフォルト設定でインストールすれば良いと思いますが、インストールするフォルダに関してはProgram Files以外(ファイルの編集が可能なところ)を指定するのが良いと思います。設定ファイルを編集する必要があるためです。
また、Ntp Pool Projectのサーバー(pool.ntp.org)を国または地域から選んで追加する項目がありますが、日本の選択肢が無いので、ここは適当に選ぶかnoneを選択し、後で設定ファイルから手動で編集します。
設定ファイルは\etc\ntp.conf
です。これを開き、編集します。
ここはntpdの設定ファイルと基本的に同じなので、ntpdの情報も参考にできます。
ここでは、restrict
でアクセス制御を行い、pool
でNTPサーバーを指定します。
また、ドリフトファイルとログファイルの出力を行います。
編集例を後述します。
指定するNTPサーバーは、できるだけ近い場所のNTPサーバーが望ましいです。これを3つくらい指定します。編集例では、jp.pool.ntp.orgの他にntp.jst.mfeed.ad.jp、time.windows.comを指定しています。
※time.windows.comは日本にサーバーがあります。
例:pool ntp.jst.mfeed.ad.jp iburst minpoll 6 maxpoll 6
pool
での指定では、DNSラウンドロビンを用いているドメインを指定した場合は、その中の全てのIPアドレスを参照します。そのため、ntp1.jst.mfeed.ad.jp、ntp2.jst.mfeed.ad.jp、ntp3.jst.mfeed.ad.jpと並べて記述する必要がありません。
また、Windows特有の問題として、サーバーへのポーリング間隔(アクセス頻度)が6(64秒)を超えると正確な補正ができなくなるという情報があります。私の環境でもそれを確認しました。そのため、オプションでmaxpoll 6
と記述しています。
この場合、64秒間隔という短い間隔でアクセスすることになります。そのため、サーバーとして有名なntp.nict.jpはアクセス間隔に制限があるため用いていません。
iburst
オプションを付けると、サービス起動時に8回連続でサーバーへの問い合わせを行い、初回同期速度を速めます。推奨。
ドリフトファイルは、周波数オフセットが記録されるファイルです。周波数オフセットとは、ローカルクロック(クライアントPCの内部時計)の進み具合と、NTPサーバーの時刻の進み具合との差を表したものです。算出した周波数オフセットを元に時刻補正を行います。
ドリフトファイルがあると、サービスの起動毎に周波数オフセットの算出をし直す必要が無くなります。
ログファイルは、loopstatsを出力するようにします。時刻補正のタイミングで参照サーバーとのオフセットおよび周波数オフセットを記録するもののようです。ただし詳しいことは分かりません(が、時刻オフセットの推移を確認するのに使用しています)。
以下が編集例です。青文字の部分が、デフォルトからの変更・追加部分です。
# NTP Network Time Protocol
# **** ATTENTION ****: *You have to restart the NTP service when you change this file to activate the changes*
# PLEASE CHECK THIS FILE CAREFULLY AND MODIFY IT IF REQUIRED
# Configuration File created by Windows Binary Distribution Installer Rev.: 1.27 mbg
# please check http://www.ntp.org for additional documentation and background information
# restrict access to avoid abuse of NTP for traffic amplification attacks
# see http://news.meinberg.de/244 for details
restrict default noquery nopeer nomodify notrap
restrict -6 default noquery nopeer nomodify notrap
# allow status queries and everything else from localhost
restrict 127.0.0.1
restrict -6 ::1
# if you need to allow access from a remote host, you can add lines like this:
# restrict <IP OF REMOTE HOST>
#サーバーとしても用い、自宅LAN上の他のクライアントPCからアクセスさせるには以下を追加。
#ただしファイアウォール設定で、ポート:123、プロトコル:UDPを送受信とも許可する必要があります。
restrict 192.168.0.0 mask 255.255.255.0 nomodify notrap
#追加。NTPサーバーからのアクセスを許可。
restrict source nomodify noquery notrap
# Use drift file
#(出力先は自動設定されるはず)
driftfile "C:\NTP\etc\ntp.drift"
# your local system clock, could be used as a backup
# (this is only useful if you need to distribute time no matter how good or bad it is)
#server 127.127.1.0
# but it should operate at a high stratum level to let the clients know and force them to
# use any other timesource they may have.
#fudge 127.127.1.0 stratum 12
# Use a NTP server from the ntp pool project (see http://www.pool.ntp.org)
# Please note that you need at least four different servers to be at least protected against
# one falseticker. If you only rely on internet time, it is highly recommended to add
# additional servers here.
# The 'iburst' keyword speeds up initial synchronization, please check the documentation for more details!
#(既に記述があれば削除して以下に置換)
pool jp.pool.ntp.org iburst minpoll 6 maxpoll 6
# Use specific NTP servers
pool ntp.jst.mfeed.ad.jp iburst minpoll 6 maxpoll 6
pool time.windows.com iburst minpoll 6 maxpoll 6
# End of generated ntp.conf --- Please edit this to suite your needs
#追加。ログファイルを出力。出力先は環境に応じて変更。
enable stats
statsdir "C:\NTP\log"
statistics loopstats
Meinberg NTPを起動するにはWindows Timeサービスを無効化する必要がありますが、Meinberg NTPをインストールした時点で自動で無効化されているはずです。
もしMeinberg NTPの起動に失敗した際は、ここを確認してください。
Windowsの「サービス」でWindows Timeのプロパティからスタートアップを「無効」にして適用した後、停止してください。
またアプリ一覧にMeinbergという項目が追加され、そこから各種操作が行えます。
ただし「Start NTP Service」「Restart NTP Service」「Stop NTP Service」は管理者として実行する必要があります。
また、PCのスリープを使用していると、復帰時に時刻が大きくずれることになりますが、Meinberg NTPはそれを適切に処理できないようで、周波数オフセットが大きくずれる等を経験しました。そのため、スリープ復帰時にNTPの再起動を行うようにタスクスケジューラに登録するのが良いと思います。
以下にチェック
「ユーザーがログオンしているかどうかにかかわらず実行する」
「最上位の特権で実行する」
スリープ復帰のイベントは上の通り、「Power-Troubleshooter」をプルダウンから選択してください。イベントビューアーからもスリープ復帰のイベントを確認でき、そこからタスク登録も可能です。
遅延時間を一応少し設けていますが、必要かは分かりません。
restartntp.batを指定してください。
開始(オプション)は作業フォルダを指定します。batファイルのあるフォルダを指定します。
「タスクが既に実行中の場合に適用される規則」は、「既存のインスタンスの停止」にします。
タスクの設定は以上です。
次に、NTP Time Server Monitorもインストールしておくと監視に便利です。
NTP Time Server Monitor
まずConfigurationタブにて設定を行います。以下を参考にしてください。
「Run at System Start」について、ここにチェックを入れるとPC起動時に自動で起動しますが、管理者として実行されないため、このツール上でNTPの再起動や停止などの操作が行えません。そのため、私はタスクスケジューラに登録して自動起動させています(最上位の特権で実行)。
「Enable DNS Lookup」は、NTPサーバーをIPアドレスではなく名称(ホスト名)で表示します。
「Logfile Locations」は環境に合わせて記述してください。
NTP StatusタブでNTPサーバーの状況を監視できます。
コンソールにてntpq -p
コマンドを行って得られる情報と同等のものがここに表示されます。
一番左のフラグ | *の付いているサーバーが時刻ソースとして現在優先的に使用しているサーバー、+の付いているサーバーが他の候補、-の付いているサーバーは候補外 |
Remote | サーバーのIPアドレスまたはホスト名 |
Refid | サーバーの参照先クロックのID |
Stratum | サーバーの階層。1に近いほど上位。原子時計などの基準クロックがStratum 0。 |
Poll | サーバーへの参照間隔(秒数) |
When | 最後の参照から経過した秒数 |
Reach | 直近8回の参照が正常に行えたかを示します。8進数で表され、0、1、3、 7、17、37、77、177、377の何れかが表示されます。0では一度も行えておらず、377では8回全て行えているという意味になります。 |
Delay | サーバーへの往復遅延(ミリ秒) |
Offset | サーバーがローカルクロックから何ミリ秒ずれているか(プラスだとローカルクロックが遅れている) |
Jitter | ゆらぎ誤差 |
Statisticsタブでログ(loopstats)をグラフに出力できます。
赤ライン(左軸)が時刻オフセット、青ライン(右軸)が周波数オフセットです。
周波数オフセットは、PPM(1/1,000,000)で表されます。1PPMは、1秒につき1マイクロ秒のずれがあることを表します。
これで一通り導入が終わりました。
次に、注意点(気づいた点)です。周波数オフセットは気温の変化などにより変化します。急激な変化がある時、ntpd(Meinberg NTP)はそれに付いてこられないようで、時刻オフセットのずれが大きめなまま、あまり修正されずに推移することがあります。周波数オフセットが安定すると時刻オフセットも0msに近い値で安定します。これは仕様だと思われます。
特に、仮想化環境では周波数オフセットが不安定かもしれないため、注意が必要です(周波数オフセットが大きいだけなら問題ありません)。
Windows Defenderの「デバイスセキュリティ」で「コア分離」をオンにしていると、Hyper-Vが有効になり、自動的に仮想化が有効になるため注意が必要だと思います。
以上、ざっと解説しました。
参考にできそうなページを以下に挙げておきます。
NTP - a comprehensive Guide on Network Time Synchronization
NTP Basics [Knowledge Base]
Time Synchronization Accuracy With NTP [Knowledge Base]
Installing NTP on Windows