Merge "Support PowerHAL AIDL service" into rvc-dev am: 73e2b381f0 am: 3b1ab4d138 am: b1e96ba27e
Change-Id: Id3f01dfae77b8a9cddeb0ea1144b7e67cc9eb6e6
This commit is contained in:
@@ -38,6 +38,8 @@ interface IPowerManager
|
||||
void releaseWakeLock(IBinder lock, int flags);
|
||||
void updateWakeLockUids(IBinder lock, in int[] uids);
|
||||
oneway void powerHint(int hintId, int data);
|
||||
oneway void setPowerBoost(int boost, int durationMs);
|
||||
oneway void setPowerMode(int mode, boolean enabled);
|
||||
|
||||
void updateWakeLockWorkSource(IBinder lock, in WorkSource ws, String historyTag);
|
||||
boolean isWakeLockLevelSupported(int level);
|
||||
|
||||
@@ -201,6 +201,119 @@ public abstract class PowerManagerInternal {
|
||||
*/
|
||||
public abstract void powerHint(int hintId, int data);
|
||||
|
||||
/**
|
||||
* Boost: It is sent when user interacting with the device, for example,
|
||||
* touchscreen events are incoming.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Boost.aidl
|
||||
*/
|
||||
public static final int BOOST_INTERACTION = 0;
|
||||
|
||||
/**
|
||||
* Boost: It indicates that the framework is likely to provide a new display
|
||||
* frame soon. This implies that the device should ensure that the display
|
||||
* processing path is powered up and ready to receive that update.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Boost.aidl
|
||||
*/
|
||||
public static final int BOOST_DISPLAY_UPDATE_IMMINENT = 1;
|
||||
|
||||
/**
|
||||
* SetPowerBoost() indicates the device may need to boost some resources, as
|
||||
* the load is likely to increase before the kernel governors can react.
|
||||
* Depending on the boost, it may be appropriate to raise the frequencies of
|
||||
* CPU, GPU, memory subsystem, or stop CPU from going into deep sleep state.
|
||||
*
|
||||
* @param boost Boost which is to be set with a timeout.
|
||||
* @param durationMs The expected duration of the user's interaction, if
|
||||
* known, or 0 if the expected duration is unknown.
|
||||
* a negative value indicates canceling previous boost.
|
||||
* A given platform can choose to boost some time based on durationMs,
|
||||
* and may also pick an appropriate timeout for 0 case.
|
||||
*/
|
||||
public abstract void setPowerBoost(int boost, int durationMs);
|
||||
|
||||
/**
|
||||
* Mode: It indicates that the device is to allow wake up when the screen
|
||||
* is tapped twice.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Mode.aidl
|
||||
*/
|
||||
public static final int MODE_DOUBLE_TAP_TO_WAKE = 0;
|
||||
|
||||
/**
|
||||
* Mode: It indicates Low power mode is activated or not. Low power mode
|
||||
* is intended to save battery at the cost of performance.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Mode.aidl
|
||||
*/
|
||||
public static final int MODE_LOW_POWER = 1;
|
||||
|
||||
/**
|
||||
* Mode: It indicates Sustained Performance mode is activated or not.
|
||||
* Sustained performance mode is intended to provide a consistent level of
|
||||
* performance for a prolonged amount of time.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Mode.aidl
|
||||
*/
|
||||
public static final int MODE_SUSTAINED_PERFORMANCE = 2;
|
||||
|
||||
/**
|
||||
* Mode: It sets the device to a fixed performance level which can be sustained
|
||||
* under normal indoor conditions for at least 10 minutes.
|
||||
* Fixed performance mode puts both upper and lower bounds on performance such
|
||||
* that any workload run while in a fixed performance mode should complete in
|
||||
* a repeatable amount of time.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Mode.aidl
|
||||
*/
|
||||
public static final int MODE_FIXED_PERFORMANCE = 3;
|
||||
|
||||
/**
|
||||
* Mode: It indicates VR Mode is activated or not. VR mode is intended to
|
||||
* provide minimum guarantee for performance for the amount of time the device
|
||||
* can sustain it.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Mode.aidl
|
||||
*/
|
||||
public static final int MODE_VR = 4;
|
||||
|
||||
/**
|
||||
* Mode: It indicates that an application has been launched.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Mode.aidl
|
||||
*/
|
||||
public static final int MODE_LAUNCH = 5;
|
||||
|
||||
/**
|
||||
* Mode: It indicates that the device is about to enter a period of expensive
|
||||
* rendering.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Mode.aidl
|
||||
*/
|
||||
public static final int MODE_EXPENSIVE_RENDERING = 6;
|
||||
|
||||
/**
|
||||
* Mode: It indicates that the device is about entering/leaving interactive
|
||||
* state or on-interactive state.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Mode.aidl
|
||||
*/
|
||||
public static final int MODE_INTERACTIVE = 7;
|
||||
|
||||
/**
|
||||
* Mode: It indicates the device is in device idle, externally known as doze.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Mode.aidl
|
||||
*/
|
||||
public static final int MODE_DEVICE_IDLE = 8;
|
||||
|
||||
/**
|
||||
* Mode: It indicates that display is either off or still on but is optimized
|
||||
* for low power.
|
||||
* Defined in hardware/interfaces/power/aidl/android/hardware/power/Mode.aidl
|
||||
*/
|
||||
public static final int MODE_DISPLAY_INACTIVE = 9;
|
||||
|
||||
/**
|
||||
* SetPowerMode() is called to enable/disable specific hint mode, which
|
||||
* may result in adjustment of power/performance parameters of the
|
||||
* cpufreq governor and other controls on device side.
|
||||
*
|
||||
* @param mode Mode which is to be enable/disable.
|
||||
* @param enabled true to enable, false to disable the mode.
|
||||
*/
|
||||
public abstract void setPowerMode(int mode, boolean enabled);
|
||||
|
||||
/** Returns whether there hasn't been a user activity event for the given number of ms. */
|
||||
public abstract boolean wasDeviceIdleFor(long ms);
|
||||
|
||||
|
||||
@@ -94,6 +94,7 @@ java_library_static {
|
||||
"services-stubs",
|
||||
"services.net",
|
||||
"android.hardware.light-V2.0-java",
|
||||
"android.hardware.power-java",
|
||||
"android.hardware.power-V1.0-java",
|
||||
"android.hardware.tv.cec-V1.0-java",
|
||||
"android.hardware.vibrator-java",
|
||||
|
||||
@@ -42,6 +42,8 @@ import android.hardware.SystemSensorManager;
|
||||
import android.hardware.display.AmbientDisplayConfiguration;
|
||||
import android.hardware.display.DisplayManagerInternal;
|
||||
import android.hardware.display.DisplayManagerInternal.DisplayPowerRequest;
|
||||
import android.hardware.power.Boost;
|
||||
import android.hardware.power.Mode;
|
||||
import android.hardware.power.V1_0.PowerHint;
|
||||
import android.net.Uri;
|
||||
import android.os.BatteryManager;
|
||||
@@ -732,6 +734,16 @@ public final class PowerManagerService extends SystemService
|
||||
PowerManagerService.nativeSendPowerHint(hintId, data);
|
||||
}
|
||||
|
||||
/** Wrapper for PowerManager.nativeSetPowerBoost */
|
||||
public void nativeSetPowerBoost(int boost, int durationMs) {
|
||||
PowerManagerService.nativeSetPowerBoost(boost, durationMs);
|
||||
}
|
||||
|
||||
/** Wrapper for PowerManager.nativeSetPowerMode */
|
||||
public void nativeSetPowerMode(int mode, boolean enabled) {
|
||||
PowerManagerService.nativeSetPowerMode(mode, enabled);
|
||||
}
|
||||
|
||||
/** Wrapper for PowerManager.nativeSetFeature */
|
||||
public void nativeSetFeature(int featureId, int data) {
|
||||
PowerManagerService.nativeSetFeature(featureId, data);
|
||||
@@ -817,6 +829,8 @@ public final class PowerManagerService extends SystemService
|
||||
private static native void nativeSetInteractive(boolean enable);
|
||||
private static native void nativeSetAutoSuspend(boolean enable);
|
||||
private static native void nativeSendPowerHint(int hintId, int data);
|
||||
private static native void nativeSetPowerBoost(int boost, int durationMs);
|
||||
private static native void nativeSetPowerMode(int mode, boolean enabled);
|
||||
private static native void nativeSetFeature(int featureId, int data);
|
||||
private static native boolean nativeForceSuspend();
|
||||
|
||||
@@ -3608,6 +3622,16 @@ public final class PowerManagerService extends SystemService
|
||||
mNativeWrapper.nativeSendPowerHint(hintId, data);
|
||||
}
|
||||
|
||||
private void setPowerBoostInternal(int boost, int durationMs) {
|
||||
// Maybe filter the event.
|
||||
mNativeWrapper.nativeSetPowerBoost(boost, durationMs);
|
||||
}
|
||||
|
||||
private void setPowerModeInternal(int mode, boolean enabled) {
|
||||
// Maybe filter the event.
|
||||
mNativeWrapper.nativeSetPowerMode(mode, enabled);
|
||||
}
|
||||
|
||||
@VisibleForTesting
|
||||
boolean wasDeviceIdleForInternal(long ms) {
|
||||
synchronized (mLock) {
|
||||
@@ -4663,6 +4687,26 @@ public final class PowerManagerService extends SystemService
|
||||
powerHintInternal(hintId, data);
|
||||
}
|
||||
|
||||
@Override // Binder call
|
||||
public void setPowerBoost(int boost, int durationMs) {
|
||||
if (!mSystemReady) {
|
||||
// Service not ready yet, so who the heck cares about power hints, bah.
|
||||
return;
|
||||
}
|
||||
mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
|
||||
setPowerBoostInternal(boost, durationMs);
|
||||
}
|
||||
|
||||
@Override // Binder call
|
||||
public void setPowerMode(int mode, boolean enabled) {
|
||||
if (!mSystemReady) {
|
||||
// Service not ready yet, so who the heck cares about power hints, bah.
|
||||
return;
|
||||
}
|
||||
mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
|
||||
setPowerModeInternal(mode, enabled);
|
||||
}
|
||||
|
||||
@Override // Binder call
|
||||
public void acquireWakeLock(IBinder lock, int flags, String tag, String packageName,
|
||||
WorkSource ws, String historyTag) {
|
||||
@@ -5457,6 +5501,15 @@ public final class PowerManagerService extends SystemService
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setPowerBoost(int boost, int durationMs) {
|
||||
setPowerBoostInternal(boost, durationMs);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setPowerMode(int mode, boolean enabled) {
|
||||
setPowerModeInternal(mode, enabled);
|
||||
}
|
||||
@Override
|
||||
public boolean wasDeviceIdleFor(long ms) {
|
||||
return wasDeviceIdleForInternal(ms);
|
||||
}
|
||||
|
||||
@@ -146,6 +146,7 @@ cc_defaults {
|
||||
"android.hardware.light@2.0",
|
||||
"android.hardware.power@1.0",
|
||||
"android.hardware.power@1.1",
|
||||
"android.hardware.power-cpp",
|
||||
"android.hardware.power.stats@1.0",
|
||||
"android.hardware.thermal@1.0",
|
||||
"android.hardware.tv.cec@1.0",
|
||||
|
||||
@@ -67,9 +67,9 @@ namespace android
|
||||
|
||||
static bool wakeup_init = false;
|
||||
static sem_t wakeup_sem;
|
||||
extern sp<IPowerV1_0> getPowerHalV1_0();
|
||||
extern sp<IPowerV1_1> getPowerHalV1_1();
|
||||
extern bool processPowerHalReturn(const Return<void> &ret, const char* functionName);
|
||||
extern sp<IPowerV1_0> getPowerHalHidlV1_0();
|
||||
extern sp<IPowerV1_1> getPowerHalHidlV1_1();
|
||||
extern bool processPowerHalReturn(bool isOk, const char* functionName);
|
||||
extern sp<ISuspendControlService> getSuspendControl();
|
||||
|
||||
// Java methods used in getLowPowerStats
|
||||
@@ -596,7 +596,7 @@ static void getPowerStatsHalRailEnergyData(JNIEnv* env, jobject jrailStats) {
|
||||
|
||||
// The caller must be holding powerHalMutex.
|
||||
static void getPowerHalLowPowerData(JNIEnv* env, jobject jrpmStats) {
|
||||
sp<IPowerV1_0> powerHalV1_0 = getPowerHalV1_0();
|
||||
sp<IPowerV1_0> powerHalV1_0 = getPowerHalHidlV1_0();
|
||||
if (powerHalV1_0 == nullptr) {
|
||||
ALOGE("Power Hal not loaded");
|
||||
return;
|
||||
@@ -629,12 +629,12 @@ static void getPowerHalLowPowerData(JNIEnv* env, jobject jrpmStats) {
|
||||
}
|
||||
}
|
||||
});
|
||||
if (!processPowerHalReturn(ret, "getPlatformLowPowerStats")) {
|
||||
if (!processPowerHalReturn(ret.isOk(), "getPlatformLowPowerStats")) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Trying to get IPower 1.1, this will succeed only for devices supporting 1.1
|
||||
sp<IPowerV1_1> powerHal_1_1 = getPowerHalV1_1();
|
||||
sp<IPowerV1_1> powerHal_1_1 = getPowerHalHidlV1_1();
|
||||
if (powerHal_1_1 == nullptr) {
|
||||
// This device does not support IPower@1.1, exiting gracefully
|
||||
return;
|
||||
@@ -665,7 +665,7 @@ static void getPowerHalLowPowerData(JNIEnv* env, jobject jrpmStats) {
|
||||
}
|
||||
}
|
||||
});
|
||||
processPowerHalReturn(ret, "getSubsystemLowPowerStats");
|
||||
processPowerHalReturn(ret.isOk(), "getSubsystemLowPowerStats");
|
||||
}
|
||||
|
||||
static jint getPowerHalPlatformData(JNIEnv* env, jobject outBuf) {
|
||||
@@ -675,7 +675,7 @@ static jint getPowerHalPlatformData(JNIEnv* env, jobject outBuf) {
|
||||
int total_added = -1;
|
||||
|
||||
{
|
||||
sp<IPowerV1_0> powerHalV1_0 = getPowerHalV1_0();
|
||||
sp<IPowerV1_0> powerHalV1_0 = getPowerHalHidlV1_0();
|
||||
if (powerHalV1_0 == nullptr) {
|
||||
ALOGE("Power Hal not loaded");
|
||||
return -1;
|
||||
@@ -733,7 +733,7 @@ static jint getPowerHalPlatformData(JNIEnv* env, jobject outBuf) {
|
||||
}
|
||||
);
|
||||
|
||||
if (!processPowerHalReturn(ret, "getPlatformLowPowerStats")) {
|
||||
if (!processPowerHalReturn(ret.isOk(), "getPlatformLowPowerStats")) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
@@ -753,7 +753,7 @@ static jint getPowerHalSubsystemData(JNIEnv* env, jobject outBuf) {
|
||||
|
||||
{
|
||||
// Trying to get 1.1, this will succeed only for devices supporting 1.1
|
||||
powerHal_1_1 = getPowerHalV1_1();
|
||||
powerHal_1_1 = getPowerHalHidlV1_1();
|
||||
if (powerHal_1_1 == nullptr) {
|
||||
//This device does not support IPower@1.1, exiting gracefully
|
||||
return 0;
|
||||
@@ -820,7 +820,7 @@ static jint getPowerHalSubsystemData(JNIEnv* env, jobject outBuf) {
|
||||
}
|
||||
);
|
||||
|
||||
if (!processPowerHalReturn(ret, "getSubsystemLowPowerStats")) {
|
||||
if (!processPowerHalReturn(ret.isOk(), "getSubsystemLowPowerStats")) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,6 +19,9 @@
|
||||
//#define LOG_NDEBUG 0
|
||||
|
||||
#include <android/hardware/power/1.1/IPower.h>
|
||||
#include <android/hardware/power/Boost.h>
|
||||
#include <android/hardware/power/IPower.h>
|
||||
#include <android/hardware/power/Mode.h>
|
||||
#include <android/system/suspend/1.0/ISystemSuspend.h>
|
||||
#include <android/system/suspend/ISuspendControlService.h>
|
||||
#include <nativehelper/JNIHelp.h>
|
||||
@@ -45,6 +48,8 @@
|
||||
|
||||
using android::hardware::Return;
|
||||
using android::hardware::Void;
|
||||
using android::hardware::power::Boost;
|
||||
using android::hardware::power::Mode;
|
||||
using android::hardware::power::V1_0::PowerHint;
|
||||
using android::hardware::power::V1_0::Feature;
|
||||
using android::String8;
|
||||
@@ -54,6 +59,7 @@ using android::system::suspend::V1_0::WakeLockType;
|
||||
using android::system::suspend::ISuspendControlService;
|
||||
using IPowerV1_1 = android::hardware::power::V1_1::IPower;
|
||||
using IPowerV1_0 = android::hardware::power::V1_0::IPower;
|
||||
using IPowerAidl = android::hardware::power::IPower;
|
||||
|
||||
namespace android {
|
||||
|
||||
@@ -66,11 +72,18 @@ static struct {
|
||||
// ----------------------------------------------------------------------------
|
||||
|
||||
static jobject gPowerManagerServiceObj;
|
||||
// Use getPowerHal* to retrieve a copy
|
||||
static sp<IPowerV1_0> gPowerHalV1_0_ = nullptr;
|
||||
static sp<IPowerV1_1> gPowerHalV1_1_ = nullptr;
|
||||
static bool gPowerHalExists = true;
|
||||
static sp<IPowerV1_0> gPowerHalHidlV1_0_ = nullptr;
|
||||
static sp<IPowerV1_1> gPowerHalHidlV1_1_ = nullptr;
|
||||
static sp<IPowerAidl> gPowerHalAidl_ = nullptr;
|
||||
static std::mutex gPowerHalMutex;
|
||||
|
||||
enum class HalVersion {
|
||||
NONE,
|
||||
HIDL_1_0,
|
||||
HIDL_1_1,
|
||||
AIDL,
|
||||
};
|
||||
|
||||
static nsecs_t gLastEventTime[USER_ACTIVITY_EVENT_LAST + 1];
|
||||
|
||||
// Throttling interval for user activity calls.
|
||||
@@ -88,68 +101,207 @@ static bool checkAndClearExceptionFromCallback(JNIEnv* env, const char* methodNa
|
||||
return false;
|
||||
}
|
||||
|
||||
// Check validity of current handle to the power HAL service, and call getService() if necessary.
|
||||
// Check validity of current handle to the power HAL service, and connect to it if necessary.
|
||||
// The caller must be holding gPowerHalMutex.
|
||||
static void connectPowerHalLocked() {
|
||||
if (gPowerHalExists && gPowerHalV1_0_ == nullptr) {
|
||||
gPowerHalV1_0_ = IPowerV1_0::getService();
|
||||
if (gPowerHalV1_0_ != nullptr) {
|
||||
ALOGI("Loaded power HAL 1.0 service");
|
||||
// Try cast to powerHAL V1_1
|
||||
gPowerHalV1_1_ = IPowerV1_1::castFrom(gPowerHalV1_0_);
|
||||
if (gPowerHalV1_1_ == nullptr) {
|
||||
} else {
|
||||
ALOGI("Loaded power HAL 1.1 service");
|
||||
}
|
||||
static HalVersion connectPowerHalLocked() {
|
||||
static bool gPowerHalHidlExists = true;
|
||||
static bool gPowerHalAidlExists = true;
|
||||
if (!gPowerHalHidlExists && !gPowerHalAidlExists) {
|
||||
return HalVersion::NONE;
|
||||
}
|
||||
if (gPowerHalAidlExists) {
|
||||
if (!gPowerHalAidl_) {
|
||||
gPowerHalAidl_ = waitForVintfService<IPowerAidl>();
|
||||
}
|
||||
if (gPowerHalAidl_) {
|
||||
ALOGI("Successfully connected to Power HAL AIDL service.");
|
||||
return HalVersion::AIDL;
|
||||
} else {
|
||||
ALOGI("Couldn't load power HAL service");
|
||||
gPowerHalExists = false;
|
||||
gPowerHalAidlExists = false;
|
||||
}
|
||||
}
|
||||
if (gPowerHalHidlExists && gPowerHalHidlV1_0_ == nullptr) {
|
||||
gPowerHalHidlV1_0_ = IPowerV1_0::getService();
|
||||
if (gPowerHalHidlV1_0_) {
|
||||
ALOGI("Successfully connected to Power HAL HIDL 1.0 service.");
|
||||
// Try cast to powerHAL HIDL V1_1
|
||||
gPowerHalHidlV1_1_ = IPowerV1_1::castFrom(gPowerHalHidlV1_0_);
|
||||
if (gPowerHalHidlV1_1_) {
|
||||
ALOGI("Successfully connected to Power HAL HIDL 1.1 service.");
|
||||
}
|
||||
} else {
|
||||
ALOGI("Couldn't load power HAL HIDL service");
|
||||
gPowerHalHidlExists = false;
|
||||
return HalVersion::NONE;
|
||||
}
|
||||
}
|
||||
if (gPowerHalHidlV1_1_) {
|
||||
return HalVersion::HIDL_1_1;
|
||||
} else if (gPowerHalHidlV1_0_) {
|
||||
return HalVersion::HIDL_1_0;
|
||||
}
|
||||
return HalVersion::NONE;
|
||||
}
|
||||
|
||||
// Retrieve a copy of PowerHAL V1_0
|
||||
sp<IPowerV1_0> getPowerHalV1_0() {
|
||||
// Retrieve a copy of PowerHAL HIDL V1_0
|
||||
sp<IPowerV1_0> getPowerHalHidlV1_0() {
|
||||
std::lock_guard<std::mutex> lock(gPowerHalMutex);
|
||||
connectPowerHalLocked();
|
||||
return gPowerHalV1_0_;
|
||||
HalVersion halVersion = connectPowerHalLocked();
|
||||
if (halVersion == HalVersion::HIDL_1_0 || halVersion == HalVersion::HIDL_1_1) {
|
||||
return gPowerHalHidlV1_0_;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
// Retrieve a copy of PowerHAL V1_1
|
||||
sp<IPowerV1_1> getPowerHalV1_1() {
|
||||
// Retrieve a copy of PowerHAL HIDL V1_1
|
||||
sp<IPowerV1_1> getPowerHalHidlV1_1() {
|
||||
std::lock_guard<std::mutex> lock(gPowerHalMutex);
|
||||
connectPowerHalLocked();
|
||||
return gPowerHalV1_1_;
|
||||
if (connectPowerHalLocked() == HalVersion::HIDL_1_1) {
|
||||
return gPowerHalHidlV1_1_;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
// Check if a call to a power HAL function failed; if so, log the failure and invalidate the
|
||||
// current handle to the power HAL service.
|
||||
bool processPowerHalReturn(const Return<void> &ret, const char* functionName) {
|
||||
if (!ret.isOk()) {
|
||||
bool processPowerHalReturn(bool isOk, const char* functionName) {
|
||||
if (!isOk) {
|
||||
ALOGE("%s() failed: power HAL service not available.", functionName);
|
||||
gPowerHalMutex.lock();
|
||||
gPowerHalV1_0_ = nullptr;
|
||||
gPowerHalV1_1_ = nullptr;
|
||||
gPowerHalHidlV1_0_ = nullptr;
|
||||
gPowerHalHidlV1_1_ = nullptr;
|
||||
gPowerHalAidl_ = nullptr;
|
||||
gPowerHalMutex.unlock();
|
||||
}
|
||||
return ret.isOk();
|
||||
return isOk;
|
||||
}
|
||||
|
||||
static void sendPowerHint(PowerHint hintId, uint32_t data) {
|
||||
sp<IPowerV1_1> powerHalV1_1 = getPowerHalV1_1();
|
||||
Return<void> ret;
|
||||
if (powerHalV1_1 != nullptr) {
|
||||
ret = powerHalV1_1->powerHintAsync(hintId, data);
|
||||
processPowerHalReturn(ret, "powerHintAsync");
|
||||
} else {
|
||||
sp<IPowerV1_0> powerHalV1_0 = getPowerHalV1_0();
|
||||
if (powerHalV1_0 != nullptr) {
|
||||
ret = powerHalV1_0->powerHint(hintId, data);
|
||||
processPowerHalReturn(ret, "powerHint");
|
||||
std::unique_lock<std::mutex> lock(gPowerHalMutex);
|
||||
switch (connectPowerHalLocked()) {
|
||||
case HalVersion::NONE:
|
||||
return;
|
||||
case HalVersion::HIDL_1_0: {
|
||||
sp<IPowerV1_0> handle = gPowerHalHidlV1_0_;
|
||||
lock.unlock();
|
||||
auto ret = handle->powerHint(hintId, data);
|
||||
processPowerHalReturn(ret.isOk(), "powerHint");
|
||||
break;
|
||||
}
|
||||
case HalVersion::HIDL_1_1: {
|
||||
sp<IPowerV1_1> handle = gPowerHalHidlV1_1_;
|
||||
lock.unlock();
|
||||
auto ret = handle->powerHintAsync(hintId, data);
|
||||
processPowerHalReturn(ret.isOk(), "powerHintAsync");
|
||||
break;
|
||||
}
|
||||
case HalVersion::AIDL: {
|
||||
if (hintId == PowerHint::INTERACTION) {
|
||||
sp<IPowerAidl> handle = gPowerHalAidl_;
|
||||
lock.unlock();
|
||||
auto ret = handle->setBoost(Boost::INTERACTION, data);
|
||||
processPowerHalReturn(ret.isOk(), "setBoost");
|
||||
break;
|
||||
} else if (hintId == PowerHint::LAUNCH) {
|
||||
sp<IPowerAidl> handle = gPowerHalAidl_;
|
||||
lock.unlock();
|
||||
auto ret = handle->setMode(Mode::LAUNCH, static_cast<bool>(data));
|
||||
processPowerHalReturn(ret.isOk(), "setMode");
|
||||
break;
|
||||
} else {
|
||||
ALOGE("Unsupported power hint: %s.", toString(hintId).c_str());
|
||||
return;
|
||||
}
|
||||
}
|
||||
default: {
|
||||
ALOGE("Unknown power HAL state");
|
||||
return;
|
||||
}
|
||||
}
|
||||
SurfaceComposerClient::notifyPowerHint(static_cast<int32_t>(hintId));
|
||||
}
|
||||
|
||||
enum class HalSupport {
|
||||
UNKNOWN = 0,
|
||||
ON,
|
||||
OFF,
|
||||
};
|
||||
|
||||
static void setPowerBoost(Boost boost, int32_t durationMs) {
|
||||
// Android framework only sends boost upto DISPLAY_UPDATE_IMMINENT.
|
||||
// Need to increase the array size if more boost supported.
|
||||
static std::array<std::atomic<HalSupport>,
|
||||
static_cast<int32_t>(Boost::DISPLAY_UPDATE_IMMINENT) + 1>
|
||||
boostSupportedArray = {HalSupport::UNKNOWN};
|
||||
|
||||
// Quick return if boost is not supported by HAL
|
||||
if (boost > Boost::DISPLAY_UPDATE_IMMINENT ||
|
||||
boostSupportedArray[static_cast<int32_t>(boost)] == HalSupport::OFF) {
|
||||
ALOGV("Skipped setPowerBoost %s because HAL doesn't support it", toString(boost).c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
std::unique_lock<std::mutex> lock(gPowerHalMutex);
|
||||
if (connectPowerHalLocked() != HalVersion::AIDL) {
|
||||
ALOGV("Power HAL AIDL not available");
|
||||
return;
|
||||
}
|
||||
sp<IPowerAidl> handle = gPowerHalAidl_;
|
||||
lock.unlock();
|
||||
|
||||
if (boostSupportedArray[static_cast<int32_t>(boost)] == HalSupport::UNKNOWN) {
|
||||
bool isSupported = false;
|
||||
handle->isBoostSupported(boost, &isSupported);
|
||||
boostSupportedArray[static_cast<int32_t>(boost)] =
|
||||
isSupported ? HalSupport::ON : HalSupport::OFF;
|
||||
if (!isSupported) {
|
||||
ALOGV("Skipped setPowerBoost %s because HAL doesn't support it",
|
||||
toString(boost).c_str());
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
SurfaceComposerClient::notifyPowerHint(static_cast<int32_t>(hintId));
|
||||
auto ret = handle->setBoost(boost, durationMs);
|
||||
processPowerHalReturn(ret.isOk(), "setPowerBoost");
|
||||
}
|
||||
|
||||
static void setPowerMode(Mode mode, bool enabled) {
|
||||
// Android framework only sends mode upto DISPLAY_INACTIVE.
|
||||
// Need to increase the array if more mode supported.
|
||||
static std::array<std::atomic<HalSupport>,
|
||||
static_cast<int32_t>(Mode::DISPLAY_INACTIVE) + 1>
|
||||
modeSupportedArray = {HalSupport::UNKNOWN};
|
||||
|
||||
// Quick return if mode is not supported by HAL
|
||||
if (mode > Mode::DISPLAY_INACTIVE ||
|
||||
modeSupportedArray[static_cast<int32_t>(mode)] == HalSupport::OFF) {
|
||||
ALOGV("Skipped setPowerMode %s because HAL doesn't support it", toString(mode).c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
std::unique_lock<std::mutex> lock(gPowerHalMutex);
|
||||
if (connectPowerHalLocked() != HalVersion::AIDL) {
|
||||
ALOGV("Power HAL AIDL not available");
|
||||
return;
|
||||
}
|
||||
sp<IPowerAidl> handle = gPowerHalAidl_;
|
||||
lock.unlock();
|
||||
|
||||
if (modeSupportedArray[static_cast<int32_t>(mode)] == HalSupport::UNKNOWN) {
|
||||
bool isSupported = false;
|
||||
handle->isModeSupported(mode, &isSupported);
|
||||
modeSupportedArray[static_cast<int32_t>(mode)] =
|
||||
isSupported ? HalSupport::ON : HalSupport::OFF;
|
||||
if (!isSupported) {
|
||||
ALOGV("Skipped setPowerMode %s because HAL doesn't support it", toString(mode).c_str());
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
auto ret = handle->setMode(mode, enabled);
|
||||
processPowerHalReturn(ret.isOk(), "setPowerMode");
|
||||
}
|
||||
|
||||
void android_server_PowerManagerService_userActivity(nsecs_t eventTime, int32_t eventType) {
|
||||
@@ -253,14 +405,34 @@ static void nativeReleaseSuspendBlocker(JNIEnv *env, jclass /* clazz */, jstring
|
||||
}
|
||||
|
||||
static void nativeSetInteractive(JNIEnv* /* env */, jclass /* clazz */, jboolean enable) {
|
||||
sp<IPowerV1_0> powerHalV1_0 = getPowerHalV1_0();
|
||||
if (powerHalV1_0 != nullptr) {
|
||||
android::base::Timer t;
|
||||
Return<void> ret = powerHalV1_0->setInteractive(enable);
|
||||
processPowerHalReturn(ret, "setInteractive");
|
||||
if (t.duration() > 20ms) {
|
||||
ALOGD("Excessive delay in setInteractive(%s) while turning screen %s",
|
||||
enable ? "true" : "false", enable ? "on" : "off");
|
||||
std::unique_lock<std::mutex> lock(gPowerHalMutex);
|
||||
switch (connectPowerHalLocked()) {
|
||||
case HalVersion::NONE:
|
||||
return;
|
||||
case HalVersion::HIDL_1_0:
|
||||
FALLTHROUGH_INTENDED;
|
||||
case HalVersion::HIDL_1_1: {
|
||||
android::base::Timer t;
|
||||
sp<IPowerV1_0> handle = gPowerHalHidlV1_0_;
|
||||
lock.unlock();
|
||||
auto ret = handle->setInteractive(enable);
|
||||
processPowerHalReturn(ret.isOk(), "setInteractive");
|
||||
if (t.duration() > 20ms) {
|
||||
ALOGD("Excessive delay in setInteractive(%s) while turning screen %s",
|
||||
enable ? "true" : "false", enable ? "on" : "off");
|
||||
}
|
||||
return;
|
||||
}
|
||||
case HalVersion::AIDL: {
|
||||
sp<IPowerAidl> handle = gPowerHalAidl_;
|
||||
lock.unlock();
|
||||
auto ret = handle->setMode(Mode::INTERACTIVE, enable);
|
||||
processPowerHalReturn(ret.isOk(), "setMode");
|
||||
return;
|
||||
}
|
||||
default: {
|
||||
ALOGE("Unknown power HAL state");
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -285,11 +457,38 @@ static void nativeSendPowerHint(JNIEnv* /* env */, jclass /* clazz */, jint hint
|
||||
sendPowerHint(static_cast<PowerHint>(hintId), data);
|
||||
}
|
||||
|
||||
static void nativeSetPowerBoost(JNIEnv* /* env */, jclass /* clazz */, jint boost,
|
||||
jint durationMs) {
|
||||
setPowerBoost(static_cast<Boost>(boost), durationMs);
|
||||
}
|
||||
|
||||
static void nativeSetPowerMode(JNIEnv* /* env */, jclass /* clazz */, jint mode, jboolean enabled) {
|
||||
setPowerMode(static_cast<Mode>(mode), enabled);
|
||||
}
|
||||
|
||||
static void nativeSetFeature(JNIEnv* /* env */, jclass /* clazz */, jint featureId, jint data) {
|
||||
sp<IPowerV1_0> powerHalV1_0 = getPowerHalV1_0();
|
||||
if (powerHalV1_0 != nullptr) {
|
||||
Return<void> ret = powerHalV1_0->setFeature((Feature)featureId, static_cast<bool>(data));
|
||||
processPowerHalReturn(ret, "setFeature");
|
||||
std::unique_lock<std::mutex> lock(gPowerHalMutex);
|
||||
switch (connectPowerHalLocked()) {
|
||||
case HalVersion::NONE:
|
||||
return;
|
||||
case HalVersion::HIDL_1_0:
|
||||
FALLTHROUGH_INTENDED;
|
||||
case HalVersion::HIDL_1_1: {
|
||||
sp<IPowerV1_0> handle = gPowerHalHidlV1_0_;
|
||||
lock.unlock();
|
||||
auto ret = handle->setFeature(static_cast<Feature>(featureId), static_cast<bool>(data));
|
||||
processPowerHalReturn(ret.isOk(), "setFeature");
|
||||
return;
|
||||
}
|
||||
case HalVersion::AIDL: {
|
||||
auto ret = gPowerHalAidl_->setMode(Mode::DOUBLE_TAP_TO_WAKE, static_cast<bool>(data));
|
||||
processPowerHalReturn(ret.isOk(), "setMode");
|
||||
return;
|
||||
}
|
||||
default: {
|
||||
ALOGE("Unknown power HAL state");
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -317,6 +516,10 @@ static const JNINativeMethod gPowerManagerServiceMethods[] = {
|
||||
(void*) nativeSetAutoSuspend },
|
||||
{ "nativeSendPowerHint", "(II)V",
|
||||
(void*) nativeSendPowerHint },
|
||||
{ "nativeSetPowerBoost", "(II)V",
|
||||
(void*) nativeSetPowerBoost },
|
||||
{ "nativeSetPowerMode", "(IZ)V",
|
||||
(void*) nativeSetPowerMode },
|
||||
{ "nativeSetFeature", "(II)V",
|
||||
(void*) nativeSetFeature },
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user