Merge "Enable ANGLE as a Game Dashboard Intervention" into sc-qpr1-dev
This commit is contained in:
committed by
Android (Google) Code Review
commit
4de992c9cb
@@ -135,6 +135,7 @@ public final class GameManager {
|
|||||||
throw e.rethrowFromSystemServer();
|
throw e.rethrowFromSystemServer();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a list of supported game modes for a given package.
|
* Returns a list of supported game modes for a given package.
|
||||||
* <p>
|
* <p>
|
||||||
@@ -151,4 +152,20 @@ public final class GameManager {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns if ANGLE is enabled for a given package.
|
||||||
|
* <p>
|
||||||
|
* The caller must have {@link android.Manifest.permission#MANAGE_GAME_MODE}.
|
||||||
|
*
|
||||||
|
* @hide
|
||||||
|
*/
|
||||||
|
@UserHandleAware
|
||||||
|
@RequiresPermission(Manifest.permission.MANAGE_GAME_MODE)
|
||||||
|
public @GameMode boolean isAngleEnabled(@NonNull String packageName) {
|
||||||
|
try {
|
||||||
|
return mService.getAngleEnabled(packageName, mContext.getUserId());
|
||||||
|
} catch (RemoteException e) {
|
||||||
|
throw e.rethrowFromSystemServer();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -23,4 +23,5 @@ interface IGameManagerService {
|
|||||||
int getGameMode(String packageName, int userId);
|
int getGameMode(String packageName, int userId);
|
||||||
void setGameMode(String packageName, int gameMode, int userId);
|
void setGameMode(String packageName, int gameMode, int userId);
|
||||||
int[] getAvailableGameModes(String packageName);
|
int[] getAvailableGameModes(String packageName);
|
||||||
|
boolean getAngleEnabled(String packageName, int userId);
|
||||||
}
|
}
|
||||||
@@ -17,6 +17,7 @@
|
|||||||
package android.os;
|
package android.os;
|
||||||
|
|
||||||
import android.app.Activity;
|
import android.app.Activity;
|
||||||
|
import android.app.GameManager;
|
||||||
import android.content.BroadcastReceiver;
|
import android.content.BroadcastReceiver;
|
||||||
import android.content.ContentResolver;
|
import android.content.ContentResolver;
|
||||||
import android.content.Context;
|
import android.content.Context;
|
||||||
@@ -113,6 +114,7 @@ public class GraphicsEnvironment {
|
|||||||
private ClassLoader mClassLoader;
|
private ClassLoader mClassLoader;
|
||||||
private String mLibrarySearchPaths;
|
private String mLibrarySearchPaths;
|
||||||
private String mLibraryPermittedPaths;
|
private String mLibraryPermittedPaths;
|
||||||
|
private GameManager mGameManager;
|
||||||
|
|
||||||
private int mAngleOptInIndex = -1;
|
private int mAngleOptInIndex = -1;
|
||||||
|
|
||||||
@@ -125,6 +127,8 @@ public class GraphicsEnvironment {
|
|||||||
final ApplicationInfo appInfoWithMetaData =
|
final ApplicationInfo appInfoWithMetaData =
|
||||||
getAppInfoWithMetadata(context, pm, packageName);
|
getAppInfoWithMetadata(context, pm, packageName);
|
||||||
|
|
||||||
|
mGameManager = context.getSystemService(GameManager.class);
|
||||||
|
|
||||||
Trace.traceBegin(Trace.TRACE_TAG_GRAPHICS, "setupGpuLayers");
|
Trace.traceBegin(Trace.TRACE_TAG_GRAPHICS, "setupGpuLayers");
|
||||||
setupGpuLayers(context, coreSettings, pm, packageName, appInfoWithMetaData);
|
setupGpuLayers(context, coreSettings, pm, packageName, appInfoWithMetaData);
|
||||||
Trace.traceEnd(Trace.TRACE_TAG_GRAPHICS);
|
Trace.traceEnd(Trace.TRACE_TAG_GRAPHICS);
|
||||||
@@ -142,6 +146,23 @@ public class GraphicsEnvironment {
|
|||||||
Trace.traceEnd(Trace.TRACE_TAG_GRAPHICS);
|
Trace.traceEnd(Trace.TRACE_TAG_GRAPHICS);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Query to determine if the Game Mode has enabled ANGLE.
|
||||||
|
*/
|
||||||
|
private boolean isAngleEnabledByGameMode(Context context, String packageName) {
|
||||||
|
try {
|
||||||
|
final boolean gameModeEnabledAngle =
|
||||||
|
(mGameManager != null) && mGameManager.isAngleEnabled(packageName);
|
||||||
|
Log.v(TAG, "ANGLE GameManagerService for " + packageName + ": " + gameModeEnabledAngle);
|
||||||
|
return gameModeEnabledAngle;
|
||||||
|
} catch (SecurityException e) {
|
||||||
|
Log.e(TAG, "Caught exception while querying GameManagerService if ANGLE is enabled "
|
||||||
|
+ "for package: " + packageName);
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Query to determine if ANGLE should be used
|
* Query to determine if ANGLE should be used
|
||||||
*/
|
*/
|
||||||
@@ -163,7 +184,9 @@ public class GraphicsEnvironment {
|
|||||||
Log.v(TAG, "ANGLE developer option for " + packageName + ": " + devOptIn);
|
Log.v(TAG, "ANGLE developer option for " + packageName + ": " + devOptIn);
|
||||||
}
|
}
|
||||||
|
|
||||||
return requested;
|
final boolean gameModeEnabledAngle = isAngleEnabledByGameMode(context, packageName);
|
||||||
|
|
||||||
|
return requested || gameModeEnabledAngle;
|
||||||
}
|
}
|
||||||
|
|
||||||
private int getVulkanVersion(PackageManager pm) {
|
private int getVulkanVersion(PackageManager pm) {
|
||||||
@@ -521,16 +544,20 @@ public class GraphicsEnvironment {
|
|||||||
|
|
||||||
if (DEBUG) Log.v(TAG, "ANGLE package libs: " + paths);
|
if (DEBUG) Log.v(TAG, "ANGLE package libs: " + paths);
|
||||||
|
|
||||||
// If the user has set the developer option to something other than default,
|
// We need to call setAngleInfo() with the package name and the developer option value
|
||||||
// we need to call setAngleInfo() with the package name and the developer
|
//(native/angle/other). Then later when we are actually trying to load a driver,
|
||||||
// option value (native/angle/other). Then later when we are actually trying to
|
//GraphicsEnv::getShouldUseAngle() has seen the package name before and can confidently
|
||||||
// load a driver, GraphicsEnv::getShouldUseAngle() has seen the package name before
|
//answer yes/no based on the previously set developer option value.
|
||||||
// and can confidently answer yes/no based on the previously set developer
|
final String devOptIn;
|
||||||
// option value.
|
|
||||||
final String devOptIn = getDriverForPackage(context, bundle, packageName);
|
|
||||||
final String[] features = getAngleEglFeatures(context, bundle);
|
final String[] features = getAngleEglFeatures(context, bundle);
|
||||||
|
final boolean gameModeEnabledAngle = isAngleEnabledByGameMode(context, packageName);
|
||||||
|
if (gameModeEnabledAngle) {
|
||||||
|
devOptIn = ANGLE_GL_DRIVER_CHOICE_ANGLE;
|
||||||
|
} else {
|
||||||
|
devOptIn = getDriverForPackage(context, bundle, packageName);
|
||||||
|
}
|
||||||
setAngleInfo(paths, packageName, devOptIn, features);
|
setAngleInfo(paths, packageName, devOptIn, features);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -271,6 +271,13 @@ public final class GameManagerService extends IGameManagerService.Stub {
|
|||||||
public static final String METADATA_WM_ALLOW_DOWNSCALE =
|
public static final String METADATA_WM_ALLOW_DOWNSCALE =
|
||||||
"com.android.graphics.intervention.wm.allowDownscale";
|
"com.android.graphics.intervention.wm.allowDownscale";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Metadata that can be included in the app manifest to allow/disallow any ANGLE
|
||||||
|
* interventions. Default value is TRUE.
|
||||||
|
*/
|
||||||
|
public static final String METADATA_ANGLE_ALLOW_ANGLE =
|
||||||
|
"com.android.graphics.intervention.angle.allowAngle";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Metadata that needs to be included in the app manifest to OPT-IN to PERFORMANCE mode.
|
* Metadata that needs to be included in the app manifest to OPT-IN to PERFORMANCE mode.
|
||||||
* This means the app will assume full responsibility for the experience provided by this
|
* This means the app will assume full responsibility for the experience provided by this
|
||||||
@@ -294,6 +301,7 @@ public final class GameManagerService extends IGameManagerService.Stub {
|
|||||||
private boolean mPerfModeOptedIn;
|
private boolean mPerfModeOptedIn;
|
||||||
private boolean mBatteryModeOptedIn;
|
private boolean mBatteryModeOptedIn;
|
||||||
private boolean mAllowDownscale;
|
private boolean mAllowDownscale;
|
||||||
|
private boolean mAllowAngle;
|
||||||
|
|
||||||
GamePackageConfiguration(String packageName, int userId) {
|
GamePackageConfiguration(String packageName, int userId) {
|
||||||
mPackageName = packageName;
|
mPackageName = packageName;
|
||||||
@@ -305,10 +313,12 @@ public final class GameManagerService extends IGameManagerService.Stub {
|
|||||||
mPerfModeOptedIn = ai.metaData.getBoolean(METADATA_PERFORMANCE_MODE_ENABLE);
|
mPerfModeOptedIn = ai.metaData.getBoolean(METADATA_PERFORMANCE_MODE_ENABLE);
|
||||||
mBatteryModeOptedIn = ai.metaData.getBoolean(METADATA_BATTERY_MODE_ENABLE);
|
mBatteryModeOptedIn = ai.metaData.getBoolean(METADATA_BATTERY_MODE_ENABLE);
|
||||||
mAllowDownscale = ai.metaData.getBoolean(METADATA_WM_ALLOW_DOWNSCALE, true);
|
mAllowDownscale = ai.metaData.getBoolean(METADATA_WM_ALLOW_DOWNSCALE, true);
|
||||||
|
mAllowAngle = ai.metaData.getBoolean(METADATA_ANGLE_ALLOW_ANGLE, true);
|
||||||
} else {
|
} else {
|
||||||
mPerfModeOptedIn = false;
|
mPerfModeOptedIn = false;
|
||||||
mBatteryModeOptedIn = false;
|
mBatteryModeOptedIn = false;
|
||||||
mAllowDownscale = true;
|
mAllowDownscale = true;
|
||||||
|
mAllowAngle = true;
|
||||||
}
|
}
|
||||||
} catch (PackageManager.NameNotFoundException e) {
|
} catch (PackageManager.NameNotFoundException e) {
|
||||||
// Not all packages are installed, hence ignore those that are not installed yet.
|
// Not all packages are installed, hence ignore those that are not installed yet.
|
||||||
@@ -340,14 +350,26 @@ public final class GameManagerService extends IGameManagerService.Stub {
|
|||||||
public static final String MODE_KEY = "mode";
|
public static final String MODE_KEY = "mode";
|
||||||
public static final String SCALING_KEY = "downscaleFactor";
|
public static final String SCALING_KEY = "downscaleFactor";
|
||||||
public static final String DEFAULT_SCALING = "1.0";
|
public static final String DEFAULT_SCALING = "1.0";
|
||||||
|
public static final String ANGLE_KEY = "useAngle";
|
||||||
|
|
||||||
private final @GameMode int mGameMode;
|
private final @GameMode int mGameMode;
|
||||||
private final String mScaling;
|
private final String mScaling;
|
||||||
|
private final boolean mUseAngle;
|
||||||
|
|
||||||
GameModeConfiguration(KeyValueListParser parser) {
|
GameModeConfiguration(KeyValueListParser parser) {
|
||||||
mGameMode = parser.getInt(MODE_KEY, GameManager.GAME_MODE_UNSUPPORTED);
|
mGameMode = parser.getInt(MODE_KEY, GameManager.GAME_MODE_UNSUPPORTED);
|
||||||
mScaling = !mAllowDownscale || isGameModeOptedIn(mGameMode)
|
// isGameModeOptedIn() returns if an app will handle all of the changes necessary
|
||||||
|
// for a particular game mode. If so, the Android framework (i.e.
|
||||||
|
// GameManagerService) will not do anything for the app (like window scaling or
|
||||||
|
// using ANGLE).
|
||||||
|
mScaling = !mAllowDownscale || willGamePerformOptimizations(mGameMode)
|
||||||
? DEFAULT_SCALING : parser.getString(SCALING_KEY, DEFAULT_SCALING);
|
? DEFAULT_SCALING : parser.getString(SCALING_KEY, DEFAULT_SCALING);
|
||||||
|
// We only want to use ANGLE if:
|
||||||
|
// - We're allowed to use ANGLE (the app hasn't opted out via the manifest) AND
|
||||||
|
// - The app has not opted in to performing the work itself AND
|
||||||
|
// - The Phenotype config has enabled it.
|
||||||
|
mUseAngle = mAllowAngle && !willGamePerformOptimizations(mGameMode)
|
||||||
|
&& parser.getBoolean(ANGLE_KEY, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
public int getGameMode() {
|
public int getGameMode() {
|
||||||
@@ -358,6 +380,10 @@ public final class GameManagerService extends IGameManagerService.Stub {
|
|||||||
return mScaling;
|
return mScaling;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean getUseAngle() {
|
||||||
|
return mUseAngle;
|
||||||
|
}
|
||||||
|
|
||||||
public boolean isValid() {
|
public boolean isValid() {
|
||||||
return (mGameMode == GameManager.GAME_MODE_PERFORMANCE
|
return (mGameMode == GameManager.GAME_MODE_PERFORMANCE
|
||||||
|| mGameMode == GameManager.GAME_MODE_BATTERY)
|
|| mGameMode == GameManager.GAME_MODE_BATTERY)
|
||||||
@@ -368,7 +394,8 @@ public final class GameManagerService extends IGameManagerService.Stub {
|
|||||||
* @hide
|
* @hide
|
||||||
*/
|
*/
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return "[Game Mode:" + mGameMode + ",Scaling:" + mScaling + "]";
|
return "[Game Mode:" + mGameMode + ",Scaling:" + mScaling + ",Use Angle:"
|
||||||
|
+ mUseAngle + "]";
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -384,13 +411,14 @@ public final class GameManagerService extends IGameManagerService.Stub {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets whether a package has opted into a game mode via its manifest.
|
* Returns if the app will assume full responsibility for the experience provided by this
|
||||||
|
* mode. If True, the system will not perform any interventions for the app.
|
||||||
*
|
*
|
||||||
* @return True if the app package has specified in its metadata either:
|
* @return True if the app package has specified in its metadata either:
|
||||||
* "com.android.app.gamemode.performance.enabled" or
|
* "com.android.app.gamemode.performance.enabled" or
|
||||||
* "com.android.app.gamemode.battery.enabled" with a value of "true"
|
* "com.android.app.gamemode.battery.enabled" with a value of "true"
|
||||||
*/
|
*/
|
||||||
public boolean isGameModeOptedIn(@GameMode int gameMode) {
|
public boolean willGamePerformOptimizations(@GameMode int gameMode) {
|
||||||
return (mBatteryModeOptedIn && gameMode == GameManager.GAME_MODE_BATTERY)
|
return (mBatteryModeOptedIn && gameMode == GameManager.GAME_MODE_BATTERY)
|
||||||
|| (mPerfModeOptedIn && gameMode == GameManager.GAME_MODE_PERFORMANCE);
|
|| (mPerfModeOptedIn && gameMode == GameManager.GAME_MODE_PERFORMANCE);
|
||||||
}
|
}
|
||||||
@@ -631,7 +659,34 @@ public final class GameManagerService extends IGameManagerService.Stub {
|
|||||||
mHandler.sendMessageDelayed(msg, WRITE_SETTINGS_DELAY);
|
mHandler.sendMessageDelayed(msg, WRITE_SETTINGS_DELAY);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
updateCompatModeDownscale(packageName, gameMode);
|
updateInterventions(packageName, gameMode);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get if ANGLE is enabled for the package for the currently enabled game mode.
|
||||||
|
* Checks that the caller has {@link android.Manifest.permission#MANAGE_GAME_MODE}.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
@RequiresPermission(Manifest.permission.MANAGE_GAME_MODE)
|
||||||
|
public @GameMode boolean getAngleEnabled(String packageName, int userId)
|
||||||
|
throws SecurityException {
|
||||||
|
final int gameMode = getGameMode(packageName, userId);
|
||||||
|
if (gameMode == GameManager.GAME_MODE_UNSUPPORTED) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
synchronized (mDeviceConfigLock) {
|
||||||
|
final GamePackageConfiguration config = mConfigs.get(packageName);
|
||||||
|
if (config == null) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
GamePackageConfiguration.GameModeConfiguration gameModeConfiguration =
|
||||||
|
config.getGameModeConfiguration(gameMode);
|
||||||
|
if (gameModeConfiguration == null) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return gameModeConfiguration.getUseAngle();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -753,7 +808,7 @@ public final class GameManagerService extends IGameManagerService.Stub {
|
|||||||
if (DEBUG) {
|
if (DEBUG) {
|
||||||
Slog.v(TAG, dumpDeviceConfigs());
|
Slog.v(TAG, dumpDeviceConfigs());
|
||||||
}
|
}
|
||||||
if (packageConfig.isGameModeOptedIn(gameMode)) {
|
if (packageConfig.willGamePerformOptimizations(gameMode)) {
|
||||||
disableCompatScale(packageName);
|
disableCompatScale(packageName);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -782,6 +837,17 @@ public final class GameManagerService extends IGameManagerService.Stub {
|
|||||||
return (bitField & modeToBitmask(gameMode)) != 0;
|
return (bitField & modeToBitmask(gameMode)) != 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@RequiresPermission(Manifest.permission.WRITE_SECURE_SETTINGS)
|
||||||
|
private void updateUseAngle(String packageName, @GameMode int gameMode) {
|
||||||
|
// TODO (b/188475576): Nothing to do yet. Remove if it's still empty when we're ready to
|
||||||
|
// ship.
|
||||||
|
}
|
||||||
|
|
||||||
|
private void updateInterventions(String packageName, @GameMode int gameMode) {
|
||||||
|
updateCompatModeDownscale(packageName, gameMode);
|
||||||
|
updateUseAngle(packageName, gameMode);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @hide
|
* @hide
|
||||||
*/
|
*/
|
||||||
@@ -839,11 +905,11 @@ public final class GameManagerService extends IGameManagerService.Stub {
|
|||||||
if (newGameMode != gameMode) {
|
if (newGameMode != gameMode) {
|
||||||
setGameMode(packageName, newGameMode, userId);
|
setGameMode(packageName, newGameMode, userId);
|
||||||
}
|
}
|
||||||
updateCompatModeDownscale(packageName, gameMode);
|
updateInterventions(packageName, gameMode);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
Slog.e(TAG, "Failed to update compat modes for user: " + userId);
|
Slog.e(TAG, "Failed to update compat modes for user " + userId + ": " + e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -182,7 +182,14 @@ public class GameManagerServiceTests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void mockDeviceConfigPerformance() {
|
private void mockDeviceConfigPerformance() {
|
||||||
String configString = "mode=2,downscaleFactor=0.5";
|
String configString = "mode=2,downscaleFactor=0.5,useAngle=false";
|
||||||
|
when(DeviceConfig.getProperty(anyString(), anyString()))
|
||||||
|
.thenReturn(configString);
|
||||||
|
}
|
||||||
|
|
||||||
|
// ANGLE will be disabled for most apps, so treat enabling ANGLE as a special case.
|
||||||
|
private void mockDeviceConfigPerformanceEnableAngle() {
|
||||||
|
String configString = "mode=2,downscaleFactor=0.5,useAngle=true";
|
||||||
when(DeviceConfig.getProperty(anyString(), anyString()))
|
when(DeviceConfig.getProperty(anyString(), anyString()))
|
||||||
.thenReturn(configString);
|
.thenReturn(configString);
|
||||||
}
|
}
|
||||||
@@ -212,7 +219,8 @@ public class GameManagerServiceTests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void mockGameModeOptInAll() throws Exception {
|
private void mockGameModeOptInAll() throws Exception {
|
||||||
final ApplicationInfo applicationInfo = new ApplicationInfo();
|
final ApplicationInfo applicationInfo = mMockPackageManager.getApplicationInfoAsUser(
|
||||||
|
mPackageName, PackageManager.GET_META_DATA, USER_ID_1);
|
||||||
Bundle metaDataBundle = new Bundle();
|
Bundle metaDataBundle = new Bundle();
|
||||||
metaDataBundle.putBoolean(
|
metaDataBundle.putBoolean(
|
||||||
GameManagerService.GamePackageConfiguration.METADATA_PERFORMANCE_MODE_ENABLE, true);
|
GameManagerService.GamePackageConfiguration.METADATA_PERFORMANCE_MODE_ENABLE, true);
|
||||||
@@ -224,7 +232,8 @@ public class GameManagerServiceTests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void mockGameModeOptInPerformance() throws Exception {
|
private void mockGameModeOptInPerformance() throws Exception {
|
||||||
final ApplicationInfo applicationInfo = new ApplicationInfo();
|
final ApplicationInfo applicationInfo = mMockPackageManager.getApplicationInfoAsUser(
|
||||||
|
mPackageName, PackageManager.GET_META_DATA, USER_ID_1);
|
||||||
Bundle metaDataBundle = new Bundle();
|
Bundle metaDataBundle = new Bundle();
|
||||||
metaDataBundle.putBoolean(
|
metaDataBundle.putBoolean(
|
||||||
GameManagerService.GamePackageConfiguration.METADATA_PERFORMANCE_MODE_ENABLE, true);
|
GameManagerService.GamePackageConfiguration.METADATA_PERFORMANCE_MODE_ENABLE, true);
|
||||||
@@ -234,7 +243,8 @@ public class GameManagerServiceTests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void mockGameModeOptInBattery() throws Exception {
|
private void mockGameModeOptInBattery() throws Exception {
|
||||||
final ApplicationInfo applicationInfo = new ApplicationInfo();
|
final ApplicationInfo applicationInfo = mMockPackageManager.getApplicationInfoAsUser(
|
||||||
|
mPackageName, PackageManager.GET_META_DATA, USER_ID_1);
|
||||||
Bundle metaDataBundle = new Bundle();
|
Bundle metaDataBundle = new Bundle();
|
||||||
metaDataBundle.putBoolean(
|
metaDataBundle.putBoolean(
|
||||||
GameManagerService.GamePackageConfiguration.METADATA_BATTERY_MODE_ENABLE, true);
|
GameManagerService.GamePackageConfiguration.METADATA_BATTERY_MODE_ENABLE, true);
|
||||||
@@ -244,7 +254,8 @@ public class GameManagerServiceTests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void mockInterventionAllowDownscaleTrue() throws Exception {
|
private void mockInterventionAllowDownscaleTrue() throws Exception {
|
||||||
final ApplicationInfo applicationInfo = new ApplicationInfo();
|
final ApplicationInfo applicationInfo = mMockPackageManager.getApplicationInfoAsUser(
|
||||||
|
mPackageName, PackageManager.GET_META_DATA, USER_ID_1);
|
||||||
Bundle metaDataBundle = new Bundle();
|
Bundle metaDataBundle = new Bundle();
|
||||||
metaDataBundle.putBoolean(
|
metaDataBundle.putBoolean(
|
||||||
GameManagerService.GamePackageConfiguration.METADATA_WM_ALLOW_DOWNSCALE, true);
|
GameManagerService.GamePackageConfiguration.METADATA_WM_ALLOW_DOWNSCALE, true);
|
||||||
@@ -254,7 +265,8 @@ public class GameManagerServiceTests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void mockInterventionAllowDownscaleFalse() throws Exception {
|
private void mockInterventionAllowDownscaleFalse() throws Exception {
|
||||||
final ApplicationInfo applicationInfo = new ApplicationInfo();
|
final ApplicationInfo applicationInfo = mMockPackageManager.getApplicationInfoAsUser(
|
||||||
|
mPackageName, PackageManager.GET_META_DATA, USER_ID_1);
|
||||||
Bundle metaDataBundle = new Bundle();
|
Bundle metaDataBundle = new Bundle();
|
||||||
metaDataBundle.putBoolean(
|
metaDataBundle.putBoolean(
|
||||||
GameManagerService.GamePackageConfiguration.METADATA_WM_ALLOW_DOWNSCALE, false);
|
GameManagerService.GamePackageConfiguration.METADATA_WM_ALLOW_DOWNSCALE, false);
|
||||||
@@ -263,6 +275,27 @@ public class GameManagerServiceTests {
|
|||||||
.thenReturn(applicationInfo);
|
.thenReturn(applicationInfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void mockInterventionAllowAngleTrue() throws Exception {
|
||||||
|
final ApplicationInfo applicationInfo = mMockPackageManager.getApplicationInfoAsUser(
|
||||||
|
mPackageName, PackageManager.GET_META_DATA, USER_ID_1);
|
||||||
|
Bundle metaDataBundle = new Bundle();
|
||||||
|
metaDataBundle.putBoolean(
|
||||||
|
GameManagerService.GamePackageConfiguration.METADATA_ANGLE_ALLOW_ANGLE, true);
|
||||||
|
when(mMockPackageManager.getApplicationInfoAsUser(anyString(), anyInt(), anyInt()))
|
||||||
|
.thenReturn(applicationInfo);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void mockInterventionAllowAngleFalse() throws Exception {
|
||||||
|
final ApplicationInfo applicationInfo = mMockPackageManager.getApplicationInfoAsUser(
|
||||||
|
mPackageName, PackageManager.GET_META_DATA, USER_ID_1);
|
||||||
|
Bundle metaDataBundle = new Bundle();
|
||||||
|
metaDataBundle.putBoolean(
|
||||||
|
GameManagerService.GamePackageConfiguration.METADATA_ANGLE_ALLOW_ANGLE, false);
|
||||||
|
applicationInfo.metaData = metaDataBundle;
|
||||||
|
when(mMockPackageManager.getApplicationInfoAsUser(anyString(), anyInt(), anyInt()))
|
||||||
|
.thenReturn(applicationInfo);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* By default game mode is not supported.
|
* By default game mode is not supported.
|
||||||
*/
|
*/
|
||||||
@@ -427,6 +460,19 @@ public class GameManagerServiceTests {
|
|||||||
assertEquals(config.getGameModeConfiguration(gameMode).getScaling(), scaling);
|
assertEquals(config.getGameModeConfiguration(gameMode).getScaling(), scaling);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void checkAngleEnabled(GameManagerService gameManagerService, int gameMode,
|
||||||
|
boolean angleEnabled) {
|
||||||
|
gameManagerService.updateConfigsForUser(USER_ID_1, mPackageName);
|
||||||
|
|
||||||
|
// Validate GamePackageConfiguration returns the correct value.
|
||||||
|
GameManagerService.GamePackageConfiguration config =
|
||||||
|
gameManagerService.getConfig(mPackageName);
|
||||||
|
assertEquals(config.getGameModeConfiguration(gameMode).getUseAngle(), angleEnabled);
|
||||||
|
|
||||||
|
// Validate GameManagerService.getAngleEnabled() returns the correct value.
|
||||||
|
assertEquals(gameManagerService.getAngleEnabled(mPackageName, USER_ID_1), angleEnabled);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Phenotype device config exists, but is only propagating the default value.
|
* Phenotype device config exists, but is only propagating the default value.
|
||||||
*/
|
*/
|
||||||
@@ -591,6 +637,50 @@ public class GameManagerServiceTests {
|
|||||||
checkDownscaling(GameManager.GAME_MODE_PERFORMANCE, "0.5");
|
checkDownscaling(GameManager.GAME_MODE_PERFORMANCE, "0.5");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* PERFORMANCE game mode is configured through Phenotype. The app hasn't specified any metadata.
|
||||||
|
*/
|
||||||
|
@Test
|
||||||
|
public void testInterventionAllowAngleDefault() throws Exception {
|
||||||
|
GameManagerService gameManagerService = new GameManagerService(mMockContext);
|
||||||
|
gameManagerService.onUserStarting(USER_ID_1);
|
||||||
|
mockDeviceConfigPerformance();
|
||||||
|
mockModifyGameModeGranted();
|
||||||
|
checkAngleEnabled(gameManagerService, GameManager.GAME_MODE_PERFORMANCE, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* PERFORMANCE game mode is configured through Phenotype. The app has opted-out of ANGLE.
|
||||||
|
*/
|
||||||
|
@Test
|
||||||
|
public void testInterventionAllowAngleFalse() throws Exception {
|
||||||
|
GameManagerService gameManagerService = new GameManagerService(mMockContext);
|
||||||
|
gameManagerService.onUserStarting(USER_ID_1);
|
||||||
|
mockDeviceConfigPerformanceEnableAngle();
|
||||||
|
mockInterventionAllowAngleFalse();
|
||||||
|
mockModifyGameModeGranted();
|
||||||
|
checkAngleEnabled(gameManagerService, GameManager.GAME_MODE_PERFORMANCE, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* PERFORMANCE game mode is configured through Phenotype. The app has redundantly specified
|
||||||
|
* the ANGLE metadata default value of "true".
|
||||||
|
*/
|
||||||
|
@Test
|
||||||
|
public void testInterventionAllowAngleTrue() throws Exception {
|
||||||
|
mockDeviceConfigPerformanceEnableAngle();
|
||||||
|
mockInterventionAllowAngleTrue();
|
||||||
|
|
||||||
|
GameManagerService gameManagerService = new GameManagerService(mMockContext);
|
||||||
|
gameManagerService.onUserStarting(USER_ID_1);
|
||||||
|
mockModifyGameModeGranted();
|
||||||
|
gameManagerService.setGameMode(mPackageName, GameManager.GAME_MODE_PERFORMANCE, USER_ID_1);
|
||||||
|
assertEquals(GameManager.GAME_MODE_PERFORMANCE,
|
||||||
|
gameManagerService.getGameMode(mPackageName, USER_ID_1));
|
||||||
|
|
||||||
|
checkAngleEnabled(gameManagerService, GameManager.GAME_MODE_PERFORMANCE, true);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* PERFORMANCE game mode is configured through Phenotype, but the app has also opted into the
|
* PERFORMANCE game mode is configured through Phenotype, but the app has also opted into the
|
||||||
* same mode. No interventions for this game mode should be available in this case.
|
* same mode. No interventions for this game mode should be available in this case.
|
||||||
|
|||||||
Reference in New Issue
Block a user