1/* 2 * Copyright (C) 2008 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package com.android.settings; 18 19import static android.Manifest.permission.READ_EXTERNAL_STORAGE; 20 21import android.app.ActionBar; 22import android.app.Activity; 23import android.app.ActivityManagerNative; 24import android.app.ActivityThread; 25import android.app.AlertDialog; 26import android.app.Dialog; 27import android.app.DialogFragment; 28import android.app.admin.DevicePolicyManager; 29import android.app.backup.IBackupManager; 30import android.content.ContentResolver; 31import android.content.Context; 32import android.content.DialogInterface; 33import android.content.DialogInterface.OnClickListener; 34import android.content.Intent; 35import android.content.pm.ApplicationInfo; 36import android.content.pm.PackageManager; 37import android.content.pm.ResolveInfo; 38import android.os.AsyncTask; 39import android.os.BatteryManager; 40import android.os.Build; 41import android.os.Bundle; 42import android.os.IBinder; 43import android.os.Parcel; 44import android.os.RemoteException; 45import android.os.ServiceManager; 46import android.os.StrictMode; 47import android.os.SystemProperties; 48import android.os.Trace; 49import android.preference.CheckBoxPreference; 50import android.preference.ListPreference; 51import android.preference.MultiCheckPreference; 52import android.preference.Preference; 53import android.preference.Preference.OnPreferenceChangeListener; 54import android.preference.PreferenceFragment; 55import android.preference.PreferenceGroup; 56import android.preference.PreferenceScreen; 57import android.provider.Settings; 58import android.text.TextUtils; 59import android.util.Log; 60import android.view.Gravity; 61import android.view.HardwareRenderer; 62import android.view.IWindowManager; 63import android.view.View; 64import android.widget.CompoundButton; 65import android.widget.Switch; 66 67import java.util.ArrayList; 68import java.util.HashSet; 69import java.util.List; 70 71/* 72 * Displays preferences for application developers. 73 */ 74public class DevelopmentSettings extends PreferenceFragment 75 implements DialogInterface.OnClickListener, DialogInterface.OnDismissListener, 76 OnPreferenceChangeListener, CompoundButton.OnCheckedChangeListener { 77 78 /** 79 * Preference file were development settings prefs are stored. 80 */ 81 public static final String PREF_FILE = "development"; 82 83 /** 84 * Whether to show the development settings to the user. Default is false. 85 */ 86 public static final String PREF_SHOW = "show"; 87 88 private static final String ENABLE_ADB = "enable_adb"; 89 private static final String KEEP_SCREEN_ON = "keep_screen_on"; 90 private static final String ALLOW_MOCK_LOCATION = "allow_mock_location"; 91 private static final String HDCP_CHECKING_KEY = "hdcp_checking"; 92 private static final String HDCP_CHECKING_PROPERTY = "persist.sys.hdcp_checking"; 93 private static final String ENFORCE_READ_EXTERNAL = "enforce_read_external"; 94 private static final String LOCAL_BACKUP_PASSWORD = "local_backup_password"; 95 private static final String HARDWARE_UI_PROPERTY = "persist.sys.ui.hw"; 96 private static final String MSAA_PROPERTY = "debug.egl.force_msaa"; 97 private static final String BUGREPORT = "bugreport"; 98 private static final String BUGREPORT_IN_POWER_KEY = "bugreport_in_power"; 99 private static final String OPENGL_TRACES_PROPERTY = "debug.egl.trace"; 100 101 private static final String DEBUG_APP_KEY = "debug_app"; 102 private static final String WAIT_FOR_DEBUGGER_KEY = "wait_for_debugger"; 103 private static final String VERIFY_APPS_OVER_USB_KEY = "verify_apps_over_usb"; 104 private static final String STRICT_MODE_KEY = "strict_mode"; 105 private static final String POINTER_LOCATION_KEY = "pointer_location"; 106 private static final String SHOW_TOUCHES_KEY = "show_touches"; 107 private static final String SHOW_SCREEN_UPDATES_KEY = "show_screen_updates"; 108 private static final String DISABLE_OVERLAYS_KEY = "disable_overlays"; 109 private static final String SHOW_CPU_USAGE_KEY = "show_cpu_usage"; 110 private static final String FORCE_HARDWARE_UI_KEY = "force_hw_ui"; 111 private static final String FORCE_MSAA_KEY = "force_msaa"; 112 private static final String TRACK_FRAME_TIME_KEY = "track_frame_time"; 113 private static final String SHOW_HW_SCREEN_UPDATES_KEY = "show_hw_screen_udpates"; 114 private static final String SHOW_HW_LAYERS_UPDATES_KEY = "show_hw_layers_udpates"; 115 private static final String SHOW_HW_OVERDRAW_KEY = "show_hw_overdraw"; 116 private static final String DEBUG_LAYOUT_KEY = "debug_layout"; 117 private static final String WINDOW_ANIMATION_SCALE_KEY = "window_animation_scale"; 118 private static final String TRANSITION_ANIMATION_SCALE_KEY = "transition_animation_scale"; 119 private static final String ANIMATOR_DURATION_SCALE_KEY = "animator_duration_scale"; 120 private static final String OVERLAY_DISPLAY_DEVICES_KEY = "overlay_display_devices"; 121 private static final String DEBUG_DEBUGGING_CATEGORY_KEY = "debug_debugging_category"; 122 private static final String OPENGL_TRACES_KEY = "enable_opengl_traces"; 123 124 private static final String ENABLE_TRACES_KEY = "enable_traces"; 125 126 private static final String IMMEDIATELY_DESTROY_ACTIVITIES_KEY 127 = "immediately_destroy_activities"; 128 private static final String APP_PROCESS_LIMIT_KEY = "app_process_limit"; 129 130 private static final String SHOW_ALL_ANRS_KEY = "show_all_anrs"; 131 132 private static final String TAG_CONFIRM_ENFORCE = "confirm_enforce"; 133 134 private static final String PACKAGE_MIME_TYPE = "application/vnd.android.package-archive"; 135 136 private static final int RESULT_DEBUG_APP = 1000; 137 138 private IWindowManager mWindowManager; 139 private IBackupManager mBackupManager; 140 private DevicePolicyManager mDpm; 141 142 private Switch mEnabledSwitch; 143 private boolean mLastEnabledState; 144 private boolean mHaveDebugSettings; 145 private boolean mDontPokeProperties; 146 147 private CheckBoxPreference mEnableAdb; 148 private Preference mBugreport; 149 private CheckBoxPreference mBugreportInPower; 150 private CheckBoxPreference mKeepScreenOn; 151 private CheckBoxPreference mEnforceReadExternal; 152 private CheckBoxPreference mAllowMockLocation; 153 private PreferenceScreen mPassword; 154 155 private String mDebugApp; 156 private Preference mDebugAppPref; 157 private CheckBoxPreference mWaitForDebugger; 158 private CheckBoxPreference mVerifyAppsOverUsb; 159 160 private CheckBoxPreference mStrictMode; 161 private CheckBoxPreference mPointerLocation; 162 private CheckBoxPreference mShowTouches; 163 private CheckBoxPreference mShowScreenUpdates; 164 private CheckBoxPreference mDisableOverlays; 165 private CheckBoxPreference mShowCpuUsage; 166 private CheckBoxPreference mForceHardwareUi; 167 private CheckBoxPreference mForceMsaa; 168 private CheckBoxPreference mTrackFrameTime; 169 private CheckBoxPreference mShowHwScreenUpdates; 170 private CheckBoxPreference mShowHwLayersUpdates; 171 private CheckBoxPreference mShowHwOverdraw; 172 private CheckBoxPreference mDebugLayout; 173 private ListPreference mWindowAnimationScale; 174 private ListPreference mTransitionAnimationScale; 175 private ListPreference mAnimatorDurationScale; 176 private ListPreference mOverlayDisplayDevices; 177 private ListPreference mOpenGLTraces; 178 private MultiCheckPreference mEnableTracesPref; 179 180 private CheckBoxPreference mImmediatelyDestroyActivities; 181 private ListPreference mAppProcessLimit; 182 183 private CheckBoxPreference mShowAllANRs; 184 185 private final ArrayList<Preference> mAllPrefs = new ArrayList<Preference>(); 186 private final ArrayList<CheckBoxPreference> mResetCbPrefs 187 = new ArrayList<CheckBoxPreference>(); 188 189 private final HashSet<Preference> mDisabledPrefs = new HashSet<Preference>(); 190 191 // To track whether a confirmation dialog was clicked. 192 private boolean mDialogClicked; 193 private Dialog mEnableDialog; 194 private Dialog mAdbDialog; 195 196 @Override 197 public void onCreate(Bundle icicle) { 198 super.onCreate(icicle); 199 200 mWindowManager = IWindowManager.Stub.asInterface(ServiceManager.getService("window")); 201 mBackupManager = IBackupManager.Stub.asInterface( 202 ServiceManager.getService(Context.BACKUP_SERVICE)); 203 mDpm = (DevicePolicyManager)getActivity().getSystemService(Context.DEVICE_POLICY_SERVICE); 204 205 addPreferencesFromResource(R.xml.development_prefs); 206 207 mEnableAdb = findAndInitCheckboxPref(ENABLE_ADB); 208 mBugreport = findPreference(BUGREPORT); 209 mBugreportInPower = findAndInitCheckboxPref(BUGREPORT_IN_POWER_KEY); 210 mKeepScreenOn = findAndInitCheckboxPref(KEEP_SCREEN_ON); 211 mEnforceReadExternal = findAndInitCheckboxPref(ENFORCE_READ_EXTERNAL); 212 mAllowMockLocation = findAndInitCheckboxPref(ALLOW_MOCK_LOCATION); 213 mPassword = (PreferenceScreen) findPreference(LOCAL_BACKUP_PASSWORD); 214 mAllPrefs.add(mPassword); 215 216 mDebugAppPref = findPreference(DEBUG_APP_KEY); 217 mAllPrefs.add(mDebugAppPref); 218 mWaitForDebugger = findAndInitCheckboxPref(WAIT_FOR_DEBUGGER_KEY); 219 mVerifyAppsOverUsb = findAndInitCheckboxPref(VERIFY_APPS_OVER_USB_KEY); 220 if (!showVerifierSetting()) { 221 PreferenceGroup debugDebuggingCategory = (PreferenceGroup) 222 findPreference(DEBUG_DEBUGGING_CATEGORY_KEY); 223 if (debugDebuggingCategory != null) { 224 debugDebuggingCategory.removePreference(mVerifyAppsOverUsb); 225 } else { 226 mVerifyAppsOverUsb.setEnabled(false); 227 } 228 } 229 mStrictMode = findAndInitCheckboxPref(STRICT_MODE_KEY); 230 mPointerLocation = findAndInitCheckboxPref(POINTER_LOCATION_KEY); 231 mShowTouches = findAndInitCheckboxPref(SHOW_TOUCHES_KEY); 232 mShowScreenUpdates = findAndInitCheckboxPref(SHOW_SCREEN_UPDATES_KEY); 233 mDisableOverlays = findAndInitCheckboxPref(DISABLE_OVERLAYS_KEY); 234 mShowCpuUsage = findAndInitCheckboxPref(SHOW_CPU_USAGE_KEY); 235 mForceHardwareUi = findAndInitCheckboxPref(FORCE_HARDWARE_UI_KEY); 236 mForceMsaa = findAndInitCheckboxPref(FORCE_MSAA_KEY); 237 mTrackFrameTime = findAndInitCheckboxPref(TRACK_FRAME_TIME_KEY); 238 mShowHwScreenUpdates = findAndInitCheckboxPref(SHOW_HW_SCREEN_UPDATES_KEY); 239 mShowHwLayersUpdates = findAndInitCheckboxPref(SHOW_HW_LAYERS_UPDATES_KEY); 240 mShowHwOverdraw = findAndInitCheckboxPref(SHOW_HW_OVERDRAW_KEY); 241 mDebugLayout = findAndInitCheckboxPref(DEBUG_LAYOUT_KEY); 242 mWindowAnimationScale = (ListPreference) findPreference(WINDOW_ANIMATION_SCALE_KEY); 243 mAllPrefs.add(mWindowAnimationScale); 244 mWindowAnimationScale.setOnPreferenceChangeListener(this); 245 mTransitionAnimationScale = (ListPreference) findPreference(TRANSITION_ANIMATION_SCALE_KEY); 246 mAllPrefs.add(mTransitionAnimationScale); 247 mTransitionAnimationScale.setOnPreferenceChangeListener(this); 248 mAnimatorDurationScale = (ListPreference) findPreference(ANIMATOR_DURATION_SCALE_KEY); 249 mAllPrefs.add(mAnimatorDurationScale); 250 mAnimatorDurationScale.setOnPreferenceChangeListener(this); 251 mOverlayDisplayDevices = (ListPreference) findPreference(OVERLAY_DISPLAY_DEVICES_KEY); 252 mAllPrefs.add(mOverlayDisplayDevices); 253 mOverlayDisplayDevices.setOnPreferenceChangeListener(this); 254 mOpenGLTraces = (ListPreference) findPreference(OPENGL_TRACES_KEY); 255 mAllPrefs.add(mOpenGLTraces); 256 mOpenGLTraces.setOnPreferenceChangeListener(this); 257 mEnableTracesPref = (MultiCheckPreference)findPreference(ENABLE_TRACES_KEY); 258 String[] traceValues = new String[Trace.TRACE_TAGS.length]; 259 for (int i=Trace.TRACE_FLAGS_START_BIT; i<traceValues.length; i++) { 260 traceValues[i] = Integer.toString(1<<i); 261 } 262 mEnableTracesPref.setEntries(Trace.TRACE_TAGS); 263 mEnableTracesPref.setEntryValues(traceValues); 264 mAllPrefs.add(mEnableTracesPref); 265 mEnableTracesPref.setOnPreferenceChangeListener(this); 266 267 mImmediatelyDestroyActivities = (CheckBoxPreference) findPreference( 268 IMMEDIATELY_DESTROY_ACTIVITIES_KEY); 269 mAllPrefs.add(mImmediatelyDestroyActivities); 270 mResetCbPrefs.add(mImmediatelyDestroyActivities); 271 mAppProcessLimit = (ListPreference) findPreference(APP_PROCESS_LIMIT_KEY); 272 mAllPrefs.add(mAppProcessLimit); 273 mAppProcessLimit.setOnPreferenceChangeListener(this); 274 275 mShowAllANRs = (CheckBoxPreference) findPreference( 276 SHOW_ALL_ANRS_KEY); 277 mAllPrefs.add(mShowAllANRs); 278 mResetCbPrefs.add(mShowAllANRs); 279 280 Preference hdcpChecking = findPreference(HDCP_CHECKING_KEY); 281 if (hdcpChecking != null) { 282 mAllPrefs.add(hdcpChecking); 283 } 284 removeHdcpOptionsForProduction(); 285 } 286 287 private CheckBoxPreference findAndInitCheckboxPref(String key) { 288 CheckBoxPreference pref = (CheckBoxPreference) findPreference(key); 289 if (pref == null) { 290 throw new IllegalArgumentException("Cannot find preference with key = " + key); 291 } 292 mAllPrefs.add(pref); 293 mResetCbPrefs.add(pref); 294 return pref; 295 } 296 297 @Override 298 public void onActivityCreated(Bundle savedInstanceState) { 299 super.onActivityCreated(savedInstanceState); 300 301 final Activity activity = getActivity(); 302 mEnabledSwitch = new Switch(activity); 303 304 final int padding = activity.getResources().getDimensionPixelSize( 305 R.dimen.action_bar_switch_padding); 306 mEnabledSwitch.setPadding(0, 0, padding, 0); 307 mEnabledSwitch.setOnCheckedChangeListener(this); 308 } 309 310 @Override 311 public void onStart() { 312 super.onStart(); 313 final Activity activity = getActivity(); 314 activity.getActionBar().setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM, 315 ActionBar.DISPLAY_SHOW_CUSTOM); 316 activity.getActionBar().setCustomView(mEnabledSwitch, new ActionBar.LayoutParams( 317 ActionBar.LayoutParams.WRAP_CONTENT, 318 ActionBar.LayoutParams.WRAP_CONTENT, 319 Gravity.CENTER_VERTICAL | Gravity.END)); 320 } 321 322 @Override 323 public void onStop() { 324 super.onStop(); 325 final Activity activity = getActivity(); 326 activity.getActionBar().setDisplayOptions(0, ActionBar.DISPLAY_SHOW_CUSTOM); 327 activity.getActionBar().setCustomView(null); 328 } 329 330 private void removeHdcpOptionsForProduction() { 331 if ("user".equals(Build.TYPE)) { 332 Preference hdcpChecking = findPreference(HDCP_CHECKING_KEY); 333 if (hdcpChecking != null) { 334 // Remove the preference 335 getPreferenceScreen().removePreference(hdcpChecking); 336 mAllPrefs.remove(hdcpChecking); 337 } 338 } 339 } 340 341 private void setPrefsEnabledState(boolean enabled) { 342 for (int i = 0; i < mAllPrefs.size(); i++) { 343 Preference pref = mAllPrefs.get(i); 344 pref.setEnabled(enabled && !mDisabledPrefs.contains(pref)); 345 } 346 updateAllOptions(); 347 } 348 349 @Override 350 public void onResume() { 351 super.onResume(); 352 353 if (mDpm.getMaximumTimeToLock(null) > 0) { 354 // A DeviceAdmin has specified a maximum time until the device 355 // will lock... in this case we can't allow the user to turn 356 // on "stay awake when plugged in" because that would defeat the 357 // restriction. 358 mDisabledPrefs.add(mKeepScreenOn); 359 } else { 360 mDisabledPrefs.remove(mKeepScreenOn); 361 } 362 363 final ContentResolver cr = getActivity().getContentResolver(); 364 mLastEnabledState = Settings.Global.getInt(cr, 365 Settings.Global.DEVELOPMENT_SETTINGS_ENABLED, 0) != 0; 366 mEnabledSwitch.setChecked(mLastEnabledState); 367 setPrefsEnabledState(mLastEnabledState); 368 369 if (mHaveDebugSettings && !mLastEnabledState) { 370 // Overall debugging is disabled, but there are some debug 371 // settings that are enabled. This is an invalid state. Switch 372 // to debug settings being enabled, so the user knows there is 373 // stuff enabled and can turn it all off if they want. 374 Settings.Global.putInt(getActivity().getContentResolver(), 375 Settings.Global.DEVELOPMENT_SETTINGS_ENABLED, 1); 376 mLastEnabledState = true; 377 mEnabledSwitch.setChecked(mLastEnabledState); 378 setPrefsEnabledState(mLastEnabledState); 379 } 380 } 381 382 void updateCheckBox(CheckBoxPreference checkBox, boolean value) { 383 checkBox.setChecked(value); 384 mHaveDebugSettings |= value; 385 } 386 387 private void updateAllOptions() { 388 final Context context = getActivity(); 389 final ContentResolver cr = context.getContentResolver(); 390 mHaveDebugSettings = false; 391 updateCheckBox(mEnableAdb, Settings.Global.getInt(cr, 392 Settings.Global.ADB_ENABLED, 0) != 0); 393 updateCheckBox(mBugreportInPower, Settings.Secure.getInt(cr, 394 Settings.Secure.BUGREPORT_IN_POWER_MENU, 0) != 0); 395 updateCheckBox(mKeepScreenOn, Settings.Global.getInt(cr, 396 Settings.Global.STAY_ON_WHILE_PLUGGED_IN, 0) != 0); 397 updateCheckBox(mEnforceReadExternal, isPermissionEnforced(READ_EXTERNAL_STORAGE)); 398 updateCheckBox(mAllowMockLocation, Settings.Secure.getInt(cr, 399 Settings.Secure.ALLOW_MOCK_LOCATION, 0) != 0); 400 updateHdcpValues(); 401 updatePasswordSummary(); 402 updateDebuggerOptions(); 403 updateStrictModeVisualOptions(); 404 updatePointerLocationOptions(); 405 updateShowTouchesOptions(); 406 updateFlingerOptions(); 407 updateCpuUsageOptions(); 408 updateHardwareUiOptions(); 409 updateMsaaOptions(); 410 updateTrackFrameTimeOptions(); 411 updateShowHwScreenUpdatesOptions(); 412 updateShowHwLayersUpdatesOptions(); 413 updateShowHwOverdrawOptions(); 414 updateDebugLayoutOptions(); 415 updateAnimationScaleOptions(); 416 updateOverlayDisplayDevicesOptions(); 417 updateOpenGLTracesOptions(); 418 updateEnableTracesOptions(); 419 updateImmediatelyDestroyActivitiesOptions(); 420 updateAppProcessLimitOptions(); 421 updateShowAllANRsOptions(); 422 updateVerifyAppsOverUsbOptions(); 423 updateBugreportOptions(); 424 } 425 426 private void resetDangerousOptions() { 427 mDontPokeProperties = true; 428 for (int i=0; i<mResetCbPrefs.size(); i++) { 429 CheckBoxPreference cb = mResetCbPrefs.get(i); 430 if (cb.isChecked()) { 431 cb.setChecked(false); 432 onPreferenceTreeClick(null, cb); 433 } 434 } 435 resetDebuggerOptions(); 436 writeAnimationScaleOption(0, mWindowAnimationScale, null); 437 writeAnimationScaleOption(1, mTransitionAnimationScale, null); 438 writeAnimationScaleOption(2, mAnimatorDurationScale, null); 439 writeOverlayDisplayDevicesOptions(null); 440 writeEnableTracesOptions(0); 441 writeAppProcessLimitOptions(null); 442 mHaveDebugSettings = false; 443 updateAllOptions(); 444 mDontPokeProperties = false; 445 pokeSystemProperties(); 446 } 447 448 private void updateHdcpValues() { 449 int index = 1; // Defaults to drm-only. Needs to match with R.array.hdcp_checking_values 450 ListPreference hdcpChecking = (ListPreference) findPreference(HDCP_CHECKING_KEY); 451 if (hdcpChecking != null) { 452 String currentValue = SystemProperties.get(HDCP_CHECKING_PROPERTY); 453 String[] values = getResources().getStringArray(R.array.hdcp_checking_values); 454 String[] summaries = getResources().getStringArray(R.array.hdcp_checking_summaries); 455 for (int i = 0; i < values.length; i++) { 456 if (currentValue.equals(values[i])) { 457 index = i; 458 break; 459 } 460 } 461 hdcpChecking.setValue(values[index]); 462 hdcpChecking.setSummary(summaries[index]); 463 hdcpChecking.setOnPreferenceChangeListener(this); 464 } 465 } 466 467 private void updatePasswordSummary() { 468 try { 469 if (mBackupManager.hasBackupPassword()) { 470 mPassword.setSummary(R.string.local_backup_password_summary_change); 471 } else { 472 mPassword.setSummary(R.string.local_backup_password_summary_none); 473 } 474 } catch (RemoteException e) { 475 // Not much we can do here 476 } 477 } 478 479 private void writeDebuggerOptions() { 480 try { 481 ActivityManagerNative.getDefault().setDebugApp( 482 mDebugApp, mWaitForDebugger.isChecked(), true); 483 } catch (RemoteException ex) { 484 } 485 } 486 487 private static void resetDebuggerOptions() { 488 try { 489 ActivityManagerNative.getDefault().setDebugApp( 490 null, false, true); 491 } catch (RemoteException ex) { 492 } 493 } 494 495 private void updateDebuggerOptions() { 496 mDebugApp = Settings.Global.getString( 497 getActivity().getContentResolver(), Settings.Global.DEBUG_APP); 498 updateCheckBox(mWaitForDebugger, Settings.Global.getInt( 499 getActivity().getContentResolver(), Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0); 500 if (mDebugApp != null && mDebugApp.length() > 0) { 501 String label; 502 try { 503 ApplicationInfo ai = getActivity().getPackageManager().getApplicationInfo(mDebugApp, 504 PackageManager.GET_DISABLED_COMPONENTS); 505 CharSequence lab = getActivity().getPackageManager().getApplicationLabel(ai); 506 label = lab != null ? lab.toString() : mDebugApp; 507 } catch (PackageManager.NameNotFoundException e) { 508 label = mDebugApp; 509 } 510 mDebugAppPref.setSummary(getResources().getString(R.string.debug_app_set, label)); 511 mWaitForDebugger.setEnabled(true); 512 mHaveDebugSettings = true; 513 } else { 514 mDebugAppPref.setSummary(getResources().getString(R.string.debug_app_not_set)); 515 mWaitForDebugger.setEnabled(false); 516 } 517 } 518 519 private void updateVerifyAppsOverUsbOptions() { 520 updateCheckBox(mVerifyAppsOverUsb, Settings.Global.getInt(getActivity().getContentResolver(), 521 Settings.Global.PACKAGE_VERIFIER_INCLUDE_ADB, 1) != 0); 522 mVerifyAppsOverUsb.setEnabled(enableVerifierSetting()); 523 } 524 525 private void writeVerifyAppsOverUsbOptions() { 526 Settings.Global.putInt(getActivity().getContentResolver(), 527 Settings.Global.PACKAGE_VERIFIER_INCLUDE_ADB, mVerifyAppsOverUsb.isChecked() ? 1 : 0); 528 } 529 530 private boolean enableVerifierSetting() { 531 final ContentResolver cr = getActivity().getContentResolver(); 532 if (Settings.Global.getInt(cr, Settings.Global.ADB_ENABLED, 0) == 0) { 533 return false; 534 } 535 if (Settings.Global.getInt(cr, Settings.Global.PACKAGE_VERIFIER_ENABLE, 1) == 0) { 536 return false; 537 } else { 538 final PackageManager pm = getActivity().getPackageManager(); 539 final Intent verification = new Intent(Intent.ACTION_PACKAGE_NEEDS_VERIFICATION); 540 verification.setType(PACKAGE_MIME_TYPE); 541 verification.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION); 542 final List<ResolveInfo> receivers = pm.queryBroadcastReceivers(verification, 0); 543 if (receivers.size() == 0) { 544 return false; 545 } 546 } 547 return true; 548 } 549 550 private boolean showVerifierSetting() { 551 return Settings.Global.getInt(getActivity().getContentResolver(), 552 Settings.Global.PACKAGE_VERIFIER_SETTING_VISIBLE, 1) > 0; 553 } 554 555 private void updateBugreportOptions() { 556 if ("user".equals(Build.TYPE)) { 557 final ContentResolver resolver = getActivity().getContentResolver(); 558 final boolean adbEnabled = Settings.Global.getInt( 559 resolver, Settings.Global.ADB_ENABLED, 0) != 0; 560 if (adbEnabled) { 561 mBugreport.setEnabled(true); 562 mBugreportInPower.setEnabled(true); 563 } else { 564 mBugreport.setEnabled(false); 565 mBugreportInPower.setEnabled(false); 566 mBugreportInPower.setChecked(false); 567 Settings.Secure.putInt(resolver, Settings.Secure.BUGREPORT_IN_POWER_MENU, 0); 568 } 569 } else { 570 mBugreportInPower.setEnabled(true); 571 } 572 } 573 574 // Returns the current state of the system property that controls 575 // strictmode flashes. One of: 576 // 0: not explicitly set one way or another 577 // 1: on 578 // 2: off 579 private static int currentStrictModeActiveIndex() { 580 if (TextUtils.isEmpty(SystemProperties.get(StrictMode.VISUAL_PROPERTY))) { 581 return 0; 582 } 583 boolean enabled = SystemProperties.getBoolean(StrictMode.VISUAL_PROPERTY, false); 584 return enabled ? 1 : 2; 585 } 586 587 private void writeStrictModeVisualOptions() { 588 try { 589 mWindowManager.setStrictModeVisualIndicatorPreference(mStrictMode.isChecked() 590 ? "1" : ""); 591 } catch (RemoteException e) { 592 } 593 } 594 595 private void updateStrictModeVisualOptions() { 596 updateCheckBox(mStrictMode, currentStrictModeActiveIndex() == 1); 597 } 598 599 private void writePointerLocationOptions() { 600 Settings.System.putInt(getActivity().getContentResolver(), 601 Settings.System.POINTER_LOCATION, mPointerLocation.isChecked() ? 1 : 0); 602 } 603 604 private void updatePointerLocationOptions() { 605 updateCheckBox(mPointerLocation, Settings.System.getInt(getActivity().getContentResolver(), 606 Settings.System.POINTER_LOCATION, 0) != 0); 607 } 608 609 private void writeShowTouchesOptions() { 610 Settings.System.putInt(getActivity().getContentResolver(), 611 Settings.System.SHOW_TOUCHES, mShowTouches.isChecked() ? 1 : 0); 612 } 613 614 private void updateShowTouchesOptions() { 615 updateCheckBox(mShowTouches, Settings.System.getInt(getActivity().getContentResolver(), 616 Settings.System.SHOW_TOUCHES, 0) != 0); 617 } 618 619 private void updateFlingerOptions() { 620 // magic communication with surface flinger. 621 try { 622 IBinder flinger = ServiceManager.getService("SurfaceFlinger"); 623 if (flinger != null) { 624 Parcel data = Parcel.obtain(); 625 Parcel reply = Parcel.obtain(); 626 data.writeInterfaceToken("android.ui.ISurfaceComposer"); 627 flinger.transact(1010, data, reply, 0); 628 @SuppressWarnings("unused") 629 int showCpu = reply.readInt(); 630 @SuppressWarnings("unused") 631 int enableGL = reply.readInt(); 632 int showUpdates = reply.readInt(); 633 updateCheckBox(mShowScreenUpdates, showUpdates != 0); 634 @SuppressWarnings("unused") 635 int showBackground = reply.readInt(); 636 int disableOverlays = reply.readInt(); 637 updateCheckBox(mDisableOverlays, disableOverlays != 0); 638 reply.recycle(); 639 data.recycle(); 640 } 641 } catch (RemoteException ex) { 642 } 643 } 644 645 private void writeShowUpdatesOption() { 646 try { 647 IBinder flinger = ServiceManager.getService("SurfaceFlinger"); 648 if (flinger != null) { 649 Parcel data = Parcel.obtain(); 650 data.writeInterfaceToken("android.ui.ISurfaceComposer"); 651 final int showUpdates = mShowScreenUpdates.isChecked() ? 1 : 0; 652 data.writeInt(showUpdates); 653 flinger.transact(1002, data, null, 0); 654 data.recycle(); 655 656 updateFlingerOptions(); 657 } 658 } catch (RemoteException ex) { 659 } 660 } 661 662 private void writeDisableOverlaysOption() { 663 try { 664 IBinder flinger = ServiceManager.getService("SurfaceFlinger"); 665 if (flinger != null) { 666 Parcel data = Parcel.obtain(); 667 data.writeInterfaceToken("android.ui.ISurfaceComposer"); 668 final int disableOverlays = mDisableOverlays.isChecked() ? 1 : 0; 669 data.writeInt(disableOverlays); 670 flinger.transact(1008, data, null, 0); 671 data.recycle(); 672 673 updateFlingerOptions(); 674 } 675 } catch (RemoteException ex) { 676 } 677 } 678 679 private void updateHardwareUiOptions() { 680 updateCheckBox(mForceHardwareUi, SystemProperties.getBoolean(HARDWARE_UI_PROPERTY, false)); 681 } 682 683 private void writeHardwareUiOptions() { 684 SystemProperties.set(HARDWARE_UI_PROPERTY, mForceHardwareUi.isChecked() ? "true" : "false"); 685 pokeSystemProperties(); 686 } 687 688 private void updateMsaaOptions() { 689 updateCheckBox(mForceMsaa, SystemProperties.getBoolean(MSAA_PROPERTY, false)); 690 } 691 692 private void writeMsaaOptions() { 693 SystemProperties.set(MSAA_PROPERTY, mForceMsaa.isChecked() ? "true" : "false"); 694 pokeSystemProperties(); 695 } 696 697 private void updateTrackFrameTimeOptions() { 698 updateCheckBox(mTrackFrameTime, 699 SystemProperties.getBoolean(HardwareRenderer.PROFILE_PROPERTY, false)); 700 } 701 702 private void writeTrackFrameTimeOptions() { 703 SystemProperties.set(HardwareRenderer.PROFILE_PROPERTY, 704 mTrackFrameTime.isChecked() ? "true" : "false"); 705 pokeSystemProperties(); 706 } 707 708 private void updateShowHwScreenUpdatesOptions() { 709 updateCheckBox(mShowHwScreenUpdates, 710 SystemProperties.getBoolean(HardwareRenderer.DEBUG_DIRTY_REGIONS_PROPERTY, false)); 711 } 712 713 private void writeShowHwScreenUpdatesOptions() { 714 SystemProperties.set(HardwareRenderer.DEBUG_DIRTY_REGIONS_PROPERTY, 715 mShowHwScreenUpdates.isChecked() ? "true" : null); 716 pokeSystemProperties(); 717 } 718 719 private void updateShowHwLayersUpdatesOptions() { 720 updateCheckBox(mShowHwLayersUpdates, SystemProperties.getBoolean( 721 HardwareRenderer.DEBUG_SHOW_LAYERS_UPDATES_PROPERTY, false)); 722 } 723 724 private void writeShowHwLayersUpdatesOptions() { 725 SystemProperties.set(HardwareRenderer.DEBUG_SHOW_LAYERS_UPDATES_PROPERTY, 726 mShowHwLayersUpdates.isChecked() ? "true" : null); 727 pokeSystemProperties(); 728 } 729 730 private void updateShowHwOverdrawOptions() { 731 updateCheckBox(mShowHwOverdraw, SystemProperties.getBoolean( 732 HardwareRenderer.DEBUG_SHOW_OVERDRAW_PROPERTY, false)); 733 } 734 735 private void writeShowHwOverdrawOptions() { 736 SystemProperties.set(HardwareRenderer.DEBUG_SHOW_OVERDRAW_PROPERTY, 737 mShowHwOverdraw.isChecked() ? "true" : null); 738 pokeSystemProperties(); 739 } 740 741 private void updateDebugLayoutOptions() { 742 updateCheckBox(mDebugLayout, 743 SystemProperties.getBoolean(View.DEBUG_LAYOUT_PROPERTY, false)); 744 } 745 746 private void writeDebugLayoutOptions() { 747 SystemProperties.set(View.DEBUG_LAYOUT_PROPERTY, 748 mDebugLayout.isChecked() ? "true" : "false"); 749 pokeSystemProperties(); 750 } 751 752 private void updateCpuUsageOptions() { 753 updateCheckBox(mShowCpuUsage, Settings.Global.getInt(getActivity().getContentResolver(), 754 Settings.Global.SHOW_PROCESSES, 0) != 0); 755 } 756 757 private void writeCpuUsageOptions() { 758 boolean value = mShowCpuUsage.isChecked(); 759 Settings.Global.putInt(getActivity().getContentResolver(), 760 Settings.Global.SHOW_PROCESSES, value ? 1 : 0); 761 Intent service = (new Intent()) 762 .setClassName("com.android.systemui", "com.android.systemui.LoadAverageService"); 763 if (value) { 764 getActivity().startService(service); 765 } else { 766 getActivity().stopService(service); 767 } 768 } 769 770 private void writeImmediatelyDestroyActivitiesOptions() { 771 try { 772 ActivityManagerNative.getDefault().setAlwaysFinish( 773 mImmediatelyDestroyActivities.isChecked()); 774 } catch (RemoteException ex) { 775 } 776 } 777 778 private void updateImmediatelyDestroyActivitiesOptions() { 779 updateCheckBox(mImmediatelyDestroyActivities, Settings.Global.getInt( 780 getActivity().getContentResolver(), Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0); 781 } 782 783 private void updateAnimationScaleValue(int which, ListPreference pref) { 784 try { 785 float scale = mWindowManager.getAnimationScale(which); 786 if (scale != 1) { 787 mHaveDebugSettings = true; 788 } 789 CharSequence[] values = pref.getEntryValues(); 790 for (int i=0; i<values.length; i++) { 791 float val = Float.parseFloat(values[i].toString()); 792 if (scale <= val) { 793 pref.setValueIndex(i); 794 pref.setSummary(pref.getEntries()[i]); 795 return; 796 } 797 } 798 pref.setValueIndex(values.length-1); 799 pref.setSummary(pref.getEntries()[0]); 800 } catch (RemoteException e) { 801 } 802 } 803 804 private void updateAnimationScaleOptions() { 805 updateAnimationScaleValue(0, mWindowAnimationScale); 806 updateAnimationScaleValue(1, mTransitionAnimationScale); 807 updateAnimationScaleValue(2, mAnimatorDurationScale); 808 } 809 810 private void writeAnimationScaleOption(int which, ListPreference pref, Object newValue) { 811 try { 812 float scale = newValue != null ? Float.parseFloat(newValue.toString()) : 1; 813 mWindowManager.setAnimationScale(which, scale); 814 updateAnimationScaleValue(which, pref); 815 } catch (RemoteException e) { 816 } 817 } 818 819 private void updateOverlayDisplayDevicesOptions() { 820 String value = Settings.Global.getString(getActivity().getContentResolver(), 821 Settings.Global.OVERLAY_DISPLAY_DEVICES); 822 if (value == null) { 823 value = ""; 824 } 825 826 CharSequence[] values = mOverlayDisplayDevices.getEntryValues(); 827 for (int i = 0; i < values.length; i++) { 828 if (value.contentEquals(values[i])) { 829 mOverlayDisplayDevices.setValueIndex(i); 830 mOverlayDisplayDevices.setSummary(mOverlayDisplayDevices.getEntries()[i]); 831 return; 832 } 833 } 834 mOverlayDisplayDevices.setValueIndex(0); 835 mOverlayDisplayDevices.setSummary(mOverlayDisplayDevices.getEntries()[0]); 836 } 837 838 private void writeOverlayDisplayDevicesOptions(Object newValue) { 839 Settings.Global.putString(getActivity().getContentResolver(), 840 Settings.Global.OVERLAY_DISPLAY_DEVICES, (String)newValue); 841 updateOverlayDisplayDevicesOptions(); 842 } 843 844 private void updateOpenGLTracesOptions() { 845 String value = SystemProperties.get(OPENGL_TRACES_PROPERTY); 846 if (value == null) { 847 value = ""; 848 } 849 850 CharSequence[] values = mOpenGLTraces.getEntryValues(); 851 for (int i = 0; i < values.length; i++) { 852 if (value.contentEquals(values[i])) { 853 mOpenGLTraces.setValueIndex(i); 854 mOpenGLTraces.setSummary(mOpenGLTraces.getEntries()[i]); 855 return; 856 } 857 } 858 mOpenGLTraces.setValueIndex(0); 859 mOpenGLTraces.setSummary(mOpenGLTraces.getEntries()[0]); 860 } 861 862 private void writeOpenGLTracesOptions(Object newValue) { 863 SystemProperties.set(OPENGL_TRACES_PROPERTY, newValue == null ? "" : newValue.toString()); 864 pokeSystemProperties(); 865 updateOpenGLTracesOptions(); 866 } 867 868 private void updateAppProcessLimitOptions() { 869 try { 870 int limit = ActivityManagerNative.getDefault().getProcessLimit(); 871 CharSequence[] values = mAppProcessLimit.getEntryValues(); 872 for (int i=0; i<values.length; i++) { 873 int val = Integer.parseInt(values[i].toString()); 874 if (val >= limit) { 875 if (i != 0) { 876 mHaveDebugSettings = true; 877 } 878 mAppProcessLimit.setValueIndex(i); 879 mAppProcessLimit.setSummary(mAppProcessLimit.getEntries()[i]); 880 return; 881 } 882 } 883 mAppProcessLimit.setValueIndex(0); 884 mAppProcessLimit.setSummary(mAppProcessLimit.getEntries()[0]); 885 } catch (RemoteException e) { 886 } 887 } 888 889 private void writeAppProcessLimitOptions(Object newValue) { 890 try { 891 int limit = newValue != null ? Integer.parseInt(newValue.toString()) : -1; 892 ActivityManagerNative.getDefault().setProcessLimit(limit); 893 updateAppProcessLimitOptions(); 894 } catch (RemoteException e) { 895 } 896 } 897 898 private void writeShowAllANRsOptions() { 899 Settings.Secure.putInt(getActivity().getContentResolver(), 900 Settings.Secure.ANR_SHOW_BACKGROUND, 901 mShowAllANRs.isChecked() ? 1 : 0); 902 } 903 904 private void updateShowAllANRsOptions() { 905 updateCheckBox(mShowAllANRs, Settings.Secure.getInt( 906 getActivity().getContentResolver(), Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0); 907 } 908 909 private void updateEnableTracesOptions() { 910 long flags = SystemProperties.getLong(Trace.PROPERTY_TRACE_TAG_ENABLEFLAGS, 0); 911 String[] values = mEnableTracesPref.getEntryValues(); 912 int numSet = 0; 913 for (int i=Trace.TRACE_FLAGS_START_BIT; i<values.length; i++) { 914 boolean set = (flags&(1<<i)) != 0; 915 mEnableTracesPref.setValue(i-Trace.TRACE_FLAGS_START_BIT, set); 916 if (set) { 917 numSet++; 918 } 919 } 920 if (numSet == 0) { 921 mEnableTracesPref.setSummary(R.string.enable_traces_summary_none); 922 } else if (numSet == values.length) { 923 mHaveDebugSettings = true; 924 mEnableTracesPref.setSummary(R.string.enable_traces_summary_all); 925 } else { 926 mHaveDebugSettings = true; 927 mEnableTracesPref.setSummary(getString(R.string.enable_traces_summary_num, numSet)); 928 } 929 } 930 931 private void writeEnableTracesOptions() { 932 long value = 0; 933 String[] values = mEnableTracesPref.getEntryValues(); 934 for (int i=Trace.TRACE_FLAGS_START_BIT; i<values.length; i++) { 935 if (mEnableTracesPref.getValue(i-Trace.TRACE_FLAGS_START_BIT)) { 936 value |= 1<<i; 937 } 938 } 939 writeEnableTracesOptions(value); 940 // Make sure summary is updated. 941 updateEnableTracesOptions(); 942 } 943 944 private void writeEnableTracesOptions(long value) { 945 SystemProperties.set(Trace.PROPERTY_TRACE_TAG_ENABLEFLAGS, 946 "0x" + Long.toString(value, 16)); 947 pokeSystemProperties(); 948 } 949 950 @Override 951 public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) { 952 if (buttonView == mEnabledSwitch) { 953 if (isChecked != mLastEnabledState) { 954 if (isChecked) { 955 mDialogClicked = false; 956 if (mEnableDialog != null) dismissDialogs(); 957 mEnableDialog = new AlertDialog.Builder(getActivity()).setMessage( 958 getActivity().getResources().getString( 959 R.string.dev_settings_warning_message)) 960 .setTitle(R.string.dev_settings_warning_title) 961 .setIconAttribute(android.R.attr.alertDialogIcon) 962 .setPositiveButton(android.R.string.yes, this) 963 .setNegativeButton(android.R.string.no, this) 964 .show(); 965 mEnableDialog.setOnDismissListener(this); 966 } else { 967 resetDangerousOptions(); 968 Settings.Global.putInt(getActivity().getContentResolver(), 969 Settings.Global.DEVELOPMENT_SETTINGS_ENABLED, 0); 970 mLastEnabledState = isChecked; 971 setPrefsEnabledState(mLastEnabledState); 972 } 973 } 974 } 975 } 976 977 @Override 978 public void onActivityResult(int requestCode, int resultCode, Intent data) { 979 if (requestCode == RESULT_DEBUG_APP) { 980 if (resultCode == Activity.RESULT_OK) { 981 mDebugApp = data.getAction(); 982 writeDebuggerOptions(); 983 updateDebuggerOptions(); 984 } 985 } else { 986 super.onActivityResult(requestCode, resultCode, data); 987 } 988 } 989 990 @Override 991 public boolean onPreferenceTreeClick(PreferenceScreen preferenceScreen, Preference preference) { 992 993 if (Utils.isMonkeyRunning()) { 994 return false; 995 } 996 997 if (preference == mEnableAdb) { 998 if (mEnableAdb.isChecked()) { 999 mDialogClicked = false; 1000 if (mAdbDialog != null) dismissDialogs(); 1001 mAdbDialog = new AlertDialog.Builder(getActivity()).setMessage( 1002 getActivity().getResources().getString(R.string.adb_warning_message)) 1003 .setTitle(R.string.adb_warning_title) 1004 .setIconAttribute(android.R.attr.alertDialogIcon) 1005 .setPositiveButton(android.R.string.yes, this) 1006 .setNegativeButton(android.R.string.no, this) 1007 .show(); 1008 mAdbDialog.setOnDismissListener(this); 1009 } else { 1010 Settings.Global.putInt(getActivity().getContentResolver(), 1011 Settings.Global.ADB_ENABLED, 0); 1012 mVerifyAppsOverUsb.setEnabled(false); 1013 mVerifyAppsOverUsb.setChecked(false); 1014 updateBugreportOptions(); 1015 } 1016 } else if (preference == mBugreportInPower) { 1017 Settings.Secure.putInt(getActivity().getContentResolver(), 1018 Settings.Secure.BUGREPORT_IN_POWER_MENU, 1019 mBugreportInPower.isChecked() ? 1 : 0); 1020 } else if (preference == mKeepScreenOn) { 1021 Settings.Global.putInt(getActivity().getContentResolver(), 1022 Settings.Global.STAY_ON_WHILE_PLUGGED_IN, 1023 mKeepScreenOn.isChecked() ? 1024 (BatteryManager.BATTERY_PLUGGED_AC | BatteryManager.BATTERY_PLUGGED_USB) : 0); 1025 } else if (preference == mEnforceReadExternal) { 1026 if (mEnforceReadExternal.isChecked()) { 1027 ConfirmEnforceFragment.show(this); 1028 } else { 1029 setPermissionEnforced(getActivity(), READ_EXTERNAL_STORAGE, false); 1030 } 1031 } else if (preference == mAllowMockLocation) { 1032 Settings.Secure.putInt(getActivity().getContentResolver(), 1033 Settings.Secure.ALLOW_MOCK_LOCATION, 1034 mAllowMockLocation.isChecked() ? 1 : 0); 1035 } else if (preference == mDebugAppPref) { 1036 startActivityForResult(new Intent(getActivity(), AppPicker.class), RESULT_DEBUG_APP); 1037 } else if (preference == mWaitForDebugger) { 1038 writeDebuggerOptions(); 1039 } else if (preference == mVerifyAppsOverUsb) { 1040 writeVerifyAppsOverUsbOptions(); 1041 } else if (preference == mStrictMode) { 1042 writeStrictModeVisualOptions(); 1043 } else if (preference == mPointerLocation) { 1044 writePointerLocationOptions(); 1045 } else if (preference == mShowTouches) { 1046 writeShowTouchesOptions(); 1047 } else if (preference == mShowScreenUpdates) { 1048 writeShowUpdatesOption(); 1049 } else if (preference == mDisableOverlays) { 1050 writeDisableOverlaysOption(); 1051 } else if (preference == mShowCpuUsage) { 1052 writeCpuUsageOptions(); 1053 } else if (preference == mImmediatelyDestroyActivities) { 1054 writeImmediatelyDestroyActivitiesOptions(); 1055 } else if (preference == mShowAllANRs) { 1056 writeShowAllANRsOptions(); 1057 } else if (preference == mForceHardwareUi) { 1058 writeHardwareUiOptions(); 1059 } else if (preference == mForceMsaa) { 1060 writeMsaaOptions(); 1061 } else if (preference == mTrackFrameTime) { 1062 writeTrackFrameTimeOptions(); 1063 } else if (preference == mShowHwScreenUpdates) { 1064 writeShowHwScreenUpdatesOptions(); 1065 } else if (preference == mShowHwLayersUpdates) { 1066 writeShowHwLayersUpdatesOptions(); 1067 } else if (preference == mShowHwOverdraw) { 1068 writeShowHwOverdrawOptions(); 1069 } else if (preference == mDebugLayout) { 1070 writeDebugLayoutOptions(); 1071 } 1072 1073 return false; 1074 } 1075 1076 @Override 1077 public boolean onPreferenceChange(Preference preference, Object newValue) { 1078 if (HDCP_CHECKING_KEY.equals(preference.getKey())) { 1079 SystemProperties.set(HDCP_CHECKING_PROPERTY, newValue.toString()); 1080 updateHdcpValues(); 1081 pokeSystemProperties(); 1082 return true; 1083 } else if (preference == mWindowAnimationScale) { 1084 writeAnimationScaleOption(0, mWindowAnimationScale, newValue); 1085 return true; 1086 } else if (preference == mTransitionAnimationScale) { 1087 writeAnimationScaleOption(1, mTransitionAnimationScale, newValue); 1088 return true; 1089 } else if (preference == mAnimatorDurationScale) { 1090 writeAnimationScaleOption(2, mAnimatorDurationScale, newValue); 1091 return true; 1092 } else if (preference == mOverlayDisplayDevices) { 1093 writeOverlayDisplayDevicesOptions(newValue); 1094 return true; 1095 } else if (preference == mOpenGLTraces) { 1096 writeOpenGLTracesOptions(newValue); 1097 return true; 1098 } else if (preference == mEnableTracesPref) { 1099 writeEnableTracesOptions(); 1100 return true; 1101 } else if (preference == mAppProcessLimit) { 1102 writeAppProcessLimitOptions(newValue); 1103 return true; 1104 } 1105 return false; 1106 } 1107 1108 private void dismissDialogs() { 1109 if (mAdbDialog != null) { 1110 mAdbDialog.dismiss(); 1111 mAdbDialog = null; 1112 } 1113 if (mEnableDialog != null) { 1114 mEnableDialog.dismiss(); 1115 mEnableDialog = null; 1116 } 1117 } 1118 1119 public void onClick(DialogInterface dialog, int which) { 1120 if (dialog == mAdbDialog) { 1121 if (which == DialogInterface.BUTTON_POSITIVE) { 1122 mDialogClicked = true; 1123 Settings.Global.putInt(getActivity().getContentResolver(), 1124 Settings.Global.ADB_ENABLED, 1); 1125 mVerifyAppsOverUsb.setEnabled(true); 1126 updateVerifyAppsOverUsbOptions(); 1127 updateBugreportOptions(); 1128 } else { 1129 // Reset the toggle 1130 mEnableAdb.setChecked(false); 1131 } 1132 } else if (dialog == mEnableDialog) { 1133 if (which == DialogInterface.BUTTON_POSITIVE) { 1134 mDialogClicked = true; 1135 Settings.Global.putInt(getActivity().getContentResolver(), 1136 Settings.Global.DEVELOPMENT_SETTINGS_ENABLED, 1); 1137 mLastEnabledState = true; 1138 setPrefsEnabledState(mLastEnabledState); 1139 } else { 1140 // Reset the toggle 1141 mEnabledSwitch.setChecked(false); 1142 } 1143 } 1144 } 1145 1146 public void onDismiss(DialogInterface dialog) { 1147 // Assuming that onClick gets called first 1148 if (dialog == mAdbDialog) { 1149 if (!mDialogClicked) { 1150 mEnableAdb.setChecked(false); 1151 } 1152 mAdbDialog = null; 1153 } else if (dialog == mEnableDialog) { 1154 if (!mDialogClicked) { 1155 mEnabledSwitch.setChecked(false); 1156 } 1157 mEnableDialog = null; 1158 } 1159 } 1160 1161 @Override 1162 public void onDestroy() { 1163 dismissDialogs(); 1164 super.onDestroy(); 1165 } 1166 1167 void pokeSystemProperties() { 1168 if (!mDontPokeProperties) { 1169 //noinspection unchecked 1170 (new SystemPropPoker()).execute(); 1171 } 1172 } 1173 1174 static class SystemPropPoker extends AsyncTask<Void, Void, Void> { 1175 @Override 1176 protected Void doInBackground(Void... params) { 1177 String[] services; 1178 try { 1179 services = ServiceManager.listServices(); 1180 } catch (RemoteException e) { 1181 return null; 1182 } 1183 for (String service : services) { 1184 IBinder obj = ServiceManager.checkService(service); 1185 if (obj != null) { 1186 Parcel data = Parcel.obtain(); 1187 try { 1188 obj.transact(IBinder.SYSPROPS_TRANSACTION, data, null, 0); 1189 } catch (RemoteException e) { 1190 } catch (Exception e) { 1191 Log.i("DevSettings", "Somone wrote a bad service '" + service 1192 + "' that doesn't like to be poked: " + e); 1193 } 1194 data.recycle(); 1195 } 1196 } 1197 return null; 1198 } 1199 } 1200 1201 /** 1202 * Dialog to confirm enforcement of {@link android.Manifest.permission#READ_EXTERNAL_STORAGE}. 1203 */ 1204 public static class ConfirmEnforceFragment extends DialogFragment { 1205 public static void show(DevelopmentSettings parent) { 1206 final ConfirmEnforceFragment dialog = new ConfirmEnforceFragment(); 1207 dialog.setTargetFragment(parent, 0); 1208 dialog.show(parent.getFragmentManager(), TAG_CONFIRM_ENFORCE); 1209 } 1210 1211 @Override 1212 public Dialog onCreateDialog(Bundle savedInstanceState) { 1213 final Context context = getActivity(); 1214 1215 final AlertDialog.Builder builder = new AlertDialog.Builder(context); 1216 builder.setTitle(R.string.enforce_read_external_confirm_title); 1217 builder.setMessage(R.string.enforce_read_external_confirm_message); 1218 1219 builder.setPositiveButton(android.R.string.ok, new OnClickListener() { 1220 @Override 1221 public void onClick(DialogInterface dialog, int which) { 1222 setPermissionEnforced(context, READ_EXTERNAL_STORAGE, true); 1223 ((DevelopmentSettings) getTargetFragment()).updateAllOptions(); 1224 } 1225 }); 1226 builder.setNegativeButton(android.R.string.cancel, new OnClickListener() { 1227 @Override 1228 public void onClick(DialogInterface dialog, int which) { 1229 ((DevelopmentSettings) getTargetFragment()).updateAllOptions(); 1230 } 1231 }); 1232 1233 return builder.create(); 1234 } 1235 } 1236 1237 private static boolean isPermissionEnforced(String permission) { 1238 try { 1239 return ActivityThread.getPackageManager().isPermissionEnforced(permission); 1240 } catch (RemoteException e) { 1241 throw new RuntimeException("Problem talking with PackageManager", e); 1242 } 1243 } 1244 1245 private static void setPermissionEnforced( 1246 Context context, String permission, boolean enforced) { 1247 try { 1248 // TODO: offload to background thread 1249 ActivityThread.getPackageManager() 1250 .setPermissionEnforced(READ_EXTERNAL_STORAGE, enforced); 1251 } catch (RemoteException e) { 1252 throw new RuntimeException("Problem talking with PackageManager", e); 1253 } 1254 } 1255} 1256