أولوية مصدر الوقت

يستخدم إطار عمل Android مصادر زمنية متنوعة لمزامنة الوقت. تركّز هذه الصفحة على مصادر الوقت التلقائية لبروتوكول وقت الشبكة (NTP) وهوية الشبكة والمنطقة الزمنية (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)
  • الشبكة (NTP)

الاختبار

للتحقق من أن الجهاز يستخدم NITZ عندما لا يكون NTP متاحًا (عندما تكون بيانات الجوّال وWi-Fi متوقفة)، عليك إجراء ما يلي:

  1. التأكد من توفّر شريحة SIM صالحة في DUT
  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}