1 /* 2 * Copyright (C) 2018 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 17 package android.provider; 18 19 import static android.Manifest.permission.WRITE_ALLOWLISTED_DEVICE_CONFIG; 20 import static android.Manifest.permission.READ_DEVICE_CONFIG; 21 import static android.Manifest.permission.WRITE_DEVICE_CONFIG; 22 import static android.Manifest.permission.READ_WRITE_SYNC_DISABLED_MODE_CONFIG; 23 24 import android.Manifest; 25 import android.annotation.CallbackExecutor; 26 import android.annotation.IntDef; 27 import android.annotation.NonNull; 28 import android.annotation.Nullable; 29 import android.annotation.RequiresPermission; 30 import android.annotation.SuppressLint; 31 import android.annotation.SystemApi; 32 import android.content.ContentResolver; 33 import android.database.ContentObserver; 34 import android.net.Uri; 35 import android.util.ArrayMap; 36 import android.util.Log; 37 import android.util.Pair; 38 39 import com.android.internal.annotations.GuardedBy; 40 41 import java.lang.annotation.ElementType; 42 import java.lang.annotation.Retention; 43 import java.lang.annotation.RetentionPolicy; 44 import java.lang.annotation.Target; 45 46 import java.util.Arrays; 47 import java.util.Collections; 48 import java.util.HashMap; 49 import java.util.List; 50 import java.util.Map; 51 import java.util.Objects; 52 import java.util.Set; 53 import java.util.concurrent.Executor; 54 55 /** 56 * Device level configuration parameters which can be tuned by a separate configuration service. 57 * Namespaces that end in "_native" such as {@link #NAMESPACE_NETD_NATIVE} are intended to be used 58 * by native code and should be pushed to system properties to make them accessible. 59 * 60 * @hide 61 */ 62 @SystemApi 63 public final class DeviceConfig { 64 /** 65 * Namespace for all accessibility related features. 66 * 67 * @hide 68 */ 69 @SystemApi 70 public static final String NAMESPACE_ACCESSIBILITY = "accessibility"; 71 72 /** 73 * Namespace for activity manager related features. These features will be applied 74 * immediately upon change. 75 * 76 * @hide 77 */ 78 @SystemApi 79 public static final String NAMESPACE_ACTIVITY_MANAGER = "activity_manager"; 80 81 /** 82 * Namespace for activity manager, specific to the "component alias" feature. We needed a 83 * different namespace in order to avoid phonetype from resetting it. 84 * @hide 85 */ 86 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 87 public static final String NAMESPACE_ACTIVITY_MANAGER_COMPONENT_ALIAS = "activity_manager_ca"; 88 89 /** 90 * Namespace for features related to auto pin confirmation. 91 * 92 * @hide 93 */ 94 @SystemApi 95 public static final String NAMESPACE_AUTO_PIN_CONFIRMATION = "auto_pin_confirmation"; 96 97 /** 98 * Namespace for all activity manager related features that are used at the native level. 99 * These features are applied at reboot. 100 * 101 * @hide 102 */ 103 @SystemApi 104 public static final String NAMESPACE_ACTIVITY_MANAGER_NATIVE_BOOT = 105 "activity_manager_native_boot"; 106 107 /** 108 * Namespace for AlarmManager configurations. 109 * 110 * @hide 111 */ 112 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 113 public static final String NAMESPACE_ALARM_MANAGER = "alarm_manager"; 114 115 /** 116 * Namespace for all app compat related features. These features will be applied 117 * immediately upon change. 118 * 119 * @hide 120 */ 121 @SystemApi 122 public static final String NAMESPACE_APP_COMPAT = "app_compat"; 123 124 /** 125 * Namespace for all app hibernation related features. 126 * @hide 127 */ 128 @SystemApi 129 public static final String NAMESPACE_APP_HIBERNATION = "app_hibernation"; 130 131 /** 132 * Namespace for all AppSearch related features. 133 * @hide 134 */ 135 @SystemApi 136 public static final String NAMESPACE_APPSEARCH = "appsearch"; 137 138 /** 139 * Namespace for app standby configurations. 140 * 141 * @hide 142 */ 143 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 144 public static final String NAMESPACE_APP_STANDBY = "app_standby"; 145 146 /** 147 * Namespace for all App Cloning related features. 148 * @hide 149 */ 150 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 151 public static final String NAMESPACE_APP_CLONING = "app_cloning"; 152 153 /** 154 * Namespace for AttentionManagerService related features. 155 * 156 * @hide 157 */ 158 @SystemApi 159 public static final String NAMESPACE_ATTENTION_MANAGER_SERVICE = "attention_manager_service"; 160 161 /** 162 * Namespace for autofill feature that provides suggestions across all apps when 163 * the user interacts with input fields. 164 * 165 * @hide 166 */ 167 @SystemApi 168 public static final String NAMESPACE_AUTOFILL = "autofill"; 169 170 /** 171 * Namespace for battery saver feature. 172 * 173 * @hide 174 */ 175 @SystemApi 176 public static final String NAMESPACE_BATTERY_SAVER = "battery_saver"; 177 178 /** 179 * Namespace for holding battery stats configuration. 180 * 181 * @hide 182 */ 183 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 184 public static final String NAMESPACE_BATTERY_STATS = "battery_stats"; 185 186 /** 187 * Namespace for blobstore feature that allows apps to share data blobs. 188 * 189 * @hide 190 */ 191 @SystemApi 192 public static final String NAMESPACE_BLOBSTORE = "blobstore"; 193 194 /** 195 * Namespace for all Bluetooth related features. 196 * 197 * @hide 198 */ 199 @SystemApi 200 public static final String NAMESPACE_BLUETOOTH = "bluetooth"; 201 202 /** 203 * Namespace for all camera-related features that are used at the native level. 204 * 205 * @hide 206 */ 207 @SystemApi 208 public static final String NAMESPACE_CAMERA_NATIVE = "camera_native"; 209 210 /** 211 * Namespace for cellular security related features. 212 * 213 * @hide 214 */ 215 @SystemApi 216 public static final String NAMESPACE_CELLULAR_SECURITY = "cellular_security"; 217 218 /** 219 * Namespace for features relating to clipboard. 220 * 221 * @hide 222 */ 223 @SystemApi 224 public static final String NAMESPACE_CLIPBOARD = "clipboard"; 225 226 /** 227 * Namespace for all networking connectivity related features. 228 * 229 * @hide 230 */ 231 @SystemApi 232 public static final String NAMESPACE_CONNECTIVITY = "connectivity"; 233 234 /** 235 * Namespace for CaptivePortalLogin module. 236 * 237 * @hide 238 */ 239 @SystemApi 240 public static final String NAMESPACE_CAPTIVEPORTALLOGIN = "captive_portal_login"; 241 242 /** 243 * Namespace for all EdgeTpu related features. 244 * 245 * @hide 246 */ 247 @SystemApi 248 public static final String NAMESPACE_EDGETPU_NATIVE = "edgetpu_native"; 249 250 /** 251 * Namespace for all HealthFitness related features. 252 * 253 * @hide 254 */ 255 @SystemApi 256 public static final String NAMESPACE_HEALTH_FITNESS = "health_fitness"; 257 258 /** 259 * Namespace for Tethering module. 260 * 261 * @hide 262 */ 263 @SystemApi 264 public static final String NAMESPACE_TETHERING = "tethering"; 265 266 267 /** 268 * Namespace for Nearby module. 269 * 270 * @hide 271 */ 272 @SystemApi 273 public static final String NAMESPACE_NEARBY = "nearby"; 274 275 /** 276 * Namespace for content capture feature used by on-device machine intelligence 277 * to provide suggestions in a privacy-safe manner. 278 * 279 * @hide 280 */ 281 @SystemApi 282 public static final String NAMESPACE_CONTENT_CAPTURE = "content_capture"; 283 284 /** 285 * Namespace for credential manager. 286 * 287 * @hide 288 */ 289 @SystemApi 290 public static final String NAMESPACE_CREDENTIAL = "credential_manager"; 291 292 /** 293 * Namespace for device idle configurations. 294 * 295 * @hide 296 */ 297 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 298 public static final String NAMESPACE_DEVICE_IDLE = "device_idle"; 299 300 /** 301 * Namespace for how dex runs. The feature requires a reboot to reach a clean state. 302 * 303 * @deprecated No longer used 304 * @hide 305 */ 306 @Deprecated 307 @SystemApi 308 public static final String NAMESPACE_DEX_BOOT = "dex_boot"; 309 310 /** 311 * Namespace for display manager related features. The names to access the properties in this 312 * namespace should be defined in {@link android.hardware.display.DisplayManager}. 313 * 314 * @hide 315 */ 316 @SystemApi 317 public static final String NAMESPACE_DISPLAY_MANAGER = "display_manager"; 318 319 /** 320 * Namespace for all Game Driver features. 321 * 322 * @hide 323 */ 324 @SystemApi 325 public static final String NAMESPACE_GAME_DRIVER = "game_driver"; 326 327 /** 328 * Namespace for all HDMI Control features. 329 * 330 * @hide 331 */ 332 @SystemApi 333 public static final String NAMESPACE_HDMI_CONTROL = "hdmi_control"; 334 335 /** 336 * Namespace for all input-related features that are used at the native level. 337 * These features are applied at reboot. 338 * 339 * @hide 340 */ 341 @SystemApi 342 public static final String NAMESPACE_INPUT_NATIVE_BOOT = "input_native_boot"; 343 344 /** 345 * Namespace for attention-based features provided by on-device machine intelligence. 346 * 347 * @hide 348 */ 349 @SystemApi 350 public static final String NAMESPACE_INTELLIGENCE_ATTENTION = "intelligence_attention"; 351 352 /** 353 * Definitions for properties related to Content Suggestions. 354 * 355 * @hide 356 */ 357 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 358 public static final String NAMESPACE_INTELLIGENCE_CONTENT_SUGGESTIONS = 359 "intelligence_content_suggestions"; 360 361 /** 362 * Namespace for JobScheduler configurations. 363 * @hide 364 */ 365 @SystemApi 366 public static final String NAMESPACE_JOB_SCHEDULER = "jobscheduler"; 367 368 /** 369 * Namespace for all lmkd related features. 370 * 371 * @hide 372 */ 373 @SystemApi 374 public static final String NAMESPACE_LMKD_NATIVE = "lmkd_native"; 375 376 /** 377 * Namespace for all location related features. 378 * 379 * @hide 380 */ 381 @SystemApi 382 public static final String NAMESPACE_LOCATION = "location"; 383 384 /** 385 * Namespace for all media related features. 386 * 387 * @hide 388 */ 389 @SystemApi 390 public static final String NAMESPACE_MEDIA = "media"; 391 392 /** 393 * Namespace for all media native related features. 394 * 395 * @hide 396 */ 397 @SystemApi 398 public static final String NAMESPACE_MEDIA_NATIVE = "media_native"; 399 400 /** 401 * Namespace for all Kernel Multi-Gen LRU feature. 402 * 403 * @hide 404 */ 405 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 406 public static final String NAMESPACE_MGLRU_NATIVE = "mglru_native"; 407 408 /** 409 * Namespace for all netd related features. 410 * 411 * @hide 412 */ 413 @SystemApi 414 public static final String NAMESPACE_NETD_NATIVE = "netd_native"; 415 416 /** 417 * Namespace for all Android NNAPI related features. 418 * 419 * @hide 420 */ 421 @SystemApi 422 public static final String NAMESPACE_NNAPI_NATIVE = "nnapi_native"; 423 424 /** 425 * Namespace for all OnDevicePersonalization related feature. 426 * @hide 427 */ 428 @SystemApi 429 public static final String NAMESPACE_ON_DEVICE_PERSONALIZATION = "on_device_personalization"; 430 431 /** 432 * Namespace for features related to the Package Manager Service. 433 * 434 * @hide 435 */ 436 @SystemApi 437 public static final String NAMESPACE_PACKAGE_MANAGER_SERVICE = "package_manager_service"; 438 439 /** 440 * Namespace for features related to the Profcollect native Service. 441 * These features are applied at reboot. 442 * 443 * @hide 444 */ 445 @SystemApi 446 public static final String NAMESPACE_PROFCOLLECT_NATIVE_BOOT = "profcollect_native_boot"; 447 448 /** 449 * Namespace for features related to Reboot Readiness detection. 450 * 451 * @hide 452 */ 453 @SystemApi 454 public static final String NAMESPACE_REBOOT_READINESS = "reboot_readiness"; 455 456 /** 457 * Namespace for Remote Key Provisioning related features. 458 * 459 * @hide 460 */ 461 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 462 public static final String NAMESPACE_REMOTE_KEY_PROVISIONING_NATIVE = 463 "remote_key_provisioning_native"; 464 465 /** 466 * Namespace for Rollback flags that are applied immediately. 467 * 468 * @hide 469 */ 470 @SystemApi 471 public static final String NAMESPACE_ROLLBACK = "rollback"; 472 473 /** 474 * Namespace for Rollback flags that are applied after a reboot. 475 * 476 * @hide 477 */ 478 @SystemApi 479 public static final String NAMESPACE_ROLLBACK_BOOT = "rollback_boot"; 480 481 /** 482 * Namespace for Rotation Resolver Manager Service. 483 * 484 * @hide 485 */ 486 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 487 public static final String NAMESPACE_ROTATION_RESOLVER = "rotation_resolver"; 488 489 /** 490 * Namespace for all runtime related features that don't require a reboot to become active. 491 * There are no feature flags using NAMESPACE_RUNTIME. 492 * 493 * @hide 494 */ 495 @SystemApi 496 public static final String NAMESPACE_RUNTIME = "runtime"; 497 498 /** 499 * Namespace for all runtime related features that require system properties for accessing 500 * the feature flags from C++ or Java language code. One example is the app image startup 501 * cache feature use_app_image_startup_cache. 502 * 503 * @hide 504 */ 505 @SystemApi 506 public static final String NAMESPACE_RUNTIME_NATIVE = "runtime_native"; 507 508 /** 509 * Namespace for all runtime native boot related features. Boot in this case refers to the 510 * fact that the properties only take effect after rebooting the device. 511 * 512 * @hide 513 */ 514 @SystemApi 515 public static final String NAMESPACE_RUNTIME_NATIVE_BOOT = "runtime_native_boot"; 516 517 /** 518 * Namespace for system scheduler related features. These features will be applied 519 * immediately upon change. 520 * 521 * @hide 522 */ 523 @SystemApi 524 public static final String NAMESPACE_SCHEDULER = "scheduler"; 525 526 /** 527 * Namespace for all SdkSandbox related features. 528 * @hide 529 */ 530 @SystemApi 531 public static final String NAMESPACE_SDK_SANDBOX = "sdk_sandbox"; 532 533 /** 534 * Namespace for settings statistics features. 535 * 536 * @hide 537 */ 538 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 539 public static final String NAMESPACE_SETTINGS_STATS = "settings_stats"; 540 541 /** 542 * Namespace for all statsd java features that can be applied immediately. 543 * 544 * @hide 545 */ 546 @SystemApi 547 public static final String NAMESPACE_STATSD_JAVA = "statsd_java"; 548 549 /** 550 * Namespace for all statsd java features that are applied on boot. 551 * 552 * @hide 553 */ 554 @SystemApi 555 public static final String NAMESPACE_STATSD_JAVA_BOOT = "statsd_java_boot"; 556 557 /** 558 * Namespace for all statsd native features that can be applied immediately. 559 * 560 * @hide 561 */ 562 @SystemApi 563 public static final String NAMESPACE_STATSD_NATIVE = "statsd_native"; 564 565 /** 566 * Namespace for all statsd native features that are applied on boot. 567 * 568 * @hide 569 */ 570 @SystemApi 571 public static final String NAMESPACE_STATSD_NATIVE_BOOT = "statsd_native_boot"; 572 573 /** 574 * Namespace for storage-related features. 575 * 576 * @deprecated Replace storage namespace with storage_native_boot. 577 * @hide 578 */ 579 @Deprecated 580 @SystemApi 581 public static final String NAMESPACE_STORAGE = "storage"; 582 583 /** 584 * Namespace for storage-related features, including native and boot. 585 * 586 * @hide 587 */ 588 @SystemApi 589 public static final String NAMESPACE_STORAGE_NATIVE_BOOT = "storage_native_boot"; 590 591 /** 592 * Namespace for all AdServices related features. 593 * @hide 594 */ 595 @SystemApi 596 public static final String NAMESPACE_ADSERVICES = "adservices"; 597 598 /** 599 * Namespace for all SurfaceFlinger features that are used at the native level. 600 * These features are applied on boot or after reboot. 601 * 602 * @hide 603 */ 604 @SystemApi 605 public static final String NAMESPACE_SURFACE_FLINGER_NATIVE_BOOT = 606 "surface_flinger_native_boot"; 607 608 /** 609 * Namespace for swcodec native related features. 610 * 611 * @hide 612 */ 613 @SystemApi 614 public static final String NAMESPACE_SWCODEC_NATIVE = "swcodec_native"; 615 616 617 /** 618 * Namespace for System UI related features. 619 * 620 * @hide 621 */ 622 @SystemApi 623 public static final String NAMESPACE_SYSTEMUI = "systemui"; 624 625 /** 626 * Namespace for system time and time zone detection related features / behavior. 627 * 628 * @hide 629 */ 630 @SystemApi 631 public static final String NAMESPACE_SYSTEM_TIME = "system_time"; 632 633 /** 634 * Namespace for TARE configurations. 635 * 636 * @hide 637 */ 638 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 639 public static final String NAMESPACE_TARE = "tare"; 640 641 /** 642 * Telephony related properties. 643 * 644 * @hide 645 */ 646 @SystemApi 647 public static final String NAMESPACE_TELEPHONY = "telephony"; 648 649 /** 650 * Namespace for TextClassifier related features. 651 * 652 * @hide 653 * @see android.provider.Settings.Global.TEXT_CLASSIFIER_CONSTANTS 654 */ 655 @SystemApi 656 public static final String NAMESPACE_TEXTCLASSIFIER = "textclassifier"; 657 658 /** 659 * Namespace for contacts provider related features. 660 * 661 * @hide 662 */ 663 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 664 public static final String NAMESPACE_CONTACTS_PROVIDER = "contacts_provider"; 665 666 /** 667 * Namespace for settings ui related features 668 * 669 * @hide 670 */ 671 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 672 public static final String NAMESPACE_SETTINGS_UI = "settings_ui"; 673 674 /** 675 * Namespace for android related features, i.e. for flags that affect not just a single 676 * component, but the entire system. 677 * 678 * The keys for this namespace are defined in {@link AndroidDeviceConfig}. 679 * 680 * @hide 681 */ 682 @SystemApi 683 public static final String NAMESPACE_ANDROID = "android"; 684 685 /** 686 * Namespace for window manager related features. 687 * 688 * @hide 689 */ 690 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 691 public static final String NAMESPACE_WINDOW_MANAGER = "window_manager"; 692 693 /** 694 * Namespace for window manager features accessible by native code and 695 * loaded once per boot. 696 * 697 * @hide 698 */ 699 @SystemApi 700 public static final String NAMESPACE_WINDOW_MANAGER_NATIVE_BOOT = "window_manager_native_boot"; 701 702 /** 703 * Definitions for selection toolbar related functions. 704 * 705 * @hide 706 */ 707 @SystemApi 708 public static final String NAMESPACE_SELECTION_TOOLBAR = "selection_toolbar"; 709 710 /** 711 * Definitions for voice interaction related functions. 712 * 713 * @hide 714 */ 715 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 716 public static final String NAMESPACE_VOICE_INTERACTION = "voice_interaction"; 717 718 /** 719 * Namespace for DevicePolicyManager related features. 720 * 721 * @hide 722 */ 723 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 724 public static final String NAMESPACE_DEVICE_POLICY_MANAGER = 725 "device_policy_manager"; 726 727 /** 728 * List of namespaces which can be read without READ_DEVICE_CONFIG permission 729 * 730 * @hide 731 */ 732 @NonNull 733 private static final List<String> PUBLIC_NAMESPACES = 734 Arrays.asList(NAMESPACE_TEXTCLASSIFIER, NAMESPACE_RUNTIME, NAMESPACE_STATSD_JAVA, 735 NAMESPACE_STATSD_JAVA_BOOT, NAMESPACE_SELECTION_TOOLBAR, NAMESPACE_AUTOFILL, 736 NAMESPACE_DEVICE_POLICY_MANAGER, NAMESPACE_CONTENT_CAPTURE); 737 /** 738 * Privacy related properties definitions. 739 * 740 * @hide 741 */ 742 @SystemApi 743 public static final String NAMESPACE_PRIVACY = "privacy"; 744 745 /** 746 * Namespace for biometrics related features 747 * 748 * @hide 749 */ 750 @SystemApi 751 public static final String NAMESPACE_BIOMETRICS = "biometrics"; 752 753 /** 754 * Permission related properties definitions. 755 * 756 * @hide 757 */ 758 @SystemApi 759 public static final String NAMESPACE_PERMISSIONS = "permissions"; 760 761 /** 762 * Namespace for ota related features. 763 * 764 * @hide 765 */ 766 @SystemApi 767 public static final String NAMESPACE_OTA = "ota"; 768 769 /** 770 * Namespace for all widget related features. 771 * 772 * @hide 773 */ 774 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 775 public static final String NAMESPACE_WIDGET = "widget"; 776 777 /** 778 * Namespace for connectivity thermal power manager features. 779 * 780 * @hide 781 */ 782 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 783 public static final String NAMESPACE_CONNECTIVITY_THERMAL_POWER_MANAGER = 784 "connectivity_thermal_power_manager"; 785 786 /** 787 * Namespace for configuration related features. 788 * 789 * @hide 790 */ 791 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 792 public static final String NAMESPACE_CONFIGURATION = "configuration"; 793 794 /** 795 * LatencyTracker properties definitions. 796 * 797 * @hide 798 */ 799 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 800 public static final String NAMESPACE_LATENCY_TRACKER = "latency_tracker"; 801 802 /** 803 * InteractionJankMonitor properties definitions. 804 * 805 * @hide 806 */ 807 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 808 @SuppressLint("IntentName") 809 public static final String NAMESPACE_INTERACTION_JANK_MONITOR = "interaction_jank_monitor"; 810 811 /** 812 * Namespace for game overlay related features. 813 * 814 * @hide 815 */ 816 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 817 public static final String NAMESPACE_GAME_OVERLAY = "game_overlay"; 818 819 /** 820 * Namespace for Android Virtualization Framework related features accessible by native code. 821 * 822 * @hide 823 */ 824 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 825 public static final String NAMESPACE_VIRTUALIZATION_FRAMEWORK_NATIVE = 826 "virtualization_framework_native"; 827 828 /** 829 * Namespace for Constrain Display APIs related features. 830 * 831 * @hide 832 */ 833 @SystemApi 834 public static final String NAMESPACE_CONSTRAIN_DISPLAY_APIS = "constrain_display_apis"; 835 836 /** 837 * Namespace for App Compat Overrides related features. 838 * 839 * @hide 840 */ 841 @SystemApi 842 public static final String NAMESPACE_APP_COMPAT_OVERRIDES = "app_compat_overrides"; 843 844 /** 845 * Namespace for all ultra wideband (uwb) related features. 846 * 847 * @hide 848 */ 849 @SystemApi 850 public static final String NAMESPACE_UWB = "uwb"; 851 852 /** 853 * Namespace for AmbientContextEventManagerService related features. 854 * 855 * @hide 856 */ 857 @SystemApi 858 public static final String NAMESPACE_AMBIENT_CONTEXT_MANAGER_SERVICE = 859 "ambient_context_manager_service"; 860 861 /** 862 * Namespace for WearableSensingManagerService related features. 863 * 864 * @hide 865 */ 866 @SystemApi 867 public static final String NAMESPACE_WEARABLE_SENSING = 868 "wearable_sensing"; 869 870 /** 871 * Namespace for Vendor System Native related features. 872 * 873 * @hide 874 */ 875 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 876 public static final String NAMESPACE_VENDOR_SYSTEM_NATIVE = "vendor_system_native"; 877 878 /** 879 * Namespace for Vendor System Native Boot related features. 880 * 881 * @hide 882 */ 883 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 884 public static final String NAMESPACE_VENDOR_SYSTEM_NATIVE_BOOT = "vendor_system_native_boot"; 885 886 /** 887 * Namespace for memory safety related features (e.g. MTE) that need a reboot to be applied 888 * 889 * @hide 890 */ 891 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 892 public static final String NAMESPACE_MEMORY_SAFETY_NATIVE_BOOT = "memory_safety_native_boot"; 893 894 /** 895 * Namespace for memory safety related features (e.g. MTE) 896 * 897 * @hide 898 */ 899 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 900 public static final String NAMESPACE_MEMORY_SAFETY_NATIVE = "memory_safety_native"; 901 902 /** 903 * Namespace for wear OS platform features. 904 * 905 * @hide 906 */ 907 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 908 public static final String NAMESPACE_WEAR = "wear"; 909 910 /** 911 * Namespace for the input method manager platform features. 912 * 913 * @hide 914 */ 915 @SystemApi 916 public static final String NAMESPACE_INPUT_METHOD_MANAGER = "input_method_manager"; 917 918 /** 919 * Namespace for backup and restore service related features. 920 * 921 * @hide 922 */ 923 @SystemApi 924 public static final String NAMESPACE_BACKUP_AND_RESTORE = "backup_and_restore"; 925 926 /** 927 * Namespace for ARC App Compat related features. 928 * 929 * @hide 930 */ 931 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) 932 public static final String NAMESPACE_ARC_APP_COMPAT = "arc_app_compat"; 933 934 /** 935 * Namespace for remote authentication features. 936 * 937 * @hide 938 */ 939 @SystemApi 940 public static final String NAMESPACE_REMOTE_AUTH = "remote_auth"; 941 942 /** 943 * The modes that can be used when disabling syncs to the 'config' settings. 944 * @hide 945 */ 946 @IntDef(prefix = "SYNC_DISABLED_MODE_", 947 value = { SYNC_DISABLED_MODE_NONE, SYNC_DISABLED_MODE_PERSISTENT, 948 SYNC_DISABLED_MODE_UNTIL_REBOOT }) 949 @Retention(RetentionPolicy.SOURCE) 950 @Target({ElementType.TYPE_PARAMETER, ElementType.TYPE_USE}) 951 public @interface SyncDisabledMode {} 952 953 /** 954 * Sync is not disabled. 955 * 956 * @hide 957 */ 958 @SystemApi 959 public static final int SYNC_DISABLED_MODE_NONE = 0; 960 961 /** 962 * Disabling of Config bulk update / syncing is persistent, i.e. it survives a device 963 * reboot. 964 * 965 * @hide 966 */ 967 @SystemApi 968 public static final int SYNC_DISABLED_MODE_PERSISTENT = 1; 969 970 /** 971 * Disabling of Config bulk update / syncing is not persistent, i.e. it will 972 * not survive a device reboot. 973 * 974 * @hide 975 */ 976 @SystemApi 977 public static final int SYNC_DISABLED_MODE_UNTIL_REBOOT = 2; 978 979 private static final Object sLock = new Object(); 980 @GuardedBy("sLock") 981 private static ArrayMap<OnPropertiesChangedListener, Pair<String, Executor>> sListeners = 982 new ArrayMap<>(); 983 @GuardedBy("sLock") 984 private static Map<String, Pair<ContentObserver, Integer>> sNamespaces = new HashMap<>(); 985 private static final String TAG = "DeviceConfig"; 986 987 /** 988 * Interface for monitoring callback functions. 989 * 990 * @hide 991 */ 992 @SystemApi 993 public interface MonitorCallback { 994 /** 995 * Callback for updating a namespace. 996 * Reports that a config in the given namespace has changed. 997 * Isn't called for {@link DeviceConfig#getPublicNamespaces() public namespaces}. 998 * 999 * @param updatedNamespace the namespace, within which at least one config has changed. 1000 * @hide 1001 */ 1002 @SystemApi onNamespaceUpdate(@onNull String updatedNamespace)1003 void onNamespaceUpdate(@NonNull String updatedNamespace); 1004 1005 /** 1006 * Callback for accessing device config. 1007 * Reports an access to a the given namespace and the given calling package. 1008 * Isn't called for {@link DeviceConfig#getPublicNamespaces() public namespaces}. 1009 * 1010 * @param callingPackage the calling package id. 1011 * @param namespace the namespace, within which one of its config has been accessed. 1012 * @hide 1013 */ 1014 @SystemApi onDeviceConfigAccess(@onNull String callingPackage, @NonNull String namespace)1015 void onDeviceConfigAccess(@NonNull String callingPackage, @NonNull String namespace); 1016 } 1017 1018 // Should never be invoked DeviceConfig()1019 private DeviceConfig() { 1020 } 1021 1022 /** 1023 * Look up the value of a property for a particular namespace. 1024 * 1025 * @param namespace The namespace containing the property to look up. 1026 * @param name The name of the property to look up. 1027 * @return the corresponding value, or null if not present. 1028 * @hide 1029 */ 1030 @SystemApi 1031 @RequiresPermission(READ_DEVICE_CONFIG) 1032 @Nullable getProperty(@onNull String namespace, @NonNull String name)1033 public static String getProperty(@NonNull String namespace, @NonNull String name) { 1034 // Fetch all properties for the namespace at once and cache them in the local process, so we 1035 // incur the cost of the IPC less often. Lookups happen much more frequently than updates, 1036 // and we want to optimize the former. 1037 return getProperties(namespace, name).getString(name, null); 1038 } 1039 1040 /** 1041 * Look up the values of multiple properties for a particular namespace. The lookup is atomic, 1042 * such that the values of these properties cannot change between the time when the first is 1043 * fetched and the time when the last is fetched. 1044 * <p> 1045 * Each call to {@link #setProperties(Properties)} is also atomic and ensures that either none 1046 * or all of the change is picked up here, but never only part of it. 1047 * 1048 * @param namespace The namespace containing the properties to look up. 1049 * @param names The names of properties to look up, or empty to fetch all properties for the 1050 * given namespace. 1051 * @return {@link Properties} object containing the requested properties. This reflects the 1052 * state of these properties at the time of the lookup, and is not updated to reflect any 1053 * future changes. The keyset of this Properties object will contain only the intersection 1054 * of properties already set and properties requested via the names parameter. Properties 1055 * that are already set but were not requested will not be contained here. Properties that 1056 * are not set, but were requested will not be contained here either. 1057 * @hide 1058 */ 1059 @SystemApi 1060 @NonNull 1061 @RequiresPermission(READ_DEVICE_CONFIG) getProperties(@onNull String namespace, @NonNull String ... names)1062 public static Properties getProperties(@NonNull String namespace, @NonNull String ... names) { 1063 return new Properties(namespace, 1064 Settings.Config.getStrings(namespace, Arrays.asList(names))); 1065 } 1066 1067 /** 1068 * Look up the String value of a property for a particular namespace. 1069 * 1070 * @param namespace The namespace containing the property to look up. 1071 * @param name The name of the property to look up. 1072 * @param defaultValue The value to return if the property does not exist or has no non-null 1073 * value. 1074 * @return the corresponding value, or defaultValue if none exists. 1075 * @hide 1076 */ 1077 @SystemApi 1078 @RequiresPermission(READ_DEVICE_CONFIG) 1079 @Nullable getString(@onNull String namespace, @NonNull String name, @Nullable String defaultValue)1080 public static String getString(@NonNull String namespace, @NonNull String name, 1081 @Nullable String defaultValue) { 1082 String value = getProperty(namespace, name); 1083 return value != null ? value : defaultValue; 1084 } 1085 1086 /** 1087 * Look up the boolean value of a property for a particular namespace. 1088 * 1089 * @param namespace The namespace containing the property to look up. 1090 * @param name The name of the property to look up. 1091 * @param defaultValue The value to return if the property does not exist or has no non-null 1092 * value. 1093 * @return the corresponding value, or defaultValue if none exists. 1094 * @hide 1095 */ 1096 @SystemApi 1097 @RequiresPermission(READ_DEVICE_CONFIG) getBoolean(@onNull String namespace, @NonNull String name, boolean defaultValue)1098 public static boolean getBoolean(@NonNull String namespace, @NonNull String name, 1099 boolean defaultValue) { 1100 String value = getProperty(namespace, name); 1101 return value != null ? Boolean.parseBoolean(value) : defaultValue; 1102 } 1103 1104 /** 1105 * Look up the int value of a property for a particular namespace. 1106 * 1107 * @param namespace The namespace containing the property to look up. 1108 * @param name The name of the property to look up. 1109 * @param defaultValue The value to return if the property does not exist, has no non-null 1110 * value, or fails to parse into an int. 1111 * @return the corresponding value, or defaultValue if either none exists or it does not parse. 1112 * @hide 1113 */ 1114 @SystemApi 1115 @RequiresPermission(READ_DEVICE_CONFIG) getInt(@onNull String namespace, @NonNull String name, int defaultValue)1116 public static int getInt(@NonNull String namespace, @NonNull String name, int defaultValue) { 1117 String value = getProperty(namespace, name); 1118 if (value == null) { 1119 return defaultValue; 1120 } 1121 try { 1122 return Integer.parseInt(value); 1123 } catch (NumberFormatException e) { 1124 Log.e(TAG, "Parsing integer failed for " + namespace + ":" + name); 1125 return defaultValue; 1126 } 1127 } 1128 1129 /** 1130 * Look up the long value of a property for a particular namespace. 1131 * 1132 * @param namespace The namespace containing the property to look up. 1133 * @param name The name of the property to look up. 1134 * @param defaultValue The value to return if the property does not exist, has no non-null 1135 * value, or fails to parse into a long. 1136 * @return the corresponding value, or defaultValue if either none exists or it does not parse. 1137 * @hide 1138 */ 1139 @SystemApi 1140 @RequiresPermission(READ_DEVICE_CONFIG) getLong(@onNull String namespace, @NonNull String name, long defaultValue)1141 public static long getLong(@NonNull String namespace, @NonNull String name, long defaultValue) { 1142 String value = getProperty(namespace, name); 1143 if (value == null) { 1144 return defaultValue; 1145 } 1146 try { 1147 return Long.parseLong(value); 1148 } catch (NumberFormatException e) { 1149 Log.e(TAG, "Parsing long failed for " + namespace + ":" + name); 1150 return defaultValue; 1151 } 1152 } 1153 1154 /** 1155 * Look up the float value of a property for a particular namespace. 1156 * 1157 * @param namespace The namespace containing the property to look up. 1158 * @param name The name of the property to look up. 1159 * @param defaultValue The value to return if the property does not exist, has no non-null 1160 * value, or fails to parse into a float. 1161 * @return the corresponding value, or defaultValue if either none exists or it does not parse. 1162 * @hide 1163 */ 1164 @SystemApi 1165 @RequiresPermission(READ_DEVICE_CONFIG) getFloat(@onNull String namespace, @NonNull String name, float defaultValue)1166 public static float getFloat(@NonNull String namespace, @NonNull String name, 1167 float defaultValue) { 1168 String value = getProperty(namespace, name); 1169 if (value == null) { 1170 return defaultValue; 1171 } 1172 try { 1173 return Float.parseFloat(value); 1174 } catch (NumberFormatException e) { 1175 Log.e(TAG, "Parsing float failed for " + namespace + ":" + name); 1176 return defaultValue; 1177 } 1178 } 1179 1180 /** 1181 * Create a new property with the provided name and value in the provided namespace, or 1182 * update the value of such a property if it already exists. The same name can exist in multiple 1183 * namespaces and might have different values in any or all namespaces. 1184 * <p> 1185 * The method takes an argument indicating whether to make the value the default for this 1186 * property. 1187 * <p> 1188 * All properties stored for a particular scope can be reverted to their default values 1189 * by passing the namespace to {@link #resetToDefaults(int, String)}. 1190 * 1191 * @param namespace The namespace containing the property to create or update. 1192 * @param name The name of the property to create or update. 1193 * @param value The value to store for the property. 1194 * @param makeDefault Whether to make the new value the default one. 1195 * @return {@code true} if the value was set, {@code false} if the storage implementation throws 1196 * errors. 1197 * @hide 1198 * @see #resetToDefaults(int, String). 1199 */ 1200 @SystemApi 1201 @RequiresPermission(anyOf = {WRITE_DEVICE_CONFIG, WRITE_ALLOWLISTED_DEVICE_CONFIG}) setProperty(@onNull String namespace, @NonNull String name, @Nullable String value, boolean makeDefault)1202 public static boolean setProperty(@NonNull String namespace, @NonNull String name, 1203 @Nullable String value, boolean makeDefault) { 1204 return Settings.Config.putString(namespace, name, value, makeDefault); 1205 } 1206 1207 /** 1208 * Set all of the properties for a specific namespace. Pre-existing properties will be updated 1209 * and new properties will be added if necessary. Any pre-existing properties for the specific 1210 * namespace which are not part of the provided {@link Properties} object will be deleted from 1211 * the namespace. These changes are all applied atomically, such that no calls to read or reset 1212 * these properties can happen in the middle of this update. 1213 * <p> 1214 * Each call to {@link #getProperties(String, String...)} is also atomic and ensures that either 1215 * none or all of this update is picked up, but never only part of it. 1216 * 1217 * @param properties the complete set of properties to set for a specific namespace. 1218 * @throws BadConfigException if the provided properties are banned by RescueParty. 1219 * @return {@code true} if the values were set, {@code false} otherwise. 1220 * @hide 1221 */ 1222 @SystemApi 1223 @RequiresPermission(anyOf = {WRITE_DEVICE_CONFIG, WRITE_ALLOWLISTED_DEVICE_CONFIG}) setProperties(@onNull Properties properties)1224 public static boolean setProperties(@NonNull Properties properties) throws BadConfigException { 1225 return Settings.Config.setStrings(properties.getNamespace(), 1226 properties.mMap); 1227 } 1228 1229 /** 1230 * Delete a property with the provided name and value in the provided namespace 1231 * 1232 * @param namespace The namespace containing the property to delete. 1233 * @param name The name of the property to delete. 1234 * @return {@code true} if the property was deleted or it did not exist in the first place. 1235 * Return {@code false} if the storage implementation throws errors. 1236 * @hide 1237 */ 1238 @SystemApi 1239 @RequiresPermission(anyOf = {WRITE_DEVICE_CONFIG, WRITE_ALLOWLISTED_DEVICE_CONFIG}) deleteProperty(@onNull String namespace, @NonNull String name)1240 public static boolean deleteProperty(@NonNull String namespace, @NonNull String name) { 1241 return Settings.Config.deleteString(namespace, name); 1242 } 1243 1244 /** 1245 * Reset properties to their default values by removing the underlying values. 1246 * <p> 1247 * The method accepts an optional namespace parameter. If provided, only properties set within 1248 * that namespace will be reset. Otherwise, all properties will be reset. 1249 * <p> 1250 * Note: This method should only be used by {@link com.android.server.RescueParty}. It was 1251 * designed to be used in the event of boot or crash loops caused by flag changes. It does not 1252 * revert flag values to defaults - instead it removes the property entirely which causes the 1253 * consumer of the flag to use hardcoded defaults upon retrieval. 1254 * <p> 1255 * To clear values for a namespace without removing the underlying properties, construct a 1256 * {@link Properties} object with the caller's namespace and either an empty flag map, or some 1257 * snapshot of flag values. Then use {@link #setProperties(Properties)} to remove all flags 1258 * under the namespace, or set them to the values in the snapshot. 1259 * <p> 1260 * To revert values for testing, one should mock DeviceConfig using 1261 * {@link com.android.server.testables.TestableDeviceConfig} where possible. Otherwise, fallback 1262 * to using {@link #setProperties(Properties)} as outlined above. 1263 * 1264 * @param resetMode The reset mode to use. 1265 * @param namespace Optionally, the specific namespace which resets will be limited to. 1266 * @hide 1267 * @see #setProperty(String, String, String, boolean) 1268 */ 1269 @SystemApi 1270 @RequiresPermission(anyOf = {WRITE_DEVICE_CONFIG, WRITE_ALLOWLISTED_DEVICE_CONFIG}) resetToDefaults(int resetMode, @Nullable String namespace)1271 public static void resetToDefaults(int resetMode, @Nullable String namespace) { 1272 Settings.Config.resetToDefaults(resetMode, namespace); 1273 } 1274 1275 /** 1276 * Disables or re-enables bulk modifications ({@link #setProperties(Properties)}) to device 1277 * config values. This is intended for use during tests to prevent a sync operation clearing 1278 * config values which could influence the outcome of the tests, i.e. by changing behavior. 1279 * 1280 * @param syncDisabledMode the mode to use, see {@link #SYNC_DISABLED_MODE_NONE}, 1281 * {@link #SYNC_DISABLED_MODE_PERSISTENT} and {@link #SYNC_DISABLED_MODE_UNTIL_REBOOT} 1282 * 1283 * @see #getSyncDisabledMode() 1284 * @hide 1285 */ 1286 @SystemApi 1287 @RequiresPermission(anyOf = {WRITE_DEVICE_CONFIG, READ_WRITE_SYNC_DISABLED_MODE_CONFIG}) setSyncDisabledMode(@yncDisabledMode int syncDisabledMode)1288 public static void setSyncDisabledMode(@SyncDisabledMode int syncDisabledMode) { 1289 Settings.Config.setSyncDisabledMode(syncDisabledMode); 1290 } 1291 1292 /** 1293 * Returns the current mode of sync disabling. 1294 * 1295 * @see #setSyncDisabledMode(int) 1296 * @hide 1297 */ 1298 @SystemApi 1299 @RequiresPermission(anyOf = {WRITE_DEVICE_CONFIG, READ_WRITE_SYNC_DISABLED_MODE_CONFIG}) getSyncDisabledMode()1300 public static int getSyncDisabledMode() { 1301 return Settings.Config.getSyncDisabledMode(); 1302 } 1303 1304 /** 1305 * Add a listener for property changes. 1306 * <p> 1307 * This listener will be called whenever properties in the specified namespace change. Callbacks 1308 * will be made on the specified executor. Future calls to this method with the same listener 1309 * will replace the old namespace and executor. Remove the listener entirely by calling 1310 * {@link #removeOnPropertiesChangedListener(OnPropertiesChangedListener)}. 1311 * 1312 * @param namespace The namespace containing properties to monitor. 1313 * @param executor The executor which will be used to run callbacks. 1314 * @param onPropertiesChangedListener The listener to add. 1315 * @hide 1316 * @see #removeOnPropertiesChangedListener(OnPropertiesChangedListener) 1317 */ 1318 @SystemApi addOnPropertiesChangedListener( @onNull String namespace, @NonNull @CallbackExecutor Executor executor, @NonNull OnPropertiesChangedListener onPropertiesChangedListener)1319 public static void addOnPropertiesChangedListener( 1320 @NonNull String namespace, 1321 @NonNull @CallbackExecutor Executor executor, 1322 @NonNull OnPropertiesChangedListener onPropertiesChangedListener) { 1323 synchronized (sLock) { 1324 Pair<String, Executor> oldNamespace = sListeners.get(onPropertiesChangedListener); 1325 if (oldNamespace == null) { 1326 // Brand new listener, add it to the list. 1327 sListeners.put(onPropertiesChangedListener, new Pair<>(namespace, executor)); 1328 incrementNamespace(namespace); 1329 } else if (namespace.equals(oldNamespace.first)) { 1330 // Listener is already registered for this namespace, update executor just in case. 1331 sListeners.put(onPropertiesChangedListener, new Pair<>(namespace, executor)); 1332 } else { 1333 // Update this listener from an old namespace to the new one. 1334 decrementNamespace(sListeners.get(onPropertiesChangedListener).first); 1335 sListeners.put(onPropertiesChangedListener, new Pair<>(namespace, executor)); 1336 incrementNamespace(namespace); 1337 } 1338 } 1339 } 1340 1341 /** 1342 * Remove a listener for property changes. The listener will receive no further notification of 1343 * property changes. 1344 * 1345 * @param onPropertiesChangedListener The listener to remove. 1346 * @hide 1347 * @see #addOnPropertiesChangedListener(String, Executor, OnPropertiesChangedListener) 1348 */ 1349 @SystemApi removeOnPropertiesChangedListener( @onNull OnPropertiesChangedListener onPropertiesChangedListener)1350 public static void removeOnPropertiesChangedListener( 1351 @NonNull OnPropertiesChangedListener onPropertiesChangedListener) { 1352 Objects.requireNonNull(onPropertiesChangedListener); 1353 synchronized (sLock) { 1354 if (sListeners.containsKey(onPropertiesChangedListener)) { 1355 decrementNamespace(sListeners.get(onPropertiesChangedListener).first); 1356 sListeners.remove(onPropertiesChangedListener); 1357 } 1358 } 1359 } 1360 1361 /** 1362 * Setter callback for monitoring Config table. 1363 * 1364 * @param executor the {@link Executor} on which to invoke the callback 1365 * @param callback callback to set 1366 * 1367 * @hide 1368 */ 1369 @SystemApi 1370 @RequiresPermission(Manifest.permission.MONITOR_DEVICE_CONFIG_ACCESS) setMonitorCallback( @onNull ContentResolver resolver, @NonNull @CallbackExecutor Executor executor, @NonNull MonitorCallback callback)1371 public static void setMonitorCallback( 1372 @NonNull ContentResolver resolver, 1373 @NonNull @CallbackExecutor Executor executor, 1374 @NonNull MonitorCallback callback) { 1375 Settings.Config.setMonitorCallback(resolver, executor, callback); 1376 } 1377 1378 /** 1379 * Clear callback for monitoring Config table. 1380 * this may only be used to clear callback function registered by 1381 * {@link DeviceConfig#setMonitorCallback} 1382 * @hide 1383 */ 1384 @SystemApi 1385 @RequiresPermission(Manifest.permission.MONITOR_DEVICE_CONFIG_ACCESS) clearMonitorCallback(@onNull ContentResolver resolver)1386 public static void clearMonitorCallback(@NonNull ContentResolver resolver) { 1387 Settings.Config.clearMonitorCallback(resolver); 1388 } 1389 1390 /** 1391 * Increment the count used to represent the number of listeners subscribed to the given 1392 * namespace. If this is the first (i.e. incrementing from 0 to 1) for the given namespace, a 1393 * ContentObserver is registered. 1394 * 1395 * @param namespace The namespace to increment the count for. 1396 */ 1397 @GuardedBy("sLock") incrementNamespace(@onNull String namespace)1398 private static void incrementNamespace(@NonNull String namespace) { 1399 Objects.requireNonNull(namespace); 1400 Pair<ContentObserver, Integer> namespaceCount = sNamespaces.get(namespace); 1401 if (namespaceCount != null) { 1402 sNamespaces.put(namespace, new Pair<>(namespaceCount.first, namespaceCount.second + 1)); 1403 } else { 1404 // This is a new namespace, register a ContentObserver for it. 1405 ContentObserver contentObserver = new ContentObserver(null) { 1406 @Override 1407 public void onChange(boolean selfChange, Uri uri) { 1408 if (uri != null) { 1409 handleChange(uri); 1410 } 1411 } 1412 }; 1413 Settings.Config 1414 .registerContentObserver(namespace, true, contentObserver); 1415 sNamespaces.put(namespace, new Pair<>(contentObserver, 1)); 1416 } 1417 } 1418 1419 /** 1420 * Decrement the count used to represent the number of listeners subscribed to the given 1421 * namespace. If this is the final decrement call (i.e. decrementing from 1 to 0) for the given 1422 * namespace, the ContentObserver that had been tracking it will be removed. 1423 * 1424 * @param namespace The namespace to decrement the count for. 1425 */ 1426 @GuardedBy("sLock") decrementNamespace(@onNull String namespace)1427 private static void decrementNamespace(@NonNull String namespace) { 1428 Objects.requireNonNull(namespace); 1429 Pair<ContentObserver, Integer> namespaceCount = sNamespaces.get(namespace); 1430 if (namespaceCount == null) { 1431 // This namespace is not registered and does not need to be decremented 1432 return; 1433 } else if (namespaceCount.second > 1) { 1434 sNamespaces.put(namespace, new Pair<>(namespaceCount.first, namespaceCount.second - 1)); 1435 } else { 1436 // Decrementing a namespace to zero means we no longer need its ContentObserver. 1437 Settings.Config.unregisterContentObserver(namespaceCount.first); 1438 sNamespaces.remove(namespace); 1439 } 1440 } 1441 handleChange(@onNull Uri uri)1442 private static void handleChange(@NonNull Uri uri) { 1443 Objects.requireNonNull(uri); 1444 List<String> pathSegments = uri.getPathSegments(); 1445 // pathSegments(0) is "config" 1446 final String namespace = pathSegments.get(1); 1447 Properties.Builder propBuilder = new Properties.Builder(namespace); 1448 try { 1449 Properties allProperties = getProperties(namespace); 1450 for (int i = 2; i < pathSegments.size(); ++i) { 1451 String key = pathSegments.get(i); 1452 propBuilder.setString(key, allProperties.getString(key, null)); 1453 } 1454 } catch (SecurityException e) { 1455 // Silently failing to not crash binder or listener threads. 1456 Log.e(TAG, "OnPropertyChangedListener update failed: permission violation."); 1457 return; 1458 } 1459 Properties properties = propBuilder.build(); 1460 1461 synchronized (sLock) { 1462 for (int i = 0; i < sListeners.size(); i++) { 1463 if (namespace.equals(sListeners.valueAt(i).first)) { 1464 final OnPropertiesChangedListener listener = sListeners.keyAt(i); 1465 sListeners.valueAt(i).second.execute(() -> { 1466 listener.onPropertiesChanged(properties); 1467 }); 1468 } 1469 } 1470 } 1471 } 1472 1473 /** 1474 * Returns list of namespaces that can be read without READ_DEVICE_CONFIG_PERMISSION; 1475 * @hide 1476 */ 1477 @SystemApi getPublicNamespaces()1478 public static @NonNull List<String> getPublicNamespaces() { 1479 return PUBLIC_NAMESPACES; 1480 } 1481 1482 /** 1483 * Returns list of flags that can be written with adb as non-root. 1484 * @hide 1485 */ 1486 @SystemApi getAdbWritableFlags()1487 public static @NonNull Set<String> getAdbWritableFlags() { 1488 return WritableFlags.ALLOWLIST; 1489 } 1490 1491 /** 1492 * Interface for monitoring changes to properties. Implementations will receive callbacks when 1493 * properties change, including a {@link Properties} object which contains a single namespace 1494 * and all of the properties which changed for that namespace. This includes properties which 1495 * were added, updated, or deleted. This is not necessarily a complete list of all properties 1496 * belonging to the namespace, as properties which don't change are omitted. 1497 * <p> 1498 * Override {@link #onPropertiesChanged(Properties)} to handle callbacks for changes. 1499 * 1500 * @hide 1501 */ 1502 @SystemApi 1503 public interface OnPropertiesChangedListener { 1504 /** 1505 * Called when one or more properties have changed, providing a Properties object with all 1506 * of the changed properties. This object will contain only properties which have changed, 1507 * not the complete set of all properties belonging to the namespace. 1508 * 1509 * @param properties Contains the complete collection of properties which have changed for a 1510 * single namespace. This includes only those which were added, updated, 1511 * or deleted. 1512 */ onPropertiesChanged(@onNull Properties properties)1513 void onPropertiesChanged(@NonNull Properties properties); 1514 } 1515 1516 /** 1517 * Thrown by {@link #setProperties(Properties)} when a configuration is rejected. This 1518 * happens if RescueParty has identified a bad configuration and reset the namespace. 1519 * 1520 * @hide 1521 */ 1522 @SystemApi 1523 public static class BadConfigException extends Exception {} 1524 1525 /** 1526 * A mapping of properties to values, as well as a single namespace which they all belong to. 1527 * 1528 * @hide 1529 */ 1530 @SystemApi 1531 public static class Properties { 1532 private final String mNamespace; 1533 private final HashMap<String, String> mMap; 1534 private Set<String> mKeyset; 1535 1536 /** 1537 * Create a mapping of properties to values and the namespace they belong to. 1538 * 1539 * @param namespace The namespace these properties belong to. 1540 * @param keyValueMap A map between property names and property values. 1541 * @hide 1542 */ 1543 @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) Properties(@onNull String namespace, @Nullable Map<String, String> keyValueMap)1544 public Properties(@NonNull String namespace, @Nullable Map<String, String> keyValueMap) { 1545 Objects.requireNonNull(namespace); 1546 mNamespace = namespace; 1547 mMap = new HashMap(); 1548 if (keyValueMap != null) { 1549 mMap.putAll(keyValueMap); 1550 } 1551 } 1552 1553 /** 1554 * @return the namespace all properties within this instance belong to. 1555 */ 1556 @NonNull getNamespace()1557 public String getNamespace() { 1558 return mNamespace; 1559 } 1560 1561 /** 1562 * @return the non-null set of property names. 1563 */ 1564 @NonNull getKeyset()1565 public Set<String> getKeyset() { 1566 if (mKeyset == null) { 1567 mKeyset = Collections.unmodifiableSet(mMap.keySet()); 1568 } 1569 return mKeyset; 1570 } 1571 1572 /** 1573 * Look up the String value of a property. 1574 * 1575 * @param name The name of the property to look up. 1576 * @param defaultValue The value to return if the property has not been defined. 1577 * @return the corresponding value, or defaultValue if none exists. 1578 */ 1579 @Nullable getString(@onNull String name, @Nullable String defaultValue)1580 public String getString(@NonNull String name, @Nullable String defaultValue) { 1581 Objects.requireNonNull(name); 1582 String value = mMap.get(name); 1583 return value != null ? value : defaultValue; 1584 } 1585 1586 /** 1587 * Look up the boolean value of a property. 1588 * 1589 * @param name The name of the property to look up. 1590 * @param defaultValue The value to return if the property has not been defined. 1591 * @return the corresponding value, or defaultValue if none exists. 1592 */ getBoolean(@onNull String name, boolean defaultValue)1593 public boolean getBoolean(@NonNull String name, boolean defaultValue) { 1594 Objects.requireNonNull(name); 1595 String value = mMap.get(name); 1596 return value != null ? Boolean.parseBoolean(value) : defaultValue; 1597 } 1598 1599 /** 1600 * Look up the int value of a property. 1601 * 1602 * @param name The name of the property to look up. 1603 * @param defaultValue The value to return if the property has not been defined or fails to 1604 * parse into an int. 1605 * @return the corresponding value, or defaultValue if no valid int is available. 1606 */ getInt(@onNull String name, int defaultValue)1607 public int getInt(@NonNull String name, int defaultValue) { 1608 Objects.requireNonNull(name); 1609 String value = mMap.get(name); 1610 if (value == null) { 1611 return defaultValue; 1612 } 1613 try { 1614 return Integer.parseInt(value); 1615 } catch (NumberFormatException e) { 1616 Log.e(TAG, "Parsing int failed for " + name); 1617 return defaultValue; 1618 } 1619 } 1620 1621 /** 1622 * Look up the long value of a property. 1623 * 1624 * @param name The name of the property to look up. 1625 * @param defaultValue The value to return if the property has not been defined. or fails to 1626 * parse into a long. 1627 * @return the corresponding value, or defaultValue if no valid long is available. 1628 */ getLong(@onNull String name, long defaultValue)1629 public long getLong(@NonNull String name, long defaultValue) { 1630 Objects.requireNonNull(name); 1631 String value = mMap.get(name); 1632 if (value == null) { 1633 return defaultValue; 1634 } 1635 try { 1636 return Long.parseLong(value); 1637 } catch (NumberFormatException e) { 1638 Log.e(TAG, "Parsing long failed for " + name); 1639 return defaultValue; 1640 } 1641 } 1642 1643 /** 1644 * Look up the int value of a property. 1645 * 1646 * @param name The name of the property to look up. 1647 * @param defaultValue The value to return if the property has not been defined. or fails to 1648 * parse into a float. 1649 * @return the corresponding value, or defaultValue if no valid float is available. 1650 */ getFloat(@onNull String name, float defaultValue)1651 public float getFloat(@NonNull String name, float defaultValue) { 1652 Objects.requireNonNull(name); 1653 String value = mMap.get(name); 1654 if (value == null) { 1655 return defaultValue; 1656 } 1657 try { 1658 return Float.parseFloat(value); 1659 } catch (NumberFormatException e) { 1660 Log.e(TAG, "Parsing float failed for " + name); 1661 return defaultValue; 1662 } 1663 } 1664 1665 /** 1666 * Builder class for the construction of {@link Properties} objects. 1667 */ 1668 public static final class Builder { 1669 @NonNull 1670 private final String mNamespace; 1671 @NonNull 1672 private final Map<String, String> mKeyValues = new HashMap<>(); 1673 1674 /** 1675 * Create a new Builders for the specified namespace. 1676 * @param namespace non null namespace. 1677 */ Builder(@onNull String namespace)1678 public Builder(@NonNull String namespace) { 1679 mNamespace = namespace; 1680 } 1681 1682 /** 1683 * Add a new property with the specified key and value. 1684 * @param name non null name of the property. 1685 * @param value nullable string value of the property. 1686 * @return this Builder object 1687 */ 1688 @NonNull setString(@onNull String name, @Nullable String value)1689 public Builder setString(@NonNull String name, @Nullable String value) { 1690 mKeyValues.put(name, value); 1691 return this; 1692 } 1693 1694 /** 1695 * Add a new property with the specified key and value. 1696 * @param name non null name of the property. 1697 * @param value nullable string value of the property. 1698 * @return this Builder object 1699 */ 1700 @NonNull setBoolean(@onNull String name, boolean value)1701 public Builder setBoolean(@NonNull String name, boolean value) { 1702 mKeyValues.put(name, Boolean.toString(value)); 1703 return this; 1704 } 1705 1706 /** 1707 * Add a new property with the specified key and value. 1708 * @param name non null name of the property. 1709 * @param value int value of the property. 1710 * @return this Builder object 1711 */ 1712 @NonNull setInt(@onNull String name, int value)1713 public Builder setInt(@NonNull String name, int value) { 1714 mKeyValues.put(name, Integer.toString(value)); 1715 return this; 1716 } 1717 1718 /** 1719 * Add a new property with the specified key and value. 1720 * @param name non null name of the property. 1721 * @param value long value of the property. 1722 * @return this Builder object 1723 */ 1724 @NonNull setLong(@onNull String name, long value)1725 public Builder setLong(@NonNull String name, long value) { 1726 mKeyValues.put(name, Long.toString(value)); 1727 return this; 1728 } 1729 1730 /** 1731 * Add a new property with the specified key and value. 1732 * @param name non null name of the property. 1733 * @param value float value of the property. 1734 * @return this Builder object 1735 */ 1736 @NonNull setFloat(@onNull String name, float value)1737 public Builder setFloat(@NonNull String name, float value) { 1738 mKeyValues.put(name, Float.toString(value)); 1739 return this; 1740 } 1741 1742 /** 1743 * Create a new {@link Properties} object. 1744 * @return non null Properties. 1745 */ 1746 @NonNull build()1747 public Properties build() { 1748 return new Properties(mNamespace, mKeyValues); 1749 } 1750 } 1751 } 1752 1753 } 1754