Fix: Retrieval of location to caclulate twilight
The provider determined by getBestProvider may not have a LastKnownLocation and
therefore the system might use a fake location, even if one provider will have
a location.
Change-Id: Iec4a377b141b0260af5611f51affa5f0c4a84ed2
diff --git a/services/java/com/android/server/UiModeManagerService.java b/services/java/com/android/server/UiModeManagerService.java
index 8103d7c..84790ca 100644
--- a/services/java/com/android/server/UiModeManagerService.java
+++ b/services/java/com/android/server/UiModeManagerService.java
@@ -52,6 +52,7 @@
import java.io.FileDescriptor;
import java.io.PrintWriter;
+import java.util.Iterator;
import com.android.internal.R;
import com.android.internal.app.DisableCarModeActivity;
@@ -76,10 +77,10 @@
private final Context mContext;
final Object mLock = new Object();
-
+
private int mDockState = Intent.EXTRA_DOCK_STATE_UNDOCKED;
private int mLastBroadcastState = Intent.EXTRA_DOCK_STATE_UNDOCKED;
-
+
private int mNightMode = UiModeManager.MODE_NIGHT_NO;
private boolean mCarModeEnabled = false;
private boolean mCharging = false;
@@ -89,10 +90,10 @@
private boolean mComputedNightMode;
private int mCurUiMode = 0;
private int mSetUiMode = 0;
-
+
private boolean mHoldingConfiguration = false;
private Configuration mConfiguration = new Configuration();
-
+
private boolean mSystemReady;
private NotificationManager mNotificationManager;
@@ -138,7 +139,7 @@
Slog.w(TAG, e.getCause());
}
}
-
+
if (mHoldingConfiguration) {
mHoldingConfiguration = false;
updateConfigurationLocked();
@@ -255,7 +256,7 @@
mContext = context;
ServiceManager.addService(Context.UI_MODE_SERVICE, this);
-
+
mAlarmManager =
(AlarmManager)mContext.getSystemService(Context.ALARM_SERVICE);
mLocationManager =
@@ -304,7 +305,7 @@
return mCurUiMode & Configuration.UI_MODE_TYPE_MASK;
}
}
-
+
public void setNightMode(int mode) throws RemoteException {
synchronized (mLock) {
switch (mode) {
@@ -318,18 +319,18 @@
if (!isDoingNightMode()) {
return;
}
-
+
if (mNightMode != mode) {
mNightMode = mode;
updateLocked();
}
}
}
-
+
public int getNightMode() throws RemoteException {
return mNightMode;
}
-
+
void systemReady() {
synchronized (mLock) {
mSystemReady = true;
@@ -342,7 +343,7 @@
boolean isDoingNightMode() {
return mCarModeEnabled || mDockState != Intent.EXTRA_DOCK_STATE_UNDOCKED;
}
-
+
void setCarModeLocked(boolean enabled) {
if (mCarModeEnabled != enabled) {
mCarModeEnabled = enabled;
@@ -399,12 +400,12 @@
uiMode = Configuration.UI_MODE_TYPE_NORMAL |
Configuration.UI_MODE_NIGHT_NO;
}
-
+
mCurUiMode = uiMode;
-
+
if (!mHoldingConfiguration && uiMode != mSetUiMode) {
mSetUiMode = uiMode;
-
+
try {
final IActivityManager am = ActivityManagerNative.getDefault();
mConfiguration.uiMode = uiMode;
@@ -414,10 +415,10 @@
}
}
}
-
+
final void updateLocked() {
long ident = Binder.clearCallingIdentity();
-
+
try {
String action = null;
String oldAction = null;
@@ -426,11 +427,11 @@
} else if (mLastBroadcastState == Intent.EXTRA_DOCK_STATE_DESK) {
oldAction = UiModeManager.ACTION_EXIT_DESK_MODE;
}
-
+
if (mCarModeEnabled) {
if (mLastBroadcastState != Intent.EXTRA_DOCK_STATE_CAR) {
adjustStatusBarCarModeLocked();
-
+
if (oldAction != null) {
mContext.sendBroadcast(new Intent(oldAction));
}
@@ -449,11 +450,11 @@
if (mLastBroadcastState == Intent.EXTRA_DOCK_STATE_CAR) {
adjustStatusBarCarModeLocked();
}
-
+
mLastBroadcastState = Intent.EXTRA_DOCK_STATE_UNDOCKED;
action = oldAction;
}
-
+
if (action != null) {
// Send the ordered broadcast; the result receiver will receive after all
// broadcasts have been sent. If any broadcast receiver changes the result
@@ -468,7 +469,7 @@
// the broacast and started the home activity.
mHoldingConfiguration = true;
}
-
+
updateConfigurationLocked();
// keep screen on when charging and in car mode
@@ -609,14 +610,18 @@
}
private void retrieveLocation() {
- Location location;
- Criteria criteria = new Criteria();
- criteria.setSpeedRequired(false);
- criteria.setAltitudeRequired(false);
- criteria.setBearingRequired(false);
- criteria.setAccuracy(Criteria.ACCURACY_FINE);
- final String bestProvider = mLocationManager.getBestProvider(criteria, true);
- location = mLocationManager.getLastKnownLocation(bestProvider);
+ Location location = null;
+ final Iterator<String> providers =
+ mLocationManager.getProviders(new Criteria(), true).iterator();
+ while (providers.hasNext()) {
+ final Location lastKnownLocation =
+ mLocationManager.getLastKnownLocation(providers.next());
+ // pick the most recent location
+ if (location == null || (lastKnownLocation != null &&
+ location.getTime() < lastKnownLocation.getTime())) {
+ location = lastKnownLocation;
+ }
+ }
// In the case there is no location available (e.g. GPS fix or network location
// is not available yet), the longitude of the location is estimated using the timezone,
// latitude and accuracy are set to get a good average.
@@ -684,18 +689,18 @@
mComputedNightMode = nightMode;
}
-
+
@Override
protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
if (mContext.checkCallingOrSelfPermission(android.Manifest.permission.DUMP)
!= PackageManager.PERMISSION_GRANTED) {
-
+
pw.println("Permission Denial: can't dump uimode service from from pid="
+ Binder.getCallingPid()
+ ", uid=" + Binder.getCallingUid());
return;
}
-
+
synchronized (mLock) {
pw.println("Current UI Mode Service state:");
pw.print(" mDockState="); pw.print(mDockState);