시간 소스 우선순위

Android 프레임워크는 시간 동기화를 위해 다양한 시간 소스를 사용합니다. 이 페이지에서는 네트워크 시간 프로토콜(NTP)과 네트워크 ID 및 시간대(NITZ) 자동 시간 소스를 중점적으로 다룹니다. Android 12 이상에서는 기본적으로 프레임워크가 시간 소스로 NTP를 NITZ보다 우선시합니다. NTP가 NITZ보다 더 정확하고 신뢰할 수 있기 때문입니다. NTP를 사용할 수 없는 상황에서는 프레임워크가 NITZ로 대체됩니다. 이는 이전 버전 플랫폼의 기본 우선순위와 반대입니다. Android 11 이하에서는 기본적으로 프레임워크가 NITZ를 NTP보다 우선시합니다.

이 변경에 관한 자세한 내용은 다음 AOSP 패치를 참고하세요. 1563678, 1513323.

시간 소스 우선순위 구성

특정 Android 버전에 기본적으로 우선순위를 갖는 시간 소스를 구성하려면 빌드 시 frameworks/base/core/res/res/values/config.xml에서 config_autoTimeSourcesPriority 키를 구성합니다. 목록에서 상위에 있는 시간 소스의 시간 추천이 목록 하위에 있는 소스의 추천보다 우선합니다.

구성할 수 있는 Android 시간 소스는 TimeDetectorStrategy.java에 있습니다. 다음 소스는 기본적으로 사용하도록 구성되어 있습니다.

  • 전화 통신(NITZ)
  • 네트워크(NTP)

테스트

NTP를 사용할 수 없을 때(모바일 데이터 및 Wi-Fi가 사용 중지된 경우) 기기에서 NITZ를 사용하는지 확인하려면 다음을 따르세요.

  1. DUT에서 작동하는 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(전화 통신)를 모두 사용하여 추천이 생성됩니다. 이 테스트 사례에서는 NTP가 사용 중지되었으므로 Telephony suggestion history 섹션에만 추천이 포함됩니다.

Time change log 섹션에는 기기의 시스템 시계 변경사항 및 사용된 추천이 기록됩니다. 시스템 시계는 config_autoTimeSourcesPriority 키의 우선순위 목록에 있는 시간 소스의 순서에 따라 설정됩니다. 그러나 우선순위가 더 높은 소스의 추천도 너무 오래되거나 무효한 경우 무시될 수도 있습니다. 또한 우선순위가 가장 높은 유효한 추천이 기기의 현재 시스템 시계 시간과 몇 초 이내로 일치하면 시간은 변경되지 않습니다. 이 테스트 사례에서는 추천이 오래되지 않았다면 Telephony suggestion history의 추천 중 하나를 사용하여 시스템 시계가 설정됩니다.

다음은 NTP를 사용할 수 없을 때 기기가 NITZ 사용으로 대체하는 출력의 예입니다.

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}