Comprensione della registrazione

Questo articolo tratta il processo di registrazione, inclusi gli standard di registro, le linee guida sui livelli, le classi, gli scopi e le approssimazioni multistack.

Standard di registro

L'accesso in Android è complesso a causa del mix di standard utilizzati combinati in logcat . Di seguito vengono dettagliate le principali norme utilizzate:

Fonte Esempi Guida al livello dello stack
RFC 5424 (standard syslog ) Kernel Linux, molte applicazioni Unix Kernel, demoni di sistema
android.util.Log Framework Android + registrazione delle applicazioni Framework Android e applicazione di sistema
java.util.logging.Level Accesso generale in Java applicazione non di sistema

Figura 1: standard del livello di registro.

Sebbene ciascuno di questi standard abbia un livello di costruzione simile, varia in termini di granularità. Gli equivalenti approssimativi tra gli standard sono i seguenti:

Livello RFC 5424 Gravità RFC 5424 Descrizione RFC 5424 android.util.Log java.util.logging.Level
0 Emergenza Il sistema è inutilizzabile Log.e / Log.wtf SEVERE
1 Mettere in guardia È necessario agire immediatamente Log.e / Log.wtf SEVERE
2 Critico Condizioni critiche Log.e / Log.wtf SEVERE
3 Errore Condizioni di errore Log.e SEVERE
4 Avvertimento Condizioni di avvertimento Log.w WARNING
5 Avviso Normale ma significativo Log.w WARNING
6 Informazioni Messaggi informativi Log.i INFO
7 Debug Messaggi a livello di debug Log.d CONFIG , FINE
- - Messaggi dettagliati Log.v FINER / FINEST

Figura 2: livelli di registrazione syslog , Android e Java.

Linee guida sul livello di registro

Esistono linee guida esistenti fornite per ciascuno standard di registro. Il livello di log scelto segue lo standard appropriato utilizzato, come l'utilizzo dello standard syslog per lo sviluppo del kernel.

Gli ordini a livello di log, dal meno al più, sono mostrati nelle tre figure seguenti:

ERROR Questi registri vengono sempre conservati.
WARN Questi registri vengono sempre conservati.
INFO Questi registri vengono sempre conservati.
DEBUG Questi registri vengono compilati ma eliminati in fase di esecuzione.
VERBOSE Questi registri non vengono mai compilati in un'applicazione se non durante lo sviluppo.

Figura 3: android.util.Log

CONFIG Livello di messaggio per i messaggi di configurazione statici
FINE Livello del messaggio che fornisce informazioni di traccia
FINER Indica un messaggio di traccia abbastanza dettagliato
FINEST Indica un messaggio di traccia altamente dettagliato
INFO Livello messaggio per messaggi informativi
SEVERE Livello del messaggio che indica un errore grave
WARNING Livello del messaggio che indica un potenziale problema

Figura 4: java.util.Logging.Level .

0 Emergenza Il sistema è inutilizzabile
1 Mettere in guardia È necessario agire immediatamente
2 Critico Condizioni critiche
3 Errore Condizioni di errore
4 Avvertimento Condizioni di avvertimento
5 Avviso Condizioni normali ma significative
6 Informativo Messaggi informativi
7 Debug Messaggi a livello di debug

Figura 5: RFC 5424 - Sezione 6.2.1 .

Registrazione dell'applicazione

La registrazione selettiva viene eseguita con TAG dalla classe android.util.Log utilizzando Log#isLoggable , come mostrato di seguito:

if (Log.isLoggable("FOO_TAG", Log.VERBOSE)) {
 Log.v("FOO_TAG", "Message for logging.");
}

I registri possono essere ottimizzati in fase di esecuzione per fornire un livello selezionato di registrazione come mostrato di seguito:

adb shell setprop log.tag.FOO_TAG VERBOSE

Le proprietà log.tag.* vengono reimpostate al riavvio. Esistono varianti persistenti che rimangono anche dopo i riavvii. Vedi sotto:

adb shell setprop persist.log.tag.FOO_TAG VERBOSE

I controlli Log#isLoggable lasciano tracce di log nel codice dell'applicazione. I flag booleani DEBUG ignorano le tracce di log utilizzando le ottimizzazioni del compilatore impostate su false , come mostrato di seguito:

private final static boolean DEBUG = false;

… If (DEBUG) { Log.v("FOO_TAG", "Extra debug logging."); }

La registrazione può essere rimossa in base all'APK tramite i set di regole ProGuard di R8 in fase di compilazione. L'esempio seguente rimuove tutto ciò che è al di sotto del livello INFO di registrazione per android.util.Log :

# This allows proguard to strip isLoggable() blocks containing only <=INFO log
# code from release builds.
-assumenosideeffects class android.util.Log {
  static *** i(...);
  static *** d(...);
  static *** v(...);
  static *** isLoggable(...);
}
-maximumremovedandroidloglevel 4

Ciò è utile per gestire più tipi di build di applicazioni (ad esempio, build di sviluppo e build di rilascio) in cui si prevede che il codice sottostante sia lo stesso, ma i livelli di log consentiti sono diversi. È necessario impostare e seguire una politica esplicita per le applicazioni (in particolare le applicazioni di sistema) per decidere in che modo i tipi di build e le aspettative di rilascio influiscono sull'output del registro.

Accesso al sistema nel runtime Android (ART)

Sono disponibili diverse classi per le applicazioni e i servizi di sistema:

Classe Scopo
android.telephony.Rlog Registrazione radiofonica
android.util.Log Registrazione generale dell'applicazione
android.util.EventLog Registrazione degli eventi diagnostici dell'integratore di sistema
android.util.Slog Registrazione del framework della piattaforma

Figura 6: classi e scopi del registro di sistema disponibili.

Sebbene android.util.Log e android.util.Slog utilizzino gli stessi standard di livello di log, Slog è una classe @hide utilizzabile solo dalla piattaforma. I livelli EventLog sono mappati alle voci nel file event.logtags in /system/etc/event-log-tags .

Registrazione nativa

La registrazione in C/C++ segue lo standard syslog con syslog (2) corrispondente al syslog del kernel Linux che controlla il buffer printk e syslog (3) corrispondente al logger generale del sistema. Android utilizza la libreria liblog per la registrazione generale del sistema.

liblog fornisce wrapper per i gruppi di sottoblog utilizzando il seguente modulo macro:

[Sublog Buffer ID] LOG [Log Level ID]

RLOGD , ad esempio, corrisponde a [Radio log buffer ID] LOG [Debug Level] . I principali wrapper liblog sono i seguenti:

Classe involucro Funzioni di esempio
log_main.h ALOGV , ALOGW
log_radio.h RLOGD , RLOGE
log_system.h SLOGI , SLOGW

Figura 7: wrapper liblog .

Android dispone di interfacce di livello superiore per la registrazione che sono preferite rispetto all'utilizzo diretto liblog , come mostrato di seguito:

Biblioteca Utilizzo
async_safe Libreria solo per la registrazione da ambienti sicuri con segnale asincrono
libbase Libreria di registrazione che fornisce un'interfaccia di flusso C++ per la registrazione, simile alla registrazione in stile Google (glog). libbase è utilizzabile in entrambi i progetti esterni ed è disponibile nelle applicazioni che utilizzano libbase_ndk .

Figura 8: Librerie di log di livello superiore.

Approssimazioni multistack

A causa delle differenze nella granularità e nell'intento del livello, non esistono corrispondenze chiare o esatte dei diversi standard di registrazione. Ad esempio, i livelli java.util.logging.Level e android.util.Log per i log degli errori non corrispondono 1:1:

java.util.Logging.Level android.util.Log
ACUTO Log.wtf
ACUTO Log.e

Figura 9: livello di errore nella registrazione Java standard rispetto alla registrazione Android.

In casi come questo, utilizzare lo standard individuale per determinare quale livello applicare.

Durante lo sviluppo del sistema con più componenti a livello di stack, seguire la Figura 1 per determinare quale standard utilizzare per componente. Per una guida approssimativa alla messaggistica di livello, seguire la Figura 2.

Sicurezza e privacy

Non registrare informazioni di identificazione personale (PII). Ciò include dettagli come:

  • Indirizzi email
  • Numeri di telefono
  • Nomi

Allo stesso modo, alcuni dettagli sono considerati sensibili anche se non esplicitamente identificabili personalmente.

Ad esempio, sebbene le informazioni sul fuso orario non siano considerate identificabili personalmente, forniscono un'indicazione della posizione approssimativa di un utente.

La politica di registro e i dettagli accettabili devono essere gestiti come parte della revisione della sicurezza e della privacy prima del rilascio.

Registri del dispositivo

L'accesso a tutti i log del dispositivo, incluso l'utilizzo android.permission.READ_LOGS , è limitato:

  • Se un'app in background richiede l'accesso a tutti i registri del dispositivo, la richiesta viene automaticamente negata a meno che l'app:
    • condivide l'UID del sistema.
    • utilizza un processo di sistema nativo ( UID < APP_UID ).
    • utilizza DropBoxManager .
    • accede solo al buffer del registro eventi.
    • utilizza l'API EventLog .
    • utilizza test strumentati.
  • Se un'app in primo piano con READ_LOGS richiede l'accesso ai log del dispositivo, il sistema richiede all'utente di approvare o negare la richiesta di accesso.