Be more comprehensive about boot time RTC check

If we detect that the RTC is uninitialized at boot time, we advance
to the nearest safe estimated time that we can determine.  We can't
necessarily touch read/write filesystems at this point, so we have
been using the timestamp of the root filesystem.  Unfortunately, on
retail devices that timestamp is often artificial, and quite far in
the past by today's standards (e.g. some time in 2009).

We now consult a variety of milestones to get a better estimate for
the latest possible "the current date cannot be earlier than this"
reference point:  the root filesystem timestamp, the Build.TIME
system variable, and the [ro.build.date.utc] system property if
available.  The latter two, in particular, are typically within
at most two years of the current real time/date, rather than the
eight or nine years of offset that we see with the root filesystem
timestamp.

Test: manually boot with system time forced to the 0 epoch
Test: CTS
Bug: 65354678
Bug: 63711349
Change-Id: I36bbe6dfebba79ad83ce536917d6893427a026dd
diff --git a/services/core/java/com/android/server/AlarmManagerService.java b/services/core/java/com/android/server/AlarmManagerService.java
index 854c03f..08034f7 100644
--- a/services/core/java/com/android/server/AlarmManagerService.java
+++ b/services/core/java/com/android/server/AlarmManagerService.java
@@ -48,6 +48,7 @@
 import android.database.ContentObserver;
 import android.net.Uri;
 import android.os.Binder;
+import android.os.Build;
 import android.os.Bundle;
 import android.os.Environment;
 import android.os.Handler;
@@ -1306,8 +1307,12 @@
             // because kernel doesn't keep this after reboot
             setTimeZoneImpl(SystemProperties.get(TIMEZONE_PROPERTY));
 
-            // Also sure that we're booting with a halfway sensible current time
-            final long systemBuildTime = Environment.getRootDirectory().lastModified();
+            // Ensure that we're booting with a halfway sensible current time.  Use the
+            // most recent of Build.TIME, the root file system's timestamp, and the
+            // value of the ro.build.date.utc system property (which is in seconds).
+            final long systemBuildTime =  Long.max(
+                    1000L * SystemProperties.getLong("ro.build.date.utc", -1L),
+                    Long.max(Environment.getRootDirectory().lastModified(), Build.TIME));
             if (mInjector.getCurrentTimeMillis() < systemBuildTime) {
                 Slog.i(TAG, "Current time only " + mInjector.getCurrentTimeMillis()
                         + ", advancing to build time " + systemBuildTime);