डायरेक्ट बूट मोड के साथ काम करना

Android 7.0, सुरक्षित डायरेक्ट बूट मोड में चलता है. ऐसा तब होता है, जब डिवाइस चालू हो, लेकिन उपयोगकर्ता ने डिवाइस को अनलॉक न किया हो. इसके लिए, सिस्टम डेटा को दो स्टोरेज लोकेशन में सेव करता है:

  • क्रेडेंशियल एन्क्रिप्टेड स्टोरेज, जो डिफ़ॉल्ट स्टोरेज की जगह है. यह सिर्फ़ तब उपलब्ध होता है, जब उपयोगकर्ता डिवाइस को अनलॉक कर लेता है.
  • डिवाइस का एन्क्रिप्ट किया गया स्टोरेज, जो डायरेक्ट बूट मोड के दौरान और उपयोगकर्ता के डिवाइस को अनलॉक करने के बाद, दोनों समय उपलब्ध रहता है.

डिफ़ॉल्ट रूप से, डायरेक्ट बूट मोड के दौरान ऐप्लिकेशन नहीं चलते. अगर आपके ऐप्लिकेशन को डायरेक्ट बूट मोड के दौरान कोई कार्रवाई करनी है, तो इस मोड के दौरान चलाए जाने वाले ऐप्लिकेशन कॉम्पोनेंट को रजिस्टर किया जा सकता है. डायरेक्ट बूट मोड के दौरान, ऐप्लिकेशन को चलाने की ज़रूरत के कुछ सामान्य उदाहरणों में ये शामिल हैं:

  • ऐसे ऐप्लिकेशन जिनमें सूचनाएं शेड्यूल की गई हैं. जैसे, अलार्म क्लॉक ऐप्लिकेशन.
  • ऐसे ऐप्लिकेशन जो उपयोगकर्ताओं को ज़रूरी सूचनाएं देते हैं. जैसे, एसएमएस ऐप्लिकेशन.
  • सुलभता सेवाएं देने वाले ऐप्लिकेशन, जैसे कि Talkback.

अगर आपके ऐप्लिकेशन को डायरेक्ट बूट मोड में चलने के दौरान डेटा ऐक्सेस करना है, तो डिवाइस के एन्क्रिप्ट किए गए स्टोरेज का इस्तेमाल करें. डिवाइस के एन्क्रिप्ट किए गए स्टोरेज में मौजूद डेटा को एक ऐसी कुंजी से एन्क्रिप्ट किया जाता है जो डिवाइस के वेरिफ़ाइड बूट के बाद ही उपलब्ध होती है.

जिस डेटा को उपयोगकर्ता के क्रेडेंशियल से जुड़ी कुंजी के साथ एन्क्रिप्ट (सुरक्षित) करना ज़रूरी है उसके लिए, क्रेडेंशियल एन्क्रिप्टेड स्टोरेज का इस्तेमाल करें. जैसे, पिन या पासवर्ड. क्रेडेंशियल एन्क्रिप्ट (सुरक्षित) करने वाला स्टोरेज, उपयोगकर्ता के डिवाइस को अनलॉक करने के बाद उपलब्ध होता है. यह तब तक उपलब्ध रहता है, जब तक उपयोगकर्ता डिवाइस को रीस्टार्ट नहीं करता. अगर उपयोगकर्ता डिवाइस को अनलॉक करने के बाद लॉक स्क्रीन की सुविधा चालू करता है, तो क्रेडेंशियल एन्क्रिप्ट (सुरक्षित) करने वाला स्टोरेज उपलब्ध रहता है.

डायरेक्ट बूट के दौरान ऐप्लिकेशन चलाने के लिए ऐक्सेस का अनुरोध करना

ऐप्लिकेशन को अपने कॉम्पोनेंट को सिस्टम के साथ रजिस्टर करना होगा. इसके बाद ही, वे डायरेक्ट बूट मोड के दौरान चल सकते हैं या डिवाइस के एन्क्रिप्ट (सुरक्षित) किए गए स्टोरेज को ऐक्सेस कर सकते हैं. ऐप्लिकेशन, कॉम्पोनेंट को एन्क्रिप्शन की जानकारी देने वाले के तौर पर मार्क करके, सिस्टम के साथ रजिस्टर करते हैं. अपने कॉम्पोनेंट को एन्क्रिप्शन अवेयर के तौर पर मार्क करने के लिए, अपने मेनिफ़ेस्ट में android:directBootAware एट्रिब्यूट को 'सही है' पर सेट करें.

एन्क्रिप्ट (सुरक्षित) करने की सुविधा वाले कॉम्पोनेंट, डिवाइस के रीस्टार्ट होने पर सिस्टम से ACTION_LOCKED_BOOT_COMPLETED ब्रॉडकास्ट मैसेज पाने के लिए रजिस्टर कर सकते हैं. इस समय, डिवाइस का एन्क्रिप्ट (सुरक्षित) किया गया स्टोरेज उपलब्ध होता है. साथ ही, आपका कॉम्पोनेंट उन टास्क को पूरा कर सकता है जिन्हें डायरेक्ट बूट मोड के दौरान चलाना ज़रूरी है. जैसे, शेड्यूल किए गए अलार्म को ट्रिगर करना.

यहां दिया गया कोड स्निपेट, ऐप्लिकेशन मेनिफ़ेस्ट में BroadcastReceiver को एन्क्रिप्शन की जानकारी देने वाले के तौर पर रजिस्टर करने और ACTION_LOCKED_BOOT_COMPLETED के लिए इंटेंट फ़िल्टर जोड़ने का एक उदाहरण है:

<receiver
  android:directBootAware="true" >
  ...
  <intent-filter>
    <action android:name="android.intent.action.LOCKED_BOOT_COMPLETED" />
  </intent-filter>
</receiver>

डिवाइस अनलॉक होने के बाद, सभी कॉम्पोनेंट, डिवाइस के एन्क्रिप्ट किए गए स्टोरेज और क्रेडेंशियल के एन्क्रिप्ट किए गए स्टोरेज, दोनों को ऐक्सेस कर सकते हैं.

डिवाइस के एन्क्रिप्ट किए गए स्टोरेज को ऐक्सेस करना

डिवाइस के एन्क्रिप्ट (सुरक्षित) किए गए स्टोरेज को ऐक्सेस करने के लिए, Context.createDeviceProtectedStorageContext() को कॉल करके दूसरा Context इंस्टेंस बनाएं. इस कॉन्टेक्स्ट का इस्तेमाल करके किए गए सभी स्टोरेज एपीआई कॉल, डिवाइस के एन्क्रिप्ट किए गए स्टोरेज को ऐक्सेस करते हैं. नीचे दिए गए उदाहरण में, डिवाइस के एन्क्रिप्ट किए गए स्टोरेज को ऐक्सेस किया गया है और ऐप्लिकेशन के डेटा की मौजूदा फ़ाइल को खोला गया है:

Kotlin

val directBootContext: Context = appContext.createDeviceProtectedStorageContext()
// Access appDataFilename that lives in device encrypted storage
val inStream: InputStream = directBootContext.openFileInput(appDataFilename)
// Use inStream to read content...

Java

Context directBootContext = appContext.createDeviceProtectedStorageContext();
// Access appDataFilename that lives in device encrypted storage
FileInputStream inStream = directBootContext.openFileInput(appDataFilename);
// Use inStream to read content...

डिवाइस के एन्क्रिप्ट किए गए स्टोरेज का इस्तेमाल सिर्फ़ उस जानकारी के लिए करें जिसे डायरेक्ट बूट मोड के दौरान ऐक्सेस करना ज़रूरी है. डिवाइस के एन्क्रिप्ट किए गए स्टोरेज का इस्तेमाल, एन्क्रिप्ट किए गए सामान्य स्टोरेज के तौर पर न करें. उपयोगकर्ता की निजी जानकारी या एन्क्रिप्ट (सुरक्षित) किए गए ऐसे डेटा के लिए क्रेडेंशियल एन्क्रिप्टेड स्टोरेज का इस्तेमाल करें जिसकी ज़रूरत डायरेक्ट बूट मोड के दौरान नहीं होती.

उपयोगकर्ता के अनलॉक करने की सूचना पाना

डिवाइस को रीस्टार्ट करने के बाद, जब उपयोगकर्ता उसे अनलॉक करता है, तो आपका ऐप्लिकेशन क्रेडेंशियल एन्क्रिप्टेड स्टोरेज को ऐक्सेस करने के लिए स्विच कर सकता है. साथ ही, उपयोगकर्ता के क्रेडेंशियल पर निर्भर रहने वाली सामान्य सिस्टम सेवाओं का इस्तेमाल कर सकता है.

डिवाइस को रीबूट करने के बाद, जब उपयोगकर्ता उसे अनलॉक करे, तब सूचना पाने के लिए, चल रहे कॉम्पोनेंट से BroadcastReceiver को रजिस्टर करें, ताकि अनलॉक करने की सूचना वाले मैसेज सुने जा सकें. जब उपयोगकर्ता बूट होने के बाद डिवाइस को अनलॉक करता है:

  • अगर आपके ऐप्लिकेशन में फ़ोरग्राउंड प्रोसेस हैं जिनके लिए तुरंत सूचना की ज़रूरत है, तो ACTION_USER_UNLOCKED मैसेज सुनें.
  • अगर आपका ऐप्लिकेशन सिर्फ़ बैकग्राउंड में चल रही ऐसी प्रोसेस का इस्तेमाल करता है जो देरी से मिलने वाली सूचना पर कार्रवाई कर सकती हैं, तो ACTION_BOOT_COMPLETED मैसेज सुनें.

अगर उपयोगकर्ता ने डिवाइस को अनलॉक कर दिया है, तो UserManager.isUserUnlocked() को कॉल करके इसका पता लगाया जा सकता है.

मौजूदा डेटा माइग्रेट करना

अगर कोई उपयोगकर्ता डायरेक्ट बूट मोड का इस्तेमाल करने के लिए अपने डिवाइस को अपडेट करता है, तो हो सकता है कि आपके पास ऐसा डेटा हो जिसे डिवाइस के एन्क्रिप्ट किए गए स्टोरेज में माइग्रेट करना पड़े. क्रेडेंशियल एन्क्रिप्टेड स्टोरेज और डिवाइस एन्क्रिप्टेड स्टोरेज के बीच, प्राथमिकता और डेटाबेस डेटा को माइग्रेट करने के लिए, Context.moveSharedPreferencesFrom() और Context.moveDatabaseFrom() का इस्तेमाल करें. इसमें डेस्टिनेशन कॉन्टेक्स्ट को मेथड कॉलर और सोर्स कॉन्टेक्स्ट को आर्ग्युमेंट के तौर पर इस्तेमाल करें.

उपयोगकर्ता की निजी जानकारी, जैसे कि पासवर्ड या अनुमति देने वाले टोकन को क्रेडेंशियल एन्क्रिप्टेड स्टोरेज से डिवाइस एन्क्रिप्टेड स्टोरेज में माइग्रेट न करें. डिवाइस के एन्क्रिप्ट किए गए स्टोरेज में कौनसा डेटा माइग्रेट करना है, यह तय करने के लिए अपनी सूझ-बूझ का इस्तेमाल करें. कुछ मामलों में, आपको एन्क्रिप्ट (सुरक्षित) किए गए दोनों स्टोर में, डेटा के अलग-अलग सेट मैनेज करने पड़ सकते हैं.

एन्क्रिप्ट (सुरक्षित) किए गए डेटा को पहचानने वाले ऐप्लिकेशन की जांच करना

डायरेक्ट बूट मोड चालू करके, एन्क्रिप्ट (सुरक्षित) किए गए डेटा को ऐक्सेस करने वाले ऐप्लिकेशन की जांच करें.

Android के हाल ही के वर्शन पर चलने वाले ज़्यादातर डिवाइसों में, लॉकस्क्रीन क्रेडेंशियल (पिन, पैटर्न या पासवर्ड) सेट होने पर, डायरेक्ट बूट मोड चालू हो जाता है. खास तौर पर, यह उन सभी डिवाइसों पर होता है जो अलग-अलग फ़ाइलों को अलग-अलग तरीकों से एन्क्रिप्ट करने का तरीका का इस्तेमाल करते हैं. यह देखने के लिए कि कोई डिवाइस, अलग-अलग फ़ाइलों को अलग-अलग तरीकों से एन्क्रिप्ट करने का तरीका का इस्तेमाल करता है या नहीं, यह शेल निर्देश चलाएं:

adb shell getprop ro.crypto.type

अगर आउटपुट file है, तो इसका मतलब है कि डिवाइस पर अलग-अलग फ़ाइलों को अलग-अलग तरीकों से एन्क्रिप्ट करने का तरीका चालू है.

जिन डिवाइसों पर डिफ़ॉल्ट रूप से, अलग-अलग फ़ाइलों को अलग-अलग तरीकों से एन्क्रिप्ट करने का तरीका इस्तेमाल नहीं किया जाता है उन पर डायरेक्ट बूट मोड को टेस्ट करने के लिए, अन्य विकल्प हो सकते हैं:

  • पूरी ड्राइव को सुरक्षित रखने की सुविधा (ro.crypto.type=block) का इस्तेमाल करने वाले और Android 7.0 से लेकर Android 12 तक के वर्शन पर काम करने वाले कुछ डिवाइसों को, फ़ाइल-आधारित एन्क्रिप्शन की सुविधा पर स्विच किया जा सकता है. ऐसा करने के दो तरीके हैं:

      चेतावनी: अलग-अलग फ़ाइलों को अलग-अलग तरीकों से एन्क्रिप्ट करने के तरीके में बदलने का कोई भी तरीका, डिवाइस पर मौजूद उपयोगकर्ता के सभी डेटा को मिटा देता है.

    • अगर आपने डिवाइस पर डेवलपर के लिए सेटिंग और टूल को पहले से चालू नहीं किया है, तो सेटिंग > फ़ोन के बारे में जानकारी पर जाएं. इसके बाद, बिल्ड नंबर पर सात बार टैप करें. इसके बाद, सेटिंग > डेवलपर के लिए सेटिंग और टूल पर जाएं और फ़ाइल एन्क्रिप्शन में बदलें को चुनें.
    • इसके अलावा, ये शेल कमांड चलाएं:
      adb reboot-bootloader
      fastboot --wipe-and-use-fbe
      
  • Android 13 या इससे पहले के वर्शन वाले डिवाइसों में, "एम्युलेट किया गया" डायरेक्ट बूट मोड काम करता है. यह मोड, फ़ाइल से जुड़ी अनुमतियों का इस्तेमाल करके, एन्क्रिप्ट यानी सुरक्षित की गई फ़ाइलों के लॉक और अनलॉक होने के असर को सिम्युलेट करता है. डेवलपमेंट के दौरान सिर्फ़ एम्युलेट किए गए मोड का इस्तेमाल करें. इससे डेटा मिट सकता है. एम्युलेट किए गए डायरेक्ट बूट मोड को चालू करने के लिए, डिवाइस पर लॉक पैटर्न सेट करें. लॉक पैटर्न सेट करते समय, सुरक्षित स्टार्ट-अप स्क्रीन के लिए पूछे जाने पर, "नहीं, धन्यवाद" चुनें. इसके बाद, यह शेल कमांड चलाएं:

    adb shell sm set-emulate-fbe true
    

    एम्युलेट किए गए डायरेक्ट बूट मोड को बंद करने के लिए, यह शेल कमांड चलाएं:

    adb shell sm set-emulate-fbe false
    

    इनमें से किसी भी निर्देश को चलाने पर, डिवाइस रीबूट हो जाता है.

डिवाइस से जुड़ी नीति के एन्क्रिप्शन का स्टेटस देखना

डिवाइस एडमिनिस्ट्रेशन ऐप्लिकेशन, DevicePolicyManager.getStorageEncryptionStatus() का इस्तेमाल करके, डिवाइस के एन्क्रिप्शन का मौजूदा स्टेटस देख सकते हैं.

अगर आपका ऐप्लिकेशन, Android 7.0 (एपीआई 24) से कम के एपीआई लेवल को टारगेट करता है, तो getStorageEncryptionStatus(), अलग-अलग फ़ाइलों को अलग-अलग तरीकों से एन्क्रिप्ट करने का तरीका ENCRYPTION_STATUS_ACTIVE दिखाता है. ऐसा तब होता है, जब डिवाइस में पूरी ड्राइव को सुरक्षित रखने की सुविधा या डायरेक्ट बूट के साथ अलग-अलग फ़ाइलों को अलग-अलग तरीकों से एन्क्रिप्ट करने का तरीका की सुविधा का इस्तेमाल किया जा रहा हो. दोनों ही मामलों में, डेटा को हमेशा एन्क्रिप्ट (सुरक्षित) करके सेव किया जाता है.

अगर आपका ऐप्लिकेशन Android 7.0 (एपीआई 24) या इसके बाद के वर्शन को टारगेट करता है, तो डिवाइस के पूरी ड्राइव को सुरक्षित रखने की सुविधा का इस्तेमाल करने पर, getStorageEncryptionStatus(), ENCRYPTION_STATUS_ACTIVE दिखाता है. अगर डिवाइस, डायरेक्ट बूट के साथ अलग-अलग फ़ाइलों को अलग-अलग तरीकों से एन्क्रिप्ट करने का तरीका का इस्तेमाल कर रहा है, तो यह ENCRYPTION_STATUS_ACTIVE_PER_USER दिखाता है.

अगर आपने Android 7.0 को टारगेट करने वाला डिवाइस एडमिन ऐप्लिकेशन बनाया है, तो पक्का करें कि आपने ENCRYPTION_STATUS_ACTIVE और ENCRYPTION_STATUS_ACTIVE_PER_USER, दोनों की जांच की हो. इससे यह पता चलता है कि डिवाइस एन्क्रिप्ट (सुरक्षित) किया गया है या नहीं.

कुछ और कोड सैंपल

DirectBoot सैंपल से, इस पेज पर बताए गए एपीआई के इस्तेमाल के बारे में ज़्यादा जानकारी मिलती है.