Приоритет источника времени

Фреймворк Android использует различные источники времени для синхронизации времени. На этой странице основное внимание уделяется автоматическим источникам времени Network Time Protocol (NTP) и Network Identity and Time Zone (NITZ). По умолчанию в Android 12 и выше фреймворк отдает приоритет NTP как источнику времени над NITZ, поскольку NTP более точен и надежен, чем NITZ. В ситуациях, когда NTP недоступен, фреймворк возвращается к NITZ. Это обратный приоритет по умолчанию из более ранних версий платформы. По умолчанию в Android 11 и ниже фреймворк отдает приоритет NITZ над NTP.

Более подробную информацию об этом изменении можно найти в следующих исправлениях AOSP: 1563678 , 1513323 .

Настроить приоритет источника времени

Чтобы настроить, какой источник времени будет иметь приоритет по умолчанию для определенной версии Android, настройте ключ config_autoTimeSourcesPriority в frameworks/base/core/res/res/values/config.xml во время сборки. Предложения по времени из источника времени, который находится выше в списке, имеют приоритет над источниками, которые находятся ниже в списке.

Источники времени Android, которые можно настроить, находятся в TimeDetectorStrategy.java . Следующие источники настроены для использования по умолчанию:

  • Телефония (NITZ)
  • Сеть (НТП)

Тестирование

Чтобы убедиться, что устройство использует NITZ, когда NTP недоступен (когда отключены мобильные данные и Wi-Fi), выполните следующие действия:

  1. Убедитесь, что в проверяемом устройстве установлена ​​рабочая SIM-карта.
  2. Отключите мобильные данные и Wi-Fi
  3. Переведите устройство в режим полета, чтобы убедиться, что сотовая связь выключена.
  4. Отключить автоматическое определение времени
  5. Установите часы вручную на неправильное значение времени в будущем
  6. Перезагрузите устройство.
  7. Включить автоматическое определение времени
  8. Выведите устройство из режима полета.

Эти шаги запускают изменение системных часов, как только получен сигнал NITZ. Чтобы проверить, как установлено время устройства, выполните следующую команду:

adb shell dumpsys time_detector

Чтобы убедиться, что системные часы используют NITZ, проверьте следующее в выводе команды:

  • mEnvironment.isAutoTimeDetectionEnabled() имеет true .
  • mEnvironment.autoOriginPriorities() содержит список источников времени, при этом источники, расположенные выше в списке, имеют приоритет над источниками, расположенными ниже в списке.
  • Раздел Time change log показывает, что системные часы установлены с использованием подсказки телефонии.
  • Раздел Telephony suggestion history содержит предложения по времени.
  • Раздел Network suggestion history пуст.

Предложения времени в разделах Telephony suggestion history и Network suggestion history считаются источником истины для времени. Если устройство подключено к Интернету и имеет SIM-карту, предложения генерируются с использованием как NTP (сеть), так и NITZ (телефония). В этом тестовом случае только раздел Telephony suggestion history содержит предложения, поскольку NTP отключен.

Раздел Time change log записывает изменения, внесенные в системные часы устройства, и использованное предложение. Системные часы устанавливаются на основе порядка источников времени в списке приоритетов в ключе config_autoTimeSourcesPriority . Однако предложения из источника с более высоким приоритетом могут быть проигнорированы, если предложение слишком старое или недействительное. Кроме того, если действительное предложение с самым высоким приоритетом совпадает с текущим временем системных часов устройства с точностью до нескольких секунд, время не будет изменено. В этом тестовом случае, пока предложения не устарели, системные часы устанавливаются с использованием одного из предложений из Telephony suggestion history .

Ниже приведен пример выходных данных, в которых устройство переходит на использование NITZ, когда NTP недоступен.

TimeDetectorStrategy:
  mLastAutoSystemClockTimeSet=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000}
  mEnvironment.isAutoTimeDetectionEnabled()=true
  mEnvironment.elapsedRealtimeMillis()=73059
  mEnvironment.systemClockMillis()=1614186767818
  mEnvironment.systemClockUpdateThresholdMillis()=2000
  mEnvironment.autoTimeLowerBound()=2021-02-24T15:44:15Z(1614181455000)
  mEnvironment.autoOriginPriorities()=[network,telephony]
  Time change log:
    66261 / 2021-02-24T17:12:41.020Z - Set system clock using time=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000} cause=Found good telephony suggestion., bestTelephonySuggestion=TelephonyTimeSuggestion{mSlotIndex='0', mUtcTime=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000}, mDebugInfo=[Sending new time suggestion nitzSignal=TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}}, reason=handleNitzReceived(TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}})]}, detectionReason=New telephony time suggested. timeSuggestion=TelephonyTimeSuggestion{mSlotIndex='0', mUtcTime=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000}, mDebugInfo=[Sending new time suggestion nitzSignal=TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}}, reason=handleNitzReceived(TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}})]} elapsedRealtimeMillis=66259 newSystemClockMillis=1614186761019
  Telephony suggestion history:
    key idx: 0=0
    val idx: 0=TelephonyTimeSuggestion{mSlotIndex='0', mUtcTime=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000}, mDebugInfo=[Sending new time suggestion nitzSignal=TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}}, reason=handleNitzReceived(TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}})]}
      Historic values=[
        0@PT1M6.258S: TelephonyTimeSuggestion{mSlotIndex='0', mUtcTime=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000}, mDebugInfo=[Sending new time suggestion nitzSignal=TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}}, reason=handleNitzReceived(TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}})]}
      ]
  Network suggestion history:
    {Empty}
  Gnss suggestion history:
    {Empty}
  External suggestion history:
    {Empty}

Для сравнения с результатами в тестовом сценарии ниже приведен пример типичного результата, когда устройство получает предложения по времени от источников времени NTP и NITZ.

TimeDetectorStrategy:
  mLastAutoSystemClockTimeSet=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000}
  mEnvironment.isAutoTimeDetectionEnabled()=true
  mEnvironment.elapsedRealtimeMillis()=302926
  mEnvironment.systemClockMillis()=1614186997685
  mEnvironment.systemClockUpdateThresholdMillis()=2000
  mEnvironment.autoTimeLowerBound()=2021-02-24T15:44:15Z(1614181455000)
  mEnvironment.autoOriginPriorities()=[network,telephony]
  Time change log:
    66261 / 2021-02-24T17:12:41.020Z - Set system clock using time=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000} cause=Found good telephony suggestion., bestTelephonySuggestion=TelephonyTimeSuggestion{mSlotIndex='0', mUtcTime=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000}, mDebugInfo=[Sending new time suggestion nitzSignal=TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}}, reason=handleNitzReceived(TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}})]}, detectionReason=New telephony time suggested. timeSuggestion=TelephonyTimeSuggestion{mSlotIndex='0', mUtcTime=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000}, mDebugInfo=[Sending new time suggestion nitzSignal=TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}}, reason=handleNitzReceived(TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}})]} elapsedRealtimeMillis=66259 newSystemClockMillis=1614186761019
  Telephony suggestion history:
    key idx: 0=0
    val idx: 0=TelephonyTimeSuggestion{mSlotIndex='0', mUtcTime=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000}, mDebugInfo=[Sending new time suggestion nitzSignal=TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}}, reason=handleNitzReceived(TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}})]}
      Historic values=[
        0@PT1M6.258S: TelephonyTimeSuggestion{mSlotIndex='0', mUtcTime=TimestampedValue{mReferenceTimeMillis=66240, mValue=1614186761000}, mDebugInfo=[Sending new time suggestion nitzSignal=TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}}, reason=handleNitzReceived(TimestampedValue{mReferenceTimeMillis=66240, mValue=NitzData{mOriginalString=21/02/24,17:12:41+00,00, mZoneOffset=0, mDstOffset=0, mCurrentTimeMillis=1614186761000, mEmulatorHostTimeZone=null}})]}
      ]
  Network suggestion history:
    0@PT4M4.04S: NetworkTimeSuggestion{mUtcTime=TimestampedValue{mReferenceTimeMillis=244038, mValue=1614186939242}, mDebugInfo=[Origin: NetworkTimeUpdateService. event=3]}
  Gnss suggestion history:
    {Empty}
  External suggestion history:
    {Empty}