Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is there a unique boot session id or count on an android device?

Tags:

java

android

The app I'm writing needs to know if a 'boot session', for want of a better term, has changed but it doesn't need to actually start at boot and I would prefer if possible not to have to use the RECEIVE_BOOT_COMPLETED permission.

So I was wondering if there is any device-wide boot session id or count I can query and store in my db to check against later. I know I can get the time in milliseconds since boot but I don't think that will be useful in this case.

Thanks in advance for any help.

like image 423
mark_w Avatar asked Mar 25 '14 13:03

mark_w


2 Answers

Yes, on API >= 24. You can use the BOOT_COUNT global settings variable. To read this, try a snippet like this:

int boot_count = Settings.Global.getInt(getContext().getContentResolver(),
                                        Settings.Global.BOOT_COUNT);

Pre-API 24, you're stuck catching RECEIVE_BOOT_COMPLETED.

like image 82
George Hilliard Avatar answered Sep 28 '22 05:09

George Hilliard


I use this code to get a unique boot ID on all versions of Android. For Nougat and later, I use Settings.Global.BOOT_COUNT. For versions older than Nougat, I read a unique boot ID from "/proc/sys/kernel/random/boot_id". I haven't had any issues with file access on Android 5 in my testing. Tested on Android 5, 8, 9, and 11 on real devices with a release build of our app.

This does not rely on the system clock, which can jump around or be changed by the user.

Thanks to this answer from @george-hilliard for the Settings.Global.BOOT_COUNT solution.

String bootId = "";

if ( Build.VERSION.SDK_INT >= Build.VERSION_CODES.N ) { // Starting in Android 7 / N(ougat) / API Level 24, we have access to `Settings.Global.BOOT_COUNT`, which increments with every boot.
  bootId = Settings.Global.getString( getApplicationContext().getContentResolver(), Settings.Global.BOOT_COUNT );
}
else { // Before Android 7 / N(ougat) / API Level 24, we need to get the boot id from the /proc/sys/kernel/random/boot_id file. Example boot_id: "691aa77e-aff4-47c2-829e-a34df426c7e7".
 File bootIdFile = new File( "/proc/sys/kernel/random/boot_id" );

  if ( bootIdFile.exists() ) {
    FileInputStream inputStream = null;

    try {
      inputStream           = new FileInputStream( bootIdFile );
      BufferedReader reader = new BufferedReader( new InputStreamReader( inputStream ) );
      bootId                = reader.readLine().trim(); // Read first line of file to get the boot id and remove any leading and trailing spaces.
    }
    catch ( FileNotFoundException error ) {
      error.printStackTrace();
    }
    catch ( IOException error ) {
      error.printStackTrace();
    }
    finally {
      if ( inputStream != null ) try { inputStream.close(); } catch (IOException error ) { error.printStackTrace();; }
    }
  }
}

if ( bootId == "" ) {
  Log.e( "UniqueTag", "Could not retrieve boot ID. Build.VERSION.SDK_INT: " + Build.VERSION.SDK_INT );
}
like image 43
Jarod Legault Avatar answered Sep 28 '22 05:09

Jarod Legault