Identificatori del dispositivo

Android 10 modifica le autorizzazioni per gli identificatori del dispositivo in modo che tutti gli identificatori del dispositivo siano ora protetti dall'autorizzazione READ_PRIVILEGED_PHONE_STATE . Prima di Android 10, gli identificatori di dispositivo persistenti (IMEI / MEID, IMSI, SIM e build seriale) erano protetti READ_PHONE_STATE runtime READ_PHONE_STATE . L'autorizzazione READ_PRIVILEGED_PHONE_STATE viene concessa solo alle app firmate con la chiave della piattaforma e le app di sistema privilegiate.

Ulteriori informazioni sui nuovi requisiti di autorizzazione sono disponibili nelle pagine Javadoc per TelephonyManager.java e Build.java .

Questa modifica influisce sulle seguenti API:

  • TelephonyManager # getDeviceId
  • TelephonyManager # getImei
  • TelephonyManager # getMeid
  • TelephonyManager # getSimSerialNumber
  • TelephonyManager # getSubscriberId
  • Compila # getSerial

Accesso per le app dell'operatore senza l'autorizzazione READ_PRIVILEGED_PHONE_STATE

Le app READ_PRIVILEGED_PHONE_STATE precaricate che non si qualificano per l'autorizzazione READ_PRIVILEGED_PHONE_STATE possono implementare una delle opzioni nella tabella seguente.

Opzione Desciption Limitazioni
Privilegi dell'operatore UICC La piattaforma Android carica i certificati archiviati nell'UICC e concede l'autorizzazione alle app firmate da questi certificati per effettuare chiamate a metodi speciali. I gestori legacy hanno una popolazione SIM ampia e consolidata, che non è facilmente aggiornabile. Inoltre, i gestori che non dispongono dei diritti di creazione di nuove SIM (ad esempio, MVNO che hanno SIM emesse da MNO) non possono aggiungere o aggiornare certificati sulle SIM.
Whitelist OEM Gli OEM possono utilizzare OP_READ_DEVICE_IDENTIFIER per fornire identificatori di dispositivo alle app OP_READ_DEVICE_IDENTIFIER autorizzate. Questa soluzione non è scalabile per tutti i vettori.
Codice di assegnazione del tipo (TAC) Utilizza il metodo getTypeAllocationCode , introdotto in Android 10, per esporre il TAC che restituisce le informazioni sul produttore e sul modello. Le informazioni nel TAC sono inadeguate per identificare un dispositivo specifico.
MSISDN I vettori possono utilizzare il numero di telefono (MSISDN), disponibile in TelephonyManager con il gruppo di autorizzazioni PHONE , per cercare l'IMEI sui loro sistemi di backend. Ciò richiede investimenti significativi per i vettori. I vettori che mappano le chiavi di rete utilizzando IMSI richiedono risorse tecniche significative per passare a MSISDN .

Tutte le app del gestore possono accedere agli identificatori del dispositivo aggiornando il file CarrierConfig.xml con l'hash del certificato di firma dell'app del gestore. Quando l'app dell'operatore chiama un metodo per leggere le informazioni privilegiate, la piattaforma cerca una corrispondenza dell'hash del certificato di firma dell'app (firma SHA-1 o SHA-256 del certificato) nel file CarrierConfig.xml . Se viene trovata una corrispondenza, vengono restituite le informazioni richieste. Se non viene trovata alcuna corrispondenza, viene restituita un'eccezione di sicurezza.

Per implementare questa soluzione, i vettori DEVONO seguire questi passaggi:

  1. Aggiorna CarrierConfig.xml con l'hash del certificato di firma dell'app del gestore e invia una patch .
  2. Richiedi agli OEM di aggiornare la loro build con QPR1 + (consigliato) OPPURE queste patch di piattaforma richieste e la patch contenente il file CarrierConfig.xml aggiornato dal passaggio 1 sopra.

Implementazione

Aggiorna la tua whitelist di autorizzazioni privilegiate per concedere l'autorizzazione READ_PRIVILEGED_PHONE_STATE alle app privilegiate che richiedono l'accesso agli identificatori del dispositivo.

Per ulteriori informazioni sulla whitelist, fare riferimento a Whitelisting di autorizzazioni privilegiate .

Per richiamare le API interessate, un'app deve soddisfare uno dei seguenti requisiti:

  • Se l'app è un'applicazione privilegiata precaricata, necessita dell'autorizzazione READ_PRIVILEGED_PHONE_STATE dichiarata in AndroidManifest.xml. L'app deve anche autorizzare questa autorizzazione privilegiata.
  • Le app fornite tramite Google Play richiedono privilegi di operatore. Ulteriori informazioni sulla concessione dei privilegi dell'operatore nella pagina Privilegi dell'operatore UICC .
  • READ_PHONE_STATE proprietario del dispositivo o del profilo a cui è stata concessa l'autorizzazione READ_PHONE_STATE .

Un'app che non soddisfa nessuno di questi requisiti ha il seguente comportamento:

  • Se l'app ha come target la pre-Q e non ha l'autorizzazione READ_PHONE_STATE concessa, viene attivata SecurityException . questo è il comportamento pre-Q corrente poiché questa autorizzazione è richiesta per richiamare queste API.
  • Se l'app è destinata alla pre-Q e dispone dell'autorizzazione READ_PHONE_STATE , riceve un valore null per tutte le API di TelephonyManager e Build.UNKNOWN per il metodo Build#getSerial .
  • Se l'app è destinata ad Android 10 o versioni successive e non soddisfa nessuno dei nuovi requisiti, riceve un'eccezione SecurityException.

Validazione e test

La Compatibility Test Suite (CTS) include test per verificare il comportamento di accesso all'identificatore del dispositivo previsto per le app con privilegi di operatore, proprietari di dispositivi e profili e quelle app che si prevede non abbiano accesso agli identificatori del dispositivo.

I seguenti test CTS sono specifici per questa funzione.

cts-tradefed run cts -m CtsCarrierApiTestCases -t
    android.carrierapi.cts.CarrierApiTest

cts-tradefed run cts -m CtsTelephonyTestCases -t
    android.telephony.cts.TelephonyManagerTest

cts-tradefed run cts -m CtsTelephony3TestCases

cts-tradefed run cts -m CtsPermissionTestCases -t
    android.permission.cts.TelephonyManagerPermissionTest

cts-tradefed run cts -m CtsDevicePolicyManagerTestCases -t
    com.android.cts.devicepolicy.DeviceOwnerTest#testDeviceOwnerCanGetDeviceIdentifiers

cts-tradefed run cts -m CtsDevicePolicyManagerTestCases -t
    com.android.cts.devicepolicy.ManagedProfileTest#testProfileOwnerCanGetDeviceIdentifiers

cts-tradefed run cts -m CtsDevicePolicyManagerTestCases -t
    com.android.cts.devicepolicy.ManagedProfileTest#testProfileOwnerCannotGetDeviceIdentifiersWithoutPermission

cts-tradefed run cts -m CtsDevicePolicyManagerTestCases -t
    com.android.cts.devicepolicy.DeviceOwnerTest#testDeviceOwnerCannotGetDeviceIdentifiersWithoutPermission

Domande frequenti

Quante app possono essere CarrierConfig.xml nella whitelist in CarrierConfig.xml per un dato (MCC, MNC)?

Non c'è limite al numero di hash di certificato inclusi nell'array.

Quali parametri CarrierConfig in CarrierConfig.xml devo utilizzare per inserire un'app nella whitelist?

Utilizza il seguente elemento di configurazione di primo livello all'interno del CarrierConfig.xml specifico dalle opzioni AOSP che stai configurando:

<string-array name="carrier_certificate_string_array" num="2">
    <item value="BF02262E5EF59FDD53E57059082F1A7914F284B"/>
    <item value="9F3868A3E1DD19A5311D511A60CF94D975A344B"/>
</string-array>

Esiste un modello CarrierConfig di base che posso utilizzare?

Usa il seguente modello. Questo dovrebbe essere aggiunto alla risorsa pertinente .

<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<carrier_config>
    <string-array name="carrier_certificate_string_array"
num="1">
        <item value="CERTIFICATE_HASH_HERE"/>
    </string-array>
</carrier_config>

La SIM dell'operatore deve essere nel dispositivo per accedere agli identificatori del dispositivo?

Il CarrierConfig.xml utilizzato è determinato in base alla SIM attualmente inserita. Ciò significa che se l'app dell'operatore X tenta di ottenere i privilegi di accesso mentre è inserita la SIM dell'operatore Y, il dispositivo non troverà una corrispondenza per l'hash e restituirà un'eccezione di sicurezza.

Sui dispositivi multi-SIM, l'operatore n. 1 ha privilegi di accesso solo per la SIM n. 1 e viceversa.

In che modo gli operatori convertono il certificato di firma di un'app in un hash?

Per convertire i certificati di firma in un hash prima di aggiungerli a CarrierConfig.xml , eseguire le operazioni seguenti:

  1. Converti la firma del certificato di firma in una matrice di byte utilizzando toByteArray .
  2. Utilizzare MessageDigest per convertire la matrice di byte in un hash di tipo byte [].
  3. Converti l'hash da byte [] in un formato stringa esadecimale. Per un esempio, vedere IccUtils.java .

    List<String> certHashes = new ArrayList<>();
    PackageInfo pInfo; // Carrier app PackageInfo
    MessageDigest md =
    MessageDigest.getInstance("SHA-256");
    for (Signature signature : pInfo.signatures) {
        certHashes.add(bytesToHexString(md.digest(signature.toByteArray()));
    }
    
  4. Se certHashes è un array di dimensione 2 con un valore di 12345 e 54321 , aggiungi quanto segue al file di configurazione del vettore.

    <string-array name="carrier_certificate_string_array" num="2">
        <item value="12345"/>
        <item value="54321"/>
    </string-array>