PCで遊んだ日々の備忘録

Making PC and Customization PC

Ubuntu と Windows 10 の時間のズレを合わせる

我が家で保有するパソコンの 8割は Ubuntuまたは Ubuntuフレーバー(Lubuntu, Xubuntu など)と Windows 10 のマルチブート環境で運用しています。この環境で起こるのが Windows側で時計の時刻が「9時間遅れる」現象です。

下の画像は BIOSユーティリティのスクリーンショットです。

日付が 23:51 金曜日[04/10/2020] になっていますがこの時の日本時間は 08:51 土曜日[04/11/2020] と、このようなズレ方をします。

一般的にパソコンの OS上の時間のズレは CMOSバックアップ用電池(マザーボードに付いているボタン電池)切れとか電池切れ真近などと言われているようですがこの場合は当てはまりません。各OSの仕様に由来します。

このページでは マルチブート環境下 の Ubuntu 18.04 LTS と Windows 10 間の時刻のズレを解消する方法を掲載しています。(2020年4月)


現象と原因

Ubuntuを起動してデスクトップ上部パネルに表示される時刻が日本標準時であることを確認した後、PCシャットダウンまたは再起動して Windows 10 を起動するとデスクトップタスクバーに表示される時刻が日本時間よりキッチリ 9時間遅れて表示される。

下の画像は NICT(情報通信研究機構)の 日本標準時 のページです。ウェブブラウザーでアクセスするとアクセスしたパソコンの時間のズレを確認できます。

ご覧のように「あなたのコンピュータの内蔵時計」時刻が日本標準時ではなく協定世界時になっています。

これまで Windowsでは自動的にインターネット時間サーバー(Network Time Protocol server)に同期すると思っていたが、いつまで経っても時間補正がかからないので手動で同期しました。タスク スケジューラーを弄くったところで変化なしでした。

どうやら Time Synchronization は機能していない模様です。(注1.)

時間同期した後 Windowsを先に起動すると時刻のズレは起きません。しかし Ubuntuを先に起動すると、この現象は確実に再現します。

原因は下記のような Linux OSの仕様でした。

ハードウェアクロックの時刻は Linuxシステム立ち上げ時に hwclockコマンドで読み取られ、システムクロックに設定されます。また、システムの停止時に、hwclockコマンドによってシステムクロックの時刻がハードウェアクロックに設定されます。

これは Linux認定試験(LPIC)受験者向けの サイト に掲載されていたものです。ネット上の情報はどれもこのようなものです。分かりにくいですよね。

⌚凡例に置き換えてみる

上記引用文を下表の凡例に置き換えてみると少しは分かりやすくなると思います。

ハードウェア クロック, リアルタイム クロック(RTC) マザーボードの時計
システム クロック(UTC) Ubuntu の内部時計
ローカル タイム(Local time) デスクトップに表示される時刻
ローカル タイムゾーン(Local TZ) アジア / 東京の時刻

マザーボードの時計(RTC)は Linux システム立ち上げ時に hwclockコマンドで読み取られ、Ubuntu の内部時計(UTC)に設定されます。また、システムの停止時に、hwclockコマンドによって Ubuntu の内部時計(UTC)の時刻がマザーボードの時計(RTC)に設定されます。

つまりマザーボードの時計(RTC)は常に UTC時刻に固定されるという訳です。

解説

Ubuntuを起動するとマザーボードの時計(ハードウェア クロック または リアルタイム クロック と呼ばれる)を UTC(協定世界時=日本標準時から 9時間遅れ)の時刻に書き換えてしまう。ちなみに GMT(グリニッジ平均時)も日本標準時から 9時間遅れ。GMT と UTC の違いは何?

Ubuntuは UTCを基準(システム クロック)とし、インストール時に設定したタイムゾーン(アジア、東京など)の時刻に補正したローカル タイムをデスクトップに表示する。Windowsとのマルチブート環境でなければこれで問題ない。

一方 Ubuntuのシャットダウン後に起動した Windowsはマザーボードの時計を参照するので 9時間ズレる。Windowsの時刻を修正した後 PCシャットダウンしてマザーボードの時刻を日本時間で上書きしても次回 Ubuntuを先に起動すれば同じことの繰り返しになるので永久にズレたままになる。

ズレてもインターネット上の NTPサーバー(time.windows.com , time.nist.gov)に同期する設定なのでマザーボードの時計が狂っていたとしても直ちに日本標準時に補正されるはずである。なぜ補正されないのか分からなかった。(注1.)

注1. 自動的に時間補正されない理由のヒントは下記リンク先へどうぞ。

スタンドアロン環境で Windows Time サービスが自動的に起動しない

ワークグループ環境においてWindows Time サービスが自動で起動する

Workgroup 環境での Windows の時刻同期の設定方法

▲ 目次へ

Windows 10 側で対処する

Windowsが参照しているインターネット上の NTPサーバーを変更して後、Windowsサービスである Windows Time の設定を変更します。得体の知れないレジストリを触らないで時刻を同期する方法です。

補足|ここで NTPサーバーを変更するのは個人の好みです。デフォルトのままでも問題ありません。

コントロールパネル から [日付と時刻] を開いて インターネット時刻 タブ内 設定の変更 ボタンを押すとインターネット時刻を設定するダイアログボックスが開きます。

[サーバー(E):]の欄に

 ntp.nict.jp 

と入力して OK ボタンを押してダイアログボックスを閉じます。

この時 今すぐ更新(U) ボタンは押しません。理由は次のパートで設定する Windows Time の動作確認の際、タスクバーの時計の時刻が変わる瞬間を見たいからです。

Windows Time はネットワーク上のクライアントとサーバーの日時の同期を維持する Windowsサービスですがデフォルトでは「手動」に設定されています。

これを「自動(遅延開始)」または「自動」に設定します。前者はシステムの起動に支障がないように起動開始から 2分後にサービスがスタートします。

コントロールパネルから [管理ツール] を開いて サービス 内の Windows Time をダブルクリックするとプロパティが開きます。そしてスタートアップの種類で「自動(遅延開始)」を選択し OK ボタンで閉じます。

次に、念のためタスクスケジューラ ライブラリ / Microsoft/ Windows/ Time Synchronization/ にトリガーの記述がないことを確認してパソコン再起動します。

サインインしておよそ 2分後、タスクバー時計の時刻が変わる瞬間を見れます。そしてイベントビューアーにも時刻が切り替わった旨のメッセージがあります。

Windowsサービスの画像

Windowsサービス

タスクスケジューラの画像

タスクスケジューラ

イベントビューアーの画像

イベントビューアー

当方の環境でスタートアップの種類を「自動」に設定してみたら、サインイン後デスクトップが表示されてから時刻が修正されるまで2~3秒でした。

ただし「自動(遅延開始)」、「自動」いずれの場合もサインイン画面の時間は UTC、つまりズレています。ここも修正したいならレジストリを弄るしかありません。

サービスが発動しないときは

次のコマンドをユーザーまたは管理者権限のコマンドプロンプトからで実行して、

 C:¥Windows¥system32 > sc qtriggerinfo w32time 
結果
[SC] QueryServiceConfig2 SUCCESS
サービス名:W32time
 サービスの開始
  ドメインの参加状態:1ce20aba-9851-4421-9430-1ddeb766e809 [ドメインに参加済みです] 
 

[ドメインに参加済みです] の結果が返ってこない場合、サービスは開始されません。前述の 注1.リンク先 に解決策が載っています。

以上が時刻補正の設定です。Ubuntu側の設定は不要です。

▲ 目次へ

Ubuntu 側で対処する

もう1つの対処法は Windows側のハードウェア クロックのタイムゾーンを UTCに設定するか、Ubuntu側のハードウェア クロックのタイムゾーンをローカルタイムに設定するかです。このセクションは後者の方です。

下記は Linuxを標準OSに産業用組込みボードなど供給している ベンダーのサイト に掲載されていたものです。

ハードウェアクロックは UTCで保存するか ローカルタイムで保存するか、選択することができます。UTCで保存しておけば、タイムゾーンを変更してもハードウェアクロックを変更しなくとも良いので、通常は問題ないでしょう。しかしながら、Windowsではローカルタイムで保存します。そのため、PC Linuxではローカルタイムをハードウェアクロックに保存することが多いようです。

ネット上で公開されている Linuxの時間管理に関する記事の中で最も分かり易かったので引用しました。

ローカルタイムで保存がデフォルトの Windowsを UTCで保存するようにするには レジストリを変更 する必要があります。しかし、Windows 10のレジストリを触りたくない場合 Ubuntu側をローカルタイムで保存するように設定する方法があります。

  • Ubuntu 18.04 LTS のネットワーク時刻同期は ntpd ではなく、systemd-timedatesyncd が使用されている。
  • カーネルによる自動ハードウェアクロック同期(11分モード)の動作中に hwclock --adjustコマンドを使用してはいけない。(ubuntu mauals:16.04 LTS, 18.04 LTS より)
  • ハードウェアクロック(RTC)のローカルタイム(JST)設定は Ubuntu非推奨である。
  • 意味も分からず、やみくもにコマンド実行しないこと。

11分モードを一言でいうと、「11分ごとにシステム時刻をハードウェアクロック(RTC)にコピーするモード」です。adjtimexコマンドと ntptimeコマンドで確認できます。

下記は ubuntu manuals:18.04 LTS からの引用です。

If the kernel is compiled with the '11 minute mode' option it will be active when the kernel's clock discipline is in a synchronized state. When in this state, bit 6 (the bit that is set in the mask 0x0040) of the kernel's time_status variable is unset. This value is output as the 'status' line of the adjtimex --print or ntptime commands.
カーネルが '11 分モード' オプションでコンパイルされている場合、カーネルのクロック規律が同期状態にあるときにアクティブになります。 この状態にあるとき、カーネルの time_status 変数のビット 6 (マスク 0x0040 にセットされているビット) はアンセットされます。 この値は adjtimex --print または ntptime コマンドの 'status' 行として出力されます。

ubuntu manuals ページの NOTES セクション中断あたり Automatic Hardware Clock Synchronization by the Kernel に記載されています。なお、同ページの日本語訳のページが存在しますが内容が少し異なるようです

adjtimexは入っていなかったのでインストールしてから確認しました。端末から

 xfce4-terminal
 $ sudo apt install adjtimex
 $ adjtimex --print
結果
 mode: 0
   ⋮
(中略)
 status: 8193
(後略)
 

続けて

 $ ntptime
結果
 ntp_gettime() returns code 0 (OK)
   ⋮
(中略)
 ntp_adjtime() returns code 0 (OK)
   ⋮
(中略)
 status: 0x2001 (PLL,NANO),
(後略)

両コマンドの status の結果だけ抜き出しています。(中略)と(後略)の部分は下の画像を参照してください。実際に実機上でコマンド実行した結果のスクリーンショットです。

adjtimex の status: 8193 は何を意味しているのか分かりませんでした。ntptime の status:0x2001 (PLL,NANO) の内 PLL と NANO は

PLL Enable phase-locked loop (PLL) updates via ADJ_OFFSET. / ADJ_OFFSETで位相同期ループ(PLL)の更新を有効にする
NANO Resolution (0 = microsecond, 1 = nanoseconds) / 分解能(0=マイクロ秒、1=ナノ秒)

これだけではよく分かりませんね。もう少し調べてみると ADJTIMEX(2) Linux Programmer's Manual のページの RETURN VALUE のセクションに

RETURN VALUE [返り値]

On success, adjtimex() and ntp_adjtime() return the clock state; that is, one of the following values:

[成功すると adjtimex()とntp_adjtime()はクロック状態を返します]

TIME_OK・・・Clock synchronized, no leap second adjustment pending.

[クロックが同期しており、うるう秒の調整は保留されていません]

(中略)

TIME_ERROR・・・The system clock is not synchronized to a reliable server. This value is returned when any of the following holds true:

[システムクロックが信頼できるサーバーに同期されていません。この値は、以下のいずれかが真の場合に返されます]

* Either STA_UNSYNC or STA_CLOCKERR is set.

[STA_UNSYNC または STA_CLOCKERR が設定されている]

(後略)

  • STA_UNSYNC・・・Clock unsynchronized.(クロックが非同期)

と記載されています。これをコマンド結果と照らし合わせてみると、時刻のエラーがないこと、 UNSYNC の表示がないことから 11分モードが有効であることが分かりました。

ネットワーク時刻同期の現状(システムの時刻と日付、現在の設定)と NTP参照サーバーを確認します。ubuntu manuals

時刻同期の現状

まず systemd - timesyncd の設定を確認します。端末から

 $ timedatectl
結果
                       Local time: 日 2020-04-05 10:39:17 JST 
                   Universal time: 日 2020-04-05 01:39:17 UTC
                         RTC time: 日 2020-04-05 01:39:17
                        Time zone: Asia/Tokyo (JST, +0900)
        System clock synchronized: yes
 systemd-timesyncd.service active: yes
                  RTC in local TZ: no
 

ハードウェア クロック(RTC)は UTC、タイムゾーンはアジア/東京、システムクロックは同期しており、systemd-timesyncd.serviceはアクティブになっています。

ntp参照サーバー

次に、systemctl の systemd-timesyncd でネットワーク時刻同期の NTPサーバーを確認します。

 $ systemctl status systemd-timesyncd.service
結果
● systemd-timesyncd.service - Network Time Synchronization
   ⋮
(中略)
  Status: "Synchronized to time server 91.189.91.157:123 (ntp.ubuntu.com)." 
   ⋮
(中略)
 4月 05 14:08:27 f-system systemd-timesyncd[9879]:Synchronized to time server
 91.189.91.157:123 (ntp.ubuntu.com).

結果の(中略)部分は下の画像をご覧ください。参照サーバーは ntp.ubuntu.com です。

systemctl statusコマンド実行結果の画像

NTP参照サーバー

参照サーバー設定ファイルの画像

設定ファイル

参照サーバーの設定ファイルである / etc/ systemd/ timesyncd.conf に ntp.ubuntu.com の記述はありますが設定項目は全てコメントアウト(無効化)されています。つまり ntp.ubuntu.com がデフォルトのサーバーということです。

今回は確認だけで、ntp.nict.jp への変更はしませんでした。

今度は hwclockコマンド で現在のハードウェア クロック即ちマザーボードの時刻を確認してみます。

 $ sudo hwclock -r --debug または hwclock --show --debug
結果
hwclock from util-linux 2.31.1
System Time: 1586043500.764608
Trying to open: /dev/rtc0
Using the rtc interface to the clock.
ハードウェアの時刻が UTC に設定されているものと仮定します。
クロックティックを待っています...
...クロックティックを取得しました
ハードウェアの時計から読み込んだ時刻: 2020/04/04 23:38:21
ハードウェアの時刻値 : 2020/04/04 23:38:21 = 1969 年から 1586043501 秒経過
Time since last adjustment is 1586043501 seconds
Calculated Hardware Clock drift is 0.000000 seconds
2020-04-05 08:38:20.749089+0900
 

最終行朱色文字は hwclockコマンドを実行した時刻、即ちデスクトップに表示される時刻です。9時間の差があるのでハードウェア クロックは UTCに設定されていることが分かります。

UTC(協定世界時)モードを JST(日本標準時)モードに変更します。まずは PC再起動して BIOSに入って現在の時刻が日本時間より 9時間遅れていることを確認します。

参考までに / etc/ default/ rcS ファイルで UTC=yes/no を設定することはできません。by Ask Ubuntu

端末から

 $ timedatectl set-local-rtc 1 --adjust-system-clock 

を実行します。

下記はコマンドオプションの説明です。(ubuntu manuals:timedatectl - 18.04 LTSより)

set-local-rtc [BOOL] ブール値・・・true(真), false(偽)

Takes a boolean argument. If "0", the system is configured to maintain the RTC in universal time. If "1", it will maintain the RTC in local time instead. Note that maintaining the RTC in the local timezone is not fully supported and will create various problems with time zone changes and daylight saving adjustments. If at all possible, keep the RTC in UTC mode. Note that invoking this will also synchronize the RTC from the system clock, unless --adjust-system-clock is passed (see above). This command will change the 3rd line of /etc/adjtime, as documented in hwclock(8).

ブール値を取ります。"0" の場合、システムは普遍的な時間でRTCを維持するように設定されています。"1" の場合は、現地時間でのRTCを維持します。 ローカルタイムゾーンでのRTCの維持は完全にはサポートされておらず、タイムゾーンの変更やサマータイムの調整で様々な問題が発生するので注意が必要です。 可能な限り、RTC を UTC モードにしてください。これを実行すると、 --adjust-system-clock が渡されない限り、システムクロックから RTC を同期させることに注意してください(上記参照)。このコマンドは、hwclock(8) で文書化されているように、/etc/adjtime の 3 行目を変更します。

--adjust-system-clock

If set-local-rtc is invoked and this option is passed, the system clock is synchronized from the RTC again, taking the new setting into account. Otherwise, the RTC is synchronized from the system clock.

set-local-rtc が起動され、このオプションが渡された場合、システムクロックは新しい設定を考慮して再び RTC から同期されます。そうでなければ RTCはシステムクロックから同期しています。

サービスを再起動して変更された内容を確認します。

 $ systemctl restart systemd-timesyncd.service 
 $ timedatectl

以下がその結果です。(日本語訳は管理人が付け加えたもので実際には出力されません)

                      Local time: 土 2020-04-11 09:18:52 JST
                  Universal time: 土 2020-04-11 00:18:52 UTC
                        RTC time: 土 2020-04-11 00:18:52
                       Time zone: Asia/Tokyo (JST, +0900)
       System clock synchronized: no
systemd-timesyncd.service active: yes
                 RTC in local TZ: yes
Warning: The system is configured to read the RTC time in the local time zone.
         This mode can not be fully supported. It will create various problems
         with time zone changes and daylight saving time adjustments. The RTC
         time is never updated, it relies on external facilities to maintain it. 
         If at all possible, use RTC in UTC by calling
         'timedatectl set-local-rtc 0'.
警告:システムは、ローカルタイムゾーンのRTC時刻を読み取るように設定されています。
     このモードは完全には対応していません。
     時間帯の変更やサマータイムの調整で様々な問題が発生します。
     RTCの時刻は決して更新されず、維持するために外部の設備に依存しています。
     可能であれば'timedatectl set-local-rtc 0'を呼び出してUTCでRTCを使用してください。

ご覧のように システムクロック同期が無効に、RTC がローカルタイムゾーンで有効になることでマザーボードに UTC時刻を書き込まないようになります。

また、上述の引用文中にもあるように ローカルタイム(JST)モードは非推奨のため警告が出ています。前出の ubuntu manuals と同じ文言です。

最後に PC再起動して BIOSに入って時刻が日本時間になっていることを確認します。

UTCモードに戻すには

 $ timedatectl set-local-rtc 0 --adjust-system-clock 
 $ systemctl restart systemd-timesyncd.service

を実行します。

以上が時刻補正の設定です。Windows 10側の設定は不要です。

▲ 目次へ

雑感

結局のところ Ubuntu 18.04 LTS は設定変更後の動作確認ができたところで元の設定に戻して、Windows 10 だけ変更しました。理由は

  • RTCをローカルタイムに設定するのは Ubuntu非推奨であることがマニュアルに記載されている
  • 設定の際、確認のため PCを何度も再起動しなければならない
  • 1台の PCに入っている Linux、Windows 共に複数ある
  • Ubuntu ログイン画面は UTC時刻だがログインして 2~3秒で日本時間になる
  • Windows サインイン画面は UTC時刻だがサインインして 2~3秒で日本時間になる
  • Windows レジストリを触らなくてよい

です。どう考えても Windows 側を設定変更したくなるでしょう。

どうしても時刻補正のタイムラグを 0にしたければ Windowsを UTC基準へ、つまりレジストリを編集するしかないようですね。こちら、1次情報源を調べていないし試してもいないので本当にうまくいくのか不明です。

Windows10アップデートがある度にネットに溢れる不具合を見るに付け、とてもじゃないがレジストリ触る気になれないな

それと本文中にも書いていますが、意味も分からず やみくもにコマンド実行しないでね。

余談ですが、電池切れで ...

管理人は CMOSバックアップ用電池切れで時間がズレる経験をしたことがありません。経験したのはある日突然、PC電源投入すると POST画面が表示され、日付が工場出荷状態にリセットされる現象です。本当に電池切れで時間がズレるのでしょうかね。

▲ 目次へ

クリエイティブ・コモンズ・ライセンス
Top of Pageの画像
sidemenuの画像