Merge "Add cooling device into thermal service" into qt-dev
This commit is contained in:
committed by
Android (Google) Code Review
commit
6e14a0326e
19
core/java/android/os/CoolingDevice.aidl
Normal file
19
core/java/android/os/CoolingDevice.aidl
Normal file
@@ -0,0 +1,19 @@
|
||||
/*
|
||||
** Copyright 2019, The Android Open Source Project
|
||||
**
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
** you may not use this file except in compliance with the License.
|
||||
** You may obtain a copy of the License at
|
||||
**
|
||||
** http://www.apache.org/licenses/LICENSE-2.0
|
||||
**
|
||||
** Unless required by applicable law or agreed to in writing, software
|
||||
** distributed under the License is distributed on an "AS IS" BASIS,
|
||||
** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
** See the License for the specific language governing permissions and
|
||||
** limitations under the License.
|
||||
*/
|
||||
|
||||
package android.os;
|
||||
|
||||
parcelable CoolingDevice;
|
||||
166
core/java/android/os/CoolingDevice.java
Normal file
166
core/java/android/os/CoolingDevice.java
Normal file
@@ -0,0 +1,166 @@
|
||||
/*
|
||||
* Copyright (c) 2019 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package android.os;
|
||||
|
||||
import android.annotation.IntDef;
|
||||
import android.annotation.NonNull;
|
||||
import android.hardware.thermal.V2_0.CoolingType;
|
||||
|
||||
import com.android.internal.util.Preconditions;
|
||||
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
|
||||
/**
|
||||
* Cooling device values used by IThermalService.
|
||||
*
|
||||
* @hide
|
||||
*/
|
||||
public final class CoolingDevice implements Parcelable {
|
||||
/**
|
||||
* Current throttle state of the cooling device. The value can any unsigned integer
|
||||
* numbers between 0 and max_state defined in its driver, usually representing the
|
||||
* associated device's power state. 0 means device is not in throttling, higher value
|
||||
* means deeper throttling.
|
||||
*/
|
||||
private final long mValue;
|
||||
/** A cooling device type from ThermalHAL */
|
||||
private final int mType;
|
||||
/** Name of this cooling device */
|
||||
private final String mName;
|
||||
|
||||
@IntDef(prefix = { "TYPE_" }, value = {
|
||||
TYPE_FAN,
|
||||
TYPE_BATTERY,
|
||||
TYPE_CPU,
|
||||
TYPE_GPU,
|
||||
TYPE_MODEM,
|
||||
TYPE_NPU,
|
||||
TYPE_COMPONENT,
|
||||
})
|
||||
@Retention(RetentionPolicy.SOURCE)
|
||||
public @interface Type {}
|
||||
|
||||
/** Keep in sync with hardware/interfaces/thermal/2.0/types.hal */
|
||||
/** Fan for active cooling */
|
||||
public static final int TYPE_FAN = CoolingType.FAN;
|
||||
/** Battery charging cooling deivice */
|
||||
public static final int TYPE_BATTERY = CoolingType.BATTERY;
|
||||
/** CPU cooling deivice */
|
||||
public static final int TYPE_CPU = CoolingType.CPU;
|
||||
/** GPU cooling deivice */
|
||||
public static final int TYPE_GPU = CoolingType.GPU;
|
||||
/** Modem cooling deivice */
|
||||
public static final int TYPE_MODEM = CoolingType.MODEM;
|
||||
/** NPU/TPU cooling deivice */
|
||||
public static final int TYPE_NPU = CoolingType.NPU;
|
||||
/** Generic passive cooling deivice */
|
||||
public static final int TYPE_COMPONENT = CoolingType.COMPONENT;
|
||||
|
||||
/**
|
||||
* Verify a valid cooling device type.
|
||||
*
|
||||
* @return true if a cooling device type is valid otherwise false.
|
||||
*/
|
||||
public static boolean isValidType(@Type int type) {
|
||||
return type >= TYPE_FAN && type <= TYPE_COMPONENT;
|
||||
}
|
||||
|
||||
public CoolingDevice(long value, @Type int type, @NonNull String name) {
|
||||
Preconditions.checkArgument(isValidType(type), "Invalid Type");
|
||||
mValue = value;
|
||||
mType = type;
|
||||
mName = Preconditions.checkStringNotEmpty(name);
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the cooling device value.
|
||||
*
|
||||
* @return a cooling device value in int.
|
||||
*/
|
||||
public long getValue() {
|
||||
return mValue;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the cooling device type.
|
||||
*
|
||||
* @return a cooling device type: TYPE_*
|
||||
*/
|
||||
public @Type int getType() {
|
||||
return mType;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the cooling device name.
|
||||
*
|
||||
* @return a cooling device name as String.
|
||||
*/
|
||||
public String getName() {
|
||||
return mName;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "CoolingDevice{mValue=" + mValue + ", mType=" + mType + ", mName=" + mName + "}";
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int hash = mName.hashCode();
|
||||
hash = 31 * hash + Long.hashCode(mValue);
|
||||
hash = 31 * hash + mType;
|
||||
return hash;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (!(o instanceof CoolingDevice)) {
|
||||
return false;
|
||||
}
|
||||
CoolingDevice other = (CoolingDevice) o;
|
||||
return other.mValue == mValue && other.mType == mType && other.mName.equals(mName);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeToParcel(Parcel p, int flags) {
|
||||
p.writeLong(mValue);
|
||||
p.writeInt(mType);
|
||||
p.writeString(mName);
|
||||
}
|
||||
|
||||
public static final @android.annotation.NonNull Parcelable.Creator<CoolingDevice> CREATOR =
|
||||
new Parcelable.Creator<CoolingDevice>() {
|
||||
@Override
|
||||
public CoolingDevice createFromParcel(Parcel p) {
|
||||
long value = p.readLong();
|
||||
int type = p.readInt();
|
||||
String name = p.readString();
|
||||
return new CoolingDevice(value, type, name);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CoolingDevice[] newArray(int size) {
|
||||
return new CoolingDevice[size];
|
||||
}
|
||||
};
|
||||
|
||||
@Override
|
||||
public int describeContents() {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
@@ -16,6 +16,7 @@
|
||||
|
||||
package android.os;
|
||||
|
||||
import android.os.CoolingDevice;
|
||||
import android.os.IThermalEventListener;
|
||||
import android.os.IThermalStatusListener;
|
||||
import android.os.Temperature;
|
||||
@@ -52,7 +53,7 @@ interface IThermalService {
|
||||
|
||||
/**
|
||||
* Get current temperature with its throttling status.
|
||||
* @return list of android.os.Temperature
|
||||
* @return list of {@link android.os.Temperature}.
|
||||
* {@hide}
|
||||
*/
|
||||
List<Temperature> getCurrentTemperatures();
|
||||
@@ -87,4 +88,19 @@ interface IThermalService {
|
||||
* {@hide}
|
||||
*/
|
||||
int getCurrentThermalStatus();
|
||||
|
||||
/**
|
||||
* Get current cooling devices.
|
||||
* @return list of {@link android.os.CoolingDevice}.
|
||||
* {@hide}
|
||||
*/
|
||||
List<CoolingDevice> getCurrentCoolingDevices();
|
||||
|
||||
/**
|
||||
* Get current cooling devices on given type.
|
||||
* @param type the cooling device type to query.
|
||||
* @return list of {@link android.os.CoolingDevice}.
|
||||
* {@hide}
|
||||
*/
|
||||
List<CoolingDevice> getCurrentCoolingDevicesWithType(in int type);
|
||||
}
|
||||
|
||||
@@ -17,9 +17,12 @@
|
||||
package android.os;
|
||||
|
||||
import android.annotation.IntDef;
|
||||
import android.annotation.NonNull;
|
||||
import android.hardware.thermal.V2_0.TemperatureType;
|
||||
import android.hardware.thermal.V2_0.ThrottlingSeverity;
|
||||
|
||||
import com.android.internal.util.Preconditions;
|
||||
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
|
||||
@@ -30,13 +33,13 @@ import java.lang.annotation.RetentionPolicy;
|
||||
*/
|
||||
public final class Temperature implements Parcelable {
|
||||
/** Temperature value */
|
||||
private float mValue;
|
||||
/** A temperature type from ThermalHAL */
|
||||
private int mType;
|
||||
/** Name of this temperature */
|
||||
private String mName;
|
||||
private final float mValue;
|
||||
/** A Temperature type from ThermalHAL */
|
||||
private final int mType;
|
||||
/** Name of this Temperature */
|
||||
private final String mName;
|
||||
/** The level of the sensor is currently in throttling */
|
||||
private int mStatus;
|
||||
private final int mStatus;
|
||||
|
||||
@IntDef(prefix = { "THROTTLING_" }, value = {
|
||||
THROTTLING_NONE,
|
||||
@@ -75,7 +78,7 @@ public final class Temperature implements Parcelable {
|
||||
@Retention(RetentionPolicy.SOURCE)
|
||||
public @interface Type {}
|
||||
|
||||
/* Keep in sync with hardware/interfaces/thermal/2.0/types.hal */
|
||||
/** Keep in sync with hardware/interfaces/thermal/2.0/types.hal */
|
||||
public static final int TYPE_UNKNOWN = TemperatureType.UNKNOWN;
|
||||
public static final int TYPE_CPU = TemperatureType.CPU;
|
||||
public static final int TYPE_GPU = TemperatureType.GPU;
|
||||
@@ -89,9 +92,9 @@ public final class Temperature implements Parcelable {
|
||||
public static final int TYPE_NPU = TemperatureType.NPU;
|
||||
|
||||
/**
|
||||
* Verify a valid temperature type.
|
||||
* Verify a valid Temperature type.
|
||||
*
|
||||
* @return true if a temperature type is valid otherwise false.
|
||||
* @return true if a Temperature type is valid otherwise false.
|
||||
*/
|
||||
public static boolean isValidType(@Type int type) {
|
||||
return type >= TYPE_UNKNOWN && type <= TYPE_NPU;
|
||||
@@ -106,67 +109,75 @@ public final class Temperature implements Parcelable {
|
||||
return status >= THROTTLING_NONE && status <= THROTTLING_SHUTDOWN;
|
||||
}
|
||||
|
||||
public Temperature() {
|
||||
this(Float.NaN, TYPE_UNKNOWN, "", THROTTLING_NONE);
|
||||
}
|
||||
|
||||
public Temperature(float value, @Type int type, String name, @ThrottlingStatus int status) {
|
||||
public Temperature(float value, @Type int type,
|
||||
@NonNull String name, @ThrottlingStatus int status) {
|
||||
Preconditions.checkArgument(isValidType(type), "Invalid Type");
|
||||
Preconditions.checkArgument(isValidStatus(status) , "Invalid Status");
|
||||
mValue = value;
|
||||
mType = isValidType(type) ? type : TYPE_UNKNOWN;
|
||||
mName = name;
|
||||
mStatus = isValidStatus(status) ? status : THROTTLING_NONE;
|
||||
mType = type;
|
||||
mName = Preconditions.checkStringNotEmpty(name);
|
||||
mStatus = status;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the temperature value.
|
||||
* Return the Temperature value.
|
||||
*
|
||||
* @return a temperature value in floating point could be NaN.
|
||||
* @return a Temperature value in floating point could be NaN.
|
||||
*/
|
||||
public float getValue() {
|
||||
return mValue;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the temperature type.
|
||||
* Return the Temperature type.
|
||||
*
|
||||
* @return a temperature type: TYPE_*
|
||||
* @return a Temperature type: TYPE_*
|
||||
*/
|
||||
public @Type int getType() {
|
||||
return mType;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the temperature name.
|
||||
* Return the Temperature name.
|
||||
*
|
||||
* @return a temperature name as String.
|
||||
* @return a Temperature name as String.
|
||||
*/
|
||||
public String getName() {
|
||||
return mName;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the temperature throttling status.
|
||||
* Return the Temperature throttling status.
|
||||
*
|
||||
* @return a temperature throttling status: THROTTLING_*
|
||||
* @return a Temperature throttling status: THROTTLING_*
|
||||
*/
|
||||
public @ThrottlingStatus int getStatus() {
|
||||
return mStatus;
|
||||
}
|
||||
|
||||
private Temperature(Parcel p) {
|
||||
readFromParcel(p);
|
||||
@Override
|
||||
public String toString() {
|
||||
return "Temperature{mValue=" + mValue + ", mType=" + mType
|
||||
+ ", mName=" + mName + ", mStatus=" + mStatus + "}";
|
||||
}
|
||||
|
||||
/**
|
||||
* Fill in Temperature members from a Parcel.
|
||||
*
|
||||
* @param p the parceled Temperature object.
|
||||
*/
|
||||
public void readFromParcel(Parcel p) {
|
||||
mValue = p.readFloat();
|
||||
mType = p.readInt();
|
||||
mName = p.readString();
|
||||
mStatus = p.readInt();
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int hash = mName.hashCode();
|
||||
hash = 31 * hash + Float.hashCode(mValue);
|
||||
hash = 31 * hash + mType;
|
||||
hash = 31 * hash + mStatus;
|
||||
return hash;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (!(o instanceof Temperature)) {
|
||||
return false;
|
||||
}
|
||||
Temperature other = (Temperature) o;
|
||||
return other.mValue == mValue && other.mType == mType
|
||||
&& other.mName.equals(mName) && other.mStatus == mStatus;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -181,13 +192,18 @@ public final class Temperature implements Parcelable {
|
||||
new Parcelable.Creator<Temperature>() {
|
||||
@Override
|
||||
public Temperature createFromParcel(Parcel p) {
|
||||
return new Temperature(p);
|
||||
float value = p.readFloat();
|
||||
int type = p.readInt();
|
||||
String name = p.readString();
|
||||
int status = p.readInt();
|
||||
return new Temperature(value, type, name, status);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Temperature[] newArray(int size) {
|
||||
return new Temperature[size];
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
@Override
|
||||
|
||||
@@ -24,6 +24,7 @@ import android.hardware.thermal.V1_1.IThermalCallback;
|
||||
import android.hardware.thermal.V2_0.IThermalChangedCallback;
|
||||
import android.hardware.thermal.V2_0.ThrottlingSeverity;
|
||||
import android.os.Binder;
|
||||
import android.os.CoolingDevice;
|
||||
import android.os.HwBinder;
|
||||
import android.os.IThermalEventListener;
|
||||
import android.os.IThermalService;
|
||||
@@ -49,8 +50,10 @@ import java.io.FileDescriptor;
|
||||
import java.io.PrintWriter;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.NoSuchElementException;
|
||||
import java.util.concurrent.atomic.AtomicBoolean;
|
||||
|
||||
/**
|
||||
* This is a system service that listens to HAL thermal events and dispatch those to listeners.
|
||||
@@ -93,8 +96,7 @@ public class ThermalManagerService extends SystemService {
|
||||
private ThermalHalWrapper mHalWrapper;
|
||||
|
||||
/** Hal ready. */
|
||||
@GuardedBy("mLock")
|
||||
private boolean mHalReady;
|
||||
private final AtomicBoolean mHalReady = new AtomicBoolean();
|
||||
|
||||
/** Invalid throttling status */
|
||||
private static final int INVALID_THROTTLING = Integer.MIN_VALUE;
|
||||
@@ -150,7 +152,7 @@ public class ThermalManagerService extends SystemService {
|
||||
onTemperatureChanged(temperatures.get(i), false);
|
||||
}
|
||||
onTemperatureMapChangedLocked();
|
||||
mHalReady = halConnected /* true */;
|
||||
mHalReady.set(true);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -298,20 +300,6 @@ public class ThermalManagerService extends SystemService {
|
||||
}
|
||||
}
|
||||
|
||||
private void dumpTemperaturesLocked(PrintWriter pw, String prefix,
|
||||
Collection<Temperature> temperatures) {
|
||||
for (Temperature t : temperatures) {
|
||||
pw.print(prefix);
|
||||
String out = String.format("Name: %s, Type: %d, Status: %d, Value: %f",
|
||||
t.getName(),
|
||||
t.getType(),
|
||||
t.getStatus(),
|
||||
t.getValue()
|
||||
);
|
||||
pw.println(out);
|
||||
}
|
||||
}
|
||||
|
||||
@VisibleForTesting
|
||||
final IThermalService.Stub mService = new IThermalService.Stub() {
|
||||
@Override
|
||||
@@ -324,7 +312,7 @@ public class ThermalManagerService extends SystemService {
|
||||
if (!mThermalEventListeners.register(listener, null)) {
|
||||
return false;
|
||||
}
|
||||
if (mHalReady) {
|
||||
if (mHalReady.get()) {
|
||||
// Notify its callback after new client registered.
|
||||
postEventListenerCurrentTemperatures(listener, null);
|
||||
}
|
||||
@@ -346,7 +334,7 @@ public class ThermalManagerService extends SystemService {
|
||||
if (!mThermalEventListeners.register(listener, new Integer(type))) {
|
||||
return false;
|
||||
}
|
||||
if (mHalReady) {
|
||||
if (mHalReady.get()) {
|
||||
// Notify its callback after new client registered.
|
||||
postEventListenerCurrentTemperatures(listener, new Integer(type));
|
||||
}
|
||||
@@ -377,7 +365,7 @@ public class ThermalManagerService extends SystemService {
|
||||
android.Manifest.permission.DEVICE_POWER, null);
|
||||
final long token = Binder.clearCallingIdentity();
|
||||
try {
|
||||
if (!mHalReady) {
|
||||
if (!mHalReady.get()) {
|
||||
return new ArrayList<>();
|
||||
}
|
||||
return mHalWrapper.getCurrentTemperatures(false, 0 /* not used */);
|
||||
@@ -392,7 +380,7 @@ public class ThermalManagerService extends SystemService {
|
||||
android.Manifest.permission.DEVICE_POWER, null);
|
||||
final long token = Binder.clearCallingIdentity();
|
||||
try {
|
||||
if (!mHalReady) {
|
||||
if (!mHalReady.get()) {
|
||||
return new ArrayList<>();
|
||||
}
|
||||
return mHalWrapper.getCurrentTemperatures(true, type);
|
||||
@@ -410,7 +398,7 @@ public class ThermalManagerService extends SystemService {
|
||||
if (!mThermalStatusListeners.register(listener)) {
|
||||
return false;
|
||||
}
|
||||
if (mHalReady) {
|
||||
if (mHalReady.get()) {
|
||||
// Notify its callback after new client registered.
|
||||
postStatusListener(listener);
|
||||
}
|
||||
@@ -446,6 +434,43 @@ public class ThermalManagerService extends SystemService {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<CoolingDevice> getCurrentCoolingDevices() {
|
||||
getContext().enforceCallingOrSelfPermission(
|
||||
android.Manifest.permission.DEVICE_POWER, null);
|
||||
final long token = Binder.clearCallingIdentity();
|
||||
try {
|
||||
if (!mHalReady.get()) {
|
||||
return new ArrayList<>();
|
||||
}
|
||||
return mHalWrapper.getCurrentCoolingDevices(false, 0);
|
||||
} finally {
|
||||
Binder.restoreCallingIdentity(token);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<CoolingDevice> getCurrentCoolingDevicesWithType(int type) {
|
||||
getContext().enforceCallingOrSelfPermission(
|
||||
android.Manifest.permission.DEVICE_POWER, null);
|
||||
final long token = Binder.clearCallingIdentity();
|
||||
try {
|
||||
if (!mHalReady.get()) {
|
||||
return new ArrayList<>();
|
||||
}
|
||||
return mHalWrapper.getCurrentCoolingDevices(true, type);
|
||||
} finally {
|
||||
Binder.restoreCallingIdentity(token);
|
||||
}
|
||||
}
|
||||
|
||||
private void dumpItemsLocked(PrintWriter pw, String prefix,
|
||||
Collection<?> items) {
|
||||
for (Iterator iterator = items.iterator(); iterator.hasNext();) {
|
||||
pw.println(prefix + iterator.next().toString());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
|
||||
if (!DumpUtils.checkDumpPermission(getContext(), TAG, pw)) {
|
||||
@@ -461,17 +486,19 @@ public class ThermalManagerService extends SystemService {
|
||||
mThermalStatusListeners.dump(pw, "\t");
|
||||
pw.println("Thermal Status: " + mStatus);
|
||||
pw.println("Cached temperatures:");
|
||||
dumpTemperaturesLocked(pw, "\t", mTemperatureMap.values());
|
||||
pw.println("HAL Ready: " + mHalReady);
|
||||
if (mHalReady) {
|
||||
dumpItemsLocked(pw, "\t", mTemperatureMap.values());
|
||||
pw.println("HAL Ready: " + mHalReady.get());
|
||||
if (mHalReady.get()) {
|
||||
pw.println("HAL connection:");
|
||||
mHalWrapper.dump(pw, "\t");
|
||||
pw.println("Current temperatures from HAL:");
|
||||
dumpTemperaturesLocked(pw, "\t",
|
||||
dumpItemsLocked(pw, "\t",
|
||||
mHalWrapper.getCurrentTemperatures(false, 0));
|
||||
pw.println("Current cooling devices from HAL:");
|
||||
dumpItemsLocked(pw, "\t",
|
||||
mHalWrapper.getCurrentCoolingDevices(false, 0));
|
||||
}
|
||||
}
|
||||
|
||||
} finally {
|
||||
Binder.restoreCallingIdentity(token);
|
||||
}
|
||||
@@ -588,6 +615,9 @@ public class ThermalManagerService extends SystemService {
|
||||
protected abstract List<Temperature> getCurrentTemperatures(boolean shouldFilter,
|
||||
int type);
|
||||
|
||||
protected abstract List<CoolingDevice> getCurrentCoolingDevices(boolean shouldFilter,
|
||||
int type);
|
||||
|
||||
protected abstract boolean connectToHal();
|
||||
|
||||
protected abstract void dump(PrintWriter pw, String prefix);
|
||||
@@ -663,6 +693,42 @@ public class ThermalManagerService extends SystemService {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected List<CoolingDevice> getCurrentCoolingDevices(boolean shouldFilter,
|
||||
int type) {
|
||||
synchronized (mHalLock) {
|
||||
List<CoolingDevice> ret = new ArrayList<>();
|
||||
if (mThermalHal10 == null) {
|
||||
return ret;
|
||||
}
|
||||
try {
|
||||
mThermalHal10.getCoolingDevices((status, coolingDevices) -> {
|
||||
if (ThermalStatusCode.SUCCESS == status.code) {
|
||||
for (android.hardware.thermal.V1_0.CoolingDevice
|
||||
coolingDevice : coolingDevices) {
|
||||
if (shouldFilter && type != coolingDevice.type) {
|
||||
continue;
|
||||
}
|
||||
ret.add(new CoolingDevice(
|
||||
(long) coolingDevice.currentValue,
|
||||
coolingDevice.type,
|
||||
coolingDevice.name));
|
||||
}
|
||||
} else {
|
||||
Slog.e(TAG,
|
||||
"Couldn't get cooling device because of HAL error: "
|
||||
+ status.debugMessage);
|
||||
}
|
||||
|
||||
});
|
||||
} catch (RemoteException e) {
|
||||
Slog.e(TAG, "Couldn't getCurrentCoolingDevices, reconnecting...", e);
|
||||
connectToHal();
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected boolean connectToHal() {
|
||||
synchronized (mHalLock) {
|
||||
@@ -756,6 +822,42 @@ public class ThermalManagerService extends SystemService {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected List<CoolingDevice> getCurrentCoolingDevices(boolean shouldFilter,
|
||||
int type) {
|
||||
synchronized (mHalLock) {
|
||||
List<CoolingDevice> ret = new ArrayList<>();
|
||||
if (mThermalHal11 == null) {
|
||||
return ret;
|
||||
}
|
||||
try {
|
||||
mThermalHal11.getCoolingDevices((status, coolingDevices) -> {
|
||||
if (ThermalStatusCode.SUCCESS == status.code) {
|
||||
for (android.hardware.thermal.V1_0.CoolingDevice
|
||||
coolingDevice : coolingDevices) {
|
||||
if (shouldFilter && type != coolingDevice.type) {
|
||||
continue;
|
||||
}
|
||||
ret.add(new CoolingDevice(
|
||||
(long) coolingDevice.currentValue,
|
||||
coolingDevice.type,
|
||||
coolingDevice.name));
|
||||
}
|
||||
} else {
|
||||
Slog.e(TAG,
|
||||
"Couldn't get cooling device because of HAL error: "
|
||||
+ status.debugMessage);
|
||||
}
|
||||
|
||||
});
|
||||
} catch (RemoteException e) {
|
||||
Slog.e(TAG, "Couldn't getCurrentCoolingDevices, reconnecting...", e);
|
||||
connectToHal();
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected boolean connectToHal() {
|
||||
synchronized (mHalLock) {
|
||||
@@ -817,9 +919,7 @@ public class ThermalManagerService extends SystemService {
|
||||
}
|
||||
try {
|
||||
mThermalHal20.getCurrentTemperatures(shouldFilter, type,
|
||||
(ThermalStatus status,
|
||||
ArrayList<android.hardware.thermal.V2_0.Temperature>
|
||||
temperatures) -> {
|
||||
(status, temperatures) -> {
|
||||
if (ThermalStatusCode.SUCCESS == status.code) {
|
||||
for (android.hardware.thermal.V2_0.Temperature
|
||||
temperature : temperatures) {
|
||||
@@ -843,6 +943,39 @@ public class ThermalManagerService extends SystemService {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected List<CoolingDevice> getCurrentCoolingDevices(boolean shouldFilter,
|
||||
int type) {
|
||||
synchronized (mHalLock) {
|
||||
List<CoolingDevice> ret = new ArrayList<>();
|
||||
if (mThermalHal20 == null) {
|
||||
return ret;
|
||||
}
|
||||
try {
|
||||
mThermalHal20.getCurrentCoolingDevices(shouldFilter, type,
|
||||
(status, coolingDevices) -> {
|
||||
if (ThermalStatusCode.SUCCESS == status.code) {
|
||||
for (android.hardware.thermal.V2_0.CoolingDevice
|
||||
coolingDevice : coolingDevices) {
|
||||
ret.add(new CoolingDevice(
|
||||
coolingDevice.value, coolingDevice.type,
|
||||
coolingDevice.name));
|
||||
}
|
||||
} else {
|
||||
Slog.e(TAG,
|
||||
"Couldn't get cooling device because of HAL error: "
|
||||
+ status.debugMessage);
|
||||
}
|
||||
|
||||
});
|
||||
} catch (RemoteException e) {
|
||||
Slog.e(TAG, "Couldn't getCurrentCoolingDevices, reconnecting...", e);
|
||||
connectToHal();
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected boolean connectToHal() {
|
||||
synchronized (mHalLock) {
|
||||
|
||||
@@ -28,6 +28,7 @@ import static org.mockito.Mockito.verify;
|
||||
import static org.mockito.Mockito.when;
|
||||
|
||||
import android.content.Context;
|
||||
import android.os.CoolingDevice;
|
||||
import android.os.IBinder;
|
||||
import android.os.IPowerManager;
|
||||
import android.os.IThermalEventListener;
|
||||
@@ -85,6 +86,8 @@ public class ThermalManagerServiceTest {
|
||||
private class ThermalHalFake extends ThermalHalWrapper {
|
||||
private static final int INIT_STATUS = Temperature.THROTTLING_NONE;
|
||||
private ArrayList<Temperature> mTemperatureList = new ArrayList<>();
|
||||
private ArrayList<CoolingDevice> mCoolingDeviceList = new ArrayList<>();
|
||||
|
||||
private Temperature mSkin1 = new Temperature(0, Temperature.TYPE_SKIN, "skin1",
|
||||
INIT_STATUS);
|
||||
private Temperature mSkin2 = new Temperature(0, Temperature.TYPE_SKIN, "skin2",
|
||||
@@ -93,17 +96,40 @@ public class ThermalManagerServiceTest {
|
||||
INIT_STATUS);
|
||||
private Temperature mUsbPort = new Temperature(0, Temperature.TYPE_USB_PORT, "usbport",
|
||||
INIT_STATUS);
|
||||
private CoolingDevice mCpu = new CoolingDevice(0, CoolingDevice.TYPE_BATTERY, "cpu");
|
||||
private CoolingDevice mGpu = new CoolingDevice(0, CoolingDevice.TYPE_BATTERY, "gpu");
|
||||
|
||||
ThermalHalFake() {
|
||||
mTemperatureList.add(mSkin1);
|
||||
mTemperatureList.add(mSkin2);
|
||||
mTemperatureList.add(mBattery);
|
||||
mTemperatureList.add(mUsbPort);
|
||||
mCoolingDeviceList.add(mCpu);
|
||||
mCoolingDeviceList.add(mGpu);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected List<Temperature> getCurrentTemperatures(boolean shouldFilter, int type) {
|
||||
return mTemperatureList;
|
||||
List<Temperature> ret = new ArrayList<>();
|
||||
for (Temperature temperature : mTemperatureList) {
|
||||
if (shouldFilter && type != temperature.getType()) {
|
||||
continue;
|
||||
}
|
||||
ret.add(temperature);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected List<CoolingDevice> getCurrentCoolingDevices(boolean shouldFilter, int type) {
|
||||
List<CoolingDevice> ret = new ArrayList<>();
|
||||
for (CoolingDevice cdev : mCoolingDeviceList) {
|
||||
if (shouldFilter && type != cdev.getType()) {
|
||||
continue;
|
||||
}
|
||||
ret.add(cdev);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -117,8 +143,10 @@ public class ThermalManagerServiceTest {
|
||||
}
|
||||
}
|
||||
|
||||
private void assertTemperatureEquals(List<Temperature> expected, List<Temperature> value) {
|
||||
assertEquals(new HashSet<>(expected), new HashSet<>(value));
|
||||
private void assertListEqualsIgnoringOrder(List<?> actual, List<?> expected) {
|
||||
HashSet<?> actualSet = new HashSet<>(actual);
|
||||
HashSet<?> expectedSet = new HashSet<>(expected);
|
||||
assertEquals(expectedSet, actualSet);
|
||||
}
|
||||
|
||||
@Before
|
||||
@@ -148,13 +176,14 @@ public class ThermalManagerServiceTest {
|
||||
ArgumentCaptor<Temperature> captor = ArgumentCaptor.forClass(Temperature.class);
|
||||
verify(mEventListener1, timeout(CALLBACK_TIMEOUT_MILLI_SEC)
|
||||
.times(4)).notifyThrottling(captor.capture());
|
||||
assertTemperatureEquals(mFakeHal.mTemperatureList, captor.getAllValues());
|
||||
assertListEqualsIgnoringOrder(mFakeHal.mTemperatureList, captor.getAllValues());
|
||||
verify(mStatusListener1, timeout(CALLBACK_TIMEOUT_MILLI_SEC)
|
||||
.times(1)).onStatusChange(Temperature.THROTTLING_NONE);
|
||||
captor = ArgumentCaptor.forClass(Temperature.class);
|
||||
verify(mEventListener2, timeout(CALLBACK_TIMEOUT_MILLI_SEC)
|
||||
.times(2)).notifyThrottling(captor.capture());
|
||||
assertTemperatureEquals(new ArrayList<>(Arrays.asList(mFakeHal.mSkin1, mFakeHal.mSkin2)),
|
||||
assertListEqualsIgnoringOrder(
|
||||
new ArrayList<>(Arrays.asList(mFakeHal.mSkin1, mFakeHal.mSkin2)),
|
||||
captor.getAllValues());
|
||||
verify(mStatusListener2, timeout(CALLBACK_TIMEOUT_MILLI_SEC)
|
||||
.times(1)).onStatusChange(Temperature.THROTTLING_NONE);
|
||||
@@ -185,7 +214,7 @@ public class ThermalManagerServiceTest {
|
||||
ArgumentCaptor<Temperature> captor = ArgumentCaptor.forClass(Temperature.class);
|
||||
verify(mEventListener1, timeout(CALLBACK_TIMEOUT_MILLI_SEC)
|
||||
.times(4)).notifyThrottling(captor.capture());
|
||||
assertTemperatureEquals(mFakeHal.mTemperatureList, captor.getAllValues());
|
||||
assertListEqualsIgnoringOrder(mFakeHal.mTemperatureList, captor.getAllValues());
|
||||
verify(mStatusListener1, timeout(CALLBACK_TIMEOUT_MILLI_SEC)
|
||||
.times(1)).onStatusChange(Temperature.THROTTLING_NONE);
|
||||
// Register new callbacks and verify old ones are not called (remained same) while new
|
||||
@@ -200,7 +229,8 @@ public class ThermalManagerServiceTest {
|
||||
captor = ArgumentCaptor.forClass(Temperature.class);
|
||||
verify(mEventListener2, timeout(CALLBACK_TIMEOUT_MILLI_SEC)
|
||||
.times(2)).notifyThrottling(captor.capture());
|
||||
assertTemperatureEquals(new ArrayList<>(Arrays.asList(mFakeHal.mSkin1, mFakeHal.mSkin2)),
|
||||
assertListEqualsIgnoringOrder(
|
||||
new ArrayList<>(Arrays.asList(mFakeHal.mSkin1, mFakeHal.mSkin2)),
|
||||
captor.getAllValues());
|
||||
verify(mStatusListener2, timeout(CALLBACK_TIMEOUT_MILLI_SEC)
|
||||
.times(1)).onStatusChange(Temperature.THROTTLING_NONE);
|
||||
@@ -260,9 +290,9 @@ public class ThermalManagerServiceTest {
|
||||
|
||||
@Test
|
||||
public void testGetCurrentTemperatures() throws RemoteException {
|
||||
assertTemperatureEquals(mFakeHal.getCurrentTemperatures(false, 0),
|
||||
assertListEqualsIgnoringOrder(mFakeHal.getCurrentTemperatures(false, 0),
|
||||
mService.mService.getCurrentTemperatures());
|
||||
assertTemperatureEquals(mFakeHal.getCurrentTemperatures(true, Temperature.TYPE_SKIN),
|
||||
assertListEqualsIgnoringOrder(mFakeHal.getCurrentTemperatures(true, Temperature.TYPE_SKIN),
|
||||
mService.mService.getCurrentTemperaturesWithType(Temperature.TYPE_SKIN));
|
||||
}
|
||||
|
||||
@@ -300,4 +330,16 @@ public class ThermalManagerServiceTest {
|
||||
mService.mService.getCurrentTemperaturesWithType(Temperature.TYPE_SKIN).size());
|
||||
assertEquals(Temperature.THROTTLING_NONE, mService.mService.getCurrentThermalStatus());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testGetCurrentCoolingDevices() throws RemoteException {
|
||||
assertListEqualsIgnoringOrder(mFakeHal.getCurrentCoolingDevices(false, 0),
|
||||
mService.mService.getCurrentCoolingDevices());
|
||||
assertListEqualsIgnoringOrder(
|
||||
mFakeHal.getCurrentCoolingDevices(false, CoolingDevice.TYPE_BATTERY),
|
||||
mService.mService.getCurrentCoolingDevices());
|
||||
assertListEqualsIgnoringOrder(
|
||||
mFakeHal.getCurrentCoolingDevices(true, CoolingDevice.TYPE_CPU),
|
||||
mService.mService.getCurrentCoolingDevicesWithType(CoolingDevice.TYPE_CPU));
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user