Loading core/java/android/app/time/ExternalTimeSuggestion.java +31 −33 Original line number Diff line number Diff line Loading @@ -19,15 +19,14 @@ package android.app.time; import android.annotation.CurrentTimeMillisLong; import android.annotation.ElapsedRealtimeLong; import android.annotation.NonNull; import android.annotation.Nullable; import android.annotation.SystemApi; import android.app.timedetector.TimeSuggestionHelper; import android.os.Parcel; import android.os.Parcelable; import android.os.ShellCommand; import android.os.TimestampedValue; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.io.PrintWriter; import java.util.List; import java.util.Objects; Loading Loading @@ -75,7 +74,9 @@ public final class ExternalTimeSuggestion implements Parcelable { public static final @NonNull Creator<ExternalTimeSuggestion> CREATOR = new Creator<ExternalTimeSuggestion>() { public ExternalTimeSuggestion createFromParcel(Parcel in) { return ExternalTimeSuggestion.createFromParcel(in); TimeSuggestionHelper helper = TimeSuggestionHelper.handleCreateFromParcel( ExternalTimeSuggestion.class, in); return new ExternalTimeSuggestion(helper); } public ExternalTimeSuggestion[] newArray(int size) { Loading @@ -83,10 +84,7 @@ public final class ExternalTimeSuggestion implements Parcelable { } }; @NonNull private final TimestampedValue<Long> mUnixEpochTime; @Nullable private ArrayList<String> mDebugInfo; @NonNull private final TimeSuggestionHelper mTimeSuggestionHelper; /** * Creates a time suggestion cross-referenced to the elapsed realtime clock. See {@link Loading @@ -98,17 +96,12 @@ public final class ExternalTimeSuggestion implements Parcelable { */ public ExternalTimeSuggestion(@ElapsedRealtimeLong long elapsedRealtimeMillis, @CurrentTimeMillisLong long suggestionMillis) { mUnixEpochTime = new TimestampedValue(elapsedRealtimeMillis, suggestionMillis); mTimeSuggestionHelper = new TimeSuggestionHelper(ExternalTimeSuggestion.class, new TimestampedValue<>(elapsedRealtimeMillis, suggestionMillis)); } private static ExternalTimeSuggestion createFromParcel(Parcel in) { TimestampedValue<Long> utcTime = in.readParcelable(null /* classLoader */); ExternalTimeSuggestion suggestion = new ExternalTimeSuggestion(utcTime.getReferenceTimeMillis(), utcTime.getValue()); @SuppressWarnings("unchecked") ArrayList<String> debugInfo = (ArrayList<String>) in.readArrayList(null /* classLoader */); suggestion.mDebugInfo = debugInfo; return suggestion; private ExternalTimeSuggestion(@NonNull TimeSuggestionHelper helper) { mTimeSuggestionHelper = Objects.requireNonNull(helper); } @Override Loading @@ -118,8 +111,7 @@ public final class ExternalTimeSuggestion implements Parcelable { @Override public void writeToParcel(@NonNull Parcel dest, int flags) { dest.writeParcelable(mUnixEpochTime, 0); dest.writeList(mDebugInfo); mTimeSuggestionHelper.handleWriteToParcel(dest, flags); } /** Loading @@ -127,7 +119,7 @@ public final class ExternalTimeSuggestion implements Parcelable { */ @NonNull public TimestampedValue<Long> getUnixEpochTime() { return mUnixEpochTime; return mTimeSuggestionHelper.getUnixEpochTime(); } /** Loading @@ -135,9 +127,7 @@ public final class ExternalTimeSuggestion implements Parcelable { */ @NonNull public List<String> getDebugInfo() { return mDebugInfo == null ? Collections.emptyList() : Collections.unmodifiableList(mDebugInfo); return mTimeSuggestionHelper.getDebugInfo(); } /** Loading @@ -146,10 +136,7 @@ public final class ExternalTimeSuggestion implements Parcelable { * #equals(Object)} and {@link #hashCode()}. */ public void addDebugInfo(@NonNull String... debugInfos) { if (mDebugInfo == null) { mDebugInfo = new ArrayList<>(); } mDebugInfo.addAll(Arrays.asList(debugInfos)); mTimeSuggestionHelper.addDebugInfo(debugInfos); } @Override Loading @@ -161,18 +148,29 @@ public final class ExternalTimeSuggestion implements Parcelable { return false; } ExternalTimeSuggestion that = (ExternalTimeSuggestion) o; return Objects.equals(mUnixEpochTime, that.mUnixEpochTime); return mTimeSuggestionHelper.handleEquals(that.mTimeSuggestionHelper); } @Override public int hashCode() { return Objects.hash(mUnixEpochTime); return mTimeSuggestionHelper.hashCode(); } @Override public String toString() { return "ExternalTimeSuggestion{" + "mUnixEpochTime=" + mUnixEpochTime + ", mDebugInfo=" + mDebugInfo + '}'; return mTimeSuggestionHelper.handleToString(); } /** @hide */ public static ExternalTimeSuggestion parseCommandLineArg(@NonNull ShellCommand cmd) throws IllegalArgumentException { return new ExternalTimeSuggestion( TimeSuggestionHelper.handleParseCommandLineArg(ExternalTimeSuggestion.class, cmd)); } /** @hide */ public static void printCommandLineOpts(PrintWriter pw) { TimeSuggestionHelper.handlePrintCommandLineOpts( pw, "External", ExternalTimeSuggestion.class); } } core/java/android/app/timedetector/GnssTimeSuggestion.java +30 −41 Original line number Diff line number Diff line Loading @@ -17,30 +17,19 @@ package android.app.timedetector; import android.annotation.NonNull; import android.annotation.Nullable; import android.os.Parcel; import android.os.Parcelable; import android.os.ShellCommand; import android.os.TimestampedValue; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.io.PrintWriter; import java.util.List; import java.util.Objects; /** * A time signal from a GNSS source. * * <p>{@code unixEpochTime} is the suggested time. The {@code unixEpochTime.value} is the number of * milliseconds elapsed since 1/1/1970 00:00:00 UTC according to the Unix time system. The {@code * unixEpochTime.referenceTimeMillis} is the value of the elapsed realtime clock when the {@code * unixEpochTime.value} was established. Note that the elapsed realtime clock is considered accurate * but it is volatile, so time suggestions cannot be persisted across device resets. * * <p>{@code debugInfo} contains debugging metadata associated with the suggestion. This is used to * record why the suggestion exists and how it was entered. This information exists only to aid in * debugging and therefore is used by {@link #toString()}, but it is not for use in detection * logic and is not considered in {@link #hashCode()} or {@link #equals(Object)}. * <p>See {@link TimeSuggestionHelper} for property information. * * @hide */ Loading @@ -49,7 +38,9 @@ public final class GnssTimeSuggestion implements Parcelable { public static final @NonNull Creator<GnssTimeSuggestion> CREATOR = new Creator<GnssTimeSuggestion>() { public GnssTimeSuggestion createFromParcel(Parcel in) { return GnssTimeSuggestion.createFromParcel(in); TimeSuggestionHelper helper = TimeSuggestionHelper.handleCreateFromParcel( GnssTimeSuggestion.class, in); return new GnssTimeSuggestion(helper); } public GnssTimeSuggestion[] newArray(int size) { Loading @@ -57,21 +48,14 @@ public final class GnssTimeSuggestion implements Parcelable { } }; @NonNull private final TimestampedValue<Long> mUnixEpochTime; @Nullable private ArrayList<String> mDebugInfo; @NonNull private final TimeSuggestionHelper mTimeSuggestionHelper; public GnssTimeSuggestion(@NonNull TimestampedValue<Long> unixEpochTime) { mUnixEpochTime = Objects.requireNonNull(unixEpochTime); Objects.requireNonNull(unixEpochTime.getValue()); mTimeSuggestionHelper = new TimeSuggestionHelper(GnssTimeSuggestion.class, unixEpochTime); } private static GnssTimeSuggestion createFromParcel(Parcel in) { TimestampedValue<Long> unixEpochTime = in.readParcelable(null /* classLoader */); GnssTimeSuggestion suggestion = new GnssTimeSuggestion(unixEpochTime); @SuppressWarnings("unchecked") ArrayList<String> debugInfo = (ArrayList<String>) in.readArrayList(null /* classLoader */); suggestion.mDebugInfo = debugInfo; return suggestion; private GnssTimeSuggestion(@NonNull TimeSuggestionHelper helper) { mTimeSuggestionHelper = Objects.requireNonNull(helper); } @Override Loading @@ -81,19 +65,17 @@ public final class GnssTimeSuggestion implements Parcelable { @Override public void writeToParcel(@NonNull Parcel dest, int flags) { dest.writeParcelable(mUnixEpochTime, 0); dest.writeList(mDebugInfo); mTimeSuggestionHelper.handleWriteToParcel(dest, flags); } @NonNull public TimestampedValue<Long> getUnixEpochTime() { return mUnixEpochTime; return mTimeSuggestionHelper.getUnixEpochTime(); } @NonNull public List<String> getDebugInfo() { return mDebugInfo == null ? Collections.emptyList() : Collections.unmodifiableList(mDebugInfo); return mTimeSuggestionHelper.getDebugInfo(); } /** Loading @@ -102,10 +84,7 @@ public final class GnssTimeSuggestion implements Parcelable { * {@link #equals(Object)} and {@link #hashCode()}. */ public void addDebugInfo(String... debugInfos) { if (mDebugInfo == null) { mDebugInfo = new ArrayList<>(); } mDebugInfo.addAll(Arrays.asList(debugInfos)); mTimeSuggestionHelper.addDebugInfo(debugInfos); } @Override Loading @@ -117,19 +96,29 @@ public final class GnssTimeSuggestion implements Parcelable { return false; } GnssTimeSuggestion that = (GnssTimeSuggestion) o; return Objects.equals(mUnixEpochTime, that.mUnixEpochTime); return mTimeSuggestionHelper.handleEquals(that.mTimeSuggestionHelper); } @Override public int hashCode() { return Objects.hash(mUnixEpochTime); return mTimeSuggestionHelper.hashCode(); } @Override public String toString() { return "GnssTimeSuggestion{" + "mUnixEpochTime=" + mUnixEpochTime + ", mDebugInfo=" + mDebugInfo + '}'; return mTimeSuggestionHelper.handleToString(); } /** Parses command line args to create a {@link GnssTimeSuggestion}. */ public static GnssTimeSuggestion parseCommandLineArg(@NonNull ShellCommand cmd) throws IllegalArgumentException { TimeSuggestionHelper suggestionHelper = TimeSuggestionHelper.handleParseCommandLineArg(GnssTimeSuggestion.class, cmd); return new GnssTimeSuggestion(suggestionHelper); } /** Prints the command line args needed to create a {@link GnssTimeSuggestion}. */ public static void printCommandLineOpts(PrintWriter pw) { TimeSuggestionHelper.handlePrintCommandLineOpts(pw, "GNSS", GnssTimeSuggestion.class); } } core/java/android/app/timedetector/ManualTimeSuggestion.java +29 −40 Original line number Diff line number Diff line Loading @@ -20,27 +20,17 @@ import android.annotation.NonNull; import android.annotation.Nullable; import android.os.Parcel; import android.os.Parcelable; import android.os.ShellCommand; import android.os.TimestampedValue; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.io.PrintWriter; import java.util.List; import java.util.Objects; /** * A time signal from a manual (user provided) source. * * <p>{@code unixEpochTime} is the suggested time. The {@code unixEpochTime.value} is the number of * milliseconds elapsed since 1/1/1970 00:00:00 UTC. The {@code unixEpochTime.referenceTimeMillis} * is the value of the elapsed realtime clock when the {@code unixEpochTime.value} was established. * Note that the elapsed realtime clock is considered accurate but it is volatile, so time * suggestions cannot be persisted across device resets. * * <p>{@code debugInfo} contains debugging metadata associated with the suggestion. This is used to * record why the suggestion exists and how it was entered. This information exists only to aid in * debugging and therefore is used by {@link #toString()}, but it is not for use in detection * logic and is not considered in {@link #hashCode()} or {@link #equals(Object)}. * <p>See {@link TimeSuggestionHelper} for property information. * * @hide */ Loading @@ -49,7 +39,9 @@ public final class ManualTimeSuggestion implements Parcelable { public static final @NonNull Creator<ManualTimeSuggestion> CREATOR = new Creator<ManualTimeSuggestion>() { public ManualTimeSuggestion createFromParcel(Parcel in) { return ManualTimeSuggestion.createFromParcel(in); TimeSuggestionHelper helper = TimeSuggestionHelper.handleCreateFromParcel( ManualTimeSuggestion.class, in); return new ManualTimeSuggestion(helper); } public ManualTimeSuggestion[] newArray(int size) { Loading @@ -57,21 +49,14 @@ public final class ManualTimeSuggestion implements Parcelable { } }; @NonNull private final TimestampedValue<Long> mUnixEpochTime; @Nullable private ArrayList<String> mDebugInfo; @NonNull private final TimeSuggestionHelper mTimeSuggestionHelper; public ManualTimeSuggestion(@NonNull TimestampedValue<Long> unixEpochTime) { mUnixEpochTime = Objects.requireNonNull(unixEpochTime); Objects.requireNonNull(unixEpochTime.getValue()); mTimeSuggestionHelper = new TimeSuggestionHelper(ManualTimeSuggestion.class, unixEpochTime); } private static ManualTimeSuggestion createFromParcel(Parcel in) { TimestampedValue<Long> unixEpochTime = in.readParcelable(null /* classLoader */); ManualTimeSuggestion suggestion = new ManualTimeSuggestion(unixEpochTime); @SuppressWarnings("unchecked") ArrayList<String> debugInfo = (ArrayList<String>) in.readArrayList(null /* classLoader */); suggestion.mDebugInfo = debugInfo; return suggestion; private ManualTimeSuggestion(@NonNull TimeSuggestionHelper helper) { mTimeSuggestionHelper = Objects.requireNonNull(helper); } @Override Loading @@ -81,19 +66,17 @@ public final class ManualTimeSuggestion implements Parcelable { @Override public void writeToParcel(@NonNull Parcel dest, int flags) { dest.writeParcelable(mUnixEpochTime, 0); dest.writeList(mDebugInfo); mTimeSuggestionHelper.handleWriteToParcel(dest, flags); } @NonNull public TimestampedValue<Long> getUnixEpochTime() { return mUnixEpochTime; return mTimeSuggestionHelper.getUnixEpochTime(); } @NonNull public List<String> getDebugInfo() { return mDebugInfo == null ? Collections.emptyList() : Collections.unmodifiableList(mDebugInfo); return mTimeSuggestionHelper.getDebugInfo(); } /** Loading @@ -102,10 +85,7 @@ public final class ManualTimeSuggestion implements Parcelable { * {@link #equals(Object)} and {@link #hashCode()}. */ public void addDebugInfo(String... debugInfos) { if (mDebugInfo == null) { mDebugInfo = new ArrayList<>(); } mDebugInfo.addAll(Arrays.asList(debugInfos)); mTimeSuggestionHelper.addDebugInfo(debugInfos); } @Override Loading @@ -117,19 +97,28 @@ public final class ManualTimeSuggestion implements Parcelable { return false; } ManualTimeSuggestion that = (ManualTimeSuggestion) o; return Objects.equals(mUnixEpochTime, that.mUnixEpochTime); return mTimeSuggestionHelper.handleEquals(that.mTimeSuggestionHelper); } @Override public int hashCode() { return Objects.hash(mUnixEpochTime); return mTimeSuggestionHelper.hashCode(); } @Override public String toString() { return "ManualTimeSuggestion{" + "mUnixEpochTime=" + mUnixEpochTime + ", mDebugInfo=" + mDebugInfo + '}'; return mTimeSuggestionHelper.handleToString(); } /** @hide */ public static ManualTimeSuggestion parseCommandLineArg(@NonNull ShellCommand cmd) throws IllegalArgumentException { return new ManualTimeSuggestion( TimeSuggestionHelper.handleParseCommandLineArg(ManualTimeSuggestion.class, cmd)); } /** @hide */ public static void printCommandLineOpts(PrintWriter pw) { TimeSuggestionHelper.handlePrintCommandLineOpts(pw, "Manual", ManualTimeSuggestion.class); } } core/java/android/app/timedetector/NetworkTimeSuggestion.java +33 −45 Original line number Diff line number Diff line Loading @@ -17,31 +17,19 @@ package android.app.timedetector; import android.annotation.NonNull; import android.annotation.Nullable; import android.os.Parcel; import android.os.Parcelable; import android.os.ShellCommand; import android.os.TimestampedValue; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.io.PrintWriter; import java.util.List; import java.util.Objects; /** * A time signal from a network time source like NTP. * * <p>{@code unixEpochTime} contains the suggested time. The {@code unixEpochTime.value} is the * number of milliseconds elapsed since 1/1/1970 00:00:00 UTC according to the Unix time system. * The {@code unixEpochTime.referenceTimeMillis} is the value of the elapsed realtime clock when * the {@code unixEpochTime.value} was established. Note that the elapsed realtime clock is * considered accurate but it is volatile, so time suggestions cannot be persisted across device * resets. * * <p>{@code debugInfo} contains debugging metadata associated with the suggestion. This is used to * record why the suggestion exists and how it was determined. This information exists only to aid * in debugging and therefore is used by {@link #toString()}, but it is not for use in detection * logic and is not considered in {@link #hashCode()} or {@link #equals(Object)}. * <p>See {@link TimeSuggestionHelper} for property information. * * @hide */ Loading @@ -50,7 +38,9 @@ public final class NetworkTimeSuggestion implements Parcelable { public static final @NonNull Creator<NetworkTimeSuggestion> CREATOR = new Creator<NetworkTimeSuggestion>() { public NetworkTimeSuggestion createFromParcel(Parcel in) { return NetworkTimeSuggestion.createFromParcel(in); TimeSuggestionHelper helper = TimeSuggestionHelper.handleCreateFromParcel( NetworkTimeSuggestion.class, in); return new NetworkTimeSuggestion(helper); } public NetworkTimeSuggestion[] newArray(int size) { Loading @@ -58,21 +48,15 @@ public final class NetworkTimeSuggestion implements Parcelable { } }; @NonNull private final TimestampedValue<Long> mUnixEpochTime; @Nullable private ArrayList<String> mDebugInfo; @NonNull private final TimeSuggestionHelper mTimeSuggestionHelper; public NetworkTimeSuggestion(@NonNull TimestampedValue<Long> unixEpochTime) { mUnixEpochTime = Objects.requireNonNull(unixEpochTime); Objects.requireNonNull(unixEpochTime.getValue()); mTimeSuggestionHelper = new TimeSuggestionHelper( NetworkTimeSuggestion.class, unixEpochTime); } private static NetworkTimeSuggestion createFromParcel(Parcel in) { TimestampedValue<Long> unixEpochTime = in.readParcelable(null /* classLoader */); NetworkTimeSuggestion suggestion = new NetworkTimeSuggestion(unixEpochTime); @SuppressWarnings("unchecked") ArrayList<String> debugInfo = (ArrayList<String>) in.readArrayList(null /* classLoader */); suggestion.mDebugInfo = debugInfo; return suggestion; private NetworkTimeSuggestion(@NonNull TimeSuggestionHelper helper) { mTimeSuggestionHelper = Objects.requireNonNull(helper); } @Override Loading @@ -82,35 +66,30 @@ public final class NetworkTimeSuggestion implements Parcelable { @Override public void writeToParcel(@NonNull Parcel dest, int flags) { dest.writeParcelable(mUnixEpochTime, 0); dest.writeList(mDebugInfo); mTimeSuggestionHelper.handleWriteToParcel(dest, flags); } @NonNull public TimestampedValue<Long> getUnixEpochTime() { return mUnixEpochTime; return mTimeSuggestionHelper.getUnixEpochTime(); } @NonNull public List<String> getDebugInfo() { return mDebugInfo == null ? Collections.emptyList() : Collections.unmodifiableList(mDebugInfo); return mTimeSuggestionHelper.getDebugInfo(); } /** * Associates information with the instance that can be useful for debugging / logging. The * information is present in {@link #toString()} but is not considered for * {@link #equals(Object)} and {@link #hashCode()}. * information is present in {@link #toString()} but is not considered for {@link * #equals(Object)} and {@link #hashCode()}. */ public void addDebugInfo(String... debugInfos) { if (mDebugInfo == null) { mDebugInfo = new ArrayList<>(); } mDebugInfo.addAll(Arrays.asList(debugInfos)); mTimeSuggestionHelper.addDebugInfo(debugInfos); } @Override public boolean equals(@Nullable Object o) { public boolean equals(Object o) { if (this == o) { return true; } Loading @@ -118,19 +97,28 @@ public final class NetworkTimeSuggestion implements Parcelable { return false; } NetworkTimeSuggestion that = (NetworkTimeSuggestion) o; return Objects.equals(mUnixEpochTime, that.mUnixEpochTime); return mTimeSuggestionHelper.handleEquals(that.mTimeSuggestionHelper); } @Override public int hashCode() { return Objects.hash(mUnixEpochTime); return mTimeSuggestionHelper.hashCode(); } @Override public String toString() { return "NetworkTimeSuggestion{" + "mUnixEpochTime=" + mUnixEpochTime + ", mDebugInfo=" + mDebugInfo + '}'; return mTimeSuggestionHelper.handleToString(); } /** @hide */ public static NetworkTimeSuggestion parseCommandLineArg(@NonNull ShellCommand cmd) throws IllegalArgumentException { return new NetworkTimeSuggestion( TimeSuggestionHelper.handleParseCommandLineArg(NetworkTimeSuggestion.class, cmd)); } /** @hide */ public static void printCommandLineOpts(PrintWriter pw) { TimeSuggestionHelper.handlePrintCommandLineOpts(pw, "Network", NetworkTimeSuggestion.class); } } core/java/android/app/timedetector/TelephonyTimeSuggestion.java +57 −0 Original line number Diff line number Diff line Loading @@ -20,8 +20,10 @@ import android.annotation.NonNull; import android.annotation.Nullable; import android.os.Parcel; import android.os.Parcelable; import android.os.ShellCommand; import android.os.TimestampedValue; import java.io.PrintWriter; import java.util.ArrayList; import java.util.Collections; import java.util.List; Loading Loading @@ -88,6 +90,61 @@ public final class TelephonyTimeSuggestion implements Parcelable { return suggestion; } /** @hide */ public static TelephonyTimeSuggestion parseCommandLineArg(@NonNull ShellCommand cmd) throws IllegalArgumentException { Integer slotIndex = null; Long referenceTimeMillis = null; Long unixEpochTimeMillis = null; String opt; while ((opt = cmd.getNextArg()) != null) { switch (opt) { case "--slot_index": { slotIndex = Integer.parseInt(cmd.getNextArgRequired()); break; } case "--reference_time": { referenceTimeMillis = Long.parseLong(cmd.getNextArgRequired()); break; } case "--unix_epoch_time": { unixEpochTimeMillis = Long.parseLong(cmd.getNextArgRequired()); break; } default: { throw new IllegalArgumentException("Unknown option: " + opt); } } } if (slotIndex == null) { throw new IllegalArgumentException("No slotIndex specified."); } if (referenceTimeMillis == null) { throw new IllegalArgumentException("No referenceTimeMillis specified."); } if (unixEpochTimeMillis == null) { throw new IllegalArgumentException("No unixEpochTimeMillis specified."); } TimestampedValue<Long> timeSignal = new TimestampedValue<>(referenceTimeMillis, unixEpochTimeMillis); Builder builder = new Builder(slotIndex) .setUnixEpochTime(timeSignal) .addDebugInfo("Command line injection"); return builder.build(); } /** @hide */ public static void printCommandLineOpts(PrintWriter pw) { pw.println("Telephony suggestion options:"); pw.println(" --slot_index <number>"); pw.println(" --reference_time <elapsed realtime millis>"); pw.println(" --unix_epoch_time <Unix epoch time millis>"); pw.println(); pw.println("See " + TelephonyTimeSuggestion.class.getName() + " for more information"); } @Override public int describeContents() { return 0; Loading Loading
core/java/android/app/time/ExternalTimeSuggestion.java +31 −33 Original line number Diff line number Diff line Loading @@ -19,15 +19,14 @@ package android.app.time; import android.annotation.CurrentTimeMillisLong; import android.annotation.ElapsedRealtimeLong; import android.annotation.NonNull; import android.annotation.Nullable; import android.annotation.SystemApi; import android.app.timedetector.TimeSuggestionHelper; import android.os.Parcel; import android.os.Parcelable; import android.os.ShellCommand; import android.os.TimestampedValue; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.io.PrintWriter; import java.util.List; import java.util.Objects; Loading Loading @@ -75,7 +74,9 @@ public final class ExternalTimeSuggestion implements Parcelable { public static final @NonNull Creator<ExternalTimeSuggestion> CREATOR = new Creator<ExternalTimeSuggestion>() { public ExternalTimeSuggestion createFromParcel(Parcel in) { return ExternalTimeSuggestion.createFromParcel(in); TimeSuggestionHelper helper = TimeSuggestionHelper.handleCreateFromParcel( ExternalTimeSuggestion.class, in); return new ExternalTimeSuggestion(helper); } public ExternalTimeSuggestion[] newArray(int size) { Loading @@ -83,10 +84,7 @@ public final class ExternalTimeSuggestion implements Parcelable { } }; @NonNull private final TimestampedValue<Long> mUnixEpochTime; @Nullable private ArrayList<String> mDebugInfo; @NonNull private final TimeSuggestionHelper mTimeSuggestionHelper; /** * Creates a time suggestion cross-referenced to the elapsed realtime clock. See {@link Loading @@ -98,17 +96,12 @@ public final class ExternalTimeSuggestion implements Parcelable { */ public ExternalTimeSuggestion(@ElapsedRealtimeLong long elapsedRealtimeMillis, @CurrentTimeMillisLong long suggestionMillis) { mUnixEpochTime = new TimestampedValue(elapsedRealtimeMillis, suggestionMillis); mTimeSuggestionHelper = new TimeSuggestionHelper(ExternalTimeSuggestion.class, new TimestampedValue<>(elapsedRealtimeMillis, suggestionMillis)); } private static ExternalTimeSuggestion createFromParcel(Parcel in) { TimestampedValue<Long> utcTime = in.readParcelable(null /* classLoader */); ExternalTimeSuggestion suggestion = new ExternalTimeSuggestion(utcTime.getReferenceTimeMillis(), utcTime.getValue()); @SuppressWarnings("unchecked") ArrayList<String> debugInfo = (ArrayList<String>) in.readArrayList(null /* classLoader */); suggestion.mDebugInfo = debugInfo; return suggestion; private ExternalTimeSuggestion(@NonNull TimeSuggestionHelper helper) { mTimeSuggestionHelper = Objects.requireNonNull(helper); } @Override Loading @@ -118,8 +111,7 @@ public final class ExternalTimeSuggestion implements Parcelable { @Override public void writeToParcel(@NonNull Parcel dest, int flags) { dest.writeParcelable(mUnixEpochTime, 0); dest.writeList(mDebugInfo); mTimeSuggestionHelper.handleWriteToParcel(dest, flags); } /** Loading @@ -127,7 +119,7 @@ public final class ExternalTimeSuggestion implements Parcelable { */ @NonNull public TimestampedValue<Long> getUnixEpochTime() { return mUnixEpochTime; return mTimeSuggestionHelper.getUnixEpochTime(); } /** Loading @@ -135,9 +127,7 @@ public final class ExternalTimeSuggestion implements Parcelable { */ @NonNull public List<String> getDebugInfo() { return mDebugInfo == null ? Collections.emptyList() : Collections.unmodifiableList(mDebugInfo); return mTimeSuggestionHelper.getDebugInfo(); } /** Loading @@ -146,10 +136,7 @@ public final class ExternalTimeSuggestion implements Parcelable { * #equals(Object)} and {@link #hashCode()}. */ public void addDebugInfo(@NonNull String... debugInfos) { if (mDebugInfo == null) { mDebugInfo = new ArrayList<>(); } mDebugInfo.addAll(Arrays.asList(debugInfos)); mTimeSuggestionHelper.addDebugInfo(debugInfos); } @Override Loading @@ -161,18 +148,29 @@ public final class ExternalTimeSuggestion implements Parcelable { return false; } ExternalTimeSuggestion that = (ExternalTimeSuggestion) o; return Objects.equals(mUnixEpochTime, that.mUnixEpochTime); return mTimeSuggestionHelper.handleEquals(that.mTimeSuggestionHelper); } @Override public int hashCode() { return Objects.hash(mUnixEpochTime); return mTimeSuggestionHelper.hashCode(); } @Override public String toString() { return "ExternalTimeSuggestion{" + "mUnixEpochTime=" + mUnixEpochTime + ", mDebugInfo=" + mDebugInfo + '}'; return mTimeSuggestionHelper.handleToString(); } /** @hide */ public static ExternalTimeSuggestion parseCommandLineArg(@NonNull ShellCommand cmd) throws IllegalArgumentException { return new ExternalTimeSuggestion( TimeSuggestionHelper.handleParseCommandLineArg(ExternalTimeSuggestion.class, cmd)); } /** @hide */ public static void printCommandLineOpts(PrintWriter pw) { TimeSuggestionHelper.handlePrintCommandLineOpts( pw, "External", ExternalTimeSuggestion.class); } }
core/java/android/app/timedetector/GnssTimeSuggestion.java +30 −41 Original line number Diff line number Diff line Loading @@ -17,30 +17,19 @@ package android.app.timedetector; import android.annotation.NonNull; import android.annotation.Nullable; import android.os.Parcel; import android.os.Parcelable; import android.os.ShellCommand; import android.os.TimestampedValue; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.io.PrintWriter; import java.util.List; import java.util.Objects; /** * A time signal from a GNSS source. * * <p>{@code unixEpochTime} is the suggested time. The {@code unixEpochTime.value} is the number of * milliseconds elapsed since 1/1/1970 00:00:00 UTC according to the Unix time system. The {@code * unixEpochTime.referenceTimeMillis} is the value of the elapsed realtime clock when the {@code * unixEpochTime.value} was established. Note that the elapsed realtime clock is considered accurate * but it is volatile, so time suggestions cannot be persisted across device resets. * * <p>{@code debugInfo} contains debugging metadata associated with the suggestion. This is used to * record why the suggestion exists and how it was entered. This information exists only to aid in * debugging and therefore is used by {@link #toString()}, but it is not for use in detection * logic and is not considered in {@link #hashCode()} or {@link #equals(Object)}. * <p>See {@link TimeSuggestionHelper} for property information. * * @hide */ Loading @@ -49,7 +38,9 @@ public final class GnssTimeSuggestion implements Parcelable { public static final @NonNull Creator<GnssTimeSuggestion> CREATOR = new Creator<GnssTimeSuggestion>() { public GnssTimeSuggestion createFromParcel(Parcel in) { return GnssTimeSuggestion.createFromParcel(in); TimeSuggestionHelper helper = TimeSuggestionHelper.handleCreateFromParcel( GnssTimeSuggestion.class, in); return new GnssTimeSuggestion(helper); } public GnssTimeSuggestion[] newArray(int size) { Loading @@ -57,21 +48,14 @@ public final class GnssTimeSuggestion implements Parcelable { } }; @NonNull private final TimestampedValue<Long> mUnixEpochTime; @Nullable private ArrayList<String> mDebugInfo; @NonNull private final TimeSuggestionHelper mTimeSuggestionHelper; public GnssTimeSuggestion(@NonNull TimestampedValue<Long> unixEpochTime) { mUnixEpochTime = Objects.requireNonNull(unixEpochTime); Objects.requireNonNull(unixEpochTime.getValue()); mTimeSuggestionHelper = new TimeSuggestionHelper(GnssTimeSuggestion.class, unixEpochTime); } private static GnssTimeSuggestion createFromParcel(Parcel in) { TimestampedValue<Long> unixEpochTime = in.readParcelable(null /* classLoader */); GnssTimeSuggestion suggestion = new GnssTimeSuggestion(unixEpochTime); @SuppressWarnings("unchecked") ArrayList<String> debugInfo = (ArrayList<String>) in.readArrayList(null /* classLoader */); suggestion.mDebugInfo = debugInfo; return suggestion; private GnssTimeSuggestion(@NonNull TimeSuggestionHelper helper) { mTimeSuggestionHelper = Objects.requireNonNull(helper); } @Override Loading @@ -81,19 +65,17 @@ public final class GnssTimeSuggestion implements Parcelable { @Override public void writeToParcel(@NonNull Parcel dest, int flags) { dest.writeParcelable(mUnixEpochTime, 0); dest.writeList(mDebugInfo); mTimeSuggestionHelper.handleWriteToParcel(dest, flags); } @NonNull public TimestampedValue<Long> getUnixEpochTime() { return mUnixEpochTime; return mTimeSuggestionHelper.getUnixEpochTime(); } @NonNull public List<String> getDebugInfo() { return mDebugInfo == null ? Collections.emptyList() : Collections.unmodifiableList(mDebugInfo); return mTimeSuggestionHelper.getDebugInfo(); } /** Loading @@ -102,10 +84,7 @@ public final class GnssTimeSuggestion implements Parcelable { * {@link #equals(Object)} and {@link #hashCode()}. */ public void addDebugInfo(String... debugInfos) { if (mDebugInfo == null) { mDebugInfo = new ArrayList<>(); } mDebugInfo.addAll(Arrays.asList(debugInfos)); mTimeSuggestionHelper.addDebugInfo(debugInfos); } @Override Loading @@ -117,19 +96,29 @@ public final class GnssTimeSuggestion implements Parcelable { return false; } GnssTimeSuggestion that = (GnssTimeSuggestion) o; return Objects.equals(mUnixEpochTime, that.mUnixEpochTime); return mTimeSuggestionHelper.handleEquals(that.mTimeSuggestionHelper); } @Override public int hashCode() { return Objects.hash(mUnixEpochTime); return mTimeSuggestionHelper.hashCode(); } @Override public String toString() { return "GnssTimeSuggestion{" + "mUnixEpochTime=" + mUnixEpochTime + ", mDebugInfo=" + mDebugInfo + '}'; return mTimeSuggestionHelper.handleToString(); } /** Parses command line args to create a {@link GnssTimeSuggestion}. */ public static GnssTimeSuggestion parseCommandLineArg(@NonNull ShellCommand cmd) throws IllegalArgumentException { TimeSuggestionHelper suggestionHelper = TimeSuggestionHelper.handleParseCommandLineArg(GnssTimeSuggestion.class, cmd); return new GnssTimeSuggestion(suggestionHelper); } /** Prints the command line args needed to create a {@link GnssTimeSuggestion}. */ public static void printCommandLineOpts(PrintWriter pw) { TimeSuggestionHelper.handlePrintCommandLineOpts(pw, "GNSS", GnssTimeSuggestion.class); } }
core/java/android/app/timedetector/ManualTimeSuggestion.java +29 −40 Original line number Diff line number Diff line Loading @@ -20,27 +20,17 @@ import android.annotation.NonNull; import android.annotation.Nullable; import android.os.Parcel; import android.os.Parcelable; import android.os.ShellCommand; import android.os.TimestampedValue; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.io.PrintWriter; import java.util.List; import java.util.Objects; /** * A time signal from a manual (user provided) source. * * <p>{@code unixEpochTime} is the suggested time. The {@code unixEpochTime.value} is the number of * milliseconds elapsed since 1/1/1970 00:00:00 UTC. The {@code unixEpochTime.referenceTimeMillis} * is the value of the elapsed realtime clock when the {@code unixEpochTime.value} was established. * Note that the elapsed realtime clock is considered accurate but it is volatile, so time * suggestions cannot be persisted across device resets. * * <p>{@code debugInfo} contains debugging metadata associated with the suggestion. This is used to * record why the suggestion exists and how it was entered. This information exists only to aid in * debugging and therefore is used by {@link #toString()}, but it is not for use in detection * logic and is not considered in {@link #hashCode()} or {@link #equals(Object)}. * <p>See {@link TimeSuggestionHelper} for property information. * * @hide */ Loading @@ -49,7 +39,9 @@ public final class ManualTimeSuggestion implements Parcelable { public static final @NonNull Creator<ManualTimeSuggestion> CREATOR = new Creator<ManualTimeSuggestion>() { public ManualTimeSuggestion createFromParcel(Parcel in) { return ManualTimeSuggestion.createFromParcel(in); TimeSuggestionHelper helper = TimeSuggestionHelper.handleCreateFromParcel( ManualTimeSuggestion.class, in); return new ManualTimeSuggestion(helper); } public ManualTimeSuggestion[] newArray(int size) { Loading @@ -57,21 +49,14 @@ public final class ManualTimeSuggestion implements Parcelable { } }; @NonNull private final TimestampedValue<Long> mUnixEpochTime; @Nullable private ArrayList<String> mDebugInfo; @NonNull private final TimeSuggestionHelper mTimeSuggestionHelper; public ManualTimeSuggestion(@NonNull TimestampedValue<Long> unixEpochTime) { mUnixEpochTime = Objects.requireNonNull(unixEpochTime); Objects.requireNonNull(unixEpochTime.getValue()); mTimeSuggestionHelper = new TimeSuggestionHelper(ManualTimeSuggestion.class, unixEpochTime); } private static ManualTimeSuggestion createFromParcel(Parcel in) { TimestampedValue<Long> unixEpochTime = in.readParcelable(null /* classLoader */); ManualTimeSuggestion suggestion = new ManualTimeSuggestion(unixEpochTime); @SuppressWarnings("unchecked") ArrayList<String> debugInfo = (ArrayList<String>) in.readArrayList(null /* classLoader */); suggestion.mDebugInfo = debugInfo; return suggestion; private ManualTimeSuggestion(@NonNull TimeSuggestionHelper helper) { mTimeSuggestionHelper = Objects.requireNonNull(helper); } @Override Loading @@ -81,19 +66,17 @@ public final class ManualTimeSuggestion implements Parcelable { @Override public void writeToParcel(@NonNull Parcel dest, int flags) { dest.writeParcelable(mUnixEpochTime, 0); dest.writeList(mDebugInfo); mTimeSuggestionHelper.handleWriteToParcel(dest, flags); } @NonNull public TimestampedValue<Long> getUnixEpochTime() { return mUnixEpochTime; return mTimeSuggestionHelper.getUnixEpochTime(); } @NonNull public List<String> getDebugInfo() { return mDebugInfo == null ? Collections.emptyList() : Collections.unmodifiableList(mDebugInfo); return mTimeSuggestionHelper.getDebugInfo(); } /** Loading @@ -102,10 +85,7 @@ public final class ManualTimeSuggestion implements Parcelable { * {@link #equals(Object)} and {@link #hashCode()}. */ public void addDebugInfo(String... debugInfos) { if (mDebugInfo == null) { mDebugInfo = new ArrayList<>(); } mDebugInfo.addAll(Arrays.asList(debugInfos)); mTimeSuggestionHelper.addDebugInfo(debugInfos); } @Override Loading @@ -117,19 +97,28 @@ public final class ManualTimeSuggestion implements Parcelable { return false; } ManualTimeSuggestion that = (ManualTimeSuggestion) o; return Objects.equals(mUnixEpochTime, that.mUnixEpochTime); return mTimeSuggestionHelper.handleEquals(that.mTimeSuggestionHelper); } @Override public int hashCode() { return Objects.hash(mUnixEpochTime); return mTimeSuggestionHelper.hashCode(); } @Override public String toString() { return "ManualTimeSuggestion{" + "mUnixEpochTime=" + mUnixEpochTime + ", mDebugInfo=" + mDebugInfo + '}'; return mTimeSuggestionHelper.handleToString(); } /** @hide */ public static ManualTimeSuggestion parseCommandLineArg(@NonNull ShellCommand cmd) throws IllegalArgumentException { return new ManualTimeSuggestion( TimeSuggestionHelper.handleParseCommandLineArg(ManualTimeSuggestion.class, cmd)); } /** @hide */ public static void printCommandLineOpts(PrintWriter pw) { TimeSuggestionHelper.handlePrintCommandLineOpts(pw, "Manual", ManualTimeSuggestion.class); } }
core/java/android/app/timedetector/NetworkTimeSuggestion.java +33 −45 Original line number Diff line number Diff line Loading @@ -17,31 +17,19 @@ package android.app.timedetector; import android.annotation.NonNull; import android.annotation.Nullable; import android.os.Parcel; import android.os.Parcelable; import android.os.ShellCommand; import android.os.TimestampedValue; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.io.PrintWriter; import java.util.List; import java.util.Objects; /** * A time signal from a network time source like NTP. * * <p>{@code unixEpochTime} contains the suggested time. The {@code unixEpochTime.value} is the * number of milliseconds elapsed since 1/1/1970 00:00:00 UTC according to the Unix time system. * The {@code unixEpochTime.referenceTimeMillis} is the value of the elapsed realtime clock when * the {@code unixEpochTime.value} was established. Note that the elapsed realtime clock is * considered accurate but it is volatile, so time suggestions cannot be persisted across device * resets. * * <p>{@code debugInfo} contains debugging metadata associated with the suggestion. This is used to * record why the suggestion exists and how it was determined. This information exists only to aid * in debugging and therefore is used by {@link #toString()}, but it is not for use in detection * logic and is not considered in {@link #hashCode()} or {@link #equals(Object)}. * <p>See {@link TimeSuggestionHelper} for property information. * * @hide */ Loading @@ -50,7 +38,9 @@ public final class NetworkTimeSuggestion implements Parcelable { public static final @NonNull Creator<NetworkTimeSuggestion> CREATOR = new Creator<NetworkTimeSuggestion>() { public NetworkTimeSuggestion createFromParcel(Parcel in) { return NetworkTimeSuggestion.createFromParcel(in); TimeSuggestionHelper helper = TimeSuggestionHelper.handleCreateFromParcel( NetworkTimeSuggestion.class, in); return new NetworkTimeSuggestion(helper); } public NetworkTimeSuggestion[] newArray(int size) { Loading @@ -58,21 +48,15 @@ public final class NetworkTimeSuggestion implements Parcelable { } }; @NonNull private final TimestampedValue<Long> mUnixEpochTime; @Nullable private ArrayList<String> mDebugInfo; @NonNull private final TimeSuggestionHelper mTimeSuggestionHelper; public NetworkTimeSuggestion(@NonNull TimestampedValue<Long> unixEpochTime) { mUnixEpochTime = Objects.requireNonNull(unixEpochTime); Objects.requireNonNull(unixEpochTime.getValue()); mTimeSuggestionHelper = new TimeSuggestionHelper( NetworkTimeSuggestion.class, unixEpochTime); } private static NetworkTimeSuggestion createFromParcel(Parcel in) { TimestampedValue<Long> unixEpochTime = in.readParcelable(null /* classLoader */); NetworkTimeSuggestion suggestion = new NetworkTimeSuggestion(unixEpochTime); @SuppressWarnings("unchecked") ArrayList<String> debugInfo = (ArrayList<String>) in.readArrayList(null /* classLoader */); suggestion.mDebugInfo = debugInfo; return suggestion; private NetworkTimeSuggestion(@NonNull TimeSuggestionHelper helper) { mTimeSuggestionHelper = Objects.requireNonNull(helper); } @Override Loading @@ -82,35 +66,30 @@ public final class NetworkTimeSuggestion implements Parcelable { @Override public void writeToParcel(@NonNull Parcel dest, int flags) { dest.writeParcelable(mUnixEpochTime, 0); dest.writeList(mDebugInfo); mTimeSuggestionHelper.handleWriteToParcel(dest, flags); } @NonNull public TimestampedValue<Long> getUnixEpochTime() { return mUnixEpochTime; return mTimeSuggestionHelper.getUnixEpochTime(); } @NonNull public List<String> getDebugInfo() { return mDebugInfo == null ? Collections.emptyList() : Collections.unmodifiableList(mDebugInfo); return mTimeSuggestionHelper.getDebugInfo(); } /** * Associates information with the instance that can be useful for debugging / logging. The * information is present in {@link #toString()} but is not considered for * {@link #equals(Object)} and {@link #hashCode()}. * information is present in {@link #toString()} but is not considered for {@link * #equals(Object)} and {@link #hashCode()}. */ public void addDebugInfo(String... debugInfos) { if (mDebugInfo == null) { mDebugInfo = new ArrayList<>(); } mDebugInfo.addAll(Arrays.asList(debugInfos)); mTimeSuggestionHelper.addDebugInfo(debugInfos); } @Override public boolean equals(@Nullable Object o) { public boolean equals(Object o) { if (this == o) { return true; } Loading @@ -118,19 +97,28 @@ public final class NetworkTimeSuggestion implements Parcelable { return false; } NetworkTimeSuggestion that = (NetworkTimeSuggestion) o; return Objects.equals(mUnixEpochTime, that.mUnixEpochTime); return mTimeSuggestionHelper.handleEquals(that.mTimeSuggestionHelper); } @Override public int hashCode() { return Objects.hash(mUnixEpochTime); return mTimeSuggestionHelper.hashCode(); } @Override public String toString() { return "NetworkTimeSuggestion{" + "mUnixEpochTime=" + mUnixEpochTime + ", mDebugInfo=" + mDebugInfo + '}'; return mTimeSuggestionHelper.handleToString(); } /** @hide */ public static NetworkTimeSuggestion parseCommandLineArg(@NonNull ShellCommand cmd) throws IllegalArgumentException { return new NetworkTimeSuggestion( TimeSuggestionHelper.handleParseCommandLineArg(NetworkTimeSuggestion.class, cmd)); } /** @hide */ public static void printCommandLineOpts(PrintWriter pw) { TimeSuggestionHelper.handlePrintCommandLineOpts(pw, "Network", NetworkTimeSuggestion.class); } }
core/java/android/app/timedetector/TelephonyTimeSuggestion.java +57 −0 Original line number Diff line number Diff line Loading @@ -20,8 +20,10 @@ import android.annotation.NonNull; import android.annotation.Nullable; import android.os.Parcel; import android.os.Parcelable; import android.os.ShellCommand; import android.os.TimestampedValue; import java.io.PrintWriter; import java.util.ArrayList; import java.util.Collections; import java.util.List; Loading Loading @@ -88,6 +90,61 @@ public final class TelephonyTimeSuggestion implements Parcelable { return suggestion; } /** @hide */ public static TelephonyTimeSuggestion parseCommandLineArg(@NonNull ShellCommand cmd) throws IllegalArgumentException { Integer slotIndex = null; Long referenceTimeMillis = null; Long unixEpochTimeMillis = null; String opt; while ((opt = cmd.getNextArg()) != null) { switch (opt) { case "--slot_index": { slotIndex = Integer.parseInt(cmd.getNextArgRequired()); break; } case "--reference_time": { referenceTimeMillis = Long.parseLong(cmd.getNextArgRequired()); break; } case "--unix_epoch_time": { unixEpochTimeMillis = Long.parseLong(cmd.getNextArgRequired()); break; } default: { throw new IllegalArgumentException("Unknown option: " + opt); } } } if (slotIndex == null) { throw new IllegalArgumentException("No slotIndex specified."); } if (referenceTimeMillis == null) { throw new IllegalArgumentException("No referenceTimeMillis specified."); } if (unixEpochTimeMillis == null) { throw new IllegalArgumentException("No unixEpochTimeMillis specified."); } TimestampedValue<Long> timeSignal = new TimestampedValue<>(referenceTimeMillis, unixEpochTimeMillis); Builder builder = new Builder(slotIndex) .setUnixEpochTime(timeSignal) .addDebugInfo("Command line injection"); return builder.build(); } /** @hide */ public static void printCommandLineOpts(PrintWriter pw) { pw.println("Telephony suggestion options:"); pw.println(" --slot_index <number>"); pw.println(" --reference_time <elapsed realtime millis>"); pw.println(" --unix_epoch_time <Unix epoch time millis>"); pw.println(); pw.println("See " + TelephonyTimeSuggestion.class.getName() + " for more information"); } @Override public int describeContents() { return 0; Loading